aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorMike Pall <mike>2010-12-05 21:50:52 +0100
committerMike Pall <mike>2010-12-05 22:12:31 +0100
commit5a13fa69d95993fa68b12be4091f48b80844bdcf (patch)
tree73ec2ee4d64eec20245f198fde91eff9b3eadf35 /src
parentb1fb71fb981c464868e6bc669363658a98ecbd9e (diff)
downloadluajit-5a13fa69d95993fa68b12be4091f48b80844bdcf.tar.gz
luajit-5a13fa69d95993fa68b12be4091f48b80844bdcf.tar.bz2
luajit-5a13fa69d95993fa68b12be4091f48b80844bdcf.zip
Add IR_KINT64.
Diffstat (limited to 'src')
-rw-r--r--src/lj_asm.c65
-rw-r--r--src/lj_def.h3
-rw-r--r--src/lj_ir.c94
-rw-r--r--src/lj_ir.h40
-rw-r--r--src/lj_iropt.h19
-rw-r--r--src/lj_jit.h2
-rw-r--r--src/lj_opt_mem.c2
-rw-r--r--src/lj_record.c3
-rw-r--r--src/lj_trace.c2
9 files changed, 135 insertions, 95 deletions
diff --git a/src/lj_asm.c b/src/lj_asm.c
index 6bb2b8c6..4c31a3e9 100644
--- a/src/lj_asm.c
+++ b/src/lj_asm.c
@@ -384,15 +384,23 @@ static void emit_loadi(ASMState *as, Reg r, int32_t i)
384 emit_loadi(as, (r), ptr2addr((addr))) 384 emit_loadi(as, (r), ptr2addr((addr)))
385 385
386#if LJ_64 386#if LJ_64
387/* mov r, imm64 */ 387/* mov r, imm64 or shorter 32 bit extended load. */
388static void emit_loadu64(ASMState *as, Reg r, uint64_t i) 388static void emit_loadu64(ASMState *as, Reg r, uint64_t u64)
389{ 389{
390 MCode *p = as->mcp; 390 if (checku32(u64)) { /* 32 bit load clears upper 32 bits. */
391 *(uint64_t *)(p-8) = i; 391 emit_loadi(as, r, (int32_t)u64);
392 p[-9] = (MCode)(XI_MOVri+(r&7)); 392 } else if (checki32((int64_t)u64)) { /* Sign-extended 32 bit load. */
393 p[-10] = 0x48 + ((r>>3)&1); 393 MCode *p = as->mcp;
394 p -= 10; 394 *(int32_t *)(p-4) = (int32_t)u64;
395 as->mcp = p; 395 as->mcp = emit_opm(XO_MOVmi, XM_REG, REX_64, r, p, -4);
396 } else { /* Full-size 64 bit load. */
397 MCode *p = as->mcp;
398 *(uint64_t *)(p-8) = u64;
399 p[-9] = (MCode)(XI_MOVri+(r&7));
400 p[-10] = 0x48 + ((r>>3)&1);
401 p -= 10;
402 as->mcp = p;
403 }
396} 404}
397#endif 405#endif
398 406
@@ -618,6 +626,10 @@ static Reg ra_rematk(ASMState *as, IRIns *ir)
618 } else if (ir->o == IR_KPRI) { /* REF_NIL stores ASMREF_L register. */ 626 } else if (ir->o == IR_KPRI) { /* REF_NIL stores ASMREF_L register. */
619 lua_assert(irt_isnil(ir->t)); 627 lua_assert(irt_isnil(ir->t));
620 emit_getgl(as, r, jit_L); 628 emit_getgl(as, r, jit_L);
629#if LJ_64 /* NYI: 32 bit register pairs. */
630 } else if (ir->o == IR_KINT64) {
631 emit_loadu64(as, r, ir_kint64(ir)->u64);
632#endif
621 } else { 633 } else {
622 lua_assert(ir->o == IR_KINT || ir->o == IR_KGC || 634 lua_assert(ir->o == IR_KINT || ir->o == IR_KGC ||
623 ir->o == IR_KPTR || ir->o == IR_KNULL); 635 ir->o == IR_KPTR || ir->o == IR_KNULL);
@@ -909,6 +921,11 @@ static void ra_left(ASMState *as, Reg dest, IRRef lref)
909 emit_loadn(as, dest, tv); 921 emit_loadn(as, dest, tv);
910 return; 922 return;
911 } 923 }
924#if LJ_64 /* NYI: 32 bit register pairs. */
925 } else if (ir->o == IR_KINT64) {
926 emit_loadu64(as, dest, ir_kint64(ir)->u64);
927 return;
928#endif
912 } else { 929 } else {
913 lua_assert(ir->o == IR_KINT || ir->o == IR_KGC || 930 lua_assert(ir->o == IR_KINT || ir->o == IR_KGC ||
914 ir->o == IR_KPTR || ir->o == IR_KNULL); 931 ir->o == IR_KPTR || ir->o == IR_KNULL);
@@ -1343,7 +1360,8 @@ static void asm_gencall(ASMState *as, const CCallInfo *ci, IRRef *args)
1343 lua_assert(!(nargs > 2 && (ci->flags&CCI_FASTCALL))); /* Avoid stack adj. */ 1360 lua_assert(!(nargs > 2 && (ci->flags&CCI_FASTCALL))); /* Avoid stack adj. */
1344 emit_call(as, ci->func); 1361 emit_call(as, ci->func);
1345 for (n = 0; n < nargs; n++) { /* Setup args. */ 1362 for (n = 0; n < nargs; n++) { /* Setup args. */
1346 IRIns *ir = IR(args[n]); 1363 IRRef ref = args[n];
1364 IRIns *ir = IR(ref);
1347 Reg r; 1365 Reg r;
1348#if LJ_64 && LJ_ABI_WIN 1366#if LJ_64 && LJ_ABI_WIN
1349 /* Windows/x64 argument registers are strictly positional. */ 1367 /* Windows/x64 argument registers are strictly positional. */
@@ -1364,38 +1382,42 @@ static void asm_gencall(ASMState *as, const CCallInfo *ci, IRRef *args)
1364 } 1382 }
1365#endif 1383#endif
1366 if (r) { /* Argument is in a register. */ 1384 if (r) { /* Argument is in a register. */
1367 if (r < RID_MAX_GPR && args[n] < ASMREF_TMP1) { 1385 if (r < RID_MAX_GPR && ref < ASMREF_TMP1) {
1368 emit_loadi(as, r, ir->i); 1386#if LJ_64 /* NYI: 32 bit register pairs. */
1387 if (ir->o == IR_KINT64)
1388 emit_loadu64(as, r, ir_kint64(ir)->u64);
1389 else
1390#endif
1391 emit_loadi(as, r, ir->i);
1369 } else { 1392 } else {
1370 lua_assert(rset_test(as->freeset, r)); /* Must have been evicted. */ 1393 lua_assert(rset_test(as->freeset, r)); /* Must have been evicted. */
1371 if (ra_hasreg(ir->r)) { 1394 if (ra_hasreg(ir->r)) {
1372 ra_noweak(as, ir->r); 1395 ra_noweak(as, ir->r);
1373 ra_movrr(as, ir, r, ir->r); 1396 ra_movrr(as, ir, r, ir->r);
1374 } else { 1397 } else {
1375 ra_allocref(as, args[n], RID2RSET(r)); 1398 ra_allocref(as, ref, RID2RSET(r));
1376 } 1399 }
1377 } 1400 }
1378 } else if (irt_isnum(ir->t)) { /* FP argument is on stack. */ 1401 } else if (irt_isnum(ir->t)) { /* FP argument is on stack. */
1379 if (!LJ_64 && (ofs & 4) && irref_isk(args[n])) { 1402 if (LJ_32 && (ofs & 4) && irref_isk(ref)) {
1380 /* Split stores for unaligned FP consts. */ 1403 /* Split stores for unaligned FP consts. */
1381 emit_movmroi(as, RID_ESP, ofs, (int32_t)ir_knum(ir)->u32.lo); 1404 emit_movmroi(as, RID_ESP, ofs, (int32_t)ir_knum(ir)->u32.lo);
1382 emit_movmroi(as, RID_ESP, ofs+4, (int32_t)ir_knum(ir)->u32.hi); 1405 emit_movmroi(as, RID_ESP, ofs+4, (int32_t)ir_knum(ir)->u32.hi);
1383 } else { 1406 } else {
1384 if ((allow & RSET_FPR) == RSET_EMPTY) 1407 if ((allow & RSET_FPR) == RSET_EMPTY)
1385 lj_trace_err(as->J, LJ_TRERR_NYICOAL); 1408 lj_trace_err(as->J, LJ_TRERR_NYICOAL);
1386 r = ra_alloc1(as, args[n], allow & RSET_FPR); 1409 r = ra_alloc1(as, ref, allow & RSET_FPR);
1387 allow &= ~RID2RSET(r); 1410 allow &= ~RID2RSET(r);
1388 emit_rmro(as, XO_MOVSDto, r, RID_ESP, ofs); 1411 emit_rmro(as, XO_MOVSDto, r, RID_ESP, ofs);
1389 } 1412 }
1390 ofs += 8; 1413 ofs += 8;
1391 } else { /* Non-FP argument is on stack. */ 1414 } else { /* Non-FP argument is on stack. */
1392 /* NYI: no widening for 64 bit parameters on x64. */ 1415 if (LJ_32 && ref < ASMREF_TMP1) {
1393 if (args[n] < ASMREF_TMP1) {
1394 emit_movmroi(as, RID_ESP, ofs, ir->i); 1416 emit_movmroi(as, RID_ESP, ofs, ir->i);
1395 } else { 1417 } else {
1396 if ((allow & RSET_GPR) == RSET_EMPTY) 1418 if ((allow & RSET_GPR) == RSET_EMPTY)
1397 lj_trace_err(as->J, LJ_TRERR_NYICOAL); 1419 lj_trace_err(as->J, LJ_TRERR_NYICOAL);
1398 r = ra_alloc1(as, args[n], allow & RSET_GPR); 1420 r = ra_alloc1(as, ref, allow & RSET_GPR);
1399 allow &= ~RID2RSET(r); 1421 allow &= ~RID2RSET(r);
1400 emit_movtomro(as, REX_64IR(ir, r), RID_ESP, ofs); 1422 emit_movtomro(as, REX_64IR(ir, r), RID_ESP, ofs);
1401 } 1423 }
@@ -1936,8 +1958,9 @@ static void asm_fstore(ASMState *as, IRIns *ir)
1936 /* The IRT_I16/IRT_U16 stores should never be simplified for constant 1958 /* The IRT_I16/IRT_U16 stores should never be simplified for constant
1937 ** values since mov word [mem], imm16 has a length-changing prefix. 1959 ** values since mov word [mem], imm16 has a length-changing prefix.
1938 */ 1960 */
1939 lua_assert(!(irref_isk(ir->op2) && irt_is64(ir->t))); /* NYI: KINT64. */ 1961 if (!irref_isk(ir->op2) || irt_isi16(ir->t) || irt_isu16(ir->t) ||
1940 if (!irref_isk(ir->op2) || irt_isi16(ir->t) || irt_isu16(ir->t)) { 1962 (LJ_64 && irt_is64(ir->t) &&
1963 !checki32((int64_t)ir_k64(IR(ir->op2))->u64))) {
1941 RegSet allow8 = (irt_isi8(ir->t) || irt_isu8(ir->t)) ? RSET_GPR8 : RSET_GPR; 1964 RegSet allow8 = (irt_isi8(ir->t) || irt_isu8(ir->t)) ? RSET_GPR8 : RSET_GPR;
1942 src = ra_alloc1(as, ir->op2, allow8); 1965 src = ra_alloc1(as, ir->op2, allow8);
1943 rset_clear(allow, src); 1966 rset_clear(allow, src);
@@ -2496,7 +2519,7 @@ static void asm_add(ASMState *as, IRIns *ir)
2496 if (irt_isnum(ir->t)) 2519 if (irt_isnum(ir->t))
2497 asm_fparith(as, ir, XO_ADDSD); 2520 asm_fparith(as, ir, XO_ADDSD);
2498 else if ((as->flags & JIT_F_LEA_AGU) || as->testmcp == as->mcp || 2521 else if ((as->flags & JIT_F_LEA_AGU) || as->testmcp == as->mcp ||
2499 !asm_lea(as, ir)) 2522 irt_is64(ir->t) || !asm_lea(as, ir))
2500 asm_intarith(as, ir, XOg_ADD); 2523 asm_intarith(as, ir, XOg_ADD);
2501} 2524}
2502 2525
@@ -2615,7 +2638,7 @@ static void asm_comp_(ASMState *as, IRIns *ir, int cc)
2615 else if ((cc & 0xa) == 0x2) cc ^= 5; /* A <-> B, AE <-> BE */ 2638 else if ((cc & 0xa) == 0x2) cc ^= 5; /* A <-> B, AE <-> BE */
2616 lref = ir->op2; rref = ir->op1; 2639 lref = ir->op2; rref = ir->op1;
2617 } 2640 }
2618 if (irref_isk(rref)) { 2641 if (irref_isk(rref) && IR(rref)->o != IR_KINT64) {
2619 IRIns *irl = IR(lref); 2642 IRIns *irl = IR(lref);
2620 int32_t imm = IR(rref)->i; 2643 int32_t imm = IR(rref)->i;
2621 /* Check wether we can use test ins. Not for unsigned, since CF=0. */ 2644 /* Check wether we can use test ins. Not for unsigned, since CF=0. */
diff --git a/src/lj_def.h b/src/lj_def.h
index 074090af..e72a8ef9 100644
--- a/src/lj_def.h
+++ b/src/lj_def.h
@@ -62,7 +62,7 @@ typedef unsigned __int32 uintptr_t;
62#define LJ_MIN_SBUF 32 /* Min. string buffer length. */ 62#define LJ_MIN_SBUF 32 /* Min. string buffer length. */
63#define LJ_MIN_VECSZ 8 /* Min. size for growable vectors. */ 63#define LJ_MIN_VECSZ 8 /* Min. size for growable vectors. */
64#define LJ_MIN_IRSZ 32 /* Min. size for growable IR. */ 64#define LJ_MIN_IRSZ 32 /* Min. size for growable IR. */
65#define LJ_MIN_KNUMSZ 16 /* Min. size for chained KNUM array. */ 65#define LJ_MIN_K64SZ 16 /* Min. size for chained K64Array. */
66 66
67/* JIT compiler limits. */ 67/* JIT compiler limits. */
68#define LJ_MAX_JSLOTS 250 /* Max. # of stack slots for a trace. */ 68#define LJ_MAX_JSLOTS 250 /* Max. # of stack slots for a trace. */
@@ -90,6 +90,7 @@ typedef unsigned __int32 uintptr_t;
90#define checki16(x) ((x) == (int32_t)(int16_t)(x)) 90#define checki16(x) ((x) == (int32_t)(int16_t)(x))
91#define checku16(x) ((x) == (int32_t)(uint16_t)(x)) 91#define checku16(x) ((x) == (int32_t)(uint16_t)(x))
92#define checki32(x) ((x) == (int32_t)(x)) 92#define checki32(x) ((x) == (int32_t)(x))
93#define checku32(x) ((x) == (uint32_t)(x))
93#define checkptr32(x) ((uintptr_t)(x) == (uint32_t)(uintptr_t)(x)) 94#define checkptr32(x) ((uintptr_t)(x) == (uint32_t)(uintptr_t)(x))
94 95
95/* Every half-decent C compiler transforms this into a rotate instruction. */ 96/* Every half-decent C compiler transforms this into a rotate instruction. */
diff --git a/src/lj_ir.c b/src/lj_ir.c
index 529c333b..d39a345f 100644
--- a/src/lj_ir.c
+++ b/src/lj_ir.c
@@ -167,88 +167,95 @@ found:
167 return TREF(ref, IRT_INT); 167 return TREF(ref, IRT_INT);
168} 168}
169 169
170/* The MRef inside the KNUM IR instruction holds the address of the constant 170/* The MRef inside the KNUM/KINT64 IR instructions holds the address of the
171** (an aligned double or a special 64 bit pattern). The KNUM constants 171** 64 bit constant. The constants themselves are stored in a chained array
172** themselves are stored in a chained array and shared across traces. 172** and shared across traces.
173** 173**
174** Rationale for choosing this data structure: 174** Rationale for choosing this data structure:
175** - The address of the constants is embedded in the generated machine code 175** - The address of the constants is embedded in the generated machine code
176** and must never move. A resizable array or hash table wouldn't work. 176** and must never move. A resizable array or hash table wouldn't work.
177** - Most apps need very few non-integer constants (less than a dozen). 177** - Most apps need very few non-32 bit integer constants (less than a dozen).
178** - Linear search is hard to beat in terms of speed and low complexity. 178** - Linear search is hard to beat in terms of speed and low complexity.
179*/ 179*/
180typedef struct KNumArray { 180typedef struct K64Array {
181 MRef next; /* Pointer to next list. */ 181 MRef next; /* Pointer to next list. */
182 MSize numk; /* Number of used elements in this array. */ 182 MSize numk; /* Number of used elements in this array. */
183 TValue k[LJ_MIN_KNUMSZ]; /* Array of constants. */ 183 TValue k[LJ_MIN_K64SZ]; /* Array of constants. */
184} KNumArray; 184} K64Array;
185 185
186/* Free all chained arrays. */ 186/* Free all chained arrays. */
187void lj_ir_knum_freeall(jit_State *J) 187void lj_ir_k64_freeall(jit_State *J)
188{ 188{
189 KNumArray *kn; 189 K64Array *k;
190 for (kn = mref(J->knum, KNumArray); kn; ) { 190 for (k = mref(J->k64, K64Array); k; ) {
191 KNumArray *next = mref(kn->next, KNumArray); 191 K64Array *next = mref(k->next, K64Array);
192 lj_mem_free(J2G(J), kn, sizeof(KNumArray)); 192 lj_mem_free(J2G(J), k, sizeof(K64Array));
193 kn = next; 193 k = next;
194 } 194 }
195} 195}
196 196
197/* Find KNUM constant in chained array or add it. */ 197/* Find 64 bit constant in chained array or add it. */
198static cTValue *ir_knum_find(jit_State *J, uint64_t nn) 198static cTValue *ir_k64_find(jit_State *J, uint64_t u64)
199{ 199{
200 KNumArray *kn, *knp = NULL; 200 K64Array *k, *kp = NULL;
201 TValue *ntv; 201 TValue *ntv;
202 MSize idx; 202 MSize idx;
203 /* Search for the constant in the whole chain of arrays. */ 203 /* Search for the constant in the whole chain of arrays. */
204 for (kn = mref(J->knum, KNumArray); kn; kn = mref(kn->next, KNumArray)) { 204 for (k = mref(J->k64, K64Array); k; k = mref(k->next, K64Array)) {
205 knp = kn; /* Remember previous element in list. */ 205 kp = k; /* Remember previous element in list. */
206 for (idx = 0; idx < kn->numk; idx++) { /* Search one array. */ 206 for (idx = 0; idx < k->numk; idx++) { /* Search one array. */
207 TValue *tv = &kn->k[idx]; 207 TValue *tv = &k->k[idx];
208 if (tv->u64 == nn) /* Needed for +-0/NaN/absmask. */ 208 if (tv->u64 == u64) /* Needed for +-0/NaN/absmask. */
209 return tv; 209 return tv;
210 } 210 }
211 } 211 }
212 /* Constant was not found, need to add it. */ 212 /* Constant was not found, need to add it. */
213 if (!(knp && knp->numk < LJ_MIN_KNUMSZ)) { /* Allocate a new array. */ 213 if (!(kp && kp->numk < LJ_MIN_K64SZ)) { /* Allocate a new array. */
214 KNumArray *nkn = lj_mem_newt(J->L, sizeof(KNumArray), KNumArray); 214 K64Array *kn = lj_mem_newt(J->L, sizeof(K64Array), K64Array);
215 setmref(nkn->next, NULL); 215 setmref(kn->next, NULL);
216 nkn->numk = 0; 216 kn->numk = 0;
217 if (knp) 217 if (kp)
218 setmref(knp->next, nkn); /* Chain to the end of the list. */ 218 setmref(kp->next, kn); /* Chain to the end of the list. */
219 else 219 else
220 setmref(J->knum, nkn); /* Link first array. */ 220 setmref(J->k64, kn); /* Link first array. */
221 knp = nkn; 221 kp = kn;
222 } 222 }
223 ntv = &knp->k[knp->numk++]; /* Add to current array. */ 223 ntv = &kp->k[kp->numk++]; /* Add to current array. */
224 ntv->u64 = nn; 224 ntv->u64 = u64;
225 return ntv; 225 return ntv;
226} 226}
227 227
228/* Intern FP constant, given by its address. */ 228/* Intern 64 bit constant, given by its address. */
229TRef lj_ir_knum_addr(jit_State *J, cTValue *tv) 229TRef lj_ir_k64(jit_State *J, IROp op, cTValue *tv)
230{ 230{
231 IRIns *ir, *cir = J->cur.ir; 231 IRIns *ir, *cir = J->cur.ir;
232 IRRef ref; 232 IRRef ref;
233 for (ref = J->chain[IR_KNUM]; ref; ref = cir[ref].prev) 233 IRType t = op == IR_KNUM ? IRT_NUM : IRT_I64;
234 if (ir_knum(&cir[ref]) == tv) 234 for (ref = J->chain[op]; ref; ref = cir[ref].prev)
235 if (ir_k64(&cir[ref]) == tv)
235 goto found; 236 goto found;
236 ref = ir_nextk(J); 237 ref = ir_nextk(J);
237 ir = IR(ref); 238 ir = IR(ref);
238 lua_assert(checkptr32(tv)); 239 lua_assert(checkptr32(tv));
239 setmref(ir->ptr, tv); 240 setmref(ir->ptr, tv);
240 ir->t.irt = IRT_NUM; 241 ir->t.irt = t;
241 ir->o = IR_KNUM; 242 ir->o = op;
242 ir->prev = J->chain[IR_KNUM]; 243 ir->prev = J->chain[op];
243 J->chain[IR_KNUM] = (IRRef1)ref; 244 J->chain[op] = (IRRef1)ref;
244found: 245found:
245 return TREF(ref, IRT_NUM); 246 return TREF(ref, t);
246} 247}
247 248
248/* Intern FP constant, given by its 64 bit pattern. */ 249/* Intern FP constant, given by its 64 bit pattern. */
249TRef lj_ir_knum_nn(jit_State *J, uint64_t nn) 250TRef lj_ir_knum_u64(jit_State *J, uint64_t u64)
251{
252 return lj_ir_k64(J, IR_KNUM, ir_k64_find(J, u64));
253}
254
255/* Intern 64 bit integer constant. */
256TRef lj_ir_kint64(jit_State *J, uint64_t u64)
250{ 257{
251 return lj_ir_knum_addr(J, ir_knum_find(J, nn)); 258 return lj_ir_k64(J, IR_KINT64, ir_k64_find(J, u64));
252} 259}
253 260
254/* Check whether a number is int and return it. -0 is NOT considered an int. */ 261/* Check whether a number is int and return it. -0 is NOT considered an int. */
@@ -373,6 +380,9 @@ void lj_ir_kvalue(lua_State *L, TValue *tv, const IRIns *ir)
373 } else if (irt_isnum(ir->t)) { 380 } else if (irt_isnum(ir->t)) {
374 lua_assert(ir->o == IR_KNUM); 381 lua_assert(ir->o == IR_KNUM);
375 setnumV(tv, ir_knum(ir)->n); 382 setnumV(tv, ir_knum(ir)->n);
383 } else if (irt_is64(ir->t)) {
384 lua_assert(ir->o == IR_KINT64);
385 setnumV(tv, (int64_t)ir_kint64(ir)->u64); /* NYI: use FFI int64_t. */
376 } else if (irt_ispri(ir->t)) { 386 } else if (irt_ispri(ir->t)) {
377 lua_assert(ir->o == IR_KPRI); 387 lua_assert(ir->o == IR_KPRI);
378 setitype(tv, irt_toitype(ir->t)); 388 setitype(tv, irt_toitype(ir->t));
diff --git a/src/lj_ir.h b/src/lj_ir.h
index 9d90d69f..b8ea0fa9 100644
--- a/src/lj_ir.h
+++ b/src/lj_ir.h
@@ -12,6 +12,24 @@
12 12
13/* IR instruction definition. Order matters, see below. */ 13/* IR instruction definition. Order matters, see below. */
14#define IRDEF(_) \ 14#define IRDEF(_) \
15 /* Guarded assertions. */ \
16 /* Must be properly aligned to flip opposites (^1) and (un)ordered (^4). */ \
17 _(LT, N , ref, ref) \
18 _(GE, N , ref, ref) \
19 _(LE, N , ref, ref) \
20 _(GT, N , ref, ref) \
21 \
22 _(ULT, N , ref, ref) \
23 _(UGE, N , ref, ref) \
24 _(ULE, N , ref, ref) \
25 _(UGT, N , ref, ref) \
26 \
27 _(EQ, C , ref, ref) \
28 _(NE, C , ref, ref) \
29 \
30 _(ABC, N , ref, ref) \
31 _(RETF, S , ref, ref) \
32 \
15 /* Miscellaneous ops. */ \ 33 /* Miscellaneous ops. */ \
16 _(NOP, N , ___, ___) \ 34 _(NOP, N , ___, ___) \
17 _(BASE, N , lit, lit) \ 35 _(BASE, N , lit, lit) \
@@ -26,26 +44,9 @@
26 _(KPTR, N , cst, ___) \ 44 _(KPTR, N , cst, ___) \
27 _(KNULL, N , cst, ___) \ 45 _(KNULL, N , cst, ___) \
28 _(KNUM, N , cst, ___) \ 46 _(KNUM, N , cst, ___) \
47 _(KINT64, N , cst, ___) \
29 _(KSLOT, N , ref, lit) \ 48 _(KSLOT, N , ref, lit) \
30 \ 49 \
31 /* Guarded assertions. */ \
32 /* Must be properly aligned to flip opposites (^1) and (un)ordered (^4). */ \
33 _(EQ, C , ref, ref) \
34 _(NE, C , ref, ref) \
35 \
36 _(ABC, N , ref, ref) \
37 _(RETF, S , ref, ref) \
38 \
39 _(LT, N , ref, ref) \
40 _(GE, N , ref, ref) \
41 _(LE, N , ref, ref) \
42 _(GT, N , ref, ref) \
43 \
44 _(ULT, N , ref, ref) \
45 _(UGE, N , ref, ref) \
46 _(ULE, N , ref, ref) \
47 _(UGT, N , ref, ref) \
48 \
49 /* Bit ops. */ \ 50 /* Bit ops. */ \
50 _(BNOT, N , ref, ___) \ 51 _(BNOT, N , ref, ___) \
51 _(BSWAP, N , ref, ___) \ 52 _(BSWAP, N , ref, ___) \
@@ -536,6 +537,9 @@ typedef union IRIns {
536#define ir_ktab(ir) (gco2tab(ir_kgc((ir)))) 537#define ir_ktab(ir) (gco2tab(ir_kgc((ir))))
537#define ir_kfunc(ir) (gco2func(ir_kgc((ir)))) 538#define ir_kfunc(ir) (gco2func(ir_kgc((ir))))
538#define ir_knum(ir) check_exp((ir)->o == IR_KNUM, mref((ir)->ptr, cTValue)) 539#define ir_knum(ir) check_exp((ir)->o == IR_KNUM, mref((ir)->ptr, cTValue))
540#define ir_kint64(ir) check_exp((ir)->o == IR_KINT64, mref((ir)->ptr,cTValue))
541#define ir_k64(ir) \
542 check_exp((ir)->o == IR_KNUM || (ir)->o == IR_KINT64, mref((ir)->ptr,cTValue))
539#define ir_kptr(ir) check_exp((ir)->o == IR_KPTR, mref((ir)->ptr, void)) 543#define ir_kptr(ir) check_exp((ir)->o == IR_KPTR, mref((ir)->ptr, void))
540 544
541LJ_STATIC_ASSERT((int)IRT_GUARD == (int)IRM_W); 545LJ_STATIC_ASSERT((int)IRT_GUARD == (int)IRM_W);
diff --git a/src/lj_iropt.h b/src/lj_iropt.h
index 00bb2496..c05040d6 100644
--- a/src/lj_iropt.h
+++ b/src/lj_iropt.h
@@ -39,10 +39,11 @@ static LJ_AINLINE IRRef lj_ir_nextins(jit_State *J)
39 39
40/* Interning of constants. */ 40/* Interning of constants. */
41LJ_FUNC TRef LJ_FASTCALL lj_ir_kint(jit_State *J, int32_t k); 41LJ_FUNC TRef LJ_FASTCALL lj_ir_kint(jit_State *J, int32_t k);
42LJ_FUNC void lj_ir_knum_freeall(jit_State *J); 42LJ_FUNC void lj_ir_k64_freeall(jit_State *J);
43LJ_FUNC TRef lj_ir_knum_addr(jit_State *J, cTValue *tv); 43LJ_FUNC TRef lj_ir_k64(jit_State *J, IROp op, cTValue *tv);
44LJ_FUNC TRef lj_ir_knum_nn(jit_State *J, uint64_t nn); 44LJ_FUNC TRef lj_ir_knum_u64(jit_State *J, uint64_t u64);
45LJ_FUNC TRef lj_ir_knumint(jit_State *J, lua_Number n); 45LJ_FUNC TRef lj_ir_knumint(jit_State *J, lua_Number n);
46LJ_FUNC TRef lj_ir_kint64(jit_State *J, uint64_t u64);
46LJ_FUNC TRef lj_ir_kgc(jit_State *J, GCobj *o, IRType t); 47LJ_FUNC TRef lj_ir_kgc(jit_State *J, GCobj *o, IRType t);
47LJ_FUNC TRef lj_ir_kptr(jit_State *J, void *ptr); 48LJ_FUNC TRef lj_ir_kptr(jit_State *J, void *ptr);
48LJ_FUNC TRef lj_ir_knull(jit_State *J, IRType t); 49LJ_FUNC TRef lj_ir_knull(jit_State *J, IRType t);
@@ -52,7 +53,7 @@ static LJ_AINLINE TRef lj_ir_knum(jit_State *J, lua_Number n)
52{ 53{
53 TValue tv; 54 TValue tv;
54 tv.n = n; 55 tv.n = n;
55 return lj_ir_knum_nn(J, tv.u64); 56 return lj_ir_knum_u64(J, tv.u64);
56} 57}
57 58
58#define lj_ir_kstr(J, str) lj_ir_kgc(J, obj2gco((str)), IRT_STR) 59#define lj_ir_kstr(J, str) lj_ir_kgc(J, obj2gco((str)), IRT_STR)
@@ -60,13 +61,13 @@ static LJ_AINLINE TRef lj_ir_knum(jit_State *J, lua_Number n)
60#define lj_ir_kfunc(J, func) lj_ir_kgc(J, obj2gco((func)), IRT_FUNC) 61#define lj_ir_kfunc(J, func) lj_ir_kgc(J, obj2gco((func)), IRT_FUNC)
61 62
62/* Special FP constants. */ 63/* Special FP constants. */
63#define lj_ir_knum_zero(J) lj_ir_knum_nn(J, U64x(00000000,00000000)) 64#define lj_ir_knum_zero(J) lj_ir_knum_u64(J, U64x(00000000,00000000))
64#define lj_ir_knum_one(J) lj_ir_knum_nn(J, U64x(3ff00000,00000000)) 65#define lj_ir_knum_one(J) lj_ir_knum_u64(J, U64x(3ff00000,00000000))
65#define lj_ir_knum_tobit(J) lj_ir_knum_nn(J, U64x(43380000,00000000)) 66#define lj_ir_knum_tobit(J) lj_ir_knum_u64(J, U64x(43380000,00000000))
66 67
67/* Special 128 bit SIMD constants. */ 68/* Special 128 bit SIMD constants. */
68#define lj_ir_knum_abs(J) lj_ir_knum_addr(J, LJ_KSIMD(J, LJ_KSIMD_ABS)) 69#define lj_ir_knum_abs(J) lj_ir_k64(J, IR_KNUM, LJ_KSIMD(J, LJ_KSIMD_ABS))
69#define lj_ir_knum_neg(J) lj_ir_knum_addr(J, LJ_KSIMD(J, LJ_KSIMD_NEG)) 70#define lj_ir_knum_neg(J) lj_ir_k64(J, IR_KNUM, LJ_KSIMD(J, LJ_KSIMD_NEG))
70 71
71/* Access to constants. */ 72/* Access to constants. */
72LJ_FUNC void lj_ir_kvalue(lua_State *L, TValue *tv, const IRIns *ir); 73LJ_FUNC void lj_ir_kvalue(lua_State *L, TValue *tv, const IRIns *ir);
diff --git a/src/lj_jit.h b/src/lj_jit.h
index d309f828..c5902a61 100644
--- a/src/lj_jit.h
+++ b/src/lj_jit.h
@@ -271,7 +271,7 @@ typedef struct jit_State {
271 int32_t framedepth; /* Current frame depth. */ 271 int32_t framedepth; /* Current frame depth. */
272 int32_t retdepth; /* Return frame depth (count of RETF). */ 272 int32_t retdepth; /* Return frame depth (count of RETF). */
273 273
274 MRef knum; /* Pointer to chained array of KNUM constants. */ 274 MRef k64; /* Pointer to chained array of 64 bit constants. */
275 TValue ksimd[LJ_KSIMD__MAX*2+1]; /* 16 byte aligned SIMD constants. */ 275 TValue ksimd[LJ_KSIMD__MAX*2+1]; /* 16 byte aligned SIMD constants. */
276 276
277 IRIns *irbuf; /* Temp. IR instruction buffer. Biased with REF_BIAS. */ 277 IRIns *irbuf; /* Temp. IR instruction buffer. Biased with REF_BIAS. */
diff --git a/src/lj_opt_mem.c b/src/lj_opt_mem.c
index ee573cad..9b96d66e 100644
--- a/src/lj_opt_mem.c
+++ b/src/lj_opt_mem.c
@@ -188,7 +188,7 @@ static TRef fwd_ahload(jit_State *J, IRRef xref)
188 tv = lj_tab_get(J->L, ir_ktab(IR(ir->op1)), &keyv); 188 tv = lj_tab_get(J->L, ir_ktab(IR(ir->op1)), &keyv);
189 lua_assert(itype2irt(tv) == irt_type(fins->t)); 189 lua_assert(itype2irt(tv) == irt_type(fins->t));
190 if (irt_isnum(fins->t)) 190 if (irt_isnum(fins->t))
191 return lj_ir_knum_nn(J, tv->u64); 191 return lj_ir_knum_u64(J, tv->u64);
192 else 192 else
193 return lj_ir_kstr(J, strV(tv)); 193 return lj_ir_kstr(J, strV(tv));
194 } 194 }
diff --git a/src/lj_record.c b/src/lj_record.c
index de3f6a64..967022f5 100644
--- a/src/lj_record.c
+++ b/src/lj_record.c
@@ -1863,7 +1863,8 @@ static void rec_setup_side(jit_State *J, GCtrace *T)
1863 case IR_KPRI: tr = TREF_PRI(irt_type(ir->t)); break; 1863 case IR_KPRI: tr = TREF_PRI(irt_type(ir->t)); break;
1864 case IR_KINT: tr = lj_ir_kint(J, ir->i); break; 1864 case IR_KINT: tr = lj_ir_kint(J, ir->i); break;
1865 case IR_KGC: tr = lj_ir_kgc(J, ir_kgc(ir), irt_t(ir->t)); break; 1865 case IR_KGC: tr = lj_ir_kgc(J, ir_kgc(ir), irt_t(ir->t)); break;
1866 case IR_KNUM: tr = lj_ir_knum_addr(J, ir_knum(ir)); break; 1866 case IR_KNUM: tr = lj_ir_k64(J, IR_KNUM, ir_knum(ir)); break;
1867 case IR_KINT64: tr = lj_ir_k64(J, IR_KINT64, ir_kint64(ir)); break;
1867 case IR_KPTR: tr = lj_ir_kptr(J, ir_kptr(ir)); break; /* Continuation. */ 1868 case IR_KPTR: tr = lj_ir_kptr(J, ir_kptr(ir)); break; /* Continuation. */
1868 /* Inherited SLOADs don't need a guard or type check. */ 1869 /* Inherited SLOADs don't need a guard or type check. */
1869 case IR_SLOAD: 1870 case IR_SLOAD:
diff --git a/src/lj_trace.c b/src/lj_trace.c
index 8589a9e9..b9439c9f 100644
--- a/src/lj_trace.c
+++ b/src/lj_trace.c
@@ -306,7 +306,7 @@ void lj_trace_freestate(global_State *g)
306 } 306 }
307#endif 307#endif
308 lj_mcode_free(J); 308 lj_mcode_free(J);
309 lj_ir_knum_freeall(J); 309 lj_ir_k64_freeall(J);
310 lj_mem_freevec(g, J->snapmapbuf, J->sizesnapmap, SnapEntry); 310 lj_mem_freevec(g, J->snapmapbuf, J->sizesnapmap, SnapEntry);
311 lj_mem_freevec(g, J->snapbuf, J->sizesnap, SnapShot); 311 lj_mem_freevec(g, J->snapbuf, J->sizesnap, SnapShot);
312 lj_mem_freevec(g, J->irbuf + J->irbotlim, J->irtoplim - J->irbotlim, IRIns); 312 lj_mem_freevec(g, J->irbuf + J->irbotlim, J->irtoplim - J->irbotlim, IRIns);