aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorRoberto Ierusalimschy <roberto@inf.puc-rio.br>2013-08-18 13:12:18 -0300
committerRoberto Ierusalimschy <roberto@inf.puc-rio.br>2013-08-18 13:12:18 -0300
commitcaceeab750ed80e94f8ec763248ae04cd90fefb5 (patch)
tree2f5b0e8d457dd29d5525d924e6bd4d2328292d84
parent3991312b94c0862577a5998fcf9ea93c81c6933c (diff)
downloadlua-caceeab750ed80e94f8ec763248ae04cd90fefb5.tar.gz
lua-caceeab750ed80e94f8ec763248ae04cd90fefb5.tar.bz2
lua-caceeab750ed80e94f8ec763248ae04cd90fefb5.zip
'next' field for tables changed from pointer to integer (for better
alignment on 64-bit machines)
-rw-r--r--lobject.h4
-rw-r--r--ltable.c68
-rw-r--r--ltests.c6
3 files changed, 49 insertions, 29 deletions
diff --git a/lobject.h b/lobject.h
index ba425fed..3ab75ad5 100644
--- a/lobject.h
+++ b/lobject.h
@@ -1,5 +1,5 @@
1/* 1/*
2** $Id: lobject.h,v 2.78 2013/05/14 15:59:04 roberto Exp roberto $ 2** $Id: lobject.h,v 2.79 2013/08/07 12:18:11 roberto Exp roberto $
3** Type definitions for Lua objects 3** Type definitions for Lua objects
4** See Copyright Notice in lua.h 4** See Copyright Notice in lua.h
5*/ 5*/
@@ -438,7 +438,7 @@ typedef union Closure {
438typedef union TKey { 438typedef union TKey {
439 struct { 439 struct {
440 TValuefields; 440 TValuefields;
441 struct Node *next; /* for chaining */ 441 int next; /* for chaining (offset for next node) */
442 } nk; 442 } nk;
443 TValue tvk; 443 TValue tvk;
444} TKey; 444} TKey;
diff --git a/ltable.c b/ltable.c
index 6a7e28f0..f5b8fcf6 100644
--- a/ltable.c
+++ b/ltable.c
@@ -1,5 +1,5 @@
1/* 1/*
2** $Id: ltable.c,v 2.77 2013/05/29 14:05:03 roberto Exp roberto $ 2** $Id: ltable.c,v 2.78 2013/06/20 15:02:49 roberto Exp roberto $
3** Lua tables (hash) 3** Lua tables (hash)
4** See Copyright Notice in lua.h 4** See Copyright Notice in lua.h
5*/ 5*/
@@ -79,7 +79,7 @@
79 79
80static const Node dummynode_ = { 80static const Node dummynode_ = {
81 {NILCONSTANT}, /* value */ 81 {NILCONSTANT}, /* value */
82 {{NILCONSTANT, NULL}} /* key */ 82 {{NILCONSTANT, 0}} /* key */
83}; 83};
84 84
85 85
@@ -158,6 +158,7 @@ static int findindex (lua_State *L, Table *t, StkId key) {
158 if (0 < i && i <= t->sizearray) /* is `key' inside array part? */ 158 if (0 < i && i <= t->sizearray) /* is `key' inside array part? */
159 return i-1; /* yes; that's the index (corrected to C) */ 159 return i-1; /* yes; that's the index (corrected to C) */
160 else { 160 else {
161 int nx;
161 Node *n = mainposition(t, key); 162 Node *n = mainposition(t, key);
162 for (;;) { /* check whether `key' is somewhere in the chain */ 163 for (;;) { /* check whether `key' is somewhere in the chain */
163 /* key may be dead already, but it is ok to use it in `next' */ 164 /* key may be dead already, but it is ok to use it in `next' */
@@ -168,9 +169,10 @@ static int findindex (lua_State *L, Table *t, StkId key) {
168 /* hash elements are numbered after array ones */ 169 /* hash elements are numbered after array ones */
169 return i + t->sizearray; 170 return i + t->sizearray;
170 } 171 }
171 else n = gnext(n); 172 nx = gnext(n);
172 if (n == NULL) 173 if (nx == 0)
173 luaG_runerror(L, "invalid key to " LUA_QL("next")); /* key not found */ 174 luaG_runerror(L, "invalid key to " LUA_QL("next")); /* key not found */
175 else n += nx;
174 } 176 }
175 } 177 }
176} 178}
@@ -301,7 +303,7 @@ static void setnodevector (lua_State *L, Table *t, int size) {
301 t->node = luaM_newvector(L, size, Node); 303 t->node = luaM_newvector(L, size, Node);
302 for (i=0; i<size; i++) { 304 for (i=0; i<size; i++) {
303 Node *n = gnode(t, i); 305 Node *n = gnode(t, i);
304 gnext(n) = NULL; 306 gnext(n) = 0;
305 setnilvalue(gkey(n)); 307 setnilvalue(gkey(n));
306 setnilvalue(gval(n)); 308 setnilvalue(gval(n));
307 } 309 }
@@ -429,27 +431,33 @@ TValue *luaH_newkey (lua_State *L, Table *t, const TValue *key) {
429 mp = mainposition(t, key); 431 mp = mainposition(t, key);
430 if (!ttisnil(gval(mp)) || isdummy(mp)) { /* main position is taken? */ 432 if (!ttisnil(gval(mp)) || isdummy(mp)) { /* main position is taken? */
431 Node *othern; 433 Node *othern;
432 Node *n = getfreepos(t); /* get a free place */ 434 Node *f = getfreepos(t); /* get a free place */
433 if (n == NULL) { /* cannot find a free place? */ 435 if (f == NULL) { /* cannot find a free place? */
434 rehash(L, t, key); /* grow table */ 436 rehash(L, t, key); /* grow table */
435 /* whatever called 'newkey' take care of TM cache and GC barrier */ 437 /* whatever called 'newkey' take care of TM cache and GC barrier */
436 return luaH_set(L, t, key); /* insert key into grown table */ 438 return luaH_set(L, t, key); /* insert key into grown table */
437 } 439 }
438 lua_assert(!isdummy(n)); 440 lua_assert(!isdummy(f));
439 othern = mainposition(t, gkey(mp)); 441 othern = mainposition(t, gkey(mp));
440 if (othern != mp) { /* is colliding node out of its main position? */ 442 if (othern != mp) { /* is colliding node out of its main position? */
441 /* yes; move colliding node into free position */ 443 /* yes; move colliding node into free position */
442 while (gnext(othern) != mp) othern = gnext(othern); /* find previous */ 444 while (othern + gnext(othern) != mp) /* find previous */
443 gnext(othern) = n; /* redo the chain with `n' in place of `mp' */ 445 othern += gnext(othern);
444 *n = *mp; /* copy colliding node into free pos. (mp->next also goes) */ 446 gnext(othern) = f - othern; /* re-chain with 'f' in place of 'mp' */
445 gnext(mp) = NULL; /* now `mp' is free */ 447 *f = *mp; /* copy colliding node into free pos. (mp->next also goes) */
448 if (gnext(mp) != 0) {
449 gnext(f) += mp - f; /* correct 'next' */
450 gnext(mp) = 0; /* now 'mp' is free */
451 }
446 setnilvalue(gval(mp)); 452 setnilvalue(gval(mp));
447 } 453 }
448 else { /* colliding node is in its own main position */ 454 else { /* colliding node is in its own main position */
449 /* new node will go into free position */ 455 /* new node will go into free position */
450 gnext(n) = gnext(mp); /* chain new position */ 456 if (gnext(mp) != 0)
451 gnext(mp) = n; 457 gnext(f) = (mp + gnext(mp)) - f; /* chain new position */
452 mp = n; 458 else lua_assert(gnext(f) == 0);
459 gnext(mp) = f - mp;
460 mp = f;
453 } 461 }
454 } 462 }
455 setobj2t(L, gkey(mp), key); 463 setobj2t(L, gkey(mp), key);
@@ -468,11 +476,15 @@ const TValue *luaH_getint (Table *t, lua_Integer key) {
468 return &t->array[key - 1]; 476 return &t->array[key - 1];
469 else { 477 else {
470 Node *n = hashint(t, key); 478 Node *n = hashint(t, key);
471 do { /* check whether `key' is somewhere in the chain */ 479 for (;;) { /* check whether `key' is somewhere in the chain */
472 if (ttisinteger(gkey(n)) && ivalue(gkey(n)) == key) 480 if (ttisinteger(gkey(n)) && ivalue(gkey(n)) == key)
473 return gval(n); /* that's it */ 481 return gval(n); /* that's it */
474 else n = gnext(n); 482 else {
475 } while (n); 483 int nx = gnext(n);
484 if (nx == 0) break;
485 n += nx;
486 }
487 };
476 return luaO_nilobject; 488 return luaO_nilobject;
477 } 489 }
478} 490}
@@ -484,11 +496,15 @@ const TValue *luaH_getint (Table *t, lua_Integer key) {
484const TValue *luaH_getstr (Table *t, TString *key) { 496const TValue *luaH_getstr (Table *t, TString *key) {
485 Node *n = hashstr(t, key); 497 Node *n = hashstr(t, key);
486 lua_assert(key->tsv.tt == LUA_TSHRSTR); 498 lua_assert(key->tsv.tt == LUA_TSHRSTR);
487 do { /* check whether `key' is somewhere in the chain */ 499 for (;;) { /* check whether `key' is somewhere in the chain */
488 if (ttisshrstring(gkey(n)) && eqshrstr(rawtsvalue(gkey(n)), key)) 500 if (ttisshrstring(gkey(n)) && eqshrstr(rawtsvalue(gkey(n)), key))
489 return gval(n); /* that's it */ 501 return gval(n); /* that's it */
490 else n = gnext(n); 502 else {
491 } while (n); 503 int nx = gnext(n);
504 if (nx == 0) break;
505 n += nx;
506 }
507 };
492 return luaO_nilobject; 508 return luaO_nilobject;
493} 509}
494 510
@@ -509,11 +525,15 @@ const TValue *luaH_get (Table *t, const TValue *key) {
509 } 525 }
510 default: { 526 default: {
511 Node *n = mainposition(t, key); 527 Node *n = mainposition(t, key);
512 do { /* check whether `key' is somewhere in the chain */ 528 for (;;) { /* check whether `key' is somewhere in the chain */
513 if (luaV_rawequalobj(gkey(n), key)) 529 if (luaV_rawequalobj(gkey(n), key))
514 return gval(n); /* that's it */ 530 return gval(n); /* that's it */
515 else n = gnext(n); 531 else {
516 } while (n); 532 int nx = gnext(n);
533 if (nx == 0) break;
534 n += nx;
535 }
536 };
517 return luaO_nilobject; 537 return luaO_nilobject;
518 } 538 }
519 } 539 }
diff --git a/ltests.c b/ltests.c
index e99b2b61..1fb01cfd 100644
--- a/ltests.c
+++ b/ltests.c
@@ -1,5 +1,5 @@
1/* 1/*
2** $Id: ltests.c,v 2.142 2013/08/16 18:55:49 roberto Exp roberto $ 2** $Id: ltests.c,v 2.143 2013/08/16 19:02:31 roberto Exp roberto $
3** Internal Module for Debugging of the Lua Implementation 3** Internal Module for Debugging of the Lua Implementation
4** See Copyright Notice in lua.h 4** See Copyright Notice in lua.h
5*/ 5*/
@@ -718,8 +718,8 @@ static int table_query (lua_State *L) {
718 else 718 else
719 lua_pushliteral(L, "<undef>"); 719 lua_pushliteral(L, "<undef>");
720 pushobject(L, gval(gnode(t, i))); 720 pushobject(L, gval(gnode(t, i)));
721 if (gnext(&t->node[i])) 721 if (gnext(&t->node[i]) != 0)
722 lua_pushinteger(L, gnext(&t->node[i]) - t->node); 722 lua_pushinteger(L, gnext(&t->node[i]));
723 else 723 else
724 lua_pushnil(L); 724 lua_pushnil(L);
725 } 725 }