Commit 763957e6 by Nicolas Capens Committed by Nicolas Capens

Ignore rasterization state pointers when rasterization is disabled

The Vulkan specification for VkGraphicsPipelineCreateInfo states: * pViewportState is a pointer to a VkPipelineViewportStateCreateInfo structure, and is ignored if the pipeline has rasterization disabled. * pMultisampleState is a pointer to a VkPipelineMultisampleStateCreateInfo structure, and is ignored if the pipeline has rasterization disabled. * pDepthStencilState is a pointer to a VkPipelineDepthStencilStateCreateInfo structure, and is ignored if the pipeline has rasterization disabled or if the subpass of the render pass the pipeline is created against does not use a depth/stencil attachment. * pColorBlendState is a pointer to a VkPipelineColorBlendStateCreateInfo structure, and is ignored if the pipeline has rasterization disabled or if the subpass of the render pass the pipeline is created against does not use any color attachments. Also remove the UNSUPPORTED() for pTessellationState since it is valid for the application to provide a non-null pointer even though tessellation is not supported. Bug: b/155359026 Change-Id: Ic1cd9224b159cca66f0dbf1b1a563efc56386866 Reviewed-on: https://swiftshader-review.googlesource.com/c/SwiftShader/+/45728 Presubmit-Ready: Nicolas Capens <nicolascapens@google.com> Tested-by: 's avatarNicolas Capens <nicolascapens@google.com> Kokoro-Result: kokoro <noreply+kokoro@google.com> Reviewed-by: 's avatarAlexis Hétu <sugoi@google.com>
parent 15d3dda5
......@@ -166,11 +166,6 @@ GraphicsPipeline::GraphicsPipeline(const VkGraphicsPipelineCreateInfo *pCreateIn
UNSUPPORTED("pCreateInfo->flags %d", int(pCreateInfo->flags));
}
if(pCreateInfo->pTessellationState != nullptr)
{
UNSUPPORTED("pCreateInfo->pTessellationState");
}
if(pCreateInfo->pDynamicState)
{
if(pCreateInfo->pDynamicState->flags != 0)
......@@ -246,32 +241,6 @@ GraphicsPipeline::GraphicsPipeline(const VkGraphicsPipelineCreateInfo *pCreateIn
primitiveRestartEnable = (inputAssemblyState->primitiveRestartEnable != VK_FALSE);
context.topology = inputAssemblyState->topology;
const VkPipelineViewportStateCreateInfo *viewportState = pCreateInfo->pViewportState;
if(viewportState)
{
if(viewportState->flags != 0)
{
// Vulkan 1.2: "flags is reserved for future use." "flags must be 0"
UNSUPPORTED("pCreateInfo->pViewportState->flags %d", int(pCreateInfo->pViewportState->flags));
}
if((viewportState->viewportCount != 1) ||
(viewportState->scissorCount != 1))
{
UNSUPPORTED("VkPhysicalDeviceFeatures::multiViewport");
}
if(!hasDynamicState(VK_DYNAMIC_STATE_SCISSOR))
{
scissor = viewportState->pScissors[0];
}
if(!hasDynamicState(VK_DYNAMIC_STATE_VIEWPORT))
{
viewport = viewportState->pViewports[0];
}
}
const VkPipelineRasterizationStateCreateInfo *rasterizationState = pCreateInfo->pRasterizationState;
if(rasterizationState->flags != 0)
......@@ -326,9 +295,36 @@ GraphicsPipeline::GraphicsPipeline(const VkGraphicsPipelineCreateInfo *pCreateIn
// TODO(b/147812380): Eliminate the dependency between multisampling and batch size.
context.sampleCount = 1;
const VkPipelineMultisampleStateCreateInfo *multisampleState = pCreateInfo->pMultisampleState;
if(multisampleState)
// Only access rasterization state if rasterization is not disabled.
if(rasterizationState->rasterizerDiscardEnable == VK_FALSE)
{
const VkPipelineViewportStateCreateInfo *viewportState = pCreateInfo->pViewportState;
const VkPipelineMultisampleStateCreateInfo *multisampleState = pCreateInfo->pMultisampleState;
const VkPipelineDepthStencilStateCreateInfo *depthStencilState = pCreateInfo->pDepthStencilState;
const VkPipelineColorBlendStateCreateInfo *colorBlendState = pCreateInfo->pColorBlendState;
if(viewportState->flags != 0)
{
// Vulkan 1.2: "flags is reserved for future use." "flags must be 0"
UNSUPPORTED("pCreateInfo->pViewportState->flags %d", int(pCreateInfo->pViewportState->flags));
}
if((viewportState->viewportCount != 1) ||
(viewportState->scissorCount != 1))
{
UNSUPPORTED("VkPhysicalDeviceFeatures::multiViewport");
}
if(!hasDynamicState(VK_DYNAMIC_STATE_SCISSOR))
{
scissor = viewportState->pScissors[0];
}
if(!hasDynamicState(VK_DYNAMIC_STATE_VIEWPORT))
{
viewport = viewportState->pViewports[0];
}
if(multisampleState->flags != 0)
{
// Vulkan 1.2: "flags is reserved for future use." "flags must be 0"
......@@ -367,73 +363,81 @@ GraphicsPipeline::GraphicsPipeline(const VkGraphicsPipelineCreateInfo *pCreateIn
}
context.alphaToCoverage = (multisampleState->alphaToCoverageEnable != VK_FALSE);
}
else
{
context.sampleCount = 1;
}
context.multiSampleMask = context.sampleMask & ((unsigned)0xFFFFFFFF >> (32 - context.sampleCount));
const VkPipelineDepthStencilStateCreateInfo *depthStencilState = pCreateInfo->pDepthStencilState;
if(depthStencilState)
{
if(depthStencilState->flags != 0)
{
// Vulkan 1.2: "flags is reserved for future use." "flags must be 0"
UNSUPPORTED("pCreateInfo->pDepthStencilState->flags %d", int(pCreateInfo->pDepthStencilState->flags));
}
const vk::RenderPass *renderPass = vk::Cast(pCreateInfo->renderPass);
const VkSubpassDescription &subpass = renderPass->getSubpass(pCreateInfo->subpass);
if(depthStencilState->depthBoundsTestEnable != VK_FALSE)
// Ignore pDepthStencilState when "the subpass of the render pass the pipeline is created against does not use a depth/stencil attachment"
if(subpass.pDepthStencilAttachment && subpass.pDepthStencilAttachment->attachment != VK_ATTACHMENT_UNUSED)
{
UNSUPPORTED("VkPhysicalDeviceFeatures::depthBounds");
}
if(depthStencilState->flags != 0)
{
// Vulkan 1.2: "flags is reserved for future use." "flags must be 0"
UNSUPPORTED("pCreateInfo->pDepthStencilState->flags %d", int(pCreateInfo->pDepthStencilState->flags));
}
context.depthBoundsTestEnable = (depthStencilState->depthBoundsTestEnable != VK_FALSE);
context.depthBufferEnable = (depthStencilState->depthTestEnable != VK_FALSE);
context.depthWriteEnable = (depthStencilState->depthWriteEnable != VK_FALSE);
context.depthCompareMode = depthStencilState->depthCompareOp;
if(depthStencilState->depthBoundsTestEnable != VK_FALSE)
{
UNSUPPORTED("VkPhysicalDeviceFeatures::depthBounds");
}
context.stencilEnable = (depthStencilState->stencilTestEnable != VK_FALSE);
if(context.stencilEnable)
{
context.frontStencil = depthStencilState->front;
context.backStencil = depthStencilState->back;
}
}
context.depthBoundsTestEnable = (depthStencilState->depthBoundsTestEnable != VK_FALSE);
context.depthBufferEnable = (depthStencilState->depthTestEnable != VK_FALSE);
context.depthWriteEnable = (depthStencilState->depthWriteEnable != VK_FALSE);
context.depthCompareMode = depthStencilState->depthCompareOp;
const VkPipelineColorBlendStateCreateInfo *colorBlendState = pCreateInfo->pColorBlendState;
if(colorBlendState)
{
if(pCreateInfo->pColorBlendState->flags != 0)
{
// Vulkan 1.2: "flags is reserved for future use." "flags must be 0"
UNSUPPORTED("pCreateInfo->pColorBlendState->flags %d", int(pCreateInfo->pColorBlendState->flags));
context.stencilEnable = (depthStencilState->stencilTestEnable != VK_FALSE);
if(context.stencilEnable)
{
context.frontStencil = depthStencilState->front;
context.backStencil = depthStencilState->back;
}
}
if(colorBlendState->logicOpEnable != VK_FALSE)
bool colorAttachmentUsed = false;
for(uint32_t i = 0; i < subpass.colorAttachmentCount; i++)
{
UNSUPPORTED("VkPhysicalDeviceFeatures::logicOp");
if(subpass.pColorAttachments[i].attachment != VK_ATTACHMENT_UNUSED)
{
colorAttachmentUsed = true;
break;
}
}
if(!hasDynamicState(VK_DYNAMIC_STATE_BLEND_CONSTANTS))
// Ignore pColorBlendState when "the subpass of the render pass the pipeline is created against does not use any color attachments"
if(colorAttachmentUsed)
{
blendConstants.x = colorBlendState->blendConstants[0];
blendConstants.y = colorBlendState->blendConstants[1];
blendConstants.z = colorBlendState->blendConstants[2];
blendConstants.w = colorBlendState->blendConstants[3];
}
if(colorBlendState->flags != 0)
{
// Vulkan 1.2: "flags is reserved for future use." "flags must be 0"
UNSUPPORTED("pCreateInfo->pColorBlendState->flags %d", int(pCreateInfo->pColorBlendState->flags));
}
for(auto i = 0u; i < colorBlendState->attachmentCount; i++)
{
const VkPipelineColorBlendAttachmentState &attachment = colorBlendState->pAttachments[i];
context.colorWriteMask[i] = attachment.colorWriteMask;
if(colorBlendState->logicOpEnable != VK_FALSE)
{
UNSUPPORTED("VkPhysicalDeviceFeatures::logicOp");
}
if(!hasDynamicState(VK_DYNAMIC_STATE_BLEND_CONSTANTS))
{
blendConstants.x = colorBlendState->blendConstants[0];
blendConstants.y = colorBlendState->blendConstants[1];
blendConstants.z = colorBlendState->blendConstants[2];
blendConstants.w = colorBlendState->blendConstants[3];
}
for(auto i = 0u; i < colorBlendState->attachmentCount; i++)
{
const VkPipelineColorBlendAttachmentState &attachment = colorBlendState->pAttachments[i];
context.colorWriteMask[i] = attachment.colorWriteMask;
context.setBlendState(i, { (attachment.blendEnable != VK_FALSE),
attachment.srcColorBlendFactor, attachment.dstColorBlendFactor, attachment.colorBlendOp,
attachment.srcAlphaBlendFactor, attachment.dstAlphaBlendFactor, attachment.alphaBlendOp });
context.setBlendState(i, { (attachment.blendEnable != VK_FALSE),
attachment.srcColorBlendFactor, attachment.dstColorBlendFactor, attachment.colorBlendOp,
attachment.srcAlphaBlendFactor, attachment.dstAlphaBlendFactor, attachment.alphaBlendOp });
}
}
}
context.multiSampleMask = context.sampleMask & ((unsigned)0xFFFFFFFF >> (32 - context.sampleCount));
}
void GraphicsPipeline::destroyPipeline(const VkAllocationCallbacks *pAllocator)
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment