Showing the changes to src/lcode.c (1 of 57 files). Show all
Unified · Split
| @@ -1,16 +1,18 @@ | |||
| 1 | /* | 1 | /* |
| 2 | ** $Id: lcode.c,v 2.90 2014/05/08 18:58:46 roberto Exp $ | 2 | ** $Id: lcode.c,v 2.97 2014/11/24 14:59:22 roberto Exp $ |
| 3 | ** Code generator for Lua | 3 | ** Code generator for Lua |
| 4 | ** See Copyright Notice in lua.h | 4 | ** See Copyright Notice in lua.h |
| 5 | */ | 5 | */ |
| 6 | 6 | ||
| 7 | #define lcode_c | ||
| 8 | #define LUA_CORE | ||
| 9 | |||
| 10 | #include "lprefix.h" | ||
| 11 | |||
| 7 | 12 | ||
| 8 | #include <math.h> | 13 | #include <math.h> |
| 9 | #include <stdlib.h> | 14 | #include <stdlib.h> |
| 10 | 15 | ||
| 11 | #define lcode_c | ||
| 12 | #define LUA_CORE | ||
| 13 | |||
| 14 | #include "lua.h" | 16 | #include "lua.h" |
| 15 | 17 | ||
| 16 | #include "lcode.h" | 18 | #include "lcode.h" |
| @@ -27,7 +29,11 @@ · 10 unmodified lines | |||
| 27 | #include "lvm.h" | 29 | #include "lvm.h" |
| 28 | 30 | ||
| 29 | 31 | ||
| 30 | /* test for x == -0 */ | 32 | /* Maximum number of registers in a Lua function */ |
| 33 | #define MAXREGS 250 | ||
| 34 | |||
| 35 | |||
| 36 | /* test for x == -0 ('signbit' needs 'math.h') */ | ||
| 31 | #if defined(signbit) | 37 | #if defined(signbit) |
| 32 | #define isminuszero(x) ((x) == 0.0 && signbit(x)) | 38 | #define isminuszero(x) ((x) == 0.0 && signbit(x)) |
| 33 | #else | 39 | #else |
| @@ -107,7 +113,7 @@ static void fixjump (FuncState *fs, int pc, int dest) { · 73 unmodified lines | |||
| 107 | 113 | ||
| 108 | 114 | ||
| 109 | /* | 115 | /* |
| 110 | ** returns current `pc' and marks it as a jump target (to avoid wrong | 116 | ** returns current 'pc' and marks it as a jump target (to avoid wrong |
| 111 | ** optimizations with consecutive instructions not in the same basic block). | 117 | ** optimizations with consecutive instructions not in the same basic block). |
| 112 | */ | 118 | */ |
| 113 | int luaK_getlabel (FuncState *fs) { | 119 | int luaK_getlabel (FuncState *fs) { |
| @@ -230,7 +236,7 @@ void luaK_concat (FuncState *fs, int *l1, int l2) { · 116 unmodified lines | |||
| 230 | 236 | ||
| 231 | static int luaK_code (FuncState *fs, Instruction i) { | 237 | static int luaK_code (FuncState *fs, Instruction i) { |
| 232 | Proto *f = fs->f; | 238 | Proto *f = fs->f; |
| 233 | dischargejpc(fs); /* `pc' will change */ | 239 | dischargejpc(fs); /* 'pc' will change */ |
| 234 | /* put new instruction in code array */ | 240 | /* put new instruction in code array */ |
| 235 | luaM_growvector(fs->ls->L, f->code, fs->pc, f->sizecode, Instruction, | 241 | luaM_growvector(fs->ls->L, f->code, fs->pc, f->sizecode, Instruction, |
| 236 | MAX_INT, "opcodes"); | 242 | MAX_INT, "opcodes"); |
| @@ -280,7 +286,7 @@ int luaK_codek (FuncState *fs, int reg, int k) { · 43 unmodified lines | |||
| 280 | void luaK_checkstack (FuncState *fs, int n) { | 286 | void luaK_checkstack (FuncState *fs, int n) { |
| 281 | int newstack = fs->freereg + n; | 287 | int newstack = fs->freereg + n; |
| 282 | if (newstack > fs->f->maxstacksize) { | 288 | if (newstack > fs->f->maxstacksize) { |
| 283 | if (newstack >= MAXSTACK) | 289 | if (newstack >= MAXREGS) |
| 284 | luaX_syntaxerror(fs->ls, "function or expression too complex"); | 290 | luaX_syntaxerror(fs->ls, "function or expression too complex"); |
| 285 | fs->f->maxstacksize = cast_byte(newstack); | 291 | fs->f->maxstacksize = cast_byte(newstack); |
| 286 | } | 292 | } |
| @@ -503,7 +509,7 @@ static void discharge2anyreg (FuncState *fs, expdesc *e) { · 216 unmodified lines | |||
| 503 | static void exp2reg (FuncState *fs, expdesc *e, int reg) { | 509 | static void exp2reg (FuncState *fs, expdesc *e, int reg) { |
| 504 | discharge2reg(fs, e, reg); | 510 | discharge2reg(fs, e, reg); |
| 505 | if (e->k == VJMP) | 511 | if (e->k == VJMP) |
| 506 | luaK_concat(fs, &e->t, e->u.info); /* put this jump in `t' list */ | 512 | luaK_concat(fs, &e->t, e->u.info); /* put this jump in 't' list */ |
| 507 | if (hasjumps(e)) { | 513 | if (hasjumps(e)) { |
| 508 | int final; /* position after whole expression */ | 514 | int final; /* position after whole expression */ |
| 509 | int p_f = NO_JUMP; /* position of an eventual LOAD false */ | 515 | int p_f = NO_JUMP; /* position of an eventual LOAD false */ |
| @@ -585,7 +591,7 @@ int luaK_exp2RK (FuncState *fs, expdesc *e) { · 75 unmodified lines | |||
| 585 | } | 591 | } |
| 586 | case VK: { | 592 | case VK: { |
| 587 | vk: | 593 | vk: |
| 588 | if (e->u.info <= MAXINDEXRK) /* constant fits in argC? */ | 594 | if (e->u.info <= MAXINDEXRK) /* constant fits in 'argC'? */ |
| 589 | return RKASK(e->u.info); | 595 | return RKASK(e->u.info); |
| 590 | else break; | 596 | else break; |
| 591 | } | 597 | } |
| @@ -677,7 +683,7 @@ void luaK_goiftrue (FuncState *fs, expdesc *e) { · 85 unmodified lines | |||
| 677 | break; | 683 | break; |
| 678 | } | 684 | } |
| 679 | } | 685 | } |
| 680 | luaK_concat(fs, &e->f, pc); /* insert last jump in `f' list */ | 686 | luaK_concat(fs, &e->f, pc); /* insert last jump in 'f' list */ |
| 681 | luaK_patchtohere(fs, e->t); | 687 | luaK_patchtohere(fs, e->t); |
| 682 | e->t = NO_JUMP; | 688 | e->t = NO_JUMP; |
| 683 | } | 689 | } |
| @@ -700,7 +706,7 @@ void luaK_goiffalse (FuncState *fs, expdesc *e) { · 16 unmodified lines | |||
| 700 | break; | 706 | break; |
| 701 | } | 707 | } |
| 702 | } | 708 | } |
| 703 | luaK_concat(fs, &e->t, pc); /* insert last jump in `t' list */ | 709 | luaK_concat(fs, &e->t, pc); /* insert last jump in 't' list */ |
| 704 | luaK_patchtohere(fs, e->f); | 710 | luaK_patchtohere(fs, e->f); |
| 705 | e->f = NO_JUMP; | 711 | e->f = NO_JUMP; |
| 706 | } | 712 | } |
| @@ -762,12 +768,10 @@ static int validop (int op, TValue *v1, TValue *v2) { · 55 unmodified lines | |||
| 762 | (cast_void(tonumber(v2, &b)), b))) | 768 | (cast_void(tonumber(v2, &b)), b))) |
| 763 | return 0; | 769 | return 0; |
| 764 | switch (op) { | 770 | switch (op) { |
| 765 | case LUA_OPIDIV: /* division by 0 and conversion errors */ | ||
| 766 | return (tointeger(v1, &i) && tointeger(v2, &i) && i != 0); | ||
| 767 | case LUA_OPBAND: case LUA_OPBOR: case LUA_OPBXOR: | 771 | case LUA_OPBAND: case LUA_OPBOR: case LUA_OPBXOR: |
| 768 | case LUA_OPSHL: case LUA_OPSHR: case LUA_OPBNOT: /* conversion errors */ | 772 | case LUA_OPSHL: case LUA_OPSHR: case LUA_OPBNOT: /* conversion errors */ |
| 769 | return (tointeger(v1, &i) && tointeger(v2, &i)); | 773 | return (tointeger(v1, &i) && tointeger(v2, &i)); |
| 770 | case LUA_OPMOD: /* integer module by 0 */ | 774 | case LUA_OPIDIV: case LUA_OPMOD: /* integer division by 0 */ |
| 771 | return !(ttisinteger(v1) && ttisinteger(v2) && ivalue(v2) == 0); | 775 | return !(ttisinteger(v1) && ttisinteger(v2) && ivalue(v2) == 0); |
| 772 | default: return 1; /* everything else is valid */ | 776 | default: return 1; /* everything else is valid */ |
| 773 | } | 777 | } |
| @@ -797,19 +801,30 @@ static int constfolding (FuncState *fs, int op, expdesc *e1, expdesc *e2) { · 23 unmodified lines | |||
| 797 | } | 801 | } |
| 798 | 802 | ||
| 799 | 803 | ||
| 800 | static void codearith (FuncState *fs, OpCode op, | 804 | /* |
| 801 | expdesc *e1, expdesc *e2, int line) { | 805 | ** Code for binary and unary expressions that "produce values" |
| 802 | if (!constfolding(fs, op - OP_ADD + LUA_OPADD, e1, e2)) { | 806 | ** (arithmetic operations, bitwise operations, concat, length). First |
| 807 | ** try to do constant folding (only for numeric [arithmetic and | ||
| 808 | ** bitwise] operations, which is what 'lua_arith' accepts). | ||
| 809 | ** Expression to produce final result will be encoded in 'e1'. | ||
| 810 | */ | ||
| 811 | static void codeexpval (FuncState *fs, OpCode op, | ||
| 812 | expdesc *e1, expdesc *e2, int line) { | ||
| 813 | lua_assert(op >= OP_ADD); | ||
| 814 | if (op <= OP_BNOT && constfolding(fs, op - OP_ADD + LUA_OPADD, e1, e2)) | ||
| 815 | return; /* result has been folded */ | ||
| 816 | else { | ||
| 803 | int o1, o2; | 817 | int o1, o2; |
| 804 | if (op == OP_UNM || op == OP_BNOT || op == OP_LEN) { | 818 | /* move operands to registers (if needed) */ |
| 805 | o2 = 0; | 819 | if (op == OP_UNM || op == OP_BNOT || op == OP_LEN) { /* unary op? */ |
| 820 | o2 = 0; /* no second expression */ | ||
| 806 | o1 = luaK_exp2anyreg(fs, e1); /* cannot operate on constants */ | 821 | o1 = luaK_exp2anyreg(fs, e1); /* cannot operate on constants */ |
| 807 | } | 822 | } |
| 808 | else { /* regular case (binary operators) */ | 823 | else { /* regular case (binary operators) */ |
| 809 | o2 = luaK_exp2RK(fs, e2); | 824 | o2 = luaK_exp2RK(fs, e2); /* both operands are "RK" */ |
| 810 | o1 = luaK_exp2RK(fs, e1); | 825 | o1 = luaK_exp2RK(fs, e1); |
| 811 | } | 826 | } |
| 812 | if (o1 > o2) { | 827 | if (o1 > o2) { /* free registers in proper order */ |
| 813 | freeexp(fs, e1); | 828 | freeexp(fs, e1); |
| 814 | freeexp(fs, e2); | 829 | freeexp(fs, e2); |
| 815 | } | 830 | } |
| @@ -817,8 +832,8 @@ static void codearith (FuncState *fs, OpCode op, · 1 unmodified line | |||
| 817 | freeexp(fs, e2); | 832 | freeexp(fs, e2); |
| 818 | freeexp(fs, e1); | 833 | freeexp(fs, e1); |
| 819 | } | 834 | } |
| 820 | e1->u.info = luaK_codeABC(fs, op, 0, o1, o2); | 835 | e1->u.info = luaK_codeABC(fs, op, 0, o1, o2); /* generate opcode */ |
| 821 | e1->k = VRELOCABLE; | 836 | e1->k = VRELOCABLE; /* all those operations are relocable */ |
| 822 | luaK_fixline(fs, line); | 837 | luaK_fixline(fs, line); |
| 823 | } | 838 | } |
| 824 | } | 839 | } |
| @@ -831,7 +846,7 @@ static void codecomp (FuncState *fs, OpCode op, int cond, expdesc *e1, · 6 unmodified lines | |||
| 831 | freeexp(fs, e2); | 846 | freeexp(fs, e2); |
| 832 | freeexp(fs, e1); | 847 | freeexp(fs, e1); |
| 833 | if (cond == 0 && op != OP_EQ) { | 848 | if (cond == 0 && op != OP_EQ) { |
| 834 | int temp; /* exchange args to replace by `<' or `<=' */ | 849 | int temp; /* exchange args to replace by '<' or '<=' */ |
| 835 | temp = o1; o1 = o2; o2 = temp; /* o1 <==> o2 */ | 850 | temp = o1; o1 = o2; o2 = temp; /* o1 <==> o2 */ |
| 836 | cond = 1; | 851 | cond = 1; |
| 837 | } | 852 | } |
| @@ -845,7 +860,7 @@ void luaK_prefix (FuncState *fs, UnOpr op, expdesc *e, int line) { · 7 unmodified lines | |||
| 845 | e2.t = e2.f = NO_JUMP; e2.k = VKINT; e2.u.ival = 0; | 860 | e2.t = e2.f = NO_JUMP; e2.k = VKINT; e2.u.ival = 0; |
| 846 | switch (op) { | 861 | switch (op) { |
| 847 | case OPR_MINUS: case OPR_BNOT: case OPR_LEN: { | 862 | case OPR_MINUS: case OPR_BNOT: case OPR_LEN: { |
| 848 | codearith(fs, cast(OpCode, (op - OPR_MINUS) + OP_UNM), e, &e2, line); | 863 | codeexpval(fs, cast(OpCode, (op - OPR_MINUS) + OP_UNM), e, &e2, line); |
| 849 | break; | 864 | break; |
| 850 | } | 865 | } |
| 851 | case OPR_NOT: codenot(fs, e); break; | 866 | case OPR_NOT: codenot(fs, e); break; |
| @@ -865,7 +880,7 @@ void luaK_infix (FuncState *fs, BinOpr op, expdesc *v) { · 13 unmodified lines | |||
| 865 | break; | 880 | break; |
| 866 | } | 881 | } |
| 867 | case OPR_CONCAT: { | 882 | case OPR_CONCAT: { |
| 868 | luaK_exp2nextreg(fs, v); /* operand must be on the `stack' */ | 883 | luaK_exp2nextreg(fs, v); /* operand must be on the 'stack' */ |
| 869 | break; | 884 | break; |
| 870 | } | 885 | } |
| 871 | case OPR_ADD: case OPR_SUB: | 886 | case OPR_ADD: case OPR_SUB: |
| @@ -911,7 +926,7 @@ void luaK_posfix (FuncState *fs, BinOpr op, · 39 unmodified lines | |||
| 911 | } | 926 | } |
| 912 | else { | 927 | else { |
| 913 | luaK_exp2nextreg(fs, e2); /* operand must be on the 'stack' */ | 928 | luaK_exp2nextreg(fs, e2); /* operand must be on the 'stack' */ |
| 914 | codearith(fs, OP_CONCAT, e1, e2, line); | 929 | codeexpval(fs, OP_CONCAT, e1, e2, line); |
| 915 | } | 930 | } |
| 916 | break; | 931 | break; |
| 917 | } | 932 | } |
| @@ -919,7 +934,7 @@ void luaK_posfix (FuncState *fs, BinOpr op, · 1 unmodified line | |||
| 919 | case OPR_IDIV: case OPR_MOD: case OPR_POW: | 934 | case OPR_IDIV: case OPR_MOD: case OPR_POW: |
| 920 | case OPR_BAND: case OPR_BOR: case OPR_BXOR: | 935 | case OPR_BAND: case OPR_BOR: case OPR_BXOR: |
| 921 | case OPR_SHL: case OPR_SHR: { | 936 | case OPR_SHL: case OPR_SHR: { |
| 922 | codearith(fs, cast(OpCode, (op - OPR_ADD) + OP_ADD), e1, e2, line); | 937 | codeexpval(fs, cast(OpCode, (op - OPR_ADD) + OP_ADD), e1, e2, line); |
| 923 | break; | 938 | break; |
| 924 | } | 939 | } |
| 925 | case OPR_EQ: case OPR_LT: case OPR_LE: { | 940 | case OPR_EQ: case OPR_LT: case OPR_LE: { |