[llvm-branch-commits] [RISCV] Select the capability ABI by default when the Y extension is enabled (PR #213411)

via llvm-branch-commits llvm-branch-commits at lists.llvm.org
Fri Jul 31 22:53:01 PDT 2026


llvmorg-github-actions[bot] wrote:


<!--LLVM PR SUMMARY COMMENT-->

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

Author: Alexander Richardson (arichardson)

<details>
<summary>Changes</summary>

computeDefaultABI() previously had no knowledge of the Y (CHERI)
extension, so a target with Y enabled and no explicit -target-abi
would fall back to the plain integer ABI instead of il32pc64(d)/
l64pc128(d).

This change was created with the help of AI tools


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


5 Files Affected:

- (modified) llvm/lib/TargetParser/RISCVISAInfo.cpp (+10-7) 
- (modified) llvm/test/CodeGen/RISCV/attributes.ll (+1-1) 
- (modified) llvm/test/CodeGen/RISCV/rvy/rvy-invalid-operands.mir (+2-2) 
- (modified) llvm/unittests/Target/RISCV/RISCVBaseInfoTest.cpp (+25) 
- (modified) llvm/unittests/TargetParser/RISCVISAInfoTest.cpp (+16) 


``````````diff
diff --git a/llvm/lib/TargetParser/RISCVISAInfo.cpp b/llvm/lib/TargetParser/RISCVISAInfo.cpp
index 9d4ce85efe187..5ec7d456eb36a 100644
--- a/llvm/lib/TargetParser/RISCVISAInfo.cpp
+++ b/llvm/lib/TargetParser/RISCVISAInfo.cpp
@@ -1082,24 +1082,27 @@ RISCVISAInfo::postProcessAndChecking(std::unique_ptr<RISCVISAInfo> &&ISAInfo) {
 }
 
 StringRef RISCVISAInfo::computeDefaultABI() const {
+  bool HasY = Exts.count("y") != 0;
   if (XLen == 32) {
     if (Exts.count("xcheriot"))
       return "cheriot";
     if (Exts.count("e"))
-      return "ilp32e";
+      return HasY ? "il32pc64e" : "ilp32e";
     if (Exts.count("d"))
-      return "ilp32d";
+      return HasY ? "il32pc64d" : "ilp32d";
     if (Exts.count("f"))
-      return "ilp32f";
-    return "ilp32";
+      return HasY ? "il32pc64f" : "ilp32f";
+    return HasY ? "il32pc64" : "ilp32";
   } else if (XLen == 64) {
+    // There is no l64pc128e ABI, so RV64E still uses the integer ABI even
+    // when the Y extension is enabled.
     if (Exts.count("e"))
       return "lp64e";
     if (Exts.count("d"))
-      return "lp64d";
+      return HasY ? "l64pc128d" : "lp64d";
     if (Exts.count("f"))
-      return "lp64f";
-    return "lp64";
+      return HasY ? "l64pc128f" : "lp64f";
+    return HasY ? "l64pc128" : "lp64";
   }
   llvm_unreachable("Invalid XLEN");
 }
diff --git a/llvm/test/CodeGen/RISCV/attributes.ll b/llvm/test/CodeGen/RISCV/attributes.ll
index e5f1aa0292dd9..a8775d0faa7a8 100644
--- a/llvm/test/CodeGen/RISCV/attributes.ll
+++ b/llvm/test/CodeGen/RISCV/attributes.ll
@@ -323,7 +323,7 @@
 ; RUN: llc -mtriple=riscv64 -mattr=+sdext  %s -o - | FileCheck --check-prefix=RV64SDEXT %s
 ; RUN: llc -mtriple=riscv64 -mattr=+sdtrig  %s -o - | FileCheck --check-prefix=RV64SDTRIG %s
 ; RUN: llc -mtriple=riscv64 -mattr=+experimental-p %s -o - | FileCheck --check-prefix=RV64P %s
-; RUN: llc -mtriple=riscv64 -mattr=+experimental-y %s -o - | FileCheck --check-prefix=RV64Y %s
+; RUN: llc -mtriple=riscv64 -mattr=+experimental-y -target-abi lp64 %s -o - | FileCheck --check-prefix=RV64Y %s
 ; RUN: llc -mtriple=riscv64 -mattr=+experimental-zibi %s -o - | FileCheck --check-prefix=RV64ZIBI %s
 ; RUN: llc -mtriple=riscv64 -mattr=+experimental-zilx %s -o - | FileCheck --check-prefix=RV64ZILX %s
 ; RUN: llc -mtriple=riscv64 -mattr=+experimental-zvqwbdota8i %s -o - | FileCheck --check-prefixes=CHECK,RV64ZVQWBDOTA8I %s
diff --git a/llvm/test/CodeGen/RISCV/rvy/rvy-invalid-operands.mir b/llvm/test/CodeGen/RISCV/rvy/rvy-invalid-operands.mir
index 269ba1f4da870..d5939613b9b65 100644
--- a/llvm/test/CodeGen/RISCV/rvy/rvy-invalid-operands.mir
+++ b/llvm/test/CodeGen/RISCV/rvy/rvy-invalid-operands.mir
@@ -1,6 +1,6 @@
-# RUN: not --crash llc -mtriple=riscv32 -mattr=+experimental-y -run-pass machineverifier %s -o - 2>&1 \
+# RUN: not --crash llc -mtriple=riscv32 -mattr=+experimental-y -target-abi ilp32 -run-pass machineverifier %s -o - 2>&1 \
 # RUN:    | FileCheck %s --check-prefixes=CHECK,CHECK-32 --implicit-check-not="Bad machine code"
-# RUN: not --crash llc -mtriple=riscv64 -mattr=+experimental-y -run-pass machineverifier %s -o - 2>&1 \
+# RUN: not --crash llc -mtriple=riscv64 -mattr=+experimental-y -target-abi lp64 -run-pass machineverifier %s -o - 2>&1 \
 # RUN:    | FileCheck %s --check-prefixes=CHECK,CHECK-64  --implicit-check-not="Bad machine code"
 
 # CHECK:      *** Bad machine code: Invalid immediate ***
diff --git a/llvm/unittests/Target/RISCV/RISCVBaseInfoTest.cpp b/llvm/unittests/Target/RISCV/RISCVBaseInfoTest.cpp
index aaec27e166256..0e368953dcbda 100644
--- a/llvm/unittests/Target/RISCV/RISCVBaseInfoTest.cpp
+++ b/llvm/unittests/Target/RISCV/RISCVBaseInfoTest.cpp
@@ -57,6 +57,31 @@ TEST(ComputeTargetABI, SelectsExpectedABI) {
   EXPECT_EQ(computeTargetABI("riscv64", "+f"), RISCVABI::ABI_LP64F);
   EXPECT_EQ(computeTargetABI("riscv64", "+f,+d"), RISCVABI::ABI_LP64D);
 
+  // With the Y extension enabled and no explicit -target-abi, the capability
+  // ABI is selected by default.
+  EXPECT_EQ(computeTargetABI("riscv32", "+experimental-y"),
+            RISCVABI::ABI_IL32PC64);
+  EXPECT_EQ(computeTargetABI("riscv32", "+experimental-y,+f"),
+            RISCVABI::ABI_IL32PC64F);
+  EXPECT_EQ(computeTargetABI("riscv32", "+experimental-y,+f,+d"),
+            RISCVABI::ABI_IL32PC64D);
+  EXPECT_EQ(computeTargetABI("riscv64", "+experimental-y"),
+            RISCVABI::ABI_L64PC128);
+  EXPECT_EQ(computeTargetABI("riscv64", "+experimental-y,+f"),
+            RISCVABI::ABI_L64PC128F);
+  EXPECT_EQ(computeTargetABI("riscv64", "+experimental-y,+f,+d"),
+            RISCVABI::ABI_L64PC128D);
+
+  // An explicitly requested ABI is unaffected by the Y-based default: even
+  // with Y (and F/D) enabled, asking for the plain integer ABI still gives
+  // the integer ABI rather than the capability one.
+  EXPECT_EQ(
+      computeTargetABI("riscv32", "+experimental-y", /*ABIName=*/"ilp32"),
+      RISCVABI::ABI_ILP32);
+  EXPECT_EQ(computeTargetABI("riscv64", "+experimental-y,+f,+d",
+                              /*ABIName=*/"lp64d"),
+            RISCVABI::ABI_LP64D);
+
   // CHERIoT always selects the cheriot ABI by default.
   EXPECT_EQ(computeTargetABI("riscv32", "+xcheriot"), RISCVABI::ABI_CHERIOT);
 }
diff --git a/llvm/unittests/TargetParser/RISCVISAInfoTest.cpp b/llvm/unittests/TargetParser/RISCVISAInfoTest.cpp
index 04cbe8b9f661d..769f28ed7a3ff 100644
--- a/llvm/unittests/TargetParser/RISCVISAInfoTest.cpp
+++ b/llvm/unittests/TargetParser/RISCVISAInfoTest.cpp
@@ -1260,6 +1260,22 @@ TEST(ComputeDefaultABI, SelectsExpectedABI) {
   EXPECT_EQ(GetABIFromFeatures(64, {"+f", "+d"}), "lp64d");
   EXPECT_EQ(GetABIFromFeatures(64, {"+e"}), "lp64e");
 
+  // With the Y extension enabled, the capability ABI is selected by default.
+  // Arch strings can't currently combine 'y' with 'e', or place 'y' anywhere
+  // other than right after the base ISA letter (see RejectsInvalidYPosition),
+  // so use parseFeatures to build the extension sets directly instead.
+  EXPECT_EQ(GetABIFromFeatures(32, {"+experimental-y"}), "il32pc64");
+  EXPECT_EQ(GetABIFromFeatures(32, {"+experimental-y", "+f"}), "il32pc64f");
+  EXPECT_EQ(GetABIFromFeatures(32, {"+experimental-y", "+f", "+d"}),
+            "il32pc64d");
+  EXPECT_EQ(GetABIFromFeatures(32, {"+experimental-y", "+e"}), "il32pc64e");
+  EXPECT_EQ(GetABIFromFeatures(64, {"+experimental-y"}), "l64pc128");
+  EXPECT_EQ(GetABIFromFeatures(64, {"+experimental-y", "+f"}), "l64pc128f");
+  EXPECT_EQ(GetABIFromFeatures(64, {"+experimental-y", "+f", "+d"}),
+            "l64pc128d");
+  // There is no l64pc128e ABI, so RV64E+Y still defaults to the integer ABI.
+  EXPECT_EQ(GetABIFromFeatures(64, {"+experimental-y", "+e"}), "lp64e");
+
   // CHERIoT always selects the cheriot ABI by default.
   EXPECT_EQ(GetABIFromFeatures(32, {"+xcheriot"}), "cheriot");
 }

``````````

</details>


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


More information about the llvm-branch-commits mailing list