aboutsummaryrefslogtreecommitdiff
path: root/layers/core_validation.cpp
diff options
context:
space:
mode:
authorTobin Ehlis <tobine@google.com>2017-01-19 12:05:27 -0700
committerTobin Ehlis <tobine@google.com>2017-01-20 13:13:16 -0700
commitb845f5a3c174b11c5807146d45c3d79183260a45 (patch)
treed93327c4b6f8f6355c1f904361afe6d8ac694b88 /layers/core_validation.cpp
parent71d48ce7a4529786c3109c6939b2598cf668d50f (diff)
downloadusermoji-b845f5a3c174b11c5807146d45c3d79183260a45.tar.xz
layers:Synch validation updates
I started scrubbing the valid usage blocks for synch validation and made a few different updates here. Added a missing unique error id and a comment for another. Got a bit sidetracked and decided to implement a check for all stageMasks to make sure that they don't set geometry shader or tessellation shader bits if those featurse aren't enabled. Added a test to verify new check and made a bunch of updates to the database file.
Diffstat (limited to 'layers/core_validation.cpp')
-rw-r--r--layers/core_validation.cpp47
1 files changed, 45 insertions, 2 deletions
diff --git a/layers/core_validation.cpp b/layers/core_validation.cpp
index 68cb1b64..fd21f013 100644
--- a/layers/core_validation.cpp
+++ b/layers/core_validation.cpp
@@ -4334,6 +4334,28 @@ VKAPI_ATTR void VKAPI_CALL DestroyDevice(VkDevice device, const VkAllocationCall
static const VkExtensionProperties instance_extensions[] = {{VK_EXT_DEBUG_REPORT_EXTENSION_NAME, VK_EXT_DEBUG_REPORT_SPEC_VERSION}};
+// For given stage mask, if Geometry shader stage is on w/o GS being enabled, report geo_error_id
+// and if Tessellation Control or Evaluation shader stages are on w/o TS being enabled, report tess_error_id
+static bool ValidateStageMaskGsTsEnables(layer_data *dev_data, VkPipelineStageFlags stageMask, const char *caller,
+ UNIQUE_VALIDATION_ERROR_CODE geo_error_id, UNIQUE_VALIDATION_ERROR_CODE tess_error_id) {
+ bool skip = false;
+ if (!dev_data->enabled_features.geometryShader && (stageMask & VK_PIPELINE_STAGE_GEOMETRY_SHADER_BIT)) {
+ skip |= log_msg(dev_data->report_data, VK_DEBUG_REPORT_ERROR_BIT_EXT, VK_DEBUG_REPORT_OBJECT_TYPE_UNKNOWN_EXT, 0, __LINE__,
+ geo_error_id, "DL", "%s call includes a stageMask with VK_PIPELINE_STAGE_GEOMETRY_SHADER_BIT bit set when "
+ "device does not have geometryShader feature enabled. %s",
+ caller, validation_error_map[geo_error_id]);
+ }
+ if (!dev_data->enabled_features.tessellationShader &&
+ (stageMask & (VK_PIPELINE_STAGE_TESSELLATION_CONTROL_SHADER_BIT | VK_PIPELINE_STAGE_TESSELLATION_EVALUATION_SHADER_BIT))) {
+ skip |= log_msg(dev_data->report_data, VK_DEBUG_REPORT_ERROR_BIT_EXT, VK_DEBUG_REPORT_OBJECT_TYPE_UNKNOWN_EXT, 0, __LINE__,
+ tess_error_id, "DL", "%s call includes a stageMask with VK_PIPELINE_STAGE_TESSELLATION_CONTROL_SHADER_BIT "
+ "and/or VK_PIPELINE_STAGE_TESSELLATION_EVALUATION_SHADER_BIT bit(s) set when device "
+ "does not have tessellationShader feature enabled. %s",
+ caller, validation_error_map[tess_error_id]);
+ }
+ return skip;
+}
+
// This validates that the initial layout specified in the command buffer for
// the IMAGE is the same
// as the global IMAGE layout
@@ -4803,6 +4825,8 @@ QueueSubmit(VkQueue queue, uint32_t submitCount, const VkSubmitInfo *pSubmits, V
vector<SEMAPHORE_WAIT> semaphore_waits;
vector<VkSemaphore> semaphore_signals;
for (uint32_t i = 0; i < submit->waitSemaphoreCount; ++i) {
+ skip_call |= ValidateStageMaskGsTsEnables(dev_data, submit->pWaitDstStageMask[i], "vkQueueSubmit()",
+ VALIDATION_ERROR_00142, VALIDATION_ERROR_00143);
VkSemaphore semaphore = submit->pWaitSemaphores[i];
auto pSemaphore = getSemaphoreNode(dev_data, semaphore);
if (pSemaphore) {
@@ -5299,8 +5323,8 @@ static bool PreCallValidateDestroyFence(layer_data *dev_data, VkFence fence, FEN
if (*fence_node) {
if ((*fence_node)->state == FENCE_INFLIGHT) {
skip |= log_msg(dev_data->report_data, VK_DEBUG_REPORT_ERROR_BIT_EXT, VK_DEBUG_REPORT_OBJECT_TYPE_FENCE_EXT,
- (uint64_t)(fence), __LINE__, DRAWSTATE_INVALID_FENCE, "DS", "Fence 0x%" PRIx64 " is in use.",
- (uint64_t)(fence));
+ (uint64_t)(fence), __LINE__, VALIDATION_ERROR_00173, "DS", "Fence 0x%" PRIx64 " is in use. %s",
+ (uint64_t)(fence), validation_error_map[VALIDATION_ERROR_00173]);
}
}
return skip;
@@ -9084,6 +9108,8 @@ CmdSetEvent(VkCommandBuffer commandBuffer, VkEvent event, VkPipelineStageFlags s
skip_call |= ValidateCmd(dev_data, pCB, CMD_SETEVENT, "vkCmdSetEvent()");
UpdateCmdBufferLastCmd(dev_data, pCB, CMD_SETEVENT);
skip_call |= insideRenderPass(dev_data, pCB, "vkCmdSetEvent()", VALIDATION_ERROR_00238);
+ skip_call |=
+ ValidateStageMaskGsTsEnables(dev_data, stageMask, "vkCmdSetEvent()", VALIDATION_ERROR_00230, VALIDATION_ERROR_00231);
auto event_state = getEventNode(dev_data, event);
if (event_state) {
addCommandBufferBinding(&event_state->cb_bindings,
@@ -9113,6 +9139,8 @@ CmdResetEvent(VkCommandBuffer commandBuffer, VkEvent event, VkPipelineStageFlags
skip_call |= ValidateCmd(dev_data, pCB, CMD_RESETEVENT, "vkCmdResetEvent()");
UpdateCmdBufferLastCmd(dev_data, pCB, CMD_RESETEVENT);
skip_call |= insideRenderPass(dev_data, pCB, "vkCmdResetEvent()", VALIDATION_ERROR_00249);
+ skip_call |=
+ ValidateStageMaskGsTsEnables(dev_data, stageMask, "vkCmdResetEvent()", VALIDATION_ERROR_00240, VALIDATION_ERROR_00241);
auto event_state = getEventNode(dev_data, event);
if (event_state) {
addCommandBufferBinding(&event_state->cb_bindings,
@@ -9123,6 +9151,7 @@ CmdResetEvent(VkCommandBuffer commandBuffer, VkEvent event, VkPipelineStageFlags
if (!pCB->waitedEvents.count(event)) {
pCB->writeEventsBeforeWait.push_back(event);
}
+ // TODO : Add check for VALIDATION_ERROR_00226
std::function<bool(VkQueue)> eventUpdate =
std::bind(setEventStageMask, std::placeholders::_1, commandBuffer, event, VkPipelineStageFlags(0));
pCB->eventUpdates.push_back(eventUpdate);
@@ -9602,6 +9631,10 @@ VKAPI_ATTR void VKAPI_CALL CmdWaitEvents(VkCommandBuffer commandBuffer, uint32_t
if (cb_state) {
skip |= ValidateStageMasksAgainstQueueCapabilities(dev_data, cb_state, sourceStageMask, dstStageMask, "vkCmdWaitEvents",
VALIDATION_ERROR_02510);
+ skip |= ValidateStageMaskGsTsEnables(dev_data, sourceStageMask, "vkCmdWaitEvents()", VALIDATION_ERROR_02067,
+ VALIDATION_ERROR_02069);
+ skip |= ValidateStageMaskGsTsEnables(dev_data, dstStageMask, "vkCmdWaitEvents()", VALIDATION_ERROR_02068,
+ VALIDATION_ERROR_02070);
auto first_event_index = cb_state->events.size();
for (uint32_t i = 0; i < eventCount; ++i) {
auto event_state = getEventNode(dev_data, pEvents[i]);
@@ -9647,6 +9680,10 @@ VKAPI_ATTR void VKAPI_CALL CmdPipelineBarrier(VkCommandBuffer commandBuffer, VkP
skip |= ValidateStageMasksAgainstQueueCapabilities(dev_data, cb_state, srcStageMask, dstStageMask, "vkCmdPipelineBarrier",
VALIDATION_ERROR_02513);
skip |= ValidateCmd(dev_data, cb_state, CMD_PIPELINEBARRIER, "vkCmdPipelineBarrier()");
+ skip |= ValidateStageMaskGsTsEnables(dev_data, srcStageMask, "vkCmdPipelineBarrier()", VALIDATION_ERROR_00265,
+ VALIDATION_ERROR_00267);
+ skip |= ValidateStageMaskGsTsEnables(dev_data, dstStageMask, "vkCmdPipelineBarrier()", VALIDATION_ERROR_00266,
+ VALIDATION_ERROR_00268);
UpdateCmdBufferLastCmd(dev_data, cb_state, CMD_PIPELINEBARRIER);
skip |= TransitionImageLayouts(commandBuffer, imageMemoryBarrierCount, pImageMemoryBarriers);
skip |= ValidateBarriers("vkCmdPipelineBarrier", commandBuffer, memoryBarrierCount, pMemoryBarriers,
@@ -10698,6 +10735,12 @@ VKAPI_ATTR VkResult VKAPI_CALL CreateRenderPass(VkDevice device, const VkRenderP
// TODO: As part of wrapping up the mem_tracker/core_validation merge the following routine should be consolidated with
// ValidateLayouts.
skip_call |= ValidateRenderpassAttachmentUsage(dev_data, pCreateInfo);
+ for (uint32_t i = 0; i < pCreateInfo->dependencyCount; ++i) {
+ skip_call |= ValidateStageMaskGsTsEnables(dev_data, pCreateInfo->pDependencies[i].srcStageMask, "vkCreateRenderPass()",
+ VALIDATION_ERROR_00368, VALIDATION_ERROR_00370);
+ skip_call |= ValidateStageMaskGsTsEnables(dev_data, pCreateInfo->pDependencies[i].dstStageMask, "vkCreateRenderPass()",
+ VALIDATION_ERROR_00369, VALIDATION_ERROR_00371);
+ }
if (!skip_call) {
skip_call |= ValidateLayouts(dev_data, device, pCreateInfo);
}