nebius/SWE-rebench-V2-PRs huggingface dataset:
Repository: tetratelabs/wazero
Pull request #1740 (2023-10-01 07:22:45)

wazevo: fix simd bit shift test temp reg usage
- continues #1496 
- addresses an incorrect usage of registers in #1738, removes useless instruction


Patch:
diff --git a/internal/engine/wazevo/backend/isa/arm64/lower_instr.go b/internal/engine/wazevo/backend/isa/arm64/lower_instr.go
index 9e15a7d8..236e72e7 100644
--- a/internal/engine/wazevo/backend/isa/arm64/lower_instr.go
+++ b/internal/engine/wazevo/backend/isa/arm64/lower_instr.go
@@ -586,10 +586,6 @@ func (m *machine) lowerVShift(op ssa.Opcode, rd, rn, rm operand, arr vecArrangem
 
 	tmp := operandNR(m.compiler.AllocateVReg(regalloc.RegTypeFloat))
 
-	mov := m.allocateInstr()
-	mov.asFpuMov128(tmp.nr(), rm.nr())
-	m.insert(mov)
-
 	and := m.allocateInstr()
 	and.asALUBitmaskImm(aluOpAnd, rm.nr(), tmp.nr(), uint64(modulo), false)
 	m.insert(and)
@@ -603,7 +599,7 @@ func (m *machine) lowerVShift(op ssa.Opcode, rd, rn, rm operand, arr vecArrangem
 
 	// Copy the shift amount into a vector register as sshl/ushl requires it to be there.
 	dup := m.allocateInstr()
-	dup.asVecDup(rd, rm, arr)
+	dup.asVecDup(rd, tmp, arr)
 	m.insert(dup)
 
 	if op == ssa.OpcodeVIshl || op == ssa.OpcodeVSshr {


Test patch:
diff --git a/internal/engine/wazevo/backend/isa/arm64/lower_instr_test.go b/internal/engine/wazevo/backend/isa/arm64/lower_instr_test.go
index a8f3af20..f0db9ea5 100644
--- a/internal/engine/wazevo/backend/isa/arm64/lower_instr_test.go
+++ b/internal/engine/wazevo/backend/isa/arm64/lower_instr_test.go
@@ -739,38 +739,35 @@ func TestMachine_lowerVShift(t *testing.T) {
 			op:          ssa.OpcodeVIshl,
 			arrangement: vecArrangement16B,
 			expectedAsm: `
-mov v1?.16b, x15.16b
 and s1?, w15, #0x7
-dup x1.16b, x15
+dup x1.16b, d1?
 sshl x1.16b, x2.16b, x1.16b
 `,
-			expectedBytes: "e01daf4ee0090012e10d014e4144214e",
+			expectedBytes: "e0090012010c014e4144214e",
 		},
 		{
 			name:        "VSshr",
 			op:          ssa.OpcodeVSshr,
 			arrangement: vecArrangement16B,
 			expectedAsm: `
-mov v1?.16b, x15.16b
 and s1?, w15, #0x7
 sub s1?, wzr, s1?
-dup x1.16b, x15
+dup x1.16b, d1?
 sshl x1.16b, x2.16b, x1.16b
 `,
-			expectedBytes: "e01daf4ee0090012e003004be10d014e4144214e",
+			expectedBytes: "e0090012e003004b010c014e4144214e",
 		},
 		{
 			name:        "VUshr",
 			op:          ssa.OpcodeVUshr,
 			arrangement: vecArrangement16B,
 			expectedAsm: `
-mov v1?.16b, x15.16b
 and s1?, w15, #0x7
 sub s1?, wzr, s1?
-dup x1.16b, x15
+dup x1.16b, d1?
 ushl x1.16b, x2.16b, x1.16b
 `,
-			expectedBytes: "e01daf4ee0090012e003004be10d014e4144216e",
+			expectedBytes: "e0090012e003004b010c014e4144216e",
 		},
 	} {
 		t.Run(tc.name, func(t *testing.T) {
Repository: tetratelabs/wazero
Pull request #1760 (2023-10-05 06:07:19)

wazevo(arm64): do not optimize out Ireduce
pointed out by the fuzzer

#1496 


Patch:
diff --git a/internal/engine/wazevo/backend/isa/arm64/instr.go b/internal/engine/wazevo/backend/isa/arm64/instr.go
index f0d6138d..4c60024a 100644
--- a/internal/engine/wazevo/backend/isa/arm64/instr.go
+++ b/internal/engine/wazevo/backend/isa/arm64/instr.go
@@ -835,7 +835,9 @@ func (i *instruction) asVecRRR(op vecOp, rd, rn, rm operand, arr vecArrangement)
 
 func (i *instruction) isCopy() bool {
 	op := i.kind
-	return op == mov64 || op == mov32 || op == fpuMov64 || op == fpuMov128
+	// We do not include mov32 as it is not a copy instruction in the sense that it does not preserve the upper 32 bits,
+	// and it is only used in the translation of IReduce, not the actual copy indeed.
+	return op == mov64 || op == fpuMov64 || op == fpuMov128
 }
 
 // String implements fmt.Stringer.


Test patch:
diff --git a/internal/engine/wazevo/backend/isa/arm64/instr_test.go b/internal/engine/wazevo/backend/isa/arm64/instr_test.go
index 69464472..65d27287 100644
--- a/internal/engine/wazevo/backend/isa/arm64/instr_test.go
+++ b/internal/engine/wazevo/backend/isa/arm64/instr_test.go
@@ -67,3 +67,10 @@ func TestInstruction_String(t *testing.T) {
 		t.Run(tc.exp, func(t *testing.T) { require.Equal(t, tc.exp, tc.i.String()) })
 	}
 }
+
+func TestInstruction_isCopy(t *testing.T) {
+	require.False(t, (&instruction{kind: mov32}).isCopy())
+	require.True(t, (&instruction{kind: mov64}).isCopy())
+	require.True(t, (&instruction{kind: fpuMov64}).isCopy())
+	require.True(t, (&instruction{kind: fpuMov128}).isCopy())
+}
Repository: tetratelabs/wazero
Pull request #1768 (2023-10-09 02:14:23)

wazevo(arm64): fixes Rotl translation not to override rm
detected by the fuzzer

#1496 


Patch:
diff --git a/internal/engine/wazevo/backend/isa/arm64/lower_instr.go b/internal/engine/wazevo/backend/isa/arm64/lower_instr.go
index f38a1225..241e8fc4 100644
--- a/internal/engine/wazevo/backend/isa/arm64/lower_instr.go
+++ b/internal/engine/wazevo/backend/isa/arm64/lower_instr.go
@@ -1551,14 +1551,20 @@ func (m *machine) lowerRotl(si *ssa.Instruction) {
 
 	rn := m.getOperand_NR(m.compiler.ValueDefinition(x), extModeNone)
 	rm := m.getOperand_NR(m.compiler.ValueDefinition(y), extModeNone)
+	tmp := operandNR(m.compiler.AllocateVReg(regalloc.RegTypeInt))
 	rd := operandNR(m.compiler.VRegOf(r))
 
+	// Encode rotl as neg + rotr: neg is a sub against the zero-reg.
+	m.lowerRotlImpl(rd, rn, rm, tmp, _64)
+}
+
+func (m *machine) lowerRotlImpl(rd, rn, rm, tmp operand, is64bit bool) {
 	// Encode rotl as neg + rotr: neg is a sub against the zero-reg.
 	neg := m.allocateInstr()
-	neg.asALU(aluOpSub, rm, operandNR(xzrVReg), rm, _64)
+	neg.asALU(aluOpSub, tmp, operandNR(xzrVReg), rm, is64bit)
 	m.insert(neg)
 	alu := m.allocateInstr()
-	alu.asALU(aluOpRotR, rd, rn, rm, _64)
+	alu.asALU(aluOpRotR, rd, rn, tmp, is64bit)
 	m.insert(alu)
 }
 


Test patch:
diff --git a/internal/engine/wazevo/backend/isa/arm64/lower_instr_test.go b/internal/engine/wazevo/backend/isa/arm64/lower_instr_test.go
index b8eaaa7b..e8db25f5 100644
--- a/internal/engine/wazevo/backend/isa/arm64/lower_instr_test.go
+++ b/internal/engine/wazevo/backend/isa/arm64/lower_instr_test.go
@@ -895,3 +895,41 @@ bit v5?.8b, v4?.8b, v2?.8b
 		})
 	}
 }
+
+func TestMachine_lowerRotl(t *testing.T) {
+	for _, tc := range []struct {
+		_64bit bool
+		exp    string
+	}{
+		{
+			_64bit: false,
+			exp: `
+sub w1?, wzr, w3?
+ror w4?, w2?, w1?
+`,
+		},
+		{
+			_64bit: true,
+			exp: `
+sub x1?, xzr, x3?
+ror x4?, x2?, x1?
+`,
+		},
+	} {
+		t.Run(fmt.Sprintf("64bit=%v", tc._64bit), func(t *testing.T) {
+			_, _, m := newSetupWithMockContext()
+			tmpI := operandNR(m.compiler.AllocateVReg(regalloc.RegTypeInt))
+			rn := operandNR(m.compiler.AllocateVReg(regalloc.RegTypeInt))
+			rm := operandNR(m.compiler.AllocateVReg(regalloc.RegTypeInt))
+			rd := operandNR(m.compiler.AllocateVReg(regalloc.RegTypeInt))
+
+			require.Equal(t, 1, int(tmpI.reg().ID()))
+			require.Equal(t, 2, int(rn.reg().ID()))
+			require.Equal(t, 3, int(rm.reg().ID()))
+			require.Equal(t, 4, int(rd.reg().ID()))
+
+			m.lowerRotlImpl(rd, rn, rm, tmpI, tc._64bit)
+			require.Equal(t, tc.exp, "\n"+formatEmittedInstructionsInCurrentBlock(m)+"\n")
+		})
+	}
+}