diff --git a/llvm/lib/Target/RISCV/RISCVISelLowering.cpp b/llvm/lib/Target/RISCV/RISCVISelLowering.cpp index 8e248d22b5776..f030982cb815d 100644 --- a/llvm/lib/Target/RISCV/RISCVISelLowering.cpp +++ b/llvm/lib/Target/RISCV/RISCVISelLowering.cpp @@ -3113,12 +3113,13 @@ static SDValue lowerBUILD_VECTOR(SDValue Op, SelectionDAG &DAG, bool Negate = false; int64_t SplatStepVal = StepNumerator; unsigned StepOpcode = ISD::MUL; - if (StepNumerator != 1) { - if (isPowerOf2_64(std::abs(StepNumerator))) { - Negate = StepNumerator < 0; - StepOpcode = ISD::SHL; - SplatStepVal = Log2_64(std::abs(StepNumerator)); - } + // Exclude INT64_MIN to avoid passing it to std::abs. We won't optimize it + // anyway as the shift of 63 won't fit in uimm5. + if (StepNumerator != 1 && StepNumerator != INT64_MIN && + isPowerOf2_64(std::abs(StepNumerator))) { + Negate = StepNumerator < 0; + StepOpcode = ISD::SHL; + SplatStepVal = Log2_64(std::abs(StepNumerator)); } // Only emit VIDs with suitably-small steps/addends. We use imm5 is a