MCPcopy Create free account
hub / github.com/ObEngine/ObEngine / luaH_newkey

Function luaH_newkey

extlibs/lua/src/ltable.c:621–672  ·  view source on GitHub ↗

** inserts a new key into a hash table; first, check whether key's main ** position is free. If not, check whether colliding node is in its main ** position or not: if it is not, move colliding node to an empty place and ** put new key in its main position; otherwise (colliding node is in its main ** position), new key goes to an empty position. */

Source from the content-addressed store, hash-verified

619** position), new key goes to an empty position.
620*/
621TValue *luaH_newkey (lua_State *L, Table *t, const TValue *key) {
622 Node *mp;
623 TValue aux;
624 if (unlikely(ttisnil(key)))
625 luaG_runerror(L, "table index is nil");
626 else if (ttisfloat(key)) {
627 lua_Number f = fltvalue(key);
628 lua_Integer k;
629 if (luaV_flttointeger(f, &k, F2Ieq)) { /* does key fit in an integer? */
630 setivalue(&aux, k);
631 key = &aux; /* insert it as an integer */
632 }
633 else if (unlikely(luai_numisnan(f)))
634 luaG_runerror(L, "table index is NaN");
635 }
636 mp = mainpositionTV(t, key);
637 if (!isempty(gval(mp)) || isdummy(t)) { /* main position is taken? */
638 Node *othern;
639 Node *f = getfreepos(t); /* get a free place */
640 if (f == NULL) { /* cannot find a free place? */
641 rehash(L, t, key); /* grow table */
642 /* whatever called 'newkey' takes care of TM cache */
643 return luaH_set(L, t, key); /* insert key into grown table */
644 }
645 lua_assert(!isdummy(t));
646 othern = mainposition(t, keytt(mp), &keyval(mp));
647 if (othern != mp) { /* is colliding node out of its main position? */
648 /* yes; move colliding node into free position */
649 while (othern + gnext(othern) != mp) /* find previous */
650 othern += gnext(othern);
651 gnext(othern) = cast_int(f - othern); /* rechain to point to 'f' */
652 *f = *mp; /* copy colliding node into free pos. (mp->next also goes) */
653 if (gnext(mp) != 0) {
654 gnext(f) += cast_int(mp - f); /* correct 'next' */
655 gnext(mp) = 0; /* now 'mp' is free */
656 }
657 setempty(gval(mp));
658 }
659 else { /* colliding node is in its own main position */
660 /* new node will go into free position */
661 if (gnext(mp) != 0)
662 gnext(f) = cast_int((mp + gnext(mp)) - f); /* chain new position */
663 else lua_assert(gnext(f) == 0);
664 gnext(mp) = cast_int(f - mp);
665 mp = f;
666 }
667 }
668 setnodekey(L, mp, key);
669 luaC_barrierback(L, obj2gco(t), key);
670 lua_assert(isempty(gval(mp)));
671 return gval(mp);
672}
673
674
675/*

Callers 3

luaV_finishsetFunction · 0.85
luaH_setFunction · 0.85
luaH_setintFunction · 0.85

Calls 7

luaG_runerrorFunction · 0.85
luaV_flttointegerFunction · 0.85
mainpositionTVFunction · 0.85
getfreeposFunction · 0.85
rehashFunction · 0.85
luaH_setFunction · 0.85
mainpositionFunction · 0.85

Tested by

no test coverage detected