class AsmVariantInfo {
public:
+ std::string RegisterPrefix;
std::string TokenizingCharacters;
std::string SeparatorCharacters;
std::string BreakCharacters;
+ int AsmVariantNo;
};
/// MatchableInfo - Helper class for storing the necessary information for an
void initialize(const AsmMatcherInfo &Info,
SmallPtrSetImpl<Record*> &SingletonRegisters,
- int AsmVariantNo, StringRef RegisterPrefix,
AsmVariantInfo const &Variant);
/// validate - Return true if this matchable is a valid thing to match against
// Find the ResOperand that refers to the operand we're aliasing away
// and update it to refer to the combined operand instead.
- for (unsigned i = 0, e = ResOperands.size(); i != e; ++i) {
- ResOperand &Op = ResOperands[i];
+ for (ResOperand &Op : ResOperands) {
if (Op.Kind == ResOperand::RenderAsmOperand &&
Op.AsmOperandNum == (unsigned)SrcAsmOperand) {
Op.AsmOperandNum = DstAsmOperand;
AsmOperands.erase(AsmOperands.begin() + SrcAsmOperand);
// Adjust the ResOperand references to any AsmOperands that followed
// the one we just deleted.
- for (unsigned i = 0, e = ResOperands.size(); i != e; ++i) {
- ResOperand &Op = ResOperands[i];
+ for (ResOperand &Op : ResOperands) {
switch(Op.Kind) {
default:
// Nothing to do for operands that don't reference AsmOperands.
void MatchableInfo::initialize(const AsmMatcherInfo &Info,
SmallPtrSetImpl<Record*> &SingletonRegisters,
- int AsmVariantNo, StringRef RegisterPrefix,
AsmVariantInfo const &Variant) {
- AsmVariantID = AsmVariantNo;
+ AsmVariantID = Variant.AsmVariantNo;
AsmString =
- CodeGenInstruction::FlattenAsmStringVariants(AsmString, AsmVariantNo);
+ CodeGenInstruction::FlattenAsmStringVariants(AsmString,
+ Variant.AsmVariantNo);
tokenizeAsmString(Info, Variant);
// Collect singleton registers, if used.
for (MatchableInfo::AsmOperand &Op : AsmOperands) {
- extractSingletonRegisterForAsmOperand(Op, Info, RegisterPrefix);
+ extractSingletonRegisterForAsmOperand(Op, Info, Variant.RegisterPrefix);
if (Record *Reg = Op.SingletonReg)
SingletonRegisters.insert(Reg);
}
void MatchableInfo::tokenizeAsmString(const AsmMatcherInfo &Info,
AsmVariantInfo const &Variant) {
StringRef String = AsmString;
- unsigned Prev = 0;
+ size_t Prev = 0;
bool InTok = false;
std::string Separators = Variant.TokenizingCharacters +
Variant.SeparatorCharacters;
- for (unsigned i = 0, e = String.size(); i != e; ++i) {
+ for (size_t i = 0, e = String.size(); i != e; ++i) {
if(Variant.BreakCharacters.find(String[i]) != std::string::npos) {
if(InTok) {
addAsmOperand(Prev, i, Separators);
break;
}
- StringRef::iterator End = std::find(String.begin() + i, String.end(),'}');
- assert(End != String.end() && "Missing brace in operand reference!");
- size_t EndPos = End - String.begin();
+ size_t EndPos = String.find('}', i);
+ assert(EndPos != StringRef::npos &&
+ "Missing brace in operand reference!");
addAsmOperand(i, EndPos+1, Separators);
Prev = EndPos + 1;
i = EndPos;
// Also, check for instructions which reference the operand multiple times;
// this implies a constraint we would not honor.
std::set<std::string> OperandNames;
- for (unsigned i = 0, e = AsmOperands.size(); i != e; ++i) {
- StringRef Tok = AsmOperands[i].Token;
+ for (const AsmOperand &Op : AsmOperands) {
+ StringRef Tok = Op.Token;
if (Tok[0] == '$' && Tok.find(':') != StringRef::npos)
PrintFatalError(TheDef->getLoc(),
"matchable with operand modifier '" + Tok +
Record *AsmVariant = Target.getAsmParserVariant(VC);
std::string CommentDelimiter =
AsmVariant->getValueAsString("CommentDelimiter");
- std::string RegisterPrefix = AsmVariant->getValueAsString("RegisterPrefix");
AsmVariantInfo Variant;
+ Variant.RegisterPrefix = AsmVariant->getValueAsString("RegisterPrefix");
Variant.TokenizingCharacters =
AsmVariant->getValueAsString("TokenizingCharacters");
Variant.SeparatorCharacters =
AsmVariant->getValueAsString("SeparatorCharacters");
Variant.BreakCharacters =
AsmVariant->getValueAsString("BreakCharacters");
- int AsmVariantNo = AsmVariant->getValueAsInt("Variant");
+ Variant.AsmVariantNo = AsmVariant->getValueAsInt("Variant");
for (const CodeGenInstruction *CGI : Target.instructions()) {
auto II = llvm::make_unique<MatchableInfo>(*CGI);
- II->initialize(*this, SingletonRegisters, AsmVariantNo, RegisterPrefix,
- Variant);
+ II->initialize(*this, SingletonRegisters, Variant);
// Ignore instructions which shouldn't be matched and diagnose invalid
// instruction definitions with an error.
Records.getAllDerivedDefinitions("InstAlias");
for (unsigned i = 0, e = AllInstAliases.size(); i != e; ++i) {
auto Alias = llvm::make_unique<CodeGenInstAlias>(AllInstAliases[i],
- AsmVariantNo, Target);
+ Variant.AsmVariantNo,
+ Target);
// If the tblgen -match-prefix option is specified (for tblgen hackers),
// filter the set of instruction aliases we consider, based on the target
auto II = llvm::make_unique<MatchableInfo>(std::move(Alias));
- II->initialize(*this, SingletonRegisters, AsmVariantNo, RegisterPrefix,
- Variant);
+ II->initialize(*this, SingletonRegisters, Variant);
// Validate the alias definitions.
II->validate(CommentDelimiter, false);
StringRef Token = Op.Token;
// Check for singleton registers.
- if (Record *RegRecord = II->AsmOperands[i].SingletonReg) {
+ if (Record *RegRecord = Op.SingletonReg) {
Op.Class = RegisterClasses[RegRecord];
assert(Op.Class && Op.Class->Registers.size() == 1 &&
"Unexpected class for singleton register");
// information.
std::vector<Record*> AllTokenAliases =
Records.getAllDerivedDefinitions("TokenAlias");
- for (unsigned i = 0, e = AllTokenAliases.size(); i != e; ++i) {
- Record *Rec = AllTokenAliases[i];
+ for (Record *Rec : AllTokenAliases) {
ClassInfo *FromClass = getTokenClass(Rec->getValueAsString("FromToken"));
ClassInfo *ToClass = getTokenClass(Rec->getValueAsString("ToToken"));
if (FromClass == ToClass)
// Loop over all operands of the result instruction, determining how to
// populate them.
- for (unsigned i = 0, e = ResultInst->Operands.size(); i != e; ++i) {
- const CGIOperandList::OperandInfo &OpInfo = ResultInst->Operands[i];
-
+ for (const CGIOperandList::OperandInfo &OpInfo : ResultInst->Operands) {
// If this is a tied operand, just copy from the previously handled operand.
int TiedOp = -1;
if (OpInfo.MINumOperands == 1)
}
static unsigned getConverterOperandID(const std::string &Name,
- SetVector<std::string> &Table,
+ SmallSetVector<std::string, 16> &Table,
bool &IsNew) {
IsNew = Table.insert(Name);
static void emitConvertFuncs(CodeGenTarget &Target, StringRef ClassName,
std::vector<std::unique_ptr<MatchableInfo>> &Infos,
raw_ostream &OS) {
- SetVector<std::string> OperandConversionKinds;
- SetVector<std::string> InstructionConversionKinds;
+ SmallSetVector<std::string, 16> OperandConversionKinds;
+ SmallSetVector<std::string, 16> InstructionConversionKinds;
std::vector<std::vector<uint8_t> > ConversionTable;
size_t MaxRowLength = 2; // minimum is custom converter plus terminator.
OS << " if (A == B)\n";
OS << " return true;\n\n";
- std::string OStr;
- raw_string_ostream SS(OStr);
- unsigned Count = 0;
- SS << " switch (A) {\n";
- SS << " default:\n";
- SS << " return false;\n";
+ bool EmittedSwitch = false;
for (const auto &A : Infos) {
std::vector<StringRef> SuperClasses;
for (const auto &B : Infos) {
if (SuperClasses.empty())
continue;
- ++Count;
- SS << "\n case " << A.Name << ":\n";
+ // If this is the first SuperClass, emit the switch header.
+ if (!EmittedSwitch) {
+ OS << " switch (A) {\n"
+ OS << " default:\n";
+ OS << " return false;\n";
+ EmittedSwitch = true;
+ }
+
+ OS << "\n case " << A.Name << ":\n";
if (SuperClasses.size() == 1) {
- SS << " return B == " << SuperClasses.back().str() << ";\n";
+ OS << " return B == " << SuperClasses.back().str() << ";\n";
continue;
}
if (!SuperClasses.empty()) {
- SS << " switch (B) {\n";
- SS << " default: return false;\n";
- for (unsigned i = 0, e = SuperClasses.size(); i != e; ++i)
- SS << " case " << SuperClasses[i].str() << ": return true;\n";
- SS << " }\n";
+ OS << " switch (B) {\n";
+ OS << " default: return false;\n";
+ for (StringRef SC : SuperClasses)
+ OS << " case " << SC << ": return true;\n";
+ OS << " }\n";
} else {
// No case statement to emit
- SS << " return false;\n";
+ OS << " return false;\n";
}
}
- SS << " }\n";
+ OS << " }\n";
- // If there were case statements emitted into the string stream, write them
- // to the output stream, otherwise write the default.
- if (Count)
- OS << SS.str();
- else
+ // If there were case statements emitted into the string stream write the
+ // default.
+ if (!EmittedSwitch)
OS << " return false;\n";
OS << "}\n\n";
<< "&Operands);\n";
OS << " void convertToMapAndConstraints(unsigned Kind,\n ";
OS << " const OperandVector &Operands) override;\n";
- OS << " bool mnemonicIsValid(StringRef Mnemonic, unsigned VariantID) override;\n";
+ OS << " bool mnemonicIsValid(StringRef Mnemonic, unsigned VariantID);\n";
OS << " unsigned MatchInstructionImpl(const OperandVector &Operands,\n"
<< " MCInst &Inst,\n"
<< " uint64_t &ErrorInfo,"
}
OS << " }\n";
OS << " // Search the table.\n";
- OS << " std::pair<const MatchEntry*, const MatchEntry*>"
+ OS << " std::pair<const MatchEntry*, const MatchEntry*> "
"MnemonicRange(Start, End);\n";
OS << " unsigned SIndex = Mnemonic.empty() ? 0 : 1;\n";
OS << " if (!Mnemonic.empty())\n";
if (HasDeprecation) {
OS << " std::string Info;\n";
- OS << " if (MII.get(Inst.getOpcode()).getDeprecatedInfo(Inst, STI, Info)) {\n";
+ OS << " if (MII.get(Inst.getOpcode()).getDeprecatedInfo(Inst, getSTI(), Info)) {\n";
OS << " SMLoc Loc = ((" << Target.getName()
<< "Operand&)*Operands[0]).getStartLoc();\n";
OS << " getParser().Warning(Loc, Info, None);\n";