radv: use ref counting for VS prologs and PS epilogs

With GPL, it will be possible to create VS prologs and PS epilogs
from libraries, so reference counting is useful here too.

Signed-off-by: Samuel Pitoiset <samuel.pitoiset@gmail.com>
Reviewed-By: Tatsuyuki Ishi <ishitatsuyuki@gmail.com>
Reviewed-by: Bas Nieuwenhuizen <bas@basnieuwenhuizen.nl>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/17628>
This commit is contained in:
Samuel Pitoiset 2022-07-19 14:36:28 +02:00 committed by Marge Bot
parent a2b8a92c72
commit 1fb12d2cce
4 changed files with 35 additions and 8 deletions

View file

@ -3184,7 +3184,7 @@ lookup_vs_prolog(struct radv_cmd_buffer *cmd_buffer, struct radv_shader *vs_shad
prolog = radv_create_vs_prolog(device, &key);
uint32_t *key2 = malloc(key_size * 4);
if (!prolog || !key2) {
radv_shader_part_destroy(device, prolog);
radv_shader_part_unref(device, prolog);
free(key2);
u_rwlock_wrunlock(&device->vs_prologs_lock);
return NULL;

View file

@ -3029,16 +3029,24 @@ radv_device_finish_vs_prologs(struct radv_device *device)
hash_table_foreach(device->vs_prologs, entry)
{
free((void *)entry->key);
radv_shader_part_destroy(device, entry->data);
radv_shader_part_unref(device, entry->data);
}
_mesa_hash_table_destroy(device->vs_prologs, NULL);
}
for (unsigned i = 0; i < ARRAY_SIZE(device->simple_vs_prologs); i++)
radv_shader_part_destroy(device, device->simple_vs_prologs[i]);
for (unsigned i = 0; i < ARRAY_SIZE(device->simple_vs_prologs); i++) {
if (!device->simple_vs_prologs[i])
continue;
for (unsigned i = 0; i < ARRAY_SIZE(device->instance_rate_vs_prologs); i++)
radv_shader_part_destroy(device, device->instance_rate_vs_prologs[i]);
radv_shader_part_unref(device, device->simple_vs_prologs[i]);
}
for (unsigned i = 0; i < ARRAY_SIZE(device->instance_rate_vs_prologs); i++) {
if (!device->instance_rate_vs_prologs[i])
continue;
radv_shader_part_unref(device, device->instance_rate_vs_prologs[i]);
}
}
VkResult

View file

@ -2335,6 +2335,8 @@ upload_shader_part(struct radv_device *device, struct radv_shader_part_binary *b
if (!shader_part)
return NULL;
shader_part->ref_count = 1;
shader_part->alloc = radv_alloc_shader_memory(device, code_size, NULL);
if (!shader_part->alloc) {
free(shader_part);
@ -2516,8 +2518,7 @@ radv_shader_destroy(struct radv_device *device, struct radv_shader *shader)
void
radv_shader_part_destroy(struct radv_device *device, struct radv_shader_part *shader_part)
{
if (!shader_part)
return;
assert(shader_part->ref_count == 0);
radv_free_shader_memory(device, shader_part->alloc);
free(shader_part->disasm_string);

View file

@ -513,6 +513,8 @@ struct radv_trap_handler_shader {
};
struct radv_shader_part {
uint32_t ref_count;
struct radeon_winsys_bo *bo;
union radv_shader_arena_block *alloc;
uint32_t rsrc1;
@ -637,6 +639,22 @@ radv_shader_unref(struct radv_device *device, struct radv_shader *shader)
radv_shader_destroy(device, shader);
}
static inline struct radv_shader_part *
radv_shader_part_ref(struct radv_shader_part *shader_part)
{
assert(shader_part && shader_part->ref_count >= 1);
p_atomic_inc(&shader_part->ref_count);
return shader_part;
}
static inline void
radv_shader_part_unref(struct radv_device *device, struct radv_shader_part *shader_part)
{
assert(shader_part && shader_part->ref_count >= 1);
if (p_atomic_dec_zero(&shader_part->ref_count))
radv_shader_part_destroy(device, shader_part);
}
static inline unsigned
calculate_tess_lds_size(enum amd_gfx_level gfx_level, unsigned tcs_num_input_vertices,
unsigned tcs_num_output_vertices, unsigned tcs_num_inputs,