diff options
Diffstat (limited to 'src/lj_asm_ppc.h')
-rw-r--r-- | src/lj_asm_ppc.h | 27 |
1 files changed, 17 insertions, 10 deletions
diff --git a/src/lj_asm_ppc.h b/src/lj_asm_ppc.h index 6555312d..8e9a92a4 100644 --- a/src/lj_asm_ppc.h +++ b/src/lj_asm_ppc.h | |||
@@ -840,23 +840,30 @@ static void asm_hrefk(ASMState *as, IRIns *ir) | |||
840 | static void asm_uref(ASMState *as, IRIns *ir) | 840 | static void asm_uref(ASMState *as, IRIns *ir) |
841 | { | 841 | { |
842 | Reg dest = ra_dest(as, ir, RSET_GPR); | 842 | Reg dest = ra_dest(as, ir, RSET_GPR); |
843 | if (irref_isk(ir->op1)) { | 843 | int guarded = (irt_t(ir->t) & (IRT_GUARD|IRT_TYPE)) == (IRT_GUARD|IRT_PGC); |
844 | if (irref_isk(ir->op1) && !guarded) { | ||
844 | GCfunc *fn = ir_kfunc(IR(ir->op1)); | 845 | GCfunc *fn = ir_kfunc(IR(ir->op1)); |
845 | MRef *v = &gcref(fn->l.uvptr[(ir->op2 >> 8)])->uv.v; | 846 | MRef *v = &gcref(fn->l.uvptr[(ir->op2 >> 8)])->uv.v; |
846 | emit_lsptr(as, PPCI_LWZ, dest, v, RSET_GPR); | 847 | emit_lsptr(as, PPCI_LWZ, dest, v, RSET_GPR); |
847 | } else { | 848 | } else { |
848 | Reg uv = ra_scratch(as, RSET_GPR); | 849 | if (guarded) { |
849 | Reg func = ra_alloc1(as, ir->op1, RSET_GPR); | 850 | asm_guardcc(as, ir->o == IR_UREFC ? CC_NE : CC_EQ); |
850 | if (ir->o == IR_UREFC) { | ||
851 | asm_guardcc(as, CC_NE); | ||
852 | emit_ai(as, PPCI_CMPWI, RID_TMP, 1); | 851 | emit_ai(as, PPCI_CMPWI, RID_TMP, 1); |
853 | emit_tai(as, PPCI_ADDI, dest, uv, (int32_t)offsetof(GCupval, tv)); | 852 | } |
854 | emit_tai(as, PPCI_LBZ, RID_TMP, uv, (int32_t)offsetof(GCupval, closed)); | 853 | if (ir->o == IR_UREFC) |
854 | emit_tai(as, PPCI_ADDI, dest, dest, (int32_t)offsetof(GCupval, tv)); | ||
855 | else | ||
856 | emit_tai(as, PPCI_LWZ, dest, dest, (int32_t)offsetof(GCupval, v)); | ||
857 | if (guarded) | ||
858 | emit_tai(as, PPCI_LBZ, RID_TMP, dest, (int32_t)offsetof(GCupval, closed)); | ||
859 | if (irref_isk(ir->op1)) { | ||
860 | GCfunc *fn = ir_kfunc(IR(ir->op1)); | ||
861 | int32_t k = (int32_t)gcrefu(fn->l.uvptr[(ir->op2 >> 8)]); | ||
862 | emit_loadi(as, dest, k); | ||
855 | } else { | 863 | } else { |
856 | emit_tai(as, PPCI_LWZ, dest, uv, (int32_t)offsetof(GCupval, v)); | 864 | emit_tai(as, PPCI_LWZ, dest, ra_alloc1(as, ir->op1, RSET_GPR), |
865 | (int32_t)offsetof(GCfuncL, uvptr) + 4*(int32_t)(ir->op2 >> 8)); | ||
857 | } | 866 | } |
858 | emit_tai(as, PPCI_LWZ, uv, func, | ||
859 | (int32_t)offsetof(GCfuncL, uvptr) + 4*(int32_t)(ir->op2 >> 8)); | ||
860 | } | 867 | } |
861 | } | 868 | } |
862 | 869 | ||