mirror of
https://git.code.sf.net/p/libpng/code.git
synced 2025-07-10 18:04:09 +02:00
Make png_struct palette, trans_alpha private
This removes the side-effect on the png_struct palette of calling png_set_PLTE or png_set_tRNS. NOTE: this is a quiet API change, it was possible before to alter the palette on a PNG image by using png_set_PLTE, but this was unintended and inconsistent with the other png_set APIs. Fix a bug in palette index checking; png_struct::num_palette could, in principle, get changed by the transformations (e.g. png_set_quantize) and this would invalidate the check. The palette checking init function now makes a copy of png_struct::num_palette. Fix a bug in pngvalid error handling. A png_error in png_write_info is not continuable (a valid image cannot necessarily be written afterward) because the png_error aborts the write of subsequent pre-IDAT chunks. In particular an abort as a result of a bogus colorspace information (gAMA, cHRM, sBIT etc) prevents the write of the PLTE chunk. Signed-off-by: John Bowler <jbowler@acm.org>
This commit is contained in:
@@ -4276,62 +4276,71 @@ make_error(png_store* const ps, png_byte const colour_type,
|
||||
#undef exception__env
|
||||
|
||||
/* And clear these flags */
|
||||
ps->expect_error = 0;
|
||||
ps->expect_warning = 0;
|
||||
|
||||
/* Now write the whole image, just to make sure that the detected, or
|
||||
* undetected, errro has not created problems inside libpng.
|
||||
*/
|
||||
if (png_get_rowbytes(pp, pi) !=
|
||||
transform_rowsize(pp, colour_type, bit_depth))
|
||||
png_error(pp, "row size incorrect");
|
||||
if (ps->expect_error)
|
||||
ps->expect_error = 0;
|
||||
|
||||
else
|
||||
{
|
||||
int npasses = set_write_interlace_handling(pp, interlace_type);
|
||||
int pass;
|
||||
/* Now write the whole image, just to make sure that the detected, or
|
||||
* undetected, errro has not created problems inside libpng. This
|
||||
* doesn't work if there was a png_error in png_write_info because that
|
||||
* can abort before PLTE was written.
|
||||
*/
|
||||
if (png_get_rowbytes(pp, pi) !=
|
||||
transform_rowsize(pp, colour_type, bit_depth))
|
||||
png_error(pp, "row size incorrect");
|
||||
|
||||
if (npasses != npasses_from_interlace_type(pp, interlace_type))
|
||||
png_error(pp, "write: png_set_interlace_handling failed");
|
||||
|
||||
for (pass=0; pass<npasses; ++pass)
|
||||
else
|
||||
{
|
||||
png_uint_32 y;
|
||||
int npasses = set_write_interlace_handling(pp, interlace_type);
|
||||
int pass;
|
||||
|
||||
for (y=0; y<h; ++y)
|
||||
if (npasses != npasses_from_interlace_type(pp, interlace_type))
|
||||
png_error(pp, "write: png_set_interlace_handling failed");
|
||||
|
||||
for (pass=0; pass<npasses; ++pass)
|
||||
{
|
||||
png_byte buffer[TRANSFORM_ROWMAX];
|
||||
png_uint_32 y;
|
||||
|
||||
transform_row(pp, buffer, colour_type, bit_depth, y);
|
||||
for (y=0; y<h; ++y)
|
||||
{
|
||||
png_byte buffer[TRANSFORM_ROWMAX];
|
||||
|
||||
# if do_own_interlace
|
||||
/* If do_own_interlace *and* the image is interlaced we need a
|
||||
* reduced interlace row; this may be reduced to empty.
|
||||
*/
|
||||
if (interlace_type == PNG_INTERLACE_ADAM7)
|
||||
{
|
||||
/* The row must not be written if it doesn't exist, notice
|
||||
* that there are two conditions here, either the row isn't
|
||||
* ever in the pass or the row would be but isn't wide
|
||||
* enough to contribute any pixels. In fact the wPass test
|
||||
* can be used to skip the whole y loop in this case.
|
||||
transform_row(pp, buffer, colour_type, bit_depth, y);
|
||||
|
||||
# if do_own_interlace
|
||||
/* If do_own_interlace *and* the image is interlaced we
|
||||
* need a reduced interlace row; this may be reduced to
|
||||
* empty.
|
||||
*/
|
||||
if (PNG_ROW_IN_INTERLACE_PASS(y, pass) &&
|
||||
PNG_PASS_COLS(w, pass) > 0)
|
||||
interlace_row(buffer, buffer,
|
||||
bit_size(pp, colour_type, bit_depth), w, pass,
|
||||
0/*data always bigendian*/);
|
||||
else
|
||||
continue;
|
||||
}
|
||||
# endif /* do_own_interlace */
|
||||
if (interlace_type == PNG_INTERLACE_ADAM7)
|
||||
{
|
||||
/* The row must not be written if it doesn't exist,
|
||||
* notice that there are two conditions here, either the
|
||||
* row isn't ever in the pass or the row would be but
|
||||
* isn't wide enough to contribute any pixels. In fact
|
||||
* the wPass test can be used to skip the whole y loop
|
||||
* in this case.
|
||||
*/
|
||||
if (PNG_ROW_IN_INTERLACE_PASS(y, pass) &&
|
||||
PNG_PASS_COLS(w, pass) > 0)
|
||||
interlace_row(buffer, buffer,
|
||||
bit_size(pp, colour_type, bit_depth), w, pass,
|
||||
0/*data always bigendian*/);
|
||||
else
|
||||
continue;
|
||||
}
|
||||
# endif /* do_own_interlace */
|
||||
|
||||
png_write_row(pp, buffer);
|
||||
png_write_row(pp, buffer);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
} /* image writing */
|
||||
|
||||
png_write_end(pp, pi);
|
||||
png_write_end(pp, pi);
|
||||
}
|
||||
|
||||
/* The following deletes the file that was just written. */
|
||||
store_write_reset(ps);
|
||||
|
||||
Reference in New Issue
Block a user