1 /*
2 * Copyright (c) 1988-1997 Sam Leffler
3 * Copyright (c) 1991-1997 Silicon Graphics, Inc.
4 *
5 * Permission to use, copy, modify, distribute, and sell this software and
6 * its documentation for any purpose is hereby granted without fee, provided
7 * that (i) the above copyright notices and this permission notice appear in
8 * all copies of the software and related documentation, and (ii) the names of
9 * Sam Leffler and Silicon Graphics may not be used in any advertising or
10 * publicity relating to the software without the specific, prior written
11 * permission of Sam Leffler and Silicon Graphics.
12 *
13 * THE SOFTWARE IS PROVIDED "AS-IS" AND WITHOUT WARRANTY OF ANY KIND,
14 * EXPRESS, IMPLIED OR OTHERWISE, INCLUDING WITHOUT LIMITATION, ANY
15 * WARRANTY OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE.
16 *
17 * IN NO EVENT SHALL SAM LEFFLER OR SILICON GRAPHICS BE LIABLE FOR
18 * ANY SPECIAL, INCIDENTAL, INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND,
19 * OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS,
20 * WHETHER OR NOT ADVISED OF THE POSSIBILITY OF DAMAGE, AND ON ANY THEORY OF
21 * LIABILITY, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE
22 * OF THIS SOFTWARE.
23 */
24
25 /*
26 * TIFF Library.
27 *
28 * Directory Tag Get & Set Routines.
29 * (and also some miscellaneous stuff)
30 */
31 #include "tiffiop.h"
32 #include <float.h> /*--: for Rational2Double */
33
34 /*
35 * These are used in the backwards compatibility code...
36 */
37 #define DATATYPE_VOID 0 /* !untyped data */
38 #define DATATYPE_INT 1 /* !signed integer data */
39 #define DATATYPE_UINT 2 /* !unsigned integer data */
40 #define DATATYPE_IEEEFP 3 /* !IEEE floating point data */
41
42 static void
setByteArray(void ** vpp,void * vp,size_t nmemb,size_t elem_size)43 setByteArray(void** vpp, void* vp, size_t nmemb, size_t elem_size)
44 {
45 if (*vpp) {
46 _TIFFfree(*vpp);
47 *vpp = 0;
48 }
49 if (vp) {
50 tmsize_t bytes = _TIFFMultiplySSize(NULL, nmemb, elem_size, NULL);
51 if (bytes)
52 *vpp = (void*) _TIFFmalloc(bytes);
53 if (*vpp)
54 _TIFFmemcpy(*vpp, vp, bytes);
55 }
56 }
_TIFFsetByteArray(void ** vpp,void * vp,uint32_t n)57 void _TIFFsetByteArray(void** vpp, void* vp, uint32_t n)
58 { setByteArray(vpp, vp, n, 1); }
_TIFFsetString(char ** cpp,char * cp)59 void _TIFFsetString(char** cpp, char* cp)
60 { setByteArray((void**) cpp, (void*) cp, strlen(cp)+1, 1); }
_TIFFsetNString(char ** cpp,char * cp,uint32_t n)61 static void _TIFFsetNString(char** cpp, char* cp, uint32_t n)
62 { setByteArray((void**) cpp, (void*) cp, n, 1); }
_TIFFsetShortArray(uint16_t ** wpp,uint16_t * wp,uint32_t n)63 void _TIFFsetShortArray(uint16_t** wpp, uint16_t* wp, uint32_t n)
64 { setByteArray((void**) wpp, (void*) wp, n, sizeof (uint16_t)); }
_TIFFsetLongArray(uint32_t ** lpp,uint32_t * lp,uint32_t n)65 void _TIFFsetLongArray(uint32_t** lpp, uint32_t* lp, uint32_t n)
66 { setByteArray((void**) lpp, (void*) lp, n, sizeof (uint32_t)); }
_TIFFsetLong8Array(uint64_t ** lpp,uint64_t * lp,uint32_t n)67 static void _TIFFsetLong8Array(uint64_t** lpp, uint64_t* lp, uint32_t n)
68 { setByteArray((void**) lpp, (void*) lp, n, sizeof (uint64_t)); }
_TIFFsetFloatArray(float ** fpp,float * fp,uint32_t n)69 void _TIFFsetFloatArray(float** fpp, float* fp, uint32_t n)
70 { setByteArray((void**) fpp, (void*) fp, n, sizeof (float)); }
_TIFFsetDoubleArray(double ** dpp,double * dp,uint32_t n)71 void _TIFFsetDoubleArray(double** dpp, double* dp, uint32_t n)
72 { setByteArray((void**) dpp, (void*) dp, n, sizeof (double)); }
73
74 static void
setDoubleArrayOneValue(double ** vpp,double value,size_t nmemb)75 setDoubleArrayOneValue(double** vpp, double value, size_t nmemb)
76 {
77 if (*vpp)
78 _TIFFfree(*vpp);
79 *vpp = _TIFFmalloc(nmemb*sizeof(double));
80 if (*vpp)
81 {
82 while (nmemb--)
83 ((double*)*vpp)[nmemb] = value;
84 }
85 }
86
87 /*
88 * Install extra samples information.
89 */
90 static int
setExtraSamples(TIFF * tif,va_list ap,uint32_t * v)91 setExtraSamples(TIFF* tif, va_list ap, uint32_t* v)
92 {
93 /* XXX: Unassociated alpha data == 999 is a known Corel Draw bug, see below */
94 #define EXTRASAMPLE_COREL_UNASSALPHA 999
95
96 uint16_t* va;
97 uint32_t i;
98 TIFFDirectory* td = &tif->tif_dir;
99 static const char module[] = "setExtraSamples";
100
101 *v = (uint16_t) va_arg(ap, uint16_vap);
102 if ((uint16_t) *v > td->td_samplesperpixel)
103 return 0;
104 va = va_arg(ap, uint16_t*);
105 if (*v > 0 && va == NULL) /* typically missing param */
106 return 0;
107 for (i = 0; i < *v; i++) {
108 if (va[i] > EXTRASAMPLE_UNASSALPHA) {
109 /*
110 * XXX: Corel Draw is known to produce incorrect
111 * ExtraSamples tags which must be patched here if we
112 * want to be able to open some of the damaged TIFF
113 * files:
114 */
115 if (va[i] == EXTRASAMPLE_COREL_UNASSALPHA)
116 va[i] = EXTRASAMPLE_UNASSALPHA;
117 else
118 return 0;
119 }
120 }
121
122 if ( td->td_transferfunction[0] != NULL && (td->td_samplesperpixel - *v > 1) &&
123 !(td->td_samplesperpixel - td->td_extrasamples > 1))
124 {
125 TIFFWarningExt(tif->tif_clientdata,module,
126 "ExtraSamples tag value is changing, "
127 "but TransferFunction was read with a different value. Canceling it");
128 TIFFClrFieldBit(tif,FIELD_TRANSFERFUNCTION);
129 _TIFFfree(td->td_transferfunction[0]);
130 td->td_transferfunction[0] = NULL;
131 }
132
133 td->td_extrasamples = (uint16_t) *v;
134 _TIFFsetShortArray(&td->td_sampleinfo, va, td->td_extrasamples);
135 return 1;
136
137 #undef EXTRASAMPLE_COREL_UNASSALPHA
138 }
139
140 /*
141 * Confirm we have "samplesperpixel" ink names separated by \0. Returns
142 * zero if the ink names are not as expected.
143 */
144 static uint32_t
checkInkNamesString(TIFF * tif,uint32_t slen,const char * s)145 checkInkNamesString(TIFF* tif, uint32_t slen, const char* s)
146 {
147 TIFFDirectory* td = &tif->tif_dir;
148 uint16_t i = td->td_samplesperpixel;
149
150 if (slen > 0) {
151 const char* ep = s+slen;
152 const char* cp = s;
153 for (; i > 0; i--) {
154 for (; cp < ep && *cp != '\0'; cp++) {}
155 if (cp >= ep)
156 goto bad;
157 cp++; /* skip \0 */
158 }
159 return ((uint32_t)(cp - s));
160 }
161 bad:
162 TIFFErrorExt(tif->tif_clientdata, "TIFFSetField",
163 "%s: Invalid InkNames value; expecting %"PRIu16" names, found %"PRIu16,
164 tif->tif_name,
165 td->td_samplesperpixel,
166 (uint16_t)(td->td_samplesperpixel-i));
167 return (0);
168 }
169
170 static int
_TIFFVSetField(TIFF * tif,uint32_t tag,va_list ap)171 _TIFFVSetField(TIFF* tif, uint32_t tag, va_list ap)
172 {
173 static const char module[] = "_TIFFVSetField";
174
175 TIFFDirectory* td = &tif->tif_dir;
176 int status = 1;
177 uint32_t v32, i, v;
178 double dblval;
179 char* s;
180 const TIFFField *fip = TIFFFindField(tif, tag, TIFF_ANY);
181 uint32_t standard_tag = tag;
182 if( fip == NULL ) /* cannot happen since OkToChangeTag() already checks it */
183 return 0;
184 /*
185 * We want to force the custom code to be used for custom
186 * fields even if the tag happens to match a well known
187 * one - important for reinterpreted handling of standard
188 * tag values in custom directories (i.e. EXIF)
189 */
190 if (fip->field_bit == FIELD_CUSTOM) {
191 standard_tag = 0;
192 }
193
194 switch (standard_tag) {
195 case TIFFTAG_SUBFILETYPE:
196 td->td_subfiletype = (uint32_t) va_arg(ap, uint32_t);
197 break;
198 case TIFFTAG_IMAGEWIDTH:
199 td->td_imagewidth = (uint32_t) va_arg(ap, uint32_t);
200 break;
201 case TIFFTAG_IMAGELENGTH:
202 td->td_imagelength = (uint32_t) va_arg(ap, uint32_t);
203 break;
204 case TIFFTAG_BITSPERSAMPLE:
205 td->td_bitspersample = (uint16_t) va_arg(ap, uint16_vap);
206 /*
207 * If the data require post-decoding processing to byte-swap
208 * samples, set it up here. Note that since tags are required
209 * to be ordered, compression code can override this behavior
210 * in the setup method if it wants to roll the post decoding
211 * work in with its normal work.
212 */
213 if (tif->tif_flags & TIFF_SWAB) {
214 if (td->td_bitspersample == 8)
215 tif->tif_postdecode = _TIFFNoPostDecode;
216 else if (td->td_bitspersample == 16)
217 tif->tif_postdecode = _TIFFSwab16BitData;
218 else if (td->td_bitspersample == 24)
219 tif->tif_postdecode = _TIFFSwab24BitData;
220 else if (td->td_bitspersample == 32)
221 tif->tif_postdecode = _TIFFSwab32BitData;
222 else if (td->td_bitspersample == 64)
223 tif->tif_postdecode = _TIFFSwab64BitData;
224 else if (td->td_bitspersample == 128) /* two 64's */
225 tif->tif_postdecode = _TIFFSwab64BitData;
226 }
227 break;
228 case TIFFTAG_COMPRESSION:
229 v = (uint16_t) va_arg(ap, uint16_vap);
230 /*
231 * If we're changing the compression scheme, the notify the
232 * previous module so that it can cleanup any state it's
233 * setup.
234 */
235 if (TIFFFieldSet(tif, FIELD_COMPRESSION)) {
236 if ((uint32_t)td->td_compression == v)
237 break;
238 (*tif->tif_cleanup)(tif);
239 tif->tif_flags &= ~TIFF_CODERSETUP;
240 }
241 /*
242 * Setup new compression routine state.
243 */
244 if( (status = TIFFSetCompressionScheme(tif, v)) != 0 )
245 td->td_compression = (uint16_t) v;
246 else
247 status = 0;
248 break;
249 case TIFFTAG_PHOTOMETRIC:
250 td->td_photometric = (uint16_t) va_arg(ap, uint16_vap);
251 break;
252 case TIFFTAG_THRESHHOLDING:
253 td->td_threshholding = (uint16_t) va_arg(ap, uint16_vap);
254 break;
255 case TIFFTAG_FILLORDER:
256 v = (uint16_t) va_arg(ap, uint16_vap);
257 if (v != FILLORDER_LSB2MSB && v != FILLORDER_MSB2LSB)
258 goto badvalue;
259 td->td_fillorder = (uint16_t) v;
260 break;
261 case TIFFTAG_ORIENTATION:
262 v = (uint16_t) va_arg(ap, uint16_vap);
263 if (v < ORIENTATION_TOPLEFT || ORIENTATION_LEFTBOT < v)
264 goto badvalue;
265 else
266 td->td_orientation = (uint16_t) v;
267 break;
268 case TIFFTAG_SAMPLESPERPIXEL:
269 v = (uint16_t) va_arg(ap, uint16_vap);
270 if (v == 0)
271 goto badvalue;
272 if( v != td->td_samplesperpixel )
273 {
274 /* See http://bugzilla.maptools.org/show_bug.cgi?id=2500 */
275 if( td->td_sminsamplevalue != NULL )
276 {
277 TIFFWarningExt(tif->tif_clientdata,module,
278 "SamplesPerPixel tag value is changing, "
279 "but SMinSampleValue tag was read with a different value. Canceling it");
280 TIFFClrFieldBit(tif,FIELD_SMINSAMPLEVALUE);
281 _TIFFfree(td->td_sminsamplevalue);
282 td->td_sminsamplevalue = NULL;
283 }
284 if( td->td_smaxsamplevalue != NULL )
285 {
286 TIFFWarningExt(tif->tif_clientdata,module,
287 "SamplesPerPixel tag value is changing, "
288 "but SMaxSampleValue tag was read with a different value. Canceling it");
289 TIFFClrFieldBit(tif,FIELD_SMAXSAMPLEVALUE);
290 _TIFFfree(td->td_smaxsamplevalue);
291 td->td_smaxsamplevalue = NULL;
292 }
293 /* Test if 3 transfer functions instead of just one are now needed
294 See http://bugzilla.maptools.org/show_bug.cgi?id=2820 */
295 if( td->td_transferfunction[0] != NULL && (v - td->td_extrasamples > 1) &&
296 !(td->td_samplesperpixel - td->td_extrasamples > 1))
297 {
298 TIFFWarningExt(tif->tif_clientdata,module,
299 "SamplesPerPixel tag value is changing, "
300 "but TransferFunction was read with a different value. Canceling it");
301 TIFFClrFieldBit(tif,FIELD_TRANSFERFUNCTION);
302 _TIFFfree(td->td_transferfunction[0]);
303 td->td_transferfunction[0] = NULL;
304 }
305 }
306 td->td_samplesperpixel = (uint16_t) v;
307 break;
308 case TIFFTAG_ROWSPERSTRIP:
309 v32 = (uint32_t) va_arg(ap, uint32_t);
310 if (v32 == 0)
311 goto badvalue32;
312 td->td_rowsperstrip = v32;
313 if (!TIFFFieldSet(tif, FIELD_TILEDIMENSIONS)) {
314 td->td_tilelength = v32;
315 td->td_tilewidth = td->td_imagewidth;
316 }
317 break;
318 case TIFFTAG_MINSAMPLEVALUE:
319 td->td_minsamplevalue = (uint16_t) va_arg(ap, uint16_vap);
320 break;
321 case TIFFTAG_MAXSAMPLEVALUE:
322 td->td_maxsamplevalue = (uint16_t) va_arg(ap, uint16_vap);
323 break;
324 case TIFFTAG_SMINSAMPLEVALUE:
325 if (tif->tif_flags & TIFF_PERSAMPLE)
326 _TIFFsetDoubleArray(&td->td_sminsamplevalue, va_arg(ap, double*), td->td_samplesperpixel);
327 else
328 setDoubleArrayOneValue(&td->td_sminsamplevalue, va_arg(ap, double), td->td_samplesperpixel);
329 break;
330 case TIFFTAG_SMAXSAMPLEVALUE:
331 if (tif->tif_flags & TIFF_PERSAMPLE)
332 _TIFFsetDoubleArray(&td->td_smaxsamplevalue, va_arg(ap, double*), td->td_samplesperpixel);
333 else
334 setDoubleArrayOneValue(&td->td_smaxsamplevalue, va_arg(ap, double), td->td_samplesperpixel);
335 break;
336 case TIFFTAG_XRESOLUTION:
337 dblval = va_arg(ap, double);
338 if( dblval < 0 )
339 goto badvaluedouble;
340 td->td_xresolution = _TIFFClampDoubleToFloat( dblval );
341 break;
342 case TIFFTAG_YRESOLUTION:
343 dblval = va_arg(ap, double);
344 if( dblval < 0 )
345 goto badvaluedouble;
346 td->td_yresolution = _TIFFClampDoubleToFloat( dblval );
347 break;
348 case TIFFTAG_PLANARCONFIG:
349 v = (uint16_t) va_arg(ap, uint16_vap);
350 if (v != PLANARCONFIG_CONTIG && v != PLANARCONFIG_SEPARATE)
351 goto badvalue;
352 td->td_planarconfig = (uint16_t) v;
353 break;
354 case TIFFTAG_XPOSITION:
355 td->td_xposition = _TIFFClampDoubleToFloat( va_arg(ap, double) );
356 break;
357 case TIFFTAG_YPOSITION:
358 td->td_yposition = _TIFFClampDoubleToFloat( va_arg(ap, double) );
359 break;
360 case TIFFTAG_RESOLUTIONUNIT:
361 v = (uint16_t) va_arg(ap, uint16_vap);
362 if (v < RESUNIT_NONE || RESUNIT_CENTIMETER < v)
363 goto badvalue;
364 td->td_resolutionunit = (uint16_t) v;
365 break;
366 case TIFFTAG_PAGENUMBER:
367 td->td_pagenumber[0] = (uint16_t) va_arg(ap, uint16_vap);
368 td->td_pagenumber[1] = (uint16_t) va_arg(ap, uint16_vap);
369 break;
370 case TIFFTAG_HALFTONEHINTS:
371 td->td_halftonehints[0] = (uint16_t) va_arg(ap, uint16_vap);
372 td->td_halftonehints[1] = (uint16_t) va_arg(ap, uint16_vap);
373 break;
374 case TIFFTAG_COLORMAP:
375 v32 = (uint32_t)(1L << td->td_bitspersample);
376 _TIFFsetShortArray(&td->td_colormap[0], va_arg(ap, uint16_t*), v32);
377 _TIFFsetShortArray(&td->td_colormap[1], va_arg(ap, uint16_t*), v32);
378 _TIFFsetShortArray(&td->td_colormap[2], va_arg(ap, uint16_t*), v32);
379 break;
380 case TIFFTAG_EXTRASAMPLES:
381 if (!setExtraSamples(tif, ap, &v))
382 goto badvalue;
383 break;
384 case TIFFTAG_MATTEING:
385 td->td_extrasamples = (((uint16_t) va_arg(ap, uint16_vap)) != 0);
386 if (td->td_extrasamples) {
387 uint16_t sv = EXTRASAMPLE_ASSOCALPHA;
388 _TIFFsetShortArray(&td->td_sampleinfo, &sv, 1);
389 }
390 break;
391 case TIFFTAG_TILEWIDTH:
392 v32 = (uint32_t) va_arg(ap, uint32_t);
393 if (v32 % 16) {
394 if (tif->tif_mode != O_RDONLY)
395 goto badvalue32;
396 TIFFWarningExt(tif->tif_clientdata, tif->tif_name,
397 "Nonstandard tile width %"PRIu32", convert file", v32);
398 }
399 td->td_tilewidth = v32;
400 tif->tif_flags |= TIFF_ISTILED;
401 break;
402 case TIFFTAG_TILELENGTH:
403 v32 = (uint32_t) va_arg(ap, uint32_t);
404 if (v32 % 16) {
405 if (tif->tif_mode != O_RDONLY)
406 goto badvalue32;
407 TIFFWarningExt(tif->tif_clientdata, tif->tif_name,
408 "Nonstandard tile length %"PRIu32", convert file", v32);
409 }
410 td->td_tilelength = v32;
411 tif->tif_flags |= TIFF_ISTILED;
412 break;
413 case TIFFTAG_TILEDEPTH:
414 v32 = (uint32_t) va_arg(ap, uint32_t);
415 if (v32 == 0)
416 goto badvalue32;
417 td->td_tiledepth = v32;
418 break;
419 case TIFFTAG_DATATYPE:
420 v = (uint16_t) va_arg(ap, uint16_vap);
421 switch (v) {
422 case DATATYPE_VOID: v = SAMPLEFORMAT_VOID; break;
423 case DATATYPE_INT: v = SAMPLEFORMAT_INT; break;
424 case DATATYPE_UINT: v = SAMPLEFORMAT_UINT; break;
425 case DATATYPE_IEEEFP: v = SAMPLEFORMAT_IEEEFP;break;
426 default: goto badvalue;
427 }
428 td->td_sampleformat = (uint16_t) v;
429 break;
430 case TIFFTAG_SAMPLEFORMAT:
431 v = (uint16_t) va_arg(ap, uint16_vap);
432 if (v < SAMPLEFORMAT_UINT || SAMPLEFORMAT_COMPLEXIEEEFP < v)
433 goto badvalue;
434 td->td_sampleformat = (uint16_t) v;
435
436 /* Try to fix up the SWAB function for complex data. */
437 if( td->td_sampleformat == SAMPLEFORMAT_COMPLEXINT
438 && td->td_bitspersample == 32
439 && tif->tif_postdecode == _TIFFSwab32BitData )
440 tif->tif_postdecode = _TIFFSwab16BitData;
441 else if( (td->td_sampleformat == SAMPLEFORMAT_COMPLEXINT
442 || td->td_sampleformat == SAMPLEFORMAT_COMPLEXIEEEFP)
443 && td->td_bitspersample == 64
444 && tif->tif_postdecode == _TIFFSwab64BitData )
445 tif->tif_postdecode = _TIFFSwab32BitData;
446 break;
447 case TIFFTAG_IMAGEDEPTH:
448 td->td_imagedepth = (uint32_t) va_arg(ap, uint32_t);
449 break;
450 case TIFFTAG_SUBIFD:
451 if ((tif->tif_flags & TIFF_INSUBIFD) == 0) {
452 td->td_nsubifd = (uint16_t) va_arg(ap, uint16_vap);
453 _TIFFsetLong8Array(&td->td_subifd, (uint64_t*) va_arg(ap, uint64_t*),
454 (uint32_t) td->td_nsubifd);
455 } else {
456 TIFFErrorExt(tif->tif_clientdata, module,
457 "%s: Sorry, cannot nest SubIFDs",
458 tif->tif_name);
459 status = 0;
460 }
461 break;
462 case TIFFTAG_YCBCRPOSITIONING:
463 td->td_ycbcrpositioning = (uint16_t) va_arg(ap, uint16_vap);
464 break;
465 case TIFFTAG_YCBCRSUBSAMPLING:
466 td->td_ycbcrsubsampling[0] = (uint16_t) va_arg(ap, uint16_vap);
467 td->td_ycbcrsubsampling[1] = (uint16_t) va_arg(ap, uint16_vap);
468 break;
469 case TIFFTAG_TRANSFERFUNCTION:
470 v = (td->td_samplesperpixel - td->td_extrasamples) > 1 ? 3 : 1;
471 for (i = 0; i < v; i++)
472 _TIFFsetShortArray(&td->td_transferfunction[i],
473 va_arg(ap, uint16_t*), 1U << td->td_bitspersample);
474 break;
475 case TIFFTAG_REFERENCEBLACKWHITE:
476 /* XXX should check for null range */
477 _TIFFsetFloatArray(&td->td_refblackwhite, va_arg(ap, float*), 6);
478 break;
479 case TIFFTAG_INKNAMES:
480 v = (uint16_t) va_arg(ap, uint16_vap);
481 s = va_arg(ap, char*);
482 v = checkInkNamesString(tif, v, s);
483 status = v > 0;
484 if( v > 0 ) {
485 _TIFFsetNString(&td->td_inknames, s, v);
486 td->td_inknameslen = v;
487 }
488 break;
489 case TIFFTAG_PERSAMPLE:
490 v = (uint16_t) va_arg(ap, uint16_vap);
491 if( v == PERSAMPLE_MULTI )
492 tif->tif_flags |= TIFF_PERSAMPLE;
493 else
494 tif->tif_flags &= ~TIFF_PERSAMPLE;
495 break;
496 default: {
497 TIFFTagValue *tv;
498 int tv_size, iCustom;
499
500 /*
501 * This can happen if multiple images are open with different
502 * codecs which have private tags. The global tag information
503 * table may then have tags that are valid for one file but not
504 * the other. If the client tries to set a tag that is not valid
505 * for the image's codec then we'll arrive here. This
506 * happens, for example, when tiffcp is used to convert between
507 * compression schemes and codec-specific tags are blindly copied.
508 */
509 if(fip->field_bit != FIELD_CUSTOM) {
510 TIFFErrorExt(tif->tif_clientdata, module,
511 "%s: Invalid %stag \"%s\" (not supported by codec)",
512 tif->tif_name, isPseudoTag(tag) ? "pseudo-" : "",
513 fip->field_name);
514 status = 0;
515 break;
516 }
517
518 /*
519 * Find the existing entry for this custom value.
520 */
521 tv = NULL;
522 for (iCustom = 0; iCustom < td->td_customValueCount; iCustom++) {
523 if (td->td_customValues[iCustom].info->field_tag == tag) {
524 tv = td->td_customValues + iCustom;
525 if (tv->value != NULL) {
526 _TIFFfree(tv->value);
527 tv->value = NULL;
528 }
529 break;
530 }
531 }
532
533 /*
534 * Grow the custom list if the entry was not found.
535 */
536 if(tv == NULL) {
537 TIFFTagValue *new_customValues;
538
539 td->td_customValueCount++;
540 new_customValues = (TIFFTagValue *)
541 _TIFFrealloc(td->td_customValues,
542 sizeof(TIFFTagValue) * td->td_customValueCount);
543 if (!new_customValues) {
544 TIFFErrorExt(tif->tif_clientdata, module,
545 "%s: Failed to allocate space for list of custom values",
546 tif->tif_name);
547 status = 0;
548 goto end;
549 }
550
551 td->td_customValues = new_customValues;
552
553 tv = td->td_customValues + (td->td_customValueCount - 1);
554 tv->info = fip;
555 tv->value = NULL;
556 tv->count = 0;
557 }
558
559 /*
560 * Set custom value ... save a copy of the custom tag value.
561 */
562 tv_size = _TIFFDataSize(fip->field_type);
563 /*--: Rational2Double: For Rationals evaluate "set_field_type" to determine internal storage size. */
564 if (fip->field_type == TIFF_RATIONAL || fip->field_type == TIFF_SRATIONAL) {
565 tv_size = _TIFFSetGetFieldSize(fip->set_field_type);
566 }
567 if (tv_size == 0) {
568 status = 0;
569 TIFFErrorExt(tif->tif_clientdata, module,
570 "%s: Bad field type %d for \"%s\"",
571 tif->tif_name, fip->field_type,
572 fip->field_name);
573 goto end;
574 }
575
576 if (fip->field_type == TIFF_ASCII)
577 {
578 uint32_t ma;
579 char* mb;
580 if (fip->field_passcount)
581 {
582 assert(fip->field_writecount==TIFF_VARIABLE2);
583 ma=(uint32_t)va_arg(ap, uint32_t);
584 mb=(char*)va_arg(ap,char*);
585 }
586 else
587 {
588 mb=(char*)va_arg(ap,char*);
589 ma=(uint32_t)(strlen(mb) + 1);
590 }
591 tv->count=ma;
592 setByteArray(&tv->value,mb,ma,1);
593 }
594 else
595 {
596 if (fip->field_passcount) {
597 if (fip->field_writecount == TIFF_VARIABLE2)
598 tv->count = (uint32_t) va_arg(ap, uint32_t);
599 else
600 tv->count = (int) va_arg(ap, int);
601 } else if (fip->field_writecount == TIFF_VARIABLE
602 || fip->field_writecount == TIFF_VARIABLE2)
603 tv->count = 1;
604 else if (fip->field_writecount == TIFF_SPP)
605 tv->count = td->td_samplesperpixel;
606 else
607 tv->count = fip->field_writecount;
608
609 if (tv->count == 0) {
610 status = 0;
611 TIFFErrorExt(tif->tif_clientdata, module,
612 "%s: Null count for \"%s\" (type "
613 "%d, writecount %d, passcount %d)",
614 tif->tif_name,
615 fip->field_name,
616 fip->field_type,
617 fip->field_writecount,
618 fip->field_passcount);
619 goto end;
620 }
621
622 tv->value = _TIFFCheckMalloc(tif, tv->count, tv_size,
623 "custom tag binary object");
624 if (!tv->value) {
625 status = 0;
626 goto end;
627 }
628
629 if (fip->field_tag == TIFFTAG_DOTRANGE
630 && strcmp(fip->field_name,"DotRange") == 0) {
631 /* TODO: This is an evil exception and should not have been
632 handled this way ... likely best if we move it into
633 the directory structure with an explicit field in
634 libtiff 4.1 and assign it a FIELD_ value */
635 uint16_t v2[2];
636 v2[0] = (uint16_t)va_arg(ap, int);
637 v2[1] = (uint16_t)va_arg(ap, int);
638 _TIFFmemcpy(tv->value, &v2, 4);
639 }
640
641 else if (fip->field_passcount
642 || fip->field_writecount == TIFF_VARIABLE
643 || fip->field_writecount == TIFF_VARIABLE2
644 || fip->field_writecount == TIFF_SPP
645 || tv->count > 1) {
646 /*--: Rational2Double: For Rationals tv_size is set above to 4 or 8 according to fip->set_field_type! */
647 _TIFFmemcpy(tv->value, va_arg(ap, void *),
648 tv->count * tv_size);
649 } else {
650 char *val = (char *)tv->value;
651 assert( tv->count == 1 );
652
653 switch (fip->field_type) {
654 case TIFF_BYTE:
655 case TIFF_UNDEFINED:
656 {
657 uint8_t v2 = (uint8_t)va_arg(ap, int);
658 _TIFFmemcpy(val, &v2, tv_size);
659 }
660 break;
661 case TIFF_SBYTE:
662 {
663 int8_t v2 = (int8_t)va_arg(ap, int);
664 _TIFFmemcpy(val, &v2, tv_size);
665 }
666 break;
667 case TIFF_SHORT:
668 {
669 uint16_t v2 = (uint16_t)va_arg(ap, int);
670 _TIFFmemcpy(val, &v2, tv_size);
671 }
672 break;
673 case TIFF_SSHORT:
674 {
675 int16_t v2 = (int16_t)va_arg(ap, int);
676 _TIFFmemcpy(val, &v2, tv_size);
677 }
678 break;
679 case TIFF_LONG:
680 case TIFF_IFD:
681 {
682 uint32_t v2 = va_arg(ap, uint32_t);
683 _TIFFmemcpy(val, &v2, tv_size);
684 }
685 break;
686 case TIFF_SLONG:
687 {
688 int32_t v2 = va_arg(ap, int32_t);
689 _TIFFmemcpy(val, &v2, tv_size);
690 }
691 break;
692 case TIFF_LONG8:
693 case TIFF_IFD8:
694 {
695 uint64_t v2 = va_arg(ap, uint64_t);
696 _TIFFmemcpy(val, &v2, tv_size);
697 }
698 break;
699 case TIFF_SLONG8:
700 {
701 int64_t v2 = va_arg(ap, int64_t);
702 _TIFFmemcpy(val, &v2, tv_size);
703 }
704 break;
705 case TIFF_RATIONAL:
706 case TIFF_SRATIONAL:
707 /*-- Rational2Double: For Rationals tv_size is set above to 4 or 8 according to fip->set_field_type! */
708 {
709 if (tv_size == 8) {
710 double v2 = va_arg(ap, double);
711 _TIFFmemcpy(val, &v2, tv_size);
712 } else {
713 /*-- default should be tv_size == 4 */
714 float v3 = (float)va_arg(ap, double);
715 _TIFFmemcpy(val, &v3, tv_size);
716 /*-- ToDo: After Testing, this should be removed and tv_size==4 should be set as default. */
717 if (tv_size != 4) {
718 TIFFErrorExt(0,"TIFFLib: _TIFFVSetField()", "Rational2Double: .set_field_type in not 4 but %d", tv_size);
719 }
720 }
721 }
722 break;
723 case TIFF_FLOAT:
724 {
725 float v2 = _TIFFClampDoubleToFloat(va_arg(ap, double));
726 _TIFFmemcpy(val, &v2, tv_size);
727 }
728 break;
729 case TIFF_DOUBLE:
730 {
731 double v2 = va_arg(ap, double);
732 _TIFFmemcpy(val, &v2, tv_size);
733 }
734 break;
735 default:
736 _TIFFmemset(val, 0, tv_size);
737 status = 0;
738 break;
739 }
740 }
741 }
742 }
743 }
744 if (status) {
745 const TIFFField* fip2=TIFFFieldWithTag(tif,tag);
746 if (fip2)
747 TIFFSetFieldBit(tif, fip2->field_bit);
748 tif->tif_flags |= TIFF_DIRTYDIRECT;
749 }
750
751 end:
752 va_end(ap);
753 return (status);
754 badvalue:
755 {
756 const TIFFField* fip2=TIFFFieldWithTag(tif,tag);
757 TIFFErrorExt(tif->tif_clientdata, module,
758 "%s: Bad value %"PRIu32" for \"%s\" tag",
759 tif->tif_name, v,
760 fip2 ? fip2->field_name : "Unknown");
761 va_end(ap);
762 }
763 return (0);
764 badvalue32:
765 {
766 const TIFFField* fip2=TIFFFieldWithTag(tif,tag);
767 TIFFErrorExt(tif->tif_clientdata, module,
768 "%s: Bad value %"PRIu32" for \"%s\" tag",
769 tif->tif_name, v32,
770 fip2 ? fip2->field_name : "Unknown");
771 va_end(ap);
772 }
773 return (0);
774 badvaluedouble:
775 {
776 const TIFFField* fip2=TIFFFieldWithTag(tif,tag);
777 TIFFErrorExt(tif->tif_clientdata, module,
778 "%s: Bad value %f for \"%s\" tag",
779 tif->tif_name, dblval,
780 fip2 ? fip2->field_name : "Unknown");
781 va_end(ap);
782 }
783 return (0);
784 }
785
786 /*
787 * Return 1/0 according to whether or not
788 * it is permissible to set the tag's value.
789 * Note that we allow ImageLength to be changed
790 * so that we can append and extend to images.
791 * Any other tag may not be altered once writing
792 * has commenced, unless its value has no effect
793 * on the format of the data that is written.
794 */
795 static int
OkToChangeTag(TIFF * tif,uint32_t tag)796 OkToChangeTag(TIFF* tif, uint32_t tag)
797 {
798 const TIFFField* fip = TIFFFindField(tif, tag, TIFF_ANY);
799 if (!fip) { /* unknown tag */
800 TIFFErrorExt(tif->tif_clientdata, "TIFFSetField", "%s: Unknown %stag %"PRIu32,
801 tif->tif_name, isPseudoTag(tag) ? "pseudo-" : "", tag);
802 return (0);
803 }
804 if (tag != TIFFTAG_IMAGELENGTH && (tif->tif_flags & TIFF_BEENWRITING) &&
805 !fip->field_oktochange) {
806 /*
807 * Consult info table to see if tag can be changed
808 * after we've started writing. We only allow changes
809 * to those tags that don't/shouldn't affect the
810 * compression and/or format of the data.
811 */
812 TIFFErrorExt(tif->tif_clientdata, "TIFFSetField",
813 "%s: Cannot modify tag \"%s\" while writing",
814 tif->tif_name, fip->field_name);
815 return (0);
816 }
817 return (1);
818 }
819
820 /*
821 * Record the value of a field in the
822 * internal directory structure. The
823 * field will be written to the file
824 * when/if the directory structure is
825 * updated.
826 */
827 int
TIFFSetField(TIFF * tif,uint32_t tag,...)828 TIFFSetField(TIFF* tif, uint32_t tag, ...)
829 {
830 va_list ap;
831 int status;
832
833 va_start(ap, tag);
834 status = TIFFVSetField(tif, tag, ap);
835 va_end(ap);
836 return (status);
837 }
838
839 /*
840 * Clear the contents of the field in the internal structure.
841 */
842 int
TIFFUnsetField(TIFF * tif,uint32_t tag)843 TIFFUnsetField(TIFF* tif, uint32_t tag)
844 {
845 const TIFFField *fip = TIFFFieldWithTag(tif, tag);
846 TIFFDirectory* td = &tif->tif_dir;
847
848 if( !fip )
849 return 0;
850
851 if( fip->field_bit != FIELD_CUSTOM )
852 TIFFClrFieldBit(tif, fip->field_bit);
853 else
854 {
855 TIFFTagValue *tv = NULL;
856 int i;
857
858 for (i = 0; i < td->td_customValueCount; i++) {
859
860 tv = td->td_customValues + i;
861 if( tv->info->field_tag == tag )
862 break;
863 }
864
865 if( i < td->td_customValueCount )
866 {
867 _TIFFfree(tv->value);
868 for( ; i < td->td_customValueCount-1; i++) {
869 td->td_customValues[i] = td->td_customValues[i+1];
870 }
871 td->td_customValueCount--;
872 }
873 }
874
875 tif->tif_flags |= TIFF_DIRTYDIRECT;
876
877 return (1);
878 }
879
880 /*
881 * Like TIFFSetField, but taking a varargs
882 * parameter list. This routine is useful
883 * for building higher-level interfaces on
884 * top of the library.
885 */
886 int
TIFFVSetField(TIFF * tif,uint32_t tag,va_list ap)887 TIFFVSetField(TIFF* tif, uint32_t tag, va_list ap)
888 {
889 return OkToChangeTag(tif, tag) ?
890 (*tif->tif_tagmethods.vsetfield)(tif, tag, ap) : 0;
891 }
892
893 static int
_TIFFVGetField(TIFF * tif,uint32_t tag,va_list ap)894 _TIFFVGetField(TIFF* tif, uint32_t tag, va_list ap)
895 {
896 TIFFDirectory* td = &tif->tif_dir;
897 int ret_val = 1;
898 uint32_t standard_tag = tag;
899 const TIFFField* fip = TIFFFindField(tif, tag, TIFF_ANY);
900 if( fip == NULL ) /* cannot happen since TIFFGetField() already checks it */
901 return 0;
902
903 /*
904 * We want to force the custom code to be used for custom
905 * fields even if the tag happens to match a well known
906 * one - important for reinterpreted handling of standard
907 * tag values in custom directories (i.e. EXIF)
908 */
909 if (fip->field_bit == FIELD_CUSTOM) {
910 standard_tag = 0;
911 }
912
913 if( standard_tag == TIFFTAG_NUMBEROFINKS )
914 {
915 int i;
916 for (i = 0; i < td->td_customValueCount; i++) {
917 uint16_t val;
918 TIFFTagValue *tv = td->td_customValues + i;
919 if (tv->info->field_tag != standard_tag)
920 continue;
921 if( tv->value == NULL )
922 return 0;
923 val = *(uint16_t *)tv->value;
924 /* Truncate to SamplesPerPixel, since the */
925 /* setting code for INKNAMES assume that there are SamplesPerPixel */
926 /* inknames. */
927 /* Fixes http://bugzilla.maptools.org/show_bug.cgi?id=2599 */
928 if( val > td->td_samplesperpixel )
929 {
930 TIFFWarningExt(tif->tif_clientdata,"_TIFFVGetField",
931 "Truncating NumberOfInks from %u to %"PRIu16,
932 val, td->td_samplesperpixel);
933 val = td->td_samplesperpixel;
934 }
935 *va_arg(ap, uint16_t*) = val;
936 return 1;
937 }
938 return 0;
939 }
940
941 switch (standard_tag) {
942 case TIFFTAG_SUBFILETYPE:
943 *va_arg(ap, uint32_t*) = td->td_subfiletype;
944 break;
945 case TIFFTAG_IMAGEWIDTH:
946 *va_arg(ap, uint32_t*) = td->td_imagewidth;
947 break;
948 case TIFFTAG_IMAGELENGTH:
949 *va_arg(ap, uint32_t*) = td->td_imagelength;
950 break;
951 case TIFFTAG_BITSPERSAMPLE:
952 *va_arg(ap, uint16_t*) = td->td_bitspersample;
953 break;
954 case TIFFTAG_COMPRESSION:
955 *va_arg(ap, uint16_t*) = td->td_compression;
956 break;
957 case TIFFTAG_PHOTOMETRIC:
958 *va_arg(ap, uint16_t*) = td->td_photometric;
959 break;
960 case TIFFTAG_THRESHHOLDING:
961 *va_arg(ap, uint16_t*) = td->td_threshholding;
962 break;
963 case TIFFTAG_FILLORDER:
964 *va_arg(ap, uint16_t*) = td->td_fillorder;
965 break;
966 case TIFFTAG_ORIENTATION:
967 *va_arg(ap, uint16_t*) = td->td_orientation;
968 break;
969 case TIFFTAG_SAMPLESPERPIXEL:
970 *va_arg(ap, uint16_t*) = td->td_samplesperpixel;
971 break;
972 case TIFFTAG_ROWSPERSTRIP:
973 *va_arg(ap, uint32_t*) = td->td_rowsperstrip;
974 break;
975 case TIFFTAG_MINSAMPLEVALUE:
976 *va_arg(ap, uint16_t*) = td->td_minsamplevalue;
977 break;
978 case TIFFTAG_MAXSAMPLEVALUE:
979 *va_arg(ap, uint16_t*) = td->td_maxsamplevalue;
980 break;
981 case TIFFTAG_SMINSAMPLEVALUE:
982 if (tif->tif_flags & TIFF_PERSAMPLE)
983 *va_arg(ap, double**) = td->td_sminsamplevalue;
984 else
985 {
986 /* libtiff historically treats this as a single value. */
987 uint16_t i;
988 double v = td->td_sminsamplevalue[0];
989 for (i=1; i < td->td_samplesperpixel; ++i)
990 if( td->td_sminsamplevalue[i] < v )
991 v = td->td_sminsamplevalue[i];
992 *va_arg(ap, double*) = v;
993 }
994 break;
995 case TIFFTAG_SMAXSAMPLEVALUE:
996 if (tif->tif_flags & TIFF_PERSAMPLE)
997 *va_arg(ap, double**) = td->td_smaxsamplevalue;
998 else
999 {
1000 /* libtiff historically treats this as a single value. */
1001 uint16_t i;
1002 double v = td->td_smaxsamplevalue[0];
1003 for (i=1; i < td->td_samplesperpixel; ++i)
1004 if( td->td_smaxsamplevalue[i] > v )
1005 v = td->td_smaxsamplevalue[i];
1006 *va_arg(ap, double*) = v;
1007 }
1008 break;
1009 case TIFFTAG_XRESOLUTION:
1010 *va_arg(ap, float*) = td->td_xresolution;
1011 break;
1012 case TIFFTAG_YRESOLUTION:
1013 *va_arg(ap, float*) = td->td_yresolution;
1014 break;
1015 case TIFFTAG_PLANARCONFIG:
1016 *va_arg(ap, uint16_t*) = td->td_planarconfig;
1017 break;
1018 case TIFFTAG_XPOSITION:
1019 *va_arg(ap, float*) = td->td_xposition;
1020 break;
1021 case TIFFTAG_YPOSITION:
1022 *va_arg(ap, float*) = td->td_yposition;
1023 break;
1024 case TIFFTAG_RESOLUTIONUNIT:
1025 *va_arg(ap, uint16_t*) = td->td_resolutionunit;
1026 break;
1027 case TIFFTAG_PAGENUMBER:
1028 *va_arg(ap, uint16_t*) = td->td_pagenumber[0];
1029 *va_arg(ap, uint16_t*) = td->td_pagenumber[1];
1030 break;
1031 case TIFFTAG_HALFTONEHINTS:
1032 *va_arg(ap, uint16_t*) = td->td_halftonehints[0];
1033 *va_arg(ap, uint16_t*) = td->td_halftonehints[1];
1034 break;
1035 case TIFFTAG_COLORMAP:
1036 *va_arg(ap, const uint16_t**) = td->td_colormap[0];
1037 *va_arg(ap, const uint16_t**) = td->td_colormap[1];
1038 *va_arg(ap, const uint16_t**) = td->td_colormap[2];
1039 break;
1040 case TIFFTAG_STRIPOFFSETS:
1041 case TIFFTAG_TILEOFFSETS:
1042 _TIFFFillStriles( tif );
1043 *va_arg(ap, const uint64_t**) = td->td_stripoffset_p;
1044 break;
1045 case TIFFTAG_STRIPBYTECOUNTS:
1046 case TIFFTAG_TILEBYTECOUNTS:
1047 _TIFFFillStriles( tif );
1048 *va_arg(ap, const uint64_t**) = td->td_stripbytecount_p;
1049 break;
1050 case TIFFTAG_MATTEING:
1051 *va_arg(ap, uint16_t*) =
1052 (td->td_extrasamples == 1 &&
1053 td->td_sampleinfo[0] == EXTRASAMPLE_ASSOCALPHA);
1054 break;
1055 case TIFFTAG_EXTRASAMPLES:
1056 *va_arg(ap, uint16_t*) = td->td_extrasamples;
1057 *va_arg(ap, const uint16_t**) = td->td_sampleinfo;
1058 break;
1059 case TIFFTAG_TILEWIDTH:
1060 *va_arg(ap, uint32_t*) = td->td_tilewidth;
1061 break;
1062 case TIFFTAG_TILELENGTH:
1063 *va_arg(ap, uint32_t*) = td->td_tilelength;
1064 break;
1065 case TIFFTAG_TILEDEPTH:
1066 *va_arg(ap, uint32_t*) = td->td_tiledepth;
1067 break;
1068 case TIFFTAG_DATATYPE:
1069 switch (td->td_sampleformat) {
1070 case SAMPLEFORMAT_UINT:
1071 *va_arg(ap, uint16_t*) = DATATYPE_UINT;
1072 break;
1073 case SAMPLEFORMAT_INT:
1074 *va_arg(ap, uint16_t*) = DATATYPE_INT;
1075 break;
1076 case SAMPLEFORMAT_IEEEFP:
1077 *va_arg(ap, uint16_t*) = DATATYPE_IEEEFP;
1078 break;
1079 case SAMPLEFORMAT_VOID:
1080 *va_arg(ap, uint16_t*) = DATATYPE_VOID;
1081 break;
1082 }
1083 break;
1084 case TIFFTAG_SAMPLEFORMAT:
1085 *va_arg(ap, uint16_t*) = td->td_sampleformat;
1086 break;
1087 case TIFFTAG_IMAGEDEPTH:
1088 *va_arg(ap, uint32_t*) = td->td_imagedepth;
1089 break;
1090 case TIFFTAG_SUBIFD:
1091 *va_arg(ap, uint16_t*) = td->td_nsubifd;
1092 *va_arg(ap, const uint64_t**) = td->td_subifd;
1093 break;
1094 case TIFFTAG_YCBCRPOSITIONING:
1095 *va_arg(ap, uint16_t*) = td->td_ycbcrpositioning;
1096 break;
1097 case TIFFTAG_YCBCRSUBSAMPLING:
1098 *va_arg(ap, uint16_t*) = td->td_ycbcrsubsampling[0];
1099 *va_arg(ap, uint16_t*) = td->td_ycbcrsubsampling[1];
1100 break;
1101 case TIFFTAG_TRANSFERFUNCTION:
1102 *va_arg(ap, const uint16_t**) = td->td_transferfunction[0];
1103 if (td->td_samplesperpixel - td->td_extrasamples > 1) {
1104 *va_arg(ap, const uint16_t**) = td->td_transferfunction[1];
1105 *va_arg(ap, const uint16_t**) = td->td_transferfunction[2];
1106 } else {
1107 *va_arg(ap, const uint16_t**) = NULL;
1108 *va_arg(ap, const uint16_t**) = NULL;
1109 }
1110 break;
1111 case TIFFTAG_REFERENCEBLACKWHITE:
1112 *va_arg(ap, const float**) = td->td_refblackwhite;
1113 break;
1114 case TIFFTAG_INKNAMES:
1115 *va_arg(ap, const char**) = td->td_inknames;
1116 break;
1117 default:
1118 {
1119 int i;
1120
1121 /*
1122 * This can happen if multiple images are open
1123 * with different codecs which have private
1124 * tags. The global tag information table may
1125 * then have tags that are valid for one file
1126 * but not the other. If the client tries to
1127 * get a tag that is not valid for the image's
1128 * codec then we'll arrive here.
1129 */
1130 if( fip->field_bit != FIELD_CUSTOM )
1131 {
1132 TIFFErrorExt(tif->tif_clientdata, "_TIFFVGetField",
1133 "%s: Invalid %stag \"%s\" "
1134 "(not supported by codec)",
1135 tif->tif_name,
1136 isPseudoTag(tag) ? "pseudo-" : "",
1137 fip->field_name);
1138 ret_val = 0;
1139 break;
1140 }
1141
1142 /*
1143 * Do we have a custom value?
1144 */
1145 ret_val = 0;
1146 for (i = 0; i < td->td_customValueCount; i++) {
1147 TIFFTagValue *tv = td->td_customValues + i;
1148
1149 if (tv->info->field_tag != tag)
1150 continue;
1151
1152 if (fip->field_passcount) {
1153 if (fip->field_readcount == TIFF_VARIABLE2)
1154 *va_arg(ap, uint32_t*) = (uint32_t)tv->count;
1155 else /* Assume TIFF_VARIABLE */
1156 *va_arg(ap, uint16_t*) = (uint16_t)tv->count;
1157 *va_arg(ap, const void **) = tv->value;
1158 ret_val = 1;
1159 } else if (fip->field_tag == TIFFTAG_DOTRANGE
1160 && strcmp(fip->field_name,"DotRange") == 0) {
1161 /* TODO: This is an evil exception and should not have been
1162 handled this way ... likely best if we move it into
1163 the directory structure with an explicit field in
1164 libtiff 4.1 and assign it a FIELD_ value */
1165 *va_arg(ap, uint16_t*) = ((uint16_t *)tv->value)[0];
1166 *va_arg(ap, uint16_t*) = ((uint16_t *)tv->value)[1];
1167 ret_val = 1;
1168 } else {
1169 if (fip->field_type == TIFF_ASCII
1170 || fip->field_readcount == TIFF_VARIABLE
1171 || fip->field_readcount == TIFF_VARIABLE2
1172 || fip->field_readcount == TIFF_SPP
1173 || tv->count > 1) {
1174 *va_arg(ap, void **) = tv->value;
1175 ret_val = 1;
1176 } else {
1177 char *val = (char *)tv->value;
1178 assert( tv->count == 1 );
1179 switch (fip->field_type) {
1180 case TIFF_BYTE:
1181 case TIFF_UNDEFINED:
1182 *va_arg(ap, uint8_t*) =
1183 *(uint8_t *)val;
1184 ret_val = 1;
1185 break;
1186 case TIFF_SBYTE:
1187 *va_arg(ap, int8_t*) =
1188 *(int8_t *)val;
1189 ret_val = 1;
1190 break;
1191 case TIFF_SHORT:
1192 *va_arg(ap, uint16_t*) =
1193 *(uint16_t *)val;
1194 ret_val = 1;
1195 break;
1196 case TIFF_SSHORT:
1197 *va_arg(ap, int16_t*) =
1198 *(int16_t *)val;
1199 ret_val = 1;
1200 break;
1201 case TIFF_LONG:
1202 case TIFF_IFD:
1203 *va_arg(ap, uint32_t*) =
1204 *(uint32_t *)val;
1205 ret_val = 1;
1206 break;
1207 case TIFF_SLONG:
1208 *va_arg(ap, int32_t*) =
1209 *(int32_t *)val;
1210 ret_val = 1;
1211 break;
1212 case TIFF_LONG8:
1213 case TIFF_IFD8:
1214 *va_arg(ap, uint64_t*) =
1215 *(uint64_t *)val;
1216 ret_val = 1;
1217 break;
1218 case TIFF_SLONG8:
1219 *va_arg(ap, int64_t*) =
1220 *(int64_t *)val;
1221 ret_val = 1;
1222 break;
1223 case TIFF_RATIONAL:
1224 case TIFF_SRATIONAL:
1225 {
1226 /*-- Rational2Double: For Rationals evaluate "set_field_type" to determine internal storage size and return value size. */
1227 int tv_size = _TIFFSetGetFieldSize(fip->set_field_type);
1228 if (tv_size == 8) {
1229 *va_arg(ap, double*) = *(double *)val;
1230 ret_val = 1;
1231 } else {
1232 /*-- default should be tv_size == 4 */
1233 *va_arg(ap, float*) = *(float *)val;
1234 ret_val = 1;
1235 /*-- ToDo: After Testing, this should be removed and tv_size==4 should be set as default. */
1236 if (tv_size != 4) {
1237 TIFFErrorExt(0,"TIFFLib: _TIFFVGetField()", "Rational2Double: .set_field_type in not 4 but %d", tv_size);
1238 }
1239 }
1240 }
1241 break;
1242 case TIFF_FLOAT:
1243 *va_arg(ap, float*) =
1244 *(float *)val;
1245 ret_val = 1;
1246 break;
1247 case TIFF_DOUBLE:
1248 *va_arg(ap, double*) =
1249 *(double *)val;
1250 ret_val = 1;
1251 break;
1252 default:
1253 ret_val = 0;
1254 break;
1255 }
1256 }
1257 }
1258 break;
1259 }
1260 }
1261 }
1262 return(ret_val);
1263 }
1264
1265 /*
1266 * Return the value of a field in the
1267 * internal directory structure.
1268 */
1269 int
TIFFGetField(TIFF * tif,uint32_t tag,...)1270 TIFFGetField(TIFF* tif, uint32_t tag, ...)
1271 {
1272 int status;
1273 va_list ap;
1274
1275 va_start(ap, tag);
1276 status = TIFFVGetField(tif, tag, ap);
1277 va_end(ap);
1278 return (status);
1279 }
1280
1281 /*
1282 * Like TIFFGetField, but taking a varargs
1283 * parameter list. This routine is useful
1284 * for building higher-level interfaces on
1285 * top of the library.
1286 */
1287 int
TIFFVGetField(TIFF * tif,uint32_t tag,va_list ap)1288 TIFFVGetField(TIFF* tif, uint32_t tag, va_list ap)
1289 {
1290 const TIFFField* fip = TIFFFindField(tif, tag, TIFF_ANY);
1291 return (fip && (isPseudoTag(tag) || TIFFFieldSet(tif, fip->field_bit)) ?
1292 (*tif->tif_tagmethods.vgetfield)(tif, tag, ap) : 0);
1293 }
1294
1295 #define CleanupField(member) { \
1296 if (td->member) { \
1297 _TIFFfree(td->member); \
1298 td->member = 0; \
1299 } \
1300 }
1301
1302 /*
1303 * Release storage associated with a directory.
1304 */
1305 void
TIFFFreeDirectory(TIFF * tif)1306 TIFFFreeDirectory(TIFF* tif)
1307 {
1308 TIFFDirectory *td = &tif->tif_dir;
1309 int i;
1310
1311 _TIFFmemset(td->td_fieldsset, 0, FIELD_SETLONGS);
1312 CleanupField(td_sminsamplevalue);
1313 CleanupField(td_smaxsamplevalue);
1314 CleanupField(td_colormap[0]);
1315 CleanupField(td_colormap[1]);
1316 CleanupField(td_colormap[2]);
1317 CleanupField(td_sampleinfo);
1318 CleanupField(td_subifd);
1319 CleanupField(td_inknames);
1320 CleanupField(td_refblackwhite);
1321 CleanupField(td_transferfunction[0]);
1322 CleanupField(td_transferfunction[1]);
1323 CleanupField(td_transferfunction[2]);
1324 CleanupField(td_stripoffset_p);
1325 CleanupField(td_stripbytecount_p);
1326 td->td_stripoffsetbyteallocsize = 0;
1327 TIFFClrFieldBit(tif, FIELD_YCBCRSUBSAMPLING);
1328 TIFFClrFieldBit(tif, FIELD_YCBCRPOSITIONING);
1329
1330 /* Cleanup custom tag values */
1331 for( i = 0; i < td->td_customValueCount; i++ ) {
1332 if (td->td_customValues[i].value)
1333 _TIFFfree(td->td_customValues[i].value);
1334 }
1335
1336 td->td_customValueCount = 0;
1337 CleanupField(td_customValues);
1338
1339 _TIFFmemset( &(td->td_stripoffset_entry), 0, sizeof(TIFFDirEntry));
1340 _TIFFmemset( &(td->td_stripbytecount_entry), 0, sizeof(TIFFDirEntry));
1341 }
1342 #undef CleanupField
1343
1344 /*
1345 * Client Tag extension support (from Niles Ritter).
1346 */
1347 static TIFFExtendProc _TIFFextender = (TIFFExtendProc) NULL;
1348
1349 TIFFExtendProc
TIFFSetTagExtender(TIFFExtendProc extender)1350 TIFFSetTagExtender(TIFFExtendProc extender)
1351 {
1352 TIFFExtendProc prev = _TIFFextender;
1353 _TIFFextender = extender;
1354 return (prev);
1355 }
1356
1357 /*
1358 * Setup for a new directory. Should we automatically call
1359 * TIFFWriteDirectory() if the current one is dirty?
1360 *
1361 * The newly created directory will not exist on the file till
1362 * TIFFWriteDirectory(), TIFFFlush() or TIFFClose() is called.
1363 */
1364 int
TIFFCreateDirectory(TIFF * tif)1365 TIFFCreateDirectory(TIFF* tif)
1366 {
1367 TIFFDefaultDirectory(tif);
1368 tif->tif_diroff = 0;
1369 tif->tif_nextdiroff = 0;
1370 tif->tif_curoff = 0;
1371 tif->tif_row = (uint32_t) -1;
1372 tif->tif_curstrip = (uint32_t) -1;
1373
1374 return 0;
1375 }
1376
1377 int
TIFFCreateCustomDirectory(TIFF * tif,const TIFFFieldArray * infoarray)1378 TIFFCreateCustomDirectory(TIFF* tif, const TIFFFieldArray* infoarray)
1379 {
1380 TIFFDefaultDirectory(tif);
1381
1382 /*
1383 * Reset the field definitions to match the application provided list.
1384 * Hopefully TIFFDefaultDirectory() won't have done anything irreversible
1385 * based on it's assumption this is an image directory.
1386 */
1387 _TIFFSetupFields(tif, infoarray);
1388
1389 tif->tif_diroff = 0;
1390 tif->tif_nextdiroff = 0;
1391 tif->tif_curoff = 0;
1392 tif->tif_row = (uint32_t) -1;
1393 tif->tif_curstrip = (uint32_t) -1;
1394
1395 return 0;
1396 }
1397
1398 int
TIFFCreateEXIFDirectory(TIFF * tif)1399 TIFFCreateEXIFDirectory(TIFF* tif)
1400 {
1401 const TIFFFieldArray* exifFieldArray;
1402 exifFieldArray = _TIFFGetExifFields();
1403 return TIFFCreateCustomDirectory(tif, exifFieldArray);
1404 }
1405
1406 /*
1407 * Creates the EXIF GPS custom directory
1408 */
1409 int
TIFFCreateGPSDirectory(TIFF * tif)1410 TIFFCreateGPSDirectory(TIFF* tif)
1411 {
1412 const TIFFFieldArray* gpsFieldArray;
1413 gpsFieldArray = _TIFFGetGpsFields();
1414 return TIFFCreateCustomDirectory(tif, gpsFieldArray);
1415 }
1416
1417 /*
1418 * Setup a default directory structure.
1419 */
1420 int
TIFFDefaultDirectory(TIFF * tif)1421 TIFFDefaultDirectory(TIFF* tif)
1422 {
1423 register TIFFDirectory* td = &tif->tif_dir;
1424 const TIFFFieldArray* tiffFieldArray;
1425
1426 tiffFieldArray = _TIFFGetFields();
1427 _TIFFSetupFields(tif, tiffFieldArray);
1428
1429 _TIFFmemset(td, 0, sizeof (*td));
1430 td->td_fillorder = FILLORDER_MSB2LSB;
1431 td->td_bitspersample = 1;
1432 td->td_threshholding = THRESHHOLD_BILEVEL;
1433 td->td_orientation = ORIENTATION_TOPLEFT;
1434 td->td_samplesperpixel = 1;
1435 td->td_rowsperstrip = (uint32_t) -1;
1436 td->td_tilewidth = 0;
1437 td->td_tilelength = 0;
1438 td->td_tiledepth = 1;
1439 #ifdef STRIPBYTECOUNTSORTED_UNUSED
1440 td->td_stripbytecountsorted = 1; /* Our own arrays always sorted. */
1441 #endif
1442 td->td_resolutionunit = RESUNIT_INCH;
1443 td->td_sampleformat = SAMPLEFORMAT_UINT;
1444 td->td_imagedepth = 1;
1445 td->td_ycbcrsubsampling[0] = 2;
1446 td->td_ycbcrsubsampling[1] = 2;
1447 td->td_ycbcrpositioning = YCBCRPOSITION_CENTERED;
1448 tif->tif_postdecode = _TIFFNoPostDecode;
1449 tif->tif_foundfield = NULL;
1450 tif->tif_tagmethods.vsetfield = _TIFFVSetField;
1451 tif->tif_tagmethods.vgetfield = _TIFFVGetField;
1452 tif->tif_tagmethods.printdir = NULL;
1453 /*
1454 * Give client code a chance to install their own
1455 * tag extensions & methods, prior to compression overloads,
1456 * but do some prior cleanup first. (http://trac.osgeo.org/gdal/ticket/5054)
1457 */
1458 if (tif->tif_nfieldscompat > 0) {
1459 uint32_t i;
1460
1461 for (i = 0; i < tif->tif_nfieldscompat; i++) {
1462 if (tif->tif_fieldscompat[i].allocated_size)
1463 _TIFFfree(tif->tif_fieldscompat[i].fields);
1464 }
1465 _TIFFfree(tif->tif_fieldscompat);
1466 tif->tif_nfieldscompat = 0;
1467 tif->tif_fieldscompat = NULL;
1468 }
1469 if (_TIFFextender)
1470 (*_TIFFextender)(tif);
1471 (void) TIFFSetField(tif, TIFFTAG_COMPRESSION, COMPRESSION_NONE);
1472 /*
1473 * NB: The directory is marked dirty as a result of setting
1474 * up the default compression scheme. However, this really
1475 * isn't correct -- we want TIFF_DIRTYDIRECT to be set only
1476 * if the user does something. We could just do the setup
1477 * by hand, but it seems better to use the normal mechanism
1478 * (i.e. TIFFSetField).
1479 */
1480 tif->tif_flags &= ~TIFF_DIRTYDIRECT;
1481
1482 /*
1483 * As per http://bugzilla.remotesensing.org/show_bug.cgi?id=19
1484 * we clear the ISTILED flag when setting up a new directory.
1485 * Should we also be clearing stuff like INSUBIFD?
1486 */
1487 tif->tif_flags &= ~TIFF_ISTILED;
1488
1489 return (1);
1490 }
1491
1492 static int
TIFFAdvanceDirectory(TIFF * tif,uint64_t * nextdir,uint64_t * off)1493 TIFFAdvanceDirectory(TIFF* tif, uint64_t* nextdir, uint64_t* off)
1494 {
1495 static const char module[] = "TIFFAdvanceDirectory";
1496 if (isMapped(tif))
1497 {
1498 uint64_t poff=*nextdir;
1499 if (!(tif->tif_flags&TIFF_BIGTIFF))
1500 {
1501 tmsize_t poffa,poffb,poffc,poffd;
1502 uint16_t dircount;
1503 uint32_t nextdir32;
1504 poffa=(tmsize_t)poff;
1505 poffb=poffa+sizeof(uint16_t);
1506 if (((uint64_t)poffa != poff) || (poffb < poffa) || (poffb < (tmsize_t)sizeof(uint16_t)) || (poffb > tif->tif_size))
1507 {
1508 TIFFErrorExt(tif->tif_clientdata,module,"Error fetching directory count");
1509 *nextdir=0;
1510 return(0);
1511 }
1512 _TIFFmemcpy(&dircount,tif->tif_base+poffa,sizeof(uint16_t));
1513 if (tif->tif_flags&TIFF_SWAB)
1514 TIFFSwabShort(&dircount);
1515 poffc=poffb+dircount*12;
1516 poffd=poffc+sizeof(uint32_t);
1517 if ((poffc<poffb) || (poffc<dircount*12) || (poffd<poffc) || (poffd<(tmsize_t)sizeof(uint32_t)) || (poffd > tif->tif_size))
1518 {
1519 TIFFErrorExt(tif->tif_clientdata,module,"Error fetching directory link");
1520 return(0);
1521 }
1522 if (off!=NULL)
1523 *off=(uint64_t)poffc;
1524 _TIFFmemcpy(&nextdir32,tif->tif_base+poffc,sizeof(uint32_t));
1525 if (tif->tif_flags&TIFF_SWAB)
1526 TIFFSwabLong(&nextdir32);
1527 *nextdir=nextdir32;
1528 }
1529 else
1530 {
1531 tmsize_t poffa,poffb,poffc,poffd;
1532 uint64_t dircount64;
1533 uint16_t dircount16;
1534 poffa=(tmsize_t)poff;
1535 poffb=poffa+sizeof(uint64_t);
1536 if (((uint64_t)poffa != poff) || (poffb < poffa) || (poffb < (tmsize_t)sizeof(uint64_t)) || (poffb > tif->tif_size))
1537 {
1538 TIFFErrorExt(tif->tif_clientdata,module,"Error fetching directory count");
1539 return(0);
1540 }
1541 _TIFFmemcpy(&dircount64,tif->tif_base+poffa,sizeof(uint64_t));
1542 if (tif->tif_flags&TIFF_SWAB)
1543 TIFFSwabLong8(&dircount64);
1544 if (dircount64>0xFFFF)
1545 {
1546 TIFFErrorExt(tif->tif_clientdata,module,"Sanity check on directory count failed");
1547 return(0);
1548 }
1549 dircount16=(uint16_t)dircount64;
1550 poffc=poffb+dircount16*20;
1551 poffd=poffc+sizeof(uint64_t);
1552 if ((poffc<poffb) || (poffc<dircount16*20) || (poffd<poffc) || (poffd<(tmsize_t)sizeof(uint64_t)) || (poffd > tif->tif_size))
1553 {
1554 TIFFErrorExt(tif->tif_clientdata,module,"Error fetching directory link");
1555 return(0);
1556 }
1557 if (off!=NULL)
1558 *off=(uint64_t)poffc;
1559 _TIFFmemcpy(nextdir,tif->tif_base+poffc,sizeof(uint64_t));
1560 if (tif->tif_flags&TIFF_SWAB)
1561 TIFFSwabLong8(nextdir);
1562 }
1563 return(1);
1564 }
1565 else
1566 {
1567 if (!(tif->tif_flags&TIFF_BIGTIFF))
1568 {
1569 uint16_t dircount;
1570 uint32_t nextdir32;
1571 if (!SeekOK(tif, *nextdir) ||
1572 !ReadOK(tif, &dircount, sizeof (uint16_t))) {
1573 TIFFErrorExt(tif->tif_clientdata, module, "%s: Error fetching directory count",
1574 tif->tif_name);
1575 return (0);
1576 }
1577 if (tif->tif_flags & TIFF_SWAB)
1578 TIFFSwabShort(&dircount);
1579 if (off != NULL)
1580 *off = TIFFSeekFile(tif,
1581 dircount*12, SEEK_CUR);
1582 else
1583 (void) TIFFSeekFile(tif,
1584 dircount*12, SEEK_CUR);
1585 if (!ReadOK(tif, &nextdir32, sizeof (uint32_t))) {
1586 TIFFErrorExt(tif->tif_clientdata, module, "%s: Error fetching directory link",
1587 tif->tif_name);
1588 return (0);
1589 }
1590 if (tif->tif_flags & TIFF_SWAB)
1591 TIFFSwabLong(&nextdir32);
1592 *nextdir=nextdir32;
1593 }
1594 else
1595 {
1596 uint64_t dircount64;
1597 uint16_t dircount16;
1598 if (!SeekOK(tif, *nextdir) ||
1599 !ReadOK(tif, &dircount64, sizeof (uint64_t))) {
1600 TIFFErrorExt(tif->tif_clientdata, module, "%s: Error fetching directory count",
1601 tif->tif_name);
1602 return (0);
1603 }
1604 if (tif->tif_flags & TIFF_SWAB)
1605 TIFFSwabLong8(&dircount64);
1606 if (dircount64>0xFFFF)
1607 {
1608 TIFFErrorExt(tif->tif_clientdata, module, "Error fetching directory count");
1609 return(0);
1610 }
1611 dircount16 = (uint16_t)dircount64;
1612 if (off != NULL)
1613 *off = TIFFSeekFile(tif,
1614 dircount16*20, SEEK_CUR);
1615 else
1616 (void) TIFFSeekFile(tif,
1617 dircount16*20, SEEK_CUR);
1618 if (!ReadOK(tif, nextdir, sizeof (uint64_t))) {
1619 TIFFErrorExt(tif->tif_clientdata, module,
1620 "%s: Error fetching directory link",
1621 tif->tif_name);
1622 return (0);
1623 }
1624 if (tif->tif_flags & TIFF_SWAB)
1625 TIFFSwabLong8(nextdir);
1626 }
1627 return (1);
1628 }
1629 }
1630
1631 /*
1632 * Count the number of directories in a file.
1633 */
1634 uint16_t
TIFFNumberOfDirectories(TIFF * tif)1635 TIFFNumberOfDirectories(TIFF* tif)
1636 {
1637 static const char module[] = "TIFFNumberOfDirectories";
1638 uint64_t nextdir;
1639 uint16_t n;
1640 if (!(tif->tif_flags&TIFF_BIGTIFF))
1641 nextdir = tif->tif_header.classic.tiff_diroff;
1642 else
1643 nextdir = tif->tif_header.big.tiff_diroff;
1644 n = 0;
1645 while (nextdir != 0 && TIFFAdvanceDirectory(tif, &nextdir, NULL))
1646 {
1647 if (n != 65535) {
1648 ++n;
1649 }
1650 else
1651 {
1652 TIFFErrorExt(tif->tif_clientdata, module,
1653 "Directory count exceeded 65535 limit,"
1654 " giving up on counting.");
1655 return (65535);
1656 }
1657 }
1658 return (n);
1659 }
1660
1661 /*
1662 * Set the n-th directory as the current directory.
1663 * NB: Directories are numbered starting at 0.
1664 */
1665 int
TIFFSetDirectory(TIFF * tif,uint16_t dirn)1666 TIFFSetDirectory(TIFF* tif, uint16_t dirn)
1667 {
1668 uint64_t nextdir;
1669 uint16_t n;
1670
1671 if (!(tif->tif_flags&TIFF_BIGTIFF))
1672 nextdir = tif->tif_header.classic.tiff_diroff;
1673 else
1674 nextdir = tif->tif_header.big.tiff_diroff;
1675 for (n = dirn; n > 0 && nextdir != 0; n--)
1676 if (!TIFFAdvanceDirectory(tif, &nextdir, NULL))
1677 return (0);
1678 tif->tif_nextdiroff = nextdir;
1679 /*
1680 * Set curdir to the actual directory index. The
1681 * -1 is because TIFFReadDirectory will increment
1682 * tif_curdir after successfully reading the directory.
1683 */
1684 tif->tif_curdir = (dirn - n) - 1;
1685 /*
1686 * Reset tif_dirnumber counter and start new list of seen directories.
1687 * We need this to prevent IFD loops.
1688 */
1689 tif->tif_dirnumber = 0;
1690 return (TIFFReadDirectory(tif));
1691 }
1692
1693 /*
1694 * Set the current directory to be the directory
1695 * located at the specified file offset. This interface
1696 * is used mainly to access directories linked with
1697 * the SubIFD tag (e.g. thumbnail images).
1698 */
1699 int
TIFFSetSubDirectory(TIFF * tif,uint64_t diroff)1700 TIFFSetSubDirectory(TIFF* tif, uint64_t diroff)
1701 {
1702 tif->tif_nextdiroff = diroff;
1703 /*
1704 * Reset tif_dirnumber counter and start new list of seen directories.
1705 * We need this to prevent IFD loops.
1706 */
1707 tif->tif_dirnumber = 0;
1708 return (TIFFReadDirectory(tif));
1709 }
1710
1711 /*
1712 * Return file offset of the current directory.
1713 */
1714 uint64_t
TIFFCurrentDirOffset(TIFF * tif)1715 TIFFCurrentDirOffset(TIFF* tif)
1716 {
1717 return (tif->tif_diroff);
1718 }
1719
1720 /*
1721 * Return an indication of whether or not we are
1722 * at the last directory in the file.
1723 */
1724 int
TIFFLastDirectory(TIFF * tif)1725 TIFFLastDirectory(TIFF* tif)
1726 {
1727 return (tif->tif_nextdiroff == 0);
1728 }
1729
1730 /*
1731 * Unlink the specified directory from the directory chain.
1732 */
1733 int
TIFFUnlinkDirectory(TIFF * tif,uint16_t dirn)1734 TIFFUnlinkDirectory(TIFF* tif, uint16_t dirn)
1735 {
1736 static const char module[] = "TIFFUnlinkDirectory";
1737 uint64_t nextdir;
1738 uint64_t off;
1739 uint16_t n;
1740
1741 if (tif->tif_mode == O_RDONLY) {
1742 TIFFErrorExt(tif->tif_clientdata, module,
1743 "Can not unlink directory in read-only file");
1744 return (0);
1745 }
1746 /*
1747 * Go to the directory before the one we want
1748 * to unlink and nab the offset of the link
1749 * field we'll need to patch.
1750 */
1751 if (!(tif->tif_flags&TIFF_BIGTIFF))
1752 {
1753 nextdir = tif->tif_header.classic.tiff_diroff;
1754 off = 4;
1755 }
1756 else
1757 {
1758 nextdir = tif->tif_header.big.tiff_diroff;
1759 off = 8;
1760 }
1761 for (n = dirn-1; n > 0; n--) {
1762 if (nextdir == 0) {
1763 TIFFErrorExt(tif->tif_clientdata, module, "Directory %"PRIu16" does not exist", dirn);
1764 return (0);
1765 }
1766 if (!TIFFAdvanceDirectory(tif, &nextdir, &off))
1767 return (0);
1768 }
1769 /*
1770 * Advance to the directory to be unlinked and fetch
1771 * the offset of the directory that follows.
1772 */
1773 if (!TIFFAdvanceDirectory(tif, &nextdir, NULL))
1774 return (0);
1775 /*
1776 * Go back and patch the link field of the preceding
1777 * directory to point to the offset of the directory
1778 * that follows.
1779 */
1780 (void) TIFFSeekFile(tif, off, SEEK_SET);
1781 if (!(tif->tif_flags&TIFF_BIGTIFF))
1782 {
1783 uint32_t nextdir32;
1784 nextdir32=(uint32_t)nextdir;
1785 assert((uint64_t)nextdir32 == nextdir);
1786 if (tif->tif_flags & TIFF_SWAB)
1787 TIFFSwabLong(&nextdir32);
1788 if (!WriteOK(tif, &nextdir32, sizeof (uint32_t))) {
1789 TIFFErrorExt(tif->tif_clientdata, module, "Error writing directory link");
1790 return (0);
1791 }
1792 }
1793 else
1794 {
1795 if (tif->tif_flags & TIFF_SWAB)
1796 TIFFSwabLong8(&nextdir);
1797 if (!WriteOK(tif, &nextdir, sizeof (uint64_t))) {
1798 TIFFErrorExt(tif->tif_clientdata, module, "Error writing directory link");
1799 return (0);
1800 }
1801 }
1802 /*
1803 * Leave directory state setup safely. We don't have
1804 * facilities for doing inserting and removing directories,
1805 * so it's safest to just invalidate everything. This
1806 * means that the caller can only append to the directory
1807 * chain.
1808 */
1809 (*tif->tif_cleanup)(tif);
1810 if ((tif->tif_flags & TIFF_MYBUFFER) && tif->tif_rawdata) {
1811 _TIFFfree(tif->tif_rawdata);
1812 tif->tif_rawdata = NULL;
1813 tif->tif_rawcc = 0;
1814 tif->tif_rawdataoff = 0;
1815 tif->tif_rawdataloaded = 0;
1816 }
1817 tif->tif_flags &= ~(TIFF_BEENWRITING|TIFF_BUFFERSETUP|TIFF_POSTENCODE|TIFF_BUF4WRITE);
1818 TIFFFreeDirectory(tif);
1819 TIFFDefaultDirectory(tif);
1820 tif->tif_diroff = 0; /* force link on next write */
1821 tif->tif_nextdiroff = 0; /* next write must be at end */
1822 tif->tif_curoff = 0;
1823 tif->tif_row = (uint32_t) -1;
1824 tif->tif_curstrip = (uint32_t) -1;
1825 return (1);
1826 }
1827
1828 /* vim: set ts=8 sts=8 sw=8 noet: */
1829 /*
1830 * Local Variables:
1831 * mode: c
1832 * c-basic-offset: 8
1833 * fill-column: 78
1834 * End:
1835 */
1836