diff --git a/src/file/gif/format.c b/src/file/gif/format.c index c31d47312..4b6e78e70 100644 --- a/src/file/gif/format.c +++ b/src/file/gif/format.c @@ -1,3 +1,4 @@ +#include #include #include #include @@ -65,6 +66,7 @@ read_palette (FILE * file, GIF_PALETTE *palette) static int lzw_read_pixel (int pos, unsigned char *data) { unsigned char *bitmap = data; + assert(pos >= 0); return bitmap[pos]; } @@ -73,6 +75,8 @@ static int lzw_read_pixel (int pos, unsigned char *data) static void lzw_write_pixel (int pos, int c, unsigned char *data) { unsigned char *bitmap = data; + assert(pos >= 0); + assert(c >= 0 && c <= 255); bitmap[pos] = c; } @@ -272,6 +276,8 @@ load_object (FILE * file, long size, void (*progress) (void *, float), void *dp) frame.yoff = fgetw (file); w = fgetw (file); h = fgetw (file); + if (w < 1 || h < 1) + goto error; bmp = calloc (w, h); if (!bmp) goto error; @@ -293,7 +299,8 @@ load_object (FILE * file, long size, void (*progress) (void *, float), void *dp) if (i & 64) interlaced = 1; - if (LZW_decode (file, lzw_write_pixel, bmp)) + if (ferror (file) || + LZW_decode (file, lzw_write_pixel, bmp)) goto error; if (interlaced) diff --git a/src/file/gif/lzw.c b/src/file/gif/lzw.c index d28e92c76..c2616bceb 100644 --- a/src/file/gif/lzw.c +++ b/src/file/gif/lzw.c @@ -60,8 +60,8 @@ write_code (FILE * file, unsigned char *buf, int *bit_pos, int bit_size, int cod int LZW_decode (FILE * file, - void (*write_pixel)(int pos, int code, unsigned char *data), - unsigned char *data) + void (*write_pixel)(int pos, int code, unsigned char *data), + unsigned char *data) { unsigned char buf[256]; int orig_bit_size; @@ -98,12 +98,12 @@ LZW_decode (FILE * file, /* Expect to read clear code as first code here. */ prev = read_code (file, buf, &bit_pos, bit_size); - if (prev == -1) + if (prev == -1 || ferror (file)) return -1; do { code = read_code (file, buf, &bit_pos, bit_size); - if (code == -1) + if (code == -1 || ferror (file)) return -1; if (code == clear_marker) { @@ -126,9 +126,13 @@ LZW_decode (FILE * file, /* Output the code. */ out_pos += codes[c].len; + i = 0; do { + if (out_pos - i < 0) + return -1; + write_pixel (out_pos - i, codes[c].c, data); if (codes[c].len) c = codes[c].prefix; @@ -171,7 +175,7 @@ LZW_decode (FILE * file, static int get_minimum_bitsize (int (*read_pixel)(int pos, unsigned char *data), - int size, unsigned char *data) + int size, unsigned char *data) { int i, max = 0, b = 2; for (i = 0; i < size; i++) @@ -189,7 +193,7 @@ get_minimum_bitsize (int (*read_pixel)(int pos, unsigned char *data), void LZW_encode (FILE * file, int (*read_pixel)(int pos, unsigned char *data), - int size, unsigned char *data) + int size, unsigned char *data) { unsigned char buf[256]; int orig_bit_size;