diff --git a/cranelift/codegen/src/isa/pulley_shared/lower.isle b/cranelift/codegen/src/isa/pulley_shared/lower.isle index ffbfdaa107b4..c1f3883b207d 100644 --- a/cranelift/codegen/src/isa/pulley_shared/lower.isle +++ b/cranelift/codegen/src/isa/pulley_shared/lower.isle @@ -206,18 +206,26 @@ ;;;; Rules for `band` ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; (rule 0 (lower (has_type (fits_in_32 _) (band a b))) - (pulley_xand32 a b)) + (pulley_xband32 a b)) (rule 1 (lower (has_type $I64 (band a b))) - (pulley_xand64 a b)) + (pulley_xband64 a b)) ;;;; Rules for `bor` ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; (rule 0 (lower (has_type (fits_in_32 _) (bor a b))) - (pulley_xor32 a b)) + (pulley_xbor32 a b)) (rule 1 (lower (has_type $I64 (bor a b))) - (pulley_xor64 a b)) + (pulley_xbor64 a b)) + +;;;; Rules for `bxor` ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; + +(rule 0 (lower (has_type (fits_in_32 _) (bxor a b))) + (pulley_xbxor32 a b)) + +(rule 1 (lower (has_type $I64 (bxor a b))) + (pulley_xbxor64 a b)) ;;;; Rules for `ctz` ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; @@ -451,3 +459,17 @@ (rule (emit_cond (Cond.IfXslteq64 src1 src2)) (pulley_xslteq64 src1 src2)) (rule (emit_cond (Cond.IfXult64 src1 src2)) (pulley_xult64 src1 src2)) (rule (emit_cond (Cond.IfXulteq64 src1 src2)) (pulley_xulteq64 src1 src2)) + +;;;; Rules for `bitcast` ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; + +(rule (lower (has_type $F32 (bitcast _flags val @ (value_type $I32)))) + (pulley_bitcast_float_from_int_32 val)) + +(rule (lower (has_type $F64 (bitcast _flags val @ (value_type $I64)))) + (pulley_bitcast_float_from_int_64 val)) + +(rule (lower (has_type $I32 (bitcast _flags val @ (value_type $F32)))) + (pulley_bitcast_int_from_float_32 val)) + +(rule (lower (has_type $I64 (bitcast _flags val @ (value_type $F64)))) + (pulley_bitcast_int_from_float_64 val)) diff --git a/crates/wast-util/src/lib.rs b/crates/wast-util/src/lib.rs index 666adaf8d393..59a4c0003121 100644 --- a/crates/wast-util/src/lib.rs +++ b/crates/wast-util/src/lib.rs @@ -395,7 +395,6 @@ impl WastTest { // features in Pulley are implemented. if config.compiler == Compiler::CraneliftPulley { let unsupported = [ - "misc_testsuite/component-model/fused.wast", "misc_testsuite/component-model/strings.wast", "misc_testsuite/embenchen_fannkuch.wast", "misc_testsuite/embenchen_fasta.wast", @@ -403,7 +402,6 @@ impl WastTest { "misc_testsuite/embenchen_primes.wast", "misc_testsuite/float-round-doesnt-load-too-much.wast", "misc_testsuite/int-to-float-splat.wast", - "misc_testsuite/issue1809.wast", "misc_testsuite/issue4840.wast", "misc_testsuite/issue4890.wast", "misc_testsuite/issue6562.wast", @@ -440,7 +438,6 @@ impl WastTest { "spec_testsuite/call.wast", "spec_testsuite/call_indirect.wast", "spec_testsuite/conversions.wast", - "spec_testsuite/endianness.wast", "spec_testsuite/f32.wast", "spec_testsuite/f32_bitwise.wast", "spec_testsuite/f32_cmp.wast", @@ -449,7 +446,6 @@ impl WastTest { "spec_testsuite/f64_cmp.wast", "spec_testsuite/fac.wast", "spec_testsuite/float_exprs.wast", - "spec_testsuite/float_literals.wast", "spec_testsuite/float_misc.wast", "spec_testsuite/global.wast", "spec_testsuite/i32.wast", @@ -462,13 +458,11 @@ impl WastTest { "spec_testsuite/local_set.wast", "spec_testsuite/local_tee.wast", "spec_testsuite/loop.wast", - "spec_testsuite/memory.wast", "spec_testsuite/proposals/annotations/simd_lane.wast", "spec_testsuite/proposals/extended-const/global.wast", "spec_testsuite/proposals/multi-memory/float_exprs0.wast", "spec_testsuite/proposals/multi-memory/float_exprs1.wast", "spec_testsuite/proposals/multi-memory/imports.wast", - "spec_testsuite/proposals/multi-memory/memory.wast", "spec_testsuite/proposals/multi-memory/simd_memory-multi.wast", "spec_testsuite/proposals/relaxed-simd/i16x8_relaxed_q15mulr_s.wast", "spec_testsuite/proposals/relaxed-simd/i32x4_relaxed_trunc.wast", @@ -479,7 +473,6 @@ impl WastTest { "spec_testsuite/proposals/relaxed-simd/relaxed_min_max.wast", "spec_testsuite/proposals/threads/atomic.wast", "spec_testsuite/proposals/threads/imports.wast", - "spec_testsuite/proposals/threads/memory.wast", "spec_testsuite/select.wast", "spec_testsuite/simd_address.wast", "spec_testsuite/simd_align.wast", diff --git a/pulley/src/interp.rs b/pulley/src/interp.rs index c880eb1d40ff..2154664ab9b6 100644 --- a/pulley/src/interp.rs +++ b/pulley/src/interp.rs @@ -1474,25 +1474,25 @@ impl OpVisitor for Interpreter<'_> { fn bitcast_int_from_float_32(&mut self, dst: XReg, src: FReg) -> ControlFlow { let val = self.state[src].get_f32(); - self.state[dst].set_u64(u32::from_ne_bytes(val.to_ne_bytes()).into()); + self.state[dst].set_u32(val.to_bits()); ControlFlow::Continue(()) } fn bitcast_int_from_float_64(&mut self, dst: XReg, src: FReg) -> ControlFlow { let val = self.state[src].get_f64(); - self.state[dst].set_u64(u64::from_ne_bytes(val.to_ne_bytes())); + self.state[dst].set_u64(val.to_bits()); ControlFlow::Continue(()) } fn bitcast_float_from_int_32(&mut self, dst: FReg, src: XReg) -> ControlFlow { let val = self.state[src].get_u32(); - self.state[dst].set_f32(f32::from_ne_bytes(val.to_ne_bytes())); + self.state[dst].set_f32(f32::from_bits(val)); ControlFlow::Continue(()) } fn bitcast_float_from_int_64(&mut self, dst: FReg, src: XReg) -> ControlFlow { let val = self.state[src].get_u64(); - self.state[dst].set_f64(f64::from_ne_bytes(val.to_ne_bytes())); + self.state[dst].set_f64(f64::from_bits(val)); ControlFlow::Continue(()) } @@ -1657,34 +1657,48 @@ impl OpVisitor for Interpreter<'_> { } } - fn xand32(&mut self, operands: BinaryOperands) -> ControlFlow { + fn xband32(&mut self, operands: BinaryOperands) -> ControlFlow { let a = self.state[operands.src1].get_u32(); let b = self.state[operands.src2].get_u32(); self.state[operands.dst].set_u32(a & b); ControlFlow::Continue(()) } - fn xand64(&mut self, operands: BinaryOperands) -> ControlFlow { + fn xband64(&mut self, operands: BinaryOperands) -> ControlFlow { let a = self.state[operands.src1].get_u64(); let b = self.state[operands.src2].get_u64(); self.state[operands.dst].set_u64(a & b); ControlFlow::Continue(()) } - fn xor32(&mut self, operands: BinaryOperands) -> ControlFlow { + fn xbor32(&mut self, operands: BinaryOperands) -> ControlFlow { let a = self.state[operands.src1].get_u32(); let b = self.state[operands.src2].get_u32(); self.state[operands.dst].set_u32(a | b); ControlFlow::Continue(()) } - fn xor64(&mut self, operands: BinaryOperands) -> ControlFlow { + fn xbor64(&mut self, operands: BinaryOperands) -> ControlFlow { let a = self.state[operands.src1].get_u64(); let b = self.state[operands.src2].get_u64(); self.state[operands.dst].set_u64(a | b); ControlFlow::Continue(()) } + fn xbxor32(&mut self, operands: BinaryOperands) -> ControlFlow { + let a = self.state[operands.src1].get_u32(); + let b = self.state[operands.src2].get_u32(); + self.state[operands.dst].set_u32(a ^ b); + ControlFlow::Continue(()) + } + + fn xbxor64(&mut self, operands: BinaryOperands) -> ControlFlow { + let a = self.state[operands.src1].get_u64(); + let b = self.state[operands.src2].get_u64(); + self.state[operands.dst].set_u64(a ^ b); + ControlFlow::Continue(()) + } + fn fconst32(&mut self, dst: FReg, bits: u32) -> ControlFlow { self.state[dst].set_f32(f32::from_bits(bits)); ControlFlow::Continue(()) diff --git a/pulley/src/lib.rs b/pulley/src/lib.rs index a2a462ad5b25..7052e18e84ed 100644 --- a/pulley/src/lib.rs +++ b/pulley/src/lib.rs @@ -357,13 +357,18 @@ macro_rules! for_each_op { xrem64_u = XRem64U { operands: BinaryOperands }; /// `low32(dst) = low32(src1) & low32(src2)` - xand32 = XAnd32 { operands: BinaryOperands }; + xband32 = XBand32 { operands: BinaryOperands }; /// `dst = src1 & src2` - xand64 = XAnd64 { operands: BinaryOperands }; + xband64 = XBand64 { operands: BinaryOperands }; /// `low32(dst) = low32(src1) | low32(src2)` - xor32 = XOr32 { operands: BinaryOperands }; + xbor32 = XBor32 { operands: BinaryOperands }; /// `dst = src1 | src2` - xor64 = XOr64 { operands: BinaryOperands }; + xbor64 = XBor64 { operands: BinaryOperands }; + + /// `low32(dst) = low32(src1) ^ low32(src2)` + xbxor32 = XBxor32 { operands: BinaryOperands }; + /// `dst = src1 ^ src2` + xbxor64 = XBxor64 { operands: BinaryOperands }; /// `low32(dst) = bits` fconst32 = FConst32 { dst: FReg, bits: u32 };