diff --git a/rtengine/dcraw.cc b/rtengine/dcraw.cc index 07dad00a8..eebd516c6 100644 --- a/rtengine/dcraw.cc +++ b/rtengine/dcraw.cc @@ -5587,10 +5587,10 @@ void CLASS parse_kodak_ifd (int base) int CLASS parse_tiff_ifd (int base) { unsigned entries, tag, type, len, plen=16, save; - int ifd, use_cm=0, cfa, i, j, c, ima_len=0; + int ifd, use_cm=0, cfa, i, j, c, ima_len=0,cm_D65=1; char software[64], *cbuf, *cp; uchar cfa_pat[16], cfa_pc[] = { 0,1,2,3 }, tab[256]; - double cc[4][4], cm[4][3], cam_xyz[4][3], num; + double cc[2][4][4], cm[2][4][3], cam_xyz[4][3], num; double ab[]={ 1,1,1,1 }, asn[] = { 0,0,0,0 }, xyz[] = { 1,1,1 }; unsigned sony_curve[] = { 0,0,0,0,0,4095 }; unsigned *buf, sony_offset=0, sony_length=0, sony_key=0; @@ -5602,7 +5602,10 @@ int CLASS parse_tiff_ifd (int base) ifd = tiff_nifds++; for (j=0; j < 4; j++) for (i=0; i < 4; i++) - cc[j][i] = i == j; + { + cc[0][j][i] = i == j; + cc[1][j][i] = i == j; + } entries = get2(); if (entries > 512) return 1; while (entries--) { @@ -6014,13 +6017,13 @@ guess_cfa_pc: case 50721: /* ColorMatrix1 */ case 50722: /* ColorMatrix2 */ FORCC for (j=0; j < 3; j++) - cm[c][j] = getreal(type); + cm[tag-50721][c][j] = getreal(type); use_cm = 1; break; case 50723: /* CameraCalibration1 */ case 50724: /* CameraCalibration2 */ for (i=0; i < colors; i++) - FORCC cc[i][c] = getreal(type); + FORCC cc[tag-50723][i][c] = getreal(type); break; case 50727: /* AnalogBalance */ FORCC ab[c] = getreal(type); @@ -6043,6 +6046,11 @@ guess_cfa_pc: case 50752: read_shorts (cr2_slice, 3); break; + case 50778: + case 50779: + if( get2() == 21 ) + cm_D65 = (tag-50778); + break; case 50829: /* ActiveArea */ top_margin = getint(type); left_margin = getint(type); @@ -6088,11 +6096,11 @@ guess_cfa_pc: free (buf); } for (i=0; i < colors; i++) - FORCC cc[i][c] *= ab[i]; + FORCC cc[cm_D65][i][c] *= ab[i]; if (use_cm) { FORCC for (i=0; i < 3; i++) for (cam_xyz[c][i]=j=0; j < colors; j++) - cam_xyz[c][i] += cc[c][j] * cm[j][i] * xyz[i]; + cam_xyz[c][i] += cc[cm_D65][c][j] * cm[cm_D65][j][i] * xyz[i]; cam_xyz_coeff (cmatrix, cam_xyz); } if (asn[0]) { @@ -6100,7 +6108,7 @@ guess_cfa_pc: FORCC cam_mul[c] = 1 / asn[c]; } if (!use_cm) - FORCC pre_mul[c] /= cc[c][c]; + FORCC pre_mul[c] /= cc[cm_D65][c][c]; return 0; } @@ -7932,6 +7940,11 @@ void CLASS adobe_coeff (const char *make, const char *model) } if (white_level > -1) { maximum = (ushort)white_level; + if(tiff_bps > 0) { + unsigned compare = ((uint64_t)1 << tiff_bps) - 1; // use uint64_t to avoid overflow if tiff_bps == 32 + while(maximum > compare) + maximum >>= 1; + } } if (trans[0]) { for (j=0; j < 12; j++) { @@ -9242,9 +9255,9 @@ dng_skip: if (raw_width < width ) raw_width = width; } if (!tiff_bps) tiff_bps = 12; - if (!maximum) maximum = (1 << tiff_bps) - 1; + if (!maximum) maximum = ((uint64_t)1 << tiff_bps) - 1; // use uint64_t to avoid overflow if tiff_bps == 32 if (!load_raw || height < 22 || width < 22 || - tiff_bps > 16 || tiff_samples > 6 || colors > 4) + tiff_samples > 6 || colors > 4) is_raw = 0; #ifdef NO_JASPER if (load_raw == &CLASS redcine_load_raw) { diff --git a/rtengine/dcraw.patch b/rtengine/dcraw.patch index c60dfed73..6dbd193fc 100755 --- a/rtengine/dcraw.patch +++ b/rtengine/dcraw.patch @@ -1,5 +1,5 @@ ---- dcraw.c 2015-05-12 14:05:10 +0000 -+++ dcraw.cc 2015-05-12 13:59:13 +0000 +--- dcraw.c 2015-05-14 22:11:59 +0000 ++++ dcraw.cc 2015-05-15 11:53:23 +0000 @@ -1,3 +1,15 @@ +/*RT*/#include +/*RT*/#include @@ -681,7 +681,8 @@ - int code[16][16][32], size=16, *ip, sum[4]; - int f, c, i, x, y, row, col, shift, color; - ushort *pix; -- ++/* RT: delete interpolation functions */ + - if (verbose) fprintf (stderr,_("Bilinear interpolation...\n")); - if (filters == 9) size = 6; - border_interpolate(1); @@ -864,8 +865,7 @@ - int dir[5] = { 1, width, -1, -width, 1 }; - int row, col, diff[2], guess[2], c, d, i; - ushort (*pix)[4]; -+/* RT: delete interpolation functions */ - +- - border_interpolate(3); - if (verbose) fprintf (stderr,_("PPG interpolation...\n")); - @@ -931,7 +931,7 @@ - char (*homo)[TS][TS], *buffer; - - if (verbose) fprintf (stderr,_("AHD interpolation...\n")); -- + - cielab (0,0); - border_interpolate(5); - buffer = (char *) malloc (26*TS*TS); @@ -942,7 +942,7 @@ - - for (top=2; top < height-5; top += TS-6) - for (left=2; left < width-5; left += TS-6) { - +- -/* Interpolate green horizontally and vertically: */ - for (row=top; row < top+TS && row < height-2; row++) { - col = left + (FC(row,left) & 1); @@ -1053,7 +1053,7 @@ if (tag == 0x1d) while ((c = fgetc(ifp)) && c != EOF) serial = serial*10 + (isdigit(c) ? c - '0' : c % 10); -@@ -5613,8 +5581,8 @@ +@@ -5613,28 +5581,31 @@ } } @@ -1064,7 +1064,14 @@ int CLASS parse_tiff_ifd (int base) { -@@ -5627,7 +5595,7 @@ + unsigned entries, tag, type, len, plen=16, save; +- int ifd, use_cm=0, cfa, i, j, c, ima_len=0; ++ int ifd, use_cm=0, cfa, i, j, c, ima_len=0,cm_D65=1; + char software[64], *cbuf, *cp; + uchar cfa_pat[16], cfa_pc[] = { 0,1,2,3 }, tab[256]; +- double cc[4][4], cm[4][3], cam_xyz[4][3], num; ++ double cc[2][4][4], cm[2][4][3], cam_xyz[4][3], num; + double ab[]={ 1,1,1,1 }, asn[] = { 0,0,0,0 }, xyz[] = { 1,1,1 }; unsigned sony_curve[] = { 0,0,0,0,0,4095 }; unsigned *buf, sony_offset=0, sony_length=0, sony_key=0; struct jhead jh; @@ -1073,7 +1080,18 @@ if (tiff_nifds >= sizeof tiff_ifd / sizeof tiff_ifd[0]) return 1; -@@ -5702,7 +5670,8 @@ + ifd = tiff_nifds++; + for (j=0; j < 4; j++) + for (i=0; i < 4; i++) +- cc[j][i] = i == j; ++ { ++ cc[0][j][i] = i == j; ++ cc[1][j][i] = i == j; ++ } + entries = get2(); + if (entries > 512) return 1; + while (entries--) { +@@ -5702,7 +5673,8 @@ fgets (make, 64, ifp); break; case 272: /* Model */ @@ -1083,7 +1101,7 @@ break; case 280: /* Panasonic RW2 offset */ if (type != 4) break; -@@ -5762,6 +5731,9 @@ +@@ -5762,6 +5734,9 @@ case 315: /* Artist */ fread (artist, 64, 1, ifp); break; @@ -1093,7 +1111,7 @@ case 322: /* TileWidth */ tiff_ifd[ifd].tile_width = getint(type); break; -@@ -5777,6 +5749,9 @@ +@@ -5777,6 +5752,9 @@ is_raw = 5; } break; @@ -1103,7 +1121,7 @@ case 330: /* SubIFDs */ if (!strcmp(model,"DSLR-A100") && tiff_ifd[ifd].width == 3872) { load_raw = &CLASS sony_arw_load_raw; -@@ -5790,6 +5765,9 @@ +@@ -5790,6 +5768,9 @@ fseek (ifp, i+4, SEEK_SET); } break; @@ -1113,7 +1131,7 @@ case 400: strcpy (make, "Sarnoff"); maximum = 0xfff; -@@ -5971,6 +5949,9 @@ +@@ -5971,6 +5952,9 @@ if (!make[0]) strcpy (make, "DNG"); is_raw = 1; break; @@ -1123,7 +1141,7 @@ case 50710: /* CFAPlaneColor */ if (filters == 9) break; if (len > 4) len = 4; -@@ -6002,12 +5983,21 @@ +@@ -6002,12 +5986,21 @@ case 61450: cblack[4] = cblack[5] = MIN(sqrt(len),64); case 50714: /* BlackLevel */ @@ -1151,7 +1169,35 @@ case 50715: /* BlackLevelDeltaH */ case 50716: /* BlackLevelDeltaV */ for (num=i=0; i < len; i++) -@@ -6085,12 +6075,15 @@ +@@ -6024,13 +6017,13 @@ + case 50721: /* ColorMatrix1 */ + case 50722: /* ColorMatrix2 */ + FORCC for (j=0; j < 3; j++) +- cm[c][j] = getreal(type); ++ cm[tag-50721][c][j] = getreal(type); + use_cm = 1; + break; + case 50723: /* CameraCalibration1 */ + case 50724: /* CameraCalibration2 */ + for (i=0; i < colors; i++) +- FORCC cc[i][c] = getreal(type); ++ FORCC cc[tag-50723][i][c] = getreal(type); + break; + case 50727: /* AnalogBalance */ + FORCC ab[c] = getreal(type); +@@ -6053,6 +6046,11 @@ + case 50752: + read_shorts (cr2_slice, 3); + break; ++ case 50778: ++ case 50779: ++ if( get2() == 21 ) ++ cm_D65 = (tag-50778); ++ break; + case 50829: /* ActiveArea */ + top_margin = getint(type); + left_margin = getint(type); +@@ -6085,21 +6083,24 @@ fread (buf, sony_length, 1, ifp); sony_decrypt (buf, sony_length/4, 1, sony_key); sfp = ifp; @@ -1173,7 +1219,26 @@ ifp = sfp; free (buf); } -@@ -6114,6 +6107,7 @@ + for (i=0; i < colors; i++) +- FORCC cc[i][c] *= ab[i]; ++ FORCC cc[cm_D65][i][c] *= ab[i]; + if (use_cm) { + FORCC for (i=0; i < 3; i++) + for (cam_xyz[c][i]=j=0; j < colors; j++) +- cam_xyz[c][i] += cc[c][j] * cm[j][i] * xyz[i]; ++ cam_xyz[c][i] += cc[cm_D65][c][j] * cm[cm_D65][j][i] * xyz[i]; + cam_xyz_coeff (cmatrix, cam_xyz); + } + if (asn[0]) { +@@ -6107,13 +6108,14 @@ + FORCC cam_mul[c] = 1 / asn[c]; + } + if (!use_cm) +- FORCC pre_mul[c] /= cc[c][c]; ++ FORCC pre_mul[c] /= cc[cm_D65][c][c]; + return 0; + } + int CLASS parse_tiff (int base) { int doff; @@ -1181,7 +1246,7 @@ fseek (ifp, base, SEEK_SET); order = get2(); -@@ -6191,7 +6185,7 @@ +@@ -6191,7 +6193,7 @@ case 8: load_raw = &CLASS eight_bit_load_raw; break; case 12: if (tiff_ifd[raw].phint == 2) load_flags = 6; @@ -1190,7 +1255,7 @@ case 14: load_flags = 0; case 16: load_raw = &CLASS unpacked_load_raw; if (!strncmp(make,"OLYMPUS",7) && -@@ -6230,6 +6224,7 @@ +@@ -6230,6 +6232,7 @@ case 32803: load_raw = &CLASS kodak_65000_load_raw; } case 32867: case 34892: break; @@ -1198,7 +1263,7 @@ default: is_raw = 0; } if (!dng_version) -@@ -6315,7 +6310,7 @@ +@@ -6315,7 +6318,7 @@ { const char *file, *ext; char *jname, *jfile, *jext; @@ -1207,7 +1272,7 @@ ext = strrchr (ifname, '.'); file = strrchr (ifname, '/'); -@@ -6337,13 +6332,14 @@ +@@ -6337,13 +6340,14 @@ } else while (isdigit(*--jext)) { if (*jext != '9') { @@ -1224,7 +1289,7 @@ if (verbose) fprintf (stderr,_("Reading metadata from %s ...\n"), jname); parse_tiff (12); -@@ -6688,7 +6684,11 @@ +@@ -6688,7 +6692,11 @@ order = get2(); hlen = get4(); if (get4() == 0x48454150) /* "HEAP" */ @@ -1236,7 +1301,7 @@ if (parse_tiff (save+6)) apply_tiff(); fseek (ifp, save+len, SEEK_SET); } -@@ -6960,7 +6960,8 @@ +@@ -6960,7 +6968,8 @@ { static const struct { const char *prefix; @@ -1246,7 +1311,7 @@ } table[] = { { "AgfaPhoto DC-833m", 0, 0, /* DJC */ { 11438,-3762,-1115,-2409,9914,2497,-1227,2295,5300 } }, -@@ -7919,6 +7920,27 @@ +@@ -7919,6 +7928,32 @@ } break; } @@ -1262,6 +1327,11 @@ + } + if (white_level > -1) { + maximum = (ushort)white_level; ++ if(tiff_bps > 0) { ++ unsigned compare = ((uint64_t)1 << tiff_bps) - 1; // use uint64_t to avoid overflow if tiff_bps == 32 ++ while(maximum > compare) ++ maximum >>= 1; ++ } + } + if (trans[0]) { + for (j=0; j < 12; j++) { @@ -1274,7 +1344,7 @@ } void CLASS simple_coeff (int index) -@@ -8229,7 +8251,7 @@ +@@ -8229,7 +8264,7 @@ tiff_flip = flip = filters = UINT_MAX; /* unknown */ raw_height = raw_width = fuji_width = fuji_layout = cr2_slice[0] = 0; maximum = height = width = top_margin = left_margin = 0; @@ -1283,7 +1353,7 @@ iso_speed = shutter = aperture = focal_len = unique_id = 0; tiff_nifds = 0; memset (tiff_ifd, 0, sizeof tiff_ifd); -@@ -8261,13 +8283,20 @@ +@@ -8261,13 +8296,20 @@ fread (head, 1, 32, ifp); fseek (ifp, 0, SEEK_END); flen = fsize = ftell(ifp); @@ -1306,7 +1376,7 @@ parse_ciff (hlen, flen-hlen, 0); load_raw = &CLASS canon_load_raw; } else if (parse_tiff(0)) apply_tiff(); -@@ -8313,6 +8342,7 @@ +@@ -8313,6 +8355,7 @@ fseek (ifp, 100+28*(shot_select > 0), SEEK_SET); parse_tiff (data_offset = get4()); parse_tiff (thumb_offset+12); @@ -1314,7 +1384,7 @@ apply_tiff(); } else if (!memcmp (head,"RIFF",4)) { fseek (ifp, 0, SEEK_SET); -@@ -8426,9 +8456,10 @@ +@@ -8426,9 +8469,10 @@ if (make[0] == 0) parse_smal (0, flen); if (make[0] == 0) { parse_jpeg(0); @@ -1328,7 +1398,7 @@ strcpy (make, "OmniVision"); data_offset = ftell(ifp) + 0x8000-32; width = raw_width; -@@ -8437,6 +8468,7 @@ +@@ -8437,6 +8481,7 @@ filters = 0x16161616; } else is_raw = 0; } @@ -1336,7 +1406,7 @@ for (i=0; i < sizeof corp / sizeof *corp; i++) if (strcasestr (make, corp[i])) /* Simplify company names */ -@@ -8468,7 +8500,7 @@ +@@ -8468,7 +8513,7 @@ if (height == 3136 && width == 4864) /* Pentax K20D and Samsung GX20 */ { height = 3124; width = 4688; filters = 0x16161616; } if (width == 4352 && (!strcmp(model,"K-r") || !strcmp(model,"K-x"))) @@ -1345,7 +1415,7 @@ if (width >= 4960 && !strncmp(model,"K-5",3)) { left_margin = 10; width = 4950; filters = 0x16161616; } if (width == 4736 && !strcmp(model,"K-7")) -@@ -8487,6 +8519,7 @@ +@@ -8487,6 +8532,7 @@ switch (tiff_compress) { case 1: load_raw = &CLASS packed_dng_load_raw; break; case 7: load_raw = &CLASS lossless_dng_load_raw; break; @@ -1353,7 +1423,7 @@ case 34892: load_raw = &CLASS lossy_dng_load_raw; break; default: load_raw = 0; } -@@ -8541,6 +8574,7 @@ +@@ -8541,6 +8587,7 @@ if (height > width) pixel_aspect = 2; filters = 0; simple_coeff(0); @@ -1361,7 +1431,7 @@ } else if (!strcmp(make,"Canon") && tiff_bps == 15) { switch (width) { case 3344: width -= 66; -@@ -8846,24 +8880,53 @@ +@@ -8846,24 +8893,53 @@ if (load_raw == &CLASS lossless_jpeg_load_raw) load_raw = &CLASS hasselblad_load_raw; if (raw_width == 7262) { @@ -1420,7 +1490,7 @@ } else if (raw_width == 4090) { strcpy (model, "V96C"); height -= (top_margin = 6); -@@ -8921,6 +8984,7 @@ +@@ -8921,6 +8997,7 @@ filters = 0x16161616; } } else if (!strcmp(make,"Leica") || !strcmp(make,"Panasonic")) { @@ -1428,7 +1498,7 @@ if ((flen - data_offset) / (raw_width*8/7) == raw_height) load_raw = &CLASS panasonic_load_raw; if (!load_raw) { -@@ -8938,6 +9002,7 @@ +@@ -8938,6 +9015,7 @@ } filters = 0x01010101 * (uchar) "\x94\x61\x49\x16" [((filters-1) ^ (left_margin & 1) ^ (top_margin << 1)) & 3]; @@ -1436,7 +1506,7 @@ } else if (!strcmp(model,"C770UZ")) { height = 1718; width = 2304; -@@ -9155,6 +9220,14 @@ +@@ -9155,6 +9233,14 @@ memcpy (rgb_cam, cmatrix, sizeof cmatrix); raw_color = 0; } @@ -1451,7 +1521,19 @@ if (raw_color) adobe_coeff (make, model); if (load_raw == &CLASS kodak_radc_load_raw) if (raw_color) adobe_coeff ("Apple","Quicktake"); -@@ -9250,194 +9323,249 @@ +@@ -9169,9 +9255,9 @@ + if (raw_width < width ) raw_width = width; + } + if (!tiff_bps) tiff_bps = 12; +- if (!maximum) maximum = (1 << tiff_bps) - 1; ++ if (!maximum) maximum = ((uint64_t)1 << tiff_bps) - 1; // use uint64_t to avoid overflow if tiff_bps == 32 + if (!load_raw || height < 22 || width < 22 || +- tiff_bps > 16 || tiff_samples > 6 || colors > 4) ++ tiff_samples > 6 || colors > 4) + is_raw = 0; + #ifdef NO_JASPER + if (load_raw == &CLASS redcine_load_raw) { +@@ -9250,194 +9336,249 @@ } #endif @@ -1880,7 +1962,7 @@ struct tiff_tag { ushort tag, type; -@@ -9461,590 +9589,11 @@ +@@ -9461,590 +9602,11 @@ char desc[512], make[64], model[64], soft[32], date[20], artist[64]; }; diff --git a/rtengine/rawimage.cc b/rtengine/rawimage.cc index a91e20edb..f206a25d2 100755 --- a/rtengine/rawimage.cc +++ b/rtengine/rawimage.cc @@ -449,14 +449,19 @@ int RawImage::loadRaw (bool loadData, bool closeFile, ProgressListener *plistene bool black_from_cc = false; if (cc) { for (int i = 0; i < 4; i++) { - if (RT_blacklevel_from_constant) { - black_c4[i] = cblack[i] + cc->get_BlackLevel(i, iso_speed); - } - // load 4 channel white level here, will be used if available - if (RT_whitelevel_from_constant) { - maximum_c4[i] = cc->get_WhiteLevel(i, iso_speed, aperture); - } - } + if (RT_blacklevel_from_constant) { + black_c4[i] = cblack[i] + cc->get_BlackLevel(i, iso_speed); + } + // load 4 channel white level here, will be used if available + if (RT_whitelevel_from_constant) { + maximum_c4[i] = cc->get_WhiteLevel(i, iso_speed, aperture); + if(tiff_bps > 0 && !isFoveon()) { + unsigned compare = ((uint64_t)1 << tiff_bps) - 1; // use uint64_t to avoid overflow if tiff_bps == 32 + while(maximum_c4[i] > compare) + maximum_c4[i] >>= 1; + } + } + } } if (black_c4[0] == -1) { if(isXtrans())