00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016 #define PNG_INTERNAL
00017 #include "png.h"
00018
00019 #if defined(PNG_READ_SUPPORTED)
00020
00021
00022 void PNGAPI
00023 png_set_crc_action(png_structp png_ptr, int crit_action, int ancil_action)
00024 {
00025 png_debug(1, "in png_set_crc_action\n");
00026
00027 if(png_ptr == NULL) return;
00028 switch (crit_action)
00029 {
00030 case PNG_CRC_NO_CHANGE:
00031 break;
00032 case PNG_CRC_WARN_USE:
00033 png_ptr->flags &= ~PNG_FLAG_CRC_CRITICAL_MASK;
00034 png_ptr->flags |= PNG_FLAG_CRC_CRITICAL_USE;
00035 break;
00036 case PNG_CRC_QUIET_USE:
00037 png_ptr->flags &= ~PNG_FLAG_CRC_CRITICAL_MASK;
00038 png_ptr->flags |= PNG_FLAG_CRC_CRITICAL_USE |
00039 PNG_FLAG_CRC_CRITICAL_IGNORE;
00040 break;
00041 case PNG_CRC_WARN_DISCARD:
00042 png_warning(png_ptr, "Can't discard critical data on CRC error.");
00043 case PNG_CRC_ERROR_QUIT:
00044 case PNG_CRC_DEFAULT:
00045 default:
00046 png_ptr->flags &= ~PNG_FLAG_CRC_CRITICAL_MASK;
00047 break;
00048 }
00049
00050 switch (ancil_action)
00051 {
00052 case PNG_CRC_NO_CHANGE:
00053 break;
00054 case PNG_CRC_WARN_USE:
00055 png_ptr->flags &= ~PNG_FLAG_CRC_ANCILLARY_MASK;
00056 png_ptr->flags |= PNG_FLAG_CRC_ANCILLARY_USE;
00057 break;
00058 case PNG_CRC_QUIET_USE:
00059 png_ptr->flags &= ~PNG_FLAG_CRC_ANCILLARY_MASK;
00060 png_ptr->flags |= PNG_FLAG_CRC_ANCILLARY_USE |
00061 PNG_FLAG_CRC_ANCILLARY_NOWARN;
00062 break;
00063 case PNG_CRC_ERROR_QUIT:
00064 png_ptr->flags &= ~PNG_FLAG_CRC_ANCILLARY_MASK;
00065 png_ptr->flags |= PNG_FLAG_CRC_ANCILLARY_NOWARN;
00066 break;
00067 case PNG_CRC_WARN_DISCARD:
00068 case PNG_CRC_DEFAULT:
00069 default:
00070 png_ptr->flags &= ~PNG_FLAG_CRC_ANCILLARY_MASK;
00071 break;
00072 }
00073 }
00074
00075 #if defined(PNG_READ_BACKGROUND_SUPPORTED) && \
00076 defined(PNG_FLOATING_POINT_SUPPORTED)
00077
00078 void PNGAPI
00079 png_set_background(png_structp png_ptr,
00080 png_color_16p background_color, int background_gamma_code,
00081 int need_expand, double background_gamma)
00082 {
00083 png_debug(1, "in png_set_background\n");
00084 if(png_ptr == NULL) return;
00085 if (background_gamma_code == PNG_BACKGROUND_GAMMA_UNKNOWN)
00086 {
00087 png_warning(png_ptr, "Application must supply a known background gamma");
00088 return;
00089 }
00090
00091 png_ptr->transformations |= PNG_BACKGROUND;
00092 png_memcpy(&(png_ptr->background), background_color,
00093 png_sizeof(png_color_16));
00094 png_ptr->background_gamma = (float)background_gamma;
00095 png_ptr->background_gamma_type = (png_byte)(background_gamma_code);
00096 png_ptr->transformations |= (need_expand ? PNG_BACKGROUND_EXPAND : 0);
00097 }
00098 #endif
00099
00100 #if defined(PNG_READ_16_TO_8_SUPPORTED)
00101
00102 void PNGAPI
00103 png_set_strip_16(png_structp png_ptr)
00104 {
00105 png_debug(1, "in png_set_strip_16\n");
00106 if(png_ptr == NULL) return;
00107 png_ptr->transformations |= PNG_16_TO_8;
00108 }
00109 #endif
00110
00111 #if defined(PNG_READ_STRIP_ALPHA_SUPPORTED)
00112 void PNGAPI
00113 png_set_strip_alpha(png_structp png_ptr)
00114 {
00115 png_debug(1, "in png_set_strip_alpha\n");
00116 if(png_ptr == NULL) return;
00117 png_ptr->flags |= PNG_FLAG_STRIP_ALPHA;
00118 }
00119 #endif
00120
00121 #if defined(PNG_READ_DITHER_SUPPORTED)
00122
00123
00124
00125
00126
00127
00128
00129
00130
00131 typedef struct png_dsort_struct
00132 {
00133 struct png_dsort_struct FAR * next;
00134 png_byte left;
00135 png_byte right;
00136 } png_dsort;
00137 typedef png_dsort FAR * png_dsortp;
00138 typedef png_dsort FAR * FAR * png_dsortpp;
00139
00140 void PNGAPI
00141 png_set_dither(png_structp png_ptr, png_colorp palette,
00142 int num_palette, int maximum_colors, png_uint_16p histogram,
00143 int full_dither)
00144 {
00145 png_debug(1, "in png_set_dither\n");
00146 if(png_ptr == NULL) return;
00147 png_ptr->transformations |= PNG_DITHER;
00148
00149 if (!full_dither)
00150 {
00151 int i;
00152
00153 png_ptr->dither_index = (png_bytep)png_malloc(png_ptr,
00154 (png_uint_32)(num_palette * png_sizeof (png_byte)));
00155 for (i = 0; i < num_palette; i++)
00156 png_ptr->dither_index[i] = (png_byte)i;
00157 }
00158
00159 if (num_palette > maximum_colors)
00160 {
00161 if (histogram != NULL)
00162 {
00163
00164
00165
00166 int i;
00167
00168
00169 png_ptr->dither_sort = (png_bytep)png_malloc(png_ptr,
00170 (png_uint_32)(num_palette * png_sizeof (png_byte)));
00171
00172
00173 for (i = 0; i < num_palette; i++)
00174 png_ptr->dither_sort[i] = (png_byte)i;
00175
00176
00177
00178
00179
00180
00181
00182 for (i = num_palette - 1; i >= maximum_colors; i--)
00183 {
00184 int done;
00185 int j;
00186
00187 done = 1;
00188 for (j = 0; j < i; j++)
00189 {
00190 if (histogram[png_ptr->dither_sort[j]]
00191 < histogram[png_ptr->dither_sort[j + 1]])
00192 {
00193 png_byte t;
00194
00195 t = png_ptr->dither_sort[j];
00196 png_ptr->dither_sort[j] = png_ptr->dither_sort[j + 1];
00197 png_ptr->dither_sort[j + 1] = t;
00198 done = 0;
00199 }
00200 }
00201 if (done)
00202 break;
00203 }
00204
00205
00206 if (full_dither)
00207 {
00208 int j = num_palette;
00209
00210
00211
00212 for (i = 0; i < maximum_colors; i++)
00213 {
00214 if ((int)png_ptr->dither_sort[i] >= maximum_colors)
00215 {
00216 do
00217 j--;
00218 while ((int)png_ptr->dither_sort[j] >= maximum_colors);
00219 palette[i] = palette[j];
00220 }
00221 }
00222 }
00223 else
00224 {
00225 int j = num_palette;
00226
00227
00228
00229 for (i = 0; i < maximum_colors; i++)
00230 {
00231
00232 if ((int)png_ptr->dither_sort[i] >= maximum_colors)
00233 {
00234 png_color tmp_color;
00235
00236 do
00237 j--;
00238 while ((int)png_ptr->dither_sort[j] >= maximum_colors);
00239
00240 tmp_color = palette[j];
00241 palette[j] = palette[i];
00242 palette[i] = tmp_color;
00243
00244 png_ptr->dither_index[j] = (png_byte)i;
00245 png_ptr->dither_index[i] = (png_byte)j;
00246 }
00247 }
00248
00249
00250 for (i = 0; i < num_palette; i++)
00251 {
00252 if ((int)png_ptr->dither_index[i] >= maximum_colors)
00253 {
00254 int min_d, k, min_k, d_index;
00255
00256
00257 d_index = png_ptr->dither_index[i];
00258 min_d = PNG_COLOR_DIST(palette[d_index], palette[0]);
00259 for (k = 1, min_k = 0; k < maximum_colors; k++)
00260 {
00261 int d;
00262
00263 d = PNG_COLOR_DIST(palette[d_index], palette[k]);
00264
00265 if (d < min_d)
00266 {
00267 min_d = d;
00268 min_k = k;
00269 }
00270 }
00271
00272 png_ptr->dither_index[i] = (png_byte)min_k;
00273 }
00274 }
00275 }
00276 png_free(png_ptr, png_ptr->dither_sort);
00277 png_ptr->dither_sort=NULL;
00278 }
00279 else
00280 {
00281
00282
00283
00284
00285
00286
00287
00288
00289 int i;
00290 int max_d;
00291 int num_new_palette;
00292 png_dsortp t;
00293 png_dsortpp hash;
00294
00295 t=NULL;
00296
00297
00298 png_ptr->index_to_palette = (png_bytep)png_malloc(png_ptr,
00299 (png_uint_32)(num_palette * png_sizeof (png_byte)));
00300 png_ptr->palette_to_index = (png_bytep)png_malloc(png_ptr,
00301 (png_uint_32)(num_palette * png_sizeof (png_byte)));
00302
00303
00304 for (i = 0; i < num_palette; i++)
00305 {
00306 png_ptr->index_to_palette[i] = (png_byte)i;
00307 png_ptr->palette_to_index[i] = (png_byte)i;
00308 }
00309
00310 hash = (png_dsortpp)png_malloc(png_ptr, (png_uint_32)(769 *
00311 png_sizeof (png_dsortp)));
00312 for (i = 0; i < 769; i++)
00313 hash[i] = NULL;
00314
00315
00316 num_new_palette = num_palette;
00317
00318
00319
00320
00321
00322
00323
00324
00325
00326 max_d = 96;
00327
00328 while (num_new_palette > maximum_colors)
00329 {
00330 for (i = 0; i < num_new_palette - 1; i++)
00331 {
00332 int j;
00333
00334 for (j = i + 1; j < num_new_palette; j++)
00335 {
00336 int d;
00337
00338 d = PNG_COLOR_DIST(palette[i], palette[j]);
00339
00340 if (d <= max_d)
00341 {
00342
00343 t = (png_dsortp)png_malloc_warn(png_ptr,
00344 (png_uint_32)(png_sizeof(png_dsort)));
00345 if (t == NULL)
00346 break;
00347 t->next = hash[d];
00348 t->left = (png_byte)i;
00349 t->right = (png_byte)j;
00350 hash[d] = t;
00351 }
00352 }
00353 if (t == NULL)
00354 break;
00355 }
00356
00357 if (t != NULL)
00358 for (i = 0; i <= max_d; i++)
00359 {
00360 if (hash[i] != NULL)
00361 {
00362 png_dsortp p;
00363
00364 for (p = hash[i]; p; p = p->next)
00365 {
00366 if ((int)png_ptr->index_to_palette[p->left]
00367 < num_new_palette &&
00368 (int)png_ptr->index_to_palette[p->right]
00369 < num_new_palette)
00370 {
00371 int j, next_j;
00372
00373 if (num_new_palette & 0x01)
00374 {
00375 j = p->left;
00376 next_j = p->right;
00377 }
00378 else
00379 {
00380 j = p->right;
00381 next_j = p->left;
00382 }
00383
00384 num_new_palette--;
00385 palette[png_ptr->index_to_palette[j]]
00386 = palette[num_new_palette];
00387 if (!full_dither)
00388 {
00389 int k;
00390
00391 for (k = 0; k < num_palette; k++)
00392 {
00393 if (png_ptr->dither_index[k] ==
00394 png_ptr->index_to_palette[j])
00395 png_ptr->dither_index[k] =
00396 png_ptr->index_to_palette[next_j];
00397 if ((int)png_ptr->dither_index[k] ==
00398 num_new_palette)
00399 png_ptr->dither_index[k] =
00400 png_ptr->index_to_palette[j];
00401 }
00402 }
00403
00404 png_ptr->index_to_palette[png_ptr->palette_to_index
00405 [num_new_palette]] = png_ptr->index_to_palette[j];
00406 png_ptr->palette_to_index[png_ptr->index_to_palette[j]]
00407 = png_ptr->palette_to_index[num_new_palette];
00408
00409 png_ptr->index_to_palette[j] = (png_byte)num_new_palette;
00410 png_ptr->palette_to_index[num_new_palette] = (png_byte)j;
00411 }
00412 if (num_new_palette <= maximum_colors)
00413 break;
00414 }
00415 if (num_new_palette <= maximum_colors)
00416 break;
00417 }
00418 }
00419
00420 for (i = 0; i < 769; i++)
00421 {
00422 if (hash[i] != NULL)
00423 {
00424 png_dsortp p = hash[i];
00425 while (p)
00426 {
00427 t = p->next;
00428 png_free(png_ptr, p);
00429 p = t;
00430 }
00431 }
00432 hash[i] = 0;
00433 }
00434 max_d += 96;
00435 }
00436 png_free(png_ptr, hash);
00437 png_free(png_ptr, png_ptr->palette_to_index);
00438 png_free(png_ptr, png_ptr->index_to_palette);
00439 png_ptr->palette_to_index=NULL;
00440 png_ptr->index_to_palette=NULL;
00441 }
00442 num_palette = maximum_colors;
00443 }
00444 if (png_ptr->palette == NULL)
00445 {
00446 png_ptr->palette = palette;
00447 }
00448 png_ptr->num_palette = (png_uint_16)num_palette;
00449
00450 if (full_dither)
00451 {
00452 int i;
00453 png_bytep distance;
00454 int total_bits = PNG_DITHER_RED_BITS + PNG_DITHER_GREEN_BITS +
00455 PNG_DITHER_BLUE_BITS;
00456 int num_red = (1 << PNG_DITHER_RED_BITS);
00457 int num_green = (1 << PNG_DITHER_GREEN_BITS);
00458 int num_blue = (1 << PNG_DITHER_BLUE_BITS);
00459 png_size_t num_entries = ((png_size_t)1 << total_bits);
00460
00461 png_ptr->palette_lookup = (png_bytep )png_malloc(png_ptr,
00462 (png_uint_32)(num_entries * png_sizeof (png_byte)));
00463
00464 png_memset(png_ptr->palette_lookup, 0, num_entries *
00465 png_sizeof (png_byte));
00466
00467 distance = (png_bytep)png_malloc(png_ptr, (png_uint_32)(num_entries *
00468 png_sizeof(png_byte)));
00469
00470 png_memset(distance, 0xff, num_entries * png_sizeof(png_byte));
00471
00472 for (i = 0; i < num_palette; i++)
00473 {
00474 int ir, ig, ib;
00475 int r = (palette[i].red >> (8 - PNG_DITHER_RED_BITS));
00476 int g = (palette[i].green >> (8 - PNG_DITHER_GREEN_BITS));
00477 int b = (palette[i].blue >> (8 - PNG_DITHER_BLUE_BITS));
00478
00479 for (ir = 0; ir < num_red; ir++)
00480 {
00481
00482 int dr = ((ir > r) ? ir - r : r - ir);
00483 int index_r = (ir << (PNG_DITHER_BLUE_BITS + PNG_DITHER_GREEN_BITS));
00484
00485 for (ig = 0; ig < num_green; ig++)
00486 {
00487
00488 int dg = ((ig > g) ? ig - g : g - ig);
00489 int dt = dr + dg;
00490 int dm = ((dr > dg) ? dr : dg);
00491 int index_g = index_r | (ig << PNG_DITHER_BLUE_BITS);
00492
00493 for (ib = 0; ib < num_blue; ib++)
00494 {
00495 int d_index = index_g | ib;
00496
00497 int db = ((ib > b) ? ib - b : b - ib);
00498 int dmax = ((dm > db) ? dm : db);
00499 int d = dmax + dt + db;
00500
00501 if (d < (int)distance[d_index])
00502 {
00503 distance[d_index] = (png_byte)d;
00504 png_ptr->palette_lookup[d_index] = (png_byte)i;
00505 }
00506 }
00507 }
00508 }
00509 }
00510
00511 png_free(png_ptr, distance);
00512 }
00513 }
00514 #endif
00515
00516 #if defined(PNG_READ_GAMMA_SUPPORTED) && defined(PNG_FLOATING_POINT_SUPPORTED)
00517
00518
00519
00520
00521
00522
00523
00524
00525
00526 void PNGAPI
00527 png_set_gamma(png_structp png_ptr, double scrn_gamma, double file_gamma)
00528 {
00529 png_debug(1, "in png_set_gamma\n");
00530 if(png_ptr == NULL) return;
00531 if ((fabs(scrn_gamma * file_gamma - 1.0) > PNG_GAMMA_THRESHOLD) ||
00532 (png_ptr->color_type & PNG_COLOR_MASK_ALPHA) ||
00533 (png_ptr->color_type == PNG_COLOR_TYPE_PALETTE))
00534 png_ptr->transformations |= PNG_GAMMA;
00535 png_ptr->gamma = (float)file_gamma;
00536 png_ptr->screen_gamma = (float)scrn_gamma;
00537 }
00538 #endif
00539
00540 #if defined(PNG_READ_EXPAND_SUPPORTED)
00541
00542
00543
00544
00545 void PNGAPI
00546 png_set_expand(png_structp png_ptr)
00547 {
00548 png_debug(1, "in png_set_expand\n");
00549 if(png_ptr == NULL) return;
00550 png_ptr->transformations |= (PNG_EXPAND | PNG_EXPAND_tRNS);
00551 #ifdef PNG_WARN_UNINITIALIZED_ROW
00552 png_ptr->flags &= ~PNG_FLAG_ROW_INIT;
00553 #endif
00554 }
00555
00556
00557
00558
00559
00560
00561
00562
00563
00564
00565
00566
00567
00568
00569
00570
00571
00572
00573
00574 void PNGAPI
00575 png_set_palette_to_rgb(png_structp png_ptr)
00576 {
00577 png_debug(1, "in png_set_palette_to_rgb\n");
00578 if(png_ptr == NULL) return;
00579 png_ptr->transformations |= (PNG_EXPAND | PNG_EXPAND_tRNS);
00580 #ifdef PNG_WARN_UNINITIALIZED_ROW
00581 png_ptr->flags &= ~PNG_FLAG_ROW_INIT;
00582 #endif
00583 }
00584
00585 #if !defined(PNG_1_0_X)
00586
00587 void PNGAPI
00588 png_set_expand_gray_1_2_4_to_8(png_structp png_ptr)
00589 {
00590 png_debug(1, "in png_set_expand_gray_1_2_4_to_8\n");
00591 if(png_ptr == NULL) return;
00592 png_ptr->transformations |= PNG_EXPAND;
00593 #ifdef PNG_WARN_UNINITIALIZED_ROW
00594 png_ptr->flags &= ~PNG_FLAG_ROW_INIT;
00595 #endif
00596 }
00597 #endif
00598
00599 #if defined(PNG_1_0_X) || defined(PNG_1_2_X)
00600
00601
00602 void PNGAPI
00603 png_set_gray_1_2_4_to_8(png_structp png_ptr)
00604 {
00605 png_debug(1, "in png_set_gray_1_2_4_to_8\n");
00606 if(png_ptr == NULL) return;
00607 png_ptr->transformations |= (PNG_EXPAND | PNG_EXPAND_tRNS);
00608 }
00609 #endif
00610
00611
00612
00613 void PNGAPI
00614 png_set_tRNS_to_alpha(png_structp png_ptr)
00615 {
00616 png_debug(1, "in png_set_tRNS_to_alpha\n");
00617 png_ptr->transformations |= (PNG_EXPAND | PNG_EXPAND_tRNS);
00618 #ifdef PNG_WARN_UNINITIALIZED_ROW
00619 png_ptr->flags &= ~PNG_FLAG_ROW_INIT;
00620 #endif
00621 }
00622 #endif
00623
00624 #if defined(PNG_READ_GRAY_TO_RGB_SUPPORTED)
00625 void PNGAPI
00626 png_set_gray_to_rgb(png_structp png_ptr)
00627 {
00628 png_debug(1, "in png_set_gray_to_rgb\n");
00629 png_ptr->transformations |= PNG_GRAY_TO_RGB;
00630 #ifdef PNG_WARN_UNINITIALIZED_ROW
00631 png_ptr->flags &= ~PNG_FLAG_ROW_INIT;
00632 #endif
00633 }
00634 #endif
00635
00636 #if defined(PNG_READ_RGB_TO_GRAY_SUPPORTED)
00637 #if defined(PNG_FLOATING_POINT_SUPPORTED)
00638
00639
00640
00641
00642 void PNGAPI
00643 png_set_rgb_to_gray(png_structp png_ptr, int error_action, double red,
00644 double green)
00645 {
00646 int red_fixed = (int)((float)red*100000.0 + 0.5);
00647 int green_fixed = (int)((float)green*100000.0 + 0.5);
00648 if(png_ptr == NULL) return;
00649 png_set_rgb_to_gray_fixed(png_ptr, error_action, red_fixed, green_fixed);
00650 }
00651 #endif
00652
00653 void PNGAPI
00654 png_set_rgb_to_gray_fixed(png_structp png_ptr, int error_action,
00655 png_fixed_point red, png_fixed_point green)
00656 {
00657 png_debug(1, "in png_set_rgb_to_gray\n");
00658 if(png_ptr == NULL) return;
00659 switch(error_action)
00660 {
00661 case 1: png_ptr->transformations |= PNG_RGB_TO_GRAY;
00662 break;
00663 case 2: png_ptr->transformations |= PNG_RGB_TO_GRAY_WARN;
00664 break;
00665 case 3: png_ptr->transformations |= PNG_RGB_TO_GRAY_ERR;
00666 }
00667 if (png_ptr->color_type == PNG_COLOR_TYPE_PALETTE)
00668 #if defined(PNG_READ_EXPAND_SUPPORTED)
00669 png_ptr->transformations |= PNG_EXPAND;
00670 #else
00671 {
00672 png_warning(png_ptr, "Cannot do RGB_TO_GRAY without EXPAND_SUPPORTED.");
00673 png_ptr->transformations &= ~PNG_RGB_TO_GRAY;
00674 }
00675 #endif
00676 {
00677 png_uint_16 red_int, green_int;
00678 if(red < 0 || green < 0)
00679 {
00680 red_int = 6968;
00681 green_int = 23434;
00682 }
00683 else if(red + green < 100000L)
00684 {
00685 red_int = (png_uint_16)(((png_uint_32)red*32768L)/100000L);
00686 green_int = (png_uint_16)(((png_uint_32)green*32768L)/100000L);
00687 }
00688 else
00689 {
00690 png_warning(png_ptr, "ignoring out of range rgb_to_gray coefficients");
00691 red_int = 6968;
00692 green_int = 23434;
00693 }
00694 png_ptr->rgb_to_gray_red_coeff = red_int;
00695 png_ptr->rgb_to_gray_green_coeff = green_int;
00696 png_ptr->rgb_to_gray_blue_coeff = (png_uint_16)(32768-red_int-green_int);
00697 }
00698 }
00699 #endif
00700
00701 #if defined(PNG_READ_USER_TRANSFORM_SUPPORTED) || \
00702 defined(PNG_WRITE_USER_TRANSFORM_SUPPORTED) || \
00703 defined(PNG_LEGACY_SUPPORTED)
00704 void PNGAPI
00705 png_set_read_user_transform_fn(png_structp png_ptr, png_user_transform_ptr
00706 read_user_transform_fn)
00707 {
00708 png_debug(1, "in png_set_read_user_transform_fn\n");
00709 if(png_ptr == NULL) return;
00710 #if defined(PNG_READ_USER_TRANSFORM_SUPPORTED)
00711 png_ptr->transformations |= PNG_USER_TRANSFORM;
00712 png_ptr->read_user_transform_fn = read_user_transform_fn;
00713 #endif
00714 #ifdef PNG_LEGACY_SUPPORTED
00715 if(read_user_transform_fn)
00716 png_warning(png_ptr,
00717 "This version of libpng does not support user transforms");
00718 #endif
00719 }
00720 #endif
00721
00722
00723
00724
00725 void
00726 png_init_read_transformations(png_structp png_ptr)
00727 {
00728 png_debug(1, "in png_init_read_transformations\n");
00729 #if defined(PNG_USELESS_TESTS_SUPPORTED)
00730 if(png_ptr != NULL)
00731 #endif
00732 {
00733 #if defined(PNG_READ_BACKGROUND_SUPPORTED) || defined(PNG_READ_SHIFT_SUPPORTED) \
00734 || defined(PNG_READ_GAMMA_SUPPORTED)
00735 int color_type = png_ptr->color_type;
00736 #endif
00737
00738 #if defined(PNG_READ_EXPAND_SUPPORTED) && defined(PNG_READ_BACKGROUND_SUPPORTED)
00739
00740 #if defined(PNG_READ_GRAY_TO_RGB_SUPPORTED)
00741
00742
00743
00744
00745
00746
00747
00748
00749
00750 if ((png_ptr->transformations & PNG_BACKGROUND_EXPAND) &&
00751 !(color_type & PNG_COLOR_MASK_COLOR))
00752 {
00753 png_ptr->mode |= PNG_BACKGROUND_IS_GRAY;
00754 } else if ((png_ptr->transformations & PNG_BACKGROUND) &&
00755 !(png_ptr->transformations & PNG_BACKGROUND_EXPAND) &&
00756 (png_ptr->transformations & PNG_GRAY_TO_RGB) &&
00757 png_ptr->background.red == png_ptr->background.green &&
00758 png_ptr->background.red == png_ptr->background.blue)
00759 {
00760 png_ptr->mode |= PNG_BACKGROUND_IS_GRAY;
00761 png_ptr->background.gray = png_ptr->background.red;
00762 }
00763 #endif
00764
00765 if ((png_ptr->transformations & PNG_BACKGROUND_EXPAND) &&
00766 (png_ptr->transformations & PNG_EXPAND))
00767 {
00768 if (!(color_type & PNG_COLOR_MASK_COLOR))
00769 {
00770
00771 switch (png_ptr->bit_depth)
00772 {
00773 case 1:
00774 png_ptr->background.gray *= (png_uint_16)0xff;
00775 png_ptr->background.red = png_ptr->background.green
00776 = png_ptr->background.blue = png_ptr->background.gray;
00777 if (!(png_ptr->transformations & PNG_EXPAND_tRNS))
00778 {
00779 png_ptr->trans_values.gray *= (png_uint_16)0xff;
00780 png_ptr->trans_values.red = png_ptr->trans_values.green
00781 = png_ptr->trans_values.blue = png_ptr->trans_values.gray;
00782 }
00783 break;
00784 case 2:
00785 png_ptr->background.gray *= (png_uint_16)0x55;
00786 png_ptr->background.red = png_ptr->background.green
00787 = png_ptr->background.blue = png_ptr->background.gray;
00788 if (!(png_ptr->transformations & PNG_EXPAND_tRNS))
00789 {
00790 png_ptr->trans_values.gray *= (png_uint_16)0x55;
00791 png_ptr->trans_values.red = png_ptr->trans_values.green
00792 = png_ptr->trans_values.blue = png_ptr->trans_values.gray;
00793 }
00794 break;
00795 case 4:
00796 png_ptr->background.gray *= (png_uint_16)0x11;
00797 png_ptr->background.red = png_ptr->background.green
00798 = png_ptr->background.blue = png_ptr->background.gray;
00799 if (!(png_ptr->transformations & PNG_EXPAND_tRNS))
00800 {
00801 png_ptr->trans_values.gray *= (png_uint_16)0x11;
00802 png_ptr->trans_values.red = png_ptr->trans_values.green
00803 = png_ptr->trans_values.blue = png_ptr->trans_values.gray;
00804 }
00805 break;
00806 case 8:
00807 case 16:
00808 png_ptr->background.red = png_ptr->background.green
00809 = png_ptr->background.blue = png_ptr->background.gray;
00810 break;
00811 }
00812 }
00813 else if (color_type == PNG_COLOR_TYPE_PALETTE)
00814 {
00815 png_ptr->background.red =
00816 png_ptr->palette[png_ptr->background.index].red;
00817 png_ptr->background.green =
00818 png_ptr->palette[png_ptr->background.index].green;
00819 png_ptr->background.blue =
00820 png_ptr->palette[png_ptr->background.index].blue;
00821
00822 #if defined(PNG_READ_INVERT_ALPHA_SUPPORTED)
00823 if (png_ptr->transformations & PNG_INVERT_ALPHA)
00824 {
00825 #if defined(PNG_READ_EXPAND_SUPPORTED)
00826 if (!(png_ptr->transformations & PNG_EXPAND_tRNS))
00827 #endif
00828 {
00829
00830
00831 int i,istop;
00832 istop=(int)png_ptr->num_trans;
00833 for (i=0; i<istop; i++)
00834 png_ptr->trans[i] = (png_byte)(255 - png_ptr->trans[i]);
00835 }
00836 }
00837 #endif
00838
00839 }
00840 }
00841 #endif
00842
00843 #if defined(PNG_READ_BACKGROUND_SUPPORTED) && defined(PNG_READ_GAMMA_SUPPORTED)
00844 png_ptr->background_1 = png_ptr->background;
00845 #endif
00846 #if defined(PNG_READ_GAMMA_SUPPORTED) && defined(PNG_FLOATING_POINT_SUPPORTED)
00847
00848 if ((color_type == PNG_COLOR_TYPE_PALETTE && png_ptr->num_trans != 0)
00849 && (fabs(png_ptr->screen_gamma * png_ptr->gamma - 1.0)
00850 < PNG_GAMMA_THRESHOLD))
00851 {
00852 int i,k;
00853 k=0;
00854 for (i=0; i<png_ptr->num_trans; i++)
00855 {
00856 if (png_ptr->trans[i] != 0 && png_ptr->trans[i] != 0xff)
00857 k=1;
00858 }
00859 if (k == 0)
00860 png_ptr->transformations &= ~PNG_GAMMA;
00861 }
00862
00863 if ((png_ptr->transformations & (PNG_GAMMA | PNG_RGB_TO_GRAY)) &&
00864 png_ptr->gamma != 0.0)
00865 {
00866 png_build_gamma_table(png_ptr);
00867 #if defined(PNG_READ_BACKGROUND_SUPPORTED)
00868 if (png_ptr->transformations & PNG_BACKGROUND)
00869 {
00870 if (color_type == PNG_COLOR_TYPE_PALETTE)
00871 {
00872
00873
00874 png_color back, back_1;
00875 png_colorp palette = png_ptr->palette;
00876 int num_palette = png_ptr->num_palette;
00877 int i;
00878 if (png_ptr->background_gamma_type == PNG_BACKGROUND_GAMMA_FILE)
00879 {
00880 back.red = png_ptr->gamma_table[png_ptr->background.red];
00881 back.green = png_ptr->gamma_table[png_ptr->background.green];
00882 back.blue = png_ptr->gamma_table[png_ptr->background.blue];
00883
00884 back_1.red = png_ptr->gamma_to_1[png_ptr->background.red];
00885 back_1.green = png_ptr->gamma_to_1[png_ptr->background.green];
00886 back_1.blue = png_ptr->gamma_to_1[png_ptr->background.blue];
00887 }
00888 else
00889 {
00890 double g, gs;
00891
00892 switch (png_ptr->background_gamma_type)
00893 {
00894 case PNG_BACKGROUND_GAMMA_SCREEN:
00895 g = (png_ptr->screen_gamma);
00896 gs = 1.0;
00897 break;
00898 case PNG_BACKGROUND_GAMMA_FILE:
00899 g = 1.0 / (png_ptr->gamma);
00900 gs = 1.0 / (png_ptr->gamma * png_ptr->screen_gamma);
00901 break;
00902 case PNG_BACKGROUND_GAMMA_UNIQUE:
00903 g = 1.0 / (png_ptr->background_gamma);
00904 gs = 1.0 / (png_ptr->background_gamma *
00905 png_ptr->screen_gamma);
00906 break;
00907 default:
00908 g = 1.0;
00909 gs = 1.0;
00910 }
00911
00912 if ( fabs(gs - 1.0) < PNG_GAMMA_THRESHOLD)
00913 {
00914 back.red = (png_byte)png_ptr->background.red;
00915 back.green = (png_byte)png_ptr->background.green;
00916 back.blue = (png_byte)png_ptr->background.blue;
00917 }
00918 else
00919 {
00920 back.red = (png_byte)(pow(
00921 (double)png_ptr->background.red/255, gs) * 255.0 + .5);
00922 back.green = (png_byte)(pow(
00923 (double)png_ptr->background.green/255, gs) * 255.0 + .5);
00924 back.blue = (png_byte)(pow(
00925 (double)png_ptr->background.blue/255, gs) * 255.0 + .5);
00926 }
00927
00928 back_1.red = (png_byte)(pow(
00929 (double)png_ptr->background.red/255, g) * 255.0 + .5);
00930 back_1.green = (png_byte)(pow(
00931 (double)png_ptr->background.green/255, g) * 255.0 + .5);
00932 back_1.blue = (png_byte)(pow(
00933 (double)png_ptr->background.blue/255, g) * 255.0 + .5);
00934 }
00935 for (i = 0; i < num_palette; i++)
00936 {
00937 if (i < (int)png_ptr->num_trans && png_ptr->trans[i] != 0xff)
00938 {
00939 if (png_ptr->trans[i] == 0)
00940 {
00941 palette[i] = back;
00942 }
00943 else
00944 {
00945 png_byte v, w;
00946
00947 v = png_ptr->gamma_to_1[palette[i].red];
00948 png_composite(w, v, png_ptr->trans[i], back_1.red);
00949 palette[i].red = png_ptr->gamma_from_1[w];
00950
00951 v = png_ptr->gamma_to_1[palette[i].green];
00952 png_composite(w, v, png_ptr->trans[i], back_1.green);
00953 palette[i].green = png_ptr->gamma_from_1[w];
00954
00955 v = png_ptr->gamma_to_1[palette[i].blue];
00956 png_composite(w, v, png_ptr->trans[i], back_1.blue);
00957 palette[i].blue = png_ptr->gamma_from_1[w];
00958 }
00959 }
00960 else
00961 {
00962 palette[i].red = png_ptr->gamma_table[palette[i].red];
00963 palette[i].green = png_ptr->gamma_table[palette[i].green];
00964 palette[i].blue = png_ptr->gamma_table[palette[i].blue];
00965 }
00966 }
00967 }
00968
00969 else
00970
00971 {
00972 double m = (double)(((png_uint_32)1 << png_ptr->bit_depth) - 1);
00973 double g = 1.0;
00974 double gs = 1.0;
00975
00976 switch (png_ptr->background_gamma_type)
00977 {
00978 case PNG_BACKGROUND_GAMMA_SCREEN:
00979 g = (png_ptr->screen_gamma);
00980 gs = 1.0;
00981 break;
00982 case PNG_BACKGROUND_GAMMA_FILE:
00983 g = 1.0 / (png_ptr->gamma);
00984 gs = 1.0 / (png_ptr->gamma * png_ptr->screen_gamma);
00985 break;
00986 case PNG_BACKGROUND_GAMMA_UNIQUE:
00987 g = 1.0 / (png_ptr->background_gamma);
00988 gs = 1.0 / (png_ptr->background_gamma *
00989 png_ptr->screen_gamma);
00990 break;
00991 }
00992
00993 png_ptr->background_1.gray = (png_uint_16)(pow(
00994 (double)png_ptr->background.gray / m, g) * m + .5);
00995 png_ptr->background.gray = (png_uint_16)(pow(
00996 (double)png_ptr->background.gray / m, gs) * m + .5);
00997
00998 if ((png_ptr->background.red != png_ptr->background.green) ||
00999 (png_ptr->background.red != png_ptr->background.blue) ||
01000 (png_ptr->background.red != png_ptr->background.gray))
01001 {
01002
01003 png_ptr->background_1.red = (png_uint_16)(pow(
01004 (double)png_ptr->background.red / m, g) * m + .5);
01005 png_ptr->background_1.green = (png_uint_16)(pow(
01006 (double)png_ptr->background.green / m, g) * m + .5);
01007 png_ptr->background_1.blue = (png_uint_16)(pow(
01008 (double)png_ptr->background.blue / m, g) * m + .5);
01009 png_ptr->background.red = (png_uint_16)(pow(
01010 (double)png_ptr->background.red / m, gs) * m + .5);
01011 png_ptr->background.green = (png_uint_16)(pow(
01012 (double)png_ptr->background.green / m, gs) * m + .5);
01013 png_ptr->background.blue = (png_uint_16)(pow(
01014 (double)png_ptr->background.blue / m, gs) * m + .5);
01015 }
01016 else
01017 {
01018
01019 png_ptr->background_1.red = png_ptr->background_1.green
01020 = png_ptr->background_1.blue = png_ptr->background_1.gray;
01021 png_ptr->background.red = png_ptr->background.green
01022 = png_ptr->background.blue = png_ptr->background.gray;
01023 }
01024 }
01025 }
01026 else
01027
01028 #endif
01029 if (color_type == PNG_COLOR_TYPE_PALETTE)
01030 {
01031 png_colorp palette = png_ptr->palette;
01032 int num_palette = png_ptr->num_palette;
01033 int i;
01034
01035 for (i = 0; i < num_palette; i++)
01036 {
01037 palette[i].red = png_ptr->gamma_table[palette[i].red];
01038 palette[i].green = png_ptr->gamma_table[palette[i].green];
01039 palette[i].blue = png_ptr->gamma_table[palette[i].blue];
01040 }
01041 }
01042 }
01043 #if defined(PNG_READ_BACKGROUND_SUPPORTED)
01044 else
01045 #endif
01046 #endif
01047 #if defined(PNG_READ_BACKGROUND_SUPPORTED)
01048
01049 if ((png_ptr->transformations & PNG_BACKGROUND) &&
01050 (color_type == PNG_COLOR_TYPE_PALETTE))
01051 {
01052 int i;
01053 int istop = (int)png_ptr->num_trans;
01054 png_color back;
01055 png_colorp palette = png_ptr->palette;
01056
01057 back.red = (png_byte)png_ptr->background.red;
01058 back.green = (png_byte)png_ptr->background.green;
01059 back.blue = (png_byte)png_ptr->background.blue;
01060
01061 for (i = 0; i < istop; i++)
01062 {
01063 if (png_ptr->trans[i] == 0)
01064 {
01065 palette[i] = back;
01066 }
01067 else if (png_ptr->trans[i] != 0xff)
01068 {
01069
01070 png_composite(palette[i].red, palette[i].red,
01071 png_ptr->trans[i], back.red);
01072 png_composite(palette[i].green, palette[i].green,
01073 png_ptr->trans[i], back.green);
01074 png_composite(palette[i].blue, palette[i].blue,
01075 png_ptr->trans[i], back.blue);
01076 }
01077 }
01078 }
01079 #endif
01080
01081 #if defined(PNG_READ_SHIFT_SUPPORTED)
01082 if ((png_ptr->transformations & PNG_SHIFT) &&
01083 (color_type == PNG_COLOR_TYPE_PALETTE))
01084 {
01085 png_uint_16 i;
01086 png_uint_16 istop = png_ptr->num_palette;
01087 int sr = 8 - png_ptr->sig_bit.red;
01088 int sg = 8 - png_ptr->sig_bit.green;
01089 int sb = 8 - png_ptr->sig_bit.blue;
01090
01091 if (sr < 0 || sr > 8)
01092 sr = 0;
01093 if (sg < 0 || sg > 8)
01094 sg = 0;
01095 if (sb < 0 || sb > 8)
01096 sb = 0;
01097 for (i = 0; i < istop; i++)
01098 {
01099 png_ptr->palette[i].red >>= sr;
01100 png_ptr->palette[i].green >>= sg;
01101 png_ptr->palette[i].blue >>= sb;
01102 }
01103 }
01104 #endif
01105 }
01106 #if !defined(PNG_READ_GAMMA_SUPPORTED) && !defined(PNG_READ_SHIFT_SUPPORTED) \
01107 && !defined(PNG_READ_BACKGROUND_SUPPORTED)
01108 if(png_ptr)
01109 return;
01110 #endif
01111 }
01112
01113
01114
01115
01116
01117 void
01118 png_read_transform_info(png_structp png_ptr, png_infop info_ptr)
01119 {
01120 png_debug(1, "in png_read_transform_info\n");
01121 #if defined(PNG_READ_EXPAND_SUPPORTED)
01122 if (png_ptr->transformations & PNG_EXPAND)
01123 {
01124 if (info_ptr->color_type == PNG_COLOR_TYPE_PALETTE)
01125 {
01126 if (png_ptr->num_trans && (png_ptr->transformations & PNG_EXPAND_tRNS))
01127 info_ptr->color_type = PNG_COLOR_TYPE_RGB_ALPHA;
01128 else
01129 info_ptr->color_type = PNG_COLOR_TYPE_RGB;
01130 info_ptr->bit_depth = 8;
01131 info_ptr->num_trans = 0;
01132 }
01133 else
01134 {
01135 if (png_ptr->num_trans)
01136 {
01137 if (png_ptr->transformations & PNG_EXPAND_tRNS)
01138 info_ptr->color_type |= PNG_COLOR_MASK_ALPHA;
01139 else
01140 info_ptr->color_type |= PNG_COLOR_MASK_COLOR;
01141 }
01142 if (info_ptr->bit_depth < 8)
01143 info_ptr->bit_depth = 8;
01144 info_ptr->num_trans = 0;
01145 }
01146 }
01147 #endif
01148
01149 #if defined(PNG_READ_BACKGROUND_SUPPORTED)
01150 if (png_ptr->transformations & PNG_BACKGROUND)
01151 {
01152 info_ptr->color_type &= ~PNG_COLOR_MASK_ALPHA;
01153 info_ptr->num_trans = 0;
01154 info_ptr->background = png_ptr->background;
01155 }
01156 #endif
01157
01158 #if defined(PNG_READ_GAMMA_SUPPORTED)
01159 if (png_ptr->transformations & PNG_GAMMA)
01160 {
01161 #ifdef PNG_FLOATING_POINT_SUPPORTED
01162 info_ptr->gamma = png_ptr->gamma;
01163 #endif
01164 #ifdef PNG_FIXED_POINT_SUPPORTED
01165 info_ptr->int_gamma = png_ptr->int_gamma;
01166 #endif
01167 }
01168 #endif
01169
01170 #if defined(PNG_READ_16_TO_8_SUPPORTED)
01171 if ((png_ptr->transformations & PNG_16_TO_8) && (info_ptr->bit_depth == 16))
01172 info_ptr->bit_depth = 8;
01173 #endif
01174
01175 #if defined(PNG_READ_GRAY_TO_RGB_SUPPORTED)
01176 if (png_ptr->transformations & PNG_GRAY_TO_RGB)
01177 info_ptr->color_type |= PNG_COLOR_MASK_COLOR;
01178 #endif
01179
01180 #if defined(PNG_READ_RGB_TO_GRAY_SUPPORTED)
01181 if (png_ptr->transformations & PNG_RGB_TO_GRAY)
01182 info_ptr->color_type &= ~PNG_COLOR_MASK_COLOR;
01183 #endif
01184
01185 #if defined(PNG_READ_DITHER_SUPPORTED)
01186 if (png_ptr->transformations & PNG_DITHER)
01187 {
01188 if (((info_ptr->color_type == PNG_COLOR_TYPE_RGB) ||
01189 (info_ptr->color_type == PNG_COLOR_TYPE_RGB_ALPHA)) &&
01190 png_ptr->palette_lookup && info_ptr->bit_depth == 8)
01191 {
01192 info_ptr->color_type = PNG_COLOR_TYPE_PALETTE;
01193 }
01194 }
01195 #endif
01196
01197 #if defined(PNG_READ_PACK_SUPPORTED)
01198 if ((png_ptr->transformations & PNG_PACK) && (info_ptr->bit_depth < 8))
01199 info_ptr->bit_depth = 8;
01200 #endif
01201
01202 if (info_ptr->color_type == PNG_COLOR_TYPE_PALETTE)
01203 info_ptr->channels = 1;
01204 else if (info_ptr->color_type & PNG_COLOR_MASK_COLOR)
01205 info_ptr->channels = 3;
01206 else
01207 info_ptr->channels = 1;
01208
01209 #if defined(PNG_READ_STRIP_ALPHA_SUPPORTED)
01210 if (png_ptr->flags & PNG_FLAG_STRIP_ALPHA)
01211 info_ptr->color_type &= ~PNG_COLOR_MASK_ALPHA;
01212 #endif
01213
01214 if (info_ptr->color_type & PNG_COLOR_MASK_ALPHA)
01215 info_ptr->channels++;
01216
01217 #if defined(PNG_READ_FILLER_SUPPORTED)
01218
01219 if ((png_ptr->transformations & PNG_FILLER) &&
01220 ((info_ptr->color_type == PNG_COLOR_TYPE_RGB) ||
01221 (info_ptr->color_type == PNG_COLOR_TYPE_GRAY)))
01222 {
01223 info_ptr->channels++;
01224
01225 #if !defined(PNG_1_0_X)
01226 if (png_ptr->transformations & PNG_ADD_ALPHA)
01227 info_ptr->color_type |= PNG_COLOR_MASK_ALPHA;
01228 #endif
01229 }
01230 #endif
01231
01232 #if defined(PNG_USER_TRANSFORM_PTR_SUPPORTED) && \
01233 defined(PNG_READ_USER_TRANSFORM_SUPPORTED)
01234 if(png_ptr->transformations & PNG_USER_TRANSFORM)
01235 {
01236 if(info_ptr->bit_depth < png_ptr->user_transform_depth)
01237 info_ptr->bit_depth = png_ptr->user_transform_depth;
01238 if(info_ptr->channels < png_ptr->user_transform_channels)
01239 info_ptr->channels = png_ptr->user_transform_channels;
01240 }
01241 #endif
01242
01243 info_ptr->pixel_depth = (png_byte)(info_ptr->channels *
01244 info_ptr->bit_depth);
01245
01246 info_ptr->rowbytes = PNG_ROWBYTES(info_ptr->pixel_depth,info_ptr->width);
01247
01248 #if !defined(PNG_READ_EXPAND_SUPPORTED)
01249 if(png_ptr)
01250 return;
01251 #endif
01252 }
01253
01254
01255
01256
01257
01258 void
01259 png_do_read_transformations(png_structp png_ptr)
01260 {
01261 png_debug(1, "in png_do_read_transformations\n");
01262 if (png_ptr->row_buf == NULL)
01263 {
01264 #if !defined(PNG_NO_STDIO) && !defined(_WIN32_WCE)
01265 char msg[50];
01266
01267 png_snprintf2(msg, 50,
01268 "NULL row buffer for row %ld, pass %d", png_ptr->row_number,
01269 png_ptr->pass);
01270 png_error(png_ptr, msg);
01271 #else
01272 png_error(png_ptr, "NULL row buffer");
01273 #endif
01274 }
01275 #ifdef PNG_WARN_UNINITIALIZED_ROW
01276 if (!(png_ptr->flags & PNG_FLAG_ROW_INIT))
01277
01278
01279
01280 #if (PNG_WARN_UNINITIALIZED_ROW==1)
01281 png_error(png_ptr, "Uninitialized row");
01282 #else
01283 png_warning(png_ptr, "Uninitialized row");
01284 #endif
01285 #endif
01286
01287 #if defined(PNG_READ_EXPAND_SUPPORTED)
01288 if (png_ptr->transformations & PNG_EXPAND)
01289 {
01290 if (png_ptr->row_info.color_type == PNG_COLOR_TYPE_PALETTE)
01291 {
01292 png_do_expand_palette(&(png_ptr->row_info), png_ptr->row_buf + 1,
01293 png_ptr->palette, png_ptr->trans, png_ptr->num_trans);
01294 }
01295 else
01296 {
01297 if (png_ptr->num_trans &&
01298 (png_ptr->transformations & PNG_EXPAND_tRNS))
01299 png_do_expand(&(png_ptr->row_info), png_ptr->row_buf + 1,
01300 &(png_ptr->trans_values));
01301 else
01302 png_do_expand(&(png_ptr->row_info), png_ptr->row_buf + 1,
01303 NULL);
01304 }
01305 }
01306 #endif
01307
01308 #if defined(PNG_READ_STRIP_ALPHA_SUPPORTED)
01309 if (png_ptr->flags & PNG_FLAG_STRIP_ALPHA)
01310 png_do_strip_filler(&(png_ptr->row_info), png_ptr->row_buf + 1,
01311 PNG_FLAG_FILLER_AFTER | (png_ptr->flags & PNG_FLAG_STRIP_ALPHA));
01312 #endif
01313
01314 #if defined(PNG_READ_RGB_TO_GRAY_SUPPORTED)
01315 if (png_ptr->transformations & PNG_RGB_TO_GRAY)
01316 {
01317 int rgb_error =
01318 png_do_rgb_to_gray(png_ptr, &(png_ptr->row_info), png_ptr->row_buf + 1);
01319 if(rgb_error)
01320 {
01321 png_ptr->rgb_to_gray_status=1;
01322 if((png_ptr->transformations & PNG_RGB_TO_GRAY) ==
01323 PNG_RGB_TO_GRAY_WARN)
01324 png_warning(png_ptr, "png_do_rgb_to_gray found nongray pixel");
01325 if((png_ptr->transformations & PNG_RGB_TO_GRAY) ==
01326 PNG_RGB_TO_GRAY_ERR)
01327 png_error(png_ptr, "png_do_rgb_to_gray found nongray pixel");
01328 }
01329 }
01330 #endif
01331
01332
01333
01334
01335
01336
01337
01338
01339
01340
01341
01342
01343
01344
01345
01346
01347
01348
01349
01350
01351
01352
01353
01354
01355
01356
01357
01358
01359
01360
01361
01362 #if defined(PNG_READ_GRAY_TO_RGB_SUPPORTED)
01363
01364
01365 if ((png_ptr->transformations & PNG_GRAY_TO_RGB) &&
01366 !(png_ptr->mode & PNG_BACKGROUND_IS_GRAY))
01367 png_do_gray_to_rgb(&(png_ptr->row_info), png_ptr->row_buf + 1);
01368 #endif
01369
01370 #if defined(PNG_READ_BACKGROUND_SUPPORTED)
01371 if ((png_ptr->transformations & PNG_BACKGROUND) &&
01372 ((png_ptr->num_trans != 0 ) ||
01373 (png_ptr->color_type & PNG_COLOR_MASK_ALPHA)))
01374 png_do_background(&(png_ptr->row_info), png_ptr->row_buf + 1,
01375 &(png_ptr->trans_values), &(png_ptr->background)
01376 #if defined(PNG_READ_GAMMA_SUPPORTED)
01377 , &(png_ptr->background_1),
01378 png_ptr->gamma_table, png_ptr->gamma_from_1,
01379 png_ptr->gamma_to_1, png_ptr->gamma_16_table,
01380 png_ptr->gamma_16_from_1, png_ptr->gamma_16_to_1,
01381 png_ptr->gamma_shift
01382 #endif
01383 );
01384 #endif
01385
01386 #if defined(PNG_READ_GAMMA_SUPPORTED)
01387 if ((png_ptr->transformations & PNG_GAMMA) &&
01388 #if defined(PNG_READ_BACKGROUND_SUPPORTED)
01389 !((png_ptr->transformations & PNG_BACKGROUND) &&
01390 ((png_ptr->num_trans != 0) ||
01391 (png_ptr->color_type & PNG_COLOR_MASK_ALPHA))) &&
01392 #endif
01393 (png_ptr->color_type != PNG_COLOR_TYPE_PALETTE))
01394 png_do_gamma(&(png_ptr->row_info), png_ptr->row_buf + 1,
01395 png_ptr->gamma_table, png_ptr->gamma_16_table,
01396 png_ptr->gamma_shift);
01397 #endif
01398
01399 #if defined(PNG_READ_16_TO_8_SUPPORTED)
01400 if (png_ptr->transformations & PNG_16_TO_8)
01401 png_do_chop(&(png_ptr->row_info), png_ptr->row_buf + 1);
01402 #endif
01403
01404 #if defined(PNG_READ_DITHER_SUPPORTED)
01405 if (png_ptr->transformations & PNG_DITHER)
01406 {
01407 png_do_dither((png_row_infop)&(png_ptr->row_info), png_ptr->row_buf + 1,
01408 png_ptr->palette_lookup, png_ptr->dither_index);
01409 if(png_ptr->row_info.rowbytes == (png_uint_32)0)
01410 png_error(png_ptr, "png_do_dither returned rowbytes=0");
01411 }
01412 #endif
01413
01414 #if defined(PNG_READ_INVERT_SUPPORTED)
01415 if (png_ptr->transformations & PNG_INVERT_MONO)
01416 png_do_invert(&(png_ptr->row_info), png_ptr->row_buf + 1);
01417 #endif
01418
01419 #if defined(PNG_READ_SHIFT_SUPPORTED)
01420 if (png_ptr->transformations & PNG_SHIFT)
01421 png_do_unshift(&(png_ptr->row_info), png_ptr->row_buf + 1,
01422 &(png_ptr->shift));
01423 #endif
01424
01425 #if defined(PNG_READ_PACK_SUPPORTED)
01426 if (png_ptr->transformations & PNG_PACK)
01427 png_do_unpack(&(png_ptr->row_info), png_ptr->row_buf + 1);
01428 #endif
01429
01430 #if defined(PNG_READ_BGR_SUPPORTED)
01431 if (png_ptr->transformations & PNG_BGR)
01432 png_do_bgr(&(png_ptr->row_info), png_ptr->row_buf + 1);
01433 #endif
01434
01435 #if defined(PNG_READ_PACKSWAP_SUPPORTED)
01436 if (png_ptr->transformations & PNG_PACKSWAP)
01437 png_do_packswap(&(png_ptr->row_info), png_ptr->row_buf + 1);
01438 #endif
01439
01440 #if defined(PNG_READ_GRAY_TO_RGB_SUPPORTED)
01441
01442 if ((png_ptr->transformations & PNG_GRAY_TO_RGB) &&
01443 (png_ptr->mode & PNG_BACKGROUND_IS_GRAY))
01444 png_do_gray_to_rgb(&(png_ptr->row_info), png_ptr->row_buf + 1);
01445 #endif
01446
01447 #if defined(PNG_READ_FILLER_SUPPORTED)
01448 if (png_ptr->transformations & PNG_FILLER)
01449 png_do_read_filler(&(png_ptr->row_info), png_ptr->row_buf + 1,
01450 (png_uint_32)png_ptr->filler, png_ptr->flags);
01451 #endif
01452
01453 #if defined(PNG_READ_INVERT_ALPHA_SUPPORTED)
01454 if (png_ptr->transformations & PNG_INVERT_ALPHA)
01455 png_do_read_invert_alpha(&(png_ptr->row_info), png_ptr->row_buf + 1);
01456 #endif
01457
01458 #if defined(PNG_READ_SWAP_ALPHA_SUPPORTED)
01459 if (png_ptr->transformations & PNG_SWAP_ALPHA)
01460 png_do_read_swap_alpha(&(png_ptr->row_info), png_ptr->row_buf + 1);
01461 #endif
01462
01463 #if defined(PNG_READ_SWAP_SUPPORTED)
01464 if (png_ptr->transformations & PNG_SWAP_BYTES)
01465 png_do_swap(&(png_ptr->row_info), png_ptr->row_buf + 1);
01466 #endif
01467
01468 #if defined(PNG_READ_USER_TRANSFORM_SUPPORTED)
01469 if (png_ptr->transformations & PNG_USER_TRANSFORM)
01470 {
01471 if(png_ptr->read_user_transform_fn != NULL)
01472 (*(png_ptr->read_user_transform_fn))
01473 (png_ptr,
01474 &(png_ptr->row_info),
01475
01476
01477
01478
01479
01480
01481 png_ptr->row_buf + 1);
01482 #if defined(PNG_USER_TRANSFORM_PTR_SUPPORTED)
01483 if(png_ptr->user_transform_depth)
01484 png_ptr->row_info.bit_depth = png_ptr->user_transform_depth;
01485 if(png_ptr->user_transform_channels)
01486 png_ptr->row_info.channels = png_ptr->user_transform_channels;
01487 #endif
01488 png_ptr->row_info.pixel_depth = (png_byte)(png_ptr->row_info.bit_depth *
01489 png_ptr->row_info.channels);
01490 png_ptr->row_info.rowbytes = PNG_ROWBYTES(png_ptr->row_info.pixel_depth,
01491 png_ptr->row_info.width);
01492 }
01493 #endif
01494
01495 }
01496
01497 #if defined(PNG_READ_PACK_SUPPORTED)
01498
01499
01500
01501
01502
01503
01504 void
01505 png_do_unpack(png_row_infop row_info, png_bytep row)
01506 {
01507 png_debug(1, "in png_do_unpack\n");
01508 #if defined(PNG_USELESS_TESTS_SUPPORTED)
01509 if (row != NULL && row_info != NULL && row_info->bit_depth < 8)
01510 #else
01511 if (row_info->bit_depth < 8)
01512 #endif
01513 {
01514 png_uint_32 i;
01515 png_uint_32 row_width=row_info->width;
01516
01517 switch (row_info->bit_depth)
01518 {
01519 case 1:
01520 {
01521 png_bytep sp = row + (png_size_t)((row_width - 1) >> 3);
01522 png_bytep dp = row + (png_size_t)row_width - 1;
01523 png_uint_32 shift = 7 - (int)((row_width + 7) & 0x07);
01524 for (i = 0; i < row_width; i++)
01525 {
01526 *dp = (png_byte)((*sp >> shift) & 0x01);
01527 if (shift == 7)
01528 {
01529 shift = 0;
01530 sp--;
01531 }
01532 else
01533 shift++;
01534
01535 dp--;
01536 }
01537 break;
01538 }
01539 case 2:
01540 {
01541
01542 png_bytep sp = row + (png_size_t)((row_width - 1) >> 2);
01543 png_bytep dp = row + (png_size_t)row_width - 1;
01544 png_uint_32 shift = (int)((3 - ((row_width + 3) & 0x03)) << 1);
01545 for (i = 0; i < row_width; i++)
01546 {
01547 *dp = (png_byte)((*sp >> shift) & 0x03);
01548 if (shift == 6)
01549 {
01550 shift = 0;
01551 sp--;
01552 }
01553 else
01554 shift += 2;
01555
01556 dp--;
01557 }
01558 break;
01559 }
01560 case 4:
01561 {
01562 png_bytep sp = row + (png_size_t)((row_width - 1) >> 1);
01563 png_bytep dp = row + (png_size_t)row_width - 1;
01564 png_uint_32 shift = (int)((1 - ((row_width + 1) & 0x01)) << 2);
01565 for (i = 0; i < row_width; i++)
01566 {
01567 *dp = (png_byte)((*sp >> shift) & 0x0f);
01568 if (shift == 4)
01569 {
01570 shift = 0;
01571 sp--;
01572 }
01573 else
01574 shift = 4;
01575
01576 dp--;
01577 }
01578 break;
01579 }
01580 }
01581 row_info->bit_depth = 8;
01582 row_info->pixel_depth = (png_byte)(8 * row_info->channels);
01583 row_info->rowbytes = row_width * row_info->channels;
01584 }
01585 }
01586 #endif
01587
01588 #if defined(PNG_READ_SHIFT_SUPPORTED)
01589
01590
01591
01592
01593
01594 void
01595 png_do_unshift(png_row_infop row_info, png_bytep row, png_color_8p sig_bits)
01596 {
01597 png_debug(1, "in png_do_unshift\n");
01598 if (
01599 #if defined(PNG_USELESS_TESTS_SUPPORTED)
01600 row != NULL && row_info != NULL && sig_bits != NULL &&
01601 #endif
01602 row_info->color_type != PNG_COLOR_TYPE_PALETTE)
01603 {
01604 int shift[4];
01605 int channels = 0;
01606 int c;
01607 png_uint_16 value = 0;
01608 png_uint_32 row_width = row_info->width;
01609
01610 if (row_info->color_type & PNG_COLOR_MASK_COLOR)
01611 {
01612 shift[channels++] = row_info->bit_depth - sig_bits->red;
01613 shift[channels++] = row_info->bit_depth - sig_bits->green;
01614 shift[channels++] = row_info->bit_depth - sig_bits->blue;
01615 }
01616 else
01617 {
01618 shift[channels++] = row_info->bit_depth - sig_bits->gray;
01619 }
01620 if (row_info->color_type & PNG_COLOR_MASK_ALPHA)
01621 {
01622 shift[channels++] = row_info->bit_depth - sig_bits->alpha;
01623 }
01624
01625 for (c = 0; c < channels; c++)
01626 {
01627 if (shift[c] <= 0)
01628 shift[c] = 0;
01629 else
01630 value = 1;
01631 }
01632
01633 if (!value)
01634 return;
01635
01636 switch (row_info->bit_depth)
01637 {
01638 case 2:
01639 {
01640 png_bytep bp;
01641 png_uint_32 i;
01642 png_uint_32 istop = row_info->rowbytes;
01643
01644 for (bp = row, i = 0; i < istop; i++)
01645 {
01646 *bp >>= 1;
01647 *bp++ &= 0x55;
01648 }
01649 break;
01650 }
01651 case 4:
01652 {
01653 png_bytep bp = row;
01654 png_uint_32 i;
01655 png_uint_32 istop = row_info->rowbytes;
01656 png_byte mask = (png_byte)((((int)0xf0 >> shift[0]) & (int)0xf0) |
01657 (png_byte)((int)0xf >> shift[0]));
01658
01659 for (i = 0; i < istop; i++)
01660 {
01661 *bp >>= shift[0];
01662 *bp++ &= mask;
01663 }
01664 break;
01665 }
01666 case 8:
01667 {
01668 png_bytep bp = row;
01669 png_uint_32 i;
01670 png_uint_32 istop = row_width * channels;
01671
01672 for (i = 0; i < istop; i++)
01673 {
01674 *bp++ >>= shift[i%channels];
01675 }
01676 break;
01677 }
01678 case 16:
01679 {
01680 png_bytep bp = row;
01681 png_uint_32 i;
01682 png_uint_32 istop = channels * row_width;
01683
01684 for (i = 0; i < istop; i++)
01685 {
01686 value = (png_uint_16)((*bp << 8) + *(bp + 1));
01687 value >>= shift[i%channels];
01688 *bp++ = (png_byte)(value >> 8);
01689 *bp++ = (png_byte)(value & 0xff);
01690 }
01691 break;
01692 }
01693 }
01694 }
01695 }
01696 #endif
01697
01698 #if defined(PNG_READ_16_TO_8_SUPPORTED)
01699
01700 void
01701 png_do_chop(png_row_infop row_info, png_bytep row)
01702 {
01703 png_debug(1, "in png_do_chop\n");
01704 #if defined(PNG_USELESS_TESTS_SUPPORTED)
01705 if (row != NULL && row_info != NULL && row_info->bit_depth == 16)
01706 #else
01707 if (row_info->bit_depth == 16)
01708 #endif
01709 {
01710 png_bytep sp = row;
01711 png_bytep dp = row;
01712 png_uint_32 i;
01713 png_uint_32 istop = row_info->width * row_info->channels;
01714
01715 for (i = 0; i<istop; i++, sp += 2, dp++)
01716 {
01717 #if defined(PNG_READ_16_TO_8_ACCURATE_SCALE_SUPPORTED)
01718
01719
01720
01721
01722
01723
01724
01725
01726
01727
01728
01729
01730
01731
01732
01733
01734
01735
01736
01737
01738
01739
01740 *dp = *sp + ((((int)(*(sp + 1)) - *sp) > 128) ? 1 : 0);
01741 #else
01742
01743 *dp = *sp;
01744 #endif
01745 }
01746 row_info->bit_depth = 8;
01747 row_info->pixel_depth = (png_byte)(8 * row_info->channels);
01748 row_info->rowbytes = row_info->width * row_info->channels;
01749 }
01750 }
01751 #endif
01752
01753 #if defined(PNG_READ_SWAP_ALPHA_SUPPORTED)
01754 void
01755 png_do_read_swap_alpha(png_row_infop row_info, png_bytep row)
01756 {
01757 png_debug(1, "in png_do_read_swap_alpha\n");
01758 #if defined(PNG_USELESS_TESTS_SUPPORTED)
01759 if (row != NULL && row_info != NULL)
01760 #endif
01761 {
01762 png_uint_32 row_width = row_info->width;
01763 if (row_info->color_type == PNG_COLOR_TYPE_RGB_ALPHA)
01764 {
01765
01766 if (row_info->bit_depth == 8)
01767 {
01768 png_bytep sp = row + row_info->rowbytes;
01769 png_bytep dp = sp;
01770 png_byte save;
01771 png_uint_32 i;
01772
01773 for (i = 0; i < row_width; i++)
01774 {
01775 save = *(--sp);
01776 *(--dp) = *(--sp);
01777 *(--dp) = *(--sp);
01778 *(--dp) = *(--sp);
01779 *(--dp) = save;
01780 }
01781 }
01782
01783 else
01784 {
01785 png_bytep sp = row + row_info->rowbytes;
01786 png_bytep dp = sp;
01787 png_byte save[2];
01788 png_uint_32 i;
01789
01790 for (i = 0; i < row_width; i++)
01791 {
01792 save[0] = *(--sp);
01793 save[1] = *(--sp);
01794 *(--dp) = *(--sp);
01795 *(--dp) = *(--sp);
01796 *(--dp) = *(--sp);
01797 *(--dp) = *(--sp);
01798 *(--dp) = *(--sp);
01799 *(--dp) = *(--sp);
01800 *(--dp) = save[0];
01801 *(--dp) = save[1];
01802 }
01803 }
01804 }
01805 else if (row_info->color_type == PNG_COLOR_TYPE_GRAY_ALPHA)
01806 {
01807
01808 if (row_info->bit_depth == 8)
01809 {
01810 png_bytep sp = row + row_info->rowbytes;
01811 png_bytep dp = sp;
01812 png_byte save;
01813 png_uint_32 i;
01814
01815 for (i = 0; i < row_width; i++)
01816 {
01817 save = *(--sp);
01818 *(--dp) = *(--sp);
01819 *(--dp) = save;
01820 }
01821 }
01822
01823 else
01824 {
01825 png_bytep sp = row + row_info->rowbytes;
01826 png_bytep dp = sp;
01827 png_byte save[2];
01828 png_uint_32 i;
01829
01830 for (i = 0; i < row_width; i++)
01831 {
01832 save[0] = *(--sp);
01833 save[1] = *(--sp);
01834 *(--dp) = *(--sp);
01835 *(--dp) = *(--sp);
01836 *(--dp) = save[0];
01837 *(--dp) = save[1];
01838 }
01839 }
01840 }
01841 }
01842 }
01843 #endif
01844
01845 #if defined(PNG_READ_INVERT_ALPHA_SUPPORTED)
01846 void
01847 png_do_read_invert_alpha(png_row_infop row_info, png_bytep row)
01848 {
01849 png_debug(1, "in png_do_read_invert_alpha\n");
01850 #if defined(PNG_USELESS_TESTS_SUPPORTED)
01851 if (row != NULL && row_info != NULL)
01852 #endif
01853 {
01854 png_uint_32 row_width = row_info->width;
01855 if (row_info->color_type == PNG_COLOR_TYPE_RGB_ALPHA)
01856 {
01857
01858 if (row_info->bit_depth == 8)
01859 {
01860 png_bytep sp = row + row_info->rowbytes;
01861 png_bytep dp = sp;
01862 png_uint_32 i;
01863
01864 for (i = 0; i < row_width; i++)
01865 {
01866 *(--dp) = (png_byte)(255 - *(--sp));
01867
01868
01869
01870
01871
01872
01873
01874 sp-=3;
01875 dp=sp;
01876 }
01877 }
01878
01879 else
01880 {
01881 png_bytep sp = row + row_info->rowbytes;
01882 png_bytep dp = sp;
01883 png_uint_32 i;
01884
01885 for (i = 0; i < row_width; i++)
01886 {
01887 *(--dp) = (png_byte)(255 - *(--sp));
01888 *(--dp) = (png_byte)(255 - *(--sp));
01889
01890
01891
01892
01893
01894
01895
01896
01897
01898
01899 sp-=6;
01900 dp=sp;
01901 }
01902 }
01903 }
01904 else if (row_info->color_type == PNG_COLOR_TYPE_GRAY_ALPHA)
01905 {
01906
01907 if (row_info->bit_depth == 8)
01908 {
01909 png_bytep sp = row + row_info->rowbytes;
01910 png_bytep dp = sp;
01911 png_uint_32 i;
01912
01913 for (i = 0; i < row_width; i++)
01914 {
01915 *(--dp) = (png_byte)(255 - *(--sp));
01916 *(--dp) = *(--sp);
01917 }
01918 }
01919
01920 else
01921 {
01922 png_bytep sp = row + row_info->rowbytes;
01923 png_bytep dp = sp;
01924 png_uint_32 i;
01925
01926 for (i = 0; i < row_width; i++)
01927 {
01928 *(--dp) = (png_byte)(255 - *(--sp));
01929 *(--dp) = (png_byte)(255 - *(--sp));
01930
01931
01932
01933
01934 sp-=2;
01935 dp=sp;
01936 }
01937 }
01938 }
01939 }
01940 }
01941 #endif
01942
01943 #if defined(PNG_READ_FILLER_SUPPORTED)
01944
01945 void
01946 png_do_read_filler(png_row_infop row_info, png_bytep row,
01947 png_uint_32 filler, png_uint_32 flags)
01948 {
01949 png_uint_32 i;
01950 png_uint_32 row_width = row_info->width;
01951
01952 png_byte hi_filler = (png_byte)((filler>>8) & 0xff);
01953 png_byte lo_filler = (png_byte)(filler & 0xff);
01954
01955 png_debug(1, "in png_do_read_filler\n");
01956 if (
01957 #if defined(PNG_USELESS_TESTS_SUPPORTED)
01958 row != NULL && row_info != NULL &&
01959 #endif
01960 row_info->color_type == PNG_COLOR_TYPE_GRAY)
01961 {
01962 if(row_info->bit_depth == 8)
01963 {
01964
01965 if (flags & PNG_FLAG_FILLER_AFTER)
01966 {
01967 png_bytep sp = row + (png_size_t)row_width;
01968 png_bytep dp = sp + (png_size_t)row_width;
01969 for (i = 1; i < row_width; i++)
01970 {
01971 *(--dp) = lo_filler;
01972 *(--dp) = *(--sp);
01973 }
01974 *(--dp) = lo_filler;
01975 row_info->channels = 2;
01976 row_info->pixel_depth = 16;
01977 row_info->rowbytes = row_width * 2;
01978 }
01979
01980 else
01981 {
01982 png_bytep sp = row + (png_size_t)row_width;
01983 png_bytep dp = sp + (png_size_t)row_width;
01984 for (i = 0; i < row_width; i++)
01985 {
01986 *(--dp) = *(--sp);
01987 *(--dp) = lo_filler;
01988 }
01989 row_info->channels = 2;
01990 row_info->pixel_depth = 16;
01991 row_info->rowbytes = row_width * 2;
01992 }
01993 }
01994 else if(row_info->bit_depth == 16)
01995 {
01996
01997 if (flags & PNG_FLAG_FILLER_AFTER)
01998 {
01999 png_bytep sp = row + (png_size_t)row_width * 2;
02000 png_bytep dp = sp + (png_size_t)row_width * 2;
02001 for (i = 1; i < row_width; i++)
02002 {
02003 *(--dp) = hi_filler;
02004 *(--dp) = lo_filler;
02005 *(--dp) = *(--sp);
02006 *(--dp) = *(--sp);
02007 }
02008 *(--dp) = hi_filler;
02009 *(--dp) = lo_filler;
02010 row_info->channels = 2;
02011 row_info->pixel_depth = 32;
02012 row_info->rowbytes = row_width * 4;
02013 }
02014
02015 else
02016 {
02017 png_bytep sp = row + (png_size_t)row_width * 2;
02018 png_bytep dp = sp + (png_size_t)row_width * 2;
02019 for (i = 0; i < row_width; i++)
02020 {
02021 *(--dp) = *(--sp);
02022 *(--dp) = *(--sp);
02023 *(--dp) = hi_filler;
02024 *(--dp) = lo_filler;
02025 }
02026 row_info->channels = 2;
02027 row_info->pixel_depth = 32;
02028 row_info->rowbytes = row_width * 4;
02029 }
02030 }
02031 }
02032 else if (row_info->color_type == PNG_COLOR_TYPE_RGB)
02033 {
02034 if(row_info->bit_depth == 8)
02035 {
02036
02037 if (flags & PNG_FLAG_FILLER_AFTER)
02038 {
02039 png_bytep sp = row + (png_size_t)row_width * 3;
02040 png_bytep dp = sp + (png_size_t)row_width;
02041 for (i = 1; i < row_width; i++)
02042 {
02043 *(--dp) = lo_filler;
02044 *(--dp) = *(--sp);
02045 *(--dp) = *(--sp);
02046 *(--dp) = *(--sp);
02047 }
02048 *(--dp) = lo_filler;
02049 row_info->channels = 4;
02050 row_info->pixel_depth = 32;
02051 row_info->rowbytes = row_width * 4;
02052 }
02053
02054 else
02055 {
02056 png_bytep sp = row + (png_size_t)row_width * 3;
02057 png_bytep dp = sp + (png_size_t)row_width;
02058 for (i = 0; i < row_width; i++)
02059 {
02060 *(--dp) = *(--sp);
02061 *(--dp) = *(--sp);
02062 *(--dp) = *(--sp);
02063 *(--dp) = lo_filler;
02064 }
02065 row_info->channels = 4;
02066 row_info->pixel_depth = 32;
02067 row_info->rowbytes = row_width * 4;
02068 }
02069 }
02070 else if(row_info->bit_depth == 16)
02071 {
02072
02073 if (flags & PNG_FLAG_FILLER_AFTER)
02074 {
02075 png_bytep sp = row + (png_size_t)row_width * 6;
02076 png_bytep dp = sp + (png_size_t)row_width * 2;
02077 for (i = 1; i < row_width; i++)
02078 {
02079 *(--dp) = hi_filler;
02080 *(--dp) = lo_filler;
02081 *(--dp) = *(--sp);
02082 *(--dp) = *(--sp);
02083 *(--dp) = *(--sp);
02084 *(--dp) = *(--sp);
02085 *(--dp) = *(--sp);
02086 *(--dp) = *(--sp);
02087 }
02088 *(--dp) = hi_filler;
02089 *(--dp) = lo_filler;
02090 row_info->channels = 4;
02091 row_info->pixel_depth = 64;
02092 row_info->rowbytes = row_width * 8;
02093 }
02094
02095 else
02096 {
02097 png_bytep sp = row + (png_size_t)row_width * 6;
02098 png_bytep dp = sp + (png_size_t)row_width * 2;
02099 for (i = 0; i < row_width; i++)
02100 {
02101 *(--dp) = *(--sp);
02102 *(--dp) = *(--sp);
02103 *(--dp) = *(--sp);
02104 *(--dp) = *(--sp);
02105 *(--dp) = *(--sp);
02106 *(--dp) = *(--sp);
02107 *(--dp) = hi_filler;
02108 *(--dp) = lo_filler;
02109 }
02110 row_info->channels = 4;
02111 row_info->pixel_depth = 64;
02112 row_info->rowbytes = row_width * 8;
02113 }
02114 }
02115 }
02116 }
02117 #endif
02118
02119 #if defined(PNG_READ_GRAY_TO_RGB_SUPPORTED)
02120
02121 void
02122 png_do_gray_to_rgb(png_row_infop row_info, png_bytep row)
02123 {
02124 png_uint_32 i;
02125 png_uint_32 row_width = row_info->width;
02126
02127 png_debug(1, "in png_do_gray_to_rgb\n");
02128 if (row_info->bit_depth >= 8 &&
02129 #if defined(PNG_USELESS_TESTS_SUPPORTED)
02130 row != NULL && row_info != NULL &&
02131 #endif
02132 !(row_info->color_type & PNG_COLOR_MASK_COLOR))
02133 {
02134 if (row_info->color_type == PNG_COLOR_TYPE_GRAY)
02135 {
02136 if (row_info->bit_depth == 8)
02137 {
02138 png_bytep sp = row + (png_size_t)row_width - 1;
02139 png_bytep dp = sp + (png_size_t)row_width * 2;
02140 for (i = 0; i < row_width; i++)
02141 {
02142 *(dp--) = *sp;
02143 *(dp--) = *sp;
02144 *(dp--) = *(sp--);
02145 }
02146 }
02147 else
02148 {
02149 png_bytep sp = row + (png_size_t)row_width * 2 - 1;
02150 png_bytep dp = sp + (png_size_t)row_width * 4;
02151 for (i = 0; i < row_width; i++)
02152 {
02153 *(dp--) = *sp;
02154 *(dp--) = *(sp - 1);
02155 *(dp--) = *sp;
02156 *(dp--) = *(sp - 1);
02157 *(dp--) = *(sp--);
02158 *(dp--) = *(sp--);
02159 }
02160 }
02161 }
02162 else if (row_info->color_type == PNG_COLOR_TYPE_GRAY_ALPHA)
02163 {
02164 if (row_info->bit_depth == 8)
02165 {
02166 png_bytep sp = row + (png_size_t)row_width * 2 - 1;
02167 png_bytep dp = sp + (png_size_t)row_width * 2;
02168 for (i = 0; i < row_width; i++)
02169 {
02170 *(dp--) = *(sp--);
02171 *(dp--) = *sp;
02172 *(dp--) = *sp;
02173 *(dp--) = *(sp--);
02174 }
02175 }
02176 else
02177 {
02178 png_bytep sp = row + (png_size_t)row_width * 4 - 1;
02179 png_bytep dp = sp + (png_size_t)row_width * 4;
02180 for (i = 0; i < row_width; i++)
02181 {
02182 *(dp--) = *(sp--);
02183 *(dp--) = *(sp--);
02184 *(dp--) = *sp;
02185 *(dp--) = *(sp - 1);
02186 *(dp--) = *sp;
02187 *(dp--) = *(sp - 1);
02188 *(dp--) = *(sp--);
02189 *(dp--) = *(sp--);
02190 }
02191 }
02192 }
02193 row_info->channels += (png_byte)2;
02194 row_info->color_type |= PNG_COLOR_MASK_COLOR;
02195 row_info->pixel_depth = (png_byte)(row_info->channels *
02196 row_info->bit_depth);
02197 row_info->rowbytes = PNG_ROWBYTES(row_info->pixel_depth,row_width);
02198 }
02199 }
02200 #endif
02201
02202 #if defined(PNG_READ_RGB_TO_GRAY_SUPPORTED)
02203
02204
02205
02206
02207
02208
02209
02210
02211
02212
02213
02214
02215
02216
02217
02218
02219
02220
02221
02222 int
02223 png_do_rgb_to_gray(png_structp png_ptr, png_row_infop row_info, png_bytep row)
02224
02225 {
02226 png_uint_32 i;
02227
02228 png_uint_32 row_width = row_info->width;
02229 int rgb_error = 0;
02230
02231 png_debug(1, "in png_do_rgb_to_gray\n");
02232 if (
02233 #if defined(PNG_USELESS_TESTS_SUPPORTED)
02234 row != NULL && row_info != NULL &&
02235 #endif
02236 (row_info->color_type & PNG_COLOR_MASK_COLOR))
02237 {
02238 png_uint_32 rc = png_ptr->rgb_to_gray_red_coeff;
02239 png_uint_32 gc = png_ptr->rgb_to_gray_green_coeff;
02240 png_uint_32 bc = png_ptr->rgb_to_gray_blue_coeff;
02241
02242 if (row_info->color_type == PNG_COLOR_TYPE_RGB)
02243 {
02244 if (row_info->bit_depth == 8)
02245 {
02246 #if defined(PNG_READ_GAMMA_SUPPORTED) || defined(PNG_READ_BACKGROUND_SUPPORTED)
02247 if (png_ptr->gamma_from_1 != NULL && png_ptr->gamma_to_1 != NULL)
02248 {
02249 png_bytep sp = row;
02250 png_bytep dp = row;
02251
02252 for (i = 0; i < row_width; i++)
02253 {
02254 png_byte red = png_ptr->gamma_to_1[*(sp++)];
02255 png_byte green = png_ptr->gamma_to_1[*(sp++)];
02256 png_byte blue = png_ptr->gamma_to_1[*(sp++)];
02257 if(red != green || red != blue)
02258 {
02259 rgb_error |= 1;
02260 *(dp++) = png_ptr->gamma_from_1[
02261 (rc*red+gc*green+bc*blue)>>15];
02262 }
02263 else
02264 *(dp++) = *(sp-1);
02265 }
02266 }
02267 else
02268 #endif
02269 {
02270 png_bytep sp = row;
02271 png_bytep dp = row;
02272 for (i = 0; i < row_width; i++)
02273 {
02274 png_byte red = *(sp++);
02275 png_byte green = *(sp++);
02276 png_byte blue = *(sp++);
02277 if(red != green || red != blue)
02278 {
02279 rgb_error |= 1;
02280 *(dp++) = (png_byte)((rc*red+gc*green+bc*blue)>>15);
02281 }
02282 else
02283 *(dp++) = *(sp-1);
02284 }
02285 }
02286 }
02287
02288 else
02289 {
02290 #if defined(PNG_READ_GAMMA_SUPPORTED) || defined(PNG_READ_BACKGROUND_SUPPORTED)
02291 if (png_ptr->gamma_16_to_1 != NULL &&
02292 png_ptr->gamma_16_from_1 != NULL)
02293 {
02294 png_bytep sp = row;
02295 png_bytep dp = row;
02296 for (i = 0; i < row_width; i++)
02297 {
02298 png_uint_16 red, green, blue, w;
02299
02300 red = (png_uint_16)(((*(sp))<<8) | *(sp+1)); sp+=2;
02301 green = (png_uint_16)(((*(sp))<<8) | *(sp+1)); sp+=2;
02302 blue = (png_uint_16)(((*(sp))<<8) | *(sp+1)); sp+=2;
02303
02304 if(red == green && red == blue)
02305 w = red;
02306 else
02307 {
02308 png_uint_16 red_1 = png_ptr->gamma_16_to_1[(red&0xff) >>
02309 png_ptr->gamma_shift][red>>8];
02310 png_uint_16 green_1 = png_ptr->gamma_16_to_1[(green&0xff) >>
02311 png_ptr->gamma_shift][green>>8];
02312 png_uint_16 blue_1 = png_ptr->gamma_16_to_1[(blue&0xff) >>
02313 png_ptr->gamma_shift][blue>>8];
02314 png_uint_16 gray16 = (png_uint_16)((rc*red_1 + gc*green_1
02315 + bc*blue_1)>>15);
02316 w = png_ptr->gamma_16_from_1[(gray16&0xff) >>
02317 png_ptr->gamma_shift][gray16 >> 8];
02318 rgb_error |= 1;
02319 }
02320
02321 *(dp++) = (png_byte)((w>>8) & 0xff);
02322 *(dp++) = (png_byte)(w & 0xff);
02323 }
02324 }
02325 else
02326 #endif
02327 {
02328 png_bytep sp = row;
02329 png_bytep dp = row;
02330 for (i = 0; i < row_width; i++)
02331 {
02332 png_uint_16 red, green, blue, gray16;
02333
02334 red = (png_uint_16)(((*(sp))<<8) | *(sp+1)); sp+=2;
02335 green = (png_uint_16)(((*(sp))<<8) | *(sp+1)); sp+=2;
02336 blue = (png_uint_16)(((*(sp))<<8) | *(sp+1)); sp+=2;
02337
02338 if(red != green || red != blue)
02339 rgb_error |= 1;
02340 gray16 = (png_uint_16)((rc*red + gc*green + bc*blue)>>15);
02341 *(dp++) = (png_byte)((gray16>>8) & 0xff);
02342 *(dp++) = (png_byte)(gray16 & 0xff);
02343 }
02344 }
02345 }
02346 }
02347 if (row_info->color_type == PNG_COLOR_TYPE_RGB_ALPHA)
02348 {
02349 if (row_info->bit_depth == 8)
02350 {
02351 #if defined(PNG_READ_GAMMA_SUPPORTED) || defined(PNG_READ_BACKGROUND_SUPPORTED)
02352 if (png_ptr->gamma_from_1 != NULL && png_ptr->gamma_to_1 != NULL)
02353 {
02354 png_bytep sp = row;
02355 png_bytep dp = row;
02356 for (i = 0; i < row_width; i++)
02357 {
02358 png_byte red = png_ptr->gamma_to_1[*(sp++)];
02359 png_byte green = png_ptr->gamma_to_1[*(sp++)];
02360 png_byte blue = png_ptr->gamma_to_1[*(sp++)];
02361 if(red != green || red != blue)
02362 rgb_error |= 1;
02363 *(dp++) = png_ptr->gamma_from_1
02364 [(rc*red + gc*green + bc*blue)>>15];
02365 *(dp++) = *(sp++);
02366 }
02367 }
02368 else
02369 #endif
02370 {
02371 png_bytep sp = row;
02372 png_bytep dp = row;
02373 for (i = 0; i < row_width; i++)
02374 {
02375 png_byte red = *(sp++);
02376 png_byte green = *(sp++);
02377 png_byte blue = *(sp++);
02378 if(red != green || red != blue)
02379 rgb_error |= 1;
02380 *(dp++) = (png_byte)((rc*red + gc*green + bc*blue)>>15);
02381 *(dp++) = *(sp++);
02382 }
02383 }
02384 }
02385 else
02386 {
02387 #if defined(PNG_READ_GAMMA_SUPPORTED) || defined(PNG_READ_BACKGROUND_SUPPORTED)
02388 if (png_ptr->gamma_16_to_1 != NULL &&
02389 png_ptr->gamma_16_from_1 != NULL)
02390 {
02391 png_bytep sp = row;
02392 png_bytep dp = row;
02393 for (i = 0; i < row_width; i++)
02394 {
02395 png_uint_16 red, green, blue, w;
02396
02397 red = (png_uint_16)(((*(sp))<<8) | *(sp+1)); sp+=2;
02398 green = (png_uint_16)(((*(sp))<<8) | *(sp+1)); sp+=2;
02399 blue = (png_uint_16)(((*(sp))<<8) | *(sp+1)); sp+=2;
02400
02401 if(red == green && red == blue)
02402 w = red;
02403 else
02404 {
02405 png_uint_16 red_1 = png_ptr->gamma_16_to_1[(red&0xff) >>
02406 png_ptr->gamma_shift][red>>8];
02407 png_uint_16 green_1 = png_ptr->gamma_16_to_1[(green&0xff) >>
02408 png_ptr->gamma_shift][green>>8];
02409 png_uint_16 blue_1 = png_ptr->gamma_16_to_1[(blue&0xff) >>
02410 png_ptr->gamma_shift][blue>>8];
02411 png_uint_16 gray16 = (png_uint_16)((rc * red_1
02412 + gc * green_1 + bc * blue_1)>>15);
02413 w = png_ptr->gamma_16_from_1[(gray16&0xff) >>
02414 png_ptr->gamma_shift][gray16 >> 8];
02415 rgb_error |= 1;
02416 }
02417
02418 *(dp++) = (png_byte)((w>>8) & 0xff);
02419 *(dp++) = (png_byte)(w & 0xff);
02420 *(dp++) = *(sp++);
02421 *(dp++) = *(sp++);
02422 }
02423 }
02424 else
02425 #endif
02426 {
02427 png_bytep sp = row;
02428 png_bytep dp = row;
02429 for (i = 0; i < row_width; i++)
02430 {
02431 png_uint_16 red, green, blue, gray16;
02432 red = (png_uint_16)((*(sp)<<8) | *(sp+1)); sp+=2;
02433 green = (png_uint_16)((*(sp)<<8) | *(sp+1)); sp+=2;
02434 blue = (png_uint_16)((*(sp)<<8) | *(sp+1)); sp+=2;
02435 if(red != green || red != blue)
02436 rgb_error |= 1;
02437 gray16 = (png_uint_16)((rc*red + gc*green + bc*blue)>>15);
02438 *(dp++) = (png_byte)((gray16>>8) & 0xff);
02439 *(dp++) = (png_byte)(gray16 & 0xff);
02440 *(dp++) = *(sp++);
02441 *(dp++) = *(sp++);
02442 }
02443 }
02444 }
02445 }
02446 row_info->channels -= (png_byte)2;
02447 row_info->color_type &= ~PNG_COLOR_MASK_COLOR;
02448 row_info->pixel_depth = (png_byte)(row_info->channels *
02449 row_info->bit_depth);
02450 row_info->rowbytes = PNG_ROWBYTES(row_info->pixel_depth,row_width);
02451 }
02452 return rgb_error;
02453 }
02454 #endif
02455
02456
02457
02458
02459
02460
02461 void PNGAPI
02462 png_build_grayscale_palette(int bit_depth, png_colorp palette)
02463 {
02464 int num_palette;
02465 int color_inc;
02466 int i;
02467 int v;
02468
02469 png_debug(1, "in png_do_build_grayscale_palette\n");
02470 if (palette == NULL)
02471 return;
02472
02473 switch (bit_depth)
02474 {
02475 case 1:
02476 num_palette = 2;
02477 color_inc = 0xff;
02478 break;
02479 case 2:
02480 num_palette = 4;
02481 color_inc = 0x55;
02482 break;
02483 case 4:
02484 num_palette = 16;
02485 color_inc = 0x11;
02486 break;
02487 case 8:
02488 num_palette = 256;
02489 color_inc = 1;
02490 break;
02491 default:
02492 num_palette = 0;
02493 color_inc = 0;
02494 break;
02495 }
02496
02497 for (i = 0, v = 0; i < num_palette; i++, v += color_inc)
02498 {
02499 palette[i].red = (png_byte)v;
02500 palette[i].green = (png_byte)v;
02501 palette[i].blue = (png_byte)v;
02502 }
02503 }
02504
02505
02506 #if defined(PNG_READ_DITHER_SUPPORTED) && defined(PNG_CORRECT_PALETTE_SUPPORTED)
02507 void
02508 png_correct_palette(png_structp png_ptr, png_colorp palette,
02509 int num_palette)
02510 {
02511 png_debug(1, "in png_correct_palette\n");
02512 #if defined(PNG_READ_BACKGROUND_SUPPORTED) && \
02513 defined(PNG_READ_GAMMA_SUPPORTED) && defined(PNG_FLOATING_POINT_SUPPORTED)
02514 if (png_ptr->transformations & (PNG_GAMMA | PNG_BACKGROUND))
02515 {
02516 png_color back, back_1;
02517
02518 if (png_ptr->background_gamma_type == PNG_BACKGROUND_GAMMA_FILE)
02519 {
02520 back.red = png_ptr->gamma_table[png_ptr->background.red];
02521 back.green = png_ptr->gamma_table[png_ptr->background.green];
02522 back.blue = png_ptr->gamma_table[png_ptr->background.blue];
02523
02524 back_1.red = png_ptr->gamma_to_1[png_ptr->background.red];
02525 back_1.green = png_ptr->gamma_to_1[png_ptr->background.green];
02526 back_1.blue = png_ptr->gamma_to_1[png_ptr->background.blue];
02527 }
02528 else
02529 {
02530 double g;
02531
02532 g = 1.0 / (png_ptr->background_gamma * png_ptr->screen_gamma);
02533
02534 if (png_ptr->background_gamma_type == PNG_BACKGROUND_GAMMA_SCREEN ||
02535 fabs(g - 1.0) < PNG_GAMMA_THRESHOLD)
02536 {
02537 back.red = png_ptr->background.red;
02538 back.green = png_ptr->background.green;
02539 back.blue = png_ptr->background.blue;
02540 }
02541 else
02542 {
02543 back.red =
02544 (png_byte)(pow((double)png_ptr->background.red/255, g) *
02545 255.0 + 0.5);
02546 back.green =
02547 (png_byte)(pow((double)png_ptr->background.green/255, g) *
02548 255.0 + 0.5);
02549 back.blue =
02550 (png_byte)(pow((double)png_ptr->background.blue/255, g) *
02551 255.0 + 0.5);
02552 }
02553
02554 g = 1.0 / png_ptr->background_gamma;
02555
02556 back_1.red =
02557 (png_byte)(pow((double)png_ptr->background.red/255, g) *
02558 255.0 + 0.5);
02559 back_1.green =
02560 (png_byte)(pow((double)png_ptr->background.green/255, g) *
02561 255.0 + 0.5);
02562 back_1.blue =
02563 (png_byte)(pow((double)png_ptr->background.blue/255, g) *
02564 255.0 + 0.5);
02565 }
02566
02567 if (png_ptr->color_type == PNG_COLOR_TYPE_PALETTE)
02568 {
02569 png_uint_32 i;
02570
02571 for (i = 0; i < (png_uint_32)num_palette; i++)
02572 {
02573 if (i < png_ptr->num_trans && png_ptr->trans[i] == 0)
02574 {
02575 palette[i] = back;
02576 }
02577 else if (i < png_ptr->num_trans && png_ptr->trans[i] != 0xff)
02578 {
02579 png_byte v, w;
02580
02581 v = png_ptr->gamma_to_1[png_ptr->palette[i].red];
02582 png_composite(w, v, png_ptr->trans[i], back_1.red);
02583 palette[i].red = png_ptr->gamma_from_1[w];
02584
02585 v = png_ptr->gamma_to_1[png_ptr->palette[i].green];
02586 png_composite(w, v, png_ptr->trans[i], back_1.green);
02587 palette[i].green = png_ptr->gamma_from_1[w];
02588
02589 v = png_ptr->gamma_to_1[png_ptr->palette[i].blue];
02590 png_composite(w, v, png_ptr->trans[i], back_1.blue);
02591 palette[i].blue = png_ptr->gamma_from_1[w];
02592 }
02593 else
02594 {
02595 palette[i].red = png_ptr->gamma_table[palette[i].red];
02596 palette[i].green = png_ptr->gamma_table[palette[i].green];
02597 palette[i].blue = png_ptr->gamma_table[palette[i].blue];
02598 }
02599 }
02600 }
02601 else
02602 {
02603 int i;
02604
02605 for (i = 0; i < num_palette; i++)
02606 {
02607 if (palette[i].red == (png_byte)png_ptr->trans_values.gray)
02608 {
02609 palette[i] = back;
02610 }
02611 else
02612 {
02613 palette[i].red = png_ptr->gamma_table[palette[i].red];
02614 palette[i].green = png_ptr->gamma_table[palette[i].green];
02615 palette[i].blue = png_ptr->gamma_table[palette[i].blue];
02616 }
02617 }
02618 }
02619 }
02620 else
02621 #endif
02622 #if defined(PNG_READ_GAMMA_SUPPORTED)
02623 if (png_ptr->transformations & PNG_GAMMA)
02624 {
02625 int i;
02626
02627 for (i = 0; i < num_palette; i++)
02628 {
02629 palette[i].red = png_ptr->gamma_table[palette[i].red];
02630 palette[i].green = png_ptr->gamma_table[palette[i].green];
02631 palette[i].blue = png_ptr->gamma_table[palette[i].blue];
02632 }
02633 }
02634 #if defined(PNG_READ_BACKGROUND_SUPPORTED)
02635 else
02636 #endif
02637 #endif
02638 #if defined(PNG_READ_BACKGROUND_SUPPORTED)
02639 if (png_ptr->transformations & PNG_BACKGROUND)
02640 {
02641 if (png_ptr->color_type == PNG_COLOR_TYPE_PALETTE)
02642 {
02643 png_color back;
02644
02645 back.red = (png_byte)png_ptr->background.red;
02646 back.green = (png_byte)png_ptr->background.green;
02647 back.blue = (png_byte)png_ptr->background.blue;
02648
02649 for (i = 0; i < (int)png_ptr->num_trans; i++)
02650 {
02651 if (png_ptr->trans[i] == 0)
02652 {
02653 palette[i].red = back.red;
02654 palette[i].green = back.green;
02655 palette[i].blue = back.blue;
02656 }
02657 else if (png_ptr->trans[i] != 0xff)
02658 {
02659 png_composite(palette[i].red, png_ptr->palette[i].red,
02660 png_ptr->trans[i], back.red);
02661 png_composite(palette[i].green, png_ptr->palette[i].green,
02662 png_ptr->trans[i], back.green);
02663 png_composite(palette[i].blue, png_ptr->palette[i].blue,
02664 png_ptr->trans[i], back.blue);
02665 }
02666 }
02667 }
02668 else
02669 {
02670 int i;
02671
02672 for (i = 0; i < num_palette; i++)
02673 {
02674 if (i == (png_byte)png_ptr->trans_values.gray)
02675 {
02676 palette[i].red = (png_byte)png_ptr->background.red;
02677 palette[i].green = (png_byte)png_ptr->background.green;
02678 palette[i].blue = (png_byte)png_ptr->background.blue;
02679 }
02680 }
02681 }
02682 }
02683 #endif
02684 }
02685 #endif
02686
02687 #if defined(PNG_READ_BACKGROUND_SUPPORTED)
02688
02689
02690
02691
02692 void
02693 png_do_background(png_row_infop row_info, png_bytep row,
02694 png_color_16p trans_values, png_color_16p background
02695 #if defined(PNG_READ_GAMMA_SUPPORTED)
02696 , png_color_16p background_1,
02697 png_bytep gamma_table, png_bytep gamma_from_1, png_bytep gamma_to_1,
02698 png_uint_16pp gamma_16, png_uint_16pp gamma_16_from_1,
02699 png_uint_16pp gamma_16_to_1, int gamma_shift
02700 #endif
02701 )
02702 {
02703 png_bytep sp, dp;
02704 png_uint_32 i;
02705 png_uint_32 row_width=row_info->width;
02706 int shift;
02707
02708 png_debug(1, "in png_do_background\n");
02709 if (background != NULL &&
02710 #if defined(PNG_USELESS_TESTS_SUPPORTED)
02711 row != NULL && row_info != NULL &&
02712 #endif
02713 (!(row_info->color_type & PNG_COLOR_MASK_ALPHA) ||
02714 (row_info->color_type != PNG_COLOR_TYPE_PALETTE && trans_values)))
02715 {
02716 switch (row_info->color_type)
02717 {
02718 case PNG_COLOR_TYPE_GRAY:
02719 {
02720 switch (row_info->bit_depth)
02721 {
02722 case 1:
02723 {
02724 sp = row;
02725 shift = 7;
02726 for (i = 0; i < row_width; i++)
02727 {
02728 if ((png_uint_16)((*sp >> shift) & 0x01)
02729 == trans_values->gray)
02730 {
02731 *sp &= (png_byte)((0x7f7f >> (7 - shift)) & 0xff);
02732 *sp |= (png_byte)(background->gray << shift);
02733 }
02734 if (!shift)
02735 {
02736 shift = 7;
02737 sp++;
02738 }
02739 else
02740 shift--;
02741 }
02742 break;
02743 }
02744 case 2:
02745 {
02746 #if defined(PNG_READ_GAMMA_SUPPORTED)
02747 if (gamma_table != NULL)
02748 {
02749 sp = row;
02750 shift = 6;
02751 for (i = 0; i < row_width; i++)
02752 {
02753 if ((png_uint_16)((*sp >> shift) & 0x03)
02754 == trans_values->gray)
02755 {
02756 *sp &= (png_byte)((0x3f3f >> (6 - shift)) & 0xff);
02757 *sp |= (png_byte)(background->gray << shift);
02758 }
02759 else
02760 {
02761 png_byte p = (png_byte)((*sp >> shift) & 0x03);
02762 png_byte g = (png_byte)((gamma_table [p | (p << 2) |
02763 (p << 4) | (p << 6)] >> 6) & 0x03);
02764 *sp &= (png_byte)((0x3f3f >> (6 - shift)) & 0xff);
02765 *sp |= (png_byte)(g << shift);
02766 }
02767 if (!shift)
02768 {
02769 shift = 6;
02770 sp++;
02771 }
02772 else
02773 shift -= 2;
02774 }
02775 }
02776 else
02777 #endif
02778 {
02779 sp = row;
02780 shift = 6;
02781 for (i = 0; i < row_width; i++)
02782 {
02783 if ((png_uint_16)((*sp >> shift) & 0x03)
02784 == trans_values->gray)
02785 {
02786 *sp &= (png_byte)((0x3f3f >> (6 - shift)) & 0xff);
02787 *sp |= (png_byte)(background->gray << shift);
02788 }
02789 if (!shift)
02790 {
02791 shift = 6;
02792 sp++;
02793 }
02794 else
02795 shift -= 2;
02796 }
02797 }
02798 break;
02799 }
02800 case 4:
02801 {
02802 #if defined(PNG_READ_GAMMA_SUPPORTED)
02803 if (gamma_table != NULL)
02804 {
02805 sp = row;
02806 shift = 4;
02807 for (i = 0; i < row_width; i++)
02808 {
02809 if ((png_uint_16)((*sp >> shift) & 0x0f)
02810 == trans_values->gray)
02811 {
02812 *sp &= (png_byte)((0xf0f >> (4 - shift)) & 0xff);
02813 *sp |= (png_byte)(background->gray << shift);
02814 }
02815 else
02816 {
02817 png_byte p = (png_byte)((*sp >> shift) & 0x0f);
02818 png_byte g = (png_byte)((gamma_table[p |
02819 (p << 4)] >> 4) & 0x0f);
02820 *sp &= (png_byte)((0xf0f >> (4 - shift)) & 0xff);
02821 *sp |= (png_byte)(g << shift);
02822 }
02823 if (!shift)
02824 {
02825 shift = 4;
02826 sp++;
02827 }
02828 else
02829 shift -= 4;
02830 }
02831 }
02832 else
02833 #endif
02834 {
02835 sp = row;
02836 shift = 4;
02837 for (i = 0; i < row_width; i++)
02838 {
02839 if ((png_uint_16)((*sp >> shift) & 0x0f)
02840 == trans_values->gray)
02841 {
02842 *sp &= (png_byte)((0xf0f >> (4 - shift)) & 0xff);
02843 *sp |= (png_byte)(background->gray << shift);
02844 }
02845 if (!shift)
02846 {
02847 shift = 4;
02848 sp++;
02849 }
02850 else
02851 shift -= 4;
02852 }
02853 }
02854 break;
02855 }
02856 case 8:
02857 {
02858 #if defined(PNG_READ_GAMMA_SUPPORTED)
02859 if (gamma_table != NULL)
02860 {
02861 sp = row;
02862 for (i = 0; i < row_width; i++, sp++)
02863 {
02864 if (*sp == trans_values->gray)
02865 {
02866 *sp = (png_byte)background->gray;
02867 }
02868 else
02869 {
02870 *sp = gamma_table[*sp];
02871 }
02872 }
02873 }
02874 else
02875 #endif
02876 {
02877 sp = row;
02878 for (i = 0; i < row_width; i++, sp++)
02879 {
02880 if (*sp == trans_values->gray)
02881 {
02882 *sp = (png_byte)background->gray;
02883 }
02884 }
02885 }
02886 break;
02887 }
02888 case 16:
02889 {
02890 #if defined(PNG_READ_GAMMA_SUPPORTED)
02891 if (gamma_16 != NULL)
02892 {
02893 sp = row;
02894 for (i = 0; i < row_width; i++, sp += 2)
02895 {
02896 png_uint_16 v;
02897
02898 v = (png_uint_16)(((*sp) << 8) + *(sp + 1));
02899 if (v == trans_values->gray)
02900 {
02901
02902 *sp = (png_byte)((background->gray >> 8) & 0xff);
02903 *(sp + 1) = (png_byte)(background->gray & 0xff);
02904 }
02905 else
02906 {
02907 v = gamma_16[*(sp + 1) >> gamma_shift][*sp];
02908 *sp = (png_byte)((v >> 8) & 0xff);
02909 *(sp + 1) = (png_byte)(v & 0xff);
02910 }
02911 }
02912 }
02913 else
02914 #endif
02915 {
02916 sp = row;
02917 for (i = 0; i < row_width; i++, sp += 2)
02918 {
02919 png_uint_16 v;
02920
02921 v = (png_uint_16)(((*sp) << 8) + *(sp + 1));
02922 if (v == trans_values->gray)
02923 {
02924 *sp = (png_byte)((background->gray >> 8) & 0xff);
02925 *(sp + 1) = (png_byte)(background->gray & 0xff);
02926 }
02927 }
02928 }
02929 break;
02930 }
02931 }
02932 break;
02933 }
02934 case PNG_COLOR_TYPE_RGB:
02935 {
02936 if (row_info->bit_depth == 8)
02937 {
02938 #if defined(PNG_READ_GAMMA_SUPPORTED)
02939 if (gamma_table != NULL)
02940 {
02941 sp = row;
02942 for (i = 0; i < row_width; i++, sp += 3)
02943 {
02944 if (*sp == trans_values->red &&
02945 *(sp + 1) == trans_values->green &&
02946 *(sp + 2) == trans_values->blue)
02947 {
02948 *sp = (png_byte)background->red;
02949 *(sp + 1) = (png_byte)background->green;
02950 *(sp + 2) = (png_byte)background->blue;
02951 }
02952 else
02953 {
02954 *sp = gamma_table[*sp];
02955 *(sp + 1) = gamma_table[*(sp + 1)];
02956 *(sp + 2) = gamma_table[*(sp + 2)];
02957 }
02958 }
02959 }
02960 else
02961 #endif
02962 {
02963 sp = row;
02964 for (i = 0; i < row_width; i++, sp += 3)
02965 {
02966 if (*sp == trans_values->red &&
02967 *(sp + 1) == trans_values->green &&
02968 *(sp + 2) == trans_values->blue)
02969 {
02970 *sp = (png_byte)background->red;
02971 *(sp + 1) = (png_byte)background->green;
02972 *(sp + 2) = (png_byte)background->blue;
02973 }
02974 }
02975 }
02976 }
02977 else
02978 {
02979 #if defined(PNG_READ_GAMMA_SUPPORTED)
02980 if (gamma_16 != NULL)
02981 {
02982 sp = row;
02983 for (i = 0; i < row_width; i++, sp += 6)
02984 {
02985 png_uint_16 r = (png_uint_16)(((*sp) << 8) + *(sp + 1));
02986 png_uint_16 g = (png_uint_16)(((*(sp+2)) << 8) + *(sp+3));
02987 png_uint_16 b = (png_uint_16)(((*(sp+4)) << 8) + *(sp+5));
02988 if (r == trans_values->red && g == trans_values->green &&
02989 b == trans_values->blue)
02990 {
02991
02992 *sp = (png_byte)((background->red >> 8) & 0xff);
02993 *(sp + 1) = (png_byte)(background->red & 0xff);
02994 *(sp + 2) = (png_byte)((background->green >> 8) & 0xff);
02995 *(sp + 3) = (png_byte)(background->green & 0xff);
02996 *(sp + 4) = (png_byte)((background->blue >> 8) & 0xff);
02997 *(sp + 5) = (png_byte)(background->blue & 0xff);
02998 }
02999 else
03000 {
03001 png_uint_16 v = gamma_16[*(sp + 1) >> gamma_shift][*sp];
03002 *sp = (png_byte)((v >> 8) & 0xff);
03003 *(sp + 1) = (png_byte)(v & 0xff);
03004 v = gamma_16[*(sp + 3) >> gamma_shift][*(sp + 2)];
03005 *(sp + 2) = (png_byte)((v >> 8) & 0xff);
03006 *(sp + 3) = (png_byte)(v & 0xff);
03007 v = gamma_16[*(sp + 5) >> gamma_shift][*(sp + 4)];
03008 *(sp + 4) = (png_byte)((v >> 8) & 0xff);
03009 *(sp + 5) = (png_byte)(v & 0xff);
03010 }
03011 }
03012 }
03013 else
03014 #endif
03015 {
03016 sp = row;
03017 for (i = 0; i < row_width; i++, sp += 6)
03018 {
03019 png_uint_16 r = (png_uint_16)(((*sp) << 8) + *(sp+1));
03020 png_uint_16 g = (png_uint_16)(((*(sp+2)) << 8) + *(sp+3));
03021 png_uint_16 b = (png_uint_16)(((*(sp+4)) << 8) + *(sp+5));
03022
03023 if (r == trans_values->red && g == trans_values->green &&
03024 b == trans_values->blue)
03025 {
03026 *sp = (png_byte)((background->red >> 8) & 0xff);
03027 *(sp + 1) = (png_byte)(background->red & 0xff);
03028 *(sp + 2) = (png_byte)((background->green >> 8) & 0xff);
03029 *(sp + 3) = (png_byte)(background->green & 0xff);
03030 *(sp + 4) = (png_byte)((background->blue >> 8) & 0xff);
03031 *(sp + 5) = (png_byte)(background->blue & 0xff);
03032 }
03033 }
03034 }
03035 }
03036 break;
03037 }
03038 case PNG_COLOR_TYPE_GRAY_ALPHA:
03039 {
03040 if (row_info->bit_depth == 8)
03041 {
03042 #if defined(PNG_READ_GAMMA_SUPPORTED)
03043 if (gamma_to_1 != NULL && gamma_from_1 != NULL &&
03044 gamma_table != NULL)
03045 {
03046 sp = row;
03047 dp = row;
03048 for (i = 0; i < row_width; i++, sp += 2, dp++)
03049 {
03050 png_uint_16 a = *(sp + 1);
03051
03052 if (a == 0xff)
03053 {
03054 *dp = gamma_table[*sp];
03055 }
03056 else if (a == 0)
03057 {
03058
03059 *dp = (png_byte)background->gray;
03060 }
03061 else
03062 {
03063 png_byte v, w;
03064
03065 v = gamma_to_1[*sp];
03066 png_composite(w, v, a, background_1->gray);
03067 *dp = gamma_from_1[w];
03068 }
03069 }
03070 }
03071 else
03072 #endif
03073 {
03074 sp = row;
03075 dp = row;
03076 for (i = 0; i < row_width; i++, sp += 2, dp++)
03077 {
03078 png_byte a = *(sp + 1);
03079
03080 if (a == 0xff)
03081 {
03082 *dp = *sp;
03083 }
03084 #if defined(PNG_READ_GAMMA_SUPPORTED)
03085 else if (a == 0)
03086 {
03087 *dp = (png_byte)background->gray;
03088 }
03089 else
03090 {
03091 png_composite(*dp, *sp, a, background_1->gray);
03092 }
03093 #else
03094 *dp = (png_byte)background->gray;
03095 #endif
03096 }
03097 }
03098 }
03099 else
03100 {
03101 #if defined(PNG_READ_GAMMA_SUPPORTED)
03102 if (gamma_16 != NULL && gamma_16_from_1 != NULL &&
03103 gamma_16_to_1 != NULL)
03104 {
03105 sp = row;
03106 dp = row;
03107 for (i = 0; i < row_width; i++, sp += 4, dp += 2)
03108 {
03109 png_uint_16 a = (png_uint_16)(((*(sp+2)) << 8) + *(sp+3));
03110
03111 if (a == (png_uint_16)0xffff)
03112 {
03113 png_uint_16 v;
03114
03115 v = gamma_16[*(sp + 1) >> gamma_shift][*sp];
03116 *dp = (png_byte)((v >> 8) & 0xff);
03117 *(dp + 1) = (png_byte)(v & 0xff);
03118 }
03119 #if defined(PNG_READ_GAMMA_SUPPORTED)
03120 else if (a == 0)
03121 #else
03122 else
03123 #endif
03124 {
03125
03126 *dp = (png_byte)((background->gray >> 8) & 0xff);
03127 *(dp + 1) = (png_byte)(background->gray & 0xff);
03128 }
03129 #if defined(PNG_READ_GAMMA_SUPPORTED)
03130 else
03131 {
03132 png_uint_16 g, v, w;
03133
03134 g = gamma_16_to_1[*(sp + 1) >> gamma_shift][*sp];
03135 png_composite_16(v, g, a, background_1->gray);
03136 w = gamma_16_from_1[(v&0xff) >> gamma_shift][v >> 8];
03137 *dp = (png_byte)((w >> 8) & 0xff);
03138 *(dp + 1) = (png_byte)(w & 0xff);
03139 }
03140 #endif
03141 }
03142 }
03143 else
03144 #endif
03145 {
03146 sp = row;
03147 dp = row;
03148 for (i = 0; i < row_width; i++, sp += 4, dp += 2)
03149 {
03150 png_uint_16 a = (png_uint_16)(((*(sp+2)) << 8) + *(sp+3));
03151 if (a == (png_uint_16)0xffff)
03152 {
03153 png_memcpy(dp, sp, 2);
03154 }
03155 #if defined(PNG_READ_GAMMA_SUPPORTED)
03156 else if (a == 0)
03157 #else
03158 else
03159 #endif
03160 {
03161 *dp = (png_byte)((background->gray >> 8) & 0xff);
03162 *(dp + 1) = (png_byte)(background->gray & 0xff);
03163 }
03164 #if defined(PNG_READ_GAMMA_SUPPORTED)
03165 else
03166 {
03167 png_uint_16 g, v;
03168
03169 g = (png_uint_16)(((*sp) << 8) + *(sp + 1));
03170 png_composite_16(v, g, a, background_1->gray);
03171 *dp = (png_byte)((v >> 8) & 0xff);
03172 *(dp + 1) = (png_byte)(v & 0xff);
03173 }
03174 #endif
03175 }
03176 }
03177 }
03178 break;
03179 }
03180 case PNG_COLOR_TYPE_RGB_ALPHA:
03181 {
03182 if (row_info->bit_depth == 8)
03183 {
03184 #if defined(PNG_READ_GAMMA_SUPPORTED)
03185 if (gamma_to_1 != NULL && gamma_from_1 != NULL &&
03186 gamma_table != NULL)
03187 {
03188 sp = row;
03189 dp = row;
03190 for (i = 0; i < row_width; i++, sp += 4, dp += 3)
03191 {
03192 png_byte a = *(sp + 3);
03193
03194 if (a == 0xff)
03195 {
03196 *dp = gamma_table[*sp];
03197 *(dp + 1) = gamma_table[*(sp + 1)];
03198 *(dp + 2) = gamma_table[*(sp + 2)];
03199 }
03200 else if (a == 0)
03201 {
03202
03203 *dp = (png_byte)background->red;
03204 *(dp + 1) = (png_byte)background->green;
03205 *(dp + 2) = (png_byte)background->blue;
03206 }
03207 else
03208 {
03209 png_byte v, w;
03210
03211 v = gamma_to_1[*sp];
03212 png_composite(w, v, a, background_1->red);
03213 *dp = gamma_from_1[w];
03214 v = gamma_to_1[*(sp + 1)];
03215 png_composite(w, v, a, background_1->green);
03216 *(dp + 1) = gamma_from_1[w];
03217 v = gamma_to_1[*(sp + 2)];
03218 png_composite(w, v, a, background_1->blue);
03219 *(dp + 2) = gamma_from_1[w];
03220 }
03221 }
03222 }
03223 else
03224 #endif
03225 {
03226 sp = row;
03227 dp = row;
03228 for (i = 0; i < row_width; i++, sp += 4, dp += 3)
03229 {
03230 png_byte a = *(sp + 3);
03231
03232 if (a == 0xff)
03233 {
03234 *dp = *sp;
03235 *(dp + 1) = *(sp + 1);
03236 *(dp + 2) = *(sp + 2);
03237 }
03238 else if (a == 0)
03239 {
03240 *dp = (png_byte)background->red;
03241 *(dp + 1) = (png_byte)background->green;
03242 *(dp + 2) = (png_byte)background->blue;
03243 }
03244 else
03245 {
03246 png_composite(*dp, *sp, a, background->red);
03247 png_composite(*(dp + 1), *(sp + 1), a,
03248 background->green);
03249 png_composite(*(dp + 2), *(sp + 2), a,
03250 background->blue);
03251 }
03252 }
03253 }
03254 }
03255 else
03256 {
03257 #if defined(PNG_READ_GAMMA_SUPPORTED)
03258 if (gamma_16 != NULL && gamma_16_from_1 != NULL &&
03259 gamma_16_to_1 != NULL)
03260 {
03261 sp = row;
03262 dp = row;
03263 for (i = 0; i < row_width; i++, sp += 8, dp += 6)
03264 {
03265 png_uint_16 a = (png_uint_16)(((png_uint_16)(*(sp + 6))
03266 << 8) + (png_uint_16)(*(sp + 7)));
03267 if (a == (png_uint_16)0xffff)
03268 {
03269 png_uint_16 v;
03270
03271 v = gamma_16[*(sp + 1) >> gamma_shift][*sp];
03272 *dp = (png_byte)((v >> 8) & 0xff);
03273 *(dp + 1) = (png_byte)(v & 0xff);
03274 v = gamma_16[*(sp + 3) >> gamma_shift][*(sp + 2)];
03275 *(dp + 2) = (png_byte)((v >> 8) & 0xff);
03276 *(dp + 3) = (png_byte)(v & 0xff);
03277 v = gamma_16[*(sp + 5) >> gamma_shift][*(sp + 4)];
03278 *(dp + 4) = (png_byte)((v >> 8) & 0xff);
03279 *(dp + 5) = (png_byte)(v & 0xff);
03280 }
03281 else if (a == 0)
03282 {
03283
03284 *dp = (png_byte)((background->red >> 8) & 0xff);
03285 *(dp + 1) = (png_byte)(background->red & 0xff);
03286 *(dp + 2) = (png_byte)((background->green >> 8) & 0xff);
03287 *(dp + 3) = (png_byte)(background->green & 0xff);
03288 *(dp + 4) = (png_byte)((background->blue >> 8) & 0xff);
03289 *(dp + 5) = (png_byte)(background->blue & 0xff);
03290 }
03291 else
03292 {
03293 png_uint_16 v, w, x;
03294
03295 v = gamma_16_to_1[*(sp + 1) >> gamma_shift][*sp];
03296 png_composite_16(w, v, a, background_1->red);
03297 x = gamma_16_from_1[((w&0xff) >> gamma_shift)][w >> 8];
03298 *dp = (png_byte)((x >> 8) & 0xff);
03299 *(dp + 1) = (png_byte)(x & 0xff);
03300 v = gamma_16_to_1[*(sp + 3) >> gamma_shift][*(sp + 2)];
03301 png_composite_16(w, v, a, background_1->green);
03302 x = gamma_16_from_1[((w&0xff) >> gamma_shift)][w >> 8];
03303 *(dp + 2) = (png_byte)((x >> 8) & 0xff);
03304 *(dp + 3) = (png_byte)(x & 0xff);
03305 v = gamma_16_to_1[*(sp + 5) >> gamma_shift][*(sp + 4)];
03306 png_composite_16(w, v, a, background_1->blue);
03307 x = gamma_16_from_1[(w & 0xff) >> gamma_shift][w >> 8];
03308 *(dp + 4) = (png_byte)((x >> 8) & 0xff);
03309 *(dp + 5) = (png_byte)(x & 0xff);
03310 }
03311 }
03312 }
03313 else
03314 #endif
03315 {
03316 sp = row;
03317 dp = row;
03318 for (i = 0; i < row_width; i++, sp += 8, dp += 6)
03319 {
03320 png_uint_16 a = (png_uint_16)(((png_uint_16)(*(sp + 6))
03321 << 8) + (png_uint_16)(*(sp + 7)));
03322 if (a == (png_uint_16)0xffff)
03323 {
03324 png_memcpy(dp, sp, 6);
03325 }
03326 else if (a == 0)
03327 {
03328 *dp = (png_byte)((background->red >> 8) & 0xff);
03329 *(dp + 1) = (png_byte)(background->red & 0xff);
03330 *(dp + 2) = (png_byte)((background->green >> 8) & 0xff);
03331 *(dp + 3) = (png_byte)(background->green & 0xff);
03332 *(dp + 4) = (png_byte)((background->blue >> 8) & 0xff);
03333 *(dp + 5) = (png_byte)(background->blue & 0xff);
03334 }
03335 else
03336 {
03337 png_uint_16 v;
03338
03339 png_uint_16 r = (png_uint_16)(((*sp) << 8) + *(sp + 1));
03340 png_uint_16 g = (png_uint_16)(((*(sp + 2)) << 8)
03341 + *(sp + 3));
03342 png_uint_16 b = (png_uint_16)(((*(sp + 4)) << 8)
03343 + *(sp + 5));
03344
03345 png_composite_16(v, r, a, background->red);
03346 *dp = (png_byte)((v >> 8) & 0xff);
03347 *(dp + 1) = (png_byte)(v & 0xff);
03348 png_composite_16(v, g, a, background->green);
03349 *(dp + 2) = (png_byte)((v >> 8) & 0xff);
03350 *(dp + 3) = (png_byte)(v & 0xff);
03351 png_composite_16(v, b, a, background->blue);
03352 *(dp + 4) = (png_byte)((v >> 8) & 0xff);
03353 *(dp + 5) = (png_byte)(v & 0xff);
03354 }
03355 }
03356 }
03357 }
03358 break;
03359 }
03360 }
03361
03362 if (row_info->color_type & PNG_COLOR_MASK_ALPHA)
03363 {
03364 row_info->color_type &= ~PNG_COLOR_MASK_ALPHA;
03365 row_info->channels--;
03366 row_info->pixel_depth = (png_byte)(row_info->channels *
03367 row_info->bit_depth);
03368 row_info->rowbytes = PNG_ROWBYTES(row_info->pixel_depth,row_width);
03369 }
03370 }
03371 }
03372 #endif
03373
03374 #if defined(PNG_READ_GAMMA_SUPPORTED)
03375
03376
03377
03378
03379
03380
03381 void
03382 png_do_gamma(png_row_infop row_info, png_bytep row,
03383 png_bytep gamma_table, png_uint_16pp gamma_16_table,
03384 int gamma_shift)
03385 {
03386 png_bytep sp;
03387 png_uint_32 i;
03388 png_uint_32 row_width=row_info->width;
03389
03390 png_debug(1, "in png_do_gamma\n");
03391 if (
03392 #if defined(PNG_USELESS_TESTS_SUPPORTED)
03393 row != NULL && row_info != NULL &&
03394 #endif
03395 ((row_info->bit_depth <= 8 && gamma_table != NULL) ||
03396 (row_info->bit_depth == 16 && gamma_16_table != NULL)))
03397 {
03398 switch (row_info->color_type)
03399 {
03400 case PNG_COLOR_TYPE_RGB:
03401 {
03402 if (row_info->bit_depth == 8)
03403 {
03404 sp = row;
03405 for (i = 0; i < row_width; i++)
03406 {
03407 *sp = gamma_table[*sp];
03408 sp++;
03409 *sp = gamma_table[*sp];
03410 sp++;
03411 *sp = gamma_table[*sp];
03412 sp++;
03413 }
03414 }
03415 else
03416 {
03417 sp = row;
03418 for (i = 0; i < row_width; i++)
03419 {
03420 png_uint_16 v;
03421
03422 v = gamma_16_table[*(sp + 1) >> gamma_shift][*sp];
03423 *sp = (png_byte)((v >> 8) & 0xff);
03424 *(sp + 1) = (png_byte)(v & 0xff);
03425 sp += 2;
03426 v = gamma_16_table[*(sp + 1) >> gamma_shift][*sp];
03427 *sp = (png_byte)((v >> 8) & 0xff);
03428 *(sp + 1) = (png_byte)(v & 0xff);
03429 sp += 2;
03430 v = gamma_16_table[*(sp + 1) >> gamma_shift][*sp];
03431 *sp = (png_byte)((v >> 8) & 0xff);
03432 *(sp + 1) = (png_byte)(v & 0xff);
03433 sp += 2;
03434 }
03435 }
03436 break;
03437 }
03438 case PNG_COLOR_TYPE_RGB_ALPHA:
03439 {
03440 if (row_info->bit_depth == 8)
03441 {
03442 sp = row;
03443 for (i = 0; i < row_width; i++)
03444 {
03445 *sp = gamma_table[*sp];
03446 sp++;
03447 *sp = gamma_table[*sp];
03448 sp++;
03449 *sp = gamma_table[*sp];
03450 sp++;
03451 sp++;
03452 }
03453 }
03454 else
03455 {
03456 sp = row;
03457 for (i = 0; i < row_width; i++)
03458 {
03459 png_uint_16 v = gamma_16_table[*(sp + 1) >> gamma_shift][*sp];
03460 *sp = (png_byte)((v >> 8) & 0xff);
03461 *(sp + 1) = (png_byte)(v & 0xff);
03462 sp += 2;
03463 v = gamma_16_table[*(sp + 1) >> gamma_shift][*sp];
03464 *sp = (png_byte)((v >> 8) & 0xff);
03465 *(sp + 1) = (png_byte)(v & 0xff);
03466 sp += 2;
03467 v = gamma_16_table[*(sp + 1) >> gamma_shift][*sp];
03468 *sp = (png_byte)((v >> 8) & 0xff);
03469 *(sp + 1) = (png_byte)(v & 0xff);
03470 sp += 4;
03471 }
03472 }
03473 break;
03474 }
03475 case PNG_COLOR_TYPE_GRAY_ALPHA:
03476 {
03477 if (row_info->bit_depth == 8)
03478 {
03479 sp = row;
03480 for (i = 0; i < row_width; i++)
03481 {
03482 *sp = gamma_table[*sp];
03483 sp += 2;
03484 }
03485 }
03486 else
03487 {
03488 sp = row;
03489 for (i = 0; i < row_width; i++)
03490 {
03491 png_uint_16 v = gamma_16_table[*(sp + 1) >> gamma_shift][*sp];
03492 *sp = (png_byte)((v >> 8) & 0xff);
03493 *(sp + 1) = (png_byte)(v & 0xff);
03494 sp += 4;
03495 }
03496 }
03497 break;
03498 }
03499 case PNG_COLOR_TYPE_GRAY:
03500 {
03501 if (row_info->bit_depth == 2)
03502 {
03503 sp = row;
03504 for (i = 0; i < row_width; i += 4)
03505 {
03506 int a = *sp & 0xc0;
03507 int b = *sp & 0x30;
03508 int c = *sp & 0x0c;
03509 int d = *sp & 0x03;
03510
03511 *sp = (png_byte)(
03512 ((((int)gamma_table[a|(a>>2)|(a>>4)|(a>>6)]) ) & 0xc0)|
03513 ((((int)gamma_table[(b<<2)|b|(b>>2)|(b>>4)])>>2) & 0x30)|
03514 ((((int)gamma_table[(c<<4)|(c<<2)|c|(c>>2)])>>4) & 0x0c)|
03515 ((((int)gamma_table[(d<<6)|(d<<4)|(d<<2)|d])>>6) ));
03516 sp++;
03517 }
03518 }
03519 if (row_info->bit_depth == 4)
03520 {
03521 sp = row;
03522 for (i = 0; i < row_width; i += 2)
03523 {
03524 int msb = *sp & 0xf0;
03525 int lsb = *sp & 0x0f;
03526
03527 *sp = (png_byte)((((int)gamma_table[msb | (msb >> 4)]) & 0xf0)
03528 | (((int)gamma_table[(lsb << 4) | lsb]) >> 4));
03529 sp++;
03530 }
03531 }
03532 else if (row_info->bit_depth == 8)
03533 {
03534 sp = row;
03535 for (i = 0; i < row_width; i++)
03536 {
03537 *sp = gamma_table[*sp];
03538 sp++;
03539 }
03540 }
03541 else if (row_info->bit_depth == 16)
03542 {
03543 sp = row;
03544 for (i = 0; i < row_width; i++)
03545 {
03546 png_uint_16 v = gamma_16_table[*(sp + 1) >> gamma_shift][*sp];
03547 *sp = (png_byte)((v >> 8) & 0xff);
03548 *(sp + 1) = (png_byte)(v & 0xff);
03549 sp += 2;
03550 }
03551 }
03552 break;
03553 }
03554 }
03555 }
03556 }
03557 #endif
03558
03559 #if defined(PNG_READ_EXPAND_SUPPORTED)
03560
03561
03562
03563 void
03564 png_do_expand_palette(png_row_infop row_info, png_bytep row,
03565 png_colorp palette, png_bytep trans, int num_trans)
03566 {
03567 int shift, value;
03568 png_bytep sp, dp;
03569 png_uint_32 i;
03570 png_uint_32 row_width=row_info->width;
03571
03572 png_debug(1, "in png_do_expand_palette\n");
03573 if (
03574 #if defined(PNG_USELESS_TESTS_SUPPORTED)
03575 row != NULL && row_info != NULL &&
03576 #endif
03577 row_info->color_type == PNG_COLOR_TYPE_PALETTE)
03578 {
03579 if (row_info->bit_depth < 8)
03580 {
03581 switch (row_info->bit_depth)
03582 {
03583 case 1:
03584 {
03585 sp = row + (png_size_t)((row_width - 1) >> 3);
03586 dp = row + (png_size_t)row_width - 1;
03587 shift = 7 - (int)((row_width + 7) & 0x07);
03588 for (i = 0; i < row_width; i++)
03589 {
03590 if ((*sp >> shift) & 0x01)
03591 *dp = 1;
03592 else
03593 *dp = 0;
03594 if (shift == 7)
03595 {
03596 shift = 0;
03597 sp--;
03598 }
03599 else
03600 shift++;
03601
03602 dp--;
03603 }
03604 break;
03605 }
03606 case 2:
03607 {
03608 sp = row + (png_size_t)((row_width - 1) >> 2);
03609 dp = row + (png_size_t)row_width - 1;
03610 shift = (int)((3 - ((row_width + 3) & 0x03)) << 1);
03611 for (i = 0; i < row_width; i++)
03612 {
03613 value = (*sp >> shift) & 0x03;
03614 *dp = (png_byte)value;
03615 if (shift == 6)
03616 {
03617 shift = 0;
03618 sp--;
03619 }
03620 else
03621 shift += 2;
03622
03623 dp--;
03624 }
03625 break;
03626 }
03627 case 4:
03628 {
03629 sp = row + (png_size_t)((row_width - 1) >> 1);
03630 dp = row + (png_size_t)row_width - 1;
03631 shift = (int)((row_width & 0x01) << 2);
03632 for (i = 0; i < row_width; i++)
03633 {
03634 value = (*sp >> shift) & 0x0f;
03635 *dp = (png_byte)value;
03636 if (shift == 4)
03637 {
03638 shift = 0;
03639 sp--;
03640 }
03641 else
03642 shift += 4;
03643
03644 dp--;
03645 }
03646 break;
03647 }
03648 }
03649 row_info->bit_depth = 8;
03650 row_info->pixel_depth = 8;
03651 row_info->rowbytes = row_width;
03652 }
03653 switch (row_info->bit_depth)
03654 {
03655 case 8:
03656 {
03657 if (trans != NULL)
03658 {
03659 sp = row + (png_size_t)row_width - 1;
03660 dp = row + (png_size_t)(row_width << 2) - 1;
03661
03662 for (i = 0; i < row_width; i++)
03663 {
03664 if ((int)(*sp) >= num_trans)
03665 *dp-- = 0xff;
03666 else
03667 *dp-- = trans[*sp];
03668 *dp-- = palette[*sp].blue;
03669 *dp-- = palette[*sp].green;
03670 *dp-- = palette[*sp].red;
03671 sp--;
03672 }
03673 row_info->bit_depth = 8;
03674 row_info->pixel_depth = 32;
03675 row_info->rowbytes = row_width * 4;
03676 row_info->color_type = 6;
03677 row_info->channels = 4;
03678 }
03679 else
03680 {
03681 sp = row + (png_size_t)row_width - 1;
03682 dp = row + (png_size_t)(row_width * 3) - 1;
03683
03684 for (i = 0; i < row_width; i++)
03685 {
03686 *dp-- = palette[*sp].blue;
03687 *dp-- = palette[*sp].green;
03688 *dp-- = palette[*sp].red;
03689 sp--;
03690 }
03691 row_info->bit_depth = 8;
03692 row_info->pixel_depth = 24;
03693 row_info->rowbytes = row_width * 3;
03694 row_info->color_type = 2;
03695 row_info->channels = 3;
03696 }
03697 break;
03698 }
03699 }
03700 }
03701 }
03702
03703
03704
03705
03706 void
03707 png_do_expand(png_row_infop row_info, png_bytep row,
03708 png_color_16p trans_value)
03709 {
03710 int shift, value;
03711 png_bytep sp, dp;
03712 png_uint_32 i;
03713 png_uint_32 row_width=row_info->width;
03714
03715 png_debug(1, "in png_do_expand\n");
03716 #if defined(PNG_USELESS_TESTS_SUPPORTED)
03717 if (row != NULL && row_info != NULL)
03718 #endif
03719 {
03720 if (row_info->color_type == PNG_COLOR_TYPE_GRAY)
03721 {
03722 png_uint_16 gray = (png_uint_16)(trans_value ? trans_value->gray : 0);
03723
03724 if (row_info->bit_depth < 8)
03725 {
03726 switch (row_info->bit_depth)
03727 {
03728 case 1:
03729 {
03730 gray = (png_uint_16)((gray&0x01)*0xff);
03731 sp = row + (png_size_t)((row_width - 1) >> 3);
03732 dp = row + (png_size_t)row_width - 1;
03733 shift = 7 - (int)((row_width + 7) & 0x07);
03734 for (i = 0; i < row_width; i++)
03735 {
03736 if ((*sp >> shift) & 0x01)
03737 *dp = 0xff;
03738 else
03739 *dp = 0;
03740 if (shift == 7)
03741 {
03742 shift = 0;
03743 sp--;
03744 }
03745 else
03746 shift++;
03747
03748 dp--;
03749 }
03750 break;
03751 }
03752 case 2:
03753 {
03754 gray = (png_uint_16)((gray&0x03)*0x55);
03755 sp = row + (png_size_t)((row_width - 1) >> 2);
03756 dp = row + (png_size_t)row_width - 1;
03757 shift = (int)((3 - ((row_width + 3) & 0x03)) << 1);
03758 for (i = 0; i < row_width; i++)
03759 {
03760 value = (*sp >> shift) & 0x03;
03761 *dp = (png_byte)(value | (value << 2) | (value << 4) |
03762 (value << 6));
03763 if (shift == 6)
03764 {
03765 shift = 0;
03766 sp--;
03767 }
03768 else
03769 shift += 2;
03770
03771 dp--;
03772 }
03773 break;
03774 }
03775 case 4:
03776 {
03777 gray = (png_uint_16)((gray&0x0f)*0x11);
03778 sp = row + (png_size_t)((row_width - 1) >> 1);
03779 dp = row + (png_size_t)row_width - 1;
03780 shift = (int)((1 - ((row_width + 1) & 0x01)) << 2);
03781 for (i = 0; i < row_width; i++)
03782 {
03783 value = (*sp >> shift) & 0x0f;
03784 *dp = (png_byte)(value | (value << 4));
03785 if (shift == 4)
03786 {
03787 shift = 0;
03788 sp--;
03789 }
03790 else
03791 shift = 4;
03792
03793 dp--;
03794 }
03795 break;
03796 }
03797 }
03798 row_info->bit_depth = 8;
03799 row_info->pixel_depth = 8;
03800 row_info->rowbytes = row_width;
03801 }
03802
03803 if (trans_value != NULL)
03804 {
03805 if (row_info->bit_depth == 8)
03806 {
03807 gray = gray & 0xff;
03808 sp = row + (png_size_t)row_width - 1;
03809 dp = row + (png_size_t)(row_width << 1) - 1;
03810 for (i = 0; i < row_width; i++)
03811 {
03812 if (*sp == gray)
03813 *dp-- = 0;
03814 else
03815 *dp-- = 0xff;
03816 *dp-- = *sp--;
03817 }
03818 }
03819 else if (row_info->bit_depth == 16)
03820 {
03821 png_byte gray_high = (gray >> 8) & 0xff;
03822 png_byte gray_low = gray & 0xff;
03823 sp = row + row_info->rowbytes - 1;
03824 dp = row + (row_info->rowbytes << 1) - 1;
03825 for (i = 0; i < row_width; i++)
03826 {
03827 if (*(sp-1) == gray_high && *(sp) == gray_low)
03828 {
03829 *dp-- = 0;
03830 *dp-- = 0;
03831 }
03832 else
03833 {
03834 *dp-- = 0xff;
03835 *dp-- = 0xff;
03836 }
03837 *dp-- = *sp--;
03838 *dp-- = *sp--;
03839 }
03840 }
03841 row_info->color_type = PNG_COLOR_TYPE_GRAY_ALPHA;
03842 row_info->channels = 2;
03843 row_info->pixel_depth = (png_byte)(row_info->bit_depth << 1);
03844 row_info->rowbytes = PNG_ROWBYTES(row_info->pixel_depth,
03845 row_width);
03846 }
03847 }
03848 else if (row_info->color_type == PNG_COLOR_TYPE_RGB && trans_value)
03849 {
03850 if (row_info->bit_depth == 8)
03851 {
03852 png_byte red = trans_value->red & 0xff;
03853 png_byte green = trans_value->green & 0xff;
03854 png_byte blue = trans_value->blue & 0xff;
03855 sp = row + (png_size_t)row_info->rowbytes - 1;
03856 dp = row + (png_size_t)(row_width << 2) - 1;
03857 for (i = 0; i < row_width; i++)
03858 {
03859 if (*(sp - 2) == red && *(sp - 1) == green && *(sp) == blue)
03860 *dp-- = 0;
03861 else
03862 *dp-- = 0xff;
03863 *dp-- = *sp--;
03864 *dp-- = *sp--;
03865 *dp-- = *sp--;
03866 }
03867 }
03868 else if (row_info->bit_depth == 16)
03869 {
03870 png_byte red_high = (trans_value->red >> 8) & 0xff;
03871 png_byte green_high = (trans_value->green >> 8) & 0xff;
03872 png_byte blue_high = (trans_value->blue >> 8) & 0xff;
03873 png_byte red_low = trans_value->red & 0xff;
03874 png_byte green_low = trans_value->green & 0xff;
03875 png_byte blue_low = trans_value->blue & 0xff;
03876 sp = row + row_info->rowbytes - 1;
03877 dp = row + (png_size_t)(row_width << 3) - 1;
03878 for (i = 0; i < row_width; i++)
03879 {
03880 if (*(sp - 5) == red_high &&
03881 *(sp - 4) == red_low &&
03882 *(sp - 3) == green_high &&
03883 *(sp - 2) == green_low &&
03884 *(sp - 1) == blue_high &&
03885 *(sp ) == blue_low)
03886 {
03887 *dp-- = 0;
03888 *dp-- = 0;
03889 }
03890 else
03891 {
03892 *dp-- = 0xff;
03893 *dp-- = 0xff;
03894 }
03895 *dp-- = *sp--;
03896 *dp-- = *sp--;
03897 *dp-- = *sp--;
03898 *dp-- = *sp--;
03899 *dp-- = *sp--;
03900 *dp-- = *sp--;
03901 }
03902 }
03903 row_info->color_type = PNG_COLOR_TYPE_RGB_ALPHA;
03904 row_info->channels = 4;
03905 row_info->pixel_depth = (png_byte)(row_info->bit_depth << 2);
03906 row_info->rowbytes = PNG_ROWBYTES(row_info->pixel_depth,row_width);
03907 }
03908 }
03909 }
03910 #endif
03911
03912 #if defined(PNG_READ_DITHER_SUPPORTED)
03913 void
03914 png_do_dither(png_row_infop row_info, png_bytep row,
03915 png_bytep palette_lookup, png_bytep dither_lookup)
03916 {
03917 png_bytep sp, dp;
03918 png_uint_32 i;
03919 png_uint_32 row_width=row_info->width;
03920
03921 png_debug(1, "in png_do_dither\n");
03922 #if defined(PNG_USELESS_TESTS_SUPPORTED)
03923 if (row != NULL && row_info != NULL)
03924 #endif
03925 {
03926 if (row_info->color_type == PNG_COLOR_TYPE_RGB &&
03927 palette_lookup && row_info->bit_depth == 8)
03928 {
03929 int r, g, b, p;
03930 sp = row;
03931 dp = row;
03932 for (i = 0; i < row_width; i++)
03933 {
03934 r = *sp++;
03935 g = *sp++;
03936 b = *sp++;
03937
03938
03939
03940
03941
03942
03943
03944
03945 p = (((r >> (8 - PNG_DITHER_RED_BITS)) &
03946 ((1 << PNG_DITHER_RED_BITS) - 1)) <<
03947 (PNG_DITHER_GREEN_BITS + PNG_DITHER_BLUE_BITS)) |
03948 (((g >> (8 - PNG_DITHER_GREEN_BITS)) &
03949 ((1 << PNG_DITHER_GREEN_BITS) - 1)) <<
03950 (PNG_DITHER_BLUE_BITS)) |
03951 ((b >> (8 - PNG_DITHER_BLUE_BITS)) &
03952 ((1 << PNG_DITHER_BLUE_BITS) - 1));
03953
03954 *dp++ = palette_lookup[p];
03955 }
03956 row_info->color_type = PNG_COLOR_TYPE_PALETTE;
03957 row_info->channels = 1;
03958 row_info->pixel_depth = row_info->bit_depth;
03959 row_info->rowbytes = PNG_ROWBYTES(row_info->pixel_depth,row_width);
03960 }
03961 else if (row_info->color_type == PNG_COLOR_TYPE_RGB_ALPHA &&
03962 palette_lookup != NULL && row_info->bit_depth == 8)
03963 {
03964 int r, g, b, p;
03965 sp = row;
03966 dp = row;
03967 for (i = 0; i < row_width; i++)
03968 {
03969 r = *sp++;
03970 g = *sp++;
03971 b = *sp++;
03972 sp++;
03973
03974 p = (((r >> (8 - PNG_DITHER_RED_BITS)) &
03975 ((1 << PNG_DITHER_RED_BITS) - 1)) <<
03976 (PNG_DITHER_GREEN_BITS + PNG_DITHER_BLUE_BITS)) |
03977 (((g >> (8 - PNG_DITHER_GREEN_BITS)) &
03978 ((1 << PNG_DITHER_GREEN_BITS) - 1)) <<
03979 (PNG_DITHER_BLUE_BITS)) |
03980 ((b >> (8 - PNG_DITHER_BLUE_BITS)) &
03981 ((1 << PNG_DITHER_BLUE_BITS) - 1));
03982
03983 *dp++ = palette_lookup[p];
03984 }
03985 row_info->color_type = PNG_COLOR_TYPE_PALETTE;
03986 row_info->channels = 1;
03987 row_info->pixel_depth = row_info->bit_depth;
03988 row_info->rowbytes = PNG_ROWBYTES(row_info->pixel_depth,row_width);
03989 }
03990 else if (row_info->color_type == PNG_COLOR_TYPE_PALETTE &&
03991 dither_lookup && row_info->bit_depth == 8)
03992 {
03993 sp = row;
03994 for (i = 0; i < row_width; i++, sp++)
03995 {
03996 *sp = dither_lookup[*sp];
03997 }
03998 }
03999 }
04000 }
04001 #endif
04002
04003 #ifdef PNG_FLOATING_POINT_SUPPORTED
04004 #if defined(PNG_READ_GAMMA_SUPPORTED)
04005 static PNG_CONST int png_gamma_shift[] =
04006 {0x10, 0x21, 0x42, 0x84, 0x110, 0x248, 0x550, 0xff0, 0x00};
04007
04008
04009
04010
04011
04012
04013 void
04014 png_build_gamma_table(png_structp png_ptr)
04015 {
04016 png_debug(1, "in png_build_gamma_table\n");
04017
04018 if (png_ptr->bit_depth <= 8)
04019 {
04020 int i;
04021 double g;
04022
04023 if (png_ptr->screen_gamma > .000001)
04024 g = 1.0 / (png_ptr->gamma * png_ptr->screen_gamma);
04025 else
04026 g = 1.0;
04027
04028 png_ptr->gamma_table = (png_bytep)png_malloc(png_ptr,
04029 (png_uint_32)256);
04030
04031 for (i = 0; i < 256; i++)
04032 {
04033 png_ptr->gamma_table[i] = (png_byte)(pow((double)i / 255.0,
04034 g) * 255.0 + .5);
04035 }
04036
04037 #if defined(PNG_READ_BACKGROUND_SUPPORTED) || \
04038 defined(PNG_READ_RGB_TO_GRAY_SUPPORTED)
04039 if (png_ptr->transformations & ((PNG_BACKGROUND) | PNG_RGB_TO_GRAY))
04040 {
04041
04042 g = 1.0 / (png_ptr->gamma);
04043
04044 png_ptr->gamma_to_1 = (png_bytep)png_malloc(png_ptr,
04045 (png_uint_32)256);
04046
04047 for (i = 0; i < 256; i++)
04048 {
04049 png_ptr->gamma_to_1[i] = (png_byte)(pow((double)i / 255.0,
04050 g) * 255.0 + .5);
04051 }
04052
04053
04054 png_ptr->gamma_from_1 = (png_bytep)png_malloc(png_ptr,
04055 (png_uint_32)256);
04056
04057 if(png_ptr->screen_gamma > 0.000001)
04058 g = 1.0 / png_ptr->screen_gamma;
04059 else
04060 g = png_ptr->gamma;
04061
04062 for (i = 0; i < 256; i++)
04063 {
04064 png_ptr->gamma_from_1[i] = (png_byte)(pow((double)i / 255.0,
04065 g) * 255.0 + .5);
04066
04067 }
04068 }
04069 #endif
04070 }
04071 else
04072 {
04073 double g;
04074 int i, j, shift, num;
04075 int sig_bit;
04076 png_uint_32 ig;
04077
04078 if (png_ptr->color_type & PNG_COLOR_MASK_COLOR)
04079 {
04080 sig_bit = (int)png_ptr->sig_bit.red;
04081 if ((int)png_ptr->sig_bit.green > sig_bit)
04082 sig_bit = png_ptr->sig_bit.green;
04083 if ((int)png_ptr->sig_bit.blue > sig_bit)
04084 sig_bit = png_ptr->sig_bit.blue;
04085 }
04086 else
04087 {
04088 sig_bit = (int)png_ptr->sig_bit.gray;
04089 }
04090
04091 if (sig_bit > 0)
04092 shift = 16 - sig_bit;
04093 else
04094 shift = 0;
04095
04096 if (png_ptr->transformations & PNG_16_TO_8)
04097 {
04098 if (shift < (16 - PNG_MAX_GAMMA_8))
04099 shift = (16 - PNG_MAX_GAMMA_8);
04100 }
04101
04102 if (shift > 8)
04103 shift = 8;
04104 if (shift < 0)
04105 shift = 0;
04106
04107 png_ptr->gamma_shift = (png_byte)shift;
04108
04109 num = (1 << (8 - shift));
04110
04111 if (png_ptr->screen_gamma > .000001)
04112 g = 1.0 / (png_ptr->gamma * png_ptr->screen_gamma);
04113 else
04114 g = 1.0;
04115
04116 png_ptr->gamma_16_table = (png_uint_16pp)png_malloc(png_ptr,
04117 (png_uint_32)(num * png_sizeof (png_uint_16p)));
04118
04119 if (png_ptr->transformations & (PNG_16_TO_8 | PNG_BACKGROUND))
04120 {
04121 double fin, fout;
04122 png_uint_32 last, max;
04123
04124 for (i = 0; i < num; i++)
04125 {
04126 png_ptr->gamma_16_table[i] = (png_uint_16p)png_malloc(png_ptr,
04127 (png_uint_32)(256 * png_sizeof (png_uint_16)));
04128 }
04129
04130 g = 1.0 / g;
04131 last = 0;
04132 for (i = 0; i < 256; i++)
04133 {
04134 fout = ((double)i + 0.5) / 256.0;
04135 fin = pow(fout, g);
04136 max = (png_uint_32)(fin * (double)((png_uint_32)num << 8));
04137 while (last <= max)
04138 {
04139 png_ptr->gamma_16_table[(int)(last & (0xff >> shift))]
04140 [(int)(last >> (8 - shift))] = (png_uint_16)(
04141 (png_uint_16)i | ((png_uint_16)i << 8));
04142 last++;
04143 }
04144 }
04145 while (last < ((png_uint_32)num << 8))
04146 {
04147 png_ptr->gamma_16_table[(int)(last & (0xff >> shift))]
04148 [(int)(last >> (8 - shift))] = (png_uint_16)65535L;
04149 last++;
04150 }
04151 }
04152 else
04153 {
04154 for (i = 0; i < num; i++)
04155 {
04156 png_ptr->gamma_16_table[i] = (png_uint_16p)png_malloc(png_ptr,
04157 (png_uint_32)(256 * png_sizeof (png_uint_16)));
04158
04159 ig = (((png_uint_32)i * (png_uint_32)png_gamma_shift[shift]) >> 4);
04160 for (j = 0; j < 256; j++)
04161 {
04162 png_ptr->gamma_16_table[i][j] =
04163 (png_uint_16)(pow((double)(ig + ((png_uint_32)j << 8)) /
04164 65535.0, g) * 65535.0 + .5);
04165 }
04166 }
04167 }
04168
04169 #if defined(PNG_READ_BACKGROUND_SUPPORTED) || \
04170 defined(PNG_READ_RGB_TO_GRAY_SUPPORTED)
04171 if (png_ptr->transformations & (PNG_BACKGROUND | PNG_RGB_TO_GRAY))
04172 {
04173
04174 g = 1.0 / (png_ptr->gamma);
04175
04176 png_ptr->gamma_16_to_1 = (png_uint_16pp)png_malloc(png_ptr,
04177 (png_uint_32)(num * png_sizeof (png_uint_16p )));
04178
04179 for (i = 0; i < num; i++)
04180 {
04181 png_ptr->gamma_16_to_1[i] = (png_uint_16p)png_malloc(png_ptr,
04182 (png_uint_32)(256 * png_sizeof (png_uint_16)));
04183
04184 ig = (((png_uint_32)i *
04185 (png_uint_32)png_gamma_shift[shift]) >> 4);
04186 for (j = 0; j < 256; j++)
04187 {
04188 png_ptr->gamma_16_to_1[i][j] =
04189 (png_uint_16)(pow((double)(ig + ((png_uint_32)j << 8)) /
04190 65535.0, g) * 65535.0 + .5);
04191 }
04192 }
04193
04194 if(png_ptr->screen_gamma > 0.000001)
04195 g = 1.0 / png_ptr->screen_gamma;
04196 else
04197 g = png_ptr->gamma;
04198
04199 png_ptr->gamma_16_from_1 = (png_uint_16pp)png_malloc(png_ptr,
04200 (png_uint_32)(num * png_sizeof (png_uint_16p)));
04201
04202 for (i = 0; i < num; i++)
04203 {
04204 png_ptr->gamma_16_from_1[i] = (png_uint_16p)png_malloc(png_ptr,
04205 (png_uint_32)(256 * png_sizeof (png_uint_16)));
04206
04207 ig = (((png_uint_32)i *
04208 (png_uint_32)png_gamma_shift[shift]) >> 4);
04209 for (j = 0; j < 256; j++)
04210 {
04211 png_ptr->gamma_16_from_1[i][j] =
04212 (png_uint_16)(pow((double)(ig + ((png_uint_32)j << 8)) /
04213 65535.0, g) * 65535.0 + .5);
04214 }
04215 }
04216 }
04217 #endif
04218 }
04219 }
04220 #endif
04221
04222 #endif
04223
04224 #if defined(PNG_MNG_FEATURES_SUPPORTED)
04225
04226 void
04227 png_do_read_intrapixel(png_row_infop row_info, png_bytep row)
04228 {
04229 png_debug(1, "in png_do_read_intrapixel\n");
04230 if (
04231 #if defined(PNG_USELESS_TESTS_SUPPORTED)
04232 row != NULL && row_info != NULL &&
04233 #endif
04234 (row_info->color_type & PNG_COLOR_MASK_COLOR))
04235 {
04236 int bytes_per_pixel;
04237 png_uint_32 row_width = row_info->width;
04238 if (row_info->bit_depth == 8)
04239 {
04240 png_bytep rp;
04241 png_uint_32 i;
04242
04243 if (row_info->color_type == PNG_COLOR_TYPE_RGB)
04244 bytes_per_pixel = 3;
04245 else if (row_info->color_type == PNG_COLOR_TYPE_RGB_ALPHA)
04246 bytes_per_pixel = 4;
04247 else
04248 return;
04249
04250 for (i = 0, rp = row; i < row_width; i++, rp += bytes_per_pixel)
04251 {
04252 *(rp) = (png_byte)((256 + *rp + *(rp+1))&0xff);
04253 *(rp+2) = (png_byte)((256 + *(rp+2) + *(rp+1))&0xff);
04254 }
04255 }
04256 else if (row_info->bit_depth == 16)
04257 {
04258 png_bytep rp;
04259 png_uint_32 i;
04260
04261 if (row_info->color_type == PNG_COLOR_TYPE_RGB)
04262 bytes_per_pixel = 6;
04263 else if (row_info->color_type == PNG_COLOR_TYPE_RGB_ALPHA)
04264 bytes_per_pixel = 8;
04265 else
04266 return;
04267
04268 for (i = 0, rp = row; i < row_width; i++, rp += bytes_per_pixel)
04269 {
04270 png_uint_32 s0 = (*(rp ) << 8) | *(rp+1);
04271 png_uint_32 s1 = (*(rp+2) << 8) | *(rp+3);
04272 png_uint_32 s2 = (*(rp+4) << 8) | *(rp+5);
04273 png_uint_32 red = (png_uint_32)((s0+s1+65536L) & 0xffffL);
04274 png_uint_32 blue = (png_uint_32)((s2+s1+65536L) & 0xffffL);
04275 *(rp ) = (png_byte)((red >> 8) & 0xff);
04276 *(rp+1) = (png_byte)(red & 0xff);
04277 *(rp+4) = (png_byte)((blue >> 8) & 0xff);
04278 *(rp+5) = (png_byte)(blue & 0xff);
04279 }
04280 }
04281 }
04282 }
04283 #endif
04284 #endif