Mesa (main): mesa/shaderapi: add an optional shader override mechanism
GitLab Mirror
gitlab-mirror at kemper.freedesktop.org
Mon Jun 28 09:30:52 UTC 2021
Module: Mesa
Branch: main
Commit: 11528b621ccdfe40b10d3a9841a7f71f3fd6d848
URL: http://cgit.freedesktop.org/mesa/mesa/commit/?id=11528b621ccdfe40b10d3a9841a7f71f3fd6d848
Author: Pierre-Eric Pelloux-Prayer <pierre-eric.pelloux-prayer at amd.com>
Date: Thu May 27 16:06:15 2021 +0200
mesa/shaderapi: add an optional shader override mechanism
MESA_SHADER_READ_PATH is handy but it's not usable in
all cases.
This commit allows to implement an alternative mechanism
without assuming too much about how it's done, nor where/how
the shaders are stored.
When this is enabled MESA_SHADER_DUMP_PATH,
MESA_SHADER_CAPTURE_PATH and MESA_GLSL env var handling is
disabled.
Reviewed-by: Marek Olšák <marek.olsak at amd.com>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/11621>
---
meson.build | 6 ++++
meson_options.txt | 6 ++++
src/mesa/main/shaderapi.c | 66 +++++++++++++++++++++++++++++++++++++++++--
src/mesa/program/prog_print.c | 2 ++
4 files changed, 78 insertions(+), 2 deletions(-)
diff --git a/meson.build b/meson.build
index 0c0f71ae06a..8d74b96a27b 100644
--- a/meson.build
+++ b/meson.build
@@ -2006,6 +2006,12 @@ else
dep_lmsensors = null_dep
endif
+_shader_replacement = get_option('custom-shader-replacement')
+if _shader_replacement == ''
+else
+ pre_args += '-DCUSTOM_SHADER_REPLACEMENT'
+endif
+
with_perfetto = get_option('perfetto')
with_datasources = get_option('datasources')
with_any_datasource = with_datasources.length() != 0
diff --git a/meson_options.txt b/meson_options.txt
index 42ea224c95a..9fd9c8a2fd9 100644
--- a/meson_options.txt
+++ b/meson_options.txt
@@ -502,3 +502,9 @@ option(
choices : ['auto', 'panfrost', 'intel', 'freedreno'],
description: 'List of Perfetto datasources to build. If this is set to `auto`, datasources that can not be build are skipped. Default: [`auto`]'
)
+option(
+ 'custom-shader-replacement',
+ type : 'string',
+ value : '',
+ description : 'Enable a custom shader replacement mechanism. Note that enabling this option requires adding/generating a shader_replacement.h file that can be included (see shaderapi.c).'
+)
diff --git a/src/mesa/main/shaderapi.c b/src/mesa/main/shaderapi.c
index dab12e7a1ef..d6d42bd8d5c 100644
--- a/src/mesa/main/shaderapi.c
+++ b/src/mesa/main/shaderapi.c
@@ -64,8 +64,47 @@
#include "util/crc32.h"
#include "util/os_file.h"
#include "util/simple_list.h"
+#include "util/u_process.h"
#include "util/u_string.h"
+#ifdef ENABLE_SHADER_CACHE
+#if CUSTOM_SHADER_REPLACEMENT
+#include "shader_replacement.h"
+/* shader_replacement.h must declare a variable like this:
+
+ struct _shader_replacement {
+ // process name. If null, only sha1 is used to match
+ const char *app;
+ // original glsl shader sha1
+ const char *sha1;
+ // shader stage
+ gl_shader_stage stage;
+ ... any other information ...
+ };
+ struct _shader_replacement shader_replacements[...];
+
+ And a method to load a given replacement and return the new
+ glsl source:
+
+ char* load_shader_replacement(struct _shader_replacement *repl);
+
+ shader_replacement.h can be generated at build time, or copied
+ from an external folder, or any other method.
+*/
+#else
+struct _shader_replacement {
+ const char *app;
+ const char *sha1;
+ gl_shader_stage stage;
+};
+struct _shader_replacement shader_replacements[0];
+static char* load_shader_replacement(struct _shader_replacement *repl)
+{
+ return NULL;
+}
+#endif
+#endif
+
/**
* Return mask of GLSL_x flags by examining the MESA_GLSL env var.
*/
@@ -78,10 +117,12 @@ _mesa_get_shader_flags(void)
if (env) {
if (strstr(env, "dump_on_error"))
flags |= GLSL_DUMP_ON_ERROR;
+#ifndef CUSTOM_SHADER_REPLACEMENT
else if (strstr(env, "dump"))
flags |= GLSL_DUMP;
if (strstr(env, "log"))
flags |= GLSL_LOG;
+#endif
if (strstr(env, "cache_fb"))
flags |= GLSL_CACHE_FALLBACK;
if (strstr(env, "cache_info"))
@@ -1342,6 +1383,7 @@ link_program(struct gl_context *ctx, struct gl_shader_program *shProg,
}
}
+#ifndef CUSTOM_SHADER_REPLACEMENT
/* Capture .shader_test files. */
const char *capture_path = _mesa_get_shader_capture_path();
if (shProg->Name != 0 && shProg->Name != ~0 && capture_path != NULL) {
@@ -1386,6 +1428,7 @@ link_program(struct gl_context *ctx, struct gl_shader_program *shProg,
ralloc_free(filename);
}
+#endif
if (shProg->data->LinkStatus == LINKING_FAILURE &&
(ctx->_Shader->Flags & GLSL_REPORT_ERRORS)) {
@@ -1953,6 +1996,7 @@ construct_name(const gl_shader_stage stage, const char *sha,
void
_mesa_dump_shader_source(const gl_shader_stage stage, const char *source)
{
+#ifndef CUSTOM_SHADER_REPLACEMENT
static bool path_exists = true;
char *dump_path;
FILE *f;
@@ -1980,6 +2024,7 @@ _mesa_dump_shader_source(const gl_shader_stage stage, const char *source)
strerror(errno));
}
ralloc_free(name);
+#endif
}
/**
@@ -1996,6 +2041,24 @@ _mesa_read_shader_source(const gl_shader_stage stage, const char *source)
FILE *f;
char sha[64];
+ generate_sha1(source, sha);
+
+ const char *process_name =
+ ARRAY_SIZE(shader_replacements) ? util_get_process_name() : NULL;
+ for (size_t i = 0; i < ARRAY_SIZE(shader_replacements); i++) {
+ if (stage != shader_replacements[i].stage)
+ continue;
+
+ if (shader_replacements[i].app &&
+ strcmp(process_name, shader_replacements[i].app) != 0)
+ continue;
+
+ if (memcmp(sha, shader_replacements[i].sha1, 40) != 0)
+ continue;
+
+ return load_shader_replacement(&shader_replacements[i]);
+ }
+
if (!path_exists)
return NULL;
@@ -2005,8 +2068,7 @@ _mesa_read_shader_source(const gl_shader_stage stage, const char *source)
return NULL;
}
- char *name = construct_name(stage, generate_sha1(source, sha),
- source, read_path);
+ char *name = construct_name(stage, sha, source, read_path);
f = fopen(name, "r");
ralloc_free(name);
if (!f)
diff --git a/src/mesa/program/prog_print.c b/src/mesa/program/prog_print.c
index 8e9b1def253..6d67eb42f1b 100644
--- a/src/mesa/program/prog_print.c
+++ b/src/mesa/program/prog_print.c
@@ -962,6 +962,7 @@ _mesa_print_parameter_list(const struct gl_program_parameter_list *list)
void
_mesa_write_shader_to_file(const struct gl_shader *shader)
{
+#ifndef CUSTOM_SHADER_REPLACEMENT
const char *type = "????";
char filename[100];
FILE *f;
@@ -1012,6 +1013,7 @@ _mesa_write_shader_to_file(const struct gl_shader *shader)
}
fclose(f);
+#endif
}
More information about the mesa-commit
mailing list