@@ -22,6 +22,8 @@ namespace mlir {
22
22
23
23
using namespace mlir ;
24
24
25
+ #define DEBUG_TYPE " symbol-dce"
26
+
25
27
namespace {
26
28
struct SymbolDCE : public impl ::SymbolDCEBase<SymbolDCE> {
27
29
void runOnOperation () override ;
@@ -84,6 +86,8 @@ LogicalResult SymbolDCE::computeLiveness(Operation *symbolTableOp,
84
86
SymbolTableCollection &symbolTable,
85
87
bool symbolTableIsHidden,
86
88
DenseSet<Operation *> &liveSymbols) {
89
+ LLVM_DEBUG (llvm::dbgs () << " computeLiveness: " << symbolTableOp->getName ()
90
+ << " \n " );
87
91
// A worklist of live operations to propagate uses from.
88
92
SmallVector<Operation *, 16 > worklist;
89
93
@@ -108,15 +112,42 @@ LogicalResult SymbolDCE::computeLiveness(Operation *symbolTableOp,
108
112
// that are referenced within.
109
113
while (!worklist.empty ()) {
110
114
Operation *op = worklist.pop_back_val ();
115
+ LLVM_DEBUG (llvm::dbgs () << " processing: " << op->getName () << " \n " );
111
116
112
117
// If this is a symbol table, recursively compute its liveness.
113
118
if (op->hasTrait <OpTrait::SymbolTable>()) {
114
119
// The internal symbol table is hidden if the parent is, if its not a
115
120
// symbol, or if it is a private symbol.
116
121
SymbolOpInterface symbol = dyn_cast<SymbolOpInterface>(op);
117
122
bool symIsHidden = symbolTableIsHidden || !symbol || symbol.isPrivate ();
123
+ LLVM_DEBUG (llvm::dbgs () << " \t symbol table: " << op->getName ()
124
+ << " is hidden: " << symIsHidden << " \n " );
118
125
if (failed (computeLiveness (op, symbolTable, symIsHidden, liveSymbols)))
119
126
return failure ();
127
+ } else {
128
+ LLVM_DEBUG (llvm::dbgs ()
129
+ << " \t non-symbol table: " << op->getName () << " is hidden\n " );
130
+ // If the op is not a symbol table, then, unless op itself is dead which
131
+ // would be handled by DCE, we need to check all the regions and blocks
132
+ // within the op to find the uses (e.g., consider visibility within op as
133
+ // if top level rather than relying on pure symbol table visibility). This
134
+ // is more conservative than SymbolTable::walkSymbolTables in the case
135
+ // where there is again SymbolTable information to take advantage of.
136
+ for (auto ®ion : op->getRegions ()) {
137
+ for (auto &block : region.getBlocks ()) {
138
+ for (Operation &op : block) {
139
+ SymbolOpInterface symbol = dyn_cast<SymbolOpInterface>(&op);
140
+ if (!symbol) {
141
+ worklist.push_back (&op);
142
+ continue ;
143
+ }
144
+ bool isDiscardable =
145
+ symbol.isPrivate () && symbol.canDiscardOnUseEmpty ();
146
+ if (!isDiscardable && liveSymbols.insert (&op).second )
147
+ worklist.push_back (&op);
148
+ }
149
+ }
150
+ }
120
151
}
121
152
122
153
// Collect the uses held by this operation.
@@ -128,13 +159,27 @@ LogicalResult SymbolDCE::computeLiveness(Operation *symbolTableOp,
128
159
}
129
160
130
161
SmallVector<Operation *, 4 > resolvedSymbols;
162
+ // Get the first parent symbol table op.
163
+ Operation *parentOp = op->getParentOp ();
164
+ while (parentOp && !parentOp->hasTrait <OpTrait::SymbolTable>()) {
165
+ parentOp = parentOp->getParentOp ();
166
+ }
167
+ assert (parentOp && " operation has no parent symbol table" );
168
+
169
+ LLVM_DEBUG (llvm::dbgs () << " uses of " << op->getName () << " \n " );
131
170
for (const SymbolTable::SymbolUse &use : *uses) {
171
+ LLVM_DEBUG (llvm::dbgs () << " \t use: " << use.getUser () << " \n " );
132
172
// Lookup the symbols referenced by this use.
133
173
resolvedSymbols.clear ();
134
- if (failed (symbolTable.lookupSymbolIn (
135
- op-> getParentOp (), use. getSymbolRef (), resolvedSymbols)))
174
+ if (failed (symbolTable.lookupSymbolIn (parentOp, use. getSymbolRef (),
175
+ resolvedSymbols)))
136
176
// Ignore references to unknown symbols.
137
177
continue ;
178
+ LLVM_DEBUG ({
179
+ llvm::dbgs () << " \t\t resolved symbols: " ;
180
+ llvm::interleaveComma (resolvedSymbols, llvm::dbgs ());
181
+ llvm::dbgs () << " \n " ;
182
+ });
138
183
139
184
// Mark each of the resolved symbols as live.
140
185
for (Operation *resolvedSymbol : resolvedSymbols)
0 commit comments