diff options
author | Dominic Lachowicz <domlachowicz@gmail.com> | 2008-09-18 14:30:43 +0000 |
---|---|---|
committer | Dom Lachowicz <doml@src.gnome.org> | 2008-09-18 14:30:43 +0000 |
commit | b559c7dacc4a7f8ee0e525192775eac5207e3cc4 (patch) | |
tree | 1521ef4cf2cc22f4d2fb4fd9f9b2248589a72ea0 /gdk-pixbuf | |
parent | 08e3627b2e382d14df2b49a223b596f2510a1862 (diff) | |
download | gdk-pixbuf-b559c7dacc4a7f8ee0e525192775eac5207e3cc4.tar.gz |
Fix 2 cases where we leaked a GpImage (#552545)
2008-09-18 Dominic Lachowicz <domlachowicz@gmail.com>
* io-gdip-utils.c: Fix 2 cases where we leaked a GpImage (#552545)
svn path=/trunk/; revision=21426
Diffstat (limited to 'gdk-pixbuf')
-rw-r--r-- | gdk-pixbuf/ChangeLog | 4 | ||||
-rw-r--r-- | gdk-pixbuf/io-gdip-native.h | 29 | ||||
-rw-r--r-- | gdk-pixbuf/io-gdip-utils.c | 27 |
3 files changed, 55 insertions, 5 deletions
diff --git a/gdk-pixbuf/ChangeLog b/gdk-pixbuf/ChangeLog index 1000313c9..619dddded 100644 --- a/gdk-pixbuf/ChangeLog +++ b/gdk-pixbuf/ChangeLog @@ -1,3 +1,7 @@ +2008-09-18 Dominic Lachowicz <domlachowicz@gmail.com> + + * io-gdip-utils.c: Fix 2 cases where we leaked a GpImage (#552545) + 2008-09-17 Matthias Clasen <mclasen@redhat.com> * === Released 2.14.2 === diff --git a/gdk-pixbuf/io-gdip-native.h b/gdk-pixbuf/io-gdip-native.h index f5787ea83..24ea824f4 100644 --- a/gdk-pixbuf/io-gdip-native.h +++ b/gdk-pixbuf/io-gdip-native.h @@ -188,6 +188,26 @@ struct _ImageCodecInfo }; typedef struct _ImageCodecInfo ImageCodecInfo; +struct _BitmapData +{ + UINT Width; + UINT Height; + INT Stride; + PixelFormat PixelFormat; + VOID* Scan0; + UINT_PTR Reserved; +}; +typedef struct _BitmapData BitmapData; + +struct _GpRect +{ + INT X; + INT Y; + INT Width; + INT Height; +}; +typedef struct _GpRect GpRect; + #ifndef IStream_Release #define IStream_Release(This) (This)->lpVtbl->Release(This) #endif @@ -200,6 +220,10 @@ typedef struct _ImageCodecInfo ImageCodecInfo; #define IStream_Read(This,pv,cb,pcbRead) (This)->lpVtbl->Read(This,pv,cb,pcbRead) #endif +#ifndef IStream_SetSize +#define IStream_SetSize(This,size) (This)->lpVtbl->SetSize(This,size) +#endif + typedef GpStatus (WINGDIPAPI* GdiplusStartupFunc) (gpointer, const gpointer, gpointer); typedef GpStatus (WINGDIPAPI* GdipCreateBitmapFromStreamFunc) (gpointer, GpBitmap**); typedef GpStatus (WINGDIPAPI* GdipBitmapGetPixelFunc) (GpBitmap*, gint x, gint y, ARGB*); @@ -232,4 +256,9 @@ typedef GpStatus (WINGDIPAPI* GdipGetImageVerticalResolutionFunc) (GpImage *imag typedef GpStatus (WINGDIPAPI* GdipLoadImageFromStreamFunc) (IStream* stream, GpImage **image); typedef GpStatus (WINGDIPAPI* GdipDeleteGraphicsFunc) (GpGraphics *graphics); +typedef GpStatus (WINGDIPAPI* GdipBitmapLockBitsFunc) (GpBitmap* bitmap, const GpRect* rect, UINT flags, PixelFormat format, BitmapData* lockedBitmapData); +typedef GpStatus (WINGDIPAPI* GdipBitmapUnlockBitsFunc) (GpBitmap* bitmap, BitmapData* lockedBitmapData); +typedef GpStatus (WINGDIPAPI* GdipGetImagePixelFormatFunc) (GpImage *image, PixelFormat *format); +typedef GpStatus (WINGDIPAPI* GdipCloneBitmapAreaIFunc) (INT x, INT y, INT width, INT height, PixelFormat format, GpBitmap *srcBitmap, GpBitmap **dstBitmap); + #endif diff --git a/gdk-pixbuf/io-gdip-utils.c b/gdk-pixbuf/io-gdip-utils.c index 74a0f1758..935372516 100644 --- a/gdk-pixbuf/io-gdip-utils.c +++ b/gdk-pixbuf/io-gdip-utils.c @@ -58,6 +58,10 @@ static GdipLoadImageFromStreamFunc GdipLoadImageFromStream; static GdipDeleteGraphicsFunc GdipDeleteGraphics; static GdipGetImageEncodersFunc GdipGetImageEncoders; static GdipGetImageEncodersSizeFunc GdipGetImageEncodersSize; +static GdipBitmapLockBitsFunc GdipBitmapLockBits; +static GdipBitmapUnlockBitsFunc GdipBitmapUnlockBits; +static GdipGetImagePixelFormatFunc GdipGetImagePixelFormat; +static GdipCloneBitmapAreaIFunc GdipCloneBitmapAreaI; DEFINE_GUID(FrameDimensionTime, 0x6aedbd6d,0x3fb5,0x418a,0x83,0xa6,0x7f,0x45,0x22,0x9d,0xc8,0x72); DEFINE_GUID(FrameDimensionPage, 0x7462dc86,0x6180,0x4c7e,0x8e,0x3f,0xee,0x73,0x33,0xa7,0xa4,0x83); @@ -161,6 +165,10 @@ gdip_init (void) LOOKUP (GdipDeleteGraphics); LOOKUP (GdipGetImageEncoders); LOOKUP (GdipGetImageEncodersSize); + LOOKUP (GdipBitmapLockBits); + LOOKUP (GdipBitmapUnlockBits); + LOOKUP (GdipGetImagePixelFormat); + LOOKUP (GdipCloneBitmapAreaI); #undef LOOKUP @@ -338,12 +346,14 @@ gdip_buffer_to_bitmap (const gchar *buffer, size_t size, GError **error) GpBitmap *bitmap = NULL; IStream *stream = NULL; GpStatus status; + guint64 size64 = size; hg = gdip_buffer_to_hglobal (buffer, size, error); if (!hg) return NULL; + IStream_SetSize (stream, *(ULARGE_INTEGER *)&size64); hr = CreateStreamOnHGlobal (hg, FALSE, (LPSTREAM *)&stream); if (!SUCCEEDED (hr)) { @@ -371,6 +381,7 @@ gdip_buffer_to_image (const gchar *buffer, size_t size, GError **error) GpImage *image = NULL; IStream *stream = NULL; GpStatus status; + guint64 size64 = size; hg = gdip_buffer_to_hglobal (buffer, size, error); @@ -385,6 +396,7 @@ gdip_buffer_to_image (const gchar *buffer, size_t size, GError **error) return NULL; } + IStream_SetSize (stream, *(ULARGE_INTEGER *)&size64); status = GdipLoadImageFromStream (stream, &image); if (Ok != status) @@ -651,7 +663,7 @@ gdk_pixbuf__gdip_image_load_increment (gpointer data, } static GdkPixbuf * -gdip_bitmap_to_pixbuf (GpBitmap *bitmap) +gdip_bitmap_to_pixbuf (GpBitmap *bitmap, GError **error) { GdkPixbuf *pixbuf = NULL; guchar *cursor = NULL; @@ -667,8 +679,10 @@ gdip_bitmap_to_pixbuf (GpBitmap *bitmap) pixbuf = gdk_pixbuf_new (GDK_COLORSPACE_RGB, has_alpha, 8, width, height); - if (!pixbuf) + if (!pixbuf) { + g_set_error_literal (error, GDK_PIXBUF_ERROR, GDK_PIXBUF_ERROR_INSUFFICIENT_MEMORY, _("Couldn't load bitmap")); return NULL; + } rowstride = gdk_pixbuf_get_rowstride (pixbuf); cursor = gdk_pixbuf_get_pixels (pixbuf); @@ -677,9 +691,11 @@ gdip_bitmap_to_pixbuf (GpBitmap *bitmap) for (y = 0; y < height; y++) { for (x = 0; x < width; x++) { ARGB pixel; + GpStatus status; guchar *b = cursor + (y * rowstride + (x * n_channels)); - if (Ok != GdipBitmapGetPixel (bitmap, x, y, &pixel)) { + if (Ok != (status = GdipBitmapGetPixel (bitmap, x, y, &pixel))) { + gdip_set_error_from_gpstatus (error, GDK_PIXBUF_ERROR_FAILED, status); g_object_unref (pixbuf); return NULL; } @@ -726,14 +742,14 @@ stop_load (GpBitmap *bitmap, GdipContext *context, GError **error) gdip_bitmap_select_frame (bitmap, i, TRUE); - pixbuf = gdip_bitmap_to_pixbuf (bitmap); + pixbuf = gdip_bitmap_to_pixbuf (bitmap, error); if (!pixbuf) { if (animation != NULL) g_object_unref (G_OBJECT (animation)); + GdipDisposeImage ((GpImage *)bitmap); destroy_gdipcontext (context); - g_set_error_literal (error, GDK_PIXBUF_ERROR, GDK_PIXBUF_ERROR_INSUFFICIENT_MEMORY, _("Couldn't create pixbuf")); return FALSE; } @@ -779,6 +795,7 @@ stop_load (GpBitmap *bitmap, GdipContext *context, GError **error) if (animation != NULL) g_object_unref (G_OBJECT (animation)); + GdipDisposeImage ((GpImage *)bitmap); destroy_gdipcontext (context); return TRUE; |