1#!amber 2# 3# Copyright 2020 The Khronos Group Inc. 4# Copyright 2020 Valve Corporation. 5# 6# Licensed under the Apache License, Version 2.0 (the "License"); 7# you may not use this file except in compliance with the License. 8# You may obtain a copy of the License at 9# 10# https://www.apache.org/licenses/LICENSE-2.0 11# 12# Unless required by applicable law or agreed to in writing, software 13# distributed under the License is distributed on an "AS IS" BASIS, 14# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 15# See the License for the specific language governing permissions and 16# limitations under the License. 17 18SHADER compute comp SPIRV-ASM TARGET_ENV spv1.0 19; SPIR-V 20; Version: 1.0 21 OpCapability Shader 22 OpMemoryModel Logical GLSL450 23 OpEntryPoint GLCompute %main "main" 24 OpExecutionMode %main LocalSize 1 1 1 25 OpMemberDecorate %InputBlock 0 Offset 0 26 OpDecorate %InputBlock BufferBlock 27 OpDecorate %inputBuffer DescriptorSet 0 28 OpDecorate %inputBuffer Binding 0 29 OpMemberDecorate %OutputBlock 0 Offset 0 30 OpDecorate %OutputBlock BufferBlock 31 OpDecorate %outputBuffer DescriptorSet 0 32 OpDecorate %outputBuffer Binding 1 33 %void = OpTypeVoid 34 %voidFunc = OpTypeFunction %void 35 %uint = OpTypeInt 32 0 36 %uint_4 = OpConstant %uint 4 37 %uint_5 = OpConstant %uint 5 38 %uint_6 = OpConstant %uint 6 39 %uint_7 = OpConstant %uint 7 40 %uint_8 = OpConstant %uint 8 41 %InputBlock = OpTypeStruct %uint 42 %InputBlock_ptr = OpTypePointer Uniform %InputBlock 43 %inputBuffer = OpVariable %InputBlock_ptr Uniform 44 %int = OpTypeInt 32 1 45 %int_0 = OpConstant %int 0 46 %uint_uniform_ptr = OpTypePointer Uniform %uint 47%uint_Function_ptr = OpTypePointer Function %uint 48 %OutputBlock = OpTypeStruct %uint 49 %OutputBlock_ptr = OpTypePointer Uniform %OutputBlock 50 %outputBuffer = OpVariable %OutputBlock_ptr Uniform 51 %main = OpFunction %void None %voidFunc 52 %mainLabel = OpLabel 53; 54; %aux will contain value 4 by default and it should not be modified. 55; 56 %aux = OpVariable %uint_Function_ptr Function 57 OpStore %aux %uint_4 58 %ptrIn = OpAccessChain %uint_uniform_ptr %inputBuffer %int_0 59 %inputVal = OpLoad %uint %ptrIn 60; 61; From fauly.asm in https://gitlab.freedesktop.org/mesa/mesa/-/issues/3460 62; 63; OpSelectionMerge %3153 None 64; OpSwitch %166 %3152 0 %3153 1 %3151 2 %3150 3 %3149 65; %3152 = OpLabel 66; OpBranch %3153 67; %3151 = OpLabel 68; OpBranch %3153 69; %3150 = OpLabel 70; %345 = OpAccessChain %_ptr_StorageBuffer_v4float %71 %uint_0 %uint_37 71; %346 = OpLoad %v4float %345 72; %347 = OpBitcast %v4uint %346 73; %348 = OpCompositeExtract %uint %347 0 74; %188 = OpShiftLeftLogical %uint %348 %uint_1 75; OpBranch %3153 76; %3149 = OpLabel 77; OpBranch %3153 78; %3153 = OpLabel 79; 80; Similar structure replicated below. 81; Value 0 jumps to the merge label while the others store unexpected values in %aux. 82; 83 OpSelectionMerge %mergeLabel None 84 OpSwitch %inputVal %defaultLabel 0 %mergeLabel 1 %val1Label 2 %val2Label 3 %val3Label 85 %defaultLabel = OpLabel 86 OpStore %aux %uint_5 87 OpBranch %mergeLabel 88 %val1Label = OpLabel 89 OpStore %aux %uint_6 90 OpBranch %mergeLabel 91 %val2Label = OpLabel 92 OpStore %aux %uint_7 93 OpBranch %mergeLabel 94 %val3Label = OpLabel 95 OpStore %aux %uint_8 96 OpBranch %mergeLabel 97 %mergeLabel = OpLabel 98 %ptrOut = OpAccessChain %uint_uniform_ptr %outputBuffer %int_0 99 %aux_val = OpLoad %uint %aux 100 OpStore %ptrOut %aux_val 101 OpReturn 102 OpFunctionEnd 103END 104 105BUFFER inputBuffer DATA_TYPE uint32 DATA 0 END 106BUFFER outputBuffer DATA_TYPE uint32 DATA 0 END 107 108# Store 0 as the input value to make the switch go directly to the merge label. 109PIPELINE compute compute_pipeline 110 ATTACH comp 111 BIND BUFFER inputBuffer AS storage DESCRIPTOR_SET 0 BINDING 0 112 BIND BUFFER outputBuffer AS storage DESCRIPTOR_SET 0 BINDING 1 113END 114 115RUN compute_pipeline 1 1 1 116# Expect 4, the initial value stored in %aux before the switch. 117EXPECT outputBuffer IDX 0 EQ 4 118