aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMike Pall <mike>2010-12-05 19:49:29 +0100
committerMike Pall <mike>2010-12-05 21:01:08 +0100
commitb1fb71fb981c464868e6bc669363658a98ecbd9e (patch)
tree88fe921691d957a40c10181c8f13de201a924d31
parent6a7605ec85a6e5f91fc539a9e5c18659d73f3530 (diff)
downloadluajit-b1fb71fb981c464868e6bc669363658a98ecbd9e.tar.gz
luajit-b1fb71fb981c464868e6bc669363658a98ecbd9e.tar.bz2
luajit-b1fb71fb981c464868e6bc669363658a98ecbd9e.zip
Cleanup 64 bit IR type handling.
-rw-r--r--lib/dump.lua12
-rw-r--r--src/lj_asm.c44
-rw-r--r--src/lj_def.h1
-rw-r--r--src/lj_ir.h21
4 files changed, 48 insertions, 30 deletions
diff --git a/lib/dump.lua b/lib/dump.lua
index f567d3d7..3c726484 100644
--- a/lib/dump.lua
+++ b/lib/dump.lua
@@ -129,20 +129,23 @@ local irtype_text = {
129 "tru", 129 "tru",
130 "lud", 130 "lud",
131 "str", 131 "str",
132 "ptr", 132 "p32",
133 "thr", 133 "thr",
134 "pro", 134 "pro",
135 "fun", 135 "fun",
136 "t09", 136 "p64",
137 "cdt", 137 "cdt",
138 "tab", 138 "tab",
139 "udt", 139 "udt",
140 "num", 140 "num",
141 "int",
142 "i8 ", 141 "i8 ",
143 "u8 ", 142 "u8 ",
144 "i16", 143 "i16",
145 "u16", 144 "u16",
145 "int",
146 "u32",
147 "i64",
148 "u64",
146} 149}
147 150
148local colortype_ansi = { 151local colortype_ansi = {
@@ -165,6 +168,9 @@ local colortype_ansi = {
165 "\027[35m%s\027[m", 168 "\027[35m%s\027[m",
166 "\027[35m%s\027[m", 169 "\027[35m%s\027[m",
167 "\027[35m%s\027[m", 170 "\027[35m%s\027[m",
171 "\027[35m%s\027[m",
172 "\027[35m%s\027[m",
173 "\027[35m%s\027[m",
168} 174}
169 175
170local function colorize_text(s, t) 176local function colorize_text(s, t)
diff --git a/src/lj_asm.c b/src/lj_asm.c
index 0dfc7f04..6bb2b8c6 100644
--- a/src/lj_asm.c
+++ b/src/lj_asm.c
@@ -631,7 +631,7 @@ static int32_t ra_spill(ASMState *as, IRIns *ir)
631{ 631{
632 int32_t slot = ir->s; 632 int32_t slot = ir->s;
633 if (!ra_hasspill(slot)) { 633 if (!ra_hasspill(slot)) {
634 if (irt_isnum(ir->t) || (LJ_64 && irt_islightud(ir->t))) { 634 if (irt_is64(ir->t)) {
635 slot = as->evenspill; 635 slot = as->evenspill;
636 as->evenspill += 2; 636 as->evenspill += 2;
637 } else if (as->oddspill) { 637 } else if (as->oddspill) {
@@ -661,14 +661,14 @@ static Reg ra_releasetmp(ASMState *as, IRRef ref)
661 return r; 661 return r;
662} 662}
663 663
664/* Use 64 bit operations to handle 64 bit lightuserdata. */ 664/* Use 64 bit operations to handle 64 bit IR types. */
665#define REX_64LU(ir, r) \ 665#define REX_64IR(ir, r) \
666 ((r) | ((LJ_64 && irt_islightud((ir)->t)) ? REX_64 : 0)) 666 ((r) | ((LJ_64 && irt_is64((ir)->t)) ? REX_64 : 0))
667 667
668/* Generic move between two regs. */ 668/* Generic move between two regs. */
669static void ra_movrr(ASMState *as, IRIns *ir, Reg r1, Reg r2) 669static void ra_movrr(ASMState *as, IRIns *ir, Reg r1, Reg r2)
670{ 670{
671 emit_rr(as, r1 < RID_MAX_GPR ? XO_MOV : XMM_MOVRR(as), REX_64LU(ir, r1), r2); 671 emit_rr(as, r1 < RID_MAX_GPR ? XO_MOV : XMM_MOVRR(as), REX_64IR(ir, r1), r2);
672} 672}
673 673
674/* Restore a register (marked as free). Rematerialize or force a spill. */ 674/* Restore a register (marked as free). Rematerialize or force a spill. */
@@ -687,7 +687,7 @@ static Reg ra_restore(ASMState *as, IRRef ref)
687 ra_modified(as, r); 687 ra_modified(as, r);
688 RA_DBGX((as, "restore $i $r", ir, r)); 688 RA_DBGX((as, "restore $i $r", ir, r));
689 emit_rmro(as, r < RID_MAX_GPR ? XO_MOV : XMM_MOVRM(as), 689 emit_rmro(as, r < RID_MAX_GPR ? XO_MOV : XMM_MOVRM(as),
690 REX_64LU(ir, r), RID_ESP, ofs); 690 REX_64IR(ir, r), RID_ESP, ofs);
691 } 691 }
692 return r; 692 return r;
693 } 693 }
@@ -698,7 +698,7 @@ static void ra_save(ASMState *as, IRIns *ir, Reg r)
698{ 698{
699 RA_DBGX((as, "save $i $r", ir, r)); 699 RA_DBGX((as, "save $i $r", ir, r));
700 emit_rmro(as, r < RID_MAX_GPR ? XO_MOVto : XO_MOVSDto, 700 emit_rmro(as, r < RID_MAX_GPR ? XO_MOVto : XO_MOVSDto,
701 REX_64LU(ir, r), RID_ESP, sps_scale(ir->s)); 701 REX_64IR(ir, r), RID_ESP, sps_scale(ir->s));
702} 702}
703 703
704#define MINCOST(r) \ 704#define MINCOST(r) \
@@ -1397,7 +1397,7 @@ static void asm_gencall(ASMState *as, const CCallInfo *ci, IRRef *args)
1397 lj_trace_err(as->J, LJ_TRERR_NYICOAL); 1397 lj_trace_err(as->J, LJ_TRERR_NYICOAL);
1398 r = ra_alloc1(as, args[n], allow & RSET_GPR); 1398 r = ra_alloc1(as, args[n], allow & RSET_GPR);
1399 allow &= ~RID2RSET(r); 1399 allow &= ~RID2RSET(r);
1400 emit_movtomro(as, REX_64LU(ir, r), RID_ESP, ofs); 1400 emit_movtomro(as, REX_64IR(ir, r), RID_ESP, ofs);
1401 } 1401 }
1402 ofs += sizeof(intptr_t); 1402 ofs += sizeof(intptr_t);
1403 } 1403 }
@@ -1849,7 +1849,7 @@ static void asm_newref(ASMState *as, IRIns *ir)
1849 /* Otherwise use g->tmptv to hold the TValue. */ 1849 /* Otherwise use g->tmptv to hold the TValue. */
1850 if (!irref_isk(ir->op2)) { 1850 if (!irref_isk(ir->op2)) {
1851 Reg src = ra_alloc1(as, ir->op2, rset_exclude(RSET_GPR, tmp)); 1851 Reg src = ra_alloc1(as, ir->op2, rset_exclude(RSET_GPR, tmp));
1852 emit_movtomro(as, REX_64LU(irkey, src), tmp, 0); 1852 emit_movtomro(as, REX_64IR(irkey, src), tmp, 0);
1853 } else if (!irt_ispri(irkey->t)) { 1853 } else if (!irt_ispri(irkey->t)) {
1854 emit_movmroi(as, tmp, 0, irkey->i); 1854 emit_movmroi(as, tmp, 0, irkey->i);
1855 } 1855 }
@@ -1918,13 +1918,11 @@ static void asm_fxload(ASMState *as, IRIns *ir)
1918 case IRT_U8: xo = XO_MOVZXb; break; 1918 case IRT_U8: xo = XO_MOVZXb; break;
1919 case IRT_I16: xo = XO_MOVSXw; break; 1919 case IRT_I16: xo = XO_MOVSXw; break;
1920 case IRT_U16: xo = XO_MOVZXw; break; 1920 case IRT_U16: xo = XO_MOVZXw; break;
1921#if LJ_64
1922 case IRT_LIGHTUD:
1923 dest |= REX_64;
1924 /* fallthrough */
1925#endif
1926 default: 1921 default:
1927 lua_assert(irt_isint(ir->t) || irt_isaddr(ir->t)); 1922 if (LJ_64 && irt_is64(ir->t))
1923 dest |= REX_64;
1924 else
1925 lua_assert(irt_isint(ir->t) || irt_isu32(ir->t) || irt_isaddr(ir->t));
1928 xo = XO_MOV; 1926 xo = XO_MOV;
1929 break; 1927 break;
1930 } 1928 }
@@ -1938,6 +1936,7 @@ static void asm_fstore(ASMState *as, IRIns *ir)
1938 /* The IRT_I16/IRT_U16 stores should never be simplified for constant 1936 /* The IRT_I16/IRT_U16 stores should never be simplified for constant
1939 ** values since mov word [mem], imm16 has a length-changing prefix. 1937 ** values since mov word [mem], imm16 has a length-changing prefix.
1940 */ 1938 */
1939 lua_assert(!(irref_isk(ir->op2) && irt_is64(ir->t))); /* NYI: KINT64. */
1941 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)) {
1942 RegSet allow8 = (irt_isi8(ir->t) || irt_isu8(ir->t)) ? RSET_GPR8 : RSET_GPR; 1941 RegSet allow8 = (irt_isi8(ir->t) || irt_isu8(ir->t)) ? RSET_GPR8 : RSET_GPR;
1943 src = ra_alloc1(as, ir->op2, allow8); 1942 src = ra_alloc1(as, ir->op2, allow8);
@@ -1953,7 +1952,10 @@ static void asm_fstore(ASMState *as, IRIns *ir)
1953 case IRT_LIGHTUD: lua_assert(0); /* NYI: mask 64 bit lightuserdata. */ 1952 case IRT_LIGHTUD: lua_assert(0); /* NYI: mask 64 bit lightuserdata. */
1954#endif 1953#endif
1955 default: 1954 default:
1956 lua_assert(irt_isint(ir->t) || irt_isaddr(ir->t)); 1955 if (LJ_64 && irt_is64(ir->t))
1956 src |= REX_64;
1957 else
1958 lua_assert(irt_isint(ir->t) || irt_isu32(ir->t) || irt_isaddr(ir->t));
1957 xo = XO_MOVto; 1959 xo = XO_MOVto;
1958 break; 1960 break;
1959 } 1961 }
@@ -1963,7 +1965,7 @@ static void asm_fstore(ASMState *as, IRIns *ir)
1963 emit_i8(as, IR(ir->op2)->i); 1965 emit_i8(as, IR(ir->op2)->i);
1964 emit_mrm(as, XO_MOVmib, 0, RID_MRM); 1966 emit_mrm(as, XO_MOVmib, 0, RID_MRM);
1965 } else { 1967 } else {
1966 lua_assert(irt_isint(ir->t) || irt_isaddr(ir->t)); 1968 lua_assert(irt_isint(ir->t) || irt_isu32(ir->t) || irt_isaddr(ir->t));
1967 emit_i32(as, IR(ir->op2)->i); 1969 emit_i32(as, IR(ir->op2)->i);
1968 emit_mrm(as, XO_MOVmi, 0, RID_MRM); 1970 emit_mrm(as, XO_MOVmi, 0, RID_MRM);
1969 } 1971 }
@@ -2664,7 +2666,7 @@ static void asm_comp_(ASMState *as, IRIns *ir, int cc)
2664 asm_guardcc(as, cc); 2666 asm_guardcc(as, cc);
2665 if (usetest && left != RID_MRM) { 2667 if (usetest && left != RID_MRM) {
2666 /* Use test r,r instead of cmp r,0. */ 2668 /* Use test r,r instead of cmp r,0. */
2667 emit_rr(as, XO_TEST, REX_64LU(ir, left), left); 2669 emit_rr(as, XO_TEST, REX_64IR(ir, left), left);
2668 if (irl+1 == ir) /* Referencing previous ins? */ 2670 if (irl+1 == ir) /* Referencing previous ins? */
2669 as->testmcp = as->mcp; /* Set flag to drop test r,r if possible. */ 2671 as->testmcp = as->mcp; /* Set flag to drop test r,r if possible. */
2670 } else { 2672 } else {
@@ -2683,7 +2685,7 @@ static void asm_comp_(ASMState *as, IRIns *ir, int cc)
2683 Reg left = ra_alloc1(as, lref, RSET_GPR); 2685 Reg left = ra_alloc1(as, lref, RSET_GPR);
2684 Reg right = asm_fuseload(as, rref, rset_exclude(RSET_GPR, left)); 2686 Reg right = asm_fuseload(as, rref, rset_exclude(RSET_GPR, left));
2685 asm_guardcc(as, cc); 2687 asm_guardcc(as, cc);
2686 emit_mrm(as, XO_CMP, REX_64LU(ir, left), right); 2688 emit_mrm(as, XO_CMP, REX_64IR(ir, left), right);
2687 } 2689 }
2688 } 2690 }
2689} 2691}
@@ -2762,7 +2764,7 @@ static void asm_stack_restore(ASMState *as, SnapShot *snap)
2762 lua_assert(irt_ispri(ir->t) || irt_isaddr(ir->t)); 2764 lua_assert(irt_ispri(ir->t) || irt_isaddr(ir->t));
2763 if (!irref_isk(ref)) { 2765 if (!irref_isk(ref)) {
2764 Reg src = ra_alloc1(as, ref, rset_exclude(RSET_GPR, RID_BASE)); 2766 Reg src = ra_alloc1(as, ref, rset_exclude(RSET_GPR, RID_BASE));
2765 emit_movtomro(as, REX_64LU(ir, src), RID_BASE, ofs); 2767 emit_movtomro(as, REX_64IR(ir, src), RID_BASE, ofs);
2766 } else if (!irt_ispri(ir->t)) { 2768 } else if (!irt_ispri(ir->t)) {
2767 emit_movmroi(as, RID_BASE, ofs, ir->i); 2769 emit_movmroi(as, RID_BASE, ofs, ir->i);
2768 } 2770 }
@@ -3189,7 +3191,7 @@ static void asm_head_side(ASMState *as)
3189 int32_t ofs = sps_scale(regsp_spill(rs)); 3191 int32_t ofs = sps_scale(regsp_spill(rs));
3190 ra_free(as, r); 3192 ra_free(as, r);
3191 emit_rmro(as, r < RID_MAX_GPR ? XO_MOV : XMM_MOVRM(as), 3193 emit_rmro(as, r < RID_MAX_GPR ? XO_MOV : XMM_MOVRM(as),
3192 REX_64LU(ir, r), RID_ESP, ofs); 3194 REX_64IR(ir, r), RID_ESP, ofs);
3193 checkmclim(as); 3195 checkmclim(as);
3194 } 3196 }
3195 } 3197 }
diff --git a/src/lj_def.h b/src/lj_def.h
index bc3ae937..074090af 100644
--- a/src/lj_def.h
+++ b/src/lj_def.h
@@ -89,6 +89,7 @@ typedef unsigned __int32 uintptr_t;
89#define checku8(x) ((x) == (int32_t)(uint8_t)(x)) 89#define checku8(x) ((x) == (int32_t)(uint8_t)(x))
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 checkptr32(x) ((uintptr_t)(x) == (uint32_t)(uintptr_t)(x)) 93#define checkptr32(x) ((uintptr_t)(x) == (uint32_t)(uintptr_t)(x))
93 94
94/* Every half-decent C compiler transforms this into a rotate instruction. */ 95/* Every half-decent C compiler transforms this into a rotate instruction. */
diff --git a/src/lj_ir.h b/src/lj_ir.h
index 123d87c8..9d90d69f 100644
--- a/src/lj_ir.h
+++ b/src/lj_ir.h
@@ -315,7 +315,7 @@ typedef enum {
315 IRT_THREAD, 315 IRT_THREAD,
316 IRT_PROTO, 316 IRT_PROTO,
317 IRT_FUNC, 317 IRT_FUNC,
318 IRT_9, /* Unused (map of LJ_TTRACE). */ 318 IRT_P64, /* IRT_P64 never escapes the IR (map of LJ_TTRACE). */
319 IRT_CDATA, 319 IRT_CDATA,
320 IRT_TAB, 320 IRT_TAB,
321 IRT_UDATA, 321 IRT_UDATA,
@@ -325,12 +325,15 @@ typedef enum {
325 ** a TValue after implicit or explicit conversion (TONUM). Their types 325 ** a TValue after implicit or explicit conversion (TONUM). Their types
326 ** must be contiguous and next to IRT_NUM (see the typerange macros below). 326 ** must be contiguous and next to IRT_NUM (see the typerange macros below).
327 */ 327 */
328 IRT_INT,
329 IRT_I8, 328 IRT_I8,
330 IRT_U8, 329 IRT_U8,
331 IRT_I16, 330 IRT_I16,
332 IRT_U16, 331 IRT_U16,
333 /* There is room for 13 more types. */ 332 IRT_INT,
333 IRT_U32,
334 IRT_I64,
335 IRT_U64,
336 /* There is room for 10 more types. */
334 337
335 /* Additional flags. */ 338 /* Additional flags. */
336 IRT_MARK = 0x20, /* Marker for misc. purposes. */ 339 IRT_MARK = 0x20, /* Marker for misc. purposes. */
@@ -370,11 +373,17 @@ typedef struct IRType1 { uint8_t irt; } IRType1;
370#define irt_isu8(t) (irt_type(t) == IRT_U8) 373#define irt_isu8(t) (irt_type(t) == IRT_U8)
371#define irt_isi16(t) (irt_type(t) == IRT_I16) 374#define irt_isi16(t) (irt_type(t) == IRT_I16)
372#define irt_isu16(t) (irt_type(t) == IRT_U16) 375#define irt_isu16(t) (irt_type(t) == IRT_U16)
376#define irt_isu32(t) (irt_type(t) == IRT_U32)
373 377
374#define irt_isinteger(t) (irt_typerange((t), IRT_INT, IRT_U16)) 378#define irt_isinteger(t) (irt_typerange((t), IRT_I8, IRT_INT))
375#define irt_isgcv(t) (irt_typerange((t), IRT_STR, IRT_UDATA)) 379#define irt_isgcv(t) (irt_typerange((t), IRT_STR, IRT_UDATA))
376#define irt_isaddr(t) (irt_typerange((t), IRT_LIGHTUD, IRT_UDATA)) 380#define irt_isaddr(t) (irt_typerange((t), IRT_LIGHTUD, IRT_UDATA))
377 381
382#define IRT_IS64 \
383 ((1u<<IRT_NUM) | (1u<<IRT_I64) | (1u<<IRT_U64) | (1u<<IRT_P64) | \
384 (LJ_64 ? (1u<<IRT_LIGHTUD) : 0))
385#define irt_is64(t) ((IRT_IS64 >> irt_type(t)) & 1)
386
378static LJ_AINLINE IRType itype2irt(const TValue *tv) 387static LJ_AINLINE IRType itype2irt(const TValue *tv)
379{ 388{
380 if (tvisnum(tv)) 389 if (tvisnum(tv))
@@ -469,8 +478,8 @@ typedef uint32_t TRef;
469#define tref_isbool(tr) (tref_typerange((tr), IRT_FALSE, IRT_TRUE)) 478#define tref_isbool(tr) (tref_typerange((tr), IRT_FALSE, IRT_TRUE))
470#define tref_ispri(tr) (tref_typerange((tr), IRT_NIL, IRT_TRUE)) 479#define tref_ispri(tr) (tref_typerange((tr), IRT_NIL, IRT_TRUE))
471#define tref_istruecond(tr) (!tref_typerange((tr), IRT_NIL, IRT_FALSE)) 480#define tref_istruecond(tr) (!tref_typerange((tr), IRT_NIL, IRT_FALSE))
472#define tref_isinteger(tr) (tref_typerange((tr), IRT_INT, IRT_U16)) 481#define tref_isinteger(tr) (tref_typerange((tr), IRT_I8, IRT_INT))
473#define tref_isnumber(tr) (tref_typerange((tr), IRT_NUM, IRT_U16)) 482#define tref_isnumber(tr) (tref_typerange((tr), IRT_NUM, IRT_INT))
474#define tref_isnumber_str(tr) (tref_isnumber((tr)) || tref_isstr((tr))) 483#define tref_isnumber_str(tr) (tref_isnumber((tr)) || tref_isstr((tr)))
475#define tref_isgcv(tr) (tref_typerange((tr), IRT_STR, IRT_UDATA)) 484#define tref_isgcv(tr) (tref_typerange((tr), IRT_STR, IRT_UDATA))
476 485