text: /*-------------------------------------------------------------------------
   * Vulkan Conformance Tests
   * ------------------------
   *
   * Copyright (c) 2018 Google Inc.
   *
   * Licensed under the Apache License, Version 2.0 (the "License");
   * you may not use this file except in compliance with the License.
   * You may obtain a copy of the License at
   *
   *      http://www.apache.org/licenses/LICENSE-2.0
   *
   * Unless required by applicable law or agreed to in writing, software
   * distributed under the License is distributed on an "AS IS" BASIS,
   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
   * See the License for the specific language governing permissions and
   * limitations under the License.
   *
   *//*!
   * \file
   * \brief Metamorphic Tests
   *//*--------------------------------------------------------------------*/
  
  #include "vktMetamorphicTests.hpp"
  #include "vktMetamorphic.hpp"
  
  #include "vktTestCase.hpp"
  #include "vktTestCaseUtil.hpp"
  
  namespace vkt
  {
  namespace metamorphic
  {
  
  namespace {
  
  using namespace vk;
  
  void initPrograms1 (SourceCollections& dst)
  {
  
  	dst.spirvAsmSources.add("vert") <<
  		"               OpCapability Shader\n"
  		"          %1 = OpExtInstImport \"GLSL.std.450\"\n"
  		"               OpMemoryModel Logical GLSL450\n"
  		"               OpEntryPoint Vertex %main \"main\" %_ %pos %inColor\n"
  		"               OpSource GLSL 400\n"
  		"               OpSourceExtension \"GL_ARB_separate_shader_objects\"\n"
  		"               OpSourceExtension \"GL_ARB_shading_language_420pack\"\n"
  		"               OpName %main \"main\"\n"
  		"               OpName %gl_PerVertex \"gl_PerVertex\"\n"
  		"               OpMemberName %gl_PerVertex 0 \"gl_Position\"\n"
  		"               OpMemberName %gl_PerVertex 1 \"gl_PointSize\"\n"
  		"               OpMemberName %gl_PerVertex 2 \"gl_ClipDistance\"\n"
  		"               OpName %_ \"\"\n"
  		"               OpName %pos \"pos\"\n"
  		"               OpName %bufferVals \"bufferVals\"\n"
  		"               OpMemberName %bufferVals 0 \"f\"\n"
  		"               OpName %myBufferVals \"myBufferVals\"\n"
  		"               OpName %inColor \"inColor\"\n"
  		"               OpMemberDecorate %gl_PerVertex 0 BuiltIn Position\n"
  		"               OpMemberDecorate %gl_PerVertex 1 BuiltIn PointSize\n"
  		"               OpMemberDecorate %gl_PerVertex 2 BuiltIn ClipDistance\n"
  		"               OpDecorate %gl_PerVertex Block\n"
  		"               OpDecorate %pos Location 0\n"
  		"               OpMemberDecorate %bufferVals 0 Offset 0\n"
  		"               OpDecorate %bufferVals Block\n"
  		"               OpDecorate %myBufferVals DescriptorSet 0\n"
  		"               OpDecorate %myBufferVals Binding 0\n"
  		"               OpDecorate %inColor Location 1\n"
  		"       %void = OpTypeVoid\n"
  		"          %3 = OpTypeFunction %void\n"
  		"      %float = OpTypeFloat 32\n"
  		"    %v4float = OpTypeVector %float 4\n"
  		"       %uint = OpTypeInt 32 0\n"
  		"     %uint_1 = OpConstant %uint 1\n"
  		"%_arr_float_uint_1 = OpTypeArray %float %uint_1\n"
  		"%gl_PerVertex = OpTypeStruct %v4float %float %_arr_float_uint_1\n"
  		"%_ptr_Output_gl_PerVertex = OpTypePointer Output %gl_PerVertex\n"
  		"          %_ = OpVariable %_ptr_Output_gl_PerVertex Output\n"
  		"        %int = OpTypeInt 32 1\n"
  		"      %int_0 = OpConstant %int 0\n"
  		"%_ptr_Input_v4float = OpTypePointer Input %v4float\n"
  		"        %pos = OpVariable %_ptr_Input_v4float Input\n"
  		"%_ptr_Output_v4float = OpTypePointer Output %v4float\n"
  		" %bufferVals = OpTypeStruct %float\n"
  		"%_ptr_Uniform_bufferVals = OpTypePointer Uniform %bufferVals\n"
  		"%myBufferVals = OpVariable %_ptr_Uniform_bufferVals Uniform\n"
  		"    %inColor = OpVariable %_ptr_Input_v4float Input\n"
  		"       %main = OpFunction %void None %3\n"
  		"          %5 = OpLabel\n"
  		"         %18 = OpLoad %v4float %pos\n"
  		"         %20 = OpAccessChain %_ptr_Output_v4float %_ %int_0\n"
  		"               OpStore %20 %18\n"
  		"               OpReturn\n"
  		"               OpFunctionEnd\n";
  
  	dst.spirvAsmSources.add("frag1") <<
  		"               OpCapability Shader\n"
  		"          %1 = OpExtInstImport \"GLSL.std.450\"\n"
  		"               OpMemoryModel Logical GLSL450\n"
  		"               OpEntryPoint Fragment %main \"main\" %_GLF_color\n"
  		"               OpExecutionMode %main OriginUpperLeft\n"
  		"               OpSource ESSL 310\n"
  		"               OpName %main \"main\"\n"
  		"               OpName %i \"i\"\n"
  		"               OpName %data \"data\"\n"
  		"               OpName %i_0 \"i\"\n"
  		"               OpName %j \"j\"\n"
  		"               OpName %temp \"temp\"\n"
  		"               OpName %_GLF_color \"_GLF_color\"\n"
  		"               OpName %buf0 \"buf0\"\n"
  		"               OpMemberName %buf0 0 \"injectionSwitch\"\n"
  		"               OpName %_ \"\"\n"
  		"               OpDecorate %_GLF_color Location 0\n"
  		"               OpMemberDecorate %buf0 0 Offset 0\n"
  		"               OpDecorate %buf0 Block\n"
  		"               OpDecorate %_ DescriptorSet 0\n"
  		"               OpDecorate %_ Binding 0\n"
  		"       %void = OpTypeVoid\n"
  		"          %3 = OpTypeFunction %void\n"
  		"        %int = OpTypeInt 32 1\n"
  		"%_ptr_Function_int = OpTypePointer Function %int\n"
  		"      %int_0 = OpConstant %int 0\n"
  		"     %int_10 = OpConstant %int 10\n"
  		"       %bool = OpTypeBool\n"
  		"      %float = OpTypeFloat 32\n"
  		"       %uint = OpTypeInt 32 0\n"
  		"    %uint_10 = OpConstant %uint 10\n"
  		"%_arr_float_uint_10 = OpTypeArray %float %uint_10\n"
  		"%_ptr_Function__arr_float_uint_10 = OpTypePointer Function %_arr_float_uint_10\n"
  		"%_ptr_Function_float = OpTypePointer Function %float\n"
  		"      %int_1 = OpConstant %int 1\n"
  		"      %int_9 = OpConstant %int 9\n"
  		"    %v4float = OpTypeVector %float 4\n"
  		"%_ptr_Output_v4float = OpTypePointer Output %v4float\n"
  		" %_GLF_color = OpVariable %_ptr_Output_v4float Output\n"
  		"      %int_5 = OpConstant %int 5\n"
  		"   %float_10 = OpConstant %float 10\n"
  		"    %float_1 = OpConstant %float 1\n"
  		"    %v2float = OpTypeVector %float 2\n"
  		"       %buf0 = OpTypeStruct %v2float\n"
  		"%_ptr_Uniform_buf0 = OpTypePointer Uniform %buf0\n"
  		"          %_ = OpVariable %_ptr_Uniform_buf0 Uniform\n"
  		"       %main = OpFunction %void None %3\n"
  		"          %5 = OpLabel\n"
  		"          %i = OpVariable %_ptr_Function_int Function\n"
  		"       %data = OpVariable %_ptr_Function__arr_float_uint_10 Function\n"
  		"        %i_0 = OpVariable %_ptr_Function_int Function\n"
  		"          %j = OpVariable %_ptr_Function_int Function\n"
  		"       %temp = OpVariable %_ptr_Function_float Function\n"
  		"               OpStore %i %int_0\n"
  		"               OpBranch %10\n"
  		"         %10 = OpLabel\n"
  		"               OpLoopMerge %12 %13 None\n"
  		"               OpBranch %14\n"
  		"         %14 = OpLabel\n"
  		"         %15 = OpLoad %int %i\n"
  		"         %18 = OpSLessThan %bool %15 %int_10\n"
  		"               OpBranchConditional %18 %11 %12\n"
  		"         %11 = OpLabel\n"
  		"         %25 = OpLoad %int %i\n"
  		"         %26 = OpLoad %int %i\n"
  		"         %27 = OpISub %int %int_10 %26\n"
  		"         %28 = OpConvertSToF %float %27\n"
  		"         %30 = OpAccessChain %_ptr_Function_float %data %25\n"
  		"               OpStore %30 %28\n"
  		"               OpBranch %13\n"
  		"         %13 = OpLabel\n"
  		"         %31 = OpLoad %int %i\n"
  		"         %33 = OpIAdd %int %31 %int_1\n"
  		"               OpStore %i %33\n"
  		"               OpBranch %10\n"
  		"         %12 = OpLabel\n"
  		"               OpStore %i_0 %int_0\n"
  		"               OpBranch %35\n"
  		"         %35 = OpLabel\n"
  		"               OpLoopMerge %37 %38 None\n"
  		"               OpBranch %39\n"
  		"         %39 = OpLabel\n"
  		"         %40 = OpLoad %int %i_0\n"
  		"         %42 = OpSLessThan %bool %40 %int_9\n"
  		"               OpBranchConditional %42 %36 %37\n"
  		"         %36 = OpLabel\n"
  		"               OpStore %j %int_0\n"
  		"               OpBranch %44\n"
  		"         %44 = OpLabel\n"
  		"               OpLoopMerge %46 %47 None\n"
  		"               OpBranch %48\n"
  		"         %48 = OpLabel\n"
  		"         %49 = OpLoad %int %j\n"
  		"         %50 = OpSLessThan %bool %49 %int_10\n"
  		"               OpBranchConditional %50 %45 %46\n"
  		"         %45 = OpLabel\n"
  		"         %51 = OpLoad %int %j\n"
  		"         %52 = OpLoad %int %i_0\n"
  		"         %53 = OpIAdd %int %52 %int_1\n"
  		"         %54 = OpSLessThan %bool %51 %53\n"
  		"               OpSelectionMerge %56 None\n"
  		"               OpBranchConditional %54 %55 %56\n"
  		"         %55 = OpLabel\n"
  		"               OpBranch %47\n"
  		"         %56 = OpLabel\n"
  		"         %59 = OpLoad %int %i_0\n"
  		"         %60 = OpAccessChain %_ptr_Function_float %data %59\n"
  		"         %61 = OpLoad %float %60\n"
  		"               OpStore %temp %61\n"
  		"         %62 = OpLoad %int %i_0\n"
  		"         %63 = OpLoad %int %j\n"
  		"         %64 = OpAccessChain %_ptr_Function_float %data %63\n"
  		"         %65 = OpLoad %float %64\n"
  		"         %66 = OpAccessChain %_ptr_Function_float %data %62\n"
  		"               OpStore %66 %65\n"
  		"         %67 = OpLoad %int %j\n"
  		"         %68 = OpLoad %float %temp\n"
  		"         %69 = OpAccessChain %_ptr_Function_float %data %67\n"
  		"               OpStore %69 %68\n"
  		"               OpBranch %47\n"
  		"         %47 = OpLabel\n"
  		"         %70 = OpLoad %int %j\n"
  		"         %71 = OpIAdd %int %70 %int_1\n"
  		"               OpStore %j %71\n"
  		"               OpBranch %44\n"
  		"         %46 = OpLabel\n"
  		"               OpBranch %38\n"
  		"         %38 = OpLabel\n"
  		"         %72 = OpLoad %int %i_0\n"
  		"         %73 = OpIAdd %int %72 %int_1\n"
  		"               OpStore %i_0 %73\n"
  		"               OpBranch %35\n"
  		"         %37 = OpLabel\n"
  		"         %78 = OpAccessChain %_ptr_Function_float %data %int_5\n"
  		"         %79 = OpLoad %float %78\n"
  		"         %81 = OpFDiv %float %79 %float_10\n"
  		"         %82 = OpAccessChain %_ptr_Function_float %data %int_9\n"
  		"         %83 = OpLoad %float %82\n"
  		"         %84 = OpFDiv %float %83 %float_10\n"
  		"         %85 = OpAccessChain %_ptr_Function_float %data %int_0\n"
  		"         %86 = OpLoad %float %85\n"
  		"         %87 = OpFDiv %float %86 %float_10\n"
  		"         %89 = OpCompositeConstruct %v4float %81 %84 %87 %float_1\n"
  		"               OpStore %_GLF_color %89\n"
  		"               OpReturn\n"
  		"               OpFunctionEnd\n";
  
  	dst.spirvAsmSources.add("frag2") <<
  		"               OpCapability Shader\n"
  		"          %1 = OpExtInstImport \"GLSL.std.450\"\n"
  		"               OpMemoryModel Logical GLSL450\n"
  		"               OpEntryPoint Fragment %main \"main\" %_GLF_color\n"
  		"               OpExecutionMode %main OriginUpperLeft\n"
  		"               OpSource ESSL 310\n"
  		"               OpName %main \"main\"\n"
  		"               OpName %i \"i\"\n"
  		"               OpName %data \"data\"\n"
  		"               OpName %i_0 \"i\"\n"
  		"               OpName %j \"j\"\n"
  		"               OpName %buf0 \"buf0\"\n"
  		"               OpMemberName %buf0 0 \"injectionSwitch\"\n"
  		"               OpName %_ \"\"\n"
  		"               OpName %temp \"temp\"\n"
  		"               OpName %_GLF_color \"_GLF_color\"\n"
  		"               OpMemberDecorate %buf0 0 Offset 0\n"
  		"               OpDecorate %buf0 Block\n"
  		"               OpDecorate %_ DescriptorSet 0\n"
  		"               OpDecorate %_ Binding 0\n"
  		"               OpDecorate %_GLF_color Location 0\n"
  		"       %void = OpTypeVoid\n"
  		"          %3 = OpTypeFunction %void\n"
  		"        %int = OpTypeInt 32 1\n"
  		"%_ptr_Function_int = OpTypePointer Function %int\n"
  		"      %int_0 = OpConstant %int 0\n"
  		"     %int_10 = OpConstant %int 10\n"
  		"       %bool = OpTypeBool\n"
  		"      %float = OpTypeFloat 32\n"
  		"       %uint = OpTypeInt 32 0\n"
  		"    %uint_10 = OpConstant %uint 10\n"
  		"%_arr_float_uint_10 = OpTypeArray %float %uint_10\n"
  		"%_ptr_Function__arr_float_uint_10 = OpTypePointer Function %_arr_float_uint_10\n"
  		"%_ptr_Function_float = OpTypePointer Function %float\n"
  		"      %int_1 = OpConstant %int 1\n"
  		"      %int_9 = OpConstant %int 9\n"
  		"    %v2float = OpTypeVector %float 2\n"
  		"       %buf0 = OpTypeStruct %v2float\n"
  		"%_ptr_Uniform_buf0 = OpTypePointer Uniform %buf0\n"
  		"          %_ = OpVariable %_ptr_Uniform_buf0 Uniform\n"
  		"     %uint_0 = OpConstant %uint 0\n"
  		"%_ptr_Uniform_float = OpTypePointer Uniform %float\n"
  		"     %uint_1 = OpConstant %uint 1\n"
  		"    %v4float = OpTypeVector %float 4\n"
  		"%_ptr_Output_v4float = OpTypePointer Output %v4float\n"
  		" %_GLF_color = OpVariable %_ptr_Output_v4float Output\n"
  		"      %int_5 = OpConstant %int 5\n"
  		"   %float_10 = OpConstant %float 10\n"
  		"    %float_1 = OpConstant %float 1\n"
  		"       %main = OpFunction %void None %3\n"
  		"          %5 = OpLabel\n"
  		"          %i = OpVariable %_ptr_Function_int Function\n"
  		"       %data = OpVariable %_ptr_Function__arr_float_uint_10 Function\n"
  		"        %i_0 = OpVariable %_ptr_Function_int Function\n"
  		"          %j = OpVariable %_ptr_Function_int Function\n"
  		"         %64 = OpVariable %_ptr_Function_int Function\n"
  		"       %temp = OpVariable %_ptr_Function_float Function\n"
  		"               OpStore %i %int_0\n"
  		"               OpBranch %10\n"
  		"         %10 = OpLabel\n"
  		"               OpLoopMerge %12 %13 None\n"
  		"               OpBranch %14\n"
  		"         %14 = OpLabel\n"
  		"         %15 = OpLoad %int %i\n"
  		"         %18 = OpSLessThan %bool %15 %int_10\n"
  		"               OpBranchConditional %18 %11 %12\n"
  		"         %11 = OpLabel\n"
  		"         %25 = OpLoad %int %i\n"
  		"         %26 = OpLoad %int %i\n"
  		"         %27 = OpISub %int %int_10 %26\n"
  		"         %28 = OpConvertSToF %float %27\n"
  		"         %30 = OpAccessChain %_ptr_Function_float %data %25\n"
  		"               OpStore %30 %28\n"
  		"               OpBranch %13\n"
  		"         %13 = OpLabel\n"
  		"         %31 = OpLoad %int %i\n"
  		"         %33 = OpIAdd %int %31 %int_1\n"
  		"               OpStore %i %33\n"
  		"               OpBranch %10\n"
  		"         %12 = OpLabel\n"
  		"               OpStore %i_0 %int_0\n"
  		"               OpBranch %35\n"
  		"         %35 = OpLabel\n"
  		"               OpLoopMerge %37 %38 None\n"
  		"               OpBranch %39\n"
  		"         %39 = OpLabel\n"
  		"         %40 = OpLoad %int %i_0\n"
  		"         %42 = OpSLessThan %bool %40 %int_9\n"
  		"               OpBranchConditional %42 %36 %37\n"
  		"         %36 = OpLabel\n"
  		"               OpStore %j %int_0\n"
  		"               OpBranch %44\n"
  		"         %44 = OpLabel\n"
  		"               OpLoopMerge %46 %47 None\n"
  		"               OpBranch %48\n"
  		"         %48 = OpLabel\n"
  		"         %49 = OpLoad %int %j\n"
  		"         %50 = OpSLessThan %bool %49 %int_10\n"
  		"               OpBranchConditional %50 %45 %46\n"
  		"         %45 = OpLabel\n"
  		"         %51 = OpLoad %int %j\n"
  		"         %58 = OpAccessChain %_ptr_Uniform_float %_ %int_0 %uint_0\n"
  		"         %59 = OpLoad %float %58\n"
  		"         %61 = OpAccessChain %_ptr_Uniform_float %_ %int_0 %uint_1\n"
  		"         %62 = OpLoad %float %61\n"
  		"         %63 = OpFOrdLessThan %bool %59 %62\n"
  		"               OpSelectionMerge %66 None\n"
  		"               OpBranchConditional %63 %65 %69\n"
  		"         %65 = OpLabel\n"
  		"         %67 = OpLoad %int %i_0\n"
  		"         %68 = OpIAdd %int %67 %int_1\n"
  		"               OpStore %64 %68\n"
  		"               OpBranch %66\n"
  		"         %69 = OpLabel\n"
  		"               OpStore %64 %int_1\n"
  		"               OpBranch %66\n"
  		"         %66 = OpLabel\n"
  		"         %70 = OpLoad %int %64\n"
  		"         %71 = OpSLessThan %bool %51 %70\n"
  		"               OpSelectionMerge %73 None\n"
  		"               OpBranchConditional %71 %72 %73\n"
  		"         %72 = OpLabel\n"
  		"               OpBranch %47\n"
  		"         %73 = OpLabel\n"
  		"         %75 = OpAccessChain %_ptr_Uniform_float %_ %int_0 %uint_0\n"
  		"         %76 = OpLoad %float %75\n"
  		"         %77 = OpAccessChain %_ptr_Uniform_float %_ %int_0 %uint_1\n"
  		"         %78 = OpLoad %float %77\n"
  		"         %79 = OpFOrdGreaterThan %bool %76 %78\n"
  		"               OpSelectionMerge %81 None\n"
  		"               OpBranchConditional %79 %80 %81\n"
  		"         %80 = OpLabel\n"
  		"               OpBranch %47\n"
  		"         %81 = OpLabel\n"
  		"         %84 = OpLoad %int %i_0\n"
  		"         %85 = OpAccessChain %_ptr_Function_float %data %84\n"
  		"         %86 = OpLoad %float %85\n"
  		"               OpStore %temp %86\n"
  		"         %87 = OpLoad %int %i_0\n"
  		"         %88 = OpLoad %int %j\n"
  		"         %89 = OpAccessChain %_ptr_Function_float %data %88\n"
  		"         %90 = OpLoad %float %89\n"
  		"         %91 = OpAccessChain %_ptr_Function_float %data %87\n"
  		"               OpStore %91 %90\n"
  		"         %92 = OpLoad %int %j\n"
  		"         %93 = OpLoad %float %temp\n"
  		"         %94 = OpAccessChain %_ptr_Function_float %data %92\n"
  		"               OpStore %94 %93\n"
  		"               OpBranch %47\n"
  		"         %47 = OpLabel\n"
  		"         %95 = OpLoad %int %j\n"
  		"         %96 = OpIAdd %int %95 %int_1\n"
  		"               OpStore %j %96\n"
  		"               OpBranch %44\n"
  		"         %46 = OpLabel\n"
  		"               OpBranch %38\n"
  		"         %38 = OpLabel\n"
  		"         %97 = OpLoad %int %i_0\n"
  		"         %98 = OpIAdd %int %97 %int_1\n"
  		"               OpStore %i_0 %98\n"
  		"               OpBranch %35\n"
  		"         %37 = OpLabel\n"
  		"        %103 = OpAccessChain %_ptr_Function_float %data %int_5\n"
  		"        %104 = OpLoad %float %103\n"
  		"        %106 = OpFDiv %float %104 %float_10\n"
  		"        %107 = OpAccessChain %_ptr_Function_float %data %int_9\n"
  		"        %108 = OpLoad %float %107\n"
  		"        %109 = OpFDiv %float %108 %float_10\n"
  		"        %110 = OpAccessChain %_ptr_Function_float %data %int_0\n"
  		"        %111 = OpLoad %float %110\n"
  		"        %112 = OpFDiv %float %111 %float_10\n"
  		"        %114 = OpCompositeConstruct %v4float %106 %109 %112 %float_1\n"
  		"               OpStore %_GLF_color %114\n"
  		"               OpReturn\n"
  		"               OpFunctionEnd\n";
  
  }
  
  tcu::TestStatus runTest1 (Context& context) {
  	std::vector<UniformEntry> uniformEntries;
  	UniformEntry uniformEntry;
  
  	tcu::Vec2 u1 = tcu::Vec2(0.0f, 1.0f);
  	uniformEntry.size = sizeof(u1);
  	uniformEntry.value = (void *)(&u1);
  	uniformEntries.push_back(uniformEntry);
  
  	return renderShaderPair(context, uniformEntries);
  }
  
  } // anonymous
  
  tcu::TestCaseGroup* createTests (tcu::TestContext& testCtx)
  {
  	de::MovePtr<tcu::TestCaseGroup>	metamorphicTests	(new tcu::TestCaseGroup(testCtx, "metamorphic", "Metamorphic Tests"));
  
  	addFunctionCaseWithPrograms	(metamorphicTests.get(), "metamorphic1",	"", initPrograms1, runTest1);
  
  	return metamorphicTests.release();
  }
  
  } // metamorphic
  } // vkt
  