diff options
| author | Roberto Ierusalimschy <roberto@inf.puc-rio.br> | 2024-06-26 14:46:44 -0300 |
|---|---|---|
| committer | Roberto Ierusalimschy <roberto@inf.puc-rio.br> | 2024-06-26 14:46:44 -0300 |
| commit | fb7e5b76c9d41108c399cf4d16470018b717007b (patch) | |
| tree | cfc2b875d139727f1847100d8ae0950bee3d4f56 | |
| parent | c1dc08e8e8e22af9902a6341b4a9a9a7811954cc (diff) | |
| download | lua-fb7e5b76c9d41108c399cf4d16470018b717007b.tar.gz lua-fb7e5b76c9d41108c399cf4d16470018b717007b.tar.bz2 lua-fb7e5b76c9d41108c399cf4d16470018b717007b.zip | |
Clearer code for controlling maximum registers
Plus, added a test to check that limit.
| -rw-r--r-- | lcode.c | 6 | ||||
| -rw-r--r-- | lopcodes.h | 17 | ||||
| -rw-r--r-- | testes/code.lua | 15 |
3 files changed, 28 insertions, 10 deletions
| @@ -31,10 +31,6 @@ | |||
| 31 | #include "lvm.h" | 31 | #include "lvm.h" |
| 32 | 32 | ||
| 33 | 33 | ||
| 34 | /* Maximum number of registers in a Lua function (must fit in 8 bits) */ | ||
| 35 | #define MAXREGS 255 | ||
| 36 | |||
| 37 | |||
| 38 | #define hasjumps(e) ((e)->t != (e)->f) | 34 | #define hasjumps(e) ((e)->t != (e)->f) |
| 39 | 35 | ||
| 40 | 36 | ||
| @@ -466,7 +462,7 @@ static int luaK_codek (FuncState *fs, int reg, int k) { | |||
| 466 | void luaK_checkstack (FuncState *fs, int n) { | 462 | void luaK_checkstack (FuncState *fs, int n) { |
| 467 | int newstack = fs->freereg + n; | 463 | int newstack = fs->freereg + n; |
| 468 | if (newstack > fs->f->maxstacksize) { | 464 | if (newstack > fs->f->maxstacksize) { |
| 469 | if (newstack >= MAXREGS) | 465 | if (newstack > MAX_FSTACK) |
| 470 | luaX_syntaxerror(fs->ls, | 466 | luaX_syntaxerror(fs->ls, |
| 471 | "function or expression needs too many registers"); | 467 | "function or expression needs too many registers"); |
| 472 | fs->f->maxstacksize = cast_byte(newstack); | 468 | fs->f->maxstacksize = cast_byte(newstack); |
| @@ -23,9 +23,9 @@ iAsBx sBx (signed)(17) | A(8) | Op(7) | | |||
| 23 | iAx Ax(25) | Op(7) | | 23 | iAx Ax(25) | Op(7) | |
| 24 | isJ sJ (signed)(25) | Op(7) | | 24 | isJ sJ (signed)(25) | Op(7) | |
| 25 | 25 | ||
| 26 | A signed argument is represented in excess K: the represented value is | 26 | A signed argument is represented in excess K: The represented value is |
| 27 | the written unsigned value minus K, where K is half the maximum for the | 27 | the written unsigned value minus K, where K is half (rounded down) the |
| 28 | corresponding unsigned argument. | 28 | maximum value for the corresponding unsigned argument. |
| 29 | ===========================================================================*/ | 29 | ===========================================================================*/ |
| 30 | 30 | ||
| 31 | 31 | ||
| @@ -177,9 +177,16 @@ enum OpMode {iABC, iABx, iAsBx, iAx, isJ}; /* basic instruction formats */ | |||
| 177 | 177 | ||
| 178 | 178 | ||
| 179 | /* | 179 | /* |
| 180 | ** invalid register that fits in 8 bits | 180 | ** Maximum size for the stack of a Lua function. It must fit in 8 bits. |
| 181 | ** The highest valid register is one less than this value. | ||
| 181 | */ | 182 | */ |
| 182 | #define NO_REG MAXARG_A | 183 | #define MAX_FSTACK MAXARG_A |
| 184 | |||
| 185 | /* | ||
| 186 | ** Invalid register (one more than last valid register). | ||
| 187 | */ | ||
| 188 | #define NO_REG MAX_FSTACK | ||
| 189 | |||
| 183 | 190 | ||
| 184 | 191 | ||
| 185 | /* | 192 | /* |
diff --git a/testes/code.lua b/testes/code.lua index bd4b10d0..329619f1 100644 --- a/testes/code.lua +++ b/testes/code.lua | |||
| @@ -445,5 +445,20 @@ do -- string constants | |||
| 445 | assert(T.listk(f2)[1] == nil) | 445 | assert(T.listk(f2)[1] == nil) |
| 446 | end | 446 | end |
| 447 | 447 | ||
| 448 | |||
| 449 | do -- check number of available registers | ||
| 450 | -- 1 register for local + 1 for function + 252 arguments | ||
| 451 | local source = "local a; return a(" .. string.rep("a, ", 252) .. "a)" | ||
| 452 | local prog = T.listcode(assert(load(source))) | ||
| 453 | -- maximum valid register is 254 | ||
| 454 | for i = 1, 254 do | ||
| 455 | assert(string.find(prog[2 + i], "MOVE%s*" .. i)) | ||
| 456 | end | ||
| 457 | -- one more argument would need register #255 (but that is reserved) | ||
| 458 | source = "local a; return a(" .. string.rep("a, ", 253) .. "a)" | ||
| 459 | local _, msg = load(source) | ||
| 460 | assert(string.find(msg, "too many registers")) | ||
| 461 | end | ||
| 462 | |||
| 448 | print 'OK' | 463 | print 'OK' |
| 449 | 464 | ||
