From fc11e6ec3064302438191fc80701a4bb141f686f Mon Sep 17 00:00:00 2001 From: stephena Date: Thu, 29 Mar 2012 22:00:58 +0000 Subject: [PATCH] Updated included PNG library to 1.5.10. git-svn-id: svn://svn.code.sf.net/p/stella/code/trunk@2433 8b62c5a3-ac7e-4cc8-8f21-d9a121418aba --- Changes.txt | 2 + src/libpng/png.c | 30 ++- src/libpng/png.h | 34 ++- src/libpng/pngconf.h | 6 +- src/libpng/pngpread.c | 561 ++--------------------------------------- src/libpng/pngpriv.h | 52 +++- src/libpng/pngread.c | 21 +- src/libpng/pngrtran.c | 13 +- src/libpng/pngrutil.c | 19 +- src/libpng/pngset.c | 37 ++- src/libpng/pngstruct.h | 15 +- src/libpng/pngtrans.c | 107 +++++++- src/libpng/pngwrite.c | 16 +- src/libpng/pngwutil.c | 19 +- 14 files changed, 305 insertions(+), 627 deletions(-) diff --git a/Changes.txt b/Changes.txt index 7ef5db6df..ba723ac50 100644 --- a/Changes.txt +++ b/Changes.txt @@ -21,6 +21,8 @@ * Added emulation for MindLink controller; the Bionic Breakthrough ROM now works. + * Updated included PNG library to latest stable version. + -Have fun! diff --git a/src/libpng/png.c b/src/libpng/png.c index ca1de4866..cba18ba91 100644 --- a/src/libpng/png.c +++ b/src/libpng/png.c @@ -1,8 +1,8 @@ /* png.c - location for general purpose libpng functions * - * Last changed in libpng 1.5.7 [December 15, 2011] - * Copyright (c) 1998-2011 Glenn Randers-Pehrson + * Last changed in libpng 1.5.10 [March 8, 2012] + * Copyright (c) 1998-2012 Glenn Randers-Pehrson * (Version 0.96 Copyright (c) 1996, 1997 Andreas Dilger) * (Version 0.88 Copyright (c) 1995, 1996 Guy Eric Schalnat, Group 42, Inc.) * @@ -14,7 +14,7 @@ #include "pngpriv.h" /* Generate a compiler error if there is an old png.h in the search path. */ -typedef png_libpng_version_1_5_9 Your_png_h_is_not_version_1_5_9; +typedef png_libpng_version_1_5_10 Your_png_h_is_not_version_1_5_10; /* Tells libpng that we have already handled the first "num_bytes" bytes * of the PNG file signature. If the PNG data is embedded into another @@ -655,13 +655,13 @@ png_get_copyright(png_const_structp png_ptr) #else # ifdef __STDC__ return PNG_STRING_NEWLINE \ - "libpng version 1.5.9 - February 18, 2012" PNG_STRING_NEWLINE \ + "libpng version 1.5.10 - March 29, 2012" PNG_STRING_NEWLINE \ "Copyright (c) 1998-2011 Glenn Randers-Pehrson" PNG_STRING_NEWLINE \ "Copyright (c) 1996-1997 Andreas Dilger" PNG_STRING_NEWLINE \ "Copyright (c) 1995-1996 Guy Eric Schalnat, Group 42, Inc." \ PNG_STRING_NEWLINE; # else - return "libpng version 1.5.9 - February 18, 2012\ + return "libpng version 1.5.10 - March 29, 2012\ Copyright (c) 1998-2011 Glenn Randers-Pehrson\ Copyright (c) 1996-1997 Andreas Dilger\ Copyright (c) 1995-1996 Guy Eric Schalnat, Group 42, Inc."; @@ -1467,7 +1467,7 @@ static double png_pow10(int power) { int recip = 0; - double d = 1; + double d = 1.0; /* Handle negative exponent with a reciprocal at the end because * 10 is exact whereas .1 is inexact in base 2 @@ -1481,7 +1481,7 @@ png_pow10(int power) if (power > 0) { /* Decompose power bitwise. */ - double mult = 10; + double mult = 10.0; do { if (power & 1) d *= mult; @@ -1600,7 +1600,8 @@ png_ascii_from_fp(png_structp png_ptr, png_charp ascii, png_size_t size, { double d; - fp *= 10; + fp *= 10.0; + /* Use modf here, not floor and subtract, so that * the separation is done in one step. At the end * of the loop don't break the number into parts so @@ -1613,7 +1614,7 @@ png_ascii_from_fp(png_structp png_ptr, png_charp ascii, png_size_t size, { d = floor(fp + .5); - if (d > 9) + if (d > 9.0) { /* Rounding up to 10, handle that here. */ if (czero > 0) @@ -1621,9 +1622,10 @@ png_ascii_from_fp(png_structp png_ptr, png_charp ascii, png_size_t size, --czero, d = 1; if (cdigits == 0) --clead; } + else { - while (cdigits > 0 && d > 9) + while (cdigits > 0 && d > 9.0) { int ch = *--ascii; @@ -1648,7 +1650,7 @@ png_ascii_from_fp(png_structp png_ptr, png_charp ascii, png_size_t size, * exponent but take into account the leading * decimal point. */ - if (d > 9) /* cdigits == 0 */ + if (d > 9.0) /* cdigits == 0 */ { if (exp_b10 == (-1)) { @@ -1669,18 +1671,19 @@ png_ascii_from_fp(png_structp png_ptr, png_charp ascii, png_size_t size, ++exp_b10; /* In all cases we output a '1' */ - d = 1; + d = 1.0; } } } fp = 0; /* Guarantees termination below. */ } - if (d == 0) + if (d == 0.0) { ++czero; if (cdigits == 0) ++clead; } + else { /* Included embedded zeros in the digit count. */ @@ -1708,6 +1711,7 @@ png_ascii_from_fp(png_structp png_ptr, png_charp ascii, png_size_t size, above */ --exp_b10; } + *ascii++ = (char)(48 + (int)d), ++cdigits; } } diff --git a/src/libpng/png.h b/src/libpng/png.h index 5617c9720..4e0dee179 100644 --- a/src/libpng/png.h +++ b/src/libpng/png.h @@ -1,7 +1,7 @@ /* png.h - header file for PNG reference library * - * libpng version 1.5.9 - February 18, 2012 + * libpng version 1.5.10 - March 29, 2012 * Copyright (c) 1998-2012 Glenn Randers-Pehrson * (Version 0.96 Copyright (c) 1996, 1997 Andreas Dilger) * (Version 0.88 Copyright (c) 1995, 1996 Guy Eric Schalnat, Group 42, Inc.) @@ -11,7 +11,7 @@ * Authors and maintainers: * libpng versions 0.71, May 1995, through 0.88, January 1996: Guy Schalnat * libpng versions 0.89c, June 1996, through 0.96, May 1997: Andreas Dilger - * libpng versions 0.97, January 1998, through 1.5.9 - February 18, 2012: Glenn + * libpng versions 0.97, January 1998, through 1.5.10 - March 29, 2012: Glenn * See also "Contributing Authors", below. * * Note about libpng version numbers: @@ -172,6 +172,8 @@ * 1.5.9beta01-02 15 10509 15.so.15.9[.0] * 1.5.9rc01 15 10509 15.so.15.9[.0] * 1.5.9 15 10509 15.so.15.9[.0] + * 1.5.10beta01-05 15 10510 15.so.15.10[.0] + * 1.5.10 15 10510 15.so.15.10[.0] * * Henceforth the source version will match the shared-library major * and minor numbers; the shared-library major version number will be @@ -181,7 +183,7 @@ * to the source version x.y.z (leading zeros in y and z). Beta versions * were given the previous public release number plus a letter, until * version 1.0.6j; from then on they were given the upcoming public - * release number plus "betaNN" or "rcN". + * release number plus "betaNN" or "rcNN". * * Binary incompatibility exists only when applications make direct access * to the info_ptr or png_ptr members through png.h, and the compiled @@ -203,7 +205,7 @@ * * This code is released under the libpng license. * - * libpng versions 1.2.6, August 15, 2004, through 1.5.9, February 18, 2012, are + * libpng versions 1.2.6, August 15, 2004, through 1.5.10, March 29, 2012, are * Copyright (c) 2004, 2006-2012 Glenn Randers-Pehrson, and are * distributed according to the same disclaimer and license as libpng-1.2.5 * with the following individual added to the list of Contributing Authors: @@ -315,13 +317,13 @@ * Y2K compliance in libpng: * ========================= * - * February 18, 2012 + * March 29, 2012 * * Since the PNG Development group is an ad-hoc body, we can't make * an official declaration. * * This is your unofficial assurance that libpng from version 0.71 and - * upward through 1.5.9 are Y2K compliant. It is my belief that + * upward through 1.5.10 are Y2K compliant. It is my belief that * earlier versions were also Y2K compliant. * * Libpng only has two year fields. One is a 2-byte unsigned integer @@ -379,9 +381,9 @@ */ /* Version information for png.h - this should match the version in png.c */ -#define PNG_LIBPNG_VER_STRING "1.5.9" +#define PNG_LIBPNG_VER_STRING "1.5.10" #define PNG_HEADER_VERSION_STRING \ - " libpng version 1.5.9 - February 18, 2012\n" + " libpng version 1.5.10 - March 29, 2012\n" #define PNG_LIBPNG_VER_SONUM 15 #define PNG_LIBPNG_VER_DLLNUM 15 @@ -389,7 +391,7 @@ /* These should match the first 3 components of PNG_LIBPNG_VER_STRING: */ #define PNG_LIBPNG_VER_MAJOR 1 #define PNG_LIBPNG_VER_MINOR 5 -#define PNG_LIBPNG_VER_RELEASE 9 +#define PNG_LIBPNG_VER_RELEASE 10 /* This should match the numeric part of the final component of * PNG_LIBPNG_VER_STRING, omitting any leading zero: @@ -412,7 +414,7 @@ #define PNG_LIBPNG_BUILD_SPECIAL 32 /* Cannot be OR'ed with PNG_LIBPNG_BUILD_PRIVATE */ -#define PNG_LIBPNG_BUILD_BASE_TYPE PNG_LIBPNG_BUILD_BETA +#define PNG_LIBPNG_BUILD_BASE_TYPE PNG_LIBPNG_BUILD_STABLE /* Careful here. At one time, Guy wanted to use 082, but that would be octal. * We must not include leading zeros. @@ -420,7 +422,7 @@ * version 1.0.0 was mis-numbered 100 instead of 10000). From * version 1.0.1 it's xxyyzz, where x=major, y=minor, z=release */ -#define PNG_LIBPNG_VER 10509 /* 1.5.9 */ +#define PNG_LIBPNG_VER 10510 /* 1.5.10 */ /* Library configuration: these options cannot be changed after * the library has been built. @@ -542,7 +544,7 @@ extern "C" { /* This triggers a compiler error in png.c, if png.c and png.h * do not agree upon the version number. */ -typedef char* png_libpng_version_1_5_9; +typedef char* png_libpng_version_1_5_10; /* Three color definitions. The order of the red, green, and blue, (and the * exact size) is not important, although the size of the fields need to @@ -2637,6 +2639,12 @@ PNG_EXPORT(207, void, png_save_uint_16, (png_bytep buf, unsigned int i)); : (png_int_32)png_get_uint_32(buf))) #endif +#if defined(PNG_READ_CHECK_FOR_INVALID_INDEX_SUPPORTED) || \ + defined(PNG_WRITE_CHECK_FOR_INVALID_INDEX_SUPPORTED) +PNG_EXPORT(234, void, png_set_check_for_invalid_index, (png_structp png_ptr, + int allowed)); +#endif + /* Maintainer: Put new public prototypes here ^, in libpng.3, and project * defs */ @@ -2646,7 +2654,7 @@ PNG_EXPORT(207, void, png_save_uint_16, (png_bytep buf, unsigned int i)); * scripts/symbols.def as well. */ #ifdef PNG_EXPORT_LAST_ORDINAL - PNG_EXPORT_LAST_ORDINAL(233); + PNG_EXPORT_LAST_ORDINAL(234); #endif #ifdef __cplusplus diff --git a/src/libpng/pngconf.h b/src/libpng/pngconf.h index 1aa268bee..bbb547f8e 100644 --- a/src/libpng/pngconf.h +++ b/src/libpng/pngconf.h @@ -1,7 +1,7 @@ /* pngconf.h - machine configurable file for libpng * - * libpng version 1.5.9 - February 18, 2012 + * libpng version 1.5.10 - March 29, 2012 * * Copyright (c) 1998-2012 Glenn Randers-Pehrson * (Version 0.96 Copyright (c) 1996, 1997 Andreas Dilger) @@ -51,8 +51,8 @@ /* This controls optimization of the reading of 16 and 32 bit values * from PNG files. It can be set on a per-app-file basis - it - * just changes whether a macro is used to the function is called. - * The library builder sets the default, if read functions are not + * just changes whether a macro is used when the function is called. + * The library builder sets the default; if read functions are not * built into the library the macro implementation is forced on. */ #ifndef PNG_READ_INT_FUNCTIONS_SUPPORTED diff --git a/src/libpng/pngpread.c b/src/libpng/pngpread.c index 95a2082e4..8a5aa29ec 100644 --- a/src/libpng/pngpread.c +++ b/src/libpng/pngpread.c @@ -2,7 +2,7 @@ /* pngpread.c - read a png file in push mode * * Last changed in libpng 1.5.9 [February 18, 2012] - * Copyright (c) 1998-2011 Glenn Randers-Pehrson + * Copyright (c) 1998-2012 Glenn Randers-Pehrson * (Version 0.96 Copyright (c) 1996, 1997 Andreas Dilger) * (Version 0.88 Copyright (c) 1995, 1996 Guy Eric Schalnat, Group 42, Inc.) * @@ -128,30 +128,6 @@ png_process_some_data(png_structp png_ptr, png_infop info_ptr) break; } -#ifdef PNG_READ_tEXt_SUPPORTED - case PNG_READ_tEXt_MODE: - { - png_push_read_tEXt(png_ptr, info_ptr); - break; - } - -#endif -#ifdef PNG_READ_zTXt_SUPPORTED - case PNG_READ_zTXt_MODE: - { - png_push_read_zTXt(png_ptr, info_ptr); - break; - } - -#endif -#ifdef PNG_READ_iTXt_SUPPORTED - case PNG_READ_iTXt_MODE: - { - png_push_read_iTXt(png_ptr, info_ptr); - break; - } - -#endif case PNG_SKIP_MODE: { png_push_crc_finish(png_ptr); @@ -176,7 +152,7 @@ void /* PRIVATE */ png_push_read_sig(png_structp png_ptr, png_infop info_ptr) { png_size_t num_checked = png_ptr->sig_bytes, - num_to_check = 8 - num_checked; + num_to_check = 8 - num_checked; if (png_ptr->buffer_size < num_to_check) { @@ -196,6 +172,7 @@ png_push_read_sig(png_structp png_ptr, png_infop info_ptr) else png_error(png_ptr, "PNG file corrupted by ASCII conversion"); } + else { if (png_ptr->sig_bytes >= 8) @@ -543,7 +520,7 @@ png_push_read_chunk(png_structp png_ptr, png_infop info_ptr) return; } - png_push_handle_tEXt(png_ptr, info_ptr, png_ptr->push_length); + png_handle_tEXt(png_ptr, info_ptr, png_ptr->push_length); } #endif @@ -556,7 +533,7 @@ png_push_read_chunk(png_structp png_ptr, png_infop info_ptr) return; } - png_push_handle_zTXt(png_ptr, info_ptr, png_ptr->push_length); + png_handle_zTXt(png_ptr, info_ptr, png_ptr->push_length); } #endif @@ -569,7 +546,7 @@ png_push_read_chunk(png_structp png_ptr, png_infop info_ptr) return; } - png_push_handle_iTXt(png_ptr, info_ptr, png_ptr->push_length); + png_handle_iTXt(png_ptr, info_ptr, png_ptr->push_length); } #endif @@ -580,7 +557,7 @@ png_push_read_chunk(png_structp png_ptr, png_infop info_ptr) png_push_save_buffer(png_ptr); return; } - png_push_handle_unknown(png_ptr, info_ptr, png_ptr->push_length); + png_handle_unknown(png_ptr, info_ptr, png_ptr->push_length); } png_ptr->mode &= ~PNG_HAVE_CHUNK_HEADER; @@ -620,6 +597,7 @@ png_push_crc_finish(png_structp png_ptr) png_ptr->save_buffer_size -= save_size; png_ptr->save_buffer_ptr += save_size; } + if (png_ptr->skip_length && png_ptr->current_buffer_size) { png_size_t save_size = png_ptr->current_buffer_size; @@ -641,6 +619,7 @@ png_push_crc_finish(png_structp png_ptr) png_ptr->current_buffer_size -= save_size; png_ptr->current_buffer_ptr += save_size; } + if (!png_ptr->skip_length) { if (png_ptr->buffer_size < 4) @@ -663,6 +642,7 @@ png_push_fill_buffer(png_structp png_ptr, png_bytep buffer, png_size_t length) return; ptr = buffer; + if (png_ptr->save_buffer_size) { png_size_t save_size; @@ -680,6 +660,7 @@ png_push_fill_buffer(png_structp png_ptr, png_bytep buffer, png_size_t length) png_ptr->save_buffer_size -= save_size; png_ptr->save_buffer_ptr += save_size; } + if (length && png_ptr->current_buffer_size) { png_size_t save_size; @@ -709,6 +690,7 @@ png_push_save_buffer(png_structp png_ptr) png_bytep dp; istop = png_ptr->save_buffer_size; + for (i = 0, sp = png_ptr->save_buffer_ptr, dp = png_ptr->save_buffer; i < istop; i++, sp++, dp++) { @@ -716,6 +698,7 @@ png_push_save_buffer(png_structp png_ptr) } } } + if (png_ptr->save_buffer_size + png_ptr->current_buffer_size > png_ptr->save_buffer_max) { @@ -742,6 +725,7 @@ png_push_save_buffer(png_structp png_ptr) png_free(png_ptr, old_buffer); png_ptr->save_buffer_max = new_max; } + if (png_ptr->current_buffer_size) { png_memcpy(png_ptr->save_buffer + png_ptr->save_buffer_size, @@ -749,6 +733,7 @@ png_push_save_buffer(png_structp png_ptr) png_ptr->save_buffer_size += png_ptr->current_buffer_size; png_ptr->current_buffer_size = 0; } + png_ptr->save_buffer_ptr = png_ptr->save_buffer; png_ptr->buffer_size = 0; } @@ -850,6 +835,7 @@ png_push_read_IDAT(png_structp png_ptr) png_ptr->current_buffer_size -= save_size; png_ptr->current_buffer_ptr += save_size; } + if (!png_ptr->idat_size) { if (png_ptr->buffer_size < 4) @@ -1263,521 +1249,6 @@ png_read_push_finish_row(png_structp png_ptr) #endif /* PNG_READ_INTERLACING_SUPPORTED */ } -#ifdef PNG_READ_tEXt_SUPPORTED -void /* PRIVATE */ -png_push_handle_tEXt(png_structp png_ptr, png_infop info_ptr, png_uint_32 - length) -{ - if (!(png_ptr->mode & PNG_HAVE_IHDR) || (png_ptr->mode & PNG_HAVE_IEND)) - { - PNG_UNUSED(info_ptr) /* To quiet some compiler warnings */ - png_error(png_ptr, "Out of place tEXt"); - /* NOT REACHED */ - } - -#ifdef PNG_MAX_MALLOC_64K - png_ptr->skip_length = 0; /* This may not be necessary */ - - if (length > (png_uint_32)65535L) /* Can't hold entire string in memory */ - { - png_warning(png_ptr, "tEXt chunk too large to fit in memory"); - png_ptr->skip_length = length - (png_uint_32)65535L; - length = (png_uint_32)65535L; - } -#endif - - png_ptr->current_text = (png_charp)png_malloc(png_ptr, length + 1); - png_ptr->current_text[length] = '\0'; - png_ptr->current_text_ptr = png_ptr->current_text; - png_ptr->current_text_size = (png_size_t)length; - png_ptr->current_text_left = (png_size_t)length; - png_ptr->process_mode = PNG_READ_tEXt_MODE; -} - -void /* PRIVATE */ -png_push_read_tEXt(png_structp png_ptr, png_infop info_ptr) -{ - if (png_ptr->buffer_size && png_ptr->current_text_left) - { - png_size_t text_size; - - if (png_ptr->buffer_size < png_ptr->current_text_left) - text_size = png_ptr->buffer_size; - - else - text_size = png_ptr->current_text_left; - - png_crc_read(png_ptr, (png_bytep)png_ptr->current_text_ptr, text_size); - png_ptr->current_text_left -= text_size; - png_ptr->current_text_ptr += text_size; - } - if (!(png_ptr->current_text_left)) - { - png_textp text_ptr; - png_charp text; - png_charp key; - int ret; - - if (png_ptr->buffer_size < 4) - { - png_push_save_buffer(png_ptr); - return; - } - - png_push_crc_finish(png_ptr); - -#ifdef PNG_MAX_MALLOC_64K - if (png_ptr->skip_length) - return; -#endif - - key = png_ptr->current_text; - - for (text = key; *text; text++) - /* Empty loop */ ; - - if (text < key + png_ptr->current_text_size) - text++; - - text_ptr = (png_textp)png_malloc(png_ptr, png_sizeof(png_text)); - text_ptr->compression = PNG_TEXT_COMPRESSION_NONE; - text_ptr->key = key; - text_ptr->itxt_length = 0; - text_ptr->lang = NULL; - text_ptr->lang_key = NULL; - text_ptr->text = text; - - ret = png_set_text_2(png_ptr, info_ptr, text_ptr, 1); - - png_free(png_ptr, key); - png_free(png_ptr, text_ptr); - png_ptr->current_text = NULL; - - if (ret) - png_warning(png_ptr, "Insufficient memory to store text chunk"); - } -} -#endif - -#ifdef PNG_READ_zTXt_SUPPORTED -void /* PRIVATE */ -png_push_handle_zTXt(png_structp png_ptr, png_infop info_ptr, png_uint_32 - length) -{ - if (!(png_ptr->mode & PNG_HAVE_IHDR) || (png_ptr->mode & PNG_HAVE_IEND)) - { - PNG_UNUSED(info_ptr) /* To quiet some compiler warnings */ - png_error(png_ptr, "Out of place zTXt"); - /* NOT REACHED */ - } - -#ifdef PNG_MAX_MALLOC_64K - /* We can't handle zTXt chunks > 64K, since we don't have enough space - * to be able to store the uncompressed data. Actually, the threshold - * is probably around 32K, but it isn't as definite as 64K is. - */ - if (length > (png_uint_32)65535L) - { - png_warning(png_ptr, "zTXt chunk too large to fit in memory"); - png_push_crc_skip(png_ptr, length); - return; - } -#endif - - png_ptr->current_text = (png_charp)png_malloc(png_ptr, length + 1); - png_ptr->current_text[length] = '\0'; - png_ptr->current_text_ptr = png_ptr->current_text; - png_ptr->current_text_size = (png_size_t)length; - png_ptr->current_text_left = (png_size_t)length; - png_ptr->process_mode = PNG_READ_zTXt_MODE; -} - -void /* PRIVATE */ -png_push_read_zTXt(png_structp png_ptr, png_infop info_ptr) -{ - if (png_ptr->buffer_size && png_ptr->current_text_left) - { - png_size_t text_size; - - if (png_ptr->buffer_size < (png_uint_32)png_ptr->current_text_left) - text_size = png_ptr->buffer_size; - - else - text_size = png_ptr->current_text_left; - - png_crc_read(png_ptr, (png_bytep)png_ptr->current_text_ptr, text_size); - png_ptr->current_text_left -= text_size; - png_ptr->current_text_ptr += text_size; - } - if (!(png_ptr->current_text_left)) - { - png_textp text_ptr; - png_charp text; - png_charp key; - int ret; - png_size_t text_size, key_size; - - if (png_ptr->buffer_size < 4) - { - png_push_save_buffer(png_ptr); - return; - } - - png_push_crc_finish(png_ptr); - - key = png_ptr->current_text; - - for (text = key; *text; text++) - /* Empty loop */ ; - - /* zTXt can't have zero text */ - if (text >= key + png_ptr->current_text_size) - { - png_ptr->current_text = NULL; - png_free(png_ptr, key); - return; - } - - text++; - - if (*text != PNG_TEXT_COMPRESSION_zTXt) /* Check compression byte */ - { - png_ptr->current_text = NULL; - png_free(png_ptr, key); - return; - } - - text++; - - png_ptr->zstream.next_in = (png_bytep)text; - png_ptr->zstream.avail_in = (uInt)(png_ptr->current_text_size - - (text - key)); - png_ptr->zstream.next_out = png_ptr->zbuf; - png_ptr->zstream.avail_out = (uInt)png_ptr->zbuf_size; - - key_size = text - key; - text_size = 0; - text = NULL; - ret = Z_STREAM_END; - - while (png_ptr->zstream.avail_in) - { - ret = inflate(&png_ptr->zstream, Z_PARTIAL_FLUSH); - if (ret != Z_OK && ret != Z_STREAM_END) - { - inflateReset(&png_ptr->zstream); - png_ptr->zstream.avail_in = 0; - png_ptr->current_text = NULL; - png_free(png_ptr, key); - png_free(png_ptr, text); - return; - } - - if (!(png_ptr->zstream.avail_out) || ret == Z_STREAM_END) - { - if (text == NULL) - { - text = (png_charp)png_malloc(png_ptr, - (png_ptr->zbuf_size - - png_ptr->zstream.avail_out + key_size + 1)); - - png_memcpy(text + key_size, png_ptr->zbuf, - png_ptr->zbuf_size - png_ptr->zstream.avail_out); - - png_memcpy(text, key, key_size); - - text_size = key_size + png_ptr->zbuf_size - - png_ptr->zstream.avail_out; - - *(text + text_size) = '\0'; - } - - else - { - png_charp tmp; - - tmp = text; - text = (png_charp)png_malloc(png_ptr, text_size + - (png_ptr->zbuf_size - - png_ptr->zstream.avail_out + 1)); - - png_memcpy(text, tmp, text_size); - png_free(png_ptr, tmp); - - png_memcpy(text + text_size, png_ptr->zbuf, - png_ptr->zbuf_size - png_ptr->zstream.avail_out); - - text_size += png_ptr->zbuf_size - png_ptr->zstream.avail_out; - *(text + text_size) = '\0'; - } - - if (ret != Z_STREAM_END) - { - png_ptr->zstream.next_out = png_ptr->zbuf; - png_ptr->zstream.avail_out = (uInt)png_ptr->zbuf_size; - } - } - else - { - break; - } - - if (ret == Z_STREAM_END) - break; - } - - inflateReset(&png_ptr->zstream); - png_ptr->zstream.avail_in = 0; - - if (ret != Z_STREAM_END) - { - png_ptr->current_text = NULL; - png_free(png_ptr, key); - png_free(png_ptr, text); - return; - } - - png_ptr->current_text = NULL; - png_free(png_ptr, key); - key = text; - text += key_size; - - text_ptr = (png_textp)png_malloc(png_ptr, - png_sizeof(png_text)); - text_ptr->compression = PNG_TEXT_COMPRESSION_zTXt; - text_ptr->key = key; - text_ptr->itxt_length = 0; - text_ptr->lang = NULL; - text_ptr->lang_key = NULL; - text_ptr->text = text; - - ret = png_set_text_2(png_ptr, info_ptr, text_ptr, 1); - - png_free(png_ptr, key); - png_free(png_ptr, text_ptr); - - if (ret) - png_warning(png_ptr, "Insufficient memory to store text chunk"); - } -} -#endif - -#ifdef PNG_READ_iTXt_SUPPORTED -void /* PRIVATE */ -png_push_handle_iTXt(png_structp png_ptr, png_infop info_ptr, png_uint_32 - length) -{ - if (!(png_ptr->mode & PNG_HAVE_IHDR) || (png_ptr->mode & PNG_HAVE_IEND)) - { - PNG_UNUSED(info_ptr) /* To quiet some compiler warnings */ - png_error(png_ptr, "Out of place iTXt"); - /* NOT REACHED */ - } - -#ifdef PNG_MAX_MALLOC_64K - png_ptr->skip_length = 0; /* This may not be necessary */ - - if (length > (png_uint_32)65535L) /* Can't hold entire string in memory */ - { - png_warning(png_ptr, "iTXt chunk too large to fit in memory"); - png_ptr->skip_length = length - (png_uint_32)65535L; - length = (png_uint_32)65535L; - } -#endif - - png_ptr->current_text = (png_charp)png_malloc(png_ptr, length + 1); - png_ptr->current_text[length] = '\0'; - png_ptr->current_text_ptr = png_ptr->current_text; - png_ptr->current_text_size = (png_size_t)length; - png_ptr->current_text_left = (png_size_t)length; - png_ptr->process_mode = PNG_READ_iTXt_MODE; -} - -void /* PRIVATE */ -png_push_read_iTXt(png_structp png_ptr, png_infop info_ptr) -{ - - if (png_ptr->buffer_size && png_ptr->current_text_left) - { - png_size_t text_size; - - if (png_ptr->buffer_size < png_ptr->current_text_left) - text_size = png_ptr->buffer_size; - - else - text_size = png_ptr->current_text_left; - - png_crc_read(png_ptr, (png_bytep)png_ptr->current_text_ptr, text_size); - png_ptr->current_text_left -= text_size; - png_ptr->current_text_ptr += text_size; - } - - if (!(png_ptr->current_text_left)) - { - png_textp text_ptr; - png_charp key; - int comp_flag; - png_charp lang; - png_charp lang_key; - png_charp text; - int ret; - - if (png_ptr->buffer_size < 4) - { - png_push_save_buffer(png_ptr); - return; - } - - png_push_crc_finish(png_ptr); - -#ifdef PNG_MAX_MALLOC_64K - if (png_ptr->skip_length) - return; -#endif - - key = png_ptr->current_text; - - for (lang = key; *lang; lang++) - /* Empty loop */ ; - - if (lang < key + png_ptr->current_text_size - 3) - lang++; - - comp_flag = *lang++; - lang++; /* Skip comp_type, always zero */ - - for (lang_key = lang; *lang_key; lang_key++) - /* Empty loop */ ; - - lang_key++; /* Skip NUL separator */ - - text=lang_key; - - if (lang_key < key + png_ptr->current_text_size - 1) - { - for (; *text; text++) - /* Empty loop */ ; - } - - if (text < key + png_ptr->current_text_size) - text++; - - text_ptr = (png_textp)png_malloc(png_ptr, - png_sizeof(png_text)); - - text_ptr->compression = comp_flag + 2; - text_ptr->key = key; - text_ptr->lang = lang; - text_ptr->lang_key = lang_key; - text_ptr->text = text; - text_ptr->text_length = 0; - text_ptr->itxt_length = png_strlen(text); - - ret = png_set_text_2(png_ptr, info_ptr, text_ptr, 1); - - png_ptr->current_text = NULL; - - png_free(png_ptr, text_ptr); - if (ret) - png_warning(png_ptr, "Insufficient memory to store iTXt chunk"); - } -} -#endif - -/* This function is called when we haven't found a handler for this - * chunk. If there isn't a problem with the chunk itself (ie a bad chunk - * name or a critical chunk), the chunk is (currently) silently ignored. - */ -void /* PRIVATE */ -png_push_handle_unknown(png_structp png_ptr, png_infop info_ptr, png_uint_32 - length) -{ - png_uint_32 skip = 0; - png_uint_32 chunk_name = png_ptr->chunk_name; - - if (PNG_CHUNK_CRITICAL(chunk_name)) - { -#ifdef PNG_READ_UNKNOWN_CHUNKS_SUPPORTED - if (png_chunk_unknown_handling(png_ptr, chunk_name) != - PNG_HANDLE_CHUNK_ALWAYS -#ifdef PNG_READ_USER_CHUNKS_SUPPORTED - && png_ptr->read_user_chunk_fn == NULL -#endif - ) -#endif - png_chunk_error(png_ptr, "unknown critical chunk"); - - PNG_UNUSED(info_ptr) /* To quiet some compiler warnings */ - } - -#ifdef PNG_READ_UNKNOWN_CHUNKS_SUPPORTED - /* TODO: the code below is apparently just using the - * png_struct::unknown_chunk member as a temporarily variable, it should be - * possible to eliminate both it and the temporary buffer. - */ - if (png_ptr->flags & PNG_FLAG_KEEP_UNKNOWN_CHUNKS) - { -#ifdef PNG_MAX_MALLOC_64K - if (length > 65535) - { - png_warning(png_ptr, "unknown chunk too large to fit in memory"); - skip = length - 65535; - length = 65535; - } -#endif - /* This is just a record for the user; libpng doesn't use the character - * form of the name. - */ - PNG_CSTRING_FROM_CHUNK(png_ptr->unknown_chunk.name, png_ptr->chunk_name); - - png_ptr->unknown_chunk.size = length; - - if (length == 0) - png_ptr->unknown_chunk.data = NULL; - - else - { - png_ptr->unknown_chunk.data = (png_bytep)png_malloc(png_ptr, - png_ptr->unknown_chunk.size); - png_crc_read(png_ptr, (png_bytep)png_ptr->unknown_chunk.data, - png_ptr->unknown_chunk.size); - } - -#ifdef PNG_READ_USER_CHUNKS_SUPPORTED - if (png_ptr->read_user_chunk_fn != NULL) - { - /* Callback to user unknown chunk handler */ - int ret; - ret = (*(png_ptr->read_user_chunk_fn)) - (png_ptr, &png_ptr->unknown_chunk); - - if (ret < 0) - png_chunk_error(png_ptr, "error in user chunk"); - - if (ret == 0) - { - if (PNG_CHUNK_CRITICAL(png_ptr->chunk_name)) - if (png_chunk_unknown_handling(png_ptr, chunk_name) != - PNG_HANDLE_CHUNK_ALWAYS) - png_chunk_error(png_ptr, "unknown critical chunk"); - png_set_unknown_chunks(png_ptr, info_ptr, - &png_ptr->unknown_chunk, 1); - } - } - - else -#endif - png_set_unknown_chunks(png_ptr, info_ptr, &png_ptr->unknown_chunk, 1); - png_free(png_ptr, png_ptr->unknown_chunk.data); - png_ptr->unknown_chunk.data = NULL; - } - - else -#endif - skip=length; - png_push_crc_skip(png_ptr, skip); -} - void /* PRIVATE */ png_push_have_info(png_structp png_ptr, png_infop info_ptr) { diff --git a/src/libpng/pngpriv.h b/src/libpng/pngpriv.h index 67e486c57..e76a57975 100644 --- a/src/libpng/pngpriv.h +++ b/src/libpng/pngpriv.h @@ -2,11 +2,11 @@ /* pngpriv.h - private declarations for use inside libpng * * For conditions of distribution and use, see copyright notice in png.h - * Copyright (c) 1998-2011 Glenn Randers-Pehrson + * Copyright (c) 1998-2012 Glenn Randers-Pehrson * (Version 0.96 Copyright (c) 1996, 1997 Andreas Dilger) * (Version 0.88 Copyright (c) 1995, 1996 Guy Eric Schalnat, Group 42, Inc.) * - * Last changed in libpng 1.5.7 [December 15, 2011] + * Last changed in libpng 1.5.10 [March 29, 2012] * * This code is released under the libpng license. * For conditions of distribution and use, see the disclaimer @@ -133,6 +133,46 @@ # define PNG_DLL_EXPORT #endif +/* SECURITY and SAFETY: + * + * By default libpng is built without any internal limits on image size, + * individual heap (png_malloc) allocations or the total amount of memory used. + * If PNG_SAFE_LIMITS_SUPPORTED is defined, however, the limits below are used + * (unless individually overridden). These limits are believed to be fairly + * safe, but builders of secure systems should verify the values against the + * real system capabilities. + */ + +#ifdef PNG_SAFE_LIMITS_SUPPORTED + /* 'safe' limits */ +# ifndef PNG_USER_WIDTH_MAX +# define PNG_USER_WIDTH_MAX 1000000 +# endif +# ifndef PNG_USER_HEIGHT_MAX +# define PNG_USER_HEIGHT_MAX 1000000 +# endif +# ifndef PNG_USER_CHUNK_CACHE_MAX +# define PNG_USER_CHUNK_CACHE_MAX 128 +# endif +# ifndef PNG_USER_CHUNK_MALLOC_MAX +# define PNG_USER_CHUNK_MALLOC_MAX 8000000 +# endif +#else + /* values for no limits */ +# ifndef PNG_USER_WIDTH_MAX +# define PNG_USER_WIDTH_MAX 0x7fffffff +# endif +# ifndef PNG_USER_HEIGHT_MAX +# define PNG_USER_HEIGHT_MAX 0x7fffffff +# endif +# ifndef PNG_USER_CHUNK_CACHE_MAX +# define PNG_USER_CHUNK_CACHE_MAX 0 +# endif +# ifndef PNG_USER_CHUNK_MALLOC_MAX +# define PNG_USER_CHUNK_MALLOC_MAX 0 +# endif +#endif + /* This is used for 16 bit gamma tables - only the top level pointers are const, * this could be changed: */ @@ -426,6 +466,7 @@ typedef PNG_CONST png_uint_16p FAR * png_const_uint_16pp; #define PNG_BACKGROUND_IS_GRAY 0x800 #define PNG_HAVE_PNG_SIGNATURE 0x1000 #define PNG_HAVE_CHUNK_AFTER_IDAT 0x2000 /* Have another chunk after IDAT */ +#define PNG_HAVE_iCCP 0x4000 /* Flags for the transformations the PNG library does on the image data */ #define PNG_BGR 0x0001 @@ -1355,6 +1396,13 @@ PNG_EXTERN void png_check_IHDR PNGARG((png_structp png_ptr, int color_type, int interlace_type, int compression_type, int filter_type)); +/* Added at libpng version 1.5.10 */ +#if defined(PNG_READ_CHECK_FOR_INVALID_INDEX_SUPPORTED) || \ + defined(PNG_WRITE_CHECK_FOR_INVALID_INDEX_SUPPORTED) +PNG_EXTERN void png_do_check_palette_indexes PNGARG((png_structp png_ptr, + png_row_infop row_info)); +#endif + /* Free all memory used by the read (old method - NOT DLL EXPORTED) */ PNG_EXTERN void png_read_destroy PNGARG((png_structp png_ptr, png_infop info_ptr, png_infop end_info_ptr)); diff --git a/src/libpng/pngread.c b/src/libpng/pngread.c index 0643754da..1d8c6b334 100644 --- a/src/libpng/pngread.c +++ b/src/libpng/pngread.c @@ -1,8 +1,8 @@ /* pngread.c - read a PNG file * - * Last changed in libpng 1.5.7 [December 15, 2011] - * Copyright (c) 1998-2011 Glenn Randers-Pehrson + * Last changed in libpng 1.5.10 [March 8, 2012] + * Copyright (c) 1998-2012 Glenn Randers-Pehrson * (Version 0.96 Copyright (c) 1996, 1997 Andreas Dilger) * (Version 0.88 Copyright (c) 1995, 1996 Guy Eric Schalnat, Group 42, Inc.) * @@ -67,15 +67,11 @@ png_create_read_struct_2,(png_const_charp user_png_ver, png_voidp error_ptr, png_ptr->user_width_max = PNG_USER_WIDTH_MAX; png_ptr->user_height_max = PNG_USER_HEIGHT_MAX; -# ifdef PNG_USER_CHUNK_CACHE_MAX /* Added at libpng-1.2.43 and 1.4.0 */ png_ptr->user_chunk_cache_max = PNG_USER_CHUNK_CACHE_MAX; -# endif -# ifdef PNG_SET_USER_CHUNK_MALLOC_MAX /* Added at libpng-1.2.43 and 1.4.1 */ png_ptr->user_chunk_malloc_max = PNG_USER_CHUNK_MALLOC_MAX; -# endif #endif #ifdef PNG_SETJMP_SUPPORTED @@ -805,6 +801,13 @@ png_read_end(png_structp png_ptr, png_infop info_ptr) png_crc_finish(png_ptr, 0); /* Finish off CRC from last IDAT chunk */ +#ifdef PNG_READ_CHECK_FOR_INVALID_INDEX_SUPPORTED + /* Report invalid palette index; added at libng-1.5.10 */ + if (png_ptr->color_type == PNG_COLOR_TYPE_PALETTE && + png_ptr->num_palette_max > png_ptr->num_palette) + png_benign_error(png_ptr, "Read palette index exceeding num_palette"); +#endif + do { png_uint_32 length = png_read_chunk_header(png_ptr); @@ -1070,12 +1073,6 @@ png_read_destroy(png_structp png_ptr, png_infop info_ptr, png_free(png_ptr, png_ptr->save_buffer); #endif -#ifdef PNG_PROGRESSIVE_READ_SUPPORTED -#ifdef PNG_TEXT_SUPPORTED - png_free(png_ptr, png_ptr->current_text); -#endif /* PNG_TEXT_SUPPORTED */ -#endif /* PNG_PROGRESSIVE_READ_SUPPORTED */ - /* Save the important info out of the png_struct, in case it is * being used again. */ diff --git a/src/libpng/pngrtran.c b/src/libpng/pngrtran.c index 1079595f0..556185286 100644 --- a/src/libpng/pngrtran.c +++ b/src/libpng/pngrtran.c @@ -1,8 +1,8 @@ /* pngrtran.c - transforms the data in a row for PNG readers * - * Last changed in libpng 1.5.7 [December 15, 2011] - * Copyright (c) 1998-2011 Glenn Randers-Pehrson + * Last changed in libpng 1.5.10 [March 8, 2012] + * Copyright (c) 1998-2012 Glenn Randers-Pehrson * (Version 0.96 Copyright (c) 1996, 1997 Andreas Dilger) * (Version 0.88 Copyright (c) 1995, 1996 Guy Eric Schalnat, Group 42, Inc.) * @@ -1830,12 +1830,15 @@ png_init_read_transformations(png_structp png_ptr) #ifdef PNG_READ_SHIFT_SUPPORTED if ((png_ptr->transformations & PNG_SHIFT) && + !(png_ptr->transformations & PNG_EXPAND) && (png_ptr->color_type == PNG_COLOR_TYPE_PALETTE)) { int i; int istop = png_ptr->num_palette; int shift = 8 - png_ptr->sig_bit.red; + png_ptr->transformations &= ~PNG_SHIFT; + /* significant bits can be in the range 1 to 7 for a meaninful result, if * the number of significant bits is 0 then no shift is done (this is an * error condition which is silently ignored.) @@ -2296,6 +2299,12 @@ png_do_read_transformations(png_structp png_ptr, png_row_infop row_info) png_do_unpack(row_info, png_ptr->row_buf + 1); #endif +#ifdef PNG_READ_CHECK_FOR_INVALID_INDEX_SUPPORTED + /* Added at libpng-1.5.10 */ + if (row_info->color_type == PNG_COLOR_TYPE_PALETTE) + png_do_check_palette_indexes(png_ptr, row_info); +#endif + #ifdef PNG_READ_BGR_SUPPORTED if (png_ptr->transformations & PNG_BGR) png_do_bgr(row_info, png_ptr->row_buf + 1); diff --git a/src/libpng/pngrutil.c b/src/libpng/pngrutil.c index d6c0e0350..aa592ccfb 100644 --- a/src/libpng/pngrutil.c +++ b/src/libpng/pngrutil.c @@ -1,7 +1,7 @@ /* pngrutil.c - utilities to read a PNG file * - * Last changed in libpng 1.5.9 [February 18, 2012] + * Last changed in libpng 1.5.10 [March 8, 2012] * Copyright (c) 1998-2012 Glenn Randers-Pehrson * (Version 0.96 Copyright (c) 1996, 1997 Andreas Dilger) * (Version 0.88 Copyright (c) 1995, 1996 Guy Eric Schalnat, Group 42, Inc.) @@ -434,14 +434,12 @@ png_decompress_chunk(png_structp png_ptr, int comp_type, */ if (prefix_size >= (~(png_size_t)0) - 1 || expanded_size >= (~(png_size_t)0) - 1 - prefix_size -#ifdef PNG_SET_CHUNK_MALLOC_LIMIT_SUPPORTED +#ifdef PNG_USER_LIMITS_SUPPORTED || (png_ptr->user_chunk_malloc_max && (prefix_size + expanded_size >= png_ptr->user_chunk_malloc_max - 1)) #else -# ifdef PNG_USER_CHUNK_MALLOC_MAX || ((PNG_USER_CHUNK_MALLOC_MAX > 0) && prefix_size + expanded_size >= PNG_USER_CHUNK_MALLOC_MAX - 1) -# endif #endif ) png_warning(png_ptr, "Exceeded size limit while expanding chunk"); @@ -1259,13 +1257,16 @@ png_handle_iCCP(png_structp png_ptr, png_infop info_ptr, png_uint_32 length) /* Should be an error, but we can cope with it */ png_warning(png_ptr, "Out of place iCCP chunk"); - if (info_ptr != NULL && (info_ptr->valid & PNG_INFO_iCCP)) + if ((png_ptr->mode & PNG_HAVE_iCCP) || (info_ptr != NULL && + (info_ptr->valid & (PNG_INFO_iCCP|PNG_INFO_sRGB)))) { png_warning(png_ptr, "Duplicate iCCP chunk"); png_crc_finish(png_ptr, length); return; } + png_ptr->mode |= PNG_HAVE_iCCP; + #ifdef PNG_MAX_MALLOC_64K if (length > (png_uint_32)65535L) { @@ -1795,16 +1796,16 @@ png_handle_hIST(png_structp png_ptr, png_infop info_ptr, png_uint_32 length) return; } - num = length / 2 ; - - if (num != (unsigned int)png_ptr->num_palette || num > - (unsigned int)PNG_MAX_PALETTE_LENGTH) + if (length > 2*PNG_MAX_PALETTE_LENGTH || + length != (unsigned int) (2*png_ptr->num_palette)) { png_warning(png_ptr, "Incorrect hIST chunk length"); png_crc_finish(png_ptr, length); return; } + num = length / 2 ; + for (i = 0; i < num; i++) { png_byte buf[2]; diff --git a/src/libpng/pngset.c b/src/libpng/pngset.c index 92db3890a..e0118fa8c 100644 --- a/src/libpng/pngset.c +++ b/src/libpng/pngset.c @@ -1,8 +1,8 @@ /* pngset.c - storage of image information into info struct * - * Last changed in libpng 1.5.7 [December 15, 2011] - * Copyright (c) 1998-2011 Glenn Randers-Pehrson + * Last changed in libpng 1.5.10 [(PENDING RELEASE)] + * Copyright (c) 1998-2012 Glenn Randers-Pehrson * (Version 0.96 Copyright (c) 1996, 1997 Andreas Dilger) * (Version 0.88 Copyright (c) 1995, 1996 Guy Eric Schalnat, Group 42, Inc.) * @@ -692,24 +692,28 @@ png_set_text_2(png_structp png_ptr, png_infop info_ptr, */ if (info_ptr->num_text + num_text > info_ptr->max_text) { + int old_max_text = info_ptr->max_text; + int old_num_text = info_ptr->num_text; + if (info_ptr->text != NULL) { png_textp old_text; - int old_max; - old_max = info_ptr->max_text; info_ptr->max_text = info_ptr->num_text + num_text + 8; old_text = info_ptr->text; + info_ptr->text = (png_textp)png_malloc_warn(png_ptr, (png_size_t)(info_ptr->max_text * png_sizeof(png_text))); if (info_ptr->text == NULL) { - png_free(png_ptr, old_text); + /* Restore to previous condition */ + info_ptr->max_text = old_max_text; + info_ptr->text = old_text; return(1); } - png_memcpy(info_ptr->text, old_text, (png_size_t)(old_max * + png_memcpy(info_ptr->text, old_text, (png_size_t)(old_max_text * png_sizeof(png_text))); png_free(png_ptr, old_text); } @@ -721,7 +725,12 @@ png_set_text_2(png_structp png_ptr, png_infop info_ptr, info_ptr->text = (png_textp)png_malloc_warn(png_ptr, (png_size_t)(info_ptr->max_text * png_sizeof(png_text))); if (info_ptr->text == NULL) + { + /* Restore to previous condition */ + info_ptr->num_text = old_num_text; + info_ptr->max_text = old_max_text; return(1); + } info_ptr->free_me |= PNG_FREE_TEXT; } @@ -1281,4 +1290,20 @@ png_set_benign_errors(png_structp png_ptr, int allowed) png_ptr->flags &= ~PNG_FLAG_BENIGN_ERRORS_WARN; } #endif /* PNG_BENIGN_ERRORS_SUPPORTED */ + +#ifdef PNG_READ_CHECK_FOR_INVALID_INDEX_SUPPORTED + /* Do not report invalid palette index; added at libng-1.5.10 */ +void PNGAPI +png_set_check_for_invalid_index(png_structp png_ptr, int allowed) +{ + png_debug(1, "in png_set_check_for_invalid_index"); + + if (allowed) + png_ptr->num_palette_max = 0; + + else + png_ptr->num_palette_max = -1; +} +#endif + #endif /* PNG_READ_SUPPORTED || PNG_WRITE_SUPPORTED */ diff --git a/src/libpng/pngstruct.h b/src/libpng/pngstruct.h index 860b8bff8..43a45cdec 100644 --- a/src/libpng/pngstruct.h +++ b/src/libpng/pngstruct.h @@ -5,7 +5,7 @@ * (Version 0.96 Copyright (c) 1996, 1997 Andreas Dilger) * (Version 0.88 Copyright (c) 1995, 1996 Guy Eric Schalnat, Group 42, Inc.) * - * Last changed in libpng 1.5.9 [February 18, 2012] + * Last changed in libpng 1.5.9 [March 29, 2012] * * This code is released under the libpng license. * For conditions of distribution and use, see the disclaimer @@ -121,6 +121,12 @@ struct png_struct_def png_uint_32 crc; /* current chunk CRC value */ png_colorp palette; /* palette from the input file */ png_uint_16 num_palette; /* number of color entries in palette */ + +/* Added at libpng-1.5.10 */ +#ifdef PNG_CHECK_FOR_INVALID_INDEX_SUPPORTED + int num_palette_max; /* maximum palette index found in IDAT */ +#endif + png_uint_16 num_trans; /* number of transparency values */ png_byte compression; /* file compression type (always 0) */ png_byte filter; /* file filter type (always 0) */ @@ -211,13 +217,6 @@ struct png_struct_def int process_mode; /* what push library is currently doing */ int cur_palette; /* current push library palette index */ -# ifdef PNG_TEXT_SUPPORTED - png_size_t current_text_size; /* current size of text input data */ - png_size_t current_text_left; /* how much text left to read in input */ - png_charp current_text; /* current text chunk buffer */ - png_charp current_text_ptr; /* current location in current_text */ -# endif /* PNG_PROGRESSIVE_READ_SUPPORTED && PNG_TEXT_SUPPORTED */ - #endif /* PNG_PROGRESSIVE_READ_SUPPORTED */ #if defined(__TURBOC__) && !defined(_Windows) && !defined(__FLAT__) diff --git a/src/libpng/pngtrans.c b/src/libpng/pngtrans.c index 6a6908dcd..fef12f185 100644 --- a/src/libpng/pngtrans.c +++ b/src/libpng/pngtrans.c @@ -1,8 +1,8 @@ /* pngtrans.c - transforms the data in a row (used by both readers and writers) * - * Last changed in libpng 1.5.4 [July 7, 2011] - * Copyright (c) 1998-2011 Glenn Randers-Pehrson + * Last changed in libpng 1.5.10 [March 8, 2012] + * Copyright (c) 1998-2012 Glenn Randers-Pehrson * (Version 0.96 Copyright (c) 1996, 1997 Andreas Dilger) * (Version 0.88 Copyright (c) 1995, 1996 Guy Eric Schalnat, Group 42, Inc.) * @@ -619,6 +619,109 @@ png_do_bgr(png_row_infop row_info, png_bytep row) } #endif /* PNG_READ_BGR_SUPPORTED or PNG_WRITE_BGR_SUPPORTED */ +#if defined(PNG_READ_CHECK_FOR_INVALID_INDEX_SUPPORTED) || \ + defined(PNG_WRITE_CHECK_FOR_INVALID_INDEX_SUPPORTED) +/* Added at libpng-1.5.10 */ +void /* PRIVATE */ +png_do_check_palette_indexes(png_structp png_ptr, png_row_infop row_info) +{ + if (png_ptr->num_palette < (1 << row_info->bit_depth) && + png_ptr->num_palette_max >= 0) + { + /* Calculations moved outside switch in an attempt to stop different + * compiler warnings. 'padding' is in *bits* within the last byte, it is + * an 'int' because pixel_depth becomes an 'int' in the expression below, + * and this calculation is used because it avoids warnings that other + * forms produced on either GCC or MSVC. + */ + int padding = (-row_info->pixel_depth * row_info->width) & 7; + png_bytep rp = png_ptr->row_buf + row_info->rowbytes; + + switch (row_info->bit_depth) + { + case 1: + { + /* in this case, all bytes must be 0 so we don't need + * to unpack the pixels except for the rightmost one. + */ + for (; rp > png_ptr->row_buf; rp--) + { + if (*rp >> padding != 0) + png_ptr->num_palette_max = 1; + padding = 0; + } + + break; + } + + case 2: + { + for (; rp > png_ptr->row_buf; rp--) + { + int i = ((*rp >> padding) & 0x03); + + if (i > png_ptr->num_palette_max) + png_ptr->num_palette_max = i; + + i = (((*rp >> padding) >> 2) & 0x03); + + if (i > png_ptr->num_palette_max) + png_ptr->num_palette_max = i; + + i = (((*rp >> padding) >> 4) & 0x03); + + if (i > png_ptr->num_palette_max) + png_ptr->num_palette_max = i; + + i = (((*rp >> padding) >> 6) & 0x03); + + if (i > png_ptr->num_palette_max) + png_ptr->num_palette_max = i; + + padding = 0; + } + + break; + } + + case 4: + { + for (; rp > png_ptr->row_buf; rp--) + { + int i = ((*rp >> padding) & 0x0f); + + if (i > png_ptr->num_palette_max) + png_ptr->num_palette_max = i; + + i = (((*rp >> padding) >> 4) & 0x0f); + + if (i > png_ptr->num_palette_max) + png_ptr->num_palette_max = i; + + padding = 0; + } + + break; + } + + case 8: + { + for (; rp > png_ptr->row_buf; rp--) + { + if (*rp >= png_ptr->num_palette_max) + png_ptr->num_palette_max = (int) *rp; + } + + break; + } + + default: + break; + } + } +} +#endif /* PNG_CHECK_FOR_INVALID_INDEX_SUPPORTED */ + #if defined(PNG_READ_USER_TRANSFORM_SUPPORTED) || \ defined(PNG_WRITE_USER_TRANSFORM_SUPPORTED) #ifdef PNG_USER_TRANSFORM_PTR_SUPPORTED diff --git a/src/libpng/pngwrite.c b/src/libpng/pngwrite.c index 6d3fd4c38..b587f1b99 100644 --- a/src/libpng/pngwrite.c +++ b/src/libpng/pngwrite.c @@ -1,8 +1,8 @@ /* pngwrite.c - general routines to write a PNG file * - * Last changed in libpng 1.5.7 [December 15, 2011] - * Copyright (c) 1998-2011 Glenn Randers-Pehrson + * Last changed in libpng 1.5.10 [March 8, 2012] + * Copyright (c) 1998-2012 Glenn Randers-Pehrson * (Version 0.96 Copyright (c) 1996, 1997 Andreas Dilger) * (Version 0.88 Copyright (c) 1995, 1996 Guy Eric Schalnat, Group 42, Inc.) * @@ -305,6 +305,11 @@ png_write_end(png_structp png_ptr, png_infop info_ptr) if (!(png_ptr->mode & PNG_HAVE_IDAT)) png_error(png_ptr, "No IDATs written into file"); +#ifdef PNG_WRITE_CHECK_FOR_INVALID_INDEX_SUPPORTED + if (png_ptr->num_palette_max > png_ptr->num_palette) + png_benign_error(png_ptr, "Wrote palette index exceeding num_palette"); +#endif + /* See if user wants us to write information chunks */ if (info_ptr != NULL) { @@ -798,6 +803,13 @@ png_write_row(png_structp png_ptr, png_const_bytep row) } #endif +/* Added at libpng-1.5.10 */ +#ifdef PNG_WRITE_CHECK_FOR_INVALID_INDEX_SUPPORTED + /* Check for out-of-range palette index */ + if(row_info.color_type == PNG_COLOR_TYPE_PALETTE) + png_do_check_palette_indexes(png_ptr, &row_info); +#endif + /* Find a filter if necessary, filter the row and write it out. */ png_write_find_filter(png_ptr, &row_info); diff --git a/src/libpng/pngwutil.c b/src/libpng/pngwutil.c index da18e9502..b49704f1a 100644 --- a/src/libpng/pngwutil.c +++ b/src/libpng/pngwutil.c @@ -1,8 +1,8 @@ /* pngwutil.c - utilities to write a PNG file * - * Last changed in libpng 1.5.6 [November 3, 2011] - * Copyright (c) 1998-2011 Glenn Randers-Pehrson + * Last changed in libpng 1.5.10 [March 8, 2012] + * Copyright (c) 1998-2012 Glenn Randers-Pehrson * (Version 0.96 Copyright (c) 1996, 1997 Andreas Dilger) * (Version 0.88 Copyright (c) 1995, 1996 Guy Eric Schalnat, Group 42, Inc.) * @@ -569,14 +569,15 @@ png_text_compress(png_structp png_ptr, /* Ship the compressed text out via chunk writes */ static void /* PRIVATE */ -png_write_compressed_data_out(png_structp png_ptr, compression_state *comp) +png_write_compressed_data_out(png_structp png_ptr, compression_state *comp, + png_size_t data_len) { int i; /* Handle the no-compression case */ if (comp->input) { - png_write_chunk_data(png_ptr, comp->input, comp->input_len); + png_write_chunk_data(png_ptr, comp->input, data_len); return; } @@ -585,7 +586,7 @@ png_write_compressed_data_out(png_structp png_ptr, compression_state *comp) /* The zbuf_size test is because the code below doesn't work if zbuf_size is * '1'; simply skip it to avoid memory overwrite. */ - if (comp->input_len >= 2 && comp->input_len < 16384 && png_ptr->zbuf_size > 1) + if (data_len >= 2 && comp->input_len < 16384 && png_ptr->zbuf_size > 1) { unsigned int z_cmf; /* zlib compression method and flags */ @@ -1164,8 +1165,7 @@ png_write_iCCP(png_structp png_ptr, png_const_charp name, int compression_type, if (profile_len) { - comp.input_len = profile_len; - png_write_compressed_data_out(png_ptr, &comp); + png_write_compressed_data_out(png_ptr, &comp, profile_len); } png_write_chunk_end(png_ptr); @@ -1735,8 +1735,7 @@ png_write_zTXt(png_structp png_ptr, png_const_charp key, png_const_charp text, png_write_chunk_data(png_ptr, &buf, (png_size_t)1); /* Write the compressed data */ - comp.input_len = text_len; - png_write_compressed_data_out(png_ptr, &comp); + png_write_compressed_data_out(png_ptr, &comp, text_len); /* Close the chunk */ png_write_chunk_end(png_ptr); @@ -1827,7 +1826,7 @@ png_write_iTXt(png_structp png_ptr, int compression, png_const_charp key, png_write_chunk_data(png_ptr, (lang_key ? (png_const_bytep)lang_key : cbuf), (png_size_t)(lang_key_len + 1)); - png_write_compressed_data_out(png_ptr, &comp); + png_write_compressed_data_out(png_ptr, &comp, text_len); png_write_chunk_end(png_ptr);