summaryrefslogtreecommitdiffstats
path: root/llvm/utils
diff options
context:
space:
mode:
Diffstat (limited to 'llvm/utils')
-rw-r--r--llvm/utils/TableGen/GlobalISelEmitter.cpp69
1 files changed, 44 insertions, 25 deletions
diff --git a/llvm/utils/TableGen/GlobalISelEmitter.cpp b/llvm/utils/TableGen/GlobalISelEmitter.cpp
index d1821b64dd8..246af4c3a38 100644
--- a/llvm/utils/TableGen/GlobalISelEmitter.cpp
+++ b/llvm/utils/TableGen/GlobalISelEmitter.cpp
@@ -182,14 +182,6 @@ static Error failedImport(const Twine &Reason) {
static Error isTrivialOperatorNode(const TreePatternNode *N) {
std::string Explanation = "";
std::string Separator = "";
- if (N->isLeaf()) {
- if (isa<IntInit>(N->getLeafValue()))
- return Error::success();
-
- Explanation = "Is a leaf";
- Separator = ", ";
- }
-
if (N->hasAnyPredicate()) {
Explanation = Separator + "Has a predicate (" + explainPredicates(N) + ")";
Separator = ", ";
@@ -200,7 +192,7 @@ static Error isTrivialOperatorNode(const TreePatternNode *N) {
Separator = ", ";
}
- if (!N->isLeaf() && !N->hasAnyPredicate() && !N->getTransformFn())
+ if (!N->hasAnyPredicate() && !N->getTransformFn())
return Error::success();
return failedImport(Explanation);
@@ -2287,8 +2279,42 @@ Expected<RuleMatcher> GlobalISelEmitter::runOnPattern(const PatternToMatch &P) {
return failedImport("Src pattern root isn't a trivial operator (" +
toString(std::move(Err)) + ")");
- if (Dst->isLeaf())
+ InstructionMatcher &InsnMatcherTemp = M.addInstructionMatcher(Src->getName());
+ unsigned TempOpIdx = 0;
+ auto InsnMatcherOrError =
+ createAndImportSelDAGMatcher(InsnMatcherTemp, Src, TempOpIdx);
+ if (auto Error = InsnMatcherOrError.takeError())
+ return std::move(Error);
+ InstructionMatcher &InsnMatcher = InsnMatcherOrError.get();
+
+ if (Dst->isLeaf()) {
+ Record *RCDef = getInitValueAsRegClass(Dst->getLeafValue());
+
+ const CodeGenRegisterClass &RC = Target.getRegisterClass(RCDef);
+ if (RCDef) {
+ // We need to replace the def and all its uses with the specified
+ // operand. However, we must also insert COPY's wherever needed.
+ // For now, emit a copy and let the register allocator clean up.
+ auto &DstI = Target.getInstruction(RK.getDef("COPY"));
+ const auto &DstIOperand = DstI.Operands[0];
+
+ OperandMatcher &OM0 = InsnMatcher.getOperand(0);
+ OM0.setSymbolicName(DstIOperand.Name);
+ OM0.addPredicate<RegisterBankOperandMatcher>(RC);
+
+ auto &DstMIBuilder = M.addAction<BuildMIAction>(0, &DstI, InsnMatcher);
+ DstMIBuilder.addRenderer<CopyRenderer>(0, InsnMatcher, DstIOperand.Name);
+ DstMIBuilder.addRenderer<CopyRenderer>(0, InsnMatcher, Dst->getName());
+ M.addAction<ConstrainOperandToRegClassAction>(0, 0, RC);
+
+ // We're done with this pattern! It's eligible for GISel emission; return
+ // it.
+ ++NumPatternImported;
+ return std::move(M);
+ }
+
return failedImport("Dst pattern root isn't a known leaf");
+ }
// Start with the defined operands (i.e., the results of the root operator).
Record *DstOp = Dst->getOperator();
@@ -2301,14 +2327,6 @@ Expected<RuleMatcher> GlobalISelEmitter::runOnPattern(const PatternToMatch &P) {
to_string(Src->getExtTypes().size()) + " def(s) vs " +
to_string(DstI.Operands.NumDefs) + " def(s))");
- InstructionMatcher &InsnMatcherTemp = M.addInstructionMatcher(Src->getName());
- unsigned TempOpIdx = 0;
- auto InsnMatcherOrError =
- createAndImportSelDAGMatcher(InsnMatcherTemp, Src, TempOpIdx);
- if (auto Error = InsnMatcherOrError.takeError())
- return std::move(Error);
- InstructionMatcher &InsnMatcher = InsnMatcherOrError.get();
-
// The root of the match also has constraints on the register bank so that it
// matches the result instruction.
unsigned OpIdx = 0;
@@ -2537,13 +2555,14 @@ void GlobalISelEmitter::run(raw_ostream &OS) {
// for the matcher to reference them with.
std::vector<LLTCodeGen> TypeObjects = {
LLT::scalar(8), LLT::scalar(16), LLT::scalar(32),
- LLT::scalar(64), LLT::scalar(80), LLT::vector(8, 1),
- LLT::vector(16, 1), LLT::vector(32, 1), LLT::vector(64, 1),
- LLT::vector(8, 8), LLT::vector(16, 8), LLT::vector(32, 8),
- LLT::vector(64, 8), LLT::vector(4, 16), LLT::vector(8, 16),
- LLT::vector(16, 16), LLT::vector(32, 16), LLT::vector(2, 32),
- LLT::vector(4, 32), LLT::vector(8, 32), LLT::vector(16, 32),
- LLT::vector(2, 64), LLT::vector(4, 64), LLT::vector(8, 64),
+ LLT::scalar(64), LLT::scalar(80), LLT::scalar(128),
+ LLT::vector(8, 1), LLT::vector(16, 1), LLT::vector(32, 1),
+ LLT::vector(64, 1), LLT::vector(8, 8), LLT::vector(16, 8),
+ LLT::vector(32, 8), LLT::vector(64, 8), LLT::vector(4, 16),
+ LLT::vector(8, 16), LLT::vector(16, 16), LLT::vector(32, 16),
+ LLT::vector(2, 32), LLT::vector(4, 32), LLT::vector(8, 32),
+ LLT::vector(16, 32), LLT::vector(2, 64), LLT::vector(4, 64),
+ LLT::vector(8, 64),
};
std::sort(TypeObjects.begin(), TypeObjects.end());
OS << "enum {\n";
OpenPOWER on IntegriCloud