Skip to content

Commit 1ed1dd6

Browse files
author
Jessica Paquette
committedFeb 9, 2019
[GlobalISel] Skip patterns that define complex suboperands twice instead of dying
If we run into a pattern that looks like this: add (complex $x, $y) (complex $x, $z) We should skip the pattern instead of asserting/doing something unpredictable. This makes us return an Error in that case, and adds a testcase for skipped patterns. Differential Revision: https://reviews.llvm.org/D57980 llvm-svn: 353586
1 parent 760fee2 commit 1ed1dd6

File tree

2 files changed

+61
-6
lines changed

2 files changed

+61
-6
lines changed
 
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,45 @@
1+
// RUN: llvm-tblgen -warn-on-skipped-patterns -gen-global-isel -I %p/../../include %s -o /dev/null 2>&1 | FileCheck %s
2+
include "llvm/Target/Target.td"
3+
4+
//===- Boiler plate target code -===//
5+
def MyTargetISA : InstrInfo;
6+
def MyTarget : Target { let InstructionSet = MyTargetISA; }
7+
8+
let TargetPrefix = "mytarget" in {
9+
def int_mytarget_nop : Intrinsic<[llvm_i32_ty], [llvm_i32_ty], [IntrNoMem]>;
10+
}
11+
12+
def R0 : Register<"r0"> { let Namespace = "MyTarget"; }
13+
def GPR32 : RegisterClass<"MyTarget", [i32], 32, (add R0)>;
14+
15+
class I<dag OOps, dag IOps, list<dag> Pat>
16+
: Instruction {
17+
let Namespace = "MyTarget";
18+
let OutOperandList = OOps;
19+
let InOperandList = IOps;
20+
let Pattern = Pat;
21+
}
22+
23+
def complex : Operand<i32>, ComplexPattern<i32, 2, "SelectComplexPattern", []> {
24+
let MIOperandInfo = (ops i32imm, i32imm);
25+
}
26+
27+
def gi_complex :
28+
GIComplexOperandMatcher<s32, "selectComplexPattern">,
29+
GIComplexPatternEquiv<complex>;
30+
def complex_rr : Operand<i32>, ComplexPattern<i32, 2, "SelectComplexPatternRR", []> {
31+
let MIOperandInfo = (ops GPR32, GPR32);
32+
}
33+
34+
def gi_complex_rr :
35+
GIComplexOperandMatcher<s32, "selectComplexPatternRR">,
36+
GIComplexPatternEquiv<complex_rr>;
37+
38+
def INSN : I<(outs GPR32:$dst), (ins GPR32:$src1, complex:$src2), []>;
39+
40+
//===- Bail out when we define a variable twice wrt complex suboperands. -===//
41+
42+
// CHECK: warning: Skipped pattern: Complex suboperand referenced more than once (Operand: x)
43+
def : Pat<(add (complex_rr GPR32:$x, GPR32:$y),
44+
(complex_rr GPR32:$x, GPR32:$z)),
45+
(INSN GPR32:$z, complex:$y)>;

‎llvm/utils/TableGen/GlobalISelEmitter.cpp

+16-6
Original file line numberDiff line numberDiff line change
@@ -881,12 +881,19 @@ class RuleMatcher : public Matcher {
881881

882882
void defineOperand(StringRef SymbolicName, OperandMatcher &OM);
883883

884-
void defineComplexSubOperand(StringRef SymbolicName, Record *ComplexPattern,
885-
unsigned RendererID, unsigned SubOperandID) {
886-
assert(ComplexSubOperands.count(SymbolicName) == 0 && "Already defined");
884+
Error defineComplexSubOperand(StringRef SymbolicName, Record *ComplexPattern,
885+
unsigned RendererID, unsigned SubOperandID) {
886+
if (ComplexSubOperands.count(SymbolicName))
887+
return failedImport(
888+
"Complex suboperand referenced more than once (Operand: " +
889+
SymbolicName + ")");
890+
887891
ComplexSubOperands[SymbolicName] =
888892
std::make_tuple(ComplexPattern, RendererID, SubOperandID);
893+
894+
return Error::success();
889895
}
896+
890897
Optional<DefinedComplexPatternSubOperand>
891898
getComplexSubOperand(StringRef SymbolicName) const {
892899
const auto &I = ComplexSubOperands.find(SymbolicName);
@@ -3421,9 +3428,12 @@ Error GlobalISelEmitter::importChildMatcher(RuleMatcher &Rule,
34213428

34223429
for (unsigned i = 0, e = SrcChild->getNumChildren(); i != e; ++i) {
34233430
auto *SubOperand = SrcChild->getChild(i);
3424-
if (!SubOperand->getName().empty())
3425-
Rule.defineComplexSubOperand(SubOperand->getName(),
3426-
SrcChild->getOperator(), RendererID, i);
3431+
if (!SubOperand->getName().empty()) {
3432+
if (auto Error = Rule.defineComplexSubOperand(SubOperand->getName(),
3433+
SrcChild->getOperator(),
3434+
RendererID, i))
3435+
return Error;
3436+
}
34273437
}
34283438

34293439
return Error::success();

0 commit comments

Comments
 (0)