2 /* pngrutil.c - utilities to read a PNG file
4 * Last changed in libpng 1.4.1 [February 25, 2010]
5 * Copyright (c) 1998-2010 Glenn Randers-Pehrson
6 * (Version 0.96 Copyright (c) 1996, 1997 Andreas Dilger)
7 * (Version 0.88 Copyright (c) 1995, 1996 Guy Eric Schalnat, Group 42, Inc.)
9 * This code is released under the libpng license.
10 * For conditions of distribution and use, see the disclaimer
11 * and license in png.h
13 * This file contains routines that are only called from within
14 * libpng itself during the course of reading an image.
17 #define PNG_NO_PEDANTIC_WARNINGS
19 #ifdef PNG_READ_SUPPORTED
22 # define png_strtod(p,a,b) strtod(a,b)
24 png_get_uint_31(png_structp png_ptr, png_bytep buf)
26 png_uint_32 i = png_get_uint_32(buf);
27 if (i > PNG_UINT_31_MAX)
28 png_error(png_ptr, "PNG unsigned integer out of range");
31 #ifndef PNG_USE_READ_MACROS
32 /* Grab an unsigned 32-bit integer from a buffer in big-endian format. */
34 png_get_uint_32(png_bytep buf)
36 png_uint_32 i = ((png_uint_32)(*buf) << 24) +
37 ((png_uint_32)(*(buf + 1)) << 16) +
38 ((png_uint_32)(*(buf + 2)) << 8) +
39 (png_uint_32)(*(buf + 3));
44 /* Grab a signed 32-bit integer from a buffer in big-endian format. The
45 * data is stored in the PNG file in two's complement format, and it is
46 * assumed that the machine format for signed integers is the same.
49 png_get_int_32(png_bytep buf)
51 png_int_32 i = ((png_int_32)(*buf) << 24) +
52 ((png_int_32)(*(buf + 1)) << 16) +
53 ((png_int_32)(*(buf + 2)) << 8) +
54 (png_int_32)(*(buf + 3));
59 /* Grab an unsigned 16-bit integer from a buffer in big-endian format. */
61 png_get_uint_16(png_bytep buf)
63 png_uint_16 i = (png_uint_16)(((png_uint_16)(*buf) << 8) +
64 (png_uint_16)(*(buf + 1)));
68 #endif /* PNG_USE_READ_MACROS */
70 /* Read the chunk header (length + type name).
71 * Put the type name into png_ptr->chunk_name, and return the length.
73 png_uint_32 /* PRIVATE */
74 png_read_chunk_header(png_structp png_ptr)
79 #ifdef PNG_IO_STATE_SUPPORTED
80 /* Inform the I/O callback that the chunk header is being read.
81 * PNG_IO_CHUNK_HDR requires a single I/O call.
83 png_ptr->io_state = PNG_IO_READING | PNG_IO_CHUNK_HDR;
86 /* Read the length and the chunk name */
87 png_read_data(png_ptr, buf, 8);
88 length = png_get_uint_31(png_ptr, buf);
90 /* Put the chunk name into png_ptr->chunk_name */
91 png_memcpy(png_ptr->chunk_name, buf + 4, 4);
93 png_debug2(0, "Reading %s chunk, length = %lu",
94 png_ptr->chunk_name, length);
96 /* Reset the crc and run it over the chunk name */
97 png_reset_crc(png_ptr);
98 png_calculate_crc(png_ptr, png_ptr->chunk_name, 4);
100 /* Check to see if chunk name is valid */
101 png_check_chunk_name(png_ptr, png_ptr->chunk_name);
103 #ifdef PNG_IO_STATE_SUPPORTED
104 /* Inform the I/O callback that chunk data will (possibly) be read.
105 * PNG_IO_CHUNK_DATA does NOT require a specific number of I/O calls.
107 png_ptr->io_state = PNG_IO_READING | PNG_IO_CHUNK_DATA;
113 /* Read data, and (optionally) run it through the CRC. */
115 png_crc_read(png_structp png_ptr, png_bytep buf, png_size_t length)
119 png_read_data(png_ptr, buf, length);
120 png_calculate_crc(png_ptr, buf, length);
123 /* Optionally skip data and then check the CRC. Depending on whether we
124 * are reading a ancillary or critical chunk, and how the program has set
125 * things up, we may calculate the CRC on the data and print a message.
126 * Returns '1' if there was a CRC error, '0' otherwise.
129 png_crc_finish(png_structp png_ptr, png_uint_32 skip)
132 png_size_t istop = png_ptr->zbuf_size;
134 for (i = (png_size_t)skip; i > istop; i -= istop)
136 png_crc_read(png_ptr, png_ptr->zbuf, png_ptr->zbuf_size);
140 png_crc_read(png_ptr, png_ptr->zbuf, i);
143 if (png_crc_error(png_ptr))
145 if (((png_ptr->chunk_name[0] & 0x20) && /* Ancillary */
146 !(png_ptr->flags & PNG_FLAG_CRC_ANCILLARY_NOWARN)) ||
147 (!(png_ptr->chunk_name[0] & 0x20) && /* Critical */
148 (png_ptr->flags & PNG_FLAG_CRC_CRITICAL_USE)))
150 png_chunk_warning(png_ptr, "CRC error");
154 png_chunk_benign_error(png_ptr, "CRC error");
163 /* Compare the CRC stored in the PNG file with that calculated by libpng from
164 * the data it has read thus far.
167 png_crc_error(png_structp png_ptr)
169 png_byte crc_bytes[4];
173 if (png_ptr->chunk_name[0] & 0x20) /* ancillary */
175 if ((png_ptr->flags & PNG_FLAG_CRC_ANCILLARY_MASK) ==
176 (PNG_FLAG_CRC_ANCILLARY_USE | PNG_FLAG_CRC_ANCILLARY_NOWARN))
181 if (png_ptr->flags & PNG_FLAG_CRC_CRITICAL_IGNORE)
185 #ifdef PNG_IO_STATE_SUPPORTED
186 /* Inform the I/O callback that the chunk CRC is being read */
187 /* PNG_IO_CHUNK_CRC requires the I/O to be done at once */
188 png_ptr->io_state = PNG_IO_READING | PNG_IO_CHUNK_CRC;
191 png_read_data(png_ptr, crc_bytes, 4);
195 crc = png_get_uint_32(crc_bytes);
196 return ((int)(crc != png_ptr->crc));
202 #if defined(PNG_READ_zTXt_SUPPORTED) || defined(PNG_READ_iTXt_SUPPORTED) || \
203 defined(PNG_READ_iCCP_SUPPORTED)
205 png_inflate(png_structp png_ptr, const png_byte *data, png_size_t size,
206 png_bytep output, png_size_t output_size)
208 png_size_t count = 0;
210 png_ptr->zstream.next_in = (png_bytep)data; /* const_cast: VALID */
211 png_ptr->zstream.avail_in = size;
217 /* Reset the output buffer each time round - we empty it
218 * after every inflate call.
220 png_ptr->zstream.next_out = png_ptr->zbuf;
221 png_ptr->zstream.avail_out = png_ptr->zbuf_size;
223 ret = inflate(&png_ptr->zstream, Z_NO_FLUSH);
224 avail = png_ptr->zbuf_size - png_ptr->zstream.avail_out;
226 /* First copy/count any new output - but only if we didn't
229 if ((ret == Z_OK || ret == Z_STREAM_END) && avail > 0)
231 if (output != 0 && output_size > count)
233 int copy = output_size - count;
234 if (avail < copy) copy = avail;
235 png_memcpy(output + count, png_ptr->zbuf, copy);
243 /* Termination conditions - always reset the zstream, it
244 * must be left in inflateInit state.
246 png_ptr->zstream.avail_in = 0;
247 inflateReset(&png_ptr->zstream);
249 if (ret == Z_STREAM_END)
250 return count; /* NOTE: may be zero. */
252 /* Now handle the error codes - the API always returns 0
253 * and the error message is dumped into the uncompressed
254 * buffer if available.
258 if (png_ptr->zstream.msg != 0)
259 msg = png_ptr->zstream.msg;
262 #ifdef PNG_STDIO_SUPPORTED
266 msg = "Buffer error in compressed datastream in %s chunk";
269 msg = "Data error in compressed datastream in %s chunk";
272 msg = "Incomplete compressed datastream in %s chunk";
276 png_snprintf(umsg, sizeof umsg, msg, png_ptr->chunk_name);
279 msg = "Damaged compressed datastream in chunk other than IDAT";
283 png_warning(png_ptr, msg);
286 /* 0 means an error - notice that this code simple ignores
287 * zero length compressed chunks as a result.
294 * Decompress trailing data in a chunk. The assumption is that chunkdata
295 * points at an allocated area holding the contents of a chunk with a
296 * trailing compressed part. What we get back is an allocated area
297 * holding the original prefix part and an uncompressed version of the
298 * trailing part (the malloc area passed in is freed).
301 png_decompress_chunk(png_structp png_ptr, int comp_type,
302 png_size_t chunklength,
303 png_size_t prefix_size, png_size_t *newlength)
305 /* The caller should guarantee this */
306 if (prefix_size > chunklength)
308 /* The recovery is to delete the chunk. */
309 png_warning(png_ptr, "invalid chunklength");
310 prefix_size = 0; /* To delete everything */
313 else if (comp_type == PNG_COMPRESSION_TYPE_BASE)
315 png_size_t expanded_size = png_inflate(png_ptr,
316 (png_bytep)(png_ptr->chunkdata + prefix_size),
317 chunklength - prefix_size,
318 0/*output*/, 0/*output size*/);
320 /* Now check the limits on this chunk - if the limit fails the
321 * compressed data will be removed, the prefix will remain.
323 #ifdef PNG_SET_CHUNK_MALLOC_LIMIT_SUPPORTED
324 if (png_ptr->user_chunk_malloc_max &&
325 (prefix_size + expanded_size >= png_ptr->user_chunk_malloc_max - 1))
327 if ((PNG_USER_CHUNK_MALLOC_MAX > 0) &&
328 prefix_size + expanded_size >= PNG_USER_CHUNK_MALLOC_MAX - 1)
330 png_warning(png_ptr, "Exceeded size limit while expanding chunk");
332 /* If the size is zero either there was an error and a message
333 * has already been output (warning) or the size really is zero
334 * and we have nothing to do - the code will exit through the
337 else if (expanded_size > 0)
339 /* Success (maybe) - really uncompress the chunk. */
340 png_size_t new_size = 0;
341 png_charp text = png_malloc_warn(png_ptr,
342 prefix_size + expanded_size + 1);
346 png_memcpy(text, png_ptr->chunkdata, prefix_size);
347 new_size = png_inflate(png_ptr,
348 (png_bytep)(png_ptr->chunkdata + prefix_size),
349 chunklength - prefix_size,
350 (png_bytep)(text + prefix_size), expanded_size);
351 text[prefix_size + expanded_size] = 0; /* just in case */
353 if (new_size == expanded_size)
355 png_free(png_ptr, png_ptr->chunkdata);
356 png_ptr->chunkdata = text;
357 *newlength = prefix_size + expanded_size;
358 return; /* The success return! */
361 png_warning(png_ptr, "png_inflate logic error");
362 png_free(png_ptr, text);
365 png_warning(png_ptr, "Not enough memory to decompress chunk");
369 else /* if (comp_type != PNG_COMPRESSION_TYPE_BASE) */
373 #ifdef PNG_STDIO_SUPPORTED
374 png_snprintf(umsg, sizeof umsg, "Unknown zTXt compression type %d", comp_type);
375 png_warning(png_ptr, umsg);
377 png_warning(png_ptr, "Unknown zTXt compression type");
380 /* The recovery is to simply drop the data. */
383 /* Generic error return - leave the prefix, delete the compressed
384 * data, reallocate the chunkdata to remove the potentially large
385 * amount of compressed data.
388 png_charp text = png_malloc_warn(png_ptr, prefix_size + 1);
392 png_memcpy(text, png_ptr->chunkdata, prefix_size);
393 png_free(png_ptr, png_ptr->chunkdata);
394 png_ptr->chunkdata = text;
396 /* This is an extra zero in the 'uncompressed' part. */
397 *(png_ptr->chunkdata + prefix_size) = 0x00;
399 /* Ignore a malloc error here - it is safe. */
402 *newlength = prefix_size;
406 /* Read and check the IDHR chunk */
408 png_handle_IHDR(png_structp png_ptr, png_infop info_ptr, png_uint_32 length)
411 png_uint_32 width, height;
412 int bit_depth, color_type, compression_type, filter_type;
415 png_debug(1, "in png_handle_IHDR");
417 if (png_ptr->mode & PNG_HAVE_IHDR)
418 png_error(png_ptr, "Out of place IHDR");
420 /* Check the length */
422 png_error(png_ptr, "Invalid IHDR chunk");
424 png_ptr->mode |= PNG_HAVE_IHDR;
426 png_crc_read(png_ptr, buf, 13);
427 png_crc_finish(png_ptr, 0);
429 width = png_get_uint_31(png_ptr, buf);
430 height = png_get_uint_31(png_ptr, buf + 4);
433 compression_type = buf[10];
434 filter_type = buf[11];
435 interlace_type = buf[12];
437 /* Set internal variables */
438 png_ptr->width = width;
439 png_ptr->height = height;
440 png_ptr->bit_depth = (png_byte)bit_depth;
441 png_ptr->interlaced = (png_byte)interlace_type;
442 png_ptr->color_type = (png_byte)color_type;
443 #ifdef PNG_MNG_FEATURES_SUPPORTED
444 png_ptr->filter_type = (png_byte)filter_type;
446 png_ptr->compression_type = (png_byte)compression_type;
448 /* Find number of channels */
449 switch (png_ptr->color_type)
451 case PNG_COLOR_TYPE_GRAY:
452 case PNG_COLOR_TYPE_PALETTE:
453 png_ptr->channels = 1;
456 case PNG_COLOR_TYPE_RGB:
457 png_ptr->channels = 3;
460 case PNG_COLOR_TYPE_GRAY_ALPHA:
461 png_ptr->channels = 2;
464 case PNG_COLOR_TYPE_RGB_ALPHA:
465 png_ptr->channels = 4;
469 /* Set up other useful info */
470 png_ptr->pixel_depth = (png_byte)(png_ptr->bit_depth *
472 png_ptr->rowbytes = PNG_ROWBYTES(png_ptr->pixel_depth, png_ptr->width);
473 png_debug1(3, "bit_depth = %d", png_ptr->bit_depth);
474 png_debug1(3, "channels = %d", png_ptr->channels);
475 png_debug1(3, "rowbytes = %lu", png_ptr->rowbytes);
476 png_set_IHDR(png_ptr, info_ptr, width, height, bit_depth,
477 color_type, interlace_type, compression_type, filter_type);
480 /* Read and check the palette */
482 png_handle_PLTE(png_structp png_ptr, png_infop info_ptr, png_uint_32 length)
484 png_color palette[PNG_MAX_PALETTE_LENGTH];
486 #ifdef PNG_POINTER_INDEXING_SUPPORTED
490 png_debug(1, "in png_handle_PLTE");
492 if (!(png_ptr->mode & PNG_HAVE_IHDR))
493 png_error(png_ptr, "Missing IHDR before PLTE");
495 else if (png_ptr->mode & PNG_HAVE_IDAT)
497 png_warning(png_ptr, "Invalid PLTE after IDAT");
498 png_crc_finish(png_ptr, length);
502 else if (png_ptr->mode & PNG_HAVE_PLTE)
503 png_error(png_ptr, "Duplicate PLTE chunk");
505 png_ptr->mode |= PNG_HAVE_PLTE;
507 if (!(png_ptr->color_type&PNG_COLOR_MASK_COLOR))
510 "Ignoring PLTE chunk in grayscale PNG");
511 png_crc_finish(png_ptr, length);
514 #ifndef PNG_READ_OPT_PLTE_SUPPORTED
515 if (png_ptr->color_type != PNG_COLOR_TYPE_PALETTE)
517 png_crc_finish(png_ptr, length);
522 if (length > 3*PNG_MAX_PALETTE_LENGTH || length % 3)
524 if (png_ptr->color_type != PNG_COLOR_TYPE_PALETTE)
526 png_warning(png_ptr, "Invalid palette chunk");
527 png_crc_finish(png_ptr, length);
533 png_error(png_ptr, "Invalid palette chunk");
537 num = (int)length / 3;
539 #ifdef PNG_POINTER_INDEXING_SUPPORTED
540 for (i = 0, pal_ptr = palette; i < num; i++, pal_ptr++)
544 png_crc_read(png_ptr, buf, 3);
545 pal_ptr->red = buf[0];
546 pal_ptr->green = buf[1];
547 pal_ptr->blue = buf[2];
550 for (i = 0; i < num; i++)
554 png_crc_read(png_ptr, buf, 3);
555 /* Don't depend upon png_color being any order */
556 palette[i].red = buf[0];
557 palette[i].green = buf[1];
558 palette[i].blue = buf[2];
562 /* If we actually NEED the PLTE chunk (ie for a paletted image), we do
563 * whatever the normal CRC configuration tells us. However, if we
564 * have an RGB image, the PLTE can be considered ancillary, so
565 * we will act as though it is.
567 #ifndef PNG_READ_OPT_PLTE_SUPPORTED
568 if (png_ptr->color_type == PNG_COLOR_TYPE_PALETTE)
571 png_crc_finish(png_ptr, 0);
573 #ifndef PNG_READ_OPT_PLTE_SUPPORTED
574 else if (png_crc_error(png_ptr)) /* Only if we have a CRC error */
576 /* If we don't want to use the data from an ancillary chunk,
577 we have two options: an error abort, or a warning and we
578 ignore the data in this chunk (which should be OK, since
579 it's considered ancillary for a RGB or RGBA image). */
580 if (!(png_ptr->flags & PNG_FLAG_CRC_ANCILLARY_USE))
582 if (png_ptr->flags & PNG_FLAG_CRC_ANCILLARY_NOWARN)
584 png_chunk_benign_error(png_ptr, "CRC error");
588 png_chunk_warning(png_ptr, "CRC error");
592 /* Otherwise, we (optionally) emit a warning and use the chunk. */
593 else if (!(png_ptr->flags & PNG_FLAG_CRC_ANCILLARY_NOWARN))
595 png_chunk_warning(png_ptr, "CRC error");
600 png_set_PLTE(png_ptr, info_ptr, palette, num);
602 #ifdef PNG_READ_tRNS_SUPPORTED
603 if (png_ptr->color_type == PNG_COLOR_TYPE_PALETTE)
605 if (info_ptr != NULL && (info_ptr->valid & PNG_INFO_tRNS))
607 if (png_ptr->num_trans > (png_uint_16)num)
609 png_warning(png_ptr, "Truncating incorrect tRNS chunk length");
610 png_ptr->num_trans = (png_uint_16)num;
612 if (info_ptr->num_trans > (png_uint_16)num)
614 png_warning(png_ptr, "Truncating incorrect info tRNS chunk length");
615 info_ptr->num_trans = (png_uint_16)num;
624 png_handle_IEND(png_structp png_ptr, png_infop info_ptr, png_uint_32 length)
626 png_debug(1, "in png_handle_IEND");
628 if (!(png_ptr->mode & PNG_HAVE_IHDR) || !(png_ptr->mode & PNG_HAVE_IDAT))
630 png_error(png_ptr, "No image in file");
633 png_ptr->mode |= (PNG_AFTER_IDAT | PNG_HAVE_IEND);
637 png_warning(png_ptr, "Incorrect IEND chunk length");
639 png_crc_finish(png_ptr, length);
641 info_ptr = info_ptr; /* Quiet compiler warnings about unused info_ptr */
644 #ifdef PNG_READ_gAMA_SUPPORTED
646 png_handle_gAMA(png_structp png_ptr, png_infop info_ptr, png_uint_32 length)
648 png_fixed_point igamma;
649 #ifdef PNG_FLOATING_POINT_SUPPORTED
654 png_debug(1, "in png_handle_gAMA");
656 if (!(png_ptr->mode & PNG_HAVE_IHDR))
657 png_error(png_ptr, "Missing IHDR before gAMA");
658 else if (png_ptr->mode & PNG_HAVE_IDAT)
660 png_warning(png_ptr, "Invalid gAMA after IDAT");
661 png_crc_finish(png_ptr, length);
664 else if (png_ptr->mode & PNG_HAVE_PLTE)
665 /* Should be an error, but we can cope with it */
666 png_warning(png_ptr, "Out of place gAMA chunk");
668 if (info_ptr != NULL && (info_ptr->valid & PNG_INFO_gAMA)
669 #ifdef PNG_READ_sRGB_SUPPORTED
670 && !(info_ptr->valid & PNG_INFO_sRGB)
674 png_warning(png_ptr, "Duplicate gAMA chunk");
675 png_crc_finish(png_ptr, length);
681 png_warning(png_ptr, "Incorrect gAMA chunk length");
682 png_crc_finish(png_ptr, length);
686 png_crc_read(png_ptr, buf, 4);
687 if (png_crc_finish(png_ptr, 0))
690 igamma = (png_fixed_point)png_get_uint_32(buf);
691 /* Check for zero gamma */
695 "Ignoring gAMA chunk with gamma=0");
699 #ifdef PNG_READ_sRGB_SUPPORTED
700 if (info_ptr != NULL && (info_ptr->valid & PNG_INFO_sRGB))
701 if (PNG_OUT_OF_RANGE(igamma, 45500L, 500))
704 "Ignoring incorrect gAMA value when sRGB is also present");
705 #ifdef PNG_CONSOLE_IO_SUPPORTED
706 fprintf(stderr, "gamma = (%d/100000)", (int)igamma);
710 #endif /* PNG_READ_sRGB_SUPPORTED */
712 #ifdef PNG_FLOATING_POINT_SUPPORTED
713 file_gamma = (float)igamma / (float)100000.0;
714 # ifdef PNG_READ_GAMMA_SUPPORTED
715 png_ptr->gamma = file_gamma;
717 png_set_gAMA(png_ptr, info_ptr, file_gamma);
719 #ifdef PNG_FIXED_POINT_SUPPORTED
720 png_set_gAMA_fixed(png_ptr, info_ptr, igamma);
725 #ifdef PNG_READ_sBIT_SUPPORTED
727 png_handle_sBIT(png_structp png_ptr, png_infop info_ptr, png_uint_32 length)
732 png_debug(1, "in png_handle_sBIT");
734 buf[0] = buf[1] = buf[2] = buf[3] = 0;
736 if (!(png_ptr->mode & PNG_HAVE_IHDR))
737 png_error(png_ptr, "Missing IHDR before sBIT");
738 else if (png_ptr->mode & PNG_HAVE_IDAT)
740 png_warning(png_ptr, "Invalid sBIT after IDAT");
741 png_crc_finish(png_ptr, length);
744 else if (png_ptr->mode & PNG_HAVE_PLTE)
746 /* Should be an error, but we can cope with it */
747 png_warning(png_ptr, "Out of place sBIT chunk");
749 if (info_ptr != NULL && (info_ptr->valid & PNG_INFO_sBIT))
751 png_warning(png_ptr, "Duplicate sBIT chunk");
752 png_crc_finish(png_ptr, length);
756 if (png_ptr->color_type == PNG_COLOR_TYPE_PALETTE)
759 truelen = (png_size_t)png_ptr->channels;
761 if (length != truelen || length > 4)
763 png_warning(png_ptr, "Incorrect sBIT chunk length");
764 png_crc_finish(png_ptr, length);
768 png_crc_read(png_ptr, buf, truelen);
769 if (png_crc_finish(png_ptr, 0))
772 if (png_ptr->color_type & PNG_COLOR_MASK_COLOR)
774 png_ptr->sig_bit.red = buf[0];
775 png_ptr->sig_bit.green = buf[1];
776 png_ptr->sig_bit.blue = buf[2];
777 png_ptr->sig_bit.alpha = buf[3];
781 png_ptr->sig_bit.gray = buf[0];
782 png_ptr->sig_bit.red = buf[0];
783 png_ptr->sig_bit.green = buf[0];
784 png_ptr->sig_bit.blue = buf[0];
785 png_ptr->sig_bit.alpha = buf[1];
787 png_set_sBIT(png_ptr, info_ptr, &(png_ptr->sig_bit));
791 #ifdef PNG_READ_cHRM_SUPPORTED
793 png_handle_cHRM(png_structp png_ptr, png_infop info_ptr, png_uint_32 length)
796 #ifdef PNG_FLOATING_POINT_SUPPORTED
797 float white_x, white_y, red_x, red_y, green_x, green_y, blue_x, blue_y;
799 png_fixed_point int_x_white, int_y_white, int_x_red, int_y_red, int_x_green,
800 int_y_green, int_x_blue, int_y_blue;
802 png_uint_32 uint_x, uint_y;
804 png_debug(1, "in png_handle_cHRM");
806 if (!(png_ptr->mode & PNG_HAVE_IHDR))
807 png_error(png_ptr, "Missing IHDR before cHRM");
808 else if (png_ptr->mode & PNG_HAVE_IDAT)
810 png_warning(png_ptr, "Invalid cHRM after IDAT");
811 png_crc_finish(png_ptr, length);
814 else if (png_ptr->mode & PNG_HAVE_PLTE)
815 /* Should be an error, but we can cope with it */
816 png_warning(png_ptr, "Missing PLTE before cHRM");
818 if (info_ptr != NULL && (info_ptr->valid & PNG_INFO_cHRM)
819 #ifdef PNG_READ_sRGB_SUPPORTED
820 && !(info_ptr->valid & PNG_INFO_sRGB)
824 png_warning(png_ptr, "Duplicate cHRM chunk");
825 png_crc_finish(png_ptr, length);
831 png_warning(png_ptr, "Incorrect cHRM chunk length");
832 png_crc_finish(png_ptr, length);
836 png_crc_read(png_ptr, buf, 32);
837 if (png_crc_finish(png_ptr, 0))
840 uint_x = png_get_uint_32(buf);
841 uint_y = png_get_uint_32(buf + 4);
842 int_x_white = (png_fixed_point)uint_x;
843 int_y_white = (png_fixed_point)uint_y;
845 uint_x = png_get_uint_32(buf + 8);
846 uint_y = png_get_uint_32(buf + 12);
847 int_x_red = (png_fixed_point)uint_x;
848 int_y_red = (png_fixed_point)uint_y;
850 uint_x = png_get_uint_32(buf + 16);
851 uint_y = png_get_uint_32(buf + 20);
852 int_x_green = (png_fixed_point)uint_x;
853 int_y_green = (png_fixed_point)uint_y;
855 uint_x = png_get_uint_32(buf + 24);
856 uint_y = png_get_uint_32(buf + 28);
857 int_x_blue = (png_fixed_point)uint_x;
858 int_y_blue = (png_fixed_point)uint_y;
860 #ifdef PNG_FLOATING_POINT_SUPPORTED
861 white_x = (float)int_x_white / (float)100000.0;
862 white_y = (float)int_y_white / (float)100000.0;
863 red_x = (float)int_x_red / (float)100000.0;
864 red_y = (float)int_y_red / (float)100000.0;
865 green_x = (float)int_x_green / (float)100000.0;
866 green_y = (float)int_y_green / (float)100000.0;
867 blue_x = (float)int_x_blue / (float)100000.0;
868 blue_y = (float)int_y_blue / (float)100000.0;
871 #ifdef PNG_READ_sRGB_SUPPORTED
872 if ((info_ptr != NULL) && (info_ptr->valid & PNG_INFO_sRGB))
874 if (PNG_OUT_OF_RANGE(int_x_white, 31270, 1000) ||
875 PNG_OUT_OF_RANGE(int_y_white, 32900, 1000) ||
876 PNG_OUT_OF_RANGE(int_x_red, 64000L, 1000) ||
877 PNG_OUT_OF_RANGE(int_y_red, 33000, 1000) ||
878 PNG_OUT_OF_RANGE(int_x_green, 30000, 1000) ||
879 PNG_OUT_OF_RANGE(int_y_green, 60000L, 1000) ||
880 PNG_OUT_OF_RANGE(int_x_blue, 15000, 1000) ||
881 PNG_OUT_OF_RANGE(int_y_blue, 6000, 1000))
884 "Ignoring incorrect cHRM value when sRGB is also present");
885 #ifdef PNG_CONSOLE_IO_SUPPORTED
886 #ifdef PNG_FLOATING_POINT_SUPPORTED
887 fprintf(stderr, "wx=%f, wy=%f, rx=%f, ry=%f\n",
888 white_x, white_y, red_x, red_y);
889 fprintf(stderr, "gx=%f, gy=%f, bx=%f, by=%f\n",
890 green_x, green_y, blue_x, blue_y);
892 fprintf(stderr, "wx=%ld, wy=%ld, rx=%ld, ry=%ld\n",
893 int_x_white, int_y_white, int_x_red, int_y_red);
894 fprintf(stderr, "gx=%ld, gy=%ld, bx=%ld, by=%ld\n",
895 int_x_green, int_y_green, int_x_blue, int_y_blue);
897 #endif /* PNG_CONSOLE_IO_SUPPORTED */
901 #endif /* PNG_READ_sRGB_SUPPORTED */
903 #ifdef PNG_FLOATING_POINT_SUPPORTED
904 png_set_cHRM(png_ptr, info_ptr,
905 white_x, white_y, red_x, red_y, green_x, green_y, blue_x, blue_y);
907 #ifdef PNG_FIXED_POINT_SUPPORTED
908 png_set_cHRM_fixed(png_ptr, info_ptr,
909 int_x_white, int_y_white, int_x_red, int_y_red, int_x_green,
910 int_y_green, int_x_blue, int_y_blue);
915 #ifdef PNG_READ_sRGB_SUPPORTED
917 png_handle_sRGB(png_structp png_ptr, png_infop info_ptr, png_uint_32 length)
922 png_debug(1, "in png_handle_sRGB");
924 if (!(png_ptr->mode & PNG_HAVE_IHDR))
925 png_error(png_ptr, "Missing IHDR before sRGB");
926 else if (png_ptr->mode & PNG_HAVE_IDAT)
928 png_warning(png_ptr, "Invalid sRGB after IDAT");
929 png_crc_finish(png_ptr, length);
932 else if (png_ptr->mode & PNG_HAVE_PLTE)
933 /* Should be an error, but we can cope with it */
934 png_warning(png_ptr, "Out of place sRGB chunk");
936 if (info_ptr != NULL && (info_ptr->valid & PNG_INFO_sRGB))
938 png_warning(png_ptr, "Duplicate sRGB chunk");
939 png_crc_finish(png_ptr, length);
945 png_warning(png_ptr, "Incorrect sRGB chunk length");
946 png_crc_finish(png_ptr, length);
950 png_crc_read(png_ptr, buf, 1);
951 if (png_crc_finish(png_ptr, 0))
955 /* Check for bad intent */
956 if (intent >= PNG_sRGB_INTENT_LAST)
958 png_warning(png_ptr, "Unknown sRGB intent");
962 #if defined(PNG_READ_gAMA_SUPPORTED) && defined(PNG_READ_GAMMA_SUPPORTED)
963 if (info_ptr != NULL && (info_ptr->valid & PNG_INFO_gAMA))
965 png_fixed_point igamma;
966 #ifdef PNG_FIXED_POINT_SUPPORTED
967 igamma=info_ptr->int_gamma;
969 # ifdef PNG_FLOATING_POINT_SUPPORTED
970 igamma=(png_fixed_point)(info_ptr->gamma * 100000.);
973 if (PNG_OUT_OF_RANGE(igamma, 45500L, 500))
976 "Ignoring incorrect gAMA value when sRGB is also present");
977 #ifdef PNG_CONSOLE_IO_SUPPORTED
978 # ifdef PNG_FIXED_POINT_SUPPORTED
979 fprintf(stderr, "incorrect gamma=(%d/100000)\n",
980 (int)png_ptr->int_gamma);
982 # ifdef PNG_FLOATING_POINT_SUPPORTED
983 fprintf(stderr, "incorrect gamma=%f\n", png_ptr->gamma);
989 #endif /* PNG_READ_gAMA_SUPPORTED */
991 #ifdef PNG_READ_cHRM_SUPPORTED
992 #ifdef PNG_FIXED_POINT_SUPPORTED
993 if (info_ptr != NULL && (info_ptr->valid & PNG_INFO_cHRM))
994 if (PNG_OUT_OF_RANGE(info_ptr->int_x_white, 31270, 1000) ||
995 PNG_OUT_OF_RANGE(info_ptr->int_y_white, 32900, 1000) ||
996 PNG_OUT_OF_RANGE(info_ptr->int_x_red, 64000L, 1000) ||
997 PNG_OUT_OF_RANGE(info_ptr->int_y_red, 33000, 1000) ||
998 PNG_OUT_OF_RANGE(info_ptr->int_x_green, 30000, 1000) ||
999 PNG_OUT_OF_RANGE(info_ptr->int_y_green, 60000L, 1000) ||
1000 PNG_OUT_OF_RANGE(info_ptr->int_x_blue, 15000, 1000) ||
1001 PNG_OUT_OF_RANGE(info_ptr->int_y_blue, 6000, 1000))
1003 png_warning(png_ptr,
1004 "Ignoring incorrect cHRM value when sRGB is also present");
1006 #endif /* PNG_FIXED_POINT_SUPPORTED */
1007 #endif /* PNG_READ_cHRM_SUPPORTED */
1009 png_set_sRGB_gAMA_and_cHRM(png_ptr, info_ptr, intent);
1011 #endif /* PNG_READ_sRGB_SUPPORTED */
1013 #ifdef PNG_READ_iCCP_SUPPORTED
1015 png_handle_iCCP(png_structp png_ptr, png_infop info_ptr, png_uint_32 length)
1016 /* Note: this does not properly handle chunks that are > 64K under DOS */
1018 png_byte compression_type;
1021 png_uint_32 skip = 0;
1022 png_uint_32 profile_size, profile_length;
1023 png_size_t slength, prefix_length, data_length;
1025 png_debug(1, "in png_handle_iCCP");
1027 if (!(png_ptr->mode & PNG_HAVE_IHDR))
1028 png_error(png_ptr, "Missing IHDR before iCCP");
1029 else if (png_ptr->mode & PNG_HAVE_IDAT)
1031 png_warning(png_ptr, "Invalid iCCP after IDAT");
1032 png_crc_finish(png_ptr, length);
1035 else if (png_ptr->mode & PNG_HAVE_PLTE)
1036 /* Should be an error, but we can cope with it */
1037 png_warning(png_ptr, "Out of place iCCP chunk");
1039 if (info_ptr != NULL && (info_ptr->valid & PNG_INFO_iCCP))
1041 png_warning(png_ptr, "Duplicate iCCP chunk");
1042 png_crc_finish(png_ptr, length);
1046 #ifdef PNG_MAX_MALLOC_64K
1047 if (length > (png_uint_32)65535L)
1049 png_warning(png_ptr, "iCCP chunk too large to fit in memory");
1050 skip = length - (png_uint_32)65535L;
1051 length = (png_uint_32)65535L;
1055 png_free(png_ptr, png_ptr->chunkdata);
1056 png_ptr->chunkdata = (png_charp)png_malloc(png_ptr, length + 1);
1057 slength = (png_size_t)length;
1058 png_crc_read(png_ptr, (png_bytep)png_ptr->chunkdata, slength);
1060 if (png_crc_finish(png_ptr, skip))
1062 png_free(png_ptr, png_ptr->chunkdata);
1063 png_ptr->chunkdata = NULL;
1067 png_ptr->chunkdata[slength] = 0x00;
1069 for (profile = png_ptr->chunkdata; *profile; profile++)
1070 /* Empty loop to find end of name */ ;
1074 /* There should be at least one zero (the compression type byte)
1075 * following the separator, and we should be on it
1077 if ( profile >= png_ptr->chunkdata + slength - 1)
1079 png_free(png_ptr, png_ptr->chunkdata);
1080 png_ptr->chunkdata = NULL;
1081 png_warning(png_ptr, "Malformed iCCP chunk");
1085 /* Compression_type should always be zero */
1086 compression_type = *profile++;
1087 if (compression_type)
1089 png_warning(png_ptr, "Ignoring nonzero compression type in iCCP chunk");
1090 compression_type = 0x00; /* Reset it to zero (libpng-1.0.6 through 1.0.8
1094 prefix_length = profile - png_ptr->chunkdata;
1095 png_decompress_chunk(png_ptr, compression_type,
1096 slength, prefix_length, &data_length);
1098 profile_length = data_length - prefix_length;
1100 if ( prefix_length > data_length || profile_length < 4)
1102 png_free(png_ptr, png_ptr->chunkdata);
1103 png_ptr->chunkdata = NULL;
1104 png_warning(png_ptr, "Profile size field missing from iCCP chunk");
1108 /* Check the profile_size recorded in the first 32 bits of the ICC profile */
1109 pC = (png_bytep)(png_ptr->chunkdata + prefix_length);
1110 profile_size = ((*(pC ))<<24) |
1115 if (profile_size < profile_length)
1116 profile_length = profile_size;
1118 if (profile_size > profile_length)
1120 png_free(png_ptr, png_ptr->chunkdata);
1121 png_ptr->chunkdata = NULL;
1122 png_warning(png_ptr, "Ignoring truncated iCCP profile");
1123 #ifdef PNG_STDIO_SUPPORTED
1127 png_snprintf(umsg, 50, "declared profile size = %lu",
1128 (unsigned long)profile_size);
1129 png_warning(png_ptr, umsg);
1130 png_snprintf(umsg, 50, "actual profile length = %lu",
1131 (unsigned long)profile_length);
1132 png_warning(png_ptr, umsg);
1138 png_set_iCCP(png_ptr, info_ptr, png_ptr->chunkdata,
1139 compression_type, png_ptr->chunkdata + prefix_length, profile_length);
1140 png_free(png_ptr, png_ptr->chunkdata);
1141 png_ptr->chunkdata = NULL;
1143 #endif /* PNG_READ_iCCP_SUPPORTED */
1145 #ifdef PNG_READ_sPLT_SUPPORTED
1147 png_handle_sPLT(png_structp png_ptr, png_infop info_ptr, png_uint_32 length)
1148 /* Note: this does not properly handle chunks that are > 64K under DOS */
1150 png_bytep entry_start;
1151 png_sPLT_t new_palette;
1152 #ifdef PNG_POINTER_INDEXING_SUPPORTED
1155 int data_length, entry_size, i;
1156 png_uint_32 skip = 0;
1159 png_debug(1, "in png_handle_sPLT");
1161 #ifdef PNG_USER_LIMITS_SUPPORTED
1163 if (png_ptr->user_chunk_cache_max != 0)
1165 if (png_ptr->user_chunk_cache_max == 1)
1167 png_crc_finish(png_ptr, length);
1170 if (--png_ptr->user_chunk_cache_max == 1)
1172 png_warning(png_ptr, "No space in chunk cache for sPLT");
1173 png_crc_finish(png_ptr, length);
1179 if (!(png_ptr->mode & PNG_HAVE_IHDR))
1180 png_error(png_ptr, "Missing IHDR before sPLT");
1181 else if (png_ptr->mode & PNG_HAVE_IDAT)
1183 png_warning(png_ptr, "Invalid sPLT after IDAT");
1184 png_crc_finish(png_ptr, length);
1188 #ifdef PNG_MAX_MALLOC_64K
1189 if (length > (png_uint_32)65535L)
1191 png_warning(png_ptr, "sPLT chunk too large to fit in memory");
1192 skip = length - (png_uint_32)65535L;
1193 length = (png_uint_32)65535L;
1197 png_free(png_ptr, png_ptr->chunkdata);
1198 png_ptr->chunkdata = (png_charp)png_malloc(png_ptr, length + 1);
1199 slength = (png_size_t)length;
1200 png_crc_read(png_ptr, (png_bytep)png_ptr->chunkdata, slength);
1202 if (png_crc_finish(png_ptr, skip))
1204 png_free(png_ptr, png_ptr->chunkdata);
1205 png_ptr->chunkdata = NULL;
1209 png_ptr->chunkdata[slength] = 0x00;
1211 for (entry_start = (png_bytep)png_ptr->chunkdata; *entry_start;
1213 /* Empty loop to find end of name */ ;
1216 /* A sample depth should follow the separator, and we should be on it */
1217 if (entry_start > (png_bytep)png_ptr->chunkdata + slength - 2)
1219 png_free(png_ptr, png_ptr->chunkdata);
1220 png_ptr->chunkdata = NULL;
1221 png_warning(png_ptr, "malformed sPLT chunk");
1225 new_palette.depth = *entry_start++;
1226 entry_size = (new_palette.depth == 8 ? 6 : 10);
1227 data_length = (slength - (entry_start - (png_bytep)png_ptr->chunkdata));
1229 /* Integrity-check the data length */
1230 if (data_length % entry_size)
1232 png_free(png_ptr, png_ptr->chunkdata);
1233 png_ptr->chunkdata = NULL;
1234 png_warning(png_ptr, "sPLT chunk has bad length");
1238 new_palette.nentries = (png_int_32) ( data_length / entry_size);
1239 if ((png_uint_32) new_palette.nentries >
1240 (png_uint_32) (PNG_SIZE_MAX / png_sizeof(png_sPLT_entry)))
1242 png_warning(png_ptr, "sPLT chunk too long");
1245 new_palette.entries = (png_sPLT_entryp)png_malloc_warn(
1246 png_ptr, new_palette.nentries * png_sizeof(png_sPLT_entry));
1247 if (new_palette.entries == NULL)
1249 png_warning(png_ptr, "sPLT chunk requires too much memory");
1253 #ifdef PNG_POINTER_INDEXING_SUPPORTED
1254 for (i = 0; i < new_palette.nentries; i++)
1256 pp = new_palette.entries + i;
1258 if (new_palette.depth == 8)
1260 pp->red = *entry_start++;
1261 pp->green = *entry_start++;
1262 pp->blue = *entry_start++;
1263 pp->alpha = *entry_start++;
1267 pp->red = png_get_uint_16(entry_start); entry_start += 2;
1268 pp->green = png_get_uint_16(entry_start); entry_start += 2;
1269 pp->blue = png_get_uint_16(entry_start); entry_start += 2;
1270 pp->alpha = png_get_uint_16(entry_start); entry_start += 2;
1272 pp->frequency = png_get_uint_16(entry_start); entry_start += 2;
1275 pp = new_palette.entries;
1276 for (i = 0; i < new_palette.nentries; i++)
1279 if (new_palette.depth == 8)
1281 pp[i].red = *entry_start++;
1282 pp[i].green = *entry_start++;
1283 pp[i].blue = *entry_start++;
1284 pp[i].alpha = *entry_start++;
1288 pp[i].red = png_get_uint_16(entry_start); entry_start += 2;
1289 pp[i].green = png_get_uint_16(entry_start); entry_start += 2;
1290 pp[i].blue = png_get_uint_16(entry_start); entry_start += 2;
1291 pp[i].alpha = png_get_uint_16(entry_start); entry_start += 2;
1293 pp->frequency = png_get_uint_16(entry_start); entry_start += 2;
1297 /* Discard all chunk data except the name and stash that */
1298 new_palette.name = png_ptr->chunkdata;
1300 png_set_sPLT(png_ptr, info_ptr, &new_palette, 1);
1302 png_free(png_ptr, png_ptr->chunkdata);
1303 png_ptr->chunkdata = NULL;
1304 png_free(png_ptr, new_palette.entries);
1306 #endif /* PNG_READ_sPLT_SUPPORTED */
1308 #ifdef PNG_READ_tRNS_SUPPORTED
1310 png_handle_tRNS(png_structp png_ptr, png_infop info_ptr, png_uint_32 length)
1312 png_byte readbuf[PNG_MAX_PALETTE_LENGTH];
1314 png_debug(1, "in png_handle_tRNS");
1316 if (!(png_ptr->mode & PNG_HAVE_IHDR))
1317 png_error(png_ptr, "Missing IHDR before tRNS");
1318 else if (png_ptr->mode & PNG_HAVE_IDAT)
1320 png_warning(png_ptr, "Invalid tRNS after IDAT");
1321 png_crc_finish(png_ptr, length);
1324 else if (info_ptr != NULL && (info_ptr->valid & PNG_INFO_tRNS))
1326 png_warning(png_ptr, "Duplicate tRNS chunk");
1327 png_crc_finish(png_ptr, length);
1331 if (png_ptr->color_type == PNG_COLOR_TYPE_GRAY)
1337 png_warning(png_ptr, "Incorrect tRNS chunk length");
1338 png_crc_finish(png_ptr, length);
1342 png_crc_read(png_ptr, buf, 2);
1343 png_ptr->num_trans = 1;
1344 png_ptr->trans_color.gray = png_get_uint_16(buf);
1346 else if (png_ptr->color_type == PNG_COLOR_TYPE_RGB)
1352 png_warning(png_ptr, "Incorrect tRNS chunk length");
1353 png_crc_finish(png_ptr, length);
1356 png_crc_read(png_ptr, buf, (png_size_t)length);
1357 png_ptr->num_trans = 1;
1358 png_ptr->trans_color.red = png_get_uint_16(buf);
1359 png_ptr->trans_color.green = png_get_uint_16(buf + 2);
1360 png_ptr->trans_color.blue = png_get_uint_16(buf + 4);
1362 else if (png_ptr->color_type == PNG_COLOR_TYPE_PALETTE)
1364 if (!(png_ptr->mode & PNG_HAVE_PLTE))
1366 /* Should be an error, but we can cope with it. */
1367 png_warning(png_ptr, "Missing PLTE before tRNS");
1369 if (length > (png_uint_32)png_ptr->num_palette ||
1370 length > PNG_MAX_PALETTE_LENGTH)
1372 png_warning(png_ptr, "Incorrect tRNS chunk length");
1373 png_crc_finish(png_ptr, length);
1378 png_warning(png_ptr, "Zero length tRNS chunk");
1379 png_crc_finish(png_ptr, length);
1382 png_crc_read(png_ptr, readbuf, (png_size_t)length);
1383 png_ptr->num_trans = (png_uint_16)length;
1387 png_warning(png_ptr, "tRNS chunk not allowed with alpha channel");
1388 png_crc_finish(png_ptr, length);
1392 if (png_crc_finish(png_ptr, 0))
1394 png_ptr->num_trans = 0;
1398 png_set_tRNS(png_ptr, info_ptr, readbuf, png_ptr->num_trans,
1399 &(png_ptr->trans_color));
1403 #ifdef PNG_READ_bKGD_SUPPORTED
1405 png_handle_bKGD(png_structp png_ptr, png_infop info_ptr, png_uint_32 length)
1410 png_debug(1, "in png_handle_bKGD");
1412 if (!(png_ptr->mode & PNG_HAVE_IHDR))
1413 png_error(png_ptr, "Missing IHDR before bKGD");
1414 else if (png_ptr->mode & PNG_HAVE_IDAT)
1416 png_warning(png_ptr, "Invalid bKGD after IDAT");
1417 png_crc_finish(png_ptr, length);
1420 else if (png_ptr->color_type == PNG_COLOR_TYPE_PALETTE &&
1421 !(png_ptr->mode & PNG_HAVE_PLTE))
1423 png_warning(png_ptr, "Missing PLTE before bKGD");
1424 png_crc_finish(png_ptr, length);
1427 else if (info_ptr != NULL && (info_ptr->valid & PNG_INFO_bKGD))
1429 png_warning(png_ptr, "Duplicate bKGD chunk");
1430 png_crc_finish(png_ptr, length);
1434 if (png_ptr->color_type == PNG_COLOR_TYPE_PALETTE)
1436 else if (png_ptr->color_type & PNG_COLOR_MASK_COLOR)
1441 if (length != truelen)
1443 png_warning(png_ptr, "Incorrect bKGD chunk length");
1444 png_crc_finish(png_ptr, length);
1448 png_crc_read(png_ptr, buf, truelen);
1449 if (png_crc_finish(png_ptr, 0))
1452 /* We convert the index value into RGB components so that we can allow
1453 * arbitrary RGB values for background when we have transparency, and
1454 * so it is easy to determine the RGB values of the background color
1455 * from the info_ptr struct. */
1456 if (png_ptr->color_type == PNG_COLOR_TYPE_PALETTE)
1458 png_ptr->background.index = buf[0];
1459 if (info_ptr && info_ptr->num_palette)
1461 if (buf[0] >= info_ptr->num_palette)
1463 png_warning(png_ptr, "Incorrect bKGD chunk index value");
1466 png_ptr->background.red =
1467 (png_uint_16)png_ptr->palette[buf[0]].red;
1468 png_ptr->background.green =
1469 (png_uint_16)png_ptr->palette[buf[0]].green;
1470 png_ptr->background.blue =
1471 (png_uint_16)png_ptr->palette[buf[0]].blue;
1474 else if (!(png_ptr->color_type & PNG_COLOR_MASK_COLOR)) /* GRAY */
1476 png_ptr->background.red =
1477 png_ptr->background.green =
1478 png_ptr->background.blue =
1479 png_ptr->background.gray = png_get_uint_16(buf);
1483 png_ptr->background.red = png_get_uint_16(buf);
1484 png_ptr->background.green = png_get_uint_16(buf + 2);
1485 png_ptr->background.blue = png_get_uint_16(buf + 4);
1488 png_set_bKGD(png_ptr, info_ptr, &(png_ptr->background));
1492 #ifdef PNG_READ_hIST_SUPPORTED
1494 png_handle_hIST(png_structp png_ptr, png_infop info_ptr, png_uint_32 length)
1496 unsigned int num, i;
1497 png_uint_16 readbuf[PNG_MAX_PALETTE_LENGTH];
1499 png_debug(1, "in png_handle_hIST");
1501 if (!(png_ptr->mode & PNG_HAVE_IHDR))
1502 png_error(png_ptr, "Missing IHDR before hIST");
1503 else if (png_ptr->mode & PNG_HAVE_IDAT)
1505 png_warning(png_ptr, "Invalid hIST after IDAT");
1506 png_crc_finish(png_ptr, length);
1509 else if (!(png_ptr->mode & PNG_HAVE_PLTE))
1511 png_warning(png_ptr, "Missing PLTE before hIST");
1512 png_crc_finish(png_ptr, length);
1515 else if (info_ptr != NULL && (info_ptr->valid & PNG_INFO_hIST))
1517 png_warning(png_ptr, "Duplicate hIST chunk");
1518 png_crc_finish(png_ptr, length);
1523 if (num != (unsigned int) png_ptr->num_palette || num >
1524 (unsigned int) PNG_MAX_PALETTE_LENGTH)
1526 png_warning(png_ptr, "Incorrect hIST chunk length");
1527 png_crc_finish(png_ptr, length);
1531 for (i = 0; i < num; i++)
1535 png_crc_read(png_ptr, buf, 2);
1536 readbuf[i] = png_get_uint_16(buf);
1539 if (png_crc_finish(png_ptr, 0))
1542 png_set_hIST(png_ptr, info_ptr, readbuf);
1546 #ifdef PNG_READ_pHYs_SUPPORTED
1548 png_handle_pHYs(png_structp png_ptr, png_infop info_ptr, png_uint_32 length)
1551 png_uint_32 res_x, res_y;
1554 png_debug(1, "in png_handle_pHYs");
1556 if (!(png_ptr->mode & PNG_HAVE_IHDR))
1557 png_error(png_ptr, "Missing IHDR before pHYs");
1558 else if (png_ptr->mode & PNG_HAVE_IDAT)
1560 png_warning(png_ptr, "Invalid pHYs after IDAT");
1561 png_crc_finish(png_ptr, length);
1564 else if (info_ptr != NULL && (info_ptr->valid & PNG_INFO_pHYs))
1566 png_warning(png_ptr, "Duplicate pHYs chunk");
1567 png_crc_finish(png_ptr, length);
1573 png_warning(png_ptr, "Incorrect pHYs chunk length");
1574 png_crc_finish(png_ptr, length);
1578 png_crc_read(png_ptr, buf, 9);
1579 if (png_crc_finish(png_ptr, 0))
1582 res_x = png_get_uint_32(buf);
1583 res_y = png_get_uint_32(buf + 4);
1585 png_set_pHYs(png_ptr, info_ptr, res_x, res_y, unit_type);
1589 #ifdef PNG_READ_oFFs_SUPPORTED
1591 png_handle_oFFs(png_structp png_ptr, png_infop info_ptr, png_uint_32 length)
1594 png_int_32 offset_x, offset_y;
1597 png_debug(1, "in png_handle_oFFs");
1599 if (!(png_ptr->mode & PNG_HAVE_IHDR))
1600 png_error(png_ptr, "Missing IHDR before oFFs");
1601 else if (png_ptr->mode & PNG_HAVE_IDAT)
1603 png_warning(png_ptr, "Invalid oFFs after IDAT");
1604 png_crc_finish(png_ptr, length);
1607 else if (info_ptr != NULL && (info_ptr->valid & PNG_INFO_oFFs))
1609 png_warning(png_ptr, "Duplicate oFFs chunk");
1610 png_crc_finish(png_ptr, length);
1616 png_warning(png_ptr, "Incorrect oFFs chunk length");
1617 png_crc_finish(png_ptr, length);
1621 png_crc_read(png_ptr, buf, 9);
1622 if (png_crc_finish(png_ptr, 0))
1625 offset_x = png_get_int_32(buf);
1626 offset_y = png_get_int_32(buf + 4);
1628 png_set_oFFs(png_ptr, info_ptr, offset_x, offset_y, unit_type);
1632 #ifdef PNG_READ_pCAL_SUPPORTED
1633 /* Read the pCAL chunk (described in the PNG Extensions document) */
1635 png_handle_pCAL(png_structp png_ptr, png_infop info_ptr, png_uint_32 length)
1638 png_byte type, nparams;
1639 png_charp buf, units, endptr;
1644 png_debug(1, "in png_handle_pCAL");
1646 if (!(png_ptr->mode & PNG_HAVE_IHDR))
1647 png_error(png_ptr, "Missing IHDR before pCAL");
1648 else if (png_ptr->mode & PNG_HAVE_IDAT)
1650 png_warning(png_ptr, "Invalid pCAL after IDAT");
1651 png_crc_finish(png_ptr, length);
1654 else if (info_ptr != NULL && (info_ptr->valid & PNG_INFO_pCAL))
1656 png_warning(png_ptr, "Duplicate pCAL chunk");
1657 png_crc_finish(png_ptr, length);
1661 png_debug1(2, "Allocating and reading pCAL chunk data (%lu bytes)",
1663 png_free(png_ptr, png_ptr->chunkdata);
1664 png_ptr->chunkdata = (png_charp)png_malloc_warn(png_ptr, length + 1);
1665 if (png_ptr->chunkdata == NULL)
1667 png_warning(png_ptr, "No memory for pCAL purpose");
1670 slength = (png_size_t)length;
1671 png_crc_read(png_ptr, (png_bytep)png_ptr->chunkdata, slength);
1673 if (png_crc_finish(png_ptr, 0))
1675 png_free(png_ptr, png_ptr->chunkdata);
1676 png_ptr->chunkdata = NULL;
1680 png_ptr->chunkdata[slength] = 0x00; /* Null terminate the last string */
1682 png_debug(3, "Finding end of pCAL purpose string");
1683 for (buf = png_ptr->chunkdata; *buf; buf++)
1686 endptr = png_ptr->chunkdata + slength;
1688 /* We need to have at least 12 bytes after the purpose string
1689 in order to get the parameter information. */
1690 if (endptr <= buf + 12)
1692 png_warning(png_ptr, "Invalid pCAL data");
1693 png_free(png_ptr, png_ptr->chunkdata);
1694 png_ptr->chunkdata = NULL;
1698 png_debug(3, "Reading pCAL X0, X1, type, nparams, and units");
1699 X0 = png_get_int_32((png_bytep)buf+1);
1700 X1 = png_get_int_32((png_bytep)buf+5);
1705 png_debug(3, "Checking pCAL equation type and number of parameters");
1706 /* Check that we have the right number of parameters for known
1708 if ((type == PNG_EQUATION_LINEAR && nparams != 2) ||
1709 (type == PNG_EQUATION_BASE_E && nparams != 3) ||
1710 (type == PNG_EQUATION_ARBITRARY && nparams != 3) ||
1711 (type == PNG_EQUATION_HYPERBOLIC && nparams != 4))
1713 png_warning(png_ptr, "Invalid pCAL parameters for equation type");
1714 png_free(png_ptr, png_ptr->chunkdata);
1715 png_ptr->chunkdata = NULL;
1718 else if (type >= PNG_EQUATION_LAST)
1720 png_warning(png_ptr, "Unrecognized equation type for pCAL chunk");
1723 for (buf = units; *buf; buf++)
1724 /* Empty loop to move past the units string. */ ;
1726 png_debug(3, "Allocating pCAL parameters array");
1727 params = (png_charpp)png_malloc_warn(png_ptr,
1728 (png_size_t)(nparams * png_sizeof(png_charp)));
1731 png_free(png_ptr, png_ptr->chunkdata);
1732 png_ptr->chunkdata = NULL;
1733 png_warning(png_ptr, "No memory for pCAL params");
1737 /* Get pointers to the start of each parameter string. */
1738 for (i = 0; i < (int)nparams; i++)
1740 buf++; /* Skip the null string terminator from previous parameter. */
1742 png_debug1(3, "Reading pCAL parameter %d", i);
1743 for (params[i] = buf; buf <= endptr && *buf != 0x00; buf++)
1744 /* Empty loop to move past each parameter string */ ;
1746 /* Make sure we haven't run out of data yet */
1749 png_warning(png_ptr, "Invalid pCAL data");
1750 png_free(png_ptr, png_ptr->chunkdata);
1751 png_ptr->chunkdata = NULL;
1752 png_free(png_ptr, params);
1757 png_set_pCAL(png_ptr, info_ptr, png_ptr->chunkdata, X0, X1, type, nparams,
1760 png_free(png_ptr, png_ptr->chunkdata);
1761 png_ptr->chunkdata = NULL;
1762 png_free(png_ptr, params);
1766 #ifdef PNG_READ_sCAL_SUPPORTED
1767 /* Read the sCAL chunk */
1769 png_handle_sCAL(png_structp png_ptr, png_infop info_ptr, png_uint_32 length)
1772 #ifdef PNG_FLOATING_POINT_SUPPORTED
1773 double width, height;
1776 #ifdef PNG_FIXED_POINT_SUPPORTED
1777 png_charp swidth, sheight;
1782 png_debug(1, "in png_handle_sCAL");
1784 if (!(png_ptr->mode & PNG_HAVE_IHDR))
1785 png_error(png_ptr, "Missing IHDR before sCAL");
1786 else if (png_ptr->mode & PNG_HAVE_IDAT)
1788 png_warning(png_ptr, "Invalid sCAL after IDAT");
1789 png_crc_finish(png_ptr, length);
1792 else if (info_ptr != NULL && (info_ptr->valid & PNG_INFO_sCAL))
1794 png_warning(png_ptr, "Duplicate sCAL chunk");
1795 png_crc_finish(png_ptr, length);
1799 png_debug1(2, "Allocating and reading sCAL chunk data (%lu bytes)",
1801 png_ptr->chunkdata = (png_charp)png_malloc_warn(png_ptr, length + 1);
1802 if (png_ptr->chunkdata == NULL)
1804 png_warning(png_ptr, "Out of memory while processing sCAL chunk");
1807 slength = (png_size_t)length;
1808 png_crc_read(png_ptr, (png_bytep)png_ptr->chunkdata, slength);
1810 if (png_crc_finish(png_ptr, 0))
1812 png_free(png_ptr, png_ptr->chunkdata);
1813 png_ptr->chunkdata = NULL;
1817 png_ptr->chunkdata[slength] = 0x00; /* Null terminate the last string */
1819 ep = png_ptr->chunkdata + 1; /* Skip unit byte */
1821 #ifdef PNG_FLOATING_POINT_SUPPORTED
1822 width = png_strtod(png_ptr, ep, &vp);
1825 png_warning(png_ptr, "malformed width string in sCAL chunk");
1829 #ifdef PNG_FIXED_POINT_SUPPORTED
1830 swidth = (png_charp)png_malloc_warn(png_ptr, png_strlen(ep) + 1);
1833 png_warning(png_ptr, "Out of memory while processing sCAL chunk width");
1836 png_memcpy(swidth, ep, png_strlen(ep));
1840 for (ep = png_ptr->chunkdata; *ep; ep++)
1844 if (png_ptr->chunkdata + slength < ep)
1846 png_warning(png_ptr, "Truncated sCAL chunk");
1847 #if defined(PNG_FIXED_POINT_SUPPORTED) && \
1848 !defined(PNG_FLOATING_POINT_SUPPORTED)
1849 png_free(png_ptr, swidth);
1851 png_free(png_ptr, png_ptr->chunkdata);
1852 png_ptr->chunkdata = NULL;
1856 #ifdef PNG_FLOATING_POINT_SUPPORTED
1857 height = png_strtod(png_ptr, ep, &vp);
1860 png_warning(png_ptr, "malformed height string in sCAL chunk");
1864 #ifdef PNG_FIXED_POINT_SUPPORTED
1865 sheight = (png_charp)png_malloc_warn(png_ptr, png_strlen(ep) + 1);
1866 if (sheight == NULL)
1868 png_warning(png_ptr, "Out of memory while processing sCAL chunk height");
1871 png_memcpy(sheight, ep, png_strlen(ep));
1875 if (png_ptr->chunkdata + slength < ep
1876 #ifdef PNG_FLOATING_POINT_SUPPORTED
1877 || width <= 0. || height <= 0.
1881 png_warning(png_ptr, "Invalid sCAL data");
1882 png_free(png_ptr, png_ptr->chunkdata);
1883 png_ptr->chunkdata = NULL;
1884 #if defined(PNG_FIXED_POINT_SUPPORTED) && !defined(PNG_FLOATING_POINT_SUPPORTED)
1885 png_free(png_ptr, swidth);
1886 png_free(png_ptr, sheight);
1892 #ifdef PNG_FLOATING_POINT_SUPPORTED
1893 png_set_sCAL(png_ptr, info_ptr, png_ptr->chunkdata[0], width, height);
1895 #ifdef PNG_FIXED_POINT_SUPPORTED
1896 png_set_sCAL_s(png_ptr, info_ptr, png_ptr->chunkdata[0], swidth, sheight);
1900 png_free(png_ptr, png_ptr->chunkdata);
1901 png_ptr->chunkdata = NULL;
1902 #if defined(PNG_FIXED_POINT_SUPPORTED) && !defined(PNG_FLOATING_POINT_SUPPORTED)
1903 png_free(png_ptr, swidth);
1904 png_free(png_ptr, sheight);
1909 #ifdef PNG_READ_tIME_SUPPORTED
1911 png_handle_tIME(png_structp png_ptr, png_infop info_ptr, png_uint_32 length)
1916 png_debug(1, "in png_handle_tIME");
1918 if (!(png_ptr->mode & PNG_HAVE_IHDR))
1919 png_error(png_ptr, "Out of place tIME chunk");
1920 else if (info_ptr != NULL && (info_ptr->valid & PNG_INFO_tIME))
1922 png_warning(png_ptr, "Duplicate tIME chunk");
1923 png_crc_finish(png_ptr, length);
1927 if (png_ptr->mode & PNG_HAVE_IDAT)
1928 png_ptr->mode |= PNG_AFTER_IDAT;
1932 png_warning(png_ptr, "Incorrect tIME chunk length");
1933 png_crc_finish(png_ptr, length);
1937 png_crc_read(png_ptr, buf, 7);
1938 if (png_crc_finish(png_ptr, 0))
1941 mod_time.second = buf[6];
1942 mod_time.minute = buf[5];
1943 mod_time.hour = buf[4];
1944 mod_time.day = buf[3];
1945 mod_time.month = buf[2];
1946 mod_time.year = png_get_uint_16(buf);
1948 png_set_tIME(png_ptr, info_ptr, &mod_time);
1952 #ifdef PNG_READ_tEXt_SUPPORTED
1953 /* Note: this does not properly handle chunks that are > 64K under DOS */
1955 png_handle_tEXt(png_structp png_ptr, png_infop info_ptr, png_uint_32 length)
1960 png_uint_32 skip = 0;
1964 png_debug(1, "in png_handle_tEXt");
1966 #ifdef PNG_USER_LIMITS_SUPPORTED
1967 if (png_ptr->user_chunk_cache_max != 0)
1969 if (png_ptr->user_chunk_cache_max == 1)
1971 png_crc_finish(png_ptr, length);
1974 if (--png_ptr->user_chunk_cache_max == 1)
1976 png_warning(png_ptr, "No space in chunk cache for tEXt");
1977 png_crc_finish(png_ptr, length);
1983 if (!(png_ptr->mode & PNG_HAVE_IHDR))
1984 png_error(png_ptr, "Missing IHDR before tEXt");
1986 if (png_ptr->mode & PNG_HAVE_IDAT)
1987 png_ptr->mode |= PNG_AFTER_IDAT;
1989 #ifdef PNG_MAX_MALLOC_64K
1990 if (length > (png_uint_32)65535L)
1992 png_warning(png_ptr, "tEXt chunk too large to fit in memory");
1993 skip = length - (png_uint_32)65535L;
1994 length = (png_uint_32)65535L;
1998 png_free(png_ptr, png_ptr->chunkdata);
2000 png_ptr->chunkdata = (png_charp)png_malloc_warn(png_ptr, length + 1);
2001 if (png_ptr->chunkdata == NULL)
2003 png_warning(png_ptr, "No memory to process text chunk");
2006 slength = (png_size_t)length;
2007 png_crc_read(png_ptr, (png_bytep)png_ptr->chunkdata, slength);
2009 if (png_crc_finish(png_ptr, skip))
2011 png_free(png_ptr, png_ptr->chunkdata);
2012 png_ptr->chunkdata = NULL;
2016 key = png_ptr->chunkdata;
2018 key[slength] = 0x00;
2020 for (text = key; *text; text++)
2021 /* Empty loop to find end of key */ ;
2023 if (text != key + slength)
2026 text_ptr = (png_textp)png_malloc_warn(png_ptr,
2027 png_sizeof(png_text));
2028 if (text_ptr == NULL)
2030 png_warning(png_ptr, "Not enough memory to process text chunk");
2031 png_free(png_ptr, png_ptr->chunkdata);
2032 png_ptr->chunkdata = NULL;
2035 text_ptr->compression = PNG_TEXT_COMPRESSION_NONE;
2036 text_ptr->key = key;
2037 #ifdef PNG_iTXt_SUPPORTED
2038 text_ptr->lang = NULL;
2039 text_ptr->lang_key = NULL;
2040 text_ptr->itxt_length = 0;
2042 text_ptr->text = text;
2043 text_ptr->text_length = png_strlen(text);
2045 ret = png_set_text_2(png_ptr, info_ptr, text_ptr, 1);
2047 png_free(png_ptr, png_ptr->chunkdata);
2048 png_ptr->chunkdata = NULL;
2049 png_free(png_ptr, text_ptr);
2051 png_warning(png_ptr, "Insufficient memory to process text chunk");
2055 #ifdef PNG_READ_zTXt_SUPPORTED
2056 /* Note: this does not correctly handle chunks that are > 64K under DOS */
2058 png_handle_zTXt(png_structp png_ptr, png_infop info_ptr, png_uint_32 length)
2064 png_size_t slength, prefix_len, data_len;
2066 png_debug(1, "in png_handle_zTXt");
2068 #ifdef PNG_USER_LIMITS_SUPPORTED
2069 if (png_ptr->user_chunk_cache_max != 0)
2071 if (png_ptr->user_chunk_cache_max == 1)
2073 png_crc_finish(png_ptr, length);
2076 if (--png_ptr->user_chunk_cache_max == 1)
2078 png_warning(png_ptr, "No space in chunk cache for zTXt");
2079 png_crc_finish(png_ptr, length);
2085 if (!(png_ptr->mode & PNG_HAVE_IHDR))
2086 png_error(png_ptr, "Missing IHDR before zTXt");
2088 if (png_ptr->mode & PNG_HAVE_IDAT)
2089 png_ptr->mode |= PNG_AFTER_IDAT;
2091 #ifdef PNG_MAX_MALLOC_64K
2092 /* We will no doubt have problems with chunks even half this size, but
2093 there is no hard and fast rule to tell us where to stop. */
2094 if (length > (png_uint_32)65535L)
2096 png_warning(png_ptr, "zTXt chunk too large to fit in memory");
2097 png_crc_finish(png_ptr, length);
2102 png_free(png_ptr, png_ptr->chunkdata);
2103 png_ptr->chunkdata = (png_charp)png_malloc_warn(png_ptr, length + 1);
2104 if (png_ptr->chunkdata == NULL)
2106 png_warning(png_ptr, "Out of memory processing zTXt chunk");
2109 slength = (png_size_t)length;
2110 png_crc_read(png_ptr, (png_bytep)png_ptr->chunkdata, slength);
2111 if (png_crc_finish(png_ptr, 0))
2113 png_free(png_ptr, png_ptr->chunkdata);
2114 png_ptr->chunkdata = NULL;
2118 png_ptr->chunkdata[slength] = 0x00;
2120 for (text = png_ptr->chunkdata; *text; text++)
2123 /* zTXt must have some text after the chunkdataword */
2124 if (text >= png_ptr->chunkdata + slength - 2)
2126 png_warning(png_ptr, "Truncated zTXt chunk");
2127 png_free(png_ptr, png_ptr->chunkdata);
2128 png_ptr->chunkdata = NULL;
2133 comp_type = *(++text);
2134 if (comp_type != PNG_TEXT_COMPRESSION_zTXt)
2136 png_warning(png_ptr, "Unknown compression type in zTXt chunk");
2137 comp_type = PNG_TEXT_COMPRESSION_zTXt;
2139 text++; /* Skip the compression_method byte */
2141 prefix_len = text - png_ptr->chunkdata;
2143 png_decompress_chunk(png_ptr, comp_type,
2144 (png_size_t)length, prefix_len, &data_len);
2146 text_ptr = (png_textp)png_malloc_warn(png_ptr,
2147 png_sizeof(png_text));
2148 if (text_ptr == NULL)
2150 png_warning(png_ptr, "Not enough memory to process zTXt chunk");
2151 png_free(png_ptr, png_ptr->chunkdata);
2152 png_ptr->chunkdata = NULL;
2155 text_ptr->compression = comp_type;
2156 text_ptr->key = png_ptr->chunkdata;
2157 #ifdef PNG_iTXt_SUPPORTED
2158 text_ptr->lang = NULL;
2159 text_ptr->lang_key = NULL;
2160 text_ptr->itxt_length = 0;
2162 text_ptr->text = png_ptr->chunkdata + prefix_len;
2163 text_ptr->text_length = data_len;
2165 ret = png_set_text_2(png_ptr, info_ptr, text_ptr, 1);
2167 png_free(png_ptr, text_ptr);
2168 png_free(png_ptr, png_ptr->chunkdata);
2169 png_ptr->chunkdata = NULL;
2171 png_error(png_ptr, "Insufficient memory to store zTXt chunk");
2175 #ifdef PNG_READ_iTXt_SUPPORTED
2176 /* Note: this does not correctly handle chunks that are > 64K under DOS */
2178 png_handle_iTXt(png_structp png_ptr, png_infop info_ptr, png_uint_32 length)
2181 png_charp key, lang, text, lang_key;
2185 png_size_t slength, prefix_len, data_len;
2187 png_debug(1, "in png_handle_iTXt");
2189 #ifdef PNG_USER_LIMITS_SUPPORTED
2190 if (png_ptr->user_chunk_cache_max != 0)
2192 if (png_ptr->user_chunk_cache_max == 1)
2194 png_crc_finish(png_ptr, length);
2197 if (--png_ptr->user_chunk_cache_max == 1)
2199 png_warning(png_ptr, "No space in chunk cache for iTXt");
2200 png_crc_finish(png_ptr, length);
2206 if (!(png_ptr->mode & PNG_HAVE_IHDR))
2207 png_error(png_ptr, "Missing IHDR before iTXt");
2209 if (png_ptr->mode & PNG_HAVE_IDAT)
2210 png_ptr->mode |= PNG_AFTER_IDAT;
2212 #ifdef PNG_MAX_MALLOC_64K
2213 /* We will no doubt have problems with chunks even half this size, but
2214 there is no hard and fast rule to tell us where to stop. */
2215 if (length > (png_uint_32)65535L)
2217 png_warning(png_ptr, "iTXt chunk too large to fit in memory");
2218 png_crc_finish(png_ptr, length);
2223 png_free(png_ptr, png_ptr->chunkdata);
2224 png_ptr->chunkdata = (png_charp)png_malloc_warn(png_ptr, length + 1);
2225 if (png_ptr->chunkdata == NULL)
2227 png_warning(png_ptr, "No memory to process iTXt chunk");
2230 slength = (png_size_t)length;
2231 png_crc_read(png_ptr, (png_bytep)png_ptr->chunkdata, slength);
2232 if (png_crc_finish(png_ptr, 0))
2234 png_free(png_ptr, png_ptr->chunkdata);
2235 png_ptr->chunkdata = NULL;
2239 png_ptr->chunkdata[slength] = 0x00;
2241 for (lang = png_ptr->chunkdata; *lang; lang++)
2243 lang++; /* Skip NUL separator */
2245 /* iTXt must have a language tag (possibly empty), two compression bytes,
2246 * translated keyword (possibly empty), and possibly some text after the
2250 if (lang >= png_ptr->chunkdata + slength - 3)
2252 png_warning(png_ptr, "Truncated iTXt chunk");
2253 png_free(png_ptr, png_ptr->chunkdata);
2254 png_ptr->chunkdata = NULL;
2259 comp_flag = *lang++;
2260 comp_type = *lang++;
2263 for (lang_key = lang; *lang_key; lang_key++)
2265 lang_key++; /* Skip NUL separator */
2267 if (lang_key >= png_ptr->chunkdata + slength)
2269 png_warning(png_ptr, "Truncated iTXt chunk");
2270 png_free(png_ptr, png_ptr->chunkdata);
2271 png_ptr->chunkdata = NULL;
2275 for (text = lang_key; *text; text++)
2277 text++; /* Skip NUL separator */
2278 if (text >= png_ptr->chunkdata + slength)
2280 png_warning(png_ptr, "Malformed iTXt chunk");
2281 png_free(png_ptr, png_ptr->chunkdata);
2282 png_ptr->chunkdata = NULL;
2286 prefix_len = text - png_ptr->chunkdata;
2288 key=png_ptr->chunkdata;
2290 png_decompress_chunk(png_ptr, comp_type,
2291 (size_t)length, prefix_len, &data_len);
2293 data_len = png_strlen(png_ptr->chunkdata + prefix_len);
2294 text_ptr = (png_textp)png_malloc_warn(png_ptr,
2295 png_sizeof(png_text));
2296 if (text_ptr == NULL)
2298 png_warning(png_ptr, "Not enough memory to process iTXt chunk");
2299 png_free(png_ptr, png_ptr->chunkdata);
2300 png_ptr->chunkdata = NULL;
2303 text_ptr->compression = (int)comp_flag + 1;
2304 text_ptr->lang_key = png_ptr->chunkdata + (lang_key - key);
2305 text_ptr->lang = png_ptr->chunkdata + (lang - key);
2306 text_ptr->itxt_length = data_len;
2307 text_ptr->text_length = 0;
2308 text_ptr->key = png_ptr->chunkdata;
2309 text_ptr->text = png_ptr->chunkdata + prefix_len;
2311 ret = png_set_text_2(png_ptr, info_ptr, text_ptr, 1);
2313 png_free(png_ptr, text_ptr);
2314 png_free(png_ptr, png_ptr->chunkdata);
2315 png_ptr->chunkdata = NULL;
2317 png_error(png_ptr, "Insufficient memory to store iTXt chunk");
2321 /* This function is called when we haven't found a handler for a
2322 chunk. If there isn't a problem with the chunk itself (ie bad
2323 chunk name, CRC, or a critical chunk), the chunk is silently ignored
2324 -- unless the PNG_FLAG_UNKNOWN_CHUNKS_SUPPORTED flag is on in which
2325 case it will be saved away to be written out later. */
2327 png_handle_unknown(png_structp png_ptr, png_infop info_ptr, png_uint_32 length)
2329 png_uint_32 skip = 0;
2331 png_debug(1, "in png_handle_unknown");
2333 #ifdef PNG_USER_LIMITS_SUPPORTED
2334 if (png_ptr->user_chunk_cache_max != 0)
2336 if (png_ptr->user_chunk_cache_max == 1)
2338 png_crc_finish(png_ptr, length);
2341 if (--png_ptr->user_chunk_cache_max == 1)
2343 png_warning(png_ptr, "No space in chunk cache for unknown chunk");
2344 png_crc_finish(png_ptr, length);
2350 if (png_ptr->mode & PNG_HAVE_IDAT)
2353 if (png_memcmp(png_ptr->chunk_name, png_IDAT, 4)) /* Not an IDAT */
2354 png_ptr->mode |= PNG_AFTER_IDAT;
2357 if (!(png_ptr->chunk_name[0] & 0x20))
2359 #ifdef PNG_HANDLE_AS_UNKNOWN_SUPPORTED
2360 if (png_handle_as_unknown(png_ptr, png_ptr->chunk_name) !=
2361 PNG_HANDLE_CHUNK_ALWAYS
2362 #ifdef PNG_READ_USER_CHUNKS_SUPPORTED
2363 && png_ptr->read_user_chunk_fn == NULL
2367 png_chunk_error(png_ptr, "unknown critical chunk");
2370 #ifdef PNG_READ_UNKNOWN_CHUNKS_SUPPORTED
2371 if ((png_ptr->flags & PNG_FLAG_KEEP_UNKNOWN_CHUNKS)
2372 #ifdef PNG_READ_USER_CHUNKS_SUPPORTED
2373 || (png_ptr->read_user_chunk_fn != NULL)
2377 #ifdef PNG_MAX_MALLOC_64K
2378 if (length > (png_uint_32)65535L)
2380 png_warning(png_ptr, "unknown chunk too large to fit in memory");
2381 skip = length - (png_uint_32)65535L;
2382 length = (png_uint_32)65535L;
2385 png_memcpy((png_charp)png_ptr->unknown_chunk.name,
2386 (png_charp)png_ptr->chunk_name,
2387 png_sizeof(png_ptr->unknown_chunk.name));
2388 png_ptr->unknown_chunk.name[png_sizeof(png_ptr->unknown_chunk.name)-1]
2390 png_ptr->unknown_chunk.size = (png_size_t)length;
2392 png_ptr->unknown_chunk.data = NULL;
2395 png_ptr->unknown_chunk.data = (png_bytep)png_malloc(png_ptr, length);
2396 png_crc_read(png_ptr, (png_bytep)png_ptr->unknown_chunk.data, length);
2398 #ifdef PNG_READ_USER_CHUNKS_SUPPORTED
2399 if (png_ptr->read_user_chunk_fn != NULL)
2401 /* Callback to user unknown chunk handler */
2403 ret = (*(png_ptr->read_user_chunk_fn))
2404 (png_ptr, &png_ptr->unknown_chunk);
2406 png_chunk_error(png_ptr, "error in user chunk");
2409 if (!(png_ptr->chunk_name[0] & 0x20))
2410 #ifdef PNG_HANDLE_AS_UNKNOWN_SUPPORTED
2411 if (png_handle_as_unknown(png_ptr, png_ptr->chunk_name) !=
2412 PNG_HANDLE_CHUNK_ALWAYS)
2414 png_chunk_error(png_ptr, "unknown critical chunk");
2415 png_set_unknown_chunks(png_ptr, info_ptr,
2416 &png_ptr->unknown_chunk, 1);
2421 png_set_unknown_chunks(png_ptr, info_ptr, &png_ptr->unknown_chunk, 1);
2422 png_free(png_ptr, png_ptr->unknown_chunk.data);
2423 png_ptr->unknown_chunk.data = NULL;
2429 png_crc_finish(png_ptr, skip);
2431 #ifndef PNG_READ_USER_CHUNKS_SUPPORTED
2432 info_ptr = info_ptr; /* Quiet compiler warnings about unused info_ptr */
2436 /* This function is called to verify that a chunk name is valid.
2437 This function can't have the "critical chunk check" incorporated
2438 into it, since in the future we will need to be able to call user
2439 functions to handle unknown critical chunks after we check that
2440 the chunk name itself is valid. */
2442 #define isnonalpha(c) ((c) < 65 || (c) > 122 || ((c) > 90 && (c) < 97))
2445 png_check_chunk_name(png_structp png_ptr, png_bytep chunk_name)
2447 png_debug(1, "in png_check_chunk_name");
2448 if (isnonalpha(chunk_name[0]) || isnonalpha(chunk_name[1]) ||
2449 isnonalpha(chunk_name[2]) || isnonalpha(chunk_name[3]))
2451 png_chunk_error(png_ptr, "invalid chunk type");
2455 /* Combines the row recently read in with the existing pixels in the
2456 row. This routine takes care of alpha and transparency if requested.
2457 This routine also handles the two methods of progressive display
2458 of interlaced images, depending on the mask value.
2459 The mask value describes which pixels are to be combined with
2460 the row. The pattern always repeats every 8 pixels, so just 8
2461 bits are needed. A one indicates the pixel is to be combined,
2462 a zero indicates the pixel is to be skipped. This is in addition
2463 to any alpha or transparency value associated with the pixel. If
2464 you want all pixels to be combined, pass 0xff (255) in mask. */
2467 png_combine_row(png_structp png_ptr, png_bytep row, int mask)
2469 png_debug(1, "in png_combine_row");
2472 png_memcpy(row, png_ptr->row_buf + 1,
2473 PNG_ROWBYTES(png_ptr->row_info.pixel_depth, png_ptr->width));
2477 switch (png_ptr->row_info.pixel_depth)
2481 png_bytep sp = png_ptr->row_buf + 1;
2483 int s_inc, s_start, s_end;
2487 png_uint_32 row_width = png_ptr->width;
2489 #ifdef PNG_READ_PACKSWAP_SUPPORTED
2490 if (png_ptr->transformations & PNG_PACKSWAP)
2506 for (i = 0; i < row_width; i++)
2512 value = (*sp >> shift) & 0x01;
2513 *dp &= (png_byte)((0x7f7f >> (7 - shift)) & 0xff);
2514 *dp |= (png_byte)(value << shift);
2535 png_bytep sp = png_ptr->row_buf + 1;
2537 int s_start, s_end, s_inc;
2541 png_uint_32 row_width = png_ptr->width;
2544 #ifdef PNG_READ_PACKSWAP_SUPPORTED
2545 if (png_ptr->transformations & PNG_PACKSWAP)
2561 for (i = 0; i < row_width; i++)
2565 value = (*sp >> shift) & 0x03;
2566 *dp &= (png_byte)((0x3f3f >> (6 - shift)) & 0xff);
2567 *dp |= (png_byte)(value << shift);
2587 png_bytep sp = png_ptr->row_buf + 1;
2589 int s_start, s_end, s_inc;
2593 png_uint_32 row_width = png_ptr->width;
2596 #ifdef PNG_READ_PACKSWAP_SUPPORTED
2597 if (png_ptr->transformations & PNG_PACKSWAP)
2612 for (i = 0; i < row_width; i++)
2616 value = (*sp >> shift) & 0xf;
2617 *dp &= (png_byte)((0xf0f >> (4 - shift)) & 0xff);
2618 *dp |= (png_byte)(value << shift);
2638 png_bytep sp = png_ptr->row_buf + 1;
2640 png_size_t pixel_bytes = (png_ptr->row_info.pixel_depth >> 3);
2642 png_uint_32 row_width = png_ptr->width;
2646 for (i = 0; i < row_width; i++)
2650 png_memcpy(dp, sp, pixel_bytes);
2667 #ifdef PNG_READ_INTERLACING_SUPPORTED
2668 /* OLD pre-1.0.9 interface:
2669 void png_do_read_interlace(png_row_infop row_info, png_bytep row, int pass,
2670 png_uint_32 transformations)
2673 png_do_read_interlace(png_structp png_ptr)
2675 png_row_infop row_info = &(png_ptr->row_info);
2676 png_bytep row = png_ptr->row_buf + 1;
2677 int pass = png_ptr->pass;
2678 png_uint_32 transformations = png_ptr->transformations;
2679 /* Arrays to facilitate easy interlacing - use pass (0 - 6) as index */
2680 /* Offset to next interlace block */
2681 PNG_CONST int png_pass_inc[7] = {8, 8, 4, 4, 2, 2, 1};
2683 png_debug(1, "in png_do_read_interlace");
2684 if (row != NULL && row_info != NULL)
2686 png_uint_32 final_width;
2688 final_width = row_info->width * png_pass_inc[pass];
2690 switch (row_info->pixel_depth)
2694 png_bytep sp = row + (png_size_t)((row_info->width - 1) >> 3);
2695 png_bytep dp = row + (png_size_t)((final_width - 1) >> 3);
2697 int s_start, s_end, s_inc;
2698 int jstop = png_pass_inc[pass];
2703 #ifdef PNG_READ_PACKSWAP_SUPPORTED
2704 if (transformations & PNG_PACKSWAP)
2706 sshift = (int)((row_info->width + 7) & 0x07);
2707 dshift = (int)((final_width + 7) & 0x07);
2715 sshift = 7 - (int)((row_info->width + 7) & 0x07);
2716 dshift = 7 - (int)((final_width + 7) & 0x07);
2722 for (i = 0; i < row_info->width; i++)
2724 v = (png_byte)((*sp >> sshift) & 0x01);
2725 for (j = 0; j < jstop; j++)
2727 *dp &= (png_byte)((0x7f7f >> (7 - dshift)) & 0xff);
2728 *dp |= (png_byte)(v << dshift);
2729 if (dshift == s_end)
2737 if (sshift == s_end)
2749 png_bytep sp = row + (png_uint_32)((row_info->width - 1) >> 2);
2750 png_bytep dp = row + (png_uint_32)((final_width - 1) >> 2);
2752 int s_start, s_end, s_inc;
2753 int jstop = png_pass_inc[pass];
2756 #ifdef PNG_READ_PACKSWAP_SUPPORTED
2757 if (transformations & PNG_PACKSWAP)
2759 sshift = (int)(((row_info->width + 3) & 0x03) << 1);
2760 dshift = (int)(((final_width + 3) & 0x03) << 1);
2768 sshift = (int)((3 - ((row_info->width + 3) & 0x03)) << 1);
2769 dshift = (int)((3 - ((final_width + 3) & 0x03)) << 1);
2775 for (i = 0; i < row_info->width; i++)
2780 v = (png_byte)((*sp >> sshift) & 0x03);
2781 for (j = 0; j < jstop; j++)
2783 *dp &= (png_byte)((0x3f3f >> (6 - dshift)) & 0xff);
2784 *dp |= (png_byte)(v << dshift);
2785 if (dshift == s_end)
2793 if (sshift == s_end)
2805 png_bytep sp = row + (png_size_t)((row_info->width - 1) >> 1);
2806 png_bytep dp = row + (png_size_t)((final_width - 1) >> 1);
2808 int s_start, s_end, s_inc;
2810 int jstop = png_pass_inc[pass];
2812 #ifdef PNG_READ_PACKSWAP_SUPPORTED
2813 if (transformations & PNG_PACKSWAP)
2815 sshift = (int)(((row_info->width + 1) & 0x01) << 2);
2816 dshift = (int)(((final_width + 1) & 0x01) << 2);
2824 sshift = (int)((1 - ((row_info->width + 1) & 0x01)) << 2);
2825 dshift = (int)((1 - ((final_width + 1) & 0x01)) << 2);
2831 for (i = 0; i < row_info->width; i++)
2833 png_byte v = (png_byte)((*sp >> sshift) & 0xf);
2836 for (j = 0; j < jstop; j++)
2838 *dp &= (png_byte)((0xf0f >> (4 - dshift)) & 0xff);
2839 *dp |= (png_byte)(v << dshift);
2840 if (dshift == s_end)
2848 if (sshift == s_end)
2860 png_size_t pixel_bytes = (row_info->pixel_depth >> 3);
2861 png_bytep sp = row + (png_size_t)(row_info->width - 1)
2863 png_bytep dp = row + (png_size_t)(final_width - 1) * pixel_bytes;
2865 int jstop = png_pass_inc[pass];
2868 for (i = 0; i < row_info->width; i++)
2873 png_memcpy(v, sp, pixel_bytes);
2874 for (j = 0; j < jstop; j++)
2876 png_memcpy(dp, v, pixel_bytes);
2884 row_info->width = final_width;
2885 row_info->rowbytes = PNG_ROWBYTES(row_info->pixel_depth, final_width);
2887 #ifndef PNG_READ_PACKSWAP_SUPPORTED
2888 transformations = transformations; /* Silence compiler warning */
2891 #endif /* PNG_READ_INTERLACING_SUPPORTED */
2894 png_read_filter_row(png_structp png_ptr, png_row_infop row_info, png_bytep row,
2895 png_bytep prev_row, int filter)
2897 png_debug(1, "in png_read_filter_row");
2898 png_debug2(2, "row = %lu, filter = %d", png_ptr->row_number, filter);
2901 case PNG_FILTER_VALUE_NONE:
2903 case PNG_FILTER_VALUE_SUB:
2906 png_uint_32 istop = row_info->rowbytes;
2907 png_uint_32 bpp = (row_info->pixel_depth + 7) >> 3;
2908 png_bytep rp = row + bpp;
2911 for (i = bpp; i < istop; i++)
2913 *rp = (png_byte)(((int)(*rp) + (int)(*lp++)) & 0xff);
2918 case PNG_FILTER_VALUE_UP:
2921 png_uint_32 istop = row_info->rowbytes;
2923 png_bytep pp = prev_row;
2925 for (i = 0; i < istop; i++)
2927 *rp = (png_byte)(((int)(*rp) + (int)(*pp++)) & 0xff);
2932 case PNG_FILTER_VALUE_AVG:
2936 png_bytep pp = prev_row;
2938 png_uint_32 bpp = (row_info->pixel_depth + 7) >> 3;
2939 png_uint_32 istop = row_info->rowbytes - bpp;
2941 for (i = 0; i < bpp; i++)
2943 *rp = (png_byte)(((int)(*rp) +
2944 ((int)(*pp++) / 2 )) & 0xff);
2948 for (i = 0; i < istop; i++)
2950 *rp = (png_byte)(((int)(*rp) +
2951 (int)(*pp++ + *lp++) / 2 ) & 0xff);
2956 case PNG_FILTER_VALUE_PAETH:
2960 png_bytep pp = prev_row;
2962 png_bytep cp = prev_row;
2963 png_uint_32 bpp = (row_info->pixel_depth + 7) >> 3;
2964 png_uint_32 istop=row_info->rowbytes - bpp;
2966 for (i = 0; i < bpp; i++)
2968 *rp = (png_byte)(((int)(*rp) + (int)(*pp++)) & 0xff);
2972 for (i = 0; i < istop; i++) /* Use leftover rp,pp */
2974 int a, b, c, pa, pb, pc, p;
2988 pa = p < 0 ? -p : p;
2989 pb = pc < 0 ? -pc : pc;
2990 pc = (p + pc) < 0 ? -(p + pc) : p + pc;
2994 if (pa <= pb && pa <= pc)
3002 p = (pa <= pb && pa <= pc) ? a : (pb <= pc) ? b : c;
3004 *rp = (png_byte)(((int)(*rp) + p) & 0xff);
3010 png_warning(png_ptr, "Ignoring bad adaptive filter type");
3016 #ifdef PNG_SEQUENTIAL_READ_SUPPORTED
3018 png_read_finish_row(png_structp png_ptr)
3020 #ifdef PNG_READ_INTERLACING_SUPPORTED
3021 /* Arrays to facilitate easy interlacing - use pass (0 - 6) as index */
3023 /* Start of interlace block */
3024 PNG_CONST int png_pass_start[7] = {0, 4, 0, 2, 0, 1, 0};
3026 /* Offset to next interlace block */
3027 PNG_CONST int png_pass_inc[7] = {8, 8, 4, 4, 2, 2, 1};
3029 /* Start of interlace block in the y direction */
3030 PNG_CONST int png_pass_ystart[7] = {0, 0, 4, 0, 2, 0, 1};
3032 /* Offset to next interlace block in the y direction */
3033 PNG_CONST int png_pass_yinc[7] = {8, 8, 8, 4, 4, 2, 2};
3034 #endif /* PNG_READ_INTERLACING_SUPPORTED */
3036 png_debug(1, "in png_read_finish_row");
3037 png_ptr->row_number++;
3038 if (png_ptr->row_number < png_ptr->num_rows)
3041 #ifdef PNG_READ_INTERLACING_SUPPORTED
3042 if (png_ptr->interlaced)
3044 png_ptr->row_number = 0;
3045 png_memset(png_ptr->prev_row, 0,
3046 png_ptr->rowbytes + 1);
3050 if (png_ptr->pass >= 7)
3052 png_ptr->iwidth = (png_ptr->width +
3053 png_pass_inc[png_ptr->pass] - 1 -
3054 png_pass_start[png_ptr->pass]) /
3055 png_pass_inc[png_ptr->pass];
3057 if (!(png_ptr->transformations & PNG_INTERLACE))
3059 png_ptr->num_rows = (png_ptr->height +
3060 png_pass_yinc[png_ptr->pass] - 1 -
3061 png_pass_ystart[png_ptr->pass]) /
3062 png_pass_yinc[png_ptr->pass];
3063 if (!(png_ptr->num_rows))
3066 else /* if (png_ptr->transformations & PNG_INTERLACE) */
3068 } while (png_ptr->iwidth == 0);
3070 if (png_ptr->pass < 7)
3073 #endif /* PNG_READ_INTERLACING_SUPPORTED */
3075 if (!(png_ptr->flags & PNG_FLAG_ZLIB_FINISHED))
3081 png_ptr->zstream.next_out = (Byte *)&extra;
3082 png_ptr->zstream.avail_out = (uInt)1;
3085 if (!(png_ptr->zstream.avail_in))
3087 while (!png_ptr->idat_size)
3089 png_byte chunk_length[4];
3091 png_crc_finish(png_ptr, 0);
3093 png_read_data(png_ptr, chunk_length, 4);
3094 png_ptr->idat_size = png_get_uint_31(png_ptr, chunk_length);
3095 png_reset_crc(png_ptr);
3096 png_crc_read(png_ptr, png_ptr->chunk_name, 4);
3097 if (png_memcmp(png_ptr->chunk_name, png_IDAT, 4))
3098 png_error(png_ptr, "Not enough image data");
3101 png_ptr->zstream.avail_in = (uInt)png_ptr->zbuf_size;
3102 png_ptr->zstream.next_in = png_ptr->zbuf;
3103 if (png_ptr->zbuf_size > png_ptr->idat_size)
3104 png_ptr->zstream.avail_in = (uInt)png_ptr->idat_size;
3105 png_crc_read(png_ptr, png_ptr->zbuf, png_ptr->zstream.avail_in);
3106 png_ptr->idat_size -= png_ptr->zstream.avail_in;
3108 ret = inflate(&png_ptr->zstream, Z_PARTIAL_FLUSH);
3109 if (ret == Z_STREAM_END)
3111 if (!(png_ptr->zstream.avail_out) || png_ptr->zstream.avail_in ||
3113 png_warning(png_ptr, "Extra compressed data");
3114 png_ptr->mode |= PNG_AFTER_IDAT;
3115 png_ptr->flags |= PNG_FLAG_ZLIB_FINISHED;
3119 png_error(png_ptr, png_ptr->zstream.msg ? png_ptr->zstream.msg :
3120 "Decompression Error");
3122 if (!(png_ptr->zstream.avail_out))
3124 png_warning(png_ptr, "Extra compressed data");
3125 png_ptr->mode |= PNG_AFTER_IDAT;
3126 png_ptr->flags |= PNG_FLAG_ZLIB_FINISHED;
3131 png_ptr->zstream.avail_out = 0;
3134 if (png_ptr->idat_size || png_ptr->zstream.avail_in)
3135 png_warning(png_ptr, "Extra compression data");
3137 inflateReset(&png_ptr->zstream);
3139 png_ptr->mode |= PNG_AFTER_IDAT;
3141 #endif /* PNG_SEQUENTIAL_READ_SUPPORTED */
3144 png_read_start_row(png_structp png_ptr)
3146 #ifdef PNG_READ_INTERLACING_SUPPORTED
3147 /* Arrays to facilitate easy interlacing - use pass (0 - 6) as index */
3149 /* Start of interlace block */
3150 PNG_CONST int png_pass_start[7] = {0, 4, 0, 2, 0, 1, 0};
3152 /* Offset to next interlace block */
3153 PNG_CONST int png_pass_inc[7] = {8, 8, 4, 4, 2, 2, 1};
3155 /* Start of interlace block in the y direction */
3156 PNG_CONST int png_pass_ystart[7] = {0, 0, 4, 0, 2, 0, 1};
3158 /* Offset to next interlace block in the y direction */
3159 PNG_CONST int png_pass_yinc[7] = {8, 8, 8, 4, 4, 2, 2};
3162 int max_pixel_depth;
3163 png_size_t row_bytes;
3165 png_debug(1, "in png_read_start_row");
3166 png_ptr->zstream.avail_in = 0;
3167 png_init_read_transformations(png_ptr);
3168 #ifdef PNG_READ_INTERLACING_SUPPORTED
3169 if (png_ptr->interlaced)
3171 if (!(png_ptr->transformations & PNG_INTERLACE))
3172 png_ptr->num_rows = (png_ptr->height + png_pass_yinc[0] - 1 -
3173 png_pass_ystart[0]) / png_pass_yinc[0];
3175 png_ptr->num_rows = png_ptr->height;
3177 png_ptr->iwidth = (png_ptr->width +
3178 png_pass_inc[png_ptr->pass] - 1 -
3179 png_pass_start[png_ptr->pass]) /
3180 png_pass_inc[png_ptr->pass];
3183 #endif /* PNG_READ_INTERLACING_SUPPORTED */
3185 png_ptr->num_rows = png_ptr->height;
3186 png_ptr->iwidth = png_ptr->width;
3188 max_pixel_depth = png_ptr->pixel_depth;
3190 #ifdef PNG_READ_PACK_SUPPORTED
3191 if ((png_ptr->transformations & PNG_PACK) && png_ptr->bit_depth < 8)
3192 max_pixel_depth = 8;
3195 #ifdef PNG_READ_EXPAND_SUPPORTED
3196 if (png_ptr->transformations & PNG_EXPAND)
3198 if (png_ptr->color_type == PNG_COLOR_TYPE_PALETTE)
3200 if (png_ptr->num_trans)
3201 max_pixel_depth = 32;
3203 max_pixel_depth = 24;
3205 else if (png_ptr->color_type == PNG_COLOR_TYPE_GRAY)
3207 if (max_pixel_depth < 8)
3208 max_pixel_depth = 8;
3209 if (png_ptr->num_trans)
3210 max_pixel_depth *= 2;
3212 else if (png_ptr->color_type == PNG_COLOR_TYPE_RGB)
3214 if (png_ptr->num_trans)
3216 max_pixel_depth *= 4;
3217 max_pixel_depth /= 3;
3223 #ifdef PNG_READ_FILLER_SUPPORTED
3224 if (png_ptr->transformations & (PNG_FILLER))
3226 if (png_ptr->color_type == PNG_COLOR_TYPE_PALETTE)
3227 max_pixel_depth = 32;
3228 else if (png_ptr->color_type == PNG_COLOR_TYPE_GRAY)
3230 if (max_pixel_depth <= 8)
3231 max_pixel_depth = 16;
3233 max_pixel_depth = 32;
3235 else if (png_ptr->color_type == PNG_COLOR_TYPE_RGB)
3237 if (max_pixel_depth <= 32)
3238 max_pixel_depth = 32;
3240 max_pixel_depth = 64;
3245 #ifdef PNG_READ_GRAY_TO_RGB_SUPPORTED
3246 if (png_ptr->transformations & PNG_GRAY_TO_RGB)
3249 #ifdef PNG_READ_EXPAND_SUPPORTED
3250 (png_ptr->num_trans && (png_ptr->transformations & PNG_EXPAND)) ||
3252 #ifdef PNG_READ_FILLER_SUPPORTED
3253 (png_ptr->transformations & (PNG_FILLER)) ||
3255 png_ptr->color_type == PNG_COLOR_TYPE_GRAY_ALPHA)
3257 if (max_pixel_depth <= 16)
3258 max_pixel_depth = 32;
3260 max_pixel_depth = 64;
3264 if (max_pixel_depth <= 8)
3266 if (png_ptr->color_type == PNG_COLOR_TYPE_RGB_ALPHA)
3267 max_pixel_depth = 32;
3269 max_pixel_depth = 24;
3271 else if (png_ptr->color_type == PNG_COLOR_TYPE_RGB_ALPHA)
3272 max_pixel_depth = 64;
3274 max_pixel_depth = 48;
3279 #if defined(PNG_READ_USER_TRANSFORM_SUPPORTED) && \
3280 defined(PNG_USER_TRANSFORM_PTR_SUPPORTED)
3281 if (png_ptr->transformations & PNG_USER_TRANSFORM)
3283 int user_pixel_depth = png_ptr->user_transform_depth*
3284 png_ptr->user_transform_channels;
3285 if (user_pixel_depth > max_pixel_depth)
3286 max_pixel_depth=user_pixel_depth;
3290 /* Align the width on the next larger 8 pixels. Mainly used
3293 row_bytes = ((png_ptr->width + 7) & ~((png_uint_32)7));
3294 /* Calculate the maximum bytes needed, adding a byte and a pixel
3297 row_bytes = PNG_ROWBYTES(max_pixel_depth, row_bytes) +
3298 1 + ((max_pixel_depth + 7) >> 3);
3299 #ifdef PNG_MAX_MALLOC_64K
3300 if (row_bytes > (png_uint_32)65536L)
3301 png_error(png_ptr, "This image requires a row greater than 64KB");
3304 if (row_bytes + 48 > png_ptr->old_big_row_buf_size)
3306 png_free(png_ptr, png_ptr->big_row_buf);
3307 if (png_ptr->interlaced)
3308 png_ptr->big_row_buf = (png_bytep)png_calloc(png_ptr,
3311 png_ptr->big_row_buf = (png_bytep)png_malloc(png_ptr,
3313 png_ptr->old_big_row_buf_size = row_bytes + 48;
3315 #ifdef PNG_ALIGNED_MEMORY_SUPPORTED
3316 /* Use 16-byte aligned memory for row_buf with at least 16 bytes
3317 * of padding before and after row_buf.
3319 png_ptr->row_buf = png_ptr->big_row_buf + 32
3320 - (((png_alloc_size_t)&(png_ptr->big_row_buf[0]) + 15) % 16);
3321 png_ptr->old_big_row_buf_size = row_bytes + 48;
3323 /* Use 32 bytes of padding before and 16 bytes after row_buf. */
3324 png_ptr->row_buf = png_ptr->big_row_buf + 32;
3326 png_ptr->old_big_row_buf_size = row_bytes + 48;
3329 #ifdef PNG_MAX_MALLOC_64K
3330 if ((png_uint_32)png_ptr->rowbytes + 1 > (png_uint_32)65536L)
3331 png_error(png_ptr, "This image requires a row greater than 64KB");
3333 if ((png_uint_32)png_ptr->rowbytes > (png_uint_32)(PNG_SIZE_MAX - 1))
3334 png_error(png_ptr, "Row has too many bytes to allocate in memory");
3336 if (png_ptr->rowbytes + 1 > png_ptr->old_prev_row_size)
3338 png_free(png_ptr, png_ptr->prev_row);
3339 png_ptr->prev_row = (png_bytep)png_malloc(png_ptr, (png_uint_32)(
3340 png_ptr->rowbytes + 1));
3341 png_ptr->old_prev_row_size = png_ptr->rowbytes + 1;
3344 png_memset(png_ptr->prev_row, 0, png_ptr->rowbytes + 1);
3346 png_debug1(3, "width = %lu,", png_ptr->width);
3347 png_debug1(3, "height = %lu,", png_ptr->height);
3348 png_debug1(3, "iwidth = %lu,", png_ptr->iwidth);
3349 png_debug1(3, "num_rows = %lu,", png_ptr->num_rows);
3350 png_debug1(3, "rowbytes = %lu,", png_ptr->rowbytes);
3351 png_debug1(3, "irowbytes = %lu",
3352 PNG_ROWBYTES(png_ptr->pixel_depth, png_ptr->iwidth) + 1);
3354 png_ptr->flags |= PNG_FLAG_ROW_INIT;
3356 #endif /* PNG_READ_SUPPORTED */