Line data Source code
1 : /*
2 : * Copyright (c) 1988-1997 Sam Leffler
3 : * Copyright (c) 1991-1997 Silicon Graphics, Inc.
4 : *
5 : * Permission to use, copy, modify, distribute, and sell this software and
6 : * its documentation for any purpose is hereby granted without fee, provided
7 : * that (i) the above copyright notices and this permission notice appear in
8 : * all copies of the software and related documentation, and (ii) the names of
9 : * Sam Leffler and Silicon Graphics may not be used in any advertising or
10 : * publicity relating to the software without the specific, prior written
11 : * permission of Sam Leffler and Silicon Graphics.
12 : *
13 : * THE SOFTWARE IS PROVIDED "AS-IS" AND WITHOUT WARRANTY OF ANY KIND,
14 : * EXPRESS, IMPLIED OR OTHERWISE, INCLUDING WITHOUT LIMITATION, ANY
15 : * WARRANTY OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE.
16 : *
17 : * IN NO EVENT SHALL SAM LEFFLER OR SILICON GRAPHICS BE LIABLE FOR
18 : * ANY SPECIAL, INCIDENTAL, INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND,
19 : * OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS,
20 : * WHETHER OR NOT ADVISED OF THE POSSIBILITY OF DAMAGE, AND ON ANY THEORY OF
21 : * LIABILITY, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE
22 : * OF THIS SOFTWARE.
23 : */
24 :
25 : /*
26 : * TIFF Library.
27 : */
28 :
29 : #ifdef TIFF_DO_NOT_USE_NON_EXT_ALLOC_FUNCTIONS
30 : #undef TIFF_DO_NOT_USE_NON_EXT_ALLOC_FUNCTIONS
31 : #endif
32 :
33 : #include "tiffiop.h"
34 : #include <assert.h>
35 : #include <limits.h>
36 :
37 : /*
38 : * Dummy functions to fill the omitted client procedures.
39 : */
40 0 : static int _tiffDummyMapProc(thandle_t fd, void **pbase, toff_t *psize)
41 : {
42 : (void)fd;
43 : (void)pbase;
44 : (void)psize;
45 0 : return (0);
46 : }
47 :
48 0 : static void _tiffDummyUnmapProc(thandle_t fd, void *base, toff_t size)
49 : {
50 : (void)fd;
51 : (void)base;
52 : (void)size;
53 0 : }
54 :
55 61965 : int _TIFFgetMode(TIFFOpenOptions *opts, thandle_t clientdata, const char *mode,
56 : const char *module)
57 : {
58 61965 : int m = -1;
59 :
60 61965 : switch (mode[0])
61 : {
62 26073 : case 'r':
63 26073 : m = O_RDONLY;
64 26073 : if (mode[1] == '+')
65 3392 : m = O_RDWR;
66 26073 : break;
67 35859 : case 'w':
68 : case 'a':
69 35859 : m = O_RDWR | O_CREAT;
70 35859 : if (mode[0] == 'w')
71 35859 : m |= O_TRUNC;
72 35859 : break;
73 33 : default:
74 33 : _TIFFErrorEarly(opts, clientdata, module, "\"%s\": Bad mode", mode);
75 0 : break;
76 : }
77 61932 : return (m);
78 : }
79 :
80 61975 : TIFFOpenOptions *TIFFOpenOptionsAlloc()
81 : {
82 : TIFFOpenOptions *opts =
83 61975 : (TIFFOpenOptions *)_TIFFcalloc(1, sizeof(TIFFOpenOptions));
84 61934 : return opts;
85 : }
86 :
87 61909 : void TIFFOpenOptionsFree(TIFFOpenOptions *opts) { _TIFFfree(opts); }
88 :
89 : /** Define a limit in bytes for a single memory allocation done by libtiff.
90 : * If max_single_mem_alloc is set to 0, which is the default, no other limit
91 : * that the underlying _TIFFmalloc() or
92 : * TIFFOpenOptionsSetMaxCumulatedMemAlloc() will be applied.
93 : */
94 0 : void TIFFOpenOptionsSetMaxSingleMemAlloc(TIFFOpenOptions *opts,
95 : tmsize_t max_single_mem_alloc)
96 : {
97 0 : opts->max_single_mem_alloc = max_single_mem_alloc;
98 0 : }
99 :
100 : /** Define a limit in bytes for the cumulated memory allocations done by libtiff
101 : * on a given TIFF handle.
102 : * If max_cumulated_mem_alloc is set to 0, which is the default, no other limit
103 : * that the underlying _TIFFmalloc() or
104 : * TIFFOpenOptionsSetMaxSingleMemAlloc() will be applied.
105 : */
106 61956 : void TIFFOpenOptionsSetMaxCumulatedMemAlloc(TIFFOpenOptions *opts,
107 : tmsize_t max_cumulated_mem_alloc)
108 : {
109 61956 : opts->max_cumulated_mem_alloc = max_cumulated_mem_alloc;
110 61956 : }
111 :
112 : /** Whether a warning should be emitted when encoutering a unknown tag.
113 : * Default is FALSE since libtiff 4.7.1
114 : */
115 0 : void TIFFOpenOptionsSetWarnAboutUnknownTags(TIFFOpenOptions *opts,
116 : int warn_about_unknown_tags)
117 : {
118 0 : opts->warn_about_unknown_tags = warn_about_unknown_tags;
119 0 : }
120 :
121 61965 : void TIFFOpenOptionsSetErrorHandlerExtR(TIFFOpenOptions *opts,
122 : TIFFErrorHandlerExtR handler,
123 : void *errorhandler_user_data)
124 : {
125 61965 : opts->errorhandler = handler;
126 61965 : opts->errorhandler_user_data = errorhandler_user_data;
127 61965 : }
128 :
129 61924 : void TIFFOpenOptionsSetWarningHandlerExtR(TIFFOpenOptions *opts,
130 : TIFFErrorHandlerExtR handler,
131 : void *warnhandler_user_data)
132 : {
133 61924 : opts->warnhandler = handler;
134 61924 : opts->warnhandler_user_data = warnhandler_user_data;
135 61924 : }
136 :
137 0 : static void _TIFFEmitErrorAboveMaxSingleMemAlloc(TIFF *tif,
138 : const char *pszFunction,
139 : tmsize_t s)
140 : {
141 0 : TIFFErrorExtR(tif, pszFunction,
142 : "Memory allocation of %" PRIu64
143 : " bytes is beyond the %" PRIu64
144 : " byte limit defined in open options",
145 0 : (uint64_t)s, (uint64_t)tif->tif_max_single_mem_alloc);
146 0 : }
147 :
148 0 : static void _TIFFEmitErrorAboveMaxCumulatedMemAlloc(TIFF *tif,
149 : const char *pszFunction,
150 : tmsize_t s)
151 : {
152 0 : TIFFErrorExtR(tif, pszFunction,
153 : "Cumulated memory allocation of %" PRIu64 " + %" PRIu64
154 : " bytes is beyond the %" PRIu64
155 : " cumulated byte limit defined in open options",
156 0 : (uint64_t)tif->tif_cur_cumulated_mem_alloc, (uint64_t)s,
157 0 : (uint64_t)tif->tif_max_cumulated_mem_alloc);
158 0 : }
159 :
160 : /* When allocating memory, we write at the beginning of the buffer it size.
161 : * This allows us to keep track of the total memory allocated when we
162 : * malloc/calloc/realloc and free. In theory we need just SIZEOF_SIZE_T bytes
163 : * for that, but on x86_64, allocations of more than 16 bytes are aligned on
164 : * 16 bytes. Hence using 2 * SIZEOF_SIZE_T.
165 : * It is critical that _TIFFmallocExt/_TIFFcallocExt/_TIFFreallocExt are
166 : * paired with _TIFFfreeExt.
167 : * CMakeLists.txt defines TIFF_DO_NOT_USE_NON_EXT_ALLOC_FUNCTIONS, which in
168 : * turn disables the definition of the non Ext version in tiffio.h
169 : */
170 : #define LEADING_AREA_TO_STORE_ALLOC_SIZE (2 * SIZEOF_SIZE_T)
171 :
172 : /** malloc() version that takes into account memory-specific open options */
173 610804 : void *_TIFFmallocExt(TIFF *tif, tmsize_t s)
174 : {
175 610804 : if (tif != NULL && tif->tif_max_single_mem_alloc > 0 &&
176 0 : s > tif->tif_max_single_mem_alloc)
177 : {
178 0 : _TIFFEmitErrorAboveMaxSingleMemAlloc(tif, "_TIFFmallocExt", s);
179 0 : return NULL;
180 : }
181 610804 : if (tif != NULL && tif->tif_max_cumulated_mem_alloc > 0)
182 : {
183 547487 : if (s > tif->tif_max_cumulated_mem_alloc -
184 547487 : tif->tif_cur_cumulated_mem_alloc ||
185 547512 : s > TIFF_TMSIZE_T_MAX - LEADING_AREA_TO_STORE_ALLOC_SIZE)
186 : {
187 14 : _TIFFEmitErrorAboveMaxCumulatedMemAlloc(tif, "_TIFFmallocExt", s);
188 0 : return NULL;
189 : }
190 547473 : void *ptr = _TIFFmalloc(LEADING_AREA_TO_STORE_ALLOC_SIZE + s);
191 547587 : if (!ptr)
192 0 : return NULL;
193 547587 : tif->tif_cur_cumulated_mem_alloc += s;
194 547587 : memcpy(ptr, &s, sizeof(s));
195 547587 : return (char *)ptr + LEADING_AREA_TO_STORE_ALLOC_SIZE;
196 : }
197 63317 : return _TIFFmalloc(s);
198 : }
199 :
200 : /** calloc() version that takes into account memory-specific open options */
201 9217 : void *_TIFFcallocExt(TIFF *tif, tmsize_t nmemb, tmsize_t siz)
202 : {
203 9217 : if (nmemb <= 0 || siz <= 0 || nmemb > TIFF_TMSIZE_T_MAX / siz)
204 0 : return NULL;
205 9217 : if (tif != NULL && tif->tif_max_single_mem_alloc > 0)
206 : {
207 0 : if (nmemb * siz > tif->tif_max_single_mem_alloc)
208 : {
209 0 : _TIFFEmitErrorAboveMaxSingleMemAlloc(tif, "_TIFFcallocExt",
210 : nmemb * siz);
211 0 : return NULL;
212 : }
213 : }
214 9217 : if (tif != NULL && tif->tif_max_cumulated_mem_alloc > 0)
215 : {
216 9217 : const tmsize_t s = nmemb * siz;
217 9217 : if (s > tif->tif_max_cumulated_mem_alloc -
218 9217 : tif->tif_cur_cumulated_mem_alloc ||
219 9217 : s > TIFF_TMSIZE_T_MAX - LEADING_AREA_TO_STORE_ALLOC_SIZE)
220 : {
221 0 : _TIFFEmitErrorAboveMaxCumulatedMemAlloc(tif, "_TIFFcallocExt", s);
222 0 : return NULL;
223 : }
224 9217 : void *ptr = _TIFFcalloc(LEADING_AREA_TO_STORE_ALLOC_SIZE + s, 1);
225 9217 : if (!ptr)
226 0 : return NULL;
227 9217 : tif->tif_cur_cumulated_mem_alloc += s;
228 9217 : memcpy(ptr, &s, sizeof(s));
229 9217 : return (char *)ptr + LEADING_AREA_TO_STORE_ALLOC_SIZE;
230 : }
231 0 : return _TIFFcalloc(nmemb, siz);
232 : }
233 :
234 : /** realloc() version that takes into account memory-specific open options */
235 1573930 : void *_TIFFreallocExt(TIFF *tif, void *p, tmsize_t s)
236 : {
237 1573930 : if (tif != NULL && tif->tif_max_single_mem_alloc > 0 &&
238 0 : s > tif->tif_max_single_mem_alloc)
239 : {
240 0 : _TIFFEmitErrorAboveMaxSingleMemAlloc(tif, "_TIFFreallocExt", s);
241 0 : return NULL;
242 : }
243 1573930 : if (tif != NULL && tif->tif_max_cumulated_mem_alloc > 0)
244 : {
245 1515670 : void *oldPtr = p;
246 1515670 : tmsize_t oldSize = 0;
247 1515670 : if (p)
248 : {
249 497252 : oldPtr = (char *)p - LEADING_AREA_TO_STORE_ALLOC_SIZE;
250 497252 : memcpy(&oldSize, oldPtr, sizeof(oldSize));
251 497252 : assert(oldSize <= tif->tif_cur_cumulated_mem_alloc);
252 : }
253 1515670 : if (s > oldSize &&
254 1514360 : (s > tif->tif_max_cumulated_mem_alloc -
255 1514360 : (tif->tif_cur_cumulated_mem_alloc - oldSize) ||
256 1514290 : s > TIFF_TMSIZE_T_MAX - LEADING_AREA_TO_STORE_ALLOC_SIZE))
257 : {
258 70 : _TIFFEmitErrorAboveMaxCumulatedMemAlloc(tif, "_TIFFreallocExt",
259 : s - oldSize);
260 0 : return NULL;
261 : }
262 : void *newPtr =
263 1515600 : _TIFFrealloc(oldPtr, LEADING_AREA_TO_STORE_ALLOC_SIZE + s);
264 1516120 : if (newPtr == NULL)
265 0 : return NULL;
266 1516120 : tif->tif_cur_cumulated_mem_alloc -= oldSize;
267 1516120 : tif->tif_cur_cumulated_mem_alloc += s;
268 1516120 : memcpy(newPtr, &s, sizeof(s));
269 1516120 : return (char *)newPtr + LEADING_AREA_TO_STORE_ALLOC_SIZE;
270 : }
271 58260 : return _TIFFrealloc(p, s);
272 : }
273 :
274 : /** free() version that takes into account memory-specific open options */
275 1674470 : void _TIFFfreeExt(TIFF *tif, void *p)
276 : {
277 1674470 : if (p != NULL && tif != NULL && tif->tif_max_cumulated_mem_alloc > 0)
278 : {
279 1575760 : void *oldPtr = (char *)p - LEADING_AREA_TO_STORE_ALLOC_SIZE;
280 : tmsize_t oldSize;
281 1575760 : memcpy(&oldSize, oldPtr, sizeof(oldSize));
282 1575760 : assert(oldSize <= tif->tif_cur_cumulated_mem_alloc);
283 1575760 : tif->tif_cur_cumulated_mem_alloc -= oldSize;
284 1575760 : p = oldPtr;
285 : }
286 1674470 : _TIFFfree(p);
287 1674500 : }
288 :
289 0 : TIFF *TIFFClientOpen(const char *name, const char *mode, thandle_t clientdata,
290 : TIFFReadWriteProc readproc, TIFFReadWriteProc writeproc,
291 : TIFFSeekProc seekproc, TIFFCloseProc closeproc,
292 : TIFFSizeProc sizeproc, TIFFMapFileProc mapproc,
293 : TIFFUnmapFileProc unmapproc)
294 : {
295 0 : return TIFFClientOpenExt(name, mode, clientdata, readproc, writeproc,
296 : seekproc, closeproc, sizeproc, mapproc, unmapproc,
297 : NULL);
298 : }
299 :
300 61989 : TIFF *TIFFClientOpenExt(const char *name, const char *mode,
301 : thandle_t clientdata, TIFFReadWriteProc readproc,
302 : TIFFReadWriteProc writeproc, TIFFSeekProc seekproc,
303 : TIFFCloseProc closeproc, TIFFSizeProc sizeproc,
304 : TIFFMapFileProc mapproc, TIFFUnmapFileProc unmapproc,
305 : TIFFOpenOptions *opts)
306 : {
307 : static const char module[] = "TIFFClientOpenExt";
308 : TIFF *tif;
309 : int m;
310 : const char *cp;
311 :
312 : /* The following are configuration checks. They should be redundant, but
313 : * should not compile to any actual code in an optimised release build
314 : * anyway. If any of them fail, (makefile-based or other) configuration is
315 : * not correct */
316 : assert(sizeof(uint8_t) == 1);
317 : assert(sizeof(int8_t) == 1);
318 : assert(sizeof(uint16_t) == 2);
319 : assert(sizeof(int16_t) == 2);
320 : assert(sizeof(uint32_t) == 4);
321 : assert(sizeof(int32_t) == 4);
322 : assert(sizeof(uint64_t) == 8);
323 : assert(sizeof(int64_t) == 8);
324 : {
325 : union
326 : {
327 : uint8_t a8[2];
328 : uint16_t a16;
329 : } n;
330 61989 : n.a8[0] = 1;
331 61989 : n.a8[1] = 0;
332 : (void)n;
333 : #ifdef WORDS_BIGENDIAN
334 : assert(n.a16 == 256);
335 : #else
336 61989 : assert(n.a16 == 1);
337 : #endif
338 : }
339 :
340 61989 : m = _TIFFgetMode(opts, clientdata, mode, module);
341 61947 : if (m == -1)
342 0 : goto bad2;
343 61947 : tmsize_t size_to_alloc = (tmsize_t)(sizeof(TIFF) + strlen(name) + 1);
344 61947 : if (opts && opts->max_single_mem_alloc > 0 &&
345 0 : size_to_alloc > opts->max_single_mem_alloc)
346 : {
347 0 : _TIFFErrorEarly(opts, clientdata, module,
348 : "%s: Memory allocation of %" PRIu64
349 : " bytes is beyond the %" PRIu64
350 : " byte limit defined in open options",
351 : name, (uint64_t)size_to_alloc,
352 0 : (uint64_t)opts->max_single_mem_alloc);
353 0 : goto bad2;
354 : }
355 61947 : if (opts && opts->max_cumulated_mem_alloc > 0 &&
356 61938 : size_to_alloc > opts->max_cumulated_mem_alloc)
357 : {
358 0 : _TIFFErrorEarly(opts, clientdata, module,
359 : "%s: Memory allocation of %" PRIu64
360 : " bytes is beyond the %" PRIu64
361 : " cumulated byte limit defined in open options",
362 : name, (uint64_t)size_to_alloc,
363 0 : (uint64_t)opts->max_cumulated_mem_alloc);
364 0 : goto bad2;
365 : }
366 61947 : tif = (TIFF *)_TIFFmallocExt(NULL, size_to_alloc);
367 61966 : if (tif == NULL)
368 : {
369 0 : _TIFFErrorEarly(opts, clientdata, module,
370 : "%s: Out of memory (TIFF structure)", name);
371 0 : goto bad2;
372 : }
373 61966 : _TIFFmemset(tif, 0, sizeof(*tif));
374 61957 : tif->tif_name = (char *)tif + sizeof(TIFF);
375 61957 : strcpy(tif->tif_name, name);
376 61957 : tif->tif_mode = m & ~(O_CREAT | O_TRUNC);
377 61957 : tif->tif_curdir = TIFF_NON_EXISTENT_DIR_NUMBER; /* non-existent directory */
378 61957 : tif->tif_curdircount = TIFF_NON_EXISTENT_DIR_NUMBER;
379 61957 : tif->tif_curoff = 0;
380 61957 : tif->tif_curstrip = (uint32_t)-1; /* invalid strip */
381 61957 : tif->tif_row = (uint32_t)-1; /* read/write pre-increment */
382 61957 : tif->tif_clientdata = clientdata;
383 61957 : tif->tif_readproc = readproc;
384 61957 : tif->tif_writeproc = writeproc;
385 61957 : tif->tif_seekproc = seekproc;
386 61957 : tif->tif_closeproc = closeproc;
387 61957 : tif->tif_sizeproc = sizeproc;
388 61957 : tif->tif_mapproc = mapproc ? mapproc : _tiffDummyMapProc;
389 61957 : tif->tif_unmapproc = unmapproc ? unmapproc : _tiffDummyUnmapProc;
390 61957 : if (opts)
391 : {
392 61901 : tif->tif_errorhandler = opts->errorhandler;
393 61901 : tif->tif_errorhandler_user_data = opts->errorhandler_user_data;
394 61901 : tif->tif_warnhandler = opts->warnhandler;
395 61901 : tif->tif_warnhandler_user_data = opts->warnhandler_user_data;
396 61901 : tif->tif_max_single_mem_alloc = opts->max_single_mem_alloc;
397 61901 : tif->tif_max_cumulated_mem_alloc = opts->max_cumulated_mem_alloc;
398 61901 : tif->tif_warn_about_unknown_tags = opts->warn_about_unknown_tags;
399 : }
400 :
401 61957 : if (!readproc || !writeproc || !seekproc || !closeproc || !sizeproc)
402 : {
403 52 : TIFFErrorExtR(tif, module,
404 : "One of the client procedures is NULL pointer.");
405 0 : _TIFFfreeExt(NULL, tif);
406 0 : goto bad2;
407 : }
408 :
409 61905 : _TIFFSetDefaultCompressionState(tif); /* setup default state */
410 : /*
411 : * Default is to return data MSB2LSB and enable the
412 : * use of memory-mapped files and strip chopping when
413 : * a file is opened read-only.
414 : */
415 61968 : tif->tif_flags = FILLORDER_MSB2LSB;
416 61968 : if (m == O_RDONLY)
417 22713 : tif->tif_flags |= TIFF_MAPPED;
418 :
419 : #ifdef STRIPCHOP_DEFAULT
420 61968 : if (m == O_RDONLY || m == O_RDWR)
421 26088 : tif->tif_flags |= STRIPCHOP_DEFAULT;
422 : #endif
423 :
424 : /*
425 : * Process library-specific flags in the open mode string.
426 : * The following flags may be used to control intrinsic library
427 : * behavior that may or may not be desirable (usually for
428 : * compatibility with some application that claims to support
429 : * TIFF but only supports some brain dead idea of what the
430 : * vendor thinks TIFF is):
431 : *
432 : * 'l' use little-endian byte order for creating a file
433 : * 'b' use big-endian byte order for creating a file
434 : * 'L' read/write information using LSB2MSB bit order
435 : * 'B' read/write information using MSB2LSB bit order
436 : * 'H' read/write information using host bit order
437 : * 'M' enable use of memory-mapped files when supported
438 : * 'm' disable use of memory-mapped files
439 : * 'C' enable strip chopping support when reading
440 : * 'c' disable strip chopping support
441 : * 'h' read TIFF header only, do not load the first IFD
442 : * '4' ClassicTIFF for creating a file (default)
443 : * '8' BigTIFF for creating a file
444 : * 'D' enable use of deferred strip/tile offset/bytecount array loading.
445 : * 'O' on-demand loading of values instead of whole array loading (implies
446 : * D)
447 : *
448 : * The use of the 'l' and 'b' flags is strongly discouraged.
449 : * These flags are provided solely because numerous vendors,
450 : * typically on the PC, do not correctly support TIFF; they
451 : * only support the Intel little-endian byte order. This
452 : * support is not configured by default because it supports
453 : * the violation of the TIFF spec that says that readers *MUST*
454 : * support both byte orders. It is strongly recommended that
455 : * you not use this feature except to deal with busted apps
456 : * that write invalid TIFF. And even in those cases you should
457 : * bang on the vendors to fix their software.
458 : *
459 : * The 'L', 'B', and 'H' flags are intended for applications
460 : * that can optimize operations on data by using a particular
461 : * bit order. By default the library returns data in MSB2LSB
462 : * bit order for compatibility with older versions of this
463 : * library. Returning data in the bit order of the native CPU
464 : * makes the most sense but also requires applications to check
465 : * the value of the FillOrder tag; something they probably do
466 : * not do right now.
467 : *
468 : * The 'M' and 'm' flags are provided because some virtual memory
469 : * systems exhibit poor behavior when large images are mapped.
470 : * These options permit clients to control the use of memory-mapped
471 : * files on a per-file basis.
472 : *
473 : * The 'C' and 'c' flags are provided because the library support
474 : * for chopping up large strips into multiple smaller strips is not
475 : * application-transparent and as such can cause problems. The 'c'
476 : * option permits applications that only want to look at the tags,
477 : * for example, to get the unadulterated TIFF tag information.
478 : */
479 251867 : for (cp = mode; *cp; cp++)
480 189899 : switch (*cp)
481 : {
482 82 : case 'b':
483 : #ifndef WORDS_BIGENDIAN
484 82 : if (m & O_CREAT)
485 82 : tif->tif_flags |= TIFF_SWAB;
486 : #endif
487 82 : break;
488 28548 : case 'l':
489 : #ifdef WORDS_BIGENDIAN
490 : if ((m & O_CREAT))
491 : tif->tif_flags |= TIFF_SWAB;
492 : #endif
493 28548 : break;
494 0 : case 'B':
495 0 : tif->tif_flags =
496 0 : (tif->tif_flags & ~TIFF_FILLORDER) | FILLORDER_MSB2LSB;
497 0 : break;
498 0 : case 'L':
499 0 : tif->tif_flags =
500 0 : (tif->tif_flags & ~TIFF_FILLORDER) | FILLORDER_LSB2MSB;
501 0 : break;
502 0 : case 'H':
503 0 : TIFFWarningExtR(tif, name,
504 : "H(ost) mode is deprecated. Since "
505 : "libtiff 4.5.1, it is an alias of 'B' / "
506 : "FILLORDER_MSB2LSB.");
507 0 : tif->tif_flags =
508 0 : (tif->tif_flags & ~TIFF_FILLORDER) | FILLORDER_MSB2LSB;
509 0 : break;
510 0 : case 'M':
511 0 : if (m == O_RDONLY)
512 0 : tif->tif_flags |= TIFF_MAPPED;
513 0 : break;
514 0 : case 'm':
515 0 : if (m == O_RDONLY)
516 0 : tif->tif_flags &= ~TIFF_MAPPED;
517 0 : break;
518 19520 : case 'C':
519 19520 : if (m == O_RDONLY)
520 18818 : tif->tif_flags |= TIFF_STRIPCHOP;
521 19520 : break;
522 586 : case 'c':
523 586 : if (m == O_RDONLY)
524 586 : tif->tif_flags &= ~TIFF_STRIPCHOP;
525 586 : break;
526 0 : case 'h':
527 0 : tif->tif_flags |= TIFF_HEADERONLY;
528 0 : break;
529 76 : case '8':
530 76 : if (m & O_CREAT)
531 76 : tif->tif_flags |= TIFF_BIGTIFF;
532 76 : break;
533 20659 : case 'D':
534 20659 : tif->tif_flags |= TIFF_DEFERSTRILELOAD;
535 20659 : break;
536 19568 : case 'O':
537 19568 : if (m == O_RDONLY)
538 19571 : tif->tif_flags |=
539 : (TIFF_LAZYSTRILELOAD | TIFF_DEFERSTRILELOAD);
540 19568 : break;
541 : }
542 :
543 : #ifdef DEFER_STRILE_LOAD
544 : /* Compatibility with old DEFER_STRILE_LOAD compilation flag */
545 : /* Probably unneeded, since to the best of my knowledge (E. Rouault) */
546 : /* GDAL was the only user of this, and will now use the new 'D' flag */
547 : tif->tif_flags |= TIFF_DEFERSTRILELOAD;
548 : #endif
549 :
550 : /*
551 : * Read in TIFF header.
552 : */
553 277951 : if ((m & O_TRUNC) ||
554 26052 : !ReadOK(tif, &tif->tif_header, sizeof(TIFFHeaderClassic)))
555 : {
556 35859 : if (tif->tif_mode == O_RDONLY)
557 : {
558 0 : TIFFErrorExtR(tif, name, "Cannot read TIFF header");
559 2 : goto bad;
560 : }
561 : /*
562 : * Setup header and write.
563 : */
564 : #ifdef WORDS_BIGENDIAN
565 : tif->tif_header.common.tiff_magic =
566 : (tif->tif_flags & TIFF_SWAB) ? TIFF_LITTLEENDIAN : TIFF_BIGENDIAN;
567 : #else
568 35859 : tif->tif_header.common.tiff_magic =
569 35859 : (tif->tif_flags & TIFF_SWAB) ? TIFF_BIGENDIAN : TIFF_LITTLEENDIAN;
570 : #endif
571 : TIFFHeaderUnion tif_header_swapped;
572 35859 : if (!(tif->tif_flags & TIFF_BIGTIFF))
573 : {
574 35783 : tif->tif_header.common.tiff_version = TIFF_VERSION_CLASSIC;
575 35783 : tif->tif_header.classic.tiff_diroff = 0;
576 35783 : tif->tif_header_size = sizeof(TIFFHeaderClassic);
577 : /* Swapped copy for writing */
578 35783 : _TIFFmemcpy(&tif_header_swapped, &tif->tif_header,
579 : sizeof(TIFFHeaderUnion));
580 35783 : if (tif->tif_flags & TIFF_SWAB)
581 78 : TIFFSwabShort(&tif_header_swapped.common.tiff_version);
582 : }
583 : else
584 : {
585 76 : tif->tif_header.common.tiff_version = TIFF_VERSION_BIG;
586 76 : tif->tif_header.big.tiff_offsetsize = 8;
587 76 : tif->tif_header.big.tiff_unused = 0;
588 76 : tif->tif_header.big.tiff_diroff = 0;
589 76 : tif->tif_header_size = sizeof(TIFFHeaderBig);
590 : /* Swapped copy for writing */
591 76 : _TIFFmemcpy(&tif_header_swapped, &tif->tif_header,
592 : sizeof(TIFFHeaderUnion));
593 76 : if (tif->tif_flags & TIFF_SWAB)
594 : {
595 4 : TIFFSwabShort(&tif_header_swapped.common.tiff_version);
596 4 : TIFFSwabShort(&tif_header_swapped.big.tiff_offsetsize);
597 : }
598 : }
599 : /*
600 : * The doc for "fopen" for some STD_C_LIBs says that if you
601 : * open a file for modify ("+"), then you must fseek (or
602 : * fflush?) between any freads and fwrites. This is not
603 : * necessary on most systems, but has been shown to be needed
604 : * on Solaris.
605 : */
606 35859 : TIFFSeekFile(tif, 0, SEEK_SET);
607 35859 : if (!WriteOK(tif, &tif_header_swapped,
608 : (tmsize_t)(tif->tif_header_size)))
609 : {
610 2 : TIFFErrorExtR(tif, name, "Error writing TIFF header");
611 2 : goto bad;
612 : }
613 : /*
614 : * Setup default directory.
615 : */
616 35857 : if (!TIFFDefaultDirectory(tif))
617 0 : goto bad;
618 35857 : tif->tif_diroff = 0;
619 35857 : tif->tif_lastdiroff = 0;
620 35857 : tif->tif_setdirectory_force_absolute = FALSE;
621 : /* tif_curdircount = 0 means 'empty file opened for writing, but no IFD
622 : * written yet' */
623 35857 : tif->tif_curdircount = 0;
624 35857 : return (tif);
625 : }
626 :
627 : /*
628 : * Setup the byte order handling according to the opened file for reading.
629 : */
630 26141 : if (tif->tif_header.common.tiff_magic != TIFF_BIGENDIAN &&
631 25835 : tif->tif_header.common.tiff_magic != TIFF_LITTLEENDIAN
632 : #if MDI_SUPPORT
633 : &&
634 : #if HOST_BIGENDIAN
635 : tif->tif_header.common.tiff_magic != MDI_BIGENDIAN
636 : #else
637 : tif->tif_header.common.tiff_magic != MDI_LITTLEENDIAN
638 : #endif
639 : )
640 : {
641 : TIFFErrorExtR(tif, name,
642 : "Not a TIFF or MDI file, bad magic number %" PRIu16
643 : " (0x%" PRIx16 ")",
644 : #else
645 : )
646 : {
647 0 : TIFFErrorExtR(tif, name,
648 : "Not a TIFF file, bad magic number %" PRIu16
649 : " (0x%" PRIx16 ")",
650 : #endif
651 0 : tif->tif_header.common.tiff_magic,
652 0 : tif->tif_header.common.tiff_magic);
653 0 : goto bad;
654 : }
655 26141 : if (tif->tif_header.common.tiff_magic == TIFF_BIGENDIAN)
656 : {
657 : #ifndef WORDS_BIGENDIAN
658 218 : tif->tif_flags |= TIFF_SWAB;
659 : #endif
660 : }
661 : else
662 : {
663 : #ifdef WORDS_BIGENDIAN
664 : tif->tif_flags |= TIFF_SWAB;
665 : #endif
666 : }
667 26141 : if (tif->tif_flags & TIFF_SWAB)
668 218 : TIFFSwabShort(&tif->tif_header.common.tiff_version);
669 26070 : if ((tif->tif_header.common.tiff_version != TIFF_VERSION_CLASSIC) &&
670 298 : (tif->tif_header.common.tiff_version != TIFF_VERSION_BIG))
671 : {
672 0 : TIFFErrorExtR(tif, name,
673 : "Not a TIFF file, bad version number %" PRIu16
674 : " (0x%" PRIx16 ")",
675 0 : tif->tif_header.common.tiff_version,
676 0 : tif->tif_header.common.tiff_version);
677 0 : goto bad;
678 : }
679 26070 : if (tif->tif_header.common.tiff_version == TIFF_VERSION_CLASSIC)
680 : {
681 25772 : if (tif->tif_flags & TIFF_SWAB)
682 207 : TIFFSwabLong(&tif->tif_header.classic.tiff_diroff);
683 25749 : tif->tif_header_size = sizeof(TIFFHeaderClassic);
684 : }
685 : else
686 : {
687 298 : if (!ReadOK(tif,
688 : ((uint8_t *)(&tif->tif_header) + sizeof(TIFFHeaderClassic)),
689 : (sizeof(TIFFHeaderBig) - sizeof(TIFFHeaderClassic))))
690 : {
691 0 : TIFFErrorExtR(tif, name, "Cannot read TIFF header");
692 0 : goto bad;
693 : }
694 298 : if (tif->tif_flags & TIFF_SWAB)
695 : {
696 11 : TIFFSwabShort(&tif->tif_header.big.tiff_offsetsize);
697 11 : TIFFSwabLong8(&tif->tif_header.big.tiff_diroff);
698 : }
699 298 : if (tif->tif_header.big.tiff_offsetsize != 8)
700 : {
701 0 : TIFFErrorExtR(tif, name,
702 : "Not a TIFF file, bad BigTIFF offsetsize %" PRIu16
703 : " (0x%" PRIx16 ")",
704 0 : tif->tif_header.big.tiff_offsetsize,
705 0 : tif->tif_header.big.tiff_offsetsize);
706 0 : goto bad;
707 : }
708 298 : if (tif->tif_header.big.tiff_unused != 0)
709 : {
710 0 : TIFFErrorExtR(tif, name,
711 : "Not a TIFF file, bad BigTIFF unused %" PRIu16
712 : " (0x%" PRIx16 ")",
713 0 : tif->tif_header.big.tiff_unused,
714 0 : tif->tif_header.big.tiff_unused);
715 0 : goto bad;
716 : }
717 298 : tif->tif_header_size = sizeof(TIFFHeaderBig);
718 298 : tif->tif_flags |= TIFF_BIGTIFF;
719 : }
720 26047 : tif->tif_flags |= TIFF_MYBUFFER;
721 26047 : tif->tif_rawcp = tif->tif_rawdata = 0;
722 26047 : tif->tif_rawdatasize = 0;
723 26047 : tif->tif_rawdataoff = 0;
724 26047 : tif->tif_rawdataloaded = 0;
725 :
726 26047 : switch (mode[0])
727 : {
728 26103 : case 'r':
729 26103 : if (!(tif->tif_flags & TIFF_BIGTIFF))
730 25800 : tif->tif_nextdiroff = tif->tif_header.classic.tiff_diroff;
731 : else
732 303 : tif->tif_nextdiroff = tif->tif_header.big.tiff_diroff;
733 : /*
734 : * Try to use a memory-mapped file if the client
735 : * has not explicitly suppressed usage with the
736 : * 'm' flag in the open mode (see above).
737 : */
738 26103 : if (tif->tif_flags & TIFF_MAPPED)
739 : {
740 : toff_t n;
741 22689 : if (TIFFMapFileContents(tif, (void **)(&tif->tif_base), &n))
742 : {
743 6 : tif->tif_size = (tmsize_t)n;
744 6 : assert((toff_t)tif->tif_size == n);
745 : }
746 : else
747 22643 : tif->tif_flags &= ~TIFF_MAPPED;
748 : }
749 : /*
750 : * Sometimes we do not want to read the first directory (for
751 : * example, it may be broken) and want to proceed to other
752 : * directories. I this case we use the TIFF_HEADERONLY flag to open
753 : * file and return immediately after reading TIFF header.
754 : * However, the pointer to TIFFSetField() and TIFFGetField()
755 : * (i.e. tif->tif_tagmethods.vsetfield and
756 : * tif->tif_tagmethods.vgetfield) need to be initialized, which is
757 : * done in TIFFDefaultDirectory().
758 : */
759 26063 : if (tif->tif_flags & TIFF_HEADERONLY)
760 : {
761 0 : if (!TIFFDefaultDirectory(tif))
762 0 : goto bad;
763 0 : return (tif);
764 : }
765 :
766 : /*
767 : * Setup initial directory.
768 : */
769 26063 : if (TIFFReadDirectory(tif))
770 : {
771 26049 : return (tif);
772 : }
773 35 : break;
774 0 : case 'a':
775 : /*
776 : * New directories are automatically append
777 : * to the end of the directory chain when they
778 : * are written out (see TIFFWriteDirectory).
779 : */
780 0 : if (!TIFFDefaultDirectory(tif))
781 0 : goto bad;
782 0 : return (tif);
783 : }
784 0 : bad:
785 0 : tif->tif_mode = O_RDONLY; /* XXX avoid flush */
786 0 : TIFFCleanup(tif);
787 14 : bad2:
788 14 : return ((TIFF *)0);
789 : }
790 :
791 : /*
792 : * Query functions to access private data.
793 : */
794 :
795 : /*
796 : * Return open file's name.
797 : */
798 6 : const char *TIFFFileName(TIFF *tif) { return (tif->tif_name); }
799 :
800 : /*
801 : * Set the file name.
802 : */
803 0 : const char *TIFFSetFileName(TIFF *tif, const char *name)
804 : {
805 0 : const char *old_name = tif->tif_name;
806 0 : tif->tif_name = (char *)name;
807 0 : return (old_name);
808 : }
809 :
810 : /*
811 : * Return open file's I/O descriptor.
812 : */
813 0 : int TIFFFileno(TIFF *tif) { return (tif->tif_fd); }
814 :
815 : /*
816 : * Set open file's I/O descriptor, and return previous value.
817 : */
818 0 : int TIFFSetFileno(TIFF *tif, int fd)
819 : {
820 0 : int old_fd = tif->tif_fd;
821 0 : tif->tif_fd = fd;
822 0 : return old_fd;
823 : }
824 :
825 : /*
826 : * Return open file's clientdata.
827 : */
828 93773 : thandle_t TIFFClientdata(TIFF *tif) { return (tif->tif_clientdata); }
829 :
830 : /*
831 : * Set open file's clientdata, and return previous value.
832 : */
833 0 : thandle_t TIFFSetClientdata(TIFF *tif, thandle_t newvalue)
834 : {
835 0 : thandle_t m = tif->tif_clientdata;
836 0 : tif->tif_clientdata = newvalue;
837 0 : return m;
838 : }
839 :
840 : /*
841 : * Return read/write mode.
842 : */
843 0 : int TIFFGetMode(TIFF *tif) { return (tif->tif_mode); }
844 :
845 : /*
846 : * Return read/write mode.
847 : */
848 0 : int TIFFSetMode(TIFF *tif, int mode)
849 : {
850 0 : int old_mode = tif->tif_mode;
851 0 : tif->tif_mode = mode;
852 0 : return (old_mode);
853 : }
854 :
855 : /*
856 : * Return nonzero if file is organized in
857 : * tiles; zero if organized as strips.
858 : */
859 4814460 : int TIFFIsTiled(TIFF *tif) { return (isTiled(tif)); }
860 :
861 : /*
862 : * Return current row being read/written.
863 : */
864 0 : uint32_t TIFFCurrentRow(TIFF *tif) { return (tif->tif_row); }
865 :
866 : /*
867 : * Return index of the current directory.
868 : */
869 0 : tdir_t TIFFCurrentDirectory(TIFF *tif) { return (tif->tif_curdir); }
870 :
871 : /*
872 : * Return current strip.
873 : */
874 0 : uint32_t TIFFCurrentStrip(TIFF *tif) { return (tif->tif_curstrip); }
875 :
876 : /*
877 : * Return current tile.
878 : */
879 0 : uint32_t TIFFCurrentTile(TIFF *tif) { return (tif->tif_curtile); }
880 :
881 : /*
882 : * Return nonzero if the file has byte-swapped data.
883 : */
884 64095 : int TIFFIsByteSwapped(TIFF *tif) { return ((tif->tif_flags & TIFF_SWAB) != 0); }
885 :
886 : /*
887 : * Return nonzero if the data is returned up-sampled.
888 : */
889 0 : int TIFFIsUpSampled(TIFF *tif) { return (isUpSampled(tif)); }
890 :
891 : /*
892 : * Return nonzero if the data is returned in MSB-to-LSB bit order.
893 : */
894 0 : int TIFFIsMSB2LSB(TIFF *tif) { return (isFillOrder(tif, FILLORDER_MSB2LSB)); }
895 :
896 : /*
897 : * Return nonzero if given file was written in big-endian order.
898 : */
899 26239 : int TIFFIsBigEndian(TIFF *tif)
900 : {
901 26239 : return (tif->tif_header.common.tiff_magic == TIFF_BIGENDIAN);
902 : }
903 :
904 : /*
905 : * Return nonzero if given file is BigTIFF style.
906 : */
907 0 : int TIFFIsBigTIFF(TIFF *tif) { return ((tif->tif_flags & TIFF_BIGTIFF) != 0); }
908 :
909 : /*
910 : * Return pointer to file read method.
911 : */
912 0 : TIFFReadWriteProc TIFFGetReadProc(TIFF *tif) { return (tif->tif_readproc); }
913 :
914 : /*
915 : * Return pointer to file write method.
916 : */
917 0 : TIFFReadWriteProc TIFFGetWriteProc(TIFF *tif) { return (tif->tif_writeproc); }
918 :
919 : /*
920 : * Return pointer to file seek method.
921 : */
922 0 : TIFFSeekProc TIFFGetSeekProc(TIFF *tif) { return (tif->tif_seekproc); }
923 :
924 : /*
925 : * Return pointer to file close method.
926 : */
927 0 : TIFFCloseProc TIFFGetCloseProc(TIFF *tif) { return (tif->tif_closeproc); }
928 :
929 : /*
930 : * Return pointer to file size requesting method.
931 : */
932 11970 : TIFFSizeProc TIFFGetSizeProc(TIFF *tif) { return (tif->tif_sizeproc); }
933 :
934 : /*
935 : * Return pointer to memory mapping method.
936 : */
937 0 : TIFFMapFileProc TIFFGetMapFileProc(TIFF *tif) { return (tif->tif_mapproc); }
938 :
939 : /*
940 : * Return pointer to memory unmapping method.
941 : */
942 0 : TIFFUnmapFileProc TIFFGetUnmapFileProc(TIFF *tif)
943 : {
944 0 : return (tif->tif_unmapproc);
945 : }
|