ReactOS  0.4.14-dev-608-gd495a4f
tif_write.c
Go to the documentation of this file.
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  * Scanline-oriented Write Support
29  */
30 #include <precomp.h>
31 //#include <stdio.h>
32 
33 #define STRIPINCR 20 /* expansion factor on strip array */
34 
35 #define WRITECHECKSTRIPS(tif, module) \
36  (((tif)->tif_flags&TIFF_BEENWRITING) || TIFFWriteCheck((tif),0,module))
37 #define WRITECHECKTILES(tif, module) \
38  (((tif)->tif_flags&TIFF_BEENWRITING) || TIFFWriteCheck((tif),1,module))
39 #define BUFFERCHECK(tif) \
40  ((((tif)->tif_flags & TIFF_BUFFERSETUP) && tif->tif_rawdata) || \
41  TIFFWriteBufferSetup((tif), NULL, (tmsize_t) -1))
42 
43 static int TIFFGrowStrips(TIFF* tif, uint32 delta, const char* module);
44 static int TIFFAppendToStrip(TIFF* tif, uint32 strip, uint8* data, tmsize_t cc);
45 
46 int
47 TIFFWriteScanline(TIFF* tif, void* buf, uint32 row, uint16 sample)
48 {
49  static const char module[] = "TIFFWriteScanline";
50  register TIFFDirectory *td;
51  int status, imagegrew = 0;
52  uint32 strip;
53 
54  if (!WRITECHECKSTRIPS(tif, module))
55  return (-1);
56  /*
57  * Handle delayed allocation of data buffer. This
58  * permits it to be sized more intelligently (using
59  * directory information).
60  */
61  if (!BUFFERCHECK(tif))
62  return (-1);
63  tif->tif_flags |= TIFF_BUF4WRITE; /* not strictly sure this is right*/
64 
65  td = &tif->tif_dir;
66  /*
67  * Extend image length if needed
68  * (but only for PlanarConfig=1).
69  */
70  if (row >= td->td_imagelength) { /* extend image */
73  "Can not change \"ImageLength\" when using separate planes");
74  return (-1);
75  }
76  td->td_imagelength = row+1;
77  imagegrew = 1;
78  }
79  /*
80  * Calculate strip and check for crossings.
81  */
83  if (sample >= td->td_samplesperpixel) {
85  "%lu: Sample out of range, max %lu",
86  (unsigned long) sample, (unsigned long) td->td_samplesperpixel);
87  return (-1);
88  }
89  strip = sample*td->td_stripsperimage + row/td->td_rowsperstrip;
90  } else
91  strip = row / td->td_rowsperstrip;
92  /*
93  * Check strip array to make sure there's space. We don't support
94  * dynamically growing files that have data organized in separate
95  * bitplanes because it's too painful. In that case we require that
96  * the imagelength be set properly before the first write (so that the
97  * strips array will be fully allocated above).
98  */
99  if (strip >= td->td_nstrips && !TIFFGrowStrips(tif, 1, module))
100  return (-1);
101  if (strip != tif->tif_curstrip) {
102  /*
103  * Changing strips -- flush any data present.
104  */
105  if (!TIFFFlushData(tif))
106  return (-1);
107  tif->tif_curstrip = strip;
108  /*
109  * Watch out for a growing image. The value of strips/image
110  * will initially be 1 (since it can't be deduced until the
111  * imagelength is known).
112  */
113  if (strip >= td->td_stripsperimage && imagegrew)
114  td->td_stripsperimage =
116  if (td->td_stripsperimage == 0) {
117  TIFFErrorExt(tif->tif_clientdata, module, "Zero strips per image");
118  return (-1);
119  }
120  tif->tif_row =
121  (strip % td->td_stripsperimage) * td->td_rowsperstrip;
122  if ((tif->tif_flags & TIFF_CODERSETUP) == 0) {
123  if (!(*tif->tif_setupencode)(tif))
124  return (-1);
125  tif->tif_flags |= TIFF_CODERSETUP;
126  }
127 
128  tif->tif_rawcc = 0;
129  tif->tif_rawcp = tif->tif_rawdata;
130 
131  if( td->td_stripbytecount_p[strip] > 0 )
132  {
133  /* if we are writing over existing tiles, zero length */
134  td->td_stripbytecount_p[strip] = 0;
135 
136  /* this forces TIFFAppendToStrip() to do a seek */
137  tif->tif_curoff = 0;
138  }
139 
140  if (!(*tif->tif_preencode)(tif, sample))
141  return (-1);
142  tif->tif_flags |= TIFF_POSTENCODE;
143  }
144  /*
145  * Ensure the write is either sequential or at the
146  * beginning of a strip (or that we can randomly
147  * access the data -- i.e. no encoding).
148  */
149  if (row != tif->tif_row) {
150  if (row < tif->tif_row) {
151  /*
152  * Moving backwards within the same strip:
153  * backup to the start and then decode
154  * forward (below).
155  */
156  tif->tif_row = (strip % td->td_stripsperimage) *
157  td->td_rowsperstrip;
158  tif->tif_rawcp = tif->tif_rawdata;
159  }
160  /*
161  * Seek forward to the desired row.
162  */
163  if (!(*tif->tif_seek)(tif, row - tif->tif_row))
164  return (-1);
165  tif->tif_row = row;
166  }
167 
168  /* swab if needed - note that source buffer will be altered */
169  tif->tif_postdecode( tif, (uint8*) buf, tif->tif_scanlinesize );
170 
171  status = (*tif->tif_encoderow)(tif, (uint8*) buf,
172  tif->tif_scanlinesize, sample);
173 
174  /* we are now poised at the beginning of the next row */
175  tif->tif_row = row + 1;
176  return (status);
177 }
178 
179 /* Make sure that at the first attempt of rewriting a tile/strip, we will have */
180 /* more bytes available in the output buffer than the previous byte count, */
181 /* so that TIFFAppendToStrip() will detect the overflow when it is called the first */
182 /* time if the new compressed tile is bigger than the older one. (GDAL #4771) */
183 static int _TIFFReserveLargeEnoughWriteBuffer(TIFF* tif, uint32 strip_or_tile)
184 {
185  TIFFDirectory *td = &tif->tif_dir;
186  if( td->td_stripbytecount_p[strip_or_tile] > 0 )
187  {
188  /* The +1 is to ensure at least one extra bytes */
189  /* The +4 is because the LZW encoder flushes 4 bytes before the limit */
190  uint64 safe_buffer_size = (uint64)(td->td_stripbytecount_p[strip_or_tile] + 1 + 4);
191  if( tif->tif_rawdatasize <= (tmsize_t)safe_buffer_size )
192  {
193  if( !(TIFFWriteBufferSetup(tif, NULL,
194  (tmsize_t)TIFFroundup_64(safe_buffer_size, 1024))) )
195  return 0;
196  }
197 
198  /* Force TIFFAppendToStrip() to consider placing data at end
199  of file. */
200  tif->tif_curoff = 0;
201  }
202  return 1;
203 }
204 
205 /*
206  * Encode the supplied data and write it to the
207  * specified strip.
208  *
209  * NB: Image length must be setup before writing.
210  */
211 tmsize_t
213 {
214  static const char module[] = "TIFFWriteEncodedStrip";
215  TIFFDirectory *td = &tif->tif_dir;
216  uint16 sample;
217 
218  if (!WRITECHECKSTRIPS(tif, module))
219  return ((tmsize_t) -1);
220  /*
221  * Check strip array to make sure there's space.
222  * We don't support dynamically growing files that
223  * have data organized in separate bitplanes because
224  * it's too painful. In that case we require that
225  * the imagelength be set properly before the first
226  * write (so that the strips array will be fully
227  * allocated above).
228  */
229  if (strip >= td->td_nstrips) {
232  "Can not grow image by strips when using separate planes");
233  return ((tmsize_t) -1);
234  }
235  if (!TIFFGrowStrips(tif, 1, module))
236  return ((tmsize_t) -1);
237  td->td_stripsperimage =
239  }
240  /*
241  * Handle delayed allocation of data buffer. This
242  * permits it to be sized according to the directory
243  * info.
244  */
245  if (!BUFFERCHECK(tif))
246  return ((tmsize_t) -1);
247 
248  tif->tif_flags |= TIFF_BUF4WRITE;
249  tif->tif_curstrip = strip;
250 
251  if( !_TIFFReserveLargeEnoughWriteBuffer(tif, strip) ) {
252  return ((tmsize_t)(-1));
253  }
254 
255  tif->tif_rawcc = 0;
256  tif->tif_rawcp = tif->tif_rawdata;
257 
258  if (td->td_stripsperimage == 0) {
259  TIFFErrorExt(tif->tif_clientdata, module, "Zero strips per image");
260  return ((tmsize_t) -1);
261  }
262 
263  tif->tif_row = (strip % td->td_stripsperimage) * td->td_rowsperstrip;
264  if ((tif->tif_flags & TIFF_CODERSETUP) == 0) {
265  if (!(*tif->tif_setupencode)(tif))
266  return ((tmsize_t) -1);
267  tif->tif_flags |= TIFF_CODERSETUP;
268  }
269 
270  tif->tif_flags &= ~TIFF_POSTENCODE;
271 
272  /* shortcut to avoid an extra memcpy() */
273  if( td->td_compression == COMPRESSION_NONE )
274  {
275  /* swab if needed - note that source buffer will be altered */
276  tif->tif_postdecode( tif, (uint8*) data, cc );
277 
278  if (!isFillOrder(tif, td->td_fillorder) &&
279  (tif->tif_flags & TIFF_NOBITREV) == 0)
281 
282  if (cc > 0 &&
283  !TIFFAppendToStrip(tif, strip, (uint8*) data, cc))
284  return ((tmsize_t) -1);
285  return (cc);
286  }
287 
288  sample = (uint16)(strip / td->td_stripsperimage);
289  if (!(*tif->tif_preencode)(tif, sample))
290  return ((tmsize_t) -1);
291 
292  /* swab if needed - note that source buffer will be altered */
293  tif->tif_postdecode( tif, (uint8*) data, cc );
294 
295  if (!(*tif->tif_encodestrip)(tif, (uint8*) data, cc, sample))
296  return ((tmsize_t) -1);
297  if (!(*tif->tif_postencode)(tif))
298  return ((tmsize_t) -1);
299  if (!isFillOrder(tif, td->td_fillorder) &&
300  (tif->tif_flags & TIFF_NOBITREV) == 0)
302  if (tif->tif_rawcc > 0 &&
303  !TIFFAppendToStrip(tif, strip, tif->tif_rawdata, tif->tif_rawcc))
304  return ((tmsize_t) -1);
305  tif->tif_rawcc = 0;
306  tif->tif_rawcp = tif->tif_rawdata;
307  return (cc);
308 }
309 
310 /*
311  * Write the supplied data to the specified strip.
312  *
313  * NB: Image length must be setup before writing.
314  */
315 tmsize_t
317 {
318  static const char module[] = "TIFFWriteRawStrip";
319  TIFFDirectory *td = &tif->tif_dir;
320 
321  if (!WRITECHECKSTRIPS(tif, module))
322  return ((tmsize_t) -1);
323  /*
324  * Check strip array to make sure there's space.
325  * We don't support dynamically growing files that
326  * have data organized in separate bitplanes because
327  * it's too painful. In that case we require that
328  * the imagelength be set properly before the first
329  * write (so that the strips array will be fully
330  * allocated above).
331  */
332  if (strip >= td->td_nstrips) {
335  "Can not grow image by strips when using separate planes");
336  return ((tmsize_t) -1);
337  }
338  /*
339  * Watch out for a growing image. The value of
340  * strips/image will initially be 1 (since it
341  * can't be deduced until the imagelength is known).
342  */
343  if (strip >= td->td_stripsperimage)
344  td->td_stripsperimage =
346  if (!TIFFGrowStrips(tif, 1, module))
347  return ((tmsize_t) -1);
348  }
349  tif->tif_curstrip = strip;
350  if (td->td_stripsperimage == 0) {
351  TIFFErrorExt(tif->tif_clientdata, module,"Zero strips per image");
352  return ((tmsize_t) -1);
353  }
354  tif->tif_row = (strip % td->td_stripsperimage) * td->td_rowsperstrip;
355  return (TIFFAppendToStrip(tif, strip, (uint8*) data, cc) ?
356  cc : (tmsize_t) -1);
357 }
358 
359 /*
360  * Write and compress a tile of data. The
361  * tile is selected by the (x,y,z,s) coordinates.
362  */
363 tmsize_t
365 {
366  if (!TIFFCheckTile(tif, x, y, z, s))
367  return ((tmsize_t)(-1));
368  /*
369  * NB: A tile size of -1 is used instead of tif_tilesize knowing
370  * that TIFFWriteEncodedTile will clamp this to the tile size.
371  * This is done because the tile size may not be defined until
372  * after the output buffer is setup in TIFFWriteBufferSetup.
373  */
374  return (TIFFWriteEncodedTile(tif,
375  TIFFComputeTile(tif, x, y, z, s), buf, (tmsize_t)(-1)));
376 }
377 
378 /*
379  * Encode the supplied data and write it to the
380  * specified tile. There must be space for the
381  * data. The function clamps individual writes
382  * to a tile to the tile size, but does not (and
383  * can not) check that multiple writes to the same
384  * tile do not write more than tile size data.
385  *
386  * NB: Image length must be setup before writing; this
387  * interface does not support automatically growing
388  * the image on each write (as TIFFWriteScanline does).
389  */
390 tmsize_t
392 {
393  static const char module[] = "TIFFWriteEncodedTile";
394  TIFFDirectory *td;
395  uint16 sample;
396  uint32 howmany32;
397 
398  if (!WRITECHECKTILES(tif, module))
399  return ((tmsize_t)(-1));
400  td = &tif->tif_dir;
401  if (tile >= td->td_nstrips) {
402  TIFFErrorExt(tif->tif_clientdata, module, "Tile %lu out of range, max %lu",
403  (unsigned long) tile, (unsigned long) td->td_nstrips);
404  return ((tmsize_t)(-1));
405  }
406  /*
407  * Handle delayed allocation of data buffer. This
408  * permits it to be sized more intelligently (using
409  * directory information).
410  */
411  if (!BUFFERCHECK(tif))
412  return ((tmsize_t)(-1));
413 
414  tif->tif_flags |= TIFF_BUF4WRITE;
415  tif->tif_curtile = tile;
416 
417  if( !_TIFFReserveLargeEnoughWriteBuffer(tif, tile) ) {
418  return ((tmsize_t)(-1));
419  }
420 
421  tif->tif_rawcc = 0;
422  tif->tif_rawcp = tif->tif_rawdata;
423 
424  /*
425  * Compute tiles per row & per column to compute
426  * current row and column
427  */
428  howmany32=TIFFhowmany_32(td->td_imagelength, td->td_tilelength);
429  if (howmany32 == 0) {
430  TIFFErrorExt(tif->tif_clientdata,module,"Zero tiles");
431  return ((tmsize_t)(-1));
432  }
433  tif->tif_row = (tile % howmany32) * td->td_tilelength;
434  howmany32=TIFFhowmany_32(td->td_imagewidth, td->td_tilewidth);
435  if (howmany32 == 0) {
436  TIFFErrorExt(tif->tif_clientdata,module,"Zero tiles");
437  return ((tmsize_t)(-1));
438  }
439  tif->tif_col = (tile % howmany32) * td->td_tilewidth;
440 
441  if ((tif->tif_flags & TIFF_CODERSETUP) == 0) {
442  if (!(*tif->tif_setupencode)(tif))
443  return ((tmsize_t)(-1));
444  tif->tif_flags |= TIFF_CODERSETUP;
445  }
446  tif->tif_flags &= ~TIFF_POSTENCODE;
447 
448  /*
449  * Clamp write amount to the tile size. This is mostly
450  * done so that callers can pass in some large number
451  * (e.g. -1) and have the tile size used instead.
452  */
453  if ( cc < 1 || cc > tif->tif_tilesize)
454  cc = tif->tif_tilesize;
455 
456  /* shortcut to avoid an extra memcpy() */
457  if( td->td_compression == COMPRESSION_NONE )
458  {
459  /* swab if needed - note that source buffer will be altered */
460  tif->tif_postdecode( tif, (uint8*) data, cc );
461 
462  if (!isFillOrder(tif, td->td_fillorder) &&
463  (tif->tif_flags & TIFF_NOBITREV) == 0)
465 
466  if (cc > 0 &&
467  !TIFFAppendToStrip(tif, tile, (uint8*) data, cc))
468  return ((tmsize_t) -1);
469  return (cc);
470  }
471 
472  sample = (uint16)(tile/td->td_stripsperimage);
473  if (!(*tif->tif_preencode)(tif, sample))
474  return ((tmsize_t)(-1));
475  /* swab if needed - note that source buffer will be altered */
476  tif->tif_postdecode( tif, (uint8*) data, cc );
477 
478  if (!(*tif->tif_encodetile)(tif, (uint8*) data, cc, sample))
479  return ((tmsize_t) -1);
480  if (!(*tif->tif_postencode)(tif))
481  return ((tmsize_t)(-1));
482  if (!isFillOrder(tif, td->td_fillorder) &&
483  (tif->tif_flags & TIFF_NOBITREV) == 0)
485  if (tif->tif_rawcc > 0 && !TIFFAppendToStrip(tif, tile,
486  tif->tif_rawdata, tif->tif_rawcc))
487  return ((tmsize_t)(-1));
488  tif->tif_rawcc = 0;
489  tif->tif_rawcp = tif->tif_rawdata;
490  return (cc);
491 }
492 
493 /*
494  * Write the supplied data to the specified strip.
495  * There must be space for the data; we don't check
496  * if strips overlap!
497  *
498  * NB: Image length must be setup before writing; this
499  * interface does not support automatically growing
500  * the image on each write (as TIFFWriteScanline does).
501  */
502 tmsize_t
504 {
505  static const char module[] = "TIFFWriteRawTile";
506 
507  if (!WRITECHECKTILES(tif, module))
508  return ((tmsize_t)(-1));
509  if (tile >= tif->tif_dir.td_nstrips) {
510  TIFFErrorExt(tif->tif_clientdata, module, "Tile %lu out of range, max %lu",
511  (unsigned long) tile,
512  (unsigned long) tif->tif_dir.td_nstrips);
513  return ((tmsize_t)(-1));
514  }
515  return (TIFFAppendToStrip(tif, tile, (uint8*) data, cc) ?
516  cc : (tmsize_t)(-1));
517 }
518 
519 #define isUnspecified(tif, f) \
520  (TIFFFieldSet(tif,f) && (tif)->tif_dir.td_imagelength == 0)
521 
522 int
524 {
525  TIFFDirectory* td = &tif->tif_dir;
526 
527  if (isTiled(tif))
528  td->td_stripsperimage =
531  else
532  td->td_stripsperimage =
535  td->td_nstrips = td->td_stripsperimage;
538  td->td_stripoffset_p = (uint64 *)
540  "for \"StripOffsets\" array");
541  td->td_stripbytecount_p = (uint64 *)
543  "for \"StripByteCounts\" array");
544  if (td->td_stripoffset_p == NULL || td->td_stripbytecount_p == NULL)
545  return (0);
546  /*
547  * Place data at the end-of-file
548  * (by setting offsets to zero).
549  */
554  return (1);
555 }
556 #undef isUnspecified
557 
558 /*
559  * Verify file is writable and that the directory
560  * information is setup properly. In doing the latter
561  * we also "freeze" the state of the directory so
562  * that important information is not changed.
563  */
564 int
565 TIFFWriteCheck(TIFF* tif, int tiles, const char* module)
566 {
567  if (tif->tif_mode == O_RDONLY) {
568  TIFFErrorExt(tif->tif_clientdata, module, "File not open for writing");
569  return (0);
570  }
571  if (tiles ^ isTiled(tif)) {
572  TIFFErrorExt(tif->tif_clientdata, module, tiles ?
573  "Can not write tiles to a striped image" :
574  "Can not write scanlines to a tiled image");
575  return (0);
576  }
577 
578  _TIFFFillStriles( tif );
579 
580  /*
581  * On the first write verify all the required information
582  * has been setup and initialize any data structures that
583  * had to wait until directory information was set.
584  * Note that a lot of our work is assumed to remain valid
585  * because we disallow any of the important parameters
586  * from changing after we start writing (i.e. once
587  * TIFF_BEENWRITING is set, TIFFSetField will only allow
588  * the image's length to be changed).
589  */
590  if (!TIFFFieldSet(tif, FIELD_IMAGEDIMENSIONS)) {
592  "Must set \"ImageWidth\" before writing data");
593  return (0);
594  }
595  if (tif->tif_dir.td_samplesperpixel == 1) {
596  /*
597  * Planarconfiguration is irrelevant in case of single band
598  * images and need not be included. We will set it anyway,
599  * because this field is used in other parts of library even
600  * in the single band case.
601  */
602  if (!TIFFFieldSet(tif, FIELD_PLANARCONFIG))
604  } else {
605  if (!TIFFFieldSet(tif, FIELD_PLANARCONFIG)) {
607  "Must set \"PlanarConfiguration\" before writing data");
608  return (0);
609  }
610  }
611  if (tif->tif_dir.td_stripoffset_p == NULL && !TIFFSetupStrips(tif)) {
612  tif->tif_dir.td_nstrips = 0;
613  TIFFErrorExt(tif->tif_clientdata, module, "No space for %s arrays",
614  isTiled(tif) ? "tile" : "strip");
615  return (0);
616  }
617  if (isTiled(tif))
618  {
619  tif->tif_tilesize = TIFFTileSize(tif);
620  if (tif->tif_tilesize == 0)
621  return (0);
622  }
623  else
624  tif->tif_tilesize = (tmsize_t)(-1);
626  if (tif->tif_scanlinesize == 0)
627  return (0);
628  tif->tif_flags |= TIFF_BEENWRITING;
629 
630  if( tif->tif_dir.td_stripoffset_entry.tdir_tag != 0 &&
638  !(tif->tif_flags & TIFF_DIRTYDIRECT) )
639  {
641  }
642 
643  return (1);
644 }
645 
646 /*
647  * Setup the raw data buffer used for encoding.
648  */
649 int
651 {
652  static const char module[] = "TIFFWriteBufferSetup";
653 
654  if (tif->tif_rawdata) {
655  if (tif->tif_flags & TIFF_MYBUFFER) {
656  _TIFFfree(tif->tif_rawdata);
657  tif->tif_flags &= ~TIFF_MYBUFFER;
658  }
659  tif->tif_rawdata = NULL;
660  }
661  if (size == (tmsize_t)(-1)) {
662  size = (isTiled(tif) ?
663  tif->tif_tilesize : TIFFStripSize(tif));
664  /*
665  * Make raw data buffer at least 8K
666  */
667  if (size < 8*1024)
668  size = 8*1024;
669  bp = NULL; /* NB: force malloc */
670  }
671  if (bp == NULL) {
672  bp = _TIFFmalloc(size);
673  if (bp == NULL) {
674  TIFFErrorExt(tif->tif_clientdata, module, "No space for output buffer");
675  return (0);
676  }
677  tif->tif_flags |= TIFF_MYBUFFER;
678  } else
679  tif->tif_flags &= ~TIFF_MYBUFFER;
680  tif->tif_rawdata = (uint8*) bp;
681  tif->tif_rawdatasize = size;
682  tif->tif_rawcc = 0;
683  tif->tif_rawcp = tif->tif_rawdata;
684  tif->tif_flags |= TIFF_BUFFERSETUP;
685  return (1);
686 }
687 
688 /*
689  * Grow the strip data structures by delta strips.
690  */
691 static int
692 TIFFGrowStrips(TIFF* tif, uint32 delta, const char* module)
693 {
694  TIFFDirectory *td = &tif->tif_dir;
695  uint64* new_stripoffset;
696  uint64* new_stripbytecount;
697 
699  new_stripoffset = (uint64*)_TIFFrealloc(td->td_stripoffset_p,
700  (td->td_nstrips + delta) * sizeof (uint64));
701  new_stripbytecount = (uint64*)_TIFFrealloc(td->td_stripbytecount_p,
702  (td->td_nstrips + delta) * sizeof (uint64));
703  if (new_stripoffset == NULL || new_stripbytecount == NULL) {
704  if (new_stripoffset)
705  _TIFFfree(new_stripoffset);
706  if (new_stripbytecount)
707  _TIFFfree(new_stripbytecount);
708  td->td_nstrips = 0;
709  TIFFErrorExt(tif->tif_clientdata, module, "No space to expand strip arrays");
710  return (0);
711  }
712  td->td_stripoffset_p = new_stripoffset;
713  td->td_stripbytecount_p = new_stripbytecount;
715  0, delta*sizeof (uint64));
717  0, delta*sizeof (uint64));
718  td->td_nstrips += delta;
719  tif->tif_flags |= TIFF_DIRTYDIRECT;
720 
721  return (1);
722 }
723 
724 /*
725  * Append the data to the specified strip.
726  */
727 static int
729 {
730  static const char module[] = "TIFFAppendToStrip";
731  TIFFDirectory *td = &tif->tif_dir;
732  uint64 m;
733  int64 old_byte_count = -1;
734 
735  if (td->td_stripoffset_p[strip] == 0 || tif->tif_curoff == 0) {
736  assert(td->td_nstrips > 0);
737 
738  if( td->td_stripbytecount_p[strip] != 0
739  && td->td_stripoffset_p[strip] != 0
740  && td->td_stripbytecount_p[strip] >= (uint64) cc )
741  {
742  /*
743  * There is already tile data on disk, and the new tile
744  * data we have will fit in the same space. The only
745  * aspect of this that is risky is that there could be
746  * more data to append to this strip before we are done
747  * depending on how we are getting called.
748  */
749  if (!SeekOK(tif, td->td_stripoffset_p[strip])) {
751  "Seek error at scanline %lu",
752  (unsigned long)tif->tif_row);
753  return (0);
754  }
755  }
756  else
757  {
758  /*
759  * Seek to end of file, and set that as our location to
760  * write this strip.
761  */
762  td->td_stripoffset_p[strip] = TIFFSeekFile(tif, 0, SEEK_END);
763  tif->tif_flags |= TIFF_DIRTYSTRIP;
764  }
765 
766  tif->tif_curoff = td->td_stripoffset_p[strip];
767 
768  /*
769  * We are starting a fresh strip/tile, so set the size to zero.
770  */
771  old_byte_count = td->td_stripbytecount_p[strip];
772  td->td_stripbytecount_p[strip] = 0;
773  }
774 
775  m = tif->tif_curoff+cc;
776  if (!(tif->tif_flags&TIFF_BIGTIFF))
777  m = (uint32)m;
778  if ((m<tif->tif_curoff)||(m<(uint64)cc))
779  {
780  TIFFErrorExt(tif->tif_clientdata, module, "Maximum TIFF file size exceeded");
781  return (0);
782  }
783  if (!WriteOK(tif, data, cc)) {
784  TIFFErrorExt(tif->tif_clientdata, module, "Write error at scanline %lu",
785  (unsigned long) tif->tif_row);
786  return (0);
787  }
788  tif->tif_curoff = m;
789  td->td_stripbytecount_p[strip] += cc;
790 
791  if( (int64) td->td_stripbytecount_p[strip] != old_byte_count )
792  tif->tif_flags |= TIFF_DIRTYSTRIP;
793 
794  return (1);
795 }
796 
797 /*
798  * Internal version of TIFFFlushData that can be
799  * called by ``encodestrip routines'' w/o concern
800  * for infinite recursion.
801  */
802 int
804 {
805  if (tif->tif_rawcc > 0 && tif->tif_flags & TIFF_BUF4WRITE ) {
806  if (!isFillOrder(tif, tif->tif_dir.td_fillorder) &&
807  (tif->tif_flags & TIFF_NOBITREV) == 0)
809  tif->tif_rawcc);
810  if (!TIFFAppendToStrip(tif,
811  isTiled(tif) ? tif->tif_curtile : tif->tif_curstrip,
812  tif->tif_rawdata, tif->tif_rawcc))
813  {
814  /* We update those variables even in case of error since there's */
815  /* code that doesn't really check the return code of this */
816  /* function */
817  tif->tif_rawcc = 0;
818  tif->tif_rawcp = tif->tif_rawdata;
819  return (0);
820  }
821  tif->tif_rawcc = 0;
822  tif->tif_rawcp = tif->tif_rawdata;
823  }
824  return (1);
825 }
826 
827 /*
828  * Set the current write offset. This should only be
829  * used to set the offset to a known previous location
830  * (very carefully), or to 0 so that the next write gets
831  * appended to the end of the file.
832  */
833 void
835 {
836  tif->tif_curoff = off;
837 }
838 
839 /* vim: set ts=8 sts=8 sw=8 noet: */
840 /*
841  * Local Variables:
842  * mode: c
843  * c-basic-offset: 8
844  * fill-column: 78
845  * End:
846  */
unsigned long long uint64
Definition: platform.h:18
#define TIFF_BEENWRITING
Definition: tiffiop.h:125
uint8 * tif_rawcp
Definition: tiffiop.h:199
int TIFFCheckTile(TIFF *tif, uint32 x, uint32 y, uint32 z, uint16 s)
Definition: tif_tile.c:73
void _TIFFmemset(void *p, int v, tmsize_t c)
Definition: tif_unix.c:338
return
Definition: dirsup.c:529
union TIFFDirEntry::@3327 tdir_offset
uint32 TIFFComputeTile(TIFF *tif, uint32 x, uint32 y, uint32 z, uint16 s)
Definition: tif_tile.c:36
uint32 TIFFNumberOfStrips(TIFF *tif)
Definition: tif_strip.c:59
ActualNumberDriverObjects * sizeof(PDRIVER_OBJECT)) PDRIVER_OBJECT *DriverObjectList
int TIFFSetupStrips(TIFF *tif)
Definition: tif_write.c:523
#define TIFFhowmany_32(x, y)
Definition: tiffiop.h:264
#define FIELD_STRIPOFFSETS
Definition: tif_dir.h:162
GLenum GLuint GLenum GLsizei const GLchar * buf
Definition: glext.h:7751
TIFFCodeMethod tif_encodestrip
Definition: tiffiop.h:183
int TIFFForceStrileArrayWriting(TIFF *tif)
Definition: tif_flush.c:79
#define WriteOK(tif, buf, size)
Definition: tiffiop.h:259
#define FIELD_IMAGEDIMENSIONS
Definition: tif_dir.h:141
unsigned int uint32
Definition: types.h:32
#define TIFFSeekFile(tif, off, whence)
Definition: tiffiop.h:237
uint64 toff_t
Definition: tiffio.h:66
TIFFCodeMethod tif_encoderow
Definition: tiffiop.h:181
uint32 tif_curstrip
Definition: tiffiop.h:161
uint64 * td_stripbytecount_p
Definition: tif_dir.h:102
static int TIFFGrowStrips(TIFF *tif, uint32 delta, const char *module)
Definition: tif_write.c:692
int TIFFWriteBufferSetup(TIFF *tif, void *bp, tmsize_t size)
Definition: tif_write.c:650
#define assert(x)
Definition: debug.h:53
GLint GLint GLint GLint GLint x
Definition: gl.h:1548
#define WRITECHECKSTRIPS(tif, module)
Definition: tif_write.c:35
uint8 * tif_rawdata
Definition: tiffiop.h:195
tmsize_t tif_scanlinesize
Definition: tiffiop.h:193
uint64 tif_curoff
Definition: tiffiop.h:162
thandle_t tif_clientdata
Definition: tiffiop.h:207
long long int64
Definition: platform.h:13
uint32 TIFFNumberOfTiles(TIFF *tif)
Definition: tif_tile.c:113
tmsize_t tif_rawcc
Definition: tiffiop.h:200
tmsize_t tif_tilesize
Definition: tiffiop.h:170
int TIFFWriteScanline(TIFF *tif, void *buf, uint32 row, uint16 sample)
Definition: tif_write.c:47
#define TIFF_DIRTYDIRECT
Definition: tiffiop.h:122
const GLfloat * m
Definition: glext.h:10848
Definition: tiffiop.h:115
uint32 td_tilelength
Definition: tif_dir.h:73
tmsize_t TIFFStripSize(TIFF *tif)
Definition: tif_strip.c:202
#define TIFFSetFieldBit(tif, field)
Definition: tif_dir.h:197
#define TIFF_BIGTIFF
Definition: tiffiop.h:138
#define FIELD_STRIPBYTECOUNTS
Definition: tif_dir.h:161
TIFF_SSIZE_T tmsize_t
Definition: tiffio.h:65
int TIFFFlushData(TIFF *tif)
Definition: tif_flush.c:156
TIFFDirEntry td_stripbytecount_entry
Definition: tif_dir.h:108
void * _TIFFCheckMalloc(TIFF *tif, tmsize_t nmemb, tmsize_t elem_size, const char *what)
Definition: tif_aux.c:121
uint32 td_stripsperimage
Definition: tif_dir.h:99
int tif_mode
Definition: tiffiop.h:118
GLdouble GLdouble z
Definition: glext.h:5874
uint32 tif_flags
Definition: tiffiop.h:119
smooth NULL
Definition: ftsmooth.c:416
#define FIELD_PLANARCONFIG
Definition: tif_dir.h:158
uint16 td_planarconfig
Definition: tif_dir.h:89
TIFFCodeMethod tif_encodetile
Definition: tiffiop.h:185
#define TIFF_POSTENCODE
Definition: tiffiop.h:131
void * _TIFFmalloc(tmsize_t s)
Definition: tif_unix.c:309
TIFFSeekMethod tif_seek
Definition: tiffiop.h:187
TIFFPreMethod tif_preencode
Definition: tiffiop.h:178
#define TIFF_BUF4WRITE
Definition: tiffiop.h:139
uint32 td_nstrips
Definition: tif_dir.h:100
GLsizeiptr size
Definition: glext.h:5919
TIFFBoolMethod tif_postencode
Definition: tiffiop.h:179
if(!(yy_init))
Definition: macro.lex.yy.c:714
uint32 td_imagelength
Definition: tif_dir.h:72
TIFFPostMethod tif_postdecode
Definition: tiffiop.h:214
tmsize_t TIFFWriteEncodedTile(TIFF *tif, uint32 tile, void *data, tmsize_t cc)
Definition: tif_write.c:391
uint16 tdir_tag
Definition: tif_dir.h:53
unsigned char uint8
Definition: types.h:28
void TIFFErrorExt(thandle_t fd, const char *module, const char *fmt,...)
Definition: tif_error.c:65
GLint GLenum GLsizei GLsizei GLsizei GLint GLsizei const GLvoid * data
Definition: gl.h:1950
tmsize_t tif_rawdatasize
Definition: tiffiop.h:196
#define TIFFFieldSet(tif, field)
Definition: tif_dir.h:196
uint16 td_fillorder
Definition: tif_dir.h:80
tmsize_t TIFFWriteRawTile(TIFF *tif, uint32 tile, void *data, tmsize_t cc)
Definition: tif_write.c:503
#define FIELD_ROWSPERSTRIP
Definition: tif_dir.h:155
uint64 tdir_count
Definition: tif_dir.h:55
#define TIFF_DIRTYSTRIP
Definition: tiffiop.h:140
void * _TIFFrealloc(void *p, tmsize_t s)
Definition: tif_unix.c:332
uint32 tif_curtile
Definition: tiffiop.h:169
#define COMPRESSION_NONE
Definition: tiff.h:158
uint32 td_tilewidth
Definition: tif_dir.h:73
#define TIFF_NOBITREV
Definition: tiffiop.h:127
#define PLANARCONFIG_SEPARATE
Definition: tiff.h:241
GLdouble s
Definition: gl.h:2039
#define isTiled(tif)
Definition: tiffiop.h:229
#define TIFF_BUFFERSETUP
Definition: tiffiop.h:123
#define TIFF_CODERSETUP
Definition: tiffiop.h:124
int TIFFWriteCheck(TIFF *tif, int tiles, const char *module)
Definition: tif_write.c:565
uint32_t cc
Definition: isohybrid.c:75
void TIFFSetWriteOffset(TIFF *tif, toff_t off)
Definition: tif_write.c:834
uint32 td_rowsperstrip
Definition: tif_dir.h:83
uint32 tif_row
Definition: tiffiop.h:159
static int TIFFAppendToStrip(TIFF *tif, uint32 strip, uint8 *data, tmsize_t cc)
Definition: tif_write.c:728
tmsize_t TIFFWriteEncodedStrip(TIFF *tif, uint32 strip, void *data, tmsize_t cc)
Definition: tif_write.c:212
tmsize_t TIFFScanlineSize(TIFF *tif)
Definition: tif_strip.c:314
unsigned short uint16
Definition: types.h:30
tmsize_t TIFFWriteRawStrip(TIFF *tif, uint32 strip, void *data, tmsize_t cc)
Definition: tif_write.c:316
TIFFDirectory tif_dir
Definition: tiffiop.h:151
TIFFDirEntry td_stripoffset_entry
Definition: tif_dir.h:107
#define isFillOrder(tif, o)
Definition: tiffiop.h:231
#define FIELD_TILEDIMENSIONS
Definition: tif_dir.h:142
#define SeekOK(tif, off)
Definition: tiffiop.h:256
GLint GLint GLint GLint GLint GLint y
Definition: gl.h:1548
uint64 * td_stripoffset_p
Definition: tif_dir.h:101
tmsize_t TIFFTileSize(TIFF *tif)
Definition: tif_tile.c:257
#define TIFFroundup_64(x, y)
Definition: tiffiop.h:275
void TIFFReverseBits(uint8 *cp, tmsize_t n)
Definition: tif_swab.c:284
static int _TIFFReserveLargeEnoughWriteBuffer(TIFF *tif, uint32 strip_or_tile)
Definition: tif_write.c:183
#define SEEK_END
Definition: cabinet.c:27
uint16 td_samplesperpixel
Definition: tif_dir.h:82
uint16 td_compression
Definition: tif_dir.h:77
void _TIFFfree(void *p)
Definition: tif_unix.c:326
#define BUFFERCHECK(tif)
Definition: tif_write.c:39
uint32 tif_col
Definition: tiffiop.h:168
#define isUnspecified(tif, f)
Definition: tif_write.c:519
tmsize_t TIFFWriteTile(TIFF *tif, void *buf, uint32 x, uint32 y, uint32 z, uint16 s)
Definition: tif_write.c:364
uint32 td_imagewidth
Definition: tif_dir.h:72
uint64 toff_long8
Definition: tif_dir.h:59
static SERVICE_STATUS status
Definition: service.c:31
TIFFBoolMethod tif_setupencode
Definition: tiffiop.h:176
int TIFFFlushData1(TIFF *tif)
Definition: tif_write.c:803
#define TIFF_MYBUFFER
Definition: tiffiop.h:128
#define WRITECHECKTILES(tif, module)
Definition: tif_write.c:37
#define PLANARCONFIG_CONTIG
Definition: tiff.h:240
int _TIFFFillStriles(TIFF *tif)
Definition: tif_dirread.c:6320
struct png_info_def *typedef unsigned char **typedef struct png_info_def *typedef struct png_info_def *typedef struct png_info_def *typedef unsigned char ** row
Definition: typeof.h:78
uint16 tdir_type
Definition: tif_dir.h:54
#define O_RDONLY
Definition: acwin.h:108
off
Definition: i386-dis.c:3909
Definition: ps.c:97