Skip to content

Commit 04c08ab

Browse files
author
Scott Manley
committed
[MLIR][IR] add -mlir-print-unique-ids to AsmPrinter
Add an option to unique the numbers of values, block arguments and naming conflicts when requested and/or printing generic op form. This is helpful when debugging. For example, if you have: scf.for %0 = %1 = opA %0 scf.for %0 = %1 = opB %0 And you get a verifier error which says opB's "operand #0 does not dominate this use", it looks like %0 does dominate the use. This is not intuitive. If these were numbered uniquely, it would look like: scf.for %0 = %1 = opA %0 scf.for %2 = %3 = opB %0 And thus, much clearer as to why you are getting the error since %0 is out of scope. Since generic op form should aim to give you the most possible information, it seems like a good idea to use unique numbers in this situation. Adding an option also gives those an option to use it outside of generic op form.
1 parent d584df6 commit 04c08ab

File tree

3 files changed

+66
-3
lines changed

3 files changed

+66
-3
lines changed

mlir/include/mlir/IR/OperationSupport.h

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1219,6 +1219,9 @@ class OpPrintingFlags {
12191219
/// Return if the printer should print users of values.
12201220
bool shouldPrintValueUsers() const;
12211221

1222+
/// Return if printer should use unique IDs.
1223+
bool shouldPrintUniqueIDs() const;
1224+
12221225
private:
12231226
/// Elide large elements attributes if the number of elements is larger than
12241227
/// the upper limit.
@@ -1249,6 +1252,9 @@ class OpPrintingFlags {
12491252

12501253
/// Print users of values.
12511254
bool printValueUsersFlag : 1;
1255+
1256+
/// Print unique ids for values, block arguments and naming conflicts
1257+
bool printUniqueIDsFlag : 1;
12521258
};
12531259

12541260
//===----------------------------------------------------------------------===//

mlir/lib/IR/AsmPrinter.cpp

Lines changed: 20 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -189,6 +189,11 @@ struct AsmPrinterOptions {
189189
"mlir-print-value-users", llvm::cl::init(false),
190190
llvm::cl::desc(
191191
"Print users of operation results and block arguments as a comment")};
192+
193+
llvm::cl::opt<bool> printUniqueIDs{
194+
"mlir-print-unique-ids", llvm::cl::init(false),
195+
llvm::cl::desc("Print unique id numbers for values, block arguments and "
196+
"naming conflicts across all regions")};
192197
};
193198
} // namespace
194199

@@ -206,7 +211,7 @@ OpPrintingFlags::OpPrintingFlags()
206211
: printDebugInfoFlag(false), printDebugInfoPrettyFormFlag(false),
207212
printGenericOpFormFlag(false), skipRegionsFlag(false),
208213
assumeVerifiedFlag(false), printLocalScope(false),
209-
printValueUsersFlag(false) {
214+
printValueUsersFlag(false), printUniqueIDsFlag(false) {
210215
// Initialize based upon command line options, if they are available.
211216
if (!clOptions.isConstructed())
212217
return;
@@ -224,6 +229,7 @@ OpPrintingFlags::OpPrintingFlags()
224229
printLocalScope = clOptions->printLocalScopeOpt;
225230
skipRegionsFlag = clOptions->skipRegionsOpt;
226231
printValueUsersFlag = clOptions->printValueUsers;
232+
printUniqueIDsFlag = clOptions->printUniqueIDs;
227233
}
228234

229235
/// Enable the elision of large elements attributes, by printing a '...'
@@ -350,6 +356,11 @@ bool OpPrintingFlags::shouldPrintValueUsers() const {
350356
return printValueUsersFlag;
351357
}
352358

359+
/// Return if the printer should use unique IDs.
360+
bool OpPrintingFlags::shouldPrintUniqueIDs() const {
361+
return printUniqueIDsFlag || shouldPrintGenericOpForm();
362+
}
363+
353364
//===----------------------------------------------------------------------===//
354365
// NewLineCounter
355366
//===----------------------------------------------------------------------===//
@@ -1369,8 +1380,14 @@ SSANameState::SSANameState(Operation *op, const OpPrintingFlags &printerFlags)
13691380
while (!nameContext.empty()) {
13701381
Region *region;
13711382
UsedNamesScopeTy *parentScope;
1372-
std::tie(region, nextValueID, nextArgumentID, nextConflictID, parentScope) =
1373-
nameContext.pop_back_val();
1383+
1384+
if (printerFlags.shouldPrintUniqueIDs())
1385+
// When printing unique IDs, ignore saved ID counts from parent regions
1386+
std::tie(region, std::ignore, std::ignore, std::ignore, parentScope) =
1387+
nameContext.pop_back_val();
1388+
else
1389+
std::tie(region, nextValueID, nextArgumentID, nextConflictID,
1390+
parentScope) = nameContext.pop_back_val();
13741391

13751392
// When we switch from one subtree to another, pop the scopes(needless)
13761393
// until the parent scope.

mlir/test/IR/print-unique-ids.mlir

Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,40 @@
1+
// RUN: mlir-opt -mlir-print-unique-ids %s | FileCheck %s
2+
3+
// CHECK: %arg5
4+
// CHECK: %15
5+
module {
6+
func.func @uniqueConflicts(%arg0 : memref<i32>, %arg1 : memref<i32>) {
7+
%c0 = arith.constant 0 : index
8+
%c1 = arith.constant 1 : index
9+
%c8 = arith.constant 8 : index
10+
scf.for %arg2 = %c0 to %c8 step %c1 {
11+
%a = memref.load %arg0[] : memref<i32>
12+
%b = memref.load %arg1[] : memref<i32>
13+
%0 = arith.addi %a, %b : i32
14+
%1 = arith.subi %a, %b : i32
15+
scf.for %arg3 = %c0 to %c8 step %c1 {
16+
%a2 = memref.load %arg0[] : memref<i32>
17+
%b2 = memref.load %arg1[] : memref<i32>
18+
%2 = arith.addi %a2, %b2 : i32
19+
%3 = arith.subi %a2, %b2 : i32
20+
scf.yield
21+
}
22+
scf.for %arg3 = %c0 to %c8 step %c1 {
23+
%a2 = memref.load %arg0[] : memref<i32>
24+
%b2 = memref.load %arg1[] : memref<i32>
25+
%2 = arith.addi %a2, %b2 : i32
26+
%3 = arith.subi %a2, %b2 : i32
27+
scf.yield
28+
}
29+
scf.yield
30+
}
31+
scf.for %arg2 = %c0 to %c8 step %c1 {
32+
%a = memref.load %arg0[] : memref<i32>
33+
%b = memref.load %arg1[] : memref<i32>
34+
%0 = arith.addi %a, %b : i32
35+
%1 = arith.subi %a, %b : i32
36+
scf.yield
37+
}
38+
return
39+
}
40+
}

0 commit comments

Comments
 (0)