[llvm] d784845 - [TableGen] Fixed 64-bit filters being sliced to 32 bits in FixedLenDecoderEmitter

Cameron Desrochers via llvm-commits llvm-commits at lists.llvm.org
Mon Dec 14 09:42:45 PST 2020


Author: Cameron Desrochers
Date: 2020-12-14T12:42:35-05:00
New Revision: d784845de1f0c97a053aab281985fa4be40fcc87

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

LOG: [TableGen] Fixed 64-bit filters being sliced to 32 bits in FixedLenDecoderEmitter

When using the FixedLenDecoderEmitter, llvm-tblgen emits tables with (OPC_ExtractField, OPC_ExtractFilterValue) opcode sequences to match the contiguous fixed bits of a given instruction's encoding. This encoding is represented in a 64-bit integer. However, the filter values were represented in a 32-bit integer. As such, instructions with fixed 64-bit encodings resulted in a table with an OPC_ExtractField for all 64 bits, followed by an OPC_ExtractFilterValue containing just the low 32 bits of their encoding, causing the filter never to match.

The exact point at which the slicing occurred was during the map insertion at line 630.

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

Added: 
    

Modified: 
    llvm/utils/TableGen/FixedLenDecoderEmitter.cpp

Removed: 
    


################################################################################
diff  --git a/llvm/utils/TableGen/FixedLenDecoderEmitter.cpp b/llvm/utils/TableGen/FixedLenDecoderEmitter.cpp
index 012264cb8c24..ca071fb79901 100644
--- a/llvm/utils/TableGen/FixedLenDecoderEmitter.cpp
+++ b/llvm/utils/TableGen/FixedLenDecoderEmitter.cpp
@@ -226,6 +226,8 @@ typedef std::vector<bit_value_t> insn_t;
 
 namespace {
 
+static const uint64_t NO_FIXED_SEGMENTS_SENTINEL = -1ULL;
+
 class FilterChooser;
 
 /// Filter - Filter works with FilterChooser to produce the decoding tree for
@@ -279,7 +281,7 @@ class Filter {
   std::vector<EncodingIDAndOpcode> VariableInstructions;
 
   // Map of well-known segment value to its delegate.
-  std::map<unsigned, std::unique_ptr<const FilterChooser>> FilterChooserMap;
+  std::map<uint64_t, std::unique_ptr<const FilterChooser>> FilterChooserMap;
 
   // Number of instructions which fall under FilteredInstructions category.
   unsigned NumFiltered;
@@ -305,7 +307,7 @@ class Filter {
   const FilterChooser &getVariableFC() const {
     assert(NumFiltered == 1);
     assert(FilterChooserMap.size() == 1);
-    return *(FilterChooserMap.find((unsigned)-1)->second);
+    return *(FilterChooserMap.find(NO_FIXED_SEGMENTS_SENTINEL)->second);
   }
 
   // Divides the decoding task into sub tasks and delegates them to the
@@ -602,10 +604,9 @@ void Filter::recurse() {
 
     // Delegates to an inferior filter chooser for further processing on this
     // group of instructions whose segment values are variable.
-    FilterChooserMap.insert(
-        std::make_pair(-1U, std::make_unique<FilterChooser>(
-                                Owner->AllInstructions, VariableInstructions,
-                                Owner->Operands, BitValueArray, *Owner)));
+    FilterChooserMap.insert(std::make_pair(NO_FIXED_SEGMENTS_SENTINEL,
+        std::make_unique<FilterChooser>(Owner->AllInstructions,
+            VariableInstructions, Owner->Operands, BitValueArray, *Owner)));
   }
 
   // No need to recurse for a singleton filtered instruction.
@@ -674,7 +675,7 @@ void Filter::emitTableEntry(DecoderTableInfo &TableInfo) const {
   for (auto &Filter : FilterChooserMap) {
     // Field value -1 implies a non-empty set of variable instructions.
     // See also recurse().
-    if (Filter.first == (unsigned)-1) {
+    if (Filter.first == NO_FIXED_SEGMENTS_SENTINEL) {
       HasFallthrough = true;
 
       // Each scope should always have at least one filter value to check


        


More information about the llvm-commits mailing list