diff --git a/src/asahi/vulkan/hk_shader.c b/src/asahi/vulkan/hk_shader.c index 0e7f0b4d6f1..a21e849f290 100644 --- a/src/asahi/vulkan/hk_shader.c +++ b/src/asahi/vulkan/hk_shader.c @@ -30,6 +30,7 @@ #include "nir_xfb_info.h" #include "shader_enums.h" #include "vk_nir_convert_ycbcr.h" +#include "vk_physical_device_features.h" #include "vk_pipeline.h" #include "vk_pipeline_layout.h" #include "vk_shader.h" @@ -224,11 +225,12 @@ hk_populate_fs_key(struct hk_fs_key *key, static void hk_hash_graphics_state(struct vk_physical_device *device, const struct vk_graphics_pipeline_state *state, + const struct vk_features *features, VkShaderStageFlags stages, blake3_hash blake3_out) { struct mesa_blake3 blake3_ctx; _mesa_blake3_init(&blake3_ctx); - if (stages & VK_SHADER_STAGE_FRAGMENT_BIT) { + if (state && (stages & VK_SHADER_STAGE_FRAGMENT_BIT)) { struct hk_fs_key key; hk_populate_fs_key(&key, state); _mesa_blake3_update(&blake3_ctx, &key, sizeof(key)); @@ -1253,6 +1255,7 @@ static VkResult hk_compile_shaders(struct vk_device *vk_dev, uint32_t shader_count, struct vk_shader_compile_info *infos, const struct vk_graphics_pipeline_state *state, + const struct vk_features *features, const VkAllocationCallbacks *pAllocator, struct vk_shader **shaders_out) { @@ -1494,7 +1497,7 @@ const struct vk_device_shader_ops hk_device_shader_ops = { .get_nir_options = hk_get_nir_options, .get_spirv_options = hk_get_spirv_options, .preprocess_nir = hk_preprocess_nir, - .hash_graphics_state = hk_hash_graphics_state, + .hash_state = hk_hash_graphics_state, .compile = hk_compile_shaders, .deserialize = hk_deserialize_api_shader, .cmd_set_dynamic_graphics_state = vk_cmd_set_dynamic_graphics_state, diff --git a/src/nouveau/vulkan/nvk_shader.c b/src/nouveau/vulkan/nvk_shader.c index c998aabfe75..8f397bec013 100644 --- a/src/nouveau/vulkan/nvk_shader.c +++ b/src/nouveau/vulkan/nvk_shader.c @@ -247,14 +247,15 @@ nvk_populate_fs_key(struct nak_fs_key *key, } static void -nvk_hash_graphics_state(struct vk_physical_device *device, - const struct vk_graphics_pipeline_state *state, - VkShaderStageFlags stages, - blake3_hash blake3_out) +nvk_hash_state(struct vk_physical_device *device, + const struct vk_graphics_pipeline_state *state, + const struct vk_features *enabled_features, + VkShaderStageFlags stages, + blake3_hash blake3_out) { struct mesa_blake3 blake3_ctx; _mesa_blake3_init(&blake3_ctx); - if (stages & VK_SHADER_STAGE_FRAGMENT_BIT) { + if (state && (stages & VK_SHADER_STAGE_FRAGMENT_BIT)) { struct nak_fs_key key; nvk_populate_fs_key(&key, state); _mesa_blake3_update(&blake3_ctx, &key, sizeof(key)); @@ -1071,6 +1072,7 @@ nvk_compile_shaders(struct vk_device *vk_dev, uint32_t shader_count, struct vk_shader_compile_info *infos, const struct vk_graphics_pipeline_state *state, + const struct vk_features *enabled_features, const VkAllocationCallbacks* pAllocator, struct vk_shader **shaders_out) { @@ -1386,7 +1388,7 @@ const struct vk_device_shader_ops nvk_device_shader_ops = { .get_nir_options = nvk_get_nir_options, .get_spirv_options = nvk_get_spirv_options, .preprocess_nir = nvk_preprocess_nir, - .hash_graphics_state = nvk_hash_graphics_state, + .hash_state = nvk_hash_state, .compile = nvk_compile_shaders, .deserialize = nvk_deserialize_shader, .cmd_set_dynamic_graphics_state = vk_cmd_set_dynamic_graphics_state, diff --git a/src/panfrost/vulkan/panvk_vX_shader.c b/src/panfrost/vulkan/panvk_vX_shader.c index 51f0e8dbeb1..5b20a0ba4dc 100644 --- a/src/panfrost/vulkan/panvk_vX_shader.c +++ b/src/panfrost/vulkan/panvk_vX_shader.c @@ -436,26 +436,30 @@ panvk_preprocess_nir(UNUSED struct vk_physical_device *vk_pdev, } static void -panvk_hash_graphics_state(struct vk_physical_device *device, - const struct vk_graphics_pipeline_state *state, - VkShaderStageFlags stages, blake3_hash blake3_out) +panvk_hash_state(struct vk_physical_device *device, + const struct vk_graphics_pipeline_state *state, + const struct vk_features *enabled_features, + VkShaderStageFlags stages, blake3_hash blake3_out) { struct mesa_blake3 blake3_ctx; _mesa_blake3_init(&blake3_ctx); - /* This doesn't impact the shader compile but it does go in the - * panvk_shader and gets [de]serialized along with the binary so - * we need to hash it. - */ - bool sample_shading_enable = state->ms && state->ms->sample_shading_enable; - _mesa_blake3_update(&blake3_ctx, &sample_shading_enable, - sizeof(sample_shading_enable)); + if (state != NULL) { + /* This doesn't impact the shader compile but it does go in the + * panvk_shader and gets [de]serialized along with the binary so + * we need to hash it. + */ + bool sample_shading_enable = + state->ms && state->ms->sample_shading_enable; + _mesa_blake3_update(&blake3_ctx, &sample_shading_enable, + sizeof(sample_shading_enable)); - _mesa_blake3_update(&blake3_ctx, &state->rp->view_mask, - sizeof(state->rp->view_mask)); + _mesa_blake3_update(&blake3_ctx, &state->rp->view_mask, + sizeof(state->rp->view_mask)); - if (state->ial) - _mesa_blake3_update(&blake3_ctx, state->ial, sizeof(*state->ial)); + if (state->ial) + _mesa_blake3_update(&blake3_ctx, state->ial, sizeof(*state->ial)); + } _mesa_blake3_final(&blake3_ctx, blake3_out); } @@ -1307,6 +1311,7 @@ static VkResult panvk_compile_shaders(struct vk_device *vk_dev, uint32_t shader_count, struct vk_shader_compile_info *infos, const struct vk_graphics_pipeline_state *state, + const struct vk_features *enabled_features, const VkAllocationCallbacks *pAllocator, struct vk_shader **shaders_out) { @@ -1950,7 +1955,7 @@ const struct vk_device_shader_ops panvk_per_arch(device_shader_ops) = { .get_nir_options = panvk_get_nir_options, .get_spirv_options = panvk_get_spirv_options, .preprocess_nir = panvk_preprocess_nir, - .hash_graphics_state = panvk_hash_graphics_state, + .hash_state = panvk_hash_state, .compile = panvk_compile_shaders, .deserialize = panvk_deserialize_shader, .cmd_set_dynamic_graphics_state = vk_cmd_set_dynamic_graphics_state, diff --git a/src/vulkan/runtime/vk_pipeline.c b/src/vulkan/runtime/vk_pipeline.c index ce7a37c3151..8212c311c21 100644 --- a/src/vulkan/runtime/vk_pipeline.c +++ b/src/vulkan/runtime/vk_pipeline.c @@ -32,6 +32,7 @@ #include "vk_log.h" #include "vk_nir.h" #include "vk_physical_device.h" +#include "vk_physical_device_features.h" #include "vk_pipeline_layout.h" #include "vk_shader.h" #include "vk_shader_module.h" @@ -1237,8 +1238,8 @@ vk_graphics_pipeline_compile_shaders(struct vk_device *device, } blake3_hash state_blake3; - ops->hash_graphics_state(device->physical, state, - part_stages, state_blake3); + ops->hash_state(device->physical, state, &device->enabled_features, + part_stages, state_blake3); _mesa_blake3_update(&blake3_ctx, state_blake3, sizeof(state_blake3)); _mesa_blake3_update(&blake3_ctx, layout_blake3, sizeof(layout_blake3)); @@ -1420,7 +1421,7 @@ vk_graphics_pipeline_compile_shaders(struct vk_device *device, struct vk_shader *shaders[MESA_VK_MAX_GRAPHICS_PIPELINE_STAGES]; result = ops->compile(device, partition[p + 1] - partition[p], &infos[partition[p]], - state, + state, &device->enabled_features, &device->alloc, &shaders[partition[p]]); if (result != VK_SUCCESS) @@ -1982,6 +1983,12 @@ vk_pipeline_compile_compute_stage(struct vk_device *device, _mesa_blake3_update(&blake3_ctx, &shader_flags, sizeof(shader_flags)); + blake3_hash features_blake3; + ops->hash_state(device->physical, NULL /* state */, + &device->enabled_features, VK_SHADER_STAGE_COMPUTE_BIT, + features_blake3); + _mesa_blake3_update(&blake3_ctx, features_blake3, sizeof(features_blake3)); + for (uint32_t i = 0; i < pipeline_layout->set_count; i++) { if (pipeline_layout->set_layouts[i] != NULL) { _mesa_blake3_update(&blake3_ctx, @@ -2040,7 +2047,7 @@ vk_pipeline_compile_compute_stage(struct vk_device *device, struct vk_shader *shader; result = ops->compile(device, 1, &compile_info, NULL, - &device->alloc, &shader); + &device->enabled_features, &device->alloc, &shader); if (result != VK_SUCCESS) return result; diff --git a/src/vulkan/runtime/vk_shader.c b/src/vulkan/runtime/vk_shader.c index 3f5ed17fe3d..0594be4d41a 100644 --- a/src/vulkan/runtime/vk_shader.c +++ b/src/vulkan/runtime/vk_shader.c @@ -30,6 +30,7 @@ #include "vk_device.h" #include "vk_nir.h" #include "vk_physical_device.h" +#include "vk_physical_device_features.h" #include "vk_pipeline.h" #include "util/mesa-sha1.h" @@ -507,7 +508,7 @@ vk_common_CreateShadersEXT(VkDevice _device, struct vk_shader *shader; result = ops->compile(device, 1, &info, NULL /* state */, - pAllocator, &shader); + NULL /* features */, pAllocator, &shader); if (result != VK_SUCCESS) break; @@ -554,7 +555,7 @@ vk_common_CreateShadersEXT(VkDevice _device, struct vk_shader *shaders[VK_MAX_LINKED_SHADER_STAGES]; result = ops->compile(device, linked_count, infos, NULL /* state */, - pAllocator, shaders); + NULL /* features */, pAllocator, shaders); if (result == VK_SUCCESS) { for (uint32_t l = 0; l < linked_count; l++) pShaders[linked[l].idx] = vk_shader_to_handle(shaders[l]); diff --git a/src/vulkan/runtime/vk_shader.h b/src/vulkan/runtime/vk_shader.h index b01d4ddfa9d..8a0cc13318b 100644 --- a/src/vulkan/runtime/vk_shader.h +++ b/src/vulkan/runtime/vk_shader.h @@ -41,6 +41,7 @@ struct vk_device; struct vk_descriptor_set_layout; struct vk_dynamic_graphics_state; struct vk_graphics_pipeline_state; +struct vk_features; struct vk_physical_device; struct vk_pipeline; struct vk_pipeline_robustness_state; @@ -213,15 +214,19 @@ struct vk_device_shader_ops { */ bool link_geom_stages; - /** Hash a vk_graphics_state object + /** Hash a vk_graphics_state object and a vk_features object. * * This callback hashes whatever bits of vk_graphics_pipeline_state might * be used to compile a shader in one of the given stages. + * + * state may be null, indicating that all state is dynamic. enabled_features + * is always non-NULL. */ - void (*hash_graphics_state)(struct vk_physical_device *device, - const struct vk_graphics_pipeline_state *state, - VkShaderStageFlags stages, - blake3_hash blake3_out); + void (*hash_state)(struct vk_physical_device *device, + const struct vk_graphics_pipeline_state *state, + const struct vk_features *enabled_features, + VkShaderStageFlags stages, + blake3_hash blake3_out); /** Compile (and potentially link) a set of shaders * @@ -230,6 +235,9 @@ struct vk_device_shader_ops { * them. We also guarantee that the shaders occur in the call in Vulkan * pipeline stage order as dictated by vk_shader_cmp_graphics_stages(). * + * If state/enabled_features is NULL, the driver must conservatively assume + * all state is dynamic / all features are enabled respectively. + * * This callback consumes all input NIR shaders, regardless of whether or * not it was successful. */ @@ -237,6 +245,7 @@ struct vk_device_shader_ops { uint32_t shader_count, struct vk_shader_compile_info *infos, const struct vk_graphics_pipeline_state *state, + const struct vk_features *enabled_features, const VkAllocationCallbacks* pAllocator, struct vk_shader **shaders_out);