Skip to content

Commit

Permalink
fix a crash with heavy use of draw
Browse files Browse the repository at this point in the history
we were leaving a few bits of the original image around after
vips_image_copy_memory(), including the progress signal ... if earlier images
were freed, perhaps by a GC in a language binding, we could get a dangling
pointer

thanks Nakilon, see libvips/ruby-vips#140
  • Loading branch information
jcupitt committed Oct 9, 2017
1 parent 653e99e commit 6f16a9d
Show file tree
Hide file tree
Showing 2 changed files with 34 additions and 4 deletions.
2 changes: 2 additions & 0 deletions ChangeLog
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
29/8/17 started 8.5.9
- make --fail stop jpeg read on any libjpeg warning, thanks @mceachen
- don't build enumtypes so often, removing perl as a compile dependancy
- fix a crash with havy use of draw operations from language bindings,
thanks @Nakilon

2/8/17 started 8.5.8
- fix transparency detection in merge, thanks Haida
Expand Down
36 changes: 32 additions & 4 deletions libvips/iofuncs/image.c
Original file line number Diff line number Diff line change
Expand Up @@ -2458,6 +2458,8 @@ vips_image_write( VipsImage *image, VipsImage *out )
g_object_ref( image );
vips_object_local( out, image );
}
else {
}

return( 0 );
}
Expand Down Expand Up @@ -3010,6 +3012,9 @@ VipsImage *
vips_image_copy_memory( VipsImage *image )
{
VipsImage *new;
VipsImage *image_array[2];
size_t length;
void *data;

switch( image->dtype ) {
case VIPS_IMAGE_SETBUF:
Expand All @@ -3025,13 +3030,36 @@ vips_image_copy_memory( VipsImage *image )
case VIPS_IMAGE_OPENOUT:
case VIPS_IMAGE_OPENIN:
case VIPS_IMAGE_PARTIAL:
/* Copy to a new memory image.
/* We don't use vips_image_new_memory() and vips_image_write()
* since we want to make a break in the pipeline and we want
* to avoid all the machinery around reordering and dependancy
* links.
*
* We especially want to be able to unref input and have output
* survive. Things like the progress signal must be cleared,
* for example.
*/
new = vips_image_new_memory();
if( vips_image_write( image, new ) ) {
g_object_unref( new );

/* Write to a new memory image.
*/
if( !(data = vips_image_write_to_memory( image, &length )) )
return( NULL );
if( !(new = vips_image_new_from_memory( data, length,
image->Xsize, image->Ysize, image->Bands,
image->BandFmt )) ) {
g_free( data );
return( NULL );
}

/* Copy over other fields and the metadata.
*/
image_array[0] = image;
image_array[1] = NULL;
if( vips__image_copy_fields_array( new, image_array ) ) {
VIPS_UNREF( new );
return( NULL );
}

break;

default:
Expand Down

0 comments on commit 6f16a9d

Please sign in to comment.