diff options
author | Sean Fox <dyntryx@gmail.com> | 2008-06-22 17:17:04 +0000 |
---|---|---|
committer | Sean Fox <dyntryx@gmail.com> | 2008-06-22 17:17:04 +0000 |
commit | 419825572dbc3990ef4c7d29eb7205c8aaa0bf08 (patch) | |
tree | 6365b472ab99b1601e5692e3ab36d64846308f76 | |
parent | 8edc3daad7debb8e5d746c1b345c4de76c68a3a0 (diff) | |
download | libnsgif-419825572dbc3990ef4c7d29eb7205c8aaa0bf08.tar.gz libnsgif-419825572dbc3990ef4c7d29eb7205c8aaa0bf08.tar.bz2 |
Added consistency in the way block-data is skipped; corrected a buffering error that was causing some gif images to throw errors
svn path=/branches/dynis/libnsgif/; revision=4422
-rw-r--r-- | libnsgif.c | 54 |
1 files changed, 30 insertions, 24 deletions
@@ -450,24 +450,27 @@ int gif_initialise_frame(struct gif_animation *gif, gif_bitmap_callback_vt *bitm else gif_data += (3 + extension_size); - /* Skip all the sub-blocks + /* Repeatedly skip blocks until we get a zero block or run out of data + * This library does not process this data */ - while (gif_data[0] != 0x00) - gif_data += gif_data[0] + 1; - gif_data++; + block_size = 0; + while (block_size != 1) { + block_size = gif_data[0] + 1; + if ((gif_bytes -= block_size) < 0) + return GIF_INSUFFICIENT_FRAME_DATA; + gif_data += block_size; + } } /* Check if we've finished */ - gif_bytes = (gif_end - gif_data); - if (gif_bytes < 1) + if ((gif_bytes = (gif_end - gif_data)) < 1) return GIF_INSUFFICIENT_FRAME_DATA; - else - if (gif_data[0] == GIF_TRAILER) { - gif->buffer_position = gif_data - gif->gif_data; - gif->frame_count = frame + 1; - return 1; - } + else if (gif_data[0] == GIF_TRAILER) { + gif->buffer_position = gif_data - gif->gif_data; + gif->frame_count = frame + 1; + return 1; + } /* If we're not done, there should be an image descriptor */ @@ -549,8 +552,6 @@ int gif_initialise_frame(struct gif_animation *gif, gif_bitmap_callback_vt *bitm */ block_size = 0; while (block_size != 1) { - /* Skip the block data - */ block_size = gif_data[0] + 1; if ((gif_bytes -= block_size) < 0) return GIF_INSUFFICIENT_FRAME_DATA; @@ -700,17 +701,24 @@ int gif_decode_frame(struct gif_animation *gif, unsigned int frame, gif_bitmap_c gif_data += 2; else gif_data += (3 + extension_size); - - /* Skip all the sub-blocks + + /* Repeatedly skip blocks until we get a zero block or run out of data + * This library does not process this data */ - while (gif_data[0] != 0x00) - gif_data += gif_data[0] + 1; - gif_data++; + block_size = 0; + while (block_size != 1) { + block_size = gif_data[0] + 1; + if ((gif_bytes -= block_size) < 0) { + return_value = GIF_INSUFFICIENT_FRAME_DATA; + goto gif_decode_frame_exit; + } + gif_data += block_size; + } } /* Ensure we have enough data for the 10-byte image descriptor + 1-byte gif trailer */ - if ((gif_bytes = (gif_end - gif_data)) < 12) { + if (gif_bytes < 12) { return_value = GIF_INSUFFICIENT_FRAME_DATA; break; } @@ -876,8 +884,6 @@ int gif_decode_frame(struct gif_animation *gif, unsigned int frame, gif_bitmap_c gif_data = gif->gif_data + gif->buffer_size; block_size = 0; while (block_size != 1) { - /* Skip the block data - */ block_size = gif_data[0] + 1; if ((gif_bytes -= block_size) < 0) { return_value = GIF_INSUFFICIENT_FRAME_DATA; @@ -887,12 +893,12 @@ int gif_decode_frame(struct gif_animation *gif, unsigned int frame, gif_bitmap_c } } gif_decode_frame_exit: - /* Check for end of data */ + gif->buffer_position++; gif_bytes = gif->buffer_size - gif->buffer_position; + gif_data = gif->gif_data + gif->buffer_position; more_images &= !((gif_bytes < 1) || (gif_data[0] == GIF_TRAILER)); - gif->buffer_position++; } /* Check if we should test for optimisation |