summaryrefslogtreecommitdiff
path: root/gdk-pixbuf/io-jpeg.c
diff options
context:
space:
mode:
authorHavoc Pennington <hp@redhat.com>2000-10-18 18:42:54 +0000
committerHavoc Pennington <hp@src.gnome.org>2000-10-18 18:42:54 +0000
commit7a4c68938789206bfec3c6d15cc4bb922daf6443 (patch)
treee5f031fc609e50a8b7b12e7d6abf63cc78cc88e7 /gdk-pixbuf/io-jpeg.c
parent7420908815651a1ff2ceb1c0fb5e92fe9b260619 (diff)
downloadgtk+-7a4c68938789206bfec3c6d15cc4bb922daf6443.tar.gz
Some updates
2000-10-18 Havoc Pennington <hp@redhat.com> * gtk/gtk-sections.txt: Some updates * gdk/gdk-sections.txt: remove GdkPixbufAlphaMode * gdk-pixbuf/gdk-pixbuf-sections.txt: Add new API, remove GdkPixbufClass/GdkAnimationClass since those are private * gdk-pixbuf/Makefile.am (IGNORE_HFILES): ignore more headers 2000-10-18 Havoc Pennington <hp@redhat.com> * gtk/gtktextiter.c (gtk_text_iter_forward_to_newline): Fix a bug where any number of empty lines would get skipped * gtk/gtktextiter.h: Remove padding from GtkTextIter; live on the edge. * gtk/gtktextiter.c (gtk_text_iter_make_surreal): enhance the warning about invalid iterators (explain more thoroughly) (gtk_text_iter_in_region): rename gtk_text_iter_in_range * gtk/gtktextview.c (FOCUS_EDGE_WIDTH): Make focus rectangle less big * demos/*.c: Add error handling * gtk/gtktextbuffer.c: don't modify const iterators * gtk/gdk-pixbuf-loader.c: Add full error handling here * gtk/gtkimage.c (gtk_image_set_from_file): ignore errors on file load * gtk/gtkiconfactory.c: Update to reflect addition of error handling to gdk-pixbuf loaders 2000-10-16 Havoc Pennington <hp@redhat.com> * gdk-pixbuf-io.c (gdk_pixbuf_get_module) (gdk_pixbuf_get_named_module) (gdk_pixbuf_load_module): add error reporting here also * make-inline-pixbuf.c (main): use GError * io-xpm.c: include unistd.h * gdk-pixbuf-util.c: include string.h * io-*.c: add error reporting * gdk-pixbuf-animation.c (gdk_pixbuf_animation_new_from_file): add error reporting * gdk-pixbuf-io.c (gdk_pixbuf_new_from_file): Add error reporting * gdk-pixbuf-io.h: Add GError** to load_increment and load methods * gdk-pixbuf-io.c (gdk_pixbuf_save) (gdk_pixbuf_savev): return a G_FILE_ERROR if we fail to write or close the file. * gdk-pixbuf.h: remove GDK_PIXBUF_ERROR_IO, instead we'll use G_FILE_ERROR_*. Rename enum to GdkPixbufError, properly following the GError naming rules. Add GError** to load functions.
Diffstat (limited to 'gdk-pixbuf/io-jpeg.c')
-rw-r--r--gdk-pixbuf/io-jpeg.c79
1 files changed, 62 insertions, 17 deletions
diff --git a/gdk-pixbuf/io-jpeg.c b/gdk-pixbuf/io-jpeg.c
index 623077738d..332de30c99 100644
--- a/gdk-pixbuf/io-jpeg.c
+++ b/gdk-pixbuf/io-jpeg.c
@@ -74,6 +74,7 @@ typedef my_source_mgr * my_src_ptr;
struct error_handler_data {
struct jpeg_error_mgr pub;
sigjmp_buf setjmp_buffer;
+ GError **error;
};
/* progressive loader context */
@@ -92,30 +93,51 @@ typedef struct {
struct error_handler_data jerr;
} JpegProgContext;
-GdkPixbuf *gdk_pixbuf__jpeg_image_load (FILE *f);
+GdkPixbuf *gdk_pixbuf__jpeg_image_load (FILE *f, GError **error);
gpointer gdk_pixbuf__jpeg_image_begin_load (ModulePreparedNotifyFunc func,
ModuleUpdatedNotifyFunc func2,
ModuleFrameDoneNotifyFunc func3,
ModuleAnimationDoneNotifyFunc func4,
- gpointer user_data);
+ gpointer user_data,
+ GError **error);
void gdk_pixbuf__jpeg_image_stop_load (gpointer context);
-gboolean gdk_pixbuf__jpeg_image_load_increment(gpointer context, guchar *buf, guint size);
+gboolean gdk_pixbuf__jpeg_image_load_increment(gpointer context, guchar *buf, guint size,
+ GError **error);
static void
fatal_error_handler (j_common_ptr cinfo)
{
- /* FIXME:
- * We should somehow signal what error occurred to the caller so the
- * caller can handle the error message */
struct error_handler_data *errmgr;
-
+ char buffer[JMSG_LENGTH_MAX];
+
errmgr = (struct error_handler_data *) cinfo->err;
- cinfo->err->output_message (cinfo);
+
+ /* Create the message */
+ (* cinfo->err->format_message) (cinfo, buffer);
+
+ /* broken check for *error == NULL for robustness against
+ * crappy JPEG library
+ */
+ if (errmgr->error && *errmgr->error == NULL) {
+ g_set_error (errmgr->error,
+ GDK_PIXBUF_ERROR,
+ GDK_PIXBUF_ERROR_CORRUPT_IMAGE,
+ _("Error interpreting JPEG image file (%s)"),
+ buffer);
+ }
+
siglongjmp (errmgr->setjmp_buffer, 1);
- /* incase the jmp buf isn't initted? */
- exit(1);
+ g_assert_not_reached ();
+}
+
+static void
+output_message_handler (j_common_ptr cinfo)
+{
+ /* This method keeps libjpeg from dumping crap to stderr */
+
+ /* do nothing */
}
/* Destroy notification function for the pixbuf */
@@ -158,7 +180,7 @@ explode_gray_into_buf (struct jpeg_decompress_struct *cinfo,
/* Shared library entry point */
GdkPixbuf *
-gdk_pixbuf__jpeg_image_load (FILE *f)
+gdk_pixbuf__jpeg_image_load (FILE *f, GError **error)
{
gint w, h, i;
guchar *pixels = NULL;
@@ -175,7 +197,10 @@ gdk_pixbuf__jpeg_image_load (FILE *f)
/* setup error handler */
cinfo.err = jpeg_std_error (&jerr.pub);
jerr.pub.error_exit = fatal_error_handler;
+ jerr.pub.output_message = output_message_handler;
+ jerr.error = error;
+
if (sigsetjmp (jerr.setjmp_buffer, 1)) {
/* Whoops there was a jpeg error */
if (pixels)
@@ -199,6 +224,17 @@ gdk_pixbuf__jpeg_image_load (FILE *f)
pixels = malloc (h * w * 3);
if (!pixels) {
jpeg_destroy_decompress (&cinfo);
+
+ /* broken check for *error == NULL for robustness against
+ * crappy JPEG library
+ */
+ if (error && *error == NULL) {
+ g_set_error (error,
+ GDK_PIXBUF_ERROR,
+ GDK_PIXBUF_ERROR_INSUFFICIENT_MEMORY,
+ _("Insufficient memory to load image, try exiting some applications to free memory"));
+ }
+
return NULL;
}
@@ -286,7 +322,8 @@ gdk_pixbuf__jpeg_image_begin_load (ModulePreparedNotifyFunc prepared_func,
ModuleUpdatedNotifyFunc updated_func,
ModuleFrameDoneNotifyFunc frame_func,
ModuleAnimationDoneNotifyFunc anim_done_func,
- gpointer user_data)
+ gpointer user_data,
+ GError **error)
{
JpegProgContext *context;
my_source_mgr *src;
@@ -308,7 +345,9 @@ gdk_pixbuf__jpeg_image_begin_load (ModulePreparedNotifyFunc prepared_func,
context->cinfo.err = jpeg_std_error (&context->jerr.pub);
context->jerr.pub.error_exit = fatal_error_handler;
-
+ context->jerr.pub.output_message = output_message_handler;
+ context->jerr.error = error;
+
src = (my_src_ptr) context->cinfo.src;
src->pub.init_source = init_source;
src->pub.fill_input_buffer = fill_input_buffer;
@@ -318,6 +357,8 @@ gdk_pixbuf__jpeg_image_begin_load (ModulePreparedNotifyFunc prepared_func,
src->pub.bytes_in_buffer = 0;
src->pub.next_input_byte = NULL;
+ context->jerr.error = NULL;
+
return (gpointer) context;
}
@@ -364,7 +405,8 @@ gdk_pixbuf__jpeg_image_stop_load (gpointer data)
* append image data onto inrecrementally built output image
*/
gboolean
-gdk_pixbuf__jpeg_image_load_increment (gpointer data, guchar *buf, guint size)
+gdk_pixbuf__jpeg_image_load_increment (gpointer data, guchar *buf, guint size,
+ GError **error)
{
JpegProgContext *context = (JpegProgContext *)data;
struct jpeg_decompress_struct *cinfo;
@@ -382,6 +424,8 @@ gdk_pixbuf__jpeg_image_load_increment (gpointer data, guchar *buf, guint size)
cinfo = &context->cinfo;
+ context->jerr.error = error;
+
/* XXXXXXX (drmike) - loop(s) below need to be recoded now I
* have a grasp of what the flow needs to be!
*/
@@ -641,12 +685,13 @@ gdk_pixbuf__jpeg_image_save (FILE *f,
g_return_val_if_fail (pixels != NULL, FALSE);
/* allocate a small buffer to convert image data */
- buf = malloc (w * 3 * sizeof (guchar));
- g_return_val_if_fail (buf != NULL, FALSE);
+ buf = g_malloc (w * 3 * sizeof (guchar));
/* set up error handling */
jerr.pub.error_exit = fatal_error_handler;
-
+ jerr.pub.output_message = output_message_handler;
+ jerr.error = error;
+
cinfo.err = jpeg_std_error (&(jerr.pub));
if (sigsetjmp (jerr.setjmp_buffer, 1)) {
jpeg_destroy_compress (&cinfo);