Second attempt to fix T40833: Crash when rendering with freestyle.

The cause of the crash was identified in an uninitialized member variable
`Main->lock`.  Now that struct Main has a few member variables whose
values are dynamically allocated, per-render Freestyle-specific Main data
structures will be allocated and released using `BKE_main_new()` and
`BKE_main_free()`, respectively.

This revision complements the commit rB6135556f4556.
This commit is contained in:
Tamito Kajiyama 2014-07-01 23:35:09 +09:00
parent 61e5f81e37
commit 6c6fa749f6
Notes: blender-bot 2023-02-14 10:25:57 +01:00
Referenced by issue #40833, Crash when rendering with freestyle
4 changed files with 29 additions and 14 deletions

View File

@ -58,7 +58,7 @@ namespace Freestyle {
BlenderStrokeRenderer::BlenderStrokeRenderer(Render *re, int render_count) : StrokeRenderer()
{
freestyle_bmain = &re->freestyle_bmain;
freestyle_bmain = re->freestyle_bmain;
// for stroke mesh generation
_width = re->winx;

View File

@ -577,7 +577,7 @@ void FRS_init_stroke_rendering(Render *re)
Render *FRS_do_stroke_rendering(Render *re, SceneRenderLayer *srl, int render)
{
Main bmain = {0};
Main *freestyle_bmain = re->freestyle_bmain;
Render *freestyle_render = NULL;
Text *text, *next_text;
@ -599,7 +599,7 @@ Render *FRS_do_stroke_rendering(Render *re, SceneRenderLayer *srl, int render)
// - add style modules
// - set parameters
// - compute view map
prepare(&bmain, re, srl);
prepare(freestyle_bmain, re, srl);
if (re->test_break(re->tbh)) {
controller->CloseFile();
@ -628,11 +628,11 @@ Render *FRS_do_stroke_rendering(Render *re, SceneRenderLayer *srl, int render)
}
// Free temp main (currently only text blocks are stored there)
for (text = (Text *) bmain.text.first; text; text = next_text) {
for (text = (Text *)freestyle_bmain->text.first; text; text = next_text) {
next_text = (Text *) text->id.next;
BKE_text_unlink(&bmain, text);
BKE_libblock_free(&bmain, text);
BKE_text_unlink(freestyle_bmain, text);
BKE_libblock_free(freestyle_bmain, text);
}
return freestyle_render;

View File

@ -240,7 +240,7 @@ struct Render
ListBase volumes;
#ifdef WITH_FREESTYLE
struct Main freestyle_bmain;
struct Main *freestyle_bmain;
ListBase freestyle_renders;
#endif

View File

@ -61,6 +61,7 @@
#include "BKE_depsgraph.h"
#include "BKE_global.h"
#include "BKE_image.h"
#include "BKE_library.h"
#include "BKE_main.h"
#include "BKE_modifier.h"
#include "BKE_node.h"
@ -1822,11 +1823,13 @@ static void tag_scenes_for_render(Render *re)
}
#ifdef WITH_FREESTYLE
for (sce = re->freestyle_bmain.scene.first; sce; sce = sce->id.next) {
sce->id.flag &= ~LIB_DOIT;
if (re->freestyle_bmain) {
for (sce = re->freestyle_bmain->scene.first; sce; sce = sce->id.next) {
sce->id.flag &= ~LIB_DOIT;
#ifdef DEPSGRAPH_WORKAROUND_HACK
tag_dependend_objects_for_render(sce, renderlay);
tag_dependend_objects_for_render(sce, renderlay);
#endif
}
}
#endif
@ -1928,6 +1931,8 @@ static void add_freestyle(Render *re, int render)
actsrl = BLI_findlink(&re->r.layers, re->r.actlay);
re->freestyle_bmain = BKE_main_new();
/* We use the same window manager for freestyle bmain as
* real bmain uses. This is needed because freestyle's
* bmain could be used to tag scenes for update, which
@ -1935,7 +1940,7 @@ static void add_freestyle(Render *re, int render)
* and that function requires proper window manager
* to present (sergey)
*/
re->freestyle_bmain.wm = re->main->wm;
re->freestyle_bmain->wm = re->main->wm;
FRS_init_stroke_rendering(re);
@ -2000,10 +2005,18 @@ static void free_all_freestyle_renders(void)
if (freestyle_render) {
freestyle_scene = freestyle_render->scene;
RE_FreeRender(freestyle_render);
BKE_scene_unlink(&re1->freestyle_bmain, freestyle_scene, NULL);
BKE_scene_unlink(re1->freestyle_bmain, freestyle_scene, NULL);
}
}
BLI_freelistN(&re1->freestyle_renders);
/* detach the window manager from freestyle bmain (see comments in
* add_freestyle() for more detail)
*/
re1->freestyle_bmain->wm.first = re1->freestyle_bmain->wm.last = NULL;
BKE_main_free(re1->freestyle_bmain);
re1->freestyle_bmain = NULL;
}
}
#endif
@ -2154,8 +2167,10 @@ void RE_MergeFullSample(Render *re, Main *bmain, Scene *sce, bNodeTree *ntree)
scene->id.flag |= LIB_DOIT;
#ifdef WITH_FREESTYLE
for (scene = re->freestyle_bmain.scene.first; scene; scene = scene->id.next)
scene->id.flag &= ~LIB_DOIT;
if (re->freestyle_bmain) {
for (scene = re->freestyle_bmain->scene.first; scene; scene = scene->id.next)
scene->id.flag &= ~LIB_DOIT;
}
#endif
for (node = ntree->nodes.first; node; node = node->next) {