diff options
author | Campbell Barton <ideasman42@gmail.com> | 2011-08-31 03:08:38 +0400 |
---|---|---|
committer | Campbell Barton <ideasman42@gmail.com> | 2011-08-31 03:08:38 +0400 |
commit | c58a0c5eb814db1be08c0e8a4353ad5606a23d30 (patch) | |
tree | 8771cf76565345b4e56ab473be58ccd7e447a0a1 /source | |
parent | 5ac81bfe9c523c2ea0dcbc55bc8454c2e12239e0 (diff) |
catch exception and report an error when failing to write exr files - was crashing with debug builds.
Diffstat (limited to 'source')
-rw-r--r-- | source/blender/editors/space_image/image_ops.c | 2 | ||||
-rw-r--r-- | source/blender/imbuf/intern/openexr/openexr_api.cpp | 15 | ||||
-rw-r--r-- | source/blender/imbuf/intern/openexr/openexr_multi.h | 4 | ||||
-rw-r--r-- | source/blender/imbuf/intern/writeimage.c | 1 | ||||
-rw-r--r-- | source/blender/render/extern/include/RE_pipeline.h | 4 | ||||
-rw-r--r-- | source/blender/render/intern/source/pipeline.c | 39 |
6 files changed, 46 insertions, 19 deletions
diff --git a/source/blender/editors/space_image/image_ops.c b/source/blender/editors/space_image/image_ops.c index d58b78ff6a7..f96a8ea4d84 100644 --- a/source/blender/editors/space_image/image_ops.c +++ b/source/blender/editors/space_image/image_ops.c @@ -1069,7 +1069,7 @@ static void save_image_doit(bContext *C, SpaceImage *sima, wmOperator *op, SaveI Scene *scene= CTX_data_scene(C); RenderResult *rr= BKE_image_acquire_renderresult(scene, ima); if(rr) { - RE_WriteRenderResult(rr, simopts->filepath, simopts->quality); + RE_WriteRenderResult(op->reports, rr, simopts->filepath, simopts->quality); ok= TRUE; } else { diff --git a/source/blender/imbuf/intern/openexr/openexr_api.cpp b/source/blender/imbuf/intern/openexr/openexr_api.cpp index 7b528ed9624..88f6508d356 100644 --- a/source/blender/imbuf/intern/openexr/openexr_api.cpp +++ b/source/blender/imbuf/intern/openexr/openexr_api.cpp @@ -487,7 +487,7 @@ void IMB_exr_add_channel(void *handle, const char *layname, const char *passname } /* only used for writing temp. render results (not image files) */ -void IMB_exr_begin_write(void *handle, const char *filename, int width, int height, int compress) +int IMB_exr_begin_write(void *handle, const char *filename, int width, int height, int compress) { ExrHandle *data= (ExrHandle *)handle; Header header (width, height); @@ -504,8 +504,17 @@ void IMB_exr_begin_write(void *handle, const char *filename, int width, int heig /* header.lineOrder() = DECREASING_Y; this crashes in windows for file read! */ header.insert ("BlenderMultiChannel", StringAttribute ("Blender V2.55.1 and newer")); - - data->ofile = new OutputFile(filename, header); + + /* avoid crash/abort when we dont have permission to write here */ + try { + data->ofile = new OutputFile(filename, header); + } + catch (const std::exception &exc) { + std::cerr << "IMB_exr_begin_write: ERROR: " << exc.what() << std::endl; + data->ofile = NULL; + } + + return (data->ofile != NULL); } void IMB_exrtile_begin_write(void *handle, const char *filename, int mipmap, int width, int height, int tilex, int tiley) diff --git a/source/blender/imbuf/intern/openexr/openexr_multi.h b/source/blender/imbuf/intern/openexr/openexr_multi.h index 3d95bb7c306..58c5e0f2a3e 100644 --- a/source/blender/imbuf/intern/openexr/openexr_multi.h +++ b/source/blender/imbuf/intern/openexr/openexr_multi.h @@ -50,7 +50,7 @@ void * IMB_exr_get_handle (void); void IMB_exr_add_channel (void *handle, const char *layname, const char *passname, int xstride, int ystride, float *rect); int IMB_exr_begin_read (void *handle, const char *filename, int *width, int *height); -void IMB_exr_begin_write (void *handle, const char *filename, int width, int height, int compress); +int IMB_exr_begin_write (void *handle, const char *filename, int width, int height, int compress); void IMB_exrtile_begin_write (void *handle, const char *filename, int mipmap, int width, int height, int tilex, int tiley); void IMB_exr_set_channel (void *handle, const char *layname, const char *passname, int xstride, int ystride, float *rect); @@ -75,7 +75,7 @@ void * IMB_exr_get_handle (void) {return NULL;} void IMB_exr_add_channel (void *handle, const char *layname, const char *channame, int xstride, int ystride, float *rect) { (void)handle; (void)layname; (void)channame; (void)xstride; (void)ystride; (void)rect; } int IMB_exr_begin_read (void *handle, const char *filename, int *width, int *height) { (void)handle; (void)filename; (void)width; (void)height; return 0;} -void IMB_exr_begin_write (void *handle, const char *filename, int width, int height, int compress) { (void)handle; (void)filename; (void)width; (void)height; (void)compress; } +int IMB_exr_begin_write (void *handle, const char *filename, int width, int height, int compress) { (void)handle; (void)filename; (void)width; (void)height; (void)compress; return 0;} void IMB_exrtile_begin_write (void *handle, const char *filename, int mipmap, int width, int height, int tilex, int tiley) { (void)handle; (void)filename; (void)mipmap; (void)width; (void)height; (void)tilex; (void)tiley; } void IMB_exr_set_channel (void *handle, char *layname, const char *channame, int xstride, int ystride, float *rect) { (void)handle; (void)layname; (void)channame; (void)xstride; (void)ystride; (void)rect; } diff --git a/source/blender/imbuf/intern/writeimage.c b/source/blender/imbuf/intern/writeimage.c index cd660e11f26..b933e6d93ee 100644 --- a/source/blender/imbuf/intern/writeimage.c +++ b/source/blender/imbuf/intern/writeimage.c @@ -55,7 +55,6 @@ short IMB_saveiff(struct ImBuf *ibuf, const char *name, int flags) if(ibuf->rect==NULL && ibuf->rect_float) IMB_rect_from_float(ibuf); } - /* TODO. have const char for image write funcs */ return type->save(ibuf, name, flags); } } diff --git a/source/blender/render/extern/include/RE_pipeline.h b/source/blender/render/extern/include/RE_pipeline.h index 0736bed4faf..97ffcd95473 100644 --- a/source/blender/render/extern/include/RE_pipeline.h +++ b/source/blender/render/extern/include/RE_pipeline.h @@ -227,8 +227,8 @@ void RE_SetReports(struct Render *re, struct ReportList *reports); /* main preview render call */ void RE_PreviewRender(struct Render *re, struct Main *bmain, struct Scene *scene); -void RE_ReadRenderResult(struct Scene *scene, struct Scene *scenode); -void RE_WriteRenderResult(RenderResult *rr, const char *filename, int compress); +int RE_ReadRenderResult(struct Scene *scene, struct Scene *scenode); +int RE_WriteRenderResult(struct ReportList *reports, RenderResult *rr, const char *filename, int compress); struct RenderResult *RE_MultilayerConvert(void *exrhandle, int rectx, int recty); extern const float default_envmap_layout[]; diff --git a/source/blender/render/intern/source/pipeline.c b/source/blender/render/intern/source/pipeline.c index 0d5f8c77f6b..77b637b5129 100644 --- a/source/blender/render/intern/source/pipeline.c +++ b/source/blender/render/intern/source/pipeline.c @@ -824,11 +824,12 @@ static char *make_pass_name(RenderPass *rpass, int chan) /* filename already made absolute */ /* called from within UI, saves both rendered result as a file-read result */ -void RE_WriteRenderResult(RenderResult *rr, const char *filename, int compress) +int RE_WriteRenderResult(ReportList *reports, RenderResult *rr, const char *filename, int compress) { RenderLayer *rl; RenderPass *rpass; void *exrhandle= IMB_exr_get_handle(); + int success; BLI_make_existing_file(filename); @@ -864,11 +865,20 @@ void RE_WriteRenderResult(RenderResult *rr, const char *filename, int compress) } } } - - IMB_exr_begin_write(exrhandle, filename, rr->rectx, rr->recty, compress); - - IMB_exr_write_channels(exrhandle); + + /* when the filename has no permissions, this can fail */ + if(IMB_exr_begin_write(exrhandle, filename, rr->rectx, rr->recty, compress)) { + IMB_exr_write_channels(exrhandle); + success= TRUE; + } + else { + /* TODO, get the error from openexr's exception */ + BKE_report(reports, RPT_ERROR, "Error Writing Render Result, see console"); + success= FALSE; + } IMB_exr_close(exrhandle); + + return success; } /* callbacks for RE_MultilayerConvert */ @@ -992,9 +1002,10 @@ static int read_render_result_from_file(const char *filename, RenderResult *rr) } /* only for temp buffer files, makes exact copy of render result */ -static void read_render_result(Render *re, int sample) +static int read_render_result(Render *re, int sample) { char str[FILE_MAX]; + int success; BLI_rw_mutex_lock(&re->resultmutex, THREAD_LOCK_WRITE); @@ -1004,10 +1015,18 @@ static void read_render_result(Render *re, int sample) render_unique_exr_name(re, str, sample); printf("read exr tmp file: %s\n", str); - if(!read_render_result_from_file(str, re->result)) + if(read_render_result_from_file(str, re->result)) { + success= TRUE; + } + else { printf("cannot read: %s\n", str); + success= FALSE; + + } BLI_rw_mutex_unlock(&re->resultmutex); + + return success; } /* *************************************************** */ @@ -2981,7 +3000,7 @@ static int do_write_image_or_movie(Render *re, Scene *scene, bMovieHandle *mh, c if(re->r.imtype==R_MULTILAYER) { if(re->result) { - RE_WriteRenderResult(re->result, name, scene->r.quality); + RE_WriteRenderResult(re->reports, re->result, name, scene->r.quality); printf("Saved: %s", name); } } @@ -3198,7 +3217,7 @@ void RE_PreviewRender(Render *re, Main *bmain, Scene *sce) /* note; repeated win/disprect calc... solve that nicer, also in compo */ /* only the temp file! */ -void RE_ReadRenderResult(Scene *scene, Scene *scenode) +int RE_ReadRenderResult(Scene *scene, Scene *scenode) { Render *re; int winx, winy; @@ -3232,7 +3251,7 @@ void RE_ReadRenderResult(Scene *scene, Scene *scenode) RE_InitState(re, NULL, &scene->r, NULL, winx, winy, &disprect); re->scene= scene; - read_render_result(re, 0); + return read_render_result(re, 0); } void RE_set_max_threads(int threads) |