Revert r349041: [tblgen][disasm] Separate encodings from instructions

One of the GCC based bots is objecting to a vector of const EncodingAndInst's:
In file included from /usr/include/c++/8/vector:64,
                 from /export/users/atombot/llvm/clang-atom-d525-fedora-rel/llvm/utils/TableGen/CodeGenInstruction.h:22,
                 from /export/users/atombot/llvm/clang-atom-d525-fedora-rel/llvm/utils/TableGen/FixedLenDecoderEmitter.cpp:15:
/usr/include/c++/8/bits/stl_vector.h: In instantiation of 'class std::vector<const {anonymous}::EncodingAndInst, std::allocator<const {anonymous}::EncodingAndInst> >':
/export/users/atombot/llvm/clang-atom-d525-fedora-rel/llvm/utils/TableGen/FixedLenDecoderEmitter.cpp:375:32:   required from here
/usr/include/c++/8/bits/stl_vector.h:351:21: error: static assertion failed: std::vector must have a non-const, non-volatile value_type
       static_assert(is_same<typename remove_cv<_Tp>::type, _Tp>::value,
                     ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
/usr/include/c++/8/bits/stl_vector.h:354:21: error: static assertion failed: std::vector must have the same value_type as its allocator
       static_assert(is_same<typename _Alloc::value_type, _Tp>::value,
                     ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

llvm-svn: 349046
This commit is contained in:
Daniel Sanders 2018-12-13 15:14:21 +00:00
parent b5d284408e
commit f5f3bef035
1 changed files with 37 additions and 51 deletions

View File

@ -87,23 +87,8 @@ struct DecoderTableInfo {
DecoderSet Decoders;
};
struct EncodingAndInst {
const Record *EncodingDef;
const CodeGenInstruction *Inst;
EncodingAndInst(const Record *EncodingDef, const CodeGenInstruction *Inst)
: EncodingDef(EncodingDef), Inst(Inst) {}
};
raw_ostream &operator<<(raw_ostream &OS, const EncodingAndInst &Value) {
if (Value.EncodingDef != Value.Inst->TheDef)
OS << Value.EncodingDef->getName() << ":";
OS << Value.Inst->TheDef->getName();
return OS;
}
class FixedLenDecoderEmitter {
std::vector<EncodingAndInst> NumberedEncodings;
ArrayRef<const CodeGenInstruction *> NumberedInstructions;
public:
// Defaults preserved here for documentation, even though they aren't
@ -338,7 +323,7 @@ protected:
friend class Filter;
// Vector of codegen instructions to choose our filter.
ArrayRef<const EncodingAndInst> AllInstructions;
ArrayRef<const CodeGenInstruction *> AllInstructions;
// Vector of uid's for this filter chooser to work on.
const std::vector<unsigned> &Opcodes;
@ -366,24 +351,25 @@ protected:
const FixedLenDecoderEmitter *Emitter;
public:
FilterChooser(ArrayRef<const EncodingAndInst> Insts,
FilterChooser(ArrayRef<const CodeGenInstruction *> Insts,
const std::vector<unsigned> &IDs,
const std::map<unsigned, std::vector<OperandInfo>> &Ops,
unsigned BW, const FixedLenDecoderEmitter *E)
: AllInstructions(Insts), Opcodes(IDs), Operands(Ops),
FilterBitValues(BW, BIT_UNFILTERED), Parent(nullptr), BestIndex(-1),
BitWidth(BW), Emitter(E) {
unsigned BW,
const FixedLenDecoderEmitter *E)
: AllInstructions(Insts), Opcodes(IDs), Operands(Ops),
FilterBitValues(BW, BIT_UNFILTERED), Parent(nullptr), BestIndex(-1),
BitWidth(BW), Emitter(E) {
doFilter();
}
FilterChooser(ArrayRef<const EncodingAndInst> Insts,
FilterChooser(ArrayRef<const CodeGenInstruction *> Insts,
const std::vector<unsigned> &IDs,
const std::map<unsigned, std::vector<OperandInfo>> &Ops,
const std::vector<bit_value_t> &ParentFilterBitValues,
const FilterChooser &parent)
: AllInstructions(Insts), Opcodes(IDs), Operands(Ops),
FilterBitValues(ParentFilterBitValues), Parent(&parent), BestIndex(-1),
BitWidth(parent.BitWidth), Emitter(parent.Emitter) {
: AllInstructions(Insts), Opcodes(IDs), Operands(Ops),
FilterBitValues(ParentFilterBitValues), Parent(&parent), BestIndex(-1),
BitWidth(parent.BitWidth), Emitter(parent.Emitter) {
doFilter();
}
@ -395,7 +381,7 @@ public:
protected:
// Populates the insn given the uid.
void insnWithID(insn_t &Insn, unsigned Opcode) const {
BitsInit &Bits = getBitsField(*AllInstructions[Opcode].EncodingDef, "Inst");
BitsInit &Bits = getBitsField(*AllInstructions[Opcode]->TheDef, "Inst");
// We may have a SoftFail bitmask, which specifies a mask where an encoding
// may differ from the value in "Inst" and yet still be valid, but the
@ -403,7 +389,7 @@ protected:
//
// This is used for marking UNPREDICTABLE instructions in the ARM world.
BitsInit *SFBits =
AllInstructions[Opcode].EncodingDef->getValueAsBitsInit("SoftFail");
AllInstructions[Opcode]->TheDef->getValueAsBitsInit("SoftFail");
for (unsigned i = 0; i < BitWidth; ++i) {
if (SFBits && bitFromBits(*SFBits, i) == BIT_TRUE)
@ -413,6 +399,11 @@ protected:
}
}
// Returns the record name.
const StringRef nameWithID(unsigned Opcode) const {
return AllInstructions[Opcode]->TheDef->getName();
}
// Populates the field of the insn given the start position and the number of
// consecutive bits to scan for.
//
@ -836,7 +827,8 @@ void FixedLenDecoderEmitter::emitTable(formatted_raw_ostream &OS,
OS << (unsigned)*I++ << ", ";
if (!IsTry) {
OS << "// Opcode: " << NumberedEncodings[Opc] << "\n";
OS << "// Opcode: "
<< NumberedInstructions[Opc]->TheDef->getName() << "\n";
break;
}
@ -853,7 +845,8 @@ void FixedLenDecoderEmitter::emitTable(formatted_raw_ostream &OS,
OS << utostr(Byte) << ", ";
NumToSkip |= Byte << 16;
OS << "// Opcode: " << NumberedEncodings[Opc]
OS << "// Opcode: "
<< NumberedInstructions[Opc]->TheDef->getName()
<< ", skip to: " << ((I - Table.begin()) + NumToSkip) << "\n";
break;
}
@ -1160,7 +1153,7 @@ static void emitSinglePredicateMatch(raw_ostream &o, StringRef str,
bool FilterChooser::emitPredicateMatch(raw_ostream &o, unsigned &Indentation,
unsigned Opc) const {
ListInit *Predicates =
AllInstructions[Opc].EncodingDef->getValueAsListInit("Predicates");
AllInstructions[Opc]->TheDef->getValueAsListInit("Predicates");
bool IsFirstEmission = true;
for (unsigned i = 0; i < Predicates->size(); ++i) {
Record *Pred = Predicates->getElementAsRecord(i);
@ -1189,7 +1182,7 @@ bool FilterChooser::emitPredicateMatch(raw_ostream &o, unsigned &Indentation,
bool FilterChooser::doesOpcodeNeedPredicate(unsigned Opc) const {
ListInit *Predicates =
AllInstructions[Opc].EncodingDef->getValueAsListInit("Predicates");
AllInstructions[Opc]->TheDef->getValueAsListInit("Predicates");
for (unsigned i = 0; i < Predicates->size(); ++i) {
Record *Pred = Predicates->getElementAsRecord(i);
if (!Pred->getValue("AssemblerMatcherPredicate"))
@ -1254,10 +1247,9 @@ void FilterChooser::emitPredicateTableEntry(DecoderTableInfo &TableInfo,
void FilterChooser::emitSoftFailTableEntry(DecoderTableInfo &TableInfo,
unsigned Opc) const {
BitsInit *SFBits =
AllInstructions[Opc].EncodingDef->getValueAsBitsInit("SoftFail");
AllInstructions[Opc]->TheDef->getValueAsBitsInit("SoftFail");
if (!SFBits) return;
BitsInit *InstBits =
AllInstructions[Opc].EncodingDef->getValueAsBitsInit("Inst");
BitsInit *InstBits = AllInstructions[Opc]->TheDef->getValueAsBitsInit("Inst");
APInt PositiveMask(BitWidth, 0ULL);
APInt NegativeMask(BitWidth, 0ULL);
@ -1278,9 +1270,9 @@ void FilterChooser::emitSoftFailTableEntry(DecoderTableInfo &TableInfo,
break;
default:
// The bit is not set; this must be an error!
errs() << "SoftFail Conflict: bit SoftFail{" << i << "} in "
<< AllInstructions[Opc] << " is set but Inst{" << i
<< "} is unset!\n"
StringRef Name = AllInstructions[Opc]->TheDef->getName();
errs() << "SoftFail Conflict: bit SoftFail{" << i << "} in " << Name
<< " is set but Inst{" << i << "} is unset!\n"
<< " - You can only mark a bit as SoftFail if it is fully defined"
<< " (1/0 - not '?') in Inst\n";
return;
@ -1717,9 +1709,9 @@ void FilterChooser::emitTableEntries(DecoderTableInfo &TableInfo) const {
dumpStack(errs(), "\t\t");
for (unsigned i = 0; i < Opcodes.size(); ++i) {
errs() << '\t' << Opcodes[i] << " ";
errs() << '\t' << nameWithID(Opcodes[i]) << " ";
dumpBits(errs(),
getBitsField(*AllInstructions[Opcodes[i]].EncodingDef, "Inst"));
getBitsField(*AllInstructions[Opcodes[i]]->TheDef, "Inst"));
errs() << '\n';
}
}
@ -2334,17 +2326,13 @@ void FixedLenDecoderEmitter::run(raw_ostream &o) {
Target.reverseBitsForLittleEndianEncoding();
// Parameterize the decoders based on namespace and instruction width.
const auto &NumberedInstructions = Target.getInstructionsByEnumValue();
NumberedEncodings.reserve(NumberedInstructions.size());
for (const auto &NumberedInstruction : NumberedInstructions)
NumberedEncodings.emplace_back(NumberedInstruction->TheDef, NumberedInstruction);
NumberedInstructions = Target.getInstructionsByEnumValue();
std::map<std::pair<std::string, unsigned>,
std::vector<unsigned>> OpcMap;
std::map<unsigned, std::vector<OperandInfo>> Operands;
for (unsigned i = 0; i < NumberedEncodings.size(); ++i) {
const CodeGenInstruction *Inst = NumberedEncodings[i].Inst;
for (unsigned i = 0; i < NumberedInstructions.size(); ++i) {
const CodeGenInstruction *Inst = NumberedInstructions[i];
const Record *Def = Inst->TheDef;
unsigned Size = Def->getValueAsInt("Size");
if (Def->getValueAsString("Namespace") == "TargetOpcode" ||
@ -2365,10 +2353,8 @@ void FixedLenDecoderEmitter::run(raw_ostream &o) {
DecoderTableInfo TableInfo;
for (const auto &Opc : OpcMap) {
// Emit the decoder for this namespace+width combination.
ArrayRef<const EncodingAndInst> NumberedEncodingsRef(
NumberedEncodings.data(), NumberedEncodings.size());
FilterChooser FC(NumberedEncodingsRef, Opc.second, Operands,
8 * Opc.first.second, this);
FilterChooser FC(NumberedInstructions, Opc.second, Operands,
8*Opc.first.second, this);
// The decode table is cleared for each top level decoder function. The
// predicates and decoders themselves, however, are shared across all