/*------------------------------------------------------------------------
 * Vulkan Conformance Tests
 * ------------------------
 *
 * Copyright (c) 2020 The Khronos Group Inc.
 * Copyright (c) 2020 Advanced Micro Devices, 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 Pipeline Cache Tests
 */
/*--------------------------------------------------------------------*/

#include "vktPipelineCreationCacheControlTests.hpp"

#include "deRandom.hpp"
#include "deUniquePtr.hpp"
#include "tcuStringTemplate.hpp"
#include "vkDeviceUtil.hpp"
#include "vkRefUtil.hpp"
#include "vktConstexprVectorUtil.hpp"
#include "vktTestCase.hpp"
#include "vktTestCaseUtil.hpp"

#include <chrono>
#include <random>
#include <string>
#include <vector>

namespace vkt
{
namespace pipeline
{
namespace
{
using namespace vk;

using tcu::StringTemplate;
using tcu::TestCaseGroup;
using tcu::TestContext;
using tcu::TestStatus;

using ::std::array;
using ::std::string;
using ::std::vector;

/*--------------------------------------------------------------------*//*!
 * Elements common to all test types
 *//*--------------------------------------------------------------------*/
namespace test_common
{
static constexpr auto VK_NULL_HANDLE = DE_NULL;

using ::std::chrono::high_resolution_clock;
using ::std::chrono::microseconds;

using duration			 = high_resolution_clock::duration;
using UniquePipeline	 = Move<VkPipeline>;
using UniqueShaderModule = Move<VkShaderModule>;

/*--------------------------------------------------------------------*//*!
 * \brief Paired Vulkan API result with elapsed duration
 *//*--------------------------------------------------------------------*/
struct TimedResult
{
	VkResult result;
	duration elapsed;
};

/*--------------------------------------------------------------------*//*!
 * \brief Validation function type output from vkCreate*Pipelines()
 *
 * \param result - VkResult returned from API call
 * \param pipeliens - vector of pipelines created
 * \param elapsed - high_resolution_clock::duration of time elapsed in API
 * \param reason - output string to give the reason for failure
 *
 * \return QP_TEST_RESULT_PASS on success QP_TEST_RESULT_FAIL otherwise
 *//*--------------------------------------------------------------------*/
using Validator = qpTestResult (*)(VkResult, const vector<UniquePipeline>&, duration, string&);

static constexpr size_t VALIDATOR_ARRAY_MAX = 4;
using ValidatorArray						= ConstexprVector<Validator, VALIDATOR_ARRAY_MAX>;

/*--------------------------------------------------------------------*//*!
 * \brief Run a loop of validation tests and return the result
 *//*--------------------------------------------------------------------*/
template <typename pipelines_t, qpTestResult FAIL_RESULT = QP_TEST_RESULT_FAIL>
TestStatus validateResults(VkResult				 result,
						   const pipelines_t&	 pipelines,
						   duration				 elapsed,
						   const ValidatorArray& validators)
{
	using de::contains;
	static constexpr VkResult ALLOWED_RESULTS[] = {VK_SUCCESS, VK_ERROR_PIPELINE_COMPILE_REQUIRED_EXT};

	string reason;

	if (contains(DE_ARRAY_BEGIN(ALLOWED_RESULTS), DE_ARRAY_END(ALLOWED_RESULTS), result) == DE_FALSE)
	{
		static const StringTemplate ERROR_MSG = {"Pipeline creation returned an error result: ${0}"};
		TCU_THROW(InternalError, ERROR_MSG.format(result).c_str());
	}

	for (const auto& validator : validators)
	{
		const auto qpResult = validator(result, pipelines, elapsed, reason);
		if (qpResult != QP_TEST_RESULT_PASS)
		{
			return {qpResult, reason};
		}
	}

	return TestStatus::pass("Test passed.");
}

/*--------------------------------------------------------------------*//*!
 * \brief Generate an error if result does not match VK_RESULT
 *//*--------------------------------------------------------------------*/
template <VkResult VK_RESULT, qpTestResult FAIL_RESULT = QP_TEST_RESULT_FAIL>
qpTestResult checkResult(VkResult result, const vector<UniquePipeline>&, duration, string& reason)
{
	if (VK_RESULT != result)
	{
		static const StringTemplate ERROR_MSG = {"Got ${0}, Expected ${1}"};
		reason								  = ERROR_MSG.format(result, VK_RESULT);
		return FAIL_RESULT;
	}

	return QP_TEST_RESULT_PASS;
}

/*--------------------------------------------------------------------*//*!
 * \brief Generate an error if pipeline[INDEX] is not valid
 *//*--------------------------------------------------------------------*/
template <size_t INDEX, qpTestResult FAIL_RESULT = QP_TEST_RESULT_FAIL>
qpTestResult checkPipelineMustBeValid(VkResult, const vector<UniquePipeline>& pipelines, duration, string& reason)
{
	if (pipelines.size() <= INDEX)
	{
		static const StringTemplate ERROR_MSG = {"Index ${0} is not in created pipelines (pipelines.size(): ${1})"};
		TCU_THROW(TestError, ERROR_MSG.format(INDEX, pipelines.size()));
	}

	if (*pipelines[INDEX] == VK_NULL_HANDLE)
	{
		static const StringTemplate ERROR_MSG = {"pipelines[${0}] is not a valid VkPipeline object"};
		reason								  = ERROR_MSG.format(INDEX);
		return FAIL_RESULT;
	}

	return QP_TEST_RESULT_PASS;
}

/*--------------------------------------------------------------------*//*!
 * \brief Generate an error if pipeline[INDEX] is not VK_NULL_HANDLE
 *//*--------------------------------------------------------------------*/
template <size_t INDEX, qpTestResult FAIL_RESULT = QP_TEST_RESULT_FAIL>
qpTestResult checkPipelineMustBeNull(VkResult, const vector<UniquePipeline>& pipelines, duration, string& reason)
{
	if (pipelines.size() <= INDEX)
	{
		static const StringTemplate ERROR_MSG = {"Index ${0} is not in created pipelines (pipelines.size(): ${1})"};
		TCU_THROW(TestError, ERROR_MSG.format(INDEX, pipelines.size()));
	}

	if (*pipelines[INDEX] != VK_NULL_HANDLE)
	{
		static const StringTemplate ERROR_MSG = {"pipelines[${0}] is not VK_NULL_HANDLE"};
		reason								  = ERROR_MSG.format(INDEX);
		return FAIL_RESULT;
	}

	return QP_TEST_RESULT_PASS;
}

/*--------------------------------------------------------------------*//*!
 * \brief Generate an error if any pipeline is valid after an early-return failure
 *//*--------------------------------------------------------------------*/
template <size_t INDEX, qpTestResult FAIL_RESULT = QP_TEST_RESULT_FAIL>
qpTestResult checkPipelineNullAfterIndex(VkResult, const vector<UniquePipeline>& pipelines, duration, string& reason)
{
	if (pipelines.size() <= INDEX)
	{
		static const StringTemplate ERROR_MSG = {"Index ${0} is not in created pipelines (pipelines.size(): ${1})"};
		TCU_THROW(TestError, ERROR_MSG.format(INDEX, pipelines.size()));
	}

	if (pipelines.size() - 1 == INDEX)
	{
		static const StringTemplate ERROR_MSG = {"Index ${0} is the last pipeline, likely a malformed test case"};
		TCU_THROW(TestError, ERROR_MSG.format(INDEX));
	}

	// Only have to iterate through if the requested index is null
	if (*pipelines[INDEX] == VK_NULL_HANDLE)
	{
		for (size_t i = INDEX + 1; i < pipelines.size(); ++i)
		{
			if (*pipelines[i] != VK_NULL_HANDLE)
			{
				static const StringTemplate ERROR_MSG = {
					"pipelines[${0}] is not VK_NULL_HANDLE after a explicit early return index"};
				reason = ERROR_MSG.format(i);
				return FAIL_RESULT;
			}
		}
	}

	return QP_TEST_RESULT_PASS;
}

/*--------------------------------------------------------------------*//*!
 * Time limit constants
 *//*--------------------------------------------------------------------*/
enum ElapsedTime
{
	ELAPSED_TIME_INFINITE  = microseconds{-1}.count(),
	ELAPSED_TIME_IMMEDIATE = microseconds{500}.count(),
	ELAPSED_TIME_FAST	   = microseconds{1000}.count()
};

/*--------------------------------------------------------------------*//*!
 * \brief Generate an error if elapsed time exceeds MAX_TIME
 *//*--------------------------------------------------------------------*/
template <ElapsedTime MAX_TIME, qpTestResult FAIL_RESULT = QP_TEST_RESULT_FAIL>
qpTestResult checkElapsedTime(VkResult, const vector<UniquePipeline>&, duration elapsed, string& reason)
{
#if defined(DE_DEBUG)
	DE_UNREF(elapsed);
	DE_UNREF(reason);

	// In debug mode timing is not likely to be accurate
	return QP_TEST_RESULT_PASS;
#else

	using ::std::chrono::duration_cast;

	static constexpr microseconds ALLOWED_TIME = microseconds{MAX_TIME};

	if (elapsed > ALLOWED_TIME)
	{
		static const StringTemplate ERROR_MSG = {"pipeline creation took longer than ${0}us (actual time: ${1}us)"};
		reason = ERROR_MSG.format(ALLOWED_TIME.count(), duration_cast<microseconds>(elapsed).count());
		return FAIL_RESULT;
	}

	return QP_TEST_RESULT_PASS;
#endif
}

/*--------------------------------------------------------------------*//*!
 * \brief Test case parameters
 *//*--------------------------------------------------------------------*/
struct TestParams
{
	enum CacheType
	{
		NO_CACHE = 0,
		EXPLICIT_CACHE,
		DERIVATIVE_HANDLE,
		DERIVATIVE_INDEX
	};

	struct Iteration
	{
		static constexpr size_t MAX_VARIANTS = 4;
		using Variant						 = VkPipelineCreateFlags;
		using VariantArray					 = ConstexprVector<Variant, MAX_VARIANTS>;

		static constexpr Variant NORMAL		  = 0;
		static constexpr Variant NO_COMPILE	  = VK_PIPELINE_CREATE_FAIL_ON_PIPELINE_COMPILE_REQUIRED_BIT_EXT;
		static constexpr Variant EARLY_RETURN = NO_COMPILE | VK_PIPELINE_CREATE_EARLY_RETURN_ON_FAILURE_BIT_EXT;

		static constexpr VariantArray SINGLE_NORMAL						= VariantArray{NORMAL};
		static constexpr VariantArray SINGLE_NOCOMPILE					= VariantArray{NO_COMPILE};
		static constexpr VariantArray BATCH_NOCOMPILE_COMPILE_NOCOMPILE = VariantArray{NO_COMPILE, NORMAL, NO_COMPILE};
		static constexpr VariantArray BATCH_RETURN_COMPILE_NOCOMPILE = VariantArray{EARLY_RETURN, NORMAL, NO_COMPILE};

		inline constexpr Iteration() : variants{}, validators{} {};
		inline constexpr Iteration(const VariantArray& v, const ValidatorArray& f) : variants{v}, validators{f} {};

		VariantArray   variants;
		ValidatorArray validators;
	};

	static constexpr size_t MAX_ITERATIONS = 4;
	using IterationArray				   = ConstexprVector<Iteration, MAX_ITERATIONS>;

	const char*	   name;
	const char*	   description;
	CacheType	   cacheType;
	IterationArray iterations;
};

/*--------------------------------------------------------------------*//*!
 * \brief Verify extension and feature support
 *//*--------------------------------------------------------------------*/
void checkSupport(Context& context, const TestParams&)
{
	static constexpr char EXT_NAME[] = "VK_EXT_pipeline_creation_cache_control";
	if (!context.requireDeviceFunctionality(EXT_NAME))
	{
		TCU_THROW(NotSupportedError, "Extension 'VK_EXT_pipeline_creation_cache_control' is not supported");
	}

	const auto features = context.getPipelineCreationCacheControlFeaturesEXT();
	if (features.pipelineCreationCacheControl == DE_FALSE)
	{
		TCU_THROW(NotSupportedError, "Feature 'pipelineCreationCacheControl' is not enabled");
	}
}

/*--------------------------------------------------------------------*//*!
 * \brief Generate a random floating point number as a string
 *//*--------------------------------------------------------------------*/
float randomFloat()
{
#if !defined(DE_DEBUG)
	static de::Random state = {::std::random_device{}()};
#else
	static de::Random state = {0xDEADBEEF};
#endif

	return state.getFloat();
}

/*--------------------------------------------------------------------*//*!
 * \brief Get a string of VkResults from a vector
 *//*--------------------------------------------------------------------*/
string getResultsString(const vector<VkResult>& results)
{
	using ::std::ostringstream;

	ostringstream output;

	output << "results[" << results.size() << "]={ ";

	if (!results.empty())
	{
		output << results[0];
	}

	for (size_t i = 1; i < results.size(); ++i)
	{
		output << ", " << results[i];
	}

	output << " }";

	return output.str();
}

/*--------------------------------------------------------------------*//*!
 * \brief Cast a pointer to an the expected SPIRV type
 *//*--------------------------------------------------------------------*/
template <typename _t>
inline const deUint32* shader_cast(const _t* ptr)
{
	return reinterpret_cast<const deUint32*>(ptr);
}

/*--------------------------------------------------------------------*//*!
 * \brief Capture a container of Vulkan handles into Move<> types
 *//*--------------------------------------------------------------------*/
template <typename input_container_t,
		  typename handle_t	 = typename input_container_t::value_type,
		  typename move_t	 = Move<handle_t>,
		  typename deleter_t = Deleter<handle_t>,
		  typename output_t	 = vector<move_t>>
output_t wrapHandles(const DeviceInterface&		  vk,
					 VkDevice					  device,
					 const input_container_t&	  input,
					 const VkAllocationCallbacks* allocator = DE_NULL)
{
	using ::std::begin;
	using ::std::end;
	using ::std::transform;

	auto output = output_t{};
	output.resize(input.size());

	struct Predicate
	{
		deleter_t deleter;
		move_t	  operator()(handle_t v)
		{
			return (v != VK_NULL_HANDLE) ? move_t{check(v), deleter} : move_t{};
		}
	};

	const auto wrapHandle = Predicate{deleter_t{vk, device, allocator}};

	transform(begin(input), end(input), begin(output), wrapHandle);

	return output;
}

/*--------------------------------------------------------------------*//*!
 * \brief create vkPipelineCache for test params
 *//*--------------------------------------------------------------------*/
Move<VkPipelineCache> createPipelineCache(const DeviceInterface& vk, VkDevice device, const TestParams& params)
{
	if (params.cacheType != TestParams::EXPLICIT_CACHE)
	{
		return {};
	}

	static constexpr auto cacheInfo = VkPipelineCacheCreateInfo{
		VK_STRUCTURE_TYPE_PIPELINE_CACHE_CREATE_INFO, //sType
		DE_NULL,									  //pNext
		VkPipelineCacheCreateFlags{},				  //flags
		deUintptr{0},								  //initialDataSize
		DE_NULL										  //pInitialData
	};

	return createPipelineCache(vk, device, &cacheInfo);
}

/*--------------------------------------------------------------------*//*!
 * \brief create VkPipelineLayout with descriptor sets from test parameters
 *//*--------------------------------------------------------------------*/
Move<VkPipelineLayout> createPipelineLayout(const DeviceInterface&				 vk,
											VkDevice							 device,
											const vector<VkDescriptorSetLayout>& setLayouts,
											const TestParams&)
{
	const auto layoutCreateInfo = VkPipelineLayoutCreateInfo{
		VK_STRUCTURE_TYPE_PIPELINE_LAYOUT_CREATE_INFO, // sType
		DE_NULL,									   // pNext
		VkPipelineLayoutCreateFlags{},				   // flags
		static_cast<deUint32>(setLayouts.size()),	   // setLayoutCount
		setLayouts.data(),							   // pSetLayouts
		deUint32{0u},								   // pushConstantRangeCount
		DE_NULL,									   // pPushConstantRanges
	};

	return createPipelineLayout(vk, device, &layoutCreateInfo);
}

/*--------------------------------------------------------------------*//*!
 * \brief create basic VkPipelineLayout from test parameters
 *//*--------------------------------------------------------------------*/
Move<VkPipelineLayout> createPipelineLayout(const DeviceInterface& vk, VkDevice device, const TestParams&)
{
	static constexpr auto layoutCreateInfo = VkPipelineLayoutCreateInfo{
		VK_STRUCTURE_TYPE_PIPELINE_LAYOUT_CREATE_INFO, // sType
		DE_NULL,									   // pNext
		VkPipelineLayoutCreateFlags{},				   // flags
		deUint32{0u},								   // setLayoutCount
		DE_NULL,									   // pSetLayouts
		deUint32{0u},								   // pushConstantRangeCount
		DE_NULL,									   // pPushConstantRanges
	};

	return createPipelineLayout(vk, device, &layoutCreateInfo);
}

/*--------------------------------------------------------------------*//*!
 * \brief Create array of shader modules
 *//*--------------------------------------------------------------------*/
vector<UniqueShaderModule> createShaderModules(const DeviceInterface&	  vk,
											   VkDevice					  device,
											   const BinaryCollection&	  collection,
											   const vector<const char*>& names)
{
	auto output = vector<UniqueShaderModule>{};
	output.reserve(names.size());

	for (const auto& name : names)
	{
		const auto& binary	   = collection.get(name);
		const auto	createInfo = VkShaderModuleCreateInfo{
			 VK_STRUCTURE_TYPE_SHADER_MODULE_CREATE_INFO, // sType
			 DE_NULL,									  // pNext
			 VkShaderModuleCreateFlags{},				  // flags
			 binary.getSize(),							  // codeSize
			 shader_cast(binary.getBinary())			  // pCode
		 };

		output.push_back(createShaderModule(vk, device, &createInfo));
	}

	return output;
}

/*--------------------------------------------------------------------*//*!
 * \brief Create array of shader binding stages
 *//*--------------------------------------------------------------------*/
vector<VkPipelineShaderStageCreateInfo> createShaderStages(const vector<Move<VkShaderModule>>&	modules,
														   const vector<VkShaderStageFlagBits>& stages)
{
	DE_ASSERT(modules.size() == stages.size());

	auto output = vector<VkPipelineShaderStageCreateInfo>{};
	output.reserve(modules.size());

	int i = 0;

	for (const auto& module : modules)
	{
		const auto stageInfo = VkPipelineShaderStageCreateInfo{
			VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO, // sType
			DE_NULL,											 // pNext
			VkPipelineShaderStageCreateFlags{},					 // flags
			stages[i++],										 // stage
			*module,											 // module
			"main",												 // pName
			DE_NULL												 // pSpecializationInfo
		};

		output.push_back(stageInfo);
	}

	return output;
}

} // namespace test_common

/*--------------------------------------------------------------------*//*!
 * \brief Graphics pipeline specific testing
 *//*--------------------------------------------------------------------*/
namespace graphics_tests
{
using namespace test_common;

/*--------------------------------------------------------------------*//*!
 * \brief Common graphics pipeline create info initialization
 *//*--------------------------------------------------------------------*/
VkGraphicsPipelineCreateInfo getPipelineCreateInfoCommon()
{
	static constexpr auto VERTEX_BINDING = VkVertexInputBindingDescription{
		deUint32{0u},				// binding
		sizeof(float[4]),			// stride
		VK_VERTEX_INPUT_RATE_VERTEX // inputRate
	};

	static constexpr auto VERTEX_ATTRIBUTE = VkVertexInputAttributeDescription{
		deUint32{0u},				   // location
		deUint32{0u},				   // binding
		VK_FORMAT_R32G32B32A32_SFLOAT, // format
		deUint32{0u}				   // offset
	};

	static constexpr auto VERTEX_INPUT_STATE = VkPipelineVertexInputStateCreateInfo{
		VK_STRUCTURE_TYPE_PIPELINE_VERTEX_INPUT_STATE_CREATE_INFO, // sType
		DE_NULL,												   // pNext
		VkPipelineVertexInputStateCreateFlags{},				   // flags
		deUint32{1u},											   // vertexBindingDescriptionCount
		&VERTEX_BINDING,										   // pVertexBindingDescriptions
		deUint32{1u},											   // vertexAttributeDescriptionCount
		&VERTEX_ATTRIBUTE										   // pVertexAttributeDescriptions
	};

	static constexpr auto IA_STATE = VkPipelineInputAssemblyStateCreateInfo{
		VK_STRUCTURE_TYPE_PIPELINE_INPUT_ASSEMBLY_STATE_CREATE_INFO, // sType
		DE_NULL,													 // pNext
		VkPipelineInputAssemblyStateCreateFlags{},					 // flags
		VK_PRIMITIVE_TOPOLOGY_TRIANGLE_LIST,						 // topology
		VK_TRUE														 // primitiveRestartEnable
	};

	static constexpr auto TESSALATION_STATE = VkPipelineTessellationStateCreateInfo{
		VK_STRUCTURE_TYPE_PIPELINE_TESSELLATION_DOMAIN_ORIGIN_STATE_CREATE_INFO, // sType
		DE_NULL,																 // pNext
		VkPipelineTessellationStateCreateFlags{},								 // flags
		deUint32{0u}															 // patchControlPoints
	};

	static constexpr auto VIEWPORT = VkViewport{
		0.f, // x
		0.f, // y
		1.f, // width
		1.f, // height
		0.f, // minDepth
		1.f	 // maxDept
	};

	static constexpr auto SCISSOR_RECT = VkRect2D{
		{0, 0},	   // offset
		{256, 256} // extent
	};

	static constexpr auto VIEWPORT_STATE = VkPipelineViewportStateCreateInfo{
		VK_STRUCTURE_TYPE_PIPELINE_VIEWPORT_STATE_CREATE_INFO, // sType
		DE_NULL,											   // pNext
		VkPipelineViewportStateCreateFlags{},				   // flags
		deUint32{1u},										   // viewportCount
		&VIEWPORT,											   // pViewports
		deUint32{1u},										   // scissorCount
		&SCISSOR_RECT										   // pScissors
	};

	static constexpr auto RASTERIZATION_STATE = VkPipelineRasterizationStateCreateInfo{
		VK_STRUCTURE_TYPE_PIPELINE_RASTERIZATION_STATE_CREATE_INFO, // sType
		DE_NULL,													// pNext
		VkPipelineRasterizationStateCreateFlags{},					// flags
		VK_FALSE,													// depthClampEnable
		VK_TRUE,													// rasterizerDiscardEnable
		VK_POLYGON_MODE_FILL,										// polygonMode
		VK_CULL_MODE_NONE,											// cullMode
		VK_FRONT_FACE_CLOCKWISE,									// frontFace
		VK_FALSE,													// depthBiasEnable
		0.f,														// depthBiasConstantFactor
		0.f,														// depthBiasClamp
		0.f,														// depthBiasSlopeFactor
		1.f															// lineWidth
	};

	static constexpr auto SAMPLE_MASK = VkSampleMask{};

	static constexpr auto MULTISAMPLE_STATE = VkPipelineMultisampleStateCreateInfo{
		VK_STRUCTURE_TYPE_PIPELINE_MULTISAMPLE_STATE_CREATE_INFO, // sType
		DE_NULL,												  // pNext
		VkPipelineMultisampleStateCreateFlags{},				  // flags
		VK_SAMPLE_COUNT_1_BIT,									  // rasterizationSamples
		VK_FALSE,												  // sampleShadingEnable
		0.f,													  // minSampleShading
		&SAMPLE_MASK,											  // pSampleMask
		VK_FALSE,												  // alphaToCoverageEnable
		VK_FALSE												  // alphaToOneEnable
	};

	static constexpr auto STENCIL_OP_STATE = VkStencilOpState{
		VK_STENCIL_OP_ZERO,	  // failOp
		VK_STENCIL_OP_ZERO,	  // passOp
		VK_STENCIL_OP_ZERO,	  // depthFailOp
		VK_COMPARE_OP_ALWAYS, // compareOp
		deUint32{0u},		  // compareMask
		deUint32{0u},		  // writeMask
		deUint32{0u}		  // reference
	};

	static constexpr auto DEPTH_STENCIL_STATE = VkPipelineDepthStencilStateCreateInfo{
		VK_STRUCTURE_TYPE_PIPELINE_DEPTH_STENCIL_STATE_CREATE_INFO, // sType
		DE_NULL,													// pNext
		VkPipelineDepthStencilStateCreateFlags{},					// flags
		VK_FALSE,													// depthTestEnable
		VK_FALSE,													// depthWriteEnable
		VK_COMPARE_OP_ALWAYS,										// depthCompareOp
		VK_FALSE,													// depthBoundsTestEnable
		VK_FALSE,													// stencilTestEnable
		STENCIL_OP_STATE,											// front
		STENCIL_OP_STATE,											// back
		0.f,														// minDepthBounds
		1.f															// maxDepthBounds
	};

	static constexpr auto COLOR_FLAGS_ALL = VkColorComponentFlags{VK_COLOR_COMPONENT_R_BIT | VK_COLOR_COMPONENT_G_BIT |
																  VK_COLOR_COMPONENT_B_BIT | VK_COLOR_COMPONENT_A_BIT};

	static constexpr auto COLOR_BLEND_ATTACH_STATE = VkPipelineColorBlendAttachmentState{
		VK_FALSE,			  // blendEnable
		VK_BLEND_FACTOR_ONE,  // srcColorBlendFactor
		VK_BLEND_FACTOR_ZERO, // dstColorBlendFactor
		VK_BLEND_OP_ADD,	  // colorBlendOp
		VK_BLEND_FACTOR_ONE,  // srcAlphaBlendFactor
		VK_BLEND_FACTOR_ZERO, // dstAlphaBlendFactor
		VK_BLEND_OP_ADD,	  // alphaBlendOp
		COLOR_FLAGS_ALL		  // colorWriteMask
	};

	static constexpr auto COLOR_BLEND_STATE = VkPipelineColorBlendStateCreateInfo{
		VK_STRUCTURE_TYPE_PIPELINE_COLOR_BLEND_STATE_CREATE_INFO, // sType
		DE_NULL,												  // pNext
		VkPipelineColorBlendStateCreateFlags{},					  // flags
		VK_FALSE,												  // logicOpEnable
		VK_LOGIC_OP_SET,										  // logicOp
		deUint32{1u},											  // attachmentCount
		&COLOR_BLEND_ATTACH_STATE,								  // pAttachments
		{0.f, 0.f, 0.f, 0.f}									  // blendConstants[4]
	};

	static constexpr auto DYNAMIC_STATE = VkPipelineDynamicStateCreateInfo{
		VK_STRUCTURE_TYPE_PIPELINE_DYNAMIC_STATE_CREATE_INFO, // sType;
		DE_NULL,											  // pNext;
		VkPipelineDynamicStateCreateFlags{},				  // flags;
		deUint32{0u},										  // dynamicStateCount;
		DE_NULL												  // pDynamicStates;
	};

	return VkGraphicsPipelineCreateInfo{
		VK_STRUCTURE_TYPE_GRAPHICS_PIPELINE_CREATE_INFO, // sType
		DE_NULL,										 // pNext
		VkPipelineCreateFlags{},						 // flags
		deUint32{0u},									 // stageCount
		DE_NULL,										 // pStages
		&VERTEX_INPUT_STATE,							 // pVertexInputState
		&IA_STATE,										 // pInputAssemblyState
		&TESSALATION_STATE,								 // pTessellationState
		&VIEWPORT_STATE,								 // pViewportState
		&RASTERIZATION_STATE,							 // pRasterizationState
		&MULTISAMPLE_STATE,								 // pMultisampleState
		&DEPTH_STENCIL_STATE,							 // pDepthStencilState
		&COLOR_BLEND_STATE,								 // pColorBlendState
		&DYNAMIC_STATE,									 // pDynamicState
		VK_NULL_HANDLE,									 // layout
		VK_NULL_HANDLE,									 // renderPass
		deUint32{0u},									 // subpass
		VK_NULL_HANDLE,									 // basePipelineHandle
		deInt32{-1}										 // basePipelineIndex
	};
}

/*--------------------------------------------------------------------*//*!
 * \brief create VkGraphicsPipelineCreateInfo structs from test iteration
 *//*--------------------------------------------------------------------*/
vector<VkGraphicsPipelineCreateInfo> createPipelineCreateInfos(const TestParams::Iteration&		   iteration,
															   const VkGraphicsPipelineCreateInfo& base,
															   VkPipeline						   basePipeline,
															   const TestParams&				   testParameter)
{
	auto output = vector<VkGraphicsPipelineCreateInfo>{};
	output.reserve(iteration.variants.size());

	deInt32 count			  = 0;
	deInt32 basePipelineIndex = -1;

	for (VkPipelineCreateFlags flags : iteration.variants)
	{
		const auto curIndex	  = count++;
		auto	   createInfo = base;

		if (testParameter.cacheType == TestParams::DERIVATIVE_INDEX)
		{
			if (flags & VK_PIPELINE_CREATE_FAIL_ON_PIPELINE_COMPILE_REQUIRED_BIT_EXT)
			{
				if (basePipelineIndex != -1)
				{
					flags |= VK_PIPELINE_CREATE_DERIVATIVE_BIT;
				}
			}
			else
			{
				flags |= VK_PIPELINE_CREATE_ALLOW_DERIVATIVES_BIT;

				if (basePipelineIndex == -1)
				{
					basePipelineIndex = curIndex;
				}
			}
		}

		createInfo.flags			  = flags;
		createInfo.basePipelineHandle = basePipeline;
		createInfo.basePipelineIndex  = basePipelineIndex;

		output.push_back(createInfo);
	}

	return output;
}

/*--------------------------------------------------------------------*//*!
 * \brief create VkRenderPass object for Graphics test
 *//*--------------------------------------------------------------------*/
Move<VkRenderPass> createRenderPass(const DeviceInterface& vk, VkDevice device, const TestParams&)
{
	static constexpr auto COLOR_FORMAT = VK_FORMAT_R8G8B8A8_UNORM;

	static constexpr auto COLOR_ATTACHMENT_REF = VkAttachmentReference{
		deUint32{0u},							 // attachment
		VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL // layout
	};

	static constexpr auto SUBPASS = VkSubpassDescription{
		VkSubpassDescriptionFlags{},	 // flags
		VK_PIPELINE_BIND_POINT_GRAPHICS, // pipelineBindPoint
		deUint32{0u},					 // inputAttachmentCount
		DE_NULL,						 // pInputAttachments
		deUint32{1u},					 // colorAttachmentCount
		&COLOR_ATTACHMENT_REF,			 // pColorAttachments
		DE_NULL,						 // pResolveAttachments
		DE_NULL,						 // pDepthStencilAttachment
		deUint32{0u},					 // preserveAttachmentCount
		DE_NULL							 // pPreserveAttachments
	};

	static constexpr auto COLOR_ATTACHMENT = VkAttachmentDescription{
		VkAttachmentDescriptionFlags{},	  // flags
		COLOR_FORMAT,					  // format
		VK_SAMPLE_COUNT_1_BIT,			  // samples
		VK_ATTACHMENT_LOAD_OP_CLEAR,	  // loadOp
		VK_ATTACHMENT_STORE_OP_STORE,	  // storeOp
		VK_ATTACHMENT_LOAD_OP_DONT_CARE,  // stencilLoadOp
		VK_ATTACHMENT_STORE_OP_DONT_CARE, // stencilStoreOp
		VK_IMAGE_LAYOUT_UNDEFINED,		  // initialLayout
		VK_IMAGE_LAYOUT_PRESENT_SRC_KHR	  // finalLayout
	};

	static constexpr auto RENDER_PASS_CREATE_INFO = VkRenderPassCreateInfo{
		VK_STRUCTURE_TYPE_RENDER_PASS_CREATE_INFO, // sType
		DE_NULL,								   // pNext
		VkRenderPassCreateFlags{},				   // flags
		deUint32{1u},							   // attachmentCount
		&COLOR_ATTACHMENT,						   // pAttachments
		deUint32{1u},							   // subpassCount
		&SUBPASS,								   // pSubpasses
		deUint32{0u},							   // dependencyCount
		DE_NULL									   // pDependencies
	};

	return createRenderPass(vk, device, &RENDER_PASS_CREATE_INFO);
}

/*--------------------------------------------------------------------*//*!
 * \brief Initialize shader programs
 *//*--------------------------------------------------------------------*/
void initPrograms(SourceCollections& dst, const TestParams&)
{
	using ::glu::FragmentSource;
	using ::glu::VertexSource;

	// Vertex Shader
	static const StringTemplate VS_TEXT = {"#version 310 es\n"
										   "layout(location = 0) in vec4 position;\n"
										   "layout(location = 0) out vec3 vertColor;\n"
										   "void main (void)\n"
										   "{\n"
										   "  gl_Position = position;\n"
										   "  vertColor = vec3(${0}, ${1}, ${2});\n"
										   "}\n"};

	// Fragment Shader
	static const StringTemplate FS_TEXT = {"#version 310 es\n"
										   "precision highp float;\n"
										   "layout(location = 0) in vec3 vertColor;\n"
										   "layout(location = 0) out vec4 outColor;\n"
										   "void main (void)\n"
										   "{\n"
										   "  const vec3 fragColor = vec3(${0}, ${1}, ${2});\n"
										   "  outColor = vec4((fragColor + vertColor) * 0.5, 1.0);\n"
										   "}\n"};

	dst.glslSources.add("vertex") << VertexSource{VS_TEXT.format(randomFloat(), randomFloat(), randomFloat())};
	dst.glslSources.add("fragment") << FragmentSource{FS_TEXT.format(randomFloat(), randomFloat(), randomFloat())};
}

/*--------------------------------------------------------------------*//*!
 * \brief return both result and elapsed time from pipeline creation
 *//*--------------------------------------------------------------------*/
template <typename create_infos_t, typename pipelines_t>
TimedResult timePipelineCreation(const DeviceInterface&		  vk,
								 const VkDevice				  device,
								 const VkPipelineCache		  cache,
								 const create_infos_t&		  createInfos,
								 pipelines_t&				  pipelines,
								 const VkAllocationCallbacks* pAllocator = DE_NULL)
{
	DE_ASSERT(createInfos.size() <= pipelines.size());

	const auto timeStart = high_resolution_clock::now();
	const auto result	 = vk.createGraphicsPipelines(
		   device, cache, static_cast<deUint32>(createInfos.size()), createInfos.data(), pAllocator, pipelines.data());
	const auto elapsed = high_resolution_clock::now() - timeStart;
	return {result, elapsed};
}

/*--------------------------------------------------------------------*//*!
 * \brief Test instance function
 *//*--------------------------------------------------------------------*/
TestStatus testInstance(Context& context, const TestParams& testParameter)
{
	const auto& vk			  = context.getDeviceInterface();
	const auto	device		  = context.getDevice();
	const auto	pipelineCache = createPipelineCache(vk, device, testParameter);
	const auto	layout		  = createPipelineLayout(vk, device, testParameter);
	const auto	renderPass	  = createRenderPass(vk, device, testParameter);
	const auto	modules		  = createShaderModules(vk, device, context.getBinaryCollection(), {"vertex", "fragment"});
	const auto	shaderStages  = createShaderStages(modules, {VK_SHADER_STAGE_VERTEX_BIT, VK_SHADER_STAGE_FRAGMENT_BIT});

	// Placeholder for base pipeline if using cacheType == DERIVATIVE_HANDLE
	auto basePipeline = UniquePipeline{};

	auto baseCreateInfo		  = getPipelineCreateInfoCommon();
	baseCreateInfo.layout	  = layout.get();
	baseCreateInfo.renderPass = renderPass.get();
	baseCreateInfo.stageCount = static_cast<deUint32>(shaderStages.size());
	baseCreateInfo.pStages	  = shaderStages.data();

	auto results = vector<VkResult>{};
	results.reserve(testParameter.iterations.size());

	for (const auto& i : testParameter.iterations)
	{
		const auto createInfos = createPipelineCreateInfos(i, baseCreateInfo, basePipeline.get(), testParameter);
		auto	   created	   = vector<VkPipeline>{};
		created.resize(createInfos.size());

		const auto timedResult = timePipelineCreation(vk, device, pipelineCache.get(), createInfos, created);
		auto	   pipelines   = wrapHandles(vk, device, created);

		const auto status = validateResults(timedResult.result, pipelines, timedResult.elapsed, i.validators);
		if (status.getCode() != QP_TEST_RESULT_PASS)
		{
			return status;
		}

		if ((testParameter.cacheType == TestParams::DERIVATIVE_HANDLE) && (*basePipeline == VK_NULL_HANDLE))
		{
			for (auto& pipeline : pipelines)
			{
				if (*pipeline != VK_NULL_HANDLE)
				{
					basePipeline = pipeline;
					break;
				}
			}
		}

		results.push_back(timedResult.result);
	}

	static const StringTemplate PASS_MSG = {"Test Passed. ${0}"};
	return TestStatus::pass(PASS_MSG.format(getResultsString(results)));
}

} // namespace graphics_tests

/*--------------------------------------------------------------------*//*!
 * \brief Compute pipeline specific testing
 *//*--------------------------------------------------------------------*/
namespace compute_tests
{
using namespace test_common;

/*--------------------------------------------------------------------*//*!
 * \brief create VkComputePipelineCreateInfo structs from test iteration
 *//*--------------------------------------------------------------------*/
vector<VkComputePipelineCreateInfo> createPipelineCreateInfos(const TestParams::Iteration&		 iteration,
															  const VkComputePipelineCreateInfo& base,
															  VkPipeline						 basePipeline,
															  const TestParams&					 testParameter)
{
	auto output = vector<VkComputePipelineCreateInfo>{};
	output.reserve(iteration.variants.size());

	deInt32 count			  = 0;
	deInt32 basePipelineIndex = -1;

	for (VkPipelineCreateFlags flags : iteration.variants)
	{
		const auto curIndex	  = count++;
		auto	   createInfo = base;

		if (testParameter.cacheType == TestParams::DERIVATIVE_INDEX)
		{
			if (flags & VK_PIPELINE_CREATE_FAIL_ON_PIPELINE_COMPILE_REQUIRED_BIT_EXT)
			{
				if (basePipelineIndex != -1)
				{
					flags |= VK_PIPELINE_CREATE_DERIVATIVE_BIT;
				}
			}
			else
			{
				flags |= VK_PIPELINE_CREATE_ALLOW_DERIVATIVES_BIT;

				if (basePipelineIndex == -1)
				{
					basePipelineIndex = curIndex;
				}
			}
		}

		createInfo.flags			  = flags;
		createInfo.basePipelineHandle = basePipeline;
		createInfo.basePipelineIndex  = basePipelineIndex;

		output.push_back(createInfo);
	}

	return output;
}

/*--------------------------------------------------------------------*//*!
 * \brief create compute descriptor set layout
 *//*--------------------------------------------------------------------*/
Move<VkDescriptorSetLayout> createDescriptorSetLayout(const DeviceInterface& vk, VkDevice device, const TestParams&)
{
	static constexpr auto DESCRIPTOR_SET_LAYOUT_BINDING = VkDescriptorSetLayoutBinding{
		deUint32{0u},					   // binding
		VK_DESCRIPTOR_TYPE_STORAGE_BUFFER, // descriptorType
		deUint32{1u},					   // descriptorCount
		VK_SHADER_STAGE_COMPUTE_BIT,	   // stageFlags
		DE_NULL							   // pImmutableSamplers
	};

	static constexpr auto DESCRIPTOR_SET_LAYOUT_CREATE_INFO = VkDescriptorSetLayoutCreateInfo{
		VK_STRUCTURE_TYPE_DESCRIPTOR_SET_LAYOUT_CREATE_INFO, // sType
		DE_NULL,											 // pNext
		VkDescriptorSetLayoutCreateFlags{},					 // flags
		deUint32{1u},										 // bindingCount
		&DESCRIPTOR_SET_LAYOUT_BINDING						 // pBindings
	};

	return createDescriptorSetLayout(vk, device, &DESCRIPTOR_SET_LAYOUT_CREATE_INFO);
}

/*--------------------------------------------------------------------*//*!
 * \brief Initialize shader programs
 *//*--------------------------------------------------------------------*/
void initPrograms(SourceCollections& dst, const TestParams&)
{
	using ::glu::ComputeSource;

	static const StringTemplate CS_TEXT = {"#version 450\n"
										   "precision highp float;\n"
										   "layout (local_size_x = 64, local_size_y = 1, local_size_z = 1) in;\n"
										   "layout (std140, binding = 0) buffer buf { vec3 data[]; };\n"
										   "void main (void)\n"
										   "{\n"
										   "  data[gl_GlobalInvocationID.x] = vec3(${0}, ${1}, ${2});\n"
										   "}\n"};

	dst.glslSources.add("compute")
		<< ComputeSource{CS_TEXT.format(randomFloat(), randomFloat(), randomFloat())};
}

/*--------------------------------------------------------------------*//*!
 * \brief return both result and elapsed time from pipeline creation
 *//*--------------------------------------------------------------------*/
template <typename create_infos_t, typename pipelines_t>
TimedResult timePipelineCreation(const DeviceInterface&		  vk,
								 const VkDevice				  device,
								 const VkPipelineCache		  cache,
								 const create_infos_t&		  createInfos,
								 pipelines_t&				  pipelines,
								 const VkAllocationCallbacks* pAllocator = DE_NULL)
{
	DE_ASSERT(createInfos.size() <= pipelines.size());

	const auto timeStart = high_resolution_clock::now();
	const auto result	 = vk.createComputePipelines(
		   device, cache, static_cast<deUint32>(createInfos.size()), createInfos.data(), pAllocator, pipelines.data());
	const auto elapsed = high_resolution_clock::now() - timeStart;
	return {result, elapsed};
}

/*--------------------------------------------------------------------*//*!
 * \brief Test instance function
 *//*--------------------------------------------------------------------*/
TestStatus testInstance(Context& context, const TestParams& testParameter)
{
	const auto& vk					= context.getDeviceInterface();
	const auto	device				= context.getDevice();
	const auto	pipelineCache		= createPipelineCache(vk, device, testParameter);
	const auto	descriptorSetLayout = createDescriptorSetLayout(vk, device, testParameter);
	const auto	pipelineLayout		= createPipelineLayout(vk, device, {descriptorSetLayout.get()}, testParameter);
	const auto	modules				= createShaderModules(vk, device, context.getBinaryCollection(), {"compute"});
	const auto	shaderStages		= createShaderStages(modules, {VK_SHADER_STAGE_COMPUTE_BIT});

	// Placeholder for base pipeline if using cacheType == DERIVATIVE_HANDLE
	auto basePipeline = UniquePipeline{};

	const auto baseCreateInfo = VkComputePipelineCreateInfo{
		VK_STRUCTURE_TYPE_COMPUTE_PIPELINE_CREATE_INFO, // sType
		DE_NULL,										// pNext
		VkPipelineCreateFlags{},						// flags
		shaderStages[0],								// stage
		pipelineLayout.get(),							// layout
		VK_NULL_HANDLE,									// basePipelineHandle
		deInt32{-1}										// basePipelineIndex
	};

	auto results = vector<VkResult>{};
	results.reserve(testParameter.iterations.size());

	for (const auto& i : testParameter.iterations)
	{
		const auto createInfos = createPipelineCreateInfos(i, baseCreateInfo, basePipeline.get(), testParameter);
		auto	   created	   = vector<VkPipeline>{};
		created.resize(createInfos.size());

		const auto timedResult = timePipelineCreation(vk, device, pipelineCache.get(), createInfos, created);
		auto	   pipelines   = wrapHandles(vk, device, created);

		const auto status = validateResults(timedResult.result, pipelines, timedResult.elapsed, i.validators);
		if (status.getCode() != QP_TEST_RESULT_PASS)
		{
			return status;
		}

		if ((testParameter.cacheType == TestParams::DERIVATIVE_HANDLE) && (*basePipeline == VK_NULL_HANDLE))
		{
			for (auto& pipeline : pipelines)
			{
				if (*pipeline != VK_NULL_HANDLE)
				{
					basePipeline = pipeline;
					break;
				}
			}
		}

		results.push_back(timedResult.result);
	}

	static const StringTemplate PASS_MSG = {"Test Passed. ${0}"};
	return TestStatus::pass(PASS_MSG.format(getResultsString(results)));
}

} // namespace compute_tests

using namespace test_common;

// Disable formatting on this next block for readability
// clang-format off
/*--------------------------------------------------------------------*//*!
 * \brief Duplicate single pipeline recreation with explicit caching
 *//*--------------------------------------------------------------------*/
static constexpr TestParams DUPLICATE_SINGLE_RECREATE_EXPLICIT_CACHING =
{
	"duplicate_single_recreate_explicit_caching",
	"Duplicate single pipeline recreation with explicit caching",
	TestParams::EXPLICIT_CACHE,
	TestParams::IterationArray
	{
		TestParams::Iteration{
			// Iteration [0]: Force compilation of pipeline
			TestParams::Iteration::SINGLE_NORMAL,
			ValidatorArray{
				// Fail if result is not VK_SUCCESS
				checkResult<VK_SUCCESS>,
				// Fail if pipeline is not valid
				checkPipelineMustBeValid<0>
			}
		},
		TestParams::Iteration{
			// Iteration [1]: Request compilation of same pipeline without compile
			TestParams::Iteration::SINGLE_NOCOMPILE,
			ValidatorArray{
				// Warn if result is not VK_SUCCESS
				checkResult<VK_SUCCESS, QP_TEST_RESULT_COMPATIBILITY_WARNING>,
				// Warn if pipeline is not valid
				checkPipelineMustBeValid<0, QP_TEST_RESULT_COMPATIBILITY_WARNING>,
				// Warn if pipeline took too long
				checkElapsedTime<ELAPSED_TIME_FAST, QP_TEST_RESULT_QUALITY_WARNING>
			}
		}
	}
};

/*--------------------------------------------------------------------*//*!
 * \brief Duplicate single pipeline recreation with no explicit cache
 *//*--------------------------------------------------------------------*/
static constexpr TestParams DUPLICATE_SINGLE_RECREATE_NO_CACHING =
{
	"duplicate_single_recreate_no_caching",
	"Duplicate single pipeline recreation with no explicit cache",
	TestParams::NO_CACHE,
	TestParams::IterationArray{
		TestParams::Iteration{
			// Iteration [0]: Force compilation of pipeline
			TestParams::Iteration::SINGLE_NORMAL,
			ValidatorArray{
				// Fail if result is not VK_SUCCESS
				checkResult<VK_SUCCESS>,
				// Fail if pipeline is not valid
				checkPipelineMustBeValid<0>
			}
		},
		TestParams::Iteration{
			// Iteration [1]: Request compilation of same pipeline without compile
			TestParams::Iteration::SINGLE_NOCOMPILE,
			ValidatorArray{
				// Warn if pipeline took too long
				checkElapsedTime<ELAPSED_TIME_FAST, QP_TEST_RESULT_QUALITY_WARNING>
			}
		}
	}
};

/*--------------------------------------------------------------------*//*!
 * \brief Duplicate single pipeline recreation using derivative pipelines
 *//*--------------------------------------------------------------------*/
static constexpr TestParams DUPLICATE_SINGLE_RECREATE_DERIVATIVE =
{
	"duplicate_single_recreate_derivative",
	"Duplicate single pipeline recreation using derivative pipelines",
	TestParams::DERIVATIVE_HANDLE,
	TestParams::IterationArray{
		TestParams::Iteration{
			// Iteration [0]: Force compilation of pipeline
			TestParams::Iteration::SINGLE_NORMAL,
			ValidatorArray{
				// Fail if result is not VK_SUCCESS
				checkResult<VK_SUCCESS>,
				// Fail if pipeline is not valid
				checkPipelineMustBeValid<0>
				}
			},
		TestParams::Iteration{
			// Iteration [1]: Request compilation of same pipeline without compile
			TestParams::Iteration::SINGLE_NOCOMPILE,
			ValidatorArray{
				// Warn if pipeline took too long
				checkElapsedTime<ELAPSED_TIME_FAST, QP_TEST_RESULT_QUALITY_WARNING>
			}
		}
	}
};

/*--------------------------------------------------------------------*//*!
 * \brief Single creation of never before seen pipeline without compile
 *//*--------------------------------------------------------------------*/
static constexpr TestParams SINGLE_PIPELINE_NO_COMPILE =
{
	"single_pipeline_no_compile",
	"Single creation of never before seen pipeline without compile",
	TestParams::NO_CACHE,
	TestParams::IterationArray{
		TestParams::Iteration{
			TestParams::Iteration::SINGLE_NOCOMPILE,
			ValidatorArray{
				// Warn if pipeline took too long
				checkElapsedTime<ELAPSED_TIME_IMMEDIATE, QP_TEST_RESULT_QUALITY_WARNING>
			}
		}
	}
};

/*--------------------------------------------------------------------*//*!
 * \brief Batch creation of duplicate pipelines with explicit caching
 *//*--------------------------------------------------------------------*/
static constexpr TestParams DUPLICATE_BATCH_PIPELINES_EXPLICIT_CACHE =
{
	"duplicate_batch_pipelines_explicit_cache",
	"Batch creation of duplicate pipelines with explicit caching",
	TestParams::EXPLICIT_CACHE,
	TestParams::IterationArray{
		TestParams::Iteration{
			TestParams::Iteration::BATCH_NOCOMPILE_COMPILE_NOCOMPILE,
			ValidatorArray{
				// Fail if pipeline[1] is not valid
				checkPipelineMustBeValid<1>,
				// Warn if result is not VK_ERROR_PIPELINE_COMPILE_REQUIRED_EXT
				checkResult<VK_ERROR_PIPELINE_COMPILE_REQUIRED_EXT, QP_TEST_RESULT_COMPATIBILITY_WARNING>,
				// Warn if pipelines[0] is not VK_NULL_HANDLE
				checkPipelineMustBeNull<0, QP_TEST_RESULT_COMPATIBILITY_WARNING>,
				// Warn if pipelines[2] is not valid
				checkPipelineMustBeValid<2, QP_TEST_RESULT_COMPATIBILITY_WARNING>
			}
		}
	}
};

/*--------------------------------------------------------------------*//*!
 * \brief Batch creation of duplicate pipelines with no caching
 *//*--------------------------------------------------------------------*/
static constexpr TestParams DUPLICATE_BATCH_PIPELINES_NO_CACHE =
{
	"duplicate_batch_pipelines_no_cache",
	"Batch creation of duplicate pipelines with no caching",
	TestParams::EXPLICIT_CACHE,
	TestParams::IterationArray{
		TestParams::Iteration{
			TestParams::Iteration::BATCH_NOCOMPILE_COMPILE_NOCOMPILE,
			ValidatorArray{
				// Fail if pipeline[1] is not valid
				checkPipelineMustBeValid<1>,
				// Warn if result is not VK_ERROR_PIPELINE_COMPILE_REQUIRED_EXT
				checkResult<VK_ERROR_PIPELINE_COMPILE_REQUIRED_EXT, QP_TEST_RESULT_COMPATIBILITY_WARNING>,
				// Warn if pipelines[0] is not VK_NULL_HANDLE
				checkPipelineMustBeNull<0, QP_TEST_RESULT_COMPATIBILITY_WARNING>
			}
		}
	}
};

/*--------------------------------------------------------------------*//*!
 * \brief Batch creation of duplicate pipelines with derivative pipeline index
 *//*--------------------------------------------------------------------*/
static constexpr TestParams DUPLICATE_BATCH_PIPELINES_DERIVATIVE_INDEX =
{
	"duplicate_batch_pipelines_derivative_index",
	"Batch creation of duplicate pipelines with derivative pipeline index",
	TestParams::DERIVATIVE_INDEX,
	TestParams::IterationArray{
		TestParams::Iteration{
			TestParams::Iteration::BATCH_NOCOMPILE_COMPILE_NOCOMPILE,
			ValidatorArray{
				// Fail if pipeline[1] is not valid
				checkPipelineMustBeValid<1>,
				// Warn if result is not VK_ERROR_PIPELINE_COMPILE_REQUIRED_EXT
				checkResult<VK_ERROR_PIPELINE_COMPILE_REQUIRED_EXT, QP_TEST_RESULT_COMPATIBILITY_WARNING>,
				// Warn if pipelines[0] is not VK_NULL_HANDLE
				checkPipelineMustBeNull<0, QP_TEST_RESULT_COMPATIBILITY_WARNING>
			}
		}
	}
};

/*--------------------------------------------------------------------*//*!
 * \brief Batch creation of pipelines with early return
 *//*--------------------------------------------------------------------*/
static constexpr TestParams BATCH_PIPELINES_EARLY_RETURN =
{
	"batch_pipelines_early_return",
	"Batch creation of pipelines with early return",
	TestParams::NO_CACHE,
	TestParams::IterationArray{
		TestParams::Iteration{
			TestParams::Iteration::BATCH_RETURN_COMPILE_NOCOMPILE,
			ValidatorArray{
				// fail if a valid pipeline follows the early-return failure
				checkPipelineNullAfterIndex<0>,
				// Warn if return was not immediate
				checkElapsedTime<ELAPSED_TIME_IMMEDIATE, QP_TEST_RESULT_QUALITY_WARNING>,
				// Warn if pipelines[0] is not VK_NULL_HANDLE
				checkPipelineMustBeNull<0, QP_TEST_RESULT_COMPATIBILITY_WARNING>,
				// Warn if result is not VK_ERROR_PIPELINE_COMPILE_REQUIRED_EXT
				checkResult<VK_ERROR_PIPELINE_COMPILE_REQUIRED_EXT, QP_TEST_RESULT_COMPATIBILITY_WARNING>
			}
		}
	}
};

/*--------------------------------------------------------------------*//*!
 * \brief Full array of test cases
 *//*--------------------------------------------------------------------*/
static constexpr TestParams TEST_CASES[] =
{
	SINGLE_PIPELINE_NO_COMPILE,
	BATCH_PIPELINES_EARLY_RETURN,
	DUPLICATE_SINGLE_RECREATE_EXPLICIT_CACHING,
	DUPLICATE_SINGLE_RECREATE_NO_CACHING,
	DUPLICATE_SINGLE_RECREATE_DERIVATIVE,
	DUPLICATE_BATCH_PIPELINES_EXPLICIT_CACHE,
	DUPLICATE_BATCH_PIPELINES_NO_CACHE,
	DUPLICATE_BATCH_PIPELINES_DERIVATIVE_INDEX
};
// clang-format on

/*--------------------------------------------------------------------*//*!
 * \brief Variadic version of de::newMovePtr
 *//*--------------------------------------------------------------------*/
template <typename T, typename... args_t>
inline de::MovePtr<T> newMovePtr(args_t&&... args)
{
	return de::MovePtr<T>(new T(::std::forward<args_t>(args)...));
}

/*--------------------------------------------------------------------*//*!
 * \brief Make test group consisting of graphics pipeline tests
 *//*--------------------------------------------------------------------*/
void addGraphicsPipelineTests(TestCaseGroup& group)
{
	using namespace graphics_tests;

	auto tests = newMovePtr<TestCaseGroup>(
		group.getTestContext(), "graphics_pipelines", "Test pipeline creation cache control with graphics pipelines");

	for (const auto& params : TEST_CASES)
	{
		addFunctionCaseWithPrograms<const TestParams&>(
			tests.get(), params.name, params.description, checkSupport, initPrograms, testInstance, params);
	}

	group.addChild(tests.release());
}

/*--------------------------------------------------------------------*//*!
 * \brief Make test group consisting of compute pipeline tests
 *//*--------------------------------------------------------------------*/
void addComputePipelineTests(TestCaseGroup& group)
{
	using namespace compute_tests;

	auto tests = newMovePtr<TestCaseGroup>(
		group.getTestContext(), "compute_pipelines", "Test pipeline creation cache control with compute pipelines");

	for (const auto& params : TEST_CASES)
	{
		addFunctionCaseWithPrograms<const TestParams&>(
			tests.get(), params.name, params.description, checkSupport, initPrograms, testInstance, params);
	}

	group.addChild(tests.release());
}

} // namespace

/*--------------------------------------------------------------------*//*!
 * \brief Make pipeline creation cache control test group
 *//*--------------------------------------------------------------------*/
TestCaseGroup* createCacheControlTests(TestContext& testCtx)
{
	auto tests = newMovePtr<TestCaseGroup>(testCtx, "creation_cache_control", "pipeline creation cache control tests");

	addGraphicsPipelineTests(*tests);
	addComputePipelineTests(*tests);

	return tests.release();
}

} // namespace pipeline

} // namespace vkt
