0bce6b2147c1917849c98a9783b9bfd2efffb7a4
[imager.git] / TIFF / imtiff.c
1 #include <tiffio.h>
2 #include <string.h>
3 #include "imtiff.h"
4 #include "imext.h"
5
6 /* needed to implement our substitute TIFFIsCODECConfigured */
7 #if TIFFLIB_VERSION < 20031121
8 static int TIFFIsCODECConfigured(uint16 scheme);
9 #endif
10
11 /*
12 =head1 NAME
13
14 tiff.c - implements reading and writing tiff files, uses io layer.
15
16 =head1 SYNOPSIS
17
18    io_glue *ig = io_new_fd( fd );
19    i_img *im   = i_readtiff_wiol(ig, -1); // no limit on how much is read
20    // or 
21    io_glue *ig = io_new_fd( fd );
22    return_code = i_writetiff_wiol(im, ig); 
23
24 =head1 DESCRIPTION
25
26 tiff.c implements the basic functions to read and write tiff files.
27 It uses the iolayer and needs either a seekable source or an entire
28 memory mapped buffer.
29
30 =head1 FUNCTION REFERENCE
31
32 Some of these functions are internal.
33
34 =over
35
36 =cut
37 */
38
39 #define byteswap_macro(x) \
40      ((((x) & 0xff000000) >> 24) | (((x) & 0x00ff0000) >>  8) |     \
41       (((x) & 0x0000ff00) <<  8) | (((x) & 0x000000ff) << 24))
42
43 #define CLAMP8(x) ((x) < 0 ? 0 : (x) > 255 ? 255 : (x))
44 #define CLAMP16(x) ((x) < 0 ? 0 : (x) > 65535 ? 65535 : (x))
45
46 #define Sample16To8(num) ((num) / 257)
47
48 struct tag_name {
49   char *name;
50   uint32 tag;
51 };
52
53 static i_img *read_one_rgb_tiled(TIFF *tif, i_img_dim width, i_img_dim height, int allow_incomplete);
54 static i_img *read_one_rgb_lines(TIFF *tif, i_img_dim width, i_img_dim height, int allow_incomplete);
55
56 static struct tag_name text_tag_names[] =
57 {
58   { "tiff_documentname", TIFFTAG_DOCUMENTNAME, },
59   { "tiff_imagedescription", TIFFTAG_IMAGEDESCRIPTION, },
60   { "tiff_make", TIFFTAG_MAKE, },
61   { "tiff_model", TIFFTAG_MODEL, },
62   { "tiff_pagename", TIFFTAG_PAGENAME, },
63   { "tiff_software", TIFFTAG_SOFTWARE, },
64   { "tiff_datetime", TIFFTAG_DATETIME, },
65   { "tiff_artist", TIFFTAG_ARTIST, },
66   { "tiff_hostcomputer", TIFFTAG_HOSTCOMPUTER, },
67 };
68
69 static struct tag_name 
70 compress_values[] =
71   {
72     { "none",     COMPRESSION_NONE },
73     { "ccittrle", COMPRESSION_CCITTRLE },
74     { "fax3",     COMPRESSION_CCITTFAX3 },
75     { "t4",       COMPRESSION_CCITTFAX3 },
76     { "fax4",     COMPRESSION_CCITTFAX4 },
77     { "t6",       COMPRESSION_CCITTFAX4 },
78     { "lzw",      COMPRESSION_LZW },
79     { "jpeg",     COMPRESSION_JPEG },
80     { "packbits", COMPRESSION_PACKBITS },
81     { "deflate",  COMPRESSION_ADOBE_DEFLATE },
82     { "zip",      COMPRESSION_ADOBE_DEFLATE },
83     { "oldzip",   COMPRESSION_DEFLATE },
84     { "ccittrlew", COMPRESSION_CCITTRLEW },
85   };
86
87 static const int compress_value_count = 
88   sizeof(compress_values) / sizeof(*compress_values);
89
90 static int 
91 myTIFFIsCODECConfigured(uint16 scheme);
92
93 typedef struct read_state_tag read_state_t;
94 /* the setup function creates the image object, allocates the line buffer */
95 typedef int (*read_setup_t)(read_state_t *state);
96
97 /* the putter writes the image data provided by the getter to the
98    image, x, y, width, height describe the target area of the image,
99    extras is the extra number of pixels stored for each scanline in
100    the raster buffer, (for tiles against the right side of the
101    image) */
102
103 typedef int (*read_putter_t)(read_state_t *state, i_img_dim x, i_img_dim y,
104                              i_img_dim width, i_img_dim height, int extras);
105
106 /* reads from a tiled or strip image and calls the putter.
107    This may need a second type for handling non-contiguous images
108    at some point */
109 typedef int (*read_getter_t)(read_state_t *state, read_putter_t putter);
110
111 struct read_state_tag {
112   TIFF *tif;
113   i_img *img;
114   void *raster;
115   i_img_dim pixels_read;
116   int allow_incomplete;
117   void *line_buf;
118   uint32 width, height;
119   uint16 bits_per_sample;
120   uint16 photometric;
121
122   /* the total number of channels (samples per pixel) */
123   int samples_per_pixel;
124
125   /* if non-zero, which channel is the alpha channel, typically 3 for rgb */
126   int alpha_chan;
127
128   /* whether or not to scale the color channels based on the alpha
129      channel.  TIFF has 2 types of alpha channel, if the alpha channel
130      we use is EXTRASAMPLE_ASSOCALPHA then the color data will need to
131      be scaled to match Imager's conventions */
132   int scale_alpha;
133 };
134
135 static int tile_contig_getter(read_state_t *state, read_putter_t putter);
136 static int strip_contig_getter(read_state_t *state, read_putter_t putter);
137
138 static int setup_paletted(read_state_t *state);
139 static int paletted_putter8(read_state_t *, i_img_dim, i_img_dim, i_img_dim, i_img_dim, int);
140 static int paletted_putter4(read_state_t *, i_img_dim, i_img_dim, i_img_dim, i_img_dim, int);
141
142 static int setup_16_rgb(read_state_t *state);
143 static int setup_16_grey(read_state_t *state);
144 static int putter_16(read_state_t *, i_img_dim, i_img_dim, i_img_dim, i_img_dim, int);
145
146 static int setup_8_rgb(read_state_t *state);
147 static int setup_8_grey(read_state_t *state);
148 static int putter_8(read_state_t *, i_img_dim, i_img_dim, i_img_dim, i_img_dim, int);
149
150 static int setup_32_rgb(read_state_t *state);
151 static int setup_32_grey(read_state_t *state);
152 static int putter_32(read_state_t *, i_img_dim, i_img_dim, i_img_dim, i_img_dim, int);
153
154 static int setup_bilevel(read_state_t *state);
155 static int putter_bilevel(read_state_t *, i_img_dim, i_img_dim, i_img_dim, i_img_dim, int);
156
157 static int setup_cmyk8(read_state_t *state);
158 static int putter_cmyk8(read_state_t *, i_img_dim, i_img_dim, i_img_dim, i_img_dim, int);
159
160 static int setup_cmyk16(read_state_t *state);
161 static int putter_cmyk16(read_state_t *, i_img_dim, i_img_dim, i_img_dim, i_img_dim, int);
162 static void
163 rgb_channels(read_state_t *state, int *out_channels);
164 static void
165 grey_channels(read_state_t *state, int *out_channels);
166 static void
167 cmyk_channels(read_state_t *state, int *out_channels);
168 static void
169 fallback_rgb_channels(TIFF *tif, i_img_dim width, i_img_dim height, int *channels, int *alpha_chan);
170
171 static const int text_tag_count = 
172   sizeof(text_tag_names) / sizeof(*text_tag_names);
173
174 #if TIFFLIB_VERSION >= 20051230
175 #define USE_EXT_WARN_HANDLER
176 #endif
177
178 #define TIFFIO_MAGIC 0xC6A340CC
179
180 static void error_handler(char const *module, char const *fmt, va_list ap) {
181   mm_log((1, "tiff error fmt %s\n", fmt));
182   i_push_errorvf(0, fmt, ap);
183 }
184
185 typedef struct {
186   unsigned magic;
187   io_glue *ig;
188 #ifdef USE_EXT_WARN_HANDLER
189   char *warn_buffer;
190   size_t warn_size;
191 #endif
192 } tiffio_context_t;
193
194 static void
195 tiffio_context_init(tiffio_context_t *c, io_glue *ig);
196 static void
197 tiffio_context_final(tiffio_context_t *c);
198
199 #define WARN_BUFFER_LIMIT 10000
200
201 #ifdef USE_EXT_WARN_HANDLER
202
203 static void
204 warn_handler_ex(thandle_t h, const char *module, const char *fmt, va_list ap) {
205   tiffio_context_t *c = (tiffio_context_t *)h;
206   char buf[200];
207
208   if (c->magic != TIFFIO_MAGIC)
209     return;
210
211   buf[0] = '\0';
212 #ifdef IMAGER_VSNPRINTF
213   vsnprintf(buf, sizeof(buf), fmt, ap);
214 #else
215   vsprintf(buf, fmt, ap);
216 #endif
217   mm_log((1, "tiff warning %s\n", buf));
218
219   if (!c->warn_buffer || strlen(c->warn_buffer)+strlen(buf)+2 > c->warn_size) {
220     size_t new_size = c->warn_size + strlen(buf) + 2;
221     char *old_buffer = c->warn_buffer;
222     if (new_size > WARN_BUFFER_LIMIT) {
223       new_size = WARN_BUFFER_LIMIT;
224     }
225     c->warn_buffer = myrealloc(c->warn_buffer, new_size);
226     if (!old_buffer) c->warn_buffer[0] = '\0';
227     c->warn_size = new_size;
228   }
229   if (strlen(c->warn_buffer)+strlen(buf)+2 <= c->warn_size) {
230     strcat(c->warn_buffer, buf);
231     strcat(c->warn_buffer, "\n");
232   }
233 }
234
235 #else
236
237 static char *warn_buffer = NULL;
238 static int warn_buffer_size = 0;
239
240 static void warn_handler(char const *module, char const *fmt, va_list ap) {
241   char buf[1000];
242
243   buf[0] = '\0';
244 #ifdef IMAGER_VSNPRINTF
245   vsnprintf(buf, sizeof(buf), fmt, ap);
246 #else
247   vsprintf(buf, fmt, ap);
248 #endif
249   mm_log((1, "tiff warning %s\n", buf));
250
251   if (!warn_buffer || strlen(warn_buffer)+strlen(buf)+2 > warn_buffer_size) {
252     int new_size = warn_buffer_size + strlen(buf) + 2;
253     char *old_buffer = warn_buffer;
254     if (new_size > WARN_BUFFER_LIMIT) {
255       new_size = WARN_BUFFER_LIMIT;
256     }
257     warn_buffer = myrealloc(warn_buffer, new_size);
258     if (!old_buffer) *warn_buffer = '\0';
259     warn_buffer_size = new_size;
260   }
261   if (strlen(warn_buffer)+strlen(buf)+2 <= warn_buffer_size) {
262     strcat(warn_buffer, buf);
263     strcat(warn_buffer, "\n");
264   }
265 }
266
267 #endif
268
269 static i_mutex_t mutex;
270
271 void
272 i_tiff_init(void) {
273   mutex = i_mutex_new();
274 }
275
276 static int save_tiff_tags(TIFF *tif, i_img *im);
277
278 static void 
279 pack_4bit_to(unsigned char *dest, const unsigned char *src, i_img_dim count);
280
281
282 static toff_t sizeproc(thandle_t x) {
283         return 0;
284 }
285
286
287 /*
288 =item comp_seek(h, o, w)
289
290 Compatability for 64 bit systems like latest freebsd (internal)
291
292    h - tiff handle, cast an io_glue object
293    o - offset
294    w - whence
295
296 =cut
297 */
298
299 static
300 toff_t
301 comp_seek(thandle_t h, toff_t o, int w) {
302   io_glue *ig = ((tiffio_context_t *)h)->ig;
303   return (toff_t) i_io_seek(ig, o, w);
304 }
305
306 /*
307 =item comp_mmap(thandle_t, tdata_t*, toff_t*)
308
309 Dummy mmap stub.
310
311 This shouldn't ever be called but newer tifflibs want it anyway.
312
313 =cut
314 */
315
316 static 
317 int
318 comp_mmap(thandle_t h, tdata_t*p, toff_t*off) {
319   return -1;
320 }
321
322 /*
323 =item comp_munmap(thandle_t h, tdata_t p, toff_t off)
324
325 Dummy munmap stub.
326
327 This shouldn't ever be called but newer tifflibs want it anyway.
328
329 =cut
330 */
331
332 static void
333 comp_munmap(thandle_t h, tdata_t p, toff_t off) {
334   /* do nothing */
335 }
336
337 static tsize_t
338 comp_read(thandle_t h, tdata_t p, tsize_t size) {
339   return i_io_read(((tiffio_context_t *)h)->ig, p, size);
340 }
341
342 static tsize_t
343 comp_write(thandle_t h, tdata_t p, tsize_t size) {
344   return i_io_write(((tiffio_context_t *)h)->ig, p, size);
345 }
346
347 static int
348 comp_close(thandle_t h) {
349   return i_io_close(((tiffio_context_t *)h)->ig);
350 }
351
352 static i_img *read_one_tiff(TIFF *tif, int allow_incomplete) {
353   i_img *im;
354   uint32 width, height;
355   uint16 samples_per_pixel;
356   int tiled, error;
357   float xres, yres;
358   uint16 resunit;
359   int gotXres, gotYres;
360   uint16 photometric;
361   uint16 bits_per_sample;
362   uint16 planar_config;
363   uint16 inkset;
364   uint16 compress;
365   int i;
366   read_state_t state;
367   read_setup_t setupf = NULL;
368   read_getter_t getterf = NULL;
369   read_putter_t putterf = NULL;
370   int channels = MAXCHANNELS;
371   size_t sample_size = ~0; /* force failure if some code doesn't set it */
372   i_img_dim total_pixels;
373
374   error = 0;
375
376   TIFFGetField(tif, TIFFTAG_IMAGEWIDTH, &width);
377   TIFFGetField(tif, TIFFTAG_IMAGELENGTH, &height);
378   TIFFGetFieldDefaulted(tif, TIFFTAG_SAMPLESPERPIXEL, &samples_per_pixel);
379   tiled = TIFFIsTiled(tif);
380   TIFFGetFieldDefaulted(tif, TIFFTAG_PHOTOMETRIC, &photometric);
381   TIFFGetFieldDefaulted(tif, TIFFTAG_BITSPERSAMPLE, &bits_per_sample);
382   TIFFGetFieldDefaulted(tif, TIFFTAG_PLANARCONFIG, &planar_config);
383   TIFFGetFieldDefaulted(tif, TIFFTAG_INKSET, &inkset);
384
385   mm_log((1, "i_readtiff_wiol: width=%d, height=%d, channels=%d\n", width, height, samples_per_pixel));
386   mm_log((1, "i_readtiff_wiol: %stiled\n", tiled?"":"not "));
387   mm_log((1, "i_readtiff_wiol: %sbyte swapped\n", TIFFIsByteSwapped(tif)?"":"not "));
388
389   total_pixels = width * height;
390   memset(&state, 0, sizeof(state));
391   state.tif = tif;
392   state.allow_incomplete = allow_incomplete;
393   state.width = width;
394   state.height = height;
395   state.bits_per_sample = bits_per_sample;
396   state.samples_per_pixel = samples_per_pixel;
397   state.photometric = photometric;
398
399   /* yes, this if() is horrible */
400   if (photometric == PHOTOMETRIC_PALETTE && bits_per_sample <= 8) {
401     setupf = setup_paletted;
402     if (bits_per_sample == 8)
403       putterf = paletted_putter8;
404     else if (bits_per_sample == 4)
405       putterf = paletted_putter4;
406     else
407       mm_log((1, "unsupported paletted bits_per_sample %d\n", bits_per_sample));
408
409     sample_size = sizeof(i_sample_t);
410     channels = 1;
411   }
412   else if (bits_per_sample == 16 
413            && photometric == PHOTOMETRIC_RGB
414            && samples_per_pixel >= 3) {
415     setupf = setup_16_rgb;
416     putterf = putter_16;
417     sample_size = 2;
418     rgb_channels(&state, &channels);
419   }
420   else if (bits_per_sample == 16
421            && photometric == PHOTOMETRIC_MINISBLACK) {
422     setupf = setup_16_grey;
423     putterf = putter_16;
424     sample_size = 2;
425     grey_channels(&state, &channels);
426   }
427   else if (bits_per_sample == 8
428            && photometric == PHOTOMETRIC_MINISBLACK) {
429     setupf = setup_8_grey;
430     putterf = putter_8;
431     sample_size = 1;
432     grey_channels(&state, &channels);
433   }
434   else if (bits_per_sample == 8
435            && photometric == PHOTOMETRIC_RGB) {
436     setupf = setup_8_rgb;
437     putterf = putter_8;
438     sample_size = 1;
439     rgb_channels(&state, &channels);
440   }
441   else if (bits_per_sample == 32 
442            && photometric == PHOTOMETRIC_RGB
443            && samples_per_pixel >= 3) {
444     setupf = setup_32_rgb;
445     putterf = putter_32;
446     sample_size = sizeof(i_fsample_t);
447     rgb_channels(&state, &channels);
448   }
449   else if (bits_per_sample == 32
450            && photometric == PHOTOMETRIC_MINISBLACK) {
451     setupf = setup_32_grey;
452     putterf = putter_32;
453     sample_size = sizeof(i_fsample_t);
454     grey_channels(&state, &channels);
455   }
456   else if (bits_per_sample == 1
457            && (photometric == PHOTOMETRIC_MINISBLACK
458                || photometric == PHOTOMETRIC_MINISWHITE)
459            && samples_per_pixel == 1) {
460     setupf = setup_bilevel;
461     putterf = putter_bilevel;
462     sample_size = sizeof(i_palidx);
463     channels = 1;
464   }
465   else if (bits_per_sample == 8
466            && photometric == PHOTOMETRIC_SEPARATED
467            && inkset == INKSET_CMYK
468            && samples_per_pixel >= 4) {
469     setupf = setup_cmyk8;
470     putterf = putter_cmyk8;
471     sample_size = 1;
472     cmyk_channels(&state, &channels);
473   }
474   else if (bits_per_sample == 16
475            && photometric == PHOTOMETRIC_SEPARATED
476            && inkset == INKSET_CMYK
477            && samples_per_pixel >= 4) {
478     setupf = setup_cmyk16;
479     putterf = putter_cmyk16;
480     sample_size = 2;
481     cmyk_channels(&state, &channels);
482   }
483   else {
484     int alpha;
485     fallback_rgb_channels(tif, width, height, &channels, &alpha);
486     sample_size = 1;
487   }
488
489   if (!i_int_check_image_file_limits(width, height, channels, sample_size)) {
490     return NULL;
491   }
492
493   if (tiled) {
494     if (planar_config == PLANARCONFIG_CONTIG)
495       getterf = tile_contig_getter;
496   }
497   else {
498     if (planar_config == PLANARCONFIG_CONTIG)
499       getterf = strip_contig_getter;
500   }
501   if (setupf && getterf && putterf) {
502
503     if (!setupf(&state))
504       return NULL;
505     if (!getterf(&state, putterf) || !state.pixels_read) {
506       if (state.img)
507         i_img_destroy(state.img);
508       if (state.raster)
509         _TIFFfree(state.raster);
510       if (state.line_buf)
511         myfree(state.line_buf);
512       
513       return NULL;
514     }
515
516     if (allow_incomplete && state.pixels_read < total_pixels) {
517       i_tags_setn(&(state.img->tags), "i_incomplete", 1);
518       i_tags_setn(&(state.img->tags), "i_lines_read", 
519                   state.pixels_read / width);
520     }
521     im = state.img;
522     
523     if (state.raster)
524       _TIFFfree(state.raster);
525     if (state.line_buf)
526       myfree(state.line_buf);
527   }
528   else {
529     if (tiled) {
530       im = read_one_rgb_tiled(tif, width, height, allow_incomplete);
531     }
532     else {
533       im = read_one_rgb_lines(tif, width, height, allow_incomplete);
534     }
535   }
536
537   if (!im)
538     return NULL;
539
540   /* general metadata */
541   i_tags_setn(&im->tags, "tiff_bitspersample", bits_per_sample);
542   i_tags_setn(&im->tags, "tiff_photometric", photometric);
543   TIFFGetFieldDefaulted(tif, TIFFTAG_COMPRESSION, &compress);
544     
545   /* resolution tags */
546   TIFFGetFieldDefaulted(tif, TIFFTAG_RESOLUTIONUNIT, &resunit);
547   gotXres = TIFFGetField(tif, TIFFTAG_XRESOLUTION, &xres);
548   gotYres = TIFFGetField(tif, TIFFTAG_YRESOLUTION, &yres);
549   if (gotXres || gotYres) {
550     if (!gotXres)
551       xres = yres;
552     else if (!gotYres)
553       yres = xres;
554     i_tags_setn(&im->tags, "tiff_resolutionunit", resunit);
555     if (resunit == RESUNIT_CENTIMETER) {
556       /* from dots per cm to dpi */
557       xres *= 2.54;
558       yres *= 2.54;
559       i_tags_set(&im->tags, "tiff_resolutionunit_name", "centimeter", -1);
560     }
561     else if (resunit == RESUNIT_NONE) {
562       i_tags_setn(&im->tags, "i_aspect_only", 1);
563       i_tags_set(&im->tags, "tiff_resolutionunit_name", "none", -1);
564     }
565     else if (resunit == RESUNIT_INCH) {
566       i_tags_set(&im->tags, "tiff_resolutionunit_name", "inch", -1);
567     }
568     else {
569       i_tags_set(&im->tags, "tiff_resolutionunit_name", "unknown", -1);
570     }
571     /* tifflib doesn't seem to provide a way to get to the original rational
572        value of these, which would let me provide a more reasonable
573        precision. So make up a number. */
574     i_tags_set_float2(&im->tags, "i_xres", 0, xres, 6);
575     i_tags_set_float2(&im->tags, "i_yres", 0, yres, 6);
576   }
577
578   /* Text tags */
579   for (i = 0; i < text_tag_count; ++i) {
580     char *data;
581     if (TIFFGetField(tif, text_tag_names[i].tag, &data)) {
582       mm_log((1, "i_readtiff_wiol: tag %d has value %s\n", 
583               text_tag_names[i].tag, data));
584       i_tags_set(&im->tags, text_tag_names[i].name, data, -1);
585     }
586   }
587
588   i_tags_set(&im->tags, "i_format", "tiff", 4);
589 #ifdef USE_EXT_WARN_HANDLER
590   {
591     tiffio_context_t *ctx = TIFFClientdata(tif);
592     if (ctx->warn_buffer && ctx->warn_buffer[0]) {
593       i_tags_set(&im->tags, "i_warning", ctx->warn_buffer, -1);
594       ctx->warn_buffer[0] = '\0';
595     }
596   }
597 #else
598   if (warn_buffer && *warn_buffer) {
599     i_tags_set(&im->tags, "i_warning", warn_buffer, -1);
600     *warn_buffer = '\0';
601   }
602 #endif
603
604   for (i = 0; i < compress_value_count; ++i) {
605     if (compress_values[i].tag == compress) {
606       i_tags_set(&im->tags, "tiff_compression", compress_values[i].name, -1);
607       break;
608     }
609   }
610   
611   return im;
612 }
613
614 /*
615 =item i_readtiff_wiol(im, ig)
616
617 =cut
618 */
619 i_img*
620 i_readtiff_wiol(io_glue *ig, int allow_incomplete, int page) {
621   TIFF* tif;
622   TIFFErrorHandler old_handler;
623   TIFFErrorHandler old_warn_handler;
624 #ifdef USE_EXT_WARN_HANDLER
625   TIFFErrorHandlerExt old_ext_warn_handler;
626 #endif
627   i_img *im;
628   int current_page;
629   tiffio_context_t ctx;
630
631   i_mutex_lock(mutex);
632
633   i_clear_error();
634   old_handler = TIFFSetErrorHandler(error_handler);
635 #ifdef USE_EXT_WARN_HANDLER
636   old_warn_handler = TIFFSetWarningHandler(NULL);
637   old_ext_warn_handler = TIFFSetWarningHandlerExt(warn_handler_ex);
638 #else
639   old_warn_handler = TIFFSetWarningHandler(warn_handler);
640   if (warn_buffer)
641     *warn_buffer = '\0';
642 #endif
643
644   /* Add code to get the filename info from the iolayer */
645   /* Also add code to check for mmapped code */
646
647   mm_log((1, "i_readtiff_wiol(ig %p, allow_incomplete %d, page %d)\n", ig, allow_incomplete, page));
648   
649   tiffio_context_init(&ctx, ig);
650   tif = TIFFClientOpen("(Iolayer)", 
651                        "rm", 
652                        (thandle_t) &ctx,
653                        comp_read,
654                        comp_write,
655                        comp_seek,
656                        comp_close,
657                        sizeproc,
658                        comp_mmap,
659                        comp_munmap);
660   
661   if (!tif) {
662     mm_log((1, "i_readtiff_wiol: Unable to open tif file\n"));
663     i_push_error(0, "Error opening file");
664     TIFFSetErrorHandler(old_handler);
665     TIFFSetWarningHandler(old_warn_handler);
666 #ifdef USE_EXT_WARN_HANDLER
667     TIFFSetWarningHandlerExt(old_ext_warn_handler);
668 #endif
669     tiffio_context_final(&ctx);
670     i_mutex_unlock(mutex);
671     return NULL;
672   }
673
674   for (current_page = 0; current_page < page; ++current_page) {
675     if (!TIFFReadDirectory(tif)) {
676       mm_log((1, "i_readtiff_wiol: Unable to switch to directory %d\n", page));
677       i_push_errorf(0, "could not switch to page %d", page);
678       TIFFSetErrorHandler(old_handler);
679       TIFFSetWarningHandler(old_warn_handler);
680 #ifdef USE_EXT_WARN_HANDLER
681     TIFFSetWarningHandlerExt(old_ext_warn_handler);
682 #endif
683       TIFFClose(tif);
684       tiffio_context_final(&ctx);
685       i_mutex_unlock(mutex);
686       return NULL;
687     }
688   }
689
690   im = read_one_tiff(tif, allow_incomplete);
691
692   if (TIFFLastDirectory(tif)) mm_log((1, "Last directory of tiff file\n"));
693   TIFFSetErrorHandler(old_handler);
694   TIFFSetWarningHandler(old_warn_handler);
695 #ifdef USE_EXT_WARN_HANDLER
696     TIFFSetWarningHandlerExt(old_ext_warn_handler);
697 #endif
698   TIFFClose(tif);
699   tiffio_context_final(&ctx);
700     i_mutex_unlock(mutex);
701
702   return im;
703 }
704
705 /*
706 =item i_readtiff_multi_wiol(ig, *count)
707
708 Reads multiple images from a TIFF.
709
710 =cut
711 */
712 i_img**
713 i_readtiff_multi_wiol(io_glue *ig, int *count) {
714   TIFF* tif;
715   TIFFErrorHandler old_handler;
716   TIFFErrorHandler old_warn_handler;
717 #ifdef USE_EXT_WARN_HANDLER
718   TIFFErrorHandlerExt old_ext_warn_handler;
719 #endif
720   i_img **results = NULL;
721   int result_alloc = 0;
722   tiffio_context_t ctx;
723
724   i_mutex_lock(mutex);
725
726   i_clear_error();
727   old_handler = TIFFSetErrorHandler(error_handler);
728 #ifdef USE_EXT_WARN_HANDLER
729   old_warn_handler = TIFFSetWarningHandler(NULL);
730   old_ext_warn_handler = TIFFSetWarningHandlerExt(warn_handler_ex);
731 #else
732   old_warn_handler = TIFFSetWarningHandler(warn_handler);
733   if (warn_buffer)
734     *warn_buffer = '\0';
735 #endif
736
737   tiffio_context_init(&ctx, ig);
738
739   /* Add code to get the filename info from the iolayer */
740   /* Also add code to check for mmapped code */
741
742   mm_log((1, "i_readtiff_wiol(ig %p)\n", ig));
743   
744   tif = TIFFClientOpen("(Iolayer)", 
745                        "rm", 
746                        (thandle_t) &ctx,
747                        comp_read,
748                        comp_write,
749                        comp_seek,
750                        comp_close,
751                        sizeproc,
752                        comp_mmap,
753                        comp_munmap);
754   
755   if (!tif) {
756     mm_log((1, "i_readtiff_wiol: Unable to open tif file\n"));
757     i_push_error(0, "Error opening file");
758     TIFFSetErrorHandler(old_handler);
759     TIFFSetWarningHandler(old_warn_handler);
760 #ifdef USE_EXT_WARN_HANDLER
761     TIFFSetWarningHandlerExt(old_ext_warn_handler);
762 #endif
763     tiffio_context_final(&ctx);
764     i_mutex_unlock(mutex);
765     return NULL;
766   }
767
768   *count = 0;
769   do {
770     i_img *im = read_one_tiff(tif, 0);
771     if (!im)
772       break;
773     if (++*count > result_alloc) {
774       if (result_alloc == 0) {
775         result_alloc = 5;
776         results = mymalloc(result_alloc * sizeof(i_img *));
777       }
778       else {
779         i_img **newresults;
780         result_alloc *= 2;
781         newresults = myrealloc(results, result_alloc * sizeof(i_img *));
782         if (!newresults) {
783           i_img_destroy(im); /* don't leak it */
784           break;
785         }
786         results = newresults;
787       }
788     }
789     results[*count-1] = im;
790   } while (TIFFReadDirectory(tif));
791
792   TIFFSetWarningHandler(old_warn_handler);
793   TIFFSetErrorHandler(old_handler);
794 #ifdef USE_EXT_WARN_HANDLER
795     TIFFSetWarningHandlerExt(old_ext_warn_handler);
796 #endif
797   TIFFClose(tif);
798   tiffio_context_final(&ctx);
799   i_mutex_unlock(mutex);
800
801   return results;
802 }
803
804 undef_int
805 i_writetiff_low_faxable(TIFF *tif, i_img *im, int fine) {
806   uint32 width, height;
807   unsigned char *linebuf = NULL;
808   uint32 y;
809   int rc;
810   uint32 x;
811   uint32 rowsperstrip;
812   float vres = fine ? 196 : 98;
813   int luma_chan;
814
815   width    = im->xsize;
816   height   = im->ysize;
817
818   if (width != im->xsize || height != im->ysize) {
819     i_push_error(0, "image too large for TIFF");
820     return 0;
821   }
822
823   switch (im->channels) {
824   case 1:
825   case 2:
826     luma_chan = 0;
827     break;
828   case 3:
829   case 4:
830     luma_chan = 1;
831     break;
832   default:
833     /* This means a colorspace we don't handle yet */
834     mm_log((1, "i_writetiff_wiol_faxable: don't handle %d channel images.\n", im->channels));
835     return 0;
836   }
837
838   /* Add code to get the filename info from the iolayer */
839   /* Also add code to check for mmapped code */
840
841
842   mm_log((1, "i_writetiff_wiol_faxable: width=%d, height=%d, channels=%d\n", width, height, im->channels));
843   
844   if (!TIFFSetField(tif, TIFFTAG_IMAGEWIDTH,      width)   )
845     { mm_log((1, "i_writetiff_wiol_faxable: TIFFSetField width=%d failed\n", width)); return 0; }
846   if (!TIFFSetField(tif, TIFFTAG_IMAGELENGTH,     height)  )
847     { mm_log((1, "i_writetiff_wiol_faxable: TIFFSetField length=%d failed\n", height)); return 0; }
848   if (!TIFFSetField(tif, TIFFTAG_SAMPLESPERPIXEL, 1))
849     { mm_log((1, "i_writetiff_wiol_faxable: TIFFSetField samplesperpixel=1 failed\n")); return 0; }
850   if (!TIFFSetField(tif, TIFFTAG_ORIENTATION,  ORIENTATION_TOPLEFT))
851     { mm_log((1, "i_writetiff_wiol_faxable: TIFFSetField Orientation=topleft\n")); return 0; }
852   if (!TIFFSetField(tif, TIFFTAG_BITSPERSAMPLE,   1)        )
853     { mm_log((1, "i_writetiff_wiol_faxable: TIFFSetField bitpersample=1\n")); return 0; }
854   if (!TIFFSetField(tif, TIFFTAG_PLANARCONFIG, PLANARCONFIG_CONTIG))
855     { mm_log((1, "i_writetiff_wiol_faxable: TIFFSetField planarconfig\n")); return 0; }
856   if (!TIFFSetField(tif, TIFFTAG_PHOTOMETRIC, PHOTOMETRIC_MINISWHITE))
857     { mm_log((1, "i_writetiff_wiol_faxable: TIFFSetField photometric=%d\n", PHOTOMETRIC_MINISBLACK)); return 0; }
858   if (!TIFFSetField(tif, TIFFTAG_COMPRESSION, 3))
859     { mm_log((1, "i_writetiff_wiol_faxable: TIFFSetField compression=3\n")); return 0; }
860
861   linebuf = (unsigned char *)_TIFFmalloc( TIFFScanlineSize(tif) );
862   
863   if (!TIFFSetField(tif, TIFFTAG_ROWSPERSTRIP, TIFFDefaultStripSize(tif, -1))) {
864     mm_log((1, "i_writetiff_wiol_faxable: TIFFSetField rowsperstrip=-1\n")); return 0; }
865
866   TIFFGetField(tif, TIFFTAG_ROWSPERSTRIP, &rowsperstrip);
867   TIFFGetField(tif, TIFFTAG_ROWSPERSTRIP, &rc);
868
869   mm_log((1, "i_writetiff_wiol_faxable: TIFFGetField rowsperstrip=%d\n", rowsperstrip));
870   mm_log((1, "i_writetiff_wiol_faxable: TIFFGetField scanlinesize=%d\n", TIFFScanlineSize(tif) ));
871   mm_log((1, "i_writetiff_wiol_faxable: TIFFGetField planarconfig=%d == %d\n", rc, PLANARCONFIG_CONTIG));
872
873   if (!TIFFSetField(tif, TIFFTAG_XRESOLUTION, (float)204))
874     { mm_log((1, "i_writetiff_wiol_faxable: TIFFSetField Xresolution=204\n")); return 0; }
875   if (!TIFFSetField(tif, TIFFTAG_YRESOLUTION, vres))
876     { mm_log((1, "i_writetiff_wiol_faxable: TIFFSetField Yresolution=196\n")); return 0; }
877   if (!TIFFSetField(tif, TIFFTAG_RESOLUTIONUNIT, RESUNIT_INCH)) {
878     mm_log((1, "i_writetiff_wiol_faxable: TIFFSetField ResolutionUnit=%d\n", RESUNIT_INCH)); return 0; 
879   }
880
881   if (!save_tiff_tags(tif, im)) {
882     return 0;
883   }
884
885   for (y=0; y<height; y++) {
886     int linebufpos=0;
887     for(x=0; x<width; x+=8) { 
888       int bits;
889       int bitpos;
890       i_sample_t luma[8];
891       uint8 bitval = 128;
892       linebuf[linebufpos]=0;
893       bits = width-x; if(bits>8) bits=8;
894       i_gsamp(im, x, x+8, y, luma, &luma_chan, 1);
895       for(bitpos=0;bitpos<bits;bitpos++) {
896         linebuf[linebufpos] |= ((luma[bitpos] < 128) ? bitval : 0);
897         bitval >>= 1;
898       }
899       linebufpos++;
900     }
901     if (TIFFWriteScanline(tif, linebuf, y, 0) < 0) {
902       mm_log((1, "i_writetiff_wiol_faxable: TIFFWriteScanline failed.\n"));
903       break;
904     }
905   }
906   if (linebuf) _TIFFfree(linebuf);
907
908   return 1;
909 }
910
911 static uint16
912 find_compression(char const *name, uint16 *compress) {
913   int i;
914
915   for (i = 0; i < compress_value_count; ++i) {
916     if (strcmp(compress_values[i].name, name) == 0) {
917       *compress = (uint16)compress_values[i].tag;
918       return 1;
919     }
920   }
921   *compress = COMPRESSION_NONE;
922
923   return 0;
924 }
925
926 static uint16
927 get_compression(i_img *im, uint16 def_compress) {
928   int entry;
929   int value;
930
931   if (i_tags_find(&im->tags, "tiff_compression", 0, &entry)
932       && im->tags.tags[entry].data) {
933     uint16 compress;
934     if (find_compression(im->tags.tags[entry].data, &compress)
935         && myTIFFIsCODECConfigured(compress))
936       return compress;
937   }
938   if (i_tags_get_int(&im->tags, "tiff_compression", 0, &value)) {
939     if ((uint16)value == value
940         && myTIFFIsCODECConfigured((uint16)value))
941       return (uint16)value;
942   }
943
944   return def_compress;
945 }
946
947 int
948 i_tiff_has_compression(const char *name) {
949   uint16 compress;
950
951   if (!find_compression(name, &compress))
952     return 0;
953
954   return myTIFFIsCODECConfigured(compress);
955 }
956
957 static int
958 set_base_tags(TIFF *tif, i_img *im, uint16 compress, uint16 photometric, 
959               uint16 bits_per_sample, uint16 samples_per_pixel) {
960   double xres, yres;
961   int resunit;
962   int got_xres, got_yres;
963   int aspect_only;
964
965   if (!TIFFSetField(tif, TIFFTAG_IMAGEWIDTH, im->xsize)) {
966     i_push_error(0, "write TIFF: setting width tag");
967     return 0;
968   }
969   if (!TIFFSetField(tif, TIFFTAG_IMAGELENGTH, im->ysize)) {
970     i_push_error(0, "write TIFF: setting length tag");
971     return 0;
972   }
973   if (!TIFFSetField(tif, TIFFTAG_ORIENTATION, ORIENTATION_TOPLEFT)) {
974     i_push_error(0, "write TIFF: setting orientation tag");
975     return 0;
976   }
977   if (!TIFFSetField(tif, TIFFTAG_PLANARCONFIG, PLANARCONFIG_CONTIG)) {
978     i_push_error(0, "write TIFF: setting planar configuration tag");
979     return 0;
980   }
981   if (!TIFFSetField(tif, TIFFTAG_PHOTOMETRIC, photometric)) {
982     i_push_error(0, "write TIFF: setting photometric tag");
983     return 0;
984   }
985   if (!TIFFSetField(tif, TIFFTAG_COMPRESSION, compress)) {
986     i_push_error(0, "write TIFF: setting compression tag");
987     return 0;
988   }
989   if (!TIFFSetField(tif, TIFFTAG_BITSPERSAMPLE, bits_per_sample)) {
990     i_push_error(0, "write TIFF: setting bits per sample tag");
991     return 0;
992   }
993   if (!TIFFSetField(tif, TIFFTAG_SAMPLESPERPIXEL, samples_per_pixel)) {
994     i_push_error(0, "write TIFF: setting samples per pixel tag");
995     return 0;
996   }
997
998   got_xres = i_tags_get_float(&im->tags, "i_xres", 0, &xres);
999   got_yres = i_tags_get_float(&im->tags, "i_yres", 0, &yres);
1000   if (!i_tags_get_int(&im->tags, "i_aspect_only", 0,&aspect_only))
1001     aspect_only = 0;
1002   if (!i_tags_get_int(&im->tags, "tiff_resolutionunit", 0, &resunit))
1003     resunit = RESUNIT_INCH;
1004   if (got_xres || got_yres) {
1005     if (!got_xres)
1006       xres = yres;
1007     else if (!got_yres)
1008       yres = xres;
1009     if (aspect_only) {
1010       resunit = RESUNIT_NONE;
1011     }
1012     else {
1013       if (resunit == RESUNIT_CENTIMETER) {
1014         xres /= 2.54;
1015         yres /= 2.54;
1016       }
1017       else {
1018         resunit  = RESUNIT_INCH;
1019       }
1020     }
1021     if (!TIFFSetField(tif, TIFFTAG_XRESOLUTION, (float)xres)) {
1022       i_push_error(0, "write TIFF: setting xresolution tag");
1023       return 0;
1024     }
1025     if (!TIFFSetField(tif, TIFFTAG_YRESOLUTION, (float)yres)) {
1026       i_push_error(0, "write TIFF: setting yresolution tag");
1027       return 0;
1028     }
1029     if (!TIFFSetField(tif, TIFFTAG_RESOLUTIONUNIT, (uint16)resunit)) {
1030       i_push_error(0, "write TIFF: setting resolutionunit tag");
1031       return 0;
1032     }
1033   }
1034
1035   return 1;
1036 }
1037
1038 static int 
1039 write_one_bilevel(TIFF *tif, i_img *im, int zero_is_white) {
1040   uint16 compress = get_compression(im, COMPRESSION_PACKBITS);
1041   uint16 photometric;
1042   unsigned char *in_row;
1043   unsigned char *out_row;
1044   unsigned out_size;
1045   i_img_dim x, y;
1046   int invert;
1047
1048   mm_log((1, "tiff - write_one_bilevel(tif %p, im %p, zero_is_white %d)\n", 
1049           tif, im, zero_is_white));
1050
1051   /* ignore a silly choice */
1052   if (compress == COMPRESSION_JPEG)
1053     compress = COMPRESSION_PACKBITS;
1054
1055   switch (compress) {
1056   case COMPRESSION_CCITTRLE:
1057   case COMPRESSION_CCITTFAX3:
1058   case COMPRESSION_CCITTFAX4:
1059     /* natural fax photometric */
1060     photometric = PHOTOMETRIC_MINISWHITE;
1061     break;
1062
1063   default:
1064     /* natural for most computer images */
1065     photometric = PHOTOMETRIC_MINISBLACK;
1066     break;
1067   }
1068
1069   if (!set_base_tags(tif, im, compress, photometric, 1, 1))
1070     return 0;
1071
1072   if (!TIFFSetField(tif, TIFFTAG_ROWSPERSTRIP, TIFFDefaultStripSize(tif, -1))) {
1073     i_push_error(0, "write TIFF: setting rows per strip tag");
1074     return 0; 
1075   }
1076
1077   out_size = TIFFScanlineSize(tif);
1078   out_row = (unsigned char *)_TIFFmalloc( out_size );
1079   in_row = mymalloc(im->xsize);
1080
1081   invert = (photometric == PHOTOMETRIC_MINISWHITE) != (zero_is_white != 0);
1082
1083   for (y = 0; y < im->ysize; ++y) {
1084     int mask = 0x80;
1085     unsigned char *outp = out_row;
1086     memset(out_row, 0, out_size);
1087     i_gpal(im, 0, im->xsize, y, in_row);
1088     for (x = 0; x < im->xsize; ++x) {
1089       if (invert ? !in_row[x] : in_row[x]) {
1090         *outp |= mask;
1091       }
1092       mask >>= 1;
1093       if (!mask) {
1094         ++outp;
1095         mask = 0x80;
1096       }
1097     }
1098     if (TIFFWriteScanline(tif, out_row, y, 0) < 0) {
1099       _TIFFfree(out_row);
1100       myfree(in_row);
1101       i_push_error(0, "write TIFF: write scan line failed");
1102       return 0;
1103     }
1104   }
1105
1106   _TIFFfree(out_row);
1107   myfree(in_row);
1108
1109   return 1;
1110 }
1111
1112 static int
1113 set_palette(TIFF *tif, i_img *im, int size) {
1114   int count;
1115   uint16 *colors;
1116   uint16 *out[3];
1117   i_color c;
1118   int i, ch;
1119   
1120   colors = (uint16 *)_TIFFmalloc(sizeof(uint16) * 3 * size);
1121   out[0] = colors;
1122   out[1] = colors + size;
1123   out[2] = colors + 2 * size;
1124     
1125   count = i_colorcount(im);
1126   for (i = 0; i < count; ++i) {
1127     i_getcolors(im, i, &c, 1);
1128     for (ch = 0; ch < 3; ++ch)
1129       out[ch][i] = c.channel[ch] * 257;
1130   }
1131   for (; i < size; ++i) {
1132     for (ch = 0; ch < 3; ++ch)
1133       out[ch][i] = 0;
1134   }
1135   if (!TIFFSetField(tif, TIFFTAG_COLORMAP, out[0], out[1], out[2])) {
1136     _TIFFfree(colors);
1137     i_push_error(0, "write TIFF: setting color map");
1138     return 0;
1139   }
1140   _TIFFfree(colors);
1141   
1142   return 1;
1143 }
1144
1145 static int
1146 write_one_paletted8(TIFF *tif, i_img *im) {
1147   uint16 compress = get_compression(im, COMPRESSION_PACKBITS);
1148   unsigned char *out_row;
1149   unsigned out_size;
1150   i_img_dim y;
1151
1152   mm_log((1, "tiff - write_one_paletted8(tif %p, im %p)\n", tif, im));
1153
1154   /* ignore a silly choice */
1155   if (compress == COMPRESSION_JPEG ||
1156       compress == COMPRESSION_CCITTRLE ||
1157       compress == COMPRESSION_CCITTFAX3 ||
1158       compress == COMPRESSION_CCITTFAX4)
1159     compress = COMPRESSION_PACKBITS;
1160
1161   if (!TIFFSetField(tif, TIFFTAG_ROWSPERSTRIP, TIFFDefaultStripSize(tif, -1))) {
1162     i_push_error(0, "write TIFF: setting rows per strip tag");
1163     return 0; 
1164   }
1165
1166   if (!set_base_tags(tif, im, compress, PHOTOMETRIC_PALETTE, 8, 1))
1167     return 0;
1168
1169   if (!set_palette(tif, im, 256))
1170     return 0;
1171
1172   out_size = TIFFScanlineSize(tif);
1173   out_row = (unsigned char *)_TIFFmalloc( out_size );
1174
1175   for (y = 0; y < im->ysize; ++y) {
1176     i_gpal(im, 0, im->xsize, y, out_row);
1177     if (TIFFWriteScanline(tif, out_row, y, 0) < 0) {
1178       _TIFFfree(out_row);
1179       i_push_error(0, "write TIFF: write scan line failed");
1180       return 0;
1181     }
1182   }
1183
1184   _TIFFfree(out_row);
1185
1186   return 1;
1187 }
1188
1189 static int
1190 write_one_paletted4(TIFF *tif, i_img *im) {
1191   uint16 compress = get_compression(im, COMPRESSION_PACKBITS);
1192   unsigned char *in_row;
1193   unsigned char *out_row;
1194   size_t out_size;
1195   i_img_dim y;
1196
1197   mm_log((1, "tiff - write_one_paletted4(tif %p, im %p)\n", tif, im));
1198
1199   /* ignore a silly choice */
1200   if (compress == COMPRESSION_JPEG ||
1201       compress == COMPRESSION_CCITTRLE ||
1202       compress == COMPRESSION_CCITTFAX3 ||
1203       compress == COMPRESSION_CCITTFAX4)
1204     compress = COMPRESSION_PACKBITS;
1205
1206   if (!set_base_tags(tif, im, compress, PHOTOMETRIC_PALETTE, 4, 1))
1207     return 0;
1208
1209   if (!set_palette(tif, im, 16))
1210     return 0;
1211
1212   if (!TIFFSetField(tif, TIFFTAG_ROWSPERSTRIP, TIFFDefaultStripSize(tif, -1))) {
1213     i_push_error(0, "write TIFF: setting rows per strip tag");
1214     return 0; 
1215   }
1216
1217   in_row = mymalloc(im->xsize);
1218   out_size = TIFFScanlineSize(tif);
1219   out_row = (unsigned char *)_TIFFmalloc( out_size );
1220
1221   for (y = 0; y < im->ysize; ++y) {
1222     i_gpal(im, 0, im->xsize, y, in_row);
1223     memset(out_row, 0, out_size);
1224     pack_4bit_to(out_row, in_row, im->xsize);
1225     if (TIFFWriteScanline(tif, out_row, y, 0) < 0) {
1226       _TIFFfree(out_row);
1227       i_push_error(0, "write TIFF: write scan line failed");
1228       return 0;
1229     }
1230   }
1231
1232   myfree(in_row);
1233   _TIFFfree(out_row);
1234
1235   return 1;
1236 }
1237
1238 static int
1239 set_direct_tags(TIFF *tif, i_img *im, uint16 compress, 
1240                 uint16 bits_per_sample) {
1241   uint16 extras = EXTRASAMPLE_ASSOCALPHA;
1242   uint16 extra_count = im->channels == 2 || im->channels == 4;
1243   uint16 photometric = im->channels >= 3 ? 
1244     PHOTOMETRIC_RGB : PHOTOMETRIC_MINISBLACK;
1245
1246   if (!set_base_tags(tif, im, compress, photometric, bits_per_sample, 
1247                      im->channels)) {
1248     return 0;
1249   }
1250   
1251   if (extra_count) {
1252     if (!TIFFSetField(tif, TIFFTAG_EXTRASAMPLES, extra_count, &extras)) {
1253       i_push_error(0, "write TIFF: setting extra samples tag");
1254       return 0;
1255     }
1256   }
1257
1258   if (compress == COMPRESSION_JPEG) {
1259     int jpeg_quality;
1260     if (i_tags_get_int(&im->tags, "tiff_jpegquality", 0, &jpeg_quality)
1261         && jpeg_quality >= 0 && jpeg_quality <= 100) {
1262       if (!TIFFSetField(tif, TIFFTAG_JPEGQUALITY, jpeg_quality)) {
1263         i_push_error(0, "write TIFF: setting jpeg quality pseudo-tag");
1264         return 0;
1265       }
1266     }
1267   }
1268
1269   return 1;
1270 }
1271
1272 static int 
1273 write_one_32(TIFF *tif, i_img *im) {
1274   uint16 compress = get_compression(im, COMPRESSION_PACKBITS);
1275   unsigned *in_row;
1276   size_t out_size;
1277   uint32 *out_row;
1278   i_img_dim y;
1279   size_t sample_count = im->xsize * im->channels;
1280   size_t sample_index;
1281     
1282   mm_log((1, "tiff - write_one_32(tif %p, im %p)\n", tif, im));
1283
1284   /* only 8 and 12 bit samples are supported by jpeg compression */
1285   if (compress == COMPRESSION_JPEG)
1286     compress = COMPRESSION_PACKBITS;
1287
1288   if (!set_direct_tags(tif, im, compress, 32))
1289     return 0;
1290
1291   in_row = mymalloc(sample_count * sizeof(unsigned));
1292   out_size = TIFFScanlineSize(tif);
1293   out_row = (uint32 *)_TIFFmalloc( out_size );
1294
1295   for (y = 0; y < im->ysize; ++y) {
1296     if (i_gsamp_bits(im, 0, im->xsize, y, in_row, NULL, im->channels, 32) <= 0) {
1297       i_push_error(0, "Cannot read 32-bit samples");
1298       return 0;
1299     }
1300     for (sample_index = 0; sample_index < sample_count; ++sample_index)
1301       out_row[sample_index] = in_row[sample_index];
1302     if (TIFFWriteScanline(tif, out_row, y, 0) < 0) {
1303       myfree(in_row);
1304       _TIFFfree(out_row);
1305       i_push_error(0, "write TIFF: write scan line failed");
1306       return 0;
1307     }
1308   }
1309
1310   myfree(in_row);
1311   _TIFFfree(out_row);
1312   
1313   return 1;
1314 }
1315
1316 static int 
1317 write_one_16(TIFF *tif, i_img *im) {
1318   uint16 compress = get_compression(im, COMPRESSION_PACKBITS);
1319   unsigned *in_row;
1320   size_t out_size;
1321   uint16 *out_row;
1322   i_img_dim y;
1323   size_t sample_count = im->xsize * im->channels;
1324   size_t sample_index;
1325     
1326   mm_log((1, "tiff - write_one_16(tif %p, im %p)\n", tif, im));
1327
1328   /* only 8 and 12 bit samples are supported by jpeg compression */
1329   if (compress == COMPRESSION_JPEG)
1330     compress = COMPRESSION_PACKBITS;
1331
1332   if (!set_direct_tags(tif, im, compress, 16))
1333     return 0;
1334
1335   in_row = mymalloc(sample_count * sizeof(unsigned));
1336   out_size = TIFFScanlineSize(tif);
1337   out_row = (uint16 *)_TIFFmalloc( out_size );
1338
1339   for (y = 0; y < im->ysize; ++y) {
1340     if (i_gsamp_bits(im, 0, im->xsize, y, in_row, NULL, im->channels, 16) <= 0) {
1341       i_push_error(0, "Cannot read 16-bit samples");
1342       return 0;
1343     }
1344     for (sample_index = 0; sample_index < sample_count; ++sample_index)
1345       out_row[sample_index] = in_row[sample_index];
1346     if (TIFFWriteScanline(tif, out_row, y, 0) < 0) {
1347       myfree(in_row);
1348       _TIFFfree(out_row);
1349       i_push_error(0, "write TIFF: write scan line failed");
1350       return 0;
1351     }
1352   }
1353
1354   myfree(in_row);
1355   _TIFFfree(out_row);
1356   
1357   return 1;
1358 }
1359
1360 static int 
1361 write_one_8(TIFF *tif, i_img *im) {
1362   uint16 compress = get_compression(im, COMPRESSION_PACKBITS);
1363   size_t out_size;
1364   unsigned char *out_row;
1365   i_img_dim y;
1366   size_t sample_count = im->xsize * im->channels;
1367     
1368   mm_log((1, "tiff - write_one_8(tif %p, im %p)\n", tif, im));
1369
1370   if (!set_direct_tags(tif, im, compress, 8))
1371     return 0;
1372
1373   out_size = TIFFScanlineSize(tif);
1374   if (out_size < sample_count)
1375     out_size = sample_count;
1376   out_row = (unsigned char *)_TIFFmalloc( out_size );
1377
1378   for (y = 0; y < im->ysize; ++y) {
1379     if (i_gsamp(im, 0, im->xsize, y, out_row, NULL, im->channels) <= 0) {
1380       i_push_error(0, "Cannot read 8-bit samples");
1381       return 0;
1382     }
1383     if (TIFFWriteScanline(tif, out_row, y, 0) < 0) {
1384       _TIFFfree(out_row);
1385       i_push_error(0, "write TIFF: write scan line failed");
1386       return 0;
1387     }
1388   }
1389   _TIFFfree(out_row);
1390   
1391   return 1;
1392 }
1393
1394 static int
1395 i_writetiff_low(TIFF *tif, i_img *im) {
1396   uint32 width, height;
1397   uint16 channels;
1398   int zero_is_white;
1399
1400   width    = im->xsize;
1401   height   = im->ysize;
1402   channels = im->channels;
1403
1404   if (width != im->xsize || height != im->ysize) {
1405     i_push_error(0, "image too large for TIFF");
1406     return 0;
1407   }
1408
1409   mm_log((1, "i_writetiff_low: width=%d, height=%d, channels=%d, bits=%d\n", width, height, channels, im->bits));
1410   if (im->type == i_palette_type) {
1411     mm_log((1, "i_writetiff_low: paletted, colors=%d\n", i_colorcount(im)));
1412   }
1413   
1414   if (i_img_is_monochrome(im, &zero_is_white)) {
1415     if (!write_one_bilevel(tif, im, zero_is_white))
1416       return 0;
1417   }
1418   else if (im->type == i_palette_type) {
1419     if (i_colorcount(im) <= 16) {
1420       if (!write_one_paletted4(tif, im))
1421         return 0;
1422     }
1423     else {
1424       if (!write_one_paletted8(tif, im))
1425         return 0;
1426     }
1427   }
1428   else if (im->bits > 16) {
1429     if (!write_one_32(tif, im))
1430       return 0;
1431   }
1432   else if (im->bits > 8) {
1433     if (!write_one_16(tif, im))
1434       return 0;
1435   }
1436   else {
1437     if (!write_one_8(tif, im))
1438       return 0;
1439   }
1440
1441   if (!save_tiff_tags(tif, im))
1442     return 0;
1443
1444   return 1;
1445 }
1446
1447 /*
1448 =item i_writetiff_multi_wiol(ig, imgs, count, fine_mode)
1449
1450 Stores an image in the iolayer object.
1451
1452    ig - io_object that defines source to write to 
1453    imgs,count - the images to write
1454
1455 =cut 
1456 */
1457
1458 undef_int
1459 i_writetiff_multi_wiol(io_glue *ig, i_img **imgs, int count) {
1460   TIFF* tif;
1461   TIFFErrorHandler old_handler;
1462   int i;
1463   tiffio_context_t ctx;
1464
1465   i_mutex_lock(mutex);
1466
1467   old_handler = TIFFSetErrorHandler(error_handler);
1468
1469   i_clear_error();
1470   mm_log((1, "i_writetiff_multi_wiol(ig %p, imgs %p, count %d)\n", 
1471           ig, imgs, count));
1472
1473   tiffio_context_init(&ctx, ig);
1474   
1475   tif = TIFFClientOpen("No name", 
1476                        "wm",
1477                        (thandle_t) &ctx, 
1478                        comp_read,
1479                        comp_write,
1480                        comp_seek,
1481                        comp_close, 
1482                        sizeproc,
1483                        comp_mmap,
1484                        comp_munmap);
1485   
1486
1487
1488   if (!tif) {
1489     mm_log((1, "i_writetiff_multi_wiol: Unable to open tif file for writing\n"));
1490     i_push_error(0, "Could not create TIFF object");
1491     TIFFSetErrorHandler(old_handler);
1492     tiffio_context_final(&ctx);
1493     i_mutex_unlock(mutex);
1494     return 0;
1495   }
1496
1497   for (i = 0; i < count; ++i) {
1498     if (!i_writetiff_low(tif, imgs[i])) {
1499       TIFFClose(tif);
1500       TIFFSetErrorHandler(old_handler);
1501       tiffio_context_final(&ctx);
1502       i_mutex_unlock(mutex);
1503       return 0;
1504     }
1505
1506     if (!TIFFWriteDirectory(tif)) {
1507       i_push_error(0, "Cannot write TIFF directory");
1508       TIFFClose(tif);
1509       TIFFSetErrorHandler(old_handler);
1510       tiffio_context_final(&ctx);
1511       i_mutex_unlock(mutex);
1512       return 0;
1513     }
1514   }
1515
1516   TIFFSetErrorHandler(old_handler);
1517   (void) TIFFClose(tif);
1518   tiffio_context_final(&ctx);
1519
1520   i_mutex_unlock(mutex);
1521
1522   if (i_io_close(ig))
1523     return 0;
1524
1525   return 1;
1526 }
1527
1528 /*
1529 =item i_writetiff_multi_wiol_faxable(ig, imgs, count, fine_mode)
1530
1531 Stores an image in the iolayer object.
1532
1533    ig - io_object that defines source to write to 
1534    imgs,count - the images to write
1535    fine_mode - select fine or normal mode fax images
1536
1537 =cut 
1538 */
1539
1540
1541 undef_int
1542 i_writetiff_multi_wiol_faxable(io_glue *ig, i_img **imgs, int count, int fine) {
1543   TIFF* tif;
1544   int i;
1545   TIFFErrorHandler old_handler;
1546   tiffio_context_t ctx;
1547
1548   i_mutex_lock(mutex);
1549
1550   old_handler = TIFFSetErrorHandler(error_handler);
1551
1552   i_clear_error();
1553   mm_log((1, "i_writetiff_multi_wiol(ig %p, imgs %p, count %d)\n", 
1554           ig, imgs, count));
1555
1556   tiffio_context_init(&ctx, ig);
1557   
1558   tif = TIFFClientOpen("No name", 
1559                        "wm",
1560                        (thandle_t) &ctx, 
1561                        comp_read,
1562                        comp_write,
1563                        comp_seek,
1564                        comp_close, 
1565                        sizeproc,
1566                        comp_mmap,
1567                        comp_munmap);
1568   
1569
1570
1571   if (!tif) {
1572     mm_log((1, "i_writetiff_mulit_wiol: Unable to open tif file for writing\n"));
1573     i_push_error(0, "Could not create TIFF object");
1574     TIFFSetErrorHandler(old_handler);
1575     tiffio_context_final(&ctx);
1576     i_mutex_unlock(mutex);
1577     return 0;
1578   }
1579
1580   for (i = 0; i < count; ++i) {
1581     if (!i_writetiff_low_faxable(tif, imgs[i], fine)) {
1582       TIFFClose(tif);
1583       TIFFSetErrorHandler(old_handler);
1584       tiffio_context_final(&ctx);
1585       i_mutex_unlock(mutex);
1586       return 0;
1587     }
1588
1589     if (!TIFFWriteDirectory(tif)) {
1590       i_push_error(0, "Cannot write TIFF directory");
1591       TIFFClose(tif);
1592       TIFFSetErrorHandler(old_handler);
1593       tiffio_context_final(&ctx);
1594       i_mutex_unlock(mutex);
1595       return 0;
1596     }
1597   }
1598
1599   (void) TIFFClose(tif);
1600   TIFFSetErrorHandler(old_handler);
1601   tiffio_context_final(&ctx);
1602
1603   i_mutex_unlock(mutex);
1604
1605   if (i_io_close(ig))
1606     return 0;
1607
1608   return 1;
1609 }
1610
1611 /*
1612 =item i_writetiff_wiol(im, ig)
1613
1614 Stores an image in the iolayer object.
1615
1616    im - image object to write out
1617    ig - io_object that defines source to write to 
1618
1619 =cut 
1620 */
1621 undef_int
1622 i_writetiff_wiol(i_img *img, io_glue *ig) {
1623   TIFF* tif;
1624   TIFFErrorHandler old_handler;
1625   tiffio_context_t ctx;
1626
1627   i_mutex_lock(mutex);
1628
1629   old_handler = TIFFSetErrorHandler(error_handler);
1630
1631   i_clear_error();
1632   mm_log((1, "i_writetiff_wiol(img %p, ig %p)\n", img, ig));
1633
1634   tiffio_context_init(&ctx, ig);
1635
1636   tif = TIFFClientOpen("No name", 
1637                        "wm",
1638                        (thandle_t) &ctx, 
1639                        comp_read,
1640                        comp_write,
1641                        comp_seek,
1642                        comp_close, 
1643                        sizeproc,
1644                        comp_mmap,
1645                        comp_munmap);
1646   
1647
1648
1649   if (!tif) {
1650     mm_log((1, "i_writetiff_wiol: Unable to open tif file for writing\n"));
1651     i_push_error(0, "Could not create TIFF object");
1652     tiffio_context_final(&ctx);
1653     TIFFSetErrorHandler(old_handler);
1654     i_mutex_unlock(mutex);
1655     return 0;
1656   }
1657
1658   if (!i_writetiff_low(tif, img)) {
1659     TIFFClose(tif);
1660     tiffio_context_final(&ctx);
1661     TIFFSetErrorHandler(old_handler);
1662     i_mutex_unlock(mutex);
1663     return 0;
1664   }
1665
1666   (void) TIFFClose(tif);
1667   TIFFSetErrorHandler(old_handler);
1668   tiffio_context_final(&ctx);
1669   i_mutex_unlock(mutex);
1670
1671   if (i_io_close(ig))
1672     return 0;
1673
1674   return 1;
1675 }
1676
1677
1678
1679 /*
1680 =item i_writetiff_wiol_faxable(i_img *, io_glue *)
1681
1682 Stores an image in the iolayer object in faxable tiff format.
1683
1684    im - image object to write out
1685    ig - io_object that defines source to write to 
1686
1687 Note, this may be rewritten to use to simply be a call to a
1688 lower-level function that gives more options for writing tiff at some
1689 point.
1690
1691 =cut
1692 */
1693
1694 undef_int
1695 i_writetiff_wiol_faxable(i_img *im, io_glue *ig, int fine) {
1696   TIFF* tif;
1697   TIFFErrorHandler old_handler;
1698   tiffio_context_t ctx;
1699
1700   i_mutex_lock(mutex);
1701
1702   old_handler = TIFFSetErrorHandler(error_handler);
1703
1704   i_clear_error();
1705   mm_log((1, "i_writetiff_wiol(img %p, ig %p)\n", im, ig));
1706
1707   tiffio_context_init(&ctx, ig);
1708   
1709   tif = TIFFClientOpen("No name", 
1710                        "wm",
1711                        (thandle_t) &ctx, 
1712                        comp_read,
1713                        comp_write,
1714                        comp_seek,
1715                        comp_close, 
1716                        sizeproc,
1717                        comp_mmap,
1718                        comp_munmap);
1719   
1720
1721
1722   if (!tif) {
1723     mm_log((1, "i_writetiff_wiol: Unable to open tif file for writing\n"));
1724     i_push_error(0, "Could not create TIFF object");
1725     TIFFSetErrorHandler(old_handler);
1726     tiffio_context_final(&ctx);
1727     i_mutex_unlock(mutex);
1728     return 0;
1729   }
1730
1731   if (!i_writetiff_low_faxable(tif, im, fine)) {
1732     TIFFClose(tif);
1733     TIFFSetErrorHandler(old_handler);
1734     tiffio_context_final(&ctx);
1735     i_mutex_unlock(mutex);
1736     return 0;
1737   }
1738
1739   (void) TIFFClose(tif);
1740   TIFFSetErrorHandler(old_handler);
1741   tiffio_context_final(&ctx);
1742   i_mutex_unlock(mutex);
1743
1744   if (i_io_close(ig))
1745     return 0;
1746
1747   return 1;
1748 }
1749
1750 static int save_tiff_tags(TIFF *tif, i_img *im) {
1751   int i;
1752  
1753   for (i = 0; i < text_tag_count; ++i) {
1754     int entry;
1755     if (i_tags_find(&im->tags, text_tag_names[i].name, 0, &entry)) {
1756       if (!TIFFSetField(tif, text_tag_names[i].tag, 
1757                        im->tags.tags[entry].data)) {
1758        i_push_errorf(0, "cannot save %s to TIFF", text_tag_names[i].name);
1759        return 0;
1760       }
1761     }
1762   }
1763
1764   return 1;
1765 }
1766
1767
1768 static void
1769 unpack_4bit_to(unsigned char *dest, const unsigned char *src, 
1770                size_t src_byte_count) {
1771   while (src_byte_count > 0) {
1772     *dest++ = *src >> 4;
1773     *dest++ = *src++ & 0xf;
1774     --src_byte_count;
1775   }
1776 }
1777
1778 static void pack_4bit_to(unsigned char *dest, const unsigned char *src, 
1779                          i_img_dim pixel_count) {
1780   int i = 0;
1781   while (i < pixel_count) {
1782     if ((i & 1) == 0) {
1783       *dest = *src++ << 4;
1784     }
1785     else {
1786       *dest++ |= *src++;
1787     }
1788     ++i;
1789   }
1790 }
1791
1792 /*
1793 =item fallback_rgb_channels
1794
1795 Calculate the number of output channels when we fallback to the RGBA
1796 family of functions.
1797
1798 =cut
1799 */
1800
1801 static void
1802 fallback_rgb_channels(TIFF *tif, i_img_dim width, i_img_dim height, int *channels, int *alpha_chan) {
1803   uint16 photometric;
1804   uint16 in_channels;
1805   uint16 extra_count;
1806   uint16 *extras;
1807
1808   TIFFGetFieldDefaulted(tif, TIFFTAG_SAMPLESPERPIXEL, &in_channels);
1809   TIFFGetFieldDefaulted(tif, TIFFTAG_PHOTOMETRIC, &photometric);
1810
1811   switch (photometric) {
1812   case PHOTOMETRIC_SEPARATED:
1813     *channels = 3;
1814     break;
1815   
1816   case PHOTOMETRIC_MINISWHITE:
1817   case PHOTOMETRIC_MINISBLACK:
1818     /* the TIFF RGBA functions expand single channel grey into RGB,
1819        so reduce it, we move the alpha channel into the right place 
1820        if needed */
1821     *channels = 1;
1822     break;
1823
1824   default:
1825     *channels = 3;
1826     break;
1827   }
1828   /* TIFF images can have more than one alpha channel, but Imager can't
1829      this ignores the possibility of 2 channel images with 2 alpha,
1830      but there's not much I can do about that */
1831   *alpha_chan = 0;
1832   if (TIFFGetField(tif, TIFFTAG_EXTRASAMPLES, &extra_count, &extras)
1833       && extra_count) {
1834     *alpha_chan = (*channels)++;
1835   }
1836 }
1837
1838 static i_img *
1839 make_rgb(TIFF *tif, i_img_dim width, i_img_dim height, int *alpha_chan) {
1840   int channels = 0;
1841
1842   fallback_rgb_channels(tif, width, height, &channels, alpha_chan);
1843
1844   return i_img_8_new(width, height, channels);
1845 }
1846
1847 static i_img *
1848 read_one_rgb_lines(TIFF *tif, i_img_dim width, i_img_dim height, int allow_incomplete) {
1849   i_img *im;
1850   uint32* raster = NULL;
1851   uint32 rowsperstrip, row;
1852   i_color *line_buf;
1853   int alpha_chan;
1854   int rc;
1855
1856   im = make_rgb(tif, width, height, &alpha_chan);
1857   if (!im)
1858     return NULL;
1859
1860   rc = TIFFGetField(tif, TIFFTAG_ROWSPERSTRIP, &rowsperstrip);
1861   mm_log((1, "i_readtiff_wiol: rowsperstrip=%d rc = %d\n", rowsperstrip, rc));
1862   
1863   if (rc != 1 || rowsperstrip==-1) {
1864     rowsperstrip = height;
1865   }
1866   
1867   raster = (uint32*)_TIFFmalloc(width * rowsperstrip * sizeof (uint32));
1868   if (!raster) {
1869     i_img_destroy(im);
1870     i_push_error(0, "No space for raster buffer");
1871     return NULL;
1872   }
1873
1874   line_buf = mymalloc(sizeof(i_color) * width);
1875   
1876   for( row = 0; row < height; row += rowsperstrip ) {
1877     uint32 newrows, i_row;
1878     
1879     if (!TIFFReadRGBAStrip(tif, row, raster)) {
1880       if (allow_incomplete) {
1881         i_tags_setn(&im->tags, "i_lines_read", row);
1882         i_tags_setn(&im->tags, "i_incomplete", 1);
1883         break;
1884       }
1885       else {
1886         i_push_error(0, "could not read TIFF image strip");
1887         _TIFFfree(raster);
1888         i_img_destroy(im);
1889         return NULL;
1890       }
1891     }
1892     
1893     newrows = (row+rowsperstrip > height) ? height-row : rowsperstrip;
1894     mm_log((1, "newrows=%d\n", newrows));
1895     
1896     for( i_row = 0; i_row < newrows; i_row++ ) { 
1897       uint32 x;
1898       i_color *outp = line_buf;
1899
1900       for(x = 0; x<width; x++) {
1901         uint32 temp = raster[x+width*(newrows-i_row-1)];
1902         outp->rgba.r = TIFFGetR(temp);
1903         outp->rgba.g = TIFFGetG(temp);
1904         outp->rgba.b = TIFFGetB(temp);
1905
1906         if (alpha_chan) {
1907           /* the libtiff RGBA code expands greyscale into RGBA, so put the
1908              alpha in the right place and scale it */
1909           int ch;
1910           outp->channel[alpha_chan] = TIFFGetA(temp);
1911           if (outp->channel[alpha_chan]) {
1912             for (ch = 0; ch < alpha_chan; ++ch) {
1913               outp->channel[ch] = outp->channel[ch] * 255 / outp->channel[alpha_chan];
1914             }
1915           }
1916         }
1917
1918         outp++;
1919       }
1920       i_plin(im, 0, width, i_row+row, line_buf);
1921     }
1922   }
1923
1924   myfree(line_buf);
1925   _TIFFfree(raster);
1926   
1927   return im;
1928 }
1929
1930 /* adapted from libtiff 
1931
1932   libtiff's TIFFReadRGBATile succeeds even when asked to read an
1933   invalid tile, which means we have no way of knowing whether the data
1934   we received from it is valid or not.
1935
1936   So the caller here has set stoponerror to 1 so that
1937   TIFFRGBAImageGet() will fail.
1938
1939   read_one_rgb_tiled() then takes that into account for i_incomplete
1940   or failure.
1941  */
1942 static int
1943 myTIFFReadRGBATile(TIFFRGBAImage *img, uint32 col, uint32 row, uint32 * raster)
1944
1945 {
1946     int         ok;
1947     uint32      tile_xsize, tile_ysize;
1948     uint32      read_xsize, read_ysize;
1949     uint32      i_row;
1950
1951     /*
1952      * Verify that our request is legal - on a tile file, and on a
1953      * tile boundary.
1954      */
1955     
1956     TIFFGetFieldDefaulted(img->tif, TIFFTAG_TILEWIDTH, &tile_xsize);
1957     TIFFGetFieldDefaulted(img->tif, TIFFTAG_TILELENGTH, &tile_ysize);
1958     if( (col % tile_xsize) != 0 || (row % tile_ysize) != 0 )
1959     {
1960       i_push_errorf(0, "Row/col passed to myTIFFReadRGBATile() must be top"
1961                     "left corner of a tile.");
1962       return 0;
1963     }
1964
1965     /*
1966      * The TIFFRGBAImageGet() function doesn't allow us to get off the
1967      * edge of the image, even to fill an otherwise valid tile.  So we
1968      * figure out how much we can read, and fix up the tile buffer to
1969      * a full tile configuration afterwards.
1970      */
1971
1972     if( row + tile_ysize > img->height )
1973         read_ysize = img->height - row;
1974     else
1975         read_ysize = tile_ysize;
1976     
1977     if( col + tile_xsize > img->width )
1978         read_xsize = img->width - col;
1979     else
1980         read_xsize = tile_xsize;
1981
1982     /*
1983      * Read the chunk of imagery.
1984      */
1985     
1986     img->row_offset = row;
1987     img->col_offset = col;
1988
1989     ok = TIFFRGBAImageGet(img, raster, read_xsize, read_ysize );
1990         
1991     /*
1992      * If our read was incomplete we will need to fix up the tile by
1993      * shifting the data around as if a full tile of data is being returned.
1994      *
1995      * This is all the more complicated because the image is organized in
1996      * bottom to top format. 
1997      */
1998
1999     if( read_xsize == tile_xsize && read_ysize == tile_ysize )
2000         return( ok );
2001
2002     for( i_row = 0; i_row < read_ysize; i_row++ ) {
2003         memmove( raster + (tile_ysize - i_row - 1) * tile_xsize,
2004                  raster + (read_ysize - i_row - 1) * read_xsize,
2005                  read_xsize * sizeof(uint32) );
2006         _TIFFmemset( raster + (tile_ysize - i_row - 1) * tile_xsize+read_xsize,
2007                      0, sizeof(uint32) * (tile_xsize - read_xsize) );
2008     }
2009
2010     for( i_row = read_ysize; i_row < tile_ysize; i_row++ ) {
2011         _TIFFmemset( raster + (tile_ysize - i_row - 1) * tile_xsize,
2012                      0, sizeof(uint32) * tile_xsize );
2013     }
2014
2015     return (ok);
2016 }
2017
2018 static i_img *
2019 read_one_rgb_tiled(TIFF *tif, i_img_dim width, i_img_dim height, int allow_incomplete) {
2020   i_img *im;
2021   uint32* raster = NULL;
2022   int ok = 1;
2023   uint32 row, col;
2024   uint32 tile_width, tile_height;
2025   unsigned long pixels = 0;
2026   char  emsg[1024] = "";
2027   TIFFRGBAImage img;
2028   i_color *line;
2029   int alpha_chan;
2030   
2031   im = make_rgb(tif, width, height, &alpha_chan);
2032   if (!im)
2033     return NULL;
2034   
2035   if (!TIFFRGBAImageOK(tif, emsg) 
2036       || !TIFFRGBAImageBegin(&img, tif, 1, emsg)) {
2037     i_push_error(0, emsg);
2038     i_img_destroy(im);
2039     return( 0 );
2040   }
2041
2042   TIFFGetField(tif, TIFFTAG_TILEWIDTH, &tile_width);
2043   TIFFGetField(tif, TIFFTAG_TILELENGTH, &tile_height);
2044   mm_log((1, "i_readtiff_wiol: tile_width=%d, tile_height=%d\n", tile_width, tile_height));
2045   
2046   raster = (uint32*)_TIFFmalloc(tile_width * tile_height * sizeof (uint32));
2047   if (!raster) {
2048     i_img_destroy(im);
2049     i_push_error(0, "No space for raster buffer");
2050     TIFFRGBAImageEnd(&img);
2051     return NULL;
2052   }
2053   line = mymalloc(tile_width * sizeof(i_color));
2054   
2055   for( row = 0; row < height; row += tile_height ) {
2056     for( col = 0; col < width; col += tile_width ) {
2057       
2058       /* Read the tile into an RGBA array */
2059       if (myTIFFReadRGBATile(&img, col, row, raster)) {
2060         uint32 i_row, x;
2061         uint32 newrows = (row+tile_height > height) ? height-row : tile_height;
2062         uint32 newcols = (col+tile_width  > width ) ? width-col  : tile_width;
2063
2064         mm_log((1, "i_readtiff_wiol: tile(%d, %d) newcols=%d newrows=%d\n", col, row, newcols, newrows));
2065         for( i_row = 0; i_row < newrows; i_row++ ) {
2066           i_color *outp = line;
2067           for(x = 0; x < newcols; x++) {
2068             uint32 temp = raster[x+tile_width*(tile_height-i_row-1)];
2069             outp->rgba.r = TIFFGetR(temp);
2070             outp->rgba.g = TIFFGetG(temp);
2071             outp->rgba.b = TIFFGetB(temp);
2072             outp->rgba.a = TIFFGetA(temp);
2073
2074             if (alpha_chan) {
2075               /* the libtiff RGBA code expands greyscale into RGBA, so put the
2076                  alpha in the right place and scale it */
2077               int ch;
2078               outp->channel[alpha_chan] = TIFFGetA(temp);
2079               
2080               if (outp->channel[alpha_chan]) {
2081                 for (ch = 0; ch < alpha_chan; ++ch) {
2082                   outp->channel[ch] = outp->channel[ch] * 255 / outp->channel[alpha_chan];
2083                 }
2084               }
2085             }
2086
2087             ++outp;
2088           }
2089           i_plin(im, col, col+newcols, row+i_row, line);
2090         }
2091         pixels += newrows * newcols;
2092       }
2093       else {
2094         if (allow_incomplete) {
2095           ok = 0;
2096         }
2097         else {
2098           goto error;
2099         }
2100       }
2101     }
2102   }
2103
2104   if (!ok) {
2105     if (pixels == 0) {
2106       i_push_error(0, "TIFF: No image data could be read from the image");
2107       goto error;
2108     }
2109
2110     /* incomplete image */
2111     i_tags_setn(&im->tags, "i_incomplete", 1);
2112     i_tags_setn(&im->tags, "i_lines_read", pixels / width);
2113   }
2114
2115   myfree(line);
2116   TIFFRGBAImageEnd(&img);
2117   _TIFFfree(raster);
2118   
2119   return im;
2120
2121  error:
2122   myfree(line);
2123   _TIFFfree(raster);
2124   TIFFRGBAImageEnd(&img);
2125   i_img_destroy(im);
2126   return NULL;
2127 }
2128
2129 char const *
2130 i_tiff_libversion(void) {
2131   return TIFFGetVersion();
2132 }
2133
2134 static int 
2135 setup_paletted(read_state_t *state) {
2136   uint16 *maps[3];
2137   int i, ch;
2138   int color_count = 1 << state->bits_per_sample;
2139
2140   state->img = i_img_pal_new(state->width, state->height, 3, 256);
2141   if (!state->img)
2142     return 0;
2143
2144   /* setup the color map */
2145   if (!TIFFGetField(state->tif, TIFFTAG_COLORMAP, maps+0, maps+1, maps+2)) {
2146     i_push_error(0, "Cannot get colormap for paletted image");
2147     i_img_destroy(state->img);
2148     return 0;
2149   }
2150   for (i = 0; i < color_count; ++i) {
2151     i_color c;
2152     for (ch = 0; ch < 3; ++ch) {
2153       c.channel[ch] = Sample16To8(maps[ch][i]);
2154     }
2155     i_addcolors(state->img, &c, 1);
2156   }
2157
2158   return 1;
2159 }
2160
2161 static int 
2162 tile_contig_getter(read_state_t *state, read_putter_t putter) {
2163   uint32 tile_width, tile_height;
2164   uint32 this_tile_height, this_tile_width;
2165   uint32 rows_left, cols_left;
2166   uint32 x, y;
2167
2168   state->raster = _TIFFmalloc(TIFFTileSize(state->tif));
2169   if (!state->raster) {
2170     i_push_error(0, "tiff: Out of memory allocating tile buffer");
2171     return 0;
2172   }
2173
2174   TIFFGetField(state->tif, TIFFTAG_TILEWIDTH, &tile_width);
2175   TIFFGetField(state->tif, TIFFTAG_TILELENGTH, &tile_height);
2176   rows_left = state->height;
2177   for (y = 0; y < state->height; y += this_tile_height) {
2178     this_tile_height = rows_left > tile_height ? tile_height : rows_left;
2179
2180     cols_left = state->width;
2181     for (x = 0; x < state->width; x += this_tile_width) {
2182       this_tile_width = cols_left > tile_width ? tile_width : cols_left;
2183
2184       if (TIFFReadTile(state->tif,
2185                        state->raster,
2186                        x, y, 0, 0) < 0) {
2187         if (!state->allow_incomplete) {
2188           return 0;
2189         }
2190       }
2191       else {
2192         putter(state, x, y, this_tile_width, this_tile_height, tile_width - this_tile_width);
2193       }
2194
2195       cols_left -= this_tile_width;
2196     }
2197
2198     rows_left -= this_tile_height;
2199   }
2200
2201   return 1;
2202 }
2203
2204 static int 
2205 strip_contig_getter(read_state_t *state, read_putter_t putter) {
2206   uint32 rows_per_strip;
2207   tsize_t strip_size = TIFFStripSize(state->tif);
2208   uint32 y, strip_rows, rows_left;
2209
2210   state->raster = _TIFFmalloc(strip_size);
2211   if (!state->raster) {
2212     i_push_error(0, "tiff: Out of memory allocating strip buffer");
2213     return 0;
2214   }
2215   
2216   TIFFGetFieldDefaulted(state->tif, TIFFTAG_ROWSPERSTRIP, &rows_per_strip);
2217   rows_left = state->height;
2218   for (y = 0; y < state->height; y += strip_rows) {
2219     strip_rows = rows_left > rows_per_strip ? rows_per_strip : rows_left;
2220     if (TIFFReadEncodedStrip(state->tif,
2221                              TIFFComputeStrip(state->tif, y, 0),
2222                              state->raster,
2223                              strip_size) < 0) {
2224       if (!state->allow_incomplete)
2225         return 0;
2226     }
2227     else {
2228       putter(state, 0, y, state->width, strip_rows, 0);
2229     }
2230     rows_left -= strip_rows;
2231   }
2232
2233   return 1;
2234 }
2235
2236 static int 
2237 paletted_putter8(read_state_t *state, i_img_dim x, i_img_dim y, i_img_dim width, i_img_dim height, int extras) {
2238   unsigned char *p = state->raster;
2239
2240   state->pixels_read += width * height;
2241   while (height > 0) {
2242     i_ppal(state->img, x, x + width, y, p);
2243     p += width + extras;
2244     --height;
2245     ++y;
2246   }
2247
2248   return 1;
2249 }
2250
2251 static int 
2252 paletted_putter4(read_state_t *state, i_img_dim x, i_img_dim y, i_img_dim width, i_img_dim height, int extras) {
2253   uint32 img_line_size = (width + 1) / 2;
2254   uint32 skip_line_size = (width + extras + 1) / 2;
2255   unsigned char *p = state->raster;
2256
2257   if (!state->line_buf)
2258     state->line_buf = mymalloc(state->width);
2259
2260   state->pixels_read += width * height;
2261   while (height > 0) {
2262     unpack_4bit_to(state->line_buf, p, img_line_size);
2263     i_ppal(state->img, x, x + width, y, state->line_buf);
2264     p += skip_line_size;
2265     --height;
2266     ++y;
2267   }
2268
2269   return 1;
2270 }
2271
2272 static void
2273 rgb_channels(read_state_t *state, int *out_channels) {
2274   uint16 extra_count;
2275   uint16 *extras;
2276   
2277   /* safe defaults */
2278   *out_channels = 3;
2279   state->alpha_chan = 0;
2280   state->scale_alpha = 0;
2281
2282   /* plain RGB */
2283   if (state->samples_per_pixel == 3)
2284     return;
2285  
2286   if (!TIFFGetField(state->tif, TIFFTAG_EXTRASAMPLES, &extra_count, &extras)) {
2287     mm_log((1, "tiff: samples != 3 but no extra samples tag\n"));
2288     return;
2289   }
2290
2291   if (!extra_count) {
2292     mm_log((1, "tiff: samples != 3 but no extra samples listed"));
2293     return;
2294   }
2295
2296   ++*out_channels;
2297   state->alpha_chan = 3;
2298   switch (*extras) {
2299   case EXTRASAMPLE_UNSPECIFIED:
2300   case EXTRASAMPLE_ASSOCALPHA:
2301     state->scale_alpha = 1;
2302     break;
2303
2304   case EXTRASAMPLE_UNASSALPHA:
2305     state->scale_alpha = 0;
2306     break;
2307
2308   default:
2309     mm_log((1, "tiff: unknown extra sample type %d, treating as assoc alpha\n",
2310             *extras));
2311     state->scale_alpha = 1;
2312     break;
2313   }
2314   mm_log((1, "tiff alpha channel %d scale %d\n", state->alpha_chan, state->scale_alpha));
2315 }
2316
2317 static void
2318 grey_channels(read_state_t *state, int *out_channels) {
2319   uint16 extra_count;
2320   uint16 *extras;
2321   
2322   /* safe defaults */
2323   *out_channels = 1;
2324   state->alpha_chan = 0;
2325   state->scale_alpha = 0;
2326
2327   /* plain grey */
2328   if (state->samples_per_pixel == 1)
2329     return;
2330  
2331   if (!TIFFGetField(state->tif, TIFFTAG_EXTRASAMPLES, &extra_count, &extras)) {
2332     mm_log((1, "tiff: samples != 1 but no extra samples tag\n"));
2333     return;
2334   }
2335
2336   if (!extra_count) {
2337     mm_log((1, "tiff: samples != 1 but no extra samples listed"));
2338     return;
2339   }
2340
2341   ++*out_channels;
2342   state->alpha_chan = 1;
2343   switch (*extras) {
2344   case EXTRASAMPLE_UNSPECIFIED:
2345   case EXTRASAMPLE_ASSOCALPHA:
2346     state->scale_alpha = 1;
2347     break;
2348
2349   case EXTRASAMPLE_UNASSALPHA:
2350     state->scale_alpha = 0;
2351     break;
2352
2353   default:
2354     mm_log((1, "tiff: unknown extra sample type %d, treating as assoc alpha\n",
2355             *extras));
2356     state->scale_alpha = 1;
2357     break;
2358   }
2359 }
2360
2361 static int
2362 setup_16_rgb(read_state_t *state) {
2363   int out_channels;
2364
2365   rgb_channels(state, &out_channels);
2366
2367   state->img = i_img_16_new(state->width, state->height, out_channels);
2368   if (!state->img)
2369     return 0;
2370   state->line_buf = mymalloc(sizeof(unsigned) * state->width * out_channels);
2371
2372   return 1;
2373 }
2374
2375 static int
2376 setup_16_grey(read_state_t *state) {
2377   int out_channels;
2378
2379   grey_channels(state, &out_channels);
2380
2381   state->img = i_img_16_new(state->width, state->height, out_channels);
2382   if (!state->img)
2383     return 0;
2384   state->line_buf = mymalloc(sizeof(unsigned) * state->width * out_channels);
2385
2386   return 1;
2387 }
2388
2389 static int 
2390 putter_16(read_state_t *state, i_img_dim x, i_img_dim y, i_img_dim width, i_img_dim height, 
2391           int row_extras) {
2392   uint16 *p = state->raster;
2393   int out_chan = state->img->channels;
2394
2395   state->pixels_read += width * height;
2396   while (height > 0) {
2397     i_img_dim i;
2398     int ch;
2399     unsigned *outp = state->line_buf;
2400
2401     for (i = 0; i < width; ++i) {
2402       for (ch = 0; ch < out_chan; ++ch) {
2403         outp[ch] = p[ch];
2404       }
2405       if (state->alpha_chan && state->scale_alpha && outp[state->alpha_chan]) {
2406         for (ch = 0; ch < state->alpha_chan; ++ch) {
2407           int result = 0.5 + (outp[ch] * 65535.0 / outp[state->alpha_chan]);
2408           outp[ch] = CLAMP16(result);
2409         }
2410       }
2411       p += state->samples_per_pixel;
2412       outp += out_chan;
2413     }
2414
2415     i_psamp_bits(state->img, x, x + width, y, state->line_buf, NULL, out_chan, 16);
2416
2417     p += row_extras * state->samples_per_pixel;
2418     --height;
2419     ++y;
2420   }
2421
2422   return 1;
2423 }
2424
2425 static int
2426 setup_8_rgb(read_state_t *state) {
2427   int out_channels;
2428
2429   rgb_channels(state, &out_channels);
2430
2431   state->img = i_img_8_new(state->width, state->height, out_channels);
2432   if (!state->img)
2433     return 0;
2434   state->line_buf = mymalloc(sizeof(unsigned) * state->width * out_channels);
2435
2436   return 1;
2437 }
2438
2439 static int
2440 setup_8_grey(read_state_t *state) {
2441   int out_channels;
2442
2443   grey_channels(state, &out_channels);
2444
2445   state->img = i_img_8_new(state->width, state->height, out_channels);
2446   if (!state->img)
2447     return 0;
2448   state->line_buf = mymalloc(sizeof(i_color) * state->width * out_channels);
2449
2450   return 1;
2451 }
2452
2453 static int 
2454 putter_8(read_state_t *state, i_img_dim x, i_img_dim y, i_img_dim width, i_img_dim height, 
2455           int row_extras) {
2456   unsigned char *p = state->raster;
2457   int out_chan = state->img->channels;
2458
2459   state->pixels_read += width * height;
2460   while (height > 0) {
2461     i_img_dim i;
2462     int ch;
2463     i_color *outp = state->line_buf;
2464
2465     for (i = 0; i < width; ++i) {
2466       for (ch = 0; ch < out_chan; ++ch) {
2467         outp->channel[ch] = p[ch];
2468       }
2469       if (state->alpha_chan && state->scale_alpha 
2470           && outp->channel[state->alpha_chan]) {
2471         for (ch = 0; ch < state->alpha_chan; ++ch) {
2472           int result = (outp->channel[ch] * 255 + 127) / outp->channel[state->alpha_chan];
2473         
2474           outp->channel[ch] = CLAMP8(result);
2475         }
2476       }
2477       p += state->samples_per_pixel;
2478       outp++;
2479     }
2480
2481     i_plin(state->img, x, x + width, y, state->line_buf);
2482
2483     p += row_extras * state->samples_per_pixel;
2484     --height;
2485     ++y;
2486   }
2487
2488   return 1;
2489 }
2490
2491 static int
2492 setup_32_rgb(read_state_t *state) {
2493   int out_channels;
2494
2495   rgb_channels(state, &out_channels);
2496
2497   state->img = i_img_double_new(state->width, state->height, out_channels);
2498   if (!state->img)
2499     return 0;
2500   state->line_buf = mymalloc(sizeof(i_fcolor) * state->width);
2501
2502   return 1;
2503 }
2504
2505 static int
2506 setup_32_grey(read_state_t *state) {
2507   int out_channels;
2508
2509   grey_channels(state, &out_channels);
2510
2511   state->img = i_img_double_new(state->width, state->height, out_channels);
2512   if (!state->img)
2513     return 0;
2514   state->line_buf = mymalloc(sizeof(i_fcolor) * state->width);
2515
2516   return 1;
2517 }
2518
2519 static int 
2520 putter_32(read_state_t *state, i_img_dim x, i_img_dim y, i_img_dim width, i_img_dim height, 
2521           int row_extras) {
2522   uint32 *p = state->raster;
2523   int out_chan = state->img->channels;
2524
2525   state->pixels_read += width * height;
2526   while (height > 0) {
2527     i_img_dim i;
2528     int ch;
2529     i_fcolor *outp = state->line_buf;
2530
2531     for (i = 0; i < width; ++i) {
2532       for (ch = 0; ch < out_chan; ++ch) {
2533         outp->channel[ch] = p[ch] / 4294967295.0;
2534       }
2535       if (state->alpha_chan && state->scale_alpha && outp->channel[state->alpha_chan]) {
2536         for (ch = 0; ch < state->alpha_chan; ++ch)
2537           outp->channel[ch] /= outp->channel[state->alpha_chan];
2538       }
2539       p += state->samples_per_pixel;
2540       outp++;
2541     }
2542
2543     i_plinf(state->img, x, x + width, y, state->line_buf);
2544
2545     p += row_extras * state->samples_per_pixel;
2546     --height;
2547     ++y;
2548   }
2549
2550   return 1;
2551 }
2552
2553 static int
2554 setup_bilevel(read_state_t *state) {
2555   i_color black, white;
2556   state->img = i_img_pal_new(state->width, state->height, 1, 256);
2557   if (!state->img)
2558     return 0;
2559   black.channel[0] = black.channel[1] = black.channel[2] = 
2560     black.channel[3] = 0;
2561   white.channel[0] = white.channel[1] = white.channel[2] = 
2562     white.channel[3] = 255;
2563   if (state->photometric == PHOTOMETRIC_MINISBLACK) {
2564     i_addcolors(state->img, &black, 1);
2565     i_addcolors(state->img, &white, 1);
2566   }
2567   else {
2568     i_addcolors(state->img, &white, 1);
2569     i_addcolors(state->img, &black, 1);
2570   }
2571   state->line_buf = mymalloc(state->width);
2572
2573   return 1;
2574 }
2575
2576 static int 
2577 putter_bilevel(read_state_t *state, i_img_dim x, i_img_dim y, i_img_dim width, i_img_dim height, 
2578                int row_extras) {
2579   unsigned char *line_in = state->raster;
2580   size_t line_size = (width + row_extras + 7) / 8;
2581   
2582   /* tifflib returns the bits in MSB2LSB order even when the file is
2583      in LSB2MSB, so we only need to handle MSB2LSB */
2584   state->pixels_read += width * height;
2585   while (height > 0) {
2586     i_img_dim i;
2587     unsigned char *outp = state->line_buf;
2588     unsigned char *inp = line_in;
2589     unsigned mask = 0x80;
2590
2591     for (i = 0; i < width; ++i) {
2592       *outp++ = *inp & mask ? 1 : 0;
2593       mask >>= 1;
2594       if (!mask) {
2595         ++inp;
2596         mask = 0x80;
2597       }
2598     }
2599
2600     i_ppal(state->img, x, x + width, y, state->line_buf);
2601
2602     line_in += line_size;
2603     --height;
2604     ++y;
2605   }
2606
2607   return 1;
2608 }
2609
2610 static void
2611 cmyk_channels(read_state_t *state, int *out_channels) {
2612   uint16 extra_count;
2613   uint16 *extras;
2614   
2615   /* safe defaults */
2616   *out_channels = 3;
2617   state->alpha_chan = 0;
2618   state->scale_alpha = 0;
2619
2620   /* plain CMYK */
2621   if (state->samples_per_pixel == 4)
2622     return;
2623  
2624   if (!TIFFGetField(state->tif, TIFFTAG_EXTRASAMPLES, &extra_count, &extras)) {
2625     mm_log((1, "tiff: CMYK samples != 4 but no extra samples tag\n"));
2626     return;
2627   }
2628
2629   if (!extra_count) {
2630     mm_log((1, "tiff: CMYK samples != 4 but no extra samples listed"));
2631     return;
2632   }
2633
2634   ++*out_channels;
2635   state->alpha_chan = 4;
2636   switch (*extras) {
2637   case EXTRASAMPLE_UNSPECIFIED:
2638   case EXTRASAMPLE_ASSOCALPHA:
2639     state->scale_alpha = 1;
2640     break;
2641
2642   case EXTRASAMPLE_UNASSALPHA:
2643     state->scale_alpha = 0;
2644     break;
2645
2646   default:
2647     mm_log((1, "tiff: unknown extra sample type %d, treating as assoc alpha\n",
2648             *extras));
2649     state->scale_alpha = 1;
2650     break;
2651   }
2652 }
2653
2654 static int
2655 setup_cmyk8(read_state_t *state) {
2656   int channels;
2657
2658   cmyk_channels(state, &channels);
2659   state->img = i_img_8_new(state->width, state->height, channels);
2660
2661   state->line_buf = mymalloc(sizeof(i_color) * state->width);
2662
2663   return 1;
2664 }
2665
2666 static int 
2667 putter_cmyk8(read_state_t *state, i_img_dim x, i_img_dim y, i_img_dim width, i_img_dim height, 
2668                int row_extras) {
2669   unsigned char *p = state->raster;
2670
2671   state->pixels_read += width * height;
2672   while (height > 0) {
2673     i_img_dim i;
2674     int ch;
2675     i_color *outp = state->line_buf;
2676
2677     for (i = 0; i < width; ++i) {
2678       unsigned char c, m, y, k;
2679       c = p[0];
2680       m = p[1];
2681       y = p[2];
2682       k = 255 - p[3];
2683       outp->rgba.r = (k * (255 - c)) / 255;
2684       outp->rgba.g = (k * (255 - m)) / 255;
2685       outp->rgba.b = (k * (255 - y)) / 255;
2686       if (state->alpha_chan) {
2687         outp->rgba.a = p[state->alpha_chan];
2688         if (state->scale_alpha 
2689             && outp->rgba.a) {
2690           for (ch = 0; ch < 3; ++ch) {
2691             int result = (outp->channel[ch] * 255 + 127) / outp->rgba.a;
2692             outp->channel[ch] = CLAMP8(result);
2693           }
2694         }
2695       }
2696       p += state->samples_per_pixel;
2697       outp++;
2698     }
2699
2700     i_plin(state->img, x, x + width, y, state->line_buf);
2701
2702     p += row_extras * state->samples_per_pixel;
2703     --height;
2704     ++y;
2705   }
2706
2707   return 1;
2708 }
2709
2710 static int
2711 setup_cmyk16(read_state_t *state) {
2712   int channels;
2713
2714   cmyk_channels(state, &channels);
2715   state->img = i_img_16_new(state->width, state->height, channels);
2716
2717   state->line_buf = mymalloc(sizeof(unsigned) * state->width * channels);
2718
2719   return 1;
2720 }
2721
2722 static int 
2723 putter_cmyk16(read_state_t *state, i_img_dim x, i_img_dim y, i_img_dim width, i_img_dim height, 
2724                int row_extras) {
2725   uint16 *p = state->raster;
2726   int out_chan = state->img->channels;
2727
2728   mm_log((4, "putter_cmyk16(%p, %" i_DF ", %" i_DF ", %" i_DF
2729           ", %" i_DF ", %d)\n", state, i_DFcp(x, y), i_DFcp(width, height),
2730           row_extras));
2731
2732   state->pixels_read += width * height;
2733   while (height > 0) {
2734     i_img_dim i;
2735     int ch;
2736     unsigned *outp = state->line_buf;
2737
2738     for (i = 0; i < width; ++i) {
2739       unsigned c, m, y, k;
2740       c = p[0];
2741       m = p[1];
2742       y = p[2];
2743       k = 65535 - p[3];
2744       outp[0] = (k * (65535U - c)) / 65535U;
2745       outp[1] = (k * (65535U - m)) / 65535U;
2746       outp[2] = (k * (65535U - y)) / 65535U;
2747       if (state->alpha_chan) {
2748         outp[3] = p[state->alpha_chan];
2749         if (state->scale_alpha 
2750             && outp[3]) {
2751           for (ch = 0; ch < 3; ++ch) {
2752             int result = (outp[ch] * 65535 + 32767) / outp[3];
2753             outp[3] = CLAMP16(result);
2754           }
2755         }
2756       }
2757       p += state->samples_per_pixel;
2758       outp += out_chan;
2759     }
2760
2761     i_psamp_bits(state->img, x, x + width, y, state->line_buf, NULL, out_chan, 16);
2762
2763     p += row_extras * state->samples_per_pixel;
2764     --height;
2765     ++y;
2766   }
2767
2768   return 1;
2769 }
2770
2771 /*
2772
2773   Older versions of tifflib we support don't define this, so define it
2774   ourselves.
2775
2776   If you want this detection to do anything useful, use a newer
2777   release of tifflib.
2778
2779  */
2780 #if TIFFLIB_VERSION < 20031121
2781
2782 int 
2783 TIFFIsCODECConfigured(uint16 scheme) {
2784   switch (scheme) {
2785     /* these schemes are all shipped with tifflib */
2786  case COMPRESSION_NONE:
2787  case COMPRESSION_PACKBITS:
2788  case COMPRESSION_CCITTRLE:
2789  case COMPRESSION_CCITTRLEW:
2790  case COMPRESSION_CCITTFAX3:
2791  case COMPRESSION_CCITTFAX4:
2792     return 1;
2793
2794     /* these require external library support */
2795   default:
2796  case COMPRESSION_JPEG:
2797  case COMPRESSION_LZW:
2798  case COMPRESSION_DEFLATE:
2799  case COMPRESSION_ADOBE_DEFLATE:
2800     return 0;
2801   }
2802 }
2803
2804 #endif
2805
2806 static int 
2807 myTIFFIsCODECConfigured(uint16 scheme) {
2808 #if TIFFLIB_VERSION < 20040724
2809   if (scheme == COMPRESSION_LZW)
2810     return 0;
2811 #endif
2812
2813   return TIFFIsCODECConfigured(scheme);
2814 }
2815
2816 static void
2817 tiffio_context_init(tiffio_context_t *c, io_glue *ig) {
2818   c->magic = TIFFIO_MAGIC;
2819   c->ig = ig;
2820 #ifdef USE_EXT_WARN_HANDLER
2821   c->warn_buffer = NULL;
2822   c->warn_size = 0;
2823 #endif
2824 }
2825
2826 static void
2827 tiffio_context_final(tiffio_context_t *c) {
2828   c->magic = TIFFIO_MAGIC;
2829 #ifdef USE_EXT_WARN_HANDLER
2830   if (c->warn_buffer)
2831     myfree(c->warn_buffer);
2832 #endif
2833 }
2834
2835 /*
2836 =back
2837
2838 =head1 AUTHOR
2839
2840 Arnar M. Hrafnkelsson <addi@umich.edu>, Tony Cook <tonyc@cpan.org>
2841
2842 =head1 SEE ALSO
2843
2844 Imager(3)
2845
2846 =cut
2847 */