diff --git a/llvm/lib/Target/RISCV/RISCV.td b/llvm/lib/Target/RISCV/RISCV.td --- a/llvm/lib/Target/RISCV/RISCV.td +++ b/llvm/lib/Target/RISCV/RISCV.td @@ -62,6 +62,7 @@ def HasStdExtZba : Predicate<"Subtarget->hasStdExtZba()">, AssemblerPredicate<(all_of FeatureExtZba), "'Zba' (Address calculation 'B' Instructions)">; +def NotHasStdExtZba : Predicate<"!Subtarget->hasStdExtZba()">; def FeatureExtZbb : SubtargetFeature<"experimental-zbb", "HasStdExtZbb", "true", @@ -131,8 +132,6 @@ def HasStdExtZbbOrZbp : Predicate<"Subtarget->hasStdExtZbb() || Subtarget->hasStdExtZbp()">, AssemblerPredicate<(any_of FeatureExtZbb, FeatureExtZbp)>; -def NotHasStdExtZbbOrZbp - : Predicate<"!(Subtarget->hasStdExtZbb() || Subtarget->hasStdExtZbp())">; def FeatureExtZbproposedc : SubtargetFeature<"experimental-zbproposedc", "HasStdExtZbproposedc", "true", diff --git a/llvm/lib/Target/RISCV/RISCVInstrInfo.td b/llvm/lib/Target/RISCV/RISCVInstrInfo.td --- a/llvm/lib/Target/RISCV/RISCVInstrInfo.td +++ b/llvm/lib/Target/RISCV/RISCVInstrInfo.td @@ -1158,7 +1158,7 @@ /// RV64 patterns -let Predicates = [IsRV64, NotHasStdExtZbbOrZbp] in +let Predicates = [IsRV64, NotHasStdExtZba] in def : Pat<(and GPR:$rs1, 0xffffffff), (SRLI (SLLI GPR:$rs1, 32), 32)>; let Predicates = [IsRV64] in { diff --git a/llvm/lib/Target/RISCV/RISCVInstrInfoB.td b/llvm/lib/Target/RISCV/RISCVInstrInfoB.td --- a/llvm/lib/Target/RISCV/RISCVInstrInfoB.td +++ b/llvm/lib/Target/RISCV/RISCVInstrInfoB.td @@ -495,7 +495,7 @@ def C_NEG : RVBInstC<0b01, "c.neg">, Sched<[]>; } // DecoderNamespace = "RVBC", Predicates = [HasStdExtZbproposedc, HasStdExtC] -let DecoderNamespace = "RVBC", Predicates = [HasStdExtZbproposedc, HasStdExtZbbOrZbp, HasStdExtC, IsRV64] in +let DecoderNamespace = "RVBC", Predicates = [HasStdExtZbproposedc, HasStdExtZba, HasStdExtC, IsRV64] in def C_ZEXTW : RVBInstC<0b10, "c.zext.w">, Sched<[]>; //===----------------------------------------------------------------------===// @@ -508,9 +508,14 @@ let Predicates = [HasStdExtZbb, IsRV64] in { def : InstAlias<"zext.h $rd, $rs", (PACKW GPR:$rd, GPR:$rs, X0)>; -def : InstAlias<"zext.w $rd, $rs", (PACK GPR:$rd, GPR:$rs, X0)>; } // Predicates = [HasStdExtZbb, IsRV64] +let Predicates = [HasStdExtZba, IsRV64] in { +// NOTE: The 0.93 spec shows zext.w as an alias of pack/packw. It has been +// changed to add.uw in a draft after 0.94. +def : InstAlias<"zext.w $rd, $rs", (ADDUW GPR:$rd, GPR:$rs, X0)>; +} + let Predicates = [HasStdExtZbp] in { def : InstAlias<"rev.p $rd, $rs", (GREVI GPR:$rd, GPR:$rs, 0b00001)>; def : InstAlias<"rev2.n $rd, $rs", (GREVI GPR:$rd, GPR:$rs, 0b00010)>; @@ -626,8 +631,8 @@ (C_NEG GPRC:$rs1)>; } // Predicates = [HasStdExtZbproposedc, HasStdExtC] -let Predicates = [HasStdExtZbproposedc, HasStdExtZbbOrZbp, HasStdExtC, IsRV64] in { -def : CompressPat<(PACK GPRC:$rs1, GPRC:$rs1, X0), +let Predicates = [HasStdExtZbproposedc, HasStdExtZba, HasStdExtC, IsRV64] in { +def : CompressPat<(ADDUW GPRC:$rs1, GPRC:$rs1, X0), (C_ZEXTW GPRC:$rs1)>; } // Predicates = [HasStdExtZbproposedc, HasStdExtC, IsRV64] @@ -806,7 +811,6 @@ def : Pat<(and GPR:$rs, 0x0000FFFF), (PACK GPR:$rs, X0)>; let Predicates = [HasStdExtZbbOrZbp, IsRV64] in { def : Pat<(and GPR:$rs, 0x000000000000FFFF), (PACKW GPR:$rs, X0)>; -def : Pat<(and GPR:$rs, 0x00000000FFFFFFFF), (PACK GPR:$rs, X0)>; } let Predicates = [HasStdExtZbp, IsRV32] in { @@ -858,6 +862,7 @@ (SLLIUW GPR:$rs1, uimm5:$shamt)>; def : Pat<(add (and GPR:$rs1, (i64 0xFFFFFFFF)), GPR:$rs2), (ADDUW GPR:$rs1, GPR:$rs2)>; +def : Pat<(and GPR:$rs, 0x00000000FFFFFFFF), (ADDUW GPR:$rs, X0)>; } let Predicates = [HasStdExtZbp, IsRV64] in { diff --git a/llvm/test/CodeGen/RISCV/rv64Zba.ll b/llvm/test/CodeGen/RISCV/rv64Zba.ll --- a/llvm/test/CodeGen/RISCV/rv64Zba.ll +++ b/llvm/test/CodeGen/RISCV/rv64Zba.ll @@ -109,3 +109,23 @@ %5 = load i8, i8* %4 ret i8 %5 } + +define i64 @zextw_i64(i64 %a) nounwind { +; RV64I-LABEL: zextw_i64: +; RV64I: # %bb.0: +; RV64I-NEXT: slli a0, a0, 32 +; RV64I-NEXT: srli a0, a0, 32 +; RV64I-NEXT: ret +; +; RV64IB-LABEL: zextw_i64: +; RV64IB: # %bb.0: +; RV64IB-NEXT: zext.w a0, a0 +; RV64IB-NEXT: ret +; +; RV64IBA-LABEL: zextw_i64: +; RV64IBA: # %bb.0: +; RV64IBA-NEXT: zext.w a0, a0 +; RV64IBA-NEXT: ret + %and = and i64 %a, 4294967295 + ret i64 %and +} diff --git a/llvm/test/CodeGen/RISCV/rv64Zbbp.ll b/llvm/test/CodeGen/RISCV/rv64Zbbp.ll --- a/llvm/test/CodeGen/RISCV/rv64Zbbp.ll +++ b/llvm/test/CodeGen/RISCV/rv64Zbbp.ll @@ -792,28 +792,3 @@ %or = or i64 %shl, %and ret i64 %or } - -define i64 @zextw_i64(i64 %a) nounwind { -; RV64I-LABEL: zextw_i64: -; RV64I: # %bb.0: -; RV64I-NEXT: slli a0, a0, 32 -; RV64I-NEXT: srli a0, a0, 32 -; RV64I-NEXT: ret -; -; RV64IB-LABEL: zextw_i64: -; RV64IB: # %bb.0: -; RV64IB-NEXT: zext.w a0, a0 -; RV64IB-NEXT: ret -; -; RV64IBB-LABEL: zextw_i64: -; RV64IBB: # %bb.0: -; RV64IBB-NEXT: zext.w a0, a0 -; RV64IBB-NEXT: ret -; -; RV64IBP-LABEL: zextw_i64: -; RV64IBP: # %bb.0: -; RV64IBP-NEXT: pack a0, a0, zero -; RV64IBP-NEXT: ret - %and = and i64 %a, 4294967295 - ret i64 %and -} diff --git a/llvm/test/MC/RISCV/rv64b-aliases-valid.s b/llvm/test/MC/RISCV/rv64b-aliases-valid.s --- a/llvm/test/MC/RISCV/rv64b-aliases-valid.s +++ b/llvm/test/MC/RISCV/rv64b-aliases-valid.s @@ -23,7 +23,7 @@ # CHECK-S-OBJ: zext.h t0, t1 zext.h x5, x6 -# CHECK-S-OBJ-NOALIAS: pack t0, t1, zero +# CHECK-S-OBJ-NOALIAS: add.uw t0, t1, zero # CHECK-S-OBJ: zext.w t0, t1 zext.w x5, x6