xref: /aosp_15_r20/external/mesa3d/src/compiler/nir/tests/control_flow_tests.cpp (revision 6104692788411f58d303aa86923a9ff6ecaded22)
1 /*
2  * Copyright © 2015 Intel Corporation
3  *
4  * Permission is hereby granted, free of charge, to any person obtaining a
5  * copy of this software and associated documentation files (the "Software"),
6  * to deal in the Software without restriction, including without limitation
7  * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8  * and/or sell copies of the Software, and to permit persons to whom the
9  * Software is furnished to do so, subject to the following conditions:
10  *
11  * The above copyright notice and this permission notice (including the next
12  * paragraph) shall be included in all copies or substantial portions of the
13  * Software.
14  *
15  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
18  * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19  * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
20  * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
21  * DEALINGS IN THE SOFTWARE.
22  */
23 
24 #include "nir_test.h"
25 
26 class nir_cf_test : public nir_test {
27 protected:
nir_cf_test()28    nir_cf_test()
29       : nir_test::nir_test("nir_cf_test")
30    {
31    }
32 };
33 
TEST_F(nir_cf_test,delete_break_in_loop)34 TEST_F(nir_cf_test, delete_break_in_loop)
35 {
36    /* Create IR:
37     *
38     * while (...) { break; }
39     */
40    nir_loop *loop = nir_loop_create(b->shader);
41    nir_cf_node_insert(nir_after_cf_list(&b->impl->body), &loop->cf_node);
42 
43    b->cursor = nir_after_cf_list(&loop->body);
44 
45    nir_jump_instr *jump = nir_jump_instr_create(b->shader, nir_jump_break);
46    nir_builder_instr_insert(b, &jump->instr);
47 
48    /* At this point, we should have:
49     *
50     * impl main {
51     *         block block_0:
52     *         // preds:
53     *         // succs: block_1
54     *         loop {
55     *                 block block_1:
56     *                 // preds: block_0
57     *                 break
58     *                 // succs: block_2
59     *         }
60     *         block block_2:
61     *         // preds: block_1
62     *         // succs: block_3
63     *         block block_3:
64     * }
65     */
66    nir_block *block_0 = nir_start_block(b->impl);
67    nir_block *block_1 = nir_loop_first_block(loop);
68    nir_block *block_2 = nir_cf_node_as_block(nir_cf_node_next(&loop->cf_node));
69    nir_block *block_3 = b->impl->end_block;
70    ASSERT_EQ(nir_cf_node_block, block_0->cf_node.type);
71    ASSERT_EQ(nir_cf_node_block, block_1->cf_node.type);
72    ASSERT_EQ(nir_cf_node_block, block_2->cf_node.type);
73    ASSERT_EQ(nir_cf_node_block, block_3->cf_node.type);
74 
75    /* Verify the successors and predecessors. */
76    EXPECT_EQ(block_1, block_0->successors[0]);
77    EXPECT_EQ(NULL,    block_0->successors[1]);
78    EXPECT_EQ(block_2, block_1->successors[0]);
79    EXPECT_EQ(NULL,    block_1->successors[1]);
80    EXPECT_EQ(block_3, block_2->successors[0]);
81    EXPECT_EQ(NULL,    block_2->successors[1]);
82    EXPECT_EQ(NULL,    block_3->successors[0]);
83    EXPECT_EQ(NULL,    block_3->successors[1]);
84    EXPECT_EQ(0,       block_0->predecessors->entries);
85    EXPECT_EQ(1,       block_1->predecessors->entries);
86    EXPECT_EQ(1,       block_2->predecessors->entries);
87    EXPECT_EQ(1,       block_3->predecessors->entries);
88    EXPECT_TRUE(_mesa_set_search(block_1->predecessors, block_0));
89    EXPECT_TRUE(_mesa_set_search(block_2->predecessors, block_1));
90    EXPECT_TRUE(_mesa_set_search(block_3->predecessors, block_2));
91 
92    /* Now remove the break. */
93    nir_instr_remove(&jump->instr);
94 
95    /* At this point, we should have:
96     *
97     * impl main {
98     *         block block_0:
99     *         // preds:
100     *         // succs: block_1
101     *         loop {
102     *                 block block_1:
103     *                 // preds: block_0 block_1
104     *                 // succs: block_1
105     *         }
106     *         block block_2:
107     *         // preds:
108     *         // succs: block_3
109     *         block block_3:
110     * }
111     *
112     * Re-verify the predecessors and successors.
113     */
114    EXPECT_EQ(block_1, block_0->successors[0]);
115    EXPECT_EQ(NULL,    block_0->successors[1]);
116    EXPECT_EQ(block_1, block_1->successors[0]); /* back to itself */
117    EXPECT_EQ(NULL,    block_1->successors[1]);
118    EXPECT_EQ(block_3, block_2->successors[0]);
119    EXPECT_EQ(NULL,    block_2->successors[1]);
120    EXPECT_EQ(NULL,    block_3->successors[0]);
121    EXPECT_EQ(NULL,    block_3->successors[1]);
122    EXPECT_EQ(0,       block_0->predecessors->entries);
123    EXPECT_EQ(2,       block_1->predecessors->entries);
124    EXPECT_EQ(0,       block_2->predecessors->entries);
125    EXPECT_EQ(1,       block_3->predecessors->entries);
126    EXPECT_TRUE(_mesa_set_search(block_1->predecessors, block_0));
127    EXPECT_TRUE(_mesa_set_search(block_1->predecessors, block_1));
128    EXPECT_FALSE(_mesa_set_search(block_2->predecessors, block_1));
129    EXPECT_TRUE(_mesa_set_search(block_3->predecessors, block_2));
130 
131    nir_metadata_require(b->impl, nir_metadata_dominance);
132 }
133