xref: /haiku/src/add-ons/translators/raw/RAW.cpp (revision 893988af824e65e49e55f517b157db8386e8002b)
1 /*
2  * Copyright 2007-2008, Axel Dörfler, axeld@pinc-software.de.
3  * Distributed under the terms of the MIT License.
4  *
5  * Copyright 1997-2007, Dave Coffin, dcoffin a cybercom o net
6  * This code is based on Dave Coffin's dcraw 8.63 - it's basically the same
7  * thing in C++, but follows common sense programming rules a bit more :-)
8  * Except the Fovean functions, dcraw is public domain.
9  */
10 
11 
12 #include "RAW.h"
13 #include "ReadHelper.h"
14 
15 #include <Message.h>
16 #include <TranslationErrors.h>
17 
18 #include <ctype.h>
19 #include <stdio.h>
20 #include <stdlib.h>
21 #include <string.h>
22 
23 
24 //#define TRACE(x) printf x
25 #define TRACE(x)
26 //#define TAG(x...) printf(x)
27 #define TAG(x...)
28 
29 #define ABS(x) (((int)(x) ^ ((int)(x) >> 31)) - ((int)(x) >> 31))
30 #define LIM(x,min,max) MAX(min,MIN(x,max))
31 #define ULIM(x,y,z) ((y) < (z) ? LIM(x,y,z) : LIM(x,z,y))
32 #define CLIP(x) LIM(x,0,65535)
33 #define SWAP(a,b) { a ^= b; a ^= (b ^= a); }
34 
35 #define FC(row,col) \
36 	(fFilters >> ((((row) << 1 & 14) + ((col) & 1)) << 1) & 3)
37 
38 
39 static const uint32 kImageBufferCount = 10;
40 static const uint32 kDecodeBufferCount = 2048;
41 
42 const double xyz_rgb[3][3] = {			/* XYZ from RGB */
43   { 0.412453, 0.357580, 0.180423 },
44   { 0.212671, 0.715160, 0.072169 },
45   { 0.019334, 0.119193, 0.950227 } };
46 const float kD65White[3] = { 0.950456, 1, 1.088754 };
47 
48 struct decode {
49 	struct decode *branch[2];
50 	int32	leaf;
51 };
52 
53 struct jhead {
54 	int		bits, high, wide, clrs, restart, vpred[4];
55 	struct decode *huff[4];
56 	uint16*	row;
57 };
58 
59 struct tiff_header {
60 	uint16	order, magic;
61 	int32	image_file_directory;
62 	uint16	pad, ntag;
63 	struct tiff_tag tag[15];
64 	int32	next_image_file_directory;
65 	uint16	pad2, nexif;
66 	struct tiff_tag exif[4];
67 	int16	bps[4];
68 	int32	rat[6];
69 	char make[64], model[64], soft[32], date[20];
70 };
71 
72 
73 template<class T> inline T
74 square(const T& value)
75 {
76 	return value * value;
77 }
78 
79 
80 static inline bool
81 x_flipped(int32 orientation)
82 {
83 	return orientation == 2 || orientation == 3
84 		|| orientation == 7 || orientation == 8;
85 }
86 
87 
88 static inline bool
89 y_flipped(int32 orientation)
90 {
91 	return orientation == 3 || orientation == 4
92 		|| orientation == 6 || orientation == 7;
93 }
94 
95 
96 #if 0
97 void
98 dump_to_disk(void* data, size_t length)
99 {
100 	FILE* file = fopen("/tmp/RAW.out", "wb");
101 	if (file == NULL)
102 		return;
103 
104 	fwrite(data, length, 1, file);
105 	fclose(file);
106 }
107 #endif
108 
109 
110 //	#pragma mark -
111 
112 
113 DCRaw::DCRaw(BPositionIO& stream)
114 	:
115 	fRead(stream),
116 	fNumImages(0),
117 	fRawIndex(-1),
118 	fThumbIndex(-1),
119 	fDNGVersion(0),
120 	fIsTIFF(false),
121 	fImageData(NULL),
122 	fThreshold(0.0f),
123 	fHalfSize(false),
124 	fUseCameraWhiteBalance(true),
125 	fUseAutoWhiteBalance(true),
126 	fRawColor(true),
127 	fUseGamma(true),
128 	fBrightness(1.0f),
129 	fOutputColor(1),
130 	fHighlight(0),
131 	fDocumentMode(0),
132 	fOutputWidth(0),
133 	fOutputHeight(0),
134 	fInputWidth(0),
135 	fInputHeight(0),
136 	fTopMargin(0),
137 	fLeftMargin(0),
138 	fColors(3),
139 	fOutputProfile(NULL),
140 	fOutputBitsPerSample(8),
141 	fDecodeLeaf(0),
142 	fDecodeBitsZeroAfterMax(false),
143 	fFilters(~0),
144 	fEXIFOffset(-1),
145 	fProgressMonitor(NULL)
146 {
147 	fImages = new image_data_info[kImageBufferCount];
148 	fDecodeBuffer = new decode[kDecodeBufferCount];
149 	fCurve = new uint16[0x1000];
150 	for (uint32 i = 0; i < 0x1000; i++) {
151 		fCurve[i] = i;
152 	}
153 
154 	cbrt = new float[0x10000];
155 	fHistogram = (int32 (*)[4])calloc(sizeof(int32) * 0x2000 * 4, 1);
156 
157 	memset(fImages, 0, sizeof(image_data_info) * kImageBufferCount);
158 	memset(&fMeta, 0, sizeof(image_meta_info));
159 	memset(fUserMultipliers, 0, sizeof(fUserMultipliers));
160 	memset(fWhite, 0, sizeof(fWhite));
161 
162 	fMeta.camera_multipliers[0] = -1;
163 	fCR2Slice[0] = 0;
164 }
165 
166 
167 DCRaw::~DCRaw()
168 {
169 	delete[] fImages;
170 	delete[] fDecodeBuffer;
171 	delete[] fCurve;
172 
173 	delete[] cbrt;
174 
175 	free(fHistogram);
176 	free(fImageData);
177 }
178 
179 
180 int32
181 DCRaw::_AllocateImage()
182 {
183 	if (fNumImages + 1 == kImageBufferCount)
184 		throw (status_t)B_ERROR;
185 
186 	return fNumImages++;
187 }
188 
189 
190 image_data_info&
191 DCRaw::_Raw()
192 {
193 	if (fRawIndex < 0)
194 		fRawIndex = _AllocateImage();
195 	if (fRawIndex < 0)
196 		throw (status_t)B_ERROR;
197 
198 	return fImages[fRawIndex];
199 }
200 
201 
202 image_data_info&
203 DCRaw::_Thumb()
204 {
205 	if (fThumbIndex < 0)
206 		fThumbIndex = _AllocateImage();
207 	if (fThumbIndex < 0)
208 		throw (status_t)B_ERROR;
209 
210 	return fImages[fThumbIndex];
211 }
212 
213 
214 //! Make sure that the raw image always comes first
215 void
216 DCRaw::_CorrectIndex(uint32& index) const
217 {
218 	if (fRawIndex > 0) {
219 		if (index == 0)
220 			index = fRawIndex;
221 		else if (index <= (uint32)fRawIndex)
222 			index--;
223 	}
224 }
225 
226 
227 inline uint16&
228 DCRaw::_Bayer(int32 column, int32 row)
229 {
230 	return fImageData[((row) >> fShrink) * fOutputWidth
231 		+ ((column) >> fShrink)][FC(row, column)];
232 }
233 
234 
235 inline int32
236 DCRaw::_FilterCoefficient(int32 x, int32 y)
237 {
238 	static const char filter[16][16] = {
239 		{ 2,1,1,3,2,3,2,0,3,2,3,0,1,2,1,0 },
240 		{ 0,3,0,2,0,1,3,1,0,1,1,2,0,3,3,2 },
241 		{ 2,3,3,2,3,1,1,3,3,1,2,1,2,0,0,3 },
242 		{ 0,1,0,1,0,2,0,2,2,0,3,0,1,3,2,1 },
243 		{ 3,1,1,2,0,1,0,2,1,3,1,3,0,1,3,0 },
244 		{ 2,0,0,3,3,2,3,1,2,0,2,0,3,2,2,1 },
245 		{ 2,3,3,1,2,1,2,1,2,1,1,2,3,0,0,1 },
246 		{ 1,0,0,2,3,0,0,3,0,3,0,3,2,1,2,3 },
247 		{ 2,3,3,1,1,2,1,0,3,2,3,0,2,3,1,3 },
248 		{ 1,0,2,0,3,0,3,2,0,1,1,2,0,1,0,2 },
249 		{ 0,1,1,3,3,2,2,1,1,3,3,0,2,1,3,2 },
250 		{ 2,3,2,0,0,1,3,0,2,0,1,2,3,0,1,0 },
251 		{ 1,3,1,2,3,2,3,2,0,2,0,1,1,0,3,0 },
252 		{ 0,2,0,3,1,0,0,1,1,3,3,2,3,2,2,1 },
253 		{ 2,1,3,2,3,1,2,1,0,3,0,2,0,2,0,2 },
254 		{ 0,3,1,0,0,2,0,3,2,1,3,1,1,3,1,3 }
255 	};
256 
257 	if (fFilters != 1)
258 		return FC(y, x);
259 
260 	return filter[(y + fTopMargin) & 15][(x + fLeftMargin) & 15];
261 }
262 
263 
264 inline int32
265 DCRaw::_FlipIndex(uint32 row, uint32 col, uint32 flip)
266 {
267 	if (flip > 4)
268 		SWAP(row, col);
269 	if (y_flipped(flip))
270 		row = fInputHeight - 1 - row;
271 	if (x_flipped(flip))
272 		col = fInputWidth - 1 - col;
273 
274 	return row * fInputWidth + col;
275 }
276 
277 
278 bool
279 DCRaw::_SupportsCompression(image_data_info& image) const
280 {
281 	switch (image.compression) {
282 		//case COMPRESSION_NONE:
283 		case COMPRESSION_OLD_JPEG:
284 		case COMPRESSION_PACKBITS:
285 			return true;
286 
287 		default:
288 			return false;
289 	}
290 }
291 
292 
293 bool
294 DCRaw::_IsCanon() const
295 {
296 	return !strncasecmp(fMeta.manufacturer, "Canon", 5);
297 }
298 
299 
300 bool
301 DCRaw::_IsKodak() const
302 {
303 	return !strncasecmp(fMeta.manufacturer, "Kodak", 5);
304 }
305 
306 
307 bool
308 DCRaw::_IsNikon() const
309 {
310 	return !strncasecmp(fMeta.manufacturer, "Nikon", 5);
311 }
312 
313 
314 bool
315 DCRaw::_IsOlympus() const
316 {
317 	return !strncasecmp(fMeta.manufacturer, "Olympus", 7);
318 }
319 
320 
321 bool
322 DCRaw::_IsPentax() const
323 {
324 	return !strncasecmp(fMeta.manufacturer, "Pentax", 6);
325 }
326 
327 
328 bool
329 DCRaw::_IsSamsung() const
330 {
331 	return !strncasecmp(fMeta.manufacturer, "Samsung", 7);
332 }
333 
334 
335 void
336 DCRaw::_ParseThumbTag(off_t baseOffset, uint32 offsetTag, uint32 lengthTag)
337 {
338 	uint16 entries;
339 	fRead(entries);
340 
341 	while (entries--) {
342 		off_t nextOffset;
343 		tiff_tag tag;
344 		_ParseTIFFTag(baseOffset, tag, nextOffset);
345 
346 		if (tag.tag == offsetTag)
347 			_Thumb().data_offset = fRead.Next<uint32>();
348 		if (tag.tag == lengthTag)
349 			_Thumb().bytes = fRead.Next<uint32>();
350 
351 		fRead.Seek(nextOffset, SEEK_SET);
352 	}
353 }
354 
355 
356 void
357 DCRaw::_ParseManufacturerTag(off_t baseOffset)
358 {
359 	static const uchar xlat[2][256] = {
360 		{
361 			0xc1,0xbf,0x6d,0x0d,0x59,0xc5,0x13,0x9d,0x83,0x61,0x6b,0x4f,0xc7,0x7f,0x3d,0x3d,
362 			0x53,0x59,0xe3,0xc7,0xe9,0x2f,0x95,0xa7,0x95,0x1f,0xdf,0x7f,0x2b,0x29,0xc7,0x0d,
363 			0xdf,0x07,0xef,0x71,0x89,0x3d,0x13,0x3d,0x3b,0x13,0xfb,0x0d,0x89,0xc1,0x65,0x1f,
364 			0xb3,0x0d,0x6b,0x29,0xe3,0xfb,0xef,0xa3,0x6b,0x47,0x7f,0x95,0x35,0xa7,0x47,0x4f,
365 			0xc7,0xf1,0x59,0x95,0x35,0x11,0x29,0x61,0xf1,0x3d,0xb3,0x2b,0x0d,0x43,0x89,0xc1,
366 			0x9d,0x9d,0x89,0x65,0xf1,0xe9,0xdf,0xbf,0x3d,0x7f,0x53,0x97,0xe5,0xe9,0x95,0x17,
367 			0x1d,0x3d,0x8b,0xfb,0xc7,0xe3,0x67,0xa7,0x07,0xf1,0x71,0xa7,0x53,0xb5,0x29,0x89,
368 			0xe5,0x2b,0xa7,0x17,0x29,0xe9,0x4f,0xc5,0x65,0x6d,0x6b,0xef,0x0d,0x89,0x49,0x2f,
369 			0xb3,0x43,0x53,0x65,0x1d,0x49,0xa3,0x13,0x89,0x59,0xef,0x6b,0xef,0x65,0x1d,0x0b,
370 			0x59,0x13,0xe3,0x4f,0x9d,0xb3,0x29,0x43,0x2b,0x07,0x1d,0x95,0x59,0x59,0x47,0xfb,
371 			0xe5,0xe9,0x61,0x47,0x2f,0x35,0x7f,0x17,0x7f,0xef,0x7f,0x95,0x95,0x71,0xd3,0xa3,
372 			0x0b,0x71,0xa3,0xad,0x0b,0x3b,0xb5,0xfb,0xa3,0xbf,0x4f,0x83,0x1d,0xad,0xe9,0x2f,
373 			0x71,0x65,0xa3,0xe5,0x07,0x35,0x3d,0x0d,0xb5,0xe9,0xe5,0x47,0x3b,0x9d,0xef,0x35,
374 			0xa3,0xbf,0xb3,0xdf,0x53,0xd3,0x97,0x53,0x49,0x71,0x07,0x35,0x61,0x71,0x2f,0x43,
375 			0x2f,0x11,0xdf,0x17,0x97,0xfb,0x95,0x3b,0x7f,0x6b,0xd3,0x25,0xbf,0xad,0xc7,0xc5,
376 			0xc5,0xb5,0x8b,0xef,0x2f,0xd3,0x07,0x6b,0x25,0x49,0x95,0x25,0x49,0x6d,0x71,0xc7
377 		},
378 		{
379 			0xa7,0xbc,0xc9,0xad,0x91,0xdf,0x85,0xe5,0xd4,0x78,0xd5,0x17,0x46,0x7c,0x29,0x4c,
380 			0x4d,0x03,0xe9,0x25,0x68,0x11,0x86,0xb3,0xbd,0xf7,0x6f,0x61,0x22,0xa2,0x26,0x34,
381 			0x2a,0xbe,0x1e,0x46,0x14,0x68,0x9d,0x44,0x18,0xc2,0x40,0xf4,0x7e,0x5f,0x1b,0xad,
382 			0x0b,0x94,0xb6,0x67,0xb4,0x0b,0xe1,0xea,0x95,0x9c,0x66,0xdc,0xe7,0x5d,0x6c,0x05,
383 			0xda,0xd5,0xdf,0x7a,0xef,0xf6,0xdb,0x1f,0x82,0x4c,0xc0,0x68,0x47,0xa1,0xbd,0xee,
384 			0x39,0x50,0x56,0x4a,0xdd,0xdf,0xa5,0xf8,0xc6,0xda,0xca,0x90,0xca,0x01,0x42,0x9d,
385 			0x8b,0x0c,0x73,0x43,0x75,0x05,0x94,0xde,0x24,0xb3,0x80,0x34,0xe5,0x2c,0xdc,0x9b,
386 			0x3f,0xca,0x33,0x45,0xd0,0xdb,0x5f,0xf5,0x52,0xc3,0x21,0xda,0xe2,0x22,0x72,0x6b,
387 			0x3e,0xd0,0x5b,0xa8,0x87,0x8c,0x06,0x5d,0x0f,0xdd,0x09,0x19,0x93,0xd0,0xb9,0xfc,
388 			0x8b,0x0f,0x84,0x60,0x33,0x1c,0x9b,0x45,0xf1,0xf0,0xa3,0x94,0x3a,0x12,0x77,0x33,
389 			0x4d,0x44,0x78,0x28,0x3c,0x9e,0xfd,0x65,0x57,0x16,0x94,0x6b,0xfb,0x59,0xd0,0xc8,
390 			0x22,0x36,0xdb,0xd2,0x63,0x98,0x43,0xa1,0x04,0x87,0x86,0xf7,0xa6,0x26,0xbb,0xd6,
391 			0x59,0x4d,0xbf,0x6a,0x2e,0xaa,0x2b,0xef,0xe6,0x78,0xb6,0x4e,0xe0,0x2f,0xdc,0x7c,
392 			0xbe,0x57,0x19,0x32,0x7e,0x2a,0xd0,0xb8,0xba,0x29,0x00,0x3c,0x52,0x7d,0xa8,0x49,
393 			0x3b,0x2d,0xeb,0x25,0x49,0xfa,0xa3,0xaa,0x39,0xa7,0xc5,0xa7,0x50,0x11,0x36,0xfb,
394 			0xc6,0x67,0x4a,0xf5,0xa5,0x12,0x65,0x7e,0xb0,0xdf,0xaf,0x4e,0xb3,0x61,0x7f,0x2f
395 		}
396 	};
397 
398 	uint32 ver97 = 0, serial = 0;
399 	uchar buf97[324], ci, cj, ck;
400 	bool originalSwap = fRead.IsSwapping();
401 	image_data_info& image = fImages[fNumImages];
402 
403 	// The MakerNote might have its own TIFF header (possibly with
404 	// its own byte-order!), or it might just be a table.
405 
406 	char type[10];
407 	fRead(type, sizeof(type));
408 
409 	if (!strncmp(type, "KDK", 3)
410 		|| !strncmp(type, "VER", 3)
411 		|| !strncmp(type, "IIII", 4)
412 		|| !strncmp(type, "MMMM", 4)) {
413 		// these aren't TIFF tables
414 		return;
415 	}
416 	if (!strncmp(type, "KC", 2)			// Konica KD-400Z, KD-510Z
417 		|| !strncmp(type, "MLY", 3)) {	// Minolta DiMAGE G series
418 		fRead.SetSwap(B_HOST_IS_LENDIAN != 0);
419 			// this chunk is always in big endian
420 
421 		uint32 whiteBalance[4] = {0, 0, 0, 0};
422 
423 		off_t offset;
424 	    while ((offset = fRead.Position()) < image.data_offset
425 	    	&& offset < 16384) {
426 			whiteBalance[0] = whiteBalance[2];
427 			whiteBalance[2] = whiteBalance[1];
428 			whiteBalance[1] = whiteBalance[3];
429 
430 			whiteBalance[3] = fRead.Next<uint16>();
431 			if (whiteBalance[1] == 256 && whiteBalance[3] == 256
432 				&& whiteBalance[0] > 256 && whiteBalance[0] < 640
433 				&& whiteBalance[2] > 256 && whiteBalance[2] < 640) {
434 				for (uint32 i = 0; i < 4; i++) {
435 					fMeta.camera_multipliers[i] = whiteBalance[i];
436 				}
437 			}
438 		}
439 		goto quit;
440 	}
441 	if (!strcmp(type, "Nikon")) {
442 		baseOffset = fRead.Position();
443 
444 		uint16 endian;
445 		fRead(endian);
446 
447 #if B_HOST_IS_LENDIAN
448 		fRead.SetSwap(endian == 'MM');
449 #else
450 		fRead.SetSwap(endian == 'II');
451 #endif
452 
453 		if (fRead.Next<uint16>() != 42)
454 			goto quit;
455 
456 		uint32 offset = fRead.Next<uint32>();
457 		fRead.Seek(offset - 8, SEEK_CUR);
458 	} else if (!strncmp(type, "FUJIFILM", 8)
459 		|| !strncmp(type, "SONY", 4)
460 		|| !strcmp(type, "Panasonic")) {
461 		fRead.SetSwap(B_HOST_IS_BENDIAN != 0);
462 			// this chunk is always in little endian
463 		fRead.Seek(2, SEEK_CUR);
464 	} else if (!strcmp(type, "OLYMP")
465 		|| !strcmp(type, "LEICA")
466 		|| !strcmp(type, "Ricoh")
467 		|| !strcmp(type, "EPSON"))
468 		fRead.Seek(-2, SEEK_CUR);
469 	else if (!strcmp(type, "AOC") || !strcmp(type, "QVC"))
470 		fRead.Seek(-4, SEEK_CUR);
471 	else
472 		fRead.Seek(-10, SEEK_CUR);
473 
474 	uint16 entries;
475 	fRead(entries);
476 	if (entries > 1000)
477 		return;
478 
479 	while (entries--) {
480 		off_t nextOffset;
481 		tiff_tag tag;
482 		_ParseTIFFTag(baseOffset, tag, nextOffset);
483 		TAG("Manufacturer tag %u (type %u, length %lu)\n", tag.tag, tag.type,
484 			tag.length);
485 
486 		if (strstr(fMeta.manufacturer, "PENTAX")) {
487 			if (tag.tag == 0x1b)
488 				tag.tag = 0x1018;
489 			if (tag.tag == 0x1c)
490 				tag.tag = 0x1017;
491 		} else if (tag.tag == 2 && strstr(fMeta.manufacturer, "NIKON")) {
492 			fRead.Next<uint16>();
493 				// ignored
494 			fMeta.iso_speed = fRead.Next<uint16>();
495 		}
496 
497 		if (tag.tag == 4 && tag.length == 27) {
498 			fRead.Next<uint32>();
499 				// ignored
500 			fMeta.iso_speed = 50 * pow(2, fRead.Next<uint16>() / 32.0 - 4);
501 			fRead.Next<uint16>();
502 				// ignored
503 			fMeta.aperture = pow(2, fRead.Next<uint16>() / 64.0);
504 			fMeta.shutter = pow(2, fRead.Next<int16>() / -32.0);
505 		}
506 		if (tag.tag == 8 && tag.type == 4)
507 			fMeta.shot_order = fRead.Next<uint32>();
508 		if (tag.tag == 0xc && tag.length == 4) {
509 			fMeta.camera_multipliers[0] = fRead.NextDouble(TIFF_FRACTION_TYPE);
510 			fMeta.camera_multipliers[2] = fRead.NextDouble(TIFF_FRACTION_TYPE);
511 		}
512 		if (tag.tag == 0x10 && tag.type == 4)
513 			fUniqueID = fRead.Next<uint32>();
514 		if (tag.tag == 0x11) {
515 			if (_ParseTIFFImageFileDirectory(baseOffset, fRead.Next<uint32>())
516 					== B_OK)
517 				fNumImages++;
518 		}
519 		if (tag.tag == 0x14 && tag.length == 2560 && tag.type == 7) {
520 			fRead.Seek(1248, SEEK_CUR);
521 			goto get2_256;
522 		}
523 		if (tag.tag == 0x1d) {
524 			int c;
525 			while ((c = fRead.Next<uint8>()) && c != EOF) {
526 				serial = serial * 10 + (isdigit(c) ? c - '0' : c % 10);
527 			}
528 		}
529 		if (tag.tag == 0x81 && tag.type == 4) {
530 			_Raw().data_offset = fRead.Next<uint32>();
531 			fRead.Seek(_Raw().data_offset + 41, SEEK_SET);
532 			_Raw().height = fRead.Next<uint16>() * 2;
533 			_Raw().width  = fRead.Next<uint16>();
534 			fFilters = 0x61616161;
535 		}
536 		if ((tag.tag == 0x81 && tag.type == 7)
537 			|| (tag.tag == 0x100 && tag.type == 7)
538 			|| (tag.tag == 0x280 && tag.type == 1)) {
539 			_Thumb().data_offset = fRead.Position();
540 			_Thumb().bytes = tag.length;
541 		}
542 		if (tag.tag == 0x88 && tag.type == 4
543 			&& (_Thumb().data_offset = fRead.Next<uint32>())) {
544 			_Thumb().data_offset += baseOffset;
545 		}
546 		if (tag.tag == 0x89 && tag.type == 4)
547 			_Thumb().bytes = fRead.Next<uint32>();
548 		if (tag.tag == 0x8c)
549 			fCurveOffset = fRead.Position() + 2112;
550 		if (tag.tag == 0x96)
551 			fCurveOffset = fRead.Position() + 2;
552 		if (tag.tag == 0x97) {
553 			for (uint32 i = 0; i < 4; i++) {
554 				ver97 = (ver97 << 4) + fRead.Next<uint8>() - '0';
555 			}
556 			switch (ver97) {
557 				case 0x100:
558 					fRead.Seek(68, SEEK_CUR);
559 					for (uint32 i = 0; i < 4; i++) {
560 						fMeta.camera_multipliers[(i >> 1) | ((i & 1) << 1)]
561 							= fRead.Next<uint16>();
562 					}
563 					break;
564 				case 0x102:
565 					fRead.Seek(6, SEEK_CUR);
566 					goto get2_rggb;
567 				case 0x103:
568 					fRead.Seek(16, SEEK_CUR);
569 					for (uint32 i = 0; i < 4; i++) {
570 						fMeta.camera_multipliers[i] = fRead.Next<uint16>();
571 					}
572 					break;
573 			}
574 			if (ver97 >> 8 == 2) {
575 				if (ver97 != 0x205)
576 					fRead.Seek(280, SEEK_CUR);
577 				fRead(buf97, sizeof(buf97));
578 			}
579 		}
580 		if (tag.tag == 0xa7 && ver97 >> 8 == 2) {
581 			ci = xlat[0][serial & 0xff];
582 			cj = xlat[1][fRead.Next<uint8>() ^ fRead.Next<uint8>()
583 				^ fRead.Next<uint8>() ^ fRead.Next<uint8>()];
584 			ck = 0x60;
585 			for (uint32 i = 0; i < 324; i++) {
586 				buf97[i] ^= (cj += ci * ck++);
587 			}
588 			for (uint32 i = 0; i < 4; i++) {
589 				uint16* data = (uint16*)(buf97
590 					+ (ver97 == 0x205 ? 14 : 6) + i * 2);
591 
592 				if (fRead.IsSwapping()) {
593 					fMeta.camera_multipliers[i ^ (i >> 1)]
594 						= __swap_int16(*data);
595 				} else {
596 					fMeta.camera_multipliers[i ^ (i >> 1)] = *data;
597 				}
598 			}
599 		}
600 		if (tag.tag == 0x200 && tag.length == 4) {
601 			fMeta.black = (fRead.Next<uint16>() + fRead.Next<uint16>()
602 				+ fRead.Next<uint16>() + fRead.Next<uint16>()) / 4;
603 		}
604 		if (tag.tag == 0x201 && tag.length == 4)
605 			goto get2_rggb;
606 		if (tag.tag == 0x401 && tag.length == 4) {
607 			fMeta.black = (fRead.Next<uint32>() + fRead.Next<uint32>()
608 				+ fRead.Next<uint32>() + fRead.Next<uint32>()) / 4;
609 		}
610 		if (tag.tag == 0xe01) {
611 			// Nikon Capture Note
612 			bool previousSwap = fRead.IsSwapping();
613 			fRead.SetSwap(B_HOST_IS_BENDIAN != 0);
614 				// this chunk is always in little endian
615 
616 			off_t offset = 22;
617 			fRead.Seek(offset, SEEK_CUR);
618 
619 			int32 i = 0;
620 
621 			for (; offset + 22 < tag.length; offset += 22 + i) {
622 				tag.tag = fRead.Next<uint32>();
623 				fRead.Seek(14, SEEK_CUR);
624 				i = fRead.Next<uint32>() - 4;
625 				if (tag.tag == 0x76a43207)
626 					fMeta.flip = fRead.Next<uint16>();
627 				else
628 					fRead.Seek(i, SEEK_CUR);
629 			}
630 
631 			fRead.SetSwap(previousSwap);
632 		}
633 		if (tag.tag == 0xe80 && tag.length == 256 && tag.type == 7) {
634 			fRead.Seek(48, SEEK_CUR);
635 			fMeta.camera_multipliers[0]
636 				= fRead.Next<uint16>() * 508 * 1.078 / 0x10000;
637 			fMeta.camera_multipliers[2]
638 				= fRead.Next<uint16>() * 382 * 1.173 / 0x10000;
639 		}
640 		if (tag.tag == 0xf00 && tag.type == 7) {
641 			if (tag.length == 614)
642 				fRead.Seek(176, SEEK_CUR);
643 			else if (tag.length == 734 || tag.length == 1502)
644 				fRead.Seek(148, SEEK_CUR);
645 			else
646 				goto next;
647 			goto get2_256;
648 		}
649 		if (tag.tag == 0x1011 && tag.length == 9 && fUseCameraWhiteBalance) {
650 			for (uint32 i = 0; i < 3; i++) {
651 				for (uint32 j = 0; j < 3; j++) {
652 					fMeta.rgb_camera[i][j] = fRead.Next<int16>() / 256.0;
653 				}
654 			}
655 			fRawColor = fMeta.rgb_camera[0][0] < 1;
656 		}
657 		if (tag.tag == 0x1012 && tag.length == 4) {
658 			fMeta.black = 0;
659 			for (uint32 i = 0; i < 4; i++) {
660 				fMeta.black += fRead.Next<uint16>() << 2;
661 			}
662 		}
663 		if (tag.tag == 0x1017)
664 			fMeta.camera_multipliers[0] = fRead.Next<uint16>() / 256.0;
665 		if (tag.tag == 0x1018)
666 			fMeta.camera_multipliers[2] = fRead.Next<uint16>() / 256.0;
667 
668 		if (tag.tag == 0x2011 && tag.length == 2) {
669 get2_256:
670 			bool previousSwap = fRead.IsSwapping();
671 			fRead.SetSwap(B_HOST_IS_LENDIAN != 0);
672 				// this chunk is always in big endian
673 
674 			fMeta.camera_multipliers[0] = fRead.Next<uint16>() / 256.0;
675 			fMeta.camera_multipliers[2] = fRead.Next<uint16>() / 256.0;
676 
677 			fRead.SetSwap(previousSwap);
678 		}
679 
680 		if (tag.tag == 0x2020)
681 			_ParseThumbTag(baseOffset, 257, 258);
682 		if (tag.tag == 0xb028) {
683 			fRead.Seek(fRead.Next<uint32>(), SEEK_SET);
684 			_ParseThumbTag(baseOffset, 136, 137);
685 		}
686 
687 		if (tag.tag == 0x4001) {
688 			{
689 				off_t offset = tag.length == 582 ? 50 : tag.length == 653
690 					? 68 : 126;
691 				fRead.Seek(offset, SEEK_CUR);
692 			}
693 get2_rggb:
694 			for (uint32 i = 0; i < 4; i++) {
695 				fMeta.camera_multipliers[i ^ (i >> 1)] = fRead.Next<uint16>();
696 			}
697 		}
698 
699 next:
700     	fRead.Seek(nextOffset, SEEK_SET);
701 	}
702 
703 quit:
704 	fRead.SetSwap(originalSwap);
705 }
706 
707 
708 void
709 DCRaw::_ParseEXIF(off_t baseOffset)
710 {
711 	bool kodak = !strncmp(fMeta.manufacturer, "EASTMAN", 7);
712 
713 	uint16 entries;
714 	fRead(entries);
715 
716 	while (entries--) {
717 		off_t nextOffset;
718 		tiff_tag tag;
719 		_ParseTIFFTag(baseOffset, tag, nextOffset);
720 		TAG("EXIF tag %u (type %u, length %lu)\n", tag.tag, tag.type,
721 			tag.length);
722 
723 		switch (tag.tag) {
724 #if 0
725 			default:
726 				printf("  unhandled EXIF tag %u\n", tag.tag);
727 				break;
728 #endif
729 			case 33434:
730 				fMeta.shutter = fRead.NextDouble(TIFF_FRACTION_TYPE);
731 				break;
732 			case 33437:
733 				fMeta.aperture = fRead.NextDouble(TIFF_FRACTION_TYPE);
734 				break;
735 			case 34855:
736 				fMeta.iso_speed = fRead.Next<uint16>();
737 				break;
738 			case 36867:
739 			case 36868:
740 				fMeta.timestamp = _ParseTIFFTimestamp(false);
741 				break;
742 			case 37377:
743 			{
744 				double expo;
745 				if ((expo = -fRead.NextDouble(TIFF_FRACTION_TYPE)) < 128)
746 					fMeta.shutter = pow(2, expo);
747 				break;
748 			}
749 			case 37378:
750 				fMeta.aperture
751 					= pow(2, fRead.NextDouble(TIFF_FRACTION_TYPE) / 2);
752 				break;
753 			case 37386:
754 				fMeta.focal_length = fRead.NextDouble(TIFF_FRACTION_TYPE);
755 				break;
756 			case 37500:
757 				_ParseManufacturerTag(baseOffset);
758 				break;
759 			case 40962:
760 				if (kodak)
761 					_Raw().width = fRead.Next<uint32>();
762 				break;
763 			case 40963:
764 				if (kodak)
765 					_Raw().height = fRead.Next<uint32>();
766 				break;
767 			case 41730:
768 				if (fRead.Next<uint32>() == 0x20002) {
769 					fEXIFFilters = 0;
770 					for (uint32 c = 0; c < 8; c += 2) {
771 						fEXIFFilters |= fRead.Next<uint8>() * 0x01010101 << c;
772 					}
773 				}
774 				break;
775 		}
776 
777 		fRead.Seek(nextOffset, SEEK_SET);
778 	}
779 }
780 
781 
782 void
783 DCRaw::_ParseLinearTable(uint32 length)
784 {
785 	if (length > 0x1000)
786 		length = 0x1000;
787 
788 	fRead.NextShorts(fCurve, length);
789 
790 	for (uint32 i = length; i < 0x1000; i++) {
791 		fCurve[i] = fCurve[i - 1];
792 	}
793 
794 	fMeta.maximum = fCurve[0xfff];
795 }
796 
797 
798 /*!	This (lengthy) method contains fixes for the values in the image data to
799 	be able to actually read the image data correctly.
800 */
801 void
802 DCRaw::_FixupValues()
803 {
804 	// PENTAX and SAMSUNG section
805 	// (Samsung sells rebranded Pentax cameras)
806 
807 	if (_IsPentax() || _IsSamsung()) {
808 		if (fInputWidth == 3936 && fInputHeight == 2624) {
809 			// Pentax K10D and Samsumg GX10
810 			fInputWidth = 3896;
811 			fInputHeight = 2616;
812 		}
813 	}
814 
815 	// CANON
816 
817 	if (_IsCanon()) {
818 		bool isCR2 = false;
819 		if (strstr(fMeta.model, "EOS D2000C")) {
820 			fFilters = 0x61616161;
821 			fMeta.black = fCurve[200];
822 		}
823 
824 		switch (_Raw().width) {
825 			case 2144:
826 				fInputHeight = 1550;
827 				fInputWidth = 2088;
828 				fTopMargin = 8;
829 				fLeftMargin = 4;
830 				if (!strcmp(fMeta.model, "PowerShot G1")) {
831 					fColors = 4;
832 					fFilters = 0xb4b4b4b4;
833 				}
834 				break;
835 
836 			case 2224:
837 				fInputHeight = 1448;
838 				fInputWidth = 2176;
839 				fTopMargin = 6;
840 				fLeftMargin = 48;
841 				break;
842 
843 			case 2376:
844 				fInputHeight = 1720;
845 				fInputWidth = 2312;
846 				fTopMargin = 6;
847 				fLeftMargin = 12;
848 				break;
849 
850 			case 2672:
851 				fInputHeight = 1960;
852 				fInputWidth = 2616;
853 				fTopMargin = 6;
854 				fLeftMargin = 12;
855 				break;
856 
857 			case 3152:
858 				fInputHeight = 2056;
859 				fInputWidth = 3088;
860 				fTopMargin = 12;
861 				fLeftMargin = 64;
862 				if (fUniqueID == 0x80000170)
863 					_AdobeCoefficients("Canon", "EOS 300D");
864 				fMeta.maximum = 0xfa0;
865 				break;
866 
867 			case 3160:
868 				fInputHeight = 2328;
869 				fInputWidth = 3112;
870 				fTopMargin = 12;
871 				fLeftMargin = 44;
872 				break;
873 
874 			case 3344:
875 				fInputHeight = 2472;
876 				fInputWidth = 3288;
877 				fTopMargin = 6;
878 				fLeftMargin = 4;
879 				break;
880 
881 			case 3516:
882 				fTopMargin = 14;
883 				fLeftMargin = 42;
884 				if (fUniqueID == 0x80000189)
885 					_AdobeCoefficients("Canon", "EOS 350D");
886 				isCR2 = true;
887 				break;
888 
889 			case 3596:
890 				fTopMargin = 12;
891 				fLeftMargin = 74;
892 				isCR2 = true;
893 				break;
894 
895 			case 3948:
896 				fTopMargin = 18;
897 				fLeftMargin = 42;
898 				fInputHeight -= 2;
899 				if (fUniqueID == 0x80000236)
900 					_AdobeCoefficients("Canon", "EOS 400D");
901 				isCR2 = true;
902 				break;
903 
904 			case 3984:
905 				fTopMargin  = 20;
906 				fLeftMargin = 76;
907 				fInputHeight -= 2;
908 				fMeta.maximum = 0x3bb0;
909 				isCR2 = true;
910 				break;
911 
912 			case 4476:
913 				fTopMargin  = 34;
914 				fLeftMargin = 90;
915 				fMeta.maximum = 0xe6c;
916 				isCR2 = true;
917 				break;
918 
919 			case 5108:
920 				fTopMargin  = 13;
921 				fLeftMargin = 98;
922 				fMeta.maximum = 0xe80;
923 				isCR2 = true;
924 				break;
925 		}
926 
927 		if (isCR2) {
928 			fInputHeight -= fTopMargin;
929 			fInputWidth -= fLeftMargin;
930 		}
931 	}
932 
933 	// Olympus
934 
935 	if (_IsOlympus()) {
936 		if (!strcmp(fMeta.model,"E-300") || !strcmp(fMeta.model,"E-500")) {
937 			fInputWidth -= 20;
938 			fMeta.maximum = 0xfc30;
939 			//if (load_raw == &CLASS unpacked_load_raw) black = 0;
940 		}
941 	}
942 }
943 
944 
945 //	#pragma mark - Image Conversion
946 
947 
948 void
949 DCRaw::_ScaleColors()
950 {
951 	if (fProgressMonitor != NULL)
952 		fProgressMonitor("Scale Colors", 5, fProgressData);
953 
954 	int dblack, c, val, sum[8];
955 	uint32 row, col, x, y;
956 	double dsum[8], dmin, dmax;
957 	float scale_mul[4];
958 
959 	if (fUseCameraWhiteBalance && fMeta.camera_multipliers[0] != -1) {
960 		memset(sum, 0, sizeof(sum));
961 		for (row = 0; row < 8; row++) {
962 			for (col = 0; col < 8; col++) {
963 				c = FC(row, col);
964 				if ((val = fWhite[row][col] - fMeta.black) > 0)
965 					sum[c] += val;
966 				sum[c + 4]++;
967 			}
968 		}
969 
970 		if (sum[0] && sum[1] && sum[2] && sum[3]) {
971 			for (int c = 0; c < 4; c++) {
972 				fMeta.pre_multipliers[c] = (float)sum[c+4] / sum[c];
973 			}
974 		} else if (fMeta.camera_multipliers[0] && fMeta.camera_multipliers[2]) {
975 			memcpy(fMeta.pre_multipliers, fMeta.camera_multipliers,
976 				sizeof(fMeta.pre_multipliers));
977 		} else
978 			fprintf(stderr, "Cannot use camera white balance.\n");
979 	} else if (fUseAutoWhiteBalance) {
980 		memset(dsum, 0, sizeof(dsum));
981 		for (row = 0; row < fOutputHeight - 7; row += 8) {
982 			for (col = 0; col < fOutputWidth - 7; col += 8) {
983 				memset(sum, 0, sizeof(sum));
984 				for (y = row; y < row + 8; y++) {
985 					for (x = col; x < col + 8; x++) {
986 						for (int c = 0; c < 4; c++) {
987 							val = fImageData[y * fOutputWidth + x][c];
988 							if (!val)
989 								continue;
990 							if (val > fMeta.maximum - 25)
991 								goto skip_block;
992 							val -= fMeta.black;
993 							if (val < 0)
994 								val = 0;
995 							sum[c] += val;
996 							sum[c+4]++;
997 						}
998 					}
999 				}
1000 
1001 				for (c=0; c < 8; c++) {
1002 					dsum[c] += sum[c];
1003 				}
1004 
1005 			skip_block:
1006 				continue;
1007 			}
1008 		}
1009 		for (int c = 0; c < 4; c++) {
1010 			if (dsum[c])
1011 				fMeta.pre_multipliers[c] = dsum[c + 4] / dsum[c];
1012 		}
1013 	}
1014 
1015 
1016 	if (fUserMultipliers[0]) {
1017 		memcpy(fMeta.pre_multipliers, fUserMultipliers,
1018 			sizeof(fMeta.pre_multipliers));
1019 	}
1020 	if (fMeta.pre_multipliers[3] == 0)
1021 		fMeta.pre_multipliers[3] = fColors < 4 ? fMeta.pre_multipliers[1] : 1;
1022 
1023 	dblack = fMeta.black;
1024 	if (fThreshold)
1025 		_WaveletDenoise();
1026 
1027 	fMeta.maximum -= fMeta.black;
1028 	for (dmin = DBL_MAX, dmax = c = 0; c < 4; c++) {
1029 		if (dmin > fMeta.pre_multipliers[c])
1030 			dmin = fMeta.pre_multipliers[c];
1031 		if (dmax < fMeta.pre_multipliers[c])
1032 			dmax = fMeta.pre_multipliers[c];
1033 	}
1034 
1035 	if (!fHighlight)
1036 		dmax = dmin;
1037 
1038 	for (int c = 0; c < 4; c++) {
1039 		scale_mul[c] = (fMeta.pre_multipliers[c] /= dmax) * 65535.0
1040 			/ fMeta.maximum;
1041 	}
1042 
1043 #if 0
1044 	if (1/*verbose*/) {
1045 		fprintf(stderr, "Scaling with black %d, multipliers", dblack);
1046 		for (int c = 0; c < 4; c++) {
1047 			fprintf(stderr, " %f", fMeta.pre_multipliers[c]);
1048 		}
1049 		fputc('\n', stderr);
1050 	}
1051 #endif
1052 
1053 	for (row = 0; row < fOutputHeight; row++) {
1054 		for (col = 0; col < fOutputWidth; col++) {
1055 			for (int c = 0; c < 4; c++) {
1056 				val = fImageData[row * fOutputWidth + col][c];
1057 				if (!val)
1058 					continue;
1059 				val -= fMeta.black;
1060 				val = int(val * scale_mul[c]);
1061 				fImageData[row * fOutputWidth + col][c] = CLIP(val);
1062 			}
1063 		}
1064 	}
1065 }
1066 
1067 
1068 void
1069 DCRaw::_WaveletDenoise()
1070 {
1071 	if (fProgressMonitor != NULL)
1072 		fProgressMonitor("Wavelet Denoise", 8, fProgressData);
1073 
1074 	float *fimg, *temp, mul[2], avg, diff;
1075 	int32 scale = 1, sh, c, i, j, k, m, row, col, size, numColors, dim = 0;
1076 	int32 wlast;
1077 	ushort *window[4];
1078 	// Daubechies 9-tap/7-tap filter
1079 	static const float wlet[] =	{ 1.149604398, -1.586134342,
1080 		-0.05298011854, 0.8829110762, 0.4435068522 };
1081 
1082 	while ((fMeta.maximum << scale) < 0x10000) {
1083 		scale++;
1084 	}
1085 	fMeta.maximum <<= fMeta.maximum << --scale;
1086 	fMeta.black <<= scale;
1087 
1088 	while ((1UL << dim) < fOutputWidth || (1UL << dim) < fOutputHeight) {
1089 		dim++;
1090 	}
1091 
1092 	fimg = (float *)calloc((1UL << dim*2) + (1UL << dim) + 2, sizeof *fimg);
1093 	if (fimg == NULL)
1094 		return;
1095 
1096 	temp = fimg + (1 << dim * 2) + 1;
1097 	numColors = fColors;
1098 	if (numColors == 3 && fFilters)
1099 		numColors++;
1100 
1101 	for (c = 0; c < numColors; c++) {
1102 		// denoise R,G1,B,G3 individually
1103 		for (row = 0; row < (int32)fOutputHeight; row++) {
1104 			for (col = 0; col < (int32)fOutputWidth; col++) {
1105 				fimg[(row << dim) + col]
1106 					= fImageData[row * fOutputWidth + col][c] << scale;
1107 			}
1108 		}
1109 		for (size = 1UL << dim; size > 1; size >>= 1) {
1110 			for (sh = 0; sh <= dim; sh += dim) {
1111 				for (i = 0; i < size; i++) {
1112 					for (j = 0; j < size; j++) {
1113 						temp[j] = fimg[(i << (dim - sh)) + (j << sh)];
1114 					}
1115 					for (k = 1; k < 5; k += 2) {
1116 						temp[size] = temp[size - 2];
1117 						for (m = 1; m < size; m += 2) {
1118 							temp[m] += wlet[k] * (temp[m - 1] + temp[m + 1]);
1119 						}
1120 						temp[-1] = temp[1];
1121 						for (m = 0; m < size; m += 2) {
1122 							temp[m] += wlet[k + 1]
1123 								* (temp[m - 1] + temp[m + 1]);
1124 						}
1125 					}
1126 					for (m = 0; m < size; m++) {
1127 						temp[m] *= (m & 1) ? 1 / wlet[0] : wlet[0];
1128 					}
1129 					for (j = k = 0; j < size; j++, k += 2) {
1130 						if (k == size)
1131 							k = 1;
1132 						fimg[(i << (dim - sh)) + (j << sh)] = temp[k];
1133 					}
1134 				}
1135 			}
1136 		}
1137 
1138 		for (i = 0; i < (1 << dim * 2); i++) {
1139 			if (fimg[i] < -fThreshold)
1140 				fimg[i] += fThreshold;
1141 			else if (fimg[i] > fThreshold)
1142 				fimg[i] -= fThreshold;
1143 			else
1144 				fimg[i] = 0;
1145 		}
1146 
1147 		for (size = 2; size <= (1 << dim); size <<= 1) {
1148 			for (sh = dim; sh >= 0; sh -= dim) {
1149 				for (i = 0; i < size; i++) {
1150 					for (j = k = 0; j < size; j++, k += 2) {
1151 						if (k == size)
1152 							k = 1;
1153 						temp[k] = fimg[(i << (dim - sh)) + (j << sh)];
1154 					}
1155 					for (m = 0; m < size; m++) {
1156 						temp[m] *= (m & 1) ? wlet[0] : 1 / wlet[0];
1157 					}
1158 					for (k = 3; k > 0; k -= 2) {
1159 						temp[-1] = temp[1];
1160 						for (m = 0; m < size; m += 2) {
1161 							temp[m] -= wlet[k + 1]
1162 								* (temp[m - 1] + temp[m + 1]);
1163 						}
1164 						temp[size] = temp[size - 2];
1165 						for (m = 1; m < size; m += 2) {
1166 							temp[m] -= wlet[k] * (temp[m - 1] + temp[m + 1]);
1167 						}
1168 					}
1169 					for (j = 0; j < size; j++) {
1170 						fimg[(i << (dim - sh)) + (j << sh)] = temp[j];
1171 					}
1172 				}
1173 			}
1174 		}
1175 
1176 		for (row = 0; row < (int32)fOutputHeight; row++) {
1177 			for (col = 0; col < (int32)fOutputWidth; col++) {
1178 				fImageData[row * fOutputWidth + col][c]
1179 					= (uint16)CLIP(fimg[(row << dim) + col] + 0.5);
1180 			}
1181 		}
1182 	}
1183 
1184 	if (fFilters && fColors == 3) {
1185 		// pull G1 and G3 closer together
1186 		for (row = 0; row < 2; row++) {
1187 			mul[row] = 0.125 * fMeta.pre_multipliers[FC(row + 1, 0) | 1]
1188 				/ fMeta.pre_multipliers[FC(row, 0) | 1];
1189 		}
1190 		for (i = 0; i < 4; i++) {
1191 			window[i] = (ushort *)fimg + fInputWidth * i;
1192 		}
1193 		for (wlast = -1, row = 1; row < (int32)fInputHeight - 1; row++) {
1194 			while (wlast < (int32)row + 1) {
1195 				for (wlast++, i = 0; i < 4; i++) {
1196 					window[(i + 3) & 3] = window[i];
1197 				}
1198 				for (col = FC(wlast, 1) & 1; col < (int32)fInputWidth;
1199 						col += 2) {
1200 					window[2][col] = _Bayer(col, wlast);
1201 				}
1202 			}
1203 
1204 			for (col = (FC(row, 0) & 1) + 1; col < (int32)fInputWidth - 1;
1205 					col += 2) {
1206 				avg = ( window[0][col - 1] + window[0][col + 1]
1207 					+ window[2][col - 1] + window[2][col + 1] - fMeta.black * 4)
1208 					* mul[row & 1] + (window[1][col] - fMeta.black) * 0.5
1209 					+ fMeta.black;
1210 				diff = _Bayer(col, row) - avg;
1211 
1212 				if (diff < -fThreshold / M_SQRT2)
1213 					diff += fThreshold / M_SQRT2;
1214 				else if (diff > fThreshold / M_SQRT2)
1215 					diff -= fThreshold / M_SQRT2;
1216 				else
1217 					diff = 0;
1218 				_Bayer(col, row) = (uint16)CLIP(avg + diff + 0.5);
1219 			}
1220 		}
1221 	}
1222 
1223 	free(fimg);
1224 }
1225 
1226 
1227 void
1228 DCRaw::_PreInterpolate()
1229 {
1230 	if (fProgressMonitor != NULL)
1231 		fProgressMonitor("Pre-Interpolate", 10, fProgressData);
1232 
1233 	uint32 row, col;
1234 
1235 	if (fShrink) {
1236 		if (fHalfSize) {
1237 			fInputHeight = fOutputHeight;
1238 			fInputWidth = fOutputWidth;
1239 			fFilters = 0;
1240 		} else {
1241 			uint16 (*data)[4] = (uint16 (*)[4])calloc(fInputHeight
1242 				* fInputWidth, sizeof(*data));
1243 			if (data == NULL)
1244 				throw (status_t)B_NO_MEMORY;
1245 
1246 			for (row = 0; row < fInputHeight; row++) {
1247 				for (col = 0; col < fInputWidth; col++) {
1248 					data[row * fInputWidth + col][FC(row, col)]
1249 						= _Bayer(col, row);
1250 				}
1251 			}
1252 
1253 			free(fImageData);
1254 			fImageData = data;
1255 			fShrink = 0;
1256 		}
1257 	}
1258 
1259 	if (fFilters && fColors == 3) {
1260 //		if ((mix_green = four_color_rgb))
1261 //			fColors++;
1262 //		else
1263 		{
1264 			for (row = FC(1, 0) >> 1; row < fInputHeight; row += 2) {
1265 				for (col = FC(row, 1) & 1; col < fInputWidth; col += 2) {
1266 					fImageData[row * fInputWidth + col][1]
1267 						= fImageData[row * fInputWidth + col][3];
1268 				}
1269 			}
1270 			fFilters &= ~((fFilters & 0x55555555) << 1);
1271 		}
1272 	}
1273 }
1274 
1275 
1276 void
1277 DCRaw::_CameraToCIELab(ushort cam[4], float lab[3])
1278 {
1279 	if (cam == NULL) {
1280 		for (uint32 i = 0; i < 0x10000; i++) {
1281 			float r = i / 65535.0;
1282 			cbrt[i] = r > 0.008856 ? pow(r, 1 / 3.0) : 7.787 * r + 16 / 116.0;
1283 		}
1284 		for (uint32 i = 0; i < 3; i++) {
1285 			for (uint32 j = 0; j < fColors; j++) {
1286 				xyz_cam[i][j] = 0;
1287 				for (uint32 k = 0; k < 3; k++) {
1288 					xyz_cam[i][j] += xyz_rgb[i][k] * fMeta.rgb_camera[k][j]
1289 						/ kD65White[i];
1290 				}
1291 			}
1292 		}
1293 	} else {
1294 		float xyz[3];
1295 		xyz[0] = xyz[1] = xyz[2] = 0.5;
1296 		for (uint32 c = 0; c < fColors; c++) {
1297 			xyz[0] += xyz_cam[0][c] * cam[c];
1298 			xyz[1] += xyz_cam[1][c] * cam[c];
1299 			xyz[2] += xyz_cam[2][c] * cam[c];
1300 		}
1301 		xyz[0] = cbrt[CLIP((int) xyz[0])];
1302 		xyz[1] = cbrt[CLIP((int) xyz[1])];
1303 		xyz[2] = cbrt[CLIP((int) xyz[2])];
1304 		lab[0] = 116 * xyz[1] - 16;
1305 		lab[1] = 500 * (xyz[0] - xyz[1]);
1306 		lab[2] = 200 * (xyz[1] - xyz[2]);
1307 	}
1308 }
1309 
1310 
1311 void
1312 DCRaw::_CameraXYZCoefficients(double cameraXYZ[4][3])
1313 {
1314 	double cam_rgb[4][3], inverse[4][3], num;
1315 	uint32 i, j, k;
1316 
1317 	// Multiply out XYZ colorspace
1318 	for (i = 0; i < fColors; i++)	{
1319 		for (j = 0; j < 3; j++) {
1320 			for (cam_rgb[i][j] = k = 0; k < 3; k++) {
1321 				cam_rgb[i][j] += cameraXYZ[i][k] * xyz_rgb[k][j];
1322 			}
1323 		}
1324 	}
1325 
1326 	// Normalize cam_rgb so that cam_rgb * (1,1,1) is (1,1,1,1)
1327 	for (i = 0; i < fColors; i++) {
1328 		for (num = j = 0; j < 3; j++) {
1329 			num += cam_rgb[i][j];
1330 		}
1331 		for (j = 0; j < 3; j++) {
1332 			cam_rgb[i][j] /= num;
1333 		}
1334 		fMeta.pre_multipliers[i] = 1 / num;
1335 	}
1336 
1337 	_PseudoInverse(cam_rgb, inverse, fColors);
1338 
1339 	fRawColor = false;
1340 	for (i = 0; i < 3; i++) {
1341 		for (j=0; j < fColors; j++) {
1342 			fMeta.rgb_camera[i][j] = inverse[j][i];
1343 		}
1344 	}
1345 }
1346 
1347 
1348 /*!	Thanks to Adobe for providing these excellent CAM -> XYZ matrices!
1349 */
1350 void
1351 DCRaw::_AdobeCoefficients(char *make, char *model)
1352 {
1353 	static const struct {
1354 		const char *prefix;
1355 		short black, trans[12];
1356 	} table[] = {
1357 		{ "Canon EOS D2000", 0,
1358 			{ 24542,-10860,-3401,-1490,11370,-297,2858,-605,3225 }},
1359 		{ "Canon EOS D6000", 0,
1360 			{ 20482,-7172,-3125,-1033,10410,-285,2542,226,3136 }},
1361 		{ "Canon EOS D30", 0,
1362 			{ 9805,-2689,-1312,-5803,13064,3068,-2438,3075,8775 }},
1363 		{ "Canon EOS D60", 0,
1364 			{ 6188,-1341,-890,-7168,14489,2937,-2640,3228,8483 }},
1365 		{ "Canon EOS 5D", 0,
1366 			{ 6347,-479,-972,-8297,15954,2480,-1968,2131,7649 }},
1367 		{ "Canon EOS 20Da", 0,
1368 			{ 14155,-5065,-1382,-6550,14633,2039,-1623,1824,6561 }},
1369 		{ "Canon EOS 20D", 0,
1370 			{ 6599,-537,-891,-8071,15783,2424,-1983,2234,7462 }},
1371 		{ "Canon EOS 30D", 0,
1372 			{ 6257,-303,-1000,-7880,15621,2396,-1714,1904,7046 }},
1373 		{ "Canon EOS 350D", 0,
1374 			{ 6018,-617,-965,-8645,15881,2975,-1530,1719,7642 }},
1375 		{ "Canon EOS 400D", 0,
1376 			{ 7054,-1501,-990,-8156,15544,2812,-1278,1414,7796 }},
1377 		{ "Canon EOS-1Ds Mark II", 0,
1378 			{ 6517,-602,-867,-8180,15926,2378,-1618,1771,7633 }},
1379 		{ "Canon EOS-1D Mark II N", 0,
1380 			{ 6240,-466,-822,-8180,15825,2500,-1801,1938,8042 }},
1381 		{ "Canon EOS-1D Mark II", 0,
1382 			{ 6264,-582,-724,-8312,15948,2504,-1744,1919,8664 }},
1383 		{ "Canon EOS-1DS", 0,
1384 			{ 4374,3631,-1743,-7520,15212,2472,-2892,3632,8161 }},
1385 		{ "Canon EOS-1D", 0,
1386 			{ 6806,-179,-1020,-8097,16415,1687,-3267,4236,7690 }},
1387 		{ "Canon EOS", 0,
1388 			{ 8197,-2000,-1118,-6714,14335,2592,-2536,3178,8266 }},
1389 		{ "Canon PowerShot A50", 0,
1390 			{ -5300,9846,1776,3436,684,3939,-5540,9879,6200,-1404,11175,217 }},
1391 		{ "Canon PowerShot A5", 0,
1392 			{ -4801,9475,1952,2926,1611,4094,-5259,10164,5947,-1554,10883,547 }},
1393 		{ "Canon PowerShot G1", 0,
1394 			{ -4778,9467,2172,4743,-1141,4344,-5146,9908,6077,-1566,11051,557 }},
1395 		{ "Canon PowerShot G2", 0,
1396 			{ 9087,-2693,-1049,-6715,14382,2537,-2291,2819,7790 }},
1397 		{ "Canon PowerShot G3", 0,
1398 			{ 9212,-2781,-1073,-6573,14189,2605,-2300,2844,7664 }},
1399 		{ "Canon PowerShot G5", 0,
1400 			{ 9757,-2872,-933,-5972,13861,2301,-1622,2328,7212 }},
1401 		{ "Canon PowerShot G6", 0,
1402 			{ 9877,-3775,-871,-7613,14807,3072,-1448,1305,7485 }},
1403 		{ "Canon PowerShot Pro1", 0,
1404 			{ 10062,-3522,-999,-7643,15117,2730,-765,817,7323 }},
1405 		{ "Canon PowerShot Pro70", 34,
1406 			{ -4155,9818,1529,3939,-25,4522,-5521,9870,6610,-2238,10873,1342 }},
1407 		{ "Canon PowerShot Pro90", 0,
1408 			{ -4963,9896,2235,4642,-987,4294,-5162,10011,5859,-1770,11230,577 }},
1409 		{ "Canon PowerShot S30", 0,
1410 			{ 10566,-3652,-1129,-6552,14662,2006,-2197,2581,7670 }},
1411 		{ "Canon PowerShot S40", 0,
1412 			{ 8510,-2487,-940,-6869,14231,2900,-2318,2829,9013 }},
1413 		{ "Canon PowerShot S45", 0,
1414 			{ 8163,-2333,-955,-6682,14174,2751,-2077,2597,8041 }},
1415 		{ "Canon PowerShot S50", 0,
1416 			{ 8882,-2571,-863,-6348,14234,2288,-1516,2172,6569 }},
1417 		{ "Canon PowerShot S60", 0,
1418 			{ 8795,-2482,-797,-7804,15403,2573,-1422,1996,7082 }},
1419 		{ "Canon PowerShot S70", 0,
1420 			{ 9976,-3810,-832,-7115,14463,2906,-901,989,7889 }},
1421 		{ "Canon PowerShot A610", 0, /* DJC */
1422 			{ 15591,-6402,-1592,-5365,13198,2168,-1300,1824,5075 }},
1423 		{ "Canon PowerShot A620", 0, /* DJC */
1424 			{ 15265,-6193,-1558,-4125,12116,2010,-888,1639,5220 }},
1425 		{ "Canon PowerShot S3 IS", 0, /* DJC */
1426 			{ 14062,-5199,-1446,-4712,12470,2243,-1286,2028,4836 }},
1427 		{ "Contax N Digital", 0,
1428 			{ 7777,1285,-1053,-9280,16543,2916,-3677,5679,7060 }},
1429 		{ "EPSON R-D1", 0,
1430 			{ 6827,-1878,-732,-8429,16012,2564,-704,592,7145 }},
1431 		{ "FUJIFILM FinePix E550", 0,
1432 			{ 11044,-3888,-1120,-7248,15168,2208,-1531,2277,8069 }},
1433 		{ "FUJIFILM FinePix E900", 0,
1434 			{ 9183,-2526,-1078,-7461,15071,2574,-2022,2440,8639 }},
1435 		{ "FUJIFILM FinePix F8", 0,
1436 			{ 11044,-3888,-1120,-7248,15168,2208,-1531,2277,8069 }},
1437 		{ "FUJIFILM FinePix F7", 0,
1438 			{ 10004,-3219,-1201,-7036,15047,2107,-1863,2565,7736 }},
1439 		{ "FUJIFILM FinePix S20Pro", 0,
1440 			{ 10004,-3219,-1201,-7036,15047,2107,-1863,2565,7736 }},
1441 		{ "FUJIFILM FinePix S2Pro", 128,
1442 			{ 12492,-4690,-1402,-7033,15423,1647,-1507,2111,7697 }},
1443 		{ "FUJIFILM FinePix S3Pro", 0,
1444 			{ 11807,-4612,-1294,-8927,16968,1988,-2120,2741,8006 }},
1445 		{ "FUJIFILM FinePix S5000", 0,
1446 			{ 8754,-2732,-1019,-7204,15069,2276,-1702,2334,6982 }},
1447 		{ "FUJIFILM FinePix S5100", 0,
1448 			{ 11940,-4431,-1255,-6766,14428,2542,-993,1165,7421 }},
1449 		{ "FUJIFILM FinePix S5500", 0,
1450 			{ 11940,-4431,-1255,-6766,14428,2542,-993,1165,7421 }},
1451 		{ "FUJIFILM FinePix S5200", 0,
1452 			{ 9636,-2804,-988,-7442,15040,2589,-1803,2311,8621 }},
1453 		{ "FUJIFILM FinePix S5600", 0,
1454 			{ 9636,-2804,-988,-7442,15040,2589,-1803,2311,8621 }},
1455 		{ "FUJIFILM FinePix S6", 0,
1456 			{ 12628,-4887,-1401,-6861,14996,1962,-2198,2782,7091 }},
1457 		{ "FUJIFILM FinePix S7000", 0,
1458 			{ 10190,-3506,-1312,-7153,15051,2238,-2003,2399,7505 }},
1459 		{ "FUJIFILM FinePix S9000", 0,
1460 			{ 10491,-3423,-1145,-7385,15027,2538,-1809,2275,8692 }},
1461 		{ "FUJIFILM FinePix S9500", 0,
1462 			{ 10491,-3423,-1145,-7385,15027,2538,-1809,2275,8692 }},
1463 		{ "FUJIFILM FinePix S9100", 0,
1464 			{ 12343,-4515,-1285,-7165,14899,2435,-1895,2496,8800 }},
1465 		{ "FUJIFILM FinePix S9600", 0,
1466 			{ 12343,-4515,-1285,-7165,14899,2435,-1895,2496,8800 }},
1467 		{ "Imacon Ixpress", 0,	/* DJC */
1468 			{ 7025,-1415,-704,-5188,13765,1424,-1248,2742,6038 }},
1469 		{ "KODAK NC2000", 0,	/* DJC */
1470 			{ 16475,-6903,-1218,-851,10375,477,2505,-7,1020 }},
1471 		{ "Kodak DCS315C", 8,
1472 			{ 17523,-4827,-2510,756,8546,-137,6113,1649,2250 }},
1473 		{ "Kodak DCS330C", 8,
1474 			{ 20620,-7572,-2801,-103,10073,-396,3551,-233,2220 }},
1475 		{ "KODAK DCS420", 0,
1476 			{ 10868,-1852,-644,-1537,11083,484,2343,628,2216 }},
1477 		{ "KODAK DCS460", 0,
1478 			{ 10592,-2206,-967,-1944,11685,230,2206,670,1273 }},
1479 		{ "KODAK EOSDCS1", 0,
1480 			{ 10592,-2206,-967,-1944,11685,230,2206,670,1273 }},
1481 		{ "KODAK EOSDCS3B", 0,
1482 			{ 9898,-2700,-940,-2478,12219,206,1985,634,1031 }},
1483 		{ "Kodak DCS520C", 180,
1484 			{ 24542,-10860,-3401,-1490,11370,-297,2858,-605,3225 }},
1485 		{ "Kodak DCS560C", 188,
1486 			{ 20482,-7172,-3125,-1033,10410,-285,2542,226,3136 }},
1487 		{ "Kodak DCS620C", 180,
1488 			{ 23617,-10175,-3149,-2054,11749,-272,2586,-489,3453 }},
1489 		{ "Kodak DCS620X", 185,
1490 			{ 13095,-6231,154,12221,-21,-2137,895,4602,2258 }},
1491 		{ "Kodak DCS660C", 214,
1492 			{ 18244,-6351,-2739,-791,11193,-521,3711,-129,2802 }},
1493 		{ "Kodak DCS720X", 0,
1494 			{ 11775,-5884,950,9556,1846,-1286,-1019,6221,2728 }},
1495 		{ "Kodak DCS760C", 0,
1496 			{ 16623,-6309,-1411,-4344,13923,323,2285,274,2926 }},
1497 		{ "Kodak DCS Pro SLR", 0,
1498 			{ 5494,2393,-232,-6427,13850,2846,-1876,3997,5445 }},
1499 		{ "Kodak DCS Pro 14nx", 0,
1500 			{ 5494,2393,-232,-6427,13850,2846,-1876,3997,5445 }},
1501 		{ "Kodak DCS Pro 14", 0,
1502 			{ 7791,3128,-776,-8588,16458,2039,-2455,4006,6198 }},
1503 		{ "Kodak ProBack645", 0,
1504 			{ 16414,-6060,-1470,-3555,13037,473,2545,122,4948 }},
1505 		{ "Kodak ProBack", 0,
1506 			{ 21179,-8316,-2918,-915,11019,-165,3477,-180,4210 }},
1507 		{ "KODAK P712", 0,
1508 			{ 9658,-3314,-823,-5163,12695,2768,-1342,1843,6044 }},
1509 		{ "KODAK P850", 0,
1510 			{ 10511,-3836,-1102,-6946,14587,2558,-1481,1792,6246 }},
1511 		{ "KODAK P880", 0,
1512 			{ 12805,-4662,-1376,-7480,15267,2360,-1626,2194,7904 }},
1513 		{ "Leaf CMost", 0,
1514 			{ 3952,2189,449,-6701,14585,2275,-4536,7349,6536 }},
1515 		{ "Leaf Valeo 6", 0,
1516 			{ 3952,2189,449,-6701,14585,2275,-4536,7349,6536 }},
1517 		{ "Leaf Aptus 65", 0,
1518 			{ 7914,1414,-1190,-8777,16582,2280,-2811,4605,5562 }},
1519 		{ "Leaf Aptus 75", 0,
1520 			{ 7914,1414,-1190,-8777,16582,2280,-2811,4605,5562 }},
1521 		{ "Leaf", 0,
1522 			{ 8236,1746,-1314,-8251,15953,2428,-3673,5786,5771 }},
1523 		{ "Micron 2010", 110,	/* DJC */
1524 			{ 16695,-3761,-2151,155,9682,163,3433,951,4904 }},
1525 		{ "Minolta DiMAGE 5", 0,
1526 			{ 8983,-2942,-963,-6556,14476,2237,-2426,2887,8014 }},
1527 		{ "Minolta DiMAGE 7Hi", 0,
1528 			{ 11368,-3894,-1242,-6521,14358,2339,-2475,3056,7285 }},
1529 		{ "Minolta DiMAGE 7", 0,
1530 			{ 9144,-2777,-998,-6676,14556,2281,-2470,3019,7744 }},
1531 		{ "Minolta DiMAGE A1", 0,
1532 			{ 9274,-2547,-1167,-8220,16323,1943,-2273,2720,8340 }},
1533 		{ "MINOLTA DiMAGE A200", 0,
1534 			{ 8560,-2487,-986,-8112,15535,2771,-1209,1324,7743 }},
1535 		{ "Minolta DiMAGE A2", 0,
1536 			{ 9097,-2726,-1053,-8073,15506,2762,-966,981,7763 }},
1537 		{ "Minolta DiMAGE Z2", 0,	/* DJC */
1538 			{ 11280,-3564,-1370,-4655,12374,2282,-1423,2168,5396 }},
1539 		{ "MINOLTA DYNAX 5", 0,
1540 			{ 10284,-3283,-1086,-7957,15762,2316,-829,882,6644 }},
1541 		{ "MINOLTA DYNAX 7", 0,
1542 			{ 10239,-3104,-1099,-8037,15727,2451,-927,925,6871 }},
1543 		{ "NIKON D100", 0,
1544 			{ 5902,-933,-782,-8983,16719,2354,-1402,1455,6464 }},
1545 		{ "NIKON D1H", 0,
1546 			{ 7577,-2166,-926,-7454,15592,1934,-2377,2808,8606 }},
1547 		{ "NIKON D1X", 0,
1548 			{ 7702,-2245,-975,-9114,17242,1875,-2679,3055,8521 }},
1549 		{ "NIKON D1", 0,	/* multiplied by 2.218750, 1.0, 1.148438 */
1550 			{ 16772,-4726,-2141,-7611,15713,1972,-2846,3494,9521 }},
1551 		{ "NIKON D2H", 0,
1552 			{ 5710,-901,-615,-8594,16617,2024,-2975,4120,6830 }},
1553 		{ "NIKON D2X", 0,
1554 			{ 10231,-2769,-1255,-8301,15900,2552,-797,680,7148 }},
1555 		{ "NIKON D40", 0,
1556 			{ 6992,-1668,-806,-8138,15748,2543,-874,850,7897 }},
1557 		{ "NIKON D50", 0,
1558 			{ 7732,-2422,-789,-8238,15884,2498,-859,783,7330 }},
1559 		{ "NIKON D70", 0,
1560 			{ 7732,-2422,-789,-8238,15884,2498,-859,783,7330 }},
1561 		{ "NIKON D80", 0,
1562 			{ 8629,-2410,-883,-9055,16940,2171,-1490,1363,8520 }},
1563 		{ "NIKON D200", 0,
1564 			{ 8367,-2248,-763,-8758,16447,2422,-1527,1550,8053 }},
1565 		{ "NIKON E950", 0,		/* DJC */
1566 			{ -3746,10611,1665,9621,-1734,2114,-2389,7082,3064,3406,6116,-244 }},
1567 		{ "NIKON E995", 0,	/* copied from E5000 */
1568 			{ -5547,11762,2189,5814,-558,3342,-4924,9840,5949,688,9083,96 }},
1569 		{ "NIKON E2500", 0,
1570 			{ -5547,11762,2189,5814,-558,3342,-4924,9840,5949,688,9083,96 }},
1571 		{ "NIKON E4300", 0, /* copied from Minolta DiMAGE Z2 */
1572 			{ 11280,-3564,-1370,-4655,12374,2282,-1423,2168,5396 }},
1573 		{ "NIKON E4500", 0,
1574 			{ -5547,11762,2189,5814,-558,3342,-4924,9840,5949,688,9083,96 }},
1575 		{ "NIKON E5000", 0,
1576 			{ -5547,11762,2189,5814,-558,3342,-4924,9840,5949,688,9083,96 }},
1577 		{ "NIKON E5400", 0,
1578 			{ 9349,-2987,-1001,-7919,15766,2266,-2098,2680,6839 }},
1579 		{ "NIKON E5700", 0,
1580 			{ -5368,11478,2368,5537,-113,3148,-4969,10021,5782,778,9028,211 }},
1581 		{ "NIKON E8400", 0,
1582 			{ 7842,-2320,-992,-8154,15718,2599,-1098,1342,7560 }},
1583 		{ "NIKON E8700", 0,
1584 			{ 8489,-2583,-1036,-8051,15583,2643,-1307,1407,7354 }},
1585 		{ "NIKON E8800", 0,
1586 			{ 7971,-2314,-913,-8451,15762,2894,-1442,1520,7610 }},
1587 		{ "OLYMPUS C5050", 0,
1588 			{ 10508,-3124,-1273,-6079,14294,1901,-1653,2306,6237 }},
1589 		{ "OLYMPUS C5060", 0,
1590 			{ 10445,-3362,-1307,-7662,15690,2058,-1135,1176,7602 }},
1591 		{ "OLYMPUS C7070", 0,
1592 			{ 10252,-3531,-1095,-7114,14850,2436,-1451,1723,6365 }},
1593 		{ "OLYMPUS C70", 0,
1594 			{ 10793,-3791,-1146,-7498,15177,2488,-1390,1577,7321 }},
1595 		{ "OLYMPUS C80", 0,
1596 			{ 8606,-2509,-1014,-8238,15714,2703,-942,979,7760 }},
1597 		{ "OLYMPUS E-10", 0,
1598 			{ 12745,-4500,-1416,-6062,14542,1580,-1934,2256,6603 }},
1599 		{ "OLYMPUS E-1", 0,
1600 			{ 11846,-4767,-945,-7027,15878,1089,-2699,4122,8311 }},
1601 		{ "OLYMPUS E-20", 0,
1602 			{ 13173,-4732,-1499,-5807,14036,1895,-2045,2452,7142 }},
1603 		{ "OLYMPUS E-300", 0,
1604 			{ 7828,-1761,-348,-5788,14071,1830,-2853,4518,6557 }},
1605 		{ "OLYMPUS E-330", 0,
1606 			{ 8961,-2473,-1084,-7979,15990,2067,-2319,3035,8249 }},
1607 		{ "OLYMPUS E-400", 0,
1608 			{ 6169,-1483,-21,-7107,14761,2536,-2904,3580,8568 }},
1609 		{ "OLYMPUS E-500", 0,
1610 			{ 8136,-1968,-299,-5481,13742,1871,-2556,4205,6630 }},
1611 		{ "OLYMPUS SP350", 0,
1612 			{ 12078,-4836,-1069,-6671,14306,2578,-786,939,7418 }},
1613 		{ "OLYMPUS SP3", 0,
1614 			{ 11766,-4445,-1067,-6901,14421,2707,-1029,1217,7572 }},
1615 		{ "OLYMPUS SP500UZ", 0,
1616 			{ 9493,-3415,-666,-5211,12334,3260,-1548,2262,6482 }},
1617 		{ "OLYMPUS SP510UZ", 0,
1618 			{ 10593,-3607,-1010,-5881,13127,3084,-1200,1805,6721 }},
1619 		{ "PENTAX *ist DL2", 0,
1620 			{ 10504,-2438,-1189,-8603,16207,2531,-1022,863,12242 }},
1621 		{ "PENTAX *ist DL", 0,
1622 			{ 10829,-2838,-1115,-8339,15817,2696,-837,680,11939 }},
1623 		{ "PENTAX *ist DS2", 0,
1624 			{ 10504,-2438,-1189,-8603,16207,2531,-1022,863,12242 }},
1625 		{ "PENTAX *ist DS", 0,
1626 			{ 10371,-2333,-1206,-8688,16231,2602,-1230,1116,11282 }},
1627 		{ "PENTAX *ist D", 0,
1628 			{ 9651,-2059,-1189,-8881,16512,2487,-1460,1345,10687 }},
1629 		{ "PENTAX K10D", 0,
1630 			{ 9566,-2863,-803,-7170,15172,2112,-818,803,9705 }},
1631 		{ "PENTAX K1", 0,
1632 			{ 11095,-3157,-1324,-8377,15834,2720,-1108,947,11688 }},
1633 		{ "Panasonic DMC-FZ30", 0,
1634 			{ 10976,-4029,-1141,-7918,15491,2600,-1670,2071,8246 }},
1635 		{ "Panasonic DMC-FZ50", 0,	/* aka "LEICA V-LUX1" */
1636 			{ 7906,-2709,-594,-6231,13351,3220,-1922,2631,6537 }},
1637 		{ "Panasonic DMC-L1", 0,	/* aka "LEICA DIGILUX 3" */
1638 			{ 8054,-1885,-1025,-8349,16367,2040,-2805,3542,7629 }},
1639 		{ "Panasonic DMC-LC1", 0,	/* aka "LEICA DIGILUX 2" */
1640 			{ 11340,-4069,-1275,-7555,15266,2448,-2960,3426,7685 }},
1641 		{ "Panasonic DMC-LX1", 0,	/* aka "LEICA D-LUX2" */
1642 			{ 10704,-4187,-1230,-8314,15952,2501,-920,945,8927 }},
1643 		{ "Panasonic DMC-LX2", 0,	/* aka "LEICA D-LUX3" */
1644 			{ 8048,-2810,-623,-6450,13519,3272,-1700,2146,7049 }},
1645 		{ "SAMSUNG GX-1", 0,
1646 			{ 10504,-2438,-1189,-8603,16207,2531,-1022,863,12242 }},
1647 		{ "Sinar", 0,		/* DJC */
1648 			{ 16442,-2956,-2422,-2877,12128,750,-1136,6066,4559 }},
1649 		{ "SONY DSC-F828", 491,
1650 			{ 7924,-1910,-777,-8226,15459,2998,-1517,2199,6818,-7242,11401,3481 }},
1651 		{ "SONY DSC-R1", 512,
1652 			{ 8512,-2641,-694,-8042,15670,2526,-1821,2117,7414 }},
1653 		{ "SONY DSC-V3", 0,
1654 			{ 7511,-2571,-692,-7894,15088,3060,-948,1111,8128 }},
1655 		{ "SONY DSLR-A100", 0,
1656 			{ 9437,-2811,-774,-8405,16215,2290,-710,596,7181 }}
1657 	};
1658 	double cameraXYZ[4][3];
1659 
1660 	for (uint32 i = 0; i < sizeof table / sizeof *table; i++) {
1661 		if (!strncasecmp(model, table[i].prefix, strlen(table[i].prefix))) {
1662 			if (table[i].black)
1663 				fMeta.black = table[i].black;
1664 			for (uint32 j = 0; j < 12; j++) {
1665 				cameraXYZ[0][j] = table[i].trans[j] / 10000.0;
1666 			}
1667 			_CameraXYZCoefficients(cameraXYZ);
1668 			break;
1669 		}
1670 	}
1671 }
1672 
1673 
1674 void
1675 DCRaw::_BorderInterpolate(uint32 border)
1676 {
1677 	uint32 row, col, y, x, f, c, sum[8];
1678 
1679 	for (row = 0; row < fInputHeight; row++) {
1680 		for (col = 0; col < fInputWidth; col++) {
1681 			if (col == border && row >= border && row < fInputHeight - border)
1682 				col = fInputWidth - border;
1683 
1684 			memset(sum, 0, sizeof(sum));
1685 
1686 			for (y = row - 1; y != row + 2; y++) {
1687 				for (x = col - 1; x != col + 2; x++) {
1688 					if (y < fInputHeight && x < fInputWidth) {
1689 						f = _FilterCoefficient(x, y);
1690 						sum[f] += fImageData[y * fInputWidth + x][f];
1691 						sum[f + 4]++;
1692 					}
1693 				}
1694 			}
1695 
1696 			f = _FilterCoefficient(col, row);
1697 
1698 			for (c = 0; c < fColors; c++) {
1699 				if (c != f && sum[c + 4]) {
1700 					fImageData[row * fInputWidth + col][c]
1701 						= sum[c] / sum[c + 4];
1702 				}
1703 			}
1704 		}
1705 	}
1706 }
1707 
1708 
1709 /*!	Adaptive Homogeneity-Directed interpolation is based on
1710 	the work of Keigo Hirakawa, Thomas Parks, and Paul Lee.
1711 */
1712 void
1713 DCRaw::_AHDInterpolate()
1714 {
1715 	if (fProgressMonitor != NULL)
1716 		fProgressMonitor("Interpolate", 20, fProgressData);
1717 
1718 #define TS 256		/* Tile Size */
1719 
1720 	int i, j, tr, tc, fc, c, d, val, hm[2];
1721 	uint32 top, left, row, col;
1722 	ushort (*pix)[4], (*rix)[3];
1723 	static const int dir[4] = { -1, 1, -TS, TS };
1724 	unsigned ldiff[2][4], abdiff[2][4], leps, abeps;
1725 	float flab[3];
1726 	ushort (*rgb)[TS][TS][3];
1727 	short (*lab)[TS][TS][3];
1728 	char (*homo)[TS][TS], *buffer;
1729 
1730 	_BorderInterpolate(3);
1731 	buffer = (char *)malloc(26 * TS * TS);		/* 1664 kB */
1732 	if (buffer == NULL)
1733 		throw (status_t)B_NO_MEMORY;
1734 
1735 	rgb = (ushort(*)[TS][TS][3])buffer;
1736 	lab = (short (*)[TS][TS][3])(buffer + 12 * TS * TS);
1737 	homo = (char (*)[TS][TS])(buffer + 24 * TS * TS);
1738 	float percentage = 20;
1739 	float percentageStep = 70.0f / (fInputHeight / (TS - 6));
1740 
1741 	for (top = 0; top < fInputHeight; top += TS - 6) {
1742 		if (fProgressMonitor) {
1743 			fProgressMonitor("Interpolate", percentage, fProgressData);
1744 			percentage += percentageStep;
1745 		}
1746 
1747 		for (left = 0; left < fInputWidth; left += TS - 6) {
1748 			memset(rgb, 0, 12 * TS * TS);
1749 
1750 			/* Interpolate green horizontally and vertically: */
1751 			for (row = top < 2 ? 2 : top; row < top + TS
1752 					&& row < fInputHeight - 2; row++) {
1753 				col = left + (FC(row, left) == 1);
1754 				if (col < 2)
1755 					col += 2;
1756 				for (fc = FC(row, col); col < left + TS
1757 						&& col < fInputWidth - 2; col += 2) {
1758 					pix = fImageData + row * fInputWidth + col;
1759 					val = ((pix[-1][1] + pix[0][fc] + pix[1][1]) * 2
1760 						- pix[-2][fc] - pix[2][fc]) >> 2;
1761 					rgb[0][row - top][col - left][1]
1762 						= ULIM(val, pix[-1][1], pix[1][1]);
1763 					val = ((pix[-fInputWidth][1] + pix[0][fc]
1764 							+ pix[fInputWidth][1]) * 2
1765 						- pix[-2 * fInputWidth][fc] - pix[2 * fInputWidth][fc])
1766 							>> 2;
1767 					rgb[1][row - top][col - left][1] = ULIM(val,
1768 						pix[-fInputWidth][1], pix[fInputWidth][1]);
1769 				}
1770 			}
1771 
1772 			/* Interpolate red and blue, and convert to CIELab: */
1773 			for (d = 0; d < 2; d++) {
1774 				for (row = top + 1; row < top + TS - 1
1775 						&& row < fInputHeight - 1; row++) {
1776 					for (col = left + 1; col < left + TS - 1
1777 							&& col < fInputWidth - 1; col++) {
1778 						pix = fImageData + row * fInputWidth + col;
1779 						rix = &rgb[d][row - top][col - left];
1780 						if ((c = 2 - FC(row, col)) == 1) {
1781 							c = FC(row + 1,col);
1782 							val = pix[0][1] + ((pix[-1][2-c] + pix[1][2 - c]
1783 								- rix[-1][1] - rix[1][1] ) >> 1);
1784 							rix[0][2-c] = CLIP(val);
1785 							val = pix[0][1] + ((pix[-fInputWidth][c]
1786 								+ pix[fInputWidth][c]
1787 								- rix[-TS][1] - rix[TS][1] ) >> 1);
1788 						} else {
1789 							val = rix[0][1] + ((pix[-fInputWidth - 1][c]
1790 								+ pix[-fInputWidth + 1][c]
1791 								+ pix[fInputWidth - 1][c]
1792 								+ pix[fInputWidth + 1][c]
1793 								- rix[-TS - 1][1] - rix[-TS + 1][1]
1794 								- rix[TS - 1][1] - rix[TS + 1][1] + 1) >> 2);
1795 						}
1796 						rix[0][c] = CLIP(val);
1797 						c = FC(row, col);
1798 						rix[0][c] = pix[0][c];
1799 						_CameraToCIELab(rix[0], flab);
1800 						for (c = 0; c < 3; c++) {
1801 							lab[d][row - top][col - left][c]
1802 								= int16(64 * flab[c]);
1803 						}
1804 					}
1805 				}
1806 			}
1807 
1808 			/* Build homogeneity maps from the CIELab images: */
1809 			memset(homo, 0, 2 * TS * TS);
1810 			for (row = top + 2; row < top+TS-2 && row < fInputHeight; row++) {
1811 				tr = row - top;
1812 				for (col = left + 2; col < left + TS - 2
1813 						&& col < fInputWidth; col++) {
1814 					tc = col - left;
1815 					for (d = 0; d < 2; d++) {
1816 						for (i = 0; i < 4; i++) {
1817 							ldiff[d][i] = ABS(lab[d][tr][tc][0]
1818 									- lab[d][tr][tc+dir[i]][0]);
1819 						}
1820 					}
1821 
1822 					leps = MIN(MAX(ldiff[0][0],ldiff[0][1]),
1823 						MAX(ldiff[1][2],ldiff[1][3]));
1824 
1825 					for (d = 0; d < 2; d++) {
1826 						for (i = 0; i < 4; i++) {
1827 							if (i >> 1 == d || ldiff[d][i] <= leps) {
1828 								abdiff[d][i] = square(lab[d][tr][tc][1]
1829 										- lab[d][tr][tc+dir[i]][1])
1830 									+ square(lab[d][tr][tc][2]
1831 										- lab[d][tr][tc+dir[i]][2]);
1832 							}
1833 						}
1834 					}
1835 
1836 					abeps = MIN(MAX(abdiff[0][0],abdiff[0][1]),
1837 						MAX(abdiff[1][2],abdiff[1][3]));
1838 
1839 					for (d=0; d < 2; d++) {
1840 						for (i=0; i < 4; i++) {
1841 							if (ldiff[d][i] <= leps && abdiff[d][i] <= abeps)
1842 								homo[d][tr][tc]++;
1843 						}
1844 					}
1845 				}
1846 			}
1847 
1848 			/* Combine the most homogenous pixels for the final result: */
1849 			for (row = top + 3; row < top + TS - 3 && row < fInputHeight - 3;
1850 					row++) {
1851 				tr = row - top;
1852 				for (col = left + 3; col < left + TS - 3
1853 						&& col < fInputWidth - 3; col++) {
1854 					tc = col - left;
1855 					for (d = 0; d < 2; d++) {
1856 						for (hm[d] = 0, i = tr - 1; i <= tr + 1; i++) {
1857 							for (j = tc - 1; j <= tc + 1; j++) {
1858 								hm[d] += homo[d][i][j];
1859 							}
1860 						}
1861 					}
1862 					if (hm[0] != hm[1]) {
1863 						for (c = 0; c < 3; c++) {
1864 							fImageData[row * fInputWidth + col][c]
1865 								= rgb[hm[1] > hm[0]][tr][tc][c];
1866 						}
1867 					} else {
1868 						for (c = 0; c < 3; c++) {
1869 							fImageData[row * fInputWidth + col][c]
1870 								= (rgb[0][tr][tc][c] + rgb[1][tr][tc][c]) >> 1;
1871 						}
1872 					}
1873 				}
1874 			}
1875 		}
1876 	}
1877 	free(buffer);
1878 #undef TS
1879 }
1880 
1881 
1882 void
1883 DCRaw::_PseudoInverse(double (*in)[3], double (*out)[3], uint32 size)
1884 {
1885 	double work[3][6], num;
1886 	uint32 i, j, k;
1887 
1888 	for (i = 0; i < 3; i++) {
1889 		for (j = 0; j < 6; j++) {
1890 			work[i][j] = j == i + 3;
1891 		}
1892 		for (j = 0; j < 3; j++) {
1893 			for (k = 0; k < size; k++) {
1894 				work[i][j] += in[k][i] * in[k][j];
1895 			}
1896 		}
1897 	}
1898 
1899 	for (i = 0; i < 3; i++) {
1900 		num = work[i][i];
1901 		for (j = 0; j < 6; j++) {
1902 			work[i][j] /= num;
1903 		}
1904 		for (k = 0; k < 3; k++) {
1905 			if (k == i)
1906 				continue;
1907 
1908 			num = work[k][i];
1909 
1910 			for (j = 0; j < 6; j++) {
1911 				work[k][j] -= work[i][j] * num;
1912 			}
1913 		}
1914 	}
1915 
1916 	for (i = 0; i < size; i++) {
1917 		for (j = 0; j < 3; j++) {
1918 			for (out[i][j] = k =0; k < 3; k++) {
1919 				out[i][j] += work[j][k+3] * in[i][k];
1920 			}
1921 		}
1922 	}
1923 }
1924 
1925 
1926 void
1927 DCRaw::_ConvertToRGB()
1928 {
1929 	if (fProgressMonitor != NULL)
1930 		fProgressMonitor("Convert to RGB", 90, fProgressData);
1931 
1932 	uint32 row, col, c, i, j, k;
1933 	float out[3], out_cam[3][4];
1934 	double num, inverse[3][3];
1935 	static const double xyzd50_srgb[3][3] = {
1936 		{ 0.436083, 0.385083, 0.143055 },
1937 		{ 0.222507, 0.716888, 0.060608 },
1938 		{ 0.013930, 0.097097, 0.714022 }};
1939 	static const double rgb_rgb[3][3] = {
1940 		{ 1,0,0 }, { 0,1,0 }, { 0,0,1 }};
1941 	static const double adobe_rgb[3][3] = {
1942 		{ 0.715146, 0.284856, 0.000000 },
1943 		{ 0.000000, 1.000000, 0.000000 },
1944 		{ 0.000000, 0.041166, 0.958839 }};
1945 	static const double wide_rgb[3][3] = {
1946 		{ 0.593087, 0.404710, 0.002206 },
1947 		{ 0.095413, 0.843149, 0.061439 },
1948 		{ 0.011621, 0.069091, 0.919288 }};
1949 	static const double prophoto_rgb[3][3] = {
1950 		{ 0.529317, 0.330092, 0.140588 },
1951 		{ 0.098368, 0.873465, 0.028169 },
1952 		{ 0.016879, 0.117663, 0.865457 }};
1953 	static const double (*out_rgb[])[3]
1954 		= { rgb_rgb, adobe_rgb, wide_rgb, prophoto_rgb, xyz_rgb };
1955 	static const char *name[] = { "sRGB", "Adobe RGB (1998)", "WideGamut D65",
1956 		"ProPhoto D65", "XYZ" };
1957 	static const unsigned phead[] = { 1024, 0, 0x2100000, 0x6d6e7472,
1958 		0x52474220, 0x58595a20, 0, 0, 0, 0x61637370, 0, 0, 0x6e6f6e65,
1959 		0, 0, 0, 0, 0xf6d6, 0x10000, 0xd32d };
1960 	unsigned pbody[] = { 10,
1961 		0x63707274, 0, 36,	/* cprt */
1962 		0x64657363, 0, 40,	/* desc */
1963 		0x77747074, 0, 20,	/* wtpt */
1964 		0x626b7074, 0, 20,	/* bkpt */
1965 		0x72545243, 0, 14,	/* rTRC */
1966 		0x67545243, 0, 14,	/* gTRC */
1967 		0x62545243, 0, 14,	/* bTRC */
1968 		0x7258595a, 0, 20,	/* rXYZ */
1969 		0x6758595a, 0, 20,	/* gXYZ */
1970 		0x6258595a, 0, 20 };	/* bXYZ */
1971 	static const unsigned pwhite[] = { 0xf351, 0x10000, 0x116cc };
1972 	unsigned pcurve[] = { 0x63757276, 0, 1, 0x1000000 };
1973 
1974 	memcpy(out_cam, fMeta.rgb_camera, sizeof(out_cam));
1975 	fRawColor |= fColors == 1 || fDocumentMode
1976 		|| fOutputColor < 1 || fOutputColor > 5;
1977 	if (!fRawColor) {
1978 		fOutputProfile = (uint32 *)calloc(phead[0], 1);
1979 		if (fOutputProfile == NULL)
1980 			throw (status_t)B_NO_MEMORY;
1981 
1982 		memcpy(fOutputProfile, phead, sizeof(phead));
1983 		if (fOutputColor == 5)
1984 			fOutputProfile[4] = fOutputProfile[5];
1985 
1986 		fOutputProfile[0] = 132 + 12 * pbody[0];
1987 		for (i = 0; i < pbody[0]; i++) {
1988 			fOutputProfile[fOutputProfile[0] / 4]
1989 				= i ? (i > 1 ? 0x58595a20 : 0x64657363) : 0x74657874;
1990 			pbody[i*3+2] = fOutputProfile[0];
1991 			fOutputProfile[0] += (pbody[i*3+3] + 3) & -4;
1992 		}
1993 
1994 		memcpy(fOutputProfile + 32, pbody, sizeof(pbody));
1995 		fOutputProfile[pbody[5] / 4 + 2] = strlen(name[fOutputColor - 1]) + 1;
1996 		memcpy((char *)fOutputProfile + pbody[8] + 8, pwhite, sizeof(pwhite));
1997 		if (fOutputBitsPerSample == 8) {
1998 #ifdef SRGB_GAMMA
1999 			pcurve[3] = 0x2330000;
2000 #else
2001 			pcurve[3] = 0x1f00000;
2002 #endif
2003 		}
2004 
2005 		for (i = 4; i < 7; i++) {
2006 			memcpy((char *)fOutputProfile + pbody[i * 3 + 2], pcurve,
2007 				sizeof(pcurve));
2008 		}
2009 
2010 		_PseudoInverse((double (*)[3])out_rgb[fOutputColor - 1], inverse, 3);
2011 
2012 		for (i = 0; i < 3; i++) {
2013 			for (j = 0; j < 3; j++) {
2014 				for (num = k=0; k < 3; k++) {
2015 					num += xyzd50_srgb[i][k] * inverse[j][k];
2016 				}
2017 				fOutputProfile[pbody[j * 3 + 23] / 4 + i + 2]
2018 					= uint32(num * 0x10000 + 0.5);
2019 			}
2020 		}
2021 		for (i = 0; i < phead[0]/4; i++) {
2022 			fOutputProfile[i] = htonl(fOutputProfile[i]);
2023 		}
2024 		strcpy((char *)fOutputProfile + pbody[2] + 8,
2025 			"auto-generated by dcraw");
2026 		strcpy((char *)fOutputProfile + pbody[5] + 12, name[fOutputColor - 1]);
2027 
2028 		for (i = 0; i < 3; i++) {
2029 			for (j = 0; j < fColors; j++) {
2030 				for (out_cam[i][j] = k = 0; k < 3; k++) {
2031 					out_cam[i][j] += out_rgb[fOutputColor-1][i][k]
2032 						* fMeta.rgb_camera[k][j];
2033 				}
2034 			}
2035 		}
2036 	}
2037 
2038 	if (1/*verbose*/) {
2039 		fprintf(stderr, fRawColor ? "Building histograms...\n"
2040 			: "Converting to %s colorspace...\n", name[fOutputColor - 1]);
2041 	}
2042 
2043 	ushort* img = fImageData[0];
2044 	memset(fHistogram, 0, sizeof(int32) * 0x2000 * 4);
2045 
2046 	for (row = 0; row < fInputHeight; row++) {
2047 		for (col = 0; col < fInputWidth; col++, img += 4) {
2048 			if (!fRawColor) {
2049 				out[0] = out[1] = out[2] = 0;
2050 				for (c = 0; c < fColors; c++) {
2051 					out[0] += out_cam[0][c] * img[c];
2052 					out[1] += out_cam[1][c] * img[c];
2053 					out[2] += out_cam[2][c] * img[c];
2054 				}
2055 				for (c = 0; c < 3; c++) {
2056 					img[c] = CLIP((int)out[c]);
2057 				}
2058 			} else if (fDocumentMode)
2059 				img[0] = img[FC(row, col)];
2060 
2061 			for (c = 0; c < fColors; c++) {
2062 				fHistogram[img[c] >> 3][c]++;
2063 			}
2064 		}
2065 	}
2066 
2067 	if (fColors == 4 && fOutputColor)
2068 		fColors = 3;
2069 	if (fDocumentMode && fFilters)
2070 		fColors = 1;
2071 }
2072 
2073 
2074 void
2075 DCRaw::_GammaLookUpTable(uchar* lut)
2076 {
2077 	int32 percent, val, total, i;
2078 	float white = 0, r;
2079 
2080 	percent = int32(fInputWidth * fInputHeight * 0.01);
2081 		// 99th percentile white point
2082 
2083 	//  if (fuji_width) perc /= 2;
2084 	if (fHighlight)
2085 		percent = 0;
2086 
2087 	for (uint32 c = 0; c < fColors; c++) {
2088 		for (val = 0x2000, total = 0; --val > 32;) {
2089 			if ((total += fHistogram[val][c]) > percent)
2090 				break;
2091 		}
2092 		if (white < val)
2093 			white = val;
2094 	}
2095 
2096 	white *= 8 / fBrightness;
2097 
2098 	for (i = 0; i < 0x10000; i++) {
2099 		r = i / white;
2100 		val = int32(256 * (!fUseGamma ? r :
2101 #ifdef SRGB_GAMMA
2102 			r <= 0.00304 ? r*12.92 : pow(r,2.5/6)*1.055-0.055));
2103 #else
2104 			r <= 0.018 ? r*4.5 : pow(r,0.45)*1.099-0.099));
2105 #endif
2106 		if (val > 255)
2107 			val = 255;
2108 		lut[i] = val;
2109 	}
2110 }
2111 
2112 
2113 //	#pragma mark - Lossless JPEG
2114 
2115 
2116 void
2117 DCRaw::_InitDecoder()
2118 {
2119 	memset(fDecodeBuffer, 0, sizeof(decode) * kDecodeBufferCount);
2120 	fFreeDecode = fDecodeBuffer;
2121 }
2122 
2123 
2124 /*!	Construct a decode tree according the specification in *source.
2125 	The first 16 bytes specify how many codes should be 1-bit, 2-bit
2126 	3-bit, etc.  Bytes after that are the leaf values.
2127 
2128 	For example, if the source is
2129 
2130 	{ 0,1,4,2,3,1,2,0,0,0,0,0,0,0,0,0,
2131 	  0x04,0x03,0x05,0x06,0x02,0x07,0x01,0x08,0x09,0x00,0x0a,0x0b,0xff  },
2132 
2133 	then the code is
2134 
2135 	00		0x04
2136 	010		0x03
2137 	011		0x05
2138 	100		0x06
2139 	101		0x02
2140 	1100		0x07
2141 	1101		0x01
2142 	11100		0x08
2143 	11101		0x09
2144 	11110		0x00
2145 	111110		0x0a
2146 	1111110		0x0b
2147 	1111111		0xff
2148 */
2149 uchar *
2150 DCRaw::_MakeDecoder(const uchar* source, int level)
2151 {
2152 	if (level == 0)
2153 		fDecodeLeaf = 0;
2154 
2155 	if ((uint8*)fFreeDecode > (uint8*)fDecodeBuffer
2156 			+ sizeof(decode) * kDecodeBufferCount) {
2157 		fprintf(stderr, "decoder table overflow\n");
2158 		throw (status_t)B_ERROR;
2159 	}
2160 
2161 	struct decode* current = fFreeDecode++;
2162 
2163 	int i, next;
2164 	for (i = next = 0; i <= fDecodeLeaf && next < 16; ) {
2165 		i += source[next++];
2166 	}
2167 
2168 	if (i > fDecodeLeaf) {
2169 		if (level < next) {
2170 			current->branch[0] = fFreeDecode;
2171 			_MakeDecoder(source, level + 1);
2172 			current->branch[1] = fFreeDecode;
2173 			_MakeDecoder(source, level + 1);
2174 		} else
2175 			current->leaf = source[16 + fDecodeLeaf++];
2176 	}
2177 
2178 	return (uchar*)source + 16 + fDecodeLeaf;
2179 }
2180 
2181 
2182 /*!	Not a full implementation of Lossless JPEG, just
2183 	enough to decode Canon, Kodak and Adobe DNG images.
2184 */
2185 void
2186 DCRaw::_InitDecodeBits()
2187 {
2188 	fDecodeBits = fDecodeBitsRead = 0;
2189 	fDecodeBitsReset = false;
2190 }
2191 
2192 
2193 /*!	_GetDecodeBits(n) where 0 <= n <= 25 returns an n-bit integer
2194 */
2195 uint32
2196 DCRaw::_GetDecodeBits(uint32 numBits)
2197 {
2198 	if (numBits == 0 || fDecodeBitsReset)
2199 		return 0;
2200 
2201 	while (fDecodeBitsRead < numBits) {
2202 		uint8 c = fRead.Next<uint8>();
2203 		if ((fDecodeBitsReset = fDecodeBitsZeroAfterMax
2204 				&& c == 0xff && fRead.Next<uint8>()))
2205 			return 0;
2206 		fDecodeBits = (fDecodeBits << 8) + c;
2207 		fDecodeBitsRead += 8;
2208 	}
2209 
2210 	fDecodeBitsRead -= numBits;
2211 
2212 	return fDecodeBits << (32 - numBits - fDecodeBitsRead) >> (32 - numBits);
2213 }
2214 
2215 
2216 status_t
2217 DCRaw::_LosslessJPEGInit(struct jhead* jh, bool infoOnly)
2218 {
2219 	int i, tag, len;
2220 
2221 	_InitDecoder();
2222 
2223 	for (i = 0; i < 4; i++) {
2224 		jh->huff[i] = fFreeDecode;
2225 	}
2226 
2227 	jh->restart = INT_MAX;
2228 
2229 	uchar data[0x10000], *dp;
2230 	fRead(data, 2);
2231 	if (data[1] != 0xd8)
2232 		return B_ERROR;
2233 
2234 	do {
2235 		fRead(data, 4);
2236 		tag = data[0] << 8 | data[1];
2237 		len = (data[2] << 8 | data[3]) - 2;
2238 		if (tag <= 0xff00)
2239 			return B_ERROR;
2240 
2241 		fRead(data, len);
2242 		switch (tag) {
2243 			case 0xffc0:
2244 			case 0xffc3:
2245 				jh->bits = data[0];
2246 				jh->high = data[1] << 8 | data[2];
2247 				jh->wide = data[3] << 8 | data[4];
2248 				jh->clrs = data[5];
2249 				break;
2250 			case 0xffc4:
2251 				if (infoOnly)
2252 					break;
2253 
2254 				for (dp = data; dp < data+len && *dp < 4; ) {
2255 					jh->huff[*dp] = fFreeDecode;
2256 					dp = _MakeDecoder(++dp, 0);
2257 				}
2258 				break;
2259 			case 0xffdd:
2260 				jh->restart = data[0] << 8 | data[1];
2261 				break;
2262 		}
2263 	} while (tag != 0xffda);
2264 
2265 	if (infoOnly)
2266 		return B_OK;
2267 
2268 	jh->row = (ushort *)calloc(jh->wide*jh->clrs, 2);
2269 	if (jh->row == NULL)
2270 		throw (status_t)B_NO_MEMORY;
2271 
2272 	fDecodeBitsZeroAfterMax = true;
2273 	return B_OK;
2274 }
2275 
2276 
2277 int
2278 DCRaw::_LosslessJPEGDiff(struct decode *dindex)
2279 {
2280 	while (dindex->branch[0]) {
2281 		dindex = dindex->branch[_GetDecodeBits(1)];
2282 	}
2283 
2284 	int length = dindex->leaf;
2285 	if (length == 16 && (!fDNGVersion || fDNGVersion >= 0x1010000))
2286 		return -32768;
2287 
2288 	int diff = _GetDecodeBits(length);
2289 	if ((diff & (1 << (length - 1))) == 0)
2290 		diff -= (1 << length) - 1;
2291 
2292 	return diff;
2293 }
2294 
2295 
2296 void
2297 DCRaw::_LosslessJPEGRow(struct jhead *jh, int jrow)
2298 {
2299 	if (jrow * jh->wide % jh->restart == 0) {
2300 		for (uint32 i = 0; i < 4; i++) {
2301 			jh->vpred[i] = 1 << (jh->bits - 1);
2302 		}
2303 		if (jrow) {
2304 			uint16 mark = 0;
2305 			int c;
2306 			do {
2307 				mark = (mark << 8) + (c = fRead.Next<uint8>());
2308 			} while (c != EOF && mark >> 4 != 0xffd);
2309 		}
2310 		_InitDecodeBits();
2311 	}
2312 
2313 	uint16* outp = jh->row;
2314 
2315 	for (int32 col = 0; col < jh->wide; col++) {
2316 		for (int32 c = 0; c < jh->clrs; c++) {
2317 			int32 diff = _LosslessJPEGDiff(jh->huff[c]);
2318 			*outp = col ? outp[-jh->clrs]+diff : (jh->vpred[c] += diff);
2319 			outp++;
2320 		}
2321 	}
2322 }
2323 
2324 
2325 //	#pragma mark - RAW loaders
2326 
2327 
2328 void
2329 DCRaw::_LoadRAWUnpacked(const image_data_info& image)
2330 {
2331 	uint32 rawWidth = _Raw().width;
2332 
2333 	uint16* pixel = (uint16*)calloc(rawWidth, sizeof(uint16));
2334 	if (pixel == NULL)
2335 		return;
2336 
2337 	fRead.Seek((fTopMargin * rawWidth + fLeftMargin) * sizeof(uint16),
2338 		SEEK_CUR);
2339 
2340 	for (uint32 row = 0; row < fInputHeight; row++) {
2341 		fRead.NextShorts(pixel, rawWidth);
2342 		for (uint32 column = 0; column < fInputWidth; column++) {
2343 			_Bayer(column, row) = pixel[column];
2344 		}
2345 	}
2346 
2347 	free(pixel);
2348 }
2349 
2350 
2351 /*!	This is, for example, used in PENTAX RAW images
2352 */
2353 void
2354 DCRaw::_LoadRAWPacked12(const image_data_info& image)
2355 {
2356 	uint32 rawWidth = _Raw().width;
2357 
2358 	_InitDecodeBits();
2359 
2360 	for (uint32 row = 0; row < fInputHeight; row++) {
2361 		for (uint32 column = 0; column < fInputWidth; column++) {
2362 			//uint16 bits = _GetDecodeBits(12);
2363 			_Bayer(column, row) = _GetDecodeBits(12);
2364 			//fImageData[((row) >> fShrink)*fOutputWidth + ((column) >> fShrink)][FC(row,column)] = bits;
2365 		}
2366 		for (uint32 column = fInputWidth * 3 / 2; column < rawWidth; column++) {
2367 			_GetDecodeBits(8);
2368 		}
2369 	}
2370 }
2371 
2372 
2373 void
2374 DCRaw::_MakeCanonDecoder(uint32 table)
2375 {
2376 	static const uchar kFirstTree[3][29] = {
2377 		{ 0,1,4,2,3,1,2,0,0,0,0,0,0,0,0,0,
2378 			0x04,0x03,0x05,0x06,0x02,0x07,0x01,0x08,0x09,0x00,0x0a,0x0b,0xff },
2379 		{ 0,2,2,3,1,1,1,1,2,0,0,0,0,0,0,0,
2380 			0x03,0x02,0x04,0x01,0x05,0x00,0x06,0x07,0x09,0x08,0x0a,0x0b,0xff },
2381 		{ 0,0,6,3,1,1,2,0,0,0,0,0,0,0,0,0,
2382 			0x06,0x05,0x07,0x04,0x08,0x03,0x09,0x02,0x00,0x0a,0x01,0x0b,0xff },
2383 	};
2384 	static const uchar kSecondTree[3][180] = {
2385 		{ 0,2,2,2,1,4,2,1,2,5,1,1,0,0,0,139,
2386 			0x03,0x04,0x02,0x05,0x01,0x06,0x07,0x08,
2387 			0x12,0x13,0x11,0x14,0x09,0x15,0x22,0x00,0x21,0x16,0x0a,0xf0,
2388 			0x23,0x17,0x24,0x31,0x32,0x18,0x19,0x33,0x25,0x41,0x34,0x42,
2389 			0x35,0x51,0x36,0x37,0x38,0x29,0x79,0x26,0x1a,0x39,0x56,0x57,
2390 			0x28,0x27,0x52,0x55,0x58,0x43,0x76,0x59,0x77,0x54,0x61,0xf9,
2391 			0x71,0x78,0x75,0x96,0x97,0x49,0xb7,0x53,0xd7,0x74,0xb6,0x98,
2392 			0x47,0x48,0x95,0x69,0x99,0x91,0xfa,0xb8,0x68,0xb5,0xb9,0xd6,
2393 			0xf7,0xd8,0x67,0x46,0x45,0x94,0x89,0xf8,0x81,0xd5,0xf6,0xb4,
2394 			0x88,0xb1,0x2a,0x44,0x72,0xd9,0x87,0x66,0xd4,0xf5,0x3a,0xa7,
2395 			0x73,0xa9,0xa8,0x86,0x62,0xc7,0x65,0xc8,0xc9,0xa1,0xf4,0xd1,
2396 			0xe9,0x5a,0x92,0x85,0xa6,0xe7,0x93,0xe8,0xc1,0xc6,0x7a,0x64,
2397 			0xe1,0x4a,0x6a,0xe6,0xb3,0xf1,0xd3,0xa5,0x8a,0xb2,0x9a,0xba,
2398 			0x84,0xa4,0x63,0xe5,0xc5,0xf3,0xd2,0xc4,0x82,0xaa,0xda,0xe4,
2399 			0xf2,0xca,0x83,0xa3,0xa2,0xc3,0xea,0xc2,0xe2,0xe3,0xff,0xff },
2400 		{ 0,2,2,1,4,1,4,1,3,3,1,0,0,0,0,140,
2401 			0x02,0x03,0x01,0x04,0x05,0x12,0x11,0x06,
2402 			0x13,0x07,0x08,0x14,0x22,0x09,0x21,0x00,0x23,0x15,0x31,0x32,
2403 			0x0a,0x16,0xf0,0x24,0x33,0x41,0x42,0x19,0x17,0x25,0x18,0x51,
2404 			0x34,0x43,0x52,0x29,0x35,0x61,0x39,0x71,0x62,0x36,0x53,0x26,
2405 			0x38,0x1a,0x37,0x81,0x27,0x91,0x79,0x55,0x45,0x28,0x72,0x59,
2406 			0xa1,0xb1,0x44,0x69,0x54,0x58,0xd1,0xfa,0x57,0xe1,0xf1,0xb9,
2407 			0x49,0x47,0x63,0x6a,0xf9,0x56,0x46,0xa8,0x2a,0x4a,0x78,0x99,
2408 			0x3a,0x75,0x74,0x86,0x65,0xc1,0x76,0xb6,0x96,0xd6,0x89,0x85,
2409 			0xc9,0xf5,0x95,0xb4,0xc7,0xf7,0x8a,0x97,0xb8,0x73,0xb7,0xd8,
2410 			0xd9,0x87,0xa7,0x7a,0x48,0x82,0x84,0xea,0xf4,0xa6,0xc5,0x5a,
2411 			0x94,0xa4,0xc6,0x92,0xc3,0x68,0xb5,0xc8,0xe4,0xe5,0xe6,0xe9,
2412 			0xa2,0xa3,0xe3,0xc2,0x66,0x67,0x93,0xaa,0xd4,0xd5,0xe7,0xf8,
2413 			0x88,0x9a,0xd7,0x77,0xc4,0x64,0xe2,0x98,0xa5,0xca,0xda,0xe8,
2414 			0xf3,0xf6,0xa9,0xb2,0xb3,0xf2,0xd2,0x83,0xba,0xd3,0xff,0xff },
2415 		{ 0,0,6,2,1,3,3,2,5,1,2,2,8,10,0,117,
2416 			0x04,0x05,0x03,0x06,0x02,0x07,0x01,0x08,
2417 			0x09,0x12,0x13,0x14,0x11,0x15,0x0a,0x16,0x17,0xf0,0x00,0x22,
2418 			0x21,0x18,0x23,0x19,0x24,0x32,0x31,0x25,0x33,0x38,0x37,0x34,
2419 			0x35,0x36,0x39,0x79,0x57,0x58,0x59,0x28,0x56,0x78,0x27,0x41,
2420 			0x29,0x77,0x26,0x42,0x76,0x99,0x1a,0x55,0x98,0x97,0xf9,0x48,
2421 			0x54,0x96,0x89,0x47,0xb7,0x49,0xfa,0x75,0x68,0xb6,0x67,0x69,
2422 			0xb9,0xb8,0xd8,0x52,0xd7,0x88,0xb5,0x74,0x51,0x46,0xd9,0xf8,
2423 			0x3a,0xd6,0x87,0x45,0x7a,0x95,0xd5,0xf6,0x86,0xb4,0xa9,0x94,
2424 			0x53,0x2a,0xa8,0x43,0xf5,0xf7,0xd4,0x66,0xa7,0x5a,0x44,0x8a,
2425 			0xc9,0xe8,0xc8,0xe7,0x9a,0x6a,0x73,0x4a,0x61,0xc7,0xf4,0xc6,
2426 			0x65,0xe9,0x72,0xe6,0x71,0x91,0x93,0xa6,0xda,0x92,0x85,0x62,
2427 			0xf3,0xc5,0xb2,0xa4,0x84,0xba,0x64,0xa5,0xb3,0xd2,0x81,0xe5,
2428 			0xd3,0xaa,0xc4,0xca,0xf2,0xb1,0xe4,0xd1,0x83,0x63,0xea,0xc3,
2429 			0xe2,0x82,0xf1,0xa3,0xc2,0xa1,0xc1,0xe3,0xa2,0xe1,0xff,0xff }
2430 	};
2431 
2432 	if (table > 2)
2433 		table = 2;
2434 
2435 	_InitDecoder();
2436 
2437 	_MakeDecoder(kFirstTree[table], 0);
2438 	fSecondDecode = fFreeDecode;
2439 	_MakeDecoder(kSecondTree[table], 0);
2440 }
2441 
2442 
2443 /*!	Return 0 if the image starts with compressed data,
2444 	1 if it starts with uncompressed low-order bits.
2445 
2446 	In Canon compressed data, 0xff is always followed by 0x00.
2447 */
2448 bool
2449 DCRaw::_CanonHasLowBits()
2450 {
2451 	bool hasLowBits = true;
2452 	uchar test[0x4000 - 540];
2453 
2454 	fRead.Seek(540, SEEK_SET);
2455 	fRead(test, sizeof(test));
2456 
2457 	for (uint32 i = 0; i < sizeof(test) - 1; i++)
2458 		if (test[i] == 0xff) {
2459 			if (test[i + 1])
2460 				return 1;
2461 			hasLowBits = 0;
2462     }
2463 
2464 	return hasLowBits;
2465 }
2466 
2467 
2468 void
2469 DCRaw::_LoadRAWCanonCompressed(const image_data_info& image)
2470 {
2471 	uint32 rawWidth = _Raw().width;
2472 	int carry = 0, pnum = 0, base[2];
2473 
2474 	_MakeCanonDecoder(image.compression);
2475 
2476 	uint16* pixel = (uint16 *)calloc(rawWidth * 8, sizeof(*pixel));
2477 	if (pixel == NULL)
2478 		throw (status_t)B_NO_MEMORY;
2479 
2480 	bool hasLowBits = _CanonHasLowBits();
2481 	if (!hasLowBits)
2482 		fMeta.maximum = 0x3ff;
2483 
2484 	fRead.Seek(540 + (hasLowBits ? _Raw().height * rawWidth / 4 : 0),
2485 		SEEK_SET);
2486 
2487 	fDecodeBitsZeroAfterMax = true;
2488 	_InitDecodeBits();
2489 
2490 	for (uint32 row = 0; row < _Raw().height; row += 8) {
2491 		for (uint32 block = 0; block < rawWidth >> 3; block++) {
2492 			int diffbuf[64];
2493 			memset(diffbuf, 0, sizeof diffbuf);
2494 			struct decode* decode = fDecodeBuffer;
2495 
2496 			for (uint32 i = 0; i < 64; i++) {
2497 				struct decode* dindex = decode;
2498 				while (dindex->branch[0]) {
2499 					dindex = dindex->branch[_GetDecodeBits(1)];
2500 				}
2501 				int leaf = dindex->leaf;
2502 				decode = fSecondDecode;
2503 				if (leaf == 0 && i)
2504 					break;
2505 				if (leaf == 0xff)
2506 					continue;
2507 				i += leaf >> 4;
2508 
2509 				int len = leaf & 15;
2510 				if (len == 0)
2511 					continue;
2512 				int diff = _GetDecodeBits(len);
2513 				if ((diff & (1 << (len-1))) == 0)
2514 					diff -= (1 << len) - 1;
2515 				if (i < 64)
2516 					diffbuf[i] = diff;
2517 			}
2518 
2519 			diffbuf[0] += carry;
2520 			carry = diffbuf[0];
2521 
2522 			for (uint32 i = 0; i < 64; i++) {
2523 				if (pnum++ % _Raw().width == 0)
2524 					base[0] = base[1] = 512;
2525 				pixel[(block << 6) + i] = (base[i & 1] += diffbuf[i]);
2526 			}
2527 		}
2528 
2529 		if (hasLowBits) {
2530 			off_t savedOffset = fRead.Position();
2531 			fRead.Seek(26 + row * _Raw().width / 4, SEEK_SET);
2532 
2533 			uint16* pixelRow = pixel;
2534 			for (uint32 i = 0; i < rawWidth * 2; i++) {
2535 				uint8 c = fRead.Next<uint8>();
2536 
2537 				for (uint32 r = 0; r < 8; r += 2, pixelRow++) {
2538 					uint32 val = (*pixelRow << 2) + ((c >> r) & 3);
2539 					if (rawWidth == 2672 && val < 512)
2540 						val += 2;
2541 					*pixelRow = val;
2542 				}
2543 			}
2544 
2545 			fRead.Seek(savedOffset, SEEK_SET);
2546 		}
2547 
2548 		for (uint32 r = 0; r < 8; r++) {
2549 			uint32 irow = row - fTopMargin + r;
2550 			if (irow >= fInputHeight)
2551 				continue;
2552 
2553 			for (uint32 col = 0; col < rawWidth; col++) {
2554 				uint32 icol = col - fLeftMargin;
2555 				if (icol < fInputWidth)
2556 					_Bayer(icol, irow) = pixel[r * rawWidth + col];
2557 				else
2558 					fMeta.black += pixel[r * rawWidth + col];
2559 			}
2560 		}
2561 	}
2562 
2563 	free(pixel);
2564 
2565 	if (rawWidth > fInputWidth)
2566 		fMeta.black /= (rawWidth - fInputWidth) * fInputHeight;
2567 }
2568 
2569 
2570 void
2571 DCRaw::_LoadRAWLosslessJPEG(const image_data_info& image)
2572 {
2573 	int jwide, jrow, jcol, val, jidx, i, j, row = 0, col = 0;
2574 	uint32 rawWidth = _Raw().width;
2575 	int min = INT_MAX;
2576 
2577 	struct jhead jh;
2578 	if (_LosslessJPEGInit(&jh, false) != B_OK)
2579 		throw (status_t)B_NO_TRANSLATOR;
2580 
2581 	jwide = jh.wide * jh.clrs;
2582 
2583 	for (jrow = 0; jrow < jh.high; jrow++) {
2584 		_LosslessJPEGRow(&jh, jrow);
2585 
2586 		for (jcol = 0; jcol < jwide; jcol++) {
2587 			val = jh.row[jcol];
2588 			if (jh.bits <= 12)
2589 				val = fCurve[val];
2590 
2591 			if (fCR2Slice[0]) {
2592 				jidx = jrow * jwide + jcol;
2593 				i = jidx / (fCR2Slice[1] * jh.high);
2594 				if ((j = i >= fCR2Slice[0]))
2595 					i  = fCR2Slice[0];
2596 				jidx -= i * (fCR2Slice[1] * jh.high);
2597 				row = jidx / fCR2Slice[1 + j];
2598 				col = jidx % fCR2Slice[1 + j] + i * fCR2Slice[1];
2599 			}
2600 
2601 			if (_Raw().width == 3984 && (col -= 2) < 0) {
2602 				col += rawWidth;
2603 				row--;
2604 			}
2605 
2606 			if (uint32(row - fTopMargin) < fInputHeight) {
2607 				if (uint32(col - fLeftMargin) < fInputWidth) {
2608 					_Bayer(col - fLeftMargin, row - fTopMargin) = val;
2609 					if (min > val)
2610 						min = val;
2611 				} else
2612 					fMeta.black += val;
2613 			}
2614 			if (++col >= (int32)rawWidth) {
2615 				col = 0;
2616 				row++;
2617 			}
2618 		}
2619 	}
2620 
2621 	//dump_to_disk(fImageData, fInputWidth * fColors * 100);
2622 	free(jh.row);
2623 
2624 	if (rawWidth > fInputWidth)
2625 		fMeta.black /= (rawWidth - fInputWidth) * fInputHeight;
2626 	if (_IsKodak())
2627 		fMeta.black = min;
2628 }
2629 
2630 
2631 void
2632 DCRaw::_LoadRAW(const image_data_info& image)
2633 {
2634 #if 0
2635 	if (_IsCanon()) {
2636 		if (fIsTIFF)
2637 		else
2638 			_LoadRAWCanonCompressed(image);
2639 	} else
2640 #endif
2641 	{
2642 		switch (image.compression) {
2643 			case COMPRESSION_NONE:
2644 				_LoadRAWUnpacked(image);
2645 				break;
2646 			case COMPRESSION_OLD_JPEG:
2647 				_LoadRAWLosslessJPEG(image);
2648 				//_LoadRAWCanonCompressed(image);
2649 				break;
2650 			case COMPRESSION_PACKBITS:
2651 				_LoadRAWPacked12(image);
2652 				break;
2653 
2654 			default:
2655 				fprintf(stderr, "DCRaw: unknown compression: %ld\n",
2656 					image.compression);
2657 				throw (status_t)B_NO_TRANSLATOR;
2658 				break;
2659 		}
2660 	}
2661 }
2662 
2663 
2664 //	#pragma mark - Image writers
2665 
2666 
2667 void
2668 DCRaw::_WriteRGB32(image_data_info& image, uint8* outputBuffer)
2669 {
2670 	if (fProgressMonitor != NULL)
2671 		fProgressMonitor("Write RGB", 95, fProgressData);
2672 
2673 	uint8* line, lookUpTable[0x10000];
2674 
2675 	uint32 width = image.flip > 4 ? fOutputHeight : fOutputWidth;
2676 	uint32 height = image.flip > 4 ? fOutputWidth : fOutputHeight;
2677 	uint32 outputRow = (4 * fOutputBitsPerSample / 8) * width;
2678 	uint32 outputOffset = 0;
2679 
2680 	line = (uint8 *)malloc(outputRow);
2681 	if (line == NULL)
2682 		throw (status_t)B_NO_MEMORY;
2683 
2684 	memset(line, 0, outputRow);
2685 
2686 	if (fOutputBitsPerSample == 8)
2687 		_GammaLookUpTable(lookUpTable);
2688 
2689 	int32 sourceOffset = _FlipIndex(0, 0, image.flip);
2690 	int32 colStep = _FlipIndex(0, 1, image.flip) - sourceOffset;
2691 	int32 rowStep = _FlipIndex(1, 0, image.flip)
2692 		- _FlipIndex(0, width, image.flip);
2693 
2694 	TRACE(("flip = %ld, sourceOffset = %ld, colStep = %ld, rowStep = %ld, "
2695 		"input: %lu x %lu, output: %lu x %lu\n", image.flip, sourceOffset,
2696 		colStep, rowStep, fInputWidth, fInputHeight, width,
2697 		height));
2698 
2699 	if (fOutputBitsPerSample == 8) {
2700 		for (uint32 row = 0; row < height; row++, sourceOffset += rowStep) {
2701 			for (uint32 col = 0; col < width; col++, sourceOffset += colStep) {
2702 				line[col * 4 + 2] = lookUpTable[fImageData[sourceOffset][0]];
2703 				line[col * 4 + 1] = lookUpTable[fImageData[sourceOffset][1]];
2704 				line[col * 4 + 0] = lookUpTable[fImageData[sourceOffset][2]];
2705 			}
2706 
2707 			memcpy(&outputBuffer[outputOffset], line, outputRow);
2708 			outputOffset += outputRow;
2709 		}
2710 	} else {
2711 #if 0
2712 		uint16* ppm2 = (uint16*)line;
2713 		for (row = 0; row < fOutputHeight; row++, soff += rstep) {
2714 			for (col = 0; col < fOutputWidth; col++, soff += cstep) {
2715 				FORCC ppm2[col*colors+c] =     image[soff][c];
2716 			}
2717 			if (!output_tiff && htons(0x55aa) != 0x55aa)
2718 				swab (ppm2, ppm2, width*colors*2);
2719 			fwrite (ppm, colors*output_bps/8, width, ofp);
2720 		}
2721 #endif
2722 	}
2723 
2724 	free(line);
2725 }
2726 
2727 
2728 void
2729 DCRaw::_WriteJPEG(image_data_info& image, uint8* outputBuffer)
2730 {
2731 	fRead(outputBuffer, image.bytes);
2732 
2733 	if (outputBuffer[0] != 0xff || outputBuffer[1] != 0xd8)
2734 		throw (status_t)B_NO_TRANSLATOR;
2735 
2736 #if 0
2737 	uint8* thumb = (uint8*)malloc(image.bytes);
2738 	if (thumb == NULL)
2739 		throw (status_t)B_NO_MEMORY;
2740 
2741 	fRead(thumb, image.bytes);
2742 
2743 	uint8* data = (uint8*)fImageData;
2744 	data[0] = 0xff;
2745 	data[1] = 0xd8;
2746 
2747 	if (strcmp((char *)thumb + 6, "Exif")) {
2748 		// TODO: no EXIF data - write them ourselves
2749 	}
2750 
2751 	memcpy(&data[2], thumb + 2, image.bytes - 2);
2752 	free(thumb);
2753 #endif
2754 }
2755 
2756 
2757 //	#pragma mark - TIFF
2758 
2759 
2760 time_t
2761 DCRaw::_ParseTIFFTimestamp(bool reversed)
2762 {
2763 	char str[20];
2764 	str[19] = 0;
2765 
2766 	if (reversed) {
2767 		for (int i = 19; i--; ) {
2768 			str[i] = fRead.Next<uint8>();
2769 		}
2770 	} else
2771 		fRead(str, 19);
2772 
2773 	struct tm t;
2774 	memset(&t, 0, sizeof t);
2775 
2776 	if (sscanf(str, "%d:%d:%d %d:%d:%d", &t.tm_year, &t.tm_mon,
2777 			&t.tm_mday, &t.tm_hour, &t.tm_min, &t.tm_sec) != 6)
2778 		return 0;
2779 
2780 	t.tm_year -= 1900;
2781 	t.tm_mon -= 1;
2782 
2783 	return mktime(&t);
2784 }
2785 
2786 
2787 /*!	Reads a TIFF tag and positions the file stream to its data section
2788 */
2789 void
2790 DCRaw::_ParseTIFFTag(off_t baseOffset, tiff_tag& tag, off_t& offset)
2791 {
2792 	fRead(tag.tag);
2793 	fRead(tag.type);
2794 	fRead(tag.length);
2795 
2796 	offset = fRead.Position() + 4;
2797 
2798 	uint32 length = tag.length;
2799 
2800 	switch (tag.type) {
2801 		case TIFF_UINT16_TYPE:
2802 		case TIFF_INT16_TYPE:
2803 			length *= 2;
2804 			break;
2805 
2806 		case TIFF_UINT32_TYPE:
2807 		case TIFF_INT32_TYPE:
2808 		case TIFF_FLOAT_TYPE:
2809 			length *= 4;
2810 			break;
2811 
2812 		case TIFF_UFRACTION_TYPE:
2813 		case TIFF_FRACTION_TYPE:
2814 		case TIFF_DOUBLE_TYPE:
2815 			length *= 8;
2816 			break;
2817 
2818 		default:
2819 			break;
2820 	}
2821 
2822 	if (length > 4) {
2823 		uint32 position;
2824 		fRead(position);
2825 
2826 		fRead.Seek(baseOffset + position, SEEK_SET);
2827 	}
2828 }
2829 
2830 
2831 status_t
2832 DCRaw::_ParseTIFFImageFileDirectory(off_t baseOffset, uint32 offset)
2833 {
2834 	double analogBalance[] = {1, 1, 1, 1};
2835 	double xyz[] = {1, 1, 1, 1};
2836 	bool useColorMatrix = false;
2837 	double cameraCalibration[4][4], colorMatrix[4][3], cameraXYZ[4][3];
2838 
2839 	for (int32 j = 0; j < 4; j++) {
2840 		for (int32 i = 0; i < 4; i++) {
2841 			cameraCalibration[j][i] = i == j;
2842 		}
2843 	}
2844 
2845 	fRead.Seek(baseOffset + offset, SEEK_SET);
2846 
2847 	uint16 tags;
2848 	fRead(tags);
2849 	if (tags > 512)
2850 		return B_BAD_DATA;
2851 
2852 	image_data_info& image = fImages[fNumImages];
2853 
2854 	while (tags--) {
2855 		off_t nextOffset;
2856 		tiff_tag tag;
2857 		_ParseTIFFTag(baseOffset, tag, nextOffset);
2858 		TAG("TIFF tag: %u\n", tag.tag);
2859 
2860 		switch (tag.tag) {
2861 #if 0
2862 			default:
2863 				printf("tag %u NOT HANDLED!\n", tag.tag);
2864 				break;
2865 #endif
2866 
2867 			case 17:
2868 			case 18:
2869 				if (tag.type == 3 && tag.length == 1) {
2870 					fMeta.camera_multipliers[(tag.tag - 17) * 2]
2871 						= fRead.Next<uint16>() / 256.0;
2872 				}
2873 				break;
2874 
2875 			case 23:	// ISO speed
2876 				fMeta.iso_speed = fRead.Next(tag.type);
2877 				break;
2878 
2879 			case 36:
2880 			case 37:
2881 			case 38:
2882 				fMeta.camera_multipliers[tag.tag - 0x24] = fRead.Next<uint16>();
2883 				break;
2884 
2885 			case 39:
2886 				if (tag.length < 50 || fMeta.camera_multipliers[0])
2887 					break;
2888 
2889 				fRead.Stream().Seek(12, SEEK_CUR);
2890 				for (uint32 i = 0; i < 3; i++) {
2891 					fMeta.camera_multipliers[i] = fRead.Next<uint16>();
2892 				}
2893 				break;
2894 
2895 			case 2:		// image width
2896 			case 256:
2897 				image.width = fRead.Next(tag.type);
2898 				break;
2899 
2900 			case 3:		// image height
2901 			case 257:
2902 				image.height = fRead.Next(tag.type);
2903 				break;
2904 
2905 			case 258:	// bits per sample
2906 				image.samples = tag.length;
2907 				image.bits_per_sample = fRead.Next<uint16>();
2908 				break;
2909 
2910 			case 259:	// compression
2911 				image.compression = fRead.Next<uint16>();
2912 				break;
2913 
2914 			case 262:	// Photometric Interpretation
2915 				image.photometric_interpretation = fRead.Next<uint16>();
2916 				break;
2917 
2918 			case 271:	// manufacturer
2919 				fRead(fMeta.manufacturer, 64);
2920 				break;
2921 
2922 			case 272:	// model
2923 				fRead(fMeta.model, 64);
2924 				break;
2925 
2926 			case 273:	// Strip Offset
2927 			case 513:
2928 				image.data_offset = baseOffset + fRead.Next<uint32>();
2929 				if (!image.bits_per_sample) {
2930 					fRead.Stream().Seek(image.data_offset, SEEK_SET);
2931 					jhead jh;
2932 					if (_LosslessJPEGInit(&jh, true) == B_OK) {
2933 						image.compression = 6;
2934 						image.width = jh.wide << (jh.clrs == 2);
2935 						image.height = jh.high;
2936 						image.bits_per_sample = jh.bits;
2937 						image.samples = jh.clrs;
2938 					}
2939 				}
2940 				break;
2941 
2942 			case 274:	// Orientation
2943 				image.flip = fRead.Next<uint16>();
2944 				break;
2945 
2946 			case 277:	// Samples Per Pixel
2947 				image.samples = fRead.Next(tag.type);
2948 				break;
2949 
2950 			case 279:	// Strip Byte Counts
2951 			case 514:
2952 				image.bytes = fRead.Next<uint32>();
2953 				break;
2954 
2955 			case 305:	// Software
2956 				fRead(fMeta.software, 64);
2957 				if (!strncmp(fMeta.software, "Adobe", 5)
2958 					|| !strncmp(fMeta.software, "dcraw", 5)
2959 					|| !strncmp(fMeta.software, "Bibble", 6)
2960 					|| !strncmp(fMeta.software, "Nikon Scan", 10)
2961 					|| !strcmp(fMeta.software,"Digital Photo Professional"))
2962 					throw (status_t)B_NO_TRANSLATOR;
2963 				break;
2964 
2965 			case 306:	// Date/Time
2966 				fMeta.timestamp = _ParseTIFFTimestamp(false);
2967 				break;
2968 
2969 #if 0
2970 			case 323:	// Tile Length
2971 				tile_length = fRead.Next(type);
2972 				break;
2973 
2974 			case 324:	// Tile Offsets
2975 				image.data_offset = tag.length > 1
2976 					? fRead.Stream().Position() : fRead.Next<uint32>();
2977 				if (tag.length == 4)
2978 					load_raw = &CLASS sinar_4shot_load_raw;
2979 				break;
2980 #endif
2981 
2982 			case 330:	// Sub IFDs
2983 				if (!strcmp(fMeta.model, "DSLR-A100") && image.width == 3872) {
2984 					// TODO: this might no longer work!
2985 					image.data_offset = fRead.Next<uint32>() + baseOffset;
2986 					break;
2987 				}
2988 
2989 				while (tag.length--) {
2990 					off_t nextOffset = fRead.Position() + sizeof(uint32);
2991 
2992 					fRead.Seek(fRead.Next<uint32>() + baseOffset, SEEK_SET);
2993 					if (_ParseTIFFImageFileDirectory(baseOffset) != B_OK)
2994 						break;
2995 
2996 					fNumImages++;
2997 					fRead.Seek(nextOffset, SEEK_SET);
2998 				}
2999 				break;
3000 
3001 #if 0
3002 			case 400:
3003 				strcpy(fMeta.manufacturer, "Sarnoff");
3004 				maximum = 0xfff;
3005 				break;
3006 #endif
3007 
3008 #if 0
3009 			case 29184:
3010 				sony_offset = get4();
3011 				break;
3012 			case 29185:
3013 				sony_length = get4();
3014 				break;
3015 			case 29217:
3016 				sony_key = get4();
3017 				break;
3018 #endif
3019 
3020 			case 29443:
3021 				for (uint32 i = 0; i < 4; i++) {
3022 					fMeta.camera_multipliers[i ^ (i < 2)] = fRead.Next<uint16>();
3023 				}
3024 				break;
3025 
3026 			case 33405:	// Model 2
3027 				fRead(fMeta.model + 64, 64);
3028 				break;
3029 
3030 #if 0
3031 			case 33422:	// CFA Pattern
3032 			case 64777:	// Kodak P-series
3033 			{
3034 				if ((plen=len) > 16) plen = 16;
3035 				fread (cfa_pat, 1, plen, ifp);
3036 				for (colors=cfa=i=0; i < plen; i++) {
3037 				  colors += !(cfa & (1 << cfa_pat[i]));
3038 				  cfa |= 1 << cfa_pat[i];
3039 				}
3040 				if (cfa == 070) memcpy (cfa_pc,"\003\004\005",3);	/* CMY */
3041 				if (cfa == 072) memcpy (cfa_pc,"\005\003\004\001",4);	/* GMCY */
3042 				goto guess_cfa_pc;
3043 				break;
3044 			}
3045 
3046 			case 33424:
3047 				fseek(ifp, get4()+base, SEEK_SET);
3048 				parse_kodak_ifd (base);
3049 				break;
3050 #endif
3051 
3052 			case 33434:	// Exposure Time
3053 				fMeta.shutter = fRead.NextDouble(TIFF_FRACTION_TYPE);
3054 				break;
3055 
3056 			case 33437:	// Aperture
3057 				fMeta.aperture = fRead.NextDouble(TIFF_FRACTION_TYPE);
3058 				break;
3059 
3060 			case 34306:	// Leaf white balance
3061 				for (uint32 i = 0; i < 4; i++) {
3062 					fMeta.camera_multipliers[i ^ 1] = 4096.0 / fRead.Next<uint16>();
3063 				}
3064 				break;
3065 
3066 #if 0
3067 			case 34307:	// Leaf Catch Light color matrix
3068 				fread (software, 1, 7, ifp);
3069 				if (strncmp(software,"MATRIX",6))
3070 					break;
3071 				colors = 4;
3072 				for (fRawColor = i=0; i < 3; i++) {
3073 					FORC4 fscanf (ifp, "%f", &rgb_cam[i][c^1]);
3074 					if (!use_camera_wb)
3075 						continue;
3076 					num = 0;
3077 					FORC4 num += rgb_cam[i][c];
3078 					FORC4 rgb_cam[i][c] /= num;
3079 				}
3080 				break;
3081 			case 34310:	// Leaf metadata
3082 				parse_mos (ftell(ifp));
3083 			case 34303:
3084 				strcpy(image.manufacturer, "Leaf");
3085 				break;
3086 #endif
3087 
3088 			case 34665:	// EXIF tag
3089 				fRead.Seek(fRead.Next<uint32>() + baseOffset, SEEK_SET);
3090 
3091 				fEXIFOffset = fRead.Position();
3092 				fEXIFLength = tag.length;
3093 
3094 				_ParseEXIF(baseOffset);
3095 				break;
3096 
3097 #if 0
3098 			case 34675:	// InterColorProfile
3099 			case 50831:	// AsShotICCProfile
3100 				profile_offset = fRead.Stream().Position();
3101 				profile_length = tag.length;
3102 				break;
3103 
3104 			case 37122:	// Compressed Bits Per Pixel
3105 				kodak_cbpp = fRead.Next<uint32>();
3106 				break;
3107 #endif
3108 
3109 			case 37386:	// Focal Length
3110 				fMeta.focal_length = fRead.NextDouble(TIFF_FRACTION_TYPE);
3111 				break;
3112 
3113 			case 37393:	// Image Number
3114 				fMeta.shot_order = fRead.Next(tag.type);
3115 				break;
3116 
3117 #if 0
3118 			case 37400:	// old Kodak KDC tag
3119 				for (fRawColor = i=0; i < 3; i++) {
3120 					getrat();
3121 					FORC3 rgb_cam[i][c] = getrat();
3122 				}
3123 				break;
3124 
3125 			case 46275:	// Imacon tags
3126 				strcpy (make, "Imacon");
3127 				data_offset = ftell(ifp);
3128 				ima_len = len;
3129 				break;
3130       case 46279:
3131 	fseek (ifp, 78, SEEK_CUR);
3132 	raw_width  = get4();
3133 	raw_height = get4();
3134 	left_margin = get4() & 7;
3135 	width = raw_width - left_margin - (get4() & 7);
3136 	top_margin = get4() & 7;
3137 	height = raw_height - top_margin - (get4() & 7);
3138 	fseek (ifp, 52, SEEK_CUR);
3139 	FORC3 cam_multipliers[c] = getreal(11);
3140 	fseek (ifp, 114, SEEK_CUR);
3141 	flip = (get2() >> 7) * 90;
3142 	if (width * height * 6 == ima_len) {
3143 	  if (flip % 180 == 90) SWAP(width,height);
3144 	  filters = flip = 0;
3145 	}
3146 	break;
3147       case 50454:			/* Sinar tag */
3148       case 50455:
3149 	if (!(cbuf = (char *) malloc(len))) break;
3150 	fread (cbuf, 1, len, ifp);
3151 	for (cp = cbuf-1; cp && cp < cbuf+len; cp = strchr(cp,'\n'))
3152 	  if (!strncmp (++cp,"Neutral ",8))
3153 	    sscanf (cp+8, "%f %f %f", cam_multipliers, cam_multipliers+1, cam_multipliers+2);
3154 	free (cbuf);
3155 	break;
3156 #endif
3157 
3158 			case 50706:	// DNG Version
3159 				for (int32 i = 0; i < 4; i++) {
3160 					fDNGVersion = (fDNGVersion << 8) + fRead.Next<uint8>();
3161 				}
3162 				break;
3163 
3164 #if 0
3165 			case 50710:	// CFAPlaneColor
3166 				if (len > 4)
3167 					len = 4;
3168 				colors = len;
3169 				fread(cfa_pc, 1, colors, ifp);
3170 			guess_cfa_pc:
3171 				FORCC tab[cfa_pc[c]] = c;
3172 				cdesc[c] = 0;
3173 				for (i=16; i--; )
3174 					filters = filters << 2 | tab[cfa_pat[i % plen]];
3175 				break;
3176 			case 50711:	// CFALayout
3177 				if (get2() == 2) {
3178 					fuji_width = 1;
3179 					filters = 0x49494949;
3180 				}
3181 				break;
3182 #endif
3183 
3184 			case 291:	// Linearization Table
3185 			case 50712:
3186 				_ParseLinearTable(tag.length);
3187 				break;
3188 
3189 			case 50714:			/* BlackLevel */
3190 			case 50715:			/* BlackLevelDeltaH */
3191 			case 50716:			/* BlackLevelDeltaV */
3192 			{
3193 				double black = 0.0;
3194 				for (uint32 i = 0; i < tag.length; i++) {
3195 					black += fRead.NextDouble(tag.type);
3196 				}
3197 				fMeta.black += int32(black / tag.length + 0.5);
3198 				break;
3199 			}
3200 
3201 			case 50717:	// White Level
3202 				fMeta.maximum = fRead.Next(tag.type);
3203 				break;
3204 
3205 			case 50718:	// Default Scale
3206 				fMeta.pixel_aspect = fRead.NextDouble(TIFF_FRACTION_TYPE);
3207 				fMeta.pixel_aspect /= fRead.NextDouble(TIFF_FRACTION_TYPE);
3208 				break;
3209 
3210 			case 50721:	// Color Matrix
3211 			case 50722:
3212 				for (uint32 c = 0; c < fColors; c++) {
3213 					for (uint32 j = 0; j < 3; j++) {
3214 						colorMatrix[c][j] = fRead.NextDouble(TIFF_FRACTION_TYPE);
3215 					}
3216 				}
3217 				useColorMatrix = true;
3218 				break;
3219 
3220 			case 50723:	// Camera Calibration
3221 			case 50724:
3222 				for (uint32 i = 0; i < fColors; i++) {
3223 					for (uint32 c = 0; c < fColors; c++) {
3224 						cameraCalibration[i][c] = fRead.NextDouble(
3225 							TIFF_FRACTION_TYPE);
3226 					}
3227 				}
3228 				//break;
3229 			case 50727:	// Analog Balance
3230 				for (uint32 c = 0; c < fColors; c++) {
3231 					analogBalance[c] = fRead.NextDouble(TIFF_FRACTION_TYPE);
3232 					//printf("ab: %g\n", analogBalance[c]);
3233 				}
3234 				break;
3235 #if 0
3236       case 50728:			/* AsShotNeutral */
3237 	FORCC asn[c] = getreal(type);
3238 	break;
3239       case 50729:			/* AsShotWhiteXY */
3240 	xyz[0] = getrat();
3241 	xyz[1] = getrat();
3242 	xyz[2] = 1 - xyz[0] - xyz[1];
3243 	FORC3 xyz[c] /= kD65White[c];
3244 	break;
3245       case 50740:			/* DNGPrivateData */
3246 	if (dng_version) break;
3247 	i = order;
3248 	parse_minolta (j = get4()+base);
3249 	order = i;
3250 	fseek (ifp, j, SEEK_SET);
3251 	parse_tiff_ifd (base);
3252 	break;
3253 #endif
3254 			case 50752:
3255 				fRead.NextShorts(fCR2Slice, 3);
3256 				break;
3257 
3258 			case 50829:	// Active Area
3259 				fTopMargin = fRead.Next(tag.type);
3260 				fLeftMargin = fRead.Next(tag.type);
3261 				fInputHeight = fRead.Next(tag.type) - fTopMargin;
3262 				fInputWidth = fRead.Next(tag.type) - fLeftMargin;
3263 				break;
3264 #if 0
3265       case 64772:			/* Kodak P-series */
3266 	fseek (ifp, 16, SEEK_CUR);
3267 	data_offset = get4();
3268 	fseek (ifp, 28, SEEK_CUR);
3269 	data_offset += get4();
3270 	load_raw = &CLASS packed_12_load_raw;
3271 #endif
3272 		}
3273 		fRead.Seek(nextOffset, SEEK_SET);
3274 	}
3275 
3276 	// handle SONY tags
3277 
3278 #if 0
3279 	if (sony_length && (buf = (unsigned *) malloc(sony_length))) {
3280 		fseek(ifp, sony_offset, SEEK_SET);
3281 		fread(buf, sony_length, 1, ifp);
3282 		sony_decrypt(buf, sony_length / 4, 1, sony_key);
3283 		sfp = ifp;
3284 		if ((ifp = tmpfile())) {
3285 			fwrite(buf, sony_length, 1, ifp);
3286 			fseek(ifp, 0, SEEK_SET);
3287 			parse_tiff_ifd(-sony_offset);
3288 			fclose(ifp);
3289 		}
3290 		ifp = sfp;
3291 		free(buf);
3292 	}
3293 #endif
3294 
3295 	for (uint32 i = 0; i < fColors; i++) {
3296 		for (uint32 c = 0; c < fColors; c++) {
3297 			cameraCalibration[i][c] *= analogBalance[i];
3298 		}
3299 	}
3300 
3301 	if (useColorMatrix) {
3302 		for (uint32 c = 0; c < fColors; c++) {
3303 			for (uint32 i = 0; i < 3; i++) {
3304 				cameraXYZ[c][i] = 0;
3305 				for (uint32 j = 0; j < fColors; j++) {
3306 					cameraXYZ[c][i] += cameraCalibration[c][j]
3307 						* colorMatrix[j][i] * xyz[i];
3308 				}
3309 			}
3310 		}
3311 		_CameraXYZCoefficients(cameraXYZ);
3312 	}
3313 
3314 #if 0
3315 	if (asn[0])
3316     	FORCC pre_multipliers[c] = 1 / asn[c];
3317 #endif
3318 	if (!useColorMatrix) {
3319 		for (uint32 c = 0; c < fColors; c++) {
3320 			fMeta.pre_multipliers[c] /= cameraCalibration[c][c];
3321 		}
3322 	}
3323 
3324 	return B_OK;
3325 }
3326 
3327 
3328 status_t
3329 DCRaw::_ParseTIFFImageFileDirectory(off_t baseOffset)
3330 {
3331 	while (fNumImages < kImageBufferCount) {
3332 		int32 offset;
3333 		fRead(offset);
3334 		if (offset == 0)
3335 			break;
3336 
3337 		status_t status = _ParseTIFFImageFileDirectory(baseOffset, offset);
3338 		if (status < B_OK)
3339 			return status;
3340 
3341 		fNumImages++;
3342 	}
3343 
3344 	return B_OK;
3345 }
3346 
3347 
3348 status_t
3349 DCRaw::_ParseTIFF(off_t baseOffset)
3350 {
3351 	fRead.Stream().Seek(baseOffset, SEEK_SET);
3352 
3353 	uint16 endian;
3354 	fRead(endian);
3355 	if (endian != 'MM' && endian != 'II')
3356 		return B_NO_TRANSLATOR;
3357 
3358 #if B_HOST_IS_LENDIAN
3359 	fRead.SetSwap(endian == 'MM');
3360 #else
3361 	fRead.SetSwap(endian == 'II');
3362 #endif
3363 
3364 	fRead(endian);
3365 		// dummy, not used, should be 42 for actual TIFF images,
3366 		// but may vary for RAW images
3367 
3368 	_ParseTIFFImageFileDirectory(baseOffset);
3369 	fIsTIFF = true;
3370 
3371 	uint32 maxSamples = 0;
3372 
3373 	if (fThumbIndex >= 0 && _Thumb().data_offset) {
3374 		fRead.Seek(_Thumb().data_offset, SEEK_SET);
3375 
3376 		jhead jh;
3377 		if (_LosslessJPEGInit(&jh, true)) {
3378 			_Thumb().bits_per_sample = jh.bits;
3379 			_Thumb().width = jh.wide;
3380 			_Thumb().height = jh.high;
3381 			_Thumb().bits_per_sample = 16;
3382 		}
3383 	}
3384 
3385 	// identify RAW image in list of images retrieved
3386 
3387 	for (uint32 i = 0; i < fNumImages; i++) {
3388 		if (maxSamples < fImages[i].samples)
3389 			maxSamples = fImages[i].samples;
3390 
3391 		if ((fImages[i].compression != COMPRESSION_OLD_JPEG
3392 				|| fImages[i].samples != 3)
3393 			&& _SupportsCompression(fImages[i])) {
3394 			fImages[i].is_raw = true;
3395 
3396 			if (fRawIndex < 0 || fImages[i].width * fImages[i].height
3397 					> _Raw().width * _Raw().height) {
3398 				fRawIndex = i;
3399 				//fuji_secondary = _Raw().samples == 2;
3400 			}
3401 		}
3402 	}
3403 
3404 	if (fRawIndex < 0
3405 		|| (!fDNGVersion && _Raw().samples == 3 && _Raw().bits_per_sample == 8))
3406 		throw (status_t)B_NO_TRANSLATOR;
3407 
3408 	if (fRawIndex >= 0) {
3409 		fMeta.raw_width = _Raw().width;
3410 		fMeta.raw_height = _Raw().height;
3411 	}
3412 
3413 #if 0
3414   fuji_width *= (raw_width+1)/2;
3415   if (tiff_ifd[0].flip) tiff_flip = tiff_ifd[0].flip;
3416   if (raw >= 0 && !load_raw)
3417     switch (tiff_compress) {
3418       case 0:  case 1:
3419 	load_raw = tiff_bps > 8 ?
3420 	  &CLASS unpacked_load_raw : &CLASS eight_bit_load_raw;
3421 	if (tiff_ifd[raw].bytes * 5 == raw_width * raw_height * 8)
3422 	  load_raw = &CLASS olympus_e300_load_raw;
3423 	if (tiff_bps == 12 && tiff_ifd[raw].phint == 2)
3424 	  load_raw = &CLASS olympus_cseries_load_raw;
3425 	break;
3426       case 6:  case 7:  case 99:
3427 	load_raw = &CLASS lossless_jpeg_load_raw;		break;
3428       case 262:
3429 	load_raw = &CLASS kodak_262_load_raw;			break;
3430       case 32773:
3431 	load_raw = &CLASS packed_12_load_raw;			break;
3432       case 65535:
3433 	load_raw = &CLASS pentax_k10_load_raw;			break;
3434       case 65000:
3435 	switch (tiff_ifd[raw].phint) {
3436 	  case 2: load_raw = &CLASS kodak_rgb_load_raw;   fFilters = 0;  break;
3437 	  case 6: load_raw = &CLASS kodak_ycbcr_load_raw; fFilters = 0;  break;
3438 	  case 32803: load_raw = &CLASS kodak_65000_load_raw;
3439 	}
3440     }
3441   if (tiff_samples == 3 && tiff_bps == 8)
3442     if (!dng_version) is_raw = 0;
3443 #endif
3444 
3445 #if 0
3446   if (thm >= 0) {
3447     thumb_misc |= tiff_ifd[thm].samples << 5;
3448     switch (tiff_ifd[thm].comp) {
3449       case 0:
3450 	write_thumb = &CLASS layer_thumb;
3451 	break;
3452       case 1:
3453 	if (tiff_ifd[thm].bps > 8)
3454 	  thumb_load_raw = &CLASS kodak_thumb_load_raw;
3455 	else
3456 	  write_thumb = &CLASS ppm_thumb;
3457 	break;
3458       case 65000:
3459 	thumb_load_raw = tiff_ifd[thm].phint == 6 ?
3460 		&CLASS kodak_ycbcr_load_raw : &CLASS kodak_rgb_load_raw;
3461     }
3462   }
3463 #endif
3464 	return B_OK;
3465 }
3466 
3467 
3468 //	#pragma mark -
3469 
3470 
3471 status_t
3472 DCRaw::Identify()
3473 {
3474 	fRead.Seek(0, SEEK_SET);
3475 
3476 	status_t status = B_NO_TRANSLATOR;
3477 	char header[32];
3478 	fRead(header, sizeof(header));
3479 
3480 	// check for TIFF-like files first
3481 
3482 	uint16 endian = *(uint16*)&header;
3483 	if (endian == 'II' || endian == 'MM')
3484 		status = _ParseTIFF(0);
3485 
3486 	if (status < B_OK)
3487 		return status;
3488 
3489 	// brush up some variables for later use
3490 
3491 	fInputWidth = _Raw().width;
3492 	fInputHeight = _Raw().height;
3493 
3494 	_FixupValues();
3495 
3496 	if ((_Raw().width | _Raw().height) < 0)
3497 		_Raw().width = _Raw().height = 0;
3498 	if (fMeta.maximum == 0)
3499 		fMeta.maximum = (1 << _Raw().bits_per_sample) - 1;
3500 
3501 	if (fFilters == ~0UL)
3502 		fFilters = 0x94949494;
3503 	if (fFilters && fColors == 3) {
3504 		for (int32 i = 0; i < 32; i += 4) {
3505 			if ((fFilters >> i & 15) == 9)
3506 				fFilters |= 2 << i;
3507 			if ((fFilters >> i & 15) == 6)
3508 				fFilters |= 8 << i;
3509 		}
3510 	}
3511 
3512 	if (fRawColor)
3513 		_AdobeCoefficients(fMeta.manufacturer, fMeta.model);
3514 
3515 	// remove invalid images
3516 
3517 	int32 rawCount = 0;
3518 
3519 	for (int32 i = 0; i < (int32)fNumImages; i++) {
3520 		if (fImages[i].width == 0 || fImages[i].height == 0
3521 			|| fImages[i].data_offset == 0) {
3522 			fNumImages--;
3523 			if (i == fRawIndex)
3524 				fRawIndex = -1;
3525 			else if (i < fRawIndex)
3526 				fRawIndex--;
3527 			if (i == fThumbIndex)
3528 				fThumbIndex = -1;
3529 			else if (i < fThumbIndex)
3530 				fThumbIndex--;
3531 
3532 			if (i < (int32)fNumImages) {
3533 				memmove(&fImages[i], &fImages[i + 1],
3534 					sizeof(image_data_info) * (fNumImages - i));
3535 			}
3536 			i--;
3537 		} else if (fImages[i].is_raw)
3538 			rawCount++;
3539 	}
3540 
3541 	// This is to prevent us from identifying TIFF images
3542 	if (rawCount == 0)
3543 		return B_NO_TRANSLATOR;
3544 
3545 	fMeta.flip = _Raw().flip;
3546 	return B_OK;
3547 }
3548 
3549 
3550 status_t
3551 DCRaw::ReadImageAt(uint32 index, uint8*& outputBuffer, size_t& bufferSize)
3552 {
3553 	if (index >= fNumImages)
3554 		return B_BAD_VALUE;
3555 
3556 	_CorrectIndex(index);
3557 
3558 	image_data_info& image = fImages[index];
3559 
3560 	fShrink = (fHalfSize || fThreshold) && fFilters;
3561 	fOutputWidth = (fInputWidth + fShrink) >> fShrink;
3562 	fOutputHeight = (fInputHeight + fShrink) >> fShrink;
3563 
3564 	if (image.flip > 4) {
3565 		// image is rotated
3566 		image.output_width = fOutputHeight;
3567 		image.output_height = fOutputWidth;
3568 	} else {
3569 		image.output_width = fOutputWidth;
3570 		image.output_height = fOutputHeight;
3571 	}
3572 
3573 	if (image.is_raw) {
3574 		bufferSize = fOutputWidth * 4 * fOutputHeight;
3575 
3576 		fImageData = (uint16 (*)[4])calloc(fOutputWidth * fOutputHeight
3577 			* sizeof(*fImageData) + 0, 1); //meta_length, 1);
3578 		if (fImageData == NULL)
3579 			throw (status_t)B_NO_MEMORY;
3580 	} else {
3581 		bufferSize = image.bytes + sizeof(tiff_header) + 10;
3582 			// TIFF header plus EXIF identifier
3583 	}
3584 
3585 	outputBuffer = (uint8*)malloc(bufferSize);
3586 	if (outputBuffer == NULL) {
3587 		free(fImageData);
3588 		fImageData = NULL;
3589 		throw (status_t)B_NO_MEMORY;
3590 	}
3591 
3592 	fRead.Seek(image.data_offset, SEEK_SET);
3593 
3594 	if (image.is_raw) {
3595 		_LoadRAW(image);
3596 
3597 		//bad_pixels();
3598 		//if (dark_frame) subtract (dark_frame);
3599 		//quality = 2 + !fuji_width;
3600 
3601 		if (fDocumentMode < 2)
3602 			_ScaleColors();
3603 		_PreInterpolate();
3604 		_CameraToCIELab(NULL, NULL);
3605 
3606 		if (fFilters && !fDocumentMode) {
3607 #if 0
3608 			if (quality == 0)
3609 				lin_interpolate();
3610 			else if (quality < 3 || colors > 3)
3611 				vng_interpolate();
3612 #endif
3613 			_AHDInterpolate();
3614 		}
3615 
3616 #if 0
3617 		if (fHightlight > 1)
3618 			_RecoverHighlights();
3619 		if (use_fuji_rotate) fuji_rotate();
3620 		if (mix_green && (colors = 3))
3621 			for (i=0; i < height*width; i++)
3622 				image[i][1] = (image[i][1] + image[i][3]) >> 1;
3623 #endif
3624 
3625 		_ConvertToRGB();
3626 		//if (use_fuji_rotate) stretch();
3627 
3628 		_WriteRGB32(image, outputBuffer);
3629 	} else {
3630 		_WriteJPEG(image, outputBuffer);
3631 	}
3632 
3633 	free(fImageData);
3634 	fImageData = NULL;
3635 
3636 	return B_OK;
3637 }
3638 
3639 
3640 void
3641 DCRaw::GetMetaInfo(image_meta_info& metaInfo) const
3642 {
3643 	metaInfo = fMeta;
3644 }
3645 
3646 
3647 uint32
3648 DCRaw::CountImages() const
3649 {
3650 	return fNumImages;
3651 }
3652 
3653 
3654 status_t
3655 DCRaw::ImageAt(uint32 index, image_data_info& info) const
3656 {
3657 	if (index >= fNumImages)
3658 		return B_BAD_VALUE;
3659 
3660 	_CorrectIndex(index);
3661 
3662 	info = fImages[index];
3663 	return B_OK;
3664 }
3665 
3666 
3667 status_t
3668 DCRaw::GetEXIFTag(off_t& offset, size_t& length, bool& bigEndian) const
3669 {
3670 	if (fEXIFOffset < 0)
3671 		return B_ENTRY_NOT_FOUND;
3672 
3673 	offset = fEXIFOffset;
3674 	length = fEXIFLength;
3675 
3676 #if B_HOST_IS_LENDIAN
3677 	bigEndian = fRead.IsSwapping();
3678 #else
3679 	bigEndian = !fRead.IsSwapping();
3680 #endif
3681 	return B_OK;
3682 }
3683 
3684 
3685 void
3686 DCRaw::SetProgressMonitor(monitor_hook hook, void* data)
3687 {
3688 	fProgressMonitor = hook;
3689 	fProgressData = data;
3690 }
3691 
3692 
3693 void
3694 DCRaw::SetHalfSize(bool half)
3695 {
3696 	fHalfSize = half;
3697 }
3698