diff options
Diffstat (limited to 'pngwutil.c')
-rw-r--r-- | pngwutil.c | 135 |
1 files changed, 73 insertions, 62 deletions
diff --git a/pngwutil.c b/pngwutil.c index 2ac333242..3ddecbc69 100644 --- a/pngwutil.c +++ b/pngwutil.c @@ -1,11 +1,11 @@ /* pngwutil.c - utilities to write a PNG file * - * libpng 1.0.5h - December 10, 1999 + * libpng 1.0.5q - February 5, 2000 * For conditions of distribution and use, see copyright notice in png.h * Copyright (c) 1995, 1996 Guy Eric Schalnat, Group 42, Inc. * Copyright (c) 1996, 1997 Andreas Dilger - * Copyright (c) 1998, 1999 Glenn Randers-Pehrson + * Copyright (c) 1998, 1999, 2000 Glenn Randers-Pehrson */ #define PNG_INTERNAL @@ -133,7 +133,7 @@ png_write_sig(png_structp png_ptr) (png_size_t)8 - png_ptr->sig_bytes); } -#if defined(PNG_WRITE_TEXT_SUPPORTED) +#if defined(PNG_WRITE_TEXT_SUPPORTED) || defined(PNG_WRITE_iCCP_SUPPORTED) /* * This pair of functions encapsulates the operation of (a) compressing a * text string, and (b) issuing it later as a series of chunk data writes. @@ -334,7 +334,8 @@ png_write_compressed_data_out(png_structp png_ptr, compression_state *comp) /* write saved output buffers, if any */ for (i = 0; i < comp->num_output_ptr; i++) { - png_write_chunk_data(png_ptr,(png_bytep)comp->output_ptr[i],png_ptr->zbuf_size); + png_write_chunk_data(png_ptr,(png_bytep)comp->output_ptr[i], + png_ptr->zbuf_size); png_free(png_ptr, comp->output_ptr[i]); } if (comp->max_output_ptr != 0) @@ -577,15 +578,15 @@ png_write_gAMA(png_structp png_ptr, double file_gamma) png_byte buf[4]; png_debug(1, "in png_write_gAMA\n"); - /* file_gamma is saved in 1/1000000ths */ + /* file_gamma is saved in 1/100,000ths */ igamma = (png_uint_32)(file_gamma * 100000.0 + 0.5); png_save_uint_32(buf, igamma); png_write_chunk(png_ptr, (png_bytep)png_gAMA, buf, (png_size_t)4); } #endif -void #ifdef PNG_FIXED_POINT_SUPPORTED -png_write_gAMA_fixed(png_structp png_ptr, png_uint_32 file_gamma) +void +png_write_gAMA_fixed(png_structp png_ptr, png_fixed_point file_gamma) { #ifdef PNG_USE_LOCAL_ARRAYS PNG_gAMA; @@ -593,7 +594,7 @@ png_write_gAMA_fixed(png_structp png_ptr, png_uint_32 file_gamma) png_byte buf[4]; png_debug(1, "in png_write_gAMA\n"); - /* file_gamma is saved in 1/1000000ths */ + /* file_gamma is saved in 1/100,000ths */ png_save_uint_32(buf, file_gamma); png_write_chunk(png_ptr, (png_bytep)png_gAMA, buf, (png_size_t)4); } @@ -687,8 +688,9 @@ png_write_sPLT(png_structp png_ptr, png_spalette_p spalette) /* make sure we include the NULL after the name */ png_write_chunk_start(png_ptr, (png_bytep) png_sPLT, - (png_uint_32)(name_len + 1 + palette_size)); + (png_uint_32)(name_len + 2 + palette_size)); png_write_chunk_data(png_ptr, (png_bytep)new_name, name_len + 1); + png_write_chunk_data(png_ptr, (png_bytep)&spalette->depth, 1); /* loop through each palette entry, writing appropriately */ for (ep = spalette->entries; ep<spalette->entries+spalette->nentries; ep++) @@ -784,15 +786,16 @@ png_write_cHRM(png_structp png_ptr, double white_x, double white_y, #ifdef PNG_USE_LOCAL_ARRAYS PNG_cHRM; #endif - png_uint_32 itemp; png_byte buf[32]; + png_uint_32 itemp; png_debug(1, "in png_write_cHRM\n"); - /* each value is saved in 1/1000000ths */ + /* each value is saved in 1/100,000ths */ if (white_x < 0 || white_x > 0.8 || white_y < 0 || white_y > 0.8 || white_x + white_y > 1.0) { png_warning(png_ptr, "Invalid cHRM white point specified"); + printf("white_x=%f, white_y=%f\n",white_x, white_y); return; } itemp = (png_uint_32)(white_x * 100000.0 + 0.5); @@ -838,22 +841,22 @@ png_write_cHRM(png_structp png_ptr, double white_x, double white_y, #endif #ifdef PNG_FIXED_POINT_SUPPORTED void -png_write_cHRM_fixed(png_structp png_ptr, png_uint_32 white_x, - png_uint_32 white_y, png_uint_32 red_x, png_uint_32 red_y, - png_uint_32 green_x, png_uint_32 green_y, png_uint_32 blue_x, - png_uint_32 blue_y) +png_write_cHRM_fixed(png_structp png_ptr, png_fixed_point white_x, + png_fixed_point white_y, png_fixed_point red_x, png_fixed_point red_y, + png_fixed_point green_x, png_fixed_point green_y, png_fixed_point blue_x, + png_fixed_point blue_y) { #ifdef PNG_USE_LOCAL_ARRAYS PNG_cHRM; #endif - png_uint_32 itemp; png_byte buf[32]; png_debug(1, "in png_write_cHRM\n"); - /* each value is saved int 1/1000000ths */ + /* each value is saved in 1/100,000ths */ if (white_x > 80000L || white_y > 80000L || white_x + white_y > 100000L) { - png_warning(png_ptr, "Invalid cHRM white point specified"); + png_warning(png_ptr, "Invalid fixed cHRM white point specified"); + printf("white_x=%ld, white_y=%ld\n",white_x, white_y); return; } png_save_uint_32(buf, white_x); @@ -861,7 +864,7 @@ png_write_cHRM_fixed(png_structp png_ptr, png_uint_32 white_x, if (red_x > 80000L || red_y > 80000L || red_x + red_y > 100000L) { - png_warning(png_ptr, "Invalid cHRM red point specified"); + png_warning(png_ptr, "Invalid cHRM fixed red point specified"); return; } png_save_uint_32(buf + 8, red_x); @@ -869,7 +872,7 @@ png_write_cHRM_fixed(png_structp png_ptr, png_uint_32 white_x, if (green_x > 80000L || green_y > 80000L || green_x + green_y > 100000L) { - png_warning(png_ptr, "Invalid cHRM green point specified"); + png_warning(png_ptr, "Invalid fixed cHRM green point specified"); return; } png_save_uint_32(buf + 16, green_x); @@ -877,7 +880,7 @@ png_write_cHRM_fixed(png_structp png_ptr, png_uint_32 white_x, if (blue_x > 80000L || blue_y > 80000L || blue_x + blue_y > 100000L) { - png_warning(png_ptr, "Invalid cHRM blue point specified"); + png_warning(png_ptr, "Invalid fixed cHRM blue point specified"); return; } png_save_uint_32(buf + 24, blue_x); @@ -1108,7 +1111,7 @@ png_check_keyword(png_structp png_ptr, png_charp key, png_charpp new_key) { png_free(png_ptr, *new_key); *new_key=NULL; - png_chunk_warning(png_ptr, "zero length keyword"); + png_chunk_warning(png_ptr, "Zero length keyword"); } if (key_len > 79) @@ -1143,6 +1146,8 @@ png_write_tEXt(png_structp png_ptr, png_charp key, png_charp text, if (text == NULL || *text == '\0') text_len = 0; + else + text_len = png_strlen(text); /* make sure we include the 0 after the key */ png_write_chunk_start(png_ptr, (png_bytep)png_tEXt, (png_uint_32)key_len+text_len+1); @@ -1190,6 +1195,8 @@ png_write_zTXt(png_structp png_ptr, png_charp key, png_charp text, return; } + text_len = png_strlen(text); + png_free(png_ptr, new_key); /* compute the compressed data; do it now for the length */ @@ -1215,57 +1222,48 @@ png_write_zTXt(png_structp png_ptr, png_charp key, png_charp text, /* write an iTXt chunk */ void png_write_iTXt(png_structp png_ptr, int compression, png_charp key, - png_charp lang, png_charp translated_key, png_charp text) + png_charp lang, png_charp lang_key, png_charp text) { #ifdef PNG_USE_LOCAL_ARRAYS PNG_iTXt; #endif - png_size_t lang_len, key_len, translated_key_len, text_len; + png_size_t lang_len, key_len, lang_key_len, text_len; png_charp new_lang, new_key; png_byte cbuf[2]; compression_state comp; png_debug(1, "in png_write_iTXt\n"); - translated_key_len = png_strlen(translated_key); - text_len = png_strlen(text); - - if (lang == NULL || (lang_len = png_check_keyword(png_ptr, lang, - &new_lang))==0) + if (key == NULL || (key_len = png_check_keyword(png_ptr, key, &new_key))==0) { - png_warning(png_ptr, "Empty language field in iTXt chunk"); + png_warning(png_ptr, "Empty keyword in iTXt chunk"); return; } - if (key == NULL || (key_len = png_check_keyword(png_ptr, key, &new_key))==0) + if (lang == NULL || (lang_len = png_check_keyword(png_ptr, lang, + &new_lang))==0) { - png_warning(png_ptr, "Empty keyword in iTXt chunk"); + png_warning(png_ptr, "Empty language field in iTXt chunk"); return; } + lang_key_len = png_strlen(lang_key); + text_len = png_strlen(text); if (text == NULL || *text == '\0') text_len = 0; /* compute the compressed data; do it now for the length */ - text_len = png_text_compress(png_ptr, text, text_len, compression, &comp); + text_len = png_text_compress(png_ptr, text, text_len, compression-2, &comp); /* make sure we include the compression flag, the compression byte, - * and the NULs after the key, lang, and translated_key parts */ - png_write_chunk_start(png_ptr, (png_bytep)png_iTXt, - (png_uint_32)(2 + lang_len+1 + key_len+1 + translated_key_len + - text_len)); + * and the NULs after the key, lang, and lang_key parts */ - /* set the compression bits */ - if (compression == PNG_TEXT_COMPRESSION_NONE) - { - cbuf[0] = 0; - cbuf[1] = 0; - } - else /* compression == PNG_TEXT_COMPRESSION_zTXt */ - { - cbuf[0] = 1; - cbuf[1] = 0; - } - png_write_chunk_data(png_ptr, cbuf, 2); + png_write_chunk_start(png_ptr, (png_bytep)png_iTXt, + (png_uint_32)( + 5 /* comp byte, comp flag, terminators for key, lang and lang_key */ + + key_len + + lang_len + + lang_key_len + + text_len)); /* * We leave it to the application to meet PNG-1.0 requirements on the @@ -1274,9 +1272,19 @@ png_write_iTXt(png_structp png_ptr, int compression, png_charp key, * The NUL character is forbidden by PNG-1.0 through PNG-1.2 and ISO PNG. */ png_write_chunk_data(png_ptr, (png_bytep)new_key, key_len + 1); + + /* set the compression flag */ + if (compression == PNG_ITXT_COMPRESSION_NONE || \ + compression == PNG_TEXT_COMPRESSION_NONE) + cbuf[0] = 0; + else /* compression == PNG_ITXT_COMPRESSION_zTXt */ + cbuf[0] = 1; + /* set the compression method */ + cbuf[1] = 0; + png_write_chunk_data(png_ptr, cbuf, 2); + png_write_chunk_data(png_ptr, (png_bytep)new_lang, lang_len + 1); - png_write_chunk_data(png_ptr, (png_bytep)translated_key, - translated_key_len); + png_write_chunk_data(png_ptr, (png_bytep)lang_key, lang_key_len+1); png_write_chunk_data(png_ptr, '\0', 1); png_write_compressed_data_out(png_ptr, &comp); @@ -1375,7 +1383,7 @@ png_write_pCAL(png_structp png_ptr, png_charp purpose, png_int_32 X0, /* write the sCAL chunk */ #ifdef PNG_FLOATING_POINT_SUPPORTED void -png_write_sCAL(png_structp png_ptr, png_charp unit, double width,double height) +png_write_sCAL(png_structp png_ptr, int unit, double width,double height) { #ifdef PNG_USE_LOCAL_ARRAYS PNG_sCAL; @@ -1387,19 +1395,20 @@ png_write_sCAL(png_structp png_ptr, png_charp unit, double width,double height) sprintf(wbuf, "%12.12e", width); sprintf(hbuf, "%12.12e", height); - total_len = png_strlen(unit)+1 + png_strlen(wbuf)+1 + png_strlen(hbuf); + total_len = 1 + png_strlen(wbuf)+1 + png_strlen(hbuf); png_debug1(3, "sCAL total length = %d\n", total_len); png_write_chunk_start(png_ptr, (png_bytep)png_sCAL, (png_uint_32)total_len); - png_write_chunk_data(png_ptr, (png_bytep)unit, png_strlen(unit)+1); + png_write_chunk_data(png_ptr, (png_bytep)&unit, 1); png_write_chunk_data(png_ptr, (png_bytep)wbuf, strlen(wbuf)+1); png_write_chunk_data(png_ptr, (png_bytep)hbuf, strlen(hbuf)); png_write_chunk_end(png_ptr); } -#endif +#else +#ifdef PNG_FIXED_POINT_SUPPORTED void -png_write_sCAL_s(png_structp png_ptr, png_charp unit, png_charp width, +png_write_sCAL_s(png_structp png_ptr, int unit, png_charp width, png_charp height) { #ifdef PNG_USE_LOCAL_ARRAYS @@ -1412,17 +1421,19 @@ png_write_sCAL_s(png_structp png_ptr, png_charp unit, png_charp width, sprintf(wbuf, "%s", width); sprintf(hbuf, "%s", height); - total_len = png_strlen(unit)+1 + png_strlen(wbuf)+1 + png_strlen(hbuf); + total_len = 1 + png_strlen(wbuf)+1 + png_strlen(hbuf); png_debug1(3, "sCAL total length = %d\n", total_len); png_write_chunk_start(png_ptr, (png_bytep)png_sCAL, (png_uint_32)total_len); - png_write_chunk_data(png_ptr, (png_bytep)unit, png_strlen(unit)+1); + png_write_chunk_data(png_ptr, (png_bytep)&unit, 1); png_write_chunk_data(png_ptr, (png_bytep)wbuf, strlen(wbuf)+1); png_write_chunk_data(png_ptr, (png_bytep)hbuf, strlen(hbuf)); png_write_chunk_end(png_ptr); } #endif +#endif +#endif #if defined(PNG_WRITE_pHYs_SUPPORTED) /* write the pHYs chunk */ @@ -1730,7 +1741,7 @@ png_do_write_interlace(png_row_infop row_info, png_bytep row, int pass) i += png_pass_inc[pass]) { sp = row + (png_size_t)(i >> 3); - value = (int)(*sp >> (7 - (int)(i & 7))) & 0x1; + value = (int)(*sp >> (7 - (int)(i & 0x07))) & 0x01; d |= (value << shift); if (shift == 0) @@ -1764,7 +1775,7 @@ png_do_write_interlace(png_row_infop row_info, png_bytep row, int pass) i += png_pass_inc[pass]) { sp = row + (png_size_t)(i >> 2); - value = (*sp >> ((3 - (int)(i & 3)) << 1)) & 0x3; + value = (*sp >> ((3 - (int)(i & 0x03)) << 1)) & 0x03; d |= (value << shift); if (shift == 0) @@ -1797,7 +1808,7 @@ png_do_write_interlace(png_row_infop row_info, png_bytep row, int pass) i += png_pass_inc[pass]) { sp = row + (png_size_t)(i >> 1); - value = (*sp >> ((1 - (int)(i & 1)) << 2)) & 0xf; + value = (*sp >> ((1 - (int)(i & 0x01)) << 2)) & 0x0f; d |= (value << shift); if (shift == 0) @@ -1904,7 +1915,7 @@ png_write_find_filter(png_structp png_ptr, png_row_infop row_info) /* We don't need to test the 'no filter' case if this is the only filter * that has been chosen, as it doesn't actually do anything to the data. */ - if (filter_to_do & PNG_FILTER_NONE && + if ((filter_to_do & PNG_FILTER_NONE) && filter_to_do != PNG_FILTER_NONE) { png_bytep rp; |