if (!IsNegative && isOperationLegal(ISD::SUB, VT) &&
isOperationLegal(ISD::UMIN, VT)) {
SDValue Zero = DAG.getConstant(0, dl, VT);
+ Op = DAG.getFreeze(Op);
return DAG.getNode(ISD::UMIN, dl, VT, Op,
DAG.getNode(ISD::SUB, dl, VT, Zero, Op));
}
// 0 - abs(x) -> smin(x, sub(0,x))
if (IsNegative && isOperationLegal(ISD::SUB, VT) &&
isOperationLegal(ISD::SMIN, VT)) {
+ Op = DAG.getFreeze(Op);
SDValue Zero = DAG.getConstant(0, dl, VT);
return DAG.getNode(ISD::SMIN, dl, VT, Op,
DAG.getNode(ISD::SUB, dl, VT, Zero, Op));
!isOperationLegalOrCustomOrPromote(ISD::XOR, VT)))
return SDValue();
+ Op = DAG.getFreeze(Op);
SDValue Shift =
DAG.getNode(ISD::SRA, dl, VT, Op,
DAG.getConstant(VT.getScalarSizeInBits() - 1, dl, ShVT));
+; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py
; RUN: llc < %s -mtriple=wasm32-unknown-unknown | FileCheck %s
; Regression test for PR41149.
define void @mod() {
; CHECK-LABEL: mod:
-; CHECK-NEXT: .functype mod () -> ()
-; CHECK: local.get 0
-; CHECK-NEXT: local.get 0
-; CHECK-NEXT: i32.load8_s 0
-; CHECK-NEXT: local.tee 0
-; CHECK-NEXT: local.get 0
-; CHECK-NEXT: i32.const 7
-; CHECK-NEXT: i32.shr_s
-; CHECK-NEXT: local.tee 0
-; CHECK-NEXT: i32.xor
-; CHECK-NEXT: local.get 0
-; CHECK-NEXT: i32.sub
-; CHECK-NEXT: i32.store8 0
+; CHECK: .functype mod () -> ()
+; CHECK-NEXT: .local i32
+; CHECK-NEXT: # %bb.0:
+; CHECK-NEXT: local.get 0
+; CHECK-NEXT: local.get 0
+; CHECK-NEXT: i32.load8_u 0
+; CHECK-NEXT: local.tee 0
+; CHECK-NEXT: local.get 0
+; CHECK-NEXT: i32.const 24
+; CHECK-NEXT: i32.shl
+; CHECK-NEXT: i32.const 31
+; CHECK-NEXT: i32.shr_s
+; CHECK-NEXT: local.tee 0
+; CHECK-NEXT: i32.xor
+; CHECK-NEXT: local.get 0
+; CHECK-NEXT: i32.sub
+; CHECK-NEXT: i32.store8 0
+; CHECK-NEXT: # fallthrough-return
%tmp = load <4 x i8>, <4 x i8>* undef
%tmp2 = icmp slt <4 x i8> %tmp, zeroinitializer
%tmp3 = sub <4 x i8> zeroinitializer, %tmp
define i16 @test_i16(i16 %a) nounwind {
; X86-NO-CMOV-LABEL: test_i16:
; X86-NO-CMOV: # %bb.0:
-; X86-NO-CMOV-NEXT: movswl {{[0-9]+}}(%esp), %eax
-; X86-NO-CMOV-NEXT: movl %eax, %ecx
+; X86-NO-CMOV-NEXT: movzwl {{[0-9]+}}(%esp), %eax
+; X86-NO-CMOV-NEXT: movswl %ax, %ecx
; X86-NO-CMOV-NEXT: sarl $15, %ecx
; X86-NO-CMOV-NEXT: xorl %ecx, %eax
; X86-NO-CMOV-NEXT: subl %ecx, %eax
define i16 @neg_abs_i16(i16 %x) nounwind {
; X86-LABEL: neg_abs_i16:
; X86: # %bb.0:
-; X86-NEXT: movswl {{[0-9]+}}(%esp), %ecx
-; X86-NEXT: movl %ecx, %eax
+; X86-NEXT: movzwl {{[0-9]+}}(%esp), %ecx
+; X86-NEXT: movswl %cx, %eax
; X86-NEXT: sarl $15, %eax
; X86-NEXT: xorl %eax, %ecx
; X86-NEXT: subl %ecx, %eax
; X86-NEXT: pushl %ebx
; X86-NEXT: pushl %edi
; X86-NEXT: pushl %esi
-; X86-NEXT: movl {{[0-9]+}}(%esp), %eax
; X86-NEXT: movl {{[0-9]+}}(%esp), %edx
+; X86-NEXT: movl {{[0-9]+}}(%esp), %eax
; X86-NEXT: movl %edx, %ecx
; X86-NEXT: sarl $31, %ecx
; X86-NEXT: xorl %ecx, %edx
define i16 @sub_abs_i16(i16 %x, i16 %y) nounwind {
; X86-LABEL: sub_abs_i16:
; X86: # %bb.0:
-; X86-NEXT: movswl {{[0-9]+}}(%esp), %ecx
-; X86-NEXT: movl %ecx, %eax
+; X86-NEXT: movzwl {{[0-9]+}}(%esp), %ecx
+; X86-NEXT: movswl %cx, %eax
; X86-NEXT: sarl $15, %eax
; X86-NEXT: xorl %eax, %ecx
; X86-NEXT: subl %ecx, %eax
define i16 @test_i16(i16 %a) nounwind {
; X86-NO-CMOV-LABEL: test_i16:
; X86-NO-CMOV: # %bb.0:
-; X86-NO-CMOV-NEXT: movswl {{[0-9]+}}(%esp), %eax
-; X86-NO-CMOV-NEXT: movl %eax, %ecx
+; X86-NO-CMOV-NEXT: movzwl {{[0-9]+}}(%esp), %eax
+; X86-NO-CMOV-NEXT: movswl %ax, %ecx
; X86-NO-CMOV-NEXT: sarl $15, %ecx
; X86-NO-CMOV-NEXT: xorl %ecx, %eax
; X86-NO-CMOV-NEXT: subl %ecx, %eax