Skip to content

Commit 8156816

Browse files
fangyi-zhoulanza
authored andcommitted
[CIR] Add back verification of LoopOpInterface (llvm#1641)
The verification used to require a runtime type query of `ConditionOp` which is not available outside the interface package; whereas the dialect package depends on the interface package, causing a circular dependency. This commit adds a singleton interface for `ConditionOp` to break off the circular dependency, and replaces the runtime type query using the newly added interface. Tested locally with a build with shared library enabled and verified that the build succeeds.
1 parent 1eb1b15 commit 8156816

File tree

5 files changed

+64
-61
lines changed

5 files changed

+64
-61
lines changed

clang/include/clang/CIR/Dialect/IR/CIROps.td

Lines changed: 7 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -872,11 +872,10 @@ def SelectOp : CIR_Op<"select", [Pure,
872872
// ConditionOp
873873
//===----------------------------------------------------------------------===//
874874

875-
def ConditionOp : CIR_Op<"condition", [
876-
Terminator,
877-
DeclareOpInterfaceMethods<RegionBranchTerminatorOpInterface,
878-
["getSuccessorRegions"]>
879-
]> {
875+
def ConditionOp : CIR_Op<"condition", [Terminator, CIR_ConditionOpInterface,
876+
DeclareOpInterfaceMethods<
877+
RegionBranchTerminatorOpInterface,
878+
["getSuccessorRegions"]>]> {
880879
let summary = "Loop continuation condition.";
881880
let description = [{
882881
The `cir.condition` terminates conditional regions. It takes a single
@@ -2195,10 +2194,8 @@ def BrCondOp : CIR_Op<"brcond",
21952194
// While & DoWhileOp
21962195
//===----------------------------------------------------------------------===//
21972196

2198-
class WhileOpBase<string mnemonic> : CIR_Op<mnemonic, [
2199-
LoopOpInterface,
2200-
NoRegionArguments,
2201-
]> {
2197+
class WhileOpBase<string mnemonic>
2198+
: CIR_Op<mnemonic, [CIR_LoopOpInterface, NoRegionArguments, ]> {
22022199
defvar isWhile = !eq(mnemonic, "while");
22032200
let summary = "C/C++ " # !if(isWhile, "while", "do-while") # " loop";
22042201
let builders = [
@@ -2273,7 +2270,7 @@ def DoWhileOp : WhileOpBase<"do"> {
22732270
// ForOp
22742271
//===----------------------------------------------------------------------===//
22752272

2276-
def ForOp : CIR_Op<"for", [LoopOpInterface, NoRegionArguments]> {
2273+
def ForOp : CIR_Op<"for", [CIR_LoopOpInterface, NoRegionArguments]> {
22772274
let summary = "C/C++ for loop counterpart";
22782275
let description = [{
22792276
Represents a C/C++ for loop. It consists of three regions:

clang/include/clang/CIR/Interfaces/CIRLoopOpInterface.td

Lines changed: 12 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -13,10 +13,10 @@ include "mlir/IR/OpBase.td"
1313
include "mlir/Interfaces/ControlFlowInterfaces.td"
1414
include "mlir/Interfaces/LoopLikeInterface.td"
1515

16-
def LoopOpInterface : OpInterface<"LoopOpInterface", [
17-
DeclareOpInterfaceMethods<RegionBranchOpInterface>,
18-
DeclareOpInterfaceMethods<LoopLikeOpInterface>
19-
]> {
16+
def CIR_LoopOpInterface
17+
: OpInterface<"LoopOpInterface",
18+
[DeclareOpInterfaceMethods<RegionBranchOpInterface>,
19+
DeclareOpInterfaceMethods<LoopLikeOpInterface>]> {
2020
let description = [{
2121
Contains helper functions to query properties and perform transformations
2222
on a loop.
@@ -96,4 +96,12 @@ def LoopOpInterface : OpInterface<"LoopOpInterface", [
9696
}];
9797
}
9898
99+
def CIR_ConditionOpInterface : OpInterface<"ConditionOpInterface", []> {
100+
let description = [{
101+
A singleton interface for ConditionOp only. This is used to break off a
102+
a dependency from LoopOpInterface onto ConditionOp.
103+
}];
104+
let cppNamespace = "::cir";
105+
}
106+
99107
#endif // CLANG_CIR_INTERFACES_CIRLOOPOPINTERFACE

clang/lib/CIR/Interfaces/CIRLoopOpInterface.cpp

Lines changed: 4 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -44,11 +44,10 @@ void LoopOpInterface::getLoopOpSuccessorRegions(
4444

4545
/// Verify invariants of the LoopOpInterface.
4646
llvm::LogicalResult detail::verifyLoopOpInterface(mlir::Operation *op) {
47-
// FIXME: fix this so the conditionop isn't requiring MLIRCIR
48-
// auto loopOp = mlir::cast<LoopOpInterface>(op);
49-
// if (!mlir::isa<ConditionOp>(loopOp.getCond().back().getTerminator()))
50-
// return op->emitOpError(
51-
// "expected condition region to terminate with 'cir.condition'");
47+
auto loopOp = mlir::cast<LoopOpInterface>(op);
48+
if (!mlir::isa<ConditionOpInterface>(loopOp.getCond().back().getTerminator()))
49+
return op->emitOpError(
50+
"expected condition region to terminate with 'cir.condition'");
5251
return llvm::success();
5352
}
5453

clang/test/CIR/IR/invalid.cir

Lines changed: 41 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1533,3 +1533,44 @@ cir.global external dsolocal @vfp = #cir.ptr<null> : !cir.ptr<!cir.func<(!s32i)
15331533

15341534
// expected-error @below {{integer or floating point type}}
15351535
!complex = !cir.complex<!cir.ptr<!cir.void>>
1536+
1537+
// -----
1538+
1539+
#false = #cir.bool<false> : !cir.bool
1540+
#true = #cir.bool<true> : !cir.bool
1541+
cir.func @b0() {
1542+
cir.scope {
1543+
cir.while { // expected-error {{expected condition region to terminate with 'cir.condition'}}
1544+
cir.yield
1545+
} do {
1546+
cir.br ^bb1
1547+
^bb1:
1548+
cir.return
1549+
}
1550+
}
1551+
cir.return
1552+
}
1553+
1554+
// -----
1555+
1556+
cir.func @invalid_cond_region_terminator(%arg0 : !cir.bool) -> !cir.void {
1557+
cir.do { // expected-error {{op expected condition region to terminate with 'cir.condition'}}
1558+
cir.yield
1559+
} while {
1560+
cir.yield
1561+
}
1562+
cir.return
1563+
}
1564+
1565+
// -----
1566+
1567+
cir.func @invalidConditionTerminator (%arg0 : !cir.bool) -> !cir.void {
1568+
cir.for : cond { // expected-error {{op expected condition region to terminate with 'cir.condition'}}
1569+
cir.yield
1570+
} body {
1571+
cir.yield
1572+
} step {
1573+
cir.yield
1574+
}
1575+
cir.return
1576+
}

clang/test/CIR/IR/invalid_xfail.cir

Lines changed: 0 additions & 42 deletions
This file was deleted.

0 commit comments

Comments
 (0)