From d4da9ff55ef01019c55246cd41ccd7510505cfe1 Mon Sep 17 00:00:00 2001 From: Mike Pall Date: Wed, 22 Jun 2011 20:38:07 +0200 Subject: [PATCH] x86/x64: Fix register allocation for variable shifts. --- src/lj_asm_x86.h | 18 ++++++++++-------- 1 file changed, 10 insertions(+), 8 deletions(-) diff --git a/src/lj_asm_x86.h b/src/lj_asm_x86.h index ba28792d..da818c68 100644 --- a/src/lj_asm_x86.h +++ b/src/lj_asm_x86.h @@ -1878,15 +1878,17 @@ static void asm_bitshift(ASMState *as, IRIns *ir, x86Shift xs) default: emit_shifti(as, REX_64IR(ir, xs), dest, shift); break; } } else { /* Variable shifts implicitly use register cl (i.e. ecx). */ - RegSet allow = rset_exclude(RSET_GPR, RID_ECX); - Reg right = irr->r; - if (ra_noreg(right)) { - right = ra_allocref(as, rref, RID2RSET(RID_ECX)); - } else if (right != RID_ECX) { - rset_clear(allow, right); - ra_scratch(as, RID2RSET(RID_ECX)); + Reg right; + dest = ra_dest(as, ir, rset_exclude(RSET_GPR, RID_ECX)); + if (dest == RID_ECX) { + dest = ra_scratch(as, rset_exclude(RSET_GPR, RID_ECX)); + emit_rr(as, XO_MOV, RID_ECX, dest); } - dest = ra_dest(as, ir, allow); + right = irr->r; + if (ra_noreg(right)) + right = ra_allocref(as, rref, RID2RSET(RID_ECX)); + else if (right != RID_ECX) + ra_scratch(as, RID2RSET(RID_ECX)); emit_rr(as, XO_SHIFTcl, REX_64IR(ir, xs), dest); if (right != RID_ECX) { ra_noweak(as, right);