From aa62c1b5d1d57977442786b7676ea3f36b4ffe33 Mon Sep 17 00:00:00 2001 From: Hans Goudey Date: Sun, 3 Nov 2024 10:48:39 +0100 Subject: [PATCH] Fix #129741: Two issues creating GPU shader from Python 1. Log printing casted a span of `StringRefNull` to a span of `char **` 2. Creating the shader tried to create `StringRefNull` from `nullptr`. --- source/blender/gpu/intern/gpu_shader_log.cc | 11 ++++++----- source/blender/python/gpu/gpu_py_shader.cc | 20 ++++++++++++++------ 2 files changed, 20 insertions(+), 11 deletions(-) diff --git a/source/blender/gpu/intern/gpu_shader_log.cc b/source/blender/gpu/intern/gpu_shader_log.cc index 6b8a9c49a1d..01ef65dc1aa 100644 --- a/source/blender/gpu/intern/gpu_shader_log.cc +++ b/source/blender/gpu/intern/gpu_shader_log.cc @@ -21,6 +21,8 @@ #include "CLG_log.h" +#include "fmt/format.h" + static CLG_LogRef LOG = {"gpu.shader"}; namespace blender::gpu { @@ -48,7 +50,7 @@ void Shader::print_log(Span sources, char warn_col[] = "\033[33;1m"; char info_col[] = "\033[0;2m"; char reset_col[] = "\033[0;0m"; - char *sources_combined = BLI_string_join_arrayN((const char **)sources.data(), sources.size()); + std::string sources_combined = fmt::to_string(fmt::join(sources, "")); DynStr *dynstr = BLI_dynstr_new(); if (!CLG_color_support_get(&LOG)) { @@ -106,7 +108,7 @@ void Shader::print_log(Span sources, } GPULogItem log_item; - log_line = parser->parse_line(sources_combined, log_line, log_item); + log_line = parser->parse_line(sources_combined.c_str(), log_line, log_item); /* Empty line, skip. */ if ((log_item.cursor.row == -1) && ELEM(log_line[0], '\n', '\0')) { @@ -126,7 +128,7 @@ void Shader::print_log(Span sources, found_line_id = false; } - const char *src_line = sources_combined; + const char *src_line = sources_combined.c_str(); /* Separate from previous block. */ if (previous_location.source != log_item.cursor.source || @@ -251,14 +253,13 @@ void Shader::print_log(Span sources, (severity >= CLG_SEVERITY_WARN)) { if (DEBUG_LOG_SHADER_SRC_ON_ERROR && error) { - CLG_log_str(LOG.type, severity, this->name, stage, sources_combined); + CLG_log_str(LOG.type, severity, this->name, stage, sources_combined.c_str()); } const char *_str = BLI_dynstr_get_cstring(dynstr); CLG_log_str(LOG.type, severity, this->name, stage, _str); MEM_freeN((void *)_str); } - MEM_freeN(sources_combined); BLI_dynstr_free(dynstr); } diff --git a/source/blender/python/gpu/gpu_py_shader.cc b/source/blender/python/gpu/gpu_py_shader.cc index db2e6f1c589..f9f4928e815 100644 --- a/source/blender/python/gpu/gpu_py_shader.cc +++ b/source/blender/python/gpu/gpu_py_shader.cc @@ -97,6 +97,14 @@ static int pygpu_shader_uniform_location_get(GPUShader *shader, /** \name Shader Type * \{ */ +static std::optional c_str_to_stringref_opt(const char *str) +{ + if (!str) { + return std::nullopt; + } + return blender::StringRefNull(str); +} + static PyObject *pygpu_shader__tp_new(PyTypeObject * /*type*/, PyObject *args, PyObject *kwds) { BPYGPU_IS_INIT_OR_ERROR_OBJ; @@ -138,12 +146,12 @@ static PyObject *pygpu_shader__tp_new(PyTypeObject * /*type*/, PyObject *args, P return nullptr; } - GPUShader *shader = GPU_shader_create_from_python(params.vertexcode, - params.fragcode, - params.geocode, - params.libcode, - params.defines, - params.name); + GPUShader *shader = GPU_shader_create_from_python(c_str_to_stringref_opt(params.vertexcode), + c_str_to_stringref_opt(params.fragcode), + c_str_to_stringref_opt(params.geocode), + c_str_to_stringref_opt(params.libcode), + c_str_to_stringref_opt(params.defines), + c_str_to_stringref_opt(params.name)); if (shader == nullptr) { PyErr_SetString(PyExc_Exception, "Shader Compile Error, see console for more details");