David Neto dffa60ca98 spir-writer: handle break continuing block
The continuing block can exit the loop in very constrained ways:

When a break statement is placed such that it would exit from a loop’s
§ 7.3.8 Continuing Statement, then:

   - The break statement must appear as either:
     - The only statement in the if clause of an if statement that has:
       - no else clause or an empty else clause
       - no elseif clauses
     - The only statement in the else clause of an if statement that has an
       empty if clause and no elseif clauses.
   - That if statement must appear last in the continuing clause.

By design, this allows a lossless round-trip from SPIR-V to WGSL and
back to SPIR-V.  But that requires this special case construct in WGSL
to be translated to an OpBranchConditional with one target being
the loop's megre block (which is where 'break' branches to), and the
other targets the loop header (which is the loop backedge).  That
OpBranchConditional takes the place of the normal case of an
unconditional backedge.

Avoids errors like this:
 continue construct with the continue target X is not
 post dominated by the back-edge block Y

Fixed: 1034
Change-Id: If472a179380b8d77af746a3cd8e279c8a5e56b37
Reviewed-on: https://dawn-review.googlesource.com/c/tint/+/59800
Auto-Submit: David Neto <dneto@google.com>
Kokoro: Kokoro <noreply+kokoro@google.com>
Commit-Queue: David Neto <dneto@google.com>
Reviewed-by: Ben Clayton <bclayton@google.com>
2021-07-27 15:12:27 +00:00

612 lines
22 KiB
Plaintext

; SPIR-V
; Version: 1.3
; Generator: Google Tint Compiler; 0
; Bound: 355
; Schema: 0
OpCapability Shader
OpMemoryModel Logical GLSL450
OpEntryPoint Fragment %main "main" %tint_symbol_1
OpExecutionMode %main OriginUpperLeft
OpName %x_GLF_global_loop_count "x_GLF_global_loop_count"
OpName %buf0 "buf0"
OpMemberName %buf0 0 "x_GLF_uniform_float_values"
OpName %x_7 "x_7"
OpName %buf1 "buf1"
OpMemberName %buf1 0 "x_GLF_uniform_int_values"
OpName %x_10 "x_10"
OpName %x_GLF_color "x_GLF_color"
OpName %tint_symbol_1 "tint_symbol_1"
OpName %main_1 "main_1"
OpName %f "f"
OpName %i "i"
OpName %i_1 "i_1"
OpName %i_2 "i_2"
OpName %i_3 "i_3"
OpName %i_4 "i_4"
OpName %i_5 "i_5"
OpName %i_6 "i_6"
OpName %i_7 "i_7"
OpName %i_8 "i_8"
OpName %i_9 "i_9"
OpName %i_10 "i_10"
OpName %i_11 "i_11"
OpName %i_12 "i_12"
OpName %i_13 "i_13"
OpName %i_14 "i_14"
OpName %sum "sum"
OpName %r "r"
OpName %main_out "main_out"
OpMemberName %main_out 0 "x_GLF_color_1"
OpName %tint_symbol_2 "tint_symbol_2"
OpName %tint_symbol "tint_symbol"
OpName %main "main"
OpDecorate %buf0 Block
OpMemberDecorate %buf0 0 Offset 0
OpDecorate %_arr_float_uint_3 ArrayStride 16
OpDecorate %x_7 NonWritable
OpDecorate %x_7 DescriptorSet 0
OpDecorate %x_7 Binding 0
OpDecorate %buf1 Block
OpMemberDecorate %buf1 0 Offset 0
OpDecorate %_arr_int_uint_4 ArrayStride 16
OpDecorate %x_10 NonWritable
OpDecorate %x_10 DescriptorSet 0
OpDecorate %x_10 Binding 1
OpDecorate %tint_symbol_1 Location 0
OpMemberDecorate %main_out 0 Offset 0
%int = OpTypeInt 32 1
%_ptr_Private_int = OpTypePointer Private %int
%4 = OpConstantNull %int
%x_GLF_global_loop_count = OpVariable %_ptr_Private_int Private %4
%float = OpTypeFloat 32
%uint = OpTypeInt 32 0
%uint_3 = OpConstant %uint 3
%_arr_float_uint_3 = OpTypeArray %float %uint_3
%buf0 = OpTypeStruct %_arr_float_uint_3
%_ptr_Uniform_buf0 = OpTypePointer Uniform %buf0
%x_7 = OpVariable %_ptr_Uniform_buf0 Uniform
%uint_4 = OpConstant %uint 4
%_arr_int_uint_4 = OpTypeArray %int %uint_4
%buf1 = OpTypeStruct %_arr_int_uint_4
%_ptr_Uniform_buf1 = OpTypePointer Uniform %buf1
%x_10 = OpVariable %_ptr_Uniform_buf1 Uniform
%v4float = OpTypeVector %float 4
%_ptr_Private_v4float = OpTypePointer Private %v4float
%20 = OpConstantNull %v4float
%x_GLF_color = OpVariable %_ptr_Private_v4float Private %20
%_ptr_Output_v4float = OpTypePointer Output %v4float
%tint_symbol_1 = OpVariable %_ptr_Output_v4float Output %20
%void = OpTypeVoid
%23 = OpTypeFunction %void
%_ptr_Function_float = OpTypePointer Function %float
%29 = OpConstantNull %float
%_ptr_Function_int = OpTypePointer Function %int
%int_0 = OpConstant %int 0
%uint_0 = OpConstant %uint 0
%int_1 = OpConstant %int 1
%_ptr_Uniform_float = OpTypePointer Uniform %float
%_ptr_Uniform_int = OpTypePointer Uniform %int
%bool = OpTypeBool
%int_2 = OpConstant %int 2
%int_3 = OpConstant %int 3
%int_100 = OpConstant %int 100
%main_out = OpTypeStruct %v4float
%343 = OpTypeFunction %void %main_out
%main_1 = OpFunction %void None %23
%26 = OpLabel
%f = OpVariable %_ptr_Function_float Function %29
%i = OpVariable %_ptr_Function_int Function %4
%i_1 = OpVariable %_ptr_Function_int Function %4
%i_2 = OpVariable %_ptr_Function_int Function %4
%i_3 = OpVariable %_ptr_Function_int Function %4
%i_4 = OpVariable %_ptr_Function_int Function %4
%i_5 = OpVariable %_ptr_Function_int Function %4
%i_6 = OpVariable %_ptr_Function_int Function %4
%i_7 = OpVariable %_ptr_Function_int Function %4
%i_8 = OpVariable %_ptr_Function_int Function %4
%i_9 = OpVariable %_ptr_Function_int Function %4
%i_10 = OpVariable %_ptr_Function_int Function %4
%i_11 = OpVariable %_ptr_Function_int Function %4
%i_12 = OpVariable %_ptr_Function_int Function %4
%i_13 = OpVariable %_ptr_Function_int Function %4
%i_14 = OpVariable %_ptr_Function_int Function %4
%sum = OpVariable %_ptr_Function_float Function %29
%r = OpVariable %_ptr_Function_int Function %4
OpStore %x_GLF_global_loop_count %int_0
%52 = OpAccessChain %_ptr_Uniform_float %x_7 %uint_0 %int_1
%53 = OpLoad %float %52
OpStore %f %53
%55 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_1
%56 = OpLoad %int %55
OpStore %i %56
OpBranch %57
%57 = OpLabel
OpLoopMerge %58 %59 None
OpBranch %60
%60 = OpLabel
%61 = OpLoad %int %i
%62 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_0
%63 = OpLoad %int %62
%64 = OpSLessThan %bool %61 %63
OpSelectionMerge %66 None
OpBranchConditional %64 %67 %68
%67 = OpLabel
OpBranch %66
%68 = OpLabel
OpBranch %58
%66 = OpLabel
%69 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_1
%70 = OpLoad %int %69
OpStore %i_1 %70
OpBranch %71
%71 = OpLabel
OpLoopMerge %72 %73 None
OpBranch %74
%74 = OpLabel
%75 = OpLoad %int %i_1
%76 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_0
%77 = OpLoad %int %76
%78 = OpSLessThan %bool %75 %77
OpSelectionMerge %79 None
OpBranchConditional %78 %80 %81
%80 = OpLabel
OpBranch %79
%81 = OpLabel
OpBranch %72
%79 = OpLabel
%82 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_1
%83 = OpLoad %int %82
OpStore %i_2 %83
OpBranch %84
%84 = OpLabel
OpLoopMerge %85 %86 None
OpBranch %87
%87 = OpLabel
%88 = OpLoad %int %i_2
%89 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_0
%90 = OpLoad %int %89
%91 = OpSLessThan %bool %88 %90
OpSelectionMerge %92 None
OpBranchConditional %91 %93 %94
%93 = OpLabel
OpBranch %92
%94 = OpLabel
OpBranch %85
%92 = OpLabel
%95 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_1
%96 = OpLoad %int %95
OpStore %i_3 %96
OpBranch %97
%97 = OpLabel
OpLoopMerge %98 %99 None
OpBranch %100
%100 = OpLabel
%101 = OpLoad %int %i_3
%102 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_0
%103 = OpLoad %int %102
%104 = OpSLessThan %bool %101 %103
OpSelectionMerge %105 None
OpBranchConditional %104 %106 %107
%106 = OpLabel
OpBranch %105
%107 = OpLabel
OpBranch %98
%105 = OpLabel
%108 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_1
%109 = OpLoad %int %108
OpStore %i_4 %109
OpBranch %110
%110 = OpLabel
OpLoopMerge %111 %112 None
OpBranch %113
%113 = OpLabel
%114 = OpLoad %int %i_4
%115 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_0
%116 = OpLoad %int %115
%117 = OpSLessThan %bool %114 %116
OpSelectionMerge %118 None
OpBranchConditional %117 %119 %120
%119 = OpLabel
OpBranch %118
%120 = OpLabel
OpBranch %111
%118 = OpLabel
%121 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_1
%122 = OpLoad %int %121
OpStore %i_5 %122
OpBranch %123
%123 = OpLabel
OpLoopMerge %124 %125 None
OpBranch %126
%126 = OpLabel
%127 = OpLoad %int %i_5
%128 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_0
%129 = OpLoad %int %128
%130 = OpSLessThan %bool %127 %129
OpSelectionMerge %131 None
OpBranchConditional %130 %132 %133
%132 = OpLabel
OpBranch %131
%133 = OpLabel
OpBranch %124
%131 = OpLabel
%134 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_1
%135 = OpLoad %int %134
OpStore %i_6 %135
OpBranch %136
%136 = OpLabel
OpLoopMerge %137 %138 None
OpBranch %139
%139 = OpLabel
%140 = OpLoad %int %i_6
%141 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_0
%142 = OpLoad %int %141
%143 = OpSLessThan %bool %140 %142
OpSelectionMerge %144 None
OpBranchConditional %143 %145 %146
%145 = OpLabel
OpBranch %144
%146 = OpLabel
OpBranch %137
%144 = OpLabel
%147 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_1
%148 = OpLoad %int %147
OpStore %i_7 %148
OpBranch %149
%149 = OpLabel
OpLoopMerge %150 %151 None
OpBranch %152
%152 = OpLabel
%153 = OpLoad %int %i_7
%154 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_0
%155 = OpLoad %int %154
%156 = OpSLessThan %bool %153 %155
OpSelectionMerge %157 None
OpBranchConditional %156 %158 %159
%158 = OpLabel
OpBranch %157
%159 = OpLabel
OpBranch %150
%157 = OpLabel
%160 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_1
%161 = OpLoad %int %160
OpStore %i_8 %161
OpBranch %162
%162 = OpLabel
OpLoopMerge %163 %164 None
OpBranch %165
%165 = OpLabel
%166 = OpLoad %int %i_8
%167 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_0
%168 = OpLoad %int %167
%169 = OpSLessThan %bool %166 %168
OpSelectionMerge %170 None
OpBranchConditional %169 %171 %172
%171 = OpLabel
OpBranch %170
%172 = OpLabel
OpBranch %163
%170 = OpLabel
%173 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_1
%174 = OpLoad %int %173
OpStore %i_9 %174
OpBranch %175
%175 = OpLabel
OpLoopMerge %176 %177 None
OpBranch %178
%178 = OpLabel
%179 = OpLoad %int %i_9
%180 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_0
%181 = OpLoad %int %180
%182 = OpSLessThan %bool %179 %181
OpSelectionMerge %183 None
OpBranchConditional %182 %184 %185
%184 = OpLabel
OpBranch %183
%185 = OpLabel
OpBranch %176
%183 = OpLabel
%186 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_1
%187 = OpLoad %int %186
OpStore %i_10 %187
OpBranch %188
%188 = OpLabel
OpLoopMerge %189 %190 None
OpBranch %191
%191 = OpLabel
%192 = OpLoad %int %i_10
%193 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_0
%194 = OpLoad %int %193
%195 = OpSLessThan %bool %192 %194
OpSelectionMerge %196 None
OpBranchConditional %195 %197 %198
%197 = OpLabel
OpBranch %196
%198 = OpLabel
OpBranch %189
%196 = OpLabel
%199 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_1
%200 = OpLoad %int %199
OpStore %i_11 %200
OpBranch %201
%201 = OpLabel
OpLoopMerge %202 %203 None
OpBranch %204
%204 = OpLabel
%205 = OpLoad %int %i_11
%207 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_2
%208 = OpLoad %int %207
%209 = OpSLessThan %bool %205 %208
OpSelectionMerge %210 None
OpBranchConditional %209 %211 %212
%211 = OpLabel
OpBranch %210
%212 = OpLabel
OpBranch %202
%210 = OpLabel
%213 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_1
%214 = OpLoad %int %213
OpStore %i_12 %214
OpBranch %215
%215 = OpLabel
OpLoopMerge %216 %217 None
OpBranch %218
%218 = OpLabel
%219 = OpLoad %int %i_12
%220 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_0
%221 = OpLoad %int %220
%222 = OpSLessThan %bool %219 %221
OpSelectionMerge %223 None
OpBranchConditional %222 %224 %225
%224 = OpLabel
OpBranch %223
%225 = OpLabel
OpBranch %216
%223 = OpLabel
%226 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_1
%227 = OpLoad %int %226
OpStore %i_13 %227
OpBranch %228
%228 = OpLabel
OpLoopMerge %229 %230 None
OpBranch %231
%231 = OpLabel
%232 = OpLoad %int %i_13
%233 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_0
%234 = OpLoad %int %233
%235 = OpSLessThan %bool %232 %234
OpSelectionMerge %236 None
OpBranchConditional %235 %237 %238
%237 = OpLabel
OpBranch %236
%238 = OpLabel
OpBranch %229
%236 = OpLabel
%239 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_1
%240 = OpLoad %int %239
OpStore %i_14 %240
OpBranch %241
%241 = OpLabel
OpLoopMerge %242 %243 None
OpBranch %244
%244 = OpLabel
%245 = OpLoad %int %i_14
%246 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_2
%247 = OpLoad %int %246
%248 = OpSLessThan %bool %245 %247
OpSelectionMerge %249 None
OpBranchConditional %248 %250 %251
%250 = OpLabel
OpBranch %249
%251 = OpLabel
OpBranch %242
%249 = OpLabel
OpBranch %252
%252 = OpLabel
OpLoopMerge %253 %254 None
OpBranch %255
%255 = OpLabel
%256 = OpLoad %int %x_GLF_global_loop_count
%257 = OpIAdd %int %256 %int_1
OpStore %x_GLF_global_loop_count %257
OpBranch %254
%254 = OpLabel
%258 = OpLoad %int %x_GLF_global_loop_count
%260 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_3
%261 = OpLoad %int %260
%263 = OpISub %int %int_100 %261
%264 = OpSLessThan %bool %258 %263
OpBranchConditional %264 %252 %253
%253 = OpLabel
%265 = OpAccessChain %_ptr_Uniform_float %x_7 %uint_0 %int_0
%266 = OpLoad %float %265
%267 = OpLoad %float %f
%268 = OpFAdd %float %267 %266
OpStore %f %268
OpBranch %243
%243 = OpLabel
%269 = OpLoad %int %i_14
%270 = OpIAdd %int %269 %int_1
OpStore %i_14 %270
OpBranch %241
%242 = OpLabel
OpBranch %230
%230 = OpLabel
%271 = OpLoad %int %i_13
%272 = OpIAdd %int %271 %int_1
OpStore %i_13 %272
OpBranch %228
%229 = OpLabel
OpBranch %217
%217 = OpLabel
%273 = OpLoad %int %i_12
%274 = OpIAdd %int %273 %int_1
OpStore %i_12 %274
OpBranch %215
%216 = OpLabel
OpBranch %203
%203 = OpLabel
%275 = OpLoad %int %i_11
%276 = OpIAdd %int %275 %int_1
OpStore %i_11 %276
OpBranch %201
%202 = OpLabel
OpBranch %190
%190 = OpLabel
%277 = OpLoad %int %i_10
%278 = OpIAdd %int %277 %int_1
OpStore %i_10 %278
OpBranch %188
%189 = OpLabel
OpBranch %177
%177 = OpLabel
%279 = OpLoad %int %i_9
%280 = OpIAdd %int %279 %int_1
OpStore %i_9 %280
OpBranch %175
%176 = OpLabel
OpBranch %164
%164 = OpLabel
%281 = OpLoad %int %i_8
%282 = OpIAdd %int %281 %int_1
OpStore %i_8 %282
OpBranch %162
%163 = OpLabel
OpBranch %151
%151 = OpLabel
%283 = OpLoad %int %i_7
%284 = OpIAdd %int %283 %int_1
OpStore %i_7 %284
OpBranch %149
%150 = OpLabel
OpBranch %138
%138 = OpLabel
%285 = OpLoad %int %i_6
%286 = OpIAdd %int %285 %int_1
OpStore %i_6 %286
OpBranch %136
%137 = OpLabel
OpBranch %125
%125 = OpLabel
%287 = OpLoad %int %i_5
%288 = OpIAdd %int %287 %int_1
OpStore %i_5 %288
OpBranch %123
%124 = OpLabel
OpBranch %112
%112 = OpLabel
%289 = OpLoad %int %i_4
%290 = OpIAdd %int %289 %int_1
OpStore %i_4 %290
OpBranch %110
%111 = OpLabel
OpBranch %99
%99 = OpLabel
%291 = OpLoad %int %i_3
%292 = OpIAdd %int %291 %int_1
OpStore %i_3 %292
OpBranch %97
%98 = OpLabel
OpBranch %86
%86 = OpLabel
%293 = OpLoad %int %i_2
%294 = OpIAdd %int %293 %int_1
OpStore %i_2 %294
OpBranch %84
%85 = OpLabel
OpBranch %73
%73 = OpLabel
%295 = OpLoad %int %i_1
%296 = OpIAdd %int %295 %int_1
OpStore %i_1 %296
OpBranch %71
%72 = OpLabel
OpBranch %59
%59 = OpLabel
%297 = OpLoad %int %i
%298 = OpIAdd %int %297 %int_1
OpStore %i %298
OpBranch %57
%58 = OpLabel
%299 = OpAccessChain %_ptr_Uniform_float %x_7 %uint_0 %int_1
%300 = OpLoad %float %299
OpStore %sum %300
%301 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_1
%302 = OpLoad %int %301
OpStore %r %302
OpBranch %303
%303 = OpLabel
OpLoopMerge %304 %305 None
OpBranch %306
%306 = OpLabel
%307 = OpLoad %int %x_GLF_global_loop_count
%308 = OpSLessThan %bool %307 %int_100
OpSelectionMerge %309 None
OpBranchConditional %308 %310 %311
%310 = OpLabel
OpBranch %309
%311 = OpLabel
OpBranch %304
%309 = OpLabel
%312 = OpLoad %int %x_GLF_global_loop_count
%313 = OpIAdd %int %312 %int_1
OpStore %x_GLF_global_loop_count %313
%314 = OpLoad %float %f
%315 = OpLoad %float %sum
%316 = OpFAdd %float %315 %314
OpStore %sum %316
OpBranch %305
%305 = OpLabel
%317 = OpLoad %int %r
%318 = OpIAdd %int %317 %int_1
OpStore %r %318
OpBranch %303
%304 = OpLabel
%319 = OpLoad %float %sum
%320 = OpAccessChain %_ptr_Uniform_float %x_7 %uint_0 %int_2
%321 = OpLoad %float %320
%322 = OpFOrdEqual %bool %319 %321
OpSelectionMerge %323 None
OpBranchConditional %322 %324 %325
%324 = OpLabel
%326 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_0
%327 = OpLoad %int %326
%328 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_1
%329 = OpLoad %int %328
%330 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_1
%331 = OpLoad %int %330
%332 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_0
%333 = OpLoad %int %332
%334 = OpConvertSToF %float %327
%335 = OpConvertSToF %float %329
%336 = OpConvertSToF %float %331
%337 = OpConvertSToF %float %333
%338 = OpCompositeConstruct %v4float %334 %335 %336 %337
OpStore %x_GLF_color %338
OpBranch %323
%325 = OpLabel
%339 = OpAccessChain %_ptr_Uniform_int %x_10 %uint_0 %int_1
%340 = OpLoad %int %339
%341 = OpConvertSToF %float %340
%342 = OpCompositeConstruct %v4float %341 %341 %341 %341
OpStore %x_GLF_color %342
OpBranch %323
%323 = OpLabel
OpReturn
OpFunctionEnd
%tint_symbol_2 = OpFunction %void None %343
%tint_symbol = OpFunctionParameter %main_out
%347 = OpLabel
%348 = OpCompositeExtract %v4float %tint_symbol 0
OpStore %tint_symbol_1 %348
OpReturn
OpFunctionEnd
%main = OpFunction %void None %23
%350 = OpLabel
%351 = OpFunctionCall %void %main_1
%353 = OpLoad %v4float %x_GLF_color
%354 = OpCompositeConstruct %main_out %353
%352 = OpFunctionCall %void %tint_symbol_2 %354
OpReturn
OpFunctionEnd