Add an instruction deprecation feature to TableGen.

The 'Deprecated' class allows you to specify a SubtargetFeature that the
instruction is deprecated on.

The 'ComplexDeprecationPredicate' class allows you to define a custom
predicate that is called to check for deprecation.
For example:
  ComplexDeprecationPredicate<"MCR">

would mean you would have to define the following function:
  bool getMCRDeprecationInfo(MCInst &MI, MCSubtargetInfo &STI,
                             std::string &Info)

Which returns 'false' for not deprecated, and 'true' for deprecated
and store the warning message in 'Info'.

The MCTargetAsmParser constructor was chaned to take an extra argument of
the MCInstrInfo class, so out-of-tree targets will need to be changed.



git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@190598 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
Joey Gouly
2013-09-12 10:28:05 +00:00
parent f9d2d2dc89
commit 715d98d657
20 changed files with 144 additions and 51 deletions

View File

@@ -430,6 +430,9 @@ struct MatchableInfo {
/// function.
std::string ConversionFnKind;
/// If this instruction is deprecated in some form.
bool HasDeprecation;
MatchableInfo(const CodeGenInstruction &CGI)
: AsmVariantID(0), TheDef(CGI.TheDef), DefRec(&CGI),
AsmString(CGI.AsmString) {
@@ -779,6 +782,13 @@ void MatchableInfo::initialize(const AsmMatcherInfo &Info,
if (Record *Reg = AsmOperands[i].SingletonReg)
SingletonRegisters.insert(Reg);
}
const RecordVal *DepMask = TheDef->getValue("DeprecatedFeatureMask");
if (!DepMask)
DepMask = TheDef->getValue("ComplexDeprecationPredicate");
HasDeprecation =
DepMask ? !DepMask->getValue()->getAsUnquotedString().empty() : false;
}
/// tokenizeAsmString - Tokenize a simplified assembly string.
@@ -2743,11 +2753,13 @@ void AsmMatcherEmitter::run(raw_ostream &OS) {
size_t MaxNumOperands = 0;
unsigned MaxMnemonicIndex = 0;
bool HasDeprecation = false;
for (std::vector<MatchableInfo*>::const_iterator it =
Info.Matchables.begin(), ie = Info.Matchables.end();
it != ie; ++it) {
MatchableInfo &II = **it;
MaxNumOperands = std::max(MaxNumOperands, II.AsmOperands.size());
HasDeprecation |= II.HasDeprecation;
// Store a pascal-style length byte in the mnemonic.
std::string LenMnemonic = char(II.Mnemonic.size()) + II.Mnemonic.str();
@@ -3018,6 +3030,14 @@ void AsmMatcherEmitter::run(raw_ostream &OS) {
if (!InsnCleanupFn.empty())
OS << " " << InsnCleanupFn << "(Inst);\n";
if (HasDeprecation) {
OS << " std::string Info;\n";
OS << " if (MII.get(Inst.getOpcode()).getDeprecatedInfo(Inst, STI, Info)) {\n";
OS << " SMLoc Loc = ((" << Target.getName() << "Operand*)Operands[0])->getStartLoc();\n";
OS << " Parser.Warning(Loc, Info, None);\n";
OS << " }\n";
}
OS << " return Match_Success;\n";
OS << " }\n\n";

View File

@@ -337,6 +337,20 @@ CodeGenInstruction::CodeGenInstruction(Record *R)
// Parse the DisableEncoding field.
Operands.ProcessDisableEncoding(R->getValueAsString("DisableEncoding"));
// First check for a ComplexDeprecationPredicate.
if (R->getValue("ComplexDeprecationPredicate")) {
HasComplexDeprecationPredicate = true;
DeprecatedReason = R->getValueAsString("ComplexDeprecationPredicate");
} else if (RecordVal *Dep = R->getValue("DeprecatedFeatureMask")) {
// Check if we have a Subtarget feature mask.
HasComplexDeprecationPredicate = false;
DeprecatedReason = Dep->getValue()->getAsString();
} else {
// This instruction isn't deprecated.
HasComplexDeprecationPredicate = false;
DeprecatedReason = "";
}
}
/// HasOneImplicitDefWithKnownVT - If the instruction has at least one

View File

@@ -248,6 +248,9 @@ namespace llvm {
bool isCodeGenOnly;
bool isPseudo;
std::string DeprecatedReason;
bool HasComplexDeprecationPredicate;
/// Are there any undefined flags?
bool hasUndefFlags() const {
return mayLoad_Unset || mayStore_Unset || hasSideEffects_Unset;

View File

@@ -514,6 +514,19 @@ void InstrInfoEmitter::emitRecord(const CodeGenInstruction &Inst, unsigned Num,
else
OS << "OperandInfo" << OpInfo.find(OperandInfo)->second;
CodeGenTarget &Target = CDP.getTargetInfo();
if (Inst.HasComplexDeprecationPredicate)
// Emit a function pointer to the complex predicate method.
OS << ",0"
<< ",&get" << Inst.DeprecatedReason << "DeprecationInfo";
else if (!Inst.DeprecatedReason.empty())
// Emit the Subtarget feature.
OS << "," << Target.getInstNamespace() << "::" << Inst.DeprecatedReason
<< ",0";
else
// Instruction isn't deprecated.
OS << ",0,0";
OS << " }, // Inst #" << Num << " = " << Inst.TheDef->getName() << "\n";
}