diff options
Diffstat (limited to 'src/lj_asm.c')
-rw-r--r-- | src/lj_asm.c | 44 |
1 files changed, 23 insertions, 21 deletions
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. */ |
669 | static void ra_movrr(ASMState *as, IRIns *ir, Reg r1, Reg r2) | 669 | static 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 | } |