/*-------------------------------------------------------------------------
 * Vulkan Conformance Tests
 * ------------------------
 *
 * Copyright (c) 2019 The Khronos Group 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 SPIR-V non semantic info tests
 *//*--------------------------------------------------------------------*/

#include "vkApiVersion.hpp"

#include "vktSpvAsmNonSemanticInfoTests.hpp"
#include "vktTestCase.hpp"
#include "vktSpvAsmComputeShaderCase.hpp"
#include "vktSpvAsmGraphicsShaderTestUtil.hpp"

namespace vkt
{
namespace SpirVAssembly
{

using namespace vk;

enum TestType
{
	TT_BASIC					= 0,
	TT_DUMMY_INSTRUCTION_SET,
	TT_LARGE_INSTRUCTION_NUMBER,
	TT_MANY_PARAMETERS,
	TT_ANY_CONSTANT_TYPE,
	TT_ANY_CONSTANT_TYPE_USED,
	TT_ANY_NON_CONSTANT_TYPE,
	TT_PLACEMENT
};

static ComputeShaderSpec getComputeShaderSpec ()
{
	deUint32 numElements = 10;
	std::vector<float>	inoutFloats	(10, 0);
	for (size_t ndx = 0; ndx < numElements; ++ndx)
		inoutFloats[ndx] = 1.0f * static_cast<float>(ndx);

	// in one of tests we need to do imageLoad
	// we don't need any special values in here
	std::vector<int> inputInts(256, 0);

	ComputeShaderSpec spec;
	spec.extensions.push_back("VK_KHR_shader_non_semantic_info");
	spec.inputs.push_back(BufferSp(new Float32Buffer(inoutFloats)));
	spec.inputs.push_back(Resource(BufferSp(new Int32Buffer(inputInts)), vk::VK_DESCRIPTOR_TYPE_STORAGE_IMAGE));
	spec.outputs.push_back(BufferSp(new Float32Buffer(inoutFloats)));
	spec.numWorkGroups = tcu::IVec3(numElements, 1, 1);
	return spec;
}

class SpvAsmSpirvNonSemanticInfoBasicInstance : public ComputeShaderSpec, public SpvAsmComputeShaderInstance
{
public:
	SpvAsmSpirvNonSemanticInfoBasicInstance		(Context& ctx, TestType type);

	tcu::TestStatus			iterate				(void);

protected:
	TestType m_testType;
};

SpvAsmSpirvNonSemanticInfoBasicInstance::SpvAsmSpirvNonSemanticInfoBasicInstance(Context& ctx, TestType type)
	: ComputeShaderSpec(getComputeShaderSpec())
	, SpvAsmComputeShaderInstance(ctx, *this)
	, m_testType(type)
{
}

tcu::TestStatus SpvAsmSpirvNonSemanticInfoBasicInstance::iterate (void)
{
	return SpvAsmComputeShaderInstance::iterate();
}

class SpvAsmSpirvNonSemanticInfoBasicCase : public TestCase
{
public:
	SpvAsmSpirvNonSemanticInfoBasicCase		(tcu::TestContext& testCtx, const char* name, TestType type);

	void			checkSupport			(Context& context) const;
	void			initPrograms			(vk::SourceCollections& programCollection) const;
	TestInstance*	createInstance			(Context& context) const;

protected:
	TestType m_testType;
};

SpvAsmSpirvNonSemanticInfoBasicCase::SpvAsmSpirvNonSemanticInfoBasicCase(tcu::TestContext& testCtx, const char* name, TestType type)
	: TestCase (testCtx, name, "")
	, m_testType(type)
{
}

void SpvAsmSpirvNonSemanticInfoBasicCase::checkSupport(Context& context) const
{
	context.requireDeviceFunctionality("VK_KHR_shader_non_semantic_info");
}

void SpvAsmSpirvNonSemanticInfoBasicCase::initPrograms (SourceCollections& programCollection) const
{
	std::string extendedInstructions	= "%extInstSet = OpExtInstImport \"NonSemantic.KHR.DebugInfo\"\n";
	std::string additionalDecorations	= "";
	std::string additionalPreamble		= "";
	std::string additionalTypesAndConst = "";
	std::string beginningOfMain			= "";
	std::string middleOfMain			= "";

	switch (m_testType)
	{
	case TT_BASIC:
		// Minimal test of basic functionality

		additionalPreamble +=
			"%fileStr = OpString \"path\\to\\source.file\"\n"
			"OpSource GLSL 430 %fileStr\n";
		middleOfMain +=
			"%tmp = OpExtInst %void %extInstSet 1 %main %fileStr\n";
		break;

	case TT_DUMMY_INSTRUCTION_SET:
		// Testing non existing instruction set

		extendedInstructions =
			"%extInstSet = OpExtInstImport \"NonSemantic.P.B.DummySet\"\n";
		additionalPreamble +=
			"%testStrA = OpString \"this.is.test\"\n"
			"%testStrB = OpString \"yet another test\"\n";
		middleOfMain +=
			"%tmpA = OpExtInst %void %extInstSet 55 %id %testStrA %testStrB\n"
			"OpLine %testStrA 1 1\n"
			"%tmpB = OpExtInst %void %extInstSet 99 %testStrA %main %testStrA\n"
			"OpLine %testStrB 2 2\n"
			"OpNoLine\n";
		break;

	case TT_LARGE_INSTRUCTION_NUMBER:
	{
		// Any instruction number should work - testing large values near uint::max

		deUint32 instNr = std::numeric_limits<deUint32>::max() - 1;
		middleOfMain +=
			"%tmpA = OpExtInst %void %extInstSet " + std::to_string(instNr) + " %main\n" +
			"%tmpB = OpExtInst %void %extInstSet 4294967290 %main\n";
		break;
	}

	case TT_MANY_PARAMETERS:
		// Many parameters should work - testing 100 parameters

		middleOfMain +=
			"%tmp = OpExtInst %void %extInstSet 1234";
		for (deUint32 parameterIndex = 0; parameterIndex < 100; parameterIndex++)
		{
			std::string iStr = std::to_string(parameterIndex);
			std::string strVarName = std::string("%testStr") + iStr;
			additionalPreamble += strVarName + " = OpString \"" + iStr +"\"\n";
			middleOfMain += std::string(" ") + strVarName;
		}
		middleOfMain += "\n";
		break;

	case TT_ANY_CONSTANT_TYPE:
	case TT_ANY_CONSTANT_TYPE_USED:
	{
		// Any type of constant parameter should work - testing undef,
		// int, uint, float, struct, vector, array, string, matrix

		additionalDecorations =
			"OpMemberDecorate %struct 0 Offset 0\n"
			"OpMemberDecorate %struct 1 Offset 4\n"
			"OpMemberDecorate %struct 2 Offset 16\n";

		std::string types =
			"%struct             = OpTypeStruct %f32 %fvec3 %i32\n"
			"%c_array_size       = OpConstant %u32 4\n"
			"%array4             = OpTypeArray %f32 %c_array_size\n"
			"%matrix3x3          = OpTypeMatrix %fvec3 3\n";

		std::string constans =
			"%undef      = OpUndef %i32\n"
			"%c_i32      = OpConstant %i32 -45\n"
			"%c_u32      = OpConstant %u32 99\n"
			"%c_f32      = OpConstant %f32 0.0\n"
			"%c_fvec3    = OpConstantComposite %fvec3 %c_f32 %c_f32 %c_f32\n"
			"%c_struct   = OpConstantComposite %struct %c_f32 %c_fvec3 %undef\n"
			"%c_array    = OpConstantComposite %array4 %c_f32 %c_f32 %c_f32 %c_f32\n"
			"%c_matrix   = OpConstantComposite %matrix3x3 %c_fvec3 %c_fvec3 %c_fvec3\n";

		additionalPreamble +=
			"%testStr = OpString \"\"\n";
		additionalTypesAndConst = types + constans;
		middleOfMain += "%tmp = OpExtInst %void %extInstSet 999 %main %undef %c_i32 %c_u32 %c_f32 %c_struct %c_fvec3 %c_array %testStr %c_matrix\n";
		if (m_testType == TT_ANY_CONSTANT_TYPE)
			break;

		// use all constans outside of OpExtInst
		middleOfMain +=
			"%tmp01      = OpCompositeExtract %f32 %c_fvec3 2\n"
			"%tmp02      = OpFAdd %f32 %tmp01 %c_f32\n"
			"%tmp03      = OpCompositeExtract %f32 %c_struct 0\n"
			"%tmp04      = OpFAdd %f32 %tmp02 %tmp03\n"
			"%tmp05      = OpCompositeExtract %f32 %c_array 1\n"
			"%tmp06      = OpFAdd %f32 %tmp04 %tmp05\n"
			"%tmp07      = OpCompositeExtract %fvec3 %c_matrix 1\n"
			"%tmp08      = OpCompositeExtract %f32 %tmp07 1\n"
			"%tmp09      = OpFMul %f32 %tmp06 %tmp08\n"
			"%tmp10      = OpConvertSToF %f32 %c_i32\n"
			"%tmp11      = OpFMul %f32 %tmp09 %tmp10\n"
			"              OpStore %outloc %tmp11\n";
		break;
	}

	case TT_ANY_NON_CONSTANT_TYPE:
	{
		// Any type of existing semantic result ID should be referencable. Testing
		// the result of a semantic OpExtInst, an entry point, variables of different types,
		// result IDs of buffer and texture loads, result IDs of arithmetic instructions,
		// result of an OpLoad, result of a comparison / logical instruction.

		additionalDecorations =
			"OpMemberDecorate %struct 0 Offset 0\n"
			"OpMemberDecorate %struct 1 Offset 4\n"
			"OpMemberDecorate %struct 2 Offset 16\n";
		extendedInstructions +=
			"%std450 = OpExtInstImport \"GLSL.std.450\"\n";
		additionalTypesAndConst =
			"%struct             = OpTypeStruct %f32 %fvec3 %f32\n"
			"%struct_ptr         = OpTypePointer Function %struct\n"
			"%c_array_size       = OpConstant %u32 4\n"
			"%array4             = OpTypeArray %f32 %c_array_size\n"
			"%array4_ptr         = OpTypePointer Function %array4\n"
			"%matrix3x3          = OpTypeMatrix %fvec3 3\n"
			"%matrix3x3_ptr      = OpTypePointer Function %matrix3x3\n"
			"%uvec2              = OpTypeVector %u32 2\n"
			"%fvec4              = OpTypeVector %f32 4\n"
			"%uv                 = OpConstantComposite %uvec2 %zero %zero\n";

		beginningOfMain =
			"%struct_var = OpVariable %struct_ptr Function\n"
			"%array_var  = OpVariable %array4_ptr Function\n"
			"%matrix_var = OpVariable %matrix3x3_ptr Function\n";
		middleOfMain =
			"%tmp01      = OpExtInst %void %extInstSet 486 %main %id %x %idval %struct_var %array_var %matrix_var %uvec3ptr %indata\n"
			"%arithmRes  = OpIAdd %u32 %x %x\n"
			"%extInstRes = OpExtInst %f32 %std450 FAbs %inval\n"
			"%logicRes   = OpIsNan %bool %inval\n"
			"%imgLoadRes = OpLoad %image_type %image\n"
			"%tmp02      = OpExtInst %void %extInstSet 963 %tmp01 %arithmRes %inloc %outloc %inval %extInstRes %logicRes %imgLoadRes %std450\n";
		break;
	}

	case TT_PLACEMENT:
		// The instructions should be able to be placed at global scope,
		// in the types/constants section and between function definitions

		additionalTypesAndConst =
			"%extInstA   = OpExtInst %void %extInstSet 1 %id\n"			// at global scope
			"%floatf     = OpTypeFunction %f32 %f32\n"
			"%funDefA    = OpFunction %f32 None %floatf\n"
			"%funApa     = OpFunctionParameter %f32\n"
			"%funA       = OpLabel\n"
			"              OpReturnValue %funApa\n"
			"              OpFunctionEnd\n"
			"%extInstB  = OpExtInst %void %extInstSet 3 %id\n";			// between definitions
		middleOfMain +=
			"%aRes       = OpFunctionCall %f32 %funDefA %inval\n"
			"%extInstC   = OpExtInst %void %extInstSet 4 %aRes\n"		// within a block
			"              OpStore %outloc %aRes\n";
		break;
	}

	std::string source =
		getComputeAsmShaderPreamble("", "OpExtension \"SPV_KHR_non_semantic_info\"\n" + extendedInstructions) +
		additionalPreamble +
		"OpDecorate %id BuiltIn GlobalInvocationId\n" +
		"OpDecorate %buf BufferBlock\n"
		"OpDecorate %indata DescriptorSet 0\n"
		"OpDecorate %indata Binding 0\n"
		"OpDecorate %image DescriptorSet 0\n"
		"OpDecorate %image Binding 1\n"
		"OpDecorate %image NonWritable\n"
		"OpDecorate %outdata DescriptorSet 0\n"
		"OpDecorate %outdata Binding 2\n"
		"OpDecorate %f32arr ArrayStride 4\n"
		"OpMemberDecorate %buf 0 Offset 0\n" +
		additionalDecorations +
		std::string(getComputeAsmCommonTypes()) +
		std::string(getComputeAsmInputOutputBuffer()) +
		"%id         = OpVariable %uvec3ptr Input\n"
		"%image_type = OpTypeImage %f32 2D 0 0 0 2 Rgba8\n"
		"%image_ptr  = OpTypePointer UniformConstant %image_type\n"
		"%image      = OpVariable %image_ptr UniformConstant\n"
		"%zero       = OpConstant %i32 0\n" +
		additionalTypesAndConst +
		"%main       = OpFunction %void None %voidf\n"
		"%label      = OpLabel\n" +
		beginningOfMain +
		"%idval      = OpLoad %uvec3 %id\n"
		"%x          = OpCompositeExtract %u32 %idval 0\n"
		"%inloc      = OpAccessChain %f32ptr %indata %zero %x\n"
		"%outloc     = OpAccessChain %f32ptr %outdata %zero %x\n"
		"%inval      = OpLoad %f32 %inloc\n" +
		middleOfMain +
		"             OpStore %outloc %inval\n"
		"             OpReturn\n"
		"             OpFunctionEnd\n";

	programCollection.spirvAsmSources.add("compute") << source;
}

TestInstance* SpvAsmSpirvNonSemanticInfoBasicCase::createInstance (Context& context) const
{
	return new SpvAsmSpirvNonSemanticInfoBasicInstance(context, m_testType);
}

tcu::TestCaseGroup* createNonSemanticInfoGroup(tcu::TestContext& testCtx)
{
	de::MovePtr<tcu::TestCaseGroup> group (new tcu::TestCaseGroup(testCtx, "non_semantic_info", "Test for VK_KHR_shader_non_semantic_info"));

	struct TestData
	{
		const char*	name;
		TestType	type;
	};
	std::vector<TestData> testList =
	{
		{ "basic",						TT_BASIC },
		{ "dummy_instruction_set",		TT_DUMMY_INSTRUCTION_SET },
		{ "large_instruction_number",	TT_LARGE_INSTRUCTION_NUMBER },
		{ "many_parameters",			TT_MANY_PARAMETERS },
		{ "any_constant_type",			TT_ANY_CONSTANT_TYPE },
		{ "any_constant_type_used",		TT_ANY_CONSTANT_TYPE_USED },
		{ "any_non_constant_type",		TT_ANY_NON_CONSTANT_TYPE },
		{ "placement",					TT_PLACEMENT },
	};

	for (const auto& item : testList)
		group->addChild(new SpvAsmSpirvNonSemanticInfoBasicCase(testCtx, item.name, item.type));

	return group.release();
}

} // SpirVAssembly
} // vkt
