diff --git a/llvm/lib/Target/RISCV/RISCVISelLowering.cpp b/llvm/lib/Target/RISCV/RISCVISelLowering.cpp index fae2cda13863d..1b936552d3810 100644 --- a/llvm/lib/Target/RISCV/RISCVISelLowering.cpp +++ b/llvm/lib/Target/RISCV/RISCVISelLowering.cpp @@ -310,13 +310,14 @@ RISCVTargetLowering::RISCVTargetLowering(const TargetMachine &TM, setOperationAction(ISD::VASTART, MVT::Other, Custom); setOperationAction({ISD::VAARG, ISD::VACOPY, ISD::VAEND}, MVT::Other, Expand); - if (!Subtarget.hasVendorXTHeadBb() && !Subtarget.hasVendorXqcibm()) + if (!Subtarget.hasVendorXTHeadBb() && !Subtarget.hasVendorXqcibm() && + !Subtarget.hasVendorXAndesPerf()) setOperationAction(ISD::SIGN_EXTEND_INREG, MVT::i1, Expand); setOperationAction(ISD::EH_DWARF_CFA, MVT::i32, Custom); if (!Subtarget.hasStdExtZbb() && !Subtarget.hasVendorXTHeadBb() && - !Subtarget.hasVendorXqcibm() && + !Subtarget.hasVendorXqcibm() && !Subtarget.hasVendorXAndesPerf() && !(Subtarget.hasVendorXCValu() && !Subtarget.is64Bit())) setOperationAction(ISD::SIGN_EXTEND_INREG, {MVT::i8, MVT::i16}, Expand); diff --git a/llvm/lib/Target/RISCV/RISCVInstrInfoXAndes.td b/llvm/lib/Target/RISCV/RISCVInstrInfoXAndes.td index 6afe88b805d35..ec883cd1d3157 100644 --- a/llvm/lib/Target/RISCV/RISCVInstrInfoXAndes.td +++ b/llvm/lib/Target/RISCV/RISCVInstrInfoXAndes.td @@ -466,6 +466,10 @@ def NDS_VD4DOTSU_VV : NDSRVInstVD4DOT<0b000101, "nds.vd4dotsu">; let Predicates = [HasVendorXAndesPerf] in { +def : Pat<(sext_inreg (XLenVT GPR:$rs1), i16), (NDS_BFOS GPR:$rs1, 15, 0)>; +def : Pat<(sext_inreg (XLenVT GPR:$rs1), i8), (NDS_BFOS GPR:$rs1, 7, 0)>; +def : Pat<(sext_inreg (XLenVT GPR:$rs1), i1), (NDS_BFOS GPR:$rs1, 0, 0)>; + defm : ShxAddPat<1, NDS_LEA_H>; defm : ShxAddPat<2, NDS_LEA_W>; defm : ShxAddPat<3, NDS_LEA_D>; diff --git a/llvm/test/CodeGen/RISCV/rv32xandesperf.ll b/llvm/test/CodeGen/RISCV/rv32xandesperf.ll new file mode 100644 index 0000000000000..efe5b4a306fee --- /dev/null +++ b/llvm/test/CodeGen/RISCV/rv32xandesperf.ll @@ -0,0 +1,152 @@ +; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py +; RUN: llc -O0 -mtriple=riscv32 -mattr=+xandesperf -verify-machineinstrs < %s \ +; RUN: | FileCheck %s + +define i32 @sexti1_i32(i32 %a) { +; CHECK-LABEL: sexti1_i32: +; CHECK: # %bb.0: +; CHECK-NEXT: nds.bfos a0, a0, 0, 0 +; CHECK-NEXT: ret + %shl = shl i32 %a, 31 + %shr = ashr exact i32 %shl, 31 + ret i32 %shr +} + +define i32 @sexti1_i32_2(i1 %a) { +; CHECK-LABEL: sexti1_i32_2: +; CHECK: # %bb.0: +; CHECK-NEXT: # kill: def $x11 killed $x10 +; CHECK-NEXT: nds.bfos a0, a0, 0, 0 +; CHECK-NEXT: ret + %1 = sext i1 %a to i32 + ret i32 %1 +} + +define i32 @sexti8_i32(i32 %a) { +; CHECK-LABEL: sexti8_i32: +; CHECK: # %bb.0: +; CHECK-NEXT: nds.bfos a0, a0, 7, 0 +; CHECK-NEXT: ret + %shl = shl i32 %a, 24 + %shr = ashr exact i32 %shl, 24 + ret i32 %shr +} + +define i32 @sexti8_i32_2(i8 %a) { +; CHECK-LABEL: sexti8_i32_2: +; CHECK: # %bb.0: +; CHECK-NEXT: # kill: def $x11 killed $x10 +; CHECK-NEXT: nds.bfos a0, a0, 7, 0 +; CHECK-NEXT: ret + %1 = sext i8 %a to i32 + ret i32 %1 +} + +define i32 @sexti16_i32(i32 %a) { +; CHECK-LABEL: sexti16_i32: +; CHECK: # %bb.0: +; CHECK-NEXT: nds.bfos a0, a0, 15, 0 +; CHECK-NEXT: ret + %shl = shl i32 %a, 16 + %shr = ashr exact i32 %shl, 16 + ret i32 %shr +} + +define i32 @sexti16_i32_2(i16 %a) { +; CHECK-LABEL: sexti16_i32_2: +; CHECK: # %bb.0: +; CHECK-NEXT: # kill: def $x11 killed $x10 +; CHECK-NEXT: nds.bfos a0, a0, 15, 0 +; CHECK-NEXT: ret + %1 = sext i16 %a to i32 + ret i32 %1 +} + +define i64 @sexti1_i64(i64 %a) { +; CHECK-LABEL: sexti1_i64: +; CHECK: # %bb.0: +; CHECK-NEXT: # kill: def $x11 killed $x10 +; CHECK-NEXT: nds.bfos a1, a0, 0, 0 +; CHECK-NEXT: mv a0, a1 +; CHECK-NEXT: ret + %shl = shl i64 %a, 63 + %shr = ashr exact i64 %shl, 63 + ret i64 %shr +} + +define i64 @sexti1_i64_2(i1 %a) { +; CHECK-LABEL: sexti1_i64_2: +; CHECK: # %bb.0: +; CHECK-NEXT: # kill: def $x11 killed $x10 +; CHECK-NEXT: nds.bfos a1, a0, 0, 0 +; CHECK-NEXT: mv a0, a1 +; CHECK-NEXT: ret + %1 = sext i1 %a to i64 + ret i64 %1 +} + +define i64 @sexti8_i64(i64 %a) { +; CHECK-LABEL: sexti8_i64: +; CHECK: # %bb.0: +; CHECK-NEXT: # kill: def $x11 killed $x10 +; CHECK-NEXT: nds.bfos a0, a0, 7, 0 +; CHECK-NEXT: srai a1, a0, 31 +; CHECK-NEXT: ret + %shl = shl i64 %a, 56 + %shr = ashr exact i64 %shl, 56 + ret i64 %shr +} + +define i64 @sexti8_i64_2(i8 %a) { +; CHECK-LABEL: sexti8_i64_2: +; CHECK: # %bb.0: +; CHECK-NEXT: # kill: def $x11 killed $x10 +; CHECK-NEXT: nds.bfos a0, a0, 7, 0 +; CHECK-NEXT: srai a1, a0, 31 +; CHECK-NEXT: ret + %1 = sext i8 %a to i64 + ret i64 %1 +} + +define i64 @sexti16_i64(i64 %a) { +; CHECK-LABEL: sexti16_i64: +; CHECK: # %bb.0: +; CHECK-NEXT: # kill: def $x11 killed $x10 +; CHECK-NEXT: nds.bfos a0, a0, 15, 0 +; CHECK-NEXT: srai a1, a0, 31 +; CHECK-NEXT: ret + %shl = shl i64 %a, 48 + %shr = ashr exact i64 %shl, 48 + ret i64 %shr +} + +define i64 @sexti16_i64_2(i16 %a) { +; CHECK-LABEL: sexti16_i64_2: +; CHECK: # %bb.0: +; CHECK-NEXT: # kill: def $x11 killed $x10 +; CHECK-NEXT: nds.bfos a0, a0, 15, 0 +; CHECK-NEXT: srai a1, a0, 31 +; CHECK-NEXT: ret + %1 = sext i16 %a to i64 + ret i64 %1 +} + +define i64 @sexti32_i64(i64 %a) { +; CHECK-LABEL: sexti32_i64: +; CHECK: # %bb.0: +; CHECK-NEXT: # kill: def $x11 killed $x10 +; CHECK-NEXT: srai a1, a0, 31 +; CHECK-NEXT: ret + %shl = shl i64 %a, 32 + %shr = ashr exact i64 %shl, 32 + ret i64 %shr +} + +define i64 @sexti32_i64_2(i32 %a) { +; CHECK-LABEL: sexti32_i64_2: +; CHECK: # %bb.0: +; CHECK-NEXT: srai a1, a0, 31 +; CHECK-NEXT: ret + %1 = sext i32 %a to i64 + ret i64 %1 +} diff --git a/llvm/test/CodeGen/RISCV/rv64xandesperf.ll b/llvm/test/CodeGen/RISCV/rv64xandesperf.ll new file mode 100644 index 0000000000000..9cc95ce886133 --- /dev/null +++ b/llvm/test/CodeGen/RISCV/rv64xandesperf.ll @@ -0,0 +1,135 @@ +; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py +; RUN: llc -mtriple=riscv64 -mattr=+xandesperf -verify-machineinstrs < %s \ +; RUN: | FileCheck %s + +define signext i32 @sexti1_i32(i32 signext %a) { +; CHECK-LABEL: sexti1_i32: +; CHECK: # %bb.0: +; CHECK-NEXT: nds.bfos a0, a0, 0, 0 +; CHECK-NEXT: ret + %shl = shl i32 %a, 31 + %shr = ashr exact i32 %shl, 31 + ret i32 %shr +} + +define signext i32 @sexti1_i32_2(i1 %a) { +; CHECK-LABEL: sexti1_i32_2: +; CHECK: # %bb.0: +; CHECK-NEXT: nds.bfos a0, a0, 0, 0 +; CHECK-NEXT: ret + %1 = sext i1 %a to i32 + ret i32 %1 +} + +define signext i32 @sexti8_i32(i32 signext %a) { +; CHECK-LABEL: sexti8_i32: +; CHECK: # %bb.0: +; CHECK-NEXT: nds.bfos a0, a0, 7, 0 +; CHECK-NEXT: ret + %shl = shl i32 %a, 24 + %shr = ashr exact i32 %shl, 24 + ret i32 %shr +} + +define signext i32 @sexti8_i32_2(i8 %a) { +; CHECK-LABEL: sexti8_i32_2: +; CHECK: # %bb.0: +; CHECK-NEXT: nds.bfos a0, a0, 7, 0 +; CHECK-NEXT: ret + %1 = sext i8 %a to i32 + ret i32 %1 +} + +define signext i32 @sexti16_i32(i32 signext %a) { +; CHECK-LABEL: sexti16_i32: +; CHECK: # %bb.0: +; CHECK-NEXT: nds.bfos a0, a0, 15, 0 +; CHECK-NEXT: ret + %shl = shl i32 %a, 16 + %shr = ashr exact i32 %shl, 16 + ret i32 %shr +} + +define signext i32 @sexti16_i32_2(i16 %a) { +; CHECK-LABEL: sexti16_i32_2: +; CHECK: # %bb.0: +; CHECK-NEXT: nds.bfos a0, a0, 15, 0 +; CHECK-NEXT: ret + %1 = sext i16 %a to i32 + ret i32 %1 +} + +define i64 @sexti1_i64(i64 %a) { +; CHECK-LABEL: sexti1_i64: +; CHECK: # %bb.0: +; CHECK-NEXT: nds.bfos a0, a0, 0, 0 +; CHECK-NEXT: ret + %shl = shl i64 %a, 63 + %shr = ashr exact i64 %shl, 63 + ret i64 %shr +} + +define i64 @sexti1_i64_2(i1 %a) { +; CHECK-LABEL: sexti1_i64_2: +; CHECK: # %bb.0: +; CHECK-NEXT: nds.bfos a0, a0, 0, 0 +; CHECK-NEXT: ret + %1 = sext i1 %a to i64 + ret i64 %1 +} + +define i64 @sexti8_i64(i64 %a) { +; CHECK-LABEL: sexti8_i64: +; CHECK: # %bb.0: +; CHECK-NEXT: nds.bfos a0, a0, 7, 0 +; CHECK-NEXT: ret + %shl = shl i64 %a, 56 + %shr = ashr exact i64 %shl, 56 + ret i64 %shr +} + +define i64 @sexti8_i64_2(i8 %a) { +; CHECK-LABEL: sexti8_i64_2: +; CHECK: # %bb.0: +; CHECK-NEXT: nds.bfos a0, a0, 7, 0 +; CHECK-NEXT: ret + %1 = sext i8 %a to i64 + ret i64 %1 +} + +define i64 @sexti16_i64(i64 %a) { +; CHECK-LABEL: sexti16_i64: +; CHECK: # %bb.0: +; CHECK-NEXT: nds.bfos a0, a0, 15, 0 +; CHECK-NEXT: ret + %shl = shl i64 %a, 48 + %shr = ashr exact i64 %shl, 48 + ret i64 %shr +} + +define i64 @sexti16_i64_2(i16 %a) { +; CHECK-LABEL: sexti16_i64_2: +; CHECK: # %bb.0: +; CHECK-NEXT: nds.bfos a0, a0, 15, 0 +; CHECK-NEXT: ret + %1 = sext i16 %a to i64 + ret i64 %1 +} + +define i64 @sexti32_i64(i64 %a) { +; CHECK-LABEL: sexti32_i64: +; CHECK: # %bb.0: +; CHECK-NEXT: sext.w a0, a0 +; CHECK-NEXT: ret + %shl = shl i64 %a, 32 + %shr = ashr exact i64 %shl, 32 + ret i64 %shr +} + +define i64 @sexti32_i64_2(i32 signext %a) { +; CHECK-LABEL: sexti32_i64_2: +; CHECK: # %bb.0: +; CHECK-NEXT: ret + %1 = sext i32 %a to i64 + ret i64 %1 +} diff --git a/llvm/test/CodeGen/RISCV/rv64zba.ll b/llvm/test/CodeGen/RISCV/rv64zba.ll index a0238458aff81..6b64144406375 100644 --- a/llvm/test/CodeGen/RISCV/rv64zba.ll +++ b/llvm/test/CodeGen/RISCV/rv64zba.ll @@ -2323,8 +2323,8 @@ define zeroext i32 @sext_ashr_zext_i8(i8 %a) nounwind { ; ; RV64XANDESPERF-LABEL: sext_ashr_zext_i8: ; RV64XANDESPERF: # %bb.0: -; RV64XANDESPERF-NEXT: slli a0, a0, 56 -; RV64XANDESPERF-NEXT: srai a0, a0, 31 +; RV64XANDESPERF-NEXT: nds.bfos a0, a0, 7, 0 +; RV64XANDESPERF-NEXT: slli a0, a0, 23 ; RV64XANDESPERF-NEXT: srli a0, a0, 32 ; RV64XANDESPERF-NEXT: ret %ext = sext i8 %a to i32 @@ -2472,8 +2472,8 @@ define zeroext i32 @sext_ashr_zext_i16(i16 %a) nounwind { ; ; RV64XANDESPERF-LABEL: sext_ashr_zext_i16: ; RV64XANDESPERF: # %bb.0: -; RV64XANDESPERF-NEXT: slli a0, a0, 48 -; RV64XANDESPERF-NEXT: srai a0, a0, 25 +; RV64XANDESPERF-NEXT: nds.bfos a0, a0, 15, 0 +; RV64XANDESPERF-NEXT: slli a0, a0, 23 ; RV64XANDESPERF-NEXT: srli a0, a0, 32 ; RV64XANDESPERF-NEXT: ret %ext = sext i16 %a to i32