[llvm] [RISCV] Add rules for Zca+Zcb+Zcmp+Zcmpt implying Zce. (PR #175041)

via llvm-commits llvm-commits at lists.llvm.org
Thu Jan 8 09:57:21 PST 2026


llvmbot wrote:


<!--LLVM PR SUMMARY COMMENT-->

@llvm/pr-subscribers-backend-risc-v

Author: Craig Topper (topperc)

<details>
<summary>Changes</summary>

The implication rules need to consider whether F is enabled like was done for C in #<!-- -->172860.

---
Full diff: https://github.com/llvm/llvm-project/pull/175041.diff


2 Files Affected:

- (modified) llvm/lib/TargetParser/RISCVISAInfo.cpp (+12) 
- (modified) llvm/unittests/TargetParser/RISCVISAInfoTest.cpp (+76) 


``````````diff
diff --git a/llvm/lib/TargetParser/RISCVISAInfo.cpp b/llvm/lib/TargetParser/RISCVISAInfo.cpp
index aaca51d8a9cda..29b51a7874479 100644
--- a/llvm/lib/TargetParser/RISCVISAInfo.cpp
+++ b/llvm/lib/TargetParser/RISCVISAInfo.cpp
@@ -906,6 +906,18 @@ void RISCVISAInfo::updateImplication() {
     }
   }
 
+  if (!Exts.count("zce") && Exts.count("zca") && Exts.count("zcb")  &&
+      Exts.count("zcmp") && Exts.count("zcmt")) {
+    bool ShouldAddZce = false;
+    if (XLen == 32) {
+      ShouldAddZce = !Exts.count("f") || Exts.count("zcf");
+    } else if (XLen == 64) {
+      ShouldAddZce = true;
+    }
+    if (ShouldAddZce)
+      Exts["zce"] = *findDefaultVersion("zce");
+  }
+
   // Handle I/E after implications have been resolved, in case either
   // of them was implied by another extension.
   bool HasE = Exts.count("e") != 0;
diff --git a/llvm/unittests/TargetParser/RISCVISAInfoTest.cpp b/llvm/unittests/TargetParser/RISCVISAInfoTest.cpp
index 2d0a3104f416d..e8e254bfcdc21 100644
--- a/llvm/unittests/TargetParser/RISCVISAInfoTest.cpp
+++ b/llvm/unittests/TargetParser/RISCVISAInfoTest.cpp
@@ -1045,6 +1045,82 @@ TEST(ParseArchString, ZcaImpliesC) {
   EXPECT_EQ(ExtsRV64IDZca.count("c"), 0U);
 }
 
+TEST(ParseArchString, ZcaZcbZcmpZcmtImpliesZce) {
+  // Test Zca+Zcb+Zcmp+Zcmt implies Zce behavior.
+
+  // RV32 Zca+Zcb+Zcmp+Zcmt without F implies Zce
+  auto MaybeRV32IZcaZcbZcmpZcmt = RISCVISAInfo::parseArchString("rv32i_zca_zcb_zcmp_zcmt", true);
+  ASSERT_THAT_EXPECTED(MaybeRV32IZcaZcbZcmpZcmt, Succeeded());
+  const auto &ExtsRV32IZcaZcbZcmpZcmt = (*MaybeRV32IZcaZcbZcmpZcmt)->getExtensions();
+  EXPECT_EQ(ExtsRV32IZcaZcbZcmpZcmt.size(), 8UL);
+  EXPECT_EQ(ExtsRV32IZcaZcbZcmpZcmt.count("i"), 1U);
+  EXPECT_EQ(ExtsRV32IZcaZcbZcmpZcmt.count("c"), 1U);
+  EXPECT_EQ(ExtsRV32IZcaZcbZcmpZcmt.count("zicsr"), 1U);
+  EXPECT_EQ(ExtsRV32IZcaZcbZcmpZcmt.count("zca"), 1U);
+  EXPECT_EQ(ExtsRV32IZcaZcbZcmpZcmt.count("zcb"), 1U);
+  EXPECT_EQ(ExtsRV32IZcaZcbZcmpZcmt.count("zce"), 1U);
+  EXPECT_EQ(ExtsRV32IZcaZcbZcmpZcmt.count("zcmp"), 1U);
+  EXPECT_EQ(ExtsRV32IZcaZcbZcmpZcmt.count("zcmt"), 1U);
+
+  // RV32 Zca+Zcb+Zcmp+Zcmt with Zcf implies Zce
+  auto MaybeRV32IZcaZcbZcfZcmpZcmt = RISCVISAInfo::parseArchString("rv32i_zca_zcb_zcf_zcmp_zcmt", true);
+  ASSERT_THAT_EXPECTED(MaybeRV32IZcaZcbZcfZcmpZcmt, Succeeded());
+  const auto &ExtsRV32IZcaZcbZcfZcmpZcmt = (*MaybeRV32IZcaZcbZcfZcmpZcmt)->getExtensions();
+  EXPECT_EQ(ExtsRV32IZcaZcbZcfZcmpZcmt.size(), 10UL);
+  EXPECT_EQ(ExtsRV32IZcaZcbZcfZcmpZcmt.count("i"), 1U);
+  EXPECT_EQ(ExtsRV32IZcaZcbZcfZcmpZcmt.count("f"), 1U);
+  EXPECT_EQ(ExtsRV32IZcaZcbZcfZcmpZcmt.count("c"), 1U);
+  EXPECT_EQ(ExtsRV32IZcaZcbZcfZcmpZcmt.count("zicsr"), 1U);
+  EXPECT_EQ(ExtsRV32IZcaZcbZcfZcmpZcmt.count("zca"), 1U);
+  EXPECT_EQ(ExtsRV32IZcaZcbZcfZcmpZcmt.count("zcb"), 1U);
+  EXPECT_EQ(ExtsRV32IZcaZcbZcfZcmpZcmt.count("zcf"), 1U);
+  EXPECT_EQ(ExtsRV32IZcaZcbZcfZcmpZcmt.count("zce"), 1U);
+  EXPECT_EQ(ExtsRV32IZcaZcbZcfZcmpZcmt.count("zcmp"), 1U);
+  EXPECT_EQ(ExtsRV32IZcaZcbZcfZcmpZcmt.count("zcmt"), 1U);
+
+  // RV32 with F but not Zcf, does not imply Zce
+  auto MaybeRV32IFZcaZcbZcmpZcmt = RISCVISAInfo::parseArchString("rv32if_zca_zcb_zcmp_zcmt", true);
+  ASSERT_THAT_EXPECTED(MaybeRV32IFZcaZcbZcmpZcmt, Succeeded());
+  const auto &ExtsRV32IFZcaZcbZcfZcmpZcmt = (*MaybeRV32IFZcaZcbZcmpZcmt)->getExtensions();
+  EXPECT_EQ(ExtsRV32IFZcaZcbZcfZcmpZcmt.size(), 7UL);
+  EXPECT_EQ(ExtsRV32IFZcaZcbZcfZcmpZcmt.count("i"), 1U);
+  EXPECT_EQ(ExtsRV32IFZcaZcbZcfZcmpZcmt.count("f"), 1U);
+  EXPECT_EQ(ExtsRV32IFZcaZcbZcfZcmpZcmt.count("zicsr"), 1U);
+  EXPECT_EQ(ExtsRV32IFZcaZcbZcfZcmpZcmt.count("zca"), 1U);
+  EXPECT_EQ(ExtsRV32IFZcaZcbZcfZcmpZcmt.count("zcb"), 1U);
+  EXPECT_EQ(ExtsRV32IFZcaZcbZcfZcmpZcmt.count("zcmp"), 1U);
+  EXPECT_EQ(ExtsRV32IFZcaZcbZcfZcmpZcmt.count("zcmt"), 1U);
+
+  // RV64 Zca+Zcb+Zcmp+Zcmt without F implies Zce
+  auto MaybeRV64IZcaZcbZcmpZcmt = RISCVISAInfo::parseArchString("rv64i_zca_zcb_zcmp_zcmt", true);
+  ASSERT_THAT_EXPECTED(MaybeRV64IZcaZcbZcmpZcmt, Succeeded());
+  const auto &ExtsRV64IZcaZcbZcmpZcmt = (*MaybeRV64IZcaZcbZcmpZcmt)->getExtensions();
+  EXPECT_EQ(ExtsRV64IZcaZcbZcmpZcmt.size(), 8UL);
+  EXPECT_EQ(ExtsRV64IZcaZcbZcmpZcmt.count("i"), 1U);
+  EXPECT_EQ(ExtsRV64IZcaZcbZcmpZcmt.count("c"), 1U);
+  EXPECT_EQ(ExtsRV64IZcaZcbZcmpZcmt.count("zicsr"), 1U);
+  EXPECT_EQ(ExtsRV64IZcaZcbZcmpZcmt.count("zca"), 1U);
+  EXPECT_EQ(ExtsRV64IZcaZcbZcmpZcmt.count("zcb"), 1U);
+  EXPECT_EQ(ExtsRV64IZcaZcbZcmpZcmt.count("zce"), 1U);
+  EXPECT_EQ(ExtsRV64IZcaZcbZcmpZcmt.count("zcmp"), 1U);
+  EXPECT_EQ(ExtsRV64IZcaZcbZcmpZcmt.count("zcmt"), 1U);
+
+  // RV64 Zca+Zcb+Zcmp+Zcmt with F implies Zce
+  auto MaybeRV64IFZcaZcbZcmpZcmt = RISCVISAInfo::parseArchString("rv64if_zca_zcb_zcmp_zcmt", true);
+  ASSERT_THAT_EXPECTED(MaybeRV64IFZcaZcbZcmpZcmt, Succeeded());
+  const auto &ExtsRV64IFZcaZcbZcmpZcmt = (*MaybeRV64IFZcaZcbZcmpZcmt)->getExtensions();
+  EXPECT_EQ(ExtsRV64IFZcaZcbZcmpZcmt.size(), 9UL);
+  EXPECT_EQ(ExtsRV64IFZcaZcbZcmpZcmt.count("i"), 1U);
+  EXPECT_EQ(ExtsRV64IFZcaZcbZcmpZcmt.count("f"), 1U);
+  EXPECT_EQ(ExtsRV64IFZcaZcbZcmpZcmt.count("c"), 1U);
+  EXPECT_EQ(ExtsRV64IFZcaZcbZcmpZcmt.count("zicsr"), 1U);
+  EXPECT_EQ(ExtsRV64IFZcaZcbZcmpZcmt.count("zca"), 1U);
+  EXPECT_EQ(ExtsRV64IFZcaZcbZcmpZcmt.count("zcb"), 1U);
+  EXPECT_EQ(ExtsRV64IFZcaZcbZcmpZcmt.count("zce"), 1U);
+  EXPECT_EQ(ExtsRV64IFZcaZcbZcmpZcmt.count("zcmp"), 1U);
+  EXPECT_EQ(ExtsRV64IFZcaZcbZcmpZcmt.count("zcmt"), 1U);
+}
+
 TEST(isSupportedExtensionWithVersion, AcceptsSingleExtensionWithVersion) {
   EXPECT_TRUE(RISCVISAInfo::isSupportedExtensionWithVersion("zbb1p0"));
   EXPECT_FALSE(RISCVISAInfo::isSupportedExtensionWithVersion("zbb"));

``````````

</details>


https://github.com/llvm/llvm-project/pull/175041


More information about the llvm-commits mailing list