File libpng16-CVE-2015-8126.patch of Package libpng16.1679
From 81f44665cce4cb1373f049a76f3904e981b7a766 Mon Sep 17 00:00:00 2001
From: Glenn Randers-Pehrson <glennrp at users.sourceforge.net>
Date: Thu, 29 Oct 2015 09:26:41 -0500
Subject: [PATCH] [libpng16] Reject attempt to write over-length PLTE chunk
Index: pngwutil.c
===================================================================
--- pngwutil.c.orig 2014-08-21 12:53:37.000000000 +0200
+++ pngwutil.c 2015-11-16 14:53:14.351661646 +0100
@@ -919,17 +919,20 @@
png_write_PLTE(png_structrp png_ptr, png_const_colorp palette,
png_uint_32 num_pal)
{
- png_uint_32 i;
+ png_uint_32 max_palette_length, i;
png_const_colorp pal_ptr;
png_byte buf[3];
png_debug(1, "in png_write_PLTE");
+ max_palette_length = (png_ptr->color_type == PNG_COLOR_TYPE_PALETTE) ?
+ (1 << png_ptr->bit_depth) : PNG_MAX_PALETTE_LENGTH;
+
if ((
#ifdef PNG_MNG_FEATURES_SUPPORTED
!(png_ptr->mng_features_permitted & PNG_FLAG_MNG_EMPTY_PLTE) &&
#endif
- num_pal == 0) || num_pal > 256)
+ num_pal == 0) || num_pal > max_palette_length)
{
if (png_ptr->color_type == PNG_COLOR_TYPE_PALETTE)
{
Index: pngrutil.c
===================================================================
--- pngrutil.c.orig 2015-11-16 14:53:14.344661551 +0100
+++ pngrutil.c 2015-11-16 14:54:11.410432049 +0100
@@ -867,7 +867,7 @@
png_handle_PLTE(png_structrp png_ptr, png_inforp info_ptr, png_uint_32 length)
{
png_color palette[PNG_MAX_PALETTE_LENGTH];
- int num, i;
+ int max_palette_length, num, i;
#ifdef PNG_POINTER_INDEXING_SUPPORTED
png_colorp pal_ptr;
#endif
@@ -928,6 +928,19 @@
/* The cast is safe because 'length' is less than 3*PNG_MAX_PALETTE_LENGTH */
num = (int)length / 3;
+ /* If the palette has 256 or fewer entries but is too large for the bit
+ * depth, we don't issue an error, to preserve the behavior of previous
+ * libpng versions. We silently truncate the unused extra palette entries
+ * here.
+ */
+ if (png_ptr->color_type == PNG_COLOR_TYPE_PALETTE)
+ max_palette_length = (1 << png_ptr->bit_depth);
+ else
+ max_palette_length = PNG_MAX_PALETTE_LENGTH;
+
+ if (num > max_palette_length)
+ num = max_palette_length;
+
#ifdef PNG_POINTER_INDEXING_SUPPORTED
for (i = 0, pal_ptr = palette; i < num; i++, pal_ptr++)
{
Index: pngset.c
===================================================================
--- pngset.c.orig 2014-08-21 12:53:36.000000000 +0200
+++ pngset.c 2015-11-16 14:53:14.352661659 +0100
@@ -503,12 +503,17 @@
png_const_colorp palette, int num_palette)
{
+ png_uint_32 max_palette_length;
+
png_debug1(1, "in %s storage function", "PLTE");
if (png_ptr == NULL || info_ptr == NULL)
return;
- if (num_palette < 0 || num_palette > PNG_MAX_PALETTE_LENGTH)
+ max_palette_length = (png_ptr->color_type == PNG_COLOR_TYPE_PALETTE) ?
+ (1 << png_ptr->bit_depth) : PNG_MAX_PALETTE_LENGTH;
+
+ if (num_palette < 0 || num_palette > (int) max_palette_length)
{
if (info_ptr->color_type == PNG_COLOR_TYPE_PALETTE)
png_error(png_ptr, "Invalid palette length");