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;
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];
2394 void CLASS sony_load_raw()
2398 unsigned i, key, row, col;
2400 fseek (ifp, 200896, SEEK_SET);
2401 fseek (ifp, (unsigned) fgetc(ifp)*4 - 1, SEEK_CUR);
2404 fseek (ifp, 164600, SEEK_SET);
2405 fread (head, 1, 40, ifp);
2406 sony_decrypt ((unsigned int *) head, 10, 1, key);
2407 for (i=26; i-- > 22; )
2408 key = key << 8 | head[i];
2409 fseek (ifp, data_offset, SEEK_SET);
2410 for (row=0; row < raw_height; row++) {
2411 pixel = raw_image + row*raw_width;
2412 if (fread (pixel, 2, raw_width, ifp) < raw_width) derror();
2413 sony_decrypt ((unsigned int *) pixel, raw_width/2, !row, key);
2414 for (col=0; col < raw_width; col++)
2415 if ((pixel[col] = ntohs(pixel[col])) >> 14) derror();
2420 void CLASS sony_arw_load_raw()
2423 static const ushort tab[18] =
2424 { 0xf11,0xf10,0xe0f,0xd0e,0xc0d,0xb0c,0xa0b,0x90a,0x809,
2425 0x708,0x607,0x506,0x405,0x304,0x303,0x300,0x202,0x201 };
2426 int i, c, n, col, row, len, diff, sum=0;
2428 for (n=i=0; i < 18; i++)
2429 FORC(32768 >> (tab[i] >> 8)) huff[n++] = tab[i];
2431 for (col = raw_width; col--; )
2432 for (row=0; row < raw_height+1; row+=2) {
2433 if (row == raw_height) row = 1;
2434 len = getbithuff(15,huff);
2435 diff = getbits(len);
2436 if ((diff & (1 << (len-1))) == 0)
2437 diff -= (1 << len) - 1;
2438 if ((sum += diff) >> 12) derror();
2439 if (row < height) RAW(row,col) = sum;
2443 void CLASS sony_arw2_load_raw()
2447 int row, col, val, max, min, imax, imin, sh, bit, i;
2449 data = (uchar *) malloc (raw_width);
2450 merror (data, "sony_arw2_load_raw()");
2451 for (row=0; row < height; row++) {
2452 fread (data, 1, raw_width, ifp);
2453 for (dp=data, col=0; col < raw_width-30; dp+=16) {
2454 max = 0x7ff & (val = sget4(dp));
2455 min = 0x7ff & val >> 11;
2456 imax = 0x0f & val >> 22;
2457 imin = 0x0f & val >> 26;
2458 for (sh=0; sh < 4 && 0x80 << sh <= max-min; sh++);
2459 for (bit=30, i=0; i < 16; i++)
2460 if (i == imax) pix[i] = max;
2461 else if (i == imin) pix[i] = min;
2463 pix[i] = ((sget2(dp+(bit >> 3)) >> (bit & 7) & 0x7f) << sh) + min;
2464 if (pix[i] > 0x7ff) pix[i] = 0x7ff;
2467 for (i=0; i < 16; i++, col+=2)
2468 RAW(row,col) = curve[pix[i] << 1] >> 2;
2469 col -= col & 1 ? 1:31;
2475 #define HOLE(row) ((holes >> (((row) - raw_height) & 7)) & 1)
2477 /* Kudos to Rich Taylor for figuring out SMaL's compression algorithm. */
2478 void CLASS smal_decode_segment (unsigned seg[2][2], int holes)
2480 uchar hist[3][13] = {
2481 { 7, 7, 0, 0, 63, 55, 47, 39, 31, 23, 15, 7, 0 },
2482 { 7, 7, 0, 0, 63, 55, 47, 39, 31, 23, 15, 7, 0 },
2483 { 3, 3, 0, 0, 63, 47, 31, 15, 0 } };
2484 int low, high=0xff, carry=0, nbits=8;
2485 int pix, s, count, bin, next, i, sym[3];
2486 uchar diff, pred[]={0,0};
2487 ushort data=0, range=0;
2489 fseek (ifp, seg[0][1]+1, SEEK_SET);
2491 for (pix=seg[0][0]; pix < seg[1][0]; pix++) {
2492 for (s=0; s < 3; s++) {
2493 data = data << nbits | getbits(nbits);
2495 carry = (nbits += carry+1) < 1 ? nbits-1 : 0;
2496 while (--nbits >= 0)
2497 if ((data >> nbits & 0xff) == 0xff) break;
2499 data = ((data & ((1 << (nbits-1)) - 1)) << 1) |
2500 ((data + (((data & (1 << (nbits-1)))) << 1)) & (-1 << nbits));
2505 count = ((((data-range+1) & 0xffff) << 2) - 1) / (high >> 4);
2506 for (bin=0; hist[s][bin+5] > count; bin++);
2507 low = hist[s][bin+5] * (high >> 4) >> 2;
2508 if (bin) high = hist[s][bin+4] * (high >> 4) >> 2;
2510 for (nbits=0; high << nbits < 128; nbits++);
2511 range = (range+low) << nbits;
2514 if (++hist[s][2] > hist[s][3]) {
2515 next = (next+1) & hist[s][0];
2516 hist[s][3] = (hist[s][next+4] - hist[s][next+5]) >> 2;
2519 if (hist[s][hist[s][1]+4] - hist[s][hist[s][1]+5] > 1) {
2520 if (bin < hist[s][1])
2521 for (i=bin; i < hist[s][1]; i++) hist[s][i+5]--;
2522 else if (next <= bin)
2523 for (i=hist[s][1]; i < bin; i++) hist[s][i+5]++;
2528 diff = sym[2] << 5 | sym[1] << 2 | (sym[0] & 3);
2530 diff = diff ? -diff : 0x80;
2531 if (ftell(ifp) + 12 >= seg[1][1])
2533 raw_image[pix] = pred[pix & 1] += diff;
2534 if (!(pix & 1) && HOLE(pix / raw_width)) pix += 2;
2539 void CLASS smal_v6_load_raw()
2543 fseek (ifp, 16, SEEK_SET);
2546 seg[1][0] = raw_width * raw_height;
2547 seg[1][1] = INT_MAX;
2548 smal_decode_segment (seg, 0);
2551 int CLASS median4 (int *p)
2553 int min, max, sum, i;
2555 min = max = sum = p[0];
2556 for (i=1; i < 4; i++) {
2558 if (min > p[i]) min = p[i];
2559 if (max < p[i]) max = p[i];
2561 return (sum - min - max) >> 1;
2564 void CLASS fill_holes (int holes)
2566 int row, col, val[4];
2568 for (row=2; row < height-2; row++) {
2569 if (!HOLE(row)) continue;
2570 for (col=1; col < width-1; col+=4) {
2571 val[0] = RAW(row-1,col-1);
2572 val[1] = RAW(row-1,col+1);
2573 val[2] = RAW(row+1,col-1);
2574 val[3] = RAW(row+1,col+1);
2575 RAW(row,col) = median4(val);
2577 for (col=2; col < width-2; col+=4)
2578 if (HOLE(row-2) || HOLE(row+2))
2579 RAW(row,col) = (RAW(row,col-2) + RAW(row,col+2)) >> 1;
2581 val[0] = RAW(row,col-2);
2582 val[1] = RAW(row,col+2);
2583 val[2] = RAW(row-2,col);
2584 val[3] = RAW(row+2,col);
2585 RAW(row,col) = median4(val);
2590 void CLASS smal_v9_load_raw()
2592 unsigned seg[256][2], offset, nseg, holes, i;
2594 fseek (ifp, 67, SEEK_SET);
2597 fseek (ifp, offset, SEEK_SET);
2598 for (i=0; i < nseg*2; i++)
2599 seg[0][i] = get4() + data_offset*(i & 1);
2600 fseek (ifp, 78, SEEK_SET);
2602 fseek (ifp, 88, SEEK_SET);
2603 seg[nseg][0] = raw_height * raw_width;
2604 seg[nseg][1] = get4() + data_offset;
2605 for (i=0; i < nseg; i++)
2606 smal_decode_segment (seg+i, holes);
2607 if (holes) fill_holes (holes);
2610 void CLASS redcine_load_raw()
2621 in = jas_stream_fopen (ifname, "rb");
2622 jas_stream_seek (in, data_offset+20, SEEK_SET);
2623 jimg = jas_image_decode (in, -1, 0);
2624 if (!jimg) longjmp (failure, 3);
2625 jmat = jas_matrix_create (height/2, width/2);
2626 merror (jmat, "redcine_load_raw()");
2627 img = (ushort *) calloc ((height+2)*(width+2), 2);
2628 merror (img, "redcine_load_raw()");
2630 jas_image_readcmpt (jimg, c, 0, 0, width/2, height/2, jmat);
2631 data = jas_matrix_getref (jmat, 0, 0);
2632 for (row = c >> 1; row < height; row+=2)
2633 for (col = c & 1; col < width; col+=2)
2634 img[(row+1)*(width+2)+col+1] = data[(row/2)*(width/2)+col/2];
2636 for (col=1; col <= width; col++) {
2637 img[col] = img[2*(width+2)+col];
2638 img[(height+1)*(width+2)+col] = img[(height-1)*(width+2)+col];
2640 for (row=0; row < height+2; row++) {
2641 img[row*(width+2)] = img[row*(width+2)+2];
2642 img[(row+1)*(width+2)-1] = img[(row+1)*(width+2)-3];
2644 for (row=1; row <= height; row++) {
2645 pix = img + row*(width+2) + (col = 1 + (FC(row,1) & 1));
2646 for ( ; col <= width; col+=2, pix+=2) {
2647 c = (((pix[0] - 0x800) << 3) +
2648 pix[-(width+2)] + pix[width+2] + pix[-1] + pix[1]) >> 2;
2649 pix[0] = LIM(c,0,4095);
2652 for (row=0; row < height; row++)
2653 for (col=0; col < width; col++)
2654 RAW(row,col) = curve[img[(row+1)*(width+2)+col+1]];
2656 jas_matrix_destroy (jmat);
2657 jas_image_destroy (jimg);
2658 jas_stream_close (in);
2662 /* RESTRICTED code starts here */
2664 void CLASS foveon_decoder (unsigned size, unsigned code)
2666 static unsigned huff[1024];
2671 for (i=0; i < size; i++)
2673 memset (first_decode, 0, sizeof first_decode);
2674 free_decode = first_decode;
2676 cur = free_decode++;
2677 if (free_decode > first_decode+2048) {
2678 fprintf (stderr,_("%s: decoder table overflow\n"), ifname);
2679 longjmp (failure, 2);
2682 for (i=0; i < size; i++)
2683 if (huff[i] == code) {
2687 if ((len = code >> 27) > 26) return;
2688 code = (len+1) << 27 | (code & 0x3ffffff) << 1;
2690 cur->branch[0] = free_decode;
2691 foveon_decoder (size, code);
2692 cur->branch[1] = free_decode;
2693 foveon_decoder (size, code+1);
2696 void CLASS foveon_thumb()
2698 unsigned bwide, row, col, bitbuf=0, bit=1, c, i;
2700 struct decode *dindex;
2704 fprintf (ofp, "P6\n%d %d\n255\n", thumb_width, thumb_height);
2706 if (bwide < thumb_width*3) return;
2707 buf = (char *) malloc (bwide);
2708 merror (buf, "foveon_thumb()");
2709 for (row=0; row < thumb_height; row++) {
2710 fread (buf, 1, bwide, ifp);
2711 fwrite (buf, 3, thumb_width, ofp);
2716 foveon_decoder (256, 0);
2718 for (row=0; row < thumb_height; row++) {
2719 memset (pred, 0, sizeof pred);
2721 for (bit=col=0; col < thumb_width; col++)
2723 for (dindex=first_decode; dindex->branch[0]; ) {
2724 if ((bit = (bit-1) & 31) == 31)
2725 for (i=0; i < 4; i++)
2726 bitbuf = (bitbuf << 8) + fgetc(ifp);
2727 dindex = dindex->branch[bitbuf >> bit & 1];
2729 pred[c] += dindex->leaf;
2730 fputc (pred[c], ofp);
2735 void CLASS foveon_sd_load_raw()
2737 struct decode *dindex;
2740 int pred[3], row, col, bit=-1, c, i;
2742 read_shorts ((ushort *) diff, 1024);
2743 if (!load_flags) foveon_decoder (1024, 0);
2745 for (row=0; row < height; row++) {
2746 memset (pred, 0, sizeof pred);
2747 if (!bit && !load_flags && atoi(model+2) < 14) get4();
2748 for (col=bit=0; col < width; col++) {
2751 FORC3 pred[2-c] += diff[bitbuf >> c*10 & 0x3ff];
2754 for (dindex=first_decode; dindex->branch[0]; ) {
2755 if ((bit = (bit-1) & 31) == 31)
2756 for (i=0; i < 4; i++)
2757 bitbuf = (bitbuf << 8) + fgetc(ifp);
2758 dindex = dindex->branch[bitbuf >> bit & 1];
2760 pred[c] += diff[dindex->leaf];
2761 if (pred[c] >> 16 && ~pred[c] >> 16) derror();
2763 FORC3 image[row*width+col][c] = pred[c];
2768 void CLASS foveon_huff (ushort *huff)
2770 int i, j, clen, code;
2773 for (i=0; i < 13; i++) {
2776 for (j=0; j < 256 >> clen; )
2777 huff[code+ ++j] = clen << 8 | i;
2782 void CLASS foveon_dp_load_raw()
2784 unsigned c, roff[4], row, col, diff;
2785 ushort huff[258], vpred[2][2], hpred[2];
2787 fseek (ifp, 8, SEEK_CUR);
2790 FORC3 roff[c+1] = -(-(roff[c] + get4()) & -16);
2792 fseek (ifp, data_offset+roff[c], SEEK_SET);
2794 vpred[0][0] = vpred[0][1] = vpred[1][0] = vpred[1][1] = 512;
2795 for (row=0; row < height; row++) {
2796 for (col=0; col < width; col++) {
2797 diff = ljpeg_diff(huff);
2798 if (col < 2) hpred[col] = vpred[row & 1][col] += diff;
2799 else hpred[col & 1] += diff;
2800 image[row*width+col][c] = hpred[col & 1];
2806 void CLASS foveon_load_camf()
2808 unsigned type, wide, high, i, j, row, col, diff;
2809 ushort huff[258], vpred[2][2] = {{512,512},{512,512}}, hpred[2];
2811 fseek (ifp, meta_offset, SEEK_SET);
2812 type = get4(); get4(); get4();
2816 fread (meta_data, 1, meta_length, ifp);
2817 for (i=0; i < meta_length; i++) {
2818 high = (high * 1597 + 51749) % 244944;
2819 wide = high * (INT64) 301593171 >> 24;
2820 meta_data[i] ^= ((((high << 8) - wide) >> 1) + wide) >> 17;
2822 } else if (type == 4) {
2824 meta_data = (char *) malloc (meta_length = wide*high*3/2);
2825 merror (meta_data, "foveon_load_camf()");
2829 for (j=row=0; row < high; row++) {
2830 for (col=0; col < wide; col++) {
2831 diff = ljpeg_diff(huff);
2832 if (col < 2) hpred[col] = vpred[row & 1][col] += diff;
2833 else hpred[col & 1] += diff;
2835 meta_data[j++] = hpred[0] >> 4;
2836 meta_data[j++] = hpred[0] << 4 | hpred[1] >> 8;
2837 meta_data[j++] = hpred[1];
2842 fprintf (stderr,_("%s has unknown CAMF type %d.\n"), ifname, type);
2845 const char * CLASS foveon_camf_param (const char *block, const char *param)
2848 char *pos, *cp, *dp;
2850 for (idx=0; idx < meta_length; idx += sget4(pos+8)) {
2851 pos = meta_data + idx;
2852 if (strncmp (pos, "CMb", 3)) break;
2853 if (pos[3] != 'P') continue;
2854 if (strcmp (block, pos+sget4(pos+12))) continue;
2855 cp = pos + sget4(pos+16);
2857 dp = pos + sget4(cp+4);
2860 if (!strcmp (param, dp+sget4(cp)))
2861 return dp+sget4(cp+4);
2867 void * CLASS foveon_camf_matrix (unsigned dim[3], const char *name)
2869 unsigned i, idx, type, ndim, size, *mat;
2870 char *pos, *cp, *dp;
2873 for (idx=0; idx < meta_length; idx += sget4(pos+8)) {
2874 pos = meta_data + idx;
2875 if (strncmp (pos, "CMb", 3)) break;
2876 if (pos[3] != 'M') continue;
2877 if (strcmp (name, pos+sget4(pos+12))) continue;
2878 dim[0] = dim[1] = dim[2] = 1;
2879 cp = pos + sget4(pos+16);
2881 if ((ndim = sget4(cp+4)) > 3) break;
2882 dp = pos + sget4(cp+8);
2883 for (i=ndim; i--; ) {
2887 if ((dsize = (double) dim[0]*dim[1]*dim[2]) > meta_length/4) break;
2888 mat = (unsigned *) malloc ((size = dsize) * 4);
2889 merror (mat, "foveon_camf_matrix()");
2890 for (i=0; i < size; i++)
2891 if (type && type != 6)
2892 mat[i] = sget4(dp + i*4);
2894 mat[i] = sget4(dp + i*2) & 0xffff;
2897 fprintf (stderr,_("%s: \"%s\" matrix not found!\n"), ifname, name);
2901 int CLASS foveon_fixed (void *ptr, int size, const char *name)
2906 if (!name) return 0;
2907 dp = foveon_camf_matrix (dim, name);
2909 memcpy (ptr, dp, size*4);
2914 float CLASS foveon_avg (short *pix, int range[2], float cfilt)
2917 float val, min=FLT_MAX, max=-FLT_MAX, sum=0;
2919 for (i=range[0]; i <= range[1]; i++) {
2920 sum += val = pix[i*4] + (pix[i*4]-pix[(i-1)*4]) * cfilt;
2921 if (min > val) min = val;
2922 if (max < val) max = val;
2924 if (range[1] - range[0] == 1) return sum/2;
2925 return (sum - min - max) / (range[1] - range[0] - 1);
2928 short * CLASS foveon_make_curve (double max, double mul, double filt)
2934 if (!filt) filt = 0.8;
2935 size = 4*M_PI*max / filt;
2936 if (size == UINT_MAX) size--;
2937 curve = (short *) calloc (size+1, sizeof *curve);
2938 merror (curve, "foveon_make_curve()");
2940 for (i=0; i < size; i++) {
2942 curve[i+1] = (cos(x)+1)/2 * tanh(i*filt/mul) * mul + 0.5;
2947 void CLASS foveon_make_curves
2948 (short **curvep, float dq[3], float div[3], float filt)
2950 double mul[3], max=0;
2953 FORC3 mul[c] = dq[c]/div[c];
2954 FORC3 if (max < mul[c]) max = mul[c];
2955 FORC3 curvep[c] = foveon_make_curve (max, mul[c], filt);
2958 int CLASS foveon_apply_curve (short *curve, int i)
2960 if (abs(i) >= curve[0]) return 0;
2961 return i < 0 ? -curve[1-i] : curve[1+i];
2964 #define image ((short (*)[4]) image)
2966 void CLASS foveon_interpolate()
2968 static const short hood[] = { -1,-1, -1,0, -1,1, 0,-1, 0,1, 1,-1, 1,0, 1,1 };
2969 short *pix, prev[3], *curve[8], (*shrink)[3];
2970 float cfilt=0, ddft[3][3][2], ppm[3][3][3];
2971 float cam_xyz[3][3], correct[3][3], last[3][3], trans[3][3];
2972 float chroma_dq[3], color_dq[3], diag[3][3], div[3];
2973 float (*black)[3], (*sgain)[3], (*sgrow)[3];
2974 float fsum[3], val, frow, num;
2975 int row, col, c, i, j, diff, sgx, irow, sum, min, max, limit;
2976 int dscr[2][2], dstb[4], (*smrow[7])[3], total[4], ipix[3];
2977 int work[3][3], smlast, smred, smred_p=0, dev[3];
2978 int satlev[3], keep[4], active[4];
2979 unsigned dim[3], *badpix;
2980 double dsum=0, trsum[3];
2985 fprintf (stderr,_("Foveon interpolation...\n"));
2988 foveon_fixed (dscr, 4, "DarkShieldColRange");
2989 foveon_fixed (ppm[0][0], 27, "PostPolyMatrix");
2990 foveon_fixed (satlev, 3, "SaturationLevel");
2991 foveon_fixed (keep, 4, "KeepImageArea");
2992 foveon_fixed (active, 4, "ActiveImageArea");
2993 foveon_fixed (chroma_dq, 3, "ChromaDQ");
2994 foveon_fixed (color_dq, 3,
2995 foveon_camf_param ("IncludeBlocks", "ColorDQ") ?
2996 "ColorDQ" : "ColorDQCamRGB");
2997 if (foveon_camf_param ("IncludeBlocks", "ColumnFilter"))
2998 foveon_fixed (&cfilt, 1, "ColumnFilter");
3000 memset (ddft, 0, sizeof ddft);
3001 if (!foveon_camf_param ("IncludeBlocks", "DarkDrift")
3002 || !foveon_fixed (ddft[1][0], 12, "DarkDrift"))
3003 for (i=0; i < 2; i++) {
3004 foveon_fixed (dstb, 4, i ? "DarkShieldBottom":"DarkShieldTop");
3005 for (row = dstb[1]; row <= dstb[3]; row++)
3006 for (col = dstb[0]; col <= dstb[2]; col++)
3007 FORC3 ddft[i+1][c][1] += (short) image[row*width+col][c];
3008 FORC3 ddft[i+1][c][1] /= (dstb[3]-dstb[1]+1) * (dstb[2]-dstb[0]+1);
3011 if (!(cp = foveon_camf_param ("WhiteBalanceIlluminants", model2)))
3012 { fprintf (stderr,_("%s: Invalid white balance \"%s\"\n"), ifname, model2);
3014 foveon_fixed (cam_xyz, 9, cp);
3015 foveon_fixed (correct, 9,
3016 foveon_camf_param ("WhiteBalanceCorrections", model2));
3017 memset (last, 0, sizeof last);
3018 for (i=0; i < 3; i++)
3019 for (j=0; j < 3; j++)
3020 FORC3 last[i][j] += correct[i][c] * cam_xyz[c][j];
3022 #define LAST(x,y) last[(i+x)%3][(c+y)%3]
3023 for (i=0; i < 3; i++)
3024 FORC3 diag[c][i] = LAST(1,1)*LAST(2,2) - LAST(1,2)*LAST(2,1);
3026 FORC3 div[c] = diag[c][0]*0.3127 + diag[c][1]*0.329 + diag[c][2]*0.3583;
3027 sprintf (str, "%sRGBNeutral", model2);
3028 if (foveon_camf_param ("IncludeBlocks", str))
3029 foveon_fixed (div, 3, str);
3031 FORC3 if (num < div[c]) num = div[c];
3032 FORC3 div[c] /= num;
3034 memset (trans, 0, sizeof trans);
3035 for (i=0; i < 3; i++)
3036 for (j=0; j < 3; j++)
3037 FORC3 trans[i][j] += rgb_cam[i][c] * last[c][j] * div[j];
3038 FORC3 trsum[c] = trans[c][0] + trans[c][1] + trans[c][2];
3039 dsum = (6*trsum[0] + 11*trsum[1] + 3*trsum[2]) / 20;
3040 for (i=0; i < 3; i++)
3041 FORC3 last[i][c] = trans[i][c] * dsum / trsum[i];
3042 memset (trans, 0, sizeof trans);
3043 for (i=0; i < 3; i++)
3044 for (j=0; j < 3; j++)
3045 FORC3 trans[i][j] += (i==c ? 32 : -1) * last[c][j] / 30;
3047 foveon_make_curves (curve, color_dq, div, cfilt);
3048 FORC3 chroma_dq[c] /= 3;
3049 foveon_make_curves (curve+3, chroma_dq, div, cfilt);
3050 FORC3 dsum += chroma_dq[c] / div[c];
3051 curve[6] = foveon_make_curve (dsum, dsum, cfilt);
3052 curve[7] = foveon_make_curve (dsum*2, dsum*2, cfilt);
3054 sgain = (float (*)[3]) foveon_camf_matrix (dim, "SpatialGain");
3056 sgrow = (float (*)[3]) calloc (dim[1], sizeof *sgrow);
3057 sgx = (width + dim[1]-2) / (dim[1]-1);
3059 black = (float (*)[3]) calloc (height, sizeof *black);
3060 for (row=0; row < height; row++) {
3061 float *dp0 = &ddft[0][0][0];
3062 float *dp1 = &ddft[1][0][0];
3063 float *dp2 = &ddft[2][0][0];
3064 for( i=6; --i>=0; ++dp0,++dp1,++dp2 )
3065 *dp0 = *dp1 + row / (height-1.0) * (*dp2 - *dp1);
3066 pix = image[row*width];
3067 FORC3 black[row][c] =
3068 ( foveon_avg (image[row*width]+c, dscr[0], cfilt) +
3069 foveon_avg (image[row*width]+c, dscr[1], cfilt) * 3
3070 - ddft[0][c][0] ) / 4 - ddft[0][c][1];
3072 memcpy (black, black+8, sizeof *black*8);
3073 memcpy (black+height-11, black+height-22, 11*sizeof *black);
3074 memcpy (last, black, sizeof last);
3076 for (row=1; row < height-1; row++) {
3077 FORC3 if (last[1][c] > last[0][c]) {
3078 if (last[1][c] > last[2][c])
3079 black[row][c] = (last[0][c] > last[2][c]) ? last[0][c]:last[2][c];
3081 if (last[1][c] < last[2][c])
3082 black[row][c] = (last[0][c] < last[2][c]) ? last[0][c]:last[2][c];
3083 memmove (last, last+1, 2*sizeof last[0]);
3084 memcpy (last[2], black[row+1], sizeof last[2]);
3086 FORC3 black[row][c] = (last[0][c] + last[1][c])/2;
3087 FORC3 black[0][c] = (black[1][c] + black[3][c])/2;
3089 val = 1 - exp(-1/24.0);
3090 memcpy (fsum, black, sizeof fsum);
3091 for (row=1; row < height; row++)
3092 FORC3 fsum[c] += black[row][c] =
3093 (black[row][c] - black[row-1][c])*val + black[row-1][c];
3094 memcpy (last[0], black[height-1], sizeof last[0]);
3095 FORC3 fsum[c] /= height;
3096 for (row = height; row--; )
3097 FORC3 last[0][c] = black[row][c] =
3098 (black[row][c] - fsum[c] - last[0][c])*val + last[0][c];
3100 memset (total, 0, sizeof total);
3101 for (row=2; row < height; row+=4)
3102 for (col=2; col < width; col+=4) {
3103 FORC3 total[c] += (short) image[row*width+col][c];
3106 for (row=0; row < height; row++)
3107 FORC3 black[row][c] += fsum[c]/2 + total[c]/(total[3]*100.0);
3109 for (row=0; row < height; row++) {
3110 float *dp0 = &ddft[0][0][0];
3111 float *dp1 = &ddft[1][0][0];
3112 float *dp2 = &ddft[2][0][0];
3113 for( i=6; --i>=0; ++dp0,++dp1,++dp2 )
3114 *dp0 = *dp1 + row / (height-1.0) * (*dp2 - *dp1);
3115 pix = image[row*width];
3116 memcpy (prev, pix, sizeof prev);
3117 frow = row / (height-1.0) * (dim[2]-1);
3118 if ((irow = frow) == dim[2]-1) irow--;
3120 for (i=0; i < dim[1]; i++)
3121 FORC3 sgrow[i][c] = sgain[ irow *dim[1]+i][c] * (1-frow) +
3122 sgain[(irow+1)*dim[1]+i][c] * frow;
3123 for (col=0; col < width; col++) {
3125 diff = pix[c] - prev[c];
3127 ipix[c] = pix[c] + floor ((diff + (diff*diff >> 14)) * cfilt
3128 - ddft[0][c][1] - ddft[0][c][0] * ((float) col/width - 0.5)
3132 work[0][c] = ipix[c] * ipix[c] >> 14;
3133 work[2][c] = ipix[c] * work[0][c] >> 14;
3134 work[1][2-c] = ipix[(c+1) % 3] * ipix[(c+2) % 3] >> 14;
3137 for (val=i=0; i < 3; i++)
3138 for ( j=0; j < 3; j++)
3139 val += ppm[c][i][j] * work[i][j];
3140 ipix[c] = floor ((ipix[c] + floor(val)) *
3141 ( sgrow[col/sgx ][c] * (sgx - col%sgx) +
3142 sgrow[col/sgx+1][c] * (col%sgx) ) / sgx / div[c]);
3143 if (ipix[c] > 32000) ipix[c] = 32000;
3153 if ((badpix = (unsigned int *) foveon_camf_matrix (dim, "BadPixels"))) {
3154 for (i=0; i < dim[0]; i++) {
3155 col = (badpix[i] >> 8 & 0xfff) - keep[0];
3156 row = (badpix[i] >> 20 ) - keep[1];
3157 if ((unsigned)(row-1) > height-3 || (unsigned)(col-1) > width-3)
3159 memset (fsum, 0, sizeof fsum);
3160 for (sum=j=0; j < 8; j++)
3161 if (badpix[i] & (1 << j)) {
3162 FORC3 fsum[c] += (short)
3163 image[(row+hood[j*2])*width+col+hood[j*2+1]][c];
3166 if (sum) FORC3 image[row*width+col][c] = fsum[c]/sum;
3171 /* Array for 5x5 Gaussian averaging of red values */
3172 smrow[6] = (int (*)[3]) calloc (width*5, sizeof **smrow);
3173 merror (smrow[6], "foveon_interpolate()");
3174 for (i=0; i < 5; i++)
3175 smrow[i] = smrow[6] + i*width;
3177 /* Sharpen the reds against these Gaussian averages */
3178 for (smlast=-1, row=2; row < height-2; row++) {
3179 while (smlast < row+2) {
3180 for (i=0; i < 6; i++)
3181 smrow[(i+5) % 6] = smrow[i];
3182 pix = image[++smlast*width+2];
3183 for (col=2; col < width-2; col++) {
3185 (pix[0]*6 + (pix[-4]+pix[4])*4 + pix[-8]+pix[8] + 8) >> 4;
3189 pix = image[row*width+2];
3190 for (col=2; col < width-2; col++) {
3191 smred = ( 6 * smrow[2][col][0]
3192 + 4 * (smrow[1][col][0] + smrow[3][col][0])
3193 + smrow[0][col][0] + smrow[4][col][0] + 8 ) >> 4;
3196 i = pix[0] + ((pix[0] - ((smred*7 + smred_p) >> 3)) >> 3);
3197 if (i > 32000) i = 32000;
3204 /* Adjust the brighter pixels for better linearity */
3207 i = satlev[c] / div[c];
3208 if (min > i) min = i;
3210 limit = min * 9 >> 4;
3211 for (pix=image[0]; pix < image[height*width]; pix+=4) {
3212 if (pix[0] <= limit || pix[1] <= limit || pix[2] <= limit)
3215 for (c=1; c < 3; c++) {
3216 if (min > pix[c]) min = pix[c];
3217 if (max < pix[c]) max = pix[c];
3219 if (min >= limit*2) {
3220 pix[0] = pix[1] = pix[2] = max;
3222 i = 0x4000 - ((min - limit) << 14) / limit;
3223 i = 0x4000 - (i*i >> 14);
3225 FORC3 pix[c] += (max - pix[c]) * i >> 14;
3229 Because photons that miss one detector often hit another,
3230 the sum R+G+B is much less noisy than the individual colors.
3231 So smooth the hues without smoothing the total.
3233 for (smlast=-1, row=2; row < height-2; row++) {
3234 while (smlast < row+2) {
3235 for (i=0; i < 6; i++)
3236 smrow[(i+5) % 6] = smrow[i];
3237 pix = image[++smlast*width+2];
3238 for (col=2; col < width-2; col++) {
3239 FORC3 smrow[4][col][c] = (pix[c-4]+2*pix[c]+pix[c+4]+2) >> 2;
3243 pix = image[row*width+2];
3244 for (col=2; col < width-2; col++) {
3245 FORC3 dev[c] = -foveon_apply_curve (curve[7], pix[c] -
3246 ((smrow[1][col][c] + 2*smrow[2][col][c] + smrow[3][col][c]) >> 2));
3247 sum = (dev[0] + dev[1] + dev[2]) >> 3;
3248 FORC3 pix[c] += dev[c] - sum;
3252 for (smlast=-1, row=2; row < height-2; row++) {
3253 while (smlast < row+2) {
3254 for (i=0; i < 6; i++)
3255 smrow[(i+5) % 6] = smrow[i];
3256 pix = image[++smlast*width+2];
3257 for (col=2; col < width-2; col++) {
3258 FORC3 smrow[4][col][c] =
3259 (pix[c-8]+pix[c-4]+pix[c]+pix[c+4]+pix[c+8]+2) >> 2;
3263 pix = image[row*width+2];
3264 for (col=2; col < width-2; col++) {
3265 for (total[3]=375, sum=60, c=0; c < 3; c++) {
3266 for (total[c]=i=0; i < 5; i++)
3267 total[c] += smrow[i][col][c];
3268 total[3] += total[c];
3271 if (sum < 0) sum = 0;
3272 j = total[3] > 375 ? (sum << 16) / total[3] : sum * 174;
3273 FORC3 pix[c] += foveon_apply_curve (curve[6],
3274 ((j*total[c] + 0x8000) >> 16) - pix[c]);
3279 /* Transform the image to a different colorspace */
3280 for (pix=image[0]; pix < image[height*width]; pix+=4) {
3281 FORC3 pix[c] -= foveon_apply_curve (curve[c], pix[c]);
3282 sum = (pix[0]+pix[1]+pix[1]+pix[2]) >> 2;
3283 FORC3 pix[c] -= foveon_apply_curve (curve[c], pix[c]-sum);
3285 for (dsum=i=0; i < 3; i++)
3286 dsum += trans[c][i] * pix[i];
3287 if (dsum < 0) dsum = 0;
3288 if (dsum > 24000) dsum = 24000;
3289 ipix[c] = dsum + 0.5;
3291 FORC3 pix[c] = ipix[c];
3294 /* Smooth the image bottom-to-top and save at 1/4 scale */
3295 shrink = (short (*)[3]) calloc ((width/4) * (height/4), sizeof *shrink);
3296 merror (shrink, "foveon_interpolate()");
3297 for (row = height/4; row--; )
3298 for (col=0; col < width/4; col++) {
3299 ipix[0] = ipix[1] = ipix[2] = 0;
3300 for (i=0; i < 4; i++)
3301 for (j=0; j < 4; j++)
3302 FORC3 ipix[c] += image[(row*4+i)*width+col*4+j][c];
3304 if (row+2 > height/4)
3305 shrink[row*(width/4)+col][c] = ipix[c] >> 4;
3307 shrink[row*(width/4)+col][c] =
3308 (shrink[(row+1)*(width/4)+col][c]*1840 + ipix[c]*141 + 2048) >> 12;
3310 /* From the 1/4-scale image, smooth right-to-left */
3311 for (row=0; row < (height & ~3); row++) {
3312 ipix[0] = ipix[1] = ipix[2] = 0;
3314 for (col = width & ~3 ; col--; )
3315 FORC3 smrow[0][col][c] = ipix[c] =
3316 (shrink[(row/4)*(width/4)+col/4][c]*1485 + ipix[c]*6707 + 4096) >> 13;
3318 /* Then smooth left-to-right */
3319 ipix[0] = ipix[1] = ipix[2] = 0;
3320 for (col=0; col < (width & ~3); col++)
3321 FORC3 smrow[1][col][c] = ipix[c] =
3322 (smrow[0][col][c]*1485 + ipix[c]*6707 + 4096) >> 13;
3324 /* Smooth top-to-bottom */
3326 memcpy (smrow[2], smrow[1], sizeof **smrow * width);
3328 for (col=0; col < (width & ~3); col++)
3329 FORC3 smrow[2][col][c] =
3330 (smrow[2][col][c]*6707 + smrow[1][col][c]*1485 + 4096) >> 13;
3332 /* Adjust the chroma toward the smooth values */
3333 for (col=0; col < (width & ~3); col++) {
3334 for (i=j=30, c=0; c < 3; c++) {
3335 i += smrow[2][col][c];
3336 j += image[row*width+col][c];
3339 for (sum=c=0; c < 3; c++) {
3340 ipix[c] = foveon_apply_curve (curve[c+3],
3341 ((smrow[2][col][c] * j + 0x8000) >> 16) - image[row*width+col][c]);
3346 i = image[row*width+col][c] + ipix[c] - sum;
3348 image[row*width+col][c] = i;
3354 for (i=0; i < 8; i++)
3357 /* Trim off the black border */
3358 active[1] -= keep[1];
3360 i = active[2] - active[0];
3361 for (row=0; row < active[3]-active[1]; row++)
3362 memcpy (image[row*i], image[(row+active[1])*width+active[0]],
3369 /* RESTRICTED code ends here */
3371 void CLASS crop_masked_pixels()
3374 unsigned r, c, m, mblack[8], zero, val;
3376 if (load_raw == &CLASS phase_one_load_raw ||
3377 load_raw == &CLASS phase_one_load_raw_c)
3378 phase_one_correct();
3380 for (row=0; row < raw_height-top_margin*2; row++) {
3381 for (col=0; col < fuji_width << !fuji_layout; col++) {
3383 r = fuji_width - 1 - col + (row >> 1);
3384 c = col + ((row+1) >> 1);
3386 r = fuji_width - 1 + row - (col >> 1);
3387 c = row + ((col+1) >> 1);
3389 if (r < height && c < width)
3390 BAYER(r,c) = RAW(row+top_margin,col+left_margin);
3394 for (row=0; row < height; row++)
3395 for (col=0; col < width; col++)
3396 BAYER2(row,col) = RAW(row+top_margin,col+left_margin);
3398 if (mask[0][3]) goto mask_set;
3399 if (load_raw == &CLASS canon_load_raw ||
3400 load_raw == &CLASS lossless_jpeg_load_raw) {
3401 mask[0][1] = mask[1][1] = 2;
3405 if (load_raw == &CLASS canon_600_load_raw ||
3406 load_raw == &CLASS sony_load_raw ||
3407 (load_raw == &CLASS eight_bit_load_raw && strncmp(model,"DC2",3)) ||
3408 load_raw == &CLASS kodak_262_load_raw ||
3409 (load_raw == &CLASS packed_load_raw && (load_flags & 32))) {
3411 mask[0][0] = mask[1][0] = top_margin;
3412 mask[0][2] = mask[1][2] = top_margin+height;
3413 mask[0][3] += left_margin;
3414 mask[1][1] += left_margin+width;
3415 mask[1][3] += raw_width;
3417 if (load_raw == &CLASS nokia_load_raw) {
3418 mask[0][2] = top_margin;
3422 memset (mblack, 0, sizeof mblack);
3423 for (zero=m=0; m < 8; m++)
3424 for (row=mask[m][0]; row < mask[m][2]; row++)
3425 for (col=mask[m][1]; col < mask[m][3]; col++) {
3426 c = FC(row-top_margin,col-left_margin);
3427 mblack[c] += val = RAW(row,col);
3431 if (load_raw == &CLASS canon_600_load_raw && width < raw_width) {
3432 black = (mblack[0]+mblack[1]+mblack[2]+mblack[3]) /
3433 (mblack[4]+mblack[5]+mblack[6]+mblack[7]) - 4;
3434 canon_600_correct();
3435 } else if (zero < mblack[4] && mblack[5] && mblack[6] && mblack[7])
3436 FORC4 cblack[c] = mblack[c] / mblack[4+c];
3439 void CLASS remove_zeroes()
3441 unsigned row, col, tot, n, r, c;
3443 for (row=0; row < height; row++)
3444 for (col=0; col < width; col++)
3445 if (BAYER(row,col) == 0) {
3447 for (r = row-2; r <= row+2; r++)
3448 for (c = col-2; c <= col+2; c++)
3449 if (r < height && c < width &&
3450 FC(r,c) == FC(row,col) && BAYER(r,c))
3451 tot += (n++,BAYER(r,c));
3452 if (n) BAYER(row,col) = tot/n;
3457 Seach from the current directory up to the root looking for
3458 a ".badpixels" file, and fix those pixels now.
3460 void CLASS bad_pixels (const char *cfname)
3463 char *fname, *cp, line[128];
3464 int len, time, row, col, r, c, rad, tot, n, fixed=0;
3466 if (!filters) return;
3468 fp = fopen (cfname, "r");
3470 for (len=32 ; ; len *= 2) {
3471 fname = (char *) malloc (len);
3473 if (getcwd (fname, len-16)) break;
3475 if (errno != ERANGE) return;
3477 #if defined(WIN32) || defined(DJGPP)
3478 if (fname[1] == ':')
3479 memmove (fname, fname+2, len-2);
3480 for (cp=fname; *cp; cp++)
3481 if (*cp == '\\') *cp = '/';
3483 cp = fname + strlen(fname);
3484 if (cp[-1] == '/') cp--;
3485 while (*fname == '/') {
3486 strcpy (cp, "/.badpixels");
3487 if ((fp = fopen (fname, "r"))) break;
3488 if (cp == fname) break;
3489 while (*--cp != '/');
3494 while (fgets (line, 128, fp)) {
3495 cp = strchr (line, '#');
3497 if (sscanf (line, "%d %d %d", &col, &row, &time) != 3) continue;
3498 if ((unsigned) col >= width || (unsigned) row >= height) continue;
3499 if (time > timestamp) continue;
3500 for (tot=n=0, rad=1; rad < 3 && n==0; rad++)
3501 for (r = row-rad; r <= row+rad; r++)
3502 for (c = col-rad; c <= col+rad; c++)
3503 if ((unsigned) r < height && (unsigned) c < width &&
3504 (r != row || c != col) && fcol(r,c) == fcol(row,col)) {
3508 BAYER2(row,col) = tot/n;
3511 fprintf (stderr,_("Fixed dead pixels at:"));
3512 fprintf (stderr, " %d,%d", col, row);
3515 if (fixed) fputc ('\n', stderr);
3519 void CLASS subtract (const char *fname)
3522 int dim[3]={0,0,0}, comment=0, number=0, error=0, nd=0, c, row, col;
3525 if (!(fp = fopen (fname, "rb"))) {
3526 perror (fname); return;
3528 if (fgetc(fp) != 'P' || fgetc(fp) != '5') error = 1;
3529 while (!error && nd < 3 && (c = fgetc(fp)) != EOF) {
3530 if (c == '#') comment = 1;
3531 if (c == '\n') comment = 0;
3532 if (comment) continue;
3533 if (isdigit(c)) number = 1;
3535 if (isdigit(c)) dim[nd] = dim[nd]*10 + c -'0';
3536 else if (isspace(c)) {
3541 if (error || nd < 3) {
3542 fprintf (stderr,_("%s is not a valid PGM file!\n"), fname);
3543 fclose (fp); return;
3544 } else if (dim[0] != width || dim[1] != height || dim[2] != 65535) {
3545 fprintf (stderr,_("%s has the wrong dimensions!\n"), fname);
3546 fclose (fp); return;
3548 pixel = (ushort *) calloc (width, sizeof *pixel);
3549 merror (pixel, "subtract()");
3550 for (row=0; row < height; row++) {
3551 fread (pixel, 2, width, fp);
3552 for (col=0; col < width; col++)
3553 BAYER(row,col) = MAX (BAYER(row,col) - ntohs(pixel[col]), 0);
3557 memset (cblack, 0, sizeof cblack);
3561 void CLASS gamma_curve (double pwr, double ts, int mode, int imax)
3564 double g[6], bnd[2]={0,0}, r;
3568 g[2] = g[3] = g[4] = 0;
3570 if (g[1] && (g[1]-1)*(g[0]-1) <= 0) {
3571 for (i=0; i < 48; i++) {
3572 g[2] = (bnd[0] + bnd[1])/2;
3573 if (g[0]) bnd[(pow(g[2]/g[1],-g[0]) - 1)/g[0] - 1/g[2] > -1] = g[2];
3574 else bnd[g[2]/exp(1-1/g[2]) < g[1]] = g[2];
3577 if (g[0]) g[4] = g[2] * (1/g[0] - 1);
3579 if (g[0]) g[5] = 1 / (g[1]*SQR(g[3])/2 - g[4]*(1 - g[3]) +
3580 (1 - pow(g[3],1+g[0]))*(1 + g[4])/(1 + g[0])) - 1;
3581 else g[5] = 1 / (g[1]*SQR(g[3])/2 + 1
3582 - g[2] - g[3] - g[2]*g[3]*(log(g[3]) - 1)) - 1;
3584 memcpy (gamm, g, sizeof gamm);
3587 for (i=0; i < 0x10000; i++) {
3589 if ((r = (double) i / imax) < 1)
3590 curve[i] = 0x10000 * ( mode
3591 ? (r < g[3] ? r*g[1] : (g[0] ? pow( r,g[0])*(1+g[4])-g[4] : log(r)*g[2]+1))
3592 : (r < g[2] ? r/g[1] : (g[0] ? pow((r+g[4])/(1+g[4]),1/g[0]) : exp((r-1)/g[2]))));
3596 void CLASS pseudoinverse (double (*in)[3], double (*out)[3], int size)
3598 double work[3][6], num;
3601 for (i=0; i < 3; i++) {
3602 for (j=0; j < 6; j++)
3603 work[i][j] = j == i+3;
3604 for (j=0; j < 3; j++)
3605 for (k=0; k < size; k++)
3606 work[i][j] += in[k][i] * in[k][j];
3608 for (i=0; i < 3; i++) {
3610 for (j=0; j < 6; j++)
3612 for (k=0; k < 3; k++) {
3615 for (j=0; j < 6; j++)
3616 work[k][j] -= work[i][j] * num;
3619 for (i=0; i < size; i++)
3620 for (j=0; j < 3; j++)
3621 for (out[i][j]=k=0; k < 3; k++)
3622 out[i][j] += work[j][k+3] * in[i][k];
3625 void CLASS cam_xyz_coeff (double cam_xyz[4][3])
3627 double cam_rgb[4][3], inverse[4][3], num;
3630 for (i=0; i < colors; i++) /* Multiply out XYZ colorspace */
3631 for (j=0; j < 3; j++)
3632 for (cam_rgb[i][j] = k=0; k < 3; k++)
3633 cam_rgb[i][j] += cam_xyz[i][k] * xyz_rgb[k][j];
3635 for (i=0; i < colors; i++) { /* Normalize cam_rgb so that */
3636 for (num=j=0; j < 3; j++) /* cam_rgb * (1,1,1) is (1,1,1,1) */
3637 num += cam_rgb[i][j];
3638 for (j=0; j < 3; j++)
3639 cam_rgb[i][j] /= num;
3640 pre_mul[i] = 1 / num;
3642 pseudoinverse (cam_rgb, inverse, colors);
3643 for (raw_color = i=0; i < 3; i++)
3644 for (j=0; j < colors; j++)
3645 rgb_cam[i][j] = inverse[j][i];
3649 void CLASS colorcheck()
3652 // Coordinates of the GretagMacbeth ColorChecker squares
3653 // width, height, 1st_column, 1st_row
3654 int cut[NSQ][4]; // you must set these
3655 // ColorChecker Chart under 6500-kelvin illumination
3656 static const double gmb_xyY[NSQ][3] = {
3657 { 0.400, 0.350, 10.1 }, // Dark Skin
3658 { 0.377, 0.345, 35.8 }, // Light Skin
3659 { 0.247, 0.251, 19.3 }, // Blue Sky
3660 { 0.337, 0.422, 13.3 }, // Foliage
3661 { 0.265, 0.240, 24.3 }, // Blue Flower
3662 { 0.261, 0.343, 43.1 }, // Bluish Green
3663 { 0.506, 0.407, 30.1 }, // Orange
3664 { 0.211, 0.175, 12.0 }, // Purplish Blue
3665 { 0.453, 0.306, 19.8 }, // Moderate Red
3666 { 0.285, 0.202, 6.6 }, // Purple
3667 { 0.380, 0.489, 44.3 }, // Yellow Green
3668 { 0.473, 0.438, 43.1 }, // Orange Yellow
3669 { 0.187, 0.129, 6.1 }, // Blue
3670 { 0.305, 0.478, 23.4 }, // Green
3671 { 0.539, 0.313, 12.0 }, // Red
3672 { 0.448, 0.470, 59.1 }, // Yellow
3673 { 0.364, 0.233, 19.8 }, // Magenta
3674 { 0.196, 0.252, 19.8 }, // Cyan
3675 { 0.310, 0.316, 90.0 }, // White
3676 { 0.310, 0.316, 59.1 }, // Neutral 8
3677 { 0.310, 0.316, 36.2 }, // Neutral 6.5
3678 { 0.310, 0.316, 19.8 }, // Neutral 5
3679 { 0.310, 0.316, 9.0 }, // Neutral 3.5
3680 { 0.310, 0.316, 3.1 } }; // Black
3681 double gmb_cam[NSQ][4], gmb_xyz[NSQ][3];
3682 double inverse[NSQ][3], cam_xyz[4][3], num;
3683 int c, i, j, k, sq, row, col, count[4];
3685 memset (gmb_cam, 0, sizeof gmb_cam);
3686 for (sq=0; sq < NSQ; sq++) {
3688 for (row=cut[sq][3]; row < cut[sq][3]+cut[sq][1]; row++)
3689 for (col=cut[sq][2]; col < cut[sq][2]+cut[sq][0]; col++) {
3691 if (c >= colors) c -= 2;
3692 gmb_cam[sq][c] += BAYER(row,col);
3695 FORCC gmb_cam[sq][c] = gmb_cam[sq][c]/count[c] - black;
3696 gmb_xyz[sq][0] = gmb_xyY[sq][2] * gmb_xyY[sq][0] / gmb_xyY[sq][1];
3697 gmb_xyz[sq][1] = gmb_xyY[sq][2];
3698 gmb_xyz[sq][2] = gmb_xyY[sq][2] *
3699 (1 - gmb_xyY[sq][0] - gmb_xyY[sq][1]) / gmb_xyY[sq][1];
3701 pseudoinverse (gmb_xyz, inverse, NSQ);
3702 for (i=0; i < colors; i++)
3703 for (j=0; j < 3; j++)
3704 for (cam_xyz[i][j] = k=0; k < NSQ; k++)
3705 cam_xyz[i][j] += gmb_cam[k][i] * inverse[k][j];
3706 cam_xyz_coeff (cam_xyz);
3708 printf (" { \"%s %s\", %d,\n\t{", make, model, black);
3709 num = 10000 / (cam_xyz[1][0] + cam_xyz[1][1] + cam_xyz[1][2]);
3710 FORCC for (j=0; j < 3; j++)
3711 printf ("%c%d", (c | j) ? ',':' ', (int) (cam_xyz[c][j] * num + 0.5));
3718 void CLASS hat_transform (float *temp, float *base, int st, int size, int sc)
3721 for (i=0; i < sc; i++)
3722 temp[i] = 2*base[st*i] + base[st*(sc-i)] + base[st*(i+sc)];
3723 for (; i+sc < size; i++)
3724 temp[i] = 2*base[st*i] + base[st*(i-sc)] + base[st*(i+sc)];
3725 for (; i < size; i++)
3726 temp[i] = 2*base[st*i] + base[st*(i-sc)] + base[st*(2*size-2-(i+sc))];
3729 void CLASS wavelet_denoise()
3731 float *fimg=0, *temp, thold, mul[2], avg, diff;
3732 int scale=1, size, lev, hpass, lpass, row, col, nc, c, i, wlast, blk[2];
3734 static const float noise[] =
3735 { 0.8002,0.2735,0.1202,0.0585,0.0291,0.0152,0.0080,0.0044 };
3737 if (verbose) fprintf (stderr,_("Wavelet denoising...\n"));
3739 while (maximum << scale < 0x10000) scale++;
3740 maximum <<= --scale;
3742 FORC4 cblack[c] <<= scale;
3743 if ((size = iheight*iwidth) < 0x15550000)
3744 fimg = (float *) malloc ((size*3 + iheight + iwidth) * sizeof *fimg);
3745 merror (fimg, "wavelet_denoise()");
3746 temp = fimg + size*3;
3747 if ((nc = colors) == 3 && filters) nc++;
3748 FORC(nc) { /* denoise R,G1,B,G3 individually */
3749 for (i=0; i < size; i++)
3750 fimg[i] = 256 * sqrt(image[i][c] << scale);
3751 for (hpass=lev=0; lev < 5; lev++) {
3752 lpass = size*((lev & 1)+1);
3753 for (row=0; row < iheight; row++) {
3754 hat_transform (temp, fimg+hpass+row*iwidth, 1, iwidth, 1 << lev);
3755 for (col=0; col < iwidth; col++)
3756 fimg[lpass + row*iwidth + col] = temp[col] * 0.25;
3758 for (col=0; col < iwidth; col++) {
3759 hat_transform (temp, fimg+lpass+col, iwidth, iheight, 1 << lev);
3760 for (row=0; row < iheight; row++)
3761 fimg[lpass + row*iwidth + col] = temp[row] * 0.25;
3763 thold = threshold * noise[lev];
3764 for (i=0; i < size; i++) {
3765 fimg[hpass+i] -= fimg[lpass+i];
3766 if (fimg[hpass+i] < -thold) fimg[hpass+i] += thold;
3767 else if (fimg[hpass+i] > thold) fimg[hpass+i] -= thold;
3768 else fimg[hpass+i] = 0;
3769 if (hpass) fimg[i] += fimg[hpass+i];
3773 for (i=0; i < size; i++)
3774 image[i][c] = CLIP(SQR(fimg[i]+fimg[lpass+i])/0x10000);
3776 if (filters && colors == 3) { /* pull G1 and G3 closer together */
3777 for (row=0; row < 2; row++) {
3778 mul[row] = 0.125 * pre_mul[FC(row+1,0) | 1] / pre_mul[FC(row,0) | 1];
3779 blk[row] = cblack[FC(row,0) | 1];
3781 for (i=0; i < 4; i++)
3782 window[i] = (ushort *) fimg + width*i;
3783 for (wlast=-1, row=1; row < height-1; row++) {
3784 while (wlast < row+1) {
3785 for (wlast++, i=0; i < 4; i++)
3786 window[(i+3) & 3] = window[i];
3787 for (col = FC(wlast,1) & 1; col < width; col+=2)
3788 window[2][col] = BAYER(wlast,col);
3790 thold = threshold/512;
3791 for (col = (FC(row,0) & 1)+1; col < width-1; col+=2) {
3792 avg = ( window[0][col-1] + window[0][col+1] +
3793 window[2][col-1] + window[2][col+1] - blk[~row & 1]*4 )
3794 * mul[row & 1] + (window[1][col] + blk[row & 1]) * 0.5;
3795 avg = avg < 0 ? 0 : sqrt(avg);
3796 diff = sqrt(BAYER(row,col)) - avg;
3797 if (diff < -thold) diff += thold;
3798 else if (diff > thold) diff -= thold;
3800 BAYER(row,col) = CLIP(SQR(avg+diff) + 0.5);
3807 void CLASS scale_colors()
3809 unsigned bottom, right, size, row, col, ur, uc, i, x, y, c, sum[8];
3811 double dsum[8], dmin, dmax;
3812 float scale_mul[4], fr, fc;
3813 ushort *img=0, *pix;
3816 memcpy (pre_mul, user_mul, sizeof pre_mul);
3817 if (use_auto_wb || (use_camera_wb && cam_mul[0] == -1)) {
3818 memset (dsum, 0, sizeof dsum);
3819 bottom = MIN (greybox[1]+greybox[3], height);
3820 right = MIN (greybox[0]+greybox[2], width);
3821 for (row=greybox[1]; row < bottom; row += 8)
3822 for (col=greybox[0]; col < right; col += 8) {
3823 memset (sum, 0, sizeof sum);
3824 for (y=row; y < row+8 && y < bottom; y++)
3825 for (x=col; x < col+8 && x < right; x++)
3831 val = image[y*width+x][c];
3832 if (val > maximum-25) goto skip_block;
3833 if ((val -= cblack[c]) < 0) val = 0;
3838 FORC(8) dsum[c] += sum[c];
3841 FORC4 if (dsum[c]) pre_mul[c] = dsum[c+4] / dsum[c];
3843 if (use_camera_wb && cam_mul[0] != -1) {
3844 memset (sum, 0, sizeof sum);
3845 for (row=0; row < 8; row++)
3846 for (col=0; col < 8; col++) {
3848 if ((val = white[row][col] - cblack[c]) > 0)
3852 if (sum[0] && sum[1] && sum[2] && sum[3])
3853 FORC4 pre_mul[c] = (float) sum[c+4] / sum[c];
3854 else if (cam_mul[0] && cam_mul[2])
3855 memcpy (pre_mul, cam_mul, sizeof pre_mul);
3857 fprintf (stderr,_("%s: Cannot use camera white balance.\n"), ifname);
3859 if (pre_mul[3] == 0) pre_mul[3] = colors < 4 ? pre_mul[1] : 1;
3862 if (threshold) wavelet_denoise();
3864 for (dmin=DBL_MAX, dmax=c=0; c < 4; c++) {
3865 if (dmin > pre_mul[c])
3867 if (dmax < pre_mul[c])
3870 if (!highlight) dmax = dmin;
3871 FORC4 scale_mul[c] = (pre_mul[c] /= dmax) * 65535.0 / maximum;
3874 _("Scaling with darkness %d, saturation %d, and\nmultipliers"), dark, sat);
3875 FORC4 fprintf (stderr, " %f", pre_mul[c]);
3876 fputc ('\n', stderr);
3878 size = iheight*iwidth;
3879 for (i=0; i < size*4; i++) {
3882 val -= cblack[i & 3];
3883 val *= scale_mul[i & 3];
3884 image[0][i] = CLIP(val);
3886 if ((aber[0] != 1 || aber[2] != 1) && colors == 3) {
3888 fprintf (stderr,_("Correcting chromatic aberration...\n"));
3889 for (c=0; c < 4; c+=2) {
3890 if (aber[c] == 1) continue;
3891 img = (ushort *) malloc (size * sizeof *img);
3892 merror (img, "scale_colors()");
3893 for (i=0; i < size; i++)
3894 img[i] = image[i][c];
3895 for (row=0; row < iheight; row++) {
3896 ur = fr = (row - iheight*0.5) * aber[c] + iheight*0.5;
3897 if (ur > iheight-2) continue;
3899 for (col=0; col < iwidth; col++) {
3900 uc = fc = (col - iwidth*0.5) * aber[c] + iwidth*0.5;
3901 if (uc > iwidth-2) continue;
3903 pix = img + ur*iwidth + uc;
3904 image[row*iwidth+col][c] =
3905 (pix[ 0]*(1-fc) + pix[ 1]*fc) * (1-fr) +
3906 (pix[iwidth]*(1-fc) + pix[iwidth+1]*fc) * fr;
3914 void CLASS pre_interpolate()
3924 img = (ushort (*)[4]) calloc (height*width, sizeof *img);
3925 merror (img, "pre_interpolate()");
3926 for (row=0; row < height; row++)
3927 for (col=0; col < width; col++) {
3929 img[row*width+col][c] = image[(row >> 1)*iwidth+(col >> 1)][c];
3936 if (filters > 1000 && colors == 3) {
3937 if (four_color_rgb && colors++)
3938 mix_green = !half_size;
3940 for (row = FC(1,0) >> 1; row < height; row+=2)
3941 for (col = FC(row,1) & 1; col < width; col+=2)
3942 image[row*width+col][1] = image[row*width+col][3];
3943 filters &= ~((filters & 0x55555555) << 1);
3946 if (half_size) filters = 0;
3949 void CLASS border_interpolate (int border)
3951 unsigned row, col, y, x, f, c, sum[8];
3953 for (row=0; row < height; row++)
3954 for (col=0; col < width; col++) {
3955 if (col==border && row >= border && row < height-border)
3957 memset (sum, 0, sizeof sum);
3958 for (y=row-1; y != row+2; y++)
3959 for (x=col-1; x != col+2; x++)
3960 if (y < height && x < width) {
3962 sum[f] += image[y*width+x][f];
3966 FORCC if (c != f && sum[c+4])
3967 image[row*width+col][c] = sum[c] / sum[c+4];
3971 void CLASS lin_interpolate()
3973 int code[16][16][32], size=16, *ip, sum[4];
3974 int f, c, i, x, y, row, col, shift, color;
3977 if (verbose) fprintf (stderr,_("Bilinear interpolation...\n"));
3978 if (filters == 2) size = 6;
3979 border_interpolate(1);
3980 for (row=0; row < size; row++)
3981 for (col=0; col < size; col++) {
3982 ip = code[row][col]+1;
3984 memset (sum, 0, sizeof sum);
3985 for (y=-1; y <= 1; y++)
3986 for (x=-1; x <= 1; x++) {
3987 shift = (y==0) + (x==0);
3988 color = fcol(row+y,col+x);
3989 if (color == f) continue;
3990 *ip++ = (width*y + x)*4 + color;
3993 sum[color] += 1 << shift;
3995 code[row][col][0] = (ip - code[row][col]) / 3;
3999 *ip++ = 256 / sum[c];
4002 for (row=1; row < height-1; row++)
4003 for (col=1; col < width-1; col++) {
4004 pix = image[row*width+col];
4005 ip = code[row % size][col % size];
4006 memset (sum, 0, sizeof sum);
4007 for (i=*ip++; i--; ip+=3)
4008 sum[ip[2]] += pix[ip[0]] << ip[1];
4009 for (i=colors; --i; ip+=2)
4010 pix[ip[0]] = sum[ip[0]] * ip[1] >> 8;
4015 This algorithm is officially called:
4017 "Interpolation using a Threshold-based variable number of gradients"
4019 described in http://scien.stanford.edu/pages/labsite/1999/psych221/projects/99/tingchen/algodep/vargra.html
4021 I've extended the basic idea to work with non-Bayer filter arrays.
4022 Gradients are numbered clockwise from NW=0 to W=7.
4024 void CLASS vng_interpolate()
4026 static const signed char *cp, terms[] = {
4027 -2,-2,+0,-1,0,0x01, -2,-2,+0,+0,1,0x01, -2,-1,-1,+0,0,0x01,
4028 -2,-1,+0,-1,0,0x02, -2,-1,+0,+0,0,0x03, -2,-1,+0,+1,1,0x01,
4029 -2,+0,+0,-1,0,0x06, -2,+0,+0,+0,1,0x02, -2,+0,+0,+1,0,0x03,
4030 -2,+1,-1,+0,0,0x04, -2,+1,+0,-1,1,0x04, -2,+1,+0,+0,0,0x06,
4031 -2,+1,+0,+1,0,0x02, -2,+2,+0,+0,1,0x04, -2,+2,+0,+1,0,0x04,
4032 -1,-2,-1,+0,0,0x80, -1,-2,+0,-1,0,0x01, -1,-2,+1,-1,0,0x01,
4033 -1,-2,+1,+0,1,0x01, -1,-1,-1,+1,0,0x88, -1,-1,+1,-2,0,0x40,
4034 -1,-1,+1,-1,0,0x22, -1,-1,+1,+0,0,0x33, -1,-1,+1,+1,1,0x11,
4035 -1,+0,-1,+2,0,0x08, -1,+0,+0,-1,0,0x44, -1,+0,+0,+1,0,0x11,
4036 -1,+0,+1,-2,1,0x40, -1,+0,+1,-1,0,0x66, -1,+0,+1,+0,1,0x22,
4037 -1,+0,+1,+1,0,0x33, -1,+0,+1,+2,1,0x10, -1,+1,+1,-1,1,0x44,
4038 -1,+1,+1,+0,0,0x66, -1,+1,+1,+1,0,0x22, -1,+1,+1,+2,0,0x10,
4039 -1,+2,+0,+1,0,0x04, -1,+2,+1,+0,1,0x04, -1,+2,+1,+1,0,0x04,
4040 +0,-2,+0,+0,1,0x80, +0,-1,+0,+1,1,0x88, +0,-1,+1,-2,0,0x40,
4041 +0,-1,+1,+0,0,0x11, +0,-1,+2,-2,0,0x40, +0,-1,+2,-1,0,0x20,
4042 +0,-1,+2,+0,0,0x30, +0,-1,+2,+1,1,0x10, +0,+0,+0,+2,1,0x08,
4043 +0,+0,+2,-2,1,0x40, +0,+0,+2,-1,0,0x60, +0,+0,+2,+0,1,0x20,
4044 +0,+0,+2,+1,0,0x30, +0,+0,+2,+2,1,0x10, +0,+1,+1,+0,0,0x44,
4045 +0,+1,+1,+2,0,0x10, +0,+1,+2,-1,1,0x40, +0,+1,+2,+0,0,0x60,
4046 +0,+1,+2,+1,0,0x20, +0,+1,+2,+2,0,0x10, +1,-2,+1,+0,0,0x80,
4047 +1,-1,+1,+1,0,0x88, +1,+0,+1,+2,0,0x08, +1,+0,+2,-1,0,0x40,
4049 }, chood[] = { -1,-1, -1,0, -1,+1, 0,+1, +1,+1, +1,0, +1,-1, 0,-1 };
4050 ushort (*brow[5])[4], *pix;
4051 int prow=8, pcol=2, *ip, *code[16][16], gval[8], gmin, gmax, sum[4];
4052 int row, col, x, y, x1, x2, y1, y2, t, weight, grads, color, diag;
4053 int g, diff, thold, num, c;
4056 if (verbose) fprintf (stderr,_("VNG interpolation...\n"));
4058 if (filters == 1) prow = pcol = 16;
4059 if (filters == 2) prow = pcol = 6;
4060 ip = (int *) calloc (prow*pcol, 1280);
4061 merror (ip, "vng_interpolate()");
4062 for (row=0; row < prow; row++) /* Precalculate for VNG */
4063 for (col=0; col < pcol; col++) {
4064 code[row][col] = ip;
4065 for (cp=terms, t=0; t < 64; t++) {
4066 y1 = *cp++; x1 = *cp++;
4067 y2 = *cp++; x2 = *cp++;
4070 color = fcol(row+y1,col+x1);
4071 if (fcol(row+y2,col+x2) != color) continue;
4072 diag = (fcol(row,col+1) == color && fcol(row+1,col) == color) ? 2:1;
4073 if (abs(y1-y2) == diag && abs(x1-x2) == diag) continue;
4074 *ip++ = (y1*width + x1)*4 + color;
4075 *ip++ = (y2*width + x2)*4 + color;
4077 for (g=0; g < 8; g++)
4078 if (grads & 1<<g) *ip++ = g;
4082 for (cp=chood, g=0; g < 8; g++) {
4083 y = *cp++; x = *cp++;
4084 *ip++ = (y*width + x) * 4;
4085 color = fcol(row,col);
4086 if (fcol(row+y,col+x) != color && fcol(row+y*2,col+x*2) == color)
4087 *ip++ = (y*width + x) * 8 + color;
4092 brow[4] = (ushort (*)[4]) calloc (width*3, sizeof **brow);
4093 merror (brow[4], "vng_interpolate()");
4094 for (row=0; row < 3; row++)
4095 brow[row] = brow[4] + row*width;
4096 for (row=2; row < height-2; row++) { /* Do VNG interpolation */
4097 for (col=2; col < width-2; col++) {
4098 pix = image[row*width+col];
4099 ip = code[row % prow][col % pcol];
4100 memset (gval, 0, sizeof gval);
4101 while ((g = ip[0]) != INT_MAX) { /* Calculate gradients */
4102 diff = ABS(pix[g] - pix[ip[1]]) << ip[2];
4103 gval[ip[3]] += diff;
4105 if ((g = ip[-1]) == -1) continue;
4107 while ((g = *ip++) != -1)
4111 gmin = gmax = gval[0]; /* Choose a threshold */
4112 for (g=1; g < 8; g++) {
4113 if (gmin > gval[g]) gmin = gval[g];
4114 if (gmax < gval[g]) gmax = gval[g];
4117 memcpy (brow[2][col], pix, sizeof *image);
4120 thold = gmin + (gmax >> 1);
4121 memset (sum, 0, sizeof sum);
4122 color = fcol(row,col);
4123 for (num=g=0; g < 8; g++,ip+=2) { /* Average the neighbors */
4124 if (gval[g] <= thold) {
4126 if (c == color && ip[1])
4127 sum[c] += (pix[c] + pix[ip[1]]) >> 1;
4129 sum[c] += pix[ip[0] + c];
4133 FORCC { /* Save to buffer */
4136 t += (sum[c] - sum[color]) / num;
4137 brow[2][col][c] = CLIP(t);
4140 if (row > 3) /* Write buffer to image */
4141 memcpy (image[(row-2)*width+2], brow[0]+2, (width-4)*sizeof *image);
4142 for (g=0; g < 4; g++)
4143 brow[(g-1) & 3] = brow[g];
4145 memcpy (image[(row-2)*width+2], brow[0]+2, (width-4)*sizeof *image);
4146 memcpy (image[(row-1)*width+2], brow[1]+2, (width-4)*sizeof *image);
4152 Patterned Pixel Grouping Interpolation by Alain Desbiolles
4154 void CLASS ppg_interpolate()
4156 int dir[5] = { 1, width, -1, -width, 1 };
4157 int row, col, diff[2], guess[2], c, d, i;
4160 border_interpolate(3);
4161 if (verbose) fprintf (stderr,_("PPG interpolation...\n"));
4163 /* Fill in the green layer with gradients and pattern recognition: */
4164 for (row=3; row < height-3; row++)
4165 for (col=3+(FC(row,3) & 1), c=FC(row,col); col < width-3; col+=2) {
4166 pix = image + row*width+col;
4167 for (i=0; (d=dir[i]) > 0; i++) {
4168 guess[i] = (pix[-d][1] + pix[0][c] + pix[d][1]) * 2
4169 - pix[-2*d][c] - pix[2*d][c];
4170 diff[i] = ( ABS(pix[-2*d][c] - pix[ 0][c]) +
4171 ABS(pix[ 2*d][c] - pix[ 0][c]) +
4172 ABS(pix[ -d][1] - pix[ d][1]) ) * 3 +
4173 ( ABS(pix[ 3*d][1] - pix[ d][1]) +
4174 ABS(pix[-3*d][1] - pix[-d][1]) ) * 2;
4176 d = dir[i = diff[0] > diff[1]];
4177 pix[0][1] = ULIM(guess[i] >> 2, pix[d][1], pix[-d][1]);
4179 /* Calculate red and blue for each green pixel: */
4180 for (row=1; row < height-1; row++)
4181 for (col=1+(FC(row,2) & 1), c=FC(row,col+1); col < width-1; col+=2) {
4182 pix = image + row*width+col;
4183 for (i=0; (d=dir[i]) > 0; c=2-c, i++)
4184 pix[0][c] = CLIP((pix[-d][c] + pix[d][c] + 2*pix[0][1]
4185 - pix[-d][1] - pix[d][1]) >> 1);
4187 /* Calculate blue for red pixels and vice versa: */
4188 for (row=1; row < height-1; row++)
4189 for (col=1+(FC(row,1) & 1), c=2-FC(row,col); col < width-1; col+=2) {
4190 pix = image + row*width+col;
4191 for (i=0; (d=dir[i]+dir[i+1]) > 0; i++) {
4192 diff[i] = ABS(pix[-d][c] - pix[d][c]) +
4193 ABS(pix[-d][1] - pix[0][1]) +
4194 ABS(pix[ d][1] - pix[0][1]);
4195 guess[i] = pix[-d][c] + pix[d][c] + 2*pix[0][1]
4196 - pix[-d][1] - pix[d][1];
4198 if (diff[0] != diff[1])
4199 pix[0][c] = CLIP(guess[diff[0] > diff[1]] >> 1);
4201 pix[0][c] = CLIP((guess[0]+guess[1]) >> 2);
4206 Adaptive Homogeneity-Directed interpolation is based on
4207 the work of Keigo Hirakawa, Thomas Parks, and Paul Lee.
4209 #define TS 256 /* Tile Size */
4211 void CLASS ahd_interpolate()
4213 int i, j, k, top, left, row, col, tr, tc, c, d, val, hm[2];
4214 ushort (*pix)[4], (*rix)[3];
4215 static const int dir[4] = { -1, 1, -TS, TS };
4216 unsigned ldiff[2][4], abdiff[2][4], leps, abeps;
4217 float r, cbrt[0x10000], xyz[3], xyz_cam[3][4];
4218 ushort (*rgb)[TS][TS][3];
4219 short (*lab)[TS][TS][3], (*lix)[3];
4220 char (*homo)[TS][TS], *buffer;
4222 if (verbose) fprintf (stderr,_("AHD interpolation...\n"));
4224 for (i=0; i < 0x10000; i++) {
4226 cbrt[i] = r > 0.008856 ? pow(r,1/3.0) : 7.787*r + 16/116.0;
4228 for (i=0; i < 3; i++)
4229 for (j=0; j < colors; j++)
4230 for (xyz_cam[i][j] = k=0; k < 3; k++)
4231 xyz_cam[i][j] += xyz_rgb[i][k] * rgb_cam[k][j] / d65_white[i];
4233 border_interpolate(5);
4234 buffer = (char *) malloc (26*TS*TS); /* 1664 kB */
4235 merror (buffer, "ahd_interpolate()");
4236 rgb = (ushort(*)[TS][TS][3]) buffer;
4237 lab = (short (*)[TS][TS][3])(buffer + 12*TS*TS);
4238 homo = (char (*)[TS][TS]) (buffer + 24*TS*TS);
4240 for (top=2; top < height-5; top += TS-6)
4241 for (left=2; left < width-5; left += TS-6) {
4243 /* Interpolate green horizontally and vertically: */
4244 for (row = top; row < top+TS && row < height-2; row++) {
4245 col = left + (FC(row,left) & 1);
4246 for (c = FC(row,col); col < left+TS && col < width-2; col+=2) {
4247 pix = image + row*width+col;
4248 val = ((pix[-1][1] + pix[0][c] + pix[1][1]) * 2
4249 - pix[-2][c] - pix[2][c]) >> 2;
4250 rgb[0][row-top][col-left][1] = ULIM(val,pix[-1][1],pix[1][1]);
4251 val = ((pix[-width][1] + pix[0][c] + pix[width][1]) * 2
4252 - pix[-2*width][c] - pix[2*width][c]) >> 2;
4253 rgb[1][row-top][col-left][1] = ULIM(val,pix[-width][1],pix[width][1]);
4256 /* Interpolate red and blue, and convert to CIELab: */
4257 for (d=0; d < 2; d++)
4258 for (row=top+1; row < top+TS-1 && row < height-3; row++)
4259 for (col=left+1; col < left+TS-1 && col < width-3; col++) {
4260 pix = image + row*width+col;
4261 rix = &rgb[d][row-top][col-left];
4262 lix = &lab[d][row-top][col-left];
4263 if ((c = 2 - FC(row,col)) == 1) {
4265 val = pix[0][1] + (( pix[-1][2-c] + pix[1][2-c]
4266 - rix[-1][1] - rix[1][1] ) >> 1);
4267 rix[0][2-c] = CLIP(val);
4268 val = pix[0][1] + (( pix[-width][c] + pix[width][c]
4269 - rix[-TS][1] - rix[TS][1] ) >> 1);
4271 val = rix[0][1] + (( pix[-width-1][c] + pix[-width+1][c]
4272 + pix[+width-1][c] + pix[+width+1][c]
4273 - rix[-TS-1][1] - rix[-TS+1][1]
4274 - rix[+TS-1][1] - rix[+TS+1][1] + 1) >> 2);
4275 rix[0][c] = CLIP(val);
4277 rix[0][c] = pix[0][c];
4278 xyz[0] = xyz[1] = xyz[2] = 0.5;
4280 xyz[0] += xyz_cam[0][c] * rix[0][c];
4281 xyz[1] += xyz_cam[1][c] * rix[0][c];
4282 xyz[2] += xyz_cam[2][c] * rix[0][c];
4284 xyz[0] = cbrt[CLIP((int) xyz[0])];
4285 xyz[1] = cbrt[CLIP((int) xyz[1])];
4286 xyz[2] = cbrt[CLIP((int) xyz[2])];
4287 lix[0][0] = 64 * (116 * xyz[1] - 16);
4288 lix[0][1] = 64 * 500 * (xyz[0] - xyz[1]);
4289 lix[0][2] = 64 * 200 * (xyz[1] - xyz[2]);
4291 /* Build homogeneity maps from the CIELab images: */
4292 memset (homo, 0, 2*TS*TS);
4293 for (row=top+2; row < top+TS-2 && row < height-4; row++) {
4295 for (col=left+2; col < left+TS-2 && col < width-4; col++) {
4297 for (d=0; d < 2; d++) {
4298 lix = &lab[d][tr][tc];
4299 for (i=0; i < 4; i++) {
4300 ldiff[d][i] = ABS(lix[0][0]-lix[dir[i]][0]);
4301 abdiff[d][i] = SQR(lix[0][1]-lix[dir[i]][1])
4302 + SQR(lix[0][2]-lix[dir[i]][2]);
4305 leps = MIN(MAX(ldiff[0][0],ldiff[0][1]),
4306 MAX(ldiff[1][2],ldiff[1][3]));
4307 abeps = MIN(MAX(abdiff[0][0],abdiff[0][1]),
4308 MAX(abdiff[1][2],abdiff[1][3]));
4309 for (d=0; d < 2; d++)
4310 for (i=0; i < 4; i++)
4311 if (ldiff[d][i] <= leps && abdiff[d][i] <= abeps)
4315 /* Combine the most homogenous pixels for the final result: */
4316 for (row=top+3; row < top+TS-3 && row < height-5; row++) {
4318 for (col=left+3; col < left+TS-3 && col < width-5; col++) {
4320 for (d=0; d < 2; d++)
4321 for (hm[d]=0, i=tr-1; i <= tr+1; i++)
4322 for (j=tc-1; j <= tc+1; j++)
4323 hm[d] += homo[d][i][j];
4325 FORC3 image[row*width+col][c] = rgb[hm[1] > hm[0]][tr][tc][c];
4327 FORC3 image[row*width+col][c] =
4328 (rgb[0][tr][tc][c] + rgb[1][tr][tc][c]) >> 1;
4336 void CLASS median_filter()
4339 int pass, c, i, j, k, med[9];
4340 static const uchar opt[] = /* Optimal 9-element median search */
4341 { 1,2, 4,5, 7,8, 0,1, 3,4, 6,7, 1,2, 4,5, 7,8,
4342 0,3, 5,8, 4,7, 3,6, 1,4, 2,5, 4,7, 4,2, 6,4, 4,2 };
4344 for (pass=1; pass <= med_passes; pass++) {
4346 fprintf (stderr,_("Median filter pass %d...\n"), pass);
4347 for (c=0; c < 3; c+=2) {
4348 for (pix = image; pix < image+width*height; pix++)
4349 pix[0][3] = pix[0][c];
4350 for (pix = image+width; pix < image+width*(height-1); pix++) {
4351 if ((pix-image+1) % width < 2) continue;
4352 for (k=0, i = -width; i <= width; i += width)
4353 for (j = i-1; j <= i+1; j++)
4354 med[k++] = pix[j][3] - pix[j][1];
4355 for (i=0; i < sizeof opt; i+=2)
4356 if (med[opt[i]] > med[opt[i+1]])
4357 SWAP (med[opt[i]] , med[opt[i+1]]);
4358 pix[0][c] = CLIP(med[4] + pix[0][1]);
4364 void CLASS blend_highlights()
4366 int clip=INT_MAX, row, col, c, i, j;
4367 static const float trans[2][4][4] =
4368 { { { 1,1,1 }, { 1.7320508,-1.7320508,0 }, { -1,-1,2 } },
4369 { { 1,1,1,1 }, { 1,-1,1,-1 }, { 1,1,-1,-1 }, { 1,-1,-1,1 } } };
4370 static const float itrans[2][4][4] =
4371 { { { 1,0.8660254,-0.5 }, { 1,-0.8660254,-0.5 }, { 1,0,1 } },
4372 { { 1,1,1,1 }, { 1,-1,1,-1 }, { 1,1,-1,-1 }, { 1,-1,-1,1 } } };
4373 float cam[2][4], lab[2][4], sum[2], chratio;
4375 if ((unsigned) (colors-3) > 1) return;
4376 if (verbose) fprintf (stderr,_("Blending highlights...\n"));
4377 FORCC if (clip > (i = 65535*pre_mul[c])) clip = i;
4378 for (row=0; row < height; row++)
4379 for (col=0; col < width; col++) {
4380 FORCC if (image[row*width+col][c] > clip) break;
4381 if (c == colors) continue;
4383 cam[0][c] = image[row*width+col][c];
4384 cam[1][c] = MIN(cam[0][c],clip);
4386 for (i=0; i < 2; i++) {
4387 FORCC for (lab[i][c]=j=0; j < colors; j++)
4388 lab[i][c] += trans[colors-3][c][j] * cam[i][j];
4389 for (sum[i]=0,c=1; c < colors; c++)
4390 sum[i] += SQR(lab[i][c]);
4392 chratio = sqrt(sum[1]/sum[0]);
4393 for (c=1; c < colors; c++)
4394 lab[0][c] *= chratio;
4395 FORCC for (cam[0][c]=j=0; j < colors; j++)
4396 cam[0][c] += itrans[colors-3][c][j] * lab[0][j];
4397 FORCC image[row*width+col][c] = cam[0][c] / colors;
4401 #define SCALE (4 >> shrink)
4402 void CLASS recover_highlights()
4404 float *map, sum, wgt, grow;
4405 int hsat[4], count, spread, change, val, i;
4406 unsigned high, wide, mrow, mcol, row, col, kc, c, d, y, x;
4408 static const signed char dir[8][2] =
4409 { {-1,-1}, {-1,0}, {-1,1}, {0,1}, {1,1}, {1,0}, {1,-1}, {0,-1} };
4411 if (verbose) fprintf (stderr,_("Rebuilding highlights...\n"));
4413 grow = pow (2, 4-highlight);
4414 FORCC hsat[c] = 32000 * pre_mul[c];
4415 for (kc=0, c=1; c < colors; c++)
4416 if (pre_mul[kc] < pre_mul[c]) kc = c;
4417 high = height / SCALE;
4418 wide = width / SCALE;
4419 map = (float *) calloc (high*wide, sizeof *map);
4420 merror (map, "recover_highlights()");
4421 FORCC if (c != kc) {
4422 memset (map, 0, high*wide*sizeof *map);
4423 for (mrow=0; mrow < high; mrow++)
4424 for (mcol=0; mcol < wide; mcol++) {
4425 sum = wgt = count = 0;
4426 for (row = mrow*SCALE; row < (mrow+1)*SCALE; row++)
4427 for (col = mcol*SCALE; col < (mcol+1)*SCALE; col++) {
4428 pixel = image[row*width+col];
4429 if (pixel[c] / hsat[c] == 1 && pixel[kc] > 24000) {
4435 if (count == SCALE*SCALE)
4436 map[mrow*wide+mcol] = sum / wgt;
4438 for (spread = 32/grow; spread--; ) {
4439 for (mrow=0; mrow < high; mrow++)
4440 for (mcol=0; mcol < wide; mcol++) {
4441 if (map[mrow*wide+mcol]) continue;
4443 for (d=0; d < 8; d++) {
4444 y = mrow + dir[d][0];
4445 x = mcol + dir[d][1];
4446 if (y < high && x < wide && map[y*wide+x] > 0) {
4447 sum += (1 + (d & 1)) * map[y*wide+x];
4448 count += 1 + (d & 1);
4452 map[mrow*wide+mcol] = - (sum+grow) / (count+grow);
4454 for (change=i=0; i < high*wide; i++)
4461 for (i=0; i < high*wide; i++)
4462 if (map[i] == 0) map[i] = 1;
4463 for (mrow=0; mrow < high; mrow++)
4464 for (mcol=0; mcol < wide; mcol++) {
4465 for (row = mrow*SCALE; row < (mrow+1)*SCALE; row++)
4466 for (col = mcol*SCALE; col < (mcol+1)*SCALE; col++) {
4467 pixel = image[row*width+col];
4468 if (pixel[c] / hsat[c] > 1) {
4469 val = pixel[kc] * map[mrow*wide+mcol];
4470 if (pixel[c] < val) pixel[c] = CLIP(val);
4479 void CLASS tiff_get (unsigned base,
4480 unsigned *tag, unsigned *type, unsigned *len, unsigned *save)
4485 *save = ftell(ifp) + 4;
4486 if (*len * ("11124811248488"[*type < 14 ? *type:0]-'0') > 4)
4487 fseek (ifp, get4()+base, SEEK_SET);
4490 void CLASS parse_thumb_note (int base, unsigned toff, unsigned tlen)
4492 unsigned entries, tag, type, len, save;
4496 tiff_get (base, &tag, &type, &len, &save);
4497 if (tag == toff) thumb_offset = get4()+base;
4498 if (tag == tlen) thumb_length = get4();
4499 fseek (ifp, save, SEEK_SET);
4503 int CLASS parse_tiff_ifd (int base);
4505 void CLASS parse_makernote (int base, int uptag)
4507 static const uchar xlat[2][256] = {
4508 { 0xc1,0xbf,0x6d,0x0d,0x59,0xc5,0x13,0x9d,0x83,0x61,0x6b,0x4f,0xc7,0x7f,0x3d,0x3d,
4509 0x53,0x59,0xe3,0xc7,0xe9,0x2f,0x95,0xa7,0x95,0x1f,0xdf,0x7f,0x2b,0x29,0xc7,0x0d,
4510 0xdf,0x07,0xef,0x71,0x89,0x3d,0x13,0x3d,0x3b,0x13,0xfb,0x0d,0x89,0xc1,0x65,0x1f,
4511 0xb3,0x0d,0x6b,0x29,0xe3,0xfb,0xef,0xa3,0x6b,0x47,0x7f,0x95,0x35,0xa7,0x47,0x4f,
4512 0xc7,0xf1,0x59,0x95,0x35,0x11,0x29,0x61,0xf1,0x3d,0xb3,0x2b,0x0d,0x43,0x89,0xc1,
4513 0x9d,0x9d,0x89,0x65,0xf1,0xe9,0xdf,0xbf,0x3d,0x7f,0x53,0x97,0xe5,0xe9,0x95,0x17,
4514 0x1d,0x3d,0x8b,0xfb,0xc7,0xe3,0x67,0xa7,0x07,0xf1,0x71,0xa7,0x53,0xb5,0x29,0x89,
4515 0xe5,0x2b,0xa7,0x17,0x29,0xe9,0x4f,0xc5,0x65,0x6d,0x6b,0xef,0x0d,0x89,0x49,0x2f,
4516 0xb3,0x43,0x53,0x65,0x1d,0x49,0xa3,0x13,0x89,0x59,0xef,0x6b,0xef,0x65,0x1d,0x0b,
4517 0x59,0x13,0xe3,0x4f,0x9d,0xb3,0x29,0x43,0x2b,0x07,0x1d,0x95,0x59,0x59,0x47,0xfb,
4518 0xe5,0xe9,0x61,0x47,0x2f,0x35,0x7f,0x17,0x7f,0xef,0x7f,0x95,0x95,0x71,0xd3,0xa3,
4519 0x0b,0x71,0xa3,0xad,0x0b,0x3b,0xb5,0xfb,0xa3,0xbf,0x4f,0x83,0x1d,0xad,0xe9,0x2f,
4520 0x71,0x65,0xa3,0xe5,0x07,0x35,0x3d,0x0d,0xb5,0xe9,0xe5,0x47,0x3b,0x9d,0xef,0x35,
4521 0xa3,0xbf,0xb3,0xdf,0x53,0xd3,0x97,0x53,0x49,0x71,0x07,0x35,0x61,0x71,0x2f,0x43,
4522 0x2f,0x11,0xdf,0x17,0x97,0xfb,0x95,0x3b,0x7f,0x6b,0xd3,0x25,0xbf,0xad,0xc7,0xc5,
4523 0xc5,0xb5,0x8b,0xef,0x2f,0xd3,0x07,0x6b,0x25,0x49,0x95,0x25,0x49,0x6d,0x71,0xc7 },
4524 { 0xa7,0xbc,0xc9,0xad,0x91,0xdf,0x85,0xe5,0xd4,0x78,0xd5,0x17,0x46,0x7c,0x29,0x4c,
4525 0x4d,0x03,0xe9,0x25,0x68,0x11,0x86,0xb3,0xbd,0xf7,0x6f,0x61,0x22,0xa2,0x26,0x34,
4526 0x2a,0xbe,0x1e,0x46,0x14,0x68,0x9d,0x44,0x18,0xc2,0x40,0xf4,0x7e,0x5f,0x1b,0xad,
4527 0x0b,0x94,0xb6,0x67,0xb4,0x0b,0xe1,0xea,0x95,0x9c,0x66,0xdc,0xe7,0x5d,0x6c,0x05,
4528 0xda,0xd5,0xdf,0x7a,0xef,0xf6,0xdb,0x1f,0x82,0x4c,0xc0,0x68,0x47,0xa1,0xbd,0xee,
4529 0x39,0x50,0x56,0x4a,0xdd,0xdf,0xa5,0xf8,0xc6,0xda,0xca,0x90,0xca,0x01,0x42,0x9d,
4530 0x8b,0x0c,0x73,0x43,0x75,0x05,0x94,0xde,0x24,0xb3,0x80,0x34,0xe5,0x2c,0xdc,0x9b,
4531 0x3f,0xca,0x33,0x45,0xd0,0xdb,0x5f,0xf5,0x52,0xc3,0x21,0xda,0xe2,0x22,0x72,0x6b,
4532 0x3e,0xd0,0x5b,0xa8,0x87,0x8c,0x06,0x5d,0x0f,0xdd,0x09,0x19,0x93,0xd0,0xb9,0xfc,
4533 0x8b,0x0f,0x84,0x60,0x33,0x1c,0x9b,0x45,0xf1,0xf0,0xa3,0x94,0x3a,0x12,0x77,0x33,
4534 0x4d,0x44,0x78,0x28,0x3c,0x9e,0xfd,0x65,0x57,0x16,0x94,0x6b,0xfb,0x59,0xd0,0xc8,
4535 0x22,0x36,0xdb,0xd2,0x63,0x98,0x43,0xa1,0x04,0x87,0x86,0xf7,0xa6,0x26,0xbb,0xd6,
4536 0x59,0x4d,0xbf,0x6a,0x2e,0xaa,0x2b,0xef,0xe6,0x78,0xb6,0x4e,0xe0,0x2f,0xdc,0x7c,
4537 0xbe,0x57,0x19,0x32,0x7e,0x2a,0xd0,0xb8,0xba,0x29,0x00,0x3c,0x52,0x7d,0xa8,0x49,
4538 0x3b,0x2d,0xeb,0x25,0x49,0xfa,0xa3,0xaa,0x39,0xa7,0xc5,0xa7,0x50,0x11,0x36,0xfb,
4539 0xc6,0x67,0x4a,0xf5,0xa5,0x12,0x65,0x7e,0xb0,0xdf,0xaf,0x4e,0xb3,0x61,0x7f,0x2f } };
4540 unsigned offset=0, entries, tag, type, len, save, c;
4541 unsigned ver97=0, serial=0, i, wbi=0, wb[4]={0,0,0,0};
4542 uchar buf97[324], ci, cj, ck;
4543 short morder, sorder=order;
4546 The MakerNote might have its own TIFF header (possibly with
4547 its own byte-order!), or it might just be a table.
4549 if (!strcmp(make,"Nokia")) return;
4550 fread (buf, 1, 10, ifp);
4551 if (!strncmp (buf,"KDK" ,3) || /* these aren't TIFF tables */
4552 !strncmp (buf,"VER" ,3) ||
4553 !strncmp (buf,"IIII",4) ||
4554 !strncmp (buf,"MMMM",4)) return;
4555 if (!strncmp (buf,"KC" ,2) || /* Konica KD-400Z, KD-510Z */
4556 !strncmp (buf,"MLY" ,3)) { /* Minolta DiMAGE G series */
4558 while ((i=ftell(ifp)) < data_offset && i < 16384) {
4559 wb[0] = wb[2]; wb[2] = wb[1]; wb[1] = wb[3];
4561 if (wb[1] == 256 && wb[3] == 256 &&
4562 wb[0] > 256 && wb[0] < 640 && wb[2] > 256 && wb[2] < 640)
4563 FORC4 cam_mul[c] = wb[c];
4567 if (!strcmp (buf,"Nikon")) {
4570 if (get2() != 42) goto quit;
4572 fseek (ifp, offset-8, SEEK_CUR);
4573 } else if (!strcmp (buf,"OLYMPUS")) {
4574 base = ftell(ifp)-10;
4575 fseek (ifp, -2, SEEK_CUR);
4576 order = get2(); get2();
4577 } else if (!strncmp (buf,"SONY",4) ||
4578 !strcmp (buf,"Panasonic")) {
4580 } else if (!strncmp (buf,"FUJIFILM",8)) {
4581 base = ftell(ifp)-10;
4583 fseek (ifp, 2, SEEK_CUR);
4584 } else if (!strcmp (buf,"OLYMP") ||
4585 !strcmp (buf,"LEICA") ||
4586 !strcmp (buf,"Ricoh") ||
4587 !strcmp (buf,"EPSON"))
4588 fseek (ifp, -2, SEEK_CUR);
4589 else if (!strcmp (buf,"AOC") ||
4590 !strcmp (buf,"QVC"))
4591 fseek (ifp, -4, SEEK_CUR);
4593 fseek (ifp, -10, SEEK_CUR);
4594 if (!strncmp(make,"SAMSUNG",7))
4598 if (entries > 1000) return;
4602 tiff_get (base, &tag, &type, &len, &save);
4604 if (tag == 2 && strstr(make,"NIKON") && !iso_speed)
4605 iso_speed = (get2(),get2());
4606 if (tag == 4 && len > 26 && len < 35) {
4607 if ((i=(get4(),get2())) != 0x7fff && !iso_speed)
4608 iso_speed = 50 * pow (2, i/32.0 - 4);
4609 if ((i=(get2(),get2())) != 0x7fff && !aperture)
4610 aperture = pow (2, i/64.0);
4611 if ((i=get2()) != 0xffff && !shutter)
4612 shutter = pow (2, (short) i/-32.0);
4613 wbi = (get2(),get2());
4614 shot_order = (get2(),get2());
4616 if ((tag == 4 || tag == 0x114) && !strncmp(make,"KONICA",6)) {
4617 fseek (ifp, tag == 4 ? 140:160, SEEK_CUR);
4619 case 72: flip = 0; break;
4620 case 76: flip = 6; break;
4621 case 82: flip = 5; break;
4624 if (tag == 7 && type == 2 && len > 20)
4625 fgets (model2, 64, ifp);
4626 if (tag == 8 && type == 4)
4627 shot_order = get4();
4628 if (tag == 9 && !strcmp(make,"Canon"))
4629 fread (artist, 64, 1, ifp);
4630 if (tag == 0xc && len == 4) {
4631 cam_mul[0] = getreal(type);
4632 cam_mul[2] = getreal(type);
4634 if (tag == 0xd && type == 7 && get2() == 0xaaaa) {
4635 for (c=i=2; (ushort) c != 0xbbbb && i < len; i++)
4636 c = c << 8 | fgetc(ifp);
4637 while ((i+=4) < len-5)
4638 if (get4() == 257 && (i=len) && (c = (get4(),fgetc(ifp))) < 3)
4639 flip = "065"[c]-'0';
4641 if (tag == 0x10 && type == 4)
4643 if (tag == 0x11 && is_raw && !strncmp(make,"NIKON",5)) {
4644 fseek (ifp, get4()+base, SEEK_SET);
4645 parse_tiff_ifd (base);
4647 if (tag == 0x14 && type == 7) {
4649 fseek (ifp, 1248, SEEK_CUR);
4652 fread (buf, 1, 10, ifp);
4653 if (!strncmp(buf,"NRW ",4)) {
4654 fseek (ifp, strcmp(buf+4,"0100") ? 46:1546, SEEK_CUR);
4655 cam_mul[0] = get4() << 2;
4656 cam_mul[1] = get4() + get4();
4657 cam_mul[2] = get4() << 2;
4660 if (tag == 0x15 && type == 2 && is_raw)
4661 fread (model, 64, 1, ifp);
4662 if (strstr(make,"PENTAX")) {
4663 if (tag == 0x1b) tag = 0x1018;
4664 if (tag == 0x1c) tag = 0x1017;
4667 while ((c = fgetc(ifp)) && c != EOF)
4668 serial = serial*10 + (isdigit(c) ? c - '0' : c % 10);
4669 if (tag == 0x81 && type == 4) {
4670 data_offset = get4();
4671 fseek (ifp, data_offset + 41, SEEK_SET);
4672 raw_height = get2() * 2;
4674 filters = 0x61616161;
4676 if (tag == 0x29 && type == 1) {
4677 c = wbi < 18 ? "012347800000005896"[wbi]-'0' : 0;
4678 fseek (ifp, 8 + c*32, SEEK_CUR);
4679 FORC4 cam_mul[c ^ (c >> 1) ^ 1] = get4();
4681 if ((tag == 0x81 && type == 7) ||
4682 (tag == 0x100 && type == 7) ||
4683 (tag == 0x280 && type == 1)) {
4684 thumb_offset = ftell(ifp);
4687 if (tag == 0x88 && type == 4 && (thumb_offset = get4()))
4688 thumb_offset += base;
4689 if (tag == 0x89 && type == 4)
4690 thumb_length = get4();
4691 if (tag == 0x8c || tag == 0x96)
4692 meta_offset = ftell(ifp);
4694 for (i=0; i < 4; i++)
4695 ver97 = ver97 * 10 + fgetc(ifp)-'0';
4698 fseek (ifp, 68, SEEK_CUR);
4699 FORC4 cam_mul[(c >> 1) | ((c & 1) << 1)] = get2();
4702 fseek (ifp, 6, SEEK_CUR);
4705 fseek (ifp, 16, SEEK_CUR);
4706 FORC4 cam_mul[c] = get2();
4709 if (ver97 != 205) fseek (ifp, 280, SEEK_CUR);
4710 fread (buf97, 324, 1, ifp);
4713 if (tag == 0xa1 && type == 7) {
4715 fseek (ifp, 140, SEEK_CUR);
4716 FORC3 cam_mul[c] = get4();
4718 if (tag == 0xa4 && type == 3) {
4719 fseek (ifp, wbi*48, SEEK_CUR);
4720 FORC3 cam_mul[c] = get2();
4722 if (tag == 0xa7 && (unsigned) (ver97-200) < 17) {
4723 ci = xlat[0][serial & 0xff];
4724 cj = xlat[1][fgetc(ifp)^fgetc(ifp)^fgetc(ifp)^fgetc(ifp)];
4726 for (i=0; i < 324; i++)
4727 buf97[i] ^= (cj += ci * ck++);
4728 i = "66666>666;6A;:;55"[ver97-200] - '0';
4729 FORC4 cam_mul[c ^ (c >> 1) ^ (i & 1)] =
4730 sget2 (buf97 + (i & -2) + c*2);
4732 if (tag == 0x200 && len == 3)
4733 shot_order = (get4(),get4());
4734 if (tag == 0x200 && len == 4)
4735 FORC4 cblack[c ^ c >> 1] = get2();
4736 if (tag == 0x201 && len == 4)
4738 if (tag == 0x220 && type == 7)
4739 meta_offset = ftell(ifp);
4740 if (tag == 0x401 && type == 4 && len == 4)
4741 FORC4 cblack[c ^ c >> 1] = get4();
4742 if (tag == 0xe01) { /* Nikon Capture Note */
4744 fseek (ifp, 22, SEEK_CUR);
4745 for (offset=22; offset+22 < len; offset += 22+i) {
4747 fseek (ifp, 14, SEEK_CUR);
4749 if (tag == 0x76a43207) flip = get2();
4750 else fseek (ifp, i, SEEK_CUR);
4753 if (tag == 0xe80 && len == 256 && type == 7) {
4754 fseek (ifp, 48, SEEK_CUR);
4755 cam_mul[0] = get2() * 508 * 1.078 / 0x10000;
4756 cam_mul[2] = get2() * 382 * 1.173 / 0x10000;
4758 if (tag == 0xf00 && type == 7) {
4760 fseek (ifp, 176, SEEK_CUR);
4761 else if (len == 734 || len == 1502)
4762 fseek (ifp, 148, SEEK_CUR);
4766 if ((tag == 0x1011 && len == 9) || tag == 0x20400200)
4767 for (i=0; i < 3; i++)
4768 FORC3 cmatrix[i][c] = ((short) get2()) / 256.0;
4769 if ((tag == 0x1012 || tag == 0x20400600) && len == 4)
4770 FORC4 cblack[c ^ c >> 1] = get2();
4771 if (tag == 0x1017 || tag == 0x20400100)
4772 cam_mul[0] = get2() / 256.0;
4773 if (tag == 0x1018 || tag == 0x20400100)
4774 cam_mul[2] = get2() / 256.0;
4775 if (tag == 0x2011 && len == 2) {
4778 cam_mul[0] = get2() / 256.0;
4779 cam_mul[2] = get2() / 256.0;
4781 if ((tag | 0x70) == 0x2070 && type == 4)
4782 fseek (ifp, get4()+base, SEEK_SET);
4783 if (tag == 0x2010 && type != 7)
4784 load_raw = &CLASS olympus_load_raw;
4786 parse_thumb_note (base, 257, 258);
4788 parse_makernote (base, 0x2040);
4789 if (tag == 0xb028) {
4790 fseek (ifp, get4()+base, SEEK_SET);
4791 parse_thumb_note (base, 136, 137);
4793 if (tag == 0x4001 && len > 500) {
4794 i = len == 582 ? 50 : len == 653 ? 68 : len == 5120 ? 142 : 126;
4795 fseek (ifp, i, SEEK_CUR);
4797 FORC4 cam_mul[c ^ (c >> 1)] = get2();
4798 i = len >> 3 == 164 ? 112:22;
4799 fseek (ifp, i, SEEK_CUR);
4800 FORC4 sraw_mul[c ^ (c >> 1)] = get2();
4803 FORC4 cam_mul[c ^ (c >> 1)] = get4();
4805 FORC4 cam_mul[c ^ (c >> 1)] -= get4();
4807 fseek (ifp, save, SEEK_SET);
4814 Since the TIFF DateTime string has no timezone information,
4815 assume that the camera's clock was set to Universal Time.
4817 void CLASS get_timestamp (int reversed)
4825 for (i=19; i--; ) str[i] = fgetc(ifp);
4827 fread (str, 19, 1, ifp);
4828 memset (&t, 0, sizeof t);
4829 if (sscanf (str, "%d:%d:%d %d:%d:%d", &t.tm_year, &t.tm_mon,
4830 &t.tm_mday, &t.tm_hour, &t.tm_min, &t.tm_sec) != 6)
4836 timestamp = mktime(&t);
4839 void CLASS parse_exif (int base)
4841 unsigned kodak, entries, tag, type, len, save, c;
4844 kodak = !strncmp(make,"EASTMAN",7) && tiff_nifds < 3;
4847 tiff_get (base, &tag, &type, &len, &save);
4849 case 33434: shutter = getreal(type); break;
4850 case 33437: aperture = getreal(type); break;
4851 case 34855: iso_speed = get2(); break;
4853 case 36868: get_timestamp(0); break;
4854 case 37377: if ((expo = -getreal(type)) < 128)
4855 shutter = pow (2, expo); break;
4856 case 37378: aperture = pow (2, getreal(type)/2); break;
4857 case 37386: focal_len = getreal(type); break;
4858 case 37500: parse_makernote (base, 0); break;
4859 case 40962: if (kodak) raw_width = get4(); break;
4860 case 40963: if (kodak) raw_height = get4(); break;
4862 if (get4() == 0x20002)
4863 for (exif_cfa=c=0; c < 8; c+=2)
4864 exif_cfa |= fgetc(ifp) * 0x01010101 << c;
4866 fseek (ifp, save, SEEK_SET);
4870 void CLASS parse_gps (int base)
4872 unsigned entries, tag, type, len, save, c;
4876 tiff_get (base, &tag, &type, &len, &save);
4878 case 1: case 3: case 5:
4879 gpsdata[29+tag/2] = getc(ifp); break;
4880 case 2: case 4: case 7:
4881 FORC(6) gpsdata[tag/3*6+c] = get4(); break;
4883 FORC(2) gpsdata[18+c] = get4(); break;
4885 fgets ((char *) (gpsdata+14+tag/3), MIN(len,12), ifp);
4887 fseek (ifp, save, SEEK_SET);
4891 void CLASS romm_coeff (float romm_cam[3][3])
4893 static const float rgb_romm[3][3] = /* ROMM == Kodak ProPhoto */
4894 { { 2.034193, -0.727420, -0.306766 },
4895 { -0.228811, 1.231729, -0.002922 },
4896 { -0.008565, -0.153273, 1.161839 } };
4899 for (i=0; i < 3; i++)
4900 for (j=0; j < 3; j++)
4901 for (cmatrix[i][j] = k=0; k < 3; k++)
4902 cmatrix[i][j] += rgb_romm[i][k] * romm_cam[k][j];
4905 void CLASS parse_mos (int offset)
4908 int skip, from, i, c, neut[4], planes=0, frot=0;
4909 static const char *mod[] =
4910 { "","DCB2","Volare","Cantare","CMost","Valeo 6","Valeo 11","Valeo 22",
4911 "Valeo 11p","Valeo 17","","Aptus 17","Aptus 22","Aptus 75","Aptus 65",
4912 "Aptus 54S","Aptus 65S","Aptus 75S","AFi 5","AFi 6","AFi 7",
4913 "","","","","","","","","","","","","","","","","","AFi-II 12" };
4914 float romm_cam[3][3];
4916 fseek (ifp, offset, SEEK_SET);
4918 if (get4() != 0x504b5453) break;
4920 fread (data, 1, 40, ifp);
4923 if (!strcmp(data,"JPEG_preview_data")) {
4924 thumb_offset = from;
4925 thumb_length = skip;
4927 if (!strcmp(data,"icc_camera_profile")) {
4928 profile_offset = from;
4929 profile_length = skip;
4931 if (!strcmp(data,"ShootObj_back_type")) {
4932 fscanf (ifp, "%d", &i);
4933 if ((unsigned) i < sizeof mod / sizeof (*mod))
4934 strcpy (model, mod[i]);
4936 if (!strcmp(data,"icc_camera_to_tone_matrix")) {
4937 for (i=0; i < 9; i++)
4938 romm_cam[0][i] = int_to_float(get4());
4939 romm_coeff (romm_cam);
4941 if (!strcmp(data,"CaptProf_color_matrix")) {
4942 for (i=0; i < 9; i++)
4943 fscanf (ifp, "%f", &romm_cam[0][i]);
4944 romm_coeff (romm_cam);
4946 if (!strcmp(data,"CaptProf_number_of_planes"))
4947 fscanf (ifp, "%d", &planes);
4948 if (!strcmp(data,"CaptProf_raw_data_rotation"))
4949 fscanf (ifp, "%d", &flip);
4950 if (!strcmp(data,"CaptProf_mosaic_pattern"))
4952 fscanf (ifp, "%d", &i);
4953 if (i == 1) frot = c ^ (c >> 1);
4955 if (!strcmp(data,"ImgProf_rotation_angle")) {
4956 fscanf (ifp, "%d", &i);
4959 if (!strcmp(data,"NeutObj_neutrals") && !cam_mul[0]) {
4960 FORC4 fscanf (ifp, "%d", neut+c);
4961 FORC3 cam_mul[c] = (float) neut[0] / neut[c+1];
4963 if (!strcmp(data,"Rows_data"))
4964 load_flags = get4();
4966 fseek (ifp, skip+from, SEEK_SET);
4969 filters = (planes == 1) * 0x01010101 *
4970 (uchar) "\x94\x61\x16\x49"[(flip/90 + frot) & 3];
4973 void CLASS linear_table (unsigned len)
4976 if (len > 0x1000) len = 0x1000;
4977 read_shorts (curve, len);
4978 for (i=len; i < 0x1000; i++)
4979 curve[i] = curve[i-1];
4980 maximum = curve[0xfff];
4983 void CLASS parse_kodak_ifd (int base)
4985 unsigned entries, tag, type, len, save;
4986 int i, c, wbi=-2, wbtemp=6500;
4987 float mul[3]={1,1,1}, num;
4988 static const int wbtag[] = { 64037,64040,64039,64041,-1,-1,64042 };
4991 if (entries > 1024) return;
4993 tiff_get (base, &tag, &type, &len, &save);
4994 if (tag == 1020) wbi = getint(type);
4995 if (tag == 1021 && len == 72) { /* WB set in software */
4996 fseek (ifp, 40, SEEK_CUR);
4997 FORC3 cam_mul[c] = 2048.0 / get2();
5000 if (tag == 2118) wbtemp = getint(type);
5001 if (tag == 2130 + wbi)
5002 FORC3 mul[c] = getreal(type);
5003 if (tag == 2140 + wbi && wbi >= 0)
5005 for (num=i=0; i < 4; i++)
5006 num += getreal(type) * pow (wbtemp/100.0, i);
5007 cam_mul[c] = 2048 / (num * mul[c]);
5009 if (tag == 2317) linear_table (len);
5010 if (tag == 6020) iso_speed = getint(type);
5011 if (tag == 64013) wbi = fgetc(ifp);
5012 if ((unsigned) wbi < 7 && tag == wbtag[wbi])
5013 FORC3 cam_mul[c] = get4();
5014 if (tag == 64019) width = getint(type);
5015 if (tag == 64020) height = (getint(type)+1) & -2;
5016 fseek (ifp, save, SEEK_SET);
5020 void CLASS parse_minolta (int base);
5021 int CLASS parse_tiff (int base);
5023 int CLASS parse_tiff_ifd (int base)
5025 unsigned entries, tag, type, len, plen=16, save;
5026 int ifd, use_cm=0, cfa, i, j, c, ima_len=0;
5027 int blrr=1, blrc=1, dblack[] = { 0,0,0,0 };
5028 char software[64], *cbuf, *cp;
5029 uchar cfa_pat[16], cfa_pc[] = { 0,1,2,3 }, tab[256];
5030 double cc[4][4], cm[4][3], cam_xyz[4][3], num;
5031 double ab[]={ 1,1,1,1 }, asn[] = { 0,0,0,0 }, xyz[] = { 1,1,1 };
5032 unsigned sony_curve[] = { 0,0,0,0,0,4095 };
5033 unsigned *buf, sony_offset=0, sony_length=0, sony_key=0;
5037 if (tiff_nifds >= sizeof tiff_ifd / sizeof tiff_ifd[0])
5040 for (j=0; j < 4; j++)
5041 for (i=0; i < 4; i++)
5044 if (entries > 512) return 1;
5046 tiff_get (base, &tag, &type, &len, &save);
5048 case 5: width = get2(); break;
5049 case 6: height = get2(); break;
5050 case 7: width += get2(); break;
5051 case 9: filters = get2(); break;
5053 if (type == 3 && len == 1)
5054 cam_mul[(tag-17)*2] = get2() / 256.0;
5057 if (type == 3) iso_speed = get2();
5059 case 36: case 37: case 38:
5060 cam_mul[tag-0x24] = get2();
5063 if (len < 50 || cam_mul[0]) break;
5064 fseek (ifp, 12, SEEK_CUR);
5065 FORC3 cam_mul[c] = get2();
5068 if (type != 7 || fgetc(ifp) != 0xff || fgetc(ifp) != 0xd8) break;
5069 thumb_offset = ftell(ifp) - 2;
5072 case 61440: /* Fuji HS10 table */
5073 parse_tiff_ifd (base);
5075 case 2: case 256: case 61441: /* ImageWidth */
5076 tiff_ifd[ifd].width = getint(type);
5078 case 3: case 257: case 61442: /* ImageHeight */
5079 tiff_ifd[ifd].height = getint(type);
5081 case 258: /* BitsPerSample */
5083 tiff_ifd[ifd].samples = len & 7;
5084 tiff_ifd[ifd].bps = getint(type);
5088 load_raw = &CLASS packed_load_raw;
5089 load_flags = get4() && (filters=0x16161616) ? 24:80;
5091 case 259: /* Compression */
5092 tiff_ifd[ifd].comp = getint(type);
5094 case 262: /* PhotometricInterpretation */
5095 tiff_ifd[ifd].phint = get2();
5097 case 270: /* ImageDescription */
5098 fread (desc, 512, 1, ifp);
5100 case 271: /* Make */
5101 fgets (make, 64, ifp);
5103 case 272: /* Model */
5104 fgets (model, 64, ifp);
5106 case 280: /* Panasonic RW2 offset */
5107 if (type != 4) break;
5108 load_raw = &CLASS panasonic_load_raw;
5109 load_flags = 0x2008;
5110 case 273: /* StripOffset */
5111 case 513: /* JpegIFOffset */
5113 tiff_ifd[ifd].offset = get4()+base;
5114 if (!tiff_ifd[ifd].bps && tiff_ifd[ifd].offset > 0) {
5115 fseek (ifp, tiff_ifd[ifd].offset, SEEK_SET);
5116 if (ljpeg_start (&jh, 1)) {
5117 tiff_ifd[ifd].comp = 6;
5118 tiff_ifd[ifd].width = jh.wide;
5119 tiff_ifd[ifd].height = jh.high;
5120 tiff_ifd[ifd].bps = jh.bits;
5121 tiff_ifd[ifd].samples = jh.clrs;
5122 if (!(jh.sraw || (jh.clrs & 1)))
5123 tiff_ifd[ifd].width *= jh.clrs;
5125 parse_tiff (tiff_ifd[ifd].offset + 12);
5130 case 274: /* Orientation */
5131 tiff_ifd[ifd].flip = "50132467"[get2() & 7]-'0';
5133 case 277: /* SamplesPerPixel */
5134 tiff_ifd[ifd].samples = getint(type) & 7;
5136 case 279: /* StripByteCounts */
5139 tiff_ifd[ifd].bytes = get4();
5142 FORC3 cam_mul[(4-c) % 3] = getint(type);
5144 case 305: case 11: /* Software */
5145 fgets (software, 64, ifp);
5146 if (!strncmp(software,"Adobe",5) ||
5147 !strncmp(software,"dcraw",5) ||
5148 !strncmp(software,"UFRaw",5) ||
5149 !strncmp(software,"Bibble",6) ||
5150 !strncmp(software,"Nikon Scan",10) ||
5151 !strcmp (software,"Digital Photo Professional"))
5154 case 306: /* DateTime */
5157 case 315: /* Artist */
5158 fread (artist, 64, 1, ifp);
5160 case 322: /* TileWidth */
5161 tiff_ifd[ifd].tile_width = getint(type);
5163 case 323: /* TileLength */
5164 tiff_ifd[ifd].tile_length = getint(type);
5166 case 324: /* TileOffsets */
5167 tiff_ifd[ifd].offset = len > 1 ? ftell(ifp) : get4();
5169 load_raw = &CLASS sinar_4shot_load_raw;
5173 case 330: /* SubIFDs */
5174 if (!strcmp(model,"DSLR-A100") && tiff_ifd[ifd].width == 3872) {
5175 load_raw = &CLASS sony_arw_load_raw;
5176 data_offset = get4()+base;
5181 fseek (ifp, get4()+base, SEEK_SET);
5182 if (parse_tiff_ifd (base)) break;
5183 fseek (ifp, i+4, SEEK_SET);
5187 strcpy (make, "Sarnoff");
5191 FORC4 sony_curve[c+1] = get2() >> 2 & 0xfff;
5192 for (i=0; i < 5; i++)
5193 for (j = sony_curve[i]+1; j <= sony_curve[i+1]; j++)
5194 curve[j] = curve[j-1] + (1 << i);
5196 case 29184: sony_offset = get4(); break;
5197 case 29185: sony_length = get4(); break;
5198 case 29217: sony_key = get4(); break;
5200 parse_minolta (ftell(ifp));
5204 FORC4 cam_mul[c ^ (c < 2)] = get2();
5207 FORC4 cam_mul[c] = get2();
5208 i = (cam_mul[1] == 1024 && cam_mul[2] == 1024) << 1;
5209 SWAP (cam_mul[i],cam_mul[i+1])
5211 case 33405: /* Model2 */
5212 fgets (model2, 64, ifp);
5214 case 33422: /* CFAPattern */
5215 case 64777: /* Kodak P-series */
5216 if ((plen=len) > 16) plen = 16;
5217 fread (cfa_pat, 1, plen, ifp);
5218 for (colors=cfa=i=0; i < plen; i++) {
5219 colors += !(cfa & (1 << cfa_pat[i]));
5220 cfa |= 1 << cfa_pat[i];
5222 if (cfa == 070) memcpy (cfa_pc,"\003\004\005",3); /* CMY */
5223 if (cfa == 072) memcpy (cfa_pc,"\005\003\004\001",4); /* GMCY */
5227 fseek (ifp, get4()+base, SEEK_SET);
5228 parse_kodak_ifd (base);
5230 case 33434: /* ExposureTime */
5231 shutter = getreal(type);
5233 case 33437: /* FNumber */
5234 aperture = getreal(type);
5236 case 34306: /* Leaf white balance */
5237 FORC4 cam_mul[c ^ 1] = 4096.0 / get2();
5239 case 34307: /* Leaf CatchLight color matrix */
5240 fread (software, 1, 7, ifp);
5241 if (strncmp(software,"MATRIX",6)) break;
5243 for (raw_color = i=0; i < 3; i++) {
5244 FORC4 fscanf (ifp, "%f", &rgb_cam[i][c^1]);
5245 if (!use_camera_wb) continue;
5247 FORC4 num += rgb_cam[i][c];
5248 FORC4 rgb_cam[i][c] /= num;
5251 case 34310: /* Leaf metadata */
5252 parse_mos (ftell(ifp));
5254 strcpy (make, "Leaf");
5256 case 34665: /* EXIF tag */
5257 fseek (ifp, get4()+base, SEEK_SET);
5260 case 34853: /* GPSInfo tag */
5261 fseek (ifp, get4()+base, SEEK_SET);
5264 case 34675: /* InterColorProfile */
5265 case 50831: /* AsShotICCProfile */
5266 profile_offset = ftell(ifp);
5267 profile_length = len;
5269 case 37122: /* CompressedBitsPerPixel */
5270 kodak_cbpp = get4();
5272 case 37386: /* FocalLength */
5273 focal_len = getreal(type);
5275 case 37393: /* ImageNumber */
5276 shot_order = getint(type);
5278 case 37400: /* old Kodak KDC tag */
5279 for (raw_color = i=0; i < 3; i++) {
5281 FORC3 rgb_cam[i][c] = getreal(type);
5284 case 46275: /* Imacon tags */
5285 strcpy (make, "Imacon");
5286 data_offset = ftell(ifp);
5290 if (!ima_len) break;
5291 fseek (ifp, 38, SEEK_CUR);
5293 fseek (ifp, 40, SEEK_CUR);
5295 raw_height = get4();
5296 left_margin = get4() & 7;
5297 width = raw_width - left_margin - (get4() & 7);
5298 top_margin = get4() & 7;
5299 height = raw_height - top_margin - (get4() & 7);
5300 if (raw_width == 7262) {
5305 fseek (ifp, 52, SEEK_CUR);
5306 FORC3 cam_mul[c] = getreal(11);
5307 fseek (ifp, 114, SEEK_CUR);
5308 flip = (get2() >> 7) * 90;
5309 if (width * height * 6 == ima_len) {
5310 if (flip % 180 == 90) SWAP(width,height);
5312 raw_height = height;
5313 left_margin = top_margin = filters = flip = 0;
5315 sprintf (model, "Ixpress %d-Mp", height*width/1000000);
5316 load_raw = &CLASS imacon_full_load_raw;
5318 if (left_margin & 1) filters = 0x61616161;
5319 load_raw = &CLASS unpacked_load_raw;
5323 case 50454: /* Sinar tag */
5325 if (!(cbuf = (char *) malloc(len))) break;
5326 fread (cbuf, 1, len, ifp);
5327 for (cp = cbuf-1; cp && cp < cbuf+len; cp = strchr(cp,'\n'))
5328 if (!strncmp (++cp,"Neutral ",8))
5329 sscanf (cp+8, "%f %f %f", cam_mul, cam_mul+1, cam_mul+2);
5333 if (!make[0]) strcpy (make, "Hasselblad");
5335 case 50459: /* Hasselblad tag */
5340 fseek (ifp, j+(get2(),get4()), SEEK_SET);
5346 case 50706: /* DNGVersion */
5347 FORC4 dng_version = (dng_version << 8) + fgetc(ifp);
5348 if (!make[0]) strcpy (make, "DNG");
5351 case 50710: /* CFAPlaneColor */
5352 if (len > 4) len = 4;
5354 fread (cfa_pc, 1, colors, ifp);
5356 FORCC tab[cfa_pc[c]] = c;
5359 filters = filters << 2 | tab[cfa_pat[i % plen]];
5361 case 50711: /* CFALayout */
5364 filters = 0x49494949;
5368 case 50712: /* LinearizationTable */
5371 case 50713: /* BlackLevelRepeatDim */
5377 case 50714: /* BlackLevel */
5378 black = getreal(type);
5379 if (!filters || !~filters) break;
5381 dblack[1] = (blrc == 2) ? getreal(type):dblack[0];
5382 dblack[2] = (blrr == 2) ? getreal(type):dblack[0];
5383 dblack[3] = (blrc == 2 && blrr == 2) ? getreal(type):dblack[1];
5385 filters |= ((filters >> 2 & 0x22222222) |
5386 (filters << 2 & 0x88888888)) & filters << 1;
5387 FORC4 cblack[filters >> (c << 1) & 3] = dblack[c];
5390 case 50715: /* BlackLevelDeltaH */
5391 case 50716: /* BlackLevelDeltaV */
5392 for (num=i=0; i < len; i++)
5393 num += getreal(type);
5394 black += num/len + 0.5;
5396 case 50717: /* WhiteLevel */
5397 maximum = getint(type);
5399 case 50718: /* DefaultScale */
5400 pixel_aspect = getreal(type);
5401 pixel_aspect /= getreal(type);
5403 case 50721: /* ColorMatrix1 */
5404 case 50722: /* ColorMatrix2 */
5405 FORCC for (j=0; j < 3; j++)
5406 cm[c][j] = getreal(type);
5409 case 50723: /* CameraCalibration1 */
5410 case 50724: /* CameraCalibration2 */
5411 for (i=0; i < colors; i++)
5412 FORCC cc[i][c] = getreal(type);
5414 case 50727: /* AnalogBalance */
5415 FORCC ab[c] = getreal(type);
5417 case 50728: /* AsShotNeutral */
5418 FORCC asn[c] = getreal(type);
5420 case 50729: /* AsShotWhiteXY */
5421 xyz[0] = getreal(type);
5422 xyz[1] = getreal(type);
5423 xyz[2] = 1 - xyz[0] - xyz[1];
5424 FORC3 xyz[c] /= d65_white[c];
5426 case 50740: /* DNGPrivateData */
5427 if (dng_version) break;
5428 parse_minolta (j = get4()+base);
5429 fseek (ifp, j, SEEK_SET);
5430 parse_tiff_ifd (base);
5433 read_shorts (cr2_slice, 3);
5435 case 50829: /* ActiveArea */
5436 top_margin = getint(type);
5437 left_margin = getint(type);
5438 height = getint(type) - top_margin;
5439 width = getint(type) - left_margin;
5441 case 50830: /* MaskedAreas */
5442 for (i=0; i < len && i < 32; i++)
5443 mask[0][i] = getint(type);
5446 case 51009: /* OpcodeList2 */
5447 meta_offset = ftell(ifp);
5449 case 64772: /* Kodak P-series */
5450 if (len < 13) break;
5451 fseek (ifp, 16, SEEK_CUR);
5452 data_offset = get4();
5453 fseek (ifp, 28, SEEK_CUR);
5454 data_offset += get4();
5455 load_raw = &CLASS packed_load_raw;
5458 if (type == 2) fgets (model2, 64, ifp);
5460 fseek (ifp, save, SEEK_SET);
5462 if (sony_length && (buf = (unsigned *) malloc(sony_length))) {
5463 fseek (ifp, sony_offset, SEEK_SET);
5464 fread (buf, sony_length, 1, ifp);
5465 sony_decrypt (buf, sony_length/4, 1, sony_key);
5467 if ((ifp = tmpfile())) {
5468 fwrite (buf, sony_length, 1, ifp);
5469 fseek (ifp, 0, SEEK_SET);
5470 parse_tiff_ifd (-sony_offset);
5476 for (i=0; i < colors; i++)
5477 FORCC cc[i][c] *= ab[i];
5479 FORCC for (i=0; i < 3; i++)
5480 for (cam_xyz[c][i]=j=0; j < colors; j++)
5481 cam_xyz[c][i] += cc[c][j] * cm[j][i] * xyz[i];
5482 cam_xyz_coeff (cam_xyz);
5486 FORCC cam_mul[c] = 1 / asn[c];
5489 FORCC pre_mul[c] /= cc[c][c];
5493 int CLASS parse_tiff (int base)
5497 fseek (ifp, base, SEEK_SET);
5499 if (order != 0x4949 && order != 0x4d4d) return 0;
5501 while ((doff = get4())) {
5502 fseek (ifp, doff+base, SEEK_SET);
5503 if (parse_tiff_ifd (base)) break;
5508 void CLASS apply_tiff()
5510 int max_samp=0, raw=-1, thm=-1, i;
5515 fseek (ifp, thumb_offset, SEEK_SET);
5516 if (ljpeg_start (&jh, 1)) {
5517 thumb_misc = jh.bits;
5518 thumb_width = jh.wide;
5519 thumb_height = jh.high;
5522 for (i=0; i < tiff_nifds; i++) {
5523 if (max_samp < tiff_ifd[i].samples)
5524 max_samp = tiff_ifd[i].samples;
5525 if (max_samp > 3) max_samp = 3;
5526 if ((tiff_ifd[i].comp != 6 || tiff_ifd[i].samples != 3) &&
5527 (tiff_ifd[i].width | tiff_ifd[i].height) < 0x10000 &&
5528 tiff_ifd[i].width*tiff_ifd[i].height > raw_width*raw_height) {
5529 raw_width = tiff_ifd[i].width;
5530 raw_height = tiff_ifd[i].height;
5531 tiff_bps = tiff_ifd[i].bps;
5532 tiff_compress = tiff_ifd[i].comp;
5533 data_offset = tiff_ifd[i].offset;
5534 tiff_flip = tiff_ifd[i].flip;
5535 tiff_samples = tiff_ifd[i].samples;
5536 tile_width = tiff_ifd[i].tile_width;
5537 tile_length = tiff_ifd[i].tile_length;
5541 if (!tile_width ) tile_width = INT_MAX;
5542 if (!tile_length) tile_length = INT_MAX;
5543 for (i=tiff_nifds; i--; )
5544 if (tiff_ifd[i].flip) tiff_flip = tiff_ifd[i].flip;
5545 if (raw >= 0 && !load_raw)
5546 switch (tiff_compress) {
5548 if (tiff_ifd[raw].bytes == raw_width*raw_height) {
5550 load_raw = &CLASS sony_arw2_load_raw; break;
5552 if (tiff_ifd[raw].bytes*8 != raw_width*raw_height*tiff_bps) {
5554 load_raw = &CLASS sony_arw_load_raw; break;
5560 case 32773: goto slr;
5562 if (tiff_ifd[raw].bytes*5 == raw_width*raw_height*8) {
5567 case 8: load_raw = &CLASS eight_bit_load_raw; break;
5568 case 12: if (tiff_ifd[raw].phint == 2)
5570 load_raw = &CLASS packed_load_raw; break;
5571 case 14: load_flags = 0;
5572 case 16: load_raw = &CLASS unpacked_load_raw; break;
5575 case 6: case 7: case 99:
5576 load_raw = &CLASS lossless_jpeg_load_raw; break;
5578 load_raw = &CLASS kodak_262_load_raw; break;
5580 if ((raw_width+9)/10*16*raw_height == tiff_ifd[raw].bytes) {
5581 load_raw = &CLASS packed_load_raw;
5583 } else if (raw_width*raw_height*2 == tiff_ifd[raw].bytes) {
5584 load_raw = &CLASS unpacked_load_raw;
5588 load_raw = &CLASS nikon_load_raw; break;
5590 load_raw = &CLASS lossy_dng_load_raw; break;
5592 load_raw = &CLASS pentax_load_raw; break;
5594 switch (tiff_ifd[raw].phint) {
5595 case 2: load_raw = &CLASS kodak_rgb_load_raw; filters = 0; break;
5596 case 6: load_raw = &CLASS kodak_ycbcr_load_raw; filters = 0; break;
5597 case 32803: load_raw = &CLASS kodak_65000_load_raw;
5600 default: is_raw = 0;
5603 if ( (tiff_samples == 3 && tiff_ifd[raw].bytes &&
5604 tiff_bps != 14 && tiff_bps != 2048 &&
5605 tiff_compress != 32769 && tiff_compress != 32770)
5606 || (tiff_bps == 8 && !strstr(make,"KODAK") && !strstr(make,"Kodak") &&
5607 !strstr(model2,"DEBUG RAW")))
5609 for (i=0; i < tiff_nifds; i++)
5610 if (i != raw && tiff_ifd[i].samples == max_samp &&
5611 tiff_ifd[i].width * tiff_ifd[i].height / SQR(tiff_ifd[i].bps+1) >
5612 thumb_width * thumb_height / SQR(thumb_misc+1)
5613 && tiff_ifd[i].comp != 34892) {
5614 thumb_width = tiff_ifd[i].width;
5615 thumb_height = tiff_ifd[i].height;
5616 thumb_offset = tiff_ifd[i].offset;
5617 thumb_length = tiff_ifd[i].bytes;
5618 thumb_misc = tiff_ifd[i].bps;
5622 thumb_misc |= tiff_ifd[thm].samples << 5;
5623 switch (tiff_ifd[thm].comp) {
5625 write_thumb = &CLASS layer_thumb;
5628 if (tiff_ifd[thm].bps <= 8)
5629 write_thumb = &CLASS ppm_thumb;
5630 else if (!strcmp(make,"Imacon"))
5631 write_thumb = &CLASS ppm16_thumb;
5633 thumb_load_raw = &CLASS kodak_thumb_load_raw;
5636 thumb_load_raw = tiff_ifd[thm].phint == 6 ?
5637 &CLASS kodak_ycbcr_load_raw : &CLASS kodak_rgb_load_raw;
5642 void CLASS parse_minolta (int base)
5644 int save, tag, len, offset, high=0, wide=0, i, c;
5647 fseek (ifp, base, SEEK_SET);
5648 if (fgetc(ifp) || fgetc(ifp)-'M' || fgetc(ifp)-'R') return;
5649 order = fgetc(ifp) * 0x101;
5650 offset = base + get4() + 8;
5651 while ((save=ftell(ifp)) < offset) {
5652 for (tag=i=0; i < 4; i++)
5653 tag = tag << 8 | fgetc(ifp);
5656 case 0x505244: /* PRD */
5657 fseek (ifp, 8, SEEK_CUR);
5661 case 0x574247: /* WBG */
5663 i = strcmp(model,"DiMAGE A200") ? 0:3;
5664 FORC4 cam_mul[c ^ (c >> 1) ^ i] = get2();
5666 case 0x545457: /* TTW */
5667 parse_tiff (ftell(ifp));
5668 data_offset = offset;
5670 fseek (ifp, save+len+8, SEEK_SET);
5678 Many cameras have a "debug mode" that writes JPEG and raw
5679 at the same time. The raw file has no header, so try to
5680 to open the matching JPEG file and read its metadata.
5682 void CLASS parse_external_jpeg()
5684 const char *file, *ext;
5685 char *jname, *jfile, *jext;
5688 ext = strrchr (ifname, '.');
5689 file = strrchr (ifname, '/');
5690 if (!file) file = strrchr (ifname, '\\');
5691 if (!file) file = ifname-1;
5693 if (!ext || strlen(ext) != 4 || ext-file != 8) return;
5694 jname = (char *) malloc (strlen(ifname) + 1);
5695 merror (jname, "parse_external_jpeg()");
5696 strcpy (jname, ifname);
5697 jfile = file - ifname + jname;
5698 jext = ext - ifname + jname;
5699 if (strcasecmp (ext, ".jpg")) {
5700 strcpy (jext, isupper(ext[1]) ? ".JPG":".jpg");
5701 if (isdigit(*file)) {
5702 memcpy (jfile, file+4, 4);
5703 memcpy (jfile+4, file, 4);
5706 while (isdigit(*--jext)) {
5713 if (strcmp (jname, ifname)) {
5714 if ((ifp = fopen (jname, "rb"))) {
5716 fprintf (stderr,_("Reading metadata from %s ...\n"), jname);
5724 fprintf (stderr,_("Failed to read metadata from %s\n"), jname);
5730 CIFF block 0x1030 contains an 8x8 white sample.
5731 Load this into white[][] for use in scale_colors().
5733 void CLASS ciff_block_1030()
5735 static const ushort key[] = { 0x410, 0x45f3 };
5736 int i, bpp, row, col, vbits=0;
5737 unsigned long bitbuf=0;
5739 if ((get2(),get4()) != 0x80008 || !get4()) return;
5741 if (bpp != 10 && bpp != 12) return;
5742 for (i=row=0; row < 8; row++)
5743 for (col=0; col < 8; col++) {
5745 bitbuf = bitbuf << 16 | (get2() ^ key[i++ & 1]);
5749 bitbuf << (LONG_BIT - vbits) >> (LONG_BIT - bpp);
5755 Parse a CIFF file, better known as Canon CRW format.
5757 void CLASS parse_ciff (int offset, int length)
5759 int tboff, nrecs, c, type, len, save, wbi=-1;
5760 ushort key[] = { 0x410, 0x45f3 };
5762 fseek (ifp, offset+length-4, SEEK_SET);
5763 tboff = get4() + offset;
5764 fseek (ifp, tboff, SEEK_SET);
5766 if (nrecs > 100) return;
5770 save = ftell(ifp) + 4;
5771 fseek (ifp, offset+get4(), SEEK_SET);
5772 if ((((type >> 8) + 8) | 8) == 0x38)
5773 parse_ciff (ftell(ifp), len); /* Parse a sub-table */
5776 fread (artist, 64, 1, ifp);
5777 if (type == 0x080a) {
5778 fread (make, 64, 1, ifp);
5779 fseek (ifp, strlen(make) - 63, SEEK_CUR);
5780 fread (model, 64, 1, ifp);
5782 if (type == 0x1810) {
5783 fseek (ifp, 12, SEEK_CUR);
5786 if (type == 0x1835) /* Get the decoder table */
5787 tiff_compress = get4();
5788 if (type == 0x2007) {
5789 thumb_offset = ftell(ifp);
5792 if (type == 0x1818) {
5793 shutter = pow (2, -int_to_float((get4(),get4())));
5794 aperture = pow (2, int_to_float(get4())/2);
5796 if (type == 0x102a) {
5797 iso_speed = pow (2, (get4(),get2())/32.0 - 4) * 50;
5798 aperture = pow (2, (get2(),(short)get2())/64.0);
5799 shutter = pow (2,-((short)get2())/32.0);
5800 wbi = (get2(),get2());
5801 if (wbi > 17) wbi = 0;
5802 fseek (ifp, 32, SEEK_CUR);
5803 if (shutter > 1e6) shutter = get2()/10.0;
5805 if (type == 0x102c) {
5806 if (get2() > 512) { /* Pro90, G1 */
5807 fseek (ifp, 118, SEEK_CUR);
5808 FORC4 cam_mul[c ^ 2] = get2();
5809 } else { /* G2, S30, S40 */
5810 fseek (ifp, 98, SEEK_CUR);
5811 FORC4 cam_mul[c ^ (c >> 1) ^ 1] = get2();
5814 if (type == 0x0032) {
5815 if (len == 768) { /* EOS D30 */
5816 fseek (ifp, 72, SEEK_CUR);
5817 FORC4 cam_mul[c ^ (c >> 1)] = 1024.0 / get2();
5818 if (!wbi) cam_mul[0] = -1; /* use my auto white balance */
5819 } else if (!cam_mul[0]) {
5820 if (get2() == key[0]) /* Pro1, G6, S60, S70 */
5821 c = (strstr(model,"Pro1") ?
5822 "012346000000000000":"01345:000000006008")[wbi]-'0'+ 2;
5823 else { /* G3, G5, S45, S50 */
5824 c = "023457000000006000"[wbi]-'0';
5825 key[0] = key[1] = 0;
5827 fseek (ifp, 78 + c*8, SEEK_CUR);
5828 FORC4 cam_mul[c ^ (c >> 1) ^ 1] = get2() ^ key[c & 1];
5829 if (!wbi) cam_mul[0] = -1;
5832 if (type == 0x10a9) { /* D60, 10D, 300D, and clones */
5833 if (len > 66) wbi = "0134567028"[wbi]-'0';
5834 fseek (ifp, 2 + wbi*8, SEEK_CUR);
5835 FORC4 cam_mul[c ^ (c >> 1)] = get2();
5837 if (type == 0x1030 && (0x18040 >> wbi & 1))
5838 ciff_block_1030(); /* all that don't have 0x10a9 */
5839 if (type == 0x1031) {
5840 raw_width = (get2(),get2());
5841 raw_height = get2();
5843 if (type == 0x5029) {
5844 focal_len = len >> 16;
5845 if ((len & 0xffff) == 2) focal_len /= 32;
5847 if (type == 0x5813) flash_used = int_to_float(len);
5848 if (type == 0x5814) canon_ev = int_to_float(len);
5849 if (type == 0x5817) shot_order = len;
5850 if (type == 0x5834) unique_id = len;
5851 if (type == 0x580e) timestamp = len;
5852 if (type == 0x180e) timestamp = get4();
5854 if ((type | 0x4000) == 0x580e)
5855 timestamp = mktime (gmtime (×tamp));
5857 fseek (ifp, save, SEEK_SET);
5861 void CLASS parse_rollei()
5863 char line[128], *val;
5866 fseek (ifp, 0, SEEK_SET);
5867 memset (&t, 0, sizeof t);
5869 fgets (line, 128, ifp);
5870 if ((val = strchr(line,'=')))
5873 val = line + strlen(line);
5874 if (!strcmp(line,"DAT"))
5875 sscanf (val, "%d.%d.%d", &t.tm_mday, &t.tm_mon, &t.tm_year);
5876 if (!strcmp(line,"TIM"))
5877 sscanf (val, "%d:%d:%d", &t.tm_hour, &t.tm_min, &t.tm_sec);
5878 if (!strcmp(line,"HDR"))
5879 thumb_offset = atoi(val);
5880 if (!strcmp(line,"X "))
5881 raw_width = atoi(val);
5882 if (!strcmp(line,"Y "))
5883 raw_height = atoi(val);
5884 if (!strcmp(line,"TX "))
5885 thumb_width = atoi(val);
5886 if (!strcmp(line,"TY "))
5887 thumb_height = atoi(val);
5888 } while (strncmp(line,"EOHD",4));
5889 data_offset = thumb_offset + thumb_width * thumb_height * 2;
5893 timestamp = mktime(&t);
5894 strcpy (make, "Rollei");
5895 strcpy (model,"d530flex");
5896 write_thumb = &CLASS rollei_thumb;
5899 void CLASS parse_sinar_ia()
5905 fseek (ifp, 4, SEEK_SET);
5907 fseek (ifp, get4(), SEEK_SET);
5909 off = get4(); get4();
5910 fread (str, 8, 1, ifp);
5911 if (!strcmp(str,"META")) meta_offset = off;
5912 if (!strcmp(str,"THUMB")) thumb_offset = off;
5913 if (!strcmp(str,"RAW0")) data_offset = off;
5915 fseek (ifp, meta_offset+20, SEEK_SET);
5916 fread (make, 64, 1, ifp);
5918 if ((cp = strchr(make,' '))) {
5919 strcpy (model, cp+1);
5923 raw_height = get2();
5924 load_raw = &CLASS unpacked_load_raw;
5925 thumb_width = (get4(),get2());
5926 thumb_height = get2();
5927 write_thumb = &CLASS ppm_thumb;
5931 void CLASS parse_phase_one (int base)
5933 unsigned entries, tag, /*type,*/ len, data, save, i, c;
5934 float romm_cam[3][3], *fp;
5937 memset (&ph1, 0, sizeof ph1);
5938 fseek (ifp, base, SEEK_SET);
5939 order = get4() & 0xffff;
5940 if (get4() >> 8 != 0x526177) return; /* "Raw" */
5941 fseek (ifp, get4()+base, SEEK_SET);
5950 fseek (ifp, base+data, SEEK_SET);
5952 case 0x100: flip = "0653"[data & 3]-'0'; break;
5954 for( i=9,fp=&romm_cam[0][0]; --i>=0; ++fp )
5956 romm_coeff (romm_cam);
5959 FORC3 cam_mul[c] = getreal(11);
5961 case 0x108: raw_width = data; break;
5962 case 0x109: raw_height = data; break;
5963 case 0x10a: left_margin = data; break;
5964 case 0x10b: top_margin = data; break;
5965 case 0x10c: width = data; break;
5966 case 0x10d: height = data; break;
5967 case 0x10e: ph1.format = data; break;
5968 case 0x10f: data_offset = data+base; break;
5969 case 0x110: meta_offset = data+base;
5970 meta_length = len; break;
5971 case 0x112: ph1.key_off = save - 4; break;
5972 case 0x210: ph1.tag_210 = int_to_float(data); break;
5973 case 0x21a: ph1.tag_21a = data; break;
5974 case 0x21c: strip_offset = data+base; break;
5975 case 0x21d: ph1.black = data; break;
5976 case 0x222: ph1.split_col = data; break;
5977 case 0x223: ph1.black_off = data+base; break;
5980 fread (model, 1, 63, ifp);
5981 if ((cp = strstr(model," camera"))) *cp = 0;
5983 fseek (ifp, save, SEEK_SET);
5985 load_raw = ph1.format < 3 ?
5986 &CLASS phase_one_load_raw : &CLASS phase_one_load_raw_c;
5988 strcpy (make, "Phase One");
5989 if (model[0]) return;
5990 switch (raw_height) {
5991 case 2060: strcpy (model,"LightPhase"); break;
5992 case 2682: strcpy (model,"H 10"); break;
5993 case 4128: strcpy (model,"H 20"); break;
5994 case 5488: strcpy (model,"H 25"); break;
5998 void CLASS parse_fuji (int offset)
6000 unsigned entries, tag, len, save, c;
6002 fseek (ifp, offset, SEEK_SET);
6004 if (entries > 255) return;
6010 raw_height = get2();
6012 } else if (tag == 0x121) {
6014 if ((width = get2()) == 4284) width += 3;
6015 } else if (tag == 0x130) {
6016 fuji_layout = fgetc(ifp) >> 7;
6017 fuji_width = !(fgetc(ifp) & 8);
6018 } else if (tag == 0x2ff0) {
6019 FORC4 cam_mul[c ^ 1] = get2();
6020 } else if (tag == 0xc000) {
6023 if ((width = get4()) > 10000) width = get4();
6027 fseek (ifp, save+len, SEEK_SET);
6029 height <<= fuji_layout;
6030 width >>= fuji_layout;
6033 int CLASS parse_jpeg (int offset)
6035 int len, save, hlen, mark;
6037 fseek (ifp, offset, SEEK_SET);
6038 if (fgetc(ifp) != 0xff || fgetc(ifp) != 0xd8) return 0;
6040 while (fgetc(ifp) == 0xff && (mark = fgetc(ifp)) != 0xda) {
6044 if (mark == 0xc0 || mark == 0xc3) {
6046 raw_height = get2();
6051 if (get4() == 0x48454150) /* "HEAP" */
6052 parse_ciff (save+hlen, len-hlen);
6053 if (parse_tiff (save+6)) apply_tiff();
6054 fseek (ifp, save+len, SEEK_SET);
6059 void CLASS parse_riff()
6061 unsigned i, size, end;
6062 char tag[4], date[64], month[64];
6063 static const char mon[12][4] =
6064 { "Jan","Feb","Mar","Apr","May","Jun","Jul","Aug","Sep","Oct","Nov","Dec" };
6068 fread (tag, 4, 1, ifp);
6070 end = ftell(ifp) + size;
6071 if (!memcmp(tag,"RIFF",4) || !memcmp(tag,"LIST",4)) {
6073 while (ftell(ifp)+7 < end)
6075 } else if (!memcmp(tag,"nctg",4)) {
6076 while (ftell(ifp)+7 < end) {
6079 if ((i+1) >> 1 == 10 && size == 20)
6081 else fseek (ifp, size, SEEK_CUR);
6083 } else if (!memcmp(tag,"IDIT",4) && size < 64) {
6084 fread (date, 64, 1, ifp);
6086 memset (&t, 0, sizeof t);
6087 if (sscanf (date, "%*s %s %d %d:%d:%d %d", month, &t.tm_mday,
6088 &t.tm_hour, &t.tm_min, &t.tm_sec, &t.tm_year) == 6) {
6089 for (i=0; i < 12 && strcasecmp(mon[i],month); i++);
6093 timestamp = mktime(&t);
6096 fseek (ifp, size, SEEK_CUR);
6099 void CLASS parse_smal (int offset, int fsize)
6103 fseek (ifp, offset+2, SEEK_SET);
6107 fseek (ifp, 5, SEEK_CUR);
6108 if (get4() != fsize) return;
6109 if (ver > 6) data_offset = get4();
6110 raw_height = height = get2();
6111 raw_width = width = get2();
6112 strcpy (make, "SMaL");
6113 sprintf (model, "v%d %dx%d", ver, width, height);
6114 if (ver == 6) load_raw = &CLASS smal_v6_load_raw;
6115 if (ver == 9) load_raw = &CLASS smal_v9_load_raw;
6118 void CLASS parse_cine()
6120 unsigned off_head, off_setup, off_image, i;
6123 fseek (ifp, 4, SEEK_SET);
6124 is_raw = get2() == 2;
6125 fseek (ifp, 14, SEEK_CUR);
6131 if ((i = get4())) timestamp = i;
6132 fseek (ifp, off_head+4, SEEK_SET);
6134 raw_height = get4();
6135 switch (get2(),get2()) {
6136 case 8: load_raw = &CLASS eight_bit_load_raw; break;
6137 case 16: load_raw = &CLASS unpacked_load_raw;
6139 fseek (ifp, off_setup+792, SEEK_SET);
6140 strcpy (make, "CINE");
6141 sprintf (model, "%d", get4());
6142 fseek (ifp, 12, SEEK_CUR);
6143 switch ((i=get4()) & 0xffffff) {
6144 case 3: filters = 0x94949494; break;
6145 case 4: filters = 0x49494949; break;
6146 default: is_raw = 0;
6148 fseek (ifp, 72, SEEK_CUR);
6149 switch ((get4()+3600) % 360) {
6150 case 270: flip = 4; break;
6151 case 180: flip = 1; break;
6152 case 90: flip = 7; break;
6155 cam_mul[0] = getreal(11);
6156 cam_mul[2] = getreal(11);
6157 maximum = ~(-1 << get4());
6158 fseek (ifp, 668, SEEK_CUR);
6159 shutter = get4()/1000000000.0;
6160 fseek (ifp, off_image, SEEK_SET);
6161 if (shot_select < is_raw)
6162 fseek (ifp, shot_select*8, SEEK_CUR);
6163 data_offset = (INT64) get4() + 8;
6164 data_offset += (INT64) get4() << 32;
6167 void CLASS parse_redcine()
6169 unsigned i, len, rdvo;
6173 fseek (ifp, 52, SEEK_SET);
6176 fseek (ifp, 0, SEEK_END);
6177 fseek (ifp, -(i = ftello(ifp) & 511), SEEK_CUR);
6178 if (get4() != i || get4() != 0x52454f42) {
6179 fprintf (stderr,_("%s: Tail is missing, parsing from head...\n"), ifname);
6180 fseek (ifp, 0, SEEK_SET);
6181 while ((len = get4()) != EOF) {
6182 if (get4() == 0x52454456)
6183 if (is_raw++ == shot_select)
6184 data_offset = ftello(ifp) - 8;
6185 fseek (ifp, len-8, SEEK_CUR);
6189 fseek (ifp, 12, SEEK_CUR);
6191 fseeko (ifp, rdvo+8 + shot_select*4, SEEK_SET);
6192 data_offset = get4();
6196 char * CLASS foveon_gets (int offset, char *str, int len)
6199 fseek (ifp, offset, SEEK_SET);
6200 for (i=0; i < len-1; i++)
6201 if ((str[i] = get2()) == 0) break;
6206 void CLASS parse_foveon()
6208 int entries, img=0, off, len, tag, save, i, wide, high, pent, poff[256][2];
6209 char name[64], value[64];
6211 order = 0x4949; /* Little-endian */
6212 fseek (ifp, 36, SEEK_SET);
6214 fseek (ifp, -4, SEEK_END);
6215 fseek (ifp, get4(), SEEK_SET);
6216 if (get4() != 0x64434553) return; /* SECd */
6217 entries = (get4(),get4());
6223 fseek (ifp, off, SEEK_SET);
6224 if (get4() != (0x20434553 | (tag << 24))) return;
6226 case 0x47414d49: /* IMAG */
6227 case 0x32414d49: /* IMA2 */
6228 fseek (ifp, 8, SEEK_CUR);
6232 if (wide > raw_width && high > raw_height) {
6234 case 5: load_flags = 1;
6235 case 6: load_raw = &CLASS foveon_sd_load_raw; break;
6236 case 30: load_raw = &CLASS foveon_dp_load_raw; break;
6237 default: load_raw = 0;
6241 data_offset = off+28;
6243 fseek (ifp, off+28, SEEK_SET);
6244 if (fgetc(ifp) == 0xff && fgetc(ifp) == 0xd8
6245 && thumb_length < len-28) {
6246 thumb_offset = off+28;
6247 thumb_length = len-28;
6248 write_thumb = &CLASS jpeg_thumb;
6250 if (++img == 2 && !thumb_length) {
6251 thumb_offset = off+24;
6253 thumb_height = high;
6254 write_thumb = &CLASS foveon_thumb;
6257 case 0x464d4143: /* CAMF */
6258 meta_offset = off+8;
6259 meta_length = len-28;
6261 case 0x504f5250: /* PROP */
6262 pent = (get4(),get4());
6263 fseek (ifp, 12, SEEK_CUR);
6265 if ((unsigned) pent > 256) pent=256;
6266 for (i=0; i < pent*2; i++)
6267 poff[0][i] = off + get4()*2;
6268 for (i=0; i < pent; i++) {
6269 foveon_gets (poff[i][0], name, 64);
6270 foveon_gets (poff[i][1], value, 64);
6271 if (!strcmp (name, "ISO"))
6272 iso_speed = atoi(value);
6273 if (!strcmp (name, "CAMMANUF"))
6274 strcpy (make, value);
6275 if (!strcmp (name, "CAMMODEL"))
6276 strcpy (model, value);
6277 if (!strcmp (name, "WB_DESC"))
6278 strcpy (model2, value);
6279 if (!strcmp (name, "TIME"))
6280 timestamp = atoi(value);
6281 if (!strcmp (name, "EXPTIME"))
6282 shutter = atoi(value) / 1000000.0;
6283 if (!strcmp (name, "APERTURE"))
6284 aperture = atof(value);
6285 if (!strcmp (name, "FLENGTH"))
6286 focal_len = atof(value);
6289 timestamp = mktime (gmtime (×tamp));
6292 fseek (ifp, save, SEEK_SET);
6298 All matrices are from Adobe DNG Converter unless otherwise noted.
6300 void CLASS adobe_coeff (const char *make, const char *model)
6302 static const struct {
6304 short black, maximum, trans[12];
6306 { "AGFAPHOTO DC-833m", 0, 0, /* DJC */
6307 { 11438,-3762,-1115,-2409,9914,2497,-1227,2295,5300 } },
6308 { "Apple QuickTake", 0, 0, /* DJC */
6309 { 21392,-5653,-3353,2406,8010,-415,7166,1427,2078 } },
6310 { "Canon EOS D2000", 0, 0,
6311 { 24542,-10860,-3401,-1490,11370,-297,2858,-605,3225 } },
6312 { "Canon EOS D6000", 0, 0,
6313 { 20482,-7172,-3125,-1033,10410,-285,2542,226,3136 } },
6314 { "Canon EOS D30", 0, 0,
6315 { 9805,-2689,-1312,-5803,13064,3068,-2438,3075,8775 } },
6316 { "Canon EOS D60", 0, 0xfa0,
6317 { 6188,-1341,-890,-7168,14489,2937,-2640,3228,8483 } },
6318 { "Canon EOS 5D Mark III", 0, 0x3c80,
6319 { 6722,-635,-963,-4287,12460,2028,-908,2162,5668 } },
6320 { "Canon EOS 5D Mark II", 0, 0x3cf0,
6321 { 4716,603,-830,-7798,15474,2480,-1496,1937,6651 } },
6322 { "Canon EOS 5D", 0, 0xe6c,
6323 { 6347,-479,-972,-8297,15954,2480,-1968,2131,7649 } },
6324 { "Canon EOS 6D", 0, 0x3c82,
6325 { 7034,-804,-1014,-4420,12564,2058,-851,1994,5758 } },
6326 { "Canon EOS 7D", 0, 0x3510,
6327 { 6844,-996,-856,-3876,11761,2396,-593,1772,6198 } },
6328 { "Canon EOS 10D", 0, 0xfa0,
6329 { 8197,-2000,-1118,-6714,14335,2592,-2536,3178,8266 } },
6330 { "Canon EOS 20Da", 0, 0,
6331 { 14155,-5065,-1382,-6550,14633,2039,-1623,1824,6561 } },
6332 { "Canon EOS 20D", 0, 0xfff,
6333 { 6599,-537,-891,-8071,15783,2424,-1983,2234,7462 } },
6334 { "Canon EOS 30D", 0, 0,
6335 { 6257,-303,-1000,-7880,15621,2396,-1714,1904,7046 } },
6336 { "Canon EOS 40D", 0, 0x3f60,
6337 { 6071,-747,-856,-7653,15365,2441,-2025,2553,7315 } },
6338 { "Canon EOS 50D", 0, 0x3d93,
6339 { 4920,616,-593,-6493,13964,2784,-1774,3178,7005 } },
6340 { "Canon EOS 60D", 0, 0x2ff7,
6341 { 6719,-994,-925,-4408,12426,2211,-887,2129,6051 } },
6342 { "Canon EOS 300D", 0, 0xfa0,
6343 { 8197,-2000,-1118,-6714,14335,2592,-2536,3178,8266 } },
6344 { "Canon EOS 350D", 0, 0xfff,
6345 { 6018,-617,-965,-8645,15881,2975,-1530,1719,7642 } },
6346 { "Canon EOS 400D", 0, 0xe8e,
6347 { 7054,-1501,-990,-8156,15544,2812,-1278,1414,7796 } },
6348 { "Canon EOS 450D", 0, 0x390d,
6349 { 5784,-262,-821,-7539,15064,2672,-1982,2681,7427 } },
6350 { "Canon EOS 500D", 0, 0x3479,
6351 { 4763,712,-646,-6821,14399,2640,-1921,3276,6561 } },
6352 { "Canon EOS 550D", 0, 0x3dd7,
6353 { 6941,-1164,-857,-3825,11597,2534,-416,1540,6039 } },
6354 { "Canon EOS 600D", 0, 0x3510,
6355 { 6461,-907,-882,-4300,12184,2378,-819,1944,5931 } },
6356 { "Canon EOS 650D", 0, 0x354d,
6357 { 6602,-841,-939,-4472,12458,2247,-975,2039,6148 } },
6358 { "Canon EOS 1000D", 0, 0xe43,
6359 { 6771,-1139,-977,-7818,15123,2928,-1244,1437,7533 } },
6360 { "Canon EOS 1100D", 0, 0x3510,
6361 { 6444,-904,-893,-4563,12308,2535,-903,2016,6728 } },
6362 { "Canon EOS M", 0, 0,
6363 { 6602,-841,-939,-4472,12458,2247,-975,2039,6148 } },
6364 { "Canon EOS-1Ds Mark III", 0, 0x3bb0,
6365 { 5859,-211,-930,-8255,16017,2353,-1732,1887,7448 } },
6366 { "Canon EOS-1Ds Mark II", 0, 0xe80,
6367 { 6517,-602,-867,-8180,15926,2378,-1618,1771,7633 } },
6368 { "Canon EOS-1D Mark IV", 0, 0x3bb0,
6369 { 6014,-220,-795,-4109,12014,2361,-561,1824,5787 } },
6370 { "Canon EOS-1D Mark III", 0, 0x3bb0,
6371 { 6291,-540,-976,-8350,16145,2311,-1714,1858,7326 } },
6372 { "Canon EOS-1D Mark II N", 0, 0xe80,
6373 { 6240,-466,-822,-8180,15825,2500,-1801,1938,8042 } },
6374 { "Canon EOS-1D Mark II", 0, 0xe80,
6375 { 6264,-582,-724,-8312,15948,2504,-1744,1919,8664 } },
6376 { "Canon EOS-1DS", 0, 0xe20,
6377 { 4374,3631,-1743,-7520,15212,2472,-2892,3632,8161 } },
6378 { "Canon EOS-1D X", 0, 0x3c4e,
6379 { 6847,-614,-1014,-4669,12737,2139,-1197,2488,6846 } },
6380 { "Canon EOS-1D", 0, 0xe20,
6381 { 6806,-179,-1020,-8097,16415,1687,-3267,4236,7690 } },
6382 { "Canon EOS", 0, 0,
6383 { 8197,-2000,-1118,-6714,14335,2592,-2536,3178,8266 } },
6384 { "Canon PowerShot A530", 0, 0,
6385 { 0 } }, /* don't want the A5 matrix */
6386 { "Canon PowerShot A50", 0, 0,
6387 { -5300,9846,1776,3436,684,3939,-5540,9879,6200,-1404,11175,217 } },
6388 { "Canon PowerShot A5", 0, 0,
6389 { -4801,9475,1952,2926,1611,4094,-5259,10164,5947,-1554,10883,547 } },
6390 { "Canon PowerShot G10", 0, 0,
6391 { 11093,-3906,-1028,-5047,12492,2879,-1003,1750,5561 } },
6392 { "Canon PowerShot G11", 0, 0,
6393 { 12177,-4817,-1069,-1612,9864,2049,-98,850,4471 } },
6394 { "Canon PowerShot G12", 0, 0,
6395 { 13244,-5501,-1248,-1508,9858,1935,-270,1083,4366 } },
6396 { "Canon PowerShot G15", 0, 0,
6397 { 7474,-2301,-567,-4056,11456,2975,-222,716,4181 } },
6398 { "Canon PowerShot G1 X", 0, 0,
6399 { 7378,-1255,-1043,-4088,12251,2048,-876,1946,5805 } },
6400 { "Canon PowerShot G1", 0, 0,
6401 { -4778,9467,2172,4743,-1141,4344,-5146,9908,6077,-1566,11051,557 } },
6402 { "Canon PowerShot G2", 0, 0,
6403 { 9087,-2693,-1049,-6715,14382,2537,-2291,2819,7790 } },
6404 { "Canon PowerShot G3", 0, 0,
6405 { 9212,-2781,-1073,-6573,14189,2605,-2300,2844,7664 } },
6406 { "Canon PowerShot G5", 0, 0,
6407 { 9757,-2872,-933,-5972,13861,2301,-1622,2328,7212 } },
6408 { "Canon PowerShot G6", 0, 0,
6409 { 9877,-3775,-871,-7613,14807,3072,-1448,1305,7485 } },
6410 { "Canon PowerShot G9", 0, 0,
6411 { 7368,-2141,-598,-5621,13254,2625,-1418,1696,5743 } },
6412 { "Canon PowerShot Pro1", 0, 0,
6413 { 10062,-3522,-999,-7643,15117,2730,-765,817,7323 } },
6414 { "Canon PowerShot Pro70", 34, 0,
6415 { -4155,9818,1529,3939,-25,4522,-5521,9870,6610,-2238,10873,1342 } },
6416 { "Canon PowerShot Pro90", 0, 0,
6417 { -4963,9896,2235,4642,-987,4294,-5162,10011,5859,-1770,11230,577 } },
6418 { "Canon PowerShot S30", 0, 0,
6419 { 10566,-3652,-1129,-6552,14662,2006,-2197,2581,7670 } },
6420 { "Canon PowerShot S40", 0, 0,
6421 { 8510,-2487,-940,-6869,14231,2900,-2318,2829,9013 } },
6422 { "Canon PowerShot S45", 0, 0,
6423 { 8163,-2333,-955,-6682,14174,2751,-2077,2597,8041 } },
6424 { "Canon PowerShot S50", 0, 0,
6425 { 8882,-2571,-863,-6348,14234,2288,-1516,2172,6569 } },
6426 { "Canon PowerShot S60", 0, 0,
6427 { 8795,-2482,-797,-7804,15403,2573,-1422,1996,7082 } },
6428 { "Canon PowerShot S70", 0, 0,
6429 { 9976,-3810,-832,-7115,14463,2906,-901,989,7889 } },
6430 { "Canon PowerShot S90", 0, 0,
6431 { 12374,-5016,-1049,-1677,9902,2078,-83,852,4683 } },
6432 { "Canon PowerShot S95", 0, 0,
6433 { 13440,-5896,-1279,-1236,9598,1931,-180,1001,4651 } },
6434 { "Canon PowerShot S100", 0, 0,
6435 { 7968,-2565,-636,-2873,10697,2513,180,667,4211 } },
6436 { "Canon PowerShot S110", 0, 0,
6437 { 8039,-2643,-654,-3783,11230,2930,-206,690,4194 } },
6438 { "Canon PowerShot SX1 IS", 0, 0,
6439 { 6578,-259,-502,-5974,13030,3309,-308,1058,4970 } },
6440 { "Canon PowerShot SX50 HS", 0, 0,
6441 { 12432,-4753,-1247,-2110,10691,1629,-412,1623,4926 } },
6442 { "Canon PowerShot A470", 0, 0, /* DJC */
6443 { 12513,-4407,-1242,-2680,10276,2405,-878,2215,4734 } },
6444 { "Canon PowerShot A610", 0, 0, /* DJC */
6445 { 15591,-6402,-1592,-5365,13198,2168,-1300,1824,5075 } },
6446 { "Canon PowerShot A620", 0, 0, /* DJC */
6447 { 15265,-6193,-1558,-4125,12116,2010,-888,1639,5220 } },
6448 { "Canon PowerShot A630", 0, 0, /* DJC */
6449 { 14201,-5308,-1757,-6087,14472,1617,-2191,3105,5348 } },
6450 { "Canon PowerShot A640", 0, 0, /* DJC */
6451 { 13124,-5329,-1390,-3602,11658,1944,-1612,2863,4885 } },
6452 { "Canon PowerShot A650", 0, 0, /* DJC */
6453 { 9427,-3036,-959,-2581,10671,1911,-1039,1982,4430 } },
6454 { "Canon PowerShot A720", 0, 0, /* DJC */
6455 { 14573,-5482,-1546,-1266,9799,1468,-1040,1912,3810 } },
6456 { "Canon PowerShot S3 IS", 0, 0, /* DJC */
6457 { 14062,-5199,-1446,-4712,12470,2243,-1286,2028,4836 } },
6458 { "Canon PowerShot SX110 IS", 0, 0, /* DJC */
6459 { 14134,-5576,-1527,-1991,10719,1273,-1158,1929,3581 } },
6460 { "Canon PowerShot SX220", 0, 0, /* DJC */
6461 { 13898,-5076,-1447,-1405,10109,1297,-244,1860,3687 } },
6462 { "CASIO EX-S20", 0, 0, /* DJC */
6463 { 11634,-3924,-1128,-4968,12954,2015,-1588,2648,7206 } },
6464 { "CASIO EX-Z750", 0, 0, /* DJC */
6465 { 10819,-3873,-1099,-4903,13730,1175,-1755,3751,4632 } },
6466 { "CASIO EX-Z10", 128, 0xfff, /* DJC */
6467 { 9790,-3338,-603,-2321,10222,2099,-344,1273,4799 } },
6469 { 3390,480,-500,-800,3610,340,-550,2336,1192 } },
6471 { 3390,480,-500,-800,3610,340,-550,2336,1192 } },
6473 { 20183,-4295,-423,-3940,15330,3985,-280,4870,9800 } },
6474 { "Contax N Digital", 0, 0xf1e,
6475 { 7777,1285,-1053,-9280,16543,2916,-3677,5679,7060 } },
6476 { "EPSON R-D1", 0, 0,
6477 { 6827,-1878,-732,-8429,16012,2564,-704,592,7145 } },
6478 { "FUJIFILM E550", 0, 0,
6479 { 11044,-3888,-1120,-7248,15168,2208,-1531,2277,8069 } },
6480 { "FUJIFILM E900", 0, 0,
6481 { 9183,-2526,-1078,-7461,15071,2574,-2022,2440,8639 } },
6482 { "FUJIFILM F5", 0, 0,
6483 { 13690,-5358,-1474,-3369,11600,1998,-132,1554,4395 } },
6484 { "FUJIFILM F6", 0, 0,
6485 { 13690,-5358,-1474,-3369,11600,1998,-132,1554,4395 } },
6486 { "FUJIFILM F77", 0, 0xfe9,
6487 { 13690,-5358,-1474,-3369,11600,1998,-132,1554,4395 } },
6488 { "FUJIFILM F7", 0, 0,
6489 { 10004,-3219,-1201,-7036,15047,2107,-1863,2565,7736 } },
6490 { "FUJIFILM F8", 0, 0,
6491 { 13690,-5358,-1474,-3369,11600,1998,-132,1554,4395 } },
6492 { "FUJIFILM S100FS", 514, 0,
6493 { 11521,-4355,-1065,-6524,13767,3058,-1466,1984,6045 } },
6494 { "FUJIFILM S200EXR", 512, 0x3fff,
6495 { 11401,-4498,-1312,-5088,12751,2613,-838,1568,5941 } },
6496 { "FUJIFILM S20Pro", 0, 0,
6497 { 10004,-3219,-1201,-7036,15047,2107,-1863,2565,7736 } },
6498 { "FUJIFILM S2Pro", 128, 0,
6499 { 12492,-4690,-1402,-7033,15423,1647,-1507,2111,7697 } },
6500 { "FUJIFILM S3Pro", 0, 0,
6501 { 11807,-4612,-1294,-8927,16968,1988,-2120,2741,8006 } },
6502 { "FUJIFILM S5Pro", 0, 0,
6503 { 12300,-5110,-1304,-9117,17143,1998,-1947,2448,8100 } },
6504 { "FUJIFILM S5000", 0, 0,
6505 { 8754,-2732,-1019,-7204,15069,2276,-1702,2334,6982 } },
6506 { "FUJIFILM S5100", 0, 0,
6507 { 11940,-4431,-1255,-6766,14428,2542,-993,1165,7421 } },
6508 { "FUJIFILM S5500", 0, 0,
6509 { 11940,-4431,-1255,-6766,14428,2542,-993,1165,7421 } },
6510 { "FUJIFILM S5200", 0, 0,
6511 { 9636,-2804,-988,-7442,15040,2589,-1803,2311,8621 } },
6512 { "FUJIFILM S5600", 0, 0,
6513 { 9636,-2804,-988,-7442,15040,2589,-1803,2311,8621 } },
6514 { "FUJIFILM S6", 0, 0,
6515 { 12628,-4887,-1401,-6861,14996,1962,-2198,2782,7091 } },
6516 { "FUJIFILM S7000", 0, 0,
6517 { 10190,-3506,-1312,-7153,15051,2238,-2003,2399,7505 } },
6518 { "FUJIFILM S9000", 0, 0,
6519 { 10491,-3423,-1145,-7385,15027,2538,-1809,2275,8692 } },
6520 { "FUJIFILM S9500", 0, 0,
6521 { 10491,-3423,-1145,-7385,15027,2538,-1809,2275,8692 } },
6522 { "FUJIFILM S9100", 0, 0,
6523 { 12343,-4515,-1285,-7165,14899,2435,-1895,2496,8800 } },
6524 { "FUJIFILM S9600", 0, 0,
6525 { 12343,-4515,-1285,-7165,14899,2435,-1895,2496,8800 } },
6526 { "FUJIFILM IS-1", 0, 0,
6527 { 21461,-10807,-1441,-2332,10599,1999,289,875,7703 } },
6528 { "FUJIFILM IS Pro", 0, 0,
6529 { 12300,-5110,-1304,-9117,17143,1998,-1947,2448,8100 } },
6530 { "FUJIFILM HS10 HS11", 0, 0xf68,
6531 { 12440,-3954,-1183,-1123,9674,1708,-83,1614,4086 } },
6532 { "FUJIFILM HS20EXR", 0, 0,
6533 { 13690,-5358,-1474,-3369,11600,1998,-132,1554,4395 } },
6534 { "FUJIFILM HS3", 0, 0,
6535 { 13690,-5358,-1474,-3369,11600,1998,-132,1554,4395 } },
6536 { "FUJIFILM X100", 0, 0,
6537 { 12161,-4457,-1069,-5034,12874,2400,-795,1724,6904 } },
6538 { "FUJIFILM X10", 0, 0,
6539 { 13509,-6199,-1254,-4430,12733,1865,-331,1441,5022 } },
6540 { "FUJIFILM X-Pro1", 0, 0,
6541 { 10413,-3996,-993,-3721,11640,2361,-733,1540,6011 } },
6542 { "FUJIFILM X-E1", 0, 0,
6543 { 10413,-3996,-993,-3721,11640,2361,-733,1540,6011 } },
6544 { "FUJIFILM XF1", 0, 0,
6545 { 13509,-6199,-1254,-4430,12733,1865,-331,1441,5022 } },
6546 { "FUJIFILM X-S1", 0, 0,
6547 { 13509,-6199,-1254,-4430,12733,1865,-331,1441,5022 } },
6548 { "Imacon Ixpress", 0, 0, /* DJC */
6549 { 7025,-1415,-704,-5188,13765,1424,-1248,2742,6038 } },
6550 { "KODAK NC2000", 0, 0,
6551 { 13891,-6055,-803,-465,9919,642,2121,82,1291 } },
6552 { "Kodak DCS315C", 8, 0,
6553 { 17523,-4827,-2510,756,8546,-137,6113,1649,2250 } },
6554 { "Kodak DCS330C", 8, 0,
6555 { 20620,-7572,-2801,-103,10073,-396,3551,-233,2220 } },
6556 { "KODAK DCS420", 0, 0,
6557 { 10868,-1852,-644,-1537,11083,484,2343,628,2216 } },
6558 { "KODAK DCS460", 0, 0,
6559 { 10592,-2206,-967,-1944,11685,230,2206,670,1273 } },
6560 { "KODAK EOSDCS1", 0, 0,
6561 { 10592,-2206,-967,-1944,11685,230,2206,670,1273 } },
6562 { "KODAK EOSDCS3B", 0, 0,
6563 { 9898,-2700,-940,-2478,12219,206,1985,634,1031 } },
6564 { "Kodak DCS520C", 178, 0,
6565 { 24542,-10860,-3401,-1490,11370,-297,2858,-605,3225 } },
6566 { "Kodak DCS560C", 177, 0,
6567 { 20482,-7172,-3125,-1033,10410,-285,2542,226,3136 } },
6568 { "Kodak DCS620C", 177, 0,
6569 { 23617,-10175,-3149,-2054,11749,-272,2586,-489,3453 } },
6570 { "Kodak DCS620X", 176, 0,
6571 { 13095,-6231,154,12221,-21,-2137,895,4602,2258 } },
6572 { "Kodak DCS660C", 173, 0,
6573 { 18244,-6351,-2739,-791,11193,-521,3711,-129,2802 } },
6574 { "Kodak DCS720X", 0, 0,
6575 { 11775,-5884,950,9556,1846,-1286,-1019,6221,2728 } },
6576 { "Kodak DCS760C", 0, 0,
6577 { 16623,-6309,-1411,-4344,13923,323,2285,274,2926 } },
6578 { "Kodak DCS Pro SLR", 0, 0,
6579 { 5494,2393,-232,-6427,13850,2846,-1876,3997,5445 } },
6580 { "Kodak DCS Pro 14nx", 0, 0,
6581 { 5494,2393,-232,-6427,13850,2846,-1876,3997,5445 } },
6582 { "Kodak DCS Pro 14", 0, 0,
6583 { 7791,3128,-776,-8588,16458,2039,-2455,4006,6198 } },
6584 { "Kodak ProBack645", 0, 0,
6585 { 16414,-6060,-1470,-3555,13037,473,2545,122,4948 } },
6586 { "Kodak ProBack", 0, 0,
6587 { 21179,-8316,-2918,-915,11019,-165,3477,-180,4210 } },
6588 { "KODAK P712", 0, 0,
6589 { 9658,-3314,-823,-5163,12695,2768,-1342,1843,6044 } },
6590 { "KODAK P850", 0, 0xf7c,
6591 { 10511,-3836,-1102,-6946,14587,2558,-1481,1792,6246 } },
6592 { "KODAK P880", 0, 0xfff,
6593 { 12805,-4662,-1376,-7480,15267,2360,-1626,2194,7904 } },
6594 { "KODAK EasyShare Z980", 0, 0,
6595 { 11313,-3559,-1101,-3893,11891,2257,-1214,2398,4908 } },
6596 { "KODAK EasyShare Z981", 0, 0,
6597 { 12729,-4717,-1188,-1367,9187,2582,274,860,4411 } },
6598 { "KODAK EasyShare Z990", 0, 0xfed,
6599 { 11749,-4048,-1309,-1867,10572,1489,-138,1449,4522 } },
6600 { "KODAK EASYSHARE Z1015", 0, 0xef1,
6601 { 11265,-4286,-992,-4694,12343,2647,-1090,1523,5447 } },
6602 { "Leaf CMost", 0, 0,
6603 { 3952,2189,449,-6701,14585,2275,-4536,7349,6536 } },
6604 { "Leaf Valeo 6", 0, 0,
6605 { 3952,2189,449,-6701,14585,2275,-4536,7349,6536 } },
6606 { "Leaf Aptus 54S", 0, 0,
6607 { 8236,1746,-1314,-8251,15953,2428,-3673,5786,5771 } },
6608 { "Leaf Aptus 65", 0, 0,
6609 { 7914,1414,-1190,-8777,16582,2280,-2811,4605,5562 } },
6610 { "Leaf Aptus 75", 0, 0,
6611 { 7914,1414,-1190,-8777,16582,2280,-2811,4605,5562 } },
6613 { 8236,1746,-1314,-8251,15953,2428,-3673,5786,5771 } },
6614 { "Mamiya ZD", 0, 0,
6615 { 7645,2579,-1363,-8689,16717,2015,-3712,5941,5961 } },
6616 { "Micron 2010", 110, 0, /* DJC */
6617 { 16695,-3761,-2151,155,9682,163,3433,951,4904 } },
6618 { "Minolta DiMAGE 5", 0, 0xf7d,
6619 { 8983,-2942,-963,-6556,14476,2237,-2426,2887,8014 } },
6620 { "Minolta DiMAGE 7Hi", 0, 0xf7d,
6621 { 11368,-3894,-1242,-6521,14358,2339,-2475,3056,7285 } },
6622 { "Minolta DiMAGE 7", 0, 0xf7d,
6623 { 9144,-2777,-998,-6676,14556,2281,-2470,3019,7744 } },
6624 { "Minolta DiMAGE A1", 0, 0xf8b,
6625 { 9274,-2547,-1167,-8220,16323,1943,-2273,2720,8340 } },
6626 { "MINOLTA DiMAGE A200", 0, 0,
6627 { 8560,-2487,-986,-8112,15535,2771,-1209,1324,7743 } },
6628 { "Minolta DiMAGE A2", 0, 0xf8f,
6629 { 9097,-2726,-1053,-8073,15506,2762,-966,981,7763 } },
6630 { "Minolta DiMAGE Z2", 0, 0, /* DJC */
6631 { 11280,-3564,-1370,-4655,12374,2282,-1423,2168,5396 } },
6632 { "MINOLTA DYNAX 5", 0, 0xffb,
6633 { 10284,-3283,-1086,-7957,15762,2316,-829,882,6644 } },
6634 { "MINOLTA DYNAX 7", 0, 0xffb,
6635 { 10239,-3104,-1099,-8037,15727,2451,-927,925,6871 } },
6636 { "MOTOROLA PIXL", 0, 0, /* DJC */
6637 { 8898,-989,-1033,-3292,11619,1674,-661,3178,5216 } },
6638 { "NIKON D100", 0, 0,
6639 { 5902,-933,-782,-8983,16719,2354,-1402,1455,6464 } },
6640 { "NIKON D1H", 0, 0,
6641 { 7577,-2166,-926,-7454,15592,1934,-2377,2808,8606 } },
6642 { "NIKON D1X", 0, 0,
6643 { 7702,-2245,-975,-9114,17242,1875,-2679,3055,8521 } },
6644 { "NIKON D1", 0, 0, /* multiplied by 2.218750, 1.0, 1.148438 */
6645 { 16772,-4726,-2141,-7611,15713,1972,-2846,3494,9521 } },
6646 { "NIKON D200", 0, 0xfbc,
6647 { 8367,-2248,-763,-8758,16447,2422,-1527,1550,8053 } },
6648 { "NIKON D2H", 0, 0,
6649 { 5710,-901,-615,-8594,16617,2024,-2975,4120,6830 } },
6650 { "NIKON D2X", 0, 0,
6651 { 10231,-2769,-1255,-8301,15900,2552,-797,680,7148 } },
6652 { "NIKON D3000", 0, 0,
6653 { 8736,-2458,-935,-9075,16894,2251,-1354,1242,8263 } },
6654 { "NIKON D3100", 0, 0,
6655 { 7911,-2167,-813,-5327,13150,2408,-1288,2483,7968 } },
6656 { "NIKON D3200", 0, 0xfb9,
6657 { 7013,-1408,-635,-5268,12902,2640,-1470,2801,7379 } },
6658 { "NIKON D300", 0, 0,
6659 { 9030,-1992,-715,-8465,16302,2255,-2689,3217,8069 } },
6660 { "NIKON D3X", 0, 0,
6661 { 7171,-1986,-648,-8085,15555,2718,-2170,2512,7457 } },
6662 { "NIKON D3S", 0, 0,
6663 { 8828,-2406,-694,-4874,12603,2541,-660,1509,7587 } },
6665 { 8139,-2171,-663,-8747,16541,2295,-1925,2008,8093 } },
6666 { "NIKON D40X", 0, 0,
6667 { 8819,-2543,-911,-9025,16928,2151,-1329,1213,8449 } },
6668 { "NIKON D40", 0, 0,
6669 { 6992,-1668,-806,-8138,15748,2543,-874,850,7897 } },
6671 { 8598,-2848,-857,-5618,13606,2195,-1002,1773,7137 } },
6672 { "NIKON D5000", 0, 0xf00,
6673 { 7309,-1403,-519,-8474,16008,2622,-2433,2826,8064 } },
6674 { "NIKON D5100", 0, 0x3de6,
6675 { 8198,-2239,-724,-4871,12389,2798,-1043,2050,7181 } },
6676 { "NIKON D50", 0, 0,
6677 { 7732,-2422,-789,-8238,15884,2498,-859,783,7330 } },
6678 { "NIKON D600", 0, 0x3e07,
6679 { 8178,-2245,-609,-4857,12394,2776,-1207,2086,7298 } },
6680 { "NIKON D60", 0, 0,
6681 { 8736,-2458,-935,-9075,16894,2251,-1354,1242,8263 } },
6682 { "NIKON D7000", 0, 0,
6683 { 8198,-2239,-724,-4871,12389,2798,-1043,2050,7181 } },
6684 { "NIKON D700", 0, 0,
6685 { 8139,-2171,-663,-8747,16541,2295,-1925,2008,8093 } },
6686 { "NIKON D70", 0, 0,
6687 { 7732,-2422,-789,-8238,15884,2498,-859,783,7330 } },
6688 { "NIKON D800", 0, 0,
6689 { 7866,-2108,-555,-4869,12483,2681,-1176,2069,7501 } },
6690 { "NIKON D80", 0, 0,
6691 { 8629,-2410,-883,-9055,16940,2171,-1490,1363,8520 } },
6692 { "NIKON D90", 0, 0xf00,
6693 { 7309,-1403,-519,-8474,16008,2622,-2434,2826,8064 } },
6694 { "NIKON E950", 0, 0x3dd, /* DJC */
6695 { -3746,10611,1665,9621,-1734,2114,-2389,7082,3064,3406,6116,-244 } },
6696 { "NIKON E995", 0, 0, /* copied from E5000 */
6697 { -5547,11762,2189,5814,-558,3342,-4924,9840,5949,688,9083,96 } },
6698 { "NIKON E2100", 0, 0, /* copied from Z2, new white balance */
6699 { 13142,-4152,-1596,-4655,12374,2282,-1769,2696,6711} },
6700 { "NIKON E2500", 0, 0,
6701 { -5547,11762,2189,5814,-558,3342,-4924,9840,5949,688,9083,96 } },
6702 { "NIKON E3200", 0, 0, /* DJC */
6703 { 9846,-2085,-1019,-3278,11109,2170,-774,2134,5745 } },
6704 { "NIKON E4300", 0, 0, /* copied from Minolta DiMAGE Z2 */
6705 { 11280,-3564,-1370,-4655,12374,2282,-1423,2168,5396 } },
6706 { "NIKON E4500", 0, 0,
6707 { -5547,11762,2189,5814,-558,3342,-4924,9840,5949,688,9083,96 } },
6708 { "NIKON E5000", 0, 0,
6709 { -5547,11762,2189,5814,-558,3342,-4924,9840,5949,688,9083,96 } },
6710 { "NIKON E5400", 0, 0,
6711 { 9349,-2987,-1001,-7919,15766,2266,-2098,2680,6839 } },
6712 { "NIKON E5700", 0, 0,
6713 { -5368,11478,2368,5537,-113,3148,-4969,10021,5782,778,9028,211 } },
6714 { "NIKON E8400", 0, 0,
6715 { 7842,-2320,-992,-8154,15718,2599,-1098,1342,7560 } },
6716 { "NIKON E8700", 0, 0,
6717 { 8489,-2583,-1036,-8051,15583,2643,-1307,1407,7354 } },
6718 { "NIKON E8800", 0, 0,
6719 { 7971,-2314,-913,-8451,15762,2894,-1442,1520,7610 } },
6720 { "NIKON COOLPIX P6000", 0, 0,
6721 { 9698,-3367,-914,-4706,12584,2368,-837,968,5801 } },
6722 { "NIKON COOLPIX P7000", 0, 0,
6723 { 11432,-3679,-1111,-3169,11239,2202,-791,1380,4455 } },
6724 { "NIKON COOLPIX P7100", 0, 0,
6725 { 11053,-4269,-1024,-1976,10182,2088,-526,1263,4469 } },
6726 { "NIKON COOLPIX P7700", 200, 0,
6727 { 10321,-3920,-931,-2750,11146,1824,-442,1545,5539 } },
6728 { "NIKON 1 V2", 0, 0,
6729 { 6588,-1305,-693,-3277,10987,2634,-355,2016,5106 } },
6731 { 8994,-2667,-865,-4594,12324,2552,-699,1786,6260 } },
6732 { "OLYMPUS C5050", 0, 0,
6733 { 10508,-3124,-1273,-6079,14294,1901,-1653,2306,6237 } },
6734 { "OLYMPUS C5060", 0, 0,
6735 { 10445,-3362,-1307,-7662,15690,2058,-1135,1176,7602 } },
6736 { "OLYMPUS C7070", 0, 0,
6737 { 10252,-3531,-1095,-7114,14850,2436,-1451,1723,6365 } },
6738 { "OLYMPUS C70", 0, 0,
6739 { 10793,-3791,-1146,-7498,15177,2488,-1390,1577,7321 } },
6740 { "OLYMPUS C80", 0, 0,
6741 { 8606,-2509,-1014,-8238,15714,2703,-942,979,7760 } },
6742 { "OLYMPUS E-10", 0, 0xffc,
6743 { 12745,-4500,-1416,-6062,14542,1580,-1934,2256,6603 } },
6744 { "OLYMPUS E-1", 0, 0,
6745 { 11846,-4767,-945,-7027,15878,1089,-2699,4122,8311 } },
6746 { "OLYMPUS E-20", 0, 0xffc,
6747 { 13173,-4732,-1499,-5807,14036,1895,-2045,2452,7142 } },
6748 { "OLYMPUS E-300", 0, 0,
6749 { 7828,-1761,-348,-5788,14071,1830,-2853,4518,6557 } },
6750 { "OLYMPUS E-330", 0, 0,
6751 { 8961,-2473,-1084,-7979,15990,2067,-2319,3035,8249 } },
6752 { "OLYMPUS E-30", 0, 0xfbc,
6753 { 8144,-1861,-1111,-7763,15894,1929,-1865,2542,7607 } },
6754 { "OLYMPUS E-3", 0, 0xf99,
6755 { 9487,-2875,-1115,-7533,15606,2010,-1618,2100,7389 } },
6756 { "OLYMPUS E-400", 0, 0,
6757 { 6169,-1483,-21,-7107,14761,2536,-2904,3580,8568 } },
6758 { "OLYMPUS E-410", 0, 0xf6a,
6759 { 8856,-2582,-1026,-7761,15766,2082,-2009,2575,7469 } },
6760 { "OLYMPUS E-420", 0, 0xfd7,
6761 { 8746,-2425,-1095,-7594,15612,2073,-1780,2309,7416 } },
6762 { "OLYMPUS E-450", 0, 0xfd2,
6763 { 8745,-2425,-1095,-7594,15613,2073,-1780,2309,7416 } },
6764 { "OLYMPUS E-500", 0, 0,
6765 { 8136,-1968,-299,-5481,13742,1871,-2556,4205,6630 } },
6766 { "OLYMPUS E-510", 0, 0xf6a,
6767 { 8785,-2529,-1033,-7639,15624,2112,-1783,2300,7817 } },
6768 { "OLYMPUS E-520", 0, 0xfd2,
6769 { 8344,-2322,-1020,-7596,15635,2048,-1748,2269,7287 } },
6770 { "OLYMPUS E-5", 0, 0xeec,
6771 { 11200,-3783,-1325,-4576,12593,2206,-695,1742,7504 } },
6772 { "OLYMPUS E-600", 0, 0xfaf,
6773 { 8453,-2198,-1092,-7609,15681,2008,-1725,2337,7824 } },
6774 { "OLYMPUS E-620", 0, 0xfaf,
6775 { 8453,-2198,-1092,-7609,15681,2008,-1725,2337,7824 } },
6776 { "OLYMPUS E-P1", 0, 0xffd,
6777 { 8343,-2050,-1021,-7715,15705,2103,-1831,2380,8235 } },
6778 { "OLYMPUS E-P2", 0, 0xffd,
6779 { 8343,-2050,-1021,-7715,15705,2103,-1831,2380,8235 } },
6780 { "OLYMPUS E-P3", 0, 0,
6781 { 7575,-2159,-571,-3722,11341,2725,-1434,2819,6271 } },
6782 { "OLYMPUS E-PL1s", 0, 0,
6783 { 11409,-3872,-1393,-4572,12757,2003,-709,1810,7415 } },
6784 { "OLYMPUS E-PL1", 0, 0,
6785 { 11408,-4289,-1215,-4286,12385,2118,-387,1467,7787 } },
6786 { "OLYMPUS E-PL2", 0, 0,
6787 { 15030,-5552,-1806,-3987,12387,1767,-592,1670,7023 } },
6788 { "OLYMPUS E-PL3", 0, 0,
6789 { 7575,-2159,-571,-3722,11341,2725,-1434,2819,6271 } },
6790 { "OLYMPUS E-PL5", 0, 0xfcb,
6791 { 8380,-2630,-639,-2887,10725,2496,-627,1427,5438 } },
6792 { "OLYMPUS E-PM1", 0, 0,
6793 { 7575,-2159,-571,-3722,11341,2725,-1434,2819,6271 } },
6794 { "OLYMPUS E-PM2", 0, 0,
6795 { 8380,-2630,-639,-2887,10725,2496,-627,1427,5438 } },
6796 { "OLYMPUS E-M5", 0, 0xfe1,
6797 { 8380,-2630,-639,-2887,10725,2496,-627,1427,5438 } },
6798 { "OLYMPUS SP350", 0, 0,
6799 { 12078,-4836,-1069,-6671,14306,2578,-786,939,7418 } },
6800 { "OLYMPUS SP3", 0, 0,
6801 { 11766,-4445,-1067,-6901,14421,2707,-1029,1217,7572 } },
6802 { "OLYMPUS SP500UZ", 0, 0xfff,
6803 { 9493,-3415,-666,-5211,12334,3260,-1548,2262,6482 } },
6804 { "OLYMPUS SP510UZ", 0, 0xffe,
6805 { 10593,-3607,-1010,-5881,13127,3084,-1200,1805,6721 } },
6806 { "OLYMPUS SP550UZ", 0, 0xffe,
6807 { 11597,-4006,-1049,-5432,12799,2957,-1029,1750,6516 } },
6808 { "OLYMPUS SP560UZ", 0, 0xff9,
6809 { 10915,-3677,-982,-5587,12986,2911,-1168,1968,6223 } },
6810 { "OLYMPUS SP570UZ", 0, 0,
6811 { 11522,-4044,-1146,-4736,12172,2904,-988,1829,6039 } },
6812 { "OLYMPUS XZ-1", 0, 0,
6813 { 10901,-4095,-1074,-1141,9208,2293,-62,1417,5158 } },
6814 { "OLYMPUS XZ-2", 0, 0,
6815 { 9777,-3483,-925,-2886,11297,1800,-602,1663,5134 } },
6816 { "PENTAX *ist DL2", 0, 0,
6817 { 10504,-2438,-1189,-8603,16207,2531,-1022,863,12242 } },
6818 { "PENTAX *ist DL", 0, 0,
6819 { 10829,-2838,-1115,-8339,15817,2696,-837,680,11939 } },
6820 { "PENTAX *ist DS2", 0, 0,
6821 { 10504,-2438,-1189,-8603,16207,2531,-1022,863,12242 } },
6822 { "PENTAX *ist DS", 0, 0,
6823 { 10371,-2333,-1206,-8688,16231,2602,-1230,1116,11282 } },
6824 { "PENTAX *ist D", 0, 0,
6825 { 9651,-2059,-1189,-8881,16512,2487,-1460,1345,10687 } },
6826 { "PENTAX K10D", 0, 0,
6827 { 9566,-2863,-803,-7170,15172,2112,-818,803,9705 } },
6828 { "PENTAX K1", 0, 0,
6829 { 11095,-3157,-1324,-8377,15834,2720,-1108,947,11688 } },
6830 { "PENTAX K20D", 0, 0,
6831 { 9427,-2714,-868,-7493,16092,1373,-2199,3264,7180 } },
6832 { "PENTAX K200D", 0, 0,
6833 { 9186,-2678,-907,-8693,16517,2260,-1129,1094,8524 } },
6834 { "PENTAX K2000", 0, 0,
6835 { 11057,-3604,-1155,-5152,13046,2329,-282,375,8104 } },
6836 { "PENTAX K-m", 0, 0,
6837 { 11057,-3604,-1155,-5152,13046,2329,-282,375,8104 } },
6838 { "PENTAX K-x", 0, 0,
6839 { 8843,-2837,-625,-5025,12644,2668,-411,1234,7410 } },
6840 { "PENTAX K-r", 0, 0,
6841 { 9895,-3077,-850,-5304,13035,2521,-883,1768,6936 } },
6842 { "PENTAX K-5 II", 0, 0,
6843 { 8170,-2725,-639,-4440,12017,2744,-771,1465,6599 } },
6844 { "PENTAX K-5", 0, 0,
6845 { 8713,-2833,-743,-4342,11900,2772,-722,1543,6247 } },
6846 { "PENTAX K-7", 0, 0,
6847 { 9142,-2947,-678,-8648,16967,1663,-2224,2898,8615 } },
6848 { "PENTAX 645D", 0, 0x3e00,
6849 { 10646,-3593,-1158,-3329,11699,1831,-667,2874,6287 } },
6850 { "Panasonic DMC-FZ8", 0, 0xf7f,
6851 { 8986,-2755,-802,-6341,13575,3077,-1476,2144,6379 } },
6852 { "Panasonic DMC-FZ18", 0, 0,
6853 { 9932,-3060,-935,-5809,13331,2753,-1267,2155,5575 } },
6854 { "Panasonic DMC-FZ28", 15, 0xf96,
6855 { 10109,-3488,-993,-5412,12812,2916,-1305,2140,5543 } },
6856 { "Panasonic DMC-FZ30", 0, 0xf94,
6857 { 10976,-4029,-1141,-7918,15491,2600,-1670,2071,8246 } },
6858 { "Panasonic DMC-FZ3", 143, 0,
6859 { 9938,-2780,-890,-4604,12393,2480,-1117,2304,4620 } },
6860 { "Panasonic DMC-FZ4", 143, 0,
6861 { 13639,-5535,-1371,-1698,9633,2430,316,1152,4108 } },
6862 { "Panasonic DMC-FZ50", 0, 0,
6863 { 7906,-2709,-594,-6231,13351,3220,-1922,2631,6537 } },
6864 { "LEICA V-LUX1", 0, 0,
6865 { 7906,-2709,-594,-6231,13351,3220,-1922,2631,6537 } },
6866 { "Panasonic DMC-L10", 15, 0xf96,
6867 { 8025,-1942,-1050,-7920,15904,2100,-2456,3005,7039 } },
6868 { "Panasonic DMC-L1", 0, 0xf7f,
6869 { 8054,-1885,-1025,-8349,16367,2040,-2805,3542,7629 } },
6870 { "LEICA DIGILUX 3", 0, 0xf7f,
6871 { 8054,-1885,-1025,-8349,16367,2040,-2805,3542,7629 } },
6872 { "Panasonic DMC-LC1", 0, 0,
6873 { 11340,-4069,-1275,-7555,15266,2448,-2960,3426,7685 } },
6874 { "LEICA DIGILUX 2", 0, 0,
6875 { 11340,-4069,-1275,-7555,15266,2448,-2960,3426,7685 } },
6876 { "Panasonic DMC-LX1", 0, 0xf7f,
6877 { 10704,-4187,-1230,-8314,15952,2501,-920,945,8927 } },
6878 { "LEICA D-LUX2", 0, 0xf7f,
6879 { 10704,-4187,-1230,-8314,15952,2501,-920,945,8927 } },
6880 { "Panasonic DMC-LX2", 0, 0,
6881 { 8048,-2810,-623,-6450,13519,3272,-1700,2146,7049 } },
6882 { "LEICA D-LUX3", 0, 0,
6883 { 8048,-2810,-623,-6450,13519,3272,-1700,2146,7049 } },
6884 { "Panasonic DMC-LX3", 15, 0,
6885 { 8128,-2668,-655,-6134,13307,3161,-1782,2568,6083 } },
6886 { "LEICA D-LUX 4", 15, 0,
6887 { 8128,-2668,-655,-6134,13307,3161,-1782,2568,6083 } },
6888 { "Panasonic DMC-LX5", 143, 0,
6889 { 10909,-4295,-948,-1333,9306,2399,22,1738,4582 } },
6890 { "LEICA D-LUX 5", 143, 0,
6891 { 10909,-4295,-948,-1333,9306,2399,22,1738,4582 } },
6892 { "Panasonic DMC-LX7", 143, 0,
6893 { 10148,-3743,-991,-2837,11366,1659,-701,1893,4899 } },
6894 { "LEICA D-LUX 6", 143, 0,
6895 { 10148,-3743,-991,-2837,11366,1659,-701,1893,4899 } },
6896 { "Panasonic DMC-FZ100", 143, 0xfff,
6897 { 16197,-6146,-1761,-2393,10765,1869,366,2238,5248 } },
6898 { "LEICA V-LUX 2", 143, 0xfff,
6899 { 16197,-6146,-1761,-2393,10765,1869,366,2238,5248 } },
6900 { "Panasonic DMC-FZ150", 143, 0xfff,
6901 { 11904,-4541,-1189,-2355,10899,1662,-296,1586,4289 } },
6902 { "LEICA V-LUX 3", 143, 0xfff,
6903 { 11904,-4541,-1189,-2355,10899,1662,-296,1586,4289 } },
6904 { "Panasonic DMC-FZ200", 143, 0xfff,
6905 { 8112,-2563,-740,-3730,11784,2197,-941,2075,4933 } },
6906 { "LEICA V-LUX 4", 143, 0xfff,
6907 { 8112,-2563,-740,-3730,11784,2197,-941,2075,4933 } },
6908 { "Panasonic DMC-FX150", 15, 0xfff,
6909 { 9082,-2907,-925,-6119,13377,3058,-1797,2641,5609 } },
6910 { "Panasonic DMC-G10", 0, 0,
6911 { 10113,-3400,-1114,-4765,12683,2317,-377,1437,6710 } },
6912 { "Panasonic DMC-G1", 15, 0xf94,
6913 { 8199,-2065,-1056,-8124,16156,2033,-2458,3022,7220 } },
6914 { "Panasonic DMC-G2", 15, 0xf3c,
6915 { 10113,-3400,-1114,-4765,12683,2317,-377,1437,6710 } },
6916 { "Panasonic DMC-G3", 143, 0xfff,
6917 { 6763,-1919,-863,-3868,11515,2684,-1216,2387,5879 } },
6918 { "Panasonic DMC-G5", 143, 0xfff,
6919 { 7798,-2562,-740,-3879,11584,2613,-1055,2248,5434 } },
6920 { "Panasonic DMC-GF1", 15, 0xf92,
6921 { 7888,-1902,-1011,-8106,16085,2099,-2353,2866,7330 } },
6922 { "Panasonic DMC-GF2", 143, 0xfff,
6923 { 7888,-1902,-1011,-8106,16085,2099,-2353,2866,7330 } },
6924 { "Panasonic DMC-GF3", 143, 0xfff,
6925 { 9051,-2468,-1204,-5212,13276,2121,-1197,2510,6890 } },
6926 { "Panasonic DMC-GF5", 143, 0xfff,
6927 { 8228,-2945,-660,-3938,11792,2430,-1094,2278,5793 } },
6928 { "Panasonic DMC-GH1", 15, 0xf92,
6929 { 6299,-1466,-532,-6535,13852,2969,-2331,3112,5984 } },
6930 { "Panasonic DMC-GH2", 15, 0xf95,
6931 { 7780,-2410,-806,-3913,11724,2484,-1018,2390,5298 } },
6932 { "Panasonic DMC-GH3", 144, 0,
6933 { 6559,-1752,-491,-3672,11407,2586,-962,1875,5130 } },
6934 { "Panasonic DMC-GX1", 143, 0,
6935 { 6763,-1919,-863,-3868,11515,2684,-1216,2387,5879 } },
6936 { "Phase One H 20", 0, 0, /* DJC */
6937 { 1313,1855,-109,-6715,15908,808,-327,1840,6020 } },
6938 { "Phase One H 25", 0, 0,
6939 { 2905,732,-237,-8134,16626,1476,-3038,4253,7517 } },
6940 { "Phase One P 2", 0, 0,
6941 { 2905,732,-237,-8134,16626,1476,-3038,4253,7517 } },
6942 { "Phase One P 30", 0, 0,
6943 { 4516,-245,-37,-7020,14976,2173,-3206,4671,7087 } },
6944 { "Phase One P 45", 0, 0,
6945 { 5053,-24,-117,-5684,14076,1702,-2619,4492,5849 } },
6946 { "Phase One P40", 0, 0,
6947 { 8035,435,-962,-6001,13872,2320,-1159,3065,5434 } },
6948 { "Phase One P65", 0, 0,
6949 { 8035,435,-962,-6001,13872,2320,-1159,3065,5434 } },
6950 { "RED ONE", 704, 0xffff, /* DJC */
6951 { 21014,-7891,-2613,-3056,12201,856,-2203,5125,8042 } },
6952 { "SAMSUNG EX1", 0, 0x3e00,
6953 { 8898,-2498,-994,-3144,11328,2066,-760,1381,4576 } },
6954 { "SAMSUNG EX2F", 0, 0x7ff,
6955 { 10648,-3897,-1055,-2022,10573,1668,-492,1611,4742 } },
6956 { "SAMSUNG NX2", 0, 0xfff, /* NX20, NX200, NX210 */
6957 { 6933,-2268,-753,-4921,13387,1647,-803,1641,6096 } },
6958 { "SAMSUNG NX1000", 0, 0,
6959 { 6933,-2268,-753,-4921,13387,1647,-803,1641,6096 } },
6960 { "SAMSUNG NX", 0, 0, /* NX5, NX10, NX11, NX100 */
6961 { 10332,-3234,-1168,-6111,14639,1520,-1352,2647,8331 } },
6962 { "SAMSUNG WB2000", 0, 0xfff,
6963 { 12093,-3557,-1155,-1000,9534,1733,-22,1787,4576 } },
6964 { "SAMSUNG GX-1", 0, 0,
6965 { 10504,-2438,-1189,-8603,16207,2531,-1022,863,12242 } },
6966 { "SAMSUNG S85", 0, 0xffff, /* DJC */
6967 { 11885,-3968,-1473,-4214,12299,1916,-835,1655,5549 } },
6968 { "Sinar", 0, 0, /* DJC */
6969 { 16442,-2956,-2422,-2877,12128,750,-1136,6066,4559 } },
6970 { "SONY DSC-F828", 0, 0,
6971 { 7924,-1910,-777,-8226,15459,2998,-1517,2199,6818,-7242,11401,3481 } },
6972 { "SONY DSC-R1", 512, 0,
6973 { 8512,-2641,-694,-8042,15670,2526,-1821,2117,7414 } },
6974 { "SONY DSC-V3", 0, 0,
6975 { 7511,-2571,-692,-7894,15088,3060,-948,1111,8128 } },
6976 { "SONY DSC-RX100", 200, 0,
6977 { 8651,-2754,-1057,-3464,12207,1373,-568,1398,4434 } },
6978 { "SONY DSC-RX1", 128, 0,
6979 { 6344,-1612,-462,-4863,12477,2681,-865,1786,6899 } },
6980 { "SONY DSLR-A100", 0, 0xfeb,
6981 { 9437,-2811,-774,-8405,16215,2290,-710,596,7181 } },
6982 { "SONY DSLR-A290", 0, 0,
6983 { 6038,-1484,-579,-9145,16746,2512,-875,746,7218 } },
6984 { "SONY DSLR-A2", 0, 0,
6985 { 9847,-3091,-928,-8485,16345,2225,-715,595,7103 } },
6986 { "SONY DSLR-A300", 0, 0,
6987 { 9847,-3091,-928,-8485,16345,2225,-715,595,7103 } },
6988 { "SONY DSLR-A330", 0, 0,
6989 { 9847,-3091,-929,-8485,16346,2225,-714,595,7103 } },
6990 { "SONY DSLR-A350", 0, 0xffc,
6991 { 6038,-1484,-578,-9146,16746,2513,-875,746,7217 } },
6992 { "SONY DSLR-A380", 0, 0,
6993 { 6038,-1484,-579,-9145,16746,2512,-875,746,7218 } },
6994 { "SONY DSLR-A390", 0, 0,
6995 { 6038,-1484,-579,-9145,16746,2512,-875,746,7218 } },
6996 { "SONY DSLR-A450", 128, 0xfeb,
6997 { 4950,-580,-103,-5228,12542,3029,-709,1435,7371 } },
6998 { "SONY DSLR-A580", 128, 0xfeb,
6999 { 5932,-1492,-411,-4813,12285,2856,-741,1524,6739 } },
7000 { "SONY DSLR-A5", 128, 0xfeb,
7001 { 4950,-580,-103,-5228,12542,3029,-709,1435,7371 } },
7002 { "SONY DSLR-A700", 126, 0,
7003 { 5775,-805,-359,-8574,16295,2391,-1943,2341,7249 } },
7004 { "SONY DSLR-A850", 128, 0,
7005 { 5413,-1162,-365,-5665,13098,2866,-608,1179,8440 } },
7006 { "SONY DSLR-A900", 128, 0,
7007 { 5209,-1072,-397,-8845,16120,2919,-1618,1803,8654 } },
7008 { "SONY NEX-5N", 128, 0,
7009 { 5991,-1456,-455,-4764,12135,2980,-707,1425,6701 } },
7010 { "SONY NEX-5R", 128, 0,
7011 { 6129,-1545,-418,-4930,12490,2743,-977,1693,6615 } },
7012 { "SONY NEX-3", 138, 0, /* DJC */
7013 { 6907,-1256,-645,-4940,12621,2320,-1710,2581,6230 } },
7014 { "SONY NEX-5", 116, 0, /* DJC */
7015 { 6807,-1350,-342,-4216,11649,2567,-1089,2001,6420 } },
7016 { "SONY NEX-3", 128, 0, /* Adobe */
7017 { 6549,-1550,-436,-4880,12435,2753,-854,1868,6976 } },
7018 { "SONY NEX-5", 128, 0, /* Adobe */
7019 { 6549,-1550,-436,-4880,12435,2753,-854,1868,6976 } },
7020 { "SONY NEX-6", 128, 0,
7021 { 6129,-1545,-418,-4930,12490,2743,-977,1693,6615 } },
7022 { "SONY NEX-7", 128, 0,
7023 { 5491,-1192,-363,-4951,12342,2948,-911,1722,7192 } },
7024 { "SONY NEX", 128, 0, /* NEX-C3, NEX-F3 */
7025 { 5991,-1456,-455,-4764,12135,2980,-707,1425,6701 } },
7026 { "SONY SLT-A33", 128, 0,
7027 { 6069,-1221,-366,-5221,12779,2734,-1024,2066,6834 } },
7028 { "SONY SLT-A35", 128, 0,
7029 { 5986,-1618,-415,-4557,11820,3120,-681,1404,6971 } },
7030 { "SONY SLT-A37", 128, 0,
7031 { 5991,-1456,-455,-4764,12135,2980,-707,1425,6701 } },
7032 { "SONY SLT-A55", 128, 0,
7033 { 5932,-1492,-411,-4813,12285,2856,-741,1524,6739 } },
7034 { "SONY SLT-A57", 128, 0,
7035 { 5991,-1456,-455,-4764,12135,2980,-707,1425,6701 } },
7036 { "SONY SLT-A65", 128, 0,
7037 { 5491,-1192,-363,-4951,12342,2948,-911,1722,7192 } },
7038 { "SONY SLT-A77", 128, 0,
7039 { 5491,-1192,-363,-4951,12342,2948,-911,1722,7192 } },
7040 { "SONY SLT-A99", 128, 0,
7041 { 6344,-1612,-462,-4863,12477,2681,-865,1786,6899 } },
7043 double cam_xyz[4][3];
7047 sprintf (name, "%s %s", make, model);
7048 for (i=0; i < sizeof table / sizeof *table; i++)
7049 if (!strncmp (name, table[i].prefix, strlen(table[i].prefix))) {
7050 if (table[i].black) black = (ushort) table[i].black;
7051 if (table[i].maximum) maximum = (ushort) table[i].maximum;
7052 if (table[i].trans[0]) {
7053 double *dp = &cam_xyz[0][0];
7054 const short *sp = &table[i].trans[0];
7055 for( j=12; --j>=0; ++dp,++sp ) *dp = *sp / 10000.0;
7056 cam_xyz_coeff (cam_xyz);
7062 void CLASS simple_coeff (int index)
7064 static const float table[][12] = {
7065 /* index 0 -- all Foveon cameras */
7066 { 1.4032,-0.2231,-0.1016,-0.5263,1.4816,0.017,-0.0112,0.0183,0.9113 },
7067 /* index 1 -- Kodak DC20 and DC25 */
7068 { 2.25,0.75,-1.75,-0.25,-0.25,0.75,0.75,-0.25,-0.25,-1.75,0.75,2.25 },
7069 /* index 2 -- Logitech Fotoman Pixtura */
7070 { 1.893,-0.418,-0.476,-0.495,1.773,-0.278,-1.017,-0.655,2.672 },
7071 /* index 3 -- Nikon E880, E900, and E990 */
7072 { -1.936280, 1.800443, -1.448486, 2.584324,
7073 1.405365, -0.524955, -0.289090, 0.408680,
7074 -1.204965, 1.082304, 2.941367, -1.818705 }
7078 for (raw_color = i=0; i < 3; i++)
7079 FORCC rgb_cam[i][c] = table[index][i*colors+c];
7082 short CLASS guess_byte_order (int words)
7086 double diff, sum[2] = {0,0};
7088 fread (test[0], 2, 2, ifp);
7089 for (words-=2; words--; ) {
7090 fread (test[t], 2, 1, ifp);
7091 for (msb=0; msb < 2; msb++) {
7092 diff = (test[t^2][msb] << 8 | test[t^2][!msb])
7093 - (test[t ][msb] << 8 | test[t ][!msb]);
7094 sum[msb] += diff*diff;
7098 return sum[0] < sum[1] ? 0x4d4d : 0x4949;
7101 float CLASS find_green (int bps, int bite, int off0, int off1)
7104 int vbits, col, i, c;
7105 ushort img[2][2064];
7109 fseek (ifp, c ? off1:off0, SEEK_SET);
7110 for (vbits=col=0; col < width; col++) {
7111 for (vbits -= bps; vbits < 0; vbits += bite) {
7113 for (i=0; i < bite; i+=8)
7114 bitbuf |= (unsigned) (fgetc(ifp) << i);
7116 img[c][col] = bitbuf << (64-bps-vbits) >> (64-bps);
7120 sum[ c & 1] += ABS(img[0][c]-img[1][c+1]);
7121 sum[~c & 1] += ABS(img[1][c]-img[0][c+1]);
7123 return 100 * log(sum[0]/sum[1]);
7127 Identify which camera created this file, and set global variables
7130 void CLASS identify()
7133 int hlen, flen, fsize, zero_fsize=1, i, c, is_canon;
7136 { 3130, 1743, 4, 0, -6, 0 },
7137 { 3130, 2055, 4, 0, -6, 0 },
7138 { 3130, 2319, 4, 0, -6, 0 },
7139 { 3170, 2103, 18, 0,-42, 20 },
7140 { 3170, 2367, 18, 13,-42,-21 },
7141 { 3177, 2367, 0, 0, -1, 0 },
7142 { 3304, 2458, 0, 0, -1, 0 },
7143 { 3330, 2463, 9, 0, -5, 0 },
7144 { 3330, 2479, 9, 0,-17, 4 },
7145 { 3370, 1899, 15, 0,-44, 20 },
7146 { 3370, 2235, 15, 0,-44, 20 },
7147 { 3370, 2511, 15, 10,-44,-21 },
7148 { 3690, 2751, 3, 0, -8, -3 },
7149 { 3710, 2751, 0, 0, -3, 0 },
7150 { 3724, 2450, 0, 0, 0, -2 },
7151 { 3770, 2487, 17, 0,-44, 19 },
7152 { 3770, 2799, 17, 15,-44,-19 },
7153 { 3880, 2170, 6, 0, -6, 0 },
7154 { 4060, 3018, 0, 0, 0, -2 },
7155 { 4290, 2391, 3, 0, -8, -1 },
7156 { 4330, 2439, 17, 15,-44,-19 },
7157 { 4508, 2962, 0, 0, -3, -4 },
7158 { 4508, 3330, 0, 0, -3, -6 } };
7159 static const struct {
7161 char make[12], model[19], withjpeg;
7163 { 62464, "Kodak", "DC20" ,0 },
7164 { 124928, "Kodak", "DC20" ,0 },
7165 { 1652736, "Kodak", "DCS200" ,0 },
7166 { 4159302, "Kodak", "C330" ,0 },
7167 { 4162462, "Kodak", "C330" ,0 },
7168 { 460800, "Kodak", "C603v" ,0 },
7169 { 614400, "Kodak", "C603v" ,0 },
7170 { 6163328, "Kodak", "C603" ,0 },
7171 { 6166488, "Kodak", "C603" ,0 },
7172 { 9116448, "Kodak", "C603y" ,0 },
7173 { 311696, "ST Micro", "STV680 VGA" ,0 }, /* SPYz */
7174 { 787456, "Creative", "PC-CAM 600" ,0 },
7175 { 1138688, "Minolta", "RD175" ,0 },
7176 { 3840000, "Foculus", "531C" ,0 },
7177 { 307200, "Generic", "640x480" ,0 },
7178 { 786432, "AVT", "F-080C" ,0 },
7179 { 1447680, "AVT", "F-145C" ,0 },
7180 { 1920000, "AVT", "F-201C" ,0 },
7181 { 5067304, "AVT", "F-510C" ,0 },
7182 { 5067316, "AVT", "F-510C" ,0 },
7183 { 10134608, "AVT", "F-510C" ,0 },
7184 { 10134620, "AVT", "F-510C" ,0 },
7185 { 16157136, "AVT", "F-810C" ,0 },
7186 { 1409024, "Sony", "XCD-SX910CR" ,0 },
7187 { 2818048, "Sony", "XCD-SX910CR" ,0 },
7188 { 3884928, "Micron", "2010" ,0 },
7189 { 6624000, "Pixelink", "A782" ,0 },
7190 { 13248000, "Pixelink", "A782" ,0 },
7191 { 6291456, "RoverShot","3320AF" ,0 },
7192 { 6553440, "Canon", "PowerShot A460" ,0 },
7193 { 6653280, "Canon", "PowerShot A530" ,0 },
7194 { 6573120, "Canon", "PowerShot A610" ,0 },
7195 { 9219600, "Canon", "PowerShot A620" ,0 },
7196 { 9243240, "Canon", "PowerShot A470" ,0 },
7197 { 10341600, "Canon", "PowerShot A720 IS",0 },
7198 { 10383120, "Canon", "PowerShot A630" ,0 },
7199 { 12945240, "Canon", "PowerShot A640" ,0 },
7200 { 15636240, "Canon", "PowerShot A650" ,0 },
7201 { 5298000, "Canon", "PowerShot SD300" ,0 },
7202 { 7710960, "Canon", "PowerShot S3 IS" ,0 },
7203 { 15467760, "Canon", "PowerShot SX110 IS",0 },
7204 { 15534576, "Canon", "PowerShot SX120 IS",0 },
7205 { 18653760, "Canon", "PowerShot SX20 IS",0 },
7206 { 19131120, "Canon", "PowerShot SX220 HS",0 },
7207 { 21936096, "Canon", "PowerShot SX30 IS",0 },
7208 { 5939200, "OLYMPUS", "C770UZ" ,0 },
7209 { 1581060, "NIKON", "E900" ,1 }, /* or E900s,E910 */
7210 { 2465792, "NIKON", "E950" ,1 }, /* or E800,E700 */
7211 { 2940928, "NIKON", "E2100" ,1 }, /* or E2500 */
7212 { 4771840, "NIKON", "E990" ,1 }, /* or E995, Oly C3030Z */
7213 { 4775936, "NIKON", "E3700" ,1 }, /* or Optio 33WR */
7214 { 5869568, "NIKON", "E4300" ,1 }, /* or DiMAGE Z2 */
7215 { 5865472, "NIKON", "E4500" ,1 },
7216 { 7438336, "NIKON", "E5000" ,1 }, /* or E5700 */
7217 { 8998912, "NIKON", "COOLPIX S6" ,1 },
7218 { 1976352, "CASIO", "QV-2000UX" ,1 },
7219 { 3217760, "CASIO", "QV-3*00EX" ,1 },
7220 { 6218368, "CASIO", "QV-5700" ,1 },
7221 { 6054400, "CASIO", "QV-R41" ,1 },
7222 { 7530816, "CASIO", "QV-R51" ,1 },
7223 { 7684000, "CASIO", "QV-4000" ,1 },
7224 { 2937856, "CASIO", "EX-S20" ,1 },
7225 { 4948608, "CASIO", "EX-S100" ,1 },
7226 { 7542528, "CASIO", "EX-Z50" ,1 },
7227 { 7562048, "CASIO", "EX-Z500" ,1 },
7228 { 7753344, "CASIO", "EX-Z55" ,1 },
7229 { 7816704, "CASIO", "EX-Z60" ,1 },
7230 { 10843712, "CASIO", "EX-Z75" ,1 },
7231 { 10834368, "CASIO", "EX-Z750" ,1 },
7232 { 12310144, "CASIO", "EX-Z850" ,1 },
7233 { 12489984, "CASIO", "EX-Z8" ,1 },
7234 { 15499264, "CASIO", "EX-Z1050" ,1 },
7235 { 18702336, "CASIO", "EX-ZR100" ,1 },
7236 { 7426656, "CASIO", "EX-P505" ,1 },
7237 { 9313536, "CASIO", "EX-P600" ,1 },
7238 { 10979200, "CASIO", "EX-P700" ,1 },
7239 { 3178560, "PENTAX", "Optio S" ,1 },
7240 { 4841984, "PENTAX", "Optio S" ,1 },
7241 { 6114240, "PENTAX", "Optio S4" ,1 }, /* or S4i, CASIO EX-Z4 */
7242 { 10702848, "PENTAX", "Optio 750Z" ,1 },
7243 { 15980544, "AGFAPHOTO","DC-833m" ,1 },
7244 { 16098048, "SAMSUNG", "S85" ,1 },
7245 { 16215552, "SAMSUNG", "S85" ,1 },
7246 { 20487168, "SAMSUNG", "WB550" ,1 },
7247 { 24000000, "SAMSUNG", "WB550" ,1 },
7248 { 12582980, "Sinar", "" ,0 },
7249 { 33292868, "Sinar", "" ,0 },
7250 { 44390468, "Sinar", "" ,0 } };
7251 static const char *corp[] =
7252 { "Canon", "NIKON", "EPSON", "KODAK", "Kodak", "OLYMPUS", "PENTAX",
7253 "MINOLTA", "Minolta", "Konica", "CASIO", "Sinar", "Phase One",
7254 "SAMSUNG", "Mamiya", "MOTOROLA", "LEICA" };
7256 tiff_flip = flip = filters = -1; /* 0 is valid, so -1 is unknown */
7257 raw_height = raw_width = fuji_width = fuji_layout = cr2_slice[0] = 0;
7258 maximum = height = width = top_margin = left_margin = 0;
7259 cdesc[0] = desc[0] = artist[0] = make[0] = model[0] = model2[0] = 0;
7260 iso_speed = shutter = aperture = focal_len = unique_id = 0;
7262 memset (tiff_ifd, 0, sizeof tiff_ifd);
7263 memset (gpsdata, 0, sizeof gpsdata);
7264 memset (cblack, 0, sizeof cblack);
7265 memset (white, 0, sizeof white);
7266 memset (mask, 0, sizeof mask);
7267 thumb_offset = thumb_length = thumb_width = thumb_height = 0;
7268 load_raw = thumb_load_raw = 0;
7269 write_thumb = &CLASS jpeg_thumb;
7270 data_offset = meta_length = tiff_bps = tiff_compress = 0;
7271 kodak_cbpp = zero_after_ff = dng_version = load_flags = 0;
7272 timestamp = shot_order = tiff_samples = black = is_foveon = 0;
7273 mix_green = profile_length = data_error = zero_is_bad = 0;
7274 pixel_aspect = is_raw = raw_color = 1;
7275 tile_width = tile_length = 0;
7276 for (i=0; i < 4; i++) {
7277 cam_mul[i] = i == 1;
7279 FORC3 cmatrix[c][i] = 0;
7280 FORC3 rgb_cam[c][i] = c == i;
7283 for (i=0; i < 0x10000; i++) curve[i] = i;
7287 fseek (ifp, 0, SEEK_SET);
7288 fread (head, 1, 32, ifp);
7289 fseek (ifp, 0, SEEK_END);
7290 flen = fsize = ftell(ifp);
7291 if ((cp = (char *) memmem (head, 32, "MMMM", 4)) ||
7292 (cp = (char *) memmem (head, 32, "IIII", 4))) {
7293 parse_phase_one (cp-head);
7294 if (cp-head && parse_tiff(0)) apply_tiff();
7295 } else if (order == 0x4949 || order == 0x4d4d) {
7296 if (!memcmp (head+6,"HEAPCCDR",8)) {
7298 parse_ciff (hlen, flen - hlen);
7299 } else if (parse_tiff(0)) apply_tiff();
7300 } else if (!memcmp (head,"\xff\xd8\xff\xe1",4) &&
7301 !memcmp (head+6,"Exif",4)) {
7302 fseek (ifp, 4, SEEK_SET);
7303 data_offset = 4 + get2();
7304 fseek (ifp, data_offset, SEEK_SET);
7305 if (fgetc(ifp) != 0xff)
7308 } else if (!memcmp (head+25,"ARECOYK",7)) {
7309 strcpy (make, "Contax");
7310 strcpy (model,"N Digital");
7311 fseek (ifp, 33, SEEK_SET);
7313 fseek (ifp, 60, SEEK_SET);
7314 FORC4 cam_mul[c ^ (c >> 1)] = get4();
7315 } else if (!strcmp (head, "PXN")) {
7316 strcpy (make, "Logitech");
7317 strcpy (model,"Fotoman Pixtura");
7318 } else if (!strcmp (head, "qktk")) {
7319 strcpy (make, "Apple");
7320 strcpy (model,"QuickTake 100");
7321 load_raw = &CLASS quicktake_100_load_raw;
7322 } else if (!strcmp (head, "qktn")) {
7323 strcpy (make, "Apple");
7324 strcpy (model,"QuickTake 150");
7325 load_raw = &CLASS kodak_radc_load_raw;
7326 } else if (!memcmp (head,"FUJIFILM",8)) {
7327 fseek (ifp, 84, SEEK_SET);
7328 thumb_offset = get4();
7329 thumb_length = get4();
7330 fseek (ifp, 92, SEEK_SET);
7331 parse_fuji (get4());
7332 if (thumb_offset > 120) {
7333 fseek (ifp, 120, SEEK_SET);
7334 is_raw += (i = get4()) && 1;
7335 if (is_raw == 2 && shot_select)
7338 load_raw = &CLASS unpacked_load_raw;
7339 fseek (ifp, 100+28*(shot_select > 0), SEEK_SET);
7340 parse_tiff (data_offset = get4());
7341 parse_tiff (thumb_offset+12);
7343 } else if (!memcmp (head,"RIFF",4)) {
7344 fseek (ifp, 0, SEEK_SET);
7346 } else if (!memcmp (head,"\0\001\0\001\0@",6)) {
7347 fseek (ifp, 6, SEEK_SET);
7348 fread (make, 1, 8, ifp);
7349 fread (model, 1, 8, ifp);
7350 fread (model2, 1, 16, ifp);
7351 data_offset = get2();
7354 raw_height = get2();
7355 load_raw = &CLASS nokia_load_raw;
7356 filters = 0x61616161;
7357 } else if (!memcmp (head,"NOKIARAW",8)) {
7358 strcpy (make, "NOKIA");
7359 strcpy (model, "X2");
7361 fseek (ifp, 300, SEEK_SET);
7362 data_offset = get4();
7366 data_offset += i - width * 5 / 4 * height;
7367 load_raw = &CLASS nokia_load_raw;
7368 filters = 0x61616161;
7369 } else if (!memcmp (head,"ARRI",4)) {
7371 fseek (ifp, 20, SEEK_SET);
7374 strcpy (make, "ARRI");
7375 fseek (ifp, 668, SEEK_SET);
7376 fread (model, 1, 64, ifp);
7378 load_raw = &CLASS packed_load_raw;
7380 filters = 0x61616161;
7381 } else if (!memcmp (head+4,"RED1",4)) {
7382 strcpy (make, "RED");
7383 strcpy (model,"ONE");
7385 load_raw = &CLASS redcine_load_raw;
7386 gamma_curve (1/2.4, 12.92, 1, 4095);
7387 filters = 0x49494949;
7388 } else if (!memcmp (head,"DSC-Image",9))
7390 else if (!memcmp (head,"PWAD",4))
7392 else if (!memcmp (head,"\0MRM",4))
7394 else if (!memcmp (head,"FOVb",4))
7396 else if (!memcmp (head,"CI",2))
7399 for (zero_fsize=i=0; i < sizeof table / sizeof *table; i++)
7400 if (fsize == table[i].fsize) {
7401 strcpy (make, table[i].make );
7402 strcpy (model, table[i].model);
7403 if (table[i].withjpeg)
7404 parse_external_jpeg();
7406 if (zero_fsize) fsize = 0;
7407 if (make[0] == 0) parse_smal (0, flen);
7408 if (make[0] == 0) parse_jpeg (is_raw = 0);
7410 for (i=0; i < sizeof corp / sizeof *corp; i++)
7411 if (strstr (make, corp[i])) /* Simplify company names */
7412 strcpy (make, corp[i]);
7413 if (!strncmp (make,"KODAK",5) &&
7414 ((cp = strstr(model," DIGITAL CAMERA")) ||
7415 (cp = strstr(model," Digital Camera")) ||
7416 (cp = strstr(model,"FILE VERSION"))))
7418 cp = make + strlen(make); /* Remove trailing spaces */
7419 while (*--cp == ' ') *cp = 0;
7420 cp = model + strlen(model);
7421 while (*--cp == ' ') *cp = 0;
7422 i = strlen(make); /* Remove make from model */
7423 if (!strncasecmp (model, make, i) && model[i++] == ' ')
7424 memmove (model, model+i, 64-i);
7425 if (!strncmp (model,"FinePix ",8))
7426 strcpy (model, model+8);
7427 if (!strncmp (model,"Digital Camera ",15))
7428 strcpy (model, model+15);
7429 desc[511] = artist[63] = make[63] = model[63] = model2[63] = 0;
7430 if (!is_raw) goto notraw;
7432 if (!height) height = raw_height;
7433 if (!width) width = raw_width;
7434 if (height == 2624 && width == 3936) /* Pentax K10D and Samsung GX10 */
7435 { height = 2616; width = 3896; }
7436 if (height == 3136 && width == 4864) /* Pentax K20D and Samsung GX20 */
7437 { height = 3124; width = 4688; filters = 0x16161616; }
7438 if (width == 4352 && (!strcmp(model,"K-r") || !strcmp(model,"K-x")))
7439 { width = 4309; filters = 0x16161616; }
7440 if (width >= 4960 && !strncmp(model,"K-5",3))
7441 { left_margin = 10; width = 4950; filters = 0x16161616; }
7442 if (width == 4736 && !strcmp(model,"K-7"))
7443 { height = 3122; width = 4684; filters = 0x16161616; top_margin = 2; }
7444 if (width == 7424 && !strcmp(model,"645D"))
7445 { height = 5502; width = 7328; filters = 0x61616161; top_margin = 29;
7447 if (height == 3014 && width == 4096) /* Ricoh GX200 */
7450 if (filters == UINT_MAX) filters = 0;
7451 if (filters) is_raw = tiff_samples;
7452 else colors = tiff_samples;
7453 if (tiff_compress == 1)
7454 load_raw = &CLASS packed_dng_load_raw;
7455 if (tiff_compress == 7)
7456 load_raw = &CLASS lossless_dng_load_raw;
7459 if ((is_canon = !strcmp(make,"Canon")))
7460 load_raw = memcmp (head+6,"HEAPCCDR",8) ?
7461 &CLASS lossless_jpeg_load_raw : &CLASS canon_load_raw;
7462 if (!strcmp(make,"NIKON")) {
7464 load_raw = &CLASS packed_load_raw;
7465 if (model[0] == 'E')
7466 load_flags |= !data_offset << 2 | 2;
7468 if (!strcmp(make,"CASIO")) {
7469 load_raw = &CLASS packed_load_raw;
7473 /* Set parameters based on camera name (for non-DNG files). */
7476 if (height*2 < width) pixel_aspect = 0.5;
7477 if (height > width) pixel_aspect = 2;
7480 } else if (is_canon && tiff_bps == 15) {
7482 case 3344: width -= 66;
7483 case 3872: width -= 6;
7485 if (height > width) SWAP(height,width);
7487 load_raw = &CLASS canon_sraw_load_raw;
7488 } else if (!strcmp(model,"PowerShot 600")) {
7492 pixel_aspect = 607/628.0;
7494 filters = 0xe1e4e1e4;
7495 load_raw = &CLASS canon_600_load_raw;
7496 } else if (!strcmp(model,"PowerShot A5") ||
7497 !strcmp(model,"PowerShot A5 Zoom")) {
7501 pixel_aspect = 256/235.0;
7503 filters = 0x1e4e1e4e;
7505 } else if (!strcmp(model,"PowerShot A50")) {
7510 filters = 0x1b4e4b1e;
7512 } else if (!strcmp(model,"PowerShot Pro70")) {
7516 filters = 0x1e4b4e1b;
7518 } else if (!strcmp(model,"PowerShot SD300")) {
7526 } else if (!strcmp(model,"PowerShot A460")) {
7534 } else if (!strcmp(model,"PowerShot A530")) {
7542 } else if (!strcmp(model,"PowerShot A610")) {
7543 if (canon_s2is()) strcpy (model+10, "S2 IS");
7551 } else if (!strcmp(model,"PowerShot A620")) {
7559 } else if (!strcmp(model,"PowerShot A470")) {
7567 } else if (!strcmp(model,"PowerShot A720 IS")) {
7575 } else if (!strcmp(model,"PowerShot A630")) {
7583 } else if (!strcmp(model,"PowerShot A640")) {
7591 } else if (!strcmp(model,"PowerShot A650")) {
7599 } else if (!strcmp(model,"PowerShot S3 IS")) {
7608 load_raw = &CLASS packed_load_raw;
7610 if (raw_width > 1600) zero_is_bad = 1;
7611 } else if (!strcmp(model,"PowerShot SX110 IS")) {
7618 load_raw = &CLASS packed_load_raw;
7621 } else if (!strcmp(model,"PowerShot SX120 IS")) {
7628 filters = 0x49494949;
7629 load_raw = &CLASS packed_load_raw;
7632 } else if (!strcmp(model,"PowerShot SX20 IS")) {
7639 load_raw = &CLASS packed_load_raw;
7642 } else if (!strcmp(model,"PowerShot SX220 HS")) {
7647 mask[0][0] = top_margin = 16;
7648 mask[0][2] = top_margin + height;
7649 mask[0][3] = left_margin = 92;
7650 load_raw = &CLASS packed_load_raw;
7653 } else if (!strcmp(model,"PowerShot SX30 IS")) {
7660 filters = 0x16161616;
7661 load_raw = &CLASS packed_load_raw;
7664 } else if (!strcmp(model,"PowerShot Pro90 IS")) {
7667 filters = 0xb4b4b4b4;
7668 } else if (is_canon && raw_width == 2144) {
7673 if (!strcmp(model,"PowerShot G1")) {
7675 filters = 0xb4b4b4b4;
7677 } else if (is_canon && raw_width == 2224) {
7682 } else if (is_canon && raw_width == 2376) {
7687 } else if (is_canon && raw_width == 2672) {
7692 } else if (is_canon && raw_width == 3152) {
7697 if (unique_id == 0x80000170)
7698 adobe_coeff ("Canon","EOS 300D");
7699 } else if (is_canon && raw_width == 3160) {
7704 } else if (is_canon && raw_width == 3344) {
7709 } else if (!strcmp(model,"EOS D2000C")) {
7710 filters = 0x61616161;
7712 } else if (is_canon && raw_width == 3516) {
7715 if (unique_id == 0x80000189)
7716 adobe_coeff ("Canon","EOS 350D");
7718 } else if (is_canon && raw_width == 3596) {
7722 } else if (is_canon && raw_width == 3744) {
7727 if (unique_id > 0x2720000) {
7731 } else if (is_canon && raw_width == 3944) {
7736 } else if (is_canon && raw_width == 3948) {
7740 if (unique_id == 0x80000236)
7741 adobe_coeff ("Canon","EOS 400D");
7742 if (unique_id == 0x80000254)
7743 adobe_coeff ("Canon","EOS 1000D");
7745 } else if (is_canon && raw_width == 3984) {
7750 } else if (is_canon && raw_width == 4104) {
7755 } else if (is_canon && raw_width == 4152) {
7759 } else if (is_canon && raw_width == 4160) {
7764 } else if (is_canon && raw_width == 4176) {
7768 mask[0][0] = top_margin = 17;
7769 mask[0][2] = raw_height;
7771 filters = 0x49494949;
7772 } else if (is_canon && raw_width == 4312) {
7776 if (unique_id == 0x80000176)
7777 adobe_coeff ("Canon","EOS 450D");
7779 } else if (is_canon && raw_width == 4352) {
7782 if (unique_id == 0x80000288)
7783 adobe_coeff ("Canon","EOS 1100D");
7785 } else if (is_canon && raw_width == 4476) {
7789 } else if (is_canon && raw_width == 4480) {
7794 filters = 0x49494949;
7795 } else if (is_canon && raw_width == 4496) {
7800 } else if (is_canon && raw_width == 4832) {
7801 top_margin = unique_id == 0x80000261 ? 51:26;
7803 if (unique_id == 0x80000252)
7804 adobe_coeff ("Canon","EOS 500D");
7806 } else if (is_canon && raw_width == 5108) {
7810 } else if (is_canon && raw_width == 5120) {
7811 height -= top_margin = 45;
7814 } else if (is_canon && raw_width == 5280) {
7817 if (unique_id == 0x80000301)
7818 adobe_coeff ("Canon","EOS 650D");
7820 } else if (is_canon && raw_width == 5344) {
7823 if (unique_id == 0x80000269) {
7827 adobe_coeff ("Canon","EOS-1D X");
7829 if (unique_id == 0x80000270)
7830 adobe_coeff ("Canon","EOS 550D");
7831 if (unique_id == 0x80000286)
7832 adobe_coeff ("Canon","EOS 600D");
7834 } else if (is_canon && raw_width == 5360) {
7838 } else if (is_canon && raw_width == 5568) {
7842 } else if (is_canon && raw_width == 5712) {
7847 } else if (is_canon && raw_width == 5792) {
7851 height -= top_margin;
7852 width -= left_margin;
7853 } else if (is_canon && raw_width == 5920) {
7858 } else if (!strcmp(model,"D1")) {
7859 cam_mul[0] *= 256/527.0;
7860 cam_mul[2] *= 256/317.0;
7861 } else if (!strcmp(model,"D1X")) {
7864 } else if (!strcmp(model,"D40X") ||
7865 !strcmp(model,"D60") ||
7866 !strcmp(model,"D80") ||
7867 !strcmp(model,"D3000")) {
7870 } else if (!strcmp(model,"D3") ||
7871 !strcmp(model,"D3S") ||
7872 !strcmp(model,"D700")) {
7875 } else if (!strcmp(model,"D3100")) {
7878 } else if (!strcmp(model,"D5000") ||
7879 !strcmp(model,"D90")) {
7881 } else if (!strcmp(model,"D5100") ||
7882 !strcmp(model,"D7000")) {
7884 } else if (!strcmp(model,"D3200") ||
7885 !strcmp(model,"D600") ||
7886 !strcmp(model,"D800")) {
7888 } else if (!strcmp(model,"D4")) {
7891 } else if (!strncmp(model,"D40",3) ||
7892 !strncmp(model,"D50",3) ||
7893 !strncmp(model,"D70",3)) {
7895 } else if (!strcmp(model,"D100")) {
7897 raw_width = (width += 3) + 3;
7898 } else if (!strcmp(model,"D200")) {
7901 filters = 0x94949494;
7902 } else if (!strncmp(model,"D2H",3)) {
7905 } else if (!strncmp(model,"D2X",3)) {
7906 if (width == 3264) width -= 32;
7908 } else if (!strncmp(model,"D300",4)) {
7910 } else if (!strcmp(make,"NIKON") && raw_width == 4032) {
7911 adobe_coeff ("NIKON","COOLPIX P7700");
7912 } else if (!strncmp(model,"COOLPIX P",9)) {
7914 filters = 0x94949494;
7915 if (model[9] == '7' && iso_speed >= 400)
7917 } else if (!strncmp(model,"1 ",2)) {
7919 } else if (fsize == 1581060) {
7925 filters = 0x1e1e1e1e;
7927 pre_mul[0] = 1.2085;
7928 pre_mul[1] = 1.0943;
7929 pre_mul[3] = 1.1103;
7931 } else if (fsize == 2465792) {
7936 filters = 0x4b4b4b4b;
7937 adobe_coeff ("NIKON","E950");
7940 load_raw = &CLASS packed_load_raw;
7942 } else if (fsize == 4771840) {
7946 filters = 0xe1e1e1e1;
7947 load_raw = &CLASS packed_load_raw;
7949 if (!timestamp && nikon_e995())
7950 strcpy (model, "E995");
7951 if (strcmp(model,"E995")) {
7952 filters = 0xb4b4b4b4;
7958 } else if (!strcmp(model,"E2100")) {
7959 if (!timestamp && !nikon_e2100()) goto cp_e2500;
7963 } else if (!strcmp(model,"E2500")) {
7965 strcpy (model, "E2500");
7969 filters = 0x4b4b4b4b;
7970 } else if (fsize == 4775936) {
7973 load_raw = &CLASS packed_load_raw;
7975 if (!timestamp) nikon_3700();
7976 if (model[0] == 'E' && atoi(model+1) < 3700)
7977 filters = 0x49494949;
7978 if (!strcmp(model,"Optio 33WR")) {
7980 filters = 0x16161616;
7982 if (make[0] == 'O') {
7983 i = find_green (12, 32, 1188864, 3576832);
7984 c = find_green (12, 32, 2383920, 2387016);
7985 if (abs(i) < abs(c)) {
7989 if (i < 0) filters = 0x61616161;
7991 } else if (fsize == 5869568) {
7994 filters = 0x16161616;
7995 if (!timestamp && minolta_z2()) {
7996 strcpy (make, "Minolta");
7997 strcpy (model,"DiMAGE Z2");
7999 load_raw = &CLASS packed_load_raw;
8000 load_flags = 6 + 24*(make[0] == 'M');
8001 } else if (!strcmp(model,"E4500")) {
8005 filters = 0xb4b4b4b4;
8006 } else if (fsize == 7438336) {
8010 filters = 0xb4b4b4b4;
8011 } else if (fsize == 8998912) {
8015 load_raw = &CLASS packed_load_raw;
8017 } else if (!strcmp(make,"FUJIFILM")) {
8018 if (!strcmp(model+7,"S2Pro")) {
8019 strcpy (model,"S2Pro");
8023 } else if (load_raw != &CLASS packed_load_raw)
8024 maximum = (is_raw == 2 && shot_select) ? 0x2f00 : 0x3e00;
8025 top_margin = (raw_height - height) >> 2 << 1;
8026 left_margin = (raw_width - width ) >> 2 << 1;
8027 if (width == 2848) filters = 0x16161616;
8028 if (width == 3328) {
8032 if (width == 4952) {
8036 if (fuji_layout) raw_width *= is_raw;
8037 } else if (!strcmp(model,"RD175")) {
8041 filters = 0x61616161;
8042 load_raw = &CLASS minolta_rd175_load_raw;
8043 } else if (!strcmp(model,"KD-400Z")) {
8048 } else if (!strcmp(model,"KD-510Z")) {
8050 } else if (!strcasecmp(make,"MINOLTA")) {
8051 load_raw = &CLASS unpacked_load_raw;
8053 if (!strncmp(model,"DiMAGE A",8)) {
8054 if (!strcmp(model,"DiMAGE A200"))
8055 filters = 0x49494949;
8057 load_raw = &CLASS packed_load_raw;
8058 } else if (!strncmp(model,"ALPHA",5) ||
8059 !strncmp(model,"DYNAX",5) ||
8060 !strncmp(model,"MAXXUM",6)) {
8061 sprintf (model+20, "DYNAX %-10s", model+6+(model[0]=='M'));
8062 adobe_coeff (make, model+20);
8063 load_raw = &CLASS packed_load_raw;
8064 } else if (!strncmp(model,"DiMAGE G",8)) {
8065 if (model[8] == '4') {
8068 } else if (model[8] == '5') {
8073 } else if (model[8] == '6') {
8078 filters = 0x61616161;
8080 load_raw = &CLASS unpacked_load_raw;
8084 } else if (!strcmp(model,"*ist D")) {
8085 load_raw = &CLASS unpacked_load_raw;
8087 } else if (!strcmp(model,"*ist DS")) {
8089 } else if (!strcmp(model,"Optio S")) {
8090 if (fsize == 3178560) {
8093 load_raw = &CLASS eight_bit_load_raw;
8100 load_raw = &CLASS packed_load_raw;
8103 } else if (fsize == 6114240) {
8107 load_raw = &CLASS packed_load_raw;
8109 } else if (!strcmp(model,"Optio 750Z")) {
8112 load_raw = &CLASS packed_load_raw;
8114 } else if (!strcmp(model,"DC-833m")) {
8118 filters = 0x61616161;
8119 load_raw = &CLASS unpacked_load_raw;
8121 } else if (!strncmp(model,"S85",3)) {
8124 raw_width = fsize/height/2;
8126 load_raw = &CLASS unpacked_load_raw;
8127 } else if (!strcmp(make,"SAMSUNG") && raw_width == 4704) {
8128 height -= top_margin = 8;
8129 width -= 2 * (left_margin = 8);
8131 } else if (!strcmp(make,"SAMSUNG") && raw_width == 5632) {
8135 width = 5574 - (left_margin = 32 + tiff_bps);
8136 if (tiff_bps == 12) load_flags = 80;
8137 } else if (!strcmp(model,"EX1")) {
8141 if ((width -= 6) > 3682) {
8146 } else if (!strcmp(model,"WB2000")) {
8150 if ((width -= 10) > 3718) {
8155 } else if (fsize == 20487168) {
8159 } else if (fsize == 24000000) {
8163 strcpy (model, "WB550");
8165 load_raw = &CLASS unpacked_load_raw;
8168 } else if (!strcmp(model,"EX2F")) {
8173 filters = 0x49494949;
8174 load_raw = &CLASS unpacked_load_raw;
8175 } else if (!strcmp(model,"STV680 VGA")) {
8178 load_raw = &CLASS eight_bit_load_raw;
8180 filters = 0x16161616;
8182 } else if (!strcmp(model,"N95")) {
8183 height = raw_height - (top_margin = 2);
8184 } else if (!strcmp(model,"531C")) {
8187 load_raw = &CLASS unpacked_load_raw;
8188 filters = 0x49494949;
8189 } else if (!strcmp(model,"640x480")) {
8192 load_raw = &CLASS eight_bit_load_raw;
8193 gamma_curve (0.45, 4.5, 1, 255);
8194 } else if (!strcmp(model,"F-080C")) {
8197 load_raw = &CLASS eight_bit_load_raw;
8198 } else if (!strcmp(model,"F-145C")) {
8201 load_raw = &CLASS eight_bit_load_raw;
8202 } else if (!strcmp(model,"F-201C")) {
8205 load_raw = &CLASS eight_bit_load_raw;
8206 } else if (!strcmp(model,"F-510C")) {
8209 load_raw = fsize < 7500000 ?
8210 &CLASS eight_bit_load_raw : &CLASS unpacked_load_raw;
8211 data_offset = fsize - width*height*(fsize >> 22);
8213 } else if (!strcmp(model,"F-810C")) {
8216 load_raw = &CLASS unpacked_load_raw;
8218 } else if (!strcmp(model,"XCD-SX910CR")) {
8222 filters = 0x49494949;
8224 load_raw = fsize < 2000000 ?
8225 &CLASS eight_bit_load_raw : &CLASS unpacked_load_raw;
8226 } else if (!strcmp(model,"2010")) {
8230 filters = 0x16161616;
8233 load_raw = &CLASS unpacked_load_raw;
8234 } else if (!strcmp(model,"A782")) {
8237 filters = 0x61616161;
8238 load_raw = fsize < 10000000 ?
8239 &CLASS eight_bit_load_raw : &CLASS unpacked_load_raw;
8241 } else if (!strcmp(model,"3320AF")) {
8243 raw_width = width = 2048;
8244 filters = 0x61616161;
8245 load_raw = &CLASS unpacked_load_raw;
8247 fseek (ifp, 0x300000, SEEK_SET);
8248 if ((order = guess_byte_order(0x10000)) == 0x4d4d) {
8249 height -= (top_margin = 16);
8250 width -= (left_margin = 28);
8252 strcpy (make, "ISG");
8255 } else if (!strcmp(make,"Hasselblad")) {
8256 if (load_raw == &CLASS lossless_jpeg_load_raw)
8257 load_raw = &CLASS hasselblad_load_raw;
8258 if (raw_width == 7262) {
8263 filters = 0x61616161;
8264 } else if (raw_width == 7410) {
8269 filters = 0x61616161;
8270 } else if (raw_width == 9044) {
8275 black += load_flags = 256;
8277 } else if (raw_width == 4090) {
8278 strcpy (model, "V96C");
8279 height -= (top_margin = 6);
8280 width -= (left_margin = 3) + 7;
8281 filters = 0x61616161;
8283 } else if (!strcmp(make,"Sinar")) {
8284 if (!memcmp(head,"8BPS",4)) {
8285 fseek (ifp, 14, SEEK_SET);
8288 filters = 0x61616161;
8291 if (!load_raw) load_raw = &CLASS unpacked_load_raw;
8293 } else if (!strcmp(make,"Leaf")) {
8295 fseek (ifp, data_offset, SEEK_SET);
8296 if (ljpeg_start (&jh, 1) && jh.bits == 15)
8298 if (tiff_samples > 1) filters = 0;
8299 if (tiff_samples > 1 || tile_length < raw_height) {
8300 load_raw = &CLASS leaf_hdr_load_raw;
8301 raw_width = tile_width;
8303 if ((width | height) == 2048) {
8304 if (tiff_samples == 1) {
8306 strcpy (cdesc, "RBTG");
8307 strcpy (model, "CatchLight");
8308 top_margin = 8; left_margin = 18; height = 2032; width = 2016;
8310 strcpy (model, "DCB2");
8311 top_margin = 10; left_margin = 16; height = 2028; width = 2022;
8313 } else if (width+height == 3144+2060) {
8314 if (!model[0]) strcpy (model, "Cantare");
8315 if (width > height) {
8316 top_margin = 6; left_margin = 32; height = 2048; width = 3072;
8317 filters = 0x61616161;
8319 left_margin = 6; top_margin = 32; width = 2048; height = 3072;
8320 filters = 0x16161616;
8322 if (!cam_mul[0] || model[0] == 'V') filters = 0;
8323 else is_raw = tiff_samples;
8324 } else if (width == 2116) {
8325 strcpy (model, "Valeo 6");
8326 height -= 2 * (top_margin = 30);
8327 width -= 2 * (left_margin = 55);
8328 filters = 0x49494949;
8329 } else if (width == 3171) {
8330 strcpy (model, "Valeo 6");
8331 height -= 2 * (top_margin = 24);
8332 width -= 2 * (left_margin = 24);
8333 filters = 0x16161616;
8335 } else if (!strcmp(make,"LEICA") || !strcmp(make,"Panasonic")) {
8336 if ((flen - data_offset) / (raw_width*8/7) == raw_height)
8337 load_raw = &CLASS panasonic_load_raw;
8339 load_raw = &CLASS unpacked_load_raw;
8343 if ((height += 12) > raw_height) height = raw_height;
8344 for (i=0; i < sizeof pana / sizeof *pana; i++)
8345 if (raw_width == pana[i][0] && raw_height == pana[i][1]) {
8346 left_margin = pana[i][2];
8347 top_margin = pana[i][3];
8348 width += pana[i][4];
8349 height += pana[i][5];
8351 filters = 0x01010101 * (uchar) "\x94\x61\x49\x16"
8352 [((filters-1) ^ (left_margin & 1) ^ (top_margin << 1)) & 3];
8353 } else if (!strcmp(model,"C770UZ")) {
8356 filters = 0x16161616;
8357 load_raw = &CLASS packed_load_raw;
8359 } else if (!strcmp(make,"OLYMPUS")) {
8360 height += height & 1;
8362 if (width == 4100) width -= 4;
8363 if (width == 4080) width -= 24;
8364 if (load_raw == &CLASS unpacked_load_raw)
8367 if (!strcmp(model,"E-300") ||
8368 !strcmp(model,"E-500")) {
8370 if (load_raw == &CLASS unpacked_load_raw) {
8372 memset (cblack, 0, sizeof cblack);
8374 } else if (!strcmp(model,"E-330")) {
8376 if (load_raw == &CLASS unpacked_load_raw)
8378 } else if (!strcmp(model,"SP550UZ")) {
8379 thumb_length = flen - (thumb_offset = 0xa39800);
8382 } else if (!strcmp(model,"XZ-2")) {
8383 load_raw = &CLASS packed_load_raw;
8386 } else if (!strcmp(model,"N Digital")) {
8389 filters = 0x61616161;
8390 data_offset = 0x1a00;
8391 load_raw = &CLASS packed_load_raw;
8392 } else if (!strcmp(model,"DSC-F828")) {
8396 data_offset = 862144;
8397 load_raw = &CLASS sony_load_raw;
8398 filters = 0x9c9c9c9c;
8400 strcpy (cdesc, "RGBE");
8401 } else if (!strcmp(model,"DSC-V3")) {
8405 data_offset = 787392;
8406 load_raw = &CLASS sony_load_raw;
8407 } else if (!strcmp(make,"SONY") && raw_width == 3984) {
8408 adobe_coeff ("SONY","DSC-R1");
8411 } else if (!strcmp(make,"SONY") && raw_width == 5504) {
8413 } else if (!strcmp(make,"SONY") && raw_width == 6048) {
8415 } else if (!strcmp(model,"DSLR-A100")) {
8416 if (width == 3880) {
8418 width = ++raw_width;
8423 filters = 0x61616161;
8424 } else if (!strcmp(model,"DSLR-A350")) {
8426 } else if (!strcmp(model,"PIXL")) {
8427 height -= top_margin = 4;
8428 width -= left_margin = 32;
8429 gamma_curve (0, 7, 1, 255);
8430 } else if (!strcmp(model,"C603v")) {
8433 if (fsize < 614400 || find_green (16, 16, 3840, 5120) < 25) goto c603v;
8434 strcpy (model,"KAI-0340");
8438 load_raw = &CLASS unpacked_load_raw;
8439 } else if (!strcmp(model,"C603y")) {
8444 load_raw = &CLASS kodak_yrgb_load_raw;
8445 gamma_curve (0, 3.875, 1, 255);
8446 } else if (!strcmp(model,"C603")) {
8447 raw_height = height = 2152;
8448 raw_width = width = 2864;
8450 } else if (!strcmp(model,"C330")) {
8459 if ((data_offset = fsize - raw_height*raw_width)) {
8460 fseek (ifp, 168, SEEK_SET);
8461 read_shorts (curve, 256);
8462 } else gamma_curve (0, 3.875, 1, 255);
8463 load_raw = &CLASS eight_bit_load_raw;
8464 } else if (!strncasecmp(model,"EasyShare",9)) {
8465 data_offset = data_offset < 0x15000 ? 0x15000 : 0x17000;
8466 load_raw = &CLASS packed_load_raw;
8467 } else if (!strcasecmp(make,"KODAK")) {
8468 if (filters == UINT_MAX) filters = 0x61616161;
8469 if (!strncmp(model,"NC2000",6)) {
8472 } else if (!strcmp(model,"EOSDCS3B")) {
8475 } else if (!strcmp(model,"EOSDCS1")) {
8478 } else if (!strcmp(model,"DCS420")) {
8481 } else if (!strncmp(model,"DCS460 ",7)) {
8485 } else if (!strcmp(model,"DCS460A")) {
8490 } else if (!strcmp(model,"DCS660M")) {
8494 } else if (!strcmp(model,"DCS760M")) {
8498 if (!strcmp(model+4,"20X"))
8499 strcpy (cdesc, "MYCY");
8500 if (strstr(model,"DC25")) {
8501 strcpy (model, "DC25");
8502 data_offset = 15424;
8504 if (!strncmp(model,"DC2",3)) {
8505 raw_height = height = 242;
8506 if (flen < 100000) {
8507 raw_width = 256; width = 249;
8508 pixel_aspect = (4.0*height) / (3.0*width);
8510 raw_width = 512; width = 501;
8511 pixel_aspect = (493.0*height) / (373.0*width);
8513 data_offset += raw_width + 1;
8515 filters = 0x8d8d8d8d;
8520 load_raw = &CLASS eight_bit_load_raw;
8521 } else if (!strcmp(model,"40")) {
8522 strcpy (model, "DC40");
8526 load_raw = &CLASS kodak_radc_load_raw;
8527 } else if (strstr(model,"DC50")) {
8528 strcpy (model, "DC50");
8531 data_offset = 19712;
8532 load_raw = &CLASS kodak_radc_load_raw;
8533 } else if (strstr(model,"DC120")) {
8534 strcpy (model, "DC120");
8537 pixel_aspect = height/0.75/width;
8538 load_raw = tiff_compress == 7 ?
8539 &CLASS kodak_jpeg_load_raw : &CLASS kodak_dc120_load_raw;
8540 } else if (!strcmp(model,"DCS200")) {
8543 thumb_offset = 6144;
8545 write_thumb = &CLASS layer_thumb;
8548 data_offset = 79872;
8549 load_raw = &CLASS eight_bit_load_raw;
8552 } else if (!strcmp(model,"Fotoman Pixtura")) {
8556 load_raw = &CLASS kodak_radc_load_raw;
8557 filters = 0x61616161;
8559 } else if (!strncmp(model,"QuickTake",9)) {
8560 if (head[5]) strcpy (model+10, "200");
8561 fseek (ifp, 544, SEEK_SET);
8564 data_offset = (get4(),get2()) == 30 ? 738:736;
8565 if (height > width) {
8567 fseek (ifp, data_offset-6, SEEK_SET);
8568 flip = ~get2() & 3 ? 5:6;
8570 filters = 0x61616161;
8571 } else if (!strcmp(make,"Rollei") && !load_raw) {
8572 switch (raw_width) {
8585 filters = 0x16161616;
8586 load_raw = &CLASS rollei_load_raw;
8587 } else if (!strcmp(model,"PC-CAM 600")) {
8589 data_offset = width = 1024;
8590 filters = 0x49494949;
8591 load_raw = &CLASS eight_bit_load_raw;
8592 } else if (!strcmp(model,"QV-2000UX")) {
8595 data_offset = width * 2;
8596 load_raw = &CLASS eight_bit_load_raw;
8597 } else if (fsize == 3217760) {
8601 load_raw = &CLASS eight_bit_load_raw;
8602 } else if (!strcmp(model,"QV-4000")) {
8605 load_raw = &CLASS unpacked_load_raw;
8607 } else if (!strcmp(model,"QV-5700")) {
8612 } else if (!strcmp(model,"QV-R41")) {
8617 } else if (!strcmp(model,"QV-R51")) {
8621 } else if (!strcmp(model,"EX-S20")) {
8626 } else if (!strcmp(model,"EX-S100")) {
8630 } else if (!strcmp(model,"EX-Z50")) {
8634 } else if (!strcmp(model,"EX-Z500")) {
8638 filters = 0x16161616;
8639 } else if (!strcmp(model,"EX-Z55")) {
8643 } else if (!strcmp(model,"EX-Z60")) {
8647 filters = 0x16161616;
8649 } else if (!strcmp(model,"EX-Z75")) {
8654 } else if (!strcmp(model,"EX-Z750")) {
8659 } else if (!strcmp(model,"EX-Z850")) {
8664 } else if (!strcmp(model,"EX-Z8")) {
8670 } else if (fsize == 15499264) { /* EX-Z1050 or EX-Z1080 */
8674 } else if (!strcmp(model,"EX-ZR100")) {
8679 } else if (!strcmp(model,"EX-P505")) {
8684 } else if (fsize == 9313536) { /* EX-P600 or QV-R61 */
8688 } else if (!strcmp(model,"EX-P700")) {
8694 sprintf (model, "%dx%d", width, height);
8695 if (filters == UINT_MAX) filters = 0x94949494;
8696 if (raw_color) adobe_coeff (make, model);
8697 if (load_raw == &CLASS kodak_radc_load_raw)
8698 if (raw_color) adobe_coeff ("Apple","Quicktake");
8699 if (thumb_offset && !thumb_height) {
8700 fseek (ifp, thumb_offset, SEEK_SET);
8701 if (ljpeg_start (&jh, 1)) {
8702 thumb_width = jh.wide;
8703 thumb_height = jh.high;
8708 fuji_width = width >> !fuji_layout;
8709 if (~fuji_width & 1) filters = 0x49494949;
8710 width = (height >> fuji_layout) + fuji_width;
8714 if (raw_height < height) raw_height = height;
8715 if (raw_width < width ) raw_width = width;
8717 if (!tiff_bps) tiff_bps = 12;
8718 if (!maximum) maximum = (1 << tiff_bps) - 1;
8719 if (!load_raw || height < 22) is_raw = 0;
8721 if (load_raw == &CLASS redcine_load_raw) {
8722 fprintf (stderr,_("%s: You must link dcraw with %s!!\n"),
8723 ifname, "libjasper");
8728 if (load_raw == &CLASS kodak_jpeg_load_raw ||
8729 load_raw == &CLASS lossy_dng_load_raw) {
8730 fprintf (stderr,_("%s: You must link dcraw with %s!!\n"),
8736 strcpy (cdesc, colors == 3 ? "RGBG":"GMCY");
8737 if (!raw_height) raw_height = height;
8738 if (!raw_width ) raw_width = width;
8739 if (filters && colors == 3)
8740 filters |= ((filters >> 2 & 0x22222222) |
8741 (filters << 2 & 0x88888888)) & filters << 1;
8743 if (flip == -1) flip = tiff_flip;
8744 if (flip == -1) flip = 0;
8751 sprintf(dcraw_info, "%d %d", height, width);
8753 sprintf(dcraw_info, "%d %d", width, height);
8757 void CLASS apply_profile (const char *input, const char *output)
8760 cmsHPROFILE hInProfile=0, hOutProfile=0;
8761 cmsHTRANSFORM hTransform;
8765 cmsErrorAction (LCMS_ERROR_SHOW);
8766 if (strcmp (input, "embed"))
8767 hInProfile = cmsOpenProfileFromFile (input, "r");
8768 else if (profile_length) {
8769 prof = (char *) malloc (profile_length);
8770 merror (prof, "apply_profile()");
8771 fseek (ifp, profile_offset, SEEK_SET);
8772 fread (prof, 1, profile_length, ifp);
8773 hInProfile = cmsOpenProfileFromMem (prof, profile_length);
8776 fprintf (stderr,_("%s has no embedded profile.\n"), ifname);
8777 if (!hInProfile) return;
8779 hOutProfile = cmsCreate_sRGBProfile();
8780 else if ((fp = fopen (output, "rb"))) {
8781 fread (&size, 4, 1, fp);
8782 fseek (fp, 0, SEEK_SET);
8783 oprof = (unsigned *) malloc (size = ntohl(size));
8784 merror (oprof, "apply_profile()");
8785 fread (oprof, 1, size, fp);
8787 if (!(hOutProfile = cmsOpenProfileFromMem (oprof, size))) {
8792 fprintf (stderr,_("Cannot open file %s!\n"), output);
8793 if (!hOutProfile) goto quit;
8795 fprintf (stderr,_("Applying color profile...\n"));
8796 hTransform = cmsCreateTransform (hInProfile, TYPE_RGBA_16,
8797 hOutProfile, TYPE_RGBA_16, INTENT_PERCEPTUAL, 0);
8798 cmsDoTransform (hTransform, image, image, width*height);
8799 raw_color = 1; /* Don't use rgb_cam with a profile */
8800 cmsDeleteTransform (hTransform);
8801 cmsCloseProfile (hOutProfile);
8803 cmsCloseProfile (hInProfile);
8807 void CLASS convert_to_rgb()
8809 int row, col, c, i, j, k;
8811 float out[3], out_cam[3][4];
8812 double num, inverse[3][3];
8813 static const double xyzd50_srgb[3][3] =
8814 { { 0.436083, 0.385083, 0.143055 },
8815 { 0.222507, 0.716888, 0.060608 },
8816 { 0.013930, 0.097097, 0.714022 } };
8817 static const double rgb_rgb[3][3] =
8818 { { 1,0,0 }, { 0,1,0 }, { 0,0,1 } };
8819 static const double adobe_rgb[3][3] =
8820 { { 0.715146, 0.284856, 0.000000 },
8821 { 0.000000, 1.000000, 0.000000 },
8822 { 0.000000, 0.041166, 0.958839 } };
8823 static const double wide_rgb[3][3] =
8824 { { 0.593087, 0.404710, 0.002206 },
8825 { 0.095413, 0.843149, 0.061439 },
8826 { 0.011621, 0.069091, 0.919288 } };
8827 static const double prophoto_rgb[3][3] =
8828 { { 0.529317, 0.330092, 0.140588 },
8829 { 0.098368, 0.873465, 0.028169 },
8830 { 0.016879, 0.117663, 0.865457 } };
8831 static const double (*out_rgb[])[3] =
8832 { rgb_rgb, adobe_rgb, wide_rgb, prophoto_rgb, xyz_rgb };
8833 static const char *name[] =
8834 { "sRGB", "Adobe RGB (1998)", "WideGamut D65", "ProPhoto D65", "XYZ" };
8835 static const unsigned phead[] =
8836 { 1024, 0, 0x2100000, 0x6d6e7472, 0x52474220, 0x58595a20, 0, 0, 0,
8837 0x61637370, 0, 0, 0x6e6f6e65, 0, 0, 0, 0, 0xf6d6, 0x10000, 0xd32d };
8839 { 10, 0x63707274, 0, 36, /* cprt */
8840 0x64657363, 0, 40, /* desc */
8841 0x77747074, 0, 20, /* wtpt */
8842 0x626b7074, 0, 20, /* bkpt */
8843 0x72545243, 0, 14, /* rTRC */
8844 0x67545243, 0, 14, /* gTRC */
8845 0x62545243, 0, 14, /* bTRC */
8846 0x7258595a, 0, 20, /* rXYZ */
8847 0x6758595a, 0, 20, /* gXYZ */
8848 0x6258595a, 0, 20 }; /* bXYZ */
8849 static const unsigned pwhite[] = { 0xf351, 0x10000, 0x116cc };
8850 unsigned pcurve[] = { 0x63757276, 0, 1, 0x1000000 };
8852 gamma_curve (gamm[0], gamm[1], 0, 0);
8853 memcpy (out_cam, rgb_cam, sizeof out_cam);
8854 raw_color |= colors == 1 || document_mode ||
8855 output_color < 1 || output_color > 5;
8857 oprof = (unsigned *) calloc (phead[0], 1);
8858 merror (oprof, "convert_to_rgb()");
8859 memcpy (oprof, phead, sizeof phead);
8860 if (output_color == 5) oprof[4] = oprof[5];
8861 oprof[0] = 132 + 12*pbody[0];
8862 for (i=0; i < pbody[0]; i++) {
8863 oprof[oprof[0]/4] = i ? (i > 1 ? 0x58595a20 : 0x64657363) : 0x74657874;
8864 pbody[i*3+2] = oprof[0];
8865 oprof[0] += (pbody[i*3+3] + 3) & -4;
8867 memcpy (oprof+32, pbody, sizeof pbody);
8868 oprof[pbody[5]/4+2] = strlen(name[output_color-1]) + 1;
8869 memcpy ((char *)oprof+pbody[8]+8, pwhite, sizeof pwhite);
8870 pcurve[3] = (short)(256/gamm[5]+0.5) << 16;
8871 for (i=4; i < 7; i++)
8872 memcpy ((char *)oprof+pbody[i*3+2], pcurve, sizeof pcurve);
8873 pseudoinverse ((double (*)[3]) out_rgb[output_color-1], inverse, 3);
8874 for (i=0; i < 3; i++)
8875 for (j=0; j < 3; j++) {
8876 for (num = k=0; k < 3; k++)
8877 num += xyzd50_srgb[i][k] * inverse[j][k];
8878 oprof[pbody[j*3+23]/4+i+2] = num * 0x10000 + 0.5;
8880 for (i=0; i < phead[0]/4; i++)
8881 oprof[i] = htonl(oprof[i]);
8882 strcpy ((char *)oprof+pbody[2]+8, "auto-generated by dcraw");
8883 strcpy ((char *)oprof+pbody[5]+12, name[output_color-1]);
8884 for (i=0; i < 3; i++)
8885 for (j=0; j < colors; j++)
8886 for (out_cam[i][j] = k=0; k < 3; k++)
8887 out_cam[i][j] += out_rgb[output_color-1][i][k] * rgb_cam[k][j];
8890 fprintf (stderr, raw_color ? _("Building histograms...\n") :
8891 _("Converting to %s colorspace...\n"), name[output_color-1]);
8893 memset (histogram, 0, sizeof histogram);
8894 for (img=image[0], row=0; row < height; row++)
8895 for (col=0; col < width; col++, img+=4) {
8897 out[0] = out[1] = out[2] = 0;
8899 out[0] += out_cam[0][c] * img[c];
8900 out[1] += out_cam[1][c] * img[c];
8901 out[2] += out_cam[2][c] * img[c];
8903 FORC3 img[c] = CLIP((int) out[c]);
8905 else if (document_mode)
8906 img[0] = img[fcol(row,col)];
8907 FORCC histogram[c][img[c] >> 3]++;
8909 if (colors == 4 && output_color) colors = 3;
8910 if (document_mode && filters) colors = 1;
8916 // Export color matrix to Cinelerra.
8917 // It can't be applied before interpolation.
8919 for(i = 0; i < 3; i++)
8921 for(j = 0; j < 3; j++)
8922 dcraw_matrix[k++] = rgb_cam[i][j];
8926 void CLASS fuji_rotate()
8932 ushort wide, high, (*img)[4], (*pix)[4];
8934 if (!fuji_width) return;
8936 fprintf (stderr,_("Rotating image 45 degrees...\n"));
8937 fuji_width = (fuji_width - 1 + shrink) >> shrink;
8939 wide = fuji_width / step;
8940 high = (height - fuji_width) / step;
8941 img = (ushort (*)[4]) calloc (wide*high, sizeof *img);
8942 merror (img, "fuji_rotate()");
8944 for (row=0; row < high; row++)
8945 for (col=0; col < wide; col++) {
8946 ur = r = fuji_width + (row-col)*step;
8947 uc = c = (row+col)*step;
8948 if (ur > height-2 || uc > width-2) continue;
8951 pix = image + ur*width + uc;
8952 for (i=0; i < colors; i++)
8953 img[row*wide+col][i] =
8954 (pix[ 0][i]*(1-fc) + pix[ 1][i]*fc) * (1-fr) +
8955 (pix[width][i]*(1-fc) + pix[width+1][i]*fc) * fr;
8964 void CLASS stretch()
8966 ushort newdim, (*img)[4], *pix0, *pix1;
8970 if (pixel_aspect == 1) return;
8971 if (verbose) fprintf (stderr,_("Stretching the image...\n"));
8972 if (pixel_aspect < 1) {
8973 newdim = height / pixel_aspect + 0.5;
8974 img = (ushort (*)[4]) calloc (width*newdim, sizeof *img);
8975 merror (img, "stretch()");
8976 for (rc=row=0; row < newdim; row++, rc+=pixel_aspect) {
8977 frac = rc - (c = rc);
8978 pix0 = pix1 = image[c*width];
8979 if (c+1 < height) pix1 += width*4;
8980 for (col=0; col < width; col++, pix0+=4, pix1+=4)
8981 FORCC img[row*width+col][c] = pix0[c]*(1-frac) + pix1[c]*frac + 0.5;
8985 newdim = width * pixel_aspect + 0.5;
8986 img = (ushort (*)[4]) calloc (height*newdim, sizeof *img);
8987 merror (img, "stretch()");
8988 for (rc=col=0; col < newdim; col++, rc+=1/pixel_aspect) {
8989 frac = rc - (c = rc);
8990 pix0 = pix1 = image[c];
8991 if (c+1 < width) pix1 += 4;
8992 for (row=0; row < height; row++, pix0+=width*4, pix1+=width*4)
8993 FORCC img[row*newdim+col][c] = pix0[c]*(1-frac) + pix1[c]*frac + 0.5;
9001 int CLASS flip_index (int row, int col)
9003 if (flip & 4) SWAP(row,col);
9004 if (flip & 2) row = iheight - 1 - row;
9005 if (flip & 1) col = iwidth - 1 - col;
9006 return row * iwidth + col;
9012 union { char c[4]; short s[2]; int i; } val;
9016 ushort order, magic;
9019 struct tiff_tag tag[23];
9022 struct tiff_tag exif[4];
9024 struct tiff_tag gpst[10];
9028 char desc[512], make[64], model[64], soft[32], date[20], artist[64];
9031 void CLASS tiff_set (ushort *ntag,
9032 ushort tag, ushort type, int count, int val)
9034 struct tiff_tag *tt;
9037 tt = (struct tiff_tag *)(ntag+1) + (*ntag)++;
9041 if (type < 3 && count <= 4)
9042 FORC(4) tt->val.c[c] = val >> (c << 3);
9043 else if (type == 3 && count <= 2)
9044 FORC(2) tt->val.s[c] = val >> (c << 4);
9045 else tt->val.i = val;
9048 #define TOFF(ptr) ((char *)(&(ptr)) - (char *)th)
9050 void CLASS tiff_head (struct tiff_hdr *th, int full)
9055 memset (th, 0, sizeof *th);
9056 th->order = htonl(0x4d4d4949) >> 16;
9060 tiff_set (&th->ntag, 254, 4, 1, 0);
9061 tiff_set (&th->ntag, 256, 4, 1, width);
9062 tiff_set (&th->ntag, 257, 4, 1, height);
9063 tiff_set (&th->ntag, 258, 3, colors, output_bps);
9065 th->tag[th->ntag-1].val.i = TOFF(th->bps);
9066 FORC4 th->bps[c] = output_bps;
9067 tiff_set (&th->ntag, 259, 3, 1, 1);
9068 tiff_set (&th->ntag, 262, 3, 1, 1 + (colors > 1));
9070 tiff_set (&th->ntag, 270, 2, 512, TOFF(th->desc));
9071 tiff_set (&th->ntag, 271, 2, 64, TOFF(th->make));
9072 tiff_set (&th->ntag, 272, 2, 64, TOFF(th->model));
9074 if (oprof) psize = ntohl(oprof[0]);
9075 tiff_set (&th->ntag, 273, 4, 1, sizeof *th + psize);
9076 tiff_set (&th->ntag, 277, 3, 1, colors);
9077 tiff_set (&th->ntag, 278, 4, 1, height);
9078 tiff_set (&th->ntag, 279, 4, 1, height*width*colors*output_bps/8);
9080 tiff_set (&th->ntag, 274, 3, 1, "12435867"[flip]-'0');
9081 tiff_set (&th->ntag, 282, 5, 1, TOFF(th->rat[0]));
9082 tiff_set (&th->ntag, 283, 5, 1, TOFF(th->rat[2]));
9083 tiff_set (&th->ntag, 284, 3, 1, 1);
9084 tiff_set (&th->ntag, 296, 3, 1, 2);
9085 tiff_set (&th->ntag, 305, 2, 32, TOFF(th->soft));
9086 tiff_set (&th->ntag, 306, 2, 20, TOFF(th->date));
9087 tiff_set (&th->ntag, 315, 2, 64, TOFF(th->artist));
9088 tiff_set (&th->ntag, 34665, 4, 1, TOFF(th->nexif));
9089 if (psize) tiff_set (&th->ntag, 34675, 7, psize, sizeof *th);
9090 tiff_set (&th->nexif, 33434, 5, 1, TOFF(th->rat[4]));
9091 tiff_set (&th->nexif, 33437, 5, 1, TOFF(th->rat[6]));
9092 tiff_set (&th->nexif, 34855, 3, 1, iso_speed);
9093 tiff_set (&th->nexif, 37386, 5, 1, TOFF(th->rat[8]));
9095 tiff_set (&th->ntag, 34853, 4, 1, TOFF(th->ngps));
9096 tiff_set (&th->ngps, 0, 1, 4, 0x202);
9097 tiff_set (&th->ngps, 1, 2, 2, gpsdata[29]);
9098 tiff_set (&th->ngps, 2, 5, 3, TOFF(th->gps[0]));
9099 tiff_set (&th->ngps, 3, 2, 2, gpsdata[30]);
9100 tiff_set (&th->ngps, 4, 5, 3, TOFF(th->gps[6]));
9101 tiff_set (&th->ngps, 5, 1, 1, gpsdata[31]);
9102 tiff_set (&th->ngps, 6, 5, 1, TOFF(th->gps[18]));
9103 tiff_set (&th->ngps, 7, 5, 3, TOFF(th->gps[12]));
9104 tiff_set (&th->ngps, 18, 2, 12, TOFF(th->gps[20]));
9105 tiff_set (&th->ngps, 29, 2, 12, TOFF(th->gps[23]));
9106 memcpy (th->gps, gpsdata, sizeof th->gps);
9108 th->rat[0] = th->rat[2] = 300;
9109 th->rat[1] = th->rat[3] = 1;
9110 FORC(6) th->rat[4+c] = 1000000;
9111 th->rat[4] *= shutter;
9112 th->rat[6] *= aperture;
9113 th->rat[8] *= focal_len;
9114 strncpy (th->desc, desc, 512);
9115 strncpy (th->make, make, 64);
9116 strncpy (th->model, model, 64);
9117 strcpy (th->soft, "dcraw v"DCRAW_VERSION);
9118 t = localtime (×tamp);
9119 sprintf (th->date, "%04d:%02d:%02d %02d:%02d:%02d",
9120 t->tm_year+1900,t->tm_mon+1,t->tm_mday,t->tm_hour,t->tm_min,t->tm_sec);
9121 strncpy (th->artist, artist, 64);
9124 void CLASS jpeg_thumb()
9130 thumb = (char *) malloc (thumb_length);
9131 merror (thumb, "jpeg_thumb()");
9132 fread (thumb, 1, thumb_length, ifp);
9135 if (strcmp (thumb+6, "Exif")) {
9136 memcpy (exif, "\xff\xe1 Exif\0\0", 10);
9137 exif[1] = htons (8 + sizeof th);
9138 fwrite (exif, 1, sizeof exif, ofp);
9140 fwrite (&th, 1, sizeof th, ofp);
9142 fwrite (thumb+2, 1, thumb_length-2, ofp);
9146 void CLASS write_ppm_tiff()
9151 int c, row, col, soff, rstep, cstep;
9152 int perc, val, total, white=0x2000;
9154 perc = width * height * 0.01; /* 99th percentile white level */
9155 if (fuji_width) perc /= 2;
9156 if (!((highlight & ~2) || no_auto_bright))
9157 for (white=c=0; c < colors; c++) {
9158 for (val=0x2000, total=0; --val > 32; )
9159 if ((total += histogram[c][val]) > perc) break;
9160 if (white < val) white = val;
9162 gamma_curve (gamm[0], gamm[1], 2, (white << 3)/bright);
9165 if (flip & 4) SWAP(height,width);
9166 ppm = (uchar *) calloc (width, colors*output_bps/8);
9167 ppm2 = (ushort *) ppm;
9168 merror (ppm, "write_ppm_tiff()");
9171 fwrite (&th, sizeof th, 1, ofp);
9173 fwrite (oprof, ntohl(oprof[0]), 1, ofp);
9174 } else if (colors > 3)
9176 "P7\nWIDTH %d\nHEIGHT %d\nDEPTH %d\nMAXVAL %d\nTUPLTYPE %s\nENDHDR\n",
9177 width, height, colors, (1 << output_bps)-1, cdesc);
9179 fprintf (ofp, "P%d\n%d %d\n%d\n",
9180 colors/2+5, width, height, (1 << output_bps)-1);
9181 soff = flip_index (0, 0);
9182 cstep = flip_index (0, 1) - soff;
9183 rstep = flip_index (1, 0) - flip_index (0, width);
9184 for (row=0; row < height; row++, soff += rstep) {
9185 for (col=0; col < width; col++, soff += cstep)
9186 if (output_bps == 8)
9187 FORCC ppm [col*colors+c] = curve[image[soff][c]] >> 8;
9188 else FORCC ppm2[col*colors+c] = curve[image[soff][c]];
9189 if (output_bps == 16 && !output_tiff && htons(0x55aa) != 0x55aa)
9190 swab (ppm2, ppm2, width*colors*2);
9191 fwrite (ppm, colors*output_bps/8, width, ofp);
9202 void CLASS write_cinelerra (FILE *ofp)
9207 for (row = 0; row < height; row++)
9209 output = dcraw_data[row];
9213 for (col = 0; col < width; col++)
9215 ushort *pixel = image[row * width + col];
9217 *output++ = (float)pixel[0] / 0xffff;
9218 *output++ = (float)pixel[1] / 0xffff;
9219 *output++ = (float)pixel[2] / 0xffff;
9221 if(dcraw_alpha) *output++ = 1.0;
9226 for (col = 0; col < width; col++)
9228 ushort *pixel = image[row * width + col];
9230 *output++ = (float)pixel[0] / 0xffff;
9231 *output++ = (float)pixel[1] / 0xffff;
9232 *output++ = (float)pixel[2] / 0xffff;
9234 if(dcraw_alpha) *output++ = 1.0;
9253 int CLASS dcraw_main (int argc, const char **argv)
9254 //int CLASS main (int argc, const char **argv)
9257 // Globals must be reset
9263 int arg, status=0, quality, i, c;
9264 int timestamp_only=0, thumbnail_only=0, identify_only=0;
9265 int user_qual=-1, user_black=-1, user_sat=-1, user_flip=-1;
9266 int use_fuji_rotate=1, write_to_stdout=0, read_from_stdin=0;
9267 const char *sp, *bpfile=0, *dark_frame=0, *write_ext;
9268 char opm, opt, *ofname, *cp;
9271 const char *cam_profile=0, *out_profile=0;
9275 putenv ((char *) "TZ=UTC");
9278 setlocale (LC_CTYPE, "");
9279 setlocale (LC_MESSAGES, "");
9280 bindtextdomain ("dcraw", LOCALEDIR);
9281 textdomain ("dcraw");
9285 printf(_("\nRaw photo decoder \"dcraw\" v%s"), DCRAW_VERSION);
9286 printf(_("\nby Dave Coffin, dcoffin a cybercom o net\n"));
9287 printf(_("\nUsage: %s [OPTION]... [FILE]...\n\n"), argv[0]);
9288 puts(_("-v Print verbose messages"));
9289 puts(_("-c Write image data to standard output"));
9290 puts(_("-e Extract embedded thumbnail image"));
9291 puts(_("-i Identify files without decoding them"));
9292 puts(_("-i -v Identify files and show metadata"));
9293 puts(_("-z Change file dates to camera timestamp"));
9294 puts(_("-w Use camera white balance, if possible"));
9295 puts(_("-a Average the whole image for white balance"));
9296 puts(_("-A <x y w h> Average a grey box for white balance"));
9297 puts(_("-r <r g b g> Set custom white balance"));
9298 puts(_("+M/-M Use/don't use an embedded color matrix"));
9299 puts(_("-C <r b> Correct chromatic aberration"));
9300 puts(_("-P <file> Fix the dead pixels listed in this file"));
9301 puts(_("-K <file> Subtract dark frame (16-bit raw PGM)"));
9302 puts(_("-k <num> Set the darkness level"));
9303 puts(_("-S <num> Set the saturation level"));
9304 puts(_("-n <num> Set threshold for wavelet denoising"));
9305 puts(_("-H [0-9] Highlight mode (0=clip, 1=unclip, 2=blend, 3+=rebuild)"));
9306 puts(_("-t [0-7] Flip image (0=none, 3=180, 5=90CCW, 6=90CW)"));
9307 puts(_("-o [0-5] Output colorspace (raw,sRGB,Adobe,Wide,ProPhoto,XYZ)"));
9309 puts(_("-o <file> Apply output ICC profile from file"));
9310 puts(_("-p <file> Apply camera ICC profile from file or \"embed\""));
9312 puts(_("-d Document mode (no color, no interpolation)"));
9313 puts(_("-D Document mode without scaling (totally raw)"));
9314 puts(_("-j Don't stretch or rotate raw pixels"));
9315 puts(_("-W Don't automatically brighten the image"));
9316 puts(_("-b <num> Adjust brightness (default = 1.0)"));
9317 puts(_("-g <p ts> Set custom gamma curve (default = 2.222 4.5)"));
9318 puts(_("-q [0-3] Set the interpolation quality"));
9319 puts(_("-h Half-size color image (twice as fast as \"-q 0\")"));
9320 puts(_("-f Interpolate RGGB as four colors"));
9321 puts(_("-m <num> Apply a 3x3 median filter to R-G and B-G"));
9322 puts(_("-s [0..N-1] Select one raw image or \"all\" from each file"));
9323 puts(_("-6 Write 16-bit instead of 8-bit"));
9324 puts(_("-4 Linear 16-bit, same as \"-6 -W -g 1 1\""));
9325 puts(_("-T Write TIFF instead of PPM"));
9330 for (arg=1; (((opm = argv[arg][0]) - 2) | 2) == '+'; ) {
9331 opt = argv[arg++][1];
9332 if ((cp = (char *) strchr (sp="nbrkStqmHACg", opt)))
9333 for (i=0; i < "114111111422"[cp-sp]-'0'; i++)
9334 if (!isdigit(argv[arg+i][0])) {
9335 fprintf (stderr,_("Non-numeric argument to \"-%c\"\n"), opt);
9339 case 'n': threshold = atof(argv[arg++]); break;
9340 case 'b': bright = atof(argv[arg++]); break;
9342 FORC4 user_mul[c] = atof(argv[arg++]); break;
9343 case 'C': aber[0] = 1 / atof(argv[arg++]);
9344 aber[2] = 1 / atof(argv[arg++]); break;
9345 case 'g': gamm[0] = atof(argv[arg++]);
9346 gamm[1] = atof(argv[arg++]);
9347 if (gamm[0]) gamm[0] = 1/gamm[0]; break;
9348 case 'k': user_black = atoi(argv[arg++]); break;
9349 case 'S': user_sat = atoi(argv[arg++]); break;
9350 case 't': user_flip = atoi(argv[arg++]); break;
9351 case 'q': user_qual = atoi(argv[arg++]); break;
9352 case 'm': med_passes = atoi(argv[arg++]); break;
9353 case 'H': highlight = atoi(argv[arg++]); break;
9355 shot_select = abs(atoi(argv[arg]));
9356 multi_out = !strcmp(argv[arg++],"all");
9359 if (isdigit(argv[arg][0]) && !argv[arg][1])
9360 output_color = atoi(argv[arg++]);
9362 else out_profile = argv[arg++];
9364 case 'p': cam_profile = argv[arg++];
9367 case 'P': bpfile = argv[arg++]; break;
9368 case 'K': dark_frame = argv[arg++]; break;
9369 case 'z': timestamp_only = 1; break;
9370 case 'e': thumbnail_only = 1; break;
9371 case 'i': identify_only = 1; break;
9372 case 'c': write_to_stdout = 1; break;
9373 case 'v': verbose = 1; break;
9374 case 'h': half_size = 1; /* "-h" implies "-f" */
9375 case 'f': four_color_rgb = 1; break;
9376 case 'A': FORC4 greybox[c] = atoi(argv[arg++]);
9377 case 'a': use_auto_wb = 1; break;
9378 case 'w': use_camera_wb = 1; break;
9379 case 'M': use_camera_matrix = (opm == '+'); break;
9380 case 'I': read_from_stdin = 1; break;
9381 case 'E': document_mode++;
9382 case 'D': document_mode++;
9383 case 'd': document_mode++;
9384 case 'j': use_fuji_rotate = 0; break;
9385 case 'W': no_auto_bright = 1; break;
9386 case 'T': output_tiff = 1; break;
9387 case '4': gamm[0] = gamm[1] =
9389 case '6': output_bps = 16; break;
9391 fprintf (stderr,_("Unknown option \"-%c\".\n"), opt);
9395 if (use_camera_matrix < 0)
9396 use_camera_matrix = use_camera_wb;
9398 fprintf (stderr,_("No files to process.\n"));
9401 if (write_to_stdout) {
9405 fprintf (stderr,_("Will not write an image to the terminal!\n"));
9408 #if defined(WIN32) || defined(DJGPP) || defined(__CYGWIN__)
9409 if (setmode(1,O_BINARY) < 0) {
9410 perror ("setmode()");
9415 for ( ; arg < argc; arg++) {
9420 meta_data = ofname = 0;
9422 if (setjmp (failure)) {
9423 if (fileno(ifp) > 2) fclose(ifp);
9424 if (fileno(ofp) > 2) fclose(ofp);
9429 if (!(ifp = fopen (ifname, "rb"))) {
9433 status = (identify(),!is_raw);
9436 switch ((flip+3600) % 360) {
9437 case 270: flip = 5; break;
9438 case 180: flip = 3; break;
9441 if (timestamp_only) {
9442 if ((status = !timestamp))
9443 fprintf (stderr,_("%s has no timestamp.\n"), ifname);
9444 else if (identify_only)
9445 printf ("%10ld%10d %s\n", (long) timestamp, shot_order, ifname);
9448 fprintf (stderr,_("%s time set to %d.\n"), ifname, (int) timestamp);
9449 ut.actime = ut.modtime = timestamp;
9450 utime (ifname, &ut);
9454 write_fun = &CLASS write_ppm_tiff;
9459 write_fun = write_cinelerra;
9464 if (thumbnail_only) {
9465 if ((status = !thumb_offset)) {
9466 fprintf (stderr,_("%s has no thumbnail.\n"), ifname);
9468 } else if (thumb_load_raw) {
9469 load_raw = thumb_load_raw;
9470 data_offset = thumb_offset;
9471 height = thumb_height;
9472 width = thumb_width;
9475 fseek (ifp, thumb_offset, SEEK_SET);
9476 write_fun = write_thumb;
9480 if (load_raw == &CLASS kodak_ycbcr_load_raw) {
9481 height += height & 1;
9484 if (identify_only && verbose && make[0]) {
9485 printf (_("\nFilename: %s\n"), ifname);
9486 printf (_("Timestamp: %s"), ctime(×tamp));
9487 printf (_("Camera: %s %s\n"), make, model);
9489 printf (_("Owner: %s\n"), artist);
9491 printf (_("DNG Version: "));
9492 for (i=24; i >= 0; i -= 8)
9493 printf ("%d%c", dng_version >> i & 255, i ? '.':'\n');
9495 printf (_("ISO speed: %d\n"), (int) iso_speed);
9496 printf (_("Shutter: "));
9497 if (shutter > 0 && shutter < 1)
9498 shutter = (printf ("1/"), 1 / shutter);
9499 printf (_("%0.1f sec\n"), shutter);
9500 printf (_("Aperture: f/%0.1f\n"), aperture);
9501 printf (_("Focal length: %0.1f mm\n"), focal_len);
9502 printf (_("Embedded ICC profile: %s\n"), profile_length ? _("yes"):_("no"));
9503 printf (_("Number of raw images: %d\n"), is_raw);
9504 if (pixel_aspect != 1)
9505 printf (_("Pixel Aspect Ratio: %0.6f\n"), pixel_aspect);
9507 printf (_("Thumb size: %4d x %d\n"), thumb_width, thumb_height);
9508 printf (_("Full size: %4d x %d\n"), raw_width, raw_height);
9514 // else if (!is_raw)
9515 // fprintf (stderr,_("Cannot decode file %s\n"), ifname);
9522 if (!is_raw) goto next;
9523 shrink = filters && (half_size || (!identify_only &&
9524 (threshold || aber[0] != 1 || aber[2] != 1)));
9525 iheight = (height + shrink) >> shrink;
9526 iwidth = (width + shrink) >> shrink;
9527 if (identify_only) {
9529 if (document_mode == 3) {
9530 top_margin = left_margin = fuji_width = 0;
9531 height = raw_height;
9532 if (width <= raw_width * 8 / tiff_bps)
9533 width = raw_width * 8 / tiff_bps;
9534 else width = raw_width;
9536 iheight = (height + shrink) >> shrink;
9537 iwidth = (width + shrink) >> shrink;
9538 if (use_fuji_rotate) {
9540 fuji_width = (fuji_width - 1 + shrink) >> shrink;
9541 iwidth = fuji_width / sqrt(0.5);
9542 iheight = (iheight - fuji_width) / sqrt(0.5);
9544 if (pixel_aspect < 1) iheight = iheight / pixel_aspect + 0.5;
9545 if (pixel_aspect > 1) iwidth = iwidth * pixel_aspect + 0.5;
9549 SWAP(iheight,iwidth);
9550 printf (_("Image size: %4d x %d\n"), width, height);
9551 printf (_("Output size: %4d x %d\n"), iwidth, iheight);
9552 printf (_("Raw colors: %d"), colors);
9554 printf (_("\nFilter pattern: "));
9555 for (i=0; i < 16; i++)
9556 putchar (cdesc[fcol(i >> 1,i & 1)]);
9558 printf (_("\nDaylight multipliers:"));
9559 FORCC printf (" %f", pre_mul[c]);
9560 if (cam_mul[0] > 0) {
9561 printf (_("\nCamera multipliers:"));
9562 FORC4 printf (" %f", cam_mul[c]);
9567 // printf (_("%s is a %s %s image.\n"), ifname, make, model);
9572 if (use_camera_matrix && cmatrix[0][0] > 0.25) {
9573 memcpy (rgb_cam, cmatrix, sizeof cmatrix);
9577 meta_data = (char *) malloc (meta_length);
9578 merror (meta_data, "main()");
9580 if (filters || colors == 1) {
9581 raw_image = (ushort *) calloc ((raw_height+7)*raw_width, 2);
9582 merror (raw_image, "main()");
9584 image = (ushort (*)[4]) calloc (iheight*iwidth, sizeof *image);
9585 merror (image, "main()");
9588 fprintf (stderr,_("Loading %s %s image from %s ...\n"),
9589 make, model, ifname);
9590 if (shot_select >= is_raw)
9591 fprintf (stderr,_("%s: \"-s %d\" requests a nonexistent image!\n"),
9592 ifname, shot_select);
9593 fseeko (ifp, data_offset, SEEK_SET);
9594 if (raw_image && read_from_stdin)
9595 fread (raw_image, 2, raw_height*raw_width, stdin);
9597 if (document_mode == 3) {
9598 top_margin = left_margin = fuji_width = 0;
9599 height = raw_height;
9600 if (width <= raw_width * 8 / tiff_bps)
9601 width = raw_width * 8 / tiff_bps;
9602 else width = raw_width;
9604 iheight = (height + shrink) >> shrink;
9605 iwidth = (width + shrink) >> shrink;
9607 image = (ushort (*)[4]) calloc (iheight*iwidth, sizeof *image);
9608 merror (image, "main()");
9609 crop_masked_pixels();
9612 if (zero_is_bad) remove_zeroes();
9613 bad_pixels (bpfile);
9614 if (dark_frame) subtract (dark_frame);
9615 quality = 2 + !fuji_width;
9616 if (user_qual >= 0) quality = user_qual;
9618 FORC3 if (i > cblack[c]) i = cblack[c];
9619 FORC4 cblack[c] -= i;
9621 if (user_black >= 0) black = user_black;
9622 FORC4 cblack[c] += black;
9623 if (user_sat > 0) maximum = user_sat;
9628 if (document_mode || load_raw == &CLASS foveon_dp_load_raw) {
9629 for (i=0; i < height*width*4; i++)
9630 if ((short) image[0][i] < 0) image[0][i] = 0;
9631 } else foveon_interpolate();
9632 } else if (document_mode < 2)
9635 if (filters && !document_mode) {
9638 else if (quality == 1 || colors > 3 || filters < 1000)
9640 else if (quality == 2)
9642 else ahd_interpolate();
9645 for (colors=3, i=0; i < height*width; i++)
9646 image[i][1] = (image[i][1] + image[i][3]) >> 1;
9647 if (!is_foveon && colors == 3) median_filter();
9648 if (!is_foveon && highlight == 2) blend_highlights();
9649 if (!is_foveon && highlight > 2) recover_highlights();
9650 if (use_fuji_rotate) fuji_rotate();
9652 if (cam_profile) apply_profile (cam_profile, out_profile);
9655 if (use_fuji_rotate) stretch();
9657 if (write_fun == &CLASS jpeg_thumb)
9659 else if (output_tiff && write_fun == &CLASS write_ppm_tiff)
9660 write_ext = ".tiff";
9662 write_ext = ".pgm\0.ppm\0.ppm\0.pam" + colors*5-5;
9663 ofname = (char *) malloc (strlen(ifname) + 64);
9664 merror (ofname, "main()");
9665 if (write_to_stdout)
9666 strcpy (ofname,_("standard output"));
9668 strcpy (ofname, ifname);
9669 if ((cp = strrchr (ofname, '.'))) *cp = 0;
9671 sprintf (ofname+strlen(ofname), "_%0*d",
9672 snprintf(0,0,"%d",is_raw-1), shot_select);
9674 strcat (ofname, ".thumb");
9675 strcat (ofname, write_ext);
9676 ofp = fopen (ofname, "wb");
9684 fprintf (stderr,_("Writing data to %s ...\n"), ofname);
9687 if (ofp != stdout) fclose(ofp);
9689 if (meta_data) free (meta_data);
9690 if (ofname) free (ofname);
9691 if (oprof) free (oprof);
9692 if (image) free (image);
9694 if (++shot_select < is_raw) arg--;
9695 else shot_select = 0;