diff options
author | Roberto Ierusalimschy <roberto@inf.puc-rio.br> | 2024-12-17 11:23:22 -0300 |
---|---|---|
committer | Roberto Ierusalimschy <roberto@inf.puc-rio.br> | 2024-12-17 11:23:22 -0300 |
commit | 1c40ff9faafed620aa0458b397bcbfbe19e0f663 (patch) | |
tree | edfb96022feb99244a7a6c4c9d28525e141b783e /lcode.c | |
parent | 7538f3886dfa091d661c56e48ebb1578ced8e467 (diff) | |
download | lua-1c40ff9faafed620aa0458b397bcbfbe19e0f663.tar.gz lua-1c40ff9faafed620aa0458b397bcbfbe19e0f663.tar.bz2 lua-1c40ff9faafed620aa0458b397bcbfbe19e0f663.zip |
Scanner and parser use different tables for constants
Moreover, each function being parsed has its own table.
The code is cleaner when each table is used for one specific purpose:
The scanner uses its table to anchor and unify strings, mapping strings
to themselves; the parser uses it to reuse constants in the code,
mapping constants to their indices in the constant table. A different
table for each task avoids false collisions.
Diffstat (limited to 'lcode.c')
-rw-r--r-- | lcode.c | 12 |
1 files changed, 6 insertions, 6 deletions
@@ -563,13 +563,13 @@ static int addk (FuncState *fs, Proto *f, TValue *v) { | |||
563 | static int k2proto (FuncState *fs, TValue *key, TValue *v) { | 563 | static int k2proto (FuncState *fs, TValue *key, TValue *v) { |
564 | TValue val; | 564 | TValue val; |
565 | Proto *f = fs->f; | 565 | Proto *f = fs->f; |
566 | int tag = luaH_get(fs->ls->h, key, &val); /* query scanner table */ | 566 | int tag = luaH_get(fs->kcache, key, &val); /* query scanner table */ |
567 | int k; | 567 | int k; |
568 | if (tag == LUA_VNUMINT) { /* is there an index there? */ | 568 | if (!tagisempty(tag)) { /* is there an index there? */ |
569 | k = cast_int(ivalue(&val)); | 569 | k = cast_int(ivalue(&val)); |
570 | lua_assert(k < fs->nk); | ||
570 | /* correct value? (warning: must distinguish floats from integers!) */ | 571 | /* correct value? (warning: must distinguish floats from integers!) */ |
571 | if (k < fs->nk && ttypetag(&f->k[k]) == ttypetag(v) && | 572 | if (ttypetag(&f->k[k]) == ttypetag(v) && luaV_rawequalobj(&f->k[k], v)) |
572 | luaV_rawequalobj(&f->k[k], v)) | ||
573 | return k; /* reuse index */ | 573 | return k; /* reuse index */ |
574 | } | 574 | } |
575 | /* constant not found; create a new entry */ | 575 | /* constant not found; create a new entry */ |
@@ -577,7 +577,7 @@ static int k2proto (FuncState *fs, TValue *key, TValue *v) { | |||
577 | /* cache for reuse; numerical value does not need GC barrier; | 577 | /* cache for reuse; numerical value does not need GC barrier; |
578 | table has no metatable, so it does not need to invalidate cache */ | 578 | table has no metatable, so it does not need to invalidate cache */ |
579 | setivalue(&val, k); | 579 | setivalue(&val, k); |
580 | luaH_set(fs->ls->L, fs->ls->h, key, &val); | 580 | luaH_set(fs->ls->L, fs->kcache, key, &val); |
581 | return k; | 581 | return k; |
582 | } | 582 | } |
583 | 583 | ||
@@ -659,7 +659,7 @@ static int nilK (FuncState *fs) { | |||
659 | TValue k, v; | 659 | TValue k, v; |
660 | setnilvalue(&v); | 660 | setnilvalue(&v); |
661 | /* cannot use nil as key; instead use table itself to represent nil */ | 661 | /* cannot use nil as key; instead use table itself to represent nil */ |
662 | sethvalue(fs->ls->L, &k, fs->ls->h); | 662 | sethvalue(fs->ls->L, &k, fs->kcache); |
663 | return k2proto(fs, &k, &v); | 663 | return k2proto(fs, &k, &v); |
664 | } | 664 | } |
665 | 665 | ||