[llvm] 0a35211 - [RISCV] Don't allow vector types to be used with inline asm 'r' constraint

Craig Topper via llvm-commits llvm-commits at lists.llvm.org
Thu Dec 23 18:46:49 PST 2021


Author: Craig Topper
Date: 2021-12-23T20:32:36-06:00
New Revision: 0a35211b34886423199734698116b09debc74a71

URL: https://github.com/llvm/llvm-project/commit/0a35211b34886423199734698116b09debc74a71
DIFF: https://github.com/llvm/llvm-project/commit/0a35211b34886423199734698116b09debc74a71.diff

LOG: [RISCV] Don't allow vector types to be used with inline asm 'r' constraint

The 'r' constraint uses the GPR class. There is generic support
for bitcasting and extending/truncating non-integer VTs to the
required integer VT. This doesn't work for scalable vectors and
instead crashes.

To prevent this, explicitly reject vectors. Fixed vectors might
work without crashing, but it doesn't seem worthwhile to allow.

While there remove an unnecessary level of indentation in the
"vr" and "vm" constraint handling.

Differential Revision: https://reviews.llvm.org/D115810

Added: 
    

Modified: 
    llvm/lib/Target/RISCV/RISCVISelLowering.cpp
    llvm/test/CodeGen/RISCV/inline-asm-invalid.ll

Removed: 
    


################################################################################
diff  --git a/llvm/lib/Target/RISCV/RISCVISelLowering.cpp b/llvm/lib/Target/RISCV/RISCVISelLowering.cpp
index b455fee62f543..972928f2e5b4e 100644
--- a/llvm/lib/Target/RISCV/RISCVISelLowering.cpp
+++ b/llvm/lib/Target/RISCV/RISCVISelLowering.cpp
@@ -9657,6 +9657,9 @@ RISCVTargetLowering::getRegForInlineAsmConstraint(const TargetRegisterInfo *TRI,
   if (Constraint.size() == 1) {
     switch (Constraint[0]) {
     case 'r':
+      // TODO: Support fixed vectors up to XLen for P extension?
+      if (VT.isVector())
+        break;
       return std::make_pair(0U, &RISCV::GPRRegClass);
     case 'f':
       if (Subtarget.hasStdExtZfh() && VT == MVT::f16)
@@ -9669,17 +9672,15 @@ RISCVTargetLowering::getRegForInlineAsmConstraint(const TargetRegisterInfo *TRI,
     default:
       break;
     }
-  } else {
-    if (Constraint == "vr") {
-      for (const auto *RC : {&RISCV::VRRegClass, &RISCV::VRM2RegClass,
-                             &RISCV::VRM4RegClass, &RISCV::VRM8RegClass}) {
-        if (TRI->isTypeLegalForClass(*RC, VT.SimpleTy))
-          return std::make_pair(0U, RC);
-      }
-    } else if (Constraint == "vm") {
-      if (TRI->isTypeLegalForClass(RISCV::VMV0RegClass, VT.SimpleTy))
-        return std::make_pair(0U, &RISCV::VMV0RegClass);
+  } else if (Constraint == "vr") {
+    for (const auto *RC : {&RISCV::VRRegClass, &RISCV::VRM2RegClass,
+                           &RISCV::VRM4RegClass, &RISCV::VRM8RegClass}) {
+      if (TRI->isTypeLegalForClass(*RC, VT.SimpleTy))
+        return std::make_pair(0U, RC);
     }
+  } else if (Constraint == "vm") {
+    if (TRI->isTypeLegalForClass(RISCV::VMV0RegClass, VT.SimpleTy))
+      return std::make_pair(0U, &RISCV::VMV0RegClass);
   }
 
   // Clang will correctly decode the usage of register name aliases into their

diff  --git a/llvm/test/CodeGen/RISCV/inline-asm-invalid.ll b/llvm/test/CodeGen/RISCV/inline-asm-invalid.ll
index 20ac5ef111115..14b7cb8966749 100644
--- a/llvm/test/CodeGen/RISCV/inline-asm-invalid.ll
+++ b/llvm/test/CodeGen/RISCV/inline-asm-invalid.ll
@@ -30,3 +30,15 @@ define void @constraint_f() nounwind {
   tail call void asm "fadd.d fa0, fa0, $0", "f"(double 0.0)
   ret void
 }
+
+define void @constraint_r_fixed_vec() nounwind {
+; CHECK: error: couldn't allocate input reg for constraint 'r'
+  tail call void asm "add a0, a0, $0", "r"(<4 x i32> zeroinitializer)
+  ret void
+}
+
+define void @constraint_r_scalable_vec() nounwind {
+; CHECK: error: couldn't allocate input reg for constraint 'r'
+  tail call void asm "add a0, a0, $0", "r"(<vscale x 4 x i32> zeroinitializer)
+  ret void
+}


        


More information about the llvm-commits mailing list