Index: llvm/trunk/lib/Target/ARM/ARMCodeGenPrepare.cpp =================================================================== --- llvm/trunk/lib/Target/ARM/ARMCodeGenPrepare.cpp +++ llvm/trunk/lib/Target/ARM/ARMCodeGenPrepare.cpp @@ -257,9 +257,20 @@ return false; auto *CI = cast(*I->user_begin()); + + // Don't support an icmp that deals with sign bits, including negative + // immediates if (CI->isSigned()) return false; + if (auto *Const = dyn_cast(CI->getOperand(0))) + if (Const->isNegative()) + return false; + + if (auto *Const = dyn_cast(CI->getOperand(1))) + if (Const->isNegative()) + return false; + bool NegImm = cast(I->getOperand(1))->isNegative(); bool IsDecreasing = ((Opc == Instruction::Sub) && !NegImm) || ((Opc == Instruction::Add) && NegImm); Index: llvm/trunk/test/CodeGen/ARM/arm-cgp-icmps.ll =================================================================== --- llvm/trunk/test/CodeGen/ARM/arm-cgp-icmps.ll +++ llvm/trunk/test/CodeGen/ARM/arm-cgp-icmps.ll @@ -288,3 +288,25 @@ ret i32 %res } +; CHECK-COMMON-LABEL: icmp_minus_imm +; CHECK-NODSP: subs [[SUB:r[0-9]+]], +; CHECK-NODSP: uxtb [[UXT:r[0-9]+]], +; CHECK-NODSP: cmp [[UXT]], #251 + +; CHECK-DSP: subs [[SUB:r[0-9]+]], +; CHECK-DSP: uxtb [[UXT:r[0-9]+]], +; CHECK-DSP: cmp [[UXT]], #251 + +; CHECK-DSP-IMM: ldrb [[A:r[0-9]+]], +; CHECK-DSP-IMM: movs [[MINUS_7:r[0-9]+]], #249 +; CHECK-DSP-IMM: uadd8 [[RES:r[0-9]+]], [[A]], [[MINUS_7]] +; CHECK-DSP-IMM: cmp [[RES]], #251 +define i32 @icmp_minus_imm(i8* %a) { +entry: + %0 = load i8, i8* %a, align 1 + %add.i = add i8 %0, -7 + %cmp = icmp ugt i8 %add.i, -5 + %conv1 = zext i1 %cmp to i32 + ret i32 %conv1 +} +