1 /* $Id: tif_dirwrite.c,v 1.85 2017-01-11 16:09:02 erouault Exp $ */
2
3 /*
4 * Copyright (c) 1988-1997 Sam Leffler
5 * Copyright (c) 1991-1997 Silicon Graphics, Inc.
6 *
7 * Permission to use, copy, modify, distribute, and sell this software and
8 * its documentation for any purpose is hereby granted without fee, provided
9 * that (i) the above copyright notices and this permission notice appear in
10 * all copies of the software and related documentation, and (ii) the names of
11 * Sam Leffler and Silicon Graphics may not be used in any advertising or
12 * publicity relating to the software without the specific, prior written
13 * permission of Sam Leffler and Silicon Graphics.
14 *
15 * THE SOFTWARE IS PROVIDED "AS-IS" AND WITHOUT WARRANTY OF ANY KIND,
16 * EXPRESS, IMPLIED OR OTHERWISE, INCLUDING WITHOUT LIMITATION, ANY
17 * WARRANTY OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE.
18 *
19 * IN NO EVENT SHALL SAM LEFFLER OR SILICON GRAPHICS BE LIABLE FOR
20 * ANY SPECIAL, INCIDENTAL, INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND,
21 * OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS,
22 * WHETHER OR NOT ADVISED OF THE POSSIBILITY OF DAMAGE, AND ON ANY THEORY OF
23 * LIABILITY, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE
24 * OF THIS SOFTWARE.
25 */
26
27 /*
28 * TIFF Library.
29 *
30 * Directory Write Support Routines.
31 */
32 #include "tiffiop.h"
33 #include <float.h>
34
35 #ifdef HAVE_IEEEFP
36 #define TIFFCvtNativeToIEEEFloat(tif, n, fp)
37 #define TIFFCvtNativeToIEEEDouble(tif, n, dp)
38 #else
39 extern void TIFFCvtNativeToIEEEFloat(TIFF* tif, uint32 n, float* fp);
40 extern void TIFFCvtNativeToIEEEDouble(TIFF* tif, uint32 n, double* dp);
41 #endif
42
43 static int TIFFWriteDirectorySec(TIFF* tif, int isimage, int imagedone, uint64* pdiroff);
44
45 static int TIFFWriteDirectoryTagSampleformatArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, double* value);
46 #if 0
47 static int TIFFWriteDirectoryTagSampleformatPerSample(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, double value);
48 #endif
49
50 static int TIFFWriteDirectoryTagAscii(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, char* value);
51 static int TIFFWriteDirectoryTagUndefinedArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, uint8* value);
52 #ifdef notdef
53 static int TIFFWriteDirectoryTagByte(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint8 value);
54 #endif
55 static int TIFFWriteDirectoryTagByteArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, uint8* value);
56 #if 0
57 static int TIFFWriteDirectoryTagBytePerSample(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint8 value);
58 #endif
59 #ifdef notdef
60 static int TIFFWriteDirectoryTagSbyte(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, int8 value);
61 #endif
62 static int TIFFWriteDirectoryTagSbyteArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, int8* value);
63 #if 0
64 static int TIFFWriteDirectoryTagSbytePerSample(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, int8 value);
65 #endif
66 static int TIFFWriteDirectoryTagShort(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint16 value);
67 static int TIFFWriteDirectoryTagShortArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, uint16* value);
68 static int TIFFWriteDirectoryTagShortPerSample(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint16 value);
69 #ifdef notdef
70 static int TIFFWriteDirectoryTagSshort(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, int16 value);
71 #endif
72 static int TIFFWriteDirectoryTagSshortArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, int16* value);
73 #if 0
74 static int TIFFWriteDirectoryTagSshortPerSample(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, int16 value);
75 #endif
76 static int TIFFWriteDirectoryTagLong(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 value);
77 static int TIFFWriteDirectoryTagLongArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, uint32* value);
78 #if 0
79 static int TIFFWriteDirectoryTagLongPerSample(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 value);
80 #endif
81 #ifdef notdef
82 static int TIFFWriteDirectoryTagSlong(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, int32 value);
83 #endif
84 static int TIFFWriteDirectoryTagSlongArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, int32* value);
85 #if 0
86 static int TIFFWriteDirectoryTagSlongPerSample(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, int32 value);
87 #endif
88 #ifdef notdef
89 static int TIFFWriteDirectoryTagLong8(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint64 value);
90 #endif
91 static int TIFFWriteDirectoryTagLong8Array(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, uint64* value);
92 #ifdef notdef
93 static int TIFFWriteDirectoryTagSlong8(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, int64 value);
94 #endif
95 static int TIFFWriteDirectoryTagSlong8Array(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, int64* value);
96 static int TIFFWriteDirectoryTagRational(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, double value);
97 static int TIFFWriteDirectoryTagRationalArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, float* value);
98 static int TIFFWriteDirectoryTagSrationalArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, float* value);
99 #ifdef notdef
100 static int TIFFWriteDirectoryTagFloat(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, float value);
101 #endif
102 static int TIFFWriteDirectoryTagFloatArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, float* value);
103 #if 0
104 static int TIFFWriteDirectoryTagFloatPerSample(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, float value);
105 #endif
106 #ifdef notdef
107 static int TIFFWriteDirectoryTagDouble(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, double value);
108 #endif
109 static int TIFFWriteDirectoryTagDoubleArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, double* value);
110 #if 0
111 static int TIFFWriteDirectoryTagDoublePerSample(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, double value);
112 #endif
113 static int TIFFWriteDirectoryTagIfdArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, uint32* value);
114 #ifdef notdef
115 static int TIFFWriteDirectoryTagIfd8Array(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, uint64* value);
116 #endif
117 static int TIFFWriteDirectoryTagShortLong(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 value);
118 static int TIFFWriteDirectoryTagLongLong8Array(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, uint64* value);
119 static int TIFFWriteDirectoryTagIfdIfd8Array(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, uint64* value);
120 #ifdef notdef
121 static int TIFFWriteDirectoryTagShortLongLong8Array(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, uint64* value);
122 #endif
123 static int TIFFWriteDirectoryTagColormap(TIFF* tif, uint32* ndir, TIFFDirEntry* dir);
124 static int TIFFWriteDirectoryTagTransferfunction(TIFF* tif, uint32* ndir, TIFFDirEntry* dir);
125 static int TIFFWriteDirectoryTagSubifd(TIFF* tif, uint32* ndir, TIFFDirEntry* dir);
126
127 static int TIFFWriteDirectoryTagCheckedAscii(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, char* value);
128 static int TIFFWriteDirectoryTagCheckedUndefinedArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, uint8* value);
129 #ifdef notdef
130 static int TIFFWriteDirectoryTagCheckedByte(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint8 value);
131 #endif
132 static int TIFFWriteDirectoryTagCheckedByteArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, uint8* value);
133 #ifdef notdef
134 static int TIFFWriteDirectoryTagCheckedSbyte(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, int8 value);
135 #endif
136 static int TIFFWriteDirectoryTagCheckedSbyteArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, int8* value);
137 static int TIFFWriteDirectoryTagCheckedShort(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint16 value);
138 static int TIFFWriteDirectoryTagCheckedShortArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, uint16* value);
139 #ifdef notdef
140 static int TIFFWriteDirectoryTagCheckedSshort(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, int16 value);
141 #endif
142 static int TIFFWriteDirectoryTagCheckedSshortArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, int16* value);
143 static int TIFFWriteDirectoryTagCheckedLong(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 value);
144 static int TIFFWriteDirectoryTagCheckedLongArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, uint32* value);
145 #ifdef notdef
146 static int TIFFWriteDirectoryTagCheckedSlong(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, int32 value);
147 #endif
148 static int TIFFWriteDirectoryTagCheckedSlongArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, int32* value);
149 #ifdef notdef
150 static int TIFFWriteDirectoryTagCheckedLong8(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint64 value);
151 #endif
152 static int TIFFWriteDirectoryTagCheckedLong8Array(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, uint64* value);
153 #ifdef notdef
154 static int TIFFWriteDirectoryTagCheckedSlong8(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, int64 value);
155 #endif
156 static int TIFFWriteDirectoryTagCheckedSlong8Array(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, int64* value);
157 static int TIFFWriteDirectoryTagCheckedRational(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, double value);
158 static int TIFFWriteDirectoryTagCheckedRationalArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, float* value);
159 static int TIFFWriteDirectoryTagCheckedSrationalArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, float* value);
160 #ifdef notdef
161 static int TIFFWriteDirectoryTagCheckedFloat(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, float value);
162 #endif
163 static int TIFFWriteDirectoryTagCheckedFloatArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, float* value);
164 #ifdef notdef
165 static int TIFFWriteDirectoryTagCheckedDouble(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, double value);
166 #endif
167 static int TIFFWriteDirectoryTagCheckedDoubleArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, double* value);
168 static int TIFFWriteDirectoryTagCheckedIfdArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, uint32* value);
169 static int TIFFWriteDirectoryTagCheckedIfd8Array(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, uint64* value);
170
171 static int TIFFWriteDirectoryTagData(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint16 datatype, uint32 count, uint32 datalength, void* data);
172
173 static int TIFFLinkDirectory(TIFF*);
174
175 /*
176 * Write the contents of the current directory
177 * to the specified file. This routine doesn't
178 * handle overwriting a directory with auxiliary
179 * storage that's been changed.
180 */
181 int
TIFFWriteDirectory(TIFF * tif)182 TIFFWriteDirectory(TIFF* tif)
183 {
184 return TIFFWriteDirectorySec(tif,TRUE,TRUE,NULL);
185 }
186
187 /*
188 * Similar to TIFFWriteDirectory(), writes the directory out
189 * but leaves all data structures in memory so that it can be
190 * written again. This will make a partially written TIFF file
191 * readable before it is successfully completed/closed.
192 */
193 int
TIFFCheckpointDirectory(TIFF * tif)194 TIFFCheckpointDirectory(TIFF* tif)
195 {
196 int rc;
197 /* Setup the strips arrays, if they haven't already been. */
198 if (tif->tif_dir.td_stripoffset == NULL)
199 (void) TIFFSetupStrips(tif);
200 rc = TIFFWriteDirectorySec(tif,TRUE,FALSE,NULL);
201 (void) TIFFSetWriteOffset(tif, TIFFSeekFile(tif, 0, SEEK_END));
202 return rc;
203 }
204
205 int
TIFFWriteCustomDirectory(TIFF * tif,uint64 * pdiroff)206 TIFFWriteCustomDirectory(TIFF* tif, uint64* pdiroff)
207 {
208 return TIFFWriteDirectorySec(tif,FALSE,FALSE,pdiroff);
209 }
210
211 /*
212 * Similar to TIFFWriteDirectory(), but if the directory has already
213 * been written once, it is relocated to the end of the file, in case it
214 * has changed in size. Note that this will result in the loss of the
215 * previously used directory space.
216 */
217 int
TIFFRewriteDirectory(TIFF * tif)218 TIFFRewriteDirectory( TIFF *tif )
219 {
220 static const char module[] = "TIFFRewriteDirectory";
221
222 /* We don't need to do anything special if it hasn't been written. */
223 if( tif->tif_diroff == 0 )
224 return TIFFWriteDirectory( tif );
225
226 /*
227 * Find and zero the pointer to this directory, so that TIFFLinkDirectory
228 * will cause it to be added after this directories current pre-link.
229 */
230
231 if (!(tif->tif_flags&TIFF_BIGTIFF))
232 {
233 if (tif->tif_header.classic.tiff_diroff == tif->tif_diroff)
234 {
235 tif->tif_header.classic.tiff_diroff = 0;
236 tif->tif_diroff = 0;
237
238 TIFFSeekFile(tif,4,SEEK_SET);
239 if (!WriteOK(tif, &(tif->tif_header.classic.tiff_diroff),4))
240 {
241 TIFFErrorExt(tif->tif_clientdata, tif->tif_name,
242 "Error updating TIFF header");
243 return (0);
244 }
245 }
246 else
247 {
248 uint32 nextdir;
249 nextdir = tif->tif_header.classic.tiff_diroff;
250 while(1) {
251 uint16 dircount;
252 uint32 nextnextdir;
253
254 if (!SeekOK(tif, nextdir) ||
255 !ReadOK(tif, &dircount, 2)) {
256 TIFFErrorExt(tif->tif_clientdata, module,
257 "Error fetching directory count");
258 return (0);
259 }
260 if (tif->tif_flags & TIFF_SWAB)
261 TIFFSwabShort(&dircount);
262 (void) TIFFSeekFile(tif,
263 nextdir+2+dircount*12, SEEK_SET);
264 if (!ReadOK(tif, &nextnextdir, 4)) {
265 TIFFErrorExt(tif->tif_clientdata, module,
266 "Error fetching directory link");
267 return (0);
268 }
269 if (tif->tif_flags & TIFF_SWAB)
270 TIFFSwabLong(&nextnextdir);
271 if (nextnextdir==tif->tif_diroff)
272 {
273 uint32 m;
274 m=0;
275 (void) TIFFSeekFile(tif,
276 nextdir+2+dircount*12, SEEK_SET);
277 if (!WriteOK(tif, &m, 4)) {
278 TIFFErrorExt(tif->tif_clientdata, module,
279 "Error writing directory link");
280 return (0);
281 }
282 tif->tif_diroff=0;
283 break;
284 }
285 nextdir=nextnextdir;
286 }
287 }
288 }
289 else
290 {
291 if (tif->tif_header.big.tiff_diroff == tif->tif_diroff)
292 {
293 tif->tif_header.big.tiff_diroff = 0;
294 tif->tif_diroff = 0;
295
296 TIFFSeekFile(tif,8,SEEK_SET);
297 if (!WriteOK(tif, &(tif->tif_header.big.tiff_diroff),8))
298 {
299 TIFFErrorExt(tif->tif_clientdata, tif->tif_name,
300 "Error updating TIFF header");
301 return (0);
302 }
303 }
304 else
305 {
306 uint64 nextdir;
307 nextdir = tif->tif_header.big.tiff_diroff;
308 while(1) {
309 uint64 dircount64;
310 uint16 dircount;
311 uint64 nextnextdir;
312
313 if (!SeekOK(tif, nextdir) ||
314 !ReadOK(tif, &dircount64, 8)) {
315 TIFFErrorExt(tif->tif_clientdata, module,
316 "Error fetching directory count");
317 return (0);
318 }
319 if (tif->tif_flags & TIFF_SWAB)
320 TIFFSwabLong8(&dircount64);
321 if (dircount64>0xFFFF)
322 {
323 TIFFErrorExt(tif->tif_clientdata, module,
324 "Sanity check on tag count failed, likely corrupt TIFF");
325 return (0);
326 }
327 dircount=(uint16)dircount64;
328 (void) TIFFSeekFile(tif,
329 nextdir+8+dircount*20, SEEK_SET);
330 if (!ReadOK(tif, &nextnextdir, 8)) {
331 TIFFErrorExt(tif->tif_clientdata, module,
332 "Error fetching directory link");
333 return (0);
334 }
335 if (tif->tif_flags & TIFF_SWAB)
336 TIFFSwabLong8(&nextnextdir);
337 if (nextnextdir==tif->tif_diroff)
338 {
339 uint64 m;
340 m=0;
341 (void) TIFFSeekFile(tif,
342 nextdir+8+dircount*20, SEEK_SET);
343 if (!WriteOK(tif, &m, 8)) {
344 TIFFErrorExt(tif->tif_clientdata, module,
345 "Error writing directory link");
346 return (0);
347 }
348 tif->tif_diroff=0;
349 break;
350 }
351 nextdir=nextnextdir;
352 }
353 }
354 }
355
356 /*
357 * Now use TIFFWriteDirectory() normally.
358 */
359
360 return TIFFWriteDirectory( tif );
361 }
362
363 static int
TIFFWriteDirectorySec(TIFF * tif,int isimage,int imagedone,uint64 * pdiroff)364 TIFFWriteDirectorySec(TIFF* tif, int isimage, int imagedone, uint64* pdiroff)
365 {
366 static const char module[] = "TIFFWriteDirectorySec";
367 uint32 ndir;
368 TIFFDirEntry* dir;
369 uint32 dirsize;
370 void* dirmem;
371 uint32 m;
372 if (tif->tif_mode == O_RDONLY)
373 return (1);
374
375 _TIFFFillStriles( tif );
376
377 /*
378 * Clear write state so that subsequent images with
379 * different characteristics get the right buffers
380 * setup for them.
381 */
382 if (imagedone)
383 {
384 if (tif->tif_flags & TIFF_POSTENCODE)
385 {
386 tif->tif_flags &= ~TIFF_POSTENCODE;
387 if (!(*tif->tif_postencode)(tif))
388 {
389 TIFFErrorExt(tif->tif_clientdata,module,
390 "Error post-encoding before directory write");
391 return (0);
392 }
393 }
394 (*tif->tif_close)(tif); /* shutdown encoder */
395 /*
396 * Flush any data that might have been written
397 * by the compression close+cleanup routines. But
398 * be careful not to write stuff if we didn't add data
399 * in the previous steps as the "rawcc" data may well be
400 * a previously read tile/strip in mixed read/write mode.
401 */
402 if (tif->tif_rawcc > 0
403 && (tif->tif_flags & TIFF_BEENWRITING) != 0 )
404 {
405 if( !TIFFFlushData1(tif) )
406 {
407 TIFFErrorExt(tif->tif_clientdata, module,
408 "Error flushing data before directory write");
409 return (0);
410 }
411 }
412 if ((tif->tif_flags & TIFF_MYBUFFER) && tif->tif_rawdata)
413 {
414 _TIFFfree(tif->tif_rawdata);
415 tif->tif_rawdata = NULL;
416 tif->tif_rawcc = 0;
417 tif->tif_rawdatasize = 0;
418 tif->tif_rawdataoff = 0;
419 tif->tif_rawdataloaded = 0;
420 }
421 tif->tif_flags &= ~(TIFF_BEENWRITING|TIFF_BUFFERSETUP);
422 }
423 dir=NULL;
424 dirmem=NULL;
425 dirsize=0;
426 while (1)
427 {
428 ndir=0;
429 if (isimage)
430 {
431 if (TIFFFieldSet(tif,FIELD_IMAGEDIMENSIONS))
432 {
433 if (!TIFFWriteDirectoryTagShortLong(tif,&ndir,dir,TIFFTAG_IMAGEWIDTH,tif->tif_dir.td_imagewidth))
434 goto bad;
435 if (!TIFFWriteDirectoryTagShortLong(tif,&ndir,dir,TIFFTAG_IMAGELENGTH,tif->tif_dir.td_imagelength))
436 goto bad;
437 }
438 if (TIFFFieldSet(tif,FIELD_TILEDIMENSIONS))
439 {
440 if (!TIFFWriteDirectoryTagShortLong(tif,&ndir,dir,TIFFTAG_TILEWIDTH,tif->tif_dir.td_tilewidth))
441 goto bad;
442 if (!TIFFWriteDirectoryTagShortLong(tif,&ndir,dir,TIFFTAG_TILELENGTH,tif->tif_dir.td_tilelength))
443 goto bad;
444 }
445 if (TIFFFieldSet(tif,FIELD_RESOLUTION))
446 {
447 if (!TIFFWriteDirectoryTagRational(tif,&ndir,dir,TIFFTAG_XRESOLUTION,tif->tif_dir.td_xresolution))
448 goto bad;
449 if (!TIFFWriteDirectoryTagRational(tif,&ndir,dir,TIFFTAG_YRESOLUTION,tif->tif_dir.td_yresolution))
450 goto bad;
451 }
452 if (TIFFFieldSet(tif,FIELD_POSITION))
453 {
454 if (!TIFFWriteDirectoryTagRational(tif,&ndir,dir,TIFFTAG_XPOSITION,tif->tif_dir.td_xposition))
455 goto bad;
456 if (!TIFFWriteDirectoryTagRational(tif,&ndir,dir,TIFFTAG_YPOSITION,tif->tif_dir.td_yposition))
457 goto bad;
458 }
459 if (TIFFFieldSet(tif,FIELD_SUBFILETYPE))
460 {
461 if (!TIFFWriteDirectoryTagLong(tif,&ndir,dir,TIFFTAG_SUBFILETYPE,tif->tif_dir.td_subfiletype))
462 goto bad;
463 }
464 if (TIFFFieldSet(tif,FIELD_BITSPERSAMPLE))
465 {
466 if (!TIFFWriteDirectoryTagShortPerSample(tif,&ndir,dir,TIFFTAG_BITSPERSAMPLE,tif->tif_dir.td_bitspersample))
467 goto bad;
468 }
469 if (TIFFFieldSet(tif,FIELD_COMPRESSION))
470 {
471 if (!TIFFWriteDirectoryTagShort(tif,&ndir,dir,TIFFTAG_COMPRESSION,tif->tif_dir.td_compression))
472 goto bad;
473 }
474 if (TIFFFieldSet(tif,FIELD_PHOTOMETRIC))
475 {
476 if (!TIFFWriteDirectoryTagShort(tif,&ndir,dir,TIFFTAG_PHOTOMETRIC,tif->tif_dir.td_photometric))
477 goto bad;
478 }
479 if (TIFFFieldSet(tif,FIELD_THRESHHOLDING))
480 {
481 if (!TIFFWriteDirectoryTagShort(tif,&ndir,dir,TIFFTAG_THRESHHOLDING,tif->tif_dir.td_threshholding))
482 goto bad;
483 }
484 if (TIFFFieldSet(tif,FIELD_FILLORDER))
485 {
486 if (!TIFFWriteDirectoryTagShort(tif,&ndir,dir,TIFFTAG_FILLORDER,tif->tif_dir.td_fillorder))
487 goto bad;
488 }
489 if (TIFFFieldSet(tif,FIELD_ORIENTATION))
490 {
491 if (!TIFFWriteDirectoryTagShort(tif,&ndir,dir,TIFFTAG_ORIENTATION,tif->tif_dir.td_orientation))
492 goto bad;
493 }
494 if (TIFFFieldSet(tif,FIELD_SAMPLESPERPIXEL))
495 {
496 if (!TIFFWriteDirectoryTagShort(tif,&ndir,dir,TIFFTAG_SAMPLESPERPIXEL,tif->tif_dir.td_samplesperpixel))
497 goto bad;
498 }
499 if (TIFFFieldSet(tif,FIELD_ROWSPERSTRIP))
500 {
501 if (!TIFFWriteDirectoryTagShortLong(tif,&ndir,dir,TIFFTAG_ROWSPERSTRIP,tif->tif_dir.td_rowsperstrip))
502 goto bad;
503 }
504 if (TIFFFieldSet(tif,FIELD_MINSAMPLEVALUE))
505 {
506 if (!TIFFWriteDirectoryTagShortPerSample(tif,&ndir,dir,TIFFTAG_MINSAMPLEVALUE,tif->tif_dir.td_minsamplevalue))
507 goto bad;
508 }
509 if (TIFFFieldSet(tif,FIELD_MAXSAMPLEVALUE))
510 {
511 if (!TIFFWriteDirectoryTagShortPerSample(tif,&ndir,dir,TIFFTAG_MAXSAMPLEVALUE,tif->tif_dir.td_maxsamplevalue))
512 goto bad;
513 }
514 if (TIFFFieldSet(tif,FIELD_PLANARCONFIG))
515 {
516 if (!TIFFWriteDirectoryTagShort(tif,&ndir,dir,TIFFTAG_PLANARCONFIG,tif->tif_dir.td_planarconfig))
517 goto bad;
518 }
519 if (TIFFFieldSet(tif,FIELD_RESOLUTIONUNIT))
520 {
521 if (!TIFFWriteDirectoryTagShort(tif,&ndir,dir,TIFFTAG_RESOLUTIONUNIT,tif->tif_dir.td_resolutionunit))
522 goto bad;
523 }
524 if (TIFFFieldSet(tif,FIELD_PAGENUMBER))
525 {
526 if (!TIFFWriteDirectoryTagShortArray(tif,&ndir,dir,TIFFTAG_PAGENUMBER,2,&tif->tif_dir.td_pagenumber[0]))
527 goto bad;
528 }
529 if (TIFFFieldSet(tif,FIELD_STRIPBYTECOUNTS))
530 {
531 if (!isTiled(tif))
532 {
533 if (!TIFFWriteDirectoryTagLongLong8Array(tif,&ndir,dir,TIFFTAG_STRIPBYTECOUNTS,tif->tif_dir.td_nstrips,tif->tif_dir.td_stripbytecount))
534 goto bad;
535 }
536 else
537 {
538 if (!TIFFWriteDirectoryTagLongLong8Array(tif,&ndir,dir,TIFFTAG_TILEBYTECOUNTS,tif->tif_dir.td_nstrips,tif->tif_dir.td_stripbytecount))
539 goto bad;
540 }
541 }
542 if (TIFFFieldSet(tif,FIELD_STRIPOFFSETS))
543 {
544 if (!isTiled(tif))
545 {
546 /* td_stripoffset might be NULL in an odd OJPEG case. See
547 * tif_dirread.c around line 3634.
548 * XXX: OJPEG hack.
549 * If a) compression is OJPEG, b) it's not a tiled TIFF,
550 * and c) the number of strips is 1,
551 * then we tolerate the absence of stripoffsets tag,
552 * because, presumably, all required data is in the
553 * JpegInterchangeFormat stream.
554 * We can get here when using tiffset on such a file.
555 * See http://bugzilla.maptools.org/show_bug.cgi?id=2500
556 */
557 if (tif->tif_dir.td_stripoffset != NULL &&
558 !TIFFWriteDirectoryTagLongLong8Array(tif,&ndir,dir,TIFFTAG_STRIPOFFSETS,tif->tif_dir.td_nstrips,tif->tif_dir.td_stripoffset))
559 goto bad;
560 }
561 else
562 {
563 if (!TIFFWriteDirectoryTagLongLong8Array(tif,&ndir,dir,TIFFTAG_TILEOFFSETS,tif->tif_dir.td_nstrips,tif->tif_dir.td_stripoffset))
564 goto bad;
565 }
566 }
567 if (TIFFFieldSet(tif,FIELD_COLORMAP))
568 {
569 if (!TIFFWriteDirectoryTagColormap(tif,&ndir,dir))
570 goto bad;
571 }
572 if (TIFFFieldSet(tif,FIELD_EXTRASAMPLES))
573 {
574 if (tif->tif_dir.td_extrasamples)
575 {
576 uint16 na;
577 uint16* nb;
578 TIFFGetFieldDefaulted(tif,TIFFTAG_EXTRASAMPLES,&na,&nb);
579 if (!TIFFWriteDirectoryTagShortArray(tif,&ndir,dir,TIFFTAG_EXTRASAMPLES,na,nb))
580 goto bad;
581 }
582 }
583 if (TIFFFieldSet(tif,FIELD_SAMPLEFORMAT))
584 {
585 if (!TIFFWriteDirectoryTagShortPerSample(tif,&ndir,dir,TIFFTAG_SAMPLEFORMAT,tif->tif_dir.td_sampleformat))
586 goto bad;
587 }
588 if (TIFFFieldSet(tif,FIELD_SMINSAMPLEVALUE))
589 {
590 if (!TIFFWriteDirectoryTagSampleformatArray(tif,&ndir,dir,TIFFTAG_SMINSAMPLEVALUE,tif->tif_dir.td_samplesperpixel,tif->tif_dir.td_sminsamplevalue))
591 goto bad;
592 }
593 if (TIFFFieldSet(tif,FIELD_SMAXSAMPLEVALUE))
594 {
595 if (!TIFFWriteDirectoryTagSampleformatArray(tif,&ndir,dir,TIFFTAG_SMAXSAMPLEVALUE,tif->tif_dir.td_samplesperpixel,tif->tif_dir.td_smaxsamplevalue))
596 goto bad;
597 }
598 if (TIFFFieldSet(tif,FIELD_IMAGEDEPTH))
599 {
600 if (!TIFFWriteDirectoryTagLong(tif,&ndir,dir,TIFFTAG_IMAGEDEPTH,tif->tif_dir.td_imagedepth))
601 goto bad;
602 }
603 if (TIFFFieldSet(tif,FIELD_TILEDEPTH))
604 {
605 if (!TIFFWriteDirectoryTagLong(tif,&ndir,dir,TIFFTAG_TILEDEPTH,tif->tif_dir.td_tiledepth))
606 goto bad;
607 }
608 if (TIFFFieldSet(tif,FIELD_HALFTONEHINTS))
609 {
610 if (!TIFFWriteDirectoryTagShortArray(tif,&ndir,dir,TIFFTAG_HALFTONEHINTS,2,&tif->tif_dir.td_halftonehints[0]))
611 goto bad;
612 }
613 if (TIFFFieldSet(tif,FIELD_YCBCRSUBSAMPLING))
614 {
615 if (!TIFFWriteDirectoryTagShortArray(tif,&ndir,dir,TIFFTAG_YCBCRSUBSAMPLING,2,&tif->tif_dir.td_ycbcrsubsampling[0]))
616 goto bad;
617 }
618 if (TIFFFieldSet(tif,FIELD_YCBCRPOSITIONING))
619 {
620 if (!TIFFWriteDirectoryTagShort(tif,&ndir,dir,TIFFTAG_YCBCRPOSITIONING,tif->tif_dir.td_ycbcrpositioning))
621 goto bad;
622 }
623 if (TIFFFieldSet(tif,FIELD_REFBLACKWHITE))
624 {
625 if (!TIFFWriteDirectoryTagRationalArray(tif,&ndir,dir,TIFFTAG_REFERENCEBLACKWHITE,6,tif->tif_dir.td_refblackwhite))
626 goto bad;
627 }
628 if (TIFFFieldSet(tif,FIELD_TRANSFERFUNCTION))
629 {
630 if (!TIFFWriteDirectoryTagTransferfunction(tif,&ndir,dir))
631 goto bad;
632 }
633 if (TIFFFieldSet(tif,FIELD_INKNAMES))
634 {
635 if (!TIFFWriteDirectoryTagAscii(tif,&ndir,dir,TIFFTAG_INKNAMES,tif->tif_dir.td_inknameslen,tif->tif_dir.td_inknames))
636 goto bad;
637 }
638 if (TIFFFieldSet(tif,FIELD_SUBIFD))
639 {
640 if (!TIFFWriteDirectoryTagSubifd(tif,&ndir,dir))
641 goto bad;
642 }
643 {
644 uint32 n;
645 for (n=0; n<tif->tif_nfields; n++) {
646 const TIFFField* o;
647 o = tif->tif_fields[n];
648 if ((o->field_bit>=FIELD_CODEC)&&(TIFFFieldSet(tif,o->field_bit)))
649 {
650 switch (o->get_field_type)
651 {
652 case TIFF_SETGET_ASCII:
653 {
654 uint32 pa;
655 char* pb;
656 assert(o->field_type==TIFF_ASCII);
657 assert(o->field_readcount==TIFF_VARIABLE);
658 assert(o->field_passcount==0);
659 TIFFGetField(tif,o->field_tag,&pb);
660 pa=(uint32)(strlen(pb));
661 if (!TIFFWriteDirectoryTagAscii(tif,&ndir,dir,(uint16)o->field_tag,pa,pb))
662 goto bad;
663 }
664 break;
665 case TIFF_SETGET_UINT16:
666 {
667 uint16 p;
668 assert(o->field_type==TIFF_SHORT);
669 assert(o->field_readcount==1);
670 assert(o->field_passcount==0);
671 TIFFGetField(tif,o->field_tag,&p);
672 if (!TIFFWriteDirectoryTagShort(tif,&ndir,dir,(uint16)o->field_tag,p))
673 goto bad;
674 }
675 break;
676 case TIFF_SETGET_UINT32:
677 {
678 uint32 p;
679 assert(o->field_type==TIFF_LONG);
680 assert(o->field_readcount==1);
681 assert(o->field_passcount==0);
682 TIFFGetField(tif,o->field_tag,&p);
683 if (!TIFFWriteDirectoryTagLong(tif,&ndir,dir,(uint16)o->field_tag,p))
684 goto bad;
685 }
686 break;
687 case TIFF_SETGET_C32_UINT8:
688 {
689 uint32 pa;
690 void* pb;
691 assert(o->field_type==TIFF_UNDEFINED);
692 assert(o->field_readcount==TIFF_VARIABLE2);
693 assert(o->field_passcount==1);
694 TIFFGetField(tif,o->field_tag,&pa,&pb);
695 if (!TIFFWriteDirectoryTagUndefinedArray(tif,&ndir,dir,(uint16)o->field_tag,pa,pb))
696 goto bad;
697 }
698 break;
699 default:
700 assert(0); /* we should never get here */
701 break;
702 }
703 }
704 }
705 }
706 }
707 for (m=0; m<(uint32)(tif->tif_dir.td_customValueCount); m++)
708 {
709 uint16 tag = (uint16)tif->tif_dir.td_customValues[m].info->field_tag;
710 uint32 count = tif->tif_dir.td_customValues[m].count;
711 switch (tif->tif_dir.td_customValues[m].info->field_type)
712 {
713 case TIFF_ASCII:
714 if (!TIFFWriteDirectoryTagAscii(tif,&ndir,dir,tag,count,tif->tif_dir.td_customValues[m].value))
715 goto bad;
716 break;
717 case TIFF_UNDEFINED:
718 if (!TIFFWriteDirectoryTagUndefinedArray(tif,&ndir,dir,tag,count,tif->tif_dir.td_customValues[m].value))
719 goto bad;
720 break;
721 case TIFF_BYTE:
722 if (!TIFFWriteDirectoryTagByteArray(tif,&ndir,dir,tag,count,tif->tif_dir.td_customValues[m].value))
723 goto bad;
724 break;
725 case TIFF_SBYTE:
726 if (!TIFFWriteDirectoryTagSbyteArray(tif,&ndir,dir,tag,count,tif->tif_dir.td_customValues[m].value))
727 goto bad;
728 break;
729 case TIFF_SHORT:
730 if (!TIFFWriteDirectoryTagShortArray(tif,&ndir,dir,tag,count,tif->tif_dir.td_customValues[m].value))
731 goto bad;
732 break;
733 case TIFF_SSHORT:
734 if (!TIFFWriteDirectoryTagSshortArray(tif,&ndir,dir,tag,count,tif->tif_dir.td_customValues[m].value))
735 goto bad;
736 break;
737 case TIFF_LONG:
738 if (!TIFFWriteDirectoryTagLongArray(tif,&ndir,dir,tag,count,tif->tif_dir.td_customValues[m].value))
739 goto bad;
740 break;
741 case TIFF_SLONG:
742 if (!TIFFWriteDirectoryTagSlongArray(tif,&ndir,dir,tag,count,tif->tif_dir.td_customValues[m].value))
743 goto bad;
744 break;
745 case TIFF_LONG8:
746 if (!TIFFWriteDirectoryTagLong8Array(tif,&ndir,dir,tag,count,tif->tif_dir.td_customValues[m].value))
747 goto bad;
748 break;
749 case TIFF_SLONG8:
750 if (!TIFFWriteDirectoryTagSlong8Array(tif,&ndir,dir,tag,count,tif->tif_dir.td_customValues[m].value))
751 goto bad;
752 break;
753 case TIFF_RATIONAL:
754 if (!TIFFWriteDirectoryTagRationalArray(tif,&ndir,dir,tag,count,tif->tif_dir.td_customValues[m].value))
755 goto bad;
756 break;
757 case TIFF_SRATIONAL:
758 if (!TIFFWriteDirectoryTagSrationalArray(tif,&ndir,dir,tag,count,tif->tif_dir.td_customValues[m].value))
759 goto bad;
760 break;
761 case TIFF_FLOAT:
762 if (!TIFFWriteDirectoryTagFloatArray(tif,&ndir,dir,tag,count,tif->tif_dir.td_customValues[m].value))
763 goto bad;
764 break;
765 case TIFF_DOUBLE:
766 if (!TIFFWriteDirectoryTagDoubleArray(tif,&ndir,dir,tag,count,tif->tif_dir.td_customValues[m].value))
767 goto bad;
768 break;
769 case TIFF_IFD:
770 if (!TIFFWriteDirectoryTagIfdArray(tif,&ndir,dir,tag,count,tif->tif_dir.td_customValues[m].value))
771 goto bad;
772 break;
773 case TIFF_IFD8:
774 if (!TIFFWriteDirectoryTagIfdIfd8Array(tif,&ndir,dir,tag,count,tif->tif_dir.td_customValues[m].value))
775 goto bad;
776 break;
777 default:
778 assert(0); /* we should never get here */
779 break;
780 }
781 }
782 if (dir!=NULL)
783 break;
784 dir=_TIFFmalloc(ndir*sizeof(TIFFDirEntry));
785 if (dir==NULL)
786 {
787 TIFFErrorExt(tif->tif_clientdata,module,"Out of memory");
788 goto bad;
789 }
790 if (isimage)
791 {
792 if ((tif->tif_diroff==0)&&(!TIFFLinkDirectory(tif)))
793 goto bad;
794 }
795 else
796 tif->tif_diroff=(TIFFSeekFile(tif,0,SEEK_END)+1)&(~((toff_t)1));
797 if (pdiroff!=NULL)
798 *pdiroff=tif->tif_diroff;
799 if (!(tif->tif_flags&TIFF_BIGTIFF))
800 dirsize=2+ndir*12+4;
801 else
802 dirsize=8+ndir*20+8;
803 tif->tif_dataoff=tif->tif_diroff+dirsize;
804 if (!(tif->tif_flags&TIFF_BIGTIFF))
805 tif->tif_dataoff=(uint32)tif->tif_dataoff;
806 if ((tif->tif_dataoff<tif->tif_diroff)||(tif->tif_dataoff<(uint64)dirsize))
807 {
808 TIFFErrorExt(tif->tif_clientdata,module,"Maximum TIFF file size exceeded");
809 goto bad;
810 }
811 if (tif->tif_dataoff&1)
812 tif->tif_dataoff++;
813 if (isimage)
814 tif->tif_curdir++;
815 }
816 if (isimage)
817 {
818 if (TIFFFieldSet(tif,FIELD_SUBIFD)&&(tif->tif_subifdoff==0))
819 {
820 uint32 na;
821 TIFFDirEntry* nb;
822 for (na=0, nb=dir; ; na++, nb++)
823 {
824 assert(na<ndir);
825 if (nb->tdir_tag==TIFFTAG_SUBIFD)
826 break;
827 }
828 if (!(tif->tif_flags&TIFF_BIGTIFF))
829 tif->tif_subifdoff=tif->tif_diroff+2+na*12+8;
830 else
831 tif->tif_subifdoff=tif->tif_diroff+8+na*20+12;
832 }
833 }
834 dirmem=_TIFFmalloc(dirsize);
835 if (dirmem==NULL)
836 {
837 TIFFErrorExt(tif->tif_clientdata,module,"Out of memory");
838 goto bad;
839 }
840 if (!(tif->tif_flags&TIFF_BIGTIFF))
841 {
842 uint8* n;
843 uint32 nTmp;
844 TIFFDirEntry* o;
845 n=dirmem;
846 *(uint16*)n=(uint16)ndir;
847 if (tif->tif_flags&TIFF_SWAB)
848 TIFFSwabShort((uint16*)n);
849 n+=2;
850 o=dir;
851 for (m=0; m<ndir; m++)
852 {
853 *(uint16*)n=o->tdir_tag;
854 if (tif->tif_flags&TIFF_SWAB)
855 TIFFSwabShort((uint16*)n);
856 n+=2;
857 *(uint16*)n=o->tdir_type;
858 if (tif->tif_flags&TIFF_SWAB)
859 TIFFSwabShort((uint16*)n);
860 n+=2;
861 nTmp = (uint32)o->tdir_count;
862 _TIFFmemcpy(n,&nTmp,4);
863 if (tif->tif_flags&TIFF_SWAB)
864 TIFFSwabLong((uint32*)n);
865 n+=4;
866 /* This is correct. The data has been */
867 /* swabbed previously in TIFFWriteDirectoryTagData */
868 _TIFFmemcpy(n,&o->tdir_offset,4);
869 n+=4;
870 o++;
871 }
872 nTmp = (uint32)tif->tif_nextdiroff;
873 if (tif->tif_flags&TIFF_SWAB)
874 TIFFSwabLong(&nTmp);
875 _TIFFmemcpy(n,&nTmp,4);
876 }
877 else
878 {
879 uint8* n;
880 TIFFDirEntry* o;
881 n=dirmem;
882 *(uint64*)n=ndir;
883 if (tif->tif_flags&TIFF_SWAB)
884 TIFFSwabLong8((uint64*)n);
885 n+=8;
886 o=dir;
887 for (m=0; m<ndir; m++)
888 {
889 *(uint16*)n=o->tdir_tag;
890 if (tif->tif_flags&TIFF_SWAB)
891 TIFFSwabShort((uint16*)n);
892 n+=2;
893 *(uint16*)n=o->tdir_type;
894 if (tif->tif_flags&TIFF_SWAB)
895 TIFFSwabShort((uint16*)n);
896 n+=2;
897 _TIFFmemcpy(n,&o->tdir_count,8);
898 if (tif->tif_flags&TIFF_SWAB)
899 TIFFSwabLong8((uint64*)n);
900 n+=8;
901 _TIFFmemcpy(n,&o->tdir_offset,8);
902 n+=8;
903 o++;
904 }
905 _TIFFmemcpy(n,&tif->tif_nextdiroff,8);
906 if (tif->tif_flags&TIFF_SWAB)
907 TIFFSwabLong8((uint64*)n);
908 }
909 _TIFFfree(dir);
910 dir=NULL;
911 if (!SeekOK(tif,tif->tif_diroff))
912 {
913 TIFFErrorExt(tif->tif_clientdata,module,"IO error writing directory");
914 goto bad;
915 }
916 if (!WriteOK(tif,dirmem,(tmsize_t)dirsize))
917 {
918 TIFFErrorExt(tif->tif_clientdata,module,"IO error writing directory");
919 goto bad;
920 }
921 _TIFFfree(dirmem);
922 if (imagedone)
923 {
924 TIFFFreeDirectory(tif);
925 tif->tif_flags &= ~TIFF_DIRTYDIRECT;
926 tif->tif_flags &= ~TIFF_DIRTYSTRIP;
927 (*tif->tif_cleanup)(tif);
928 /*
929 * Reset directory-related state for subsequent
930 * directories.
931 */
932 TIFFCreateDirectory(tif);
933 }
934 return(1);
935 bad:
936 if (dir!=NULL)
937 _TIFFfree(dir);
938 if (dirmem!=NULL)
939 _TIFFfree(dirmem);
940 return(0);
941 }
942
TIFFClampDoubleToFloat(double val)943 static float TIFFClampDoubleToFloat( double val )
944 {
945 if( val > FLT_MAX )
946 return FLT_MAX;
947 if( val < -FLT_MAX )
948 return -FLT_MAX;
949 return (float)val;
950 }
951
TIFFClampDoubleToInt8(double val)952 static int8 TIFFClampDoubleToInt8( double val )
953 {
954 if( val > 127 )
955 return 127;
956 if( val < -128 || val != val )
957 return -128;
958 return (int8)val;
959 }
960
TIFFClampDoubleToInt16(double val)961 static int16 TIFFClampDoubleToInt16( double val )
962 {
963 if( val > 32767 )
964 return 32767;
965 if( val < -32768 || val != val )
966 return -32768;
967 return (int16)val;
968 }
969
TIFFClampDoubleToInt32(double val)970 static int32 TIFFClampDoubleToInt32( double val )
971 {
972 if( val > 0x7FFFFFFF )
973 return 0x7FFFFFFF;
974 if( val < -0x7FFFFFFF-1 || val != val )
975 return -0x7FFFFFFF-1;
976 return (int32)val;
977 }
978
TIFFClampDoubleToUInt8(double val)979 static uint8 TIFFClampDoubleToUInt8( double val )
980 {
981 if( val < 0 )
982 return 0;
983 if( val > 255 || val != val )
984 return 255;
985 return (uint8)val;
986 }
987
TIFFClampDoubleToUInt16(double val)988 static uint16 TIFFClampDoubleToUInt16( double val )
989 {
990 if( val < 0 )
991 return 0;
992 if( val > 65535 || val != val )
993 return 65535;
994 return (uint16)val;
995 }
996
TIFFClampDoubleToUInt32(double val)997 static uint32 TIFFClampDoubleToUInt32( double val )
998 {
999 if( val < 0 )
1000 return 0;
1001 if( val > 0xFFFFFFFFU || val != val )
1002 return 0xFFFFFFFFU;
1003 return (uint32)val;
1004 }
1005
1006 static int
TIFFWriteDirectoryTagSampleformatArray(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,double * value)1007 TIFFWriteDirectoryTagSampleformatArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, double* value)
1008 {
1009 static const char module[] = "TIFFWriteDirectoryTagSampleformatArray";
1010 void* conv;
1011 uint32 i;
1012 int ok;
1013 conv = _TIFFmalloc(count*sizeof(double));
1014 if (conv == NULL)
1015 {
1016 TIFFErrorExt(tif->tif_clientdata, module, "Out of memory");
1017 return (0);
1018 }
1019
1020 switch (tif->tif_dir.td_sampleformat)
1021 {
1022 case SAMPLEFORMAT_IEEEFP:
1023 if (tif->tif_dir.td_bitspersample<=32)
1024 {
1025 for (i = 0; i < count; ++i)
1026 ((float*)conv)[i] = TIFFClampDoubleToFloat(value[i]);
1027 ok = TIFFWriteDirectoryTagFloatArray(tif,ndir,dir,tag,count,(float*)conv);
1028 }
1029 else
1030 {
1031 ok = TIFFWriteDirectoryTagDoubleArray(tif,ndir,dir,tag,count,value);
1032 }
1033 break;
1034 case SAMPLEFORMAT_INT:
1035 if (tif->tif_dir.td_bitspersample<=8)
1036 {
1037 for (i = 0; i < count; ++i)
1038 ((int8*)conv)[i] = TIFFClampDoubleToInt8(value[i]);
1039 ok = TIFFWriteDirectoryTagSbyteArray(tif,ndir,dir,tag,count,(int8*)conv);
1040 }
1041 else if (tif->tif_dir.td_bitspersample<=16)
1042 {
1043 for (i = 0; i < count; ++i)
1044 ((int16*)conv)[i] = TIFFClampDoubleToInt16(value[i]);
1045 ok = TIFFWriteDirectoryTagSshortArray(tif,ndir,dir,tag,count,(int16*)conv);
1046 }
1047 else
1048 {
1049 for (i = 0; i < count; ++i)
1050 ((int32*)conv)[i] = TIFFClampDoubleToInt32(value[i]);
1051 ok = TIFFWriteDirectoryTagSlongArray(tif,ndir,dir,tag,count,(int32*)conv);
1052 }
1053 break;
1054 case SAMPLEFORMAT_UINT:
1055 if (tif->tif_dir.td_bitspersample<=8)
1056 {
1057 for (i = 0; i < count; ++i)
1058 ((uint8*)conv)[i] = TIFFClampDoubleToUInt8(value[i]);
1059 ok = TIFFWriteDirectoryTagByteArray(tif,ndir,dir,tag,count,(uint8*)conv);
1060 }
1061 else if (tif->tif_dir.td_bitspersample<=16)
1062 {
1063 for (i = 0; i < count; ++i)
1064 ((uint16*)conv)[i] = TIFFClampDoubleToUInt16(value[i]);
1065 ok = TIFFWriteDirectoryTagShortArray(tif,ndir,dir,tag,count,(uint16*)conv);
1066 }
1067 else
1068 {
1069 for (i = 0; i < count; ++i)
1070 ((uint32*)conv)[i] = TIFFClampDoubleToUInt32(value[i]);
1071 ok = TIFFWriteDirectoryTagLongArray(tif,ndir,dir,tag,count,(uint32*)conv);
1072 }
1073 break;
1074 default:
1075 ok = 0;
1076 }
1077
1078 _TIFFfree(conv);
1079 return (ok);
1080 }
1081
1082 #if 0
1083 static int
1084 TIFFWriteDirectoryTagSampleformatPerSample(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, double value)
1085 {
1086 switch (tif->tif_dir.td_sampleformat)
1087 {
1088 case SAMPLEFORMAT_IEEEFP:
1089 if (tif->tif_dir.td_bitspersample<=32)
1090 return(TIFFWriteDirectoryTagFloatPerSample(tif,ndir,dir,tag,(float)value));
1091 else
1092 return(TIFFWriteDirectoryTagDoublePerSample(tif,ndir,dir,tag,value));
1093 case SAMPLEFORMAT_INT:
1094 if (tif->tif_dir.td_bitspersample<=8)
1095 return(TIFFWriteDirectoryTagSbytePerSample(tif,ndir,dir,tag,(int8)value));
1096 else if (tif->tif_dir.td_bitspersample<=16)
1097 return(TIFFWriteDirectoryTagSshortPerSample(tif,ndir,dir,tag,(int16)value));
1098 else
1099 return(TIFFWriteDirectoryTagSlongPerSample(tif,ndir,dir,tag,(int32)value));
1100 case SAMPLEFORMAT_UINT:
1101 if (tif->tif_dir.td_bitspersample<=8)
1102 return(TIFFWriteDirectoryTagBytePerSample(tif,ndir,dir,tag,(uint8)value));
1103 else if (tif->tif_dir.td_bitspersample<=16)
1104 return(TIFFWriteDirectoryTagShortPerSample(tif,ndir,dir,tag,(uint16)value));
1105 else
1106 return(TIFFWriteDirectoryTagLongPerSample(tif,ndir,dir,tag,(uint32)value));
1107 default:
1108 return(1);
1109 }
1110 }
1111 #endif
1112
1113 static int
TIFFWriteDirectoryTagAscii(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,char * value)1114 TIFFWriteDirectoryTagAscii(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, char* value)
1115 {
1116 if (dir==NULL)
1117 {
1118 (*ndir)++;
1119 return(1);
1120 }
1121 return(TIFFWriteDirectoryTagCheckedAscii(tif,ndir,dir,tag,count,value));
1122 }
1123
1124 static int
TIFFWriteDirectoryTagUndefinedArray(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,uint8 * value)1125 TIFFWriteDirectoryTagUndefinedArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, uint8* value)
1126 {
1127 if (dir==NULL)
1128 {
1129 (*ndir)++;
1130 return(1);
1131 }
1132 return(TIFFWriteDirectoryTagCheckedUndefinedArray(tif,ndir,dir,tag,count,value));
1133 }
1134
1135 #ifdef notdef
1136 static int
TIFFWriteDirectoryTagByte(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint8 value)1137 TIFFWriteDirectoryTagByte(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint8 value)
1138 {
1139 if (dir==NULL)
1140 {
1141 (*ndir)++;
1142 return(1);
1143 }
1144 return(TIFFWriteDirectoryTagCheckedByte(tif,ndir,dir,tag,value));
1145 }
1146 #endif
1147
1148 static int
TIFFWriteDirectoryTagByteArray(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,uint8 * value)1149 TIFFWriteDirectoryTagByteArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, uint8* value)
1150 {
1151 if (dir==NULL)
1152 {
1153 (*ndir)++;
1154 return(1);
1155 }
1156 return(TIFFWriteDirectoryTagCheckedByteArray(tif,ndir,dir,tag,count,value));
1157 }
1158
1159 #if 0
1160 static int
1161 TIFFWriteDirectoryTagBytePerSample(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint8 value)
1162 {
1163 static const char module[] = "TIFFWriteDirectoryTagBytePerSample";
1164 uint8* m;
1165 uint8* na;
1166 uint16 nb;
1167 int o;
1168 if (dir==NULL)
1169 {
1170 (*ndir)++;
1171 return(1);
1172 }
1173 m=_TIFFmalloc(tif->tif_dir.td_samplesperpixel*sizeof(uint8));
1174 if (m==NULL)
1175 {
1176 TIFFErrorExt(tif->tif_clientdata,module,"Out of memory");
1177 return(0);
1178 }
1179 for (na=m, nb=0; nb<tif->tif_dir.td_samplesperpixel; na++, nb++)
1180 *na=value;
1181 o=TIFFWriteDirectoryTagCheckedByteArray(tif,ndir,dir,tag,tif->tif_dir.td_samplesperpixel,m);
1182 _TIFFfree(m);
1183 return(o);
1184 }
1185 #endif
1186
1187 #ifdef notdef
1188 static int
TIFFWriteDirectoryTagSbyte(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,int8 value)1189 TIFFWriteDirectoryTagSbyte(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, int8 value)
1190 {
1191 if (dir==NULL)
1192 {
1193 (*ndir)++;
1194 return(1);
1195 }
1196 return(TIFFWriteDirectoryTagCheckedSbyte(tif,ndir,dir,tag,value));
1197 }
1198 #endif
1199
1200 static int
TIFFWriteDirectoryTagSbyteArray(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,int8 * value)1201 TIFFWriteDirectoryTagSbyteArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, int8* value)
1202 {
1203 if (dir==NULL)
1204 {
1205 (*ndir)++;
1206 return(1);
1207 }
1208 return(TIFFWriteDirectoryTagCheckedSbyteArray(tif,ndir,dir,tag,count,value));
1209 }
1210
1211 #if 0
1212 static int
1213 TIFFWriteDirectoryTagSbytePerSample(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, int8 value)
1214 {
1215 static const char module[] = "TIFFWriteDirectoryTagSbytePerSample";
1216 int8* m;
1217 int8* na;
1218 uint16 nb;
1219 int o;
1220 if (dir==NULL)
1221 {
1222 (*ndir)++;
1223 return(1);
1224 }
1225 m=_TIFFmalloc(tif->tif_dir.td_samplesperpixel*sizeof(int8));
1226 if (m==NULL)
1227 {
1228 TIFFErrorExt(tif->tif_clientdata,module,"Out of memory");
1229 return(0);
1230 }
1231 for (na=m, nb=0; nb<tif->tif_dir.td_samplesperpixel; na++, nb++)
1232 *na=value;
1233 o=TIFFWriteDirectoryTagCheckedSbyteArray(tif,ndir,dir,tag,tif->tif_dir.td_samplesperpixel,m);
1234 _TIFFfree(m);
1235 return(o);
1236 }
1237 #endif
1238
1239 static int
TIFFWriteDirectoryTagShort(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint16 value)1240 TIFFWriteDirectoryTagShort(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint16 value)
1241 {
1242 if (dir==NULL)
1243 {
1244 (*ndir)++;
1245 return(1);
1246 }
1247 return(TIFFWriteDirectoryTagCheckedShort(tif,ndir,dir,tag,value));
1248 }
1249
1250 static int
TIFFWriteDirectoryTagShortArray(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,uint16 * value)1251 TIFFWriteDirectoryTagShortArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, uint16* value)
1252 {
1253 if (dir==NULL)
1254 {
1255 (*ndir)++;
1256 return(1);
1257 }
1258 return(TIFFWriteDirectoryTagCheckedShortArray(tif,ndir,dir,tag,count,value));
1259 }
1260
1261 static int
TIFFWriteDirectoryTagShortPerSample(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint16 value)1262 TIFFWriteDirectoryTagShortPerSample(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint16 value)
1263 {
1264 static const char module[] = "TIFFWriteDirectoryTagShortPerSample";
1265 uint16* m;
1266 uint16* na;
1267 uint16 nb;
1268 int o;
1269 if (dir==NULL)
1270 {
1271 (*ndir)++;
1272 return(1);
1273 }
1274 m=_TIFFmalloc(tif->tif_dir.td_samplesperpixel*sizeof(uint16));
1275 if (m==NULL)
1276 {
1277 TIFFErrorExt(tif->tif_clientdata,module,"Out of memory");
1278 return(0);
1279 }
1280 for (na=m, nb=0; nb<tif->tif_dir.td_samplesperpixel; na++, nb++)
1281 *na=value;
1282 o=TIFFWriteDirectoryTagCheckedShortArray(tif,ndir,dir,tag,tif->tif_dir.td_samplesperpixel,m);
1283 _TIFFfree(m);
1284 return(o);
1285 }
1286
1287 #ifdef notdef
1288 static int
TIFFWriteDirectoryTagSshort(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,int16 value)1289 TIFFWriteDirectoryTagSshort(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, int16 value)
1290 {
1291 if (dir==NULL)
1292 {
1293 (*ndir)++;
1294 return(1);
1295 }
1296 return(TIFFWriteDirectoryTagCheckedSshort(tif,ndir,dir,tag,value));
1297 }
1298 #endif
1299
1300 static int
TIFFWriteDirectoryTagSshortArray(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,int16 * value)1301 TIFFWriteDirectoryTagSshortArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, int16* value)
1302 {
1303 if (dir==NULL)
1304 {
1305 (*ndir)++;
1306 return(1);
1307 }
1308 return(TIFFWriteDirectoryTagCheckedSshortArray(tif,ndir,dir,tag,count,value));
1309 }
1310
1311 #if 0
1312 static int
1313 TIFFWriteDirectoryTagSshortPerSample(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, int16 value)
1314 {
1315 static const char module[] = "TIFFWriteDirectoryTagSshortPerSample";
1316 int16* m;
1317 int16* na;
1318 uint16 nb;
1319 int o;
1320 if (dir==NULL)
1321 {
1322 (*ndir)++;
1323 return(1);
1324 }
1325 m=_TIFFmalloc(tif->tif_dir.td_samplesperpixel*sizeof(int16));
1326 if (m==NULL)
1327 {
1328 TIFFErrorExt(tif->tif_clientdata,module,"Out of memory");
1329 return(0);
1330 }
1331 for (na=m, nb=0; nb<tif->tif_dir.td_samplesperpixel; na++, nb++)
1332 *na=value;
1333 o=TIFFWriteDirectoryTagCheckedSshortArray(tif,ndir,dir,tag,tif->tif_dir.td_samplesperpixel,m);
1334 _TIFFfree(m);
1335 return(o);
1336 }
1337 #endif
1338
1339 static int
TIFFWriteDirectoryTagLong(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 value)1340 TIFFWriteDirectoryTagLong(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 value)
1341 {
1342 if (dir==NULL)
1343 {
1344 (*ndir)++;
1345 return(1);
1346 }
1347 return(TIFFWriteDirectoryTagCheckedLong(tif,ndir,dir,tag,value));
1348 }
1349
1350 static int
TIFFWriteDirectoryTagLongArray(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,uint32 * value)1351 TIFFWriteDirectoryTagLongArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, uint32* value)
1352 {
1353 if (dir==NULL)
1354 {
1355 (*ndir)++;
1356 return(1);
1357 }
1358 return(TIFFWriteDirectoryTagCheckedLongArray(tif,ndir,dir,tag,count,value));
1359 }
1360
1361 #if 0
1362 static int
1363 TIFFWriteDirectoryTagLongPerSample(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 value)
1364 {
1365 static const char module[] = "TIFFWriteDirectoryTagLongPerSample";
1366 uint32* m;
1367 uint32* na;
1368 uint16 nb;
1369 int o;
1370 if (dir==NULL)
1371 {
1372 (*ndir)++;
1373 return(1);
1374 }
1375 m=_TIFFmalloc(tif->tif_dir.td_samplesperpixel*sizeof(uint32));
1376 if (m==NULL)
1377 {
1378 TIFFErrorExt(tif->tif_clientdata,module,"Out of memory");
1379 return(0);
1380 }
1381 for (na=m, nb=0; nb<tif->tif_dir.td_samplesperpixel; na++, nb++)
1382 *na=value;
1383 o=TIFFWriteDirectoryTagCheckedLongArray(tif,ndir,dir,tag,tif->tif_dir.td_samplesperpixel,m);
1384 _TIFFfree(m);
1385 return(o);
1386 }
1387 #endif
1388
1389 #ifdef notdef
1390 static int
TIFFWriteDirectoryTagSlong(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,int32 value)1391 TIFFWriteDirectoryTagSlong(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, int32 value)
1392 {
1393 if (dir==NULL)
1394 {
1395 (*ndir)++;
1396 return(1);
1397 }
1398 return(TIFFWriteDirectoryTagCheckedSlong(tif,ndir,dir,tag,value));
1399 }
1400 #endif
1401
1402 static int
TIFFWriteDirectoryTagSlongArray(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,int32 * value)1403 TIFFWriteDirectoryTagSlongArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, int32* value)
1404 {
1405 if (dir==NULL)
1406 {
1407 (*ndir)++;
1408 return(1);
1409 }
1410 return(TIFFWriteDirectoryTagCheckedSlongArray(tif,ndir,dir,tag,count,value));
1411 }
1412
1413 #if 0
1414 static int
1415 TIFFWriteDirectoryTagSlongPerSample(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, int32 value)
1416 {
1417 static const char module[] = "TIFFWriteDirectoryTagSlongPerSample";
1418 int32* m;
1419 int32* na;
1420 uint16 nb;
1421 int o;
1422 if (dir==NULL)
1423 {
1424 (*ndir)++;
1425 return(1);
1426 }
1427 m=_TIFFmalloc(tif->tif_dir.td_samplesperpixel*sizeof(int32));
1428 if (m==NULL)
1429 {
1430 TIFFErrorExt(tif->tif_clientdata,module,"Out of memory");
1431 return(0);
1432 }
1433 for (na=m, nb=0; nb<tif->tif_dir.td_samplesperpixel; na++, nb++)
1434 *na=value;
1435 o=TIFFWriteDirectoryTagCheckedSlongArray(tif,ndir,dir,tag,tif->tif_dir.td_samplesperpixel,m);
1436 _TIFFfree(m);
1437 return(o);
1438 }
1439 #endif
1440
1441 #ifdef notdef
1442 static int
TIFFWriteDirectoryTagLong8(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint64 value)1443 TIFFWriteDirectoryTagLong8(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint64 value)
1444 {
1445 if (dir==NULL)
1446 {
1447 (*ndir)++;
1448 return(1);
1449 }
1450 return(TIFFWriteDirectoryTagCheckedLong8(tif,ndir,dir,tag,value));
1451 }
1452 #endif
1453
1454 static int
TIFFWriteDirectoryTagLong8Array(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,uint64 * value)1455 TIFFWriteDirectoryTagLong8Array(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, uint64* value)
1456 {
1457 if (dir==NULL)
1458 {
1459 (*ndir)++;
1460 return(1);
1461 }
1462 return(TIFFWriteDirectoryTagCheckedLong8Array(tif,ndir,dir,tag,count,value));
1463 }
1464
1465 #ifdef notdef
1466 static int
TIFFWriteDirectoryTagSlong8(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,int64 value)1467 TIFFWriteDirectoryTagSlong8(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, int64 value)
1468 {
1469 if (dir==NULL)
1470 {
1471 (*ndir)++;
1472 return(1);
1473 }
1474 return(TIFFWriteDirectoryTagCheckedSlong8(tif,ndir,dir,tag,value));
1475 }
1476 #endif
1477
1478 static int
TIFFWriteDirectoryTagSlong8Array(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,int64 * value)1479 TIFFWriteDirectoryTagSlong8Array(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, int64* value)
1480 {
1481 if (dir==NULL)
1482 {
1483 (*ndir)++;
1484 return(1);
1485 }
1486 return(TIFFWriteDirectoryTagCheckedSlong8Array(tif,ndir,dir,tag,count,value));
1487 }
1488
1489 static int
TIFFWriteDirectoryTagRational(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,double value)1490 TIFFWriteDirectoryTagRational(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, double value)
1491 {
1492 if (dir==NULL)
1493 {
1494 (*ndir)++;
1495 return(1);
1496 }
1497 return(TIFFWriteDirectoryTagCheckedRational(tif,ndir,dir,tag,value));
1498 }
1499
1500 static int
TIFFWriteDirectoryTagRationalArray(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,float * value)1501 TIFFWriteDirectoryTagRationalArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, float* value)
1502 {
1503 if (dir==NULL)
1504 {
1505 (*ndir)++;
1506 return(1);
1507 }
1508 return(TIFFWriteDirectoryTagCheckedRationalArray(tif,ndir,dir,tag,count,value));
1509 }
1510
1511 static int
TIFFWriteDirectoryTagSrationalArray(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,float * value)1512 TIFFWriteDirectoryTagSrationalArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, float* value)
1513 {
1514 if (dir==NULL)
1515 {
1516 (*ndir)++;
1517 return(1);
1518 }
1519 return(TIFFWriteDirectoryTagCheckedSrationalArray(tif,ndir,dir,tag,count,value));
1520 }
1521
1522 #ifdef notdef
TIFFWriteDirectoryTagFloat(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,float value)1523 static int TIFFWriteDirectoryTagFloat(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, float value)
1524 {
1525 if (dir==NULL)
1526 {
1527 (*ndir)++;
1528 return(1);
1529 }
1530 return(TIFFWriteDirectoryTagCheckedFloat(tif,ndir,dir,tag,value));
1531 }
1532 #endif
1533
TIFFWriteDirectoryTagFloatArray(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,float * value)1534 static int TIFFWriteDirectoryTagFloatArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, float* value)
1535 {
1536 if (dir==NULL)
1537 {
1538 (*ndir)++;
1539 return(1);
1540 }
1541 return(TIFFWriteDirectoryTagCheckedFloatArray(tif,ndir,dir,tag,count,value));
1542 }
1543
1544 #if 0
1545 static int TIFFWriteDirectoryTagFloatPerSample(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, float value)
1546 {
1547 static const char module[] = "TIFFWriteDirectoryTagFloatPerSample";
1548 float* m;
1549 float* na;
1550 uint16 nb;
1551 int o;
1552 if (dir==NULL)
1553 {
1554 (*ndir)++;
1555 return(1);
1556 }
1557 m=_TIFFmalloc(tif->tif_dir.td_samplesperpixel*sizeof(float));
1558 if (m==NULL)
1559 {
1560 TIFFErrorExt(tif->tif_clientdata,module,"Out of memory");
1561 return(0);
1562 }
1563 for (na=m, nb=0; nb<tif->tif_dir.td_samplesperpixel; na++, nb++)
1564 *na=value;
1565 o=TIFFWriteDirectoryTagCheckedFloatArray(tif,ndir,dir,tag,tif->tif_dir.td_samplesperpixel,m);
1566 _TIFFfree(m);
1567 return(o);
1568 }
1569 #endif
1570
1571 #ifdef notdef
TIFFWriteDirectoryTagDouble(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,double value)1572 static int TIFFWriteDirectoryTagDouble(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, double value)
1573 {
1574 if (dir==NULL)
1575 {
1576 (*ndir)++;
1577 return(1);
1578 }
1579 return(TIFFWriteDirectoryTagCheckedDouble(tif,ndir,dir,tag,value));
1580 }
1581 #endif
1582
TIFFWriteDirectoryTagDoubleArray(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,double * value)1583 static int TIFFWriteDirectoryTagDoubleArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, double* value)
1584 {
1585 if (dir==NULL)
1586 {
1587 (*ndir)++;
1588 return(1);
1589 }
1590 return(TIFFWriteDirectoryTagCheckedDoubleArray(tif,ndir,dir,tag,count,value));
1591 }
1592
1593 #if 0
1594 static int TIFFWriteDirectoryTagDoublePerSample(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, double value)
1595 {
1596 static const char module[] = "TIFFWriteDirectoryTagDoublePerSample";
1597 double* m;
1598 double* na;
1599 uint16 nb;
1600 int o;
1601 if (dir==NULL)
1602 {
1603 (*ndir)++;
1604 return(1);
1605 }
1606 m=_TIFFmalloc(tif->tif_dir.td_samplesperpixel*sizeof(double));
1607 if (m==NULL)
1608 {
1609 TIFFErrorExt(tif->tif_clientdata,module,"Out of memory");
1610 return(0);
1611 }
1612 for (na=m, nb=0; nb<tif->tif_dir.td_samplesperpixel; na++, nb++)
1613 *na=value;
1614 o=TIFFWriteDirectoryTagCheckedDoubleArray(tif,ndir,dir,tag,tif->tif_dir.td_samplesperpixel,m);
1615 _TIFFfree(m);
1616 return(o);
1617 }
1618 #endif
1619
1620 static int
TIFFWriteDirectoryTagIfdArray(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,uint32 * value)1621 TIFFWriteDirectoryTagIfdArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, uint32* value)
1622 {
1623 if (dir==NULL)
1624 {
1625 (*ndir)++;
1626 return(1);
1627 }
1628 return(TIFFWriteDirectoryTagCheckedIfdArray(tif,ndir,dir,tag,count,value));
1629 }
1630
1631 #ifdef notdef
1632 static int
TIFFWriteDirectoryTagIfd8Array(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,uint64 * value)1633 TIFFWriteDirectoryTagIfd8Array(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, uint64* value)
1634 {
1635 if (dir==NULL)
1636 {
1637 (*ndir)++;
1638 return(1);
1639 }
1640 return(TIFFWriteDirectoryTagCheckedIfd8Array(tif,ndir,dir,tag,count,value));
1641 }
1642 #endif
1643
1644 static int
TIFFWriteDirectoryTagShortLong(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 value)1645 TIFFWriteDirectoryTagShortLong(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 value)
1646 {
1647 if (dir==NULL)
1648 {
1649 (*ndir)++;
1650 return(1);
1651 }
1652 if (value<=0xFFFF)
1653 return(TIFFWriteDirectoryTagCheckedShort(tif,ndir,dir,tag,(uint16)value));
1654 else
1655 return(TIFFWriteDirectoryTagCheckedLong(tif,ndir,dir,tag,value));
1656 }
1657
1658 /************************************************************************/
1659 /* TIFFWriteDirectoryTagLongLong8Array() */
1660 /* */
1661 /* Write out LONG8 array as LONG8 for BigTIFF or LONG for */
1662 /* Classic TIFF with some checking. */
1663 /************************************************************************/
1664
1665 static int
TIFFWriteDirectoryTagLongLong8Array(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,uint64 * value)1666 TIFFWriteDirectoryTagLongLong8Array(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, uint64* value)
1667 {
1668 static const char module[] = "TIFFWriteDirectoryTagLongLong8Array";
1669 uint64* ma;
1670 uint32 mb;
1671 uint32* p;
1672 uint32* q;
1673 int o;
1674
1675 /* is this just a counting pass? */
1676 if (dir==NULL)
1677 {
1678 (*ndir)++;
1679 return(1);
1680 }
1681
1682 /* We always write LONG8 for BigTIFF, no checking needed. */
1683 if( tif->tif_flags&TIFF_BIGTIFF )
1684 return TIFFWriteDirectoryTagCheckedLong8Array(tif,ndir,dir,
1685 tag,count,value);
1686
1687 /*
1688 ** For classic tiff we want to verify everything is in range for LONG
1689 ** and convert to long format.
1690 */
1691
1692 p = _TIFFmalloc(count*sizeof(uint32));
1693 if (p==NULL)
1694 {
1695 TIFFErrorExt(tif->tif_clientdata,module,"Out of memory");
1696 return(0);
1697 }
1698
1699 for (q=p, ma=value, mb=0; mb<count; ma++, mb++, q++)
1700 {
1701 if (*ma>0xFFFFFFFF)
1702 {
1703 TIFFErrorExt(tif->tif_clientdata,module,
1704 "Attempt to write value larger than 0xFFFFFFFF in Classic TIFF file.");
1705 _TIFFfree(p);
1706 return(0);
1707 }
1708 *q= (uint32)(*ma);
1709 }
1710
1711 o=TIFFWriteDirectoryTagCheckedLongArray(tif,ndir,dir,tag,count,p);
1712 _TIFFfree(p);
1713
1714 return(o);
1715 }
1716
1717 /************************************************************************/
1718 /* TIFFWriteDirectoryTagIfdIfd8Array() */
1719 /* */
1720 /* Write either IFD8 or IFD array depending on file type. */
1721 /************************************************************************/
1722
1723 static int
TIFFWriteDirectoryTagIfdIfd8Array(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,uint64 * value)1724 TIFFWriteDirectoryTagIfdIfd8Array(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, uint64* value)
1725 {
1726 static const char module[] = "TIFFWriteDirectoryTagIfdIfd8Array";
1727 uint64* ma;
1728 uint32 mb;
1729 uint32* p;
1730 uint32* q;
1731 int o;
1732
1733 /* is this just a counting pass? */
1734 if (dir==NULL)
1735 {
1736 (*ndir)++;
1737 return(1);
1738 }
1739
1740 /* We always write IFD8 for BigTIFF, no checking needed. */
1741 if( tif->tif_flags&TIFF_BIGTIFF )
1742 return TIFFWriteDirectoryTagCheckedIfd8Array(tif,ndir,dir,
1743 tag,count,value);
1744
1745 /*
1746 ** For classic tiff we want to verify everything is in range for IFD
1747 ** and convert to long format.
1748 */
1749
1750 p = _TIFFmalloc(count*sizeof(uint32));
1751 if (p==NULL)
1752 {
1753 TIFFErrorExt(tif->tif_clientdata,module,"Out of memory");
1754 return(0);
1755 }
1756
1757 for (q=p, ma=value, mb=0; mb<count; ma++, mb++, q++)
1758 {
1759 if (*ma>0xFFFFFFFF)
1760 {
1761 TIFFErrorExt(tif->tif_clientdata,module,
1762 "Attempt to write value larger than 0xFFFFFFFF in Classic TIFF file.");
1763 _TIFFfree(p);
1764 return(0);
1765 }
1766 *q= (uint32)(*ma);
1767 }
1768
1769 o=TIFFWriteDirectoryTagCheckedIfdArray(tif,ndir,dir,tag,count,p);
1770 _TIFFfree(p);
1771
1772 return(o);
1773 }
1774
1775 #ifdef notdef
1776 static int
TIFFWriteDirectoryTagShortLongLong8Array(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,uint64 * value)1777 TIFFWriteDirectoryTagShortLongLong8Array(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, uint64* value)
1778 {
1779 static const char module[] = "TIFFWriteDirectoryTagShortLongLong8Array";
1780 uint64* ma;
1781 uint32 mb;
1782 uint8 n;
1783 int o;
1784 if (dir==NULL)
1785 {
1786 (*ndir)++;
1787 return(1);
1788 }
1789 n=0;
1790 for (ma=value, mb=0; mb<count; ma++, mb++)
1791 {
1792 if ((n==0)&&(*ma>0xFFFF))
1793 n=1;
1794 if ((n==1)&&(*ma>0xFFFFFFFF))
1795 {
1796 n=2;
1797 break;
1798 }
1799 }
1800 if (n==0)
1801 {
1802 uint16* p;
1803 uint16* q;
1804 p=_TIFFmalloc(count*sizeof(uint16));
1805 if (p==NULL)
1806 {
1807 TIFFErrorExt(tif->tif_clientdata,module,"Out of memory");
1808 return(0);
1809 }
1810 for (ma=value, mb=0, q=p; mb<count; ma++, mb++, q++)
1811 *q=(uint16)(*ma);
1812 o=TIFFWriteDirectoryTagCheckedShortArray(tif,ndir,dir,tag,count,p);
1813 _TIFFfree(p);
1814 }
1815 else if (n==1)
1816 {
1817 uint32* p;
1818 uint32* q;
1819 p=_TIFFmalloc(count*sizeof(uint32));
1820 if (p==NULL)
1821 {
1822 TIFFErrorExt(tif->tif_clientdata,module,"Out of memory");
1823 return(0);
1824 }
1825 for (ma=value, mb=0, q=p; mb<count; ma++, mb++, q++)
1826 *q=(uint32)(*ma);
1827 o=TIFFWriteDirectoryTagCheckedLongArray(tif,ndir,dir,tag,count,p);
1828 _TIFFfree(p);
1829 }
1830 else
1831 {
1832 assert(n==2);
1833 o=TIFFWriteDirectoryTagCheckedLong8Array(tif,ndir,dir,tag,count,value);
1834 }
1835 return(o);
1836 }
1837 #endif
1838 static int
TIFFWriteDirectoryTagColormap(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir)1839 TIFFWriteDirectoryTagColormap(TIFF* tif, uint32* ndir, TIFFDirEntry* dir)
1840 {
1841 static const char module[] = "TIFFWriteDirectoryTagColormap";
1842 uint32 m;
1843 uint16* n;
1844 int o;
1845 if (dir==NULL)
1846 {
1847 (*ndir)++;
1848 return(1);
1849 }
1850 m=(1<<tif->tif_dir.td_bitspersample);
1851 n=_TIFFmalloc(3*m*sizeof(uint16));
1852 if (n==NULL)
1853 {
1854 TIFFErrorExt(tif->tif_clientdata,module,"Out of memory");
1855 return(0);
1856 }
1857 _TIFFmemcpy(&n[0],tif->tif_dir.td_colormap[0],m*sizeof(uint16));
1858 _TIFFmemcpy(&n[m],tif->tif_dir.td_colormap[1],m*sizeof(uint16));
1859 _TIFFmemcpy(&n[2*m],tif->tif_dir.td_colormap[2],m*sizeof(uint16));
1860 o=TIFFWriteDirectoryTagCheckedShortArray(tif,ndir,dir,TIFFTAG_COLORMAP,3*m,n);
1861 _TIFFfree(n);
1862 return(o);
1863 }
1864
1865 static int
TIFFWriteDirectoryTagTransferfunction(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir)1866 TIFFWriteDirectoryTagTransferfunction(TIFF* tif, uint32* ndir, TIFFDirEntry* dir)
1867 {
1868 static const char module[] = "TIFFWriteDirectoryTagTransferfunction";
1869 uint32 m;
1870 uint16 n;
1871 uint16* o;
1872 int p;
1873 if (dir==NULL)
1874 {
1875 (*ndir)++;
1876 return(1);
1877 }
1878 m=(1<<tif->tif_dir.td_bitspersample);
1879 n=tif->tif_dir.td_samplesperpixel-tif->tif_dir.td_extrasamples;
1880 /*
1881 * Check if the table can be written as a single column,
1882 * or if it must be written as 3 columns. Note that we
1883 * write a 3-column tag if there are 2 samples/pixel and
1884 * a single column of data won't suffice--hmm.
1885 */
1886 if (n>3)
1887 n=3;
1888 if (n==3)
1889 {
1890 if (!_TIFFmemcmp(tif->tif_dir.td_transferfunction[0],tif->tif_dir.td_transferfunction[2],m*sizeof(uint16)))
1891 n=2;
1892 }
1893 if (n==2)
1894 {
1895 if (!_TIFFmemcmp(tif->tif_dir.td_transferfunction[0],tif->tif_dir.td_transferfunction[1],m*sizeof(uint16)))
1896 n=1;
1897 }
1898 if (n==0)
1899 n=1;
1900 o=_TIFFmalloc(n*m*sizeof(uint16));
1901 if (o==NULL)
1902 {
1903 TIFFErrorExt(tif->tif_clientdata,module,"Out of memory");
1904 return(0);
1905 }
1906 _TIFFmemcpy(&o[0],tif->tif_dir.td_transferfunction[0],m*sizeof(uint16));
1907 if (n>1)
1908 _TIFFmemcpy(&o[m],tif->tif_dir.td_transferfunction[1],m*sizeof(uint16));
1909 if (n>2)
1910 _TIFFmemcpy(&o[2*m],tif->tif_dir.td_transferfunction[2],m*sizeof(uint16));
1911 p=TIFFWriteDirectoryTagCheckedShortArray(tif,ndir,dir,TIFFTAG_TRANSFERFUNCTION,n*m,o);
1912 _TIFFfree(o);
1913 return(p);
1914 }
1915
1916 static int
TIFFWriteDirectoryTagSubifd(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir)1917 TIFFWriteDirectoryTagSubifd(TIFF* tif, uint32* ndir, TIFFDirEntry* dir)
1918 {
1919 static const char module[] = "TIFFWriteDirectoryTagSubifd";
1920 uint64 m;
1921 int n;
1922 if (tif->tif_dir.td_nsubifd==0)
1923 return(1);
1924 if (dir==NULL)
1925 {
1926 (*ndir)++;
1927 return(1);
1928 }
1929 m=tif->tif_dataoff;
1930 if (!(tif->tif_flags&TIFF_BIGTIFF))
1931 {
1932 uint32* o;
1933 uint64* pa;
1934 uint32* pb;
1935 uint16 p;
1936 o=_TIFFmalloc(tif->tif_dir.td_nsubifd*sizeof(uint32));
1937 if (o==NULL)
1938 {
1939 TIFFErrorExt(tif->tif_clientdata,module,"Out of memory");
1940 return(0);
1941 }
1942 pa=tif->tif_dir.td_subifd;
1943 pb=o;
1944 for (p=0; p < tif->tif_dir.td_nsubifd; p++)
1945 {
1946 assert(pa != 0);
1947 assert(*pa <= 0xFFFFFFFFUL);
1948 *pb++=(uint32)(*pa++);
1949 }
1950 n=TIFFWriteDirectoryTagCheckedIfdArray(tif,ndir,dir,TIFFTAG_SUBIFD,tif->tif_dir.td_nsubifd,o);
1951 _TIFFfree(o);
1952 }
1953 else
1954 n=TIFFWriteDirectoryTagCheckedIfd8Array(tif,ndir,dir,TIFFTAG_SUBIFD,tif->tif_dir.td_nsubifd,tif->tif_dir.td_subifd);
1955 if (!n)
1956 return(0);
1957 /*
1958 * Total hack: if this directory includes a SubIFD
1959 * tag then force the next <n> directories to be
1960 * written as ``sub directories'' of this one. This
1961 * is used to write things like thumbnails and
1962 * image masks that one wants to keep out of the
1963 * normal directory linkage access mechanism.
1964 */
1965 tif->tif_flags|=TIFF_INSUBIFD;
1966 tif->tif_nsubifd=tif->tif_dir.td_nsubifd;
1967 if (tif->tif_dir.td_nsubifd==1)
1968 tif->tif_subifdoff=0;
1969 else
1970 tif->tif_subifdoff=m;
1971 return(1);
1972 }
1973
1974 static int
TIFFWriteDirectoryTagCheckedAscii(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,char * value)1975 TIFFWriteDirectoryTagCheckedAscii(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, char* value)
1976 {
1977 assert(sizeof(char)==1);
1978 return(TIFFWriteDirectoryTagData(tif,ndir,dir,tag,TIFF_ASCII,count,count,value));
1979 }
1980
1981 static int
TIFFWriteDirectoryTagCheckedUndefinedArray(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,uint8 * value)1982 TIFFWriteDirectoryTagCheckedUndefinedArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, uint8* value)
1983 {
1984 assert(sizeof(uint8)==1);
1985 return(TIFFWriteDirectoryTagData(tif,ndir,dir,tag,TIFF_UNDEFINED,count,count,value));
1986 }
1987
1988 #ifdef notdef
1989 static int
TIFFWriteDirectoryTagCheckedByte(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint8 value)1990 TIFFWriteDirectoryTagCheckedByte(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint8 value)
1991 {
1992 assert(sizeof(uint8)==1);
1993 return(TIFFWriteDirectoryTagData(tif,ndir,dir,tag,TIFF_BYTE,1,1,&value));
1994 }
1995 #endif
1996
1997 static int
TIFFWriteDirectoryTagCheckedByteArray(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,uint8 * value)1998 TIFFWriteDirectoryTagCheckedByteArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, uint8* value)
1999 {
2000 assert(sizeof(uint8)==1);
2001 return(TIFFWriteDirectoryTagData(tif,ndir,dir,tag,TIFF_BYTE,count,count,value));
2002 }
2003
2004 #ifdef notdef
2005 static int
TIFFWriteDirectoryTagCheckedSbyte(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,int8 value)2006 TIFFWriteDirectoryTagCheckedSbyte(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, int8 value)
2007 {
2008 assert(sizeof(int8)==1);
2009 return(TIFFWriteDirectoryTagData(tif,ndir,dir,tag,TIFF_SBYTE,1,1,&value));
2010 }
2011 #endif
2012
2013 static int
TIFFWriteDirectoryTagCheckedSbyteArray(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,int8 * value)2014 TIFFWriteDirectoryTagCheckedSbyteArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, int8* value)
2015 {
2016 assert(sizeof(int8)==1);
2017 return(TIFFWriteDirectoryTagData(tif,ndir,dir,tag,TIFF_SBYTE,count,count,value));
2018 }
2019
2020 static int
TIFFWriteDirectoryTagCheckedShort(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint16 value)2021 TIFFWriteDirectoryTagCheckedShort(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint16 value)
2022 {
2023 uint16 m;
2024 assert(sizeof(uint16)==2);
2025 m=value;
2026 if (tif->tif_flags&TIFF_SWAB)
2027 TIFFSwabShort(&m);
2028 return(TIFFWriteDirectoryTagData(tif,ndir,dir,tag,TIFF_SHORT,1,2,&m));
2029 }
2030
2031 static int
TIFFWriteDirectoryTagCheckedShortArray(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,uint16 * value)2032 TIFFWriteDirectoryTagCheckedShortArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, uint16* value)
2033 {
2034 assert(count<0x80000000);
2035 assert(sizeof(uint16)==2);
2036 if (tif->tif_flags&TIFF_SWAB)
2037 TIFFSwabArrayOfShort(value,count);
2038 return(TIFFWriteDirectoryTagData(tif,ndir,dir,tag,TIFF_SHORT,count,count*2,value));
2039 }
2040
2041 #ifdef notdef
2042 static int
TIFFWriteDirectoryTagCheckedSshort(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,int16 value)2043 TIFFWriteDirectoryTagCheckedSshort(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, int16 value)
2044 {
2045 int16 m;
2046 assert(sizeof(int16)==2);
2047 m=value;
2048 if (tif->tif_flags&TIFF_SWAB)
2049 TIFFSwabShort((uint16*)(&m));
2050 return(TIFFWriteDirectoryTagData(tif,ndir,dir,tag,TIFF_SSHORT,1,2,&m));
2051 }
2052 #endif
2053
2054 static int
TIFFWriteDirectoryTagCheckedSshortArray(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,int16 * value)2055 TIFFWriteDirectoryTagCheckedSshortArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, int16* value)
2056 {
2057 assert(count<0x80000000);
2058 assert(sizeof(int16)==2);
2059 if (tif->tif_flags&TIFF_SWAB)
2060 TIFFSwabArrayOfShort((uint16*)value,count);
2061 return(TIFFWriteDirectoryTagData(tif,ndir,dir,tag,TIFF_SSHORT,count,count*2,value));
2062 }
2063
2064 static int
TIFFWriteDirectoryTagCheckedLong(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 value)2065 TIFFWriteDirectoryTagCheckedLong(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 value)
2066 {
2067 uint32 m;
2068 assert(sizeof(uint32)==4);
2069 m=value;
2070 if (tif->tif_flags&TIFF_SWAB)
2071 TIFFSwabLong(&m);
2072 return(TIFFWriteDirectoryTagData(tif,ndir,dir,tag,TIFF_LONG,1,4,&m));
2073 }
2074
2075 static int
TIFFWriteDirectoryTagCheckedLongArray(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,uint32 * value)2076 TIFFWriteDirectoryTagCheckedLongArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, uint32* value)
2077 {
2078 assert(count<0x40000000);
2079 assert(sizeof(uint32)==4);
2080 if (tif->tif_flags&TIFF_SWAB)
2081 TIFFSwabArrayOfLong(value,count);
2082 return(TIFFWriteDirectoryTagData(tif,ndir,dir,tag,TIFF_LONG,count,count*4,value));
2083 }
2084
2085 #ifdef notdef
2086 static int
TIFFWriteDirectoryTagCheckedSlong(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,int32 value)2087 TIFFWriteDirectoryTagCheckedSlong(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, int32 value)
2088 {
2089 int32 m;
2090 assert(sizeof(int32)==4);
2091 m=value;
2092 if (tif->tif_flags&TIFF_SWAB)
2093 TIFFSwabLong((uint32*)(&m));
2094 return(TIFFWriteDirectoryTagData(tif,ndir,dir,tag,TIFF_SLONG,1,4,&m));
2095 }
2096 #endif
2097
2098 static int
TIFFWriteDirectoryTagCheckedSlongArray(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,int32 * value)2099 TIFFWriteDirectoryTagCheckedSlongArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, int32* value)
2100 {
2101 assert(count<0x40000000);
2102 assert(sizeof(int32)==4);
2103 if (tif->tif_flags&TIFF_SWAB)
2104 TIFFSwabArrayOfLong((uint32*)value,count);
2105 return(TIFFWriteDirectoryTagData(tif,ndir,dir,tag,TIFF_SLONG,count,count*4,value));
2106 }
2107
2108 #ifdef notdef
2109 static int
TIFFWriteDirectoryTagCheckedLong8(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint64 value)2110 TIFFWriteDirectoryTagCheckedLong8(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint64 value)
2111 {
2112 uint64 m;
2113 assert(sizeof(uint64)==8);
2114 assert(tif->tif_flags&TIFF_BIGTIFF);
2115 m=value;
2116 if (tif->tif_flags&TIFF_SWAB)
2117 TIFFSwabLong8(&m);
2118 return(TIFFWriteDirectoryTagData(tif,ndir,dir,tag,TIFF_LONG8,1,8,&m));
2119 }
2120 #endif
2121
2122 static int
TIFFWriteDirectoryTagCheckedLong8Array(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,uint64 * value)2123 TIFFWriteDirectoryTagCheckedLong8Array(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, uint64* value)
2124 {
2125 assert(count<0x20000000);
2126 assert(sizeof(uint64)==8);
2127 assert(tif->tif_flags&TIFF_BIGTIFF);
2128 if (tif->tif_flags&TIFF_SWAB)
2129 TIFFSwabArrayOfLong8(value,count);
2130 return(TIFFWriteDirectoryTagData(tif,ndir,dir,tag,TIFF_LONG8,count,count*8,value));
2131 }
2132
2133 #ifdef notdef
2134 static int
TIFFWriteDirectoryTagCheckedSlong8(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,int64 value)2135 TIFFWriteDirectoryTagCheckedSlong8(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, int64 value)
2136 {
2137 int64 m;
2138 assert(sizeof(int64)==8);
2139 assert(tif->tif_flags&TIFF_BIGTIFF);
2140 m=value;
2141 if (tif->tif_flags&TIFF_SWAB)
2142 TIFFSwabLong8((uint64*)(&m));
2143 return(TIFFWriteDirectoryTagData(tif,ndir,dir,tag,TIFF_SLONG8,1,8,&m));
2144 }
2145 #endif
2146
2147 static int
TIFFWriteDirectoryTagCheckedSlong8Array(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,int64 * value)2148 TIFFWriteDirectoryTagCheckedSlong8Array(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, int64* value)
2149 {
2150 assert(count<0x20000000);
2151 assert(sizeof(int64)==8);
2152 assert(tif->tif_flags&TIFF_BIGTIFF);
2153 if (tif->tif_flags&TIFF_SWAB)
2154 TIFFSwabArrayOfLong8((uint64*)value,count);
2155 return(TIFFWriteDirectoryTagData(tif,ndir,dir,tag,TIFF_SLONG8,count,count*8,value));
2156 }
2157
2158 static int
TIFFWriteDirectoryTagCheckedRational(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,double value)2159 TIFFWriteDirectoryTagCheckedRational(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, double value)
2160 {
2161 static const char module[] = "TIFFWriteDirectoryTagCheckedRational";
2162 uint32 m[2];
2163 assert(sizeof(uint32)==4);
2164 if( value < 0 )
2165 {
2166 TIFFErrorExt(tif->tif_clientdata,module,"Negative value is illegal");
2167 return 0;
2168 }
2169 else if( value != value )
2170 {
2171 TIFFErrorExt(tif->tif_clientdata,module,"Not-a-number value is illegal");
2172 return 0;
2173 }
2174 else if (value==0.0)
2175 {
2176 m[0]=0;
2177 m[1]=1;
2178 }
2179 else if (value <= 0xFFFFFFFFU && value==(double)(uint32)value)
2180 {
2181 m[0]=(uint32)value;
2182 m[1]=1;
2183 }
2184 else if (value<1.0)
2185 {
2186 m[0]=(uint32)(value*0xFFFFFFFF);
2187 m[1]=0xFFFFFFFF;
2188 }
2189 else
2190 {
2191 m[0]=0xFFFFFFFF;
2192 m[1]=(uint32)(0xFFFFFFFF/value);
2193 }
2194 if (tif->tif_flags&TIFF_SWAB)
2195 {
2196 TIFFSwabLong(&m[0]);
2197 TIFFSwabLong(&m[1]);
2198 }
2199 return(TIFFWriteDirectoryTagData(tif,ndir,dir,tag,TIFF_RATIONAL,1,8,&m[0]));
2200 }
2201
2202 static int
TIFFWriteDirectoryTagCheckedRationalArray(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,float * value)2203 TIFFWriteDirectoryTagCheckedRationalArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, float* value)
2204 {
2205 static const char module[] = "TIFFWriteDirectoryTagCheckedRationalArray";
2206 uint32* m;
2207 float* na;
2208 uint32* nb;
2209 uint32 nc;
2210 int o;
2211 assert(sizeof(uint32)==4);
2212 m=_TIFFmalloc(count*2*sizeof(uint32));
2213 if (m==NULL)
2214 {
2215 TIFFErrorExt(tif->tif_clientdata,module,"Out of memory");
2216 return(0);
2217 }
2218 for (na=value, nb=m, nc=0; nc<count; na++, nb+=2, nc++)
2219 {
2220 if (*na<=0.0 || *na != *na)
2221 {
2222 nb[0]=0;
2223 nb[1]=1;
2224 }
2225 else if (*na >= 0 && *na <= (float)0xFFFFFFFFU &&
2226 *na==(float)(uint32)(*na))
2227 {
2228 nb[0]=(uint32)(*na);
2229 nb[1]=1;
2230 }
2231 else if (*na<1.0)
2232 {
2233 nb[0]=(uint32)((double)(*na)*0xFFFFFFFF);
2234 nb[1]=0xFFFFFFFF;
2235 }
2236 else
2237 {
2238 nb[0]=0xFFFFFFFF;
2239 nb[1]=(uint32)((double)0xFFFFFFFF/(*na));
2240 }
2241 }
2242 if (tif->tif_flags&TIFF_SWAB)
2243 TIFFSwabArrayOfLong(m,count*2);
2244 o=TIFFWriteDirectoryTagData(tif,ndir,dir,tag,TIFF_RATIONAL,count,count*8,&m[0]);
2245 _TIFFfree(m);
2246 return(o);
2247 }
2248
2249 static int
TIFFWriteDirectoryTagCheckedSrationalArray(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,float * value)2250 TIFFWriteDirectoryTagCheckedSrationalArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, float* value)
2251 {
2252 static const char module[] = "TIFFWriteDirectoryTagCheckedSrationalArray";
2253 int32* m;
2254 float* na;
2255 int32* nb;
2256 uint32 nc;
2257 int o;
2258 assert(sizeof(int32)==4);
2259 m=_TIFFmalloc(count*2*sizeof(int32));
2260 if (m==NULL)
2261 {
2262 TIFFErrorExt(tif->tif_clientdata,module,"Out of memory");
2263 return(0);
2264 }
2265 for (na=value, nb=m, nc=0; nc<count; na++, nb+=2, nc++)
2266 {
2267 if (*na<0.0)
2268 {
2269 if (*na==(int32)(*na))
2270 {
2271 nb[0]=(int32)(*na);
2272 nb[1]=1;
2273 }
2274 else if (*na>-1.0)
2275 {
2276 nb[0]=-(int32)((double)(-*na)*0x7FFFFFFF);
2277 nb[1]=0x7FFFFFFF;
2278 }
2279 else
2280 {
2281 nb[0]=-0x7FFFFFFF;
2282 nb[1]=(int32)((double)0x7FFFFFFF/(-*na));
2283 }
2284 }
2285 else
2286 {
2287 if (*na==(int32)(*na))
2288 {
2289 nb[0]=(int32)(*na);
2290 nb[1]=1;
2291 }
2292 else if (*na<1.0)
2293 {
2294 nb[0]=(int32)((double)(*na)*0x7FFFFFFF);
2295 nb[1]=0x7FFFFFFF;
2296 }
2297 else
2298 {
2299 nb[0]=0x7FFFFFFF;
2300 nb[1]=(int32)((double)0x7FFFFFFF/(*na));
2301 }
2302 }
2303 }
2304 if (tif->tif_flags&TIFF_SWAB)
2305 TIFFSwabArrayOfLong((uint32*)m,count*2);
2306 o=TIFFWriteDirectoryTagData(tif,ndir,dir,tag,TIFF_SRATIONAL,count,count*8,&m[0]);
2307 _TIFFfree(m);
2308 return(o);
2309 }
2310
2311 #ifdef notdef
2312 static int
TIFFWriteDirectoryTagCheckedFloat(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,float value)2313 TIFFWriteDirectoryTagCheckedFloat(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, float value)
2314 {
2315 float m;
2316 assert(sizeof(float)==4);
2317 m=value;
2318 TIFFCvtNativeToIEEEFloat(tif,1,&m);
2319 if (tif->tif_flags&TIFF_SWAB)
2320 TIFFSwabFloat(&m);
2321 return(TIFFWriteDirectoryTagData(tif,ndir,dir,tag,TIFF_FLOAT,1,4,&m));
2322 }
2323 #endif
2324
2325 static int
TIFFWriteDirectoryTagCheckedFloatArray(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,float * value)2326 TIFFWriteDirectoryTagCheckedFloatArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, float* value)
2327 {
2328 assert(count<0x40000000);
2329 assert(sizeof(float)==4);
2330 TIFFCvtNativeToIEEEFloat(tif,count,&value);
2331 if (tif->tif_flags&TIFF_SWAB)
2332 TIFFSwabArrayOfFloat(value,count);
2333 return(TIFFWriteDirectoryTagData(tif,ndir,dir,tag,TIFF_FLOAT,count,count*4,value));
2334 }
2335
2336 #ifdef notdef
2337 static int
TIFFWriteDirectoryTagCheckedDouble(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,double value)2338 TIFFWriteDirectoryTagCheckedDouble(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, double value)
2339 {
2340 double m;
2341 assert(sizeof(double)==8);
2342 m=value;
2343 TIFFCvtNativeToIEEEDouble(tif,1,&m);
2344 if (tif->tif_flags&TIFF_SWAB)
2345 TIFFSwabDouble(&m);
2346 return(TIFFWriteDirectoryTagData(tif,ndir,dir,tag,TIFF_DOUBLE,1,8,&m));
2347 }
2348 #endif
2349
2350 static int
TIFFWriteDirectoryTagCheckedDoubleArray(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,double * value)2351 TIFFWriteDirectoryTagCheckedDoubleArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, double* value)
2352 {
2353 assert(count<0x20000000);
2354 assert(sizeof(double)==8);
2355 TIFFCvtNativeToIEEEDouble(tif,count,&value);
2356 if (tif->tif_flags&TIFF_SWAB)
2357 TIFFSwabArrayOfDouble(value,count);
2358 return(TIFFWriteDirectoryTagData(tif,ndir,dir,tag,TIFF_DOUBLE,count,count*8,value));
2359 }
2360
2361 static int
TIFFWriteDirectoryTagCheckedIfdArray(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,uint32 * value)2362 TIFFWriteDirectoryTagCheckedIfdArray(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, uint32* value)
2363 {
2364 assert(count<0x40000000);
2365 assert(sizeof(uint32)==4);
2366 if (tif->tif_flags&TIFF_SWAB)
2367 TIFFSwabArrayOfLong(value,count);
2368 return(TIFFWriteDirectoryTagData(tif,ndir,dir,tag,TIFF_IFD,count,count*4,value));
2369 }
2370
2371 static int
TIFFWriteDirectoryTagCheckedIfd8Array(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint32 count,uint64 * value)2372 TIFFWriteDirectoryTagCheckedIfd8Array(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint32 count, uint64* value)
2373 {
2374 assert(count<0x20000000);
2375 assert(sizeof(uint64)==8);
2376 assert(tif->tif_flags&TIFF_BIGTIFF);
2377 if (tif->tif_flags&TIFF_SWAB)
2378 TIFFSwabArrayOfLong8(value,count);
2379 return(TIFFWriteDirectoryTagData(tif,ndir,dir,tag,TIFF_IFD8,count,count*8,value));
2380 }
2381
2382 static int
TIFFWriteDirectoryTagData(TIFF * tif,uint32 * ndir,TIFFDirEntry * dir,uint16 tag,uint16 datatype,uint32 count,uint32 datalength,void * data)2383 TIFFWriteDirectoryTagData(TIFF* tif, uint32* ndir, TIFFDirEntry* dir, uint16 tag, uint16 datatype, uint32 count, uint32 datalength, void* data)
2384 {
2385 static const char module[] = "TIFFWriteDirectoryTagData";
2386 uint32 m;
2387 m=0;
2388 while (m<(*ndir))
2389 {
2390 assert(dir[m].tdir_tag!=tag);
2391 if (dir[m].tdir_tag>tag)
2392 break;
2393 m++;
2394 }
2395 if (m<(*ndir))
2396 {
2397 uint32 n;
2398 for (n=*ndir; n>m; n--)
2399 dir[n]=dir[n-1];
2400 }
2401 dir[m].tdir_tag=tag;
2402 dir[m].tdir_type=datatype;
2403 dir[m].tdir_count=count;
2404 dir[m].tdir_offset.toff_long8 = 0;
2405 if (datalength<=((tif->tif_flags&TIFF_BIGTIFF)?0x8U:0x4U))
2406 _TIFFmemcpy(&dir[m].tdir_offset,data,datalength);
2407 else
2408 {
2409 uint64 na,nb;
2410 na=tif->tif_dataoff;
2411 nb=na+datalength;
2412 if (!(tif->tif_flags&TIFF_BIGTIFF))
2413 nb=(uint32)nb;
2414 if ((nb<na)||(nb<datalength))
2415 {
2416 TIFFErrorExt(tif->tif_clientdata,module,"Maximum TIFF file size exceeded");
2417 return(0);
2418 }
2419 if (!SeekOK(tif,na))
2420 {
2421 TIFFErrorExt(tif->tif_clientdata,module,"IO error writing tag data");
2422 return(0);
2423 }
2424 assert(datalength<0x80000000UL);
2425 if (!WriteOK(tif,data,(tmsize_t)datalength))
2426 {
2427 TIFFErrorExt(tif->tif_clientdata,module,"IO error writing tag data");
2428 return(0);
2429 }
2430 tif->tif_dataoff=nb;
2431 if (tif->tif_dataoff&1)
2432 tif->tif_dataoff++;
2433 if (!(tif->tif_flags&TIFF_BIGTIFF))
2434 {
2435 uint32 o;
2436 o=(uint32)na;
2437 if (tif->tif_flags&TIFF_SWAB)
2438 TIFFSwabLong(&o);
2439 _TIFFmemcpy(&dir[m].tdir_offset,&o,4);
2440 }
2441 else
2442 {
2443 dir[m].tdir_offset.toff_long8 = na;
2444 if (tif->tif_flags&TIFF_SWAB)
2445 TIFFSwabLong8(&dir[m].tdir_offset.toff_long8);
2446 }
2447 }
2448 (*ndir)++;
2449 return(1);
2450 }
2451
2452 /*
2453 * Link the current directory into the directory chain for the file.
2454 */
2455 static int
TIFFLinkDirectory(TIFF * tif)2456 TIFFLinkDirectory(TIFF* tif)
2457 {
2458 static const char module[] = "TIFFLinkDirectory";
2459
2460 tif->tif_diroff = (TIFFSeekFile(tif,0,SEEK_END)+1) & (~((toff_t)1));
2461
2462 /*
2463 * Handle SubIFDs
2464 */
2465 if (tif->tif_flags & TIFF_INSUBIFD)
2466 {
2467 if (!(tif->tif_flags&TIFF_BIGTIFF))
2468 {
2469 uint32 m;
2470 m = (uint32)tif->tif_diroff;
2471 if (tif->tif_flags & TIFF_SWAB)
2472 TIFFSwabLong(&m);
2473 (void) TIFFSeekFile(tif, tif->tif_subifdoff, SEEK_SET);
2474 if (!WriteOK(tif, &m, 4)) {
2475 TIFFErrorExt(tif->tif_clientdata, module,
2476 "Error writing SubIFD directory link");
2477 return (0);
2478 }
2479 /*
2480 * Advance to the next SubIFD or, if this is
2481 * the last one configured, revert back to the
2482 * normal directory linkage.
2483 */
2484 if (--tif->tif_nsubifd)
2485 tif->tif_subifdoff += 4;
2486 else
2487 tif->tif_flags &= ~TIFF_INSUBIFD;
2488 return (1);
2489 }
2490 else
2491 {
2492 uint64 m;
2493 m = tif->tif_diroff;
2494 if (tif->tif_flags & TIFF_SWAB)
2495 TIFFSwabLong8(&m);
2496 (void) TIFFSeekFile(tif, tif->tif_subifdoff, SEEK_SET);
2497 if (!WriteOK(tif, &m, 8)) {
2498 TIFFErrorExt(tif->tif_clientdata, module,
2499 "Error writing SubIFD directory link");
2500 return (0);
2501 }
2502 /*
2503 * Advance to the next SubIFD or, if this is
2504 * the last one configured, revert back to the
2505 * normal directory linkage.
2506 */
2507 if (--tif->tif_nsubifd)
2508 tif->tif_subifdoff += 8;
2509 else
2510 tif->tif_flags &= ~TIFF_INSUBIFD;
2511 return (1);
2512 }
2513 }
2514
2515 if (!(tif->tif_flags&TIFF_BIGTIFF))
2516 {
2517 uint32 m;
2518 uint32 nextdir;
2519 m = (uint32)(tif->tif_diroff);
2520 if (tif->tif_flags & TIFF_SWAB)
2521 TIFFSwabLong(&m);
2522 if (tif->tif_header.classic.tiff_diroff == 0) {
2523 /*
2524 * First directory, overwrite offset in header.
2525 */
2526 tif->tif_header.classic.tiff_diroff = (uint32) tif->tif_diroff;
2527 (void) TIFFSeekFile(tif,4, SEEK_SET);
2528 if (!WriteOK(tif, &m, 4)) {
2529 TIFFErrorExt(tif->tif_clientdata, tif->tif_name,
2530 "Error writing TIFF header");
2531 return (0);
2532 }
2533 return (1);
2534 }
2535 /*
2536 * Not the first directory, search to the last and append.
2537 */
2538 nextdir = tif->tif_header.classic.tiff_diroff;
2539 while(1) {
2540 uint16 dircount;
2541 uint32 nextnextdir;
2542
2543 if (!SeekOK(tif, nextdir) ||
2544 !ReadOK(tif, &dircount, 2)) {
2545 TIFFErrorExt(tif->tif_clientdata, module,
2546 "Error fetching directory count");
2547 return (0);
2548 }
2549 if (tif->tif_flags & TIFF_SWAB)
2550 TIFFSwabShort(&dircount);
2551 (void) TIFFSeekFile(tif,
2552 nextdir+2+dircount*12, SEEK_SET);
2553 if (!ReadOK(tif, &nextnextdir, 4)) {
2554 TIFFErrorExt(tif->tif_clientdata, module,
2555 "Error fetching directory link");
2556 return (0);
2557 }
2558 if (tif->tif_flags & TIFF_SWAB)
2559 TIFFSwabLong(&nextnextdir);
2560 if (nextnextdir==0)
2561 {
2562 (void) TIFFSeekFile(tif,
2563 nextdir+2+dircount*12, SEEK_SET);
2564 if (!WriteOK(tif, &m, 4)) {
2565 TIFFErrorExt(tif->tif_clientdata, module,
2566 "Error writing directory link");
2567 return (0);
2568 }
2569 break;
2570 }
2571 nextdir=nextnextdir;
2572 }
2573 }
2574 else
2575 {
2576 uint64 m;
2577 uint64 nextdir;
2578 m = tif->tif_diroff;
2579 if (tif->tif_flags & TIFF_SWAB)
2580 TIFFSwabLong8(&m);
2581 if (tif->tif_header.big.tiff_diroff == 0) {
2582 /*
2583 * First directory, overwrite offset in header.
2584 */
2585 tif->tif_header.big.tiff_diroff = tif->tif_diroff;
2586 (void) TIFFSeekFile(tif,8, SEEK_SET);
2587 if (!WriteOK(tif, &m, 8)) {
2588 TIFFErrorExt(tif->tif_clientdata, tif->tif_name,
2589 "Error writing TIFF header");
2590 return (0);
2591 }
2592 return (1);
2593 }
2594 /*
2595 * Not the first directory, search to the last and append.
2596 */
2597 nextdir = tif->tif_header.big.tiff_diroff;
2598 while(1) {
2599 uint64 dircount64;
2600 uint16 dircount;
2601 uint64 nextnextdir;
2602
2603 if (!SeekOK(tif, nextdir) ||
2604 !ReadOK(tif, &dircount64, 8)) {
2605 TIFFErrorExt(tif->tif_clientdata, module,
2606 "Error fetching directory count");
2607 return (0);
2608 }
2609 if (tif->tif_flags & TIFF_SWAB)
2610 TIFFSwabLong8(&dircount64);
2611 if (dircount64>0xFFFF)
2612 {
2613 TIFFErrorExt(tif->tif_clientdata, module,
2614 "Sanity check on tag count failed, likely corrupt TIFF");
2615 return (0);
2616 }
2617 dircount=(uint16)dircount64;
2618 (void) TIFFSeekFile(tif,
2619 nextdir+8+dircount*20, SEEK_SET);
2620 if (!ReadOK(tif, &nextnextdir, 8)) {
2621 TIFFErrorExt(tif->tif_clientdata, module,
2622 "Error fetching directory link");
2623 return (0);
2624 }
2625 if (tif->tif_flags & TIFF_SWAB)
2626 TIFFSwabLong8(&nextnextdir);
2627 if (nextnextdir==0)
2628 {
2629 (void) TIFFSeekFile(tif,
2630 nextdir+8+dircount*20, SEEK_SET);
2631 if (!WriteOK(tif, &m, 8)) {
2632 TIFFErrorExt(tif->tif_clientdata, module,
2633 "Error writing directory link");
2634 return (0);
2635 }
2636 break;
2637 }
2638 nextdir=nextnextdir;
2639 }
2640 }
2641 return (1);
2642 }
2643
2644 /************************************************************************/
2645 /* TIFFRewriteField() */
2646 /* */
2647 /* Rewrite a field in the directory on disk without regard to */
2648 /* updating the TIFF directory structure in memory. Currently */
2649 /* only supported for field that already exist in the on-disk */
2650 /* directory. Mainly used for updating stripoffset / */
2651 /* stripbytecount values after the directory is already on */
2652 /* disk. */
2653 /* */
2654 /* Returns zero on failure, and one on success. */
2655 /************************************************************************/
2656
2657 int
_TIFFRewriteField(TIFF * tif,uint16 tag,TIFFDataType in_datatype,tmsize_t count,void * data)2658 _TIFFRewriteField(TIFF* tif, uint16 tag, TIFFDataType in_datatype,
2659 tmsize_t count, void* data)
2660 {
2661 static const char module[] = "TIFFResetField";
2662 /* const TIFFField* fip = NULL; */
2663 uint16 dircount;
2664 tmsize_t dirsize;
2665 uint8 direntry_raw[20];
2666 uint16 entry_tag = 0;
2667 uint16 entry_type = 0;
2668 uint64 entry_count = 0;
2669 uint64 entry_offset = 0;
2670 int value_in_entry = 0;
2671 uint64 read_offset;
2672 uint8 *buf_to_write = NULL;
2673 TIFFDataType datatype;
2674
2675 /* -------------------------------------------------------------------- */
2676 /* Find field definition. */
2677 /* -------------------------------------------------------------------- */
2678 /*fip =*/ TIFFFindField(tif, tag, TIFF_ANY);
2679
2680 /* -------------------------------------------------------------------- */
2681 /* Do some checking this is a straight forward case. */
2682 /* -------------------------------------------------------------------- */
2683 if( isMapped(tif) )
2684 {
2685 TIFFErrorExt( tif->tif_clientdata, module,
2686 "Memory mapped files not currently supported for this operation." );
2687 return 0;
2688 }
2689
2690 if( tif->tif_diroff == 0 )
2691 {
2692 TIFFErrorExt( tif->tif_clientdata, module,
2693 "Attempt to reset field on directory not already on disk." );
2694 return 0;
2695 }
2696
2697 /* -------------------------------------------------------------------- */
2698 /* Read the directory entry count. */
2699 /* -------------------------------------------------------------------- */
2700 if (!SeekOK(tif, tif->tif_diroff)) {
2701 TIFFErrorExt(tif->tif_clientdata, module,
2702 "%s: Seek error accessing TIFF directory",
2703 tif->tif_name);
2704 return 0;
2705 }
2706
2707 read_offset = tif->tif_diroff;
2708
2709 if (!(tif->tif_flags&TIFF_BIGTIFF))
2710 {
2711 if (!ReadOK(tif, &dircount, sizeof (uint16))) {
2712 TIFFErrorExt(tif->tif_clientdata, module,
2713 "%s: Can not read TIFF directory count",
2714 tif->tif_name);
2715 return 0;
2716 }
2717 if (tif->tif_flags & TIFF_SWAB)
2718 TIFFSwabShort(&dircount);
2719 dirsize = 12;
2720 read_offset += 2;
2721 } else {
2722 uint64 dircount64;
2723 if (!ReadOK(tif, &dircount64, sizeof (uint64))) {
2724 TIFFErrorExt(tif->tif_clientdata, module,
2725 "%s: Can not read TIFF directory count",
2726 tif->tif_name);
2727 return 0;
2728 }
2729 if (tif->tif_flags & TIFF_SWAB)
2730 TIFFSwabLong8(&dircount64);
2731 dircount = (uint16)dircount64;
2732 dirsize = 20;
2733 read_offset += 8;
2734 }
2735
2736 /* -------------------------------------------------------------------- */
2737 /* Read through directory to find target tag. */
2738 /* -------------------------------------------------------------------- */
2739 while( dircount > 0 )
2740 {
2741 if (!ReadOK(tif, direntry_raw, dirsize)) {
2742 TIFFErrorExt(tif->tif_clientdata, module,
2743 "%s: Can not read TIFF directory entry.",
2744 tif->tif_name);
2745 return 0;
2746 }
2747
2748 memcpy( &entry_tag, direntry_raw + 0, sizeof(uint16) );
2749 if (tif->tif_flags&TIFF_SWAB)
2750 TIFFSwabShort( &entry_tag );
2751
2752 if( entry_tag == tag )
2753 break;
2754
2755 read_offset += dirsize;
2756 }
2757
2758 if( entry_tag != tag )
2759 {
2760 TIFFErrorExt(tif->tif_clientdata, module,
2761 "%s: Could not find tag %d.",
2762 tif->tif_name, tag );
2763 return 0;
2764 }
2765
2766 /* -------------------------------------------------------------------- */
2767 /* Extract the type, count and offset for this entry. */
2768 /* -------------------------------------------------------------------- */
2769 memcpy( &entry_type, direntry_raw + 2, sizeof(uint16) );
2770 if (tif->tif_flags&TIFF_SWAB)
2771 TIFFSwabShort( &entry_type );
2772
2773 if (!(tif->tif_flags&TIFF_BIGTIFF))
2774 {
2775 uint32 value;
2776
2777 memcpy( &value, direntry_raw + 4, sizeof(uint32) );
2778 if (tif->tif_flags&TIFF_SWAB)
2779 TIFFSwabLong( &value );
2780 entry_count = value;
2781
2782 memcpy( &value, direntry_raw + 8, sizeof(uint32) );
2783 if (tif->tif_flags&TIFF_SWAB)
2784 TIFFSwabLong( &value );
2785 entry_offset = value;
2786 }
2787 else
2788 {
2789 memcpy( &entry_count, direntry_raw + 4, sizeof(uint64) );
2790 if (tif->tif_flags&TIFF_SWAB)
2791 TIFFSwabLong8( &entry_count );
2792
2793 memcpy( &entry_offset, direntry_raw + 12, sizeof(uint64) );
2794 if (tif->tif_flags&TIFF_SWAB)
2795 TIFFSwabLong8( &entry_offset );
2796 }
2797
2798 /* -------------------------------------------------------------------- */
2799 /* What data type do we want to write this as? */
2800 /* -------------------------------------------------------------------- */
2801 if( TIFFDataWidth(in_datatype) == 8 && !(tif->tif_flags&TIFF_BIGTIFF) )
2802 {
2803 if( in_datatype == TIFF_LONG8 )
2804 datatype = TIFF_LONG;
2805 else if( in_datatype == TIFF_SLONG8 )
2806 datatype = TIFF_SLONG;
2807 else if( in_datatype == TIFF_IFD8 )
2808 datatype = TIFF_IFD;
2809 else
2810 datatype = in_datatype;
2811 }
2812 else
2813 datatype = in_datatype;
2814
2815 /* -------------------------------------------------------------------- */
2816 /* Prepare buffer of actual data to write. This includes */
2817 /* swabbing as needed. */
2818 /* -------------------------------------------------------------------- */
2819 buf_to_write =
2820 (uint8 *)_TIFFCheckMalloc(tif, count, TIFFDataWidth(datatype),
2821 "for field buffer.");
2822 if (!buf_to_write)
2823 return 0;
2824
2825 if( datatype == in_datatype )
2826 memcpy( buf_to_write, data, count * TIFFDataWidth(datatype) );
2827 else if( datatype == TIFF_SLONG && in_datatype == TIFF_SLONG8 )
2828 {
2829 tmsize_t i;
2830
2831 for( i = 0; i < count; i++ )
2832 {
2833 ((int32 *) buf_to_write)[i] =
2834 (int32) ((int64 *) data)[i];
2835 if( (int64) ((int32 *) buf_to_write)[i] != ((int64 *) data)[i] )
2836 {
2837 _TIFFfree( buf_to_write );
2838 TIFFErrorExt( tif->tif_clientdata, module,
2839 "Value exceeds 32bit range of output type." );
2840 return 0;
2841 }
2842 }
2843 }
2844 else if( (datatype == TIFF_LONG && in_datatype == TIFF_LONG8)
2845 || (datatype == TIFF_IFD && in_datatype == TIFF_IFD8) )
2846 {
2847 tmsize_t i;
2848
2849 for( i = 0; i < count; i++ )
2850 {
2851 ((uint32 *) buf_to_write)[i] =
2852 (uint32) ((uint64 *) data)[i];
2853 if( (uint64) ((uint32 *) buf_to_write)[i] != ((uint64 *) data)[i] )
2854 {
2855 _TIFFfree( buf_to_write );
2856 TIFFErrorExt( tif->tif_clientdata, module,
2857 "Value exceeds 32bit range of output type." );
2858 return 0;
2859 }
2860 }
2861 }
2862
2863 if( TIFFDataWidth(datatype) > 1 && (tif->tif_flags&TIFF_SWAB) )
2864 {
2865 if( TIFFDataWidth(datatype) == 2 )
2866 TIFFSwabArrayOfShort( (uint16 *) buf_to_write, count );
2867 else if( TIFFDataWidth(datatype) == 4 )
2868 TIFFSwabArrayOfLong( (uint32 *) buf_to_write, count );
2869 else if( TIFFDataWidth(datatype) == 8 )
2870 TIFFSwabArrayOfLong8( (uint64 *) buf_to_write, count );
2871 }
2872
2873 /* -------------------------------------------------------------------- */
2874 /* Is this a value that fits into the directory entry? */
2875 /* -------------------------------------------------------------------- */
2876 if (!(tif->tif_flags&TIFF_BIGTIFF))
2877 {
2878 if( TIFFDataWidth(datatype) * count <= 4 )
2879 {
2880 entry_offset = read_offset + 8;
2881 value_in_entry = 1;
2882 }
2883 }
2884 else
2885 {
2886 if( TIFFDataWidth(datatype) * count <= 8 )
2887 {
2888 entry_offset = read_offset + 12;
2889 value_in_entry = 1;
2890 }
2891 }
2892
2893 /* -------------------------------------------------------------------- */
2894 /* If the tag type, and count match, then we just write it out */
2895 /* over the old values without altering the directory entry at */
2896 /* all. */
2897 /* -------------------------------------------------------------------- */
2898 if( entry_count == (uint64)count && entry_type == (uint16) datatype )
2899 {
2900 if (!SeekOK(tif, entry_offset)) {
2901 _TIFFfree( buf_to_write );
2902 TIFFErrorExt(tif->tif_clientdata, module,
2903 "%s: Seek error accessing TIFF directory",
2904 tif->tif_name);
2905 return 0;
2906 }
2907 if (!WriteOK(tif, buf_to_write, count*TIFFDataWidth(datatype))) {
2908 _TIFFfree( buf_to_write );
2909 TIFFErrorExt(tif->tif_clientdata, module,
2910 "Error writing directory link");
2911 return (0);
2912 }
2913
2914 _TIFFfree( buf_to_write );
2915 return 1;
2916 }
2917
2918 /* -------------------------------------------------------------------- */
2919 /* Otherwise, we write the new tag data at the end of the file. */
2920 /* -------------------------------------------------------------------- */
2921 if( !value_in_entry )
2922 {
2923 entry_offset = TIFFSeekFile(tif,0,SEEK_END);
2924
2925 if (!WriteOK(tif, buf_to_write, count*TIFFDataWidth(datatype))) {
2926 _TIFFfree( buf_to_write );
2927 TIFFErrorExt(tif->tif_clientdata, module,
2928 "Error writing directory link");
2929 return (0);
2930 }
2931 }
2932 else
2933 {
2934 memcpy( &entry_offset, buf_to_write, count*TIFFDataWidth(datatype));
2935 }
2936
2937 _TIFFfree( buf_to_write );
2938 buf_to_write = 0;
2939
2940 /* -------------------------------------------------------------------- */
2941 /* Adjust the directory entry. */
2942 /* -------------------------------------------------------------------- */
2943 entry_type = datatype;
2944 memcpy( direntry_raw + 2, &entry_type, sizeof(uint16) );
2945 if (tif->tif_flags&TIFF_SWAB)
2946 TIFFSwabShort( (uint16 *) (direntry_raw + 2) );
2947
2948 if (!(tif->tif_flags&TIFF_BIGTIFF))
2949 {
2950 uint32 value;
2951
2952 value = (uint32) entry_count;
2953 memcpy( direntry_raw + 4, &value, sizeof(uint32) );
2954 if (tif->tif_flags&TIFF_SWAB)
2955 TIFFSwabLong( (uint32 *) (direntry_raw + 4) );
2956
2957 value = (uint32) entry_offset;
2958 memcpy( direntry_raw + 8, &value, sizeof(uint32) );
2959 if (tif->tif_flags&TIFF_SWAB)
2960 TIFFSwabLong( (uint32 *) (direntry_raw + 8) );
2961 }
2962 else
2963 {
2964 memcpy( direntry_raw + 4, &entry_count, sizeof(uint64) );
2965 if (tif->tif_flags&TIFF_SWAB)
2966 TIFFSwabLong8( (uint64 *) (direntry_raw + 4) );
2967
2968 memcpy( direntry_raw + 12, &entry_offset, sizeof(uint64) );
2969 if (tif->tif_flags&TIFF_SWAB)
2970 TIFFSwabLong8( (uint64 *) (direntry_raw + 12) );
2971 }
2972
2973 /* -------------------------------------------------------------------- */
2974 /* Write the directory entry out to disk. */
2975 /* -------------------------------------------------------------------- */
2976 if (!SeekOK(tif, read_offset )) {
2977 TIFFErrorExt(tif->tif_clientdata, module,
2978 "%s: Seek error accessing TIFF directory",
2979 tif->tif_name);
2980 return 0;
2981 }
2982
2983 if (!WriteOK(tif, direntry_raw,dirsize))
2984 {
2985 TIFFErrorExt(tif->tif_clientdata, module,
2986 "%s: Can not write TIFF directory entry.",
2987 tif->tif_name);
2988 return 0;
2989 }
2990
2991 return 1;
2992 }
2993 /* vim: set ts=8 sts=8 sw=8 noet: */
2994 /*
2995 * Local Variables:
2996 * mode: c
2997 * c-basic-offset: 8
2998 * fill-column: 78
2999 * End:
3000 */
3001