From f03ac5ec4ba20f044fa8d09a2d8f6533790d4dc8 Mon Sep 17 00:00:00 2001 From: Brecht Van Lommel Date: Mon, 28 Jul 2025 18:43:57 +0200 Subject: [PATCH] Fix #142876: Cycles crash with OSL and interactive updates Update use_shading, use_camera and the shading system pointers in the same location, so that when the render is interrupted they are in a consistent state. The added null pointer checks are not strictly needed, but just in case it goes out of sync for another reason. Pull Request: https://projects.blender.org/blender/blender/pulls/143467 --- intern/cycles/kernel/osl/globals.cpp | 10 +++++++--- intern/cycles/scene/osl.cpp | 15 +++++++++++---- intern/cycles/scene/osl.h | 3 +-- 3 files changed, 19 insertions(+), 9 deletions(-) diff --git a/intern/cycles/kernel/osl/globals.cpp b/intern/cycles/kernel/osl/globals.cpp index 8fc0913326d..9853cd2d1b9 100644 --- a/intern/cycles/kernel/osl/globals.cpp +++ b/intern/cycles/kernel/osl/globals.cpp @@ -23,9 +23,13 @@ OSLThreadData::OSLThreadData(OSLGlobals *osl_globals, const int thread_index) memset((void *)&shader_globals, 0, sizeof(shader_globals)); shader_globals.tracedata = &tracedata; - osl_thread_info = ss->create_thread_info(); - context = ss->get_context(osl_thread_info); - oiio_thread_info = globals->ts->get_perthread_info(); + if (ss) { + osl_thread_info = ss->create_thread_info(); + context = ss->get_context(osl_thread_info); + } + if (globals->ts) { + oiio_thread_info = globals->ts->get_perthread_info(); + } } OSLThreadData::~OSLThreadData() diff --git a/intern/cycles/scene/osl.cpp b/intern/cycles/scene/osl.cpp index bf81f044bcf..28e9d590ea1 100644 --- a/intern/cycles/scene/osl.cpp +++ b/intern/cycles/scene/osl.cpp @@ -173,6 +173,10 @@ void OSLManager::device_update_post(Device *device, ss->Shader(*group, "shader", scene->camera->script_name, "camera"); ss->ShaderGroupEnd(*group); + og->ss = ss; + og->ts = get_texture_system(); + og->services = static_cast(ss->renderer()); + og->camera_state = group; og->use_camera = true; @@ -275,11 +279,9 @@ void OSLManager::device_free(Device *device, DeviceScene * /*dscene*/, Scene *sc /* clear shader engine */ foreach_osl_device(device, [](Device *, OSLGlobals *og) { og->use_shading = false; + og->use_camera = false; og->ss = nullptr; og->ts = nullptr; - - og->use_shading = false; - og->use_camera = false; og->camera_state.reset(); }); @@ -631,7 +633,12 @@ void OSLShaderManager::device_update_specific(Device *device, LOG_INFO << "Total " << scene->shaders.size() << " shaders."; /* setup shader engine */ - OSLManager::foreach_osl_device(device, [](Device *, OSLGlobals *og) { + OSLManager::foreach_osl_device(device, [scene](Device *sub_device, OSLGlobals *og) { + OSL::ShadingSystem *ss = scene->osl_manager->get_shading_system(sub_device); + og->ss = ss; + og->ts = scene->osl_manager->get_texture_system(); + og->services = static_cast(ss->renderer()); + og->use_shading = true; og->surface_state.clear(); diff --git a/intern/cycles/scene/osl.h b/intern/cycles/scene/osl.h index 5eaf377b6ae..f3865aba6ee 100644 --- a/intern/cycles/scene/osl.h +++ b/intern/cycles/scene/osl.h @@ -80,6 +80,7 @@ class OSLManager { OSLShaderInfo *shader_loaded_info(const string &hash); OSL::ShadingSystem *get_shading_system(Device *sub_device); + OSL::TextureSystem *get_texture_system(); static void foreach_osl_device(Device *device, const std::function &callback); #endif @@ -98,8 +99,6 @@ class OSLManager { void foreach_shading_system(const std::function &callback); void foreach_render_services(const std::function &callback); - OSL::TextureSystem *get_texture_system(); - Device *device_; map loaded_shaders;