mirror of
https://gitlab.freedesktop.org/mesa/mesa.git
synced 2025-12-24 17:30:12 +01:00
mesa/st/i965: add a ProgramResourceHash for quicker resource lookup
Many resource APIs require searching by name, add a hash table to make this faster. Currently we traverse the whole resource list for name based queries, this change makes all these cases use the hash. Closes: https://gitlab.freedesktop.org/mesa/mesa/issues/2203 Signed-off-by: Tapani Pälli <tapani.palli@intel.com> Reviewed-by: Marek Olšák <marek.olsak@amd.com> Tested-by: Marge Bot <https://gitlab.freedesktop.org/mesa/mesa/merge_requests/3254> Part-of: <https://gitlab.freedesktop.org/mesa/mesa/merge_requests/3254>
This commit is contained in:
parent
5f0ff004ca
commit
dd09f1d806
7 changed files with 95 additions and 5 deletions
|
|
@ -388,6 +388,8 @@ brw_link_shader(struct gl_context *ctx, struct gl_shader_program *shProg)
|
|||
else
|
||||
nir_build_program_resource_list(ctx, shProg, true);
|
||||
|
||||
_mesa_create_program_resource_hash(shProg);
|
||||
|
||||
for (stage = 0; stage < ARRAY_SIZE(shProg->_LinkedShaders); stage++) {
|
||||
struct gl_linked_shader *shader = shProg->_LinkedShaders[stage];
|
||||
if (!shader)
|
||||
|
|
|
|||
|
|
@ -2917,6 +2917,9 @@ struct gl_shader_program_data
|
|||
*/
|
||||
union gl_constant_value *UniformDataDefaults;
|
||||
|
||||
/** Hash for quick search by name. */
|
||||
struct hash_table_u64 *ProgramResourceHash;
|
||||
|
||||
GLboolean Validated;
|
||||
|
||||
/** List of all active resources after linking. */
|
||||
|
|
|
|||
|
|
@ -37,7 +37,7 @@
|
|||
#include "compiler/glsl/ir.h"
|
||||
#include "compiler/glsl/program.h"
|
||||
#include "compiler/glsl/string_to_uint_map.h"
|
||||
|
||||
#include "util/mesa-sha1.h"
|
||||
|
||||
static GLint
|
||||
program_resource_location(struct gl_program_resource *res,
|
||||
|
|
@ -461,7 +461,7 @@ _mesa_program_resource_name(struct gl_program_resource *res)
|
|||
case GL_TESS_EVALUATION_SUBROUTINE:
|
||||
return RESOURCE_SUB(res)->name;
|
||||
default:
|
||||
assert(!"support for resource type not implemented");
|
||||
break;
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
|
@ -527,6 +527,51 @@ valid_array_index(const GLchar *name, unsigned *array_index)
|
|||
return true;
|
||||
}
|
||||
|
||||
static uint32_t
|
||||
compute_resource_key(GLenum programInterface, const char *name)
|
||||
{
|
||||
struct mesa_sha1 ctx;
|
||||
unsigned char sha1[20];
|
||||
|
||||
_mesa_sha1_init(&ctx);
|
||||
_mesa_sha1_update(&ctx, &programInterface, sizeof(programInterface));
|
||||
_mesa_sha1_update(&ctx, name, strlen(name));
|
||||
_mesa_sha1_final(&ctx, sha1);
|
||||
|
||||
return _mesa_hash_data(sha1, sizeof(sha1));
|
||||
}
|
||||
|
||||
static struct gl_program_resource *
|
||||
search_resource_hash(struct gl_shader_program *shProg,
|
||||
GLenum programInterface, const char *name,
|
||||
unsigned *array_index)
|
||||
{
|
||||
const char *base_name_end;
|
||||
long index = parse_program_resource_name(name, &base_name_end);
|
||||
char *name_copy;
|
||||
|
||||
/* If dealing with array, we need to get the basename. */
|
||||
if (index >= 0) {
|
||||
name_copy = (char *) malloc(base_name_end - name + 1);
|
||||
memcpy(name_copy, name, base_name_end - name);
|
||||
name_copy[base_name_end - name] = '\0';
|
||||
} else {
|
||||
name_copy = (char*) name;
|
||||
}
|
||||
|
||||
uint32_t key = compute_resource_key(programInterface, name_copy);
|
||||
struct gl_program_resource *res = (struct gl_program_resource *)
|
||||
_mesa_hash_table_u64_search(shProg->data->ProgramResourceHash, key);
|
||||
|
||||
if (name_copy != name)
|
||||
free(name_copy);
|
||||
|
||||
if (res && array_index)
|
||||
*array_index = index >= 0 ? index : 0;
|
||||
|
||||
return res;
|
||||
}
|
||||
|
||||
/* Find a program resource with specific name in given interface.
|
||||
*/
|
||||
struct gl_program_resource *
|
||||
|
|
@ -534,9 +579,17 @@ _mesa_program_resource_find_name(struct gl_shader_program *shProg,
|
|||
GLenum programInterface, const char *name,
|
||||
unsigned *array_index)
|
||||
{
|
||||
struct gl_program_resource *res = shProg->data->ProgramResourceList;
|
||||
for (unsigned i = 0; i < shProg->data->NumProgramResourceList;
|
||||
i++, res++) {
|
||||
struct gl_program_resource *res = NULL;
|
||||
|
||||
/* If we have a name, try the ProgramResourceHash first. */
|
||||
if (name && shProg->data->ProgramResourceHash)
|
||||
res = search_resource_hash(shProg, programInterface, name, array_index);
|
||||
|
||||
if (res)
|
||||
return res;
|
||||
|
||||
res = shProg->data->ProgramResourceList;
|
||||
for (unsigned i = 0; i < shProg->data->NumProgramResourceList; i++, res++) {
|
||||
if (res->Type != programInterface)
|
||||
continue;
|
||||
|
||||
|
|
@ -1850,3 +1903,23 @@ _mesa_validate_pipeline_io(struct gl_pipeline_object *pipeline)
|
|||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
extern "C" void
|
||||
_mesa_create_program_resource_hash(struct gl_shader_program *shProg)
|
||||
{
|
||||
/* Rebuild resource hash. */
|
||||
if (shProg->data->ProgramResourceHash)
|
||||
_mesa_hash_table_u64_destroy(shProg->data->ProgramResourceHash, NULL);
|
||||
|
||||
shProg->data->ProgramResourceHash = _mesa_hash_table_u64_create(shProg);
|
||||
|
||||
struct gl_program_resource *res = shProg->data->ProgramResourceList;
|
||||
for (unsigned i = 0; i < shProg->data->NumProgramResourceList; i++, res++) {
|
||||
const char *name = _mesa_program_resource_name(res);
|
||||
if (name) {
|
||||
uint32_t key = compute_resource_key(res->Type, name);
|
||||
_mesa_hash_table_u64_insert(shProg->data->ProgramResourceHash, key,
|
||||
res);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -332,6 +332,9 @@ _mesa_get_program_resourceiv(struct gl_shader_program *shProg,
|
|||
GLsizei bufSize, GLsizei *length,
|
||||
GLint *params);
|
||||
|
||||
extern void
|
||||
_mesa_create_program_resource_hash(struct gl_shader_program *shProg);
|
||||
|
||||
/* GL_ARB_tessellation_shader */
|
||||
void GLAPIENTRY
|
||||
_mesa_PatchParameteri_no_error(GLenum pname, GLint value);
|
||||
|
|
|
|||
|
|
@ -344,6 +344,11 @@ _mesa_clear_shader_program_data(struct gl_context *ctx,
|
|||
shProg->UniformHash = NULL;
|
||||
}
|
||||
|
||||
if (shProg->data && shProg->data->ProgramResourceHash) {
|
||||
_mesa_hash_table_u64_destroy(shProg->data->ProgramResourceHash, NULL);
|
||||
shProg->data->ProgramResourceHash = NULL;
|
||||
}
|
||||
|
||||
_mesa_reference_shader_program_data(ctx, &shProg->data, NULL);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -843,6 +843,8 @@ st_link_nir(struct gl_context *ctx,
|
|||
prev_info = info;
|
||||
}
|
||||
|
||||
_mesa_create_program_resource_hash(shader_program);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -7428,5 +7428,7 @@ st_link_tgsi(struct gl_context *ctx, struct gl_shader_program *prog)
|
|||
}
|
||||
}
|
||||
|
||||
_mesa_create_program_resource_hash(prog);
|
||||
|
||||
return GL_TRUE;
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue