misc/liblua/lstring.c
author unc0rr
Sun, 02 Dec 2012 01:25:11 +0400
changeset 8178 8bd087478b48
parent 2812 0a24853de796
permissions -rw-r--r--
Fix QSettings problems: - Reopen file in ReadOnly mode if it was open in ReadWrite mode and is being read. This is needed for stupid QSettings which opens file in ReadWrite mode just to call readAll() on it. - Implement setSize(0)
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
2812
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
     1
/*
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
     2
** $Id: lstring.c,v 2.8.1.1 2007/12/27 13:02:25 roberto Exp $
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
     3
** String table (keeps all strings handled by Lua)
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
     4
** See Copyright Notice in lua.h
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
     5
*/
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
     6
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
     7
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
     8
#include <string.h>
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
     9
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    10
#define lstring_c
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    11
#define LUA_CORE
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    12
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    13
#include "lua.h"
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    14
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    15
#include "lmem.h"
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    16
#include "lobject.h"
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    17
#include "lstate.h"
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    18
#include "lstring.h"
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    19
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    20
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    21
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    22
void luaS_resize (lua_State *L, int newsize) {
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    23
  GCObject **newhash;
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    24
  stringtable *tb;
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    25
  int i;
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    26
  if (G(L)->gcstate == GCSsweepstring)
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    27
    return;  /* cannot resize during GC traverse */
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    28
  newhash = luaM_newvector(L, newsize, GCObject *);
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    29
  tb = &G(L)->strt;
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    30
  for (i=0; i<newsize; i++) newhash[i] = NULL;
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    31
  /* rehash */
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    32
  for (i=0; i<tb->size; i++) {
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    33
    GCObject *p = tb->hash[i];
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    34
    while (p) {  /* for each node in the list */
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    35
      GCObject *next = p->gch.next;  /* save next */
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    36
      unsigned int h = gco2ts(p)->hash;
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    37
      int h1 = lmod(h, newsize);  /* new position */
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    38
      lua_assert(cast_int(h%newsize) == lmod(h, newsize));
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    39
      p->gch.next = newhash[h1];  /* chain it */
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    40
      newhash[h1] = p;
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    41
      p = next;
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    42
    }
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    43
  }
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    44
  luaM_freearray(L, tb->hash, tb->size, TString *);
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    45
  tb->size = newsize;
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    46
  tb->hash = newhash;
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    47
}
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    48
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    49
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    50
static TString *newlstr (lua_State *L, const char *str, size_t l,
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    51
                                       unsigned int h) {
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    52
  TString *ts;
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    53
  stringtable *tb;
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    54
  if (l+1 > (MAX_SIZET - sizeof(TString))/sizeof(char))
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    55
    luaM_toobig(L);
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    56
  ts = cast(TString *, luaM_malloc(L, (l+1)*sizeof(char)+sizeof(TString)));
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    57
  ts->tsv.len = l;
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    58
  ts->tsv.hash = h;
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    59
  ts->tsv.marked = luaC_white(G(L));
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    60
  ts->tsv.tt = LUA_TSTRING;
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    61
  ts->tsv.reserved = 0;
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    62
  memcpy(ts+1, str, l*sizeof(char));
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    63
  ((char *)(ts+1))[l] = '\0';  /* ending 0 */
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    64
  tb = &G(L)->strt;
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    65
  h = lmod(h, tb->size);
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    66
  ts->tsv.next = tb->hash[h];  /* chain new entry */
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    67
  tb->hash[h] = obj2gco(ts);
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    68
  tb->nuse++;
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    69
  if (tb->nuse > cast(lu_int32, tb->size) && tb->size <= MAX_INT/2)
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    70
    luaS_resize(L, tb->size*2);  /* too crowded */
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    71
  return ts;
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    72
}
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    73
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    74
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    75
TString *luaS_newlstr (lua_State *L, const char *str, size_t l) {
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    76
  GCObject *o;
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    77
  unsigned int h = cast(unsigned int, l);  /* seed */
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    78
  size_t step = (l>>5)+1;  /* if string is too long, don't hash all its chars */
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    79
  size_t l1;
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    80
  for (l1=l; l1>=step; l1-=step)  /* compute hash */
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    81
    h = h ^ ((h<<5)+(h>>2)+cast(unsigned char, str[l1-1]));
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    82
  for (o = G(L)->strt.hash[lmod(h, G(L)->strt.size)];
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    83
       o != NULL;
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    84
       o = o->gch.next) {
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    85
    TString *ts = rawgco2ts(o);
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    86
    if (ts->tsv.len == l && (memcmp(str, getstr(ts), l) == 0)) {
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    87
      /* string may be dead */
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    88
      if (isdead(G(L), o)) changewhite(o);
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    89
      return ts;
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    90
    }
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    91
  }
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    92
  return newlstr(L, str, l, h);  /* not found */
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    93
}
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    94
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    95
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    96
Udata *luaS_newudata (lua_State *L, size_t s, Table *e) {
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    97
  Udata *u;
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    98
  if (s > MAX_SIZET - sizeof(Udata))
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
    99
    luaM_toobig(L);
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
   100
  u = cast(Udata *, luaM_malloc(L, s + sizeof(Udata)));
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
   101
  u->uv.marked = luaC_white(G(L));  /* is not finalized */
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
   102
  u->uv.tt = LUA_TUSERDATA;
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
   103
  u->uv.len = s;
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
   104
  u->uv.metatable = NULL;
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
   105
  u->uv.env = e;
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
   106
  /* chain it on udata list (after main thread) */
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
   107
  u->uv.next = G(L)->mainthread->next;
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
   108
  G(L)->mainthread->next = obj2gco(u);
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
   109
  return u;
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
   110
}
0a24853de796 add liblua to sources for macosx
koda
parents:
diff changeset
   111