Fix T39985: crash while rendering a scene with compositing nodes using another scene
authorSergey Sharybin <sergey.vfx@gmail.com>
Fri, 2 May 2014 12:52:19 +0000 (14:52 +0200)
committerSergey Sharybin <sergey.vfx@gmail.com>
Fri, 2 May 2014 12:54:13 +0000 (14:54 +0200)
The issue was caused by the wrong scene used to acquire render result for.

Now made it so render pipeline reports currently rendering scene to the job
via special callback.

This also solves missing tile highlight issue when rendering multiple scenes
in the compositor.

source/blender/editors/render/render_internal.c
source/blender/render/extern/include/RE_pipeline.h
source/blender/render/intern/include/render_types.h
source/blender/render/intern/source/envmap.c
source/blender/render/intern/source/pipeline.c

index 73d52dc5782abc8930307977ef8ff074fc7d9d39..9fa312884da2ed5b9b2b99aa8935844a98677281 100644 (file)
@@ -95,6 +95,7 @@ static int render_break(void *rjv);
 typedef struct RenderJob {
        Main *main;
        Scene *scene;
+       Scene *current_scene;
        Render *re;
        SceneRenderLayer *srl;
        struct Object *camera_override;
@@ -562,6 +563,13 @@ static void image_rect_update(void *rjv, RenderResult *rr, volatile rcti *renrec
        BKE_image_release_ibuf(ima, ibuf, lock);
 }
 
+static void current_scene_update(void *rjv, Scene *scene)
+{
+       RenderJob *rj = rjv;
+       rj->current_scene = scene;
+       rj->iuser.scene = scene;
+}
+
 static void render_startjob(void *rjv, short *stop, short *do_update, float *progress)
 {
        RenderJob *rj = rjv;
@@ -866,6 +874,7 @@ static int screen_render_invoke(bContext *C, wmOperator *op, const wmEvent *even
        rj = MEM_callocN(sizeof(RenderJob), "render job");
        rj->main = mainp;
        rj->scene = scene;
+       rj->current_scene = rj->scene;
        rj->srl = srl;
        rj->camera_override = camera_override;
        rj->lay_override = 0;
@@ -938,6 +947,7 @@ static int screen_render_invoke(bContext *C, wmOperator *op, const wmEvent *even
        RE_test_break_cb(re, rj, render_breakjob);
        RE_draw_lock_cb(re, rj, render_drawlock);
        RE_display_update_cb(re, rj, image_rect_update);
+       RE_current_scene_update_cb(re, rj, current_scene_update);
        RE_stats_draw_cb(re, rj, image_renderinfo_cb);
        RE_progress_cb(re, rj, render_progress_update);
 
@@ -1481,7 +1491,7 @@ Scene *ED_render_job_get_scene(const bContext *C)
        RenderJob *rj = (RenderJob *)WM_jobs_customdata_from_type(wm, WM_JOB_TYPE_RENDER);
        
        if (rj)
-               return rj->scene;
+               return rj->current_scene;
        
        return NULL;
 }
index 6d994b36f26ca88136c29225d20964f2e91d9d83..031d6b5a51a96f0f3446159d6f346333ef346dd9 100644 (file)
@@ -257,6 +257,7 @@ void RE_stats_draw_cb       (struct Render *re, void *handle, void (*f)(void *handle,
 void RE_progress_cb    (struct Render *re, void *handle, void (*f)(void *handle, float));
 void RE_draw_lock_cb           (struct Render *re, void *handle, void (*f)(void *handle, int));
 void RE_test_break_cb  (struct Render *re, void *handle, int (*f)(void *handle));
+void RE_current_scene_update_cb(struct Render *re, void *handle, void (*f)(void *handle, struct Scene *scene));
 
 /* should move to kernel once... still unsure on how/where */
 float RE_filter_value(int type, float x);
index cfebddeba7c905f380f0928a513f70790a61d87d..eeb0544cf73f7a75bafe150ba3152df96b66bc0b 100644 (file)
@@ -256,6 +256,8 @@ struct Render
        void *dch;
        void (*display_update)(void *handle, RenderResult *rr, volatile rcti *rect);
        void *duh;
+       void (*current_scene_update)(void *handle, struct Scene *scene);
+       void *suh;
        
        void (*stats_draw)(void *handle, RenderStats *ri);
        void *sdh;
index 52ebfd07a5460b2d5afc8f817edab95142ae037f..28b29261e4e1f3a30199fb9c71ef34cf3bf05124 100644 (file)
@@ -167,6 +167,8 @@ static Render *envmap_render_copy(Render *re, EnvMap *env)
        envre->duh = re->duh;
        envre->test_break = re->test_break;
        envre->tbh = re->tbh;
+       envre->current_scene_update = re->current_scene_update;
+       envre->suh = re->suh;
        
        /* and for the evil stuff; copy the database... */
        envre->totvlak = re->totvlak;
index 36945e7081e513614fd01ca8339a0bda2152b664..232f9db1c65dc90bb69661a156f7f57068561779 100644 (file)
@@ -142,6 +142,7 @@ static int thread_break(void *UNUSED(arg))
 /* default callbacks, set in each new render */
 static void result_nothing(void *UNUSED(arg), RenderResult *UNUSED(rr)) {}
 static void result_rcti_nothing(void *UNUSED(arg), RenderResult *UNUSED(rr), volatile struct rcti *UNUSED(rect)) {}
+static void current_scene_nothing(void *UNUSED(arg), Scene *UNUSED(scene)) {}
 static void stats_nothing(void *UNUSED(arg), RenderStats *UNUSED(rs)) {}
 static void float_nothing(void *UNUSED(arg), float UNUSED(val)) {}
 static int default_break(void *UNUSED(arg)) { return G.is_break == true; }
@@ -393,6 +394,7 @@ void RE_InitRenderCB(Render *re)
        re->display_init = result_nothing;
        re->display_clear = result_nothing;
        re->display_update = result_rcti_nothing;
+       re->current_scene_update = current_scene_nothing;
        re->progress = float_nothing;
        re->test_break = default_break;
        if (G.background)
@@ -737,6 +739,11 @@ void RE_display_update_cb(Render *re, void *handle, void (*f)(void *handle, Rend
        re->display_update = f;
        re->duh = handle;
 }
+void RE_current_scene_update_cb(Render *re, void *handle, void (*f)(void *handle, Scene *scene))
+{
+       re->current_scene_update = f;
+       re->suh = handle;
+}
 void RE_stats_draw_cb(Render *re, void *handle, void (*f)(void *handle, RenderStats *rs))
 {
        re->stats_draw = f;
@@ -1188,6 +1195,8 @@ static void do_render_3d(Render *re)
 {
        int cfra_backup;
 
+       re->current_scene_update(re->suh, re->scene);
+
        /* try external */
        if (RE_engine_render(re, 0))
                return;
@@ -1593,6 +1602,8 @@ static void render_scene(Render *re, Scene *sce, int cfra)
        resc->tbh = re->tbh;
        resc->stats_draw = re->stats_draw;
        resc->sdh = re->sdh;
+       resc->current_scene_update = re->current_scene_update;
+       resc->suh = re->suh;
        
        do_render_fields_blur_3d(resc);
 }
@@ -2293,6 +2304,8 @@ static void do_render_seq(Render *re)
 /* main loop: doing sequence + fields + blur + 3d render + compositing */
 static void do_render_all_options(Render *re)
 {
+       re->current_scene_update(re->suh, re->scene);
+
        BKE_scene_camera_switch_update(re->scene);
 
        re->i.starttime = PIL_check_seconds_timer();