diff options
| author | Chris Forbes <chrisforbes@google.com> | 2017-07-24 15:35:29 -0700 |
|---|---|---|
| committer | Chris Forbes <chrisf@ijw.co.nz> | 2017-11-28 16:27:21 -0800 |
| commit | 0f36ac54143b3166c52952840ed71bf9ce041626 (patch) | |
| tree | 7494b386c353497790b52975cac1b394ba163d90 /layers/shader_validation.cpp | |
| parent | a21af959330b04bf065369063c9f384a0391ab9f (diff) | |
| download | usermoji-0f36ac54143b3166c52952840ed71bf9ce041626.tar.xz | |
layers: Add VK_EXT_validation_cache implementation for shaders
Diffstat (limited to 'layers/shader_validation.cpp')
| -rw-r--r-- | layers/shader_validation.cpp | 27 |
1 files changed, 27 insertions, 0 deletions
diff --git a/layers/shader_validation.cpp b/layers/shader_validation.cpp index 11fcbdcb..aa215fa4 100644 --- a/layers/shader_validation.cpp +++ b/layers/shader_validation.cpp @@ -35,6 +35,7 @@ #include "core_validation_types.h" #include "shader_validation.h" #include "spirv-tools/libspirv.h" +#include "xxhash.h" enum FORMAT_TYPE { FORMAT_TYPE_FLOAT = 1, // UNORM, SNORM, FLOAT, USCALED, SSCALED, SRGB -- anything we consider float in the shader @@ -1517,6 +1518,20 @@ bool validate_compute_pipeline(layer_data *dev_data, PIPELINE_STATE *pipeline) { return validate_pipeline_shader_stage(dev_data, &pCreateInfo->stage, pipeline, &module, &entrypoint); } +uint32_t ValidationCache::MakeShaderHash(VkShaderModuleCreateInfo const *smci) { + return XXH32(smci->pCode, smci->codeSize * sizeof(uint32_t), 0); +} + +static ValidationCache *GetValidationCacheInfo( + VkShaderModuleCreateInfo const *pCreateInfo) { + while ((pCreateInfo = (VkShaderModuleCreateInfo const *)pCreateInfo->pNext) != nullptr) { + if (pCreateInfo->sType == VK_STRUCTURE_TYPE_SHADER_MODULE_VALIDATION_CACHE_CREATE_INFO_EXT) + return (ValidationCache *)((VkShaderModuleValidationCacheCreateInfoEXT const *)pCreateInfo)->validationCache; + } + + return nullptr; +} + bool PreCallValidateCreateShaderModule(layer_data *dev_data, VkShaderModuleCreateInfo const *pCreateInfo, bool *spirv_valid) { bool skip = false; spv_result_t spv_valid = SPV_SUCCESS; @@ -1534,6 +1549,14 @@ bool PreCallValidateCreateShaderModule(layer_data *dev_data, VkShaderModuleCreat "SPIR-V module not valid: Codesize must be a multiple of 4 but is " PRINTF_SIZE_T_SPECIFIER ". %s", pCreateInfo->codeSize, validation_error_map[VALIDATION_ERROR_12a00ac0]); } else { + auto cache = GetValidationCacheInfo(pCreateInfo); + uint32_t hash = 0; + if (cache) { + hash = ValidationCache::MakeShaderHash(pCreateInfo); + if (cache->Contains(hash)) + return false; + } + // Use SPIRV-Tools validator to try and catch any issues with the module itself spv_context ctx = spvContextCreate(SPV_ENV_VULKAN_1_0); spv_const_binary_t binary{ pCreateInfo->pCode, pCreateInfo->codeSize / sizeof(uint32_t) }; @@ -1547,6 +1570,10 @@ bool PreCallValidateCreateShaderModule(layer_data *dev_data, VkShaderModuleCreat VK_DEBUG_REPORT_OBJECT_TYPE_UNKNOWN_EXT, 0, __LINE__, SHADER_CHECKER_INCONSISTENT_SPIRV, "SC", "SPIR-V module not valid: %s", diag && diag->error ? diag->error : "(no error text)"); } + } else { + if (cache) { + cache->Insert(hash); + } } spvDiagnosticDestroy(diag); |
