1*61046927SAndroid Build Coastguard Worker /*
2*61046927SAndroid Build Coastguard Worker * Copyright © 2014 Intel Corporation
3*61046927SAndroid Build Coastguard Worker *
4*61046927SAndroid Build Coastguard Worker * Permission is hereby granted, free of charge, to any person obtaining a
5*61046927SAndroid Build Coastguard Worker * copy of this software and associated documentation files (the "Software"),
6*61046927SAndroid Build Coastguard Worker * to deal in the Software without restriction, including without limitation
7*61046927SAndroid Build Coastguard Worker * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8*61046927SAndroid Build Coastguard Worker * and/or sell copies of the Software, and to permit persons to whom the
9*61046927SAndroid Build Coastguard Worker * Software is furnished to do so, subject to the following conditions:
10*61046927SAndroid Build Coastguard Worker *
11*61046927SAndroid Build Coastguard Worker * The above copyright notice and this permission notice (including the next
12*61046927SAndroid Build Coastguard Worker * paragraph) shall be included in all copies or substantial portions of the
13*61046927SAndroid Build Coastguard Worker * Software.
14*61046927SAndroid Build Coastguard Worker *
15*61046927SAndroid Build Coastguard Worker * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16*61046927SAndroid Build Coastguard Worker * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17*61046927SAndroid Build Coastguard Worker * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
18*61046927SAndroid Build Coastguard Worker * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19*61046927SAndroid Build Coastguard Worker * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
20*61046927SAndroid Build Coastguard Worker * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
21*61046927SAndroid Build Coastguard Worker * IN THE SOFTWARE.
22*61046927SAndroid Build Coastguard Worker *
23*61046927SAndroid Build Coastguard Worker * Authors:
24*61046927SAndroid Build Coastguard Worker * Connor Abbott ([email protected])
25*61046927SAndroid Build Coastguard Worker *
26*61046927SAndroid Build Coastguard Worker */
27*61046927SAndroid Build Coastguard Worker
28*61046927SAndroid Build Coastguard Worker #include "nir.h"
29*61046927SAndroid Build Coastguard Worker
30*61046927SAndroid Build Coastguard Worker /*
31*61046927SAndroid Build Coastguard Worker * Implements the algorithms for computing the dominance tree and the
32*61046927SAndroid Build Coastguard Worker * dominance frontier from "A Simple, Fast Dominance Algorithm" by Cooper,
33*61046927SAndroid Build Coastguard Worker * Harvey, and Kennedy.
34*61046927SAndroid Build Coastguard Worker */
35*61046927SAndroid Build Coastguard Worker
36*61046927SAndroid Build Coastguard Worker static bool
init_block(nir_block * block,nir_function_impl * impl)37*61046927SAndroid Build Coastguard Worker init_block(nir_block *block, nir_function_impl *impl)
38*61046927SAndroid Build Coastguard Worker {
39*61046927SAndroid Build Coastguard Worker if (block == nir_start_block(impl))
40*61046927SAndroid Build Coastguard Worker block->imm_dom = block;
41*61046927SAndroid Build Coastguard Worker else
42*61046927SAndroid Build Coastguard Worker block->imm_dom = NULL;
43*61046927SAndroid Build Coastguard Worker block->num_dom_children = 0;
44*61046927SAndroid Build Coastguard Worker
45*61046927SAndroid Build Coastguard Worker /* See nir_block_dominates */
46*61046927SAndroid Build Coastguard Worker block->dom_pre_index = UINT32_MAX;
47*61046927SAndroid Build Coastguard Worker block->dom_post_index = 0;
48*61046927SAndroid Build Coastguard Worker
49*61046927SAndroid Build Coastguard Worker _mesa_set_clear(block->dom_frontier, NULL);
50*61046927SAndroid Build Coastguard Worker
51*61046927SAndroid Build Coastguard Worker return true;
52*61046927SAndroid Build Coastguard Worker }
53*61046927SAndroid Build Coastguard Worker
54*61046927SAndroid Build Coastguard Worker static nir_block *
intersect(nir_block * b1,nir_block * b2)55*61046927SAndroid Build Coastguard Worker intersect(nir_block *b1, nir_block *b2)
56*61046927SAndroid Build Coastguard Worker {
57*61046927SAndroid Build Coastguard Worker while (b1 != b2) {
58*61046927SAndroid Build Coastguard Worker /*
59*61046927SAndroid Build Coastguard Worker * Note, the comparisons here are the opposite of what the paper says
60*61046927SAndroid Build Coastguard Worker * because we index blocks from beginning -> end (i.e. reverse
61*61046927SAndroid Build Coastguard Worker * post-order) instead of post-order like they assume.
62*61046927SAndroid Build Coastguard Worker */
63*61046927SAndroid Build Coastguard Worker while (b1->index > b2->index)
64*61046927SAndroid Build Coastguard Worker b1 = b1->imm_dom;
65*61046927SAndroid Build Coastguard Worker while (b2->index > b1->index)
66*61046927SAndroid Build Coastguard Worker b2 = b2->imm_dom;
67*61046927SAndroid Build Coastguard Worker }
68*61046927SAndroid Build Coastguard Worker
69*61046927SAndroid Build Coastguard Worker return b1;
70*61046927SAndroid Build Coastguard Worker }
71*61046927SAndroid Build Coastguard Worker
72*61046927SAndroid Build Coastguard Worker static bool
calc_dominance(nir_block * block)73*61046927SAndroid Build Coastguard Worker calc_dominance(nir_block *block)
74*61046927SAndroid Build Coastguard Worker {
75*61046927SAndroid Build Coastguard Worker nir_block *new_idom = NULL;
76*61046927SAndroid Build Coastguard Worker set_foreach(block->predecessors, entry) {
77*61046927SAndroid Build Coastguard Worker nir_block *pred = (nir_block *)entry->key;
78*61046927SAndroid Build Coastguard Worker
79*61046927SAndroid Build Coastguard Worker if (pred->imm_dom) {
80*61046927SAndroid Build Coastguard Worker if (new_idom)
81*61046927SAndroid Build Coastguard Worker new_idom = intersect(pred, new_idom);
82*61046927SAndroid Build Coastguard Worker else
83*61046927SAndroid Build Coastguard Worker new_idom = pred;
84*61046927SAndroid Build Coastguard Worker }
85*61046927SAndroid Build Coastguard Worker }
86*61046927SAndroid Build Coastguard Worker
87*61046927SAndroid Build Coastguard Worker if (block->imm_dom != new_idom) {
88*61046927SAndroid Build Coastguard Worker block->imm_dom = new_idom;
89*61046927SAndroid Build Coastguard Worker return true;
90*61046927SAndroid Build Coastguard Worker }
91*61046927SAndroid Build Coastguard Worker
92*61046927SAndroid Build Coastguard Worker return false;
93*61046927SAndroid Build Coastguard Worker }
94*61046927SAndroid Build Coastguard Worker
95*61046927SAndroid Build Coastguard Worker static bool
calc_dom_frontier(nir_block * block)96*61046927SAndroid Build Coastguard Worker calc_dom_frontier(nir_block *block)
97*61046927SAndroid Build Coastguard Worker {
98*61046927SAndroid Build Coastguard Worker if (block->predecessors->entries > 1) {
99*61046927SAndroid Build Coastguard Worker set_foreach(block->predecessors, entry) {
100*61046927SAndroid Build Coastguard Worker nir_block *runner = (nir_block *)entry->key;
101*61046927SAndroid Build Coastguard Worker
102*61046927SAndroid Build Coastguard Worker /* Skip unreachable predecessors */
103*61046927SAndroid Build Coastguard Worker if (runner->imm_dom == NULL)
104*61046927SAndroid Build Coastguard Worker continue;
105*61046927SAndroid Build Coastguard Worker
106*61046927SAndroid Build Coastguard Worker while (runner != block->imm_dom) {
107*61046927SAndroid Build Coastguard Worker _mesa_set_add(runner->dom_frontier, block);
108*61046927SAndroid Build Coastguard Worker runner = runner->imm_dom;
109*61046927SAndroid Build Coastguard Worker }
110*61046927SAndroid Build Coastguard Worker }
111*61046927SAndroid Build Coastguard Worker }
112*61046927SAndroid Build Coastguard Worker
113*61046927SAndroid Build Coastguard Worker return true;
114*61046927SAndroid Build Coastguard Worker }
115*61046927SAndroid Build Coastguard Worker
116*61046927SAndroid Build Coastguard Worker /*
117*61046927SAndroid Build Coastguard Worker * Compute each node's children in the dominance tree from the immediate
118*61046927SAndroid Build Coastguard Worker * dominator information. We do this in three stages:
119*61046927SAndroid Build Coastguard Worker *
120*61046927SAndroid Build Coastguard Worker * 1. Calculate the number of children each node has
121*61046927SAndroid Build Coastguard Worker * 2. Allocate arrays, setting the number of children to 0 again
122*61046927SAndroid Build Coastguard Worker * 3. For each node, add itself to its parent's list of children, using
123*61046927SAndroid Build Coastguard Worker * num_dom_children as an index - at the end of this step, num_dom_children
124*61046927SAndroid Build Coastguard Worker * for each node will be the same as it was at the end of step #1.
125*61046927SAndroid Build Coastguard Worker */
126*61046927SAndroid Build Coastguard Worker
127*61046927SAndroid Build Coastguard Worker static void
calc_dom_children(nir_function_impl * impl)128*61046927SAndroid Build Coastguard Worker calc_dom_children(nir_function_impl *impl)
129*61046927SAndroid Build Coastguard Worker {
130*61046927SAndroid Build Coastguard Worker void *mem_ctx = ralloc_parent(impl);
131*61046927SAndroid Build Coastguard Worker
132*61046927SAndroid Build Coastguard Worker nir_foreach_block_unstructured(block, impl) {
133*61046927SAndroid Build Coastguard Worker if (block->imm_dom)
134*61046927SAndroid Build Coastguard Worker block->imm_dom->num_dom_children++;
135*61046927SAndroid Build Coastguard Worker }
136*61046927SAndroid Build Coastguard Worker
137*61046927SAndroid Build Coastguard Worker nir_foreach_block_unstructured(block, impl) {
138*61046927SAndroid Build Coastguard Worker block->dom_children = ralloc_array(mem_ctx, nir_block *,
139*61046927SAndroid Build Coastguard Worker block->num_dom_children);
140*61046927SAndroid Build Coastguard Worker block->num_dom_children = 0;
141*61046927SAndroid Build Coastguard Worker }
142*61046927SAndroid Build Coastguard Worker
143*61046927SAndroid Build Coastguard Worker nir_foreach_block_unstructured(block, impl) {
144*61046927SAndroid Build Coastguard Worker if (block->imm_dom) {
145*61046927SAndroid Build Coastguard Worker block->imm_dom->dom_children[block->imm_dom->num_dom_children++] = block;
146*61046927SAndroid Build Coastguard Worker }
147*61046927SAndroid Build Coastguard Worker }
148*61046927SAndroid Build Coastguard Worker }
149*61046927SAndroid Build Coastguard Worker
150*61046927SAndroid Build Coastguard Worker static void
calc_dfs_indicies(nir_block * block,uint32_t * index)151*61046927SAndroid Build Coastguard Worker calc_dfs_indicies(nir_block *block, uint32_t *index)
152*61046927SAndroid Build Coastguard Worker {
153*61046927SAndroid Build Coastguard Worker /* UINT32_MAX has special meaning. See nir_block_dominates. */
154*61046927SAndroid Build Coastguard Worker assert(*index < UINT32_MAX - 2);
155*61046927SAndroid Build Coastguard Worker
156*61046927SAndroid Build Coastguard Worker block->dom_pre_index = (*index)++;
157*61046927SAndroid Build Coastguard Worker
158*61046927SAndroid Build Coastguard Worker for (unsigned i = 0; i < block->num_dom_children; i++)
159*61046927SAndroid Build Coastguard Worker calc_dfs_indicies(block->dom_children[i], index);
160*61046927SAndroid Build Coastguard Worker
161*61046927SAndroid Build Coastguard Worker block->dom_post_index = (*index)++;
162*61046927SAndroid Build Coastguard Worker }
163*61046927SAndroid Build Coastguard Worker
164*61046927SAndroid Build Coastguard Worker void
nir_calc_dominance_impl(nir_function_impl * impl)165*61046927SAndroid Build Coastguard Worker nir_calc_dominance_impl(nir_function_impl *impl)
166*61046927SAndroid Build Coastguard Worker {
167*61046927SAndroid Build Coastguard Worker if (impl->valid_metadata & nir_metadata_dominance)
168*61046927SAndroid Build Coastguard Worker return;
169*61046927SAndroid Build Coastguard Worker
170*61046927SAndroid Build Coastguard Worker nir_metadata_require(impl, nir_metadata_block_index);
171*61046927SAndroid Build Coastguard Worker
172*61046927SAndroid Build Coastguard Worker nir_foreach_block_unstructured(block, impl) {
173*61046927SAndroid Build Coastguard Worker init_block(block, impl);
174*61046927SAndroid Build Coastguard Worker }
175*61046927SAndroid Build Coastguard Worker
176*61046927SAndroid Build Coastguard Worker bool progress = true;
177*61046927SAndroid Build Coastguard Worker while (progress) {
178*61046927SAndroid Build Coastguard Worker progress = false;
179*61046927SAndroid Build Coastguard Worker nir_foreach_block_unstructured(block, impl) {
180*61046927SAndroid Build Coastguard Worker if (block != nir_start_block(impl))
181*61046927SAndroid Build Coastguard Worker progress |= calc_dominance(block);
182*61046927SAndroid Build Coastguard Worker }
183*61046927SAndroid Build Coastguard Worker }
184*61046927SAndroid Build Coastguard Worker
185*61046927SAndroid Build Coastguard Worker nir_foreach_block_unstructured(block, impl) {
186*61046927SAndroid Build Coastguard Worker calc_dom_frontier(block);
187*61046927SAndroid Build Coastguard Worker }
188*61046927SAndroid Build Coastguard Worker
189*61046927SAndroid Build Coastguard Worker nir_block *start_block = nir_start_block(impl);
190*61046927SAndroid Build Coastguard Worker start_block->imm_dom = NULL;
191*61046927SAndroid Build Coastguard Worker
192*61046927SAndroid Build Coastguard Worker calc_dom_children(impl);
193*61046927SAndroid Build Coastguard Worker
194*61046927SAndroid Build Coastguard Worker uint32_t dfs_index = 1;
195*61046927SAndroid Build Coastguard Worker calc_dfs_indicies(start_block, &dfs_index);
196*61046927SAndroid Build Coastguard Worker }
197*61046927SAndroid Build Coastguard Worker
198*61046927SAndroid Build Coastguard Worker void
nir_calc_dominance(nir_shader * shader)199*61046927SAndroid Build Coastguard Worker nir_calc_dominance(nir_shader *shader)
200*61046927SAndroid Build Coastguard Worker {
201*61046927SAndroid Build Coastguard Worker nir_foreach_function_impl(impl, shader) {
202*61046927SAndroid Build Coastguard Worker nir_calc_dominance_impl(impl);
203*61046927SAndroid Build Coastguard Worker }
204*61046927SAndroid Build Coastguard Worker }
205*61046927SAndroid Build Coastguard Worker
206*61046927SAndroid Build Coastguard Worker static nir_block *
block_return_if_reachable(nir_block * b)207*61046927SAndroid Build Coastguard Worker block_return_if_reachable(nir_block *b)
208*61046927SAndroid Build Coastguard Worker {
209*61046927SAndroid Build Coastguard Worker return (b && nir_block_is_reachable(b)) ? b : NULL;
210*61046927SAndroid Build Coastguard Worker }
211*61046927SAndroid Build Coastguard Worker
212*61046927SAndroid Build Coastguard Worker /**
213*61046927SAndroid Build Coastguard Worker * Computes the least common ancestor of two blocks. If one of the blocks
214*61046927SAndroid Build Coastguard Worker * is null or unreachable, the other block is returned or NULL if it's
215*61046927SAndroid Build Coastguard Worker * unreachable.
216*61046927SAndroid Build Coastguard Worker */
217*61046927SAndroid Build Coastguard Worker nir_block *
nir_dominance_lca(nir_block * b1,nir_block * b2)218*61046927SAndroid Build Coastguard Worker nir_dominance_lca(nir_block *b1, nir_block *b2)
219*61046927SAndroid Build Coastguard Worker {
220*61046927SAndroid Build Coastguard Worker if (b1 == NULL || !nir_block_is_reachable(b1))
221*61046927SAndroid Build Coastguard Worker return block_return_if_reachable(b2);
222*61046927SAndroid Build Coastguard Worker
223*61046927SAndroid Build Coastguard Worker if (b2 == NULL || !nir_block_is_reachable(b2))
224*61046927SAndroid Build Coastguard Worker return block_return_if_reachable(b1);
225*61046927SAndroid Build Coastguard Worker
226*61046927SAndroid Build Coastguard Worker assert(nir_cf_node_get_function(&b1->cf_node) ==
227*61046927SAndroid Build Coastguard Worker nir_cf_node_get_function(&b2->cf_node));
228*61046927SAndroid Build Coastguard Worker
229*61046927SAndroid Build Coastguard Worker assert(nir_cf_node_get_function(&b1->cf_node)->valid_metadata &
230*61046927SAndroid Build Coastguard Worker nir_metadata_dominance);
231*61046927SAndroid Build Coastguard Worker
232*61046927SAndroid Build Coastguard Worker return intersect(b1, b2);
233*61046927SAndroid Build Coastguard Worker }
234*61046927SAndroid Build Coastguard Worker
235*61046927SAndroid Build Coastguard Worker /**
236*61046927SAndroid Build Coastguard Worker * Returns true if parent dominates child according to the following
237*61046927SAndroid Build Coastguard Worker * definition:
238*61046927SAndroid Build Coastguard Worker *
239*61046927SAndroid Build Coastguard Worker * "The block A dominates the block B if every path from the start block
240*61046927SAndroid Build Coastguard Worker * to block B passes through A."
241*61046927SAndroid Build Coastguard Worker *
242*61046927SAndroid Build Coastguard Worker * This means, in particular, that any unreachable block is dominated by every
243*61046927SAndroid Build Coastguard Worker * other block and an unreachable block does not dominate anything except
244*61046927SAndroid Build Coastguard Worker * another unreachable block.
245*61046927SAndroid Build Coastguard Worker */
246*61046927SAndroid Build Coastguard Worker bool
nir_block_dominates(nir_block * parent,nir_block * child)247*61046927SAndroid Build Coastguard Worker nir_block_dominates(nir_block *parent, nir_block *child)
248*61046927SAndroid Build Coastguard Worker {
249*61046927SAndroid Build Coastguard Worker assert(nir_cf_node_get_function(&parent->cf_node) ==
250*61046927SAndroid Build Coastguard Worker nir_cf_node_get_function(&child->cf_node));
251*61046927SAndroid Build Coastguard Worker
252*61046927SAndroid Build Coastguard Worker assert(nir_cf_node_get_function(&parent->cf_node)->valid_metadata &
253*61046927SAndroid Build Coastguard Worker nir_metadata_dominance);
254*61046927SAndroid Build Coastguard Worker
255*61046927SAndroid Build Coastguard Worker /* If a block is unreachable, then nir_block::dom_pre_index == UINT32_MAX
256*61046927SAndroid Build Coastguard Worker * and nir_block::dom_post_index == 0. This allows us to trivially handle
257*61046927SAndroid Build Coastguard Worker * unreachable blocks here with zero extra work.
258*61046927SAndroid Build Coastguard Worker */
259*61046927SAndroid Build Coastguard Worker return child->dom_pre_index >= parent->dom_pre_index &&
260*61046927SAndroid Build Coastguard Worker child->dom_post_index <= parent->dom_post_index;
261*61046927SAndroid Build Coastguard Worker }
262*61046927SAndroid Build Coastguard Worker
263*61046927SAndroid Build Coastguard Worker bool
nir_block_is_unreachable(nir_block * block)264*61046927SAndroid Build Coastguard Worker nir_block_is_unreachable(nir_block *block)
265*61046927SAndroid Build Coastguard Worker {
266*61046927SAndroid Build Coastguard Worker assert(nir_cf_node_get_function(&block->cf_node)->valid_metadata &
267*61046927SAndroid Build Coastguard Worker nir_metadata_dominance);
268*61046927SAndroid Build Coastguard Worker assert(nir_cf_node_get_function(&block->cf_node)->valid_metadata &
269*61046927SAndroid Build Coastguard Worker nir_metadata_block_index);
270*61046927SAndroid Build Coastguard Worker
271*61046927SAndroid Build Coastguard Worker /* Unreachable blocks have no dominator. The only reachable block with no
272*61046927SAndroid Build Coastguard Worker * dominator is the start block which has index 0.
273*61046927SAndroid Build Coastguard Worker */
274*61046927SAndroid Build Coastguard Worker return block->index > 0 && block->imm_dom == NULL;
275*61046927SAndroid Build Coastguard Worker }
276*61046927SAndroid Build Coastguard Worker
277*61046927SAndroid Build Coastguard Worker void
nir_dump_dom_tree_impl(nir_function_impl * impl,FILE * fp)278*61046927SAndroid Build Coastguard Worker nir_dump_dom_tree_impl(nir_function_impl *impl, FILE *fp)
279*61046927SAndroid Build Coastguard Worker {
280*61046927SAndroid Build Coastguard Worker fprintf(fp, "digraph doms_%s {\n", impl->function->name);
281*61046927SAndroid Build Coastguard Worker
282*61046927SAndroid Build Coastguard Worker nir_foreach_block_unstructured(block, impl) {
283*61046927SAndroid Build Coastguard Worker if (block->imm_dom)
284*61046927SAndroid Build Coastguard Worker fprintf(fp, "\t%u -> %u\n", block->imm_dom->index, block->index);
285*61046927SAndroid Build Coastguard Worker }
286*61046927SAndroid Build Coastguard Worker
287*61046927SAndroid Build Coastguard Worker fprintf(fp, "}\n\n");
288*61046927SAndroid Build Coastguard Worker }
289*61046927SAndroid Build Coastguard Worker
290*61046927SAndroid Build Coastguard Worker void
nir_dump_dom_tree(nir_shader * shader,FILE * fp)291*61046927SAndroid Build Coastguard Worker nir_dump_dom_tree(nir_shader *shader, FILE *fp)
292*61046927SAndroid Build Coastguard Worker {
293*61046927SAndroid Build Coastguard Worker nir_foreach_function_impl(impl, shader) {
294*61046927SAndroid Build Coastguard Worker nir_dump_dom_tree_impl(impl, fp);
295*61046927SAndroid Build Coastguard Worker }
296*61046927SAndroid Build Coastguard Worker }
297*61046927SAndroid Build Coastguard Worker
298*61046927SAndroid Build Coastguard Worker void
nir_dump_dom_frontier_impl(nir_function_impl * impl,FILE * fp)299*61046927SAndroid Build Coastguard Worker nir_dump_dom_frontier_impl(nir_function_impl *impl, FILE *fp)
300*61046927SAndroid Build Coastguard Worker {
301*61046927SAndroid Build Coastguard Worker nir_foreach_block_unstructured(block, impl) {
302*61046927SAndroid Build Coastguard Worker fprintf(fp, "DF(%u) = {", block->index);
303*61046927SAndroid Build Coastguard Worker set_foreach(block->dom_frontier, entry) {
304*61046927SAndroid Build Coastguard Worker nir_block *df = (nir_block *)entry->key;
305*61046927SAndroid Build Coastguard Worker fprintf(fp, "%u, ", df->index);
306*61046927SAndroid Build Coastguard Worker }
307*61046927SAndroid Build Coastguard Worker fprintf(fp, "}\n");
308*61046927SAndroid Build Coastguard Worker }
309*61046927SAndroid Build Coastguard Worker }
310*61046927SAndroid Build Coastguard Worker
311*61046927SAndroid Build Coastguard Worker void
nir_dump_dom_frontier(nir_shader * shader,FILE * fp)312*61046927SAndroid Build Coastguard Worker nir_dump_dom_frontier(nir_shader *shader, FILE *fp)
313*61046927SAndroid Build Coastguard Worker {
314*61046927SAndroid Build Coastguard Worker nir_foreach_function_impl(impl, shader) {
315*61046927SAndroid Build Coastguard Worker nir_dump_dom_frontier_impl(impl, fp);
316*61046927SAndroid Build Coastguard Worker }
317*61046927SAndroid Build Coastguard Worker }
318*61046927SAndroid Build Coastguard Worker
319*61046927SAndroid Build Coastguard Worker void
nir_dump_cfg_impl(nir_function_impl * impl,FILE * fp)320*61046927SAndroid Build Coastguard Worker nir_dump_cfg_impl(nir_function_impl *impl, FILE *fp)
321*61046927SAndroid Build Coastguard Worker {
322*61046927SAndroid Build Coastguard Worker fprintf(fp, "digraph cfg_%s {\n", impl->function->name);
323*61046927SAndroid Build Coastguard Worker
324*61046927SAndroid Build Coastguard Worker nir_foreach_block_unstructured(block, impl) {
325*61046927SAndroid Build Coastguard Worker if (block->successors[0])
326*61046927SAndroid Build Coastguard Worker fprintf(fp, "\t%u -> %u\n", block->index, block->successors[0]->index);
327*61046927SAndroid Build Coastguard Worker if (block->successors[1])
328*61046927SAndroid Build Coastguard Worker fprintf(fp, "\t%u -> %u\n", block->index, block->successors[1]->index);
329*61046927SAndroid Build Coastguard Worker }
330*61046927SAndroid Build Coastguard Worker
331*61046927SAndroid Build Coastguard Worker fprintf(fp, "}\n\n");
332*61046927SAndroid Build Coastguard Worker }
333*61046927SAndroid Build Coastguard Worker
334*61046927SAndroid Build Coastguard Worker void
nir_dump_cfg(nir_shader * shader,FILE * fp)335*61046927SAndroid Build Coastguard Worker nir_dump_cfg(nir_shader *shader, FILE *fp)
336*61046927SAndroid Build Coastguard Worker {
337*61046927SAndroid Build Coastguard Worker nir_foreach_function_impl(impl, shader) {
338*61046927SAndroid Build Coastguard Worker nir_dump_cfg_impl(impl, fp);
339*61046927SAndroid Build Coastguard Worker }
340*61046927SAndroid Build Coastguard Worker }
341