[PATCH] D15755: TableGen: Add IsOptional field to AsmOperandClass

Tom Stellard via llvm-commits llvm-commits at lists.llvm.org
Wed Dec 23 11:10:44 PST 2015


tstellarAMD created this revision.
tstellarAMD added a subscriber: llvm-commits.

This makes it possible to specify some operands as optional to the AsmMatcher.
Setting this field to true will prevent the AsmMatcher from emitting
'too few operands' errors when there are missing optional operands.

http://reviews.llvm.org/D15755

Files:
  include/llvm/Target/Target.td
  utils/TableGen/AsmMatcherEmitter.cpp

Index: utils/TableGen/AsmMatcherEmitter.cpp
===================================================================
--- utils/TableGen/AsmMatcherEmitter.cpp
+++ utils/TableGen/AsmMatcherEmitter.cpp
@@ -199,6 +199,10 @@
 
   /// For custom match classes: the diagnostic kind for when the predicate fails.
   std::string DiagnosticType;
+
+  /// Is this operand optional and not always required.
+  bool IsOptional;
+
 public:
   /// isRegisterClass() - Check if this is a register class.
   bool isRegisterClass() const {
@@ -1058,6 +1062,7 @@
     Entry->RenderMethod = "<invalid>";
     Entry->ParserMethod = "";
     Entry->DiagnosticType = "";
+    Entry->IsOptional = false;
   }
 
   return Entry;
@@ -1193,6 +1198,7 @@
     CI->Registers = RS;
     // FIXME: diagnostic type.
     CI->DiagnosticType = "";
+    CI->IsOptional = false;
     RegisterSetClasses.insert(std::make_pair(RS, CI));
     ++Index;
   }
@@ -1307,6 +1313,10 @@
     if (StringInit *SI = dyn_cast<StringInit>(DiagnosticType))
       CI->DiagnosticType = SI->getValue();
 
+    Init *IsOptional = Rec->getValueInit("IsOptional");
+    if (BitInit *BI = dyn_cast<BitInit>(IsOptional))
+      CI->IsOptional = BI->getValue();
+
     ++Index;
   }
 }
@@ -2041,6 +2051,7 @@
      << "/// instruction matching.\n";
   OS << "enum MatchClassKind {\n";
   OS << "  InvalidMatchClass = 0,\n";
+  OS << "  OptionalMatchClass = 1,\n";
   for (const auto &CI : Infos) {
     OS << "  " << CI.Name << ", // ";
     if (CI.Kind == ClassInfo::Token) {
@@ -2132,6 +2143,8 @@
   SS << "    return false;\n";
   for (const auto &A : Infos) {
     std::vector<StringRef> SuperClasses;
+    if (A.IsOptional)
+      SuperClasses.push_back("OptionalMatchClass");
     for (const auto &B : Infos) {
       if (&A != &B && A.isSubsetOf(B))
         SuperClasses.push_back(B.Name);
@@ -2976,7 +2989,8 @@
   OS << "    for (unsigned i = SIndex; i != " << MaxNumOperands << "; ++i) {\n";
   OS << "      auto Formal = static_cast<MatchClassKind>(it->Classes[i]);\n";
   OS << "      if (i >= Operands.size()) {\n";
-  OS << "        OperandsValid = (Formal == " <<"InvalidMatchClass);\n";
+  OS << "        OperandsValid = (Formal == " <<"InvalidMatchClass) || " <<
+                                 "isSubclass(Formal, OptionalMatchClass);\n";
   OS << "        if (!OperandsValid) ErrorInfo = i;\n";
   OS << "        break;\n";
   OS << "      }\n";
Index: include/llvm/Target/Target.td
===================================================================
--- include/llvm/Target/Target.td
+++ include/llvm/Target/Target.td
@@ -605,6 +605,10 @@
   // match failure error message. By default, use a generic "invalid operand"
   // diagnostic. The target AsmParser maps these codes to text.
   string DiagnosticType = "";
+
+  /// Set to 1 if this operand is optional and not always required.  Optional
+  /// operands must be at the end of the operand list.
+  bit IsOptional = 0;
 }
 
 def ImmAsmOperand : AsmOperandClass {


-------------- next part --------------
A non-text attachment was scrubbed...
Name: D15755.43552.patch
Type: text/x-patch
Size: 2973 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20151223/238afba2/attachment.bin>


More information about the llvm-commits mailing list