diff options
| author | Mark Lobodzinski <mark@lunarg.com> | 2016-05-17 08:42:03 -0600 |
|---|---|---|
| committer | Mark Lobodzinski <mark@lunarg.com> | 2016-05-17 09:06:53 -0600 |
| commit | c39f89e8d87f06d7c1eae647b699c3cf0ab1aac7 (patch) | |
| tree | c868a3e2d0fa988b54d77babd9a71c80dbb23145 /layers/image.cpp | |
| parent | cff1cd36aa64b0713c068d82380bd6554984fa67 (diff) | |
| download | usermoji-c39f89e8d87f06d7c1eae647b699c3cf0ab1aac7.tar.xz | |
layers: GH485, Strengthen image format validation
CreateImage was checking that format caps weren't null, but was not
validating against color or depth/stencil attachment types.
Change-Id: Ic8996829033f552f6ef7477bdefdaba702ae2403
Diffstat (limited to 'layers/image.cpp')
| -rw-r--r-- | layers/image.cpp | 91 |
1 files changed, 69 insertions, 22 deletions
diff --git a/layers/image.cpp b/layers/image.cpp index 2fce6500..b420cad1 100644 --- a/layers/image.cpp +++ b/layers/image.cpp @@ -229,9 +229,9 @@ static inline uint32_t validate_VkImageLayoutKHR(VkImageLayout input_value) { return ((validate_VkImageLayout(input_value) == 1) || (input_value == VK_IMAGE_LAYOUT_PRESENT_SRC_KHR)); } -VKAPI_ATTR VkResult VKAPI_CALL -CreateImage(VkDevice device, const VkImageCreateInfo *pCreateInfo, const VkAllocationCallbacks *pAllocator, VkImage *pImage) { - bool skipCall = false; +VKAPI_ATTR VkResult VKAPI_CALL CreateImage(VkDevice device, const VkImageCreateInfo *pCreateInfo, + const VkAllocationCallbacks *pAllocator, VkImage *pImage) { + bool skip_call = false; VkResult result = VK_ERROR_VALIDATION_FAILED_EXT; VkImageFormatProperties ImageFormatProperties; @@ -243,13 +243,60 @@ CreateImage(VkDevice device, const VkImageCreateInfo *pCreateInfo, const VkAlloc VkFormatProperties properties; phy_dev_data->instance_dispatch_table->GetPhysicalDeviceFormatProperties(device_data->physicalDevice, pCreateInfo->format, &properties); - if ((properties.linearTilingFeatures) == 0 && (properties.optimalTilingFeatures == 0)) { - char const str[] = "vkCreateImage parameter, VkFormat pCreateInfo->format, contains unsupported format"; + std::stringstream ss; + ss << "vkCreateImage format parameter (" << string_VkFormat(pCreateInfo->format) << ") is an unsupported format"; // TODO: Verify against Valid Use section of spec. Generally if something yield an undefined result, it's invalid - skipCall |= log_msg(device_data->report_data, VK_DEBUG_REPORT_ERROR_BIT_EXT, (VkDebugReportObjectTypeEXT)0, 0, __LINE__, - IMAGE_FORMAT_UNSUPPORTED, "IMAGE", str); + skip_call |= log_msg(device_data->report_data, VK_DEBUG_REPORT_ERROR_BIT_EXT, VK_DEBUG_REPORT_OBJECT_TYPE_UNKNOWN_EXT, + 0, __LINE__, IMAGE_FORMAT_UNSUPPORTED, "IMAGE", "%s", ss.str().c_str()); } + + // Validate that format supports usage as color attachment + if (pCreateInfo->usage & VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT) { + if ((pCreateInfo->tiling == VK_IMAGE_TILING_OPTIMAL) && + ((properties.optimalTilingFeatures & VK_FORMAT_FEATURE_COLOR_ATTACHMENT_BIT) == 0)) { + std::stringstream ss; + ss << "vkCreateImage: VkFormat for TILING_OPTIMAL image (" << string_VkFormat(pCreateInfo->format) + << ") does not support requested Image usage type VK_IMAGE_USAGE_COLOR_ATTACHMENT"; + skip_call |= + log_msg(device_data->report_data, VK_DEBUG_REPORT_ERROR_BIT_EXT, VK_DEBUG_REPORT_OBJECT_TYPE_UNKNOWN_EXT, 0, + __LINE__, IMAGE_INVALID_FORMAT, "IMAGE", "%s", ss.str().c_str()); + } + if ((pCreateInfo->tiling == VK_IMAGE_TILING_LINEAR) && + ((properties.linearTilingFeatures & VK_FORMAT_FEATURE_COLOR_ATTACHMENT_BIT) == 0)) { + std::stringstream ss; + ss << "vkCreateImage: VkFormat for TILING_LINEAR image (" << string_VkFormat(pCreateInfo->format) + << ") does not support requested Image usage type VK_IMAGE_USAGE_COLOR_ATTACHMENT"; + skip_call |= + log_msg(device_data->report_data, VK_DEBUG_REPORT_ERROR_BIT_EXT, VK_DEBUG_REPORT_OBJECT_TYPE_UNKNOWN_EXT, 0, + __LINE__, IMAGE_INVALID_FORMAT, "IMAGE", "%s", ss.str().c_str()); + } + } + // Validate that format supports usage as depth/stencil attachment + if (pCreateInfo->usage & VK_IMAGE_USAGE_DEPTH_STENCIL_ATTACHMENT_BIT) { + if ((pCreateInfo->tiling == VK_IMAGE_TILING_OPTIMAL) && + ((properties.optimalTilingFeatures & VK_FORMAT_FEATURE_DEPTH_STENCIL_ATTACHMENT_BIT) == 0)) { + std::stringstream ss; + ss << "vkCreateImage: VkFormat for TILING_OPTIMAL image (" << string_VkFormat(pCreateInfo->format) + << ") does not support requested Image usage type VK_IMAGE_USAGE_DEPTH_STENCIL_ATTACHMENT"; + skip_call |= + log_msg(device_data->report_data, VK_DEBUG_REPORT_ERROR_BIT_EXT, VK_DEBUG_REPORT_OBJECT_TYPE_UNKNOWN_EXT, 0, + __LINE__, IMAGE_INVALID_FORMAT, "IMAGE", "%s", ss.str().c_str()); + } + if ((pCreateInfo->tiling == VK_IMAGE_TILING_LINEAR) && + ((properties.linearTilingFeatures & VK_FORMAT_FEATURE_DEPTH_STENCIL_ATTACHMENT_BIT) == 0)) { + std::stringstream ss; + ss << "vkCreateImage: VkFormat for TILING_LINEAR image (" << string_VkFormat(pCreateInfo->format) + << ") does not support requested Image usage type VK_IMAGE_USAGE_DEPTH_STENCIL_ATTACHMENT"; + skip_call |= + log_msg(device_data->report_data, VK_DEBUG_REPORT_ERROR_BIT_EXT, VK_DEBUG_REPORT_OBJECT_TYPE_UNKNOWN_EXT, 0, + __LINE__, IMAGE_INVALID_FORMAT, "IMAGE", "%s", ss.str().c_str()); + } + } + } else { + skip_call |= + log_msg(device_data->report_data, VK_DEBUG_REPORT_ERROR_BIT_EXT, VK_DEBUG_REPORT_OBJECT_TYPE_UNKNOWN_EXT, 0, __LINE__, + IMAGE_INVALID_FORMAT, "IMAGE", "vkCreateImage: VkFormat for image must not be VK_FORMAT_UNDEFINED"); } // Internal call to get format info. Still goes through layers, could potentially go directly to ICD. @@ -282,9 +329,9 @@ CreateImage(VkDevice device, const VkImageCreateInfo *pCreateInfo, const VkAlloc break; } if (failedMinSize) { - skipCall |= + skip_call |= log_msg(phy_dev_data->report_data, VK_DEBUG_REPORT_ERROR_BIT_EXT, VK_DEBUG_REPORT_OBJECT_TYPE_IMAGE_EXT, - (uint64_t)pImage, __LINE__, IMAGE_INVALID_FORMAT_LIMITS_VIOLATION, "Image", + 0, __LINE__, IMAGE_INVALID_FORMAT_LIMITS_VIOLATION, "Image", "CreateImage extents is 0 for at least one required dimension for image of type %d: " "Width = %d Height = %d Depth = %d.", pCreateInfo->imageType, pCreateInfo->extent.width, pCreateInfo->extent.height, pCreateInfo->extent.depth); @@ -293,8 +340,8 @@ CreateImage(VkDevice device, const VkImageCreateInfo *pCreateInfo, const VkAlloc if ((pCreateInfo->extent.depth > ImageFormatProperties.maxExtent.depth) || (pCreateInfo->extent.width > ImageFormatProperties.maxExtent.width) || (pCreateInfo->extent.height > ImageFormatProperties.maxExtent.height)) { - skipCall |= log_msg(phy_dev_data->report_data, VK_DEBUG_REPORT_ERROR_BIT_EXT, VK_DEBUG_REPORT_OBJECT_TYPE_IMAGE_EXT, - (uint64_t)pImage, __LINE__, IMAGE_INVALID_FORMAT_LIMITS_VIOLATION, "Image", + skip_call |= log_msg(phy_dev_data->report_data, VK_DEBUG_REPORT_ERROR_BIT_EXT, VK_DEBUG_REPORT_OBJECT_TYPE_IMAGE_EXT, + 0, __LINE__, IMAGE_INVALID_FORMAT_LIMITS_VIOLATION, "Image", "CreateImage extents exceed allowable limits for format: " "Width = %d Height = %d Depth = %d: Limits for Width = %d Height = %d Depth = %d for format %s.", pCreateInfo->extent.width, pCreateInfo->extent.height, pCreateInfo->extent.depth, @@ -309,42 +356,42 @@ CreateImage(VkDevice device, const VkImageCreateInfo *pCreateInfo, const VkAlloc ~(uint64_t)imageGranularity; if (totalSize > ImageFormatProperties.maxResourceSize) { - skipCall |= log_msg(phy_dev_data->report_data, VK_DEBUG_REPORT_ERROR_BIT_EXT, VK_DEBUG_REPORT_OBJECT_TYPE_IMAGE_EXT, - (uint64_t)pImage, __LINE__, IMAGE_INVALID_FORMAT_LIMITS_VIOLATION, "Image", + skip_call |= log_msg(phy_dev_data->report_data, VK_DEBUG_REPORT_ERROR_BIT_EXT, VK_DEBUG_REPORT_OBJECT_TYPE_IMAGE_EXT, + 0, __LINE__, IMAGE_INVALID_FORMAT_LIMITS_VIOLATION, "Image", "CreateImage resource size exceeds allowable maximum " "Image resource size = 0x%" PRIxLEAST64 ", maximum resource size = 0x%" PRIxLEAST64 " ", totalSize, ImageFormatProperties.maxResourceSize); } if (pCreateInfo->mipLevels > ImageFormatProperties.maxMipLevels) { - skipCall |= log_msg(phy_dev_data->report_data, VK_DEBUG_REPORT_ERROR_BIT_EXT, VK_DEBUG_REPORT_OBJECT_TYPE_IMAGE_EXT, - (uint64_t)pImage, __LINE__, IMAGE_INVALID_FORMAT_LIMITS_VIOLATION, "Image", + skip_call |= log_msg(phy_dev_data->report_data, VK_DEBUG_REPORT_ERROR_BIT_EXT, VK_DEBUG_REPORT_OBJECT_TYPE_IMAGE_EXT, + 0, __LINE__, IMAGE_INVALID_FORMAT_LIMITS_VIOLATION, "Image", "CreateImage mipLevels=%d exceeds allowable maximum supported by format of %d", pCreateInfo->mipLevels, ImageFormatProperties.maxMipLevels); } if (pCreateInfo->arrayLayers > ImageFormatProperties.maxArrayLayers) { - skipCall |= log_msg(phy_dev_data->report_data, VK_DEBUG_REPORT_ERROR_BIT_EXT, VK_DEBUG_REPORT_OBJECT_TYPE_IMAGE_EXT, - (uint64_t)pImage, __LINE__, IMAGE_INVALID_FORMAT_LIMITS_VIOLATION, "Image", + skip_call |= log_msg(phy_dev_data->report_data, VK_DEBUG_REPORT_ERROR_BIT_EXT, VK_DEBUG_REPORT_OBJECT_TYPE_IMAGE_EXT, + 0, __LINE__, IMAGE_INVALID_FORMAT_LIMITS_VIOLATION, "Image", "CreateImage arrayLayers=%d exceeds allowable maximum supported by format of %d", pCreateInfo->arrayLayers, ImageFormatProperties.maxArrayLayers); } if ((pCreateInfo->samples & ImageFormatProperties.sampleCounts) == 0) { - skipCall |= log_msg(phy_dev_data->report_data, VK_DEBUG_REPORT_ERROR_BIT_EXT, VK_DEBUG_REPORT_OBJECT_TYPE_IMAGE_EXT, - (uint64_t)pImage, __LINE__, IMAGE_INVALID_FORMAT_LIMITS_VIOLATION, "Image", + skip_call |= log_msg(phy_dev_data->report_data, VK_DEBUG_REPORT_ERROR_BIT_EXT, VK_DEBUG_REPORT_OBJECT_TYPE_IMAGE_EXT, + 0, __LINE__, IMAGE_INVALID_FORMAT_LIMITS_VIOLATION, "Image", "CreateImage samples %s is not supported by format 0x%.8X", string_VkSampleCountFlagBits(pCreateInfo->samples), ImageFormatProperties.sampleCounts); } if (pCreateInfo->initialLayout != VK_IMAGE_LAYOUT_UNDEFINED && pCreateInfo->initialLayout != VK_IMAGE_LAYOUT_PREINITIALIZED) { - skipCall |= log_msg(phy_dev_data->report_data, VK_DEBUG_REPORT_ERROR_BIT_EXT, VK_DEBUG_REPORT_OBJECT_TYPE_IMAGE_EXT, - (uint64_t)pImage, __LINE__, IMAGE_INVALID_LAYOUT, "Image", + skip_call |= log_msg(phy_dev_data->report_data, VK_DEBUG_REPORT_ERROR_BIT_EXT, VK_DEBUG_REPORT_OBJECT_TYPE_IMAGE_EXT, + 0, __LINE__, IMAGE_INVALID_LAYOUT, "Image", "vkCreateImage parameter, pCreateInfo->initialLayout, must be VK_IMAGE_LAYOUT_UNDEFINED or " "VK_IMAGE_LAYOUT_PREINITIALIZED"); } - if (!skipCall) { + if (!skip_call) { result = device_data->device_dispatch_table->CreateImage(device, pCreateInfo, pAllocator, pImage); } if (result == VK_SUCCESS) { |
