2 dcraw.c -- Dave Coffin's raw photo decoder
3 Copyright 1997-2012 by Dave Coffin, dcoffin a cybercom o net
5 This is a command-line ANSI C program to convert raw photos from
6 any digital camera on any computer running any operating system.
8 No license is required to download and use dcraw.c. However,
9 to lawfully redistribute dcraw, you must either (a) offer, at
10 no extra charge, full source code* for all executable files
11 containing RESTRICTED functions, (b) distribute this code under
12 the GPL Version 2 or later, (c) remove all RESTRICTED functions,
13 re-implement them, or copy them from an earlier, unrestricted
14 Revision of dcraw.c, or (d) purchase a license from the author.
16 The functions that process Foveon images have been RESTRICTED
17 since Revision 1.237. All other code remains free for all uses.
19 *If you have not modified dcraw.c in any way, a link to my
20 homepage qualifies as "full source code".
23 $Date: 2012/12/23 19:25:36 $
26 #define DCRAW_VERSION "9.17"
32 #define _USE_MATH_DEFINES
44 #include <sys/types.h>
57 #include <jasper/jasper.h> /* Decode RED camera movies */
60 #include <jpeglib.h> /* Decode compressed Kodak DC120 photos */
61 #endif /* and Adobe Lossy DNGs */
63 #include <lcms.h> /* Support color profiles */
67 #define _(String) gettext(String)
69 #define _(String) (String)
72 #if defined(DJGPP) || defined(__MINGW32__)
76 #define fgetc getc_unlocked
82 #include <sys/utime.h>
84 #pragma comment(lib, "ws2_32.lib")
85 #define snprintf _snprintf
86 #define strcasecmp stricmp
87 #define strncasecmp strnicmp
88 typedef __int64 INT64;
89 typedef unsigned __int64 UINT64;
93 #include <netinet/in.h>
94 typedef long long INT64;
95 typedef unsigned long long UINT64;
99 #error Please compile dcraw.c by itself.
100 #error Do not link it with ljpeg_decode.
104 #define LONG_BIT (8 * sizeof (long))
108 #define uchar unsigned char
111 #define ushort unsigned short
115 All global variables are defined here, and all functions that
116 access them are prefixed with "CLASS". Note that a thread-safe
117 C++ class cannot have non-const static local variables.
121 char dcraw_info[1024];
124 float dcraw_matrix[9];
135 char cdesc[5], desc[512], make[64], model[64], model2[64], artist[64];
136 float flash_used, canon_ev, iso_speed, shutter, aperture, focal_len;
138 unsigned shot_order, kodak_cbpp, filters, exif_cfa, unique_id;
139 off_t strip_offset, data_offset;
140 off_t thumb_offset, meta_offset, profile_offset;
141 unsigned thumb_length, meta_length, profile_length;
142 unsigned thumb_misc, *oprof, fuji_layout, shot_select=0, multi_out=0;
143 unsigned tiff_nifds, tiff_samples, tiff_bps, tiff_compress;
144 unsigned black, cblack[4], maximum, mix_green, raw_color, zero_is_bad;
145 unsigned zero_after_ff, is_raw, dng_version, is_foveon, data_error;
146 unsigned tile_width, tile_length, gpsdata[32], load_flags;
147 ushort raw_height, raw_width, height, width, top_margin, left_margin;
148 ushort shrink, iheight, iwidth, fuji_width, thumb_width, thumb_height;
149 ushort *raw_image, (*image)[4];
150 ushort white[8][8], curve[0x10000], cr2_slice[3], sraw_mul[4];
153 static int mask[8][4], flip, tiff_flip, colors;
156 double pixel_aspect, aber[4]={1,1,1,1}, gamm[6]={ 0.45,4.5,0,0,0,0 };
157 float bright=1, user_mul[4]={0,0,0,0}, threshold=0;
158 int half_size=0, four_color_rgb=0, document_mode=0, highlight=0;
159 int verbose=0, use_auto_wb=0, use_camera_wb=0, use_camera_matrix=-1;
160 int output_color=1, output_bps=8, output_tiff=0, med_passes=0;
161 int no_auto_bright=0;
162 unsigned greybox[4] = { 0, 0, UINT_MAX, UINT_MAX };
163 float cam_mul[4], pre_mul[4], cmatrix[3][4], rgb_cam[3][4];
164 const double xyz_rgb[3][3] = { /* XYZ from RGB */
165 { 0.412453, 0.357580, 0.180423 },
166 { 0.212671, 0.715160, 0.072169 },
167 { 0.019334, 0.119193, 0.950227 } };
168 const float d65_white[3] = { 0.950456, 1, 1.088754 };
169 int histogram[4][0x2000];
170 void (*write_thumb)(), (*write_fun)();
171 void (*load_raw)(), (*thumb_load_raw)();
175 struct decode *branch[2];
177 } first_decode[2048], *second_decode, *free_decode;
180 int width, height, bps, comp, phint, offset, flip, samples, bytes;
181 int tile_width, tile_length;
185 int format, key_off, black, black_off, split_col, tag_21a;
191 #define FORC(cnt) for (c=0; c < cnt; c++)
192 #define FORC3 FORC(3)
193 #define FORC4 FORC(4)
194 #define FORCC FORC(colors)
196 #define SQR(x) ((x)*(x))
197 #define ABS(x) (((int)(x) ^ ((int)(x) >> 31)) - ((int)(x) >> 31))
198 #define MIN(a,b) ((a) < (b) ? (a) : (b))
199 #define MAX(a,b) ((a) > (b) ? (a) : (b))
200 #define LIM(x,min,max) MAX(min,MIN(x,max))
201 #define ULIM(x,y,z) ((y) < (z) ? LIM(x,y,z) : LIM(x,z,y))
202 #define CLIP(x) LIM(x,0,65535)
203 #define SWAP(a,b) { a=a+b; b=a-b; a=a-b; }
206 In order to inline this calculation, I make the risky
207 assumption that all filter patterns can be described
208 by a repeating pattern of eight rows and two columns
210 Do not use the FC or BAYER macros with the Leaf CatchLight,
211 because its pattern is 16x16, not 2x8.
213 Return values are either 0/1/2/3 = G/M/C/Y or 0/1/2/3 = R/G1/B/G2
215 PowerShot 600 PowerShot A50 PowerShot Pro70 Pro90 & G1
216 0xe1e4e1e4: 0x1b4e4b1e: 0x1e4b4e1b: 0xb4b4b4b4:
218 0 1 2 3 4 5 0 1 2 3 4 5 0 1 2 3 4 5 0 1 2 3 4 5
219 0 G M G M G M 0 C Y C Y C Y 0 Y C Y C Y C 0 G M G M G M
220 1 C Y C Y C Y 1 M G M G M G 1 M G M G M G 1 Y C Y C Y C
221 2 M G M G M G 2 Y C Y C Y C 2 C Y C Y C Y
222 3 C Y C Y C Y 3 G M G M G M 3 G M G M G M
223 4 C Y C Y C Y 4 Y C Y C Y C
224 PowerShot A5 5 G M G M G M 5 G M G M G M
225 0x1e4e1e4e: 6 Y C Y C Y C 6 C Y C Y C Y
226 7 M G M G M G 7 M G M G M G
233 All RGB cameras use one of these Bayer grids:
235 0x16161616: 0x61616161: 0x49494949: 0x94949494:
237 0 1 2 3 4 5 0 1 2 3 4 5 0 1 2 3 4 5 0 1 2 3 4 5
238 0 B G B G B G 0 G R G R G R 0 G B G B G B 0 R G R G R G
239 1 G R G R G R 1 B G B G B G 1 R G R G R G 1 G B G B G B
240 2 B G B G B G 2 G R G R G R 2 G B G B G B 2 R G R G R G
241 3 G R G R G R 3 B G B G B G 3 R G R G R G 3 G B G B G B
244 #define RAW(row,col) \
245 raw_image[(row)*raw_width+(col)]
247 #define FC(row,col) \
248 (filters >> ((((row) << 1 & 14) + ((col) & 1)) << 1) & 3)
250 #define BAYER(row,col) \
251 image[((row) >> shrink)*iwidth + ((col) >> shrink)][FC(row,col)]
253 #define BAYER2(row,col) \
254 image[((row) >> shrink)*iwidth + ((col) >> shrink)][fcol(row,col)]
256 int CLASS fcol (int row, int col)
258 static const char filter[16][16] =
259 { { 2,1,1,3,2,3,2,0,3,2,3,0,1,2,1,0 },
260 { 0,3,0,2,0,1,3,1,0,1,1,2,0,3,3,2 },
261 { 2,3,3,2,3,1,1,3,3,1,2,1,2,0,0,3 },
262 { 0,1,0,1,0,2,0,2,2,0,3,0,1,3,2,1 },
263 { 3,1,1,2,0,1,0,2,1,3,1,3,0,1,3,0 },
264 { 2,0,0,3,3,2,3,1,2,0,2,0,3,2,2,1 },
265 { 2,3,3,1,2,1,2,1,2,1,1,2,3,0,0,1 },
266 { 1,0,0,2,3,0,0,3,0,3,0,3,2,1,2,3 },
267 { 2,3,3,1,1,2,1,0,3,2,3,0,2,3,1,3 },
268 { 1,0,2,0,3,0,3,2,0,1,1,2,0,1,0,2 },
269 { 0,1,1,3,3,2,2,1,1,3,3,0,2,1,3,2 },
270 { 2,3,2,0,0,1,3,0,2,0,1,2,3,0,1,0 },
271 { 1,3,1,2,3,2,3,2,0,2,0,1,1,0,3,0 },
272 { 0,2,0,3,1,0,0,1,1,3,3,2,3,2,2,1 },
273 { 2,1,3,2,3,1,2,1,0,3,0,2,0,2,0,2 },
274 { 0,3,1,0,0,2,0,3,2,1,3,1,1,3,1,3 } };
275 static const char filter2[6][6] =
283 if (filters == 1) return filter[(row+top_margin)&15][(col+left_margin)&15];
284 if (filters == 2) return filter2[(row+6) % 6][(col+6) % 6];
289 char *my_memmem (char *haystack, size_t haystacklen,
290 char *needle, size_t needlelen)
293 for (c = haystack; c <= haystack + haystacklen - needlelen; c++)
294 if (!memcmp (c, needle, needlelen))
298 #define memmem my_memmem
301 void CLASS merror (void *ptr, const char *where)
304 fprintf (stderr,_("%s: Out of memory in %s\n"), ifname, where);
305 longjmp (failure, 1);
311 fprintf (stderr, "%s: ", ifname);
313 fprintf (stderr,_("Unexpected end of file\n"));
315 fprintf (stderr,_("Corrupt data near 0x%llx\n"), (INT64) ftello(ifp));
320 ushort CLASS sget2 (uchar *s)
322 if (order == 0x4949) /* "II" means little-endian */
323 return s[0] | s[1] << 8;
324 else /* "MM" means big-endian */
325 return s[0] << 8 | s[1];
330 uchar str[2] = { 0xff,0xff };
331 fread (str, 1, 2, ifp);
335 unsigned CLASS sget4 (uchar *s)
338 return s[0] | s[1] << 8 | s[2] << 16 | s[3] << 24;
340 return s[0] << 24 | s[1] << 16 | s[2] << 8 | s[3];
342 #define sget4(s) sget4((uchar *)s)
344 unsigned CLASS get4()
346 uchar str[4] = { 0xff,0xff,0xff,0xff };
347 fread (str, 1, 4, ifp);
351 unsigned CLASS getint (int type)
353 return type == 3 ? get2() : get4();
356 float CLASS int_to_float (int i)
358 union { int i; float f; } u;
363 double CLASS getreal (int type)
365 union { char c[8]; double d; } u;
369 case 3: return (unsigned short) get2();
370 case 4: return (unsigned int) get4();
371 case 5: u.d = (unsigned int) get4();
372 return u.d / (unsigned int) get4();
373 case 8: return (signed short) get2();
374 case 9: return (signed int) get4();
375 case 10: u.d = (signed int) get4();
376 return u.d / (signed int) get4();
377 case 11: return int_to_float (get4());
379 rev = 7 * ((order == 0x4949) == (ntohs(0x1234) == 0x1234));
380 for (i=0; i < 8; i++)
381 u.c[i ^ rev] = fgetc(ifp);
383 default: return fgetc(ifp);
387 void CLASS read_shorts (ushort *pixel, int count)
389 if (fread (pixel, 2, count, ifp) < count) derror();
390 if ((order == 0x4949) == (ntohs(0x1234) == 0x1234))
391 swab (pixel, pixel, count*2);
394 void CLASS canon_600_fixed_wb (int temp)
396 static const short mul[4][5] = {
397 { 667, 358,397,565,452 },
398 { 731, 390,367,499,517 },
399 { 1119, 396,348,448,537 },
400 { 1399, 485,431,508,688 } };
405 if (*mul[lo] <= temp) break;
406 for (hi=0; hi < 3; hi++)
407 if (*mul[hi] >= temp) break;
409 frac = (float) (temp - *mul[lo]) / (*mul[hi] - *mul[lo]);
410 for (i=1; i < 5; i++)
411 pre_mul[i-1] = 1 / (frac * mul[hi][i] + (1-frac) * mul[lo][i]);
414 /* Return values: 0 = white 1 = near white 2 = not white */
415 int CLASS canon_600_color (int ratio[2], int mar)
417 int clipped=0, target, miss;
421 { ratio[1] = -104; clipped = 1; }
423 { ratio[1] = 12; clipped = 1; }
425 if (ratio[1] < -264 || ratio[1] > 461) return 2;
427 { ratio[1] = -50; clipped = 1; }
429 { ratio[1] = 307; clipped = 1; }
431 target = flash_used || ratio[1] < 197
432 ? -38 - (398 * ratio[1] >> 10)
433 : -123 + (48 * ratio[1] >> 10);
434 if (target - mar <= ratio[0] &&
435 target + 20 >= ratio[0] && !clipped) return 0;
436 miss = target - ratio[0];
437 if (abs(miss) >= mar*4) return 2;
438 if (miss < -20) miss = -20;
439 if (miss > mar) miss = mar;
440 ratio[0] = target - miss;
444 void CLASS canon_600_auto_wb()
446 int mar, row, col, i, j, st, count[] = { 0,0 };
447 int test[8], total[2][8], ratio[2][2], stat[2];
449 memset (&total, 0, sizeof total);
451 if (i < 10) mar = 150;
452 else if (i > 12) mar = 20;
453 else mar = 280 - 20 * i;
454 if (flash_used) mar = 80;
455 for (row=14; row < height-14; row+=4)
456 for (col=10; col < width; col+=2) {
457 for (i=0; i < 8; i++)
458 test[(i & 4) + FC(row+(i >> 1),col+(i & 1))] =
459 BAYER(row+(i >> 1),col+(i & 1));
460 for (i=0; i < 8; i++)
461 if (test[i] < 150 || test[i] > 1500) goto next;
462 for (i=0; i < 4; i++)
463 if (abs(test[i] - test[i+4]) > 50) goto next;
464 for (i=0; i < 2; i++) {
465 for (j=0; j < 4; j+=2)
466 ratio[i][j >> 1] = ((test[i*4+j+1]-test[i*4+j]) << 10) / test[i*4+j];
467 stat[i] = canon_600_color (ratio[i], mar);
469 if ((st = stat[0] | stat[1]) > 1) goto next;
470 for (i=0; i < 2; i++)
472 for (j=0; j < 2; j++)
473 test[i*4+j*2+1] = test[i*4+j*2] * (0x400 + ratio[i][j]) >> 10;
474 for (i=0; i < 8; i++)
475 total[st][i] += test[i];
479 if (count[0] | count[1]) {
480 st = count[0]*200 < count[1];
481 for (i=0; i < 4; i++)
482 pre_mul[i] = 1.0 / (total[st][i] + total[st][i+4]);
486 void CLASS canon_600_coeff()
488 static const short table[6][12] = {
489 { -190,702,-1878,2390, 1861,-1349,905,-393, -432,944,2617,-2105 },
490 { -1203,1715,-1136,1648, 1388,-876,267,245, -1641,2153,3921,-3409 },
491 { -615,1127,-1563,2075, 1437,-925,509,3, -756,1268,2519,-2007 },
492 { -190,702,-1886,2398, 2153,-1641,763,-251, -452,964,3040,-2528 },
493 { -190,702,-1878,2390, 1861,-1349,905,-393, -432,944,2617,-2105 },
494 { -807,1319,-1785,2297, 1388,-876,769,-257, -230,742,2067,-1555 } };
498 mc = pre_mul[1] / pre_mul[2];
499 yc = pre_mul[3] / pre_mul[2];
500 if (mc > 1 && mc <= 1.28 && yc < 0.8789) t=1;
501 if (mc > 1.28 && mc <= 2) {
502 if (yc < 0.8789) t=3;
503 else if (yc <= 2) t=4;
506 for (raw_color = i=0; i < 3; i++)
507 FORCC rgb_cam[i][c] = table[t][i*4 + c] / 1024.0;
510 void CLASS canon_600_load_raw()
512 uchar data[1120], *dp;
516 for (irow=row=0; irow < height; irow++) {
517 if (fread (data, 1, 1120, ifp) < 1120) derror();
518 pix = raw_image + row*raw_width;
519 for (dp=data; dp < data+1120; dp+=10, pix+=8) {
520 pix[0] = (dp[0] << 2) + (dp[1] >> 6 );
521 pix[1] = (dp[2] << 2) + (dp[1] >> 4 & 3);
522 pix[2] = (dp[3] << 2) + (dp[1] >> 2 & 3);
523 pix[3] = (dp[4] << 2) + (dp[1] & 3);
524 pix[4] = (dp[5] << 2) + (dp[9] & 3);
525 pix[5] = (dp[6] << 2) + (dp[9] >> 2 & 3);
526 pix[6] = (dp[7] << 2) + (dp[9] >> 4 & 3);
527 pix[7] = (dp[8] << 2) + (dp[9] >> 6 );
529 if ((row+=2) > height) row = 1;
533 void CLASS canon_600_correct()
536 static const short mul[4][2] =
537 { { 1141,1145 }, { 1128,1109 }, { 1178,1149 }, { 1128,1109 } };
539 for (row=0; row < height; row++)
540 for (col=0; col < width; col++) {
541 if ((val = BAYER(row,col) - black) < 0) val = 0;
542 val = val * mul[row & 3][col & 1] >> 9;
543 BAYER(row,col) = val;
545 canon_600_fixed_wb(1311);
548 maximum = (0x3ff - black) * 1109 >> 9;
552 int CLASS canon_s2is()
556 for (row=0; row < 100; row++) {
557 fseek (ifp, row*3340 + 3284, SEEK_SET);
558 if (getc(ifp) > 15) return 1;
564 getbits(-1) initializes the buffer
565 getbits(n) where 0 <= n <= 25 returns an n-bit integer
567 unsigned CLASS getbithuff (int nbits, ushort *huff)
569 static unsigned bitbuf=0;
570 static int vbits=0, reset=0;
574 return bitbuf = vbits = reset = 0;
575 if (nbits == 0 || vbits < 0) return 0;
576 while (!reset && vbits < nbits && (c = fgetc(ifp)) != EOF &&
577 !(reset = zero_after_ff && c == 0xff && fgetc(ifp))) {
578 bitbuf = (bitbuf << 8) + (uchar) c;
581 c = bitbuf << (32-vbits) >> (32-nbits);
583 vbits -= huff[c] >> 8;
587 if (vbits < 0) derror();
591 #define getbits(n) getbithuff(n,0)
592 #define gethuff(h) getbithuff(*h,h+1)
595 Construct a decode tree according the specification in *source.
596 The first 16 bytes specify how many codes should be 1-bit, 2-bit
597 3-bit, etc. Bytes after that are the leaf values.
599 For example, if the source is
601 { 0,1,4,2,3,1,2,0,0,0,0,0,0,0,0,0,
602 0x04,0x03,0x05,0x06,0x02,0x07,0x01,0x08,0x09,0x00,0x0a,0x0b,0xff },
620 ushort * CLASS make_decoder_ref (const uchar **source)
622 int max, len, h, i, j;
626 count = (*source += 16) - 17;
627 for (max=16; max && !count[max]; max--);
628 huff = (ushort *) calloc (1 + (1 << max), sizeof *huff);
629 merror (huff, "make_decoder()");
631 for (h=len=1; len <= max; len++)
632 for (i=0; i < count[len]; i++, ++*source)
633 for (j=0; j < 1 << (max-len); j++)
635 huff[h++] = len << 8 | **source;
639 ushort * CLASS make_decoder (const uchar *source)
641 return make_decoder_ref (&source);
644 void CLASS crw_init_tables (unsigned table, ushort *huff[2])
646 static const uchar first_tree[3][29] = {
647 { 0,1,4,2,3,1,2,0,0,0,0,0,0,0,0,0,
648 0x04,0x03,0x05,0x06,0x02,0x07,0x01,0x08,0x09,0x00,0x0a,0x0b,0xff },
649 { 0,2,2,3,1,1,1,1,2,0,0,0,0,0,0,0,
650 0x03,0x02,0x04,0x01,0x05,0x00,0x06,0x07,0x09,0x08,0x0a,0x0b,0xff },
651 { 0,0,6,3,1,1,2,0,0,0,0,0,0,0,0,0,
652 0x06,0x05,0x07,0x04,0x08,0x03,0x09,0x02,0x00,0x0a,0x01,0x0b,0xff },
654 static const uchar second_tree[3][180] = {
655 { 0,2,2,2,1,4,2,1,2,5,1,1,0,0,0,139,
656 0x03,0x04,0x02,0x05,0x01,0x06,0x07,0x08,
657 0x12,0x13,0x11,0x14,0x09,0x15,0x22,0x00,0x21,0x16,0x0a,0xf0,
658 0x23,0x17,0x24,0x31,0x32,0x18,0x19,0x33,0x25,0x41,0x34,0x42,
659 0x35,0x51,0x36,0x37,0x38,0x29,0x79,0x26,0x1a,0x39,0x56,0x57,
660 0x28,0x27,0x52,0x55,0x58,0x43,0x76,0x59,0x77,0x54,0x61,0xf9,
661 0x71,0x78,0x75,0x96,0x97,0x49,0xb7,0x53,0xd7,0x74,0xb6,0x98,
662 0x47,0x48,0x95,0x69,0x99,0x91,0xfa,0xb8,0x68,0xb5,0xb9,0xd6,
663 0xf7,0xd8,0x67,0x46,0x45,0x94,0x89,0xf8,0x81,0xd5,0xf6,0xb4,
664 0x88,0xb1,0x2a,0x44,0x72,0xd9,0x87,0x66,0xd4,0xf5,0x3a,0xa7,
665 0x73,0xa9,0xa8,0x86,0x62,0xc7,0x65,0xc8,0xc9,0xa1,0xf4,0xd1,
666 0xe9,0x5a,0x92,0x85,0xa6,0xe7,0x93,0xe8,0xc1,0xc6,0x7a,0x64,
667 0xe1,0x4a,0x6a,0xe6,0xb3,0xf1,0xd3,0xa5,0x8a,0xb2,0x9a,0xba,
668 0x84,0xa4,0x63,0xe5,0xc5,0xf3,0xd2,0xc4,0x82,0xaa,0xda,0xe4,
669 0xf2,0xca,0x83,0xa3,0xa2,0xc3,0xea,0xc2,0xe2,0xe3,0xff,0xff },
670 { 0,2,2,1,4,1,4,1,3,3,1,0,0,0,0,140,
671 0x02,0x03,0x01,0x04,0x05,0x12,0x11,0x06,
672 0x13,0x07,0x08,0x14,0x22,0x09,0x21,0x00,0x23,0x15,0x31,0x32,
673 0x0a,0x16,0xf0,0x24,0x33,0x41,0x42,0x19,0x17,0x25,0x18,0x51,
674 0x34,0x43,0x52,0x29,0x35,0x61,0x39,0x71,0x62,0x36,0x53,0x26,
675 0x38,0x1a,0x37,0x81,0x27,0x91,0x79,0x55,0x45,0x28,0x72,0x59,
676 0xa1,0xb1,0x44,0x69,0x54,0x58,0xd1,0xfa,0x57,0xe1,0xf1,0xb9,
677 0x49,0x47,0x63,0x6a,0xf9,0x56,0x46,0xa8,0x2a,0x4a,0x78,0x99,
678 0x3a,0x75,0x74,0x86,0x65,0xc1,0x76,0xb6,0x96,0xd6,0x89,0x85,
679 0xc9,0xf5,0x95,0xb4,0xc7,0xf7,0x8a,0x97,0xb8,0x73,0xb7,0xd8,
680 0xd9,0x87,0xa7,0x7a,0x48,0x82,0x84,0xea,0xf4,0xa6,0xc5,0x5a,
681 0x94,0xa4,0xc6,0x92,0xc3,0x68,0xb5,0xc8,0xe4,0xe5,0xe6,0xe9,
682 0xa2,0xa3,0xe3,0xc2,0x66,0x67,0x93,0xaa,0xd4,0xd5,0xe7,0xf8,
683 0x88,0x9a,0xd7,0x77,0xc4,0x64,0xe2,0x98,0xa5,0xca,0xda,0xe8,
684 0xf3,0xf6,0xa9,0xb2,0xb3,0xf2,0xd2,0x83,0xba,0xd3,0xff,0xff },
685 { 0,0,6,2,1,3,3,2,5,1,2,2,8,10,0,117,
686 0x04,0x05,0x03,0x06,0x02,0x07,0x01,0x08,
687 0x09,0x12,0x13,0x14,0x11,0x15,0x0a,0x16,0x17,0xf0,0x00,0x22,
688 0x21,0x18,0x23,0x19,0x24,0x32,0x31,0x25,0x33,0x38,0x37,0x34,
689 0x35,0x36,0x39,0x79,0x57,0x58,0x59,0x28,0x56,0x78,0x27,0x41,
690 0x29,0x77,0x26,0x42,0x76,0x99,0x1a,0x55,0x98,0x97,0xf9,0x48,
691 0x54,0x96,0x89,0x47,0xb7,0x49,0xfa,0x75,0x68,0xb6,0x67,0x69,
692 0xb9,0xb8,0xd8,0x52,0xd7,0x88,0xb5,0x74,0x51,0x46,0xd9,0xf8,
693 0x3a,0xd6,0x87,0x45,0x7a,0x95,0xd5,0xf6,0x86,0xb4,0xa9,0x94,
694 0x53,0x2a,0xa8,0x43,0xf5,0xf7,0xd4,0x66,0xa7,0x5a,0x44,0x8a,
695 0xc9,0xe8,0xc8,0xe7,0x9a,0x6a,0x73,0x4a,0x61,0xc7,0xf4,0xc6,
696 0x65,0xe9,0x72,0xe6,0x71,0x91,0x93,0xa6,0xda,0x92,0x85,0x62,
697 0xf3,0xc5,0xb2,0xa4,0x84,0xba,0x64,0xa5,0xb3,0xd2,0x81,0xe5,
698 0xd3,0xaa,0xc4,0xca,0xf2,0xb1,0xe4,0xd1,0x83,0x63,0xea,0xc3,
699 0xe2,0x82,0xf1,0xa3,0xc2,0xa1,0xc1,0xe3,0xa2,0xe1,0xff,0xff }
701 if (table > 2) table = 2;
702 huff[0] = make_decoder ( first_tree[table]);
703 huff[1] = make_decoder (second_tree[table]);
707 Return 0 if the image starts with compressed data,
708 1 if it starts with uncompressed low-order bits.
710 In Canon compressed data, 0xff is always followed by 0x00.
712 int CLASS canon_has_lowbits()
717 fseek (ifp, 0, SEEK_SET);
718 fread (test, 1, sizeof test, ifp);
719 for (i=540; i < sizeof test - 1; i++)
720 if (test[i] == 0xff) {
721 if (test[i+1]) return 1;
727 void CLASS canon_load_raw()
729 ushort *pixel, *prow, *huff[2];
730 int nblocks, lowbits, i, c, row, r, save, val;
731 int block, diffbuf[64], leaf, len, diff, carry=0, pnum=0, base[2];
733 crw_init_tables (tiff_compress, huff);
734 lowbits = canon_has_lowbits();
735 if (!lowbits) maximum = 0x3ff;
736 fseek (ifp, 540 + lowbits*raw_height*raw_width/4, SEEK_SET);
739 for (row=0; row < raw_height; row+=8) {
740 pixel = raw_image + row*raw_width;
741 nblocks = MIN (8, raw_height-row) * raw_width >> 6;
742 for (block=0; block < nblocks; block++) {
743 memset (diffbuf, 0, sizeof diffbuf);
744 for (i=0; i < 64; i++ ) {
745 leaf = gethuff(huff[i > 0]);
746 if (leaf == 0 && i) break;
747 if (leaf == 0xff) continue;
750 if (len == 0) continue;
752 if ((diff & (1 << (len-1))) == 0)
753 diff -= (1 << len) - 1;
754 if (i < 64) diffbuf[i] = diff;
758 for (i=0; i < 64; i++ ) {
759 if (pnum++ % raw_width == 0)
760 base[0] = base[1] = 512;
761 if ((pixel[(block << 6) + i] = base[i & 1] += diffbuf[i]) >> 10)
767 fseek (ifp, 26 + row*raw_width/4, SEEK_SET);
768 for (prow=pixel, i=0; i < raw_width*2; i++) {
770 for (r=0; r < 8; r+=2, prow++) {
771 val = (*prow << 2) + ((c >> r) & 3);
772 if (raw_width == 2672 && val < 512) val += 2;
776 fseek (ifp, save, SEEK_SET);
779 FORC(2) free (huff[c]);
783 Not a full implementation of Lossless JPEG, just
784 enough to decode Canon, Kodak and Adobe DNG images.
787 int bits, high, wide, clrs, sraw, psv, restart, vpred[6];
788 ushort *huff[6], *free[4], *row;
791 int CLASS ljpeg_start (struct jhead *jh, int info_only)
797 memset (jh, 0, sizeof *jh);
798 jh->restart = INT_MAX;
799 fread (data, 2, 1, ifp);
800 if (data[1] != 0xd8) return 0;
802 fread (data, 2, 2, ifp);
803 tag = data[0] << 8 | data[1];
804 len = (data[2] << 8 | data[3]) - 2;
805 if (tag <= 0xff00) return 0;
806 fread (data, 1, len, ifp);
809 jh->sraw = ((data[7] >> 4) * (data[7] & 15) - 1) & 3;
812 jh->high = data[1] << 8 | data[2];
813 jh->wide = data[3] << 8 | data[4];
814 jh->clrs = data[5] + jh->sraw;
815 if (len == 9 && !dng_version) getc(ifp);
818 if (info_only) break;
819 for (dp = data; dp < data+len && (c = *dp++) < 4; )
820 jh->free[c] = jh->huff[c] = make_decoder_ref (&dp);
823 jh->psv = data[1+data[0]*2];
824 jh->bits -= data[3+data[0]*2] & 15;
827 jh->restart = data[0] << 8 | data[1];
829 } while (tag != 0xffda);
830 if (info_only) return 1;
831 FORC(5) if (!jh->huff[c+1]) jh->huff[c+1] = jh->huff[c];
833 FORC(4) jh->huff[2+c] = jh->huff[1];
834 FORC(jh->sraw) jh->huff[1+c] = jh->huff[0];
836 jh->row = (ushort *) calloc (jh->wide*jh->clrs, 4);
837 merror (jh->row, "ljpeg_start()");
838 return zero_after_ff = 1;
841 void CLASS ljpeg_end (struct jhead *jh)
844 FORC4 if (jh->free[c]) free (jh->free[c]);
848 int CLASS ljpeg_diff (ushort *huff)
853 if (len == 16 && (!dng_version || dng_version >= 0x1010000))
856 if ((diff & (1 << (len-1))) == 0)
857 diff -= (1 << len) - 1;
861 ushort * CLASS ljpeg_row (int jrow, struct jhead *jh)
863 int col, c, diff, pred, spred=0;
864 ushort mark=0, *row[3];
866 if (jrow * jh->wide % jh->restart == 0) {
867 FORC(6) jh->vpred[c] = 1 << (jh->bits-1);
869 fseek (ifp, -2, SEEK_CUR);
870 do mark = (mark << 8) + (c = fgetc(ifp));
871 while (c != EOF && mark >> 4 != 0xffd);
875 FORC3 row[c] = jh->row + jh->wide*jh->clrs*((jrow+c) & 1);
876 for (col=0; col < jh->wide; col++)
878 diff = ljpeg_diff (jh->huff[c]);
879 if (jh->sraw && c <= jh->sraw && (col | c))
881 else if (col) pred = row[0][-jh->clrs];
882 else pred = (jh->vpred[c] += diff) - diff;
883 if (jrow && col) switch (jh->psv) {
885 case 2: pred = row[1][0]; break;
886 case 3: pred = row[1][-jh->clrs]; break;
887 case 4: pred = pred + row[1][0] - row[1][-jh->clrs]; break;
888 case 5: pred = pred + ((row[1][0] - row[1][-jh->clrs]) >> 1); break;
889 case 6: pred = row[1][0] + ((pred - row[1][-jh->clrs]) >> 1); break;
890 case 7: pred = (pred + row[1][0]) >> 1; break;
893 if ((**row = pred + diff) >> jh->bits) derror();
894 if (c <= jh->sraw) spred = **row;
900 void CLASS lossless_jpeg_load_raw()
902 int jwide, jrow, jcol, val, jidx, i, j, row=0, col=0;
906 if (!ljpeg_start (&jh, 0)) return;
907 jwide = jh.wide * jh.clrs;
909 for (jrow=0; jrow < jh.high; jrow++) {
910 rp = ljpeg_row (jrow, &jh);
912 row = jrow & 1 ? height-1-jrow/2 : jrow/2;
913 for (jcol=0; jcol < jwide; jcol++) {
916 jidx = jrow*jwide + jcol;
917 i = jidx / (cr2_slice[1]*jh.high);
918 if ((j = i >= cr2_slice[0]))
920 jidx -= i * (cr2_slice[1]*jh.high);
921 row = jidx / cr2_slice[1+j];
922 col = jidx % cr2_slice[1+j] + i*cr2_slice[1];
924 if (raw_width == 3984 && (col -= 2) < 0)
925 col += (row--,raw_width);
926 if (row >= 0) RAW(row,col) = val;
927 if (++col >= raw_width)
934 void CLASS canon_sraw_load_raw()
937 short *rp=0, (*ip)[4];
938 int jwide, slice, scol, ecol, row, col, jrow=0, jcol=0, pix[3], c;
939 int v[3]={0,0,0}, ver, hue;
942 if (!ljpeg_start (&jh, 0)) return;
943 jwide = (jh.wide >>= 1) * jh.clrs;
945 for (ecol=slice=0; slice <= cr2_slice[0]; slice++) {
947 ecol += cr2_slice[1] * 2 / jh.clrs;
948 if (!cr2_slice[0] || ecol > raw_width-1) ecol = raw_width & -2;
949 for (row=0; row < height; row += (jh.clrs >> 1) - 1) {
950 ip = (short (*)[4]) image + row*width;
951 for (col=scol; col < ecol; col+=2, jcol+=jh.clrs) {
952 if ((jcol %= jwide) == 0)
953 rp = (short *) ljpeg_row (jrow++, &jh);
954 if (col >= width) continue;
956 ip[col + (c >> 1)*width + (c & 1)][0] = rp[jcol+c];
957 ip[col][1] = rp[jcol+jh.clrs-2] - 16384;
958 ip[col][2] = rp[jcol+jh.clrs-1] - 16384;
962 for (cp=model2; *cp && !isdigit(*cp); cp++);
963 sscanf (cp, "%d.%d.%d", v, v+1, v+2);
964 ver = (v[0]*1000 + v[1])*1000 + v[2];
965 hue = (jh.sraw+1) << 2;
966 if (unique_id >= 0x80000281 || (unique_id == 0x80000218 && ver > 1000006))
968 ip = (short (*)[4]) image;
970 for (row=0; row < height; row++, ip+=width) {
971 if (row & (jh.sraw >> 1))
972 for (col=0; col < width; col+=2)
973 for (c=1; c < 3; c++)
975 ip[col][c] = ip[col-width][c];
976 else ip[col][c] = (ip[col-width][c] + ip[col+width][c] + 1) >> 1;
977 for (col=1; col < width; col+=2)
978 for (c=1; c < 3; c++)
980 ip[col][c] = ip[col-1][c];
981 else ip[col][c] = (ip[col-1][c] + ip[col+1][c] + 1) >> 1;
983 for ( ; rp < ip[0]; rp+=4) {
984 if (unique_id == 0x80000218 ||
985 unique_id == 0x80000250 ||
986 unique_id == 0x80000261 ||
987 unique_id == 0x80000281 ||
988 unique_id == 0x80000287) {
989 rp[1] = (rp[1] << 2) + hue;
990 rp[2] = (rp[2] << 2) + hue;
991 pix[0] = rp[0] + (( 50*rp[1] + 22929*rp[2]) >> 14);
992 pix[1] = rp[0] + ((-5640*rp[1] - 11751*rp[2]) >> 14);
993 pix[2] = rp[0] + ((29040*rp[1] - 101*rp[2]) >> 14);
995 if (unique_id < 0x80000218) rp[0] -= 512;
996 pix[0] = rp[0] + rp[2];
997 pix[2] = rp[0] + rp[1];
998 pix[1] = rp[0] + ((-778*rp[1] - (rp[2] << 11)) >> 12);
1000 FORC3 rp[c] = CLIP(pix[c] * sraw_mul[c] >> 10);
1006 void CLASS adobe_copy_pixel (unsigned row, unsigned col, ushort **rp)
1010 if (is_raw == 2 && shot_select) (*rp)++;
1012 if (row < raw_height && col < raw_width)
1013 RAW(row,col) = curve[**rp];
1016 if (row < height && col < width)
1018 image[row*width+col][c] = curve[(*rp)[c]];
1019 *rp += tiff_samples;
1021 if (is_raw == 2 && shot_select) (*rp)--;
1024 void CLASS lossless_dng_load_raw()
1026 unsigned save, trow=0, tcol=0, jwide, jrow, jcol, row, col;
1030 while (trow < raw_height) {
1032 if (tile_length < INT_MAX)
1033 fseek (ifp, get4(), SEEK_SET);
1034 if (!ljpeg_start (&jh, 0)) break;
1036 if (filters) jwide *= jh.clrs;
1038 for (row=col=jrow=0; jrow < jh.high; jrow++) {
1039 rp = ljpeg_row (jrow, &jh);
1040 for (jcol=0; jcol < jwide; jcol++) {
1041 adobe_copy_pixel (trow+row, tcol+col, &rp);
1042 if (++col >= tile_width || col >= raw_width)
1043 row += 1 + (col = 0);
1046 fseek (ifp, save+4, SEEK_SET);
1047 if ((tcol += tile_width) >= raw_width)
1048 trow += tile_length + (tcol = 0);
1053 void CLASS packed_dng_load_raw()
1058 pixel = (ushort *) calloc (raw_width * tiff_samples, sizeof *pixel);
1059 merror (pixel, "packed_dng_load_raw()");
1060 for (row=0; row < raw_height; row++) {
1062 read_shorts (pixel, raw_width * tiff_samples);
1065 for (col=0; col < raw_width * tiff_samples; col++)
1066 pixel[col] = getbits(tiff_bps);
1068 for (rp=pixel, col=0; col < raw_width; col++)
1069 adobe_copy_pixel (row, col, &rp);
1074 void CLASS pentax_load_raw()
1076 ushort bit[2][15], huff[4097];
1077 int dep, row, col, diff, c, i;
1078 ushort vpred[2][2] = {{0,0},{0,0}}, hpred[2];
1080 fseek (ifp, meta_offset, SEEK_SET);
1081 dep = (get2() + 12) & 15;
1082 fseek (ifp, 12, SEEK_CUR);
1083 FORC(dep) bit[0][c] = get2();
1084 FORC(dep) bit[1][c] = fgetc(ifp);
1086 for (i=bit[0][c]; i <= ((bit[0][c]+(4096 >> bit[1][c])-1) & 4095); )
1087 huff[++i] = bit[1][c] << 8 | c;
1089 fseek (ifp, data_offset, SEEK_SET);
1091 for (row=0; row < raw_height; row++)
1092 for (col=0; col < raw_width; col++) {
1093 diff = ljpeg_diff (huff);
1094 if (col < 2) hpred[col] = vpred[row & 1][col] += diff;
1095 else hpred[col & 1] += diff;
1096 RAW(row,col) = hpred[col & 1];
1097 if (hpred[col & 1] >> tiff_bps) derror();
1101 void CLASS nikon_load_raw()
1103 static const uchar nikon_tree[][32] = {
1104 { 0,1,5,1,1,1,1,1,1,2,0,0,0,0,0,0, /* 12-bit lossy */
1105 5,4,3,6,2,7,1,0,8,9,11,10,12 },
1106 { 0,1,5,1,1,1,1,1,1,2,0,0,0,0,0,0, /* 12-bit lossy after split */
1107 0x39,0x5a,0x38,0x27,0x16,5,4,3,2,1,0,11,12,12 },
1108 { 0,1,4,2,3,1,2,0,0,0,0,0,0,0,0,0, /* 12-bit lossless */
1109 5,4,6,3,7,2,8,1,9,0,10,11,12 },
1110 { 0,1,4,3,1,1,1,1,1,2,0,0,0,0,0,0, /* 14-bit lossy */
1111 5,6,4,7,8,3,9,2,1,0,10,11,12,13,14 },
1112 { 0,1,5,1,1,1,1,1,1,1,2,0,0,0,0,0, /* 14-bit lossy after split */
1113 8,0x5c,0x4b,0x3a,0x29,7,6,5,4,3,2,1,0,13,14 },
1114 { 0,1,4,2,2,3,1,2,0,0,0,0,0,0,0,0, /* 14-bit lossless */
1115 7,6,8,5,9,4,10,3,11,12,2,0,1,13,14 } };
1116 ushort *huff, ver0, ver1, vpred[2][2], hpred[2], csize;
1117 int i, min, max, step=0, tree=0, split=0, row, col, len, shl, diff;
1119 fseek (ifp, meta_offset, SEEK_SET);
1122 if (ver0 == 0x49 || ver1 == 0x58)
1123 fseek (ifp, 2110, SEEK_CUR);
1124 if (ver0 == 0x46) tree = 2;
1125 if (tiff_bps == 14) tree += 3;
1126 read_shorts (vpred[0], 4);
1127 max = 1 << tiff_bps & 0x7fff;
1128 if ((csize = get2()) > 1)
1129 step = max / (csize-1);
1130 if (ver0 == 0x44 && ver1 == 0x20 && step > 0) {
1131 for (i=0; i < csize; i++)
1132 curve[i*step] = get2();
1133 for (i=0; i < max; i++)
1134 curve[i] = ( curve[i-i%step]*(step-i%step) +
1135 curve[i-i%step+step]*(i%step) ) / step;
1136 fseek (ifp, meta_offset+562, SEEK_SET);
1138 } else if (ver0 != 0x46 && csize <= 0x4001)
1139 read_shorts (curve, max=csize);
1140 while (curve[max-2] == curve[max-1]) max--;
1141 huff = make_decoder (nikon_tree[tree]);
1142 fseek (ifp, data_offset, SEEK_SET);
1144 for (min=row=0; row < height; row++) {
1145 if (split && row == split) {
1147 huff = make_decoder (nikon_tree[tree+1]);
1148 max += (min = 16) << 1;
1150 for (col=0; col < raw_width; col++) {
1154 diff = ((getbits(len-shl) << 1) + 1) << shl >> 1;
1155 if ((diff & (1 << (len-1))) == 0)
1156 diff -= (1 << len) - !shl;
1157 if (col < 2) hpred[col] = vpred[row & 1][col] += diff;
1158 else hpred[col & 1] += diff;
1159 if ((ushort)(hpred[col & 1] + min) >= max) derror();
1160 RAW(row,col) = curve[LIM((short)hpred[col & 1],0,0x3fff)];
1167 Returns 1 for a Coolpix 995, 0 for anything else.
1169 int CLASS nikon_e995()
1172 const uchar often[] = { 0x00, 0x55, 0xaa, 0xff };
1174 memset (histo, 0, sizeof histo);
1175 fseek (ifp, -2000, SEEK_END);
1176 for (i=0; i < 2000; i++)
1177 histo[fgetc(ifp)]++;
1178 for (i=0; i < 4; i++)
1179 if (histo[often[i]] < 200)
1185 Returns 1 for a Coolpix 2100, 0 for anything else.
1187 int CLASS nikon_e2100()
1192 fseek (ifp, 0, SEEK_SET);
1193 for (i=0; i < 1024; i++) {
1194 fread (t, 1, 12, ifp);
1195 if (((t[2] & t[4] & t[7] & t[9]) >> 4
1196 & t[1] & t[6] & t[8] & t[11] & 3) != 3)
1202 void CLASS nikon_3700()
1206 static const struct {
1208 char make[12], model[15];
1210 { 0x00, "PENTAX", "Optio 33WR" },
1211 { 0x03, "NIKON", "E3200" },
1212 { 0x32, "NIKON", "E3700" },
1213 { 0x33, "OLYMPUS", "C740UZ" } };
1215 fseek (ifp, 3072, SEEK_SET);
1216 fread (dp, 1, 24, ifp);
1217 bits = (dp[8] & 3) << 4 | (dp[20] & 3);
1218 for (i=0; i < sizeof table / sizeof *table; i++)
1219 if (bits == table[i].bits) {
1220 strcpy (make, table[i].make );
1221 strcpy (model, table[i].model);
1226 Separates a Minolta DiMAGE Z2 from a Nikon E4300.
1228 int CLASS minolta_z2()
1233 fseek (ifp, -sizeof tail, SEEK_END);
1234 fread (tail, 1, sizeof tail, ifp);
1235 for (nz=i=0; i < sizeof tail; i++)
1240 void CLASS jpeg_thumb();
1242 void CLASS ppm_thumb()
1245 thumb_length = thumb_width*thumb_height*3;
1246 thumb = (char *) malloc (thumb_length);
1247 merror (thumb, "ppm_thumb()");
1248 fprintf (ofp, "P6\n%d %d\n255\n", thumb_width, thumb_height);
1249 fread (thumb, 1, thumb_length, ifp);
1250 fwrite (thumb, 1, thumb_length, ofp);
1254 void CLASS ppm16_thumb()
1258 thumb_length = thumb_width*thumb_height*3;
1259 thumb = (char *) calloc (thumb_length,2);
1260 merror (thumb, "ppm16_thumb()");
1261 read_shorts ((ushort *) thumb, thumb_length);
1262 for (i=0; i < thumb_length; i++)
1263 thumb[i] = ((ushort *) thumb)[i] >> 8;
1264 fprintf (ofp, "P6\n%d %d\n255\n", thumb_width, thumb_height);
1265 fwrite (thumb, 1, thumb_length, ofp);
1269 void CLASS layer_thumb()
1272 char *thumb, map[][4] = { "012","102" };
1274 colors = thumb_misc >> 5 & 7;
1275 thumb_length = thumb_width*thumb_height;
1276 thumb = (char *) calloc (colors, thumb_length);
1277 merror (thumb, "layer_thumb()");
1278 fprintf (ofp, "P%d\n%d %d\n255\n",
1279 5 + (colors >> 1), thumb_width, thumb_height);
1280 fread (thumb, thumb_length, colors, ifp);
1281 for (i=0; i < thumb_length; i++)
1282 FORCC putc (thumb[i+thumb_length*(map[thumb_misc >> 8][c]-'0')], ofp);
1286 void CLASS rollei_thumb()
1291 thumb_length = thumb_width * thumb_height;
1292 thumb = (ushort *) calloc (thumb_length, 2);
1293 merror (thumb, "rollei_thumb()");
1294 fprintf (ofp, "P6\n%d %d\n255\n", thumb_width, thumb_height);
1295 read_shorts (thumb, thumb_length);
1296 for (i=0; i < thumb_length; i++) {
1297 putc (thumb[i] << 3, ofp);
1298 putc (thumb[i] >> 5 << 2, ofp);
1299 putc (thumb[i] >> 11 << 3, ofp);
1304 void CLASS rollei_load_raw()
1307 unsigned iten=0, isix, i, buffer=0, todo[16];
1309 isix = raw_width * raw_height * 5 / 8;
1310 while (fread (pixel, 1, 10, ifp) == 10) {
1311 for (i=0; i < 10; i+=2) {
1313 todo[i+1] = pixel[i] << 8 | pixel[i+1];
1314 buffer = pixel[i] >> 2 | buffer << 6;
1316 for ( ; i < 16; i+=2) {
1318 todo[i+1] = buffer >> (14-i)*5;
1320 for (i=0; i < 16; i+=2)
1321 raw_image[todo[i]] = (todo[i+1] & 0x3ff);
1326 int CLASS raw (unsigned row, unsigned col)
1328 return (row < raw_height && col < raw_width) ? RAW(row,col) : 0;
1331 void CLASS phase_one_flat_field (int is_float, int nc)
1334 unsigned wide, y, x, c, rend, cend, row, col;
1335 float *mrow, num, mult[4];
1337 read_shorts (head, 8);
1338 wide = head[2] / head[4];
1339 mrow = (float *) calloc (nc*wide, sizeof *mrow);
1340 merror (mrow, "phase_one_flat_field()");
1341 for (y=0; y < head[3] / head[5]; y++) {
1342 for (x=0; x < wide; x++)
1343 for (c=0; c < nc; c+=2) {
1344 num = is_float ? getreal(11) : get2()/32768.0;
1345 if (y==0) mrow[c*wide+x] = num;
1346 else mrow[(c+1)*wide+x] = (num - mrow[c*wide+x]) / head[5];
1349 rend = head[1] + y*head[5];
1350 for (row = rend-head[5]; row < raw_height && row < rend; row++) {
1351 for (x=1; x < wide; x++) {
1352 for (c=0; c < nc; c+=2) {
1353 mult[c] = mrow[c*wide+x-1];
1354 mult[c+1] = (mrow[c*wide+x] - mult[c]) / head[4];
1356 cend = head[0] + x*head[4];
1357 for (col = cend-head[4]; col < raw_width && col < cend; col++) {
1358 c = nc > 2 ? FC(row-top_margin,col-left_margin) : 0;
1360 c = RAW(row,col) * mult[c];
1361 RAW(row,col) = LIM(c,0,65535);
1363 for (c=0; c < nc; c+=2)
1364 mult[c] += mult[c+1];
1367 for (x=0; x < wide; x++)
1368 for (c=0; c < nc; c+=2)
1369 mrow[c*wide+x] += mrow[(c+1)*wide+x];
1375 void CLASS phase_one_correct()
1377 unsigned entries, tag, data, save, col, row, type;
1378 int len, i, j, k, cip, val[4], dev[4], sum, max;
1379 int head[9], diff, mindiff=INT_MAX, off_412=0;
1380 static const signed char dir[12][2] =
1381 { {-1,-1}, {-1,1}, {1,-1}, {1,1}, {-2,0}, {0,-2}, {0,2}, {2,0},
1382 {-2,-2}, {-2,2}, {2,-2}, {2,2} };
1383 float poly[8], num, cfrac, frac, mult[2], *yval[2];
1386 if (half_size || !meta_length) return;
1387 if (verbose) fprintf (stderr,_("Phase One correction...\n"));
1388 fseek (ifp, meta_offset, SEEK_SET);
1390 fseek (ifp, 6, SEEK_CUR);
1391 fseek (ifp, meta_offset+get4(), SEEK_SET);
1392 entries = get4(); get4();
1398 fseek (ifp, meta_offset+data, SEEK_SET);
1399 if (tag == 0x419) { /* Polynomial curve */
1400 for (get4(), i=0; i < 8; i++)
1401 poly[i] = getreal(11);
1402 poly[3] += (ph1.tag_210 - poly[7]) * poly[6] + 1;
1403 for (i=0; i < 0x10000; i++) {
1404 num = (poly[5]*i + poly[3])*i + poly[1];
1405 curve[i] = LIM(num,0,65535);
1406 } goto apply; /* apply to right half */
1407 } else if (tag == 0x41a) { /* Polynomial curve */
1408 for (i=0; i < 4; i++)
1409 poly[i] = getreal(11);
1410 for (i=0; i < 0x10000; i++) {
1411 for (num=0, j=4; j--; )
1412 num = num * i + poly[j];
1413 curve[i] = LIM(num+i,0,65535);
1414 } apply: /* apply to whole image */
1415 for (row=0; row < raw_height; row++)
1416 for (col = (tag & 1)*ph1.split_col; col < raw_width; col++)
1417 RAW(row,col) = curve[RAW(row,col)];
1418 } else if (tag == 0x400) { /* Sensor defects */
1419 while ((len -= 8) >= 0) {
1422 type = get2(); get2();
1423 if (col >= raw_width) continue;
1424 if (type == 131) /* Bad column */
1425 for (row=0; row < raw_height; row++)
1426 if (FC(row-top_margin,col-left_margin) == 1) {
1427 for (sum=i=0; i < 4; i++)
1428 sum += val[i] = raw (row+dir[i][0], col+dir[i][1]);
1429 for (max=i=0; i < 4; i++) {
1430 dev[i] = abs((val[i] << 2) - sum);
1431 if (dev[max] < dev[i]) max = i;
1433 RAW(row,col) = (sum - val[max])/3.0 + 0.5;
1435 for (sum=0, i=8; i < 12; i++)
1436 sum += raw (row+dir[i][0], col+dir[i][1]);
1437 RAW(row,col) = 0.5 + sum * 0.0732233 +
1438 (raw(row,col-2) + raw(row,col+2)) * 0.3535534;
1440 else if (type == 129) { /* Bad pixel */
1441 if (row >= raw_height) continue;
1442 j = (FC(row-top_margin,col-left_margin) != 1) * 4;
1443 for (sum=0, i=j; i < j+8; i++)
1444 sum += raw (row+dir[i][0], col+dir[i][1]);
1445 RAW(row,col) = (sum + 4) >> 3;
1448 } else if (tag == 0x401) { /* All-color flat fields */
1449 phase_one_flat_field (1, 2);
1450 } else if (tag == 0x416 || tag == 0x410) {
1451 phase_one_flat_field (0, 2);
1452 } else if (tag == 0x40b) { /* Red+blue flat field */
1453 phase_one_flat_field (0, 4);
1454 } else if (tag == 0x412) {
1455 fseek (ifp, 36, SEEK_CUR);
1456 diff = abs (get2() - ph1.tag_21a);
1457 if (mindiff > diff) {
1459 off_412 = ftell(ifp) - 38;
1462 fseek (ifp, save, SEEK_SET);
1465 fseek (ifp, off_412, SEEK_SET);
1466 for (i=0; i < 9; i++) head[i] = get4() & 0x7fff;
1467 yval[0] = (float *) calloc (head[1]*head[3] + head[2]*head[4], 6);
1468 merror (yval[0], "phase_one_correct()");
1469 yval[1] = (float *) (yval[0] + head[1]*head[3]);
1470 xval[0] = (ushort *) (yval[1] + head[2]*head[4]);
1471 xval[1] = (ushort *) (xval[0] + head[1]*head[3]);
1473 for (i=0; i < 2; i++)
1474 for (j=0; j < head[i+1]*head[i+3]; j++)
1475 yval[i][j] = getreal(11);
1476 for (i=0; i < 2; i++)
1477 for (j=0; j < head[i+1]*head[i+3]; j++)
1478 xval[i][j] = get2();
1479 for (row=0; row < raw_height; row++)
1480 for (col=0; col < raw_width; col++) {
1481 cfrac = (float) col * head[3] / raw_width;
1482 cfrac -= cip = cfrac;
1483 num = RAW(row,col) * 0.5;
1484 for (i=cip; i < cip+2; i++) {
1485 for (k=j=0; j < head[1]; j++)
1486 if (num < xval[0][k = head[1]*i+j]) break;
1487 frac = (j == 0 || j == head[1]) ? 0 :
1488 (xval[0][k] - num) / (xval[0][k] - xval[0][k-1]);
1489 mult[i-cip] = yval[0][k-1] * frac + yval[0][k] * (1-frac);
1491 i = ((mult[0] * (1-cfrac) + mult[1] * cfrac) * row + num) * 2;
1492 RAW(row,col) = LIM(i,0,65535);
1498 void CLASS phase_one_load_raw()
1501 ushort akey, bkey, mask;
1503 fseek (ifp, ph1.key_off, SEEK_SET);
1506 mask = ph1.format == 1 ? 0x5555:0x1354;
1507 fseek (ifp, data_offset, SEEK_SET);
1508 read_shorts (raw_image, raw_width*raw_height);
1510 for (i=0; i < raw_width*raw_height; i+=2) {
1511 a = raw_image[i+0] ^ akey;
1512 b = raw_image[i+1] ^ bkey;
1513 raw_image[i+0] = (a & mask) | (b & ~mask);
1514 raw_image[i+1] = (b & mask) | (a & ~mask);
1518 unsigned CLASS ph1_bithuff (int nbits, ushort *huff)
1520 static UINT64 bitbuf=0;
1525 return bitbuf = vbits = 0;
1526 if (nbits == 0) return 0;
1527 if (vbits < nbits) {
1528 bitbuf = bitbuf << 32 | get4();
1531 c = bitbuf << (64-vbits) >> (64-nbits);
1533 vbits -= huff[c] >> 8;
1534 return (uchar) huff[c];
1539 #define ph1_bits(n) ph1_bithuff(n,0)
1540 #define ph1_huff(h) ph1_bithuff(*h,h+1)
1542 void CLASS phase_one_load_raw_c()
1544 static const int length[] = { 8,7,6,9,11,10,5,12,14,13 };
1545 int *offset, len[2], pred[2], row, col, i, j;
1549 pixel = (ushort *) calloc (raw_width + raw_height*4, 2);
1550 merror (pixel, "phase_one_load_raw_c()");
1551 offset = (int *) (pixel + raw_width);
1552 fseek (ifp, strip_offset, SEEK_SET);
1553 for (row=0; row < raw_height; row++)
1554 offset[row] = get4();
1555 black = (short (*)[2]) offset + raw_height;
1556 fseek (ifp, ph1.black_off, SEEK_SET);
1558 read_shorts ((ushort *) black[0], raw_height*2);
1559 for (i=0; i < 256; i++)
1560 curve[i] = i*i / 3.969 + 0.5;
1561 for (row=0; row < raw_height; row++) {
1562 fseek (ifp, data_offset + offset[row], SEEK_SET);
1564 pred[0] = pred[1] = 0;
1565 for (col=0; col < raw_width; col++) {
1566 if (col >= (raw_width & -8))
1567 len[0] = len[1] = 14;
1568 else if ((col & 7) == 0)
1569 for (i=0; i < 2; i++) {
1570 for (j=0; j < 5 && !ph1_bits(1); j++);
1571 if (j--) len[i] = length[j*2 + ph1_bits(1)];
1573 if ((i = len[col & 1]) == 14)
1574 pixel[col] = pred[col & 1] = ph1_bits(16);
1576 pixel[col] = pred[col & 1] += ph1_bits(i) + 1 - (1 << (i - 1));
1577 if (pred[col & 1] >> 16) derror();
1578 if (ph1.format == 5 && pixel[col] < 256)
1579 pixel[col] = curve[pixel[col]];
1581 for (col=0; col < raw_width; col++) {
1582 i = (pixel[col] << 2) - ph1.black + black[row][col >= ph1.split_col];
1583 if (i > 0) RAW(row,col) = i;
1587 maximum = 0xfffc - ph1.black;
1590 void CLASS hasselblad_load_raw()
1593 int row, col, pred[2], len[2], diff, c;
1595 if (!ljpeg_start (&jh, 0)) return;
1598 for (row=0; row < raw_height; row++) {
1599 pred[0] = pred[1] = 0x8000 + load_flags;
1600 for (col=0; col < raw_width; col+=2) {
1601 FORC(2) len[c] = ph1_huff(jh.huff[0]);
1603 diff = ph1_bits(len[c]);
1604 if ((diff & (1 << (len[c]-1))) == 0)
1605 diff -= (1 << len[c]) - 1;
1606 if (diff == 65535) diff = -32768;
1607 RAW(row,col+c) = pred[c] += diff;
1615 void CLASS leaf_hdr_load_raw()
1618 unsigned tile=0, r, c, row, col;
1621 pixel = (ushort *) calloc (raw_width, sizeof *pixel);
1622 merror (pixel, "leaf_hdr_load_raw()");
1625 for (r=0; r < raw_height; r++) {
1626 if (r % tile_length == 0) {
1627 fseek (ifp, data_offset + 4*tile++, SEEK_SET);
1628 fseek (ifp, get4(), SEEK_SET);
1630 if (filters && c != shot_select) continue;
1631 if (filters) pixel = raw_image + r*raw_width;
1632 read_shorts (pixel, raw_width);
1633 if (!filters && (row = r - top_margin) < height)
1634 for (col=0; col < width; col++)
1635 image[row*width+col][c] = pixel[col+left_margin];
1644 void CLASS unpacked_load_raw()
1646 int row, col, bits=0;
1648 while (1 << ++bits < maximum);
1649 read_shorts (raw_image, raw_width*raw_height);
1650 for (row=0; row < raw_height; row++)
1651 for (col=0; col < raw_width; col++)
1652 if ((RAW(row,col) >>= load_flags) >> bits
1653 && (unsigned) (row-top_margin) < height
1654 && (unsigned) (col-left_margin) < width) derror();
1657 void CLASS sinar_4shot_load_raw()
1660 unsigned shot, row, col, r, c;
1662 if ((shot = shot_select) || half_size) {
1664 if (shot > 3) shot = 3;
1665 fseek (ifp, data_offset + shot*4, SEEK_SET);
1666 fseek (ifp, get4(), SEEK_SET);
1667 unpacked_load_raw();
1673 image = (ushort (*)[4])
1674 calloc ((iheight=height)*(iwidth=width), sizeof *image);
1675 merror (image, "sinar_4shot_load_raw()");
1676 pixel = (ushort *) calloc (raw_width, sizeof *pixel);
1677 merror (pixel, "sinar_4shot_load_raw()");
1678 for (shot=0; shot < 4; shot++) {
1679 fseek (ifp, data_offset + shot*4, SEEK_SET);
1680 fseek (ifp, get4(), SEEK_SET);
1681 for (row=0; row < raw_height; row++) {
1682 read_shorts (pixel, raw_width);
1683 if ((r = row-top_margin - (shot >> 1 & 1)) >= height) continue;
1684 for (col=0; col < raw_width; col++) {
1685 if ((c = col-left_margin - (shot & 1)) >= width) continue;
1686 image[r*width+c][FC(row,col)] = pixel[col];
1691 shrink = filters = 0;
1694 void CLASS imacon_full_load_raw()
1698 for (row=0; row < height; row++)
1699 for (col=0; col < width; col++)
1700 read_shorts (image[row*width+col], 3);
1703 void CLASS packed_load_raw()
1705 int vbits=0, bwide, pwide, rbits, bite, half, irow, row, col, val, i;
1708 if (raw_width * 8 >= width * tiff_bps) /* Is raw_width in bytes? */
1709 pwide = (bwide = raw_width) * 8 / tiff_bps;
1710 else bwide = (pwide = raw_width) * tiff_bps / 8;
1711 rbits = bwide * 8 - pwide * tiff_bps;
1712 if (load_flags & 1) bwide = bwide * 16 / 15;
1713 bite = 8 + (load_flags & 24);
1714 half = (raw_height+1) >> 1;
1715 for (irow=0; irow < raw_height; irow++) {
1717 if (load_flags & 2 &&
1718 (row = irow % half * 2 + irow / half) == 1 &&
1720 if (vbits=0, tiff_compress)
1721 fseek (ifp, data_offset - (-half*bwide & -2048), SEEK_SET);
1723 fseek (ifp, 0, SEEK_END);
1724 fseek (ifp, ftell(ifp) >> 3 << 2, SEEK_SET);
1727 for (col=0; col < pwide; col++) {
1728 for (vbits -= tiff_bps; vbits < 0; vbits += bite) {
1730 for (i=0; i < bite; i+=8)
1731 bitbuf |= (unsigned) (fgetc(ifp) << i);
1733 val = bitbuf << (64-tiff_bps-vbits) >> (64-tiff_bps);
1734 RAW(row,col ^ (load_flags >> 6)) = val;
1735 if (load_flags & 1 && (col % 10) == 9 &&
1736 fgetc(ifp) && col < width+left_margin) derror();
1742 void CLASS nokia_load_raw()
1745 int rev, dwide, row, col, c;
1747 rev = 3 * (order == 0x4949);
1748 dwide = raw_width * 5 / 4;
1749 data = (uchar *) malloc (dwide*2);
1750 merror (data, "nokia_load_raw()");
1751 for (row=0; row < raw_height; row++) {
1752 if (fread (data+dwide, 1, dwide, ifp) < dwide) derror();
1753 FORC(dwide) data[c] = data[dwide+(c ^ rev)];
1754 for (dp=data, col=0; col < raw_width; dp+=5, col+=4)
1755 FORC4 RAW(row,col+c) = (dp[c] << 2) | (dp[4] >> (c << 1) & 3);
1761 unsigned CLASS pana_bits (int nbits)
1763 static uchar buf[0x4000];
1767 if (!nbits) return vbits=0;
1769 fread (buf+load_flags, 1, 0x4000-load_flags, ifp);
1770 fread (buf, 1, load_flags, ifp);
1772 vbits = (vbits - nbits) & 0x1ffff;
1773 byte = vbits >> 3 ^ 0x3ff0;
1774 return (buf[byte] | buf[byte+1] << 8) >> (vbits & 7) & ~(-1 << nbits);
1777 void CLASS panasonic_load_raw()
1779 int row, col, i, j, sh=0, pred[2], nonz[2];
1782 for (row=0; row < height; row++)
1783 for (col=0; col < raw_width; col++) {
1784 if ((i = col % 14) == 0)
1785 pred[0] = pred[1] = nonz[0] = nonz[1] = 0;
1786 if (i % 3 == 2) sh = 4 >> (3 - pana_bits(2));
1788 if ((j = pana_bits(8))) {
1789 if ((pred[i & 1] -= 0x80 << sh) < 0 || sh == 4)
1790 pred[i & 1] &= ~(-1 << sh);
1791 pred[i & 1] += j << sh;
1793 } else if ((nonz[i & 1] = pana_bits(8)) || i > 11)
1794 pred[i & 1] = nonz[i & 1] << 4 | pana_bits(4);
1795 if ((RAW(row,col) = pred[col & 1]) > 4098 && col < width) derror();
1799 void CLASS olympus_load_raw()
1802 int row, col, nbits, sign, low, high, i, c, w, n, nw;
1803 int acarry[2][3], *carry, pred, diff;
1807 FORC(2048 >> i) huff[++n] = (i+1) << 8 | i;
1808 fseek (ifp, 7, SEEK_CUR);
1810 for (row=0; row < height; row++) {
1811 memset (acarry, 0, sizeof acarry);
1812 for (col=0; col < raw_width; col++) {
1813 carry = acarry[col & 1];
1814 i = 2 * (carry[2] < 3);
1815 for (nbits=2+i; (ushort) carry[0] >> (nbits+i); nbits++);
1816 low = (sign = getbits(3)) & 3;
1817 sign = sign << 29 >> 31;
1818 if ((high = getbithuff(12,huff)) == 12)
1819 high = getbits(16-nbits) >> 1;
1820 carry[0] = (high << nbits) | getbits(nbits);
1821 diff = (carry[0] ^ sign) + carry[1];
1822 carry[1] = (diff*3 + carry[1]) >> 5;
1823 carry[2] = carry[0] > 16 ? 0 : carry[2]+1;
1824 if (col >= width) continue;
1825 if (row < 2 && col < 2) pred = 0;
1826 else if (row < 2) pred = RAW(row,col-2);
1827 else if (col < 2) pred = RAW(row-2,col);
1831 nw = RAW(row-2,col-2);
1832 if ((w < nw && nw < n) || (n < nw && nw < w)) {
1833 if (ABS(w-nw) > 32 || ABS(n-nw) > 32)
1835 else pred = (w + n) >> 1;
1836 } else pred = ABS(w-nw) > ABS(n-nw) ? w : n;
1838 if ((RAW(row,col) = pred + ((diff << 2) | low)) >> 12) derror();
1843 void CLASS minolta_rd175_load_raw()
1846 unsigned irow, box, row, col;
1848 for (irow=0; irow < 1481; irow++) {
1849 if (fread (pixel, 1, 768, ifp) < 768) derror();
1851 row = irow % 82 * 12 + ((box < 12) ? box | 1 : (box-12)*2);
1853 case 1477: case 1479: continue;
1854 case 1476: row = 984; break;
1855 case 1480: row = 985; break;
1856 case 1478: row = 985; box = 1;
1858 if ((box < 12) && (box & 1)) {
1859 for (col=0; col < 1533; col++, row ^= 1)
1860 if (col != 1) RAW(row,col) = (col+1) & 2 ?
1861 pixel[col/2-1] + pixel[col/2+1] : pixel[col/2] << 1;
1862 RAW(row,1) = pixel[1] << 1;
1863 RAW(row,1533) = pixel[765] << 1;
1865 for (col=row & 1; col < 1534; col+=2)
1866 RAW(row,col) = pixel[col/2] << 1;
1868 maximum = 0xff << 1;
1871 void CLASS quicktake_100_load_raw()
1873 uchar pixel[484][644];
1874 static const short gstep[16] =
1875 { -89,-60,-44,-32,-22,-15,-8,-2,2,8,15,22,32,44,60,89 };
1876 static const short rstep[6][4] =
1877 { { -3,-1,1,3 }, { -5,-1,1,5 }, { -8,-2,2,8 },
1878 { -13,-3,3,13 }, { -19,-4,4,19 }, { -28,-6,6,28 } };
1879 static const short curve[256] =
1880 { 0,1,2,3,4,5,6,7,8,9,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,
1881 28,29,30,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,53,
1882 54,55,56,57,58,59,60,61,62,63,64,65,66,67,68,69,70,71,72,74,75,76,77,78,
1883 79,80,81,82,83,84,86,88,90,92,94,97,99,101,103,105,107,110,112,114,116,
1884 118,120,123,125,127,129,131,134,136,138,140,142,144,147,149,151,153,155,
1885 158,160,162,164,166,168,171,173,175,177,179,181,184,186,188,190,192,195,
1886 197,199,201,203,205,208,210,212,214,216,218,221,223,226,230,235,239,244,
1887 248,252,257,261,265,270,274,278,283,287,291,296,300,305,309,313,318,322,
1888 326,331,335,339,344,348,352,357,361,365,370,374,379,383,387,392,396,400,
1889 405,409,413,418,422,426,431,435,440,444,448,453,457,461,466,470,474,479,
1890 483,487,492,496,500,508,519,531,542,553,564,575,587,598,609,620,631,643,
1891 654,665,676,687,698,710,721,732,743,754,766,777,788,799,810,822,833,844,
1892 855,866,878,889,900,911,922,933,945,956,967,978,989,1001,1012,1023 };
1893 int rb, row, col, sharp, val=0;
1896 memset (pixel, 0x80, sizeof pixel);
1897 for (row=2; row < height+2; row++) {
1898 for (col=2+(row & 1); col < width+2; col+=2) {
1899 val = ((pixel[row-1][col-1] + 2*pixel[row-1][col+1] +
1900 pixel[row][col-2]) >> 2) + gstep[getbits(4)];
1901 pixel[row][col] = val = LIM(val,0,255);
1903 pixel[row][col-2] = pixel[row+1][~row & 1] = val;
1905 pixel[row-1][col+1] = pixel[row-1][col+3] = val;
1907 pixel[row][col] = val;
1909 for (rb=0; rb < 2; rb++)
1910 for (row=2+rb; row < height+2; row+=2)
1911 for (col=3-(row & 1); col < width+2; col+=2) {
1912 if (row < 4 || col < 4) sharp = 2;
1914 val = ABS(pixel[row-2][col] - pixel[row][col-2])
1915 + ABS(pixel[row-2][col] - pixel[row-2][col-2])
1916 + ABS(pixel[row][col-2] - pixel[row-2][col-2]);
1917 sharp = val < 4 ? 0 : val < 8 ? 1 : val < 16 ? 2 :
1918 val < 32 ? 3 : val < 48 ? 4 : 5;
1920 val = ((pixel[row-2][col] + pixel[row][col-2]) >> 1)
1921 + rstep[sharp][getbits(2)];
1922 pixel[row][col] = val = LIM(val,0,255);
1923 if (row < 4) pixel[row-2][col+2] = val;
1924 if (col < 4) pixel[row+2][col-2] = val;
1926 for (row=2; row < height+2; row++)
1927 for (col=3-(row & 1); col < width+2; col+=2) {
1928 val = ((pixel[row][col-1] + (pixel[row][col] << 2) +
1929 pixel[row][col+1]) >> 1) - 0x100;
1930 pixel[row][col] = LIM(val,0,255);
1932 for (row=0; row < height; row++)
1933 for (col=0; col < width; col++)
1934 RAW(row,col) = curve[pixel[row+2][col+2]];
1938 #define radc_token(tree) ((signed char) getbithuff(8,huff[tree]))
1940 #define FORYX for (y=1; y < 3; y++) for (x=col+1; x >= col; x--)
1942 #define PREDICTOR (c ? (buf[c][y-1][x] + buf[c][y][x+1]) / 2 \
1943 : (buf[c][y-1][x+1] + 2*buf[c][y-1][x] + buf[c][y][x+1]) / 4)
1945 void CLASS kodak_radc_load_raw()
1947 static const char src[] = {
1948 1,1, 2,3, 3,4, 4,2, 5,7, 6,5, 7,6, 7,8,
1949 1,0, 2,1, 3,3, 4,4, 5,2, 6,7, 7,6, 8,5, 8,8,
1950 2,1, 2,3, 3,0, 3,2, 3,4, 4,6, 5,5, 6,7, 6,8,
1951 2,0, 2,1, 2,3, 3,2, 4,4, 5,6, 6,7, 7,5, 7,8,
1952 2,1, 2,4, 3,0, 3,2, 3,3, 4,7, 5,5, 6,6, 6,8,
1953 2,3, 3,1, 3,2, 3,4, 3,5, 3,6, 4,7, 5,0, 5,8,
1954 2,3, 2,6, 3,0, 3,1, 4,4, 4,5, 4,7, 5,2, 5,8,
1955 2,4, 2,7, 3,3, 3,6, 4,1, 4,2, 4,5, 5,0, 5,8,
1956 2,6, 3,1, 3,3, 3,5, 3,7, 3,8, 4,0, 5,2, 5,4,
1957 2,0, 2,1, 3,2, 3,3, 4,4, 4,5, 5,6, 5,7, 4,8,
1960 2,-17, 2,-5, 2,5, 2,17,
1961 2,-7, 2,2, 2,9, 2,18,
1962 2,-18, 2,-9, 2,-2, 2,7,
1963 2,-28, 2,28, 3,-49, 3,-9, 3,9, 4,49, 5,-79, 5,79,
1964 2,-1, 2,13, 2,26, 3,39, 4,-16, 5,55, 6,-37, 6,76,
1965 2,-26, 2,-13, 2,1, 3,-39, 4,16, 5,-55, 6,-76, 6,37
1967 ushort huff[19][256];
1968 int row, col, tree, nreps, rep, step, i, c, s, r, x, y, val;
1969 short last[3] = { 16,16,16 }, mul[3], buf[3][3][386], *bp;
1970 static const ushort pt[] =
1971 { 0,0, 1280,1344, 2320,3616, 3328,8000, 4095,16383, 65535,16383 };
1973 for (i=2; i < 12; i+=2)
1974 for (c=pt[i-2]; c <= pt[i]; c++)
1976 (c-pt[i-2]) / (pt[i]-pt[i-2]) * (pt[i+1]-pt[i-1]) + pt[i-1] + 0.5;
1977 for (s=i=0; i < sizeof src; i+=2)
1979 huff[0][s++] = src[i] << 8 | (uchar) src[i+1];
1980 s = kodak_cbpp == 243 ? 2 : 3;
1981 FORC(256) huff[18][c] = (8-s) << 8 | c >> s << s | 1 << (s-1);
1983 for ( bp=&buf[0][0][0],i=sizeof(buf)/sizeof(*bp); --i>=0; ++bp )
1985 for (row=0; row < height; row+=4) {
1986 FORC3 mul[c] = getbits(6);
1988 val = ((0x1000000/last[c] + 0x7ff) >> 12) * mul[c];
1989 s = val > 65564 ? 10:12;
1992 for (i=0; i < sizeof(buf[0])/sizeof(short); i++)
1993 for ( bp=&buf[c][0][0],i=sizeof(buf[0])/sizeof(*bp); --i>=0; ++bp )
1994 *bp = (*bp * val + x) >> s;
1996 for (r=0; r <= !c; r++) {
1997 buf[c][1][width/2] = buf[c][2][width/2] = mul[c] << 7;
1998 for (tree=1, col=width/2; col > 0; ) {
1999 if ((tree = radc_token(tree))) {
2002 FORYX buf[c][y][x] = (uchar) radc_token(18) * mul[c];
2004 FORYX buf[c][y][x] = radc_token(tree+10) * 16 + PREDICTOR;
2007 nreps = (col > 2) ? radc_token(9) + 1 : 1;
2008 for (rep=0; rep < 8 && rep < nreps && col > 0; rep++) {
2010 FORYX buf[c][y][x] = PREDICTOR;
2012 step = radc_token(10) << 4;
2013 FORYX buf[c][y][x] += step;
2016 } while (nreps == 9);
2018 for (y=0; y < 2; y++)
2019 for (x=0; x < width/2; x++) {
2020 val = (buf[c][y+1][x] << 4) / mul[c];
2021 if (val < 0) val = 0;
2022 if (c) RAW(row+y*2+c-1,x*2+2-c) = val;
2023 else RAW(row+r*2+y,x*2+y) = val;
2025 memcpy (buf[c][0]+!c, buf[c][2], sizeof buf[c][0]-2*!c);
2028 for (y=row; y < row+4; y++)
2029 for (x=0; x < width; x++)
2032 s = x+1 < width ? x+1 : x-1;
2033 val = (RAW(y,x)-2048)*2 + (RAW(y,r)+RAW(y,s))/2;
2034 if (val < 0) val = 0;
2038 for (i=0; i < height*width; i++)
2039 raw_image[i] = curve[raw_image[i]];
2047 void CLASS kodak_jpeg_load_raw() {}
2048 void CLASS lossy_dng_load_raw() {}
2052 fill_input_buffer (j_decompress_ptr cinfo)
2054 static uchar jpeg_buffer[4096];
2057 nbytes = fread (jpeg_buffer, 1, 4096, ifp);
2058 swab (jpeg_buffer, jpeg_buffer, nbytes);
2059 cinfo->src->next_input_byte = jpeg_buffer;
2060 cinfo->src->bytes_in_buffer = nbytes;
2064 void CLASS kodak_jpeg_load_raw()
2066 struct jpeg_decompress_struct cinfo;
2067 struct jpeg_error_mgr jerr;
2069 JSAMPLE (*pixel)[3];
2072 cinfo.err = jpeg_std_error (&jerr);
2073 jpeg_create_decompress (&cinfo);
2074 jpeg_stdio_src (&cinfo, ifp);
2075 cinfo.src->fill_input_buffer = fill_input_buffer;
2076 jpeg_read_header (&cinfo, TRUE);
2077 jpeg_start_decompress (&cinfo);
2078 if ((cinfo.output_width != width ) ||
2079 (cinfo.output_height*2 != height ) ||
2080 (cinfo.output_components != 3 )) {
2081 fprintf (stderr,_("%s: incorrect JPEG dimensions\n"), ifname);
2082 jpeg_destroy_decompress (&cinfo);
2083 longjmp (failure, 3);
2085 buf = (*cinfo.mem->alloc_sarray)
2086 ((j_common_ptr) &cinfo, JPOOL_IMAGE, width*3, 1);
2088 while (cinfo.output_scanline < cinfo.output_height) {
2089 row = cinfo.output_scanline * 2;
2090 jpeg_read_scanlines (&cinfo, buf, 1);
2091 pixel = (JSAMPLE (*)[3]) buf[0];
2092 for (col=0; col < width; col+=2) {
2093 RAW(row+0,col+0) = pixel[col+0][1] << 1;
2094 RAW(row+1,col+1) = pixel[col+1][1] << 1;
2095 RAW(row+0,col+1) = pixel[col][0] + pixel[col+1][0];
2096 RAW(row+1,col+0) = pixel[col][2] + pixel[col+1][2];
2099 jpeg_finish_decompress (&cinfo);
2100 jpeg_destroy_decompress (&cinfo);
2101 maximum = 0xff << 1;
2104 void CLASS lossy_dng_load_raw()
2106 struct jpeg_decompress_struct cinfo;
2107 struct jpeg_error_mgr jerr;
2109 JSAMPLE (*pixel)[3];
2110 unsigned sorder=order, ntags, opcode, deg, i, j, c;
2111 unsigned save=data_offset-4, trow=0, tcol=0, row, col;
2112 ushort curve[3][256];
2113 double coeff[9], tot;
2115 fseek (ifp, meta_offset, SEEK_SET);
2119 opcode = get4(); get4(); get4();
2121 { fseek (ifp, get4(), SEEK_CUR); continue; }
2122 fseek (ifp, 20, SEEK_CUR);
2123 if ((c = get4()) > 2) break;
2124 fseek (ifp, 12, SEEK_CUR);
2125 if ((deg = get4()) > 8) break;
2126 for (i=0; i <= deg && i < 9; i++)
2127 coeff[i] = getreal(12);
2128 for (i=0; i < 256; i++) {
2129 for (tot=j=0; j <= deg; j++)
2130 tot += coeff[j] * pow(i/255.0, j);
2131 curve[c][i] = tot*0xffff;
2135 cinfo.err = jpeg_std_error (&jerr);
2136 jpeg_create_decompress (&cinfo);
2137 while (trow < raw_height) {
2138 fseek (ifp, save+=4, SEEK_SET);
2139 if (tile_length < INT_MAX)
2140 fseek (ifp, get4(), SEEK_SET);
2141 jpeg_stdio_src (&cinfo, ifp);
2142 jpeg_read_header (&cinfo, TRUE);
2143 jpeg_start_decompress (&cinfo);
2144 buf = (*cinfo.mem->alloc_sarray)
2145 ((j_common_ptr) &cinfo, JPOOL_IMAGE, cinfo.output_width*3, 1);
2146 while (cinfo.output_scanline < cinfo.output_height &&
2147 (row = trow + cinfo.output_scanline) < height) {
2148 jpeg_read_scanlines (&cinfo, buf, 1);
2149 pixel = (JSAMPLE (*)[3]) buf[0];
2150 for (col=0; col < cinfo.output_width && tcol+col < width; col++) {
2151 FORC3 image[row*width+tcol+col][c] = curve[c][pixel[col][c]];
2154 jpeg_abort_decompress (&cinfo);
2155 if ((tcol += tile_width) >= raw_width)
2156 trow += tile_length + (tcol = 0);
2158 jpeg_destroy_decompress (&cinfo);
2163 void CLASS kodak_dc120_load_raw()
2165 static const int mul[4] = { 162, 192, 187, 92 };
2166 static const int add[4] = { 0, 636, 424, 212 };
2168 int row, shift, col;
2170 for (row=0; row < height; row++) {
2171 if (fread (pixel, 1, 848, ifp) < 848) derror();
2172 shift = row * mul[row & 3] + add[row & 3];
2173 for (col=0; col < width; col++)
2174 RAW(row,col) = (ushort) pixel[(col + shift) % 848];
2179 void CLASS eight_bit_load_raw()
2184 pixel = (uchar *) calloc (raw_width, sizeof *pixel);
2185 merror (pixel, "eight_bit_load_raw()");
2186 for (row=0; row < raw_height; row++) {
2187 if (fread (pixel, 1, raw_width, ifp) < raw_width) derror();
2188 for (col=0; col < raw_width; col++)
2189 RAW(row,col) = curve[pixel[col]];
2192 maximum = curve[0xff];
2195 void CLASS kodak_yrgb_load_raw()
2198 int row, col, y, cb, cr, rgb[3], c;
2200 pixel = (uchar *) calloc (raw_width, 3*sizeof *pixel);
2201 merror (pixel, "kodak_yrgb_load_raw()");
2202 for (row=0; row < height; row++) {
2204 if (fread (pixel, raw_width, 3, ifp) < 3) derror();
2205 for (col=0; col < raw_width; col++) {
2206 y = pixel[width*2*(row & 1) + col];
2207 cb = pixel[width + (col & -2)] - 128;
2208 cr = pixel[width + (col & -2)+1] - 128;
2209 rgb[1] = y-((cb + cr + 2) >> 2);
2210 rgb[2] = rgb[1] + cb;
2211 rgb[0] = rgb[1] + cr;
2212 FORC3 image[row*width+col][c] = curve[LIM(rgb[c],0,255)];
2216 maximum = curve[0xff];
2219 void CLASS kodak_262_load_raw()
2221 static const uchar kodak_tree[2][26] =
2222 { { 0,1,5,1,1,2,0,0,0,0,0,0,0,0,0,0, 0,1,2,3,4,5,6,7,8,9 },
2223 { 0,3,1,1,1,1,1,2,0,0,0,0,0,0,0,0, 0,1,2,3,4,5,6,7,8,9 } };
2226 int *strip, ns, c, row, col, chess, pi=0, pi1, pi2, pred, val;
2228 FORC(2) huff[c] = make_decoder (kodak_tree[c]);
2229 ns = (raw_height+63) >> 5;
2230 pixel = (uchar *) malloc (raw_width*32 + ns*4);
2231 merror (pixel, "kodak_262_load_raw()");
2232 strip = (int *) (pixel + raw_width*32);
2234 FORC(ns) strip[c] = get4();
2235 for (row=0; row < raw_height; row++) {
2236 if ((row & 31) == 0) {
2237 fseek (ifp, strip[row >> 5], SEEK_SET);
2241 for (col=0; col < raw_width; col++) {
2242 chess = (row + col) & 1;
2243 pi1 = chess ? pi-2 : pi-raw_width-1;
2244 pi2 = chess ? pi-2*raw_width : pi-raw_width+1;
2245 if (col <= chess) pi1 = -1;
2246 if (pi1 < 0) pi1 = pi2;
2247 if (pi2 < 0) pi2 = pi1;
2248 if (pi1 < 0 && col > 1) pi1 = pi2 = pi-2;
2249 pred = (pi1 < 0) ? 0 : (pixel[pi1] + pixel[pi2]) >> 1;
2250 pixel[pi] = val = pred + ljpeg_diff (huff[chess]);
2251 if (val >> 8) derror();
2252 val = curve[pixel[pi++]];
2257 FORC(2) free (huff[c]);
2260 int CLASS kodak_65000_decode (short *out, int bsize)
2265 int save, bits=0, i, j, len, diff;
2268 bsize = (bsize + 3) & -4;
2269 for (i=0; i < bsize; i+=2) {
2271 if ((blen[i ] = c & 15) > 12 ||
2272 (blen[i+1] = c >> 4) > 12 ) {
2273 fseek (ifp, save, SEEK_SET);
2274 for (i=0; i < bsize; i+=8) {
2275 read_shorts (raw, 6);
2276 out[i ] = raw[0] >> 12 << 8 | raw[2] >> 12 << 4 | raw[4] >> 12;
2277 out[i+1] = raw[1] >> 12 << 8 | raw[3] >> 12 << 4 | raw[5] >> 12;
2278 for (j=0; j < 6; j++)
2279 out[i+2+j] = raw[j] & 0xfff;
2284 if ((bsize & 7) == 4) {
2285 bitbuf = fgetc(ifp) << 8;
2286 bitbuf += fgetc(ifp);
2289 for (i=0; i < bsize; i++) {
2292 for (j=0; j < 32; j+=8)
2293 bitbuf += (INT64) fgetc(ifp) << (bits+(j^8));
2296 diff = bitbuf & (0xffff >> (16-len));
2299 if ((diff & (1 << (len-1))) == 0)
2300 diff -= (1 << len) - 1;
2306 void CLASS kodak_65000_load_raw()
2309 int row, col, len, pred[2], ret, i;
2311 for (row=0; row < height; row++)
2312 for (col=0; col < width; col+=256) {
2313 pred[0] = pred[1] = 0;
2314 len = MIN (256, width-col);
2315 ret = kodak_65000_decode (buf, len);
2316 for (i=0; i < len; i++)
2317 if ((RAW(row,col+i) = curve[ret ? buf[i] :
2318 (pred[i & 1] += buf[i])]) >> 12) derror();
2322 void CLASS kodak_ycbcr_load_raw()
2324 short buf[384], *bp;
2325 int row, col, len, c, i, j, k, y[2][2], cb, cr, rgb[3];
2328 for (row=0; row < height; row+=2)
2329 for (col=0; col < width; col+=128) {
2330 len = MIN (128, width-col);
2331 kodak_65000_decode (buf, len*3);
2332 y[0][1] = y[1][1] = cb = cr = 0;
2333 for (bp=buf, i=0; i < len; i+=2, bp+=2) {
2336 rgb[1] = -((cb + cr + 2) >> 2);
2337 rgb[2] = rgb[1] + cb;
2338 rgb[0] = rgb[1] + cr;
2339 for (j=0; j < 2; j++)
2340 for (k=0; k < 2; k++) {
2341 if ((y[j][k] = y[j][k^1] + *bp++) >> 10) derror();
2342 ip = image[(row+j)*width + col+i+k];
2343 FORC3 ip[c] = curve[LIM(y[j][k]+rgb[c], 0, 0xfff)];
2349 void CLASS kodak_rgb_load_raw()
2351 short buf[768], *bp;
2352 int row, col, len, c, i, rgb[3];
2353 ushort *ip=image[0];
2355 if (raw_image) free (raw_image);
2357 for (row=0; row < height; row++)
2358 for (col=0; col < width; col+=256) {
2359 len = MIN (256, width-col);
2360 kodak_65000_decode (buf, len*3);
2361 memset (rgb, 0, sizeof rgb);
2362 for (bp=buf, i=0; i < len; i++, ip+=4)
2363 FORC3 if ((ip[c] = rgb[c] += *bp++) >> 12) derror();
2367 void CLASS kodak_thumb_load_raw()
2370 colors = thumb_misc >> 5;
2371 for (row=0; row < height; row++)
2372 for (col=0; col < width; col++)
2373 read_shorts (image[row*width+col], colors);
2374 maximum = (1 << (thumb_misc & 31)) - 1;
2377 void CLASS sony_decrypt (unsigned *data, int len, int start, int key)
2379 static unsigned pad[128], p = 0;
2382 for (p=0; p < 4; p++)
2383 pad[p] = key = key * 48828125 + 1;
2384 pad[3] = pad[3] << 1 | (pad[0]^pad[2]) >> 31;
2385 for (p=4; p < 127; p++)
2386 pad[p] = (pad[p-4]^pad[p-2]) << 1 | (pad[p-3]^pad[p-1]) >> 31;
2387 for (p=0; p < 127; p++)
2388 pad[p] = htonl(pad[p]);
2391 *data++ ^= pad[p & 127] = pad[(p+1) & 127] ^ pad[(p+65) & 127];
2396 void CLASS sony_load_raw()
2400 unsigned i, key, row, col;
2402 fseek (ifp, 200896, SEEK_SET);
2403 fseek (ifp, (unsigned) fgetc(ifp)*4 - 1, SEEK_CUR);
2406 fseek (ifp, 164600, SEEK_SET);
2407 fread (head, 1, 40, ifp);
2408 sony_decrypt ((unsigned int *) head, 10, 1, key);
2409 for (i=26; i-- > 22; )
2410 key = key << 8 | head[i];
2411 fseek (ifp, data_offset, SEEK_SET);
2412 for (row=0; row < raw_height; row++) {
2413 pixel = raw_image + row*raw_width;
2414 if (fread (pixel, 2, raw_width, ifp) < raw_width) derror();
2415 sony_decrypt ((unsigned int *) pixel, raw_width/2, !row, key);
2416 for (col=0; col < raw_width; col++)
2417 if ((pixel[col] = ntohs(pixel[col])) >> 14) derror();
2422 void CLASS sony_arw_load_raw()
2425 static const ushort tab[18] =
2426 { 0xf11,0xf10,0xe0f,0xd0e,0xc0d,0xb0c,0xa0b,0x90a,0x809,
2427 0x708,0x607,0x506,0x405,0x304,0x303,0x300,0x202,0x201 };
2428 int i, c, n, col, row, len, diff, sum=0;
2430 for (n=i=0; i < 18; i++)
2431 FORC(32768 >> (tab[i] >> 8)) huff[n++] = tab[i];
2433 for (col = raw_width; col--; )
2434 for (row=0; row < raw_height+1; row+=2) {
2435 if (row == raw_height) row = 1;
2436 len = getbithuff(15,huff);
2437 diff = getbits(len);
2438 if ((diff & (1 << (len-1))) == 0)
2439 diff -= (1 << len) - 1;
2440 if ((sum += diff) >> 12) derror();
2441 if (row < height) RAW(row,col) = sum;
2445 void CLASS sony_arw2_load_raw()
2449 int row, col, val, max, min, imax, imin, sh, bit, i;
2451 data = (uchar *) malloc (raw_width);
2452 merror (data, "sony_arw2_load_raw()");
2453 for (row=0; row < height; row++) {
2454 fread (data, 1, raw_width, ifp);
2455 for (dp=data, col=0; col < raw_width-30; dp+=16) {
2456 max = 0x7ff & (val = sget4(dp));
2457 min = 0x7ff & val >> 11;
2458 imax = 0x0f & val >> 22;
2459 imin = 0x0f & val >> 26;
2460 for (sh=0; sh < 4 && 0x80 << sh <= max-min; sh++);
2461 for (bit=30, i=0; i < 16; i++)
2462 if (i == imax) pix[i] = max;
2463 else if (i == imin) pix[i] = min;
2465 pix[i] = ((sget2(dp+(bit >> 3)) >> (bit & 7) & 0x7f) << sh) + min;
2466 if (pix[i] > 0x7ff) pix[i] = 0x7ff;
2469 for (i=0; i < 16; i++, col+=2)
2470 RAW(row,col) = curve[pix[i] << 1] >> 2;
2471 col -= col & 1 ? 1:31;
2477 #define HOLE(row) ((holes >> (((row) - raw_height) & 7)) & 1)
2479 /* Kudos to Rich Taylor for figuring out SMaL's compression algorithm. */
2480 void CLASS smal_decode_segment (unsigned seg[2][2], int holes)
2482 uchar hist[3][13] = {
2483 { 7, 7, 0, 0, 63, 55, 47, 39, 31, 23, 15, 7, 0 },
2484 { 7, 7, 0, 0, 63, 55, 47, 39, 31, 23, 15, 7, 0 },
2485 { 3, 3, 0, 0, 63, 47, 31, 15, 0 } };
2486 int low, high=0xff, carry=0, nbits=8;
2487 int pix, s, count, bin, next, i, sym[3];
2488 uchar diff, pred[]={0,0};
2489 ushort data=0, range=0;
2491 fseek (ifp, seg[0][1]+1, SEEK_SET);
2493 for (pix=seg[0][0]; pix < seg[1][0]; pix++) {
2494 for (s=0; s < 3; s++) {
2495 data = data << nbits | getbits(nbits);
2497 carry = (nbits += carry+1) < 1 ? nbits-1 : 0;
2498 while (--nbits >= 0)
2499 if ((data >> nbits & 0xff) == 0xff) break;
2501 data = ((data & ((1 << (nbits-1)) - 1)) << 1) |
2502 ((data + (((data & (1 << (nbits-1)))) << 1)) & (-1 << nbits));
2507 count = ((((data-range+1) & 0xffff) << 2) - 1) / (high >> 4);
2508 for (bin=0; hist[s][bin+5] > count; bin++);
2509 low = hist[s][bin+5] * (high >> 4) >> 2;
2510 if (bin) high = hist[s][bin+4] * (high >> 4) >> 2;
2512 for (nbits=0; high << nbits < 128; nbits++);
2513 range = (range+low) << nbits;
2516 if (++hist[s][2] > hist[s][3]) {
2517 next = (next+1) & hist[s][0];
2518 hist[s][3] = (hist[s][next+4] - hist[s][next+5]) >> 2;
2521 if (hist[s][hist[s][1]+4] - hist[s][hist[s][1]+5] > 1) {
2522 if (bin < hist[s][1])
2523 for (i=bin; i < hist[s][1]; i++) hist[s][i+5]--;
2524 else if (next <= bin)
2525 for (i=hist[s][1]; i < bin; i++) hist[s][i+5]++;
2530 diff = sym[2] << 5 | sym[1] << 2 | (sym[0] & 3);
2532 diff = diff ? -diff : 0x80;
2533 if (ftell(ifp) + 12 >= seg[1][1])
2535 raw_image[pix] = pred[pix & 1] += diff;
2536 if (!(pix & 1) && HOLE(pix / raw_width)) pix += 2;
2541 void CLASS smal_v6_load_raw()
2545 fseek (ifp, 16, SEEK_SET);
2548 seg[1][0] = raw_width * raw_height;
2549 seg[1][1] = INT_MAX;
2550 smal_decode_segment (seg, 0);
2553 int CLASS median4 (int *p)
2555 int min, max, sum, i;
2557 min = max = sum = p[0];
2558 for (i=1; i < 4; i++) {
2560 if (min > p[i]) min = p[i];
2561 if (max < p[i]) max = p[i];
2563 return (sum - min - max) >> 1;
2566 void CLASS fill_holes (int holes)
2568 int row, col, val[4];
2570 for (row=2; row < height-2; row++) {
2571 if (!HOLE(row)) continue;
2572 for (col=1; col < width-1; col+=4) {
2573 val[0] = RAW(row-1,col-1);
2574 val[1] = RAW(row-1,col+1);
2575 val[2] = RAW(row+1,col-1);
2576 val[3] = RAW(row+1,col+1);
2577 RAW(row,col) = median4(val);
2579 for (col=2; col < width-2; col+=4)
2580 if (HOLE(row-2) || HOLE(row+2))
2581 RAW(row,col) = (RAW(row,col-2) + RAW(row,col+2)) >> 1;
2583 val[0] = RAW(row,col-2);
2584 val[1] = RAW(row,col+2);
2585 val[2] = RAW(row-2,col);
2586 val[3] = RAW(row+2,col);
2587 RAW(row,col) = median4(val);
2592 void CLASS smal_v9_load_raw()
2594 unsigned seg[256][2], offset, nseg, holes, i;
2596 fseek (ifp, 67, SEEK_SET);
2599 fseek (ifp, offset, SEEK_SET);
2600 for (i=0; i < nseg*2; i++)
2601 seg[0][i] = get4() + data_offset*(i & 1);
2602 fseek (ifp, 78, SEEK_SET);
2604 fseek (ifp, 88, SEEK_SET);
2605 seg[nseg][0] = raw_height * raw_width;
2606 seg[nseg][1] = get4() + data_offset;
2607 for (i=0; i < nseg; i++)
2608 smal_decode_segment (seg+i, holes);
2609 if (holes) fill_holes (holes);
2612 void CLASS redcine_load_raw()
2623 in = jas_stream_fopen (ifname, "rb");
2624 jas_stream_seek (in, data_offset+20, SEEK_SET);
2625 jimg = jas_image_decode (in, -1, 0);
2626 if (!jimg) longjmp (failure, 3);
2627 jmat = jas_matrix_create (height/2, width/2);
2628 merror (jmat, "redcine_load_raw()");
2629 img = (ushort *) calloc ((height+2)*(width+2), 2);
2630 merror (img, "redcine_load_raw()");
2632 jas_image_readcmpt (jimg, c, 0, 0, width/2, height/2, jmat);
2633 data = jas_matrix_getref (jmat, 0, 0);
2634 for (row = c >> 1; row < height; row+=2)
2635 for (col = c & 1; col < width; col+=2)
2636 img[(row+1)*(width+2)+col+1] = data[(row/2)*(width/2)+col/2];
2638 for (col=1; col <= width; col++) {
2639 img[col] = img[2*(width+2)+col];
2640 img[(height+1)*(width+2)+col] = img[(height-1)*(width+2)+col];
2642 for (row=0; row < height+2; row++) {
2643 img[row*(width+2)] = img[row*(width+2)+2];
2644 img[(row+1)*(width+2)-1] = img[(row+1)*(width+2)-3];
2646 for (row=1; row <= height; row++) {
2647 pix = img + row*(width+2) + (col = 1 + (FC(row,1) & 1));
2648 for ( ; col <= width; col+=2, pix+=2) {
2649 c = (((pix[0] - 0x800) << 3) +
2650 pix[-(width+2)] + pix[width+2] + pix[-1] + pix[1]) >> 2;
2651 pix[0] = LIM(c,0,4095);
2654 for (row=0; row < height; row++)
2655 for (col=0; col < width; col++)
2656 RAW(row,col) = curve[img[(row+1)*(width+2)+col+1]];
2658 jas_matrix_destroy (jmat);
2659 jas_image_destroy (jimg);
2660 jas_stream_close (in);
2664 /* RESTRICTED code starts here */
2666 void CLASS foveon_decoder (unsigned size, unsigned code)
2668 static unsigned huff[1024];
2673 for (i=0; i < size; i++)
2675 memset (first_decode, 0, sizeof first_decode);
2676 free_decode = first_decode;
2678 cur = free_decode++;
2679 if (free_decode > first_decode+2048) {
2680 fprintf (stderr,_("%s: decoder table overflow\n"), ifname);
2681 longjmp (failure, 2);
2684 for (i=0; i < size; i++)
2685 if (huff[i] == code) {
2689 if ((len = code >> 27) > 26) return;
2690 code = (len+1) << 27 | (code & 0x3ffffff) << 1;
2692 cur->branch[0] = free_decode;
2693 foveon_decoder (size, code);
2694 cur->branch[1] = free_decode;
2695 foveon_decoder (size, code+1);
2698 void CLASS foveon_thumb()
2700 unsigned bwide, row, col, bitbuf=0, bit=1, c, i;
2702 struct decode *dindex;
2706 fprintf (ofp, "P6\n%d %d\n255\n", thumb_width, thumb_height);
2708 if (bwide < thumb_width*3) return;
2709 buf = (char *) malloc (bwide);
2710 merror (buf, "foveon_thumb()");
2711 for (row=0; row < thumb_height; row++) {
2712 fread (buf, 1, bwide, ifp);
2713 fwrite (buf, 3, thumb_width, ofp);
2718 foveon_decoder (256, 0);
2720 for (row=0; row < thumb_height; row++) {
2721 memset (pred, 0, sizeof pred);
2723 for (bit=col=0; col < thumb_width; col++)
2725 for (dindex=first_decode; dindex->branch[0]; ) {
2726 if ((bit = (bit-1) & 31) == 31)
2727 for (i=0; i < 4; i++)
2728 bitbuf = (bitbuf << 8) + fgetc(ifp);
2729 dindex = dindex->branch[bitbuf >> bit & 1];
2731 pred[c] += dindex->leaf;
2732 fputc (pred[c], ofp);
2737 void CLASS foveon_sd_load_raw()
2739 struct decode *dindex;
2742 int pred[3], row, col, bit=-1, c, i;
2744 read_shorts ((ushort *) diff, 1024);
2745 if (!load_flags) foveon_decoder (1024, 0);
2747 for (row=0; row < height; row++) {
2748 memset (pred, 0, sizeof pred);
2749 if (!bit && !load_flags && atoi(model+2) < 14) get4();
2750 for (col=bit=0; col < width; col++) {
2753 FORC3 pred[2-c] += diff[bitbuf >> c*10 & 0x3ff];
2756 for (dindex=first_decode; dindex->branch[0]; ) {
2757 if ((bit = (bit-1) & 31) == 31)
2758 for (i=0; i < 4; i++)
2759 bitbuf = (bitbuf << 8) + fgetc(ifp);
2760 dindex = dindex->branch[bitbuf >> bit & 1];
2762 pred[c] += diff[dindex->leaf];
2763 if (pred[c] >> 16 && ~pred[c] >> 16) derror();
2765 FORC3 image[row*width+col][c] = pred[c];
2770 void CLASS foveon_huff (ushort *huff)
2772 int i, j, clen, code;
2775 for (i=0; i < 13; i++) {
2778 for (j=0; j < 256 >> clen; )
2779 huff[code+ ++j] = clen << 8 | i;
2784 void CLASS foveon_dp_load_raw()
2786 unsigned c, roff[4], row, col, diff;
2787 ushort huff[258], vpred[2][2], hpred[2];
2789 fseek (ifp, 8, SEEK_CUR);
2792 FORC3 roff[c+1] = -(-(roff[c] + get4()) & -16);
2794 fseek (ifp, data_offset+roff[c], SEEK_SET);
2796 vpred[0][0] = vpred[0][1] = vpred[1][0] = vpred[1][1] = 512;
2797 for (row=0; row < height; row++) {
2798 for (col=0; col < width; col++) {
2799 diff = ljpeg_diff(huff);
2800 if (col < 2) hpred[col] = vpred[row & 1][col] += diff;
2801 else hpred[col & 1] += diff;
2802 image[row*width+col][c] = hpred[col & 1];
2808 void CLASS foveon_load_camf()
2810 unsigned type, wide, high, i, j, row, col, diff;
2811 ushort huff[258], vpred[2][2] = {{512,512},{512,512}}, hpred[2];
2813 fseek (ifp, meta_offset, SEEK_SET);
2814 type = get4(); get4(); get4();
2818 fread (meta_data, 1, meta_length, ifp);
2819 for (i=0; i < meta_length; i++) {
2820 high = (high * 1597 + 51749) % 244944;
2821 wide = high * (INT64) 301593171 >> 24;
2822 meta_data[i] ^= ((((high << 8) - wide) >> 1) + wide) >> 17;
2824 } else if (type == 4) {
2826 meta_data = (char *) malloc (meta_length = wide*high*3/2);
2827 merror (meta_data, "foveon_load_camf()");
2831 for (j=row=0; row < high; row++) {
2832 for (col=0; col < wide; col++) {
2833 diff = ljpeg_diff(huff);
2834 if (col < 2) hpred[col] = vpred[row & 1][col] += diff;
2835 else hpred[col & 1] += diff;
2837 meta_data[j++] = hpred[0] >> 4;
2838 meta_data[j++] = hpred[0] << 4 | hpred[1] >> 8;
2839 meta_data[j++] = hpred[1];
2844 fprintf (stderr,_("%s has unknown CAMF type %d.\n"), ifname, type);
2847 const char * CLASS foveon_camf_param (const char *block, const char *param)
2850 char *pos, *cp, *dp;
2852 for (idx=0; idx < meta_length; idx += sget4(pos+8)) {
2853 pos = meta_data + idx;
2854 if (strncmp (pos, "CMb", 3)) break;
2855 if (pos[3] != 'P') continue;
2856 if (strcmp (block, pos+sget4(pos+12))) continue;
2857 cp = pos + sget4(pos+16);
2859 dp = pos + sget4(cp+4);
2862 if (!strcmp (param, dp+sget4(cp)))
2863 return dp+sget4(cp+4);
2869 void * CLASS foveon_camf_matrix (unsigned dim[3], const char *name)
2871 unsigned i, idx, type, ndim, size, *mat;
2872 char *pos, *cp, *dp;
2875 for (idx=0; idx < meta_length; idx += sget4(pos+8)) {
2876 pos = meta_data + idx;
2877 if (strncmp (pos, "CMb", 3)) break;
2878 if (pos[3] != 'M') continue;
2879 if (strcmp (name, pos+sget4(pos+12))) continue;
2880 dim[0] = dim[1] = dim[2] = 1;
2881 cp = pos + sget4(pos+16);
2883 if ((ndim = sget4(cp+4)) > 3) break;
2884 dp = pos + sget4(cp+8);
2885 for (i=ndim; i--; ) {
2889 if ((dsize = (double) dim[0]*dim[1]*dim[2]) > meta_length/4) break;
2890 mat = (unsigned *) malloc ((size = dsize) * 4);
2891 merror (mat, "foveon_camf_matrix()");
2892 for (i=0; i < size; i++)
2893 if (type && type != 6)
2894 mat[i] = sget4(dp + i*4);
2896 mat[i] = sget4(dp + i*2) & 0xffff;
2899 fprintf (stderr,_("%s: \"%s\" matrix not found!\n"), ifname, name);
2903 int CLASS foveon_fixed (void *ptr, int size, const char *name)
2908 if (!name) return 0;
2909 dp = foveon_camf_matrix (dim, name);
2911 memcpy (ptr, dp, size*4);
2916 float CLASS foveon_avg (short *pix, int range[2], float cfilt)
2919 float val, min=FLT_MAX, max=-FLT_MAX, sum=0;
2921 for (i=range[0]; i <= range[1]; i++) {
2922 sum += val = pix[i*4] + (pix[i*4]-pix[(i-1)*4]) * cfilt;
2923 if (min > val) min = val;
2924 if (max < val) max = val;
2926 if (range[1] - range[0] == 1) return sum/2;
2927 return (sum - min - max) / (range[1] - range[0] - 1);
2930 short * CLASS foveon_make_curve (double max, double mul, double filt)
2936 if (!filt) filt = 0.8;
2937 size = 4*M_PI*max / filt;
2938 if (size == UINT_MAX) size--;
2939 curve = (short *) calloc (size+1, sizeof *curve);
2940 merror (curve, "foveon_make_curve()");
2942 for (i=0; i < size; i++) {
2944 curve[i+1] = (cos(x)+1)/2 * tanh(i*filt/mul) * mul + 0.5;
2949 void CLASS foveon_make_curves
2950 (short **curvep, float dq[3], float div[3], float filt)
2952 double mul[3], max=0;
2955 FORC3 mul[c] = dq[c]/div[c];
2956 FORC3 if (max < mul[c]) max = mul[c];
2957 FORC3 curvep[c] = foveon_make_curve (max, mul[c], filt);
2960 int CLASS foveon_apply_curve (short *curve, int i)
2962 if (abs(i) >= curve[0]) return 0;
2963 return i < 0 ? -curve[1-i] : curve[1+i];
2966 #define image ((short (*)[4]) image)
2968 void CLASS foveon_interpolate()
2970 static const short hood[] = { -1,-1, -1,0, -1,1, 0,-1, 0,1, 1,-1, 1,0, 1,1 };
2971 short *pix, prev[3], *curve[8], (*shrink)[3];
2972 float cfilt=0, ddft[3][3][2], ppm[3][3][3];
2973 float cam_xyz[3][3], correct[3][3], last[3][3], trans[3][3];
2974 float chroma_dq[3], color_dq[3], diag[3][3], div[3];
2975 float (*black)[3], (*sgain)[3], (*sgrow)[3];
2976 float fsum[3], val, frow, num;
2977 int row, col, c, i, j, diff, sgx, irow, sum, min, max, limit;
2978 int dscr[2][2], dstb[4], (*smrow[7])[3], total[4], ipix[3];
2979 int work[3][3], smlast, smred, smred_p=0, dev[3];
2980 int satlev[3], keep[4], active[4];
2981 unsigned dim[3], *badpix;
2982 double dsum=0, trsum[3];
2987 fprintf (stderr,_("Foveon interpolation...\n"));
2990 foveon_fixed (dscr, 4, "DarkShieldColRange");
2991 foveon_fixed (ppm[0][0], 27, "PostPolyMatrix");
2992 foveon_fixed (satlev, 3, "SaturationLevel");
2993 foveon_fixed (keep, 4, "KeepImageArea");
2994 foveon_fixed (active, 4, "ActiveImageArea");
2995 foveon_fixed (chroma_dq, 3, "ChromaDQ");
2996 foveon_fixed (color_dq, 3,
2997 foveon_camf_param ("IncludeBlocks", "ColorDQ") ?
2998 "ColorDQ" : "ColorDQCamRGB");
2999 if (foveon_camf_param ("IncludeBlocks", "ColumnFilter"))
3000 foveon_fixed (&cfilt, 1, "ColumnFilter");
3002 memset (ddft, 0, sizeof ddft);
3003 if (!foveon_camf_param ("IncludeBlocks", "DarkDrift")
3004 || !foveon_fixed (ddft[1][0], 12, "DarkDrift"))
3005 for (i=0; i < 2; i++) {
3006 foveon_fixed (dstb, 4, i ? "DarkShieldBottom":"DarkShieldTop");
3007 for (row = dstb[1]; row <= dstb[3]; row++)
3008 for (col = dstb[0]; col <= dstb[2]; col++)
3009 FORC3 ddft[i+1][c][1] += (short) image[row*width+col][c];
3010 FORC3 ddft[i+1][c][1] /= (dstb[3]-dstb[1]+1) * (dstb[2]-dstb[0]+1);
3013 if (!(cp = foveon_camf_param ("WhiteBalanceIlluminants", model2)))
3014 { fprintf (stderr,_("%s: Invalid white balance \"%s\"\n"), ifname, model2);
3016 foveon_fixed (cam_xyz, 9, cp);
3017 foveon_fixed (correct, 9,
3018 foveon_camf_param ("WhiteBalanceCorrections", model2));
3019 memset (last, 0, sizeof last);
3020 for (i=0; i < 3; i++)
3021 for (j=0; j < 3; j++)
3022 FORC3 last[i][j] += correct[i][c] * cam_xyz[c][j];
3024 #define LAST(x,y) last[(i+x)%3][(c+y)%3]
3025 for (i=0; i < 3; i++)
3026 FORC3 diag[c][i] = LAST(1,1)*LAST(2,2) - LAST(1,2)*LAST(2,1);
3028 FORC3 div[c] = diag[c][0]*0.3127 + diag[c][1]*0.329 + diag[c][2]*0.3583;
3029 sprintf (str, "%sRGBNeutral", model2);
3030 if (foveon_camf_param ("IncludeBlocks", str))
3031 foveon_fixed (div, 3, str);
3033 FORC3 if (num < div[c]) num = div[c];
3034 FORC3 div[c] /= num;
3036 memset (trans, 0, sizeof trans);
3037 for (i=0; i < 3; i++)
3038 for (j=0; j < 3; j++)
3039 FORC3 trans[i][j] += rgb_cam[i][c] * last[c][j] * div[j];
3040 FORC3 trsum[c] = trans[c][0] + trans[c][1] + trans[c][2];
3041 dsum = (6*trsum[0] + 11*trsum[1] + 3*trsum[2]) / 20;
3042 for (i=0; i < 3; i++)
3043 FORC3 last[i][c] = trans[i][c] * dsum / trsum[i];
3044 memset (trans, 0, sizeof trans);
3045 for (i=0; i < 3; i++)
3046 for (j=0; j < 3; j++)
3047 FORC3 trans[i][j] += (i==c ? 32 : -1) * last[c][j] / 30;
3049 foveon_make_curves (curve, color_dq, div, cfilt);
3050 FORC3 chroma_dq[c] /= 3;
3051 foveon_make_curves (curve+3, chroma_dq, div, cfilt);
3052 FORC3 dsum += chroma_dq[c] / div[c];
3053 curve[6] = foveon_make_curve (dsum, dsum, cfilt);
3054 curve[7] = foveon_make_curve (dsum*2, dsum*2, cfilt);
3056 sgain = (float (*)[3]) foveon_camf_matrix (dim, "SpatialGain");
3058 sgrow = (float (*)[3]) calloc (dim[1], sizeof *sgrow);
3059 sgx = (width + dim[1]-2) / (dim[1]-1);
3061 black = (float (*)[3]) calloc (height, sizeof *black);
3062 for (row=0; row < height; row++) {
3063 float *dp0 = &ddft[0][0][0];
3064 float *dp1 = &ddft[1][0][0];
3065 float *dp2 = &ddft[2][0][0];
3066 for( i=6; --i>=0; ++dp0,++dp1,++dp2 )
3067 *dp0 = *dp1 + row / (height-1.0) * (*dp2 - *dp1);
3068 pix = image[row*width];
3069 FORC3 black[row][c] =
3070 ( foveon_avg (image[row*width]+c, dscr[0], cfilt) +
3071 foveon_avg (image[row*width]+c, dscr[1], cfilt) * 3
3072 - ddft[0][c][0] ) / 4 - ddft[0][c][1];
3074 memcpy (black, black+8, sizeof *black*8);
3075 memcpy (black+height-11, black+height-22, 11*sizeof *black);
3076 memcpy (last, black, sizeof last);
3078 for (row=1; row < height-1; row++) {
3079 FORC3 if (last[1][c] > last[0][c]) {
3080 if (last[1][c] > last[2][c])
3081 black[row][c] = (last[0][c] > last[2][c]) ? last[0][c]:last[2][c];
3083 if (last[1][c] < last[2][c])
3084 black[row][c] = (last[0][c] < last[2][c]) ? last[0][c]:last[2][c];
3085 memmove (last, last+1, 2*sizeof last[0]);
3086 memcpy (last[2], black[row+1], sizeof last[2]);
3088 FORC3 black[row][c] = (last[0][c] + last[1][c])/2;
3089 FORC3 black[0][c] = (black[1][c] + black[3][c])/2;
3091 val = 1 - exp(-1/24.0);
3092 memcpy (fsum, black, sizeof fsum);
3093 for (row=1; row < height; row++)
3094 FORC3 fsum[c] += black[row][c] =
3095 (black[row][c] - black[row-1][c])*val + black[row-1][c];
3096 memcpy (last[0], black[height-1], sizeof last[0]);
3097 FORC3 fsum[c] /= height;
3098 for (row = height; row--; )
3099 FORC3 last[0][c] = black[row][c] =
3100 (black[row][c] - fsum[c] - last[0][c])*val + last[0][c];
3102 memset (total, 0, sizeof total);
3103 for (row=2; row < height; row+=4)
3104 for (col=2; col < width; col+=4) {
3105 FORC3 total[c] += (short) image[row*width+col][c];
3108 for (row=0; row < height; row++)
3109 FORC3 black[row][c] += fsum[c]/2 + total[c]/(total[3]*100.0);
3111 for (row=0; row < height; row++) {
3112 float *dp0 = &ddft[0][0][0];
3113 float *dp1 = &ddft[1][0][0];
3114 float *dp2 = &ddft[2][0][0];
3115 for( i=6; --i>=0; ++dp0,++dp1,++dp2 )
3116 *dp0 = *dp1 + row / (height-1.0) * (*dp2 - *dp1);
3117 pix = image[row*width];
3118 memcpy (prev, pix, sizeof prev);
3119 frow = row / (height-1.0) * (dim[2]-1);
3120 if ((irow = frow) == dim[2]-1) irow--;
3122 for (i=0; i < dim[1]; i++)
3123 FORC3 sgrow[i][c] = sgain[ irow *dim[1]+i][c] * (1-frow) +
3124 sgain[(irow+1)*dim[1]+i][c] * frow;
3125 for (col=0; col < width; col++) {
3127 diff = pix[c] - prev[c];
3129 ipix[c] = pix[c] + floor ((diff + (diff*diff >> 14)) * cfilt
3130 - ddft[0][c][1] - ddft[0][c][0] * ((float) col/width - 0.5)
3134 work[0][c] = ipix[c] * ipix[c] >> 14;
3135 work[2][c] = ipix[c] * work[0][c] >> 14;
3136 work[1][2-c] = ipix[(c+1) % 3] * ipix[(c+2) % 3] >> 14;
3139 for (val=i=0; i < 3; i++)
3140 for ( j=0; j < 3; j++)
3141 val += ppm[c][i][j] * work[i][j];
3142 ipix[c] = floor ((ipix[c] + floor(val)) *
3143 ( sgrow[col/sgx ][c] * (sgx - col%sgx) +
3144 sgrow[col/sgx+1][c] * (col%sgx) ) / sgx / div[c]);
3145 if (ipix[c] > 32000) ipix[c] = 32000;
3155 if ((badpix = (unsigned int *) foveon_camf_matrix (dim, "BadPixels"))) {
3156 for (i=0; i < dim[0]; i++) {
3157 col = (badpix[i] >> 8 & 0xfff) - keep[0];
3158 row = (badpix[i] >> 20 ) - keep[1];
3159 if ((unsigned)(row-1) > height-3 || (unsigned)(col-1) > width-3)
3161 memset (fsum, 0, sizeof fsum);
3162 for (sum=j=0; j < 8; j++)
3163 if (badpix[i] & (1 << j)) {
3164 FORC3 fsum[c] += (short)
3165 image[(row+hood[j*2])*width+col+hood[j*2+1]][c];
3168 if (sum) FORC3 image[row*width+col][c] = fsum[c]/sum;
3173 /* Array for 5x5 Gaussian averaging of red values */
3174 smrow[6] = (int (*)[3]) calloc (width*5, sizeof **smrow);
3175 merror (smrow[6], "foveon_interpolate()");
3176 for (i=0; i < 5; i++)
3177 smrow[i] = smrow[6] + i*width;
3179 /* Sharpen the reds against these Gaussian averages */
3180 for (smlast=-1, row=2; row < height-2; row++) {
3181 while (smlast < row+2) {
3182 for (i=0; i < 6; i++)
3183 smrow[(i+5) % 6] = smrow[i];
3184 pix = image[++smlast*width+2];
3185 for (col=2; col < width-2; col++) {
3187 (pix[0]*6 + (pix[-4]+pix[4])*4 + pix[-8]+pix[8] + 8) >> 4;
3191 pix = image[row*width+2];
3192 for (col=2; col < width-2; col++) {
3193 smred = ( 6 * smrow[2][col][0]
3194 + 4 * (smrow[1][col][0] + smrow[3][col][0])
3195 + smrow[0][col][0] + smrow[4][col][0] + 8 ) >> 4;
3198 i = pix[0] + ((pix[0] - ((smred*7 + smred_p) >> 3)) >> 3);
3199 if (i > 32000) i = 32000;
3206 /* Adjust the brighter pixels for better linearity */
3209 i = satlev[c] / div[c];
3210 if (min > i) min = i;
3212 limit = min * 9 >> 4;
3213 for (pix=image[0]; pix < image[height*width]; pix+=4) {
3214 if (pix[0] <= limit || pix[1] <= limit || pix[2] <= limit)
3217 for (c=1; c < 3; c++) {
3218 if (min > pix[c]) min = pix[c];
3219 if (max < pix[c]) max = pix[c];
3221 if (min >= limit*2) {
3222 pix[0] = pix[1] = pix[2] = max;
3224 i = 0x4000 - ((min - limit) << 14) / limit;
3225 i = 0x4000 - (i*i >> 14);
3227 FORC3 pix[c] += (max - pix[c]) * i >> 14;
3231 Because photons that miss one detector often hit another,
3232 the sum R+G+B is much less noisy than the individual colors.
3233 So smooth the hues without smoothing the total.
3235 for (smlast=-1, row=2; row < height-2; row++) {
3236 while (smlast < row+2) {
3237 for (i=0; i < 6; i++)
3238 smrow[(i+5) % 6] = smrow[i];
3239 pix = image[++smlast*width+2];
3240 for (col=2; col < width-2; col++) {
3241 FORC3 smrow[4][col][c] = (pix[c-4]+2*pix[c]+pix[c+4]+2) >> 2;
3245 pix = image[row*width+2];
3246 for (col=2; col < width-2; col++) {
3247 FORC3 dev[c] = -foveon_apply_curve (curve[7], pix[c] -
3248 ((smrow[1][col][c] + 2*smrow[2][col][c] + smrow[3][col][c]) >> 2));
3249 sum = (dev[0] + dev[1] + dev[2]) >> 3;
3250 FORC3 pix[c] += dev[c] - sum;
3254 for (smlast=-1, row=2; row < height-2; row++) {
3255 while (smlast < row+2) {
3256 for (i=0; i < 6; i++)
3257 smrow[(i+5) % 6] = smrow[i];
3258 pix = image[++smlast*width+2];
3259 for (col=2; col < width-2; col++) {
3260 FORC3 smrow[4][col][c] =
3261 (pix[c-8]+pix[c-4]+pix[c]+pix[c+4]+pix[c+8]+2) >> 2;
3265 pix = image[row*width+2];
3266 for (col=2; col < width-2; col++) {
3267 for (total[3]=375, sum=60, c=0; c < 3; c++) {
3268 for (total[c]=i=0; i < 5; i++)
3269 total[c] += smrow[i][col][c];
3270 total[3] += total[c];
3273 if (sum < 0) sum = 0;
3274 j = total[3] > 375 ? (sum << 16) / total[3] : sum * 174;
3275 FORC3 pix[c] += foveon_apply_curve (curve[6],
3276 ((j*total[c] + 0x8000) >> 16) - pix[c]);
3281 /* Transform the image to a different colorspace */
3282 for (pix=image[0]; pix < image[height*width]; pix+=4) {
3283 FORC3 pix[c] -= foveon_apply_curve (curve[c], pix[c]);
3284 sum = (pix[0]+pix[1]+pix[1]+pix[2]) >> 2;
3285 FORC3 pix[c] -= foveon_apply_curve (curve[c], pix[c]-sum);
3287 for (dsum=i=0; i < 3; i++)
3288 dsum += trans[c][i] * pix[i];
3289 if (dsum < 0) dsum = 0;
3290 if (dsum > 24000) dsum = 24000;
3291 ipix[c] = dsum + 0.5;
3293 FORC3 pix[c] = ipix[c];
3296 /* Smooth the image bottom-to-top and save at 1/4 scale */
3297 shrink = (short (*)[3]) calloc ((width/4) * (height/4), sizeof *shrink);
3298 merror (shrink, "foveon_interpolate()");
3299 for (row = height/4; row--; )
3300 for (col=0; col < width/4; col++) {
3301 ipix[0] = ipix[1] = ipix[2] = 0;
3302 for (i=0; i < 4; i++)
3303 for (j=0; j < 4; j++)
3304 FORC3 ipix[c] += image[(row*4+i)*width+col*4+j][c];
3306 if (row+2 > height/4)
3307 shrink[row*(width/4)+col][c] = ipix[c] >> 4;
3309 shrink[row*(width/4)+col][c] =
3310 (shrink[(row+1)*(width/4)+col][c]*1840 + ipix[c]*141 + 2048) >> 12;
3312 /* From the 1/4-scale image, smooth right-to-left */
3313 for (row=0; row < (height & ~3); row++) {
3314 ipix[0] = ipix[1] = ipix[2] = 0;
3316 for (col = width & ~3 ; col--; )
3317 FORC3 smrow[0][col][c] = ipix[c] =
3318 (shrink[(row/4)*(width/4)+col/4][c]*1485 + ipix[c]*6707 + 4096) >> 13;
3320 /* Then smooth left-to-right */
3321 ipix[0] = ipix[1] = ipix[2] = 0;
3322 for (col=0; col < (width & ~3); col++)
3323 FORC3 smrow[1][col][c] = ipix[c] =
3324 (smrow[0][col][c]*1485 + ipix[c]*6707 + 4096) >> 13;
3326 /* Smooth top-to-bottom */
3328 memcpy (smrow[2], smrow[1], sizeof **smrow * width);
3330 for (col=0; col < (width & ~3); col++)
3331 FORC3 smrow[2][col][c] =
3332 (smrow[2][col][c]*6707 + smrow[1][col][c]*1485 + 4096) >> 13;
3334 /* Adjust the chroma toward the smooth values */
3335 for (col=0; col < (width & ~3); col++) {
3336 for (i=j=30, c=0; c < 3; c++) {
3337 i += smrow[2][col][c];
3338 j += image[row*width+col][c];
3341 for (sum=c=0; c < 3; c++) {
3342 ipix[c] = foveon_apply_curve (curve[c+3],
3343 ((smrow[2][col][c] * j + 0x8000) >> 16) - image[row*width+col][c]);
3348 i = image[row*width+col][c] + ipix[c] - sum;
3350 image[row*width+col][c] = i;
3356 for (i=0; i < 8; i++)
3359 /* Trim off the black border */
3360 active[1] -= keep[1];
3362 i = active[2] - active[0];
3363 for (row=0; row < active[3]-active[1]; row++)
3364 memcpy (image[row*i], image[(row+active[1])*width+active[0]],
3371 /* RESTRICTED code ends here */
3373 void CLASS crop_masked_pixels()
3376 unsigned r, c, m, mblack[8], zero, val;
3378 if (load_raw == &CLASS phase_one_load_raw ||
3379 load_raw == &CLASS phase_one_load_raw_c)
3380 phase_one_correct();
3382 for (row=0; row < raw_height-top_margin*2; row++) {
3383 for (col=0; col < fuji_width << !fuji_layout; col++) {
3385 r = fuji_width - 1 - col + (row >> 1);
3386 c = col + ((row+1) >> 1);
3388 r = fuji_width - 1 + row - (col >> 1);
3389 c = row + ((col+1) >> 1);
3391 if (r < height && c < width)
3392 BAYER(r,c) = RAW(row+top_margin,col+left_margin);
3396 for (row=0; row < height; row++)
3397 for (col=0; col < width; col++)
3398 BAYER2(row,col) = RAW(row+top_margin,col+left_margin);
3400 if (mask[0][3]) goto mask_set;
3401 if (load_raw == &CLASS canon_load_raw ||
3402 load_raw == &CLASS lossless_jpeg_load_raw) {
3403 mask[0][1] = mask[1][1] = 2;
3407 if (load_raw == &CLASS canon_600_load_raw ||
3408 load_raw == &CLASS sony_load_raw ||
3409 (load_raw == &CLASS eight_bit_load_raw && strncmp(model,"DC2",3)) ||
3410 load_raw == &CLASS kodak_262_load_raw ||
3411 (load_raw == &CLASS packed_load_raw && (load_flags & 32))) {
3413 mask[0][0] = mask[1][0] = top_margin;
3414 mask[0][2] = mask[1][2] = top_margin+height;
3415 mask[0][3] += left_margin;
3416 mask[1][1] += left_margin+width;
3417 mask[1][3] += raw_width;
3419 if (load_raw == &CLASS nokia_load_raw) {
3420 mask[0][2] = top_margin;
3424 memset (mblack, 0, sizeof mblack);
3425 for (zero=m=0; m < 8; m++)
3426 for (row=mask[m][0]; row < mask[m][2]; row++)
3427 for (col=mask[m][1]; col < mask[m][3]; col++) {
3428 c = FC(row-top_margin,col-left_margin);
3429 mblack[c] += val = RAW(row,col);
3433 if (load_raw == &CLASS canon_600_load_raw && width < raw_width) {
3434 black = (mblack[0]+mblack[1]+mblack[2]+mblack[3]) /
3435 (mblack[4]+mblack[5]+mblack[6]+mblack[7]) - 4;
3436 canon_600_correct();
3437 } else if (zero < mblack[4] && mblack[5] && mblack[6] && mblack[7])
3438 FORC4 cblack[c] = mblack[c] / mblack[4+c];
3441 void CLASS remove_zeroes()
3443 unsigned row, col, tot, n, r, c;
3445 for (row=0; row < height; row++)
3446 for (col=0; col < width; col++)
3447 if (BAYER(row,col) == 0) {
3449 for (r = row-2; r <= row+2; r++)
3450 for (c = col-2; c <= col+2; c++)
3451 if (r < height && c < width &&
3452 FC(r,c) == FC(row,col) && BAYER(r,c))
3453 tot += (n++,BAYER(r,c));
3454 if (n) BAYER(row,col) = tot/n;
3459 Seach from the current directory up to the root looking for
3460 a ".badpixels" file, and fix those pixels now.
3462 void CLASS bad_pixels (const char *cfname)
3465 char *fname, *cp, line[128];
3466 int len, time, row, col, r, c, rad, tot, n, fixed=0;
3468 if (!filters) return;
3470 fp = fopen (cfname, "r");
3472 for (len=32 ; ; len *= 2) {
3473 fname = (char *) malloc (len);
3475 if (getcwd (fname, len-16)) break;
3477 if (errno != ERANGE) return;
3479 #if defined(WIN32) || defined(DJGPP)
3480 if (fname[1] == ':')
3481 memmove (fname, fname+2, len-2);
3482 for (cp=fname; *cp; cp++)
3483 if (*cp == '\\') *cp = '/';
3485 cp = fname + strlen(fname);
3486 if (cp[-1] == '/') cp--;
3487 while (*fname == '/') {
3488 strcpy (cp, "/.badpixels");
3489 if ((fp = fopen (fname, "r"))) break;
3490 if (cp == fname) break;
3491 while (*--cp != '/');
3496 while (fgets (line, 128, fp)) {
3497 cp = strchr (line, '#');
3499 if (sscanf (line, "%d %d %d", &col, &row, &time) != 3) continue;
3500 if ((unsigned) col >= width || (unsigned) row >= height) continue;
3501 if (time > timestamp) continue;
3502 for (tot=n=0, rad=1; rad < 3 && n==0; rad++)
3503 for (r = row-rad; r <= row+rad; r++)
3504 for (c = col-rad; c <= col+rad; c++)
3505 if ((unsigned) r < height && (unsigned) c < width &&
3506 (r != row || c != col) && fcol(r,c) == fcol(row,col)) {
3510 BAYER2(row,col) = tot/n;
3513 fprintf (stderr,_("Fixed dead pixels at:"));
3514 fprintf (stderr, " %d,%d", col, row);
3517 if (fixed) fputc ('\n', stderr);
3521 void CLASS subtract (const char *fname)
3524 int dim[3]={0,0,0}, comment=0, number=0, error=0, nd=0, c, row, col;
3527 if (!(fp = fopen (fname, "rb"))) {
3528 perror (fname); return;
3530 if (fgetc(fp) != 'P' || fgetc(fp) != '5') error = 1;
3531 while (!error && nd < 3 && (c = fgetc(fp)) != EOF) {
3532 if (c == '#') comment = 1;
3533 if (c == '\n') comment = 0;
3534 if (comment) continue;
3535 if (isdigit(c)) number = 1;
3537 if (isdigit(c)) dim[nd] = dim[nd]*10 + c -'0';
3538 else if (isspace(c)) {
3543 if (error || nd < 3) {
3544 fprintf (stderr,_("%s is not a valid PGM file!\n"), fname);
3545 fclose (fp); return;
3546 } else if (dim[0] != width || dim[1] != height || dim[2] != 65535) {
3547 fprintf (stderr,_("%s has the wrong dimensions!\n"), fname);
3548 fclose (fp); return;
3550 pixel = (ushort *) calloc (width, sizeof *pixel);
3551 merror (pixel, "subtract()");
3552 for (row=0; row < height; row++) {
3553 fread (pixel, 2, width, fp);
3554 for (col=0; col < width; col++)
3555 BAYER(row,col) = MAX (BAYER(row,col) - ntohs(pixel[col]), 0);
3559 memset (cblack, 0, sizeof cblack);
3563 void CLASS gamma_curve (double pwr, double ts, int mode, int imax)
3566 double g[6], bnd[2]={0,0}, r;
3570 g[2] = g[3] = g[4] = 0;
3572 if (g[1] && (g[1]-1)*(g[0]-1) <= 0) {
3573 for (i=0; i < 48; i++) {
3574 g[2] = (bnd[0] + bnd[1])/2;
3575 if (g[0]) bnd[(pow(g[2]/g[1],-g[0]) - 1)/g[0] - 1/g[2] > -1] = g[2];
3576 else bnd[g[2]/exp(1-1/g[2]) < g[1]] = g[2];
3579 if (g[0]) g[4] = g[2] * (1/g[0] - 1);
3581 if (g[0]) g[5] = 1 / (g[1]*SQR(g[3])/2 - g[4]*(1 - g[3]) +
3582 (1 - pow(g[3],1+g[0]))*(1 + g[4])/(1 + g[0])) - 1;
3583 else g[5] = 1 / (g[1]*SQR(g[3])/2 + 1
3584 - g[2] - g[3] - g[2]*g[3]*(log(g[3]) - 1)) - 1;
3586 memcpy (gamm, g, sizeof gamm);
3589 for (i=0; i < 0x10000; i++) {
3591 if ((r = (double) i / imax) < 1)
3592 curve[i] = 0x10000 * ( mode
3593 ? (r < g[3] ? r*g[1] : (g[0] ? pow( r,g[0])*(1+g[4])-g[4] : log(r)*g[2]+1))
3594 : (r < g[2] ? r/g[1] : (g[0] ? pow((r+g[4])/(1+g[4]),1/g[0]) : exp((r-1)/g[2]))));
3598 void CLASS pseudoinverse (double (*in)[3], double (*out)[3], int size)
3600 double work[3][6], num;
3603 for (i=0; i < 3; i++) {
3604 for (j=0; j < 6; j++)
3605 work[i][j] = j == i+3;
3606 for (j=0; j < 3; j++)
3607 for (k=0; k < size; k++)
3608 work[i][j] += in[k][i] * in[k][j];
3610 for (i=0; i < 3; i++) {
3612 for (j=0; j < 6; j++)
3614 for (k=0; k < 3; k++) {
3617 for (j=0; j < 6; j++)
3618 work[k][j] -= work[i][j] * num;
3621 for (i=0; i < size; i++)
3622 for (j=0; j < 3; j++)
3623 for (out[i][j]=k=0; k < 3; k++)
3624 out[i][j] += work[j][k+3] * in[i][k];
3627 void CLASS cam_xyz_coeff (double cam_xyz[4][3])
3629 double cam_rgb[4][3], inverse[4][3], num;
3632 for (i=0; i < colors; i++) /* Multiply out XYZ colorspace */
3633 for (j=0; j < 3; j++)
3634 for (cam_rgb[i][j] = k=0; k < 3; k++)
3635 cam_rgb[i][j] += cam_xyz[i][k] * xyz_rgb[k][j];
3637 for (i=0; i < colors; i++) { /* Normalize cam_rgb so that */
3638 for (num=j=0; j < 3; j++) /* cam_rgb * (1,1,1) is (1,1,1,1) */
3639 num += cam_rgb[i][j];
3640 for (j=0; j < 3; j++)
3641 cam_rgb[i][j] /= num;
3642 pre_mul[i] = 1 / num;
3644 pseudoinverse (cam_rgb, inverse, colors);
3645 for (raw_color = i=0; i < 3; i++)
3646 for (j=0; j < colors; j++)
3647 rgb_cam[i][j] = inverse[j][i];
3651 void CLASS colorcheck()
3654 // Coordinates of the GretagMacbeth ColorChecker squares
3655 // width, height, 1st_column, 1st_row
3656 int cut[NSQ][4]; // you must set these
3657 // ColorChecker Chart under 6500-kelvin illumination
3658 static const double gmb_xyY[NSQ][3] = {
3659 { 0.400, 0.350, 10.1 }, // Dark Skin
3660 { 0.377, 0.345, 35.8 }, // Light Skin
3661 { 0.247, 0.251, 19.3 }, // Blue Sky
3662 { 0.337, 0.422, 13.3 }, // Foliage
3663 { 0.265, 0.240, 24.3 }, // Blue Flower
3664 { 0.261, 0.343, 43.1 }, // Bluish Green
3665 { 0.506, 0.407, 30.1 }, // Orange
3666 { 0.211, 0.175, 12.0 }, // Purplish Blue
3667 { 0.453, 0.306, 19.8 }, // Moderate Red
3668 { 0.285, 0.202, 6.6 }, // Purple
3669 { 0.380, 0.489, 44.3 }, // Yellow Green
3670 { 0.473, 0.438, 43.1 }, // Orange Yellow
3671 { 0.187, 0.129, 6.1 }, // Blue
3672 { 0.305, 0.478, 23.4 }, // Green
3673 { 0.539, 0.313, 12.0 }, // Red
3674 { 0.448, 0.470, 59.1 }, // Yellow
3675 { 0.364, 0.233, 19.8 }, // Magenta
3676 { 0.196, 0.252, 19.8 }, // Cyan
3677 { 0.310, 0.316, 90.0 }, // White
3678 { 0.310, 0.316, 59.1 }, // Neutral 8
3679 { 0.310, 0.316, 36.2 }, // Neutral 6.5
3680 { 0.310, 0.316, 19.8 }, // Neutral 5
3681 { 0.310, 0.316, 9.0 }, // Neutral 3.5
3682 { 0.310, 0.316, 3.1 } }; // Black
3683 double gmb_cam[NSQ][4], gmb_xyz[NSQ][3];
3684 double inverse[NSQ][3], cam_xyz[4][3], num;
3685 int c, i, j, k, sq, row, col, count[4];
3687 memset (gmb_cam, 0, sizeof gmb_cam);
3688 for (sq=0; sq < NSQ; sq++) {
3690 for (row=cut[sq][3]; row < cut[sq][3]+cut[sq][1]; row++)
3691 for (col=cut[sq][2]; col < cut[sq][2]+cut[sq][0]; col++) {
3693 if (c >= colors) c -= 2;
3694 gmb_cam[sq][c] += BAYER(row,col);
3697 FORCC gmb_cam[sq][c] = gmb_cam[sq][c]/count[c] - black;
3698 gmb_xyz[sq][0] = gmb_xyY[sq][2] * gmb_xyY[sq][0] / gmb_xyY[sq][1];
3699 gmb_xyz[sq][1] = gmb_xyY[sq][2];
3700 gmb_xyz[sq][2] = gmb_xyY[sq][2] *
3701 (1 - gmb_xyY[sq][0] - gmb_xyY[sq][1]) / gmb_xyY[sq][1];
3703 pseudoinverse (gmb_xyz, inverse, NSQ);
3704 for (i=0; i < colors; i++)
3705 for (j=0; j < 3; j++)
3706 for (cam_xyz[i][j] = k=0; k < NSQ; k++)
3707 cam_xyz[i][j] += gmb_cam[k][i] * inverse[k][j];
3708 cam_xyz_coeff (cam_xyz);
3710 printf (" { \"%s %s\", %d,\n\t{", make, model, black);
3711 num = 10000 / (cam_xyz[1][0] + cam_xyz[1][1] + cam_xyz[1][2]);
3712 FORCC for (j=0; j < 3; j++)
3713 printf ("%c%d", (c | j) ? ',':' ', (int) (cam_xyz[c][j] * num + 0.5));
3720 void CLASS hat_transform (float *temp, float *base, int st, int size, int sc)
3723 for (i=0; i < sc; i++)
3724 temp[i] = 2*base[st*i] + base[st*(sc-i)] + base[st*(i+sc)];
3725 for (; i+sc < size; i++)
3726 temp[i] = 2*base[st*i] + base[st*(i-sc)] + base[st*(i+sc)];
3727 for (; i < size; i++)
3728 temp[i] = 2*base[st*i] + base[st*(i-sc)] + base[st*(2*size-2-(i+sc))];
3731 void CLASS wavelet_denoise()
3733 float *fimg=0, *temp, thold, mul[2], avg, diff;
3734 int scale=1, size, lev, hpass, lpass, row, col, nc, c, i, wlast, blk[2];
3736 static const float noise[] =
3737 { 0.8002,0.2735,0.1202,0.0585,0.0291,0.0152,0.0080,0.0044 };
3739 if (verbose) fprintf (stderr,_("Wavelet denoising...\n"));
3741 while (maximum << scale < 0x10000) scale++;
3742 maximum <<= --scale;
3744 FORC4 cblack[c] <<= scale;
3745 if ((size = iheight*iwidth) < 0x15550000)
3746 fimg = (float *) malloc ((size*3 + iheight + iwidth) * sizeof *fimg);
3747 merror (fimg, "wavelet_denoise()");
3748 temp = fimg + size*3;
3749 if ((nc = colors) == 3 && filters) nc++;
3750 FORC(nc) { /* denoise R,G1,B,G3 individually */
3751 for (i=0; i < size; i++)
3752 fimg[i] = 256 * sqrt(image[i][c] << scale);
3753 for (hpass=lev=0; lev < 5; lev++) {
3754 lpass = size*((lev & 1)+1);
3755 for (row=0; row < iheight; row++) {
3756 hat_transform (temp, fimg+hpass+row*iwidth, 1, iwidth, 1 << lev);
3757 for (col=0; col < iwidth; col++)
3758 fimg[lpass + row*iwidth + col] = temp[col] * 0.25;
3760 for (col=0; col < iwidth; col++) {
3761 hat_transform (temp, fimg+lpass+col, iwidth, iheight, 1 << lev);
3762 for (row=0; row < iheight; row++)
3763 fimg[lpass + row*iwidth + col] = temp[row] * 0.25;
3765 thold = threshold * noise[lev];
3766 for (i=0; i < size; i++) {
3767 fimg[hpass+i] -= fimg[lpass+i];
3768 if (fimg[hpass+i] < -thold) fimg[hpass+i] += thold;
3769 else if (fimg[hpass+i] > thold) fimg[hpass+i] -= thold;
3770 else fimg[hpass+i] = 0;
3771 if (hpass) fimg[i] += fimg[hpass+i];
3775 for (i=0; i < size; i++)
3776 image[i][c] = CLIP(SQR(fimg[i]+fimg[lpass+i])/0x10000);
3778 if (filters && colors == 3) { /* pull G1 and G3 closer together */
3779 for (row=0; row < 2; row++) {
3780 mul[row] = 0.125 * pre_mul[FC(row+1,0) | 1] / pre_mul[FC(row,0) | 1];
3781 blk[row] = cblack[FC(row,0) | 1];
3783 for (i=0; i < 4; i++)
3784 window[i] = (ushort *) fimg + width*i;
3785 for (wlast=-1, row=1; row < height-1; row++) {
3786 while (wlast < row+1) {
3787 for (wlast++, i=0; i < 4; i++)
3788 window[(i+3) & 3] = window[i];
3789 for (col = FC(wlast,1) & 1; col < width; col+=2)
3790 window[2][col] = BAYER(wlast,col);
3792 thold = threshold/512;
3793 for (col = (FC(row,0) & 1)+1; col < width-1; col+=2) {
3794 avg = ( window[0][col-1] + window[0][col+1] +
3795 window[2][col-1] + window[2][col+1] - blk[~row & 1]*4 )
3796 * mul[row & 1] + (window[1][col] + blk[row & 1]) * 0.5;
3797 avg = avg < 0 ? 0 : sqrt(avg);
3798 diff = sqrt(BAYER(row,col)) - avg;
3799 if (diff < -thold) diff += thold;
3800 else if (diff > thold) diff -= thold;
3802 BAYER(row,col) = CLIP(SQR(avg+diff) + 0.5);
3809 void CLASS scale_colors()
3811 unsigned bottom, right, size, row, col, ur, uc, i, x, y, c, sum[8];
3813 double dsum[8], dmin, dmax;
3814 float scale_mul[4], fr, fc;
3815 ushort *img=0, *pix;
3818 memcpy (pre_mul, user_mul, sizeof pre_mul);
3819 if (use_auto_wb || (use_camera_wb && cam_mul[0] == -1)) {
3820 memset (dsum, 0, sizeof dsum);
3821 bottom = MIN (greybox[1]+greybox[3], height);
3822 right = MIN (greybox[0]+greybox[2], width);
3823 for (row=greybox[1]; row < bottom; row += 8)
3824 for (col=greybox[0]; col < right; col += 8) {
3825 memset (sum, 0, sizeof sum);
3826 for (y=row; y < row+8 && y < bottom; y++)
3827 for (x=col; x < col+8 && x < right; x++)
3833 val = image[y*width+x][c];
3834 if (val > maximum-25) goto skip_block;
3835 if ((val -= cblack[c]) < 0) val = 0;
3840 FORC(8) dsum[c] += sum[c];
3843 FORC4 if (dsum[c]) pre_mul[c] = dsum[c+4] / dsum[c];
3845 if (use_camera_wb && cam_mul[0] != -1) {
3846 memset (sum, 0, sizeof sum);
3847 for (row=0; row < 8; row++)
3848 for (col=0; col < 8; col++) {
3850 if ((val = white[row][col] - cblack[c]) > 0)
3854 if (sum[0] && sum[1] && sum[2] && sum[3])
3855 FORC4 pre_mul[c] = (float) sum[c+4] / sum[c];
3856 else if (cam_mul[0] && cam_mul[2])
3857 memcpy (pre_mul, cam_mul, sizeof pre_mul);
3859 fprintf (stderr,_("%s: Cannot use camera white balance.\n"), ifname);
3861 if (pre_mul[3] == 0) pre_mul[3] = colors < 4 ? pre_mul[1] : 1;
3864 if (threshold) wavelet_denoise();
3866 for (dmin=DBL_MAX, dmax=c=0; c < 4; c++) {
3867 if (dmin > pre_mul[c])
3869 if (dmax < pre_mul[c])
3872 if (!highlight) dmax = dmin;
3873 FORC4 scale_mul[c] = (pre_mul[c] /= dmax) * 65535.0 / maximum;
3876 _("Scaling with darkness %d, saturation %d, and\nmultipliers"), dark, sat);
3877 FORC4 fprintf (stderr, " %f", pre_mul[c]);
3878 fputc ('\n', stderr);
3880 size = iheight*iwidth;
3881 for (i=0; i < size*4; i++) {
3884 val -= cblack[i & 3];
3885 val *= scale_mul[i & 3];
3886 image[0][i] = CLIP(val);
3888 if ((aber[0] != 1 || aber[2] != 1) && colors == 3) {
3890 fprintf (stderr,_("Correcting chromatic aberration...\n"));
3891 for (c=0; c < 4; c+=2) {
3892 if (aber[c] == 1) continue;
3893 img = (ushort *) malloc (size * sizeof *img);
3894 merror (img, "scale_colors()");
3895 for (i=0; i < size; i++)
3896 img[i] = image[i][c];
3897 for (row=0; row < iheight; row++) {
3898 ur = fr = (row - iheight*0.5) * aber[c] + iheight*0.5;
3899 if (ur > iheight-2) continue;
3901 for (col=0; col < iwidth; col++) {
3902 uc = fc = (col - iwidth*0.5) * aber[c] + iwidth*0.5;
3903 if (uc > iwidth-2) continue;
3905 pix = img + ur*iwidth + uc;
3906 image[row*iwidth+col][c] =
3907 (pix[ 0]*(1-fc) + pix[ 1]*fc) * (1-fr) +
3908 (pix[iwidth]*(1-fc) + pix[iwidth+1]*fc) * fr;
3916 void CLASS pre_interpolate()
3926 img = (ushort (*)[4]) calloc (height*width, sizeof *img);
3927 merror (img, "pre_interpolate()");
3928 for (row=0; row < height; row++)
3929 for (col=0; col < width; col++) {
3931 img[row*width+col][c] = image[(row >> 1)*iwidth+(col >> 1)][c];
3938 if (filters > 1000 && colors == 3) {
3939 if (four_color_rgb && colors++)
3940 mix_green = !half_size;
3942 for (row = FC(1,0) >> 1; row < height; row+=2)
3943 for (col = FC(row,1) & 1; col < width; col+=2)
3944 image[row*width+col][1] = image[row*width+col][3];
3945 filters &= ~((filters & 0x55555555) << 1);
3948 if (half_size) filters = 0;
3951 void CLASS border_interpolate (int border)
3953 unsigned row, col, y, x, f, c, sum[8];
3955 for (row=0; row < height; row++)
3956 for (col=0; col < width; col++) {
3957 if (col==border && row >= border && row < height-border)
3959 memset (sum, 0, sizeof sum);
3960 for (y=row-1; y != row+2; y++)
3961 for (x=col-1; x != col+2; x++)
3962 if (y < height && x < width) {
3964 sum[f] += image[y*width+x][f];
3968 FORCC if (c != f && sum[c+4])
3969 image[row*width+col][c] = sum[c] / sum[c+4];
3973 void CLASS lin_interpolate()
3975 int code[16][16][32], size=16, *ip, sum[4];
3976 int f, c, i, x, y, row, col, shift, color;
3979 if (verbose) fprintf (stderr,_("Bilinear interpolation...\n"));
3980 if (filters == 2) size = 6;
3981 border_interpolate(1);
3982 for (row=0; row < size; row++)
3983 for (col=0; col < size; col++) {
3984 ip = code[row][col]+1;
3986 memset (sum, 0, sizeof sum);
3987 for (y=-1; y <= 1; y++)
3988 for (x=-1; x <= 1; x++) {
3989 shift = (y==0) + (x==0);
3990 color = fcol(row+y,col+x);
3991 if (color == f) continue;
3992 *ip++ = (width*y + x)*4 + color;
3995 sum[color] += 1 << shift;
3997 code[row][col][0] = (ip - code[row][col]) / 3;
4001 *ip++ = 256 / sum[c];
4004 for (row=1; row < height-1; row++)
4005 for (col=1; col < width-1; col++) {
4006 pix = image[row*width+col];
4007 ip = code[row % size][col % size];
4008 memset (sum, 0, sizeof sum);
4009 for (i=*ip++; i--; ip+=3)
4010 sum[ip[2]] += pix[ip[0]] << ip[1];
4011 for (i=colors; --i; ip+=2)
4012 pix[ip[0]] = sum[ip[0]] * ip[1] >> 8;
4017 This algorithm is officially called:
4019 "Interpolation using a Threshold-based variable number of gradients"
4021 described in http://scien.stanford.edu/pages/labsite/1999/psych221/projects/99/tingchen/algodep/vargra.html
4023 I've extended the basic idea to work with non-Bayer filter arrays.
4024 Gradients are numbered clockwise from NW=0 to W=7.
4026 void CLASS vng_interpolate()
4028 static const signed char *cp, terms[] = {
4029 -2,-2,+0,-1,0,0x01, -2,-2,+0,+0,1,0x01, -2,-1,-1,+0,0,0x01,
4030 -2,-1,+0,-1,0,0x02, -2,-1,+0,+0,0,0x03, -2,-1,+0,+1,1,0x01,
4031 -2,+0,+0,-1,0,0x06, -2,+0,+0,+0,1,0x02, -2,+0,+0,+1,0,0x03,
4032 -2,+1,-1,+0,0,0x04, -2,+1,+0,-1,1,0x04, -2,+1,+0,+0,0,0x06,
4033 -2,+1,+0,+1,0,0x02, -2,+2,+0,+0,1,0x04, -2,+2,+0,+1,0,0x04,
4034 -1,-2,-1,+0,0,0x80, -1,-2,+0,-1,0,0x01, -1,-2,+1,-1,0,0x01,
4035 -1,-2,+1,+0,1,0x01, -1,-1,-1,+1,0,0x88, -1,-1,+1,-2,0,0x40,
4036 -1,-1,+1,-1,0,0x22, -1,-1,+1,+0,0,0x33, -1,-1,+1,+1,1,0x11,
4037 -1,+0,-1,+2,0,0x08, -1,+0,+0,-1,0,0x44, -1,+0,+0,+1,0,0x11,
4038 -1,+0,+1,-2,1,0x40, -1,+0,+1,-1,0,0x66, -1,+0,+1,+0,1,0x22,
4039 -1,+0,+1,+1,0,0x33, -1,+0,+1,+2,1,0x10, -1,+1,+1,-1,1,0x44,
4040 -1,+1,+1,+0,0,0x66, -1,+1,+1,+1,0,0x22, -1,+1,+1,+2,0,0x10,
4041 -1,+2,+0,+1,0,0x04, -1,+2,+1,+0,1,0x04, -1,+2,+1,+1,0,0x04,
4042 +0,-2,+0,+0,1,0x80, +0,-1,+0,+1,1,0x88, +0,-1,+1,-2,0,0x40,
4043 +0,-1,+1,+0,0,0x11, +0,-1,+2,-2,0,0x40, +0,-1,+2,-1,0,0x20,
4044 +0,-1,+2,+0,0,0x30, +0,-1,+2,+1,1,0x10, +0,+0,+0,+2,1,0x08,
4045 +0,+0,+2,-2,1,0x40, +0,+0,+2,-1,0,0x60, +0,+0,+2,+0,1,0x20,
4046 +0,+0,+2,+1,0,0x30, +0,+0,+2,+2,1,0x10, +0,+1,+1,+0,0,0x44,
4047 +0,+1,+1,+2,0,0x10, +0,+1,+2,-1,1,0x40, +0,+1,+2,+0,0,0x60,
4048 +0,+1,+2,+1,0,0x20, +0,+1,+2,+2,0,0x10, +1,-2,+1,+0,0,0x80,
4049 +1,-1,+1,+1,0,0x88, +1,+0,+1,+2,0,0x08, +1,+0,+2,-1,0,0x40,
4051 }, chood[] = { -1,-1, -1,0, -1,+1, 0,+1, +1,+1, +1,0, +1,-1, 0,-1 };
4052 ushort (*brow[5])[4], *pix;
4053 int prow=8, pcol=2, *ip, *code[16][16], gval[8], gmin, gmax, sum[4];
4054 int row, col, x, y, x1, x2, y1, y2, t, weight, grads, color, diag;
4055 int g, diff, thold, num, c;
4058 if (verbose) fprintf (stderr,_("VNG interpolation...\n"));
4060 if (filters == 1) prow = pcol = 16;
4061 if (filters == 2) prow = pcol = 6;
4062 ip = (int *) calloc (prow*pcol, 1280);
4063 merror (ip, "vng_interpolate()");
4064 for (row=0; row < prow; row++) /* Precalculate for VNG */
4065 for (col=0; col < pcol; col++) {
4066 code[row][col] = ip;
4067 for (cp=terms, t=0; t < 64; t++) {
4068 y1 = *cp++; x1 = *cp++;
4069 y2 = *cp++; x2 = *cp++;
4072 color = fcol(row+y1,col+x1);
4073 if (fcol(row+y2,col+x2) != color) continue;
4074 diag = (fcol(row,col+1) == color && fcol(row+1,col) == color) ? 2:1;
4075 if (abs(y1-y2) == diag && abs(x1-x2) == diag) continue;
4076 *ip++ = (y1*width + x1)*4 + color;
4077 *ip++ = (y2*width + x2)*4 + color;
4079 for (g=0; g < 8; g++)
4080 if (grads & 1<<g) *ip++ = g;
4084 for (cp=chood, g=0; g < 8; g++) {
4085 y = *cp++; x = *cp++;
4086 *ip++ = (y*width + x) * 4;
4087 color = fcol(row,col);
4088 if (fcol(row+y,col+x) != color && fcol(row+y*2,col+x*2) == color)
4089 *ip++ = (y*width + x) * 8 + color;
4094 brow[4] = (ushort (*)[4]) calloc (width*3, sizeof **brow);
4095 merror (brow[4], "vng_interpolate()");
4096 for (row=0; row < 3; row++)
4097 brow[row] = brow[4] + row*width;
4098 for (row=2; row < height-2; row++) { /* Do VNG interpolation */
4099 for (col=2; col < width-2; col++) {
4100 pix = image[row*width+col];
4101 ip = code[row % prow][col % pcol];
4102 memset (gval, 0, sizeof gval);
4103 while ((g = ip[0]) != INT_MAX) { /* Calculate gradients */
4104 diff = ABS(pix[g] - pix[ip[1]]) << ip[2];
4105 gval[ip[3]] += diff;
4107 if ((g = ip[-1]) == -1) continue;
4109 while ((g = *ip++) != -1)
4113 gmin = gmax = gval[0]; /* Choose a threshold */
4114 for (g=1; g < 8; g++) {
4115 if (gmin > gval[g]) gmin = gval[g];
4116 if (gmax < gval[g]) gmax = gval[g];
4119 memcpy (brow[2][col], pix, sizeof *image);
4122 thold = gmin + (gmax >> 1);
4123 memset (sum, 0, sizeof sum);
4124 color = fcol(row,col);
4125 for (num=g=0; g < 8; g++,ip+=2) { /* Average the neighbors */
4126 if (gval[g] <= thold) {
4128 if (c == color && ip[1])
4129 sum[c] += (pix[c] + pix[ip[1]]) >> 1;
4131 sum[c] += pix[ip[0] + c];
4135 FORCC { /* Save to buffer */
4138 t += (sum[c] - sum[color]) / num;
4139 brow[2][col][c] = CLIP(t);
4142 if (row > 3) /* Write buffer to image */
4143 memcpy (image[(row-2)*width+2], brow[0]+2, (width-4)*sizeof *image);
4144 for (g=0; g < 4; g++)
4145 brow[(g-1) & 3] = brow[g];
4147 memcpy (image[(row-2)*width+2], brow[0]+2, (width-4)*sizeof *image);
4148 memcpy (image[(row-1)*width+2], brow[1]+2, (width-4)*sizeof *image);
4154 Patterned Pixel Grouping Interpolation by Alain Desbiolles
4156 void CLASS ppg_interpolate()
4158 int dir[5] = { 1, width, -1, -width, 1 };
4159 int row, col, diff[2], guess[2], c, d, i;
4162 border_interpolate(3);
4163 if (verbose) fprintf (stderr,_("PPG interpolation...\n"));
4165 /* Fill in the green layer with gradients and pattern recognition: */
4166 for (row=3; row < height-3; row++)
4167 for (col=3+(FC(row,3) & 1), c=FC(row,col); col < width-3; col+=2) {
4168 pix = image + row*width+col;
4169 for (i=0; (d=dir[i]) > 0; i++) {
4170 guess[i] = (pix[-d][1] + pix[0][c] + pix[d][1]) * 2
4171 - pix[-2*d][c] - pix[2*d][c];
4172 diff[i] = ( ABS(pix[-2*d][c] - pix[ 0][c]) +
4173 ABS(pix[ 2*d][c] - pix[ 0][c]) +
4174 ABS(pix[ -d][1] - pix[ d][1]) ) * 3 +
4175 ( ABS(pix[ 3*d][1] - pix[ d][1]) +
4176 ABS(pix[-3*d][1] - pix[-d][1]) ) * 2;
4178 d = dir[i = diff[0] > diff[1]];
4179 pix[0][1] = ULIM(guess[i] >> 2, pix[d][1], pix[-d][1]);
4181 /* Calculate red and blue for each green pixel: */
4182 for (row=1; row < height-1; row++)
4183 for (col=1+(FC(row,2) & 1), c=FC(row,col+1); col < width-1; col+=2) {
4184 pix = image + row*width+col;
4185 for (i=0; (d=dir[i]) > 0; c=2-c, i++)
4186 pix[0][c] = CLIP((pix[-d][c] + pix[d][c] + 2*pix[0][1]
4187 - pix[-d][1] - pix[d][1]) >> 1);
4189 /* Calculate blue for red pixels and vice versa: */
4190 for (row=1; row < height-1; row++)
4191 for (col=1+(FC(row,1) & 1), c=2-FC(row,col); col < width-1; col+=2) {
4192 pix = image + row*width+col;
4193 for (i=0; (d=dir[i]+dir[i+1]) > 0; i++) {
4194 diff[i] = ABS(pix[-d][c] - pix[d][c]) +
4195 ABS(pix[-d][1] - pix[0][1]) +
4196 ABS(pix[ d][1] - pix[0][1]);
4197 guess[i] = pix[-d][c] + pix[d][c] + 2*pix[0][1]
4198 - pix[-d][1] - pix[d][1];
4200 if (diff[0] != diff[1])
4201 pix[0][c] = CLIP(guess[diff[0] > diff[1]] >> 1);
4203 pix[0][c] = CLIP((guess[0]+guess[1]) >> 2);
4208 Adaptive Homogeneity-Directed interpolation is based on
4209 the work of Keigo Hirakawa, Thomas Parks, and Paul Lee.
4211 #define TS 256 /* Tile Size */
4213 void CLASS ahd_interpolate()
4215 int i, j, k, top, left, row, col, tr, tc, c, d, val, hm[2];
4216 ushort (*pix)[4], (*rix)[3];
4217 static const int dir[4] = { -1, 1, -TS, TS };
4218 unsigned ldiff[2][4], abdiff[2][4], leps, abeps;
4219 float r, cbrt[0x10000], xyz[3], xyz_cam[3][4];
4220 ushort (*rgb)[TS][TS][3];
4221 short (*lab)[TS][TS][3], (*lix)[3];
4222 char (*homo)[TS][TS], *buffer;
4224 if (verbose) fprintf (stderr,_("AHD interpolation...\n"));
4226 for (i=0; i < 0x10000; i++) {
4228 cbrt[i] = r > 0.008856 ? pow(r,1/3.0) : 7.787*r + 16/116.0;
4230 for (i=0; i < 3; i++)
4231 for (j=0; j < colors; j++)
4232 for (xyz_cam[i][j] = k=0; k < 3; k++)
4233 xyz_cam[i][j] += xyz_rgb[i][k] * rgb_cam[k][j] / d65_white[i];
4235 border_interpolate(5);
4236 buffer = (char *) malloc (26*TS*TS); /* 1664 kB */
4237 merror (buffer, "ahd_interpolate()");
4238 rgb = (ushort(*)[TS][TS][3]) buffer;
4239 lab = (short (*)[TS][TS][3])(buffer + 12*TS*TS);
4240 homo = (char (*)[TS][TS]) (buffer + 24*TS*TS);
4242 for (top=2; top < height-5; top += TS-6)
4243 for (left=2; left < width-5; left += TS-6) {
4245 /* Interpolate green horizontally and vertically: */
4246 for (row = top; row < top+TS && row < height-2; row++) {
4247 col = left + (FC(row,left) & 1);
4248 for (c = FC(row,col); col < left+TS && col < width-2; col+=2) {
4249 pix = image + row*width+col;
4250 val = ((pix[-1][1] + pix[0][c] + pix[1][1]) * 2
4251 - pix[-2][c] - pix[2][c]) >> 2;
4252 rgb[0][row-top][col-left][1] = ULIM(val,pix[-1][1],pix[1][1]);
4253 val = ((pix[-width][1] + pix[0][c] + pix[width][1]) * 2
4254 - pix[-2*width][c] - pix[2*width][c]) >> 2;
4255 rgb[1][row-top][col-left][1] = ULIM(val,pix[-width][1],pix[width][1]);
4258 /* Interpolate red and blue, and convert to CIELab: */
4259 for (d=0; d < 2; d++)
4260 for (row=top+1; row < top+TS-1 && row < height-3; row++)
4261 for (col=left+1; col < left+TS-1 && col < width-3; col++) {
4262 pix = image + row*width+col;
4263 rix = &rgb[d][row-top][col-left];
4264 lix = &lab[d][row-top][col-left];
4265 if ((c = 2 - FC(row,col)) == 1) {
4267 val = pix[0][1] + (( pix[-1][2-c] + pix[1][2-c]
4268 - rix[-1][1] - rix[1][1] ) >> 1);
4269 rix[0][2-c] = CLIP(val);
4270 val = pix[0][1] + (( pix[-width][c] + pix[width][c]
4271 - rix[-TS][1] - rix[TS][1] ) >> 1);
4273 val = rix[0][1] + (( pix[-width-1][c] + pix[-width+1][c]
4274 + pix[+width-1][c] + pix[+width+1][c]
4275 - rix[-TS-1][1] - rix[-TS+1][1]
4276 - rix[+TS-1][1] - rix[+TS+1][1] + 1) >> 2);
4277 rix[0][c] = CLIP(val);
4279 rix[0][c] = pix[0][c];
4280 xyz[0] = xyz[1] = xyz[2] = 0.5;
4282 xyz[0] += xyz_cam[0][c] * rix[0][c];
4283 xyz[1] += xyz_cam[1][c] * rix[0][c];
4284 xyz[2] += xyz_cam[2][c] * rix[0][c];
4286 xyz[0] = cbrt[CLIP((int) xyz[0])];
4287 xyz[1] = cbrt[CLIP((int) xyz[1])];
4288 xyz[2] = cbrt[CLIP((int) xyz[2])];
4289 lix[0][0] = 64 * (116 * xyz[1] - 16);
4290 lix[0][1] = 64 * 500 * (xyz[0] - xyz[1]);
4291 lix[0][2] = 64 * 200 * (xyz[1] - xyz[2]);
4293 /* Build homogeneity maps from the CIELab images: */
4294 memset (homo, 0, 2*TS*TS);
4295 for (row=top+2; row < top+TS-2 && row < height-4; row++) {
4297 for (col=left+2; col < left+TS-2 && col < width-4; col++) {
4299 for (d=0; d < 2; d++) {
4300 lix = &lab[d][tr][tc];
4301 for (i=0; i < 4; i++) {
4302 ldiff[d][i] = ABS(lix[0][0]-lix[dir[i]][0]);
4303 abdiff[d][i] = SQR(lix[0][1]-lix[dir[i]][1])
4304 + SQR(lix[0][2]-lix[dir[i]][2]);
4307 leps = MIN(MAX(ldiff[0][0],ldiff[0][1]),
4308 MAX(ldiff[1][2],ldiff[1][3]));
4309 abeps = MIN(MAX(abdiff[0][0],abdiff[0][1]),
4310 MAX(abdiff[1][2],abdiff[1][3]));
4311 for (d=0; d < 2; d++)
4312 for (i=0; i < 4; i++)
4313 if (ldiff[d][i] <= leps && abdiff[d][i] <= abeps)
4317 /* Combine the most homogenous pixels for the final result: */
4318 for (row=top+3; row < top+TS-3 && row < height-5; row++) {
4320 for (col=left+3; col < left+TS-3 && col < width-5; col++) {
4322 for (d=0; d < 2; d++)
4323 for (hm[d]=0, i=tr-1; i <= tr+1; i++)
4324 for (j=tc-1; j <= tc+1; j++)
4325 hm[d] += homo[d][i][j];
4327 FORC3 image[row*width+col][c] = rgb[hm[1] > hm[0]][tr][tc][c];
4329 FORC3 image[row*width+col][c] =
4330 (rgb[0][tr][tc][c] + rgb[1][tr][tc][c]) >> 1;
4338 void CLASS median_filter()
4341 int pass, c, i, j, k, med[9];
4342 static const uchar opt[] = /* Optimal 9-element median search */
4343 { 1,2, 4,5, 7,8, 0,1, 3,4, 6,7, 1,2, 4,5, 7,8,
4344 0,3, 5,8, 4,7, 3,6, 1,4, 2,5, 4,7, 4,2, 6,4, 4,2 };
4346 for (pass=1; pass <= med_passes; pass++) {
4348 fprintf (stderr,_("Median filter pass %d...\n"), pass);
4349 for (c=0; c < 3; c+=2) {
4350 for (pix = image; pix < image+width*height; pix++)
4351 pix[0][3] = pix[0][c];
4352 for (pix = image+width; pix < image+width*(height-1); pix++) {
4353 if ((pix-image+1) % width < 2) continue;
4354 for (k=0, i = -width; i <= width; i += width)
4355 for (j = i-1; j <= i+1; j++)
4356 med[k++] = pix[j][3] - pix[j][1];
4357 for (i=0; i < sizeof opt; i+=2)
4358 if (med[opt[i]] > med[opt[i+1]])
4359 SWAP (med[opt[i]] , med[opt[i+1]]);
4360 pix[0][c] = CLIP(med[4] + pix[0][1]);
4366 void CLASS blend_highlights()
4368 int clip=INT_MAX, row, col, c, i, j;
4369 static const float trans[2][4][4] =
4370 { { { 1,1,1 }, { 1.7320508,-1.7320508,0 }, { -1,-1,2 } },
4371 { { 1,1,1,1 }, { 1,-1,1,-1 }, { 1,1,-1,-1 }, { 1,-1,-1,1 } } };
4372 static const float itrans[2][4][4] =
4373 { { { 1,0.8660254,-0.5 }, { 1,-0.8660254,-0.5 }, { 1,0,1 } },
4374 { { 1,1,1,1 }, { 1,-1,1,-1 }, { 1,1,-1,-1 }, { 1,-1,-1,1 } } };
4375 float cam[2][4], lab[2][4], sum[2], chratio;
4377 if ((unsigned) (colors-3) > 1) return;
4378 if (verbose) fprintf (stderr,_("Blending highlights...\n"));
4379 FORCC if (clip > (i = 65535*pre_mul[c])) clip = i;
4380 for (row=0; row < height; row++)
4381 for (col=0; col < width; col++) {
4382 FORCC if (image[row*width+col][c] > clip) break;
4383 if (c == colors) continue;
4385 cam[0][c] = image[row*width+col][c];
4386 cam[1][c] = MIN(cam[0][c],clip);
4388 for (i=0; i < 2; i++) {
4389 FORCC for (lab[i][c]=j=0; j < colors; j++)
4390 lab[i][c] += trans[colors-3][c][j] * cam[i][j];
4391 for (sum[i]=0,c=1; c < colors; c++)
4392 sum[i] += SQR(lab[i][c]);
4394 chratio = sqrt(sum[1]/sum[0]);
4395 for (c=1; c < colors; c++)
4396 lab[0][c] *= chratio;
4397 FORCC for (cam[0][c]=j=0; j < colors; j++)
4398 cam[0][c] += itrans[colors-3][c][j] * lab[0][j];
4399 FORCC image[row*width+col][c] = cam[0][c] / colors;
4403 #define SCALE (4 >> shrink)
4404 void CLASS recover_highlights()
4406 float *map, sum, wgt, grow;
4407 int hsat[4], count, spread, change, val, i;
4408 unsigned high, wide, mrow, mcol, row, col, kc, c, d, y, x;
4410 static const signed char dir[8][2] =
4411 { {-1,-1}, {-1,0}, {-1,1}, {0,1}, {1,1}, {1,0}, {1,-1}, {0,-1} };
4413 if (verbose) fprintf (stderr,_("Rebuilding highlights...\n"));
4415 grow = pow (2, 4-highlight);
4416 FORCC hsat[c] = 32000 * pre_mul[c];
4417 for (kc=0, c=1; c < colors; c++)
4418 if (pre_mul[kc] < pre_mul[c]) kc = c;
4419 high = height / SCALE;
4420 wide = width / SCALE;
4421 map = (float *) calloc (high*wide, sizeof *map);
4422 merror (map, "recover_highlights()");
4423 FORCC if (c != kc) {
4424 memset (map, 0, high*wide*sizeof *map);
4425 for (mrow=0; mrow < high; mrow++)
4426 for (mcol=0; mcol < wide; mcol++) {
4427 sum = wgt = count = 0;
4428 for (row = mrow*SCALE; row < (mrow+1)*SCALE; row++)
4429 for (col = mcol*SCALE; col < (mcol+1)*SCALE; col++) {
4430 pixel = image[row*width+col];
4431 if (pixel[c] / hsat[c] == 1 && pixel[kc] > 24000) {
4437 if (count == SCALE*SCALE)
4438 map[mrow*wide+mcol] = sum / wgt;
4440 for (spread = 32/grow; spread--; ) {
4441 for (mrow=0; mrow < high; mrow++)
4442 for (mcol=0; mcol < wide; mcol++) {
4443 if (map[mrow*wide+mcol]) continue;
4445 for (d=0; d < 8; d++) {
4446 y = mrow + dir[d][0];
4447 x = mcol + dir[d][1];
4448 if (y < high && x < wide && map[y*wide+x] > 0) {
4449 sum += (1 + (d & 1)) * map[y*wide+x];
4450 count += 1 + (d & 1);
4454 map[mrow*wide+mcol] = - (sum+grow) / (count+grow);
4456 for (change=i=0; i < high*wide; i++)
4463 for (i=0; i < high*wide; i++)
4464 if (map[i] == 0) map[i] = 1;
4465 for (mrow=0; mrow < high; mrow++)
4466 for (mcol=0; mcol < wide; mcol++) {
4467 for (row = mrow*SCALE; row < (mrow+1)*SCALE; row++)
4468 for (col = mcol*SCALE; col < (mcol+1)*SCALE; col++) {
4469 pixel = image[row*width+col];
4470 if (pixel[c] / hsat[c] > 1) {
4471 val = pixel[kc] * map[mrow*wide+mcol];
4472 if (pixel[c] < val) pixel[c] = CLIP(val);
4481 void CLASS tiff_get (unsigned base,
4482 unsigned *tag, unsigned *type, unsigned *len, unsigned *save)
4487 *save = ftell(ifp) + 4;
4488 if (*len * ("11124811248488"[*type < 14 ? *type:0]-'0') > 4)
4489 fseek (ifp, get4()+base, SEEK_SET);
4492 void CLASS parse_thumb_note (int base, unsigned toff, unsigned tlen)
4494 unsigned entries, tag, type, len, save;
4498 tiff_get (base, &tag, &type, &len, &save);
4499 if (tag == toff) thumb_offset = get4()+base;
4500 if (tag == tlen) thumb_length = get4();
4501 fseek (ifp, save, SEEK_SET);
4505 int CLASS parse_tiff_ifd (int base);
4507 void CLASS parse_makernote (int base, int uptag)
4509 static const uchar xlat[2][256] = {
4510 { 0xc1,0xbf,0x6d,0x0d,0x59,0xc5,0x13,0x9d,0x83,0x61,0x6b,0x4f,0xc7,0x7f,0x3d,0x3d,
4511 0x53,0x59,0xe3,0xc7,0xe9,0x2f,0x95,0xa7,0x95,0x1f,0xdf,0x7f,0x2b,0x29,0xc7,0x0d,
4512 0xdf,0x07,0xef,0x71,0x89,0x3d,0x13,0x3d,0x3b,0x13,0xfb,0x0d,0x89,0xc1,0x65,0x1f,
4513 0xb3,0x0d,0x6b,0x29,0xe3,0xfb,0xef,0xa3,0x6b,0x47,0x7f,0x95,0x35,0xa7,0x47,0x4f,
4514 0xc7,0xf1,0x59,0x95,0x35,0x11,0x29,0x61,0xf1,0x3d,0xb3,0x2b,0x0d,0x43,0x89,0xc1,
4515 0x9d,0x9d,0x89,0x65,0xf1,0xe9,0xdf,0xbf,0x3d,0x7f,0x53,0x97,0xe5,0xe9,0x95,0x17,
4516 0x1d,0x3d,0x8b,0xfb,0xc7,0xe3,0x67,0xa7,0x07,0xf1,0x71,0xa7,0x53,0xb5,0x29,0x89,
4517 0xe5,0x2b,0xa7,0x17,0x29,0xe9,0x4f,0xc5,0x65,0x6d,0x6b,0xef,0x0d,0x89,0x49,0x2f,
4518 0xb3,0x43,0x53,0x65,0x1d,0x49,0xa3,0x13,0x89,0x59,0xef,0x6b,0xef,0x65,0x1d,0x0b,
4519 0x59,0x13,0xe3,0x4f,0x9d,0xb3,0x29,0x43,0x2b,0x07,0x1d,0x95,0x59,0x59,0x47,0xfb,
4520 0xe5,0xe9,0x61,0x47,0x2f,0x35,0x7f,0x17,0x7f,0xef,0x7f,0x95,0x95,0x71,0xd3,0xa3,
4521 0x0b,0x71,0xa3,0xad,0x0b,0x3b,0xb5,0xfb,0xa3,0xbf,0x4f,0x83,0x1d,0xad,0xe9,0x2f,
4522 0x71,0x65,0xa3,0xe5,0x07,0x35,0x3d,0x0d,0xb5,0xe9,0xe5,0x47,0x3b,0x9d,0xef,0x35,
4523 0xa3,0xbf,0xb3,0xdf,0x53,0xd3,0x97,0x53,0x49,0x71,0x07,0x35,0x61,0x71,0x2f,0x43,
4524 0x2f,0x11,0xdf,0x17,0x97,0xfb,0x95,0x3b,0x7f,0x6b,0xd3,0x25,0xbf,0xad,0xc7,0xc5,
4525 0xc5,0xb5,0x8b,0xef,0x2f,0xd3,0x07,0x6b,0x25,0x49,0x95,0x25,0x49,0x6d,0x71,0xc7 },
4526 { 0xa7,0xbc,0xc9,0xad,0x91,0xdf,0x85,0xe5,0xd4,0x78,0xd5,0x17,0x46,0x7c,0x29,0x4c,
4527 0x4d,0x03,0xe9,0x25,0x68,0x11,0x86,0xb3,0xbd,0xf7,0x6f,0x61,0x22,0xa2,0x26,0x34,
4528 0x2a,0xbe,0x1e,0x46,0x14,0x68,0x9d,0x44,0x18,0xc2,0x40,0xf4,0x7e,0x5f,0x1b,0xad,
4529 0x0b,0x94,0xb6,0x67,0xb4,0x0b,0xe1,0xea,0x95,0x9c,0x66,0xdc,0xe7,0x5d,0x6c,0x05,
4530 0xda,0xd5,0xdf,0x7a,0xef,0xf6,0xdb,0x1f,0x82,0x4c,0xc0,0x68,0x47,0xa1,0xbd,0xee,
4531 0x39,0x50,0x56,0x4a,0xdd,0xdf,0xa5,0xf8,0xc6,0xda,0xca,0x90,0xca,0x01,0x42,0x9d,
4532 0x8b,0x0c,0x73,0x43,0x75,0x05,0x94,0xde,0x24,0xb3,0x80,0x34,0xe5,0x2c,0xdc,0x9b,
4533 0x3f,0xca,0x33,0x45,0xd0,0xdb,0x5f,0xf5,0x52,0xc3,0x21,0xda,0xe2,0x22,0x72,0x6b,
4534 0x3e,0xd0,0x5b,0xa8,0x87,0x8c,0x06,0x5d,0x0f,0xdd,0x09,0x19,0x93,0xd0,0xb9,0xfc,
4535 0x8b,0x0f,0x84,0x60,0x33,0x1c,0x9b,0x45,0xf1,0xf0,0xa3,0x94,0x3a,0x12,0x77,0x33,
4536 0x4d,0x44,0x78,0x28,0x3c,0x9e,0xfd,0x65,0x57,0x16,0x94,0x6b,0xfb,0x59,0xd0,0xc8,
4537 0x22,0x36,0xdb,0xd2,0x63,0x98,0x43,0xa1,0x04,0x87,0x86,0xf7,0xa6,0x26,0xbb,0xd6,
4538 0x59,0x4d,0xbf,0x6a,0x2e,0xaa,0x2b,0xef,0xe6,0x78,0xb6,0x4e,0xe0,0x2f,0xdc,0x7c,
4539 0xbe,0x57,0x19,0x32,0x7e,0x2a,0xd0,0xb8,0xba,0x29,0x00,0x3c,0x52,0x7d,0xa8,0x49,
4540 0x3b,0x2d,0xeb,0x25,0x49,0xfa,0xa3,0xaa,0x39,0xa7,0xc5,0xa7,0x50,0x11,0x36,0xfb,
4541 0xc6,0x67,0x4a,0xf5,0xa5,0x12,0x65,0x7e,0xb0,0xdf,0xaf,0x4e,0xb3,0x61,0x7f,0x2f } };
4542 unsigned offset=0, entries, tag, type, len, save, c;
4543 unsigned ver97=0, serial=0, i, wbi=0, wb[4]={0,0,0,0};
4544 uchar buf97[324], ci, cj, ck;
4545 short morder, sorder=order;
4548 The MakerNote might have its own TIFF header (possibly with
4549 its own byte-order!), or it might just be a table.
4551 if (!strcmp(make,"Nokia")) return;
4552 fread (buf, 1, 10, ifp);
4553 if (!strncmp (buf,"KDK" ,3) || /* these aren't TIFF tables */
4554 !strncmp (buf,"VER" ,3) ||
4555 !strncmp (buf,"IIII",4) ||
4556 !strncmp (buf,"MMMM",4)) return;
4557 if (!strncmp (buf,"KC" ,2) || /* Konica KD-400Z, KD-510Z */
4558 !strncmp (buf,"MLY" ,3)) { /* Minolta DiMAGE G series */
4560 while ((i=ftell(ifp)) < data_offset && i < 16384) {
4561 wb[0] = wb[2]; wb[2] = wb[1]; wb[1] = wb[3];
4563 if (wb[1] == 256 && wb[3] == 256 &&
4564 wb[0] > 256 && wb[0] < 640 && wb[2] > 256 && wb[2] < 640)
4565 FORC4 cam_mul[c] = wb[c];
4569 if (!strcmp (buf,"Nikon")) {
4572 if (get2() != 42) goto quit;
4574 fseek (ifp, offset-8, SEEK_CUR);
4575 } else if (!strcmp (buf,"OLYMPUS")) {
4576 base = ftell(ifp)-10;
4577 fseek (ifp, -2, SEEK_CUR);
4578 order = get2(); get2();
4579 } else if (!strncmp (buf,"SONY",4) ||
4580 !strcmp (buf,"Panasonic")) {
4582 } else if (!strncmp (buf,"FUJIFILM",8)) {
4583 base = ftell(ifp)-10;
4585 fseek (ifp, 2, SEEK_CUR);
4586 } else if (!strcmp (buf,"OLYMP") ||
4587 !strcmp (buf,"LEICA") ||
4588 !strcmp (buf,"Ricoh") ||
4589 !strcmp (buf,"EPSON"))
4590 fseek (ifp, -2, SEEK_CUR);
4591 else if (!strcmp (buf,"AOC") ||
4592 !strcmp (buf,"QVC"))
4593 fseek (ifp, -4, SEEK_CUR);
4595 fseek (ifp, -10, SEEK_CUR);
4596 if (!strncmp(make,"SAMSUNG",7))
4600 if (entries > 1000) return;
4604 tiff_get (base, &tag, &type, &len, &save);
4606 if (tag == 2 && strstr(make,"NIKON") && !iso_speed)
4607 iso_speed = (get2(),get2());
4608 if (tag == 4 && len > 26 && len < 35) {
4609 if ((i=(get4(),get2())) != 0x7fff && !iso_speed)
4610 iso_speed = 50 * pow (2, i/32.0 - 4);
4611 if ((i=(get2(),get2())) != 0x7fff && !aperture)
4612 aperture = pow (2, i/64.0);
4613 if ((i=get2()) != 0xffff && !shutter)
4614 shutter = pow (2, (short) i/-32.0);
4615 wbi = (get2(),get2());
4616 shot_order = (get2(),get2());
4618 if ((tag == 4 || tag == 0x114) && !strncmp(make,"KONICA",6)) {
4619 fseek (ifp, tag == 4 ? 140:160, SEEK_CUR);
4621 case 72: flip = 0; break;
4622 case 76: flip = 6; break;
4623 case 82: flip = 5; break;
4626 if (tag == 7 && type == 2 && len > 20)
4627 fgets (model2, 64, ifp);
4628 if (tag == 8 && type == 4)
4629 shot_order = get4();
4630 if (tag == 9 && !strcmp(make,"Canon"))
4631 fread (artist, 64, 1, ifp);
4632 if (tag == 0xc && len == 4) {
4633 cam_mul[0] = getreal(type);
4634 cam_mul[2] = getreal(type);
4636 if (tag == 0xd && type == 7 && get2() == 0xaaaa) {
4637 for (c=i=2; (ushort) c != 0xbbbb && i < len; i++)
4638 c = c << 8 | fgetc(ifp);
4639 while ((i+=4) < len-5)
4640 if (get4() == 257 && (i=len) && (c = (get4(),fgetc(ifp))) < 3)
4641 flip = "065"[c]-'0';
4643 if (tag == 0x10 && type == 4)
4645 if (tag == 0x11 && is_raw && !strncmp(make,"NIKON",5)) {
4646 fseek (ifp, get4()+base, SEEK_SET);
4647 parse_tiff_ifd (base);
4649 if (tag == 0x14 && type == 7) {
4651 fseek (ifp, 1248, SEEK_CUR);
4654 fread (buf, 1, 10, ifp);
4655 if (!strncmp(buf,"NRW ",4)) {
4656 fseek (ifp, strcmp(buf+4,"0100") ? 46:1546, SEEK_CUR);
4657 cam_mul[0] = get4() << 2;
4658 cam_mul[1] = get4() + get4();
4659 cam_mul[2] = get4() << 2;
4662 if (tag == 0x15 && type == 2 && is_raw)
4663 fread (model, 64, 1, ifp);
4664 if (strstr(make,"PENTAX")) {
4665 if (tag == 0x1b) tag = 0x1018;
4666 if (tag == 0x1c) tag = 0x1017;
4669 while ((c = fgetc(ifp)) && c != EOF)
4670 serial = serial*10 + (isdigit(c) ? c - '0' : c % 10);
4671 if (tag == 0x81 && type == 4) {
4672 data_offset = get4();
4673 fseek (ifp, data_offset + 41, SEEK_SET);
4674 raw_height = get2() * 2;
4676 filters = 0x61616161;
4678 if (tag == 0x29 && type == 1) {
4679 c = wbi < 18 ? "012347800000005896"[wbi]-'0' : 0;
4680 fseek (ifp, 8 + c*32, SEEK_CUR);
4681 FORC4 cam_mul[c ^ (c >> 1) ^ 1] = get4();
4683 if ((tag == 0x81 && type == 7) ||
4684 (tag == 0x100 && type == 7) ||
4685 (tag == 0x280 && type == 1)) {
4686 thumb_offset = ftell(ifp);
4689 if (tag == 0x88 && type == 4 && (thumb_offset = get4()))
4690 thumb_offset += base;
4691 if (tag == 0x89 && type == 4)
4692 thumb_length = get4();
4693 if (tag == 0x8c || tag == 0x96)
4694 meta_offset = ftell(ifp);
4696 for (i=0; i < 4; i++)
4697 ver97 = ver97 * 10 + fgetc(ifp)-'0';
4700 fseek (ifp, 68, SEEK_CUR);
4701 FORC4 cam_mul[(c >> 1) | ((c & 1) << 1)] = get2();
4704 fseek (ifp, 6, SEEK_CUR);
4707 fseek (ifp, 16, SEEK_CUR);
4708 FORC4 cam_mul[c] = get2();
4711 if (ver97 != 205) fseek (ifp, 280, SEEK_CUR);
4712 fread (buf97, 324, 1, ifp);
4715 if (tag == 0xa1 && type == 7) {
4717 fseek (ifp, 140, SEEK_CUR);
4718 FORC3 cam_mul[c] = get4();
4720 if (tag == 0xa4 && type == 3) {
4721 fseek (ifp, wbi*48, SEEK_CUR);
4722 FORC3 cam_mul[c] = get2();
4724 if (tag == 0xa7 && (unsigned) (ver97-200) < 17) {
4725 ci = xlat[0][serial & 0xff];
4726 cj = xlat[1][fgetc(ifp)^fgetc(ifp)^fgetc(ifp)^fgetc(ifp)];
4728 for (i=0; i < 324; i++)
4729 buf97[i] ^= (cj += ci * ck++);
4730 i = "66666>666;6A;:;55"[ver97-200] - '0';
4731 FORC4 cam_mul[c ^ (c >> 1) ^ (i & 1)] =
4732 sget2 (buf97 + (i & -2) + c*2);
4734 if (tag == 0x200 && len == 3)
4735 shot_order = (get4(),get4());
4736 if (tag == 0x200 && len == 4)
4737 FORC4 cblack[c ^ c >> 1] = get2();
4738 if (tag == 0x201 && len == 4)
4740 if (tag == 0x220 && type == 7)
4741 meta_offset = ftell(ifp);
4742 if (tag == 0x401 && type == 4 && len == 4)
4743 FORC4 cblack[c ^ c >> 1] = get4();
4744 if (tag == 0xe01) { /* Nikon Capture Note */
4746 fseek (ifp, 22, SEEK_CUR);
4747 for (offset=22; offset+22 < len; offset += 22+i) {
4749 fseek (ifp, 14, SEEK_CUR);
4751 if (tag == 0x76a43207) flip = get2();
4752 else fseek (ifp, i, SEEK_CUR);
4755 if (tag == 0xe80 && len == 256 && type == 7) {
4756 fseek (ifp, 48, SEEK_CUR);
4757 cam_mul[0] = get2() * 508 * 1.078 / 0x10000;
4758 cam_mul[2] = get2() * 382 * 1.173 / 0x10000;
4760 if (tag == 0xf00 && type == 7) {
4762 fseek (ifp, 176, SEEK_CUR);
4763 else if (len == 734 || len == 1502)
4764 fseek (ifp, 148, SEEK_CUR);
4768 if ((tag == 0x1011 && len == 9) || tag == 0x20400200)
4769 for (i=0; i < 3; i++)
4770 FORC3 cmatrix[i][c] = ((short) get2()) / 256.0;
4771 if ((tag == 0x1012 || tag == 0x20400600) && len == 4)
4772 FORC4 cblack[c ^ c >> 1] = get2();
4773 if (tag == 0x1017 || tag == 0x20400100)
4774 cam_mul[0] = get2() / 256.0;
4775 if (tag == 0x1018 || tag == 0x20400100)
4776 cam_mul[2] = get2() / 256.0;
4777 if (tag == 0x2011 && len == 2) {
4780 cam_mul[0] = get2() / 256.0;
4781 cam_mul[2] = get2() / 256.0;
4783 if ((tag | 0x70) == 0x2070 && type == 4)
4784 fseek (ifp, get4()+base, SEEK_SET);
4785 if (tag == 0x2010 && type != 7)
4786 load_raw = &CLASS olympus_load_raw;
4788 parse_thumb_note (base, 257, 258);
4790 parse_makernote (base, 0x2040);
4791 if (tag == 0xb028) {
4792 fseek (ifp, get4()+base, SEEK_SET);
4793 parse_thumb_note (base, 136, 137);
4795 if (tag == 0x4001 && len > 500) {
4796 i = len == 582 ? 50 : len == 653 ? 68 : len == 5120 ? 142 : 126;
4797 fseek (ifp, i, SEEK_CUR);
4799 FORC4 cam_mul[c ^ (c >> 1)] = get2();
4800 i = len >> 3 == 164 ? 112:22;
4801 fseek (ifp, i, SEEK_CUR);
4802 FORC4 sraw_mul[c ^ (c >> 1)] = get2();
4805 FORC4 cam_mul[c ^ (c >> 1)] = get4();
4807 FORC4 cam_mul[c ^ (c >> 1)] -= get4();
4809 fseek (ifp, save, SEEK_SET);
4816 Since the TIFF DateTime string has no timezone information,
4817 assume that the camera's clock was set to Universal Time.
4819 void CLASS get_timestamp (int reversed)
4827 for (i=19; i--; ) str[i] = fgetc(ifp);
4829 fread (str, 19, 1, ifp);
4830 memset (&t, 0, sizeof t);
4831 if (sscanf (str, "%d:%d:%d %d:%d:%d", &t.tm_year, &t.tm_mon,
4832 &t.tm_mday, &t.tm_hour, &t.tm_min, &t.tm_sec) != 6)
4838 timestamp = mktime(&t);
4841 void CLASS parse_exif (int base)
4843 unsigned kodak, entries, tag, type, len, save, c;
4846 kodak = !strncmp(make,"EASTMAN",7) && tiff_nifds < 3;
4849 tiff_get (base, &tag, &type, &len, &save);
4851 case 33434: shutter = getreal(type); break;
4852 case 33437: aperture = getreal(type); break;
4853 case 34855: iso_speed = get2(); break;
4855 case 36868: get_timestamp(0); break;
4856 case 37377: if ((expo = -getreal(type)) < 128)
4857 shutter = pow (2, expo); break;
4858 case 37378: aperture = pow (2, getreal(type)/2); break;
4859 case 37386: focal_len = getreal(type); break;
4860 case 37500: parse_makernote (base, 0); break;
4861 case 40962: if (kodak) raw_width = get4(); break;
4862 case 40963: if (kodak) raw_height = get4(); break;
4864 if (get4() == 0x20002)
4865 for (exif_cfa=c=0; c < 8; c+=2)
4866 exif_cfa |= fgetc(ifp) * 0x01010101 << c;
4868 fseek (ifp, save, SEEK_SET);
4872 void CLASS parse_gps (int base)
4874 unsigned entries, tag, type, len, save, c;
4878 tiff_get (base, &tag, &type, &len, &save);
4880 case 1: case 3: case 5:
4881 gpsdata[29+tag/2] = getc(ifp); break;
4882 case 2: case 4: case 7:
4883 FORC(6) gpsdata[tag/3*6+c] = get4(); break;
4885 FORC(2) gpsdata[18+c] = get4(); break;
4887 fgets ((char *) (gpsdata+14+tag/3), MIN(len,12), ifp);
4889 fseek (ifp, save, SEEK_SET);
4893 void CLASS romm_coeff (float romm_cam[3][3])
4895 static const float rgb_romm[3][3] = /* ROMM == Kodak ProPhoto */
4896 { { 2.034193, -0.727420, -0.306766 },
4897 { -0.228811, 1.231729, -0.002922 },
4898 { -0.008565, -0.153273, 1.161839 } };
4901 for (i=0; i < 3; i++)
4902 for (j=0; j < 3; j++)
4903 for (cmatrix[i][j] = k=0; k < 3; k++)
4904 cmatrix[i][j] += rgb_romm[i][k] * romm_cam[k][j];
4907 void CLASS parse_mos (int offset)
4910 int skip, from, i, c, neut[4], planes=0, frot=0;
4911 static const char *mod[] =
4912 { "","DCB2","Volare","Cantare","CMost","Valeo 6","Valeo 11","Valeo 22",
4913 "Valeo 11p","Valeo 17","","Aptus 17","Aptus 22","Aptus 75","Aptus 65",
4914 "Aptus 54S","Aptus 65S","Aptus 75S","AFi 5","AFi 6","AFi 7",
4915 "","","","","","","","","","","","","","","","","","AFi-II 12" };
4916 float romm_cam[3][3];
4918 fseek (ifp, offset, SEEK_SET);
4920 if (get4() != 0x504b5453) break;
4922 fread (data, 1, 40, ifp);
4925 if (!strcmp(data,"JPEG_preview_data")) {
4926 thumb_offset = from;
4927 thumb_length = skip;
4929 if (!strcmp(data,"icc_camera_profile")) {
4930 profile_offset = from;
4931 profile_length = skip;
4933 if (!strcmp(data,"ShootObj_back_type")) {
4934 fscanf (ifp, "%d", &i);
4935 if ((unsigned) i < sizeof mod / sizeof (*mod))
4936 strcpy (model, mod[i]);
4938 if (!strcmp(data,"icc_camera_to_tone_matrix")) {
4939 for (i=0; i < 9; i++)
4940 romm_cam[0][i] = int_to_float(get4());
4941 romm_coeff (romm_cam);
4943 if (!strcmp(data,"CaptProf_color_matrix")) {
4944 for (i=0; i < 9; i++)
4945 fscanf (ifp, "%f", &romm_cam[0][i]);
4946 romm_coeff (romm_cam);
4948 if (!strcmp(data,"CaptProf_number_of_planes"))
4949 fscanf (ifp, "%d", &planes);
4950 if (!strcmp(data,"CaptProf_raw_data_rotation"))
4951 fscanf (ifp, "%d", &flip);
4952 if (!strcmp(data,"CaptProf_mosaic_pattern"))
4954 fscanf (ifp, "%d", &i);
4955 if (i == 1) frot = c ^ (c >> 1);
4957 if (!strcmp(data,"ImgProf_rotation_angle")) {
4958 fscanf (ifp, "%d", &i);
4961 if (!strcmp(data,"NeutObj_neutrals") && !cam_mul[0]) {
4962 FORC4 fscanf (ifp, "%d", neut+c);
4963 FORC3 cam_mul[c] = (float) neut[0] / neut[c+1];
4965 if (!strcmp(data,"Rows_data"))
4966 load_flags = get4();
4968 fseek (ifp, skip+from, SEEK_SET);
4971 filters = (planes == 1) * 0x01010101 *
4972 (uchar) "\x94\x61\x16\x49"[(flip/90 + frot) & 3];
4975 void CLASS linear_table (unsigned len)
4978 if (len > 0x1000) len = 0x1000;
4979 read_shorts (curve, len);
4980 for (i=len; i < 0x1000; i++)
4981 curve[i] = curve[i-1];
4982 maximum = curve[0xfff];
4985 void CLASS parse_kodak_ifd (int base)
4987 unsigned entries, tag, type, len, save;
4988 int i, c, wbi=-2, wbtemp=6500;
4989 float mul[3]={1,1,1}, num;
4990 static const int wbtag[] = { 64037,64040,64039,64041,-1,-1,64042 };
4993 if (entries > 1024) return;
4995 tiff_get (base, &tag, &type, &len, &save);
4996 if (tag == 1020) wbi = getint(type);
4997 if (tag == 1021 && len == 72) { /* WB set in software */
4998 fseek (ifp, 40, SEEK_CUR);
4999 FORC3 cam_mul[c] = 2048.0 / get2();
5002 if (tag == 2118) wbtemp = getint(type);
5003 if (tag == 2130 + wbi)
5004 FORC3 mul[c] = getreal(type);
5005 if (tag == 2140 + wbi && wbi >= 0)
5007 for (num=i=0; i < 4; i++)
5008 num += getreal(type) * pow (wbtemp/100.0, i);
5009 cam_mul[c] = 2048 / (num * mul[c]);
5011 if (tag == 2317) linear_table (len);
5012 if (tag == 6020) iso_speed = getint(type);
5013 if (tag == 64013) wbi = fgetc(ifp);
5014 if ((unsigned) wbi < 7 && tag == wbtag[wbi])
5015 FORC3 cam_mul[c] = get4();
5016 if (tag == 64019) width = getint(type);
5017 if (tag == 64020) height = (getint(type)+1) & -2;
5018 fseek (ifp, save, SEEK_SET);
5022 void CLASS parse_minolta (int base);
5023 int CLASS parse_tiff (int base);
5025 int CLASS parse_tiff_ifd (int base)
5027 unsigned entries, tag, type, len, plen=16, save;
5028 int ifd, use_cm=0, cfa, i, j, c, ima_len=0;
5029 int blrr=1, blrc=1, dblack[] = { 0,0,0,0 };
5030 char software[64], *cbuf, *cp;
5031 uchar cfa_pat[16], cfa_pc[] = { 0,1,2,3 }, tab[256];
5032 double cc[4][4], cm[4][3], cam_xyz[4][3], num;
5033 double ab[]={ 1,1,1,1 }, asn[] = { 0,0,0,0 }, xyz[] = { 1,1,1 };
5034 unsigned sony_curve[] = { 0,0,0,0,0,4095 };
5035 unsigned *buf, sony_offset=0, sony_length=0, sony_key=0;
5039 if (tiff_nifds >= sizeof tiff_ifd / sizeof tiff_ifd[0])
5042 for (j=0; j < 4; j++)
5043 for (i=0; i < 4; i++)
5046 if (entries > 512) return 1;
5048 tiff_get (base, &tag, &type, &len, &save);
5050 case 5: width = get2(); break;
5051 case 6: height = get2(); break;
5052 case 7: width += get2(); break;
5053 case 9: filters = get2(); break;
5055 if (type == 3 && len == 1)
5056 cam_mul[(tag-17)*2] = get2() / 256.0;
5059 if (type == 3) iso_speed = get2();
5061 case 36: case 37: case 38:
5062 cam_mul[tag-0x24] = get2();
5065 if (len < 50 || cam_mul[0]) break;
5066 fseek (ifp, 12, SEEK_CUR);
5067 FORC3 cam_mul[c] = get2();
5070 if (type != 7 || fgetc(ifp) != 0xff || fgetc(ifp) != 0xd8) break;
5071 thumb_offset = ftell(ifp) - 2;
5074 case 61440: /* Fuji HS10 table */
5075 parse_tiff_ifd (base);
5077 case 2: case 256: case 61441: /* ImageWidth */
5078 tiff_ifd[ifd].width = getint(type);
5080 case 3: case 257: case 61442: /* ImageHeight */
5081 tiff_ifd[ifd].height = getint(type);
5083 case 258: /* BitsPerSample */
5085 tiff_ifd[ifd].samples = len & 7;
5086 tiff_ifd[ifd].bps = getint(type);
5090 load_raw = &CLASS packed_load_raw;
5091 load_flags = get4() && (filters=0x16161616) ? 24:80;
5093 case 259: /* Compression */
5094 tiff_ifd[ifd].comp = getint(type);
5096 case 262: /* PhotometricInterpretation */
5097 tiff_ifd[ifd].phint = get2();
5099 case 270: /* ImageDescription */
5100 fread (desc, 512, 1, ifp);
5102 case 271: /* Make */
5103 fgets (make, 64, ifp);
5105 case 272: /* Model */
5106 fgets (model, 64, ifp);
5108 case 280: /* Panasonic RW2 offset */
5109 if (type != 4) break;
5110 load_raw = &CLASS panasonic_load_raw;
5111 load_flags = 0x2008;
5112 case 273: /* StripOffset */
5113 case 513: /* JpegIFOffset */
5115 tiff_ifd[ifd].offset = get4()+base;
5116 if (!tiff_ifd[ifd].bps && tiff_ifd[ifd].offset > 0) {
5117 fseek (ifp, tiff_ifd[ifd].offset, SEEK_SET);
5118 if (ljpeg_start (&jh, 1)) {
5119 tiff_ifd[ifd].comp = 6;
5120 tiff_ifd[ifd].width = jh.wide;
5121 tiff_ifd[ifd].height = jh.high;
5122 tiff_ifd[ifd].bps = jh.bits;
5123 tiff_ifd[ifd].samples = jh.clrs;
5124 if (!(jh.sraw || (jh.clrs & 1)))
5125 tiff_ifd[ifd].width *= jh.clrs;
5127 parse_tiff (tiff_ifd[ifd].offset + 12);
5132 case 274: /* Orientation */
5133 tiff_ifd[ifd].flip = "50132467"[get2() & 7]-'0';
5135 case 277: /* SamplesPerPixel */
5136 tiff_ifd[ifd].samples = getint(type) & 7;
5138 case 279: /* StripByteCounts */
5141 tiff_ifd[ifd].bytes = get4();
5144 FORC3 cam_mul[(4-c) % 3] = getint(type);
5146 case 305: case 11: /* Software */
5147 fgets (software, 64, ifp);
5148 if (!strncmp(software,"Adobe",5) ||
5149 !strncmp(software,"dcraw",5) ||
5150 !strncmp(software,"UFRaw",5) ||
5151 !strncmp(software,"Bibble",6) ||
5152 !strncmp(software,"Nikon Scan",10) ||
5153 !strcmp (software,"Digital Photo Professional"))
5156 case 306: /* DateTime */
5159 case 315: /* Artist */
5160 fread (artist, 64, 1, ifp);
5162 case 322: /* TileWidth */
5163 tiff_ifd[ifd].tile_width = getint(type);
5165 case 323: /* TileLength */
5166 tiff_ifd[ifd].tile_length = getint(type);
5168 case 324: /* TileOffsets */
5169 tiff_ifd[ifd].offset = len > 1 ? ftell(ifp) : get4();
5171 load_raw = &CLASS sinar_4shot_load_raw;
5175 case 330: /* SubIFDs */
5176 if (!strcmp(model,"DSLR-A100") && tiff_ifd[ifd].width == 3872) {
5177 load_raw = &CLASS sony_arw_load_raw;
5178 data_offset = get4()+base;
5183 fseek (ifp, get4()+base, SEEK_SET);
5184 if (parse_tiff_ifd (base)) break;
5185 fseek (ifp, i+4, SEEK_SET);
5189 strcpy (make, "Sarnoff");
5193 FORC4 sony_curve[c+1] = get2() >> 2 & 0xfff;
5194 for (i=0; i < 5; i++)
5195 for (j = sony_curve[i]+1; j <= sony_curve[i+1]; j++)
5196 curve[j] = curve[j-1] + (1 << i);
5198 case 29184: sony_offset = get4(); break;
5199 case 29185: sony_length = get4(); break;
5200 case 29217: sony_key = get4(); break;
5202 parse_minolta (ftell(ifp));
5206 FORC4 cam_mul[c ^ (c < 2)] = get2();
5209 FORC4 cam_mul[c] = get2();
5210 i = (cam_mul[1] == 1024 && cam_mul[2] == 1024) << 1;
5211 SWAP (cam_mul[i],cam_mul[i+1])
5213 case 33405: /* Model2 */
5214 fgets (model2, 64, ifp);
5216 case 33422: /* CFAPattern */
5217 case 64777: /* Kodak P-series */
5218 if ((plen=len) > 16) plen = 16;
5219 fread (cfa_pat, 1, plen, ifp);
5220 for (colors=cfa=i=0; i < plen; i++) {
5221 colors += !(cfa & (1 << cfa_pat[i]));
5222 cfa |= 1 << cfa_pat[i];
5224 if (cfa == 070) memcpy (cfa_pc,"\003\004\005",3); /* CMY */
5225 if (cfa == 072) memcpy (cfa_pc,"\005\003\004\001",4); /* GMCY */
5229 fseek (ifp, get4()+base, SEEK_SET);
5230 parse_kodak_ifd (base);
5232 case 33434: /* ExposureTime */
5233 shutter = getreal(type);
5235 case 33437: /* FNumber */
5236 aperture = getreal(type);
5238 case 34306: /* Leaf white balance */
5239 FORC4 cam_mul[c ^ 1] = 4096.0 / get2();
5241 case 34307: /* Leaf CatchLight color matrix */
5242 fread (software, 1, 7, ifp);
5243 if (strncmp(software,"MATRIX",6)) break;
5245 for (raw_color = i=0; i < 3; i++) {
5246 FORC4 fscanf (ifp, "%f", &rgb_cam[i][c^1]);
5247 if (!use_camera_wb) continue;
5249 FORC4 num += rgb_cam[i][c];
5250 FORC4 rgb_cam[i][c] /= num;
5253 case 34310: /* Leaf metadata */
5254 parse_mos (ftell(ifp));
5256 strcpy (make, "Leaf");
5258 case 34665: /* EXIF tag */
5259 fseek (ifp, get4()+base, SEEK_SET);
5262 case 34853: /* GPSInfo tag */
5263 fseek (ifp, get4()+base, SEEK_SET);
5266 case 34675: /* InterColorProfile */
5267 case 50831: /* AsShotICCProfile */
5268 profile_offset = ftell(ifp);
5269 profile_length = len;
5271 case 37122: /* CompressedBitsPerPixel */
5272 kodak_cbpp = get4();
5274 case 37386: /* FocalLength */
5275 focal_len = getreal(type);
5277 case 37393: /* ImageNumber */
5278 shot_order = getint(type);
5280 case 37400: /* old Kodak KDC tag */
5281 for (raw_color = i=0; i < 3; i++) {
5283 FORC3 rgb_cam[i][c] = getreal(type);
5286 case 46275: /* Imacon tags */
5287 strcpy (make, "Imacon");
5288 data_offset = ftell(ifp);
5292 if (!ima_len) break;
5293 fseek (ifp, 38, SEEK_CUR);
5295 fseek (ifp, 40, SEEK_CUR);
5297 raw_height = get4();
5298 left_margin = get4() & 7;
5299 width = raw_width - left_margin - (get4() & 7);
5300 top_margin = get4() & 7;
5301 height = raw_height - top_margin - (get4() & 7);
5302 if (raw_width == 7262) {
5307 fseek (ifp, 52, SEEK_CUR);
5308 FORC3 cam_mul[c] = getreal(11);
5309 fseek (ifp, 114, SEEK_CUR);
5310 flip = (get2() >> 7) * 90;
5311 if (width * height * 6 == ima_len) {
5312 if (flip % 180 == 90) SWAP(width,height);
5314 raw_height = height;
5315 left_margin = top_margin = filters = flip = 0;
5317 sprintf (model, "Ixpress %d-Mp", height*width/1000000);
5318 load_raw = &CLASS imacon_full_load_raw;
5320 if (left_margin & 1) filters = 0x61616161;
5321 load_raw = &CLASS unpacked_load_raw;
5325 case 50454: /* Sinar tag */
5327 if (!(cbuf = (char *) malloc(len))) break;
5328 fread (cbuf, 1, len, ifp);
5329 for (cp = cbuf-1; cp && cp < cbuf+len; cp = strchr(cp,'\n'))
5330 if (!strncmp (++cp,"Neutral ",8))
5331 sscanf (cp+8, "%f %f %f", cam_mul, cam_mul+1, cam_mul+2);
5335 if (!make[0]) strcpy (make, "Hasselblad");
5337 case 50459: /* Hasselblad tag */
5342 fseek (ifp, j+(get2(),get4()), SEEK_SET);
5348 case 50706: /* DNGVersion */
5349 FORC4 dng_version = (dng_version << 8) + fgetc(ifp);
5350 if (!make[0]) strcpy (make, "DNG");
5353 case 50710: /* CFAPlaneColor */
5354 if (len > 4) len = 4;
5356 fread (cfa_pc, 1, colors, ifp);
5358 FORCC tab[cfa_pc[c]] = c;
5361 filters = filters << 2 | tab[cfa_pat[i % plen]];
5363 case 50711: /* CFALayout */
5366 filters = 0x49494949;
5370 case 50712: /* LinearizationTable */
5373 case 50713: /* BlackLevelRepeatDim */
5379 case 50714: /* BlackLevel */
5380 black = getreal(type);
5381 if (!filters || !~filters) break;
5383 dblack[1] = (blrc == 2) ? getreal(type):dblack[0];
5384 dblack[2] = (blrr == 2) ? getreal(type):dblack[0];
5385 dblack[3] = (blrc == 2 && blrr == 2) ? getreal(type):dblack[1];
5387 filters |= ((filters >> 2 & 0x22222222) |
5388 (filters << 2 & 0x88888888)) & filters << 1;
5389 FORC4 cblack[filters >> (c << 1) & 3] = dblack[c];
5392 case 50715: /* BlackLevelDeltaH */
5393 case 50716: /* BlackLevelDeltaV */
5394 for (num=i=0; i < len; i++)
5395 num += getreal(type);
5396 black += num/len + 0.5;
5398 case 50717: /* WhiteLevel */
5399 maximum = getint(type);
5401 case 50718: /* DefaultScale */
5402 pixel_aspect = getreal(type);
5403 pixel_aspect /= getreal(type);
5405 case 50721: /* ColorMatrix1 */
5406 case 50722: /* ColorMatrix2 */
5407 FORCC for (j=0; j < 3; j++)
5408 cm[c][j] = getreal(type);
5411 case 50723: /* CameraCalibration1 */
5412 case 50724: /* CameraCalibration2 */
5413 for (i=0; i < colors; i++)
5414 FORCC cc[i][c] = getreal(type);
5416 case 50727: /* AnalogBalance */
5417 FORCC ab[c] = getreal(type);
5419 case 50728: /* AsShotNeutral */
5420 FORCC asn[c] = getreal(type);
5422 case 50729: /* AsShotWhiteXY */
5423 xyz[0] = getreal(type);
5424 xyz[1] = getreal(type);
5425 xyz[2] = 1 - xyz[0] - xyz[1];
5426 FORC3 xyz[c] /= d65_white[c];
5428 case 50740: /* DNGPrivateData */
5429 if (dng_version) break;
5430 parse_minolta (j = get4()+base);
5431 fseek (ifp, j, SEEK_SET);
5432 parse_tiff_ifd (base);
5435 read_shorts (cr2_slice, 3);
5437 case 50829: /* ActiveArea */
5438 top_margin = getint(type);
5439 left_margin = getint(type);
5440 height = getint(type) - top_margin;
5441 width = getint(type) - left_margin;
5443 case 50830: /* MaskedAreas */
5444 for (i=0; i < len && i < 32; i++)
5445 mask[0][i] = getint(type);
5448 case 51009: /* OpcodeList2 */
5449 meta_offset = ftell(ifp);
5451 case 64772: /* Kodak P-series */
5452 if (len < 13) break;
5453 fseek (ifp, 16, SEEK_CUR);
5454 data_offset = get4();
5455 fseek (ifp, 28, SEEK_CUR);
5456 data_offset += get4();
5457 load_raw = &CLASS packed_load_raw;
5460 if (type == 2) fgets (model2, 64, ifp);
5462 fseek (ifp, save, SEEK_SET);
5464 if (sony_length && (buf = (unsigned *) malloc(sony_length))) {
5465 fseek (ifp, sony_offset, SEEK_SET);
5466 fread (buf, sony_length, 1, ifp);
5467 sony_decrypt (buf, sony_length/4, 1, sony_key);
5469 if ((ifp = tmpfile())) {
5470 fwrite (buf, sony_length, 1, ifp);
5471 fseek (ifp, 0, SEEK_SET);
5472 parse_tiff_ifd (-sony_offset);
5478 for (i=0; i < colors; i++)
5479 FORCC cc[i][c] *= ab[i];
5481 FORCC for (i=0; i < 3; i++)
5482 for (cam_xyz[c][i]=j=0; j < colors; j++)
5483 cam_xyz[c][i] += cc[c][j] * cm[j][i] * xyz[i];
5484 cam_xyz_coeff (cam_xyz);
5488 FORCC cam_mul[c] = 1 / asn[c];
5491 FORCC pre_mul[c] /= cc[c][c];
5495 int CLASS parse_tiff (int base)
5499 fseek (ifp, base, SEEK_SET);
5501 if (order != 0x4949 && order != 0x4d4d) return 0;
5503 while ((doff = get4())) {
5504 fseek (ifp, doff+base, SEEK_SET);
5505 if (parse_tiff_ifd (base)) break;
5510 void CLASS apply_tiff()
5512 int max_samp=0, raw=-1, thm=-1, i;
5517 fseek (ifp, thumb_offset, SEEK_SET);
5518 if (ljpeg_start (&jh, 1)) {
5519 thumb_misc = jh.bits;
5520 thumb_width = jh.wide;
5521 thumb_height = jh.high;
5524 for (i=0; i < tiff_nifds; i++) {
5525 if (max_samp < tiff_ifd[i].samples)
5526 max_samp = tiff_ifd[i].samples;
5527 if (max_samp > 3) max_samp = 3;
5528 if ((tiff_ifd[i].comp != 6 || tiff_ifd[i].samples != 3) &&
5529 (tiff_ifd[i].width | tiff_ifd[i].height) < 0x10000 &&
5530 tiff_ifd[i].width*tiff_ifd[i].height > raw_width*raw_height) {
5531 raw_width = tiff_ifd[i].width;
5532 raw_height = tiff_ifd[i].height;
5533 tiff_bps = tiff_ifd[i].bps;
5534 tiff_compress = tiff_ifd[i].comp;
5535 data_offset = tiff_ifd[i].offset;
5536 tiff_flip = tiff_ifd[i].flip;
5537 tiff_samples = tiff_ifd[i].samples;
5538 tile_width = tiff_ifd[i].tile_width;
5539 tile_length = tiff_ifd[i].tile_length;
5543 if (!tile_width ) tile_width = INT_MAX;
5544 if (!tile_length) tile_length = INT_MAX;
5545 for (i=tiff_nifds; i--; )
5546 if (tiff_ifd[i].flip) tiff_flip = tiff_ifd[i].flip;
5547 if (raw >= 0 && !load_raw)
5548 switch (tiff_compress) {
5550 if (tiff_ifd[raw].bytes == raw_width*raw_height) {
5552 load_raw = &CLASS sony_arw2_load_raw; break;
5554 if (tiff_ifd[raw].bytes*8 != raw_width*raw_height*tiff_bps) {
5556 load_raw = &CLASS sony_arw_load_raw; break;
5562 case 32773: goto slr;
5564 if (tiff_ifd[raw].bytes*5 == raw_width*raw_height*8) {
5569 case 8: load_raw = &CLASS eight_bit_load_raw; break;
5570 case 12: if (tiff_ifd[raw].phint == 2)
5572 load_raw = &CLASS packed_load_raw; break;
5573 case 14: load_flags = 0;
5574 case 16: load_raw = &CLASS unpacked_load_raw; break;
5577 case 6: case 7: case 99:
5578 load_raw = &CLASS lossless_jpeg_load_raw; break;
5580 load_raw = &CLASS kodak_262_load_raw; break;
5582 if ((raw_width+9)/10*16*raw_height == tiff_ifd[raw].bytes) {
5583 load_raw = &CLASS packed_load_raw;
5585 } else if (raw_width*raw_height*2 == tiff_ifd[raw].bytes) {
5586 load_raw = &CLASS unpacked_load_raw;
5590 load_raw = &CLASS nikon_load_raw; break;
5592 load_raw = &CLASS lossy_dng_load_raw; break;
5594 load_raw = &CLASS pentax_load_raw; break;
5596 switch (tiff_ifd[raw].phint) {
5597 case 2: load_raw = &CLASS kodak_rgb_load_raw; filters = 0; break;
5598 case 6: load_raw = &CLASS kodak_ycbcr_load_raw; filters = 0; break;
5599 case 32803: load_raw = &CLASS kodak_65000_load_raw;
5602 default: is_raw = 0;
5605 if ( (tiff_samples == 3 && tiff_ifd[raw].bytes &&
5606 tiff_bps != 14 && tiff_bps != 2048 &&
5607 tiff_compress != 32769 && tiff_compress != 32770)
5608 || (tiff_bps == 8 && !strstr(make,"KODAK") && !strstr(make,"Kodak") &&
5609 !strstr(model2,"DEBUG RAW")))
5611 for (i=0; i < tiff_nifds; i++)
5612 if (i != raw && tiff_ifd[i].samples == max_samp &&
5613 tiff_ifd[i].width * tiff_ifd[i].height / SQR(tiff_ifd[i].bps+1) >
5614 thumb_width * thumb_height / SQR(thumb_misc+1)
5615 && tiff_ifd[i].comp != 34892) {
5616 thumb_width = tiff_ifd[i].width;
5617 thumb_height = tiff_ifd[i].height;
5618 thumb_offset = tiff_ifd[i].offset;
5619 thumb_length = tiff_ifd[i].bytes;
5620 thumb_misc = tiff_ifd[i].bps;
5624 thumb_misc |= tiff_ifd[thm].samples << 5;
5625 switch (tiff_ifd[thm].comp) {
5627 write_thumb = &CLASS layer_thumb;
5630 if (tiff_ifd[thm].bps <= 8)
5631 write_thumb = &CLASS ppm_thumb;
5632 else if (!strcmp(make,"Imacon"))
5633 write_thumb = &CLASS ppm16_thumb;
5635 thumb_load_raw = &CLASS kodak_thumb_load_raw;
5638 thumb_load_raw = tiff_ifd[thm].phint == 6 ?
5639 &CLASS kodak_ycbcr_load_raw : &CLASS kodak_rgb_load_raw;
5644 void CLASS parse_minolta (int base)
5646 int save, tag, len, offset, high=0, wide=0, i, c;
5649 fseek (ifp, base, SEEK_SET);
5650 if (fgetc(ifp) || fgetc(ifp)-'M' || fgetc(ifp)-'R') return;
5651 order = fgetc(ifp) * 0x101;
5652 offset = base + get4() + 8;
5653 while ((save=ftell(ifp)) < offset) {
5654 for (tag=i=0; i < 4; i++)
5655 tag = tag << 8 | fgetc(ifp);
5658 case 0x505244: /* PRD */
5659 fseek (ifp, 8, SEEK_CUR);
5663 case 0x574247: /* WBG */
5665 i = strcmp(model,"DiMAGE A200") ? 0:3;
5666 FORC4 cam_mul[c ^ (c >> 1) ^ i] = get2();
5668 case 0x545457: /* TTW */
5669 parse_tiff (ftell(ifp));
5670 data_offset = offset;
5672 fseek (ifp, save+len+8, SEEK_SET);
5680 Many cameras have a "debug mode" that writes JPEG and raw
5681 at the same time. The raw file has no header, so try to
5682 to open the matching JPEG file and read its metadata.
5684 void CLASS parse_external_jpeg()
5686 const char *file, *ext;
5687 char *jname, *jfile, *jext;
5690 ext = strrchr (ifname, '.');
5691 file = strrchr (ifname, '/');
5692 if (!file) file = strrchr (ifname, '\\');
5693 if (!file) file = ifname-1;
5695 if (!ext || strlen(ext) != 4 || ext-file != 8) return;
5696 jname = (char *) malloc (strlen(ifname) + 1);
5697 merror (jname, "parse_external_jpeg()");
5698 strcpy (jname, ifname);
5699 jfile = file - ifname + jname;
5700 jext = ext - ifname + jname;
5701 if (strcasecmp (ext, ".jpg")) {
5702 strcpy (jext, isupper(ext[1]) ? ".JPG":".jpg");
5703 if (isdigit(*file)) {
5704 memcpy (jfile, file+4, 4);
5705 memcpy (jfile+4, file, 4);
5708 while (isdigit(*--jext)) {
5715 if (strcmp (jname, ifname)) {
5716 if ((ifp = fopen (jname, "rb"))) {
5718 fprintf (stderr,_("Reading metadata from %s ...\n"), jname);
5726 fprintf (stderr,_("Failed to read metadata from %s\n"), jname);
5732 CIFF block 0x1030 contains an 8x8 white sample.
5733 Load this into white[][] for use in scale_colors().
5735 void CLASS ciff_block_1030()
5737 static const ushort key[] = { 0x410, 0x45f3 };
5738 int i, bpp, row, col, vbits=0;
5739 unsigned long bitbuf=0;
5741 if ((get2(),get4()) != 0x80008 || !get4()) return;
5743 if (bpp != 10 && bpp != 12) return;
5744 for (i=row=0; row < 8; row++)
5745 for (col=0; col < 8; col++) {
5747 bitbuf = bitbuf << 16 | (get2() ^ key[i++ & 1]);
5751 bitbuf << (LONG_BIT - vbits) >> (LONG_BIT - bpp);
5757 Parse a CIFF file, better known as Canon CRW format.
5759 void CLASS parse_ciff (int offset, int length)
5761 int tboff, nrecs, c, type, len, save, wbi=-1;
5762 ushort key[] = { 0x410, 0x45f3 };
5764 fseek (ifp, offset+length-4, SEEK_SET);
5765 tboff = get4() + offset;
5766 fseek (ifp, tboff, SEEK_SET);
5768 if (nrecs > 100) return;
5772 save = ftell(ifp) + 4;
5773 fseek (ifp, offset+get4(), SEEK_SET);
5774 if ((((type >> 8) + 8) | 8) == 0x38)
5775 parse_ciff (ftell(ifp), len); /* Parse a sub-table */
5778 fread (artist, 64, 1, ifp);
5779 if (type == 0x080a) {
5780 fread (make, 64, 1, ifp);
5781 fseek (ifp, strlen(make) - 63, SEEK_CUR);
5782 fread (model, 64, 1, ifp);
5784 if (type == 0x1810) {
5785 fseek (ifp, 12, SEEK_CUR);
5788 if (type == 0x1835) /* Get the decoder table */
5789 tiff_compress = get4();
5790 if (type == 0x2007) {
5791 thumb_offset = ftell(ifp);
5794 if (type == 0x1818) {
5795 shutter = pow (2, -int_to_float((get4(),get4())));
5796 aperture = pow (2, int_to_float(get4())/2);
5798 if (type == 0x102a) {
5799 iso_speed = pow (2, (get4(),get2())/32.0 - 4) * 50;
5800 aperture = pow (2, (get2(),(short)get2())/64.0);
5801 shutter = pow (2,-((short)get2())/32.0);
5802 wbi = (get2(),get2());
5803 if (wbi > 17) wbi = 0;
5804 fseek (ifp, 32, SEEK_CUR);
5805 if (shutter > 1e6) shutter = get2()/10.0;
5807 if (type == 0x102c) {
5808 if (get2() > 512) { /* Pro90, G1 */
5809 fseek (ifp, 118, SEEK_CUR);
5810 FORC4 cam_mul[c ^ 2] = get2();
5811 } else { /* G2, S30, S40 */
5812 fseek (ifp, 98, SEEK_CUR);
5813 FORC4 cam_mul[c ^ (c >> 1) ^ 1] = get2();
5816 if (type == 0x0032) {
5817 if (len == 768) { /* EOS D30 */
5818 fseek (ifp, 72, SEEK_CUR);
5819 FORC4 cam_mul[c ^ (c >> 1)] = 1024.0 / get2();
5820 if (!wbi) cam_mul[0] = -1; /* use my auto white balance */
5821 } else if (!cam_mul[0]) {
5822 if (get2() == key[0]) /* Pro1, G6, S60, S70 */
5823 c = (strstr(model,"Pro1") ?
5824 "012346000000000000":"01345:000000006008")[wbi]-'0'+ 2;
5825 else { /* G3, G5, S45, S50 */
5826 c = "023457000000006000"[wbi]-'0';
5827 key[0] = key[1] = 0;
5829 fseek (ifp, 78 + c*8, SEEK_CUR);
5830 FORC4 cam_mul[c ^ (c >> 1) ^ 1] = get2() ^ key[c & 1];
5831 if (!wbi) cam_mul[0] = -1;
5834 if (type == 0x10a9) { /* D60, 10D, 300D, and clones */
5835 if (len > 66) wbi = "0134567028"[wbi]-'0';
5836 fseek (ifp, 2 + wbi*8, SEEK_CUR);
5837 FORC4 cam_mul[c ^ (c >> 1)] = get2();
5839 if (type == 0x1030 && (0x18040 >> wbi & 1))
5840 ciff_block_1030(); /* all that don't have 0x10a9 */
5841 if (type == 0x1031) {
5842 raw_width = (get2(),get2());
5843 raw_height = get2();
5845 if (type == 0x5029) {
5846 focal_len = len >> 16;
5847 if ((len & 0xffff) == 2) focal_len /= 32;
5849 if (type == 0x5813) flash_used = int_to_float(len);
5850 if (type == 0x5814) canon_ev = int_to_float(len);
5851 if (type == 0x5817) shot_order = len;
5852 if (type == 0x5834) unique_id = len;
5853 if (type == 0x580e) timestamp = len;
5854 if (type == 0x180e) timestamp = get4();
5856 if ((type | 0x4000) == 0x580e)
5857 timestamp = mktime (gmtime (×tamp));
5859 fseek (ifp, save, SEEK_SET);
5863 void CLASS parse_rollei()
5865 char line[128], *val;
5868 fseek (ifp, 0, SEEK_SET);
5869 memset (&t, 0, sizeof t);
5871 fgets (line, 128, ifp);
5872 if ((val = strchr(line,'=')))
5875 val = line + strlen(line);
5876 if (!strcmp(line,"DAT"))
5877 sscanf (val, "%d.%d.%d", &t.tm_mday, &t.tm_mon, &t.tm_year);
5878 if (!strcmp(line,"TIM"))
5879 sscanf (val, "%d:%d:%d", &t.tm_hour, &t.tm_min, &t.tm_sec);
5880 if (!strcmp(line,"HDR"))
5881 thumb_offset = atoi(val);
5882 if (!strcmp(line,"X "))
5883 raw_width = atoi(val);
5884 if (!strcmp(line,"Y "))
5885 raw_height = atoi(val);
5886 if (!strcmp(line,"TX "))
5887 thumb_width = atoi(val);
5888 if (!strcmp(line,"TY "))
5889 thumb_height = atoi(val);
5890 } while (strncmp(line,"EOHD",4));
5891 data_offset = thumb_offset + thumb_width * thumb_height * 2;
5895 timestamp = mktime(&t);
5896 strcpy (make, "Rollei");
5897 strcpy (model,"d530flex");
5898 write_thumb = &CLASS rollei_thumb;
5901 void CLASS parse_sinar_ia()
5907 fseek (ifp, 4, SEEK_SET);
5909 fseek (ifp, get4(), SEEK_SET);
5911 off = get4(); get4();
5912 fread (str, 8, 1, ifp);
5913 if (!strcmp(str,"META")) meta_offset = off;
5914 if (!strcmp(str,"THUMB")) thumb_offset = off;
5915 if (!strcmp(str,"RAW0")) data_offset = off;
5917 fseek (ifp, meta_offset+20, SEEK_SET);
5918 fread (make, 64, 1, ifp);
5920 if ((cp = strchr(make,' '))) {
5921 strcpy (model, cp+1);
5925 raw_height = get2();
5926 load_raw = &CLASS unpacked_load_raw;
5927 thumb_width = (get4(),get2());
5928 thumb_height = get2();
5929 write_thumb = &CLASS ppm_thumb;
5933 void CLASS parse_phase_one (int base)
5935 unsigned entries, tag, /*type,*/ len, data, save, i, c;
5936 float romm_cam[3][3], *fp;
5939 memset (&ph1, 0, sizeof ph1);
5940 fseek (ifp, base, SEEK_SET);
5941 order = get4() & 0xffff;
5942 if (get4() >> 8 != 0x526177) return; /* "Raw" */
5943 fseek (ifp, get4()+base, SEEK_SET);
5952 fseek (ifp, base+data, SEEK_SET);
5954 case 0x100: flip = "0653"[data & 3]-'0'; break;
5956 for( i=9,fp=&romm_cam[0][0]; --i>=0; ++fp )
5958 romm_coeff (romm_cam);
5961 FORC3 cam_mul[c] = getreal(11);
5963 case 0x108: raw_width = data; break;
5964 case 0x109: raw_height = data; break;
5965 case 0x10a: left_margin = data; break;
5966 case 0x10b: top_margin = data; break;
5967 case 0x10c: width = data; break;
5968 case 0x10d: height = data; break;
5969 case 0x10e: ph1.format = data; break;
5970 case 0x10f: data_offset = data+base; break;
5971 case 0x110: meta_offset = data+base;
5972 meta_length = len; break;
5973 case 0x112: ph1.key_off = save - 4; break;
5974 case 0x210: ph1.tag_210 = int_to_float(data); break;
5975 case 0x21a: ph1.tag_21a = data; break;
5976 case 0x21c: strip_offset = data+base; break;
5977 case 0x21d: ph1.black = data; break;
5978 case 0x222: ph1.split_col = data; break;
5979 case 0x223: ph1.black_off = data+base; break;
5982 fread (model, 1, 63, ifp);
5983 if ((cp = strstr(model," camera"))) *cp = 0;
5985 fseek (ifp, save, SEEK_SET);
5987 load_raw = ph1.format < 3 ?
5988 &CLASS phase_one_load_raw : &CLASS phase_one_load_raw_c;
5990 strcpy (make, "Phase One");
5991 if (model[0]) return;
5992 switch (raw_height) {
5993 case 2060: strcpy (model,"LightPhase"); break;
5994 case 2682: strcpy (model,"H 10"); break;
5995 case 4128: strcpy (model,"H 20"); break;
5996 case 5488: strcpy (model,"H 25"); break;
6000 void CLASS parse_fuji (int offset)
6002 unsigned entries, tag, len, save, c;
6004 fseek (ifp, offset, SEEK_SET);
6006 if (entries > 255) return;
6012 raw_height = get2();
6014 } else if (tag == 0x121) {
6016 if ((width = get2()) == 4284) width += 3;
6017 } else if (tag == 0x130) {
6018 fuji_layout = fgetc(ifp) >> 7;
6019 fuji_width = !(fgetc(ifp) & 8);
6020 } else if (tag == 0x2ff0) {
6021 FORC4 cam_mul[c ^ 1] = get2();
6022 } else if (tag == 0xc000) {
6025 if ((width = get4()) > 10000) width = get4();
6029 fseek (ifp, save+len, SEEK_SET);
6031 height <<= fuji_layout;
6032 width >>= fuji_layout;
6035 int CLASS parse_jpeg (int offset)
6037 int len, save, hlen, mark;
6039 fseek (ifp, offset, SEEK_SET);
6040 if (fgetc(ifp) != 0xff || fgetc(ifp) != 0xd8) return 0;
6042 while (fgetc(ifp) == 0xff && (mark = fgetc(ifp)) != 0xda) {
6046 if (mark == 0xc0 || mark == 0xc3) {
6048 raw_height = get2();
6053 if (get4() == 0x48454150) /* "HEAP" */
6054 parse_ciff (save+hlen, len-hlen);
6055 if (parse_tiff (save+6)) apply_tiff();
6056 fseek (ifp, save+len, SEEK_SET);
6061 void CLASS parse_riff()
6063 unsigned i, size, end;
6064 char tag[4], date[64], month[64];
6065 static const char mon[12][4] =
6066 { "Jan","Feb","Mar","Apr","May","Jun","Jul","Aug","Sep","Oct","Nov","Dec" };
6070 fread (tag, 4, 1, ifp);
6072 end = ftell(ifp) + size;
6073 if (!memcmp(tag,"RIFF",4) || !memcmp(tag,"LIST",4)) {
6075 while (ftell(ifp)+7 < end)
6077 } else if (!memcmp(tag,"nctg",4)) {
6078 while (ftell(ifp)+7 < end) {
6081 if ((i+1) >> 1 == 10 && size == 20)
6083 else fseek (ifp, size, SEEK_CUR);
6085 } else if (!memcmp(tag,"IDIT",4) && size < 64) {
6086 fread (date, 64, 1, ifp);
6088 memset (&t, 0, sizeof t);
6089 if (sscanf (date, "%*s %s %d %d:%d:%d %d", month, &t.tm_mday,
6090 &t.tm_hour, &t.tm_min, &t.tm_sec, &t.tm_year) == 6) {
6091 for (i=0; i < 12 && strcasecmp(mon[i],month); i++);
6095 timestamp = mktime(&t);
6098 fseek (ifp, size, SEEK_CUR);
6101 void CLASS parse_smal (int offset, int fsize)
6105 fseek (ifp, offset+2, SEEK_SET);
6109 fseek (ifp, 5, SEEK_CUR);
6110 if (get4() != fsize) return;
6111 if (ver > 6) data_offset = get4();
6112 raw_height = height = get2();
6113 raw_width = width = get2();
6114 strcpy (make, "SMaL");
6115 sprintf (model, "v%d %dx%d", ver, width, height);
6116 if (ver == 6) load_raw = &CLASS smal_v6_load_raw;
6117 if (ver == 9) load_raw = &CLASS smal_v9_load_raw;
6120 void CLASS parse_cine()
6122 unsigned off_head, off_setup, off_image, i;
6125 fseek (ifp, 4, SEEK_SET);
6126 is_raw = get2() == 2;
6127 fseek (ifp, 14, SEEK_CUR);
6133 if ((i = get4())) timestamp = i;
6134 fseek (ifp, off_head+4, SEEK_SET);
6136 raw_height = get4();
6137 switch (get2(),get2()) {
6138 case 8: load_raw = &CLASS eight_bit_load_raw; break;
6139 case 16: load_raw = &CLASS unpacked_load_raw;
6141 fseek (ifp, off_setup+792, SEEK_SET);
6142 strcpy (make, "CINE");
6143 sprintf (model, "%d", get4());
6144 fseek (ifp, 12, SEEK_CUR);
6145 switch ((i=get4()) & 0xffffff) {
6146 case 3: filters = 0x94949494; break;
6147 case 4: filters = 0x49494949; break;
6148 default: is_raw = 0;
6150 fseek (ifp, 72, SEEK_CUR);
6151 switch ((get4()+3600) % 360) {
6152 case 270: flip = 4; break;
6153 case 180: flip = 1; break;
6154 case 90: flip = 7; break;
6157 cam_mul[0] = getreal(11);
6158 cam_mul[2] = getreal(11);
6159 maximum = ~(-1 << get4());
6160 fseek (ifp, 668, SEEK_CUR);
6161 shutter = get4()/1000000000.0;
6162 fseek (ifp, off_image, SEEK_SET);
6163 if (shot_select < is_raw)
6164 fseek (ifp, shot_select*8, SEEK_CUR);
6165 data_offset = (INT64) get4() + 8;
6166 data_offset += (INT64) get4() << 32;
6169 void CLASS parse_redcine()
6171 unsigned i, len, rdvo;
6175 fseek (ifp, 52, SEEK_SET);
6178 fseek (ifp, 0, SEEK_END);
6179 fseek (ifp, -(i = ftello(ifp) & 511), SEEK_CUR);
6180 if (get4() != i || get4() != 0x52454f42) {
6181 fprintf (stderr,_("%s: Tail is missing, parsing from head...\n"), ifname);
6182 fseek (ifp, 0, SEEK_SET);
6183 while ((len = get4()) != EOF) {
6184 if (get4() == 0x52454456)
6185 if (is_raw++ == shot_select)
6186 data_offset = ftello(ifp) - 8;
6187 fseek (ifp, len-8, SEEK_CUR);
6191 fseek (ifp, 12, SEEK_CUR);
6193 fseeko (ifp, rdvo+8 + shot_select*4, SEEK_SET);
6194 data_offset = get4();
6198 char * CLASS foveon_gets (int offset, char *str, int len)
6201 fseek (ifp, offset, SEEK_SET);
6202 for (i=0; i < len-1; i++)
6203 if ((str[i] = get2()) == 0) break;
6208 void CLASS parse_foveon()
6210 int entries, img=0, off, len, tag, save, i, wide, high, pent, poff[256][2];
6211 char name[64], value[64];
6213 order = 0x4949; /* Little-endian */
6214 fseek (ifp, 36, SEEK_SET);
6216 fseek (ifp, -4, SEEK_END);
6217 fseek (ifp, get4(), SEEK_SET);
6218 if (get4() != 0x64434553) return; /* SECd */
6219 entries = (get4(),get4());
6225 fseek (ifp, off, SEEK_SET);
6226 if (get4() != (0x20434553 | (tag << 24))) return;
6228 case 0x47414d49: /* IMAG */
6229 case 0x32414d49: /* IMA2 */
6230 fseek (ifp, 8, SEEK_CUR);
6234 if (wide > raw_width && high > raw_height) {
6236 case 5: load_flags = 1;
6237 case 6: load_raw = &CLASS foveon_sd_load_raw; break;
6238 case 30: load_raw = &CLASS foveon_dp_load_raw; break;
6239 default: load_raw = 0;
6243 data_offset = off+28;
6245 fseek (ifp, off+28, SEEK_SET);
6246 if (fgetc(ifp) == 0xff && fgetc(ifp) == 0xd8
6247 && thumb_length < len-28) {
6248 thumb_offset = off+28;
6249 thumb_length = len-28;
6250 write_thumb = &CLASS jpeg_thumb;
6252 if (++img == 2 && !thumb_length) {
6253 thumb_offset = off+24;
6255 thumb_height = high;
6256 write_thumb = &CLASS foveon_thumb;
6259 case 0x464d4143: /* CAMF */
6260 meta_offset = off+8;
6261 meta_length = len-28;
6263 case 0x504f5250: /* PROP */
6264 pent = (get4(),get4());
6265 fseek (ifp, 12, SEEK_CUR);
6267 if ((unsigned) pent > 256) pent=256;
6268 for (i=0; i < pent*2; i++)
6269 poff[0][i] = off + get4()*2;
6270 for (i=0; i < pent; i++) {
6271 foveon_gets (poff[i][0], name, 64);
6272 foveon_gets (poff[i][1], value, 64);
6273 if (!strcmp (name, "ISO"))
6274 iso_speed = atoi(value);
6275 if (!strcmp (name, "CAMMANUF"))
6276 strcpy (make, value);
6277 if (!strcmp (name, "CAMMODEL"))
6278 strcpy (model, value);
6279 if (!strcmp (name, "WB_DESC"))
6280 strcpy (model2, value);
6281 if (!strcmp (name, "TIME"))
6282 timestamp = atoi(value);
6283 if (!strcmp (name, "EXPTIME"))
6284 shutter = atoi(value) / 1000000.0;
6285 if (!strcmp (name, "APERTURE"))
6286 aperture = atof(value);
6287 if (!strcmp (name, "FLENGTH"))
6288 focal_len = atof(value);
6291 timestamp = mktime (gmtime (×tamp));
6294 fseek (ifp, save, SEEK_SET);
6300 All matrices are from Adobe DNG Converter unless otherwise noted.
6302 void CLASS adobe_coeff (const char *make, const char *model)
6304 static const struct {
6306 short black, maximum, trans[12];
6308 { "AGFAPHOTO DC-833m", 0, 0, /* DJC */
6309 { 11438,-3762,-1115,-2409,9914,2497,-1227,2295,5300 } },
6310 { "Apple QuickTake", 0, 0, /* DJC */
6311 { 21392,-5653,-3353,2406,8010,-415,7166,1427,2078 } },
6312 { "Canon EOS D2000", 0, 0,
6313 { 24542,-10860,-3401,-1490,11370,-297,2858,-605,3225 } },
6314 { "Canon EOS D6000", 0, 0,
6315 { 20482,-7172,-3125,-1033,10410,-285,2542,226,3136 } },
6316 { "Canon EOS D30", 0, 0,
6317 { 9805,-2689,-1312,-5803,13064,3068,-2438,3075,8775 } },
6318 { "Canon EOS D60", 0, 0xfa0,
6319 { 6188,-1341,-890,-7168,14489,2937,-2640,3228,8483 } },
6320 { "Canon EOS 5D Mark III", 0, 0x3c80,
6321 { 6722,-635,-963,-4287,12460,2028,-908,2162,5668 } },
6322 { "Canon EOS 5D Mark II", 0, 0x3cf0,
6323 { 4716,603,-830,-7798,15474,2480,-1496,1937,6651 } },
6324 { "Canon EOS 5D", 0, 0xe6c,
6325 { 6347,-479,-972,-8297,15954,2480,-1968,2131,7649 } },
6326 { "Canon EOS 6D", 0, 0x3c82,
6327 { 7034,-804,-1014,-4420,12564,2058,-851,1994,5758 } },
6328 { "Canon EOS 7D", 0, 0x3510,
6329 { 6844,-996,-856,-3876,11761,2396,-593,1772,6198 } },
6330 { "Canon EOS 10D", 0, 0xfa0,
6331 { 8197,-2000,-1118,-6714,14335,2592,-2536,3178,8266 } },
6332 { "Canon EOS 20Da", 0, 0,
6333 { 14155,-5065,-1382,-6550,14633,2039,-1623,1824,6561 } },
6334 { "Canon EOS 20D", 0, 0xfff,
6335 { 6599,-537,-891,-8071,15783,2424,-1983,2234,7462 } },
6336 { "Canon EOS 30D", 0, 0,
6337 { 6257,-303,-1000,-7880,15621,2396,-1714,1904,7046 } },
6338 { "Canon EOS 40D", 0, 0x3f60,
6339 { 6071,-747,-856,-7653,15365,2441,-2025,2553,7315 } },
6340 { "Canon EOS 50D", 0, 0x3d93,
6341 { 4920,616,-593,-6493,13964,2784,-1774,3178,7005 } },
6342 { "Canon EOS 60D", 0, 0x2ff7,
6343 { 6719,-994,-925,-4408,12426,2211,-887,2129,6051 } },
6344 { "Canon EOS 300D", 0, 0xfa0,
6345 { 8197,-2000,-1118,-6714,14335,2592,-2536,3178,8266 } },
6346 { "Canon EOS 350D", 0, 0xfff,
6347 { 6018,-617,-965,-8645,15881,2975,-1530,1719,7642 } },
6348 { "Canon EOS 400D", 0, 0xe8e,
6349 { 7054,-1501,-990,-8156,15544,2812,-1278,1414,7796 } },
6350 { "Canon EOS 450D", 0, 0x390d,
6351 { 5784,-262,-821,-7539,15064,2672,-1982,2681,7427 } },
6352 { "Canon EOS 500D", 0, 0x3479,
6353 { 4763,712,-646,-6821,14399,2640,-1921,3276,6561 } },
6354 { "Canon EOS 550D", 0, 0x3dd7,
6355 { 6941,-1164,-857,-3825,11597,2534,-416,1540,6039 } },
6356 { "Canon EOS 600D", 0, 0x3510,
6357 { 6461,-907,-882,-4300,12184,2378,-819,1944,5931 } },
6358 { "Canon EOS 650D", 0, 0x354d,
6359 { 6602,-841,-939,-4472,12458,2247,-975,2039,6148 } },
6360 { "Canon EOS 1000D", 0, 0xe43,
6361 { 6771,-1139,-977,-7818,15123,2928,-1244,1437,7533 } },
6362 { "Canon EOS 1100D", 0, 0x3510,
6363 { 6444,-904,-893,-4563,12308,2535,-903,2016,6728 } },
6364 { "Canon EOS M", 0, 0,
6365 { 6602,-841,-939,-4472,12458,2247,-975,2039,6148 } },
6366 { "Canon EOS-1Ds Mark III", 0, 0x3bb0,
6367 { 5859,-211,-930,-8255,16017,2353,-1732,1887,7448 } },
6368 { "Canon EOS-1Ds Mark II", 0, 0xe80,
6369 { 6517,-602,-867,-8180,15926,2378,-1618,1771,7633 } },
6370 { "Canon EOS-1D Mark IV", 0, 0x3bb0,
6371 { 6014,-220,-795,-4109,12014,2361,-561,1824,5787 } },
6372 { "Canon EOS-1D Mark III", 0, 0x3bb0,
6373 { 6291,-540,-976,-8350,16145,2311,-1714,1858,7326 } },
6374 { "Canon EOS-1D Mark II N", 0, 0xe80,
6375 { 6240,-466,-822,-8180,15825,2500,-1801,1938,8042 } },
6376 { "Canon EOS-1D Mark II", 0, 0xe80,
6377 { 6264,-582,-724,-8312,15948,2504,-1744,1919,8664 } },
6378 { "Canon EOS-1DS", 0, 0xe20,
6379 { 4374,3631,-1743,-7520,15212,2472,-2892,3632,8161 } },
6380 { "Canon EOS-1D X", 0, 0x3c4e,
6381 { 6847,-614,-1014,-4669,12737,2139,-1197,2488,6846 } },
6382 { "Canon EOS-1D", 0, 0xe20,
6383 { 6806,-179,-1020,-8097,16415,1687,-3267,4236,7690 } },
6384 { "Canon EOS", 0, 0,
6385 { 8197,-2000,-1118,-6714,14335,2592,-2536,3178,8266 } },
6386 { "Canon PowerShot A530", 0, 0,
6387 { 0 } }, /* don't want the A5 matrix */
6388 { "Canon PowerShot A50", 0, 0,
6389 { -5300,9846,1776,3436,684,3939,-5540,9879,6200,-1404,11175,217 } },
6390 { "Canon PowerShot A5", 0, 0,
6391 { -4801,9475,1952,2926,1611,4094,-5259,10164,5947,-1554,10883,547 } },
6392 { "Canon PowerShot G10", 0, 0,
6393 { 11093,-3906,-1028,-5047,12492,2879,-1003,1750,5561 } },
6394 { "Canon PowerShot G11", 0, 0,
6395 { 12177,-4817,-1069,-1612,9864,2049,-98,850,4471 } },
6396 { "Canon PowerShot G12", 0, 0,
6397 { 13244,-5501,-1248,-1508,9858,1935,-270,1083,4366 } },
6398 { "Canon PowerShot G15", 0, 0,
6399 { 7474,-2301,-567,-4056,11456,2975,-222,716,4181 } },
6400 { "Canon PowerShot G1 X", 0, 0,
6401 { 7378,-1255,-1043,-4088,12251,2048,-876,1946,5805 } },
6402 { "Canon PowerShot G1", 0, 0,
6403 { -4778,9467,2172,4743,-1141,4344,-5146,9908,6077,-1566,11051,557 } },
6404 { "Canon PowerShot G2", 0, 0,
6405 { 9087,-2693,-1049,-6715,14382,2537,-2291,2819,7790 } },
6406 { "Canon PowerShot G3", 0, 0,
6407 { 9212,-2781,-1073,-6573,14189,2605,-2300,2844,7664 } },
6408 { "Canon PowerShot G5", 0, 0,
6409 { 9757,-2872,-933,-5972,13861,2301,-1622,2328,7212 } },
6410 { "Canon PowerShot G6", 0, 0,
6411 { 9877,-3775,-871,-7613,14807,3072,-1448,1305,7485 } },
6412 { "Canon PowerShot G9", 0, 0,
6413 { 7368,-2141,-598,-5621,13254,2625,-1418,1696,5743 } },
6414 { "Canon PowerShot Pro1", 0, 0,
6415 { 10062,-3522,-999,-7643,15117,2730,-765,817,7323 } },
6416 { "Canon PowerShot Pro70", 34, 0,
6417 { -4155,9818,1529,3939,-25,4522,-5521,9870,6610,-2238,10873,1342 } },
6418 { "Canon PowerShot Pro90", 0, 0,
6419 { -4963,9896,2235,4642,-987,4294,-5162,10011,5859,-1770,11230,577 } },
6420 { "Canon PowerShot S30", 0, 0,
6421 { 10566,-3652,-1129,-6552,14662,2006,-2197,2581,7670 } },
6422 { "Canon PowerShot S40", 0, 0,
6423 { 8510,-2487,-940,-6869,14231,2900,-2318,2829,9013 } },
6424 { "Canon PowerShot S45", 0, 0,
6425 { 8163,-2333,-955,-6682,14174,2751,-2077,2597,8041 } },
6426 { "Canon PowerShot S50", 0, 0,
6427 { 8882,-2571,-863,-6348,14234,2288,-1516,2172,6569 } },
6428 { "Canon PowerShot S60", 0, 0,
6429 { 8795,-2482,-797,-7804,15403,2573,-1422,1996,7082 } },
6430 { "Canon PowerShot S70", 0, 0,
6431 { 9976,-3810,-832,-7115,14463,2906,-901,989,7889 } },
6432 { "Canon PowerShot S90", 0, 0,
6433 { 12374,-5016,-1049,-1677,9902,2078,-83,852,4683 } },
6434 { "Canon PowerShot S95", 0, 0,
6435 { 13440,-5896,-1279,-1236,9598,1931,-180,1001,4651 } },
6436 { "Canon PowerShot S100", 0, 0,
6437 { 7968,-2565,-636,-2873,10697,2513,180,667,4211 } },
6438 { "Canon PowerShot S110", 0, 0,
6439 { 8039,-2643,-654,-3783,11230,2930,-206,690,4194 } },
6440 { "Canon PowerShot SX1 IS", 0, 0,
6441 { 6578,-259,-502,-5974,13030,3309,-308,1058,4970 } },
6442 { "Canon PowerShot SX50 HS", 0, 0,
6443 { 12432,-4753,-1247,-2110,10691,1629,-412,1623,4926 } },
6444 { "Canon PowerShot A470", 0, 0, /* DJC */
6445 { 12513,-4407,-1242,-2680,10276,2405,-878,2215,4734 } },
6446 { "Canon PowerShot A610", 0, 0, /* DJC */
6447 { 15591,-6402,-1592,-5365,13198,2168,-1300,1824,5075 } },
6448 { "Canon PowerShot A620", 0, 0, /* DJC */
6449 { 15265,-6193,-1558,-4125,12116,2010,-888,1639,5220 } },
6450 { "Canon PowerShot A630", 0, 0, /* DJC */
6451 { 14201,-5308,-1757,-6087,14472,1617,-2191,3105,5348 } },
6452 { "Canon PowerShot A640", 0, 0, /* DJC */
6453 { 13124,-5329,-1390,-3602,11658,1944,-1612,2863,4885 } },
6454 { "Canon PowerShot A650", 0, 0, /* DJC */
6455 { 9427,-3036,-959,-2581,10671,1911,-1039,1982,4430 } },
6456 { "Canon PowerShot A720", 0, 0, /* DJC */
6457 { 14573,-5482,-1546,-1266,9799,1468,-1040,1912,3810 } },
6458 { "Canon PowerShot S3 IS", 0, 0, /* DJC */
6459 { 14062,-5199,-1446,-4712,12470,2243,-1286,2028,4836 } },
6460 { "Canon PowerShot SX110 IS", 0, 0, /* DJC */
6461 { 14134,-5576,-1527,-1991,10719,1273,-1158,1929,3581 } },
6462 { "Canon PowerShot SX220", 0, 0, /* DJC */
6463 { 13898,-5076,-1447,-1405,10109,1297,-244,1860,3687 } },
6464 { "CASIO EX-S20", 0, 0, /* DJC */
6465 { 11634,-3924,-1128,-4968,12954,2015,-1588,2648,7206 } },
6466 { "CASIO EX-Z750", 0, 0, /* DJC */
6467 { 10819,-3873,-1099,-4903,13730,1175,-1755,3751,4632 } },
6468 { "CASIO EX-Z10", 128, 0xfff, /* DJC */
6469 { 9790,-3338,-603,-2321,10222,2099,-344,1273,4799 } },
6471 { 3390,480,-500,-800,3610,340,-550,2336,1192 } },
6473 { 3390,480,-500,-800,3610,340,-550,2336,1192 } },
6475 { 20183,-4295,-423,-3940,15330,3985,-280,4870,9800 } },
6476 { "Contax N Digital", 0, 0xf1e,
6477 { 7777,1285,-1053,-9280,16543,2916,-3677,5679,7060 } },
6478 { "EPSON R-D1", 0, 0,
6479 { 6827,-1878,-732,-8429,16012,2564,-704,592,7145 } },
6480 { "FUJIFILM E550", 0, 0,
6481 { 11044,-3888,-1120,-7248,15168,2208,-1531,2277,8069 } },
6482 { "FUJIFILM E900", 0, 0,
6483 { 9183,-2526,-1078,-7461,15071,2574,-2022,2440,8639 } },
6484 { "FUJIFILM F5", 0, 0,
6485 { 13690,-5358,-1474,-3369,11600,1998,-132,1554,4395 } },
6486 { "FUJIFILM F6", 0, 0,
6487 { 13690,-5358,-1474,-3369,11600,1998,-132,1554,4395 } },
6488 { "FUJIFILM F77", 0, 0xfe9,
6489 { 13690,-5358,-1474,-3369,11600,1998,-132,1554,4395 } },
6490 { "FUJIFILM F7", 0, 0,
6491 { 10004,-3219,-1201,-7036,15047,2107,-1863,2565,7736 } },
6492 { "FUJIFILM F8", 0, 0,
6493 { 13690,-5358,-1474,-3369,11600,1998,-132,1554,4395 } },
6494 { "FUJIFILM S100FS", 514, 0,
6495 { 11521,-4355,-1065,-6524,13767,3058,-1466,1984,6045 } },
6496 { "FUJIFILM S200EXR", 512, 0x3fff,
6497 { 11401,-4498,-1312,-5088,12751,2613,-838,1568,5941 } },
6498 { "FUJIFILM S20Pro", 0, 0,
6499 { 10004,-3219,-1201,-7036,15047,2107,-1863,2565,7736 } },
6500 { "FUJIFILM S2Pro", 128, 0,
6501 { 12492,-4690,-1402,-7033,15423,1647,-1507,2111,7697 } },
6502 { "FUJIFILM S3Pro", 0, 0,
6503 { 11807,-4612,-1294,-8927,16968,1988,-2120,2741,8006 } },
6504 { "FUJIFILM S5Pro", 0, 0,
6505 { 12300,-5110,-1304,-9117,17143,1998,-1947,2448,8100 } },
6506 { "FUJIFILM S5000", 0, 0,
6507 { 8754,-2732,-1019,-7204,15069,2276,-1702,2334,6982 } },
6508 { "FUJIFILM S5100", 0, 0,
6509 { 11940,-4431,-1255,-6766,14428,2542,-993,1165,7421 } },
6510 { "FUJIFILM S5500", 0, 0,
6511 { 11940,-4431,-1255,-6766,14428,2542,-993,1165,7421 } },
6512 { "FUJIFILM S5200", 0, 0,
6513 { 9636,-2804,-988,-7442,15040,2589,-1803,2311,8621 } },
6514 { "FUJIFILM S5600", 0, 0,
6515 { 9636,-2804,-988,-7442,15040,2589,-1803,2311,8621 } },
6516 { "FUJIFILM S6", 0, 0,
6517 { 12628,-4887,-1401,-6861,14996,1962,-2198,2782,7091 } },
6518 { "FUJIFILM S7000", 0, 0,
6519 { 10190,-3506,-1312,-7153,15051,2238,-2003,2399,7505 } },
6520 { "FUJIFILM S9000", 0, 0,
6521 { 10491,-3423,-1145,-7385,15027,2538,-1809,2275,8692 } },
6522 { "FUJIFILM S9500", 0, 0,
6523 { 10491,-3423,-1145,-7385,15027,2538,-1809,2275,8692 } },
6524 { "FUJIFILM S9100", 0, 0,
6525 { 12343,-4515,-1285,-7165,14899,2435,-1895,2496,8800 } },
6526 { "FUJIFILM S9600", 0, 0,
6527 { 12343,-4515,-1285,-7165,14899,2435,-1895,2496,8800 } },
6528 { "FUJIFILM IS-1", 0, 0,
6529 { 21461,-10807,-1441,-2332,10599,1999,289,875,7703 } },
6530 { "FUJIFILM IS Pro", 0, 0,
6531 { 12300,-5110,-1304,-9117,17143,1998,-1947,2448,8100 } },
6532 { "FUJIFILM HS10 HS11", 0, 0xf68,
6533 { 12440,-3954,-1183,-1123,9674,1708,-83,1614,4086 } },
6534 { "FUJIFILM HS20EXR", 0, 0,
6535 { 13690,-5358,-1474,-3369,11600,1998,-132,1554,4395 } },
6536 { "FUJIFILM HS3", 0, 0,
6537 { 13690,-5358,-1474,-3369,11600,1998,-132,1554,4395 } },
6538 { "FUJIFILM X100", 0, 0,
6539 { 12161,-4457,-1069,-5034,12874,2400,-795,1724,6904 } },
6540 { "FUJIFILM X10", 0, 0,
6541 { 13509,-6199,-1254,-4430,12733,1865,-331,1441,5022 } },
6542 { "FUJIFILM X-Pro1", 0, 0,
6543 { 10413,-3996,-993,-3721,11640,2361,-733,1540,6011 } },
6544 { "FUJIFILM X-E1", 0, 0,
6545 { 10413,-3996,-993,-3721,11640,2361,-733,1540,6011 } },
6546 { "FUJIFILM XF1", 0, 0,
6547 { 13509,-6199,-1254,-4430,12733,1865,-331,1441,5022 } },
6548 { "FUJIFILM X-S1", 0, 0,
6549 { 13509,-6199,-1254,-4430,12733,1865,-331,1441,5022 } },
6550 { "Imacon Ixpress", 0, 0, /* DJC */
6551 { 7025,-1415,-704,-5188,13765,1424,-1248,2742,6038 } },
6552 { "KODAK NC2000", 0, 0,
6553 { 13891,-6055,-803,-465,9919,642,2121,82,1291 } },
6554 { "Kodak DCS315C", 8, 0,
6555 { 17523,-4827,-2510,756,8546,-137,6113,1649,2250 } },
6556 { "Kodak DCS330C", 8, 0,
6557 { 20620,-7572,-2801,-103,10073,-396,3551,-233,2220 } },
6558 { "KODAK DCS420", 0, 0,
6559 { 10868,-1852,-644,-1537,11083,484,2343,628,2216 } },
6560 { "KODAK DCS460", 0, 0,
6561 { 10592,-2206,-967,-1944,11685,230,2206,670,1273 } },
6562 { "KODAK EOSDCS1", 0, 0,
6563 { 10592,-2206,-967,-1944,11685,230,2206,670,1273 } },
6564 { "KODAK EOSDCS3B", 0, 0,
6565 { 9898,-2700,-940,-2478,12219,206,1985,634,1031 } },
6566 { "Kodak DCS520C", 178, 0,
6567 { 24542,-10860,-3401,-1490,11370,-297,2858,-605,3225 } },
6568 { "Kodak DCS560C", 177, 0,
6569 { 20482,-7172,-3125,-1033,10410,-285,2542,226,3136 } },
6570 { "Kodak DCS620C", 177, 0,
6571 { 23617,-10175,-3149,-2054,11749,-272,2586,-489,3453 } },
6572 { "Kodak DCS620X", 176, 0,
6573 { 13095,-6231,154,12221,-21,-2137,895,4602,2258 } },
6574 { "Kodak DCS660C", 173, 0,
6575 { 18244,-6351,-2739,-791,11193,-521,3711,-129,2802 } },
6576 { "Kodak DCS720X", 0, 0,
6577 { 11775,-5884,950,9556,1846,-1286,-1019,6221,2728 } },
6578 { "Kodak DCS760C", 0, 0,
6579 { 16623,-6309,-1411,-4344,13923,323,2285,274,2926 } },
6580 { "Kodak DCS Pro SLR", 0, 0,
6581 { 5494,2393,-232,-6427,13850,2846,-1876,3997,5445 } },
6582 { "Kodak DCS Pro 14nx", 0, 0,
6583 { 5494,2393,-232,-6427,13850,2846,-1876,3997,5445 } },
6584 { "Kodak DCS Pro 14", 0, 0,
6585 { 7791,3128,-776,-8588,16458,2039,-2455,4006,6198 } },
6586 { "Kodak ProBack645", 0, 0,
6587 { 16414,-6060,-1470,-3555,13037,473,2545,122,4948 } },
6588 { "Kodak ProBack", 0, 0,
6589 { 21179,-8316,-2918,-915,11019,-165,3477,-180,4210 } },
6590 { "KODAK P712", 0, 0,
6591 { 9658,-3314,-823,-5163,12695,2768,-1342,1843,6044 } },
6592 { "KODAK P850", 0, 0xf7c,
6593 { 10511,-3836,-1102,-6946,14587,2558,-1481,1792,6246 } },
6594 { "KODAK P880", 0, 0xfff,
6595 { 12805,-4662,-1376,-7480,15267,2360,-1626,2194,7904 } },
6596 { "KODAK EasyShare Z980", 0, 0,
6597 { 11313,-3559,-1101,-3893,11891,2257,-1214,2398,4908 } },
6598 { "KODAK EasyShare Z981", 0, 0,
6599 { 12729,-4717,-1188,-1367,9187,2582,274,860,4411 } },
6600 { "KODAK EasyShare Z990", 0, 0xfed,
6601 { 11749,-4048,-1309,-1867,10572,1489,-138,1449,4522 } },
6602 { "KODAK EASYSHARE Z1015", 0, 0xef1,
6603 { 11265,-4286,-992,-4694,12343,2647,-1090,1523,5447 } },
6604 { "Leaf CMost", 0, 0,
6605 { 3952,2189,449,-6701,14585,2275,-4536,7349,6536 } },
6606 { "Leaf Valeo 6", 0, 0,
6607 { 3952,2189,449,-6701,14585,2275,-4536,7349,6536 } },
6608 { "Leaf Aptus 54S", 0, 0,
6609 { 8236,1746,-1314,-8251,15953,2428,-3673,5786,5771 } },
6610 { "Leaf Aptus 65", 0, 0,
6611 { 7914,1414,-1190,-8777,16582,2280,-2811,4605,5562 } },
6612 { "Leaf Aptus 75", 0, 0,
6613 { 7914,1414,-1190,-8777,16582,2280,-2811,4605,5562 } },
6615 { 8236,1746,-1314,-8251,15953,2428,-3673,5786,5771 } },
6616 { "Mamiya ZD", 0, 0,
6617 { 7645,2579,-1363,-8689,16717,2015,-3712,5941,5961 } },
6618 { "Micron 2010", 110, 0, /* DJC */
6619 { 16695,-3761,-2151,155,9682,163,3433,951,4904 } },
6620 { "Minolta DiMAGE 5", 0, 0xf7d,
6621 { 8983,-2942,-963,-6556,14476,2237,-2426,2887,8014 } },
6622 { "Minolta DiMAGE 7Hi", 0, 0xf7d,
6623 { 11368,-3894,-1242,-6521,14358,2339,-2475,3056,7285 } },
6624 { "Minolta DiMAGE 7", 0, 0xf7d,
6625 { 9144,-2777,-998,-6676,14556,2281,-2470,3019,7744 } },
6626 { "Minolta DiMAGE A1", 0, 0xf8b,
6627 { 9274,-2547,-1167,-8220,16323,1943,-2273,2720,8340 } },
6628 { "MINOLTA DiMAGE A200", 0, 0,
6629 { 8560,-2487,-986,-8112,15535,2771,-1209,1324,7743 } },
6630 { "Minolta DiMAGE A2", 0, 0xf8f,
6631 { 9097,-2726,-1053,-8073,15506,2762,-966,981,7763 } },
6632 { "Minolta DiMAGE Z2", 0, 0, /* DJC */
6633 { 11280,-3564,-1370,-4655,12374,2282,-1423,2168,5396 } },
6634 { "MINOLTA DYNAX 5", 0, 0xffb,
6635 { 10284,-3283,-1086,-7957,15762,2316,-829,882,6644 } },
6636 { "MINOLTA DYNAX 7", 0, 0xffb,
6637 { 10239,-3104,-1099,-8037,15727,2451,-927,925,6871 } },
6638 { "MOTOROLA PIXL", 0, 0, /* DJC */
6639 { 8898,-989,-1033,-3292,11619,1674,-661,3178,5216 } },
6640 { "NIKON D100", 0, 0,
6641 { 5902,-933,-782,-8983,16719,2354,-1402,1455,6464 } },
6642 { "NIKON D1H", 0, 0,
6643 { 7577,-2166,-926,-7454,15592,1934,-2377,2808,8606 } },
6644 { "NIKON D1X", 0, 0,
6645 { 7702,-2245,-975,-9114,17242,1875,-2679,3055,8521 } },
6646 { "NIKON D1", 0, 0, /* multiplied by 2.218750, 1.0, 1.148438 */
6647 { 16772,-4726,-2141,-7611,15713,1972,-2846,3494,9521 } },
6648 { "NIKON D200", 0, 0xfbc,
6649 { 8367,-2248,-763,-8758,16447,2422,-1527,1550,8053 } },
6650 { "NIKON D2H", 0, 0,
6651 { 5710,-901,-615,-8594,16617,2024,-2975,4120,6830 } },
6652 { "NIKON D2X", 0, 0,
6653 { 10231,-2769,-1255,-8301,15900,2552,-797,680,7148 } },
6654 { "NIKON D3000", 0, 0,
6655 { 8736,-2458,-935,-9075,16894,2251,-1354,1242,8263 } },
6656 { "NIKON D3100", 0, 0,
6657 { 7911,-2167,-813,-5327,13150,2408,-1288,2483,7968 } },
6658 { "NIKON D3200", 0, 0xfb9,
6659 { 7013,-1408,-635,-5268,12902,2640,-1470,2801,7379 } },
6660 { "NIKON D300", 0, 0,
6661 { 9030,-1992,-715,-8465,16302,2255,-2689,3217,8069 } },
6662 { "NIKON D3X", 0, 0,
6663 { 7171,-1986,-648,-8085,15555,2718,-2170,2512,7457 } },
6664 { "NIKON D3S", 0, 0,
6665 { 8828,-2406,-694,-4874,12603,2541,-660,1509,7587 } },
6667 { 8139,-2171,-663,-8747,16541,2295,-1925,2008,8093 } },
6668 { "NIKON D40X", 0, 0,
6669 { 8819,-2543,-911,-9025,16928,2151,-1329,1213,8449 } },
6670 { "NIKON D40", 0, 0,
6671 { 6992,-1668,-806,-8138,15748,2543,-874,850,7897 } },
6673 { 8598,-2848,-857,-5618,13606,2195,-1002,1773,7137 } },
6674 { "NIKON D5000", 0, 0xf00,
6675 { 7309,-1403,-519,-8474,16008,2622,-2433,2826,8064 } },
6676 { "NIKON D5100", 0, 0x3de6,
6677 { 8198,-2239,-724,-4871,12389,2798,-1043,2050,7181 } },
6678 { "NIKON D50", 0, 0,
6679 { 7732,-2422,-789,-8238,15884,2498,-859,783,7330 } },
6680 { "NIKON D600", 0, 0x3e07,
6681 { 8178,-2245,-609,-4857,12394,2776,-1207,2086,7298 } },
6682 { "NIKON D60", 0, 0,
6683 { 8736,-2458,-935,-9075,16894,2251,-1354,1242,8263 } },
6684 { "NIKON D7000", 0, 0,
6685 { 8198,-2239,-724,-4871,12389,2798,-1043,2050,7181 } },
6686 { "NIKON D700", 0, 0,
6687 { 8139,-2171,-663,-8747,16541,2295,-1925,2008,8093 } },
6688 { "NIKON D70", 0, 0,
6689 { 7732,-2422,-789,-8238,15884,2498,-859,783,7330 } },
6690 { "NIKON D800", 0, 0,
6691 { 7866,-2108,-555,-4869,12483,2681,-1176,2069,7501 } },
6692 { "NIKON D80", 0, 0,
6693 { 8629,-2410,-883,-9055,16940,2171,-1490,1363,8520 } },
6694 { "NIKON D90", 0, 0xf00,
6695 { 7309,-1403,-519,-8474,16008,2622,-2434,2826,8064 } },
6696 { "NIKON E950", 0, 0x3dd, /* DJC */
6697 { -3746,10611,1665,9621,-1734,2114,-2389,7082,3064,3406,6116,-244 } },
6698 { "NIKON E995", 0, 0, /* copied from E5000 */
6699 { -5547,11762,2189,5814,-558,3342,-4924,9840,5949,688,9083,96 } },
6700 { "NIKON E2100", 0, 0, /* copied from Z2, new white balance */
6701 { 13142,-4152,-1596,-4655,12374,2282,-1769,2696,6711} },
6702 { "NIKON E2500", 0, 0,
6703 { -5547,11762,2189,5814,-558,3342,-4924,9840,5949,688,9083,96 } },
6704 { "NIKON E3200", 0, 0, /* DJC */
6705 { 9846,-2085,-1019,-3278,11109,2170,-774,2134,5745 } },
6706 { "NIKON E4300", 0, 0, /* copied from Minolta DiMAGE Z2 */
6707 { 11280,-3564,-1370,-4655,12374,2282,-1423,2168,5396 } },
6708 { "NIKON E4500", 0, 0,
6709 { -5547,11762,2189,5814,-558,3342,-4924,9840,5949,688,9083,96 } },
6710 { "NIKON E5000", 0, 0,
6711 { -5547,11762,2189,5814,-558,3342,-4924,9840,5949,688,9083,96 } },
6712 { "NIKON E5400", 0, 0,
6713 { 9349,-2987,-1001,-7919,15766,2266,-2098,2680,6839 } },
6714 { "NIKON E5700", 0, 0,
6715 { -5368,11478,2368,5537,-113,3148,-4969,10021,5782,778,9028,211 } },
6716 { "NIKON E8400", 0, 0,
6717 { 7842,-2320,-992,-8154,15718,2599,-1098,1342,7560 } },
6718 { "NIKON E8700", 0, 0,
6719 { 8489,-2583,-1036,-8051,15583,2643,-1307,1407,7354 } },
6720 { "NIKON E8800", 0, 0,
6721 { 7971,-2314,-913,-8451,15762,2894,-1442,1520,7610 } },
6722 { "NIKON COOLPIX P6000", 0, 0,
6723 { 9698,-3367,-914,-4706,12584,2368,-837,968,5801 } },
6724 { "NIKON COOLPIX P7000", 0, 0,
6725 { 11432,-3679,-1111,-3169,11239,2202,-791,1380,4455 } },
6726 { "NIKON COOLPIX P7100", 0, 0,
6727 { 11053,-4269,-1024,-1976,10182,2088,-526,1263,4469 } },
6728 { "NIKON COOLPIX P7700", 200, 0,
6729 { 10321,-3920,-931,-2750,11146,1824,-442,1545,5539 } },
6730 { "NIKON 1 V2", 0, 0,
6731 { 6588,-1305,-693,-3277,10987,2634,-355,2016,5106 } },
6733 { 8994,-2667,-865,-4594,12324,2552,-699,1786,6260 } },
6734 { "OLYMPUS C5050", 0, 0,
6735 { 10508,-3124,-1273,-6079,14294,1901,-1653,2306,6237 } },
6736 { "OLYMPUS C5060", 0, 0,
6737 { 10445,-3362,-1307,-7662,15690,2058,-1135,1176,7602 } },
6738 { "OLYMPUS C7070", 0, 0,
6739 { 10252,-3531,-1095,-7114,14850,2436,-1451,1723,6365 } },
6740 { "OLYMPUS C70", 0, 0,
6741 { 10793,-3791,-1146,-7498,15177,2488,-1390,1577,7321 } },
6742 { "OLYMPUS C80", 0, 0,
6743 { 8606,-2509,-1014,-8238,15714,2703,-942,979,7760 } },
6744 { "OLYMPUS E-10", 0, 0xffc,
6745 { 12745,-4500,-1416,-6062,14542,1580,-1934,2256,6603 } },
6746 { "OLYMPUS E-1", 0, 0,
6747 { 11846,-4767,-945,-7027,15878,1089,-2699,4122,8311 } },
6748 { "OLYMPUS E-20", 0, 0xffc,
6749 { 13173,-4732,-1499,-5807,14036,1895,-2045,2452,7142 } },
6750 { "OLYMPUS E-300", 0, 0,
6751 { 7828,-1761,-348,-5788,14071,1830,-2853,4518,6557 } },
6752 { "OLYMPUS E-330", 0, 0,
6753 { 8961,-2473,-1084,-7979,15990,2067,-2319,3035,8249 } },
6754 { "OLYMPUS E-30", 0, 0xfbc,
6755 { 8144,-1861,-1111,-7763,15894,1929,-1865,2542,7607 } },
6756 { "OLYMPUS E-3", 0, 0xf99,
6757 { 9487,-2875,-1115,-7533,15606,2010,-1618,2100,7389 } },
6758 { "OLYMPUS E-400", 0, 0,
6759 { 6169,-1483,-21,-7107,14761,2536,-2904,3580,8568 } },
6760 { "OLYMPUS E-410", 0, 0xf6a,
6761 { 8856,-2582,-1026,-7761,15766,2082,-2009,2575,7469 } },
6762 { "OLYMPUS E-420", 0, 0xfd7,
6763 { 8746,-2425,-1095,-7594,15612,2073,-1780,2309,7416 } },
6764 { "OLYMPUS E-450", 0, 0xfd2,
6765 { 8745,-2425,-1095,-7594,15613,2073,-1780,2309,7416 } },
6766 { "OLYMPUS E-500", 0, 0,
6767 { 8136,-1968,-299,-5481,13742,1871,-2556,4205,6630 } },
6768 { "OLYMPUS E-510", 0, 0xf6a,
6769 { 8785,-2529,-1033,-7639,15624,2112,-1783,2300,7817 } },
6770 { "OLYMPUS E-520", 0, 0xfd2,
6771 { 8344,-2322,-1020,-7596,15635,2048,-1748,2269,7287 } },
6772 { "OLYMPUS E-5", 0, 0xeec,
6773 { 11200,-3783,-1325,-4576,12593,2206,-695,1742,7504 } },
6774 { "OLYMPUS E-600", 0, 0xfaf,
6775 { 8453,-2198,-1092,-7609,15681,2008,-1725,2337,7824 } },
6776 { "OLYMPUS E-620", 0, 0xfaf,
6777 { 8453,-2198,-1092,-7609,15681,2008,-1725,2337,7824 } },
6778 { "OLYMPUS E-P1", 0, 0xffd,
6779 { 8343,-2050,-1021,-7715,15705,2103,-1831,2380,8235 } },
6780 { "OLYMPUS E-P2", 0, 0xffd,
6781 { 8343,-2050,-1021,-7715,15705,2103,-1831,2380,8235 } },
6782 { "OLYMPUS E-P3", 0, 0,
6783 { 7575,-2159,-571,-3722,11341,2725,-1434,2819,6271 } },
6784 { "OLYMPUS E-PL1s", 0, 0,
6785 { 11409,-3872,-1393,-4572,12757,2003,-709,1810,7415 } },
6786 { "OLYMPUS E-PL1", 0, 0,
6787 { 11408,-4289,-1215,-4286,12385,2118,-387,1467,7787 } },
6788 { "OLYMPUS E-PL2", 0, 0,
6789 { 15030,-5552,-1806,-3987,12387,1767,-592,1670,7023 } },
6790 { "OLYMPUS E-PL3", 0, 0,
6791 { 7575,-2159,-571,-3722,11341,2725,-1434,2819,6271 } },
6792 { "OLYMPUS E-PL5", 0, 0xfcb,
6793 { 8380,-2630,-639,-2887,10725,2496,-627,1427,5438 } },
6794 { "OLYMPUS E-PM1", 0, 0,
6795 { 7575,-2159,-571,-3722,11341,2725,-1434,2819,6271 } },
6796 { "OLYMPUS E-PM2", 0, 0,
6797 { 8380,-2630,-639,-2887,10725,2496,-627,1427,5438 } },
6798 { "OLYMPUS E-M5", 0, 0xfe1,
6799 { 8380,-2630,-639,-2887,10725,2496,-627,1427,5438 } },
6800 { "OLYMPUS SP350", 0, 0,
6801 { 12078,-4836,-1069,-6671,14306,2578,-786,939,7418 } },
6802 { "OLYMPUS SP3", 0, 0,
6803 { 11766,-4445,-1067,-6901,14421,2707,-1029,1217,7572 } },
6804 { "OLYMPUS SP500UZ", 0, 0xfff,
6805 { 9493,-3415,-666,-5211,12334,3260,-1548,2262,6482 } },
6806 { "OLYMPUS SP510UZ", 0, 0xffe,
6807 { 10593,-3607,-1010,-5881,13127,3084,-1200,1805,6721 } },
6808 { "OLYMPUS SP550UZ", 0, 0xffe,
6809 { 11597,-4006,-1049,-5432,12799,2957,-1029,1750,6516 } },
6810 { "OLYMPUS SP560UZ", 0, 0xff9,
6811 { 10915,-3677,-982,-5587,12986,2911,-1168,1968,6223 } },
6812 { "OLYMPUS SP570UZ", 0, 0,
6813 { 11522,-4044,-1146,-4736,12172,2904,-988,1829,6039 } },
6814 { "OLYMPUS XZ-1", 0, 0,
6815 { 10901,-4095,-1074,-1141,9208,2293,-62,1417,5158 } },
6816 { "OLYMPUS XZ-2", 0, 0,
6817 { 9777,-3483,-925,-2886,11297,1800,-602,1663,5134 } },
6818 { "PENTAX *ist DL2", 0, 0,
6819 { 10504,-2438,-1189,-8603,16207,2531,-1022,863,12242 } },
6820 { "PENTAX *ist DL", 0, 0,
6821 { 10829,-2838,-1115,-8339,15817,2696,-837,680,11939 } },
6822 { "PENTAX *ist DS2", 0, 0,
6823 { 10504,-2438,-1189,-8603,16207,2531,-1022,863,12242 } },
6824 { "PENTAX *ist DS", 0, 0,
6825 { 10371,-2333,-1206,-8688,16231,2602,-1230,1116,11282 } },
6826 { "PENTAX *ist D", 0, 0,
6827 { 9651,-2059,-1189,-8881,16512,2487,-1460,1345,10687 } },
6828 { "PENTAX K10D", 0, 0,
6829 { 9566,-2863,-803,-7170,15172,2112,-818,803,9705 } },
6830 { "PENTAX K1", 0, 0,
6831 { 11095,-3157,-1324,-8377,15834,2720,-1108,947,11688 } },
6832 { "PENTAX K20D", 0, 0,
6833 { 9427,-2714,-868,-7493,16092,1373,-2199,3264,7180 } },
6834 { "PENTAX K200D", 0, 0,
6835 { 9186,-2678,-907,-8693,16517,2260,-1129,1094,8524 } },
6836 { "PENTAX K2000", 0, 0,
6837 { 11057,-3604,-1155,-5152,13046,2329,-282,375,8104 } },
6838 { "PENTAX K-m", 0, 0,
6839 { 11057,-3604,-1155,-5152,13046,2329,-282,375,8104 } },
6840 { "PENTAX K-x", 0, 0,
6841 { 8843,-2837,-625,-5025,12644,2668,-411,1234,7410 } },
6842 { "PENTAX K-r", 0, 0,
6843 { 9895,-3077,-850,-5304,13035,2521,-883,1768,6936 } },
6844 { "PENTAX K-5 II", 0, 0,
6845 { 8170,-2725,-639,-4440,12017,2744,-771,1465,6599 } },
6846 { "PENTAX K-5", 0, 0,
6847 { 8713,-2833,-743,-4342,11900,2772,-722,1543,6247 } },
6848 { "PENTAX K-7", 0, 0,
6849 { 9142,-2947,-678,-8648,16967,1663,-2224,2898,8615 } },
6850 { "PENTAX 645D", 0, 0x3e00,
6851 { 10646,-3593,-1158,-3329,11699,1831,-667,2874,6287 } },
6852 { "Panasonic DMC-FZ8", 0, 0xf7f,
6853 { 8986,-2755,-802,-6341,13575,3077,-1476,2144,6379 } },
6854 { "Panasonic DMC-FZ18", 0, 0,
6855 { 9932,-3060,-935,-5809,13331,2753,-1267,2155,5575 } },
6856 { "Panasonic DMC-FZ28", 15, 0xf96,
6857 { 10109,-3488,-993,-5412,12812,2916,-1305,2140,5543 } },
6858 { "Panasonic DMC-FZ30", 0, 0xf94,
6859 { 10976,-4029,-1141,-7918,15491,2600,-1670,2071,8246 } },
6860 { "Panasonic DMC-FZ3", 143, 0,
6861 { 9938,-2780,-890,-4604,12393,2480,-1117,2304,4620 } },
6862 { "Panasonic DMC-FZ4", 143, 0,
6863 { 13639,-5535,-1371,-1698,9633,2430,316,1152,4108 } },
6864 { "Panasonic DMC-FZ50", 0, 0,
6865 { 7906,-2709,-594,-6231,13351,3220,-1922,2631,6537 } },
6866 { "LEICA V-LUX1", 0, 0,
6867 { 7906,-2709,-594,-6231,13351,3220,-1922,2631,6537 } },
6868 { "Panasonic DMC-L10", 15, 0xf96,
6869 { 8025,-1942,-1050,-7920,15904,2100,-2456,3005,7039 } },
6870 { "Panasonic DMC-L1", 0, 0xf7f,
6871 { 8054,-1885,-1025,-8349,16367,2040,-2805,3542,7629 } },
6872 { "LEICA DIGILUX 3", 0, 0xf7f,
6873 { 8054,-1885,-1025,-8349,16367,2040,-2805,3542,7629 } },
6874 { "Panasonic DMC-LC1", 0, 0,
6875 { 11340,-4069,-1275,-7555,15266,2448,-2960,3426,7685 } },
6876 { "LEICA DIGILUX 2", 0, 0,
6877 { 11340,-4069,-1275,-7555,15266,2448,-2960,3426,7685 } },
6878 { "Panasonic DMC-LX1", 0, 0xf7f,
6879 { 10704,-4187,-1230,-8314,15952,2501,-920,945,8927 } },
6880 { "LEICA D-LUX2", 0, 0xf7f,
6881 { 10704,-4187,-1230,-8314,15952,2501,-920,945,8927 } },
6882 { "Panasonic DMC-LX2", 0, 0,
6883 { 8048,-2810,-623,-6450,13519,3272,-1700,2146,7049 } },
6884 { "LEICA D-LUX3", 0, 0,
6885 { 8048,-2810,-623,-6450,13519,3272,-1700,2146,7049 } },
6886 { "Panasonic DMC-LX3", 15, 0,
6887 { 8128,-2668,-655,-6134,13307,3161,-1782,2568,6083 } },
6888 { "LEICA D-LUX 4", 15, 0,
6889 { 8128,-2668,-655,-6134,13307,3161,-1782,2568,6083 } },
6890 { "Panasonic DMC-LX5", 143, 0,
6891 { 10909,-4295,-948,-1333,9306,2399,22,1738,4582 } },
6892 { "LEICA D-LUX 5", 143, 0,
6893 { 10909,-4295,-948,-1333,9306,2399,22,1738,4582 } },
6894 { "Panasonic DMC-LX7", 143, 0,
6895 { 10148,-3743,-991,-2837,11366,1659,-701,1893,4899 } },
6896 { "LEICA D-LUX 6", 143, 0,
6897 { 10148,-3743,-991,-2837,11366,1659,-701,1893,4899 } },
6898 { "Panasonic DMC-FZ100", 143, 0xfff,
6899 { 16197,-6146,-1761,-2393,10765,1869,366,2238,5248 } },
6900 { "LEICA V-LUX 2", 143, 0xfff,
6901 { 16197,-6146,-1761,-2393,10765,1869,366,2238,5248 } },
6902 { "Panasonic DMC-FZ150", 143, 0xfff,
6903 { 11904,-4541,-1189,-2355,10899,1662,-296,1586,4289 } },
6904 { "LEICA V-LUX 3", 143, 0xfff,
6905 { 11904,-4541,-1189,-2355,10899,1662,-296,1586,4289 } },
6906 { "Panasonic DMC-FZ200", 143, 0xfff,
6907 { 8112,-2563,-740,-3730,11784,2197,-941,2075,4933 } },
6908 { "LEICA V-LUX 4", 143, 0xfff,
6909 { 8112,-2563,-740,-3730,11784,2197,-941,2075,4933 } },
6910 { "Panasonic DMC-FX150", 15, 0xfff,
6911 { 9082,-2907,-925,-6119,13377,3058,-1797,2641,5609 } },
6912 { "Panasonic DMC-G10", 0, 0,
6913 { 10113,-3400,-1114,-4765,12683,2317,-377,1437,6710 } },
6914 { "Panasonic DMC-G1", 15, 0xf94,
6915 { 8199,-2065,-1056,-8124,16156,2033,-2458,3022,7220 } },
6916 { "Panasonic DMC-G2", 15, 0xf3c,
6917 { 10113,-3400,-1114,-4765,12683,2317,-377,1437,6710 } },
6918 { "Panasonic DMC-G3", 143, 0xfff,
6919 { 6763,-1919,-863,-3868,11515,2684,-1216,2387,5879 } },
6920 { "Panasonic DMC-G5", 143, 0xfff,
6921 { 7798,-2562,-740,-3879,11584,2613,-1055,2248,5434 } },
6922 { "Panasonic DMC-GF1", 15, 0xf92,
6923 { 7888,-1902,-1011,-8106,16085,2099,-2353,2866,7330 } },
6924 { "Panasonic DMC-GF2", 143, 0xfff,
6925 { 7888,-1902,-1011,-8106,16085,2099,-2353,2866,7330 } },
6926 { "Panasonic DMC-GF3", 143, 0xfff,
6927 { 9051,-2468,-1204,-5212,13276,2121,-1197,2510,6890 } },
6928 { "Panasonic DMC-GF5", 143, 0xfff,
6929 { 8228,-2945,-660,-3938,11792,2430,-1094,2278,5793 } },
6930 { "Panasonic DMC-GH1", 15, 0xf92,
6931 { 6299,-1466,-532,-6535,13852,2969,-2331,3112,5984 } },
6932 { "Panasonic DMC-GH2", 15, 0xf95,
6933 { 7780,-2410,-806,-3913,11724,2484,-1018,2390,5298 } },
6934 { "Panasonic DMC-GH3", 144, 0,
6935 { 6559,-1752,-491,-3672,11407,2586,-962,1875,5130 } },
6936 { "Panasonic DMC-GX1", 143, 0,
6937 { 6763,-1919,-863,-3868,11515,2684,-1216,2387,5879 } },
6938 { "Phase One H 20", 0, 0, /* DJC */
6939 { 1313,1855,-109,-6715,15908,808,-327,1840,6020 } },
6940 { "Phase One H 25", 0, 0,
6941 { 2905,732,-237,-8134,16626,1476,-3038,4253,7517 } },
6942 { "Phase One P 2", 0, 0,
6943 { 2905,732,-237,-8134,16626,1476,-3038,4253,7517 } },
6944 { "Phase One P 30", 0, 0,
6945 { 4516,-245,-37,-7020,14976,2173,-3206,4671,7087 } },
6946 { "Phase One P 45", 0, 0,
6947 { 5053,-24,-117,-5684,14076,1702,-2619,4492,5849 } },
6948 { "Phase One P40", 0, 0,
6949 { 8035,435,-962,-6001,13872,2320,-1159,3065,5434 } },
6950 { "Phase One P65", 0, 0,
6951 { 8035,435,-962,-6001,13872,2320,-1159,3065,5434 } },
6952 { "RED ONE", 704, 0xffff, /* DJC */
6953 { 21014,-7891,-2613,-3056,12201,856,-2203,5125,8042 } },
6954 { "SAMSUNG EX1", 0, 0x3e00,
6955 { 8898,-2498,-994,-3144,11328,2066,-760,1381,4576 } },
6956 { "SAMSUNG EX2F", 0, 0x7ff,
6957 { 10648,-3897,-1055,-2022,10573,1668,-492,1611,4742 } },
6958 { "SAMSUNG NX2", 0, 0xfff, /* NX20, NX200, NX210 */
6959 { 6933,-2268,-753,-4921,13387,1647,-803,1641,6096 } },
6960 { "SAMSUNG NX1000", 0, 0,
6961 { 6933,-2268,-753,-4921,13387,1647,-803,1641,6096 } },
6962 { "SAMSUNG NX", 0, 0, /* NX5, NX10, NX11, NX100 */
6963 { 10332,-3234,-1168,-6111,14639,1520,-1352,2647,8331 } },
6964 { "SAMSUNG WB2000", 0, 0xfff,
6965 { 12093,-3557,-1155,-1000,9534,1733,-22,1787,4576 } },
6966 { "SAMSUNG GX-1", 0, 0,
6967 { 10504,-2438,-1189,-8603,16207,2531,-1022,863,12242 } },
6968 { "SAMSUNG S85", 0, 0xffff, /* DJC */
6969 { 11885,-3968,-1473,-4214,12299,1916,-835,1655,5549 } },
6970 { "Sinar", 0, 0, /* DJC */
6971 { 16442,-2956,-2422,-2877,12128,750,-1136,6066,4559 } },
6972 { "SONY DSC-F828", 0, 0,
6973 { 7924,-1910,-777,-8226,15459,2998,-1517,2199,6818,-7242,11401,3481 } },
6974 { "SONY DSC-R1", 512, 0,
6975 { 8512,-2641,-694,-8042,15670,2526,-1821,2117,7414 } },
6976 { "SONY DSC-V3", 0, 0,
6977 { 7511,-2571,-692,-7894,15088,3060,-948,1111,8128 } },
6978 { "SONY DSC-RX100", 200, 0,
6979 { 8651,-2754,-1057,-3464,12207,1373,-568,1398,4434 } },
6980 { "SONY DSC-RX1", 128, 0,
6981 { 6344,-1612,-462,-4863,12477,2681,-865,1786,6899 } },
6982 { "SONY DSLR-A100", 0, 0xfeb,
6983 { 9437,-2811,-774,-8405,16215,2290,-710,596,7181 } },
6984 { "SONY DSLR-A290", 0, 0,
6985 { 6038,-1484,-579,-9145,16746,2512,-875,746,7218 } },
6986 { "SONY DSLR-A2", 0, 0,
6987 { 9847,-3091,-928,-8485,16345,2225,-715,595,7103 } },
6988 { "SONY DSLR-A300", 0, 0,
6989 { 9847,-3091,-928,-8485,16345,2225,-715,595,7103 } },
6990 { "SONY DSLR-A330", 0, 0,
6991 { 9847,-3091,-929,-8485,16346,2225,-714,595,7103 } },
6992 { "SONY DSLR-A350", 0, 0xffc,
6993 { 6038,-1484,-578,-9146,16746,2513,-875,746,7217 } },
6994 { "SONY DSLR-A380", 0, 0,
6995 { 6038,-1484,-579,-9145,16746,2512,-875,746,7218 } },
6996 { "SONY DSLR-A390", 0, 0,
6997 { 6038,-1484,-579,-9145,16746,2512,-875,746,7218 } },
6998 { "SONY DSLR-A450", 128, 0xfeb,
6999 { 4950,-580,-103,-5228,12542,3029,-709,1435,7371 } },
7000 { "SONY DSLR-A580", 128, 0xfeb,
7001 { 5932,-1492,-411,-4813,12285,2856,-741,1524,6739 } },
7002 { "SONY DSLR-A5", 128, 0xfeb,
7003 { 4950,-580,-103,-5228,12542,3029,-709,1435,7371 } },
7004 { "SONY DSLR-A700", 126, 0,
7005 { 5775,-805,-359,-8574,16295,2391,-1943,2341,7249 } },
7006 { "SONY DSLR-A850", 128, 0,
7007 { 5413,-1162,-365,-5665,13098,2866,-608,1179,8440 } },
7008 { "SONY DSLR-A900", 128, 0,
7009 { 5209,-1072,-397,-8845,16120,2919,-1618,1803,8654 } },
7010 { "SONY NEX-5N", 128, 0,
7011 { 5991,-1456,-455,-4764,12135,2980,-707,1425,6701 } },
7012 { "SONY NEX-5R", 128, 0,
7013 { 6129,-1545,-418,-4930,12490,2743,-977,1693,6615 } },
7014 { "SONY NEX-3", 138, 0, /* DJC */
7015 { 6907,-1256,-645,-4940,12621,2320,-1710,2581,6230 } },
7016 { "SONY NEX-5", 116, 0, /* DJC */
7017 { 6807,-1350,-342,-4216,11649,2567,-1089,2001,6420 } },
7018 { "SONY NEX-3", 128, 0, /* Adobe */
7019 { 6549,-1550,-436,-4880,12435,2753,-854,1868,6976 } },
7020 { "SONY NEX-5", 128, 0, /* Adobe */
7021 { 6549,-1550,-436,-4880,12435,2753,-854,1868,6976 } },
7022 { "SONY NEX-6", 128, 0,
7023 { 6129,-1545,-418,-4930,12490,2743,-977,1693,6615 } },
7024 { "SONY NEX-7", 128, 0,
7025 { 5491,-1192,-363,-4951,12342,2948,-911,1722,7192 } },
7026 { "SONY NEX", 128, 0, /* NEX-C3, NEX-F3 */
7027 { 5991,-1456,-455,-4764,12135,2980,-707,1425,6701 } },
7028 { "SONY SLT-A33", 128, 0,
7029 { 6069,-1221,-366,-5221,12779,2734,-1024,2066,6834 } },
7030 { "SONY SLT-A35", 128, 0,
7031 { 5986,-1618,-415,-4557,11820,3120,-681,1404,6971 } },
7032 { "SONY SLT-A37", 128, 0,
7033 { 5991,-1456,-455,-4764,12135,2980,-707,1425,6701 } },
7034 { "SONY SLT-A55", 128, 0,
7035 { 5932,-1492,-411,-4813,12285,2856,-741,1524,6739 } },
7036 { "SONY SLT-A57", 128, 0,
7037 { 5991,-1456,-455,-4764,12135,2980,-707,1425,6701 } },
7038 { "SONY SLT-A65", 128, 0,
7039 { 5491,-1192,-363,-4951,12342,2948,-911,1722,7192 } },
7040 { "SONY SLT-A77", 128, 0,
7041 { 5491,-1192,-363,-4951,12342,2948,-911,1722,7192 } },
7042 { "SONY SLT-A99", 128, 0,
7043 { 6344,-1612,-462,-4863,12477,2681,-865,1786,6899 } },
7045 double cam_xyz[4][3];
7049 sprintf (name, "%s %s", make, model);
7050 for (i=0; i < sizeof table / sizeof *table; i++)
7051 if (!strncmp (name, table[i].prefix, strlen(table[i].prefix))) {
7052 if (table[i].black) black = (ushort) table[i].black;
7053 if (table[i].maximum) maximum = (ushort) table[i].maximum;
7054 if (table[i].trans[0]) {
7055 double *dp = &cam_xyz[0][0];
7056 const short *sp = &table[i].trans[0];
7057 for( j=12; --j>=0; ++dp,++sp ) *dp = *sp / 10000.0;
7058 cam_xyz_coeff (cam_xyz);
7064 void CLASS simple_coeff (int index)
7066 static const float table[][12] = {
7067 /* index 0 -- all Foveon cameras */
7068 { 1.4032,-0.2231,-0.1016,-0.5263,1.4816,0.017,-0.0112,0.0183,0.9113 },
7069 /* index 1 -- Kodak DC20 and DC25 */
7070 { 2.25,0.75,-1.75,-0.25,-0.25,0.75,0.75,-0.25,-0.25,-1.75,0.75,2.25 },
7071 /* index 2 -- Logitech Fotoman Pixtura */
7072 { 1.893,-0.418,-0.476,-0.495,1.773,-0.278,-1.017,-0.655,2.672 },
7073 /* index 3 -- Nikon E880, E900, and E990 */
7074 { -1.936280, 1.800443, -1.448486, 2.584324,
7075 1.405365, -0.524955, -0.289090, 0.408680,
7076 -1.204965, 1.082304, 2.941367, -1.818705 }
7080 for (raw_color = i=0; i < 3; i++)
7081 FORCC rgb_cam[i][c] = table[index][i*colors+c];
7084 short CLASS guess_byte_order (int words)
7088 double diff, sum[2] = {0,0};
7090 fread (test[0], 2, 2, ifp);
7091 for (words-=2; words--; ) {
7092 fread (test[t], 2, 1, ifp);
7093 for (msb=0; msb < 2; msb++) {
7094 diff = (test[t^2][msb] << 8 | test[t^2][!msb])
7095 - (test[t ][msb] << 8 | test[t ][!msb]);
7096 sum[msb] += diff*diff;
7100 return sum[0] < sum[1] ? 0x4d4d : 0x4949;
7103 float CLASS find_green (int bps, int bite, int off0, int off1)
7106 int vbits, col, i, c;
7107 ushort img[2][2064];
7111 fseek (ifp, c ? off1:off0, SEEK_SET);
7112 for (vbits=col=0; col < width; col++) {
7113 for (vbits -= bps; vbits < 0; vbits += bite) {
7115 for (i=0; i < bite; i+=8)
7116 bitbuf |= (unsigned) (fgetc(ifp) << i);
7118 img[c][col] = bitbuf << (64-bps-vbits) >> (64-bps);
7122 sum[ c & 1] += ABS(img[0][c]-img[1][c+1]);
7123 sum[~c & 1] += ABS(img[1][c]-img[0][c+1]);
7125 return 100 * log(sum[0]/sum[1]);
7129 Identify which camera created this file, and set global variables
7132 void CLASS identify()
7135 int hlen, flen, fsize, zero_fsize=1, i, c, is_canon;
7138 { 3130, 1743, 4, 0, -6, 0 },
7139 { 3130, 2055, 4, 0, -6, 0 },
7140 { 3130, 2319, 4, 0, -6, 0 },
7141 { 3170, 2103, 18, 0,-42, 20 },
7142 { 3170, 2367, 18, 13,-42,-21 },
7143 { 3177, 2367, 0, 0, -1, 0 },
7144 { 3304, 2458, 0, 0, -1, 0 },
7145 { 3330, 2463, 9, 0, -5, 0 },
7146 { 3330, 2479, 9, 0,-17, 4 },
7147 { 3370, 1899, 15, 0,-44, 20 },
7148 { 3370, 2235, 15, 0,-44, 20 },
7149 { 3370, 2511, 15, 10,-44,-21 },
7150 { 3690, 2751, 3, 0, -8, -3 },
7151 { 3710, 2751, 0, 0, -3, 0 },
7152 { 3724, 2450, 0, 0, 0, -2 },
7153 { 3770, 2487, 17, 0,-44, 19 },
7154 { 3770, 2799, 17, 15,-44,-19 },
7155 { 3880, 2170, 6, 0, -6, 0 },
7156 { 4060, 3018, 0, 0, 0, -2 },
7157 { 4290, 2391, 3, 0, -8, -1 },
7158 { 4330, 2439, 17, 15,-44,-19 },
7159 { 4508, 2962, 0, 0, -3, -4 },
7160 { 4508, 3330, 0, 0, -3, -6 } };
7161 static const struct {
7163 char make[12], model[19], withjpeg;
7165 { 62464, "Kodak", "DC20" ,0 },
7166 { 124928, "Kodak", "DC20" ,0 },
7167 { 1652736, "Kodak", "DCS200" ,0 },
7168 { 4159302, "Kodak", "C330" ,0 },
7169 { 4162462, "Kodak", "C330" ,0 },
7170 { 460800, "Kodak", "C603v" ,0 },
7171 { 614400, "Kodak", "C603v" ,0 },
7172 { 6163328, "Kodak", "C603" ,0 },
7173 { 6166488, "Kodak", "C603" ,0 },
7174 { 9116448, "Kodak", "C603y" ,0 },
7175 { 311696, "ST Micro", "STV680 VGA" ,0 }, /* SPYz */
7176 { 787456, "Creative", "PC-CAM 600" ,0 },
7177 { 1138688, "Minolta", "RD175" ,0 },
7178 { 3840000, "Foculus", "531C" ,0 },
7179 { 307200, "Generic", "640x480" ,0 },
7180 { 786432, "AVT", "F-080C" ,0 },
7181 { 1447680, "AVT", "F-145C" ,0 },
7182 { 1920000, "AVT", "F-201C" ,0 },
7183 { 5067304, "AVT", "F-510C" ,0 },
7184 { 5067316, "AVT", "F-510C" ,0 },
7185 { 10134608, "AVT", "F-510C" ,0 },
7186 { 10134620, "AVT", "F-510C" ,0 },
7187 { 16157136, "AVT", "F-810C" ,0 },
7188 { 1409024, "Sony", "XCD-SX910CR" ,0 },
7189 { 2818048, "Sony", "XCD-SX910CR" ,0 },
7190 { 3884928, "Micron", "2010" ,0 },
7191 { 6624000, "Pixelink", "A782" ,0 },
7192 { 13248000, "Pixelink", "A782" ,0 },
7193 { 6291456, "RoverShot","3320AF" ,0 },
7194 { 6553440, "Canon", "PowerShot A460" ,0 },
7195 { 6653280, "Canon", "PowerShot A530" ,0 },
7196 { 6573120, "Canon", "PowerShot A610" ,0 },
7197 { 9219600, "Canon", "PowerShot A620" ,0 },
7198 { 9243240, "Canon", "PowerShot A470" ,0 },
7199 { 10341600, "Canon", "PowerShot A720 IS",0 },
7200 { 10383120, "Canon", "PowerShot A630" ,0 },
7201 { 12945240, "Canon", "PowerShot A640" ,0 },
7202 { 15636240, "Canon", "PowerShot A650" ,0 },
7203 { 5298000, "Canon", "PowerShot SD300" ,0 },
7204 { 7710960, "Canon", "PowerShot S3 IS" ,0 },
7205 { 15467760, "Canon", "PowerShot SX110 IS",0 },
7206 { 15534576, "Canon", "PowerShot SX120 IS",0 },
7207 { 18653760, "Canon", "PowerShot SX20 IS",0 },
7208 { 19131120, "Canon", "PowerShot SX220 HS",0 },
7209 { 21936096, "Canon", "PowerShot SX30 IS",0 },
7210 { 5939200, "OLYMPUS", "C770UZ" ,0 },
7211 { 1581060, "NIKON", "E900" ,1 }, /* or E900s,E910 */
7212 { 2465792, "NIKON", "E950" ,1 }, /* or E800,E700 */
7213 { 2940928, "NIKON", "E2100" ,1 }, /* or E2500 */
7214 { 4771840, "NIKON", "E990" ,1 }, /* or E995, Oly C3030Z */
7215 { 4775936, "NIKON", "E3700" ,1 }, /* or Optio 33WR */
7216 { 5869568, "NIKON", "E4300" ,1 }, /* or DiMAGE Z2 */
7217 { 5865472, "NIKON", "E4500" ,1 },
7218 { 7438336, "NIKON", "E5000" ,1 }, /* or E5700 */
7219 { 8998912, "NIKON", "COOLPIX S6" ,1 },
7220 { 1976352, "CASIO", "QV-2000UX" ,1 },
7221 { 3217760, "CASIO", "QV-3*00EX" ,1 },
7222 { 6218368, "CASIO", "QV-5700" ,1 },
7223 { 6054400, "CASIO", "QV-R41" ,1 },
7224 { 7530816, "CASIO", "QV-R51" ,1 },
7225 { 7684000, "CASIO", "QV-4000" ,1 },
7226 { 2937856, "CASIO", "EX-S20" ,1 },
7227 { 4948608, "CASIO", "EX-S100" ,1 },
7228 { 7542528, "CASIO", "EX-Z50" ,1 },
7229 { 7562048, "CASIO", "EX-Z500" ,1 },
7230 { 7753344, "CASIO", "EX-Z55" ,1 },
7231 { 7816704, "CASIO", "EX-Z60" ,1 },
7232 { 10843712, "CASIO", "EX-Z75" ,1 },
7233 { 10834368, "CASIO", "EX-Z750" ,1 },
7234 { 12310144, "CASIO", "EX-Z850" ,1 },
7235 { 12489984, "CASIO", "EX-Z8" ,1 },
7236 { 15499264, "CASIO", "EX-Z1050" ,1 },
7237 { 18702336, "CASIO", "EX-ZR100" ,1 },
7238 { 7426656, "CASIO", "EX-P505" ,1 },
7239 { 9313536, "CASIO", "EX-P600" ,1 },
7240 { 10979200, "CASIO", "EX-P700" ,1 },
7241 { 3178560, "PENTAX", "Optio S" ,1 },
7242 { 4841984, "PENTAX", "Optio S" ,1 },
7243 { 6114240, "PENTAX", "Optio S4" ,1 }, /* or S4i, CASIO EX-Z4 */
7244 { 10702848, "PENTAX", "Optio 750Z" ,1 },
7245 { 15980544, "AGFAPHOTO","DC-833m" ,1 },
7246 { 16098048, "SAMSUNG", "S85" ,1 },
7247 { 16215552, "SAMSUNG", "S85" ,1 },
7248 { 20487168, "SAMSUNG", "WB550" ,1 },
7249 { 24000000, "SAMSUNG", "WB550" ,1 },
7250 { 12582980, "Sinar", "" ,0 },
7251 { 33292868, "Sinar", "" ,0 },
7252 { 44390468, "Sinar", "" ,0 } };
7253 static const char *corp[] =
7254 { "Canon", "NIKON", "EPSON", "KODAK", "Kodak", "OLYMPUS", "PENTAX",
7255 "MINOLTA", "Minolta", "Konica", "CASIO", "Sinar", "Phase One",
7256 "SAMSUNG", "Mamiya", "MOTOROLA", "LEICA" };
7258 tiff_flip = flip = filters = -1; /* 0 is valid, so -1 is unknown */
7259 raw_height = raw_width = fuji_width = fuji_layout = cr2_slice[0] = 0;
7260 maximum = height = width = top_margin = left_margin = 0;
7261 cdesc[0] = desc[0] = artist[0] = make[0] = model[0] = model2[0] = 0;
7262 iso_speed = shutter = aperture = focal_len = unique_id = 0;
7264 memset (tiff_ifd, 0, sizeof tiff_ifd);
7265 memset (gpsdata, 0, sizeof gpsdata);
7266 memset (cblack, 0, sizeof cblack);
7267 memset (white, 0, sizeof white);
7268 memset (mask, 0, sizeof mask);
7269 thumb_offset = thumb_length = thumb_width = thumb_height = 0;
7270 load_raw = thumb_load_raw = 0;
7271 write_thumb = &CLASS jpeg_thumb;
7272 data_offset = meta_length = tiff_bps = tiff_compress = 0;
7273 kodak_cbpp = zero_after_ff = dng_version = load_flags = 0;
7274 timestamp = shot_order = tiff_samples = black = is_foveon = 0;
7275 mix_green = profile_length = data_error = zero_is_bad = 0;
7276 pixel_aspect = is_raw = raw_color = 1;
7277 tile_width = tile_length = 0;
7278 for (i=0; i < 4; i++) {
7279 cam_mul[i] = i == 1;
7281 FORC3 cmatrix[c][i] = 0;
7282 FORC3 rgb_cam[c][i] = c == i;
7285 for (i=0; i < 0x10000; i++) curve[i] = i;
7289 fseek (ifp, 0, SEEK_SET);
7290 fread (head, 1, 32, ifp);
7291 fseek (ifp, 0, SEEK_END);
7292 flen = fsize = ftell(ifp);
7293 if ((cp = (char *) memmem (head, 32, "MMMM", 4)) ||
7294 (cp = (char *) memmem (head, 32, "IIII", 4))) {
7295 parse_phase_one (cp-head);
7296 if (cp-head && parse_tiff(0)) apply_tiff();
7297 } else if (order == 0x4949 || order == 0x4d4d) {
7298 if (!memcmp (head+6,"HEAPCCDR",8)) {
7300 parse_ciff (hlen, flen - hlen);
7301 } else if (parse_tiff(0)) apply_tiff();
7302 } else if (!memcmp (head,"\xff\xd8\xff\xe1",4) &&
7303 !memcmp (head+6,"Exif",4)) {
7304 fseek (ifp, 4, SEEK_SET);
7305 data_offset = 4 + get2();
7306 fseek (ifp, data_offset, SEEK_SET);
7307 if (fgetc(ifp) != 0xff)
7310 } else if (!memcmp (head+25,"ARECOYK",7)) {
7311 strcpy (make, "Contax");
7312 strcpy (model,"N Digital");
7313 fseek (ifp, 33, SEEK_SET);
7315 fseek (ifp, 60, SEEK_SET);
7316 FORC4 cam_mul[c ^ (c >> 1)] = get4();
7317 } else if (!strcmp (head, "PXN")) {
7318 strcpy (make, "Logitech");
7319 strcpy (model,"Fotoman Pixtura");
7320 } else if (!strcmp (head, "qktk")) {
7321 strcpy (make, "Apple");
7322 strcpy (model,"QuickTake 100");
7323 load_raw = &CLASS quicktake_100_load_raw;
7324 } else if (!strcmp (head, "qktn")) {
7325 strcpy (make, "Apple");
7326 strcpy (model,"QuickTake 150");
7327 load_raw = &CLASS kodak_radc_load_raw;
7328 } else if (!memcmp (head,"FUJIFILM",8)) {
7329 fseek (ifp, 84, SEEK_SET);
7330 thumb_offset = get4();
7331 thumb_length = get4();
7332 fseek (ifp, 92, SEEK_SET);
7333 parse_fuji (get4());
7334 if (thumb_offset > 120) {
7335 fseek (ifp, 120, SEEK_SET);
7336 is_raw += (i = get4()) && 1;
7337 if (is_raw == 2 && shot_select)
7340 load_raw = &CLASS unpacked_load_raw;
7341 fseek (ifp, 100+28*(shot_select > 0), SEEK_SET);
7342 parse_tiff (data_offset = get4());
7343 parse_tiff (thumb_offset+12);
7345 } else if (!memcmp (head,"RIFF",4)) {
7346 fseek (ifp, 0, SEEK_SET);
7348 } else if (!memcmp (head,"\0\001\0\001\0@",6)) {
7349 fseek (ifp, 6, SEEK_SET);
7350 fread (make, 1, 8, ifp);
7351 fread (model, 1, 8, ifp);
7352 fread (model2, 1, 16, ifp);
7353 data_offset = get2();
7356 raw_height = get2();
7357 load_raw = &CLASS nokia_load_raw;
7358 filters = 0x61616161;
7359 } else if (!memcmp (head,"NOKIARAW",8)) {
7360 strcpy (make, "NOKIA");
7361 strcpy (model, "X2");
7363 fseek (ifp, 300, SEEK_SET);
7364 data_offset = get4();
7368 data_offset += i - width * 5 / 4 * height;
7369 load_raw = &CLASS nokia_load_raw;
7370 filters = 0x61616161;
7371 } else if (!memcmp (head,"ARRI",4)) {
7373 fseek (ifp, 20, SEEK_SET);
7376 strcpy (make, "ARRI");
7377 fseek (ifp, 668, SEEK_SET);
7378 fread (model, 1, 64, ifp);
7380 load_raw = &CLASS packed_load_raw;
7382 filters = 0x61616161;
7383 } else if (!memcmp (head+4,"RED1",4)) {
7384 strcpy (make, "RED");
7385 strcpy (model,"ONE");
7387 load_raw = &CLASS redcine_load_raw;
7388 gamma_curve (1/2.4, 12.92, 1, 4095);
7389 filters = 0x49494949;
7390 } else if (!memcmp (head,"DSC-Image",9))
7392 else if (!memcmp (head,"PWAD",4))
7394 else if (!memcmp (head,"\0MRM",4))
7396 else if (!memcmp (head,"FOVb",4))
7398 else if (!memcmp (head,"CI",2))
7401 for (zero_fsize=i=0; i < sizeof table / sizeof *table; i++)
7402 if (fsize == table[i].fsize) {
7403 strcpy (make, table[i].make );
7404 strcpy (model, table[i].model);
7405 if (table[i].withjpeg)
7406 parse_external_jpeg();
7408 if (zero_fsize) fsize = 0;
7409 if (make[0] == 0) parse_smal (0, flen);
7410 if (make[0] == 0) parse_jpeg (is_raw = 0);
7412 for (i=0; i < sizeof corp / sizeof *corp; i++)
7413 if (strstr (make, corp[i])) /* Simplify company names */
7414 strcpy (make, corp[i]);
7415 if (!strncmp (make,"KODAK",5) &&
7416 ((cp = strstr(model," DIGITAL CAMERA")) ||
7417 (cp = strstr(model," Digital Camera")) ||
7418 (cp = strstr(model,"FILE VERSION"))))
7420 cp = make + strlen(make); /* Remove trailing spaces */
7421 while (*--cp == ' ') *cp = 0;
7422 cp = model + strlen(model);
7423 while (*--cp == ' ') *cp = 0;
7424 i = strlen(make); /* Remove make from model */
7425 if (!strncasecmp (model, make, i) && model[i++] == ' ')
7426 memmove (model, model+i, 64-i);
7427 if (!strncmp (model,"FinePix ",8))
7428 strcpy (model, model+8);
7429 if (!strncmp (model,"Digital Camera ",15))
7430 strcpy (model, model+15);
7431 desc[511] = artist[63] = make[63] = model[63] = model2[63] = 0;
7432 if (!is_raw) goto notraw;
7434 if (!height) height = raw_height;
7435 if (!width) width = raw_width;
7436 if (height == 2624 && width == 3936) /* Pentax K10D and Samsung GX10 */
7437 { height = 2616; width = 3896; }
7438 if (height == 3136 && width == 4864) /* Pentax K20D and Samsung GX20 */
7439 { height = 3124; width = 4688; filters = 0x16161616; }
7440 if (width == 4352 && (!strcmp(model,"K-r") || !strcmp(model,"K-x")))
7441 { width = 4309; filters = 0x16161616; }
7442 if (width >= 4960 && !strncmp(model,"K-5",3))
7443 { left_margin = 10; width = 4950; filters = 0x16161616; }
7444 if (width == 4736 && !strcmp(model,"K-7"))
7445 { height = 3122; width = 4684; filters = 0x16161616; top_margin = 2; }
7446 if (width == 7424 && !strcmp(model,"645D"))
7447 { height = 5502; width = 7328; filters = 0x61616161; top_margin = 29;
7449 if (height == 3014 && width == 4096) /* Ricoh GX200 */
7452 if (filters == UINT_MAX) filters = 0;
7453 if (filters) is_raw = tiff_samples;
7454 else colors = tiff_samples;
7455 if (tiff_compress == 1)
7456 load_raw = &CLASS packed_dng_load_raw;
7457 if (tiff_compress == 7)
7458 load_raw = &CLASS lossless_dng_load_raw;
7461 if ((is_canon = !strcmp(make,"Canon")))
7462 load_raw = memcmp (head+6,"HEAPCCDR",8) ?
7463 &CLASS lossless_jpeg_load_raw : &CLASS canon_load_raw;
7464 if (!strcmp(make,"NIKON")) {
7466 load_raw = &CLASS packed_load_raw;
7467 if (model[0] == 'E')
7468 load_flags |= !data_offset << 2 | 2;
7470 if (!strcmp(make,"CASIO")) {
7471 load_raw = &CLASS packed_load_raw;
7475 /* Set parameters based on camera name (for non-DNG files). */
7478 if (height*2 < width) pixel_aspect = 0.5;
7479 if (height > width) pixel_aspect = 2;
7482 } else if (is_canon && tiff_bps == 15) {
7484 case 3344: width -= 66;
7485 case 3872: width -= 6;
7487 if (height > width) SWAP(height,width);
7489 load_raw = &CLASS canon_sraw_load_raw;
7490 } else if (!strcmp(model,"PowerShot 600")) {
7494 pixel_aspect = 607/628.0;
7496 filters = 0xe1e4e1e4;
7497 load_raw = &CLASS canon_600_load_raw;
7498 } else if (!strcmp(model,"PowerShot A5") ||
7499 !strcmp(model,"PowerShot A5 Zoom")) {
7503 pixel_aspect = 256/235.0;
7505 filters = 0x1e4e1e4e;
7507 } else if (!strcmp(model,"PowerShot A50")) {
7512 filters = 0x1b4e4b1e;
7514 } else if (!strcmp(model,"PowerShot Pro70")) {
7518 filters = 0x1e4b4e1b;
7520 } else if (!strcmp(model,"PowerShot SD300")) {
7528 } else if (!strcmp(model,"PowerShot A460")) {
7536 } else if (!strcmp(model,"PowerShot A530")) {
7544 } else if (!strcmp(model,"PowerShot A610")) {
7545 if (canon_s2is()) strcpy (model+10, "S2 IS");
7553 } else if (!strcmp(model,"PowerShot A620")) {
7561 } else if (!strcmp(model,"PowerShot A470")) {
7569 } else if (!strcmp(model,"PowerShot A720 IS")) {
7577 } else if (!strcmp(model,"PowerShot A630")) {
7585 } else if (!strcmp(model,"PowerShot A640")) {
7593 } else if (!strcmp(model,"PowerShot A650")) {
7601 } else if (!strcmp(model,"PowerShot S3 IS")) {
7610 load_raw = &CLASS packed_load_raw;
7612 if (raw_width > 1600) zero_is_bad = 1;
7613 } else if (!strcmp(model,"PowerShot SX110 IS")) {
7620 load_raw = &CLASS packed_load_raw;
7623 } else if (!strcmp(model,"PowerShot SX120 IS")) {
7630 filters = 0x49494949;
7631 load_raw = &CLASS packed_load_raw;
7634 } else if (!strcmp(model,"PowerShot SX20 IS")) {
7641 load_raw = &CLASS packed_load_raw;
7644 } else if (!strcmp(model,"PowerShot SX220 HS")) {
7649 mask[0][0] = top_margin = 16;
7650 mask[0][2] = top_margin + height;
7651 mask[0][3] = left_margin = 92;
7652 load_raw = &CLASS packed_load_raw;
7655 } else if (!strcmp(model,"PowerShot SX30 IS")) {
7662 filters = 0x16161616;
7663 load_raw = &CLASS packed_load_raw;
7666 } else if (!strcmp(model,"PowerShot Pro90 IS")) {
7669 filters = 0xb4b4b4b4;
7670 } else if (is_canon && raw_width == 2144) {
7675 if (!strcmp(model,"PowerShot G1")) {
7677 filters = 0xb4b4b4b4;
7679 } else if (is_canon && raw_width == 2224) {
7684 } else if (is_canon && raw_width == 2376) {
7689 } else if (is_canon && raw_width == 2672) {
7694 } else if (is_canon && raw_width == 3152) {
7699 if (unique_id == 0x80000170)
7700 adobe_coeff ("Canon","EOS 300D");
7701 } else if (is_canon && raw_width == 3160) {
7706 } else if (is_canon && raw_width == 3344) {
7711 } else if (!strcmp(model,"EOS D2000C")) {
7712 filters = 0x61616161;
7714 } else if (is_canon && raw_width == 3516) {
7717 if (unique_id == 0x80000189)
7718 adobe_coeff ("Canon","EOS 350D");
7720 } else if (is_canon && raw_width == 3596) {
7724 } else if (is_canon && raw_width == 3744) {
7729 if (unique_id > 0x2720000) {
7733 } else if (is_canon && raw_width == 3944) {
7738 } else if (is_canon && raw_width == 3948) {
7742 if (unique_id == 0x80000236)
7743 adobe_coeff ("Canon","EOS 400D");
7744 if (unique_id == 0x80000254)
7745 adobe_coeff ("Canon","EOS 1000D");
7747 } else if (is_canon && raw_width == 3984) {
7752 } else if (is_canon && raw_width == 4104) {
7757 } else if (is_canon && raw_width == 4152) {
7761 } else if (is_canon && raw_width == 4160) {
7766 } else if (is_canon && raw_width == 4176) {
7770 mask[0][0] = top_margin = 17;
7771 mask[0][2] = raw_height;
7773 filters = 0x49494949;
7774 } else if (is_canon && raw_width == 4312) {
7778 if (unique_id == 0x80000176)
7779 adobe_coeff ("Canon","EOS 450D");
7781 } else if (is_canon && raw_width == 4352) {
7784 if (unique_id == 0x80000288)
7785 adobe_coeff ("Canon","EOS 1100D");
7787 } else if (is_canon && raw_width == 4476) {
7791 } else if (is_canon && raw_width == 4480) {
7796 filters = 0x49494949;
7797 } else if (is_canon && raw_width == 4496) {
7802 } else if (is_canon && raw_width == 4832) {
7803 top_margin = unique_id == 0x80000261 ? 51:26;
7805 if (unique_id == 0x80000252)
7806 adobe_coeff ("Canon","EOS 500D");
7808 } else if (is_canon && raw_width == 5108) {
7812 } else if (is_canon && raw_width == 5120) {
7813 height -= top_margin = 45;
7816 } else if (is_canon && raw_width == 5280) {
7819 if (unique_id == 0x80000301)
7820 adobe_coeff ("Canon","EOS 650D");
7822 } else if (is_canon && raw_width == 5344) {
7825 if (unique_id == 0x80000269) {
7829 adobe_coeff ("Canon","EOS-1D X");
7831 if (unique_id == 0x80000270)
7832 adobe_coeff ("Canon","EOS 550D");
7833 if (unique_id == 0x80000286)
7834 adobe_coeff ("Canon","EOS 600D");
7836 } else if (is_canon && raw_width == 5360) {
7840 } else if (is_canon && raw_width == 5568) {
7844 } else if (is_canon && raw_width == 5712) {
7849 } else if (is_canon && raw_width == 5792) {
7853 height -= top_margin;
7854 width -= left_margin;
7855 } else if (is_canon && raw_width == 5920) {
7860 } else if (!strcmp(model,"D1")) {
7861 cam_mul[0] *= 256/527.0;
7862 cam_mul[2] *= 256/317.0;
7863 } else if (!strcmp(model,"D1X")) {
7866 } else if (!strcmp(model,"D40X") ||
7867 !strcmp(model,"D60") ||
7868 !strcmp(model,"D80") ||
7869 !strcmp(model,"D3000")) {
7872 } else if (!strcmp(model,"D3") ||
7873 !strcmp(model,"D3S") ||
7874 !strcmp(model,"D700")) {
7877 } else if (!strcmp(model,"D3100")) {
7880 } else if (!strcmp(model,"D5000") ||
7881 !strcmp(model,"D90")) {
7883 } else if (!strcmp(model,"D5100") ||
7884 !strcmp(model,"D7000")) {
7886 } else if (!strcmp(model,"D3200") ||
7887 !strcmp(model,"D600") ||
7888 !strcmp(model,"D800")) {
7890 } else if (!strcmp(model,"D4")) {
7893 } else if (!strncmp(model,"D40",3) ||
7894 !strncmp(model,"D50",3) ||
7895 !strncmp(model,"D70",3)) {
7897 } else if (!strcmp(model,"D100")) {
7899 raw_width = (width += 3) + 3;
7900 } else if (!strcmp(model,"D200")) {
7903 filters = 0x94949494;
7904 } else if (!strncmp(model,"D2H",3)) {
7907 } else if (!strncmp(model,"D2X",3)) {
7908 if (width == 3264) width -= 32;
7910 } else if (!strncmp(model,"D300",4)) {
7912 } else if (!strcmp(make,"NIKON") && raw_width == 4032) {
7913 adobe_coeff ("NIKON","COOLPIX P7700");
7914 } else if (!strncmp(model,"COOLPIX P",9)) {
7916 filters = 0x94949494;
7917 if (model[9] == '7' && iso_speed >= 400)
7919 } else if (!strncmp(model,"1 ",2)) {
7921 } else if (fsize == 1581060) {
7927 filters = 0x1e1e1e1e;
7929 pre_mul[0] = 1.2085;
7930 pre_mul[1] = 1.0943;
7931 pre_mul[3] = 1.1103;
7933 } else if (fsize == 2465792) {
7938 filters = 0x4b4b4b4b;
7939 adobe_coeff ("NIKON","E950");
7942 load_raw = &CLASS packed_load_raw;
7944 } else if (fsize == 4771840) {
7948 filters = 0xe1e1e1e1;
7949 load_raw = &CLASS packed_load_raw;
7951 if (!timestamp && nikon_e995())
7952 strcpy (model, "E995");
7953 if (strcmp(model,"E995")) {
7954 filters = 0xb4b4b4b4;
7960 } else if (!strcmp(model,"E2100")) {
7961 if (!timestamp && !nikon_e2100()) goto cp_e2500;
7965 } else if (!strcmp(model,"E2500")) {
7967 strcpy (model, "E2500");
7971 filters = 0x4b4b4b4b;
7972 } else if (fsize == 4775936) {
7975 load_raw = &CLASS packed_load_raw;
7977 if (!timestamp) nikon_3700();
7978 if (model[0] == 'E' && atoi(model+1) < 3700)
7979 filters = 0x49494949;
7980 if (!strcmp(model,"Optio 33WR")) {
7982 filters = 0x16161616;
7984 if (make[0] == 'O') {
7985 i = find_green (12, 32, 1188864, 3576832);
7986 c = find_green (12, 32, 2383920, 2387016);
7987 if (abs(i) < abs(c)) {
7991 if (i < 0) filters = 0x61616161;
7993 } else if (fsize == 5869568) {
7996 filters = 0x16161616;
7997 if (!timestamp && minolta_z2()) {
7998 strcpy (make, "Minolta");
7999 strcpy (model,"DiMAGE Z2");
8001 load_raw = &CLASS packed_load_raw;
8002 load_flags = 6 + 24*(make[0] == 'M');
8003 } else if (!strcmp(model,"E4500")) {
8007 filters = 0xb4b4b4b4;
8008 } else if (fsize == 7438336) {
8012 filters = 0xb4b4b4b4;
8013 } else if (fsize == 8998912) {
8017 load_raw = &CLASS packed_load_raw;
8019 } else if (!strcmp(make,"FUJIFILM")) {
8020 if (!strcmp(model+7,"S2Pro")) {
8021 strcpy (model,"S2Pro");
8025 } else if (load_raw != &CLASS packed_load_raw)
8026 maximum = (is_raw == 2 && shot_select) ? 0x2f00 : 0x3e00;
8027 top_margin = (raw_height - height) >> 2 << 1;
8028 left_margin = (raw_width - width ) >> 2 << 1;
8029 if (width == 2848) filters = 0x16161616;
8030 if (width == 3328) {
8034 if (width == 4952) {
8038 if (fuji_layout) raw_width *= is_raw;
8039 } else if (!strcmp(model,"RD175")) {
8043 filters = 0x61616161;
8044 load_raw = &CLASS minolta_rd175_load_raw;
8045 } else if (!strcmp(model,"KD-400Z")) {
8050 } else if (!strcmp(model,"KD-510Z")) {
8052 } else if (!strcasecmp(make,"MINOLTA")) {
8053 load_raw = &CLASS unpacked_load_raw;
8055 if (!strncmp(model,"DiMAGE A",8)) {
8056 if (!strcmp(model,"DiMAGE A200"))
8057 filters = 0x49494949;
8059 load_raw = &CLASS packed_load_raw;
8060 } else if (!strncmp(model,"ALPHA",5) ||
8061 !strncmp(model,"DYNAX",5) ||
8062 !strncmp(model,"MAXXUM",6)) {
8063 sprintf (model+20, "DYNAX %-10s", model+6+(model[0]=='M'));
8064 adobe_coeff (make, model+20);
8065 load_raw = &CLASS packed_load_raw;
8066 } else if (!strncmp(model,"DiMAGE G",8)) {
8067 if (model[8] == '4') {
8070 } else if (model[8] == '5') {
8075 } else if (model[8] == '6') {
8080 filters = 0x61616161;
8082 load_raw = &CLASS unpacked_load_raw;
8086 } else if (!strcmp(model,"*ist D")) {
8087 load_raw = &CLASS unpacked_load_raw;
8089 } else if (!strcmp(model,"*ist DS")) {
8091 } else if (!strcmp(model,"Optio S")) {
8092 if (fsize == 3178560) {
8095 load_raw = &CLASS eight_bit_load_raw;
8102 load_raw = &CLASS packed_load_raw;
8105 } else if (fsize == 6114240) {
8109 load_raw = &CLASS packed_load_raw;
8111 } else if (!strcmp(model,"Optio 750Z")) {
8114 load_raw = &CLASS packed_load_raw;
8116 } else if (!strcmp(model,"DC-833m")) {
8120 filters = 0x61616161;
8121 load_raw = &CLASS unpacked_load_raw;
8123 } else if (!strncmp(model,"S85",3)) {
8126 raw_width = fsize/height/2;
8128 load_raw = &CLASS unpacked_load_raw;
8129 } else if (!strcmp(make,"SAMSUNG") && raw_width == 4704) {
8130 height -= top_margin = 8;
8131 width -= 2 * (left_margin = 8);
8133 } else if (!strcmp(make,"SAMSUNG") && raw_width == 5632) {
8137 width = 5574 - (left_margin = 32 + tiff_bps);
8138 if (tiff_bps == 12) load_flags = 80;
8139 } else if (!strcmp(model,"EX1")) {
8143 if ((width -= 6) > 3682) {
8148 } else if (!strcmp(model,"WB2000")) {
8152 if ((width -= 10) > 3718) {
8157 } else if (fsize == 20487168) {
8161 } else if (fsize == 24000000) {
8165 strcpy (model, "WB550");
8167 load_raw = &CLASS unpacked_load_raw;
8170 } else if (!strcmp(model,"EX2F")) {
8175 filters = 0x49494949;
8176 load_raw = &CLASS unpacked_load_raw;
8177 } else if (!strcmp(model,"STV680 VGA")) {
8180 load_raw = &CLASS eight_bit_load_raw;
8182 filters = 0x16161616;
8184 } else if (!strcmp(model,"N95")) {
8185 height = raw_height - (top_margin = 2);
8186 } else if (!strcmp(model,"531C")) {
8189 load_raw = &CLASS unpacked_load_raw;
8190 filters = 0x49494949;
8191 } else if (!strcmp(model,"640x480")) {
8194 load_raw = &CLASS eight_bit_load_raw;
8195 gamma_curve (0.45, 4.5, 1, 255);
8196 } else if (!strcmp(model,"F-080C")) {
8199 load_raw = &CLASS eight_bit_load_raw;
8200 } else if (!strcmp(model,"F-145C")) {
8203 load_raw = &CLASS eight_bit_load_raw;
8204 } else if (!strcmp(model,"F-201C")) {
8207 load_raw = &CLASS eight_bit_load_raw;
8208 } else if (!strcmp(model,"F-510C")) {
8211 load_raw = fsize < 7500000 ?
8212 &CLASS eight_bit_load_raw : &CLASS unpacked_load_raw;
8213 data_offset = fsize - width*height*(fsize >> 22);
8215 } else if (!strcmp(model,"F-810C")) {
8218 load_raw = &CLASS unpacked_load_raw;
8220 } else if (!strcmp(model,"XCD-SX910CR")) {
8224 filters = 0x49494949;
8226 load_raw = fsize < 2000000 ?
8227 &CLASS eight_bit_load_raw : &CLASS unpacked_load_raw;
8228 } else if (!strcmp(model,"2010")) {
8232 filters = 0x16161616;
8235 load_raw = &CLASS unpacked_load_raw;
8236 } else if (!strcmp(model,"A782")) {
8239 filters = 0x61616161;
8240 load_raw = fsize < 10000000 ?
8241 &CLASS eight_bit_load_raw : &CLASS unpacked_load_raw;
8243 } else if (!strcmp(model,"3320AF")) {
8245 raw_width = width = 2048;
8246 filters = 0x61616161;
8247 load_raw = &CLASS unpacked_load_raw;
8249 fseek (ifp, 0x300000, SEEK_SET);
8250 if ((order = guess_byte_order(0x10000)) == 0x4d4d) {
8251 height -= (top_margin = 16);
8252 width -= (left_margin = 28);
8254 strcpy (make, "ISG");
8257 } else if (!strcmp(make,"Hasselblad")) {
8258 if (load_raw == &CLASS lossless_jpeg_load_raw)
8259 load_raw = &CLASS hasselblad_load_raw;
8260 if (raw_width == 7262) {
8265 filters = 0x61616161;
8266 } else if (raw_width == 7410) {
8271 filters = 0x61616161;
8272 } else if (raw_width == 9044) {
8277 black += load_flags = 256;
8279 } else if (raw_width == 4090) {
8280 strcpy (model, "V96C");
8281 height -= (top_margin = 6);
8282 width -= (left_margin = 3) + 7;
8283 filters = 0x61616161;
8285 } else if (!strcmp(make,"Sinar")) {
8286 if (!memcmp(head,"8BPS",4)) {
8287 fseek (ifp, 14, SEEK_SET);
8290 filters = 0x61616161;
8293 if (!load_raw) load_raw = &CLASS unpacked_load_raw;
8295 } else if (!strcmp(make,"Leaf")) {
8297 fseek (ifp, data_offset, SEEK_SET);
8298 if (ljpeg_start (&jh, 1) && jh.bits == 15)
8300 if (tiff_samples > 1) filters = 0;
8301 if (tiff_samples > 1 || tile_length < raw_height) {
8302 load_raw = &CLASS leaf_hdr_load_raw;
8303 raw_width = tile_width;
8305 if ((width | height) == 2048) {
8306 if (tiff_samples == 1) {
8308 strcpy (cdesc, "RBTG");
8309 strcpy (model, "CatchLight");
8310 top_margin = 8; left_margin = 18; height = 2032; width = 2016;
8312 strcpy (model, "DCB2");
8313 top_margin = 10; left_margin = 16; height = 2028; width = 2022;
8315 } else if (width+height == 3144+2060) {
8316 if (!model[0]) strcpy (model, "Cantare");
8317 if (width > height) {
8318 top_margin = 6; left_margin = 32; height = 2048; width = 3072;
8319 filters = 0x61616161;
8321 left_margin = 6; top_margin = 32; width = 2048; height = 3072;
8322 filters = 0x16161616;
8324 if (!cam_mul[0] || model[0] == 'V') filters = 0;
8325 else is_raw = tiff_samples;
8326 } else if (width == 2116) {
8327 strcpy (model, "Valeo 6");
8328 height -= 2 * (top_margin = 30);
8329 width -= 2 * (left_margin = 55);
8330 filters = 0x49494949;
8331 } else if (width == 3171) {
8332 strcpy (model, "Valeo 6");
8333 height -= 2 * (top_margin = 24);
8334 width -= 2 * (left_margin = 24);
8335 filters = 0x16161616;
8337 } else if (!strcmp(make,"LEICA") || !strcmp(make,"Panasonic")) {
8338 if ((flen - data_offset) / (raw_width*8/7) == raw_height)
8339 load_raw = &CLASS panasonic_load_raw;
8341 load_raw = &CLASS unpacked_load_raw;
8345 if ((height += 12) > raw_height) height = raw_height;
8346 for (i=0; i < sizeof pana / sizeof *pana; i++)
8347 if (raw_width == pana[i][0] && raw_height == pana[i][1]) {
8348 left_margin = pana[i][2];
8349 top_margin = pana[i][3];
8350 width += pana[i][4];
8351 height += pana[i][5];
8353 filters = 0x01010101 * (uchar) "\x94\x61\x49\x16"
8354 [((filters-1) ^ (left_margin & 1) ^ (top_margin << 1)) & 3];
8355 } else if (!strcmp(model,"C770UZ")) {
8358 filters = 0x16161616;
8359 load_raw = &CLASS packed_load_raw;
8361 } else if (!strcmp(make,"OLYMPUS")) {
8362 height += height & 1;
8364 if (width == 4100) width -= 4;
8365 if (width == 4080) width -= 24;
8366 if (load_raw == &CLASS unpacked_load_raw)
8369 if (!strcmp(model,"E-300") ||
8370 !strcmp(model,"E-500")) {
8372 if (load_raw == &CLASS unpacked_load_raw) {
8374 memset (cblack, 0, sizeof cblack);
8376 } else if (!strcmp(model,"E-330")) {
8378 if (load_raw == &CLASS unpacked_load_raw)
8380 } else if (!strcmp(model,"SP550UZ")) {
8381 thumb_length = flen - (thumb_offset = 0xa39800);
8384 } else if (!strcmp(model,"XZ-2")) {
8385 load_raw = &CLASS packed_load_raw;
8388 } else if (!strcmp(model,"N Digital")) {
8391 filters = 0x61616161;
8392 data_offset = 0x1a00;
8393 load_raw = &CLASS packed_load_raw;
8394 } else if (!strcmp(model,"DSC-F828")) {
8398 data_offset = 862144;
8399 load_raw = &CLASS sony_load_raw;
8400 filters = 0x9c9c9c9c;
8402 strcpy (cdesc, "RGBE");
8403 } else if (!strcmp(model,"DSC-V3")) {
8407 data_offset = 787392;
8408 load_raw = &CLASS sony_load_raw;
8409 } else if (!strcmp(make,"SONY") && raw_width == 3984) {
8410 adobe_coeff ("SONY","DSC-R1");
8413 } else if (!strcmp(make,"SONY") && raw_width == 5504) {
8415 } else if (!strcmp(make,"SONY") && raw_width == 6048) {
8417 } else if (!strcmp(model,"DSLR-A100")) {
8418 if (width == 3880) {
8420 width = ++raw_width;
8425 filters = 0x61616161;
8426 } else if (!strcmp(model,"DSLR-A350")) {
8428 } else if (!strcmp(model,"PIXL")) {
8429 height -= top_margin = 4;
8430 width -= left_margin = 32;
8431 gamma_curve (0, 7, 1, 255);
8432 } else if (!strcmp(model,"C603v")) {
8435 if (fsize < 614400 || find_green (16, 16, 3840, 5120) < 25) goto c603v;
8436 strcpy (model,"KAI-0340");
8440 load_raw = &CLASS unpacked_load_raw;
8441 } else if (!strcmp(model,"C603y")) {
8446 load_raw = &CLASS kodak_yrgb_load_raw;
8447 gamma_curve (0, 3.875, 1, 255);
8448 } else if (!strcmp(model,"C603")) {
8449 raw_height = height = 2152;
8450 raw_width = width = 2864;
8452 } else if (!strcmp(model,"C330")) {
8461 if ((data_offset = fsize - raw_height*raw_width)) {
8462 fseek (ifp, 168, SEEK_SET);
8463 read_shorts (curve, 256);
8464 } else gamma_curve (0, 3.875, 1, 255);
8465 load_raw = &CLASS eight_bit_load_raw;
8466 } else if (!strncasecmp(model,"EasyShare",9)) {
8467 data_offset = data_offset < 0x15000 ? 0x15000 : 0x17000;
8468 load_raw = &CLASS packed_load_raw;
8469 } else if (!strcasecmp(make,"KODAK")) {
8470 if (filters == UINT_MAX) filters = 0x61616161;
8471 if (!strncmp(model,"NC2000",6)) {
8474 } else if (!strcmp(model,"EOSDCS3B")) {
8477 } else if (!strcmp(model,"EOSDCS1")) {
8480 } else if (!strcmp(model,"DCS420")) {
8483 } else if (!strncmp(model,"DCS460 ",7)) {
8487 } else if (!strcmp(model,"DCS460A")) {
8492 } else if (!strcmp(model,"DCS660M")) {
8496 } else if (!strcmp(model,"DCS760M")) {
8500 if (!strcmp(model+4,"20X"))
8501 strcpy (cdesc, "MYCY");
8502 if (strstr(model,"DC25")) {
8503 strcpy (model, "DC25");
8504 data_offset = 15424;
8506 if (!strncmp(model,"DC2",3)) {
8507 raw_height = height = 242;
8508 if (flen < 100000) {
8509 raw_width = 256; width = 249;
8510 pixel_aspect = (4.0*height) / (3.0*width);
8512 raw_width = 512; width = 501;
8513 pixel_aspect = (493.0*height) / (373.0*width);
8515 data_offset += raw_width + 1;
8517 filters = 0x8d8d8d8d;
8522 load_raw = &CLASS eight_bit_load_raw;
8523 } else if (!strcmp(model,"40")) {
8524 strcpy (model, "DC40");
8528 load_raw = &CLASS kodak_radc_load_raw;
8529 } else if (strstr(model,"DC50")) {
8530 strcpy (model, "DC50");
8533 data_offset = 19712;
8534 load_raw = &CLASS kodak_radc_load_raw;
8535 } else if (strstr(model,"DC120")) {
8536 strcpy (model, "DC120");
8539 pixel_aspect = height/0.75/width;
8540 load_raw = tiff_compress == 7 ?
8541 &CLASS kodak_jpeg_load_raw : &CLASS kodak_dc120_load_raw;
8542 } else if (!strcmp(model,"DCS200")) {
8545 thumb_offset = 6144;
8547 write_thumb = &CLASS layer_thumb;
8550 data_offset = 79872;
8551 load_raw = &CLASS eight_bit_load_raw;
8554 } else if (!strcmp(model,"Fotoman Pixtura")) {
8558 load_raw = &CLASS kodak_radc_load_raw;
8559 filters = 0x61616161;
8561 } else if (!strncmp(model,"QuickTake",9)) {
8562 if (head[5]) strcpy (model+10, "200");
8563 fseek (ifp, 544, SEEK_SET);
8566 data_offset = (get4(),get2()) == 30 ? 738:736;
8567 if (height > width) {
8569 fseek (ifp, data_offset-6, SEEK_SET);
8570 flip = ~get2() & 3 ? 5:6;
8572 filters = 0x61616161;
8573 } else if (!strcmp(make,"Rollei") && !load_raw) {
8574 switch (raw_width) {
8587 filters = 0x16161616;
8588 load_raw = &CLASS rollei_load_raw;
8589 } else if (!strcmp(model,"PC-CAM 600")) {
8591 data_offset = width = 1024;
8592 filters = 0x49494949;
8593 load_raw = &CLASS eight_bit_load_raw;
8594 } else if (!strcmp(model,"QV-2000UX")) {
8597 data_offset = width * 2;
8598 load_raw = &CLASS eight_bit_load_raw;
8599 } else if (fsize == 3217760) {
8603 load_raw = &CLASS eight_bit_load_raw;
8604 } else if (!strcmp(model,"QV-4000")) {
8607 load_raw = &CLASS unpacked_load_raw;
8609 } else if (!strcmp(model,"QV-5700")) {
8614 } else if (!strcmp(model,"QV-R41")) {
8619 } else if (!strcmp(model,"QV-R51")) {
8623 } else if (!strcmp(model,"EX-S20")) {
8628 } else if (!strcmp(model,"EX-S100")) {
8632 } else if (!strcmp(model,"EX-Z50")) {
8636 } else if (!strcmp(model,"EX-Z500")) {
8640 filters = 0x16161616;
8641 } else if (!strcmp(model,"EX-Z55")) {
8645 } else if (!strcmp(model,"EX-Z60")) {
8649 filters = 0x16161616;
8651 } else if (!strcmp(model,"EX-Z75")) {
8656 } else if (!strcmp(model,"EX-Z750")) {
8661 } else if (!strcmp(model,"EX-Z850")) {
8666 } else if (!strcmp(model,"EX-Z8")) {
8672 } else if (fsize == 15499264) { /* EX-Z1050 or EX-Z1080 */
8676 } else if (!strcmp(model,"EX-ZR100")) {
8681 } else if (!strcmp(model,"EX-P505")) {
8686 } else if (fsize == 9313536) { /* EX-P600 or QV-R61 */
8690 } else if (!strcmp(model,"EX-P700")) {
8696 sprintf (model, "%dx%d", width, height);
8697 if (filters == UINT_MAX) filters = 0x94949494;
8698 if (raw_color) adobe_coeff (make, model);
8699 if (load_raw == &CLASS kodak_radc_load_raw)
8700 if (raw_color) adobe_coeff ("Apple","Quicktake");
8701 if (thumb_offset && !thumb_height) {
8702 fseek (ifp, thumb_offset, SEEK_SET);
8703 if (ljpeg_start (&jh, 1)) {
8704 thumb_width = jh.wide;
8705 thumb_height = jh.high;
8710 fuji_width = width >> !fuji_layout;
8711 if (~fuji_width & 1) filters = 0x49494949;
8712 width = (height >> fuji_layout) + fuji_width;
8716 if (raw_height < height) raw_height = height;
8717 if (raw_width < width ) raw_width = width;
8719 if (!tiff_bps) tiff_bps = 12;
8720 if (!maximum) maximum = (1 << tiff_bps) - 1;
8721 if (!load_raw || height < 22) is_raw = 0;
8723 if (load_raw == &CLASS redcine_load_raw) {
8724 fprintf (stderr,_("%s: You must link dcraw with %s!!\n"),
8725 ifname, "libjasper");
8730 if (load_raw == &CLASS kodak_jpeg_load_raw ||
8731 load_raw == &CLASS lossy_dng_load_raw) {
8732 fprintf (stderr,_("%s: You must link dcraw with %s!!\n"),
8738 strcpy (cdesc, colors == 3 ? "RGBG":"GMCY");
8739 if (!raw_height) raw_height = height;
8740 if (!raw_width ) raw_width = width;
8741 if (filters && colors == 3)
8742 filters |= ((filters >> 2 & 0x22222222) |
8743 (filters << 2 & 0x88888888)) & filters << 1;
8745 if (flip == -1) flip = tiff_flip;
8746 if (flip == -1) flip = 0;
8753 sprintf(dcraw_info, "%d %d", height, width);
8755 sprintf(dcraw_info, "%d %d", width, height);
8759 void CLASS apply_profile (const char *input, const char *output)
8762 cmsHPROFILE hInProfile=0, hOutProfile=0;
8763 cmsHTRANSFORM hTransform;
8767 cmsErrorAction (LCMS_ERROR_SHOW);
8768 if (strcmp (input, "embed"))
8769 hInProfile = cmsOpenProfileFromFile (input, "r");
8770 else if (profile_length) {
8771 prof = (char *) malloc (profile_length);
8772 merror (prof, "apply_profile()");
8773 fseek (ifp, profile_offset, SEEK_SET);
8774 fread (prof, 1, profile_length, ifp);
8775 hInProfile = cmsOpenProfileFromMem (prof, profile_length);
8778 fprintf (stderr,_("%s has no embedded profile.\n"), ifname);
8779 if (!hInProfile) return;
8781 hOutProfile = cmsCreate_sRGBProfile();
8782 else if ((fp = fopen (output, "rb"))) {
8783 fread (&size, 4, 1, fp);
8784 fseek (fp, 0, SEEK_SET);
8785 oprof = (unsigned *) malloc (size = ntohl(size));
8786 merror (oprof, "apply_profile()");
8787 fread (oprof, 1, size, fp);
8789 if (!(hOutProfile = cmsOpenProfileFromMem (oprof, size))) {
8794 fprintf (stderr,_("Cannot open file %s!\n"), output);
8795 if (!hOutProfile) goto quit;
8797 fprintf (stderr,_("Applying color profile...\n"));
8798 hTransform = cmsCreateTransform (hInProfile, TYPE_RGBA_16,
8799 hOutProfile, TYPE_RGBA_16, INTENT_PERCEPTUAL, 0);
8800 cmsDoTransform (hTransform, image, image, width*height);
8801 raw_color = 1; /* Don't use rgb_cam with a profile */
8802 cmsDeleteTransform (hTransform);
8803 cmsCloseProfile (hOutProfile);
8805 cmsCloseProfile (hInProfile);
8809 void CLASS convert_to_rgb()
8811 int row, col, c, i, j, k;
8813 float out[3], out_cam[3][4];
8814 double num, inverse[3][3];
8815 static const double xyzd50_srgb[3][3] =
8816 { { 0.436083, 0.385083, 0.143055 },
8817 { 0.222507, 0.716888, 0.060608 },
8818 { 0.013930, 0.097097, 0.714022 } };
8819 static const double rgb_rgb[3][3] =
8820 { { 1,0,0 }, { 0,1,0 }, { 0,0,1 } };
8821 static const double adobe_rgb[3][3] =
8822 { { 0.715146, 0.284856, 0.000000 },
8823 { 0.000000, 1.000000, 0.000000 },
8824 { 0.000000, 0.041166, 0.958839 } };
8825 static const double wide_rgb[3][3] =
8826 { { 0.593087, 0.404710, 0.002206 },
8827 { 0.095413, 0.843149, 0.061439 },
8828 { 0.011621, 0.069091, 0.919288 } };
8829 static const double prophoto_rgb[3][3] =
8830 { { 0.529317, 0.330092, 0.140588 },
8831 { 0.098368, 0.873465, 0.028169 },
8832 { 0.016879, 0.117663, 0.865457 } };
8833 static const double (*out_rgb[])[3] =
8834 { rgb_rgb, adobe_rgb, wide_rgb, prophoto_rgb, xyz_rgb };
8835 static const char *name[] =
8836 { "sRGB", "Adobe RGB (1998)", "WideGamut D65", "ProPhoto D65", "XYZ" };
8837 static const unsigned phead[] =
8838 { 1024, 0, 0x2100000, 0x6d6e7472, 0x52474220, 0x58595a20, 0, 0, 0,
8839 0x61637370, 0, 0, 0x6e6f6e65, 0, 0, 0, 0, 0xf6d6, 0x10000, 0xd32d };
8841 { 10, 0x63707274, 0, 36, /* cprt */
8842 0x64657363, 0, 40, /* desc */
8843 0x77747074, 0, 20, /* wtpt */
8844 0x626b7074, 0, 20, /* bkpt */
8845 0x72545243, 0, 14, /* rTRC */
8846 0x67545243, 0, 14, /* gTRC */
8847 0x62545243, 0, 14, /* bTRC */
8848 0x7258595a, 0, 20, /* rXYZ */
8849 0x6758595a, 0, 20, /* gXYZ */
8850 0x6258595a, 0, 20 }; /* bXYZ */
8851 static const unsigned pwhite[] = { 0xf351, 0x10000, 0x116cc };
8852 unsigned pcurve[] = { 0x63757276, 0, 1, 0x1000000 };
8854 gamma_curve (gamm[0], gamm[1], 0, 0);
8855 memcpy (out_cam, rgb_cam, sizeof out_cam);
8856 raw_color |= colors == 1 || document_mode ||
8857 output_color < 1 || output_color > 5;
8859 oprof = (unsigned *) calloc (phead[0], 1);
8860 merror (oprof, "convert_to_rgb()");
8861 memcpy (oprof, phead, sizeof phead);
8862 if (output_color == 5) oprof[4] = oprof[5];
8863 oprof[0] = 132 + 12*pbody[0];
8864 for (i=0; i < pbody[0]; i++) {
8865 oprof[oprof[0]/4] = i ? (i > 1 ? 0x58595a20 : 0x64657363) : 0x74657874;
8866 pbody[i*3+2] = oprof[0];
8867 oprof[0] += (pbody[i*3+3] + 3) & -4;
8869 memcpy (oprof+32, pbody, sizeof pbody);
8870 oprof[pbody[5]/4+2] = strlen(name[output_color-1]) + 1;
8871 memcpy ((char *)oprof+pbody[8]+8, pwhite, sizeof pwhite);
8872 pcurve[3] = (short)(256/gamm[5]+0.5) << 16;
8873 for (i=4; i < 7; i++)
8874 memcpy ((char *)oprof+pbody[i*3+2], pcurve, sizeof pcurve);
8875 pseudoinverse ((double (*)[3]) out_rgb[output_color-1], inverse, 3);
8876 for (i=0; i < 3; i++)
8877 for (j=0; j < 3; j++) {
8878 for (num = k=0; k < 3; k++)
8879 num += xyzd50_srgb[i][k] * inverse[j][k];
8880 oprof[pbody[j*3+23]/4+i+2] = num * 0x10000 + 0.5;
8882 for (i=0; i < phead[0]/4; i++)
8883 oprof[i] = htonl(oprof[i]);
8884 strcpy ((char *)oprof+pbody[2]+8, "auto-generated by dcraw");
8885 strcpy ((char *)oprof+pbody[5]+12, name[output_color-1]);
8886 for (i=0; i < 3; i++)
8887 for (j=0; j < colors; j++)
8888 for (out_cam[i][j] = k=0; k < 3; k++)
8889 out_cam[i][j] += out_rgb[output_color-1][i][k] * rgb_cam[k][j];
8892 fprintf (stderr, raw_color ? _("Building histograms...\n") :
8893 _("Converting to %s colorspace...\n"), name[output_color-1]);
8895 memset (histogram, 0, sizeof histogram);
8896 for (img=image[0], row=0; row < height; row++)
8897 for (col=0; col < width; col++, img+=4) {
8899 out[0] = out[1] = out[2] = 0;
8901 out[0] += out_cam[0][c] * img[c];
8902 out[1] += out_cam[1][c] * img[c];
8903 out[2] += out_cam[2][c] * img[c];
8905 FORC3 img[c] = CLIP((int) out[c]);
8907 else if (document_mode)
8908 img[0] = img[fcol(row,col)];
8909 FORCC histogram[c][img[c] >> 3]++;
8911 if (colors == 4 && output_color) colors = 3;
8912 if (document_mode && filters) colors = 1;
8918 // Export color matrix to Cinelerra.
8919 // It can't be applied before interpolation.
8921 for(i = 0; i < 3; i++)
8923 for(j = 0; j < 3; j++)
8924 dcraw_matrix[k++] = rgb_cam[i][j];
8928 void CLASS fuji_rotate()
8934 ushort wide, high, (*img)[4], (*pix)[4];
8936 if (!fuji_width) return;
8938 fprintf (stderr,_("Rotating image 45 degrees...\n"));
8939 fuji_width = (fuji_width - 1 + shrink) >> shrink;
8941 wide = fuji_width / step;
8942 high = (height - fuji_width) / step;
8943 img = (ushort (*)[4]) calloc (wide*high, sizeof *img);
8944 merror (img, "fuji_rotate()");
8946 for (row=0; row < high; row++)
8947 for (col=0; col < wide; col++) {
8948 ur = r = fuji_width + (row-col)*step;
8949 uc = c = (row+col)*step;
8950 if (ur > height-2 || uc > width-2) continue;
8953 pix = image + ur*width + uc;
8954 for (i=0; i < colors; i++)
8955 img[row*wide+col][i] =
8956 (pix[ 0][i]*(1-fc) + pix[ 1][i]*fc) * (1-fr) +
8957 (pix[width][i]*(1-fc) + pix[width+1][i]*fc) * fr;
8966 void CLASS stretch()
8968 ushort newdim, (*img)[4], *pix0, *pix1;
8972 if (pixel_aspect == 1) return;
8973 if (verbose) fprintf (stderr,_("Stretching the image...\n"));
8974 if (pixel_aspect < 1) {
8975 newdim = height / pixel_aspect + 0.5;
8976 img = (ushort (*)[4]) calloc (width*newdim, sizeof *img);
8977 merror (img, "stretch()");
8978 for (rc=row=0; row < newdim; row++, rc+=pixel_aspect) {
8979 frac = rc - (c = rc);
8980 pix0 = pix1 = image[c*width];
8981 if (c+1 < height) pix1 += width*4;
8982 for (col=0; col < width; col++, pix0+=4, pix1+=4)
8983 FORCC img[row*width+col][c] = pix0[c]*(1-frac) + pix1[c]*frac + 0.5;
8987 newdim = width * pixel_aspect + 0.5;
8988 img = (ushort (*)[4]) calloc (height*newdim, sizeof *img);
8989 merror (img, "stretch()");
8990 for (rc=col=0; col < newdim; col++, rc+=1/pixel_aspect) {
8991 frac = rc - (c = rc);
8992 pix0 = pix1 = image[c];
8993 if (c+1 < width) pix1 += 4;
8994 for (row=0; row < height; row++, pix0+=width*4, pix1+=width*4)
8995 FORCC img[row*newdim+col][c] = pix0[c]*(1-frac) + pix1[c]*frac + 0.5;
9003 int CLASS flip_index (int row, int col)
9005 if (flip & 4) SWAP(row,col);
9006 if (flip & 2) row = iheight - 1 - row;
9007 if (flip & 1) col = iwidth - 1 - col;
9008 return row * iwidth + col;
9014 union { char c[4]; short s[2]; int i; } val;
9018 ushort order, magic;
9021 struct tiff_tag tag[23];
9024 struct tiff_tag exif[4];
9026 struct tiff_tag gpst[10];
9030 char desc[512], make[64], model[64], soft[32], date[20], artist[64];
9033 void CLASS tiff_set (ushort *ntag,
9034 ushort tag, ushort type, int count, int val)
9036 struct tiff_tag *tt;
9039 tt = (struct tiff_tag *)(ntag+1) + (*ntag)++;
9043 if (type < 3 && count <= 4)
9044 FORC(4) tt->val.c[c] = val >> (c << 3);
9045 else if (type == 3 && count <= 2)
9046 FORC(2) tt->val.s[c] = val >> (c << 4);
9047 else tt->val.i = val;
9050 #define TOFF(ptr) ((char *)(&(ptr)) - (char *)th)
9052 void CLASS tiff_head (struct tiff_hdr *th, int full)
9057 memset (th, 0, sizeof *th);
9058 th->order = htonl(0x4d4d4949) >> 16;
9062 tiff_set (&th->ntag, 254, 4, 1, 0);
9063 tiff_set (&th->ntag, 256, 4, 1, width);
9064 tiff_set (&th->ntag, 257, 4, 1, height);
9065 tiff_set (&th->ntag, 258, 3, colors, output_bps);
9067 th->tag[th->ntag-1].val.i = TOFF(th->bps);
9068 FORC4 th->bps[c] = output_bps;
9069 tiff_set (&th->ntag, 259, 3, 1, 1);
9070 tiff_set (&th->ntag, 262, 3, 1, 1 + (colors > 1));
9072 tiff_set (&th->ntag, 270, 2, 512, TOFF(th->desc));
9073 tiff_set (&th->ntag, 271, 2, 64, TOFF(th->make));
9074 tiff_set (&th->ntag, 272, 2, 64, TOFF(th->model));
9076 if (oprof) psize = ntohl(oprof[0]);
9077 tiff_set (&th->ntag, 273, 4, 1, sizeof *th + psize);
9078 tiff_set (&th->ntag, 277, 3, 1, colors);
9079 tiff_set (&th->ntag, 278, 4, 1, height);
9080 tiff_set (&th->ntag, 279, 4, 1, height*width*colors*output_bps/8);
9082 tiff_set (&th->ntag, 274, 3, 1, "12435867"[flip]-'0');
9083 tiff_set (&th->ntag, 282, 5, 1, TOFF(th->rat[0]));
9084 tiff_set (&th->ntag, 283, 5, 1, TOFF(th->rat[2]));
9085 tiff_set (&th->ntag, 284, 3, 1, 1);
9086 tiff_set (&th->ntag, 296, 3, 1, 2);
9087 tiff_set (&th->ntag, 305, 2, 32, TOFF(th->soft));
9088 tiff_set (&th->ntag, 306, 2, 20, TOFF(th->date));
9089 tiff_set (&th->ntag, 315, 2, 64, TOFF(th->artist));
9090 tiff_set (&th->ntag, 34665, 4, 1, TOFF(th->nexif));
9091 if (psize) tiff_set (&th->ntag, 34675, 7, psize, sizeof *th);
9092 tiff_set (&th->nexif, 33434, 5, 1, TOFF(th->rat[4]));
9093 tiff_set (&th->nexif, 33437, 5, 1, TOFF(th->rat[6]));
9094 tiff_set (&th->nexif, 34855, 3, 1, iso_speed);
9095 tiff_set (&th->nexif, 37386, 5, 1, TOFF(th->rat[8]));
9097 tiff_set (&th->ntag, 34853, 4, 1, TOFF(th->ngps));
9098 tiff_set (&th->ngps, 0, 1, 4, 0x202);
9099 tiff_set (&th->ngps, 1, 2, 2, gpsdata[29]);
9100 tiff_set (&th->ngps, 2, 5, 3, TOFF(th->gps[0]));
9101 tiff_set (&th->ngps, 3, 2, 2, gpsdata[30]);
9102 tiff_set (&th->ngps, 4, 5, 3, TOFF(th->gps[6]));
9103 tiff_set (&th->ngps, 5, 1, 1, gpsdata[31]);
9104 tiff_set (&th->ngps, 6, 5, 1, TOFF(th->gps[18]));
9105 tiff_set (&th->ngps, 7, 5, 3, TOFF(th->gps[12]));
9106 tiff_set (&th->ngps, 18, 2, 12, TOFF(th->gps[20]));
9107 tiff_set (&th->ngps, 29, 2, 12, TOFF(th->gps[23]));
9108 memcpy (th->gps, gpsdata, sizeof th->gps);
9110 th->rat[0] = th->rat[2] = 300;
9111 th->rat[1] = th->rat[3] = 1;
9112 FORC(6) th->rat[4+c] = 1000000;
9113 th->rat[4] *= shutter;
9114 th->rat[6] *= aperture;
9115 th->rat[8] *= focal_len;
9116 strncpy (th->desc, desc, 512);
9117 strncpy (th->make, make, 64);
9118 strncpy (th->model, model, 64);
9119 strcpy (th->soft, "dcraw v"DCRAW_VERSION);
9120 t = localtime (×tamp);
9121 sprintf (th->date, "%04d:%02d:%02d %02d:%02d:%02d",
9122 t->tm_year+1900,t->tm_mon+1,t->tm_mday,t->tm_hour,t->tm_min,t->tm_sec);
9123 strncpy (th->artist, artist, 64);
9126 void CLASS jpeg_thumb()
9132 thumb = (char *) malloc (thumb_length);
9133 merror (thumb, "jpeg_thumb()");
9134 fread (thumb, 1, thumb_length, ifp);
9137 if (strcmp (thumb+6, "Exif")) {
9138 memcpy (exif, "\xff\xe1 Exif\0\0", 10);
9139 exif[1] = htons (8 + sizeof th);
9140 fwrite (exif, 1, sizeof exif, ofp);
9142 fwrite (&th, 1, sizeof th, ofp);
9144 fwrite (thumb+2, 1, thumb_length-2, ofp);
9148 void CLASS write_ppm_tiff()
9153 int c, row, col, soff, rstep, cstep;
9154 int perc, val, total, white=0x2000;
9156 perc = width * height * 0.01; /* 99th percentile white level */
9157 if (fuji_width) perc /= 2;
9158 if (!((highlight & ~2) || no_auto_bright))
9159 for (white=c=0; c < colors; c++) {
9160 for (val=0x2000, total=0; --val > 32; )
9161 if ((total += histogram[c][val]) > perc) break;
9162 if (white < val) white = val;
9164 gamma_curve (gamm[0], gamm[1], 2, (white << 3)/bright);
9167 if (flip & 4) SWAP(height,width);
9168 ppm = (uchar *) calloc (width, colors*output_bps/8);
9169 ppm2 = (ushort *) ppm;
9170 merror (ppm, "write_ppm_tiff()");
9173 fwrite (&th, sizeof th, 1, ofp);
9175 fwrite (oprof, ntohl(oprof[0]), 1, ofp);
9176 } else if (colors > 3)
9178 "P7\nWIDTH %d\nHEIGHT %d\nDEPTH %d\nMAXVAL %d\nTUPLTYPE %s\nENDHDR\n",
9179 width, height, colors, (1 << output_bps)-1, cdesc);
9181 fprintf (ofp, "P%d\n%d %d\n%d\n",
9182 colors/2+5, width, height, (1 << output_bps)-1);
9183 soff = flip_index (0, 0);
9184 cstep = flip_index (0, 1) - soff;
9185 rstep = flip_index (1, 0) - flip_index (0, width);
9186 for (row=0; row < height; row++, soff += rstep) {
9187 for (col=0; col < width; col++, soff += cstep)
9188 if (output_bps == 8)
9189 FORCC ppm [col*colors+c] = curve[image[soff][c]] >> 8;
9190 else FORCC ppm2[col*colors+c] = curve[image[soff][c]];
9191 if (output_bps == 16 && !output_tiff && htons(0x55aa) != 0x55aa)
9192 swab (ppm2, ppm2, width*colors*2);
9193 fwrite (ppm, colors*output_bps/8, width, ofp);
9204 void CLASS write_cinelerra (FILE *ofp)
9209 for (row = 0; row < height; row++)
9211 output = dcraw_data[row];
9215 for (col = 0; col < width; col++)
9217 ushort *pixel = image[row * width + col];
9219 *output++ = (float)pixel[0] / 0xffff;
9220 *output++ = (float)pixel[1] / 0xffff;
9221 *output++ = (float)pixel[2] / 0xffff;
9223 if(dcraw_alpha) *output++ = 1.0;
9228 for (col = 0; col < width; col++)
9230 ushort *pixel = image[row * width + col];
9232 *output++ = (float)pixel[0] / 0xffff;
9233 *output++ = (float)pixel[1] / 0xffff;
9234 *output++ = (float)pixel[2] / 0xffff;
9236 if(dcraw_alpha) *output++ = 1.0;
9255 int CLASS dcraw_main (int argc, const char **argv)
9256 //int CLASS main (int argc, const char **argv)
9259 // Globals must be reset
9265 int arg, status=0, quality, i, c;
9266 int timestamp_only=0, thumbnail_only=0, identify_only=0;
9267 int user_qual=-1, user_black=-1, user_sat=-1, user_flip=-1;
9268 int use_fuji_rotate=1, write_to_stdout=0, read_from_stdin=0;
9269 const char *sp, *bpfile=0, *dark_frame=0, *write_ext;
9270 char opm, opt, *ofname, *cp;
9273 const char *cam_profile=0, *out_profile=0;
9277 putenv ((char *) "TZ=UTC");
9280 setlocale (LC_CTYPE, "");
9281 setlocale (LC_MESSAGES, "");
9282 bindtextdomain ("dcraw", LOCALEDIR);
9283 textdomain ("dcraw");
9287 printf(_("\nRaw photo decoder \"dcraw\" v%s"), DCRAW_VERSION);
9288 printf(_("\nby Dave Coffin, dcoffin a cybercom o net\n"));
9289 printf(_("\nUsage: %s [OPTION]... [FILE]...\n\n"), argv[0]);
9290 puts(_("-v Print verbose messages"));
9291 puts(_("-c Write image data to standard output"));
9292 puts(_("-e Extract embedded thumbnail image"));
9293 puts(_("-i Identify files without decoding them"));
9294 puts(_("-i -v Identify files and show metadata"));
9295 puts(_("-z Change file dates to camera timestamp"));
9296 puts(_("-w Use camera white balance, if possible"));
9297 puts(_("-a Average the whole image for white balance"));
9298 puts(_("-A <x y w h> Average a grey box for white balance"));
9299 puts(_("-r <r g b g> Set custom white balance"));
9300 puts(_("+M/-M Use/don't use an embedded color matrix"));
9301 puts(_("-C <r b> Correct chromatic aberration"));
9302 puts(_("-P <file> Fix the dead pixels listed in this file"));
9303 puts(_("-K <file> Subtract dark frame (16-bit raw PGM)"));
9304 puts(_("-k <num> Set the darkness level"));
9305 puts(_("-S <num> Set the saturation level"));
9306 puts(_("-n <num> Set threshold for wavelet denoising"));
9307 puts(_("-H [0-9] Highlight mode (0=clip, 1=unclip, 2=blend, 3+=rebuild)"));
9308 puts(_("-t [0-7] Flip image (0=none, 3=180, 5=90CCW, 6=90CW)"));
9309 puts(_("-o [0-5] Output colorspace (raw,sRGB,Adobe,Wide,ProPhoto,XYZ)"));
9311 puts(_("-o <file> Apply output ICC profile from file"));
9312 puts(_("-p <file> Apply camera ICC profile from file or \"embed\""));
9314 puts(_("-d Document mode (no color, no interpolation)"));
9315 puts(_("-D Document mode without scaling (totally raw)"));
9316 puts(_("-j Don't stretch or rotate raw pixels"));
9317 puts(_("-W Don't automatically brighten the image"));
9318 puts(_("-b <num> Adjust brightness (default = 1.0)"));
9319 puts(_("-g <p ts> Set custom gamma curve (default = 2.222 4.5)"));
9320 puts(_("-q [0-3] Set the interpolation quality"));
9321 puts(_("-h Half-size color image (twice as fast as \"-q 0\")"));
9322 puts(_("-f Interpolate RGGB as four colors"));
9323 puts(_("-m <num> Apply a 3x3 median filter to R-G and B-G"));
9324 puts(_("-s [0..N-1] Select one raw image or \"all\" from each file"));
9325 puts(_("-6 Write 16-bit instead of 8-bit"));
9326 puts(_("-4 Linear 16-bit, same as \"-6 -W -g 1 1\""));
9327 puts(_("-T Write TIFF instead of PPM"));
9332 for (arg=1; (((opm = argv[arg][0]) - 2) | 2) == '+'; ) {
9333 opt = argv[arg++][1];
9334 if ((cp = (char *) strchr (sp="nbrkStqmHACg", opt)))
9335 for (i=0; i < "114111111422"[cp-sp]-'0'; i++)
9336 if (!isdigit(argv[arg+i][0])) {
9337 fprintf (stderr,_("Non-numeric argument to \"-%c\"\n"), opt);
9341 case 'n': threshold = atof(argv[arg++]); break;
9342 case 'b': bright = atof(argv[arg++]); break;
9344 FORC4 user_mul[c] = atof(argv[arg++]); break;
9345 case 'C': aber[0] = 1 / atof(argv[arg++]);
9346 aber[2] = 1 / atof(argv[arg++]); break;
9347 case 'g': gamm[0] = atof(argv[arg++]);
9348 gamm[1] = atof(argv[arg++]);
9349 if (gamm[0]) gamm[0] = 1/gamm[0]; break;
9350 case 'k': user_black = atoi(argv[arg++]); break;
9351 case 'S': user_sat = atoi(argv[arg++]); break;
9352 case 't': user_flip = atoi(argv[arg++]); break;
9353 case 'q': user_qual = atoi(argv[arg++]); break;
9354 case 'm': med_passes = atoi(argv[arg++]); break;
9355 case 'H': highlight = atoi(argv[arg++]); break;
9357 shot_select = abs(atoi(argv[arg]));
9358 multi_out = !strcmp(argv[arg++],"all");
9361 if (isdigit(argv[arg][0]) && !argv[arg][1])
9362 output_color = atoi(argv[arg++]);
9364 else out_profile = argv[arg++];
9366 case 'p': cam_profile = argv[arg++];
9369 case 'P': bpfile = argv[arg++]; break;
9370 case 'K': dark_frame = argv[arg++]; break;
9371 case 'z': timestamp_only = 1; break;
9372 case 'e': thumbnail_only = 1; break;
9373 case 'i': identify_only = 1; break;
9374 case 'c': write_to_stdout = 1; break;
9375 case 'v': verbose = 1; break;
9376 case 'h': half_size = 1; /* "-h" implies "-f" */
9377 case 'f': four_color_rgb = 1; break;
9378 case 'A': FORC4 greybox[c] = atoi(argv[arg++]);
9379 case 'a': use_auto_wb = 1; break;
9380 case 'w': use_camera_wb = 1; break;
9381 case 'M': use_camera_matrix = (opm == '+'); break;
9382 case 'I': read_from_stdin = 1; break;
9383 case 'E': document_mode++;
9384 case 'D': document_mode++;
9385 case 'd': document_mode++;
9386 case 'j': use_fuji_rotate = 0; break;
9387 case 'W': no_auto_bright = 1; break;
9388 case 'T': output_tiff = 1; break;
9389 case '4': gamm[0] = gamm[1] =
9391 case '6': output_bps = 16; break;
9393 fprintf (stderr,_("Unknown option \"-%c\".\n"), opt);
9397 if (use_camera_matrix < 0)
9398 use_camera_matrix = use_camera_wb;
9400 fprintf (stderr,_("No files to process.\n"));
9403 if (write_to_stdout) {
9407 fprintf (stderr,_("Will not write an image to the terminal!\n"));
9410 #if defined(WIN32) || defined(DJGPP) || defined(__CYGWIN__)
9411 if (setmode(1,O_BINARY) < 0) {
9412 perror ("setmode()");
9417 for ( ; arg < argc; arg++) {
9422 meta_data = ofname = 0;
9424 if (setjmp (failure)) {
9425 if (fileno(ifp) > 2) fclose(ifp);
9426 if (fileno(ofp) > 2) fclose(ofp);
9431 if (!(ifp = fopen (ifname, "rb"))) {
9435 status = (identify(),!is_raw);
9438 switch ((flip+3600) % 360) {
9439 case 270: flip = 5; break;
9440 case 180: flip = 3; break;
9443 if (timestamp_only) {
9444 if ((status = !timestamp))
9445 fprintf (stderr,_("%s has no timestamp.\n"), ifname);
9446 else if (identify_only)
9447 printf ("%10ld%10d %s\n", (long) timestamp, shot_order, ifname);
9450 fprintf (stderr,_("%s time set to %d.\n"), ifname, (int) timestamp);
9451 ut.actime = ut.modtime = timestamp;
9452 utime (ifname, &ut);
9456 write_fun = &CLASS write_ppm_tiff;
9461 write_fun = write_cinelerra;
9466 if (thumbnail_only) {
9467 if ((status = !thumb_offset)) {
9468 fprintf (stderr,_("%s has no thumbnail.\n"), ifname);
9470 } else if (thumb_load_raw) {
9471 load_raw = thumb_load_raw;
9472 data_offset = thumb_offset;
9473 height = thumb_height;
9474 width = thumb_width;
9477 fseek (ifp, thumb_offset, SEEK_SET);
9478 write_fun = write_thumb;
9482 if (load_raw == &CLASS kodak_ycbcr_load_raw) {
9483 height += height & 1;
9486 if (identify_only && verbose && make[0]) {
9487 printf (_("\nFilename: %s\n"), ifname);
9488 printf (_("Timestamp: %s"), ctime(×tamp));
9489 printf (_("Camera: %s %s\n"), make, model);
9491 printf (_("Owner: %s\n"), artist);
9493 printf (_("DNG Version: "));
9494 for (i=24; i >= 0; i -= 8)
9495 printf ("%d%c", dng_version >> i & 255, i ? '.':'\n');
9497 printf (_("ISO speed: %d\n"), (int) iso_speed);
9498 printf (_("Shutter: "));
9499 if (shutter > 0 && shutter < 1)
9500 shutter = (printf ("1/"), 1 / shutter);
9501 printf (_("%0.1f sec\n"), shutter);
9502 printf (_("Aperture: f/%0.1f\n"), aperture);
9503 printf (_("Focal length: %0.1f mm\n"), focal_len);
9504 printf (_("Embedded ICC profile: %s\n"), profile_length ? _("yes"):_("no"));
9505 printf (_("Number of raw images: %d\n"), is_raw);
9506 if (pixel_aspect != 1)
9507 printf (_("Pixel Aspect Ratio: %0.6f\n"), pixel_aspect);
9509 printf (_("Thumb size: %4d x %d\n"), thumb_width, thumb_height);
9510 printf (_("Full size: %4d x %d\n"), raw_width, raw_height);
9516 // else if (!is_raw)
9517 // fprintf (stderr,_("Cannot decode file %s\n"), ifname);
9524 if (!is_raw) goto next;
9525 shrink = filters && (half_size || (!identify_only &&
9526 (threshold || aber[0] != 1 || aber[2] != 1)));
9527 iheight = (height + shrink) >> shrink;
9528 iwidth = (width + shrink) >> shrink;
9529 if (identify_only) {
9531 if (document_mode == 3) {
9532 top_margin = left_margin = fuji_width = 0;
9533 height = raw_height;
9534 if (width <= raw_width * 8 / tiff_bps)
9535 width = raw_width * 8 / tiff_bps;
9536 else width = raw_width;
9538 iheight = (height + shrink) >> shrink;
9539 iwidth = (width + shrink) >> shrink;
9540 if (use_fuji_rotate) {
9542 fuji_width = (fuji_width - 1 + shrink) >> shrink;
9543 iwidth = fuji_width / sqrt(0.5);
9544 iheight = (iheight - fuji_width) / sqrt(0.5);
9546 if (pixel_aspect < 1) iheight = iheight / pixel_aspect + 0.5;
9547 if (pixel_aspect > 1) iwidth = iwidth * pixel_aspect + 0.5;
9551 SWAP(iheight,iwidth);
9552 printf (_("Image size: %4d x %d\n"), width, height);
9553 printf (_("Output size: %4d x %d\n"), iwidth, iheight);
9554 printf (_("Raw colors: %d"), colors);
9556 printf (_("\nFilter pattern: "));
9557 for (i=0; i < 16; i++)
9558 putchar (cdesc[fcol(i >> 1,i & 1)]);
9560 printf (_("\nDaylight multipliers:"));
9561 FORCC printf (" %f", pre_mul[c]);
9562 if (cam_mul[0] > 0) {
9563 printf (_("\nCamera multipliers:"));
9564 FORC4 printf (" %f", cam_mul[c]);
9569 // printf (_("%s is a %s %s image.\n"), ifname, make, model);
9574 if (use_camera_matrix && cmatrix[0][0] > 0.25) {
9575 memcpy (rgb_cam, cmatrix, sizeof cmatrix);
9579 meta_data = (char *) malloc (meta_length);
9580 merror (meta_data, "main()");
9582 if (filters || colors == 1) {
9583 raw_image = (ushort *) calloc ((raw_height+7)*raw_width, 2);
9584 merror (raw_image, "main()");
9586 image = (ushort (*)[4]) calloc (iheight*iwidth, sizeof *image);
9587 merror (image, "main()");
9590 fprintf (stderr,_("Loading %s %s image from %s ...\n"),
9591 make, model, ifname);
9592 if (shot_select >= is_raw)
9593 fprintf (stderr,_("%s: \"-s %d\" requests a nonexistent image!\n"),
9594 ifname, shot_select);
9595 fseeko (ifp, data_offset, SEEK_SET);
9596 if (raw_image && read_from_stdin)
9597 fread (raw_image, 2, raw_height*raw_width, stdin);
9599 if (document_mode == 3) {
9600 top_margin = left_margin = fuji_width = 0;
9601 height = raw_height;
9602 if (width <= raw_width * 8 / tiff_bps)
9603 width = raw_width * 8 / tiff_bps;
9604 else width = raw_width;
9606 iheight = (height + shrink) >> shrink;
9607 iwidth = (width + shrink) >> shrink;
9609 image = (ushort (*)[4]) calloc (iheight*iwidth, sizeof *image);
9610 merror (image, "main()");
9611 crop_masked_pixels();
9614 if (zero_is_bad) remove_zeroes();
9615 bad_pixels (bpfile);
9616 if (dark_frame) subtract (dark_frame);
9617 quality = 2 + !fuji_width;
9618 if (user_qual >= 0) quality = user_qual;
9620 FORC3 if (i > cblack[c]) i = cblack[c];
9621 FORC4 cblack[c] -= i;
9623 if (user_black >= 0) black = user_black;
9624 FORC4 cblack[c] += black;
9625 if (user_sat > 0) maximum = user_sat;
9630 if (document_mode || load_raw == &CLASS foveon_dp_load_raw) {
9631 for (i=0; i < height*width*4; i++)
9632 if ((short) image[0][i] < 0) image[0][i] = 0;
9633 } else foveon_interpolate();
9634 } else if (document_mode < 2)
9637 if (filters && !document_mode) {
9640 else if (quality == 1 || colors > 3 || filters < 1000)
9642 else if (quality == 2)
9644 else ahd_interpolate();
9647 for (colors=3, i=0; i < height*width; i++)
9648 image[i][1] = (image[i][1] + image[i][3]) >> 1;
9649 if (!is_foveon && colors == 3) median_filter();
9650 if (!is_foveon && highlight == 2) blend_highlights();
9651 if (!is_foveon && highlight > 2) recover_highlights();
9652 if (use_fuji_rotate) fuji_rotate();
9654 if (cam_profile) apply_profile (cam_profile, out_profile);
9657 if (use_fuji_rotate) stretch();
9659 if (write_fun == &CLASS jpeg_thumb)
9661 else if (output_tiff && write_fun == &CLASS write_ppm_tiff)
9662 write_ext = ".tiff";
9664 write_ext = ".pgm\0.ppm\0.ppm\0.pam" + colors*5-5;
9665 ofname = (char *) malloc (strlen(ifname) + 64);
9666 merror (ofname, "main()");
9667 if (write_to_stdout)
9668 strcpy (ofname,_("standard output"));
9670 strcpy (ofname, ifname);
9671 if ((cp = strrchr (ofname, '.'))) *cp = 0;
9673 sprintf (ofname+strlen(ofname), "_%0*d",
9674 snprintf(0,0,"%d",is_raw-1), shot_select);
9676 strcat (ofname, ".thumb");
9677 strcat (ofname, write_ext);
9678 ofp = fopen (ofname, "wb");
9686 fprintf (stderr,_("Writing data to %s ...\n"), ofname);
9689 if (ofp != stdout) fclose(ofp);
9691 if (meta_data) free (meta_data);
9692 if (ofname) free (ofname);
9693 if (oprof) free (oprof);
9694 if (image) free (image);
9696 if (++shot_select < is_raw) arg--;
9697 else shot_select = 0;