From b51468b519f447c8e0afd492ce09d7c9485e222b Mon Sep 17 00:00:00 2001 From: Chad Versace Date: Fri, 16 Oct 2015 20:31:39 -0700 Subject: [PATCH] anv/pipeline: Validate VkGraphicsPipelineCreateInfo The Vulkan spec (20 Oct 2015, git-aa308cb) states that some fields of VkGraphicsPipelineCreateInfo are required under certain conditions. Add a new function, anv_pipeline_validate_create_info() that asserts the requirements hold. The assertions helped me discover bugs in Crucible and anv_meta.c. --- src/vulkan/anv_pipeline.c | 49 +++++++++++++++++++++++++++++++++++++++ 1 file changed, 49 insertions(+) diff --git a/src/vulkan/anv_pipeline.c b/src/vulkan/anv_pipeline.c index 7fd8c100568..28cccaa3d25 100644 --- a/src/vulkan/anv_pipeline.c +++ b/src/vulkan/anv_pipeline.c @@ -260,6 +260,51 @@ anv_pipeline_init_dynamic_state(struct anv_pipeline *pipeline, pipeline->dynamic_state_mask = states; } +static void +anv_pipeline_validate_create_info(const VkGraphicsPipelineCreateInfo *info) +{ + struct anv_render_pass *renderpass = NULL; + struct anv_subpass *subpass = NULL; + + /* Assert that all required members of VkGraphicsPipelineCreateInfo are + * present, as explained by the Vulkan (20 Oct 2015, git-aa308cb), Section + * 4.2 Graphics Pipeline. + */ + assert(info->sType == VK_STRUCTURE_TYPE_GRAPHICS_PIPELINE_CREATE_INFO); + + renderpass = anv_render_pass_from_handle(info->renderPass); + assert(renderpass); + + if (renderpass != &anv_meta_dummy_renderpass) { + assert(info->subpass < renderpass->subpass_count); + subpass = &renderpass->subpasses[info->subpass]; + } + + assert(info->stageCount >= 1); + assert(info->pVertexInputState); + assert(info->pInputAssemblyState); + assert(info->pViewportState); + assert(info->pRasterState); + assert(info->pMultisampleState); + + if (subpass && subpass->depth_stencil_attachment != VK_ATTACHMENT_UNUSED) + assert(info->pDepthStencilState); + + if (subpass && subpass->color_count > 0) + assert(info->pColorBlendState); + + for (uint32_t i = 0; i < info->stageCount; ++i) { + switch (info->pStages[i].stage) { + case VK_SHADER_STAGE_TESS_CONTROL: + case VK_SHADER_STAGE_TESS_EVALUATION: + assert(info->pTessellationState); + break; + default: + break; + } + } +} + VkResult anv_pipeline_init(struct anv_pipeline *pipeline, struct anv_device *device, const VkGraphicsPipelineCreateInfo *pCreateInfo, @@ -267,6 +312,10 @@ anv_pipeline_init(struct anv_pipeline *pipeline, struct anv_device *device, { VkResult result; + anv_validate { + anv_pipeline_validate_create_info(pCreateInfo); + } + pipeline->device = device; pipeline->layout = anv_pipeline_layout_from_handle(pCreateInfo->layout); memset(pipeline->shaders, 0, sizeof(pipeline->shaders)); -- 2.30.2