Line data Source code
1 : /* WARNING: The type of JPEG encapsulation defined by the TIFF Version 6.0
2 : specification is now totally obsolete and deprecated for new applications and
3 : images. This file was was created solely in order to read unconverted images
4 : still present on some users' computer systems. It will never be extended
5 : to write such files. Writing new-style JPEG compressed TIFFs is implemented
6 : in tif_jpeg.c.
7 :
8 : The code is carefully crafted to robustly read all gathered JPEG-in-TIFF
9 : testfiles, and anticipate as much as possible all other... But still, it may
10 : fail on some. If you encounter problems, please report them on the TIFF
11 : mailing list and/or to Joris Van Damme <info@awaresystems.be>.
12 :
13 : Please read the file called "TIFF Technical Note #2" if you need to be
14 : convinced this compression scheme is bad and breaks TIFF. That document
15 : is linked to from the LibTiff site <http://www.remotesensing.org/libtiff/>
16 : and from AWare Systems' TIFF section
17 : <http://www.awaresystems.be/imaging/tiff.html>. It is also absorbed
18 : in Adobe's specification supplements, marked "draft" up to this day, but
19 : supported by the TIFF community.
20 :
21 : This file interfaces with Release 6B of the JPEG Library written by the
22 : Independent JPEG Group. Previous versions of this file required a hack inside
23 : the LibJpeg library. This version no longer requires that. Remember to
24 : remove the hack if you update from the old version.
25 :
26 : Copyright (c) Joris Van Damme <info@awaresystems.be>
27 : Copyright (c) AWare Systems <http://www.awaresystems.be/>
28 :
29 : The licence agreement for this file is the same as the rest of the LibTiff
30 : library.
31 :
32 : IN NO EVENT SHALL JORIS VAN DAMME OR AWARE SYSTEMS BE LIABLE FOR
33 : ANY SPECIAL, INCIDENTAL, INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND,
34 : OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS,
35 : WHETHER OR NOT ADVISED OF THE POSSIBILITY OF DAMAGE, AND ON ANY THEORY OF
36 : LIABILITY, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE
37 : OF THIS SOFTWARE.
38 :
39 : Joris Van Damme and/or AWare Systems may be available for custom
40 : development. If you like what you see, and need anything similar or related,
41 : contact <info@awaresystems.be>.
42 : */
43 :
44 : /* What is what, and what is not?
45 :
46 : This decoder starts with an input stream, that is essentially the
47 : JpegInterchangeFormat stream, if any, followed by the strile data, if any.
48 : This stream is read in OJPEGReadByte and related functions.
49 :
50 : It analyzes the start of this stream, until it encounters non-marker data,
51 : i.e. compressed image data. Some of the header markers it sees have no actual
52 : content, like the SOI marker, and APP/COM markers that really shouldn't even
53 : be there. Some other markers do have content, and the valuable bits and
54 : pieces of information in these markers are saved, checking all to verify that
55 : the stream is more or less within expected bounds. This happens inside the
56 : OJPEGReadHeaderInfoSecStreamXxx functions.
57 :
58 : Some OJPEG imagery contains no valid JPEG header markers. This situation is
59 : picked up on if we've seen no SOF marker when we're at the start of the
60 : compressed image data. In this case, the tables are read from JpegXxxTables
61 : tags, and the other bits and pieces of information is initialized to its most
62 : basic value. This is implemented in the OJPEGReadHeaderInfoSecTablesXxx
63 : functions.
64 :
65 : When this is complete, a good and valid JPEG header can be assembled, and
66 : this is passed through to LibJpeg. When that's done, the remainder of the
67 : input stream, i.e. the compressed image data, can be passed through
68 : unchanged. This is done in OJPEGWriteStream functions.
69 :
70 : LibTiff rightly expects to know the subsampling values before decompression.
71 : Just like in new-style JPEG-in-TIFF, though, or even more so, actually, the
72 : YCbCrsubsampling tag is notoriously unreliable. To correct these tag values
73 : with the ones inside the JPEG stream, the first part of the input stream is
74 : pre-scanned in OJPEGSubsamplingCorrect, making no note of any other data,
75 : reporting no warnings or errors, up to the point where either these values
76 : are read, or it's clear they aren't there. This means that some of the data
77 : is read twice, but we feel speed in correcting these values is important
78 : enough to warrant this sacrifice. Although there is currently no define or
79 : other configuration mechanism to disable this behavior, the actual header
80 : scanning is build to robustly respond with error report if it should
81 : encounter an uncorrected mismatch of subsampling values. See
82 : OJPEGReadHeaderInfoSecStreamSof.
83 :
84 : The restart interval and restart markers are the most tricky part... The
85 : restart interval can be specified in a tag. It can also be set inside the
86 : input JPEG stream. It can be used inside the input JPEG stream. If reading
87 : from strile data, we've consistently discovered the need to insert restart
88 : markers in between the different striles, as is also probably the most likely
89 : interpretation of the original TIFF 6.0 specification. With all this setting
90 : of interval, and actual use of markers that is not predictable at the time of
91 : valid JPEG header assembly, the restart thing may turn out the Achilles heel
92 : of this implementation. Fortunately, most OJPEG writer vendors succeed in
93 : reading back what they write, which may be the reason why we've been able to
94 : discover ways that seem to work.
95 :
96 : Some special provision is made for planarconfig separate OJPEG files. These
97 : seem to consistently contain header info, a SOS marker, a plane, SOS marker,
98 : plane, SOS, and plane. This may or may not be a valid JPEG configuration, we
99 : don't know and don't care. We want LibTiff to be able to access the planes
100 : individually, without huge buffering inside LibJpeg, anyway. So we compose
101 : headers to feed to LibJpeg, in this case, that allow us to pass a single
102 : plane such that LibJpeg sees a valid single-channel JPEG stream. Locating
103 : subsequent SOS markers, and thus subsequent planes, is done inside
104 : OJPEGReadSecondarySos.
105 :
106 : The benefit of the scheme is... that it works, basically. We know of no other
107 : that does. It works without checking software tag, or otherwise going about
108 : things in an OJPEG flavor specific manner. Instead, it is a single scheme,
109 : that covers the cases with and without JpegInterchangeFormat, with and
110 : without striles, with part of the header in JpegInterchangeFormat and
111 : remainder in first strile, etc. It is forgiving and robust, may likely work
112 : with OJPEG flavors we've not seen yet, and makes most out of the data.
113 :
114 : Another nice side-effect is that a complete JPEG single valid stream is build
115 : if planarconfig is not separate (vast majority). We may one day use that to
116 : build converters to JPEG, and/or to new-style JPEG compression inside TIFF.
117 :
118 : A disadvantage is the lack of random access to the individual striles. This
119 : is the reason for much of the complicated restart-and-position stuff inside
120 : OJPEGPreDecode. Applications would do well accessing all striles in order, as
121 : this will result in a single sequential scan of the input stream, and no
122 : restarting of LibJpeg decoding session.
123 : */
124 :
125 : #include "tiffiop.h"
126 : #ifdef OJPEG_SUPPORT
127 :
128 : /* Configuration defines here are:
129 : * JPEG_ENCAP_EXTERNAL: The normal way to call libjpeg, uses longjump. In some
130 : * environments, like eg LibTiffDelphi, this is not possible. For this reason,
131 : * the actual calls to libjpeg, with longjump stuff, are encapsulated in
132 : * dedicated functions. When JPEG_ENCAP_EXTERNAL is defined, these encapsulating
133 : * functions are declared external to this unit, and can be defined elsewhere to
134 : * use stuff other then longjump. The default mode, without JPEG_ENCAP_EXTERNAL,
135 : * implements the call encapsulators here, internally, with normal longjump.
136 : * SETJMP, LONGJMP, JMP_BUF: On some machines/environments a longjump equivalent
137 : * is conveniently available, but still it may be worthwhile to use _setjmp or
138 : * sigsetjmp in place of plain setjmp. These macros will make it easier. It is
139 : * useless to fiddle with these if you define JPEG_ENCAP_EXTERNAL. OJPEG_BUFFER:
140 : * Define the size of the desired buffer here. Should be small enough so as to
141 : * guarantee instant processing, optimal streaming and optimal use of processor
142 : * cache, but also big enough so as to not result in significant call overhead.
143 : * It should be at least a few bytes to accommodate some structures (this is
144 : * verified in asserts), but it would not be sensible to make it this small
145 : * anyway, and it should be at most 64K since it is indexed with uint16_t. We
146 : * recommend 2K. EGYPTIANWALK: You could also define EGYPTIANWALK here, but it
147 : * is not used anywhere and has absolutely no effect. That is why most people
148 : * insist the EGYPTIANWALK is a bit silly.
149 : */
150 :
151 : /* define LIBJPEG_ENCAP_EXTERNAL */
152 : #define SETJMP(jbuf) setjmp(jbuf)
153 : #define LONGJMP(jbuf, code) longjmp(jbuf, code)
154 : #define JMP_BUF jmp_buf
155 : #define OJPEG_BUFFER 2048
156 : /* define EGYPTIANWALK */
157 :
158 : #define JPEG_MARKER_SOF0 0xC0
159 : #define JPEG_MARKER_SOF1 0xC1
160 : #define JPEG_MARKER_SOF3 0xC3
161 : #define JPEG_MARKER_DHT 0xC4
162 : #define JPEG_MARKER_RST0 0XD0
163 : #define JPEG_MARKER_SOI 0xD8
164 : #define JPEG_MARKER_EOI 0xD9
165 : #define JPEG_MARKER_SOS 0xDA
166 : #define JPEG_MARKER_DQT 0xDB
167 : #define JPEG_MARKER_DRI 0xDD
168 : #define JPEG_MARKER_APP0 0xE0
169 : #define JPEG_MARKER_COM 0xFE
170 :
171 : #define FIELD_OJPEG_JPEGINTERCHANGEFORMAT (FIELD_CODEC + 0)
172 : #define FIELD_OJPEG_JPEGINTERCHANGEFORMATLENGTH (FIELD_CODEC + 1)
173 : #define FIELD_OJPEG_JPEGQTABLES (FIELD_CODEC + 2)
174 : #define FIELD_OJPEG_JPEGDCTABLES (FIELD_CODEC + 3)
175 : #define FIELD_OJPEG_JPEGACTABLES (FIELD_CODEC + 4)
176 : #define FIELD_OJPEG_JPEGPROC (FIELD_CODEC + 5)
177 : #define FIELD_OJPEG_JPEGRESTARTINTERVAL (FIELD_CODEC + 6)
178 :
179 : static const TIFFField ojpegFields[] = {
180 : {TIFFTAG_JPEGIFOFFSET, 1, 1, TIFF_LONG8, 0, TIFF_SETGET_UINT64,
181 : FIELD_OJPEG_JPEGINTERCHANGEFORMAT, TRUE, FALSE, "JpegInterchangeFormat",
182 : NULL},
183 : {TIFFTAG_JPEGIFBYTECOUNT, 1, 1, TIFF_LONG8, 0, TIFF_SETGET_UINT64,
184 : FIELD_OJPEG_JPEGINTERCHANGEFORMATLENGTH, TRUE, FALSE,
185 : "JpegInterchangeFormatLength", NULL},
186 : {TIFFTAG_JPEGQTABLES, TIFF_VARIABLE2, TIFF_VARIABLE2, TIFF_LONG8, 0,
187 : TIFF_SETGET_C32_UINT64, FIELD_OJPEG_JPEGQTABLES, FALSE, TRUE,
188 : "JpegQTables", NULL},
189 : {TIFFTAG_JPEGDCTABLES, TIFF_VARIABLE2, TIFF_VARIABLE2, TIFF_LONG8, 0,
190 : TIFF_SETGET_C32_UINT64, FIELD_OJPEG_JPEGDCTABLES, FALSE, TRUE,
191 : "JpegDcTables", NULL},
192 : {TIFFTAG_JPEGACTABLES, TIFF_VARIABLE2, TIFF_VARIABLE2, TIFF_LONG8, 0,
193 : TIFF_SETGET_C32_UINT64, FIELD_OJPEG_JPEGACTABLES, FALSE, TRUE,
194 : "JpegAcTables", NULL},
195 : {TIFFTAG_JPEGPROC, 1, 1, TIFF_SHORT, 0, TIFF_SETGET_UINT16,
196 : FIELD_OJPEG_JPEGPROC, FALSE, FALSE, "JpegProc", NULL},
197 : {TIFFTAG_JPEGRESTARTINTERVAL, 1, 1, TIFF_SHORT, 0, TIFF_SETGET_UINT16,
198 : FIELD_OJPEG_JPEGRESTARTINTERVAL, FALSE, FALSE, "JpegRestartInterval",
199 : NULL},
200 : };
201 :
202 : #ifndef LIBJPEG_ENCAP_EXTERNAL
203 : #include <setjmp.h>
204 : #endif
205 :
206 : #include "jerror.h"
207 : #include "jpeglib.h"
208 :
209 : typedef struct jpeg_source_mgr tiff_ojpeg_source_mgr;
210 :
211 : typedef struct jpeg_error_mgr tiff_ojpeg_error_mgr;
212 :
213 : typedef struct jpeg_common_struct tiff_ojpeg_common_struct;
214 : typedef struct jpeg_decompress_struct tiff_ojpeg_decompress_struct;
215 :
216 : typedef enum
217 : {
218 : osibsNotSetYet,
219 : osibsJpegInterchangeFormat,
220 : osibsStrile,
221 : osibsEof
222 : } OJPEGStateInBufferSource;
223 :
224 : typedef enum
225 : {
226 : ososSoi,
227 : ososQTable0,
228 : ososQTable1,
229 : ososQTable2,
230 : ososQTable3,
231 : ososDcTable0,
232 : ososDcTable1,
233 : ososDcTable2,
234 : ososDcTable3,
235 : ososAcTable0,
236 : ososAcTable1,
237 : ososAcTable2,
238 : ososAcTable3,
239 : ososDri,
240 : ososSof,
241 : ososSos,
242 : ososCompressed,
243 : ososRst,
244 : ososEoi
245 : } OJPEGStateOutState;
246 :
247 : typedef struct
248 : {
249 : TIFF *tif;
250 : int decoder_ok;
251 : int error_in_raw_data_decoding;
252 : #ifndef LIBJPEG_ENCAP_EXTERNAL
253 : JMP_BUF exit_jmpbuf;
254 : #endif
255 : TIFFVGetMethod vgetparent;
256 : TIFFVSetMethod vsetparent;
257 : TIFFPrintMethod printdir;
258 : uint64_t file_size;
259 : uint32_t image_width;
260 : uint32_t image_length;
261 : uint32_t strile_width;
262 : uint32_t strile_length;
263 : uint32_t strile_length_total;
264 : uint8_t samples_per_pixel;
265 : uint8_t plane_sample_offset;
266 : uint8_t samples_per_pixel_per_plane;
267 : uint64_t jpeg_interchange_format;
268 : uint64_t jpeg_interchange_format_length;
269 : uint8_t jpeg_proc;
270 : uint8_t subsamplingcorrect;
271 : uint8_t subsamplingcorrect_done;
272 : uint8_t subsampling_tag;
273 : uint8_t subsampling_hor;
274 : uint8_t subsampling_ver;
275 : uint8_t subsampling_force_desubsampling_inside_decompression;
276 : uint8_t qtable_offset_count;
277 : uint8_t dctable_offset_count;
278 : uint8_t actable_offset_count;
279 : uint64_t qtable_offset[3];
280 : uint64_t dctable_offset[3];
281 : uint64_t actable_offset[3];
282 : uint8_t *qtable[4];
283 : uint8_t *dctable[4];
284 : uint8_t *actable[4];
285 : uint16_t restart_interval;
286 : uint8_t restart_index;
287 : uint8_t sof_log;
288 : uint8_t sof_marker_id;
289 : uint32_t sof_x;
290 : uint32_t sof_y;
291 : uint8_t sof_c[3];
292 : uint8_t sof_hv[3];
293 : uint8_t sof_tq[3];
294 : uint8_t sos_cs[3];
295 : uint8_t sos_tda[3];
296 : struct
297 : {
298 : uint8_t log;
299 : OJPEGStateInBufferSource in_buffer_source;
300 : uint32_t in_buffer_next_strile;
301 : uint64_t in_buffer_file_pos;
302 : uint64_t in_buffer_file_togo;
303 : } sos_end[3];
304 : uint8_t readheader_done;
305 : uint8_t writeheader_done;
306 : uint16_t write_cursample;
307 : uint32_t write_curstrile;
308 : uint8_t libjpeg_session_active;
309 : uint8_t libjpeg_jpeg_query_style;
310 : tiff_ojpeg_error_mgr libjpeg_jpeg_error_mgr;
311 : tiff_ojpeg_decompress_struct libjpeg_jpeg_decompress_struct;
312 : tiff_ojpeg_source_mgr libjpeg_jpeg_source_mgr;
313 : uint8_t subsampling_convert_log;
314 : uint32_t subsampling_convert_ylinelen;
315 : uint32_t subsampling_convert_ylines;
316 : uint32_t subsampling_convert_clinelen;
317 : uint32_t subsampling_convert_clines;
318 : uint32_t subsampling_convert_ybuflen;
319 : uint32_t subsampling_convert_cbuflen;
320 : uint32_t subsampling_convert_ycbcrbuflen;
321 : uint8_t *subsampling_convert_ycbcrbuf;
322 : uint8_t *subsampling_convert_ybuf;
323 : uint8_t *subsampling_convert_cbbuf;
324 : uint8_t *subsampling_convert_crbuf;
325 : uint32_t subsampling_convert_ycbcrimagelen;
326 : uint8_t **subsampling_convert_ycbcrimage;
327 : uint32_t subsampling_convert_clinelenout;
328 : uint32_t subsampling_convert_state;
329 : uint32_t bytes_per_line; /* if the codec outputs subsampled data, a 'line'
330 : in bytes_per_line */
331 : uint32_t lines_per_strile; /* and lines_per_strile means subsampling_ver
332 : desubsampled rows */
333 : OJPEGStateInBufferSource in_buffer_source;
334 : uint32_t in_buffer_next_strile;
335 : uint32_t in_buffer_strile_count;
336 : uint64_t in_buffer_file_pos;
337 : uint8_t in_buffer_file_pos_log;
338 : uint64_t in_buffer_file_togo;
339 : uint16_t in_buffer_togo;
340 : uint8_t *in_buffer_cur;
341 : uint8_t in_buffer[OJPEG_BUFFER];
342 : OJPEGStateOutState out_state;
343 : uint8_t out_buffer[OJPEG_BUFFER];
344 : uint8_t *skip_buffer;
345 : } OJPEGState;
346 :
347 : static int OJPEGVGetField(TIFF *tif, uint32_t tag, va_list ap);
348 : static int OJPEGVSetField(TIFF *tif, uint32_t tag, va_list ap);
349 : static void OJPEGPrintDir(TIFF *tif, FILE *fd, long flags);
350 :
351 : static int OJPEGFixupTags(TIFF *tif);
352 : static int OJPEGSetupDecode(TIFF *tif);
353 : static int OJPEGPreDecode(TIFF *tif, uint16_t s);
354 : static int OJPEGPreDecodeSkipRaw(TIFF *tif);
355 : static int OJPEGPreDecodeSkipScanlines(TIFF *tif);
356 : static int OJPEGDecode(TIFF *tif, uint8_t *buf, tmsize_t cc, uint16_t s);
357 : static int OJPEGDecodeRaw(TIFF *tif, uint8_t *buf, tmsize_t cc);
358 : static int OJPEGDecodeScanlines(TIFF *tif, uint8_t *buf, tmsize_t cc);
359 : static void OJPEGPostDecode(TIFF *tif, uint8_t *buf, tmsize_t cc);
360 : static int OJPEGSetupEncode(TIFF *tif);
361 : static int OJPEGPreEncode(TIFF *tif, uint16_t s);
362 : static int OJPEGEncode(TIFF *tif, uint8_t *buf, tmsize_t cc, uint16_t s);
363 : static int OJPEGPostEncode(TIFF *tif);
364 : static void OJPEGCleanup(TIFF *tif);
365 :
366 : static void OJPEGSubsamplingCorrect(TIFF *tif);
367 : static int OJPEGReadHeaderInfo(TIFF *tif);
368 : static int OJPEGReadSecondarySos(TIFF *tif, uint16_t s);
369 : static int OJPEGWriteHeaderInfo(TIFF *tif);
370 : static void OJPEGLibjpegSessionAbort(TIFF *tif);
371 :
372 : static int OJPEGReadHeaderInfoSec(TIFF *tif);
373 : static int OJPEGReadHeaderInfoSecStreamDri(TIFF *tif);
374 : static int OJPEGReadHeaderInfoSecStreamDqt(TIFF *tif);
375 : static int OJPEGReadHeaderInfoSecStreamDht(TIFF *tif);
376 : static int OJPEGReadHeaderInfoSecStreamSof(TIFF *tif, uint8_t marker_id);
377 : static int OJPEGReadHeaderInfoSecStreamSos(TIFF *tif);
378 : static int OJPEGReadHeaderInfoSecTablesQTable(TIFF *tif);
379 : static int OJPEGReadHeaderInfoSecTablesDcTable(TIFF *tif);
380 : static int OJPEGReadHeaderInfoSecTablesAcTable(TIFF *tif);
381 :
382 : static int OJPEGReadBufferFill(OJPEGState *sp);
383 : static int OJPEGReadByte(OJPEGState *sp, uint8_t *byte);
384 : static int OJPEGReadBytePeek(OJPEGState *sp, uint8_t *byte);
385 : static void OJPEGReadByteAdvance(OJPEGState *sp);
386 : static int OJPEGReadWord(OJPEGState *sp, uint16_t *word);
387 : static int OJPEGReadBlock(OJPEGState *sp, uint16_t len, void *mem);
388 : static void OJPEGReadSkip(OJPEGState *sp, uint16_t len);
389 :
390 : static int OJPEGWriteStream(TIFF *tif, void **mem, uint32_t *len);
391 : static void OJPEGWriteStreamSoi(TIFF *tif, void **mem, uint32_t *len);
392 : static void OJPEGWriteStreamQTable(TIFF *tif, uint8_t table_index, void **mem,
393 : uint32_t *len);
394 : static void OJPEGWriteStreamDcTable(TIFF *tif, uint8_t table_index, void **mem,
395 : uint32_t *len);
396 : static void OJPEGWriteStreamAcTable(TIFF *tif, uint8_t table_index, void **mem,
397 : uint32_t *len);
398 : static void OJPEGWriteStreamDri(TIFF *tif, void **mem, uint32_t *len);
399 : static void OJPEGWriteStreamSof(TIFF *tif, void **mem, uint32_t *len);
400 : static void OJPEGWriteStreamSos(TIFF *tif, void **mem, uint32_t *len);
401 : static int OJPEGWriteStreamCompressed(TIFF *tif, void **mem, uint32_t *len);
402 : static void OJPEGWriteStreamRst(TIFF *tif, void **mem, uint32_t *len);
403 : static void OJPEGWriteStreamEoi(TIFF *tif, void **mem, uint32_t *len);
404 :
405 : #ifdef LIBJPEG_ENCAP_EXTERNAL
406 : extern int jpeg_create_decompress_encap(OJPEGState *sp,
407 : tiff_ojpeg_decompress_struct *cinfo);
408 : extern int jpeg_read_header_encap(OJPEGState *sp,
409 : tiff_ojpeg_decompress_struct *cinfo,
410 : uint8_t require_image);
411 : extern int jpeg_start_decompress_encap(OJPEGState *sp,
412 : tiff_ojpeg_decompress_struct *cinfo);
413 : extern int jpeg_read_scanlines_encap(OJPEGState *sp,
414 : tiff_ojpeg_decompress_struct *cinfo,
415 : void *scanlines, uint32_t max_lines);
416 : extern int jpeg_read_raw_data_encap(OJPEGState *sp,
417 : tiff_ojpeg_decompress_struct *cinfo,
418 : void *data, uint32_t max_lines);
419 : extern void jpeg_encap_unwind(TIFF *tif);
420 : #else
421 : static int jpeg_create_decompress_encap(OJPEGState *sp,
422 : tiff_ojpeg_decompress_struct *j);
423 : static int jpeg_read_header_encap(OJPEGState *sp,
424 : tiff_ojpeg_decompress_struct *cinfo,
425 : uint8_t require_image);
426 : static int jpeg_start_decompress_encap(OJPEGState *sp,
427 : tiff_ojpeg_decompress_struct *cinfo);
428 : static int jpeg_read_scanlines_encap(OJPEGState *sp,
429 : tiff_ojpeg_decompress_struct *cinfo,
430 : void *scanlines, uint32_t max_lines);
431 : static int jpeg_read_raw_data_encap(OJPEGState *sp,
432 : tiff_ojpeg_decompress_struct *cinfo,
433 : void *data, uint32_t max_lines);
434 : static void jpeg_encap_unwind(TIFF *tif);
435 : #endif
436 :
437 : static void
438 : OJPEGLibjpegJpegErrorMgrOutputMessage(tiff_ojpeg_common_struct *cinfo);
439 : static void OJPEGLibjpegJpegErrorMgrErrorExit(tiff_ojpeg_common_struct *cinfo);
440 : static void
441 : OJPEGLibjpegJpegSourceMgrInitSource(tiff_ojpeg_decompress_struct *cinfo);
442 : static boolean
443 : OJPEGLibjpegJpegSourceMgrFillInputBuffer(tiff_ojpeg_decompress_struct *cinfo);
444 : static void
445 : OJPEGLibjpegJpegSourceMgrSkipInputData(tiff_ojpeg_decompress_struct *cinfo,
446 : long num_bytes);
447 : static boolean
448 : OJPEGLibjpegJpegSourceMgrResyncToRestart(tiff_ojpeg_decompress_struct *cinfo,
449 : int desired);
450 : static void
451 : OJPEGLibjpegJpegSourceMgrTermSource(tiff_ojpeg_decompress_struct *cinfo);
452 :
453 2 : int TIFFInitOJPEG(TIFF *tif, int scheme)
454 : {
455 : static const char module[] = "TIFFInitOJPEG";
456 : OJPEGState *sp;
457 :
458 : (void)scheme;
459 2 : assert(scheme == COMPRESSION_OJPEG);
460 :
461 : /*
462 : * Merge codec-specific tag information.
463 : */
464 2 : if (!_TIFFMergeFields(tif, ojpegFields, TIFFArrayCount(ojpegFields)))
465 : {
466 0 : TIFFErrorExtR(tif, module,
467 : "Merging Old JPEG codec-specific tags failed");
468 0 : return 0;
469 : }
470 :
471 : /* state block */
472 2 : sp = (OJPEGState *)_TIFFmallocExt(tif, sizeof(OJPEGState));
473 2 : if (sp == NULL)
474 : {
475 0 : TIFFErrorExtR(tif, module, "No space for OJPEG state block");
476 0 : return (0);
477 : }
478 2 : _TIFFmemset(sp, 0, sizeof(OJPEGState));
479 2 : sp->tif = tif;
480 2 : sp->jpeg_proc = 1;
481 2 : sp->subsampling_hor = 2;
482 2 : sp->subsampling_ver = 2;
483 2 : TIFFSetField(tif, TIFFTAG_YCBCRSUBSAMPLING, 2, 2);
484 : /* tif codec methods */
485 2 : tif->tif_fixuptags = OJPEGFixupTags;
486 2 : tif->tif_setupdecode = OJPEGSetupDecode;
487 2 : tif->tif_predecode = OJPEGPreDecode;
488 2 : tif->tif_postdecode = OJPEGPostDecode;
489 2 : tif->tif_decoderow = OJPEGDecode;
490 2 : tif->tif_decodestrip = OJPEGDecode;
491 2 : tif->tif_decodetile = OJPEGDecode;
492 2 : tif->tif_setupencode = OJPEGSetupEncode;
493 2 : tif->tif_preencode = OJPEGPreEncode;
494 2 : tif->tif_postencode = OJPEGPostEncode;
495 2 : tif->tif_encoderow = OJPEGEncode;
496 2 : tif->tif_encodestrip = OJPEGEncode;
497 2 : tif->tif_encodetile = OJPEGEncode;
498 2 : tif->tif_cleanup = OJPEGCleanup;
499 2 : tif->tif_data = (uint8_t *)sp;
500 : /* tif tag methods */
501 2 : sp->vgetparent = tif->tif_tagmethods.vgetfield;
502 2 : tif->tif_tagmethods.vgetfield = OJPEGVGetField;
503 2 : sp->vsetparent = tif->tif_tagmethods.vsetfield;
504 2 : tif->tif_tagmethods.vsetfield = OJPEGVSetField;
505 2 : sp->printdir = tif->tif_tagmethods.printdir;
506 2 : tif->tif_tagmethods.printdir = OJPEGPrintDir;
507 : /* Some OJPEG files don't have strip or tile offsets or bytecounts tags.
508 : Some others do, but have totally meaningless or corrupt values
509 : in these tags. In these cases, the JpegInterchangeFormat stream is
510 : reliable. In any case, this decoder reads the compressed data itself,
511 : from the most reliable locations, and we need to notify encapsulating
512 : LibTiff not to read raw strips or tiles for us. */
513 2 : tif->tif_flags |= TIFF_NOREADRAW;
514 2 : return (1);
515 : }
516 :
517 94 : static int OJPEGVGetField(TIFF *tif, uint32_t tag, va_list ap)
518 : {
519 94 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
520 94 : switch (tag)
521 : {
522 0 : case TIFFTAG_JPEGIFOFFSET:
523 0 : *va_arg(ap, uint64_t *) = (uint64_t)sp->jpeg_interchange_format;
524 0 : break;
525 0 : case TIFFTAG_JPEGIFBYTECOUNT:
526 0 : *va_arg(ap, uint64_t *) =
527 0 : (uint64_t)sp->jpeg_interchange_format_length;
528 0 : break;
529 8 : case TIFFTAG_YCBCRSUBSAMPLING:
530 8 : if (sp->subsamplingcorrect_done == 0)
531 2 : OJPEGSubsamplingCorrect(tif);
532 8 : *va_arg(ap, uint16_t *) = (uint16_t)sp->subsampling_hor;
533 8 : *va_arg(ap, uint16_t *) = (uint16_t)sp->subsampling_ver;
534 8 : break;
535 0 : case TIFFTAG_JPEGQTABLES:
536 0 : *va_arg(ap, uint32_t *) = (uint32_t)sp->qtable_offset_count;
537 0 : *va_arg(ap, const void **) = (const void *)sp->qtable_offset;
538 0 : break;
539 0 : case TIFFTAG_JPEGDCTABLES:
540 0 : *va_arg(ap, uint32_t *) = (uint32_t)sp->dctable_offset_count;
541 0 : *va_arg(ap, const void **) = (const void *)sp->dctable_offset;
542 0 : break;
543 0 : case TIFFTAG_JPEGACTABLES:
544 0 : *va_arg(ap, uint32_t *) = (uint32_t)sp->actable_offset_count;
545 0 : *va_arg(ap, const void **) = (const void *)sp->actable_offset;
546 0 : break;
547 0 : case TIFFTAG_JPEGPROC:
548 0 : *va_arg(ap, uint16_t *) = (uint16_t)sp->jpeg_proc;
549 0 : break;
550 0 : case TIFFTAG_JPEGRESTARTINTERVAL:
551 0 : *va_arg(ap, uint16_t *) = sp->restart_interval;
552 0 : break;
553 86 : default:
554 86 : return (*sp->vgetparent)(tif, tag, ap);
555 : }
556 8 : return (1);
557 : }
558 :
559 34 : static int OJPEGVSetField(TIFF *tif, uint32_t tag, va_list ap)
560 : {
561 : static const char module[] = "OJPEGVSetField";
562 34 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
563 : uint32_t ma;
564 : uint64_t *mb;
565 : uint32_t n;
566 : const TIFFField *fip;
567 :
568 34 : switch (tag)
569 : {
570 0 : case TIFFTAG_JPEGIFOFFSET:
571 0 : sp->jpeg_interchange_format = (uint64_t)va_arg(ap, uint64_t);
572 0 : break;
573 0 : case TIFFTAG_JPEGIFBYTECOUNT:
574 0 : sp->jpeg_interchange_format_length = (uint64_t)va_arg(ap, uint64_t);
575 0 : break;
576 2 : case TIFFTAG_YCBCRSUBSAMPLING:
577 2 : sp->subsampling_tag = 1;
578 2 : sp->subsampling_hor = (uint8_t)va_arg(ap, uint16_vap);
579 2 : sp->subsampling_ver = (uint8_t)va_arg(ap, uint16_vap);
580 2 : tif->tif_dir.td_ycbcrsubsampling[0] = sp->subsampling_hor;
581 2 : tif->tif_dir.td_ycbcrsubsampling[1] = sp->subsampling_ver;
582 2 : break;
583 2 : case TIFFTAG_JPEGQTABLES:
584 2 : ma = (uint32_t)va_arg(ap, uint32_t);
585 2 : if (ma != 0)
586 : {
587 2 : if (ma > 3)
588 : {
589 0 : TIFFErrorExtR(tif, module,
590 : "JpegQTables tag has incorrect count");
591 0 : return (0);
592 : }
593 2 : sp->qtable_offset_count = (uint8_t)ma;
594 2 : mb = (uint64_t *)va_arg(ap, uint64_t *);
595 8 : for (n = 0; n < ma; n++)
596 6 : sp->qtable_offset[n] = mb[n];
597 : }
598 2 : break;
599 2 : case TIFFTAG_JPEGDCTABLES:
600 2 : ma = (uint32_t)va_arg(ap, uint32_t);
601 2 : if (ma != 0)
602 : {
603 2 : if (ma > 3)
604 : {
605 0 : TIFFErrorExtR(tif, module,
606 : "JpegDcTables tag has incorrect count");
607 0 : return (0);
608 : }
609 2 : sp->dctable_offset_count = (uint8_t)ma;
610 2 : mb = (uint64_t *)va_arg(ap, uint64_t *);
611 8 : for (n = 0; n < ma; n++)
612 6 : sp->dctable_offset[n] = mb[n];
613 : }
614 2 : break;
615 2 : case TIFFTAG_JPEGACTABLES:
616 2 : ma = (uint32_t)va_arg(ap, uint32_t);
617 2 : if (ma != 0)
618 : {
619 2 : if (ma > 3)
620 : {
621 0 : TIFFErrorExtR(tif, module,
622 : "JpegAcTables tag has incorrect count");
623 0 : return (0);
624 : }
625 2 : sp->actable_offset_count = (uint8_t)ma;
626 2 : mb = (uint64_t *)va_arg(ap, uint64_t *);
627 8 : for (n = 0; n < ma; n++)
628 6 : sp->actable_offset[n] = mb[n];
629 : }
630 2 : break;
631 2 : case TIFFTAG_JPEGPROC:
632 2 : sp->jpeg_proc = (uint8_t)va_arg(ap, uint16_vap);
633 2 : break;
634 0 : case TIFFTAG_JPEGRESTARTINTERVAL:
635 0 : sp->restart_interval = (uint16_t)va_arg(ap, uint16_vap);
636 0 : break;
637 24 : default:
638 24 : return (*sp->vsetparent)(tif, tag, ap);
639 : }
640 10 : fip = TIFFFieldWithTag(tif, tag);
641 10 : if (fip == NULL) /* shouldn't happen */
642 0 : return (0);
643 10 : TIFFSetFieldBit(tif, fip->field_bit);
644 10 : tif->tif_flags |= TIFF_DIRTYDIRECT;
645 10 : return (1);
646 : }
647 :
648 0 : static void OJPEGPrintDir(TIFF *tif, FILE *fd, long flags)
649 : {
650 0 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
651 : uint8_t m;
652 : (void)flags;
653 0 : assert(sp != NULL);
654 0 : if (TIFFFieldSet(tif, FIELD_OJPEG_JPEGINTERCHANGEFORMAT))
655 0 : fprintf(fd, " JpegInterchangeFormat: %" PRIu64 "\n",
656 0 : (uint64_t)sp->jpeg_interchange_format);
657 0 : if (TIFFFieldSet(tif, FIELD_OJPEG_JPEGINTERCHANGEFORMATLENGTH))
658 0 : fprintf(fd, " JpegInterchangeFormatLength: %" PRIu64 "\n",
659 0 : (uint64_t)sp->jpeg_interchange_format_length);
660 0 : if (TIFFFieldSet(tif, FIELD_OJPEG_JPEGQTABLES))
661 : {
662 0 : fprintf(fd, " JpegQTables:");
663 0 : for (m = 0; m < sp->qtable_offset_count; m++)
664 0 : fprintf(fd, " %" PRIu64, (uint64_t)sp->qtable_offset[m]);
665 0 : fprintf(fd, "\n");
666 : }
667 0 : if (TIFFFieldSet(tif, FIELD_OJPEG_JPEGDCTABLES))
668 : {
669 0 : fprintf(fd, " JpegDcTables:");
670 0 : for (m = 0; m < sp->dctable_offset_count; m++)
671 0 : fprintf(fd, " %" PRIu64, (uint64_t)sp->dctable_offset[m]);
672 0 : fprintf(fd, "\n");
673 : }
674 0 : if (TIFFFieldSet(tif, FIELD_OJPEG_JPEGACTABLES))
675 : {
676 0 : fprintf(fd, " JpegAcTables:");
677 0 : for (m = 0; m < sp->actable_offset_count; m++)
678 0 : fprintf(fd, " %" PRIu64, (uint64_t)sp->actable_offset[m]);
679 0 : fprintf(fd, "\n");
680 : }
681 0 : if (TIFFFieldSet(tif, FIELD_OJPEG_JPEGPROC))
682 0 : fprintf(fd, " JpegProc: %" PRIu8 "\n", sp->jpeg_proc);
683 0 : if (TIFFFieldSet(tif, FIELD_OJPEG_JPEGRESTARTINTERVAL))
684 0 : fprintf(fd, " JpegRestartInterval: %" PRIu16 "\n",
685 0 : sp->restart_interval);
686 0 : if (sp->printdir)
687 0 : (*sp->printdir)(tif, fd, flags);
688 0 : }
689 :
690 2 : static int OJPEGFixupTags(TIFF *tif)
691 : {
692 : (void)tif;
693 2 : return (1);
694 : }
695 :
696 2 : static int OJPEGSetupDecode(TIFF *tif)
697 : {
698 : static const char module[] = "OJPEGSetupDecode";
699 2 : TIFFWarningExtR(tif, module,
700 : "Deprecated and troublesome old-style JPEG compression "
701 : "mode, please convert to new-style JPEG compression and "
702 : "notify vendor of writing software");
703 2 : return (1);
704 : }
705 :
706 2 : static int OJPEGPreDecode(TIFF *tif, uint16_t s)
707 : {
708 2 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
709 : uint32_t m;
710 2 : if (sp->subsamplingcorrect_done == 0)
711 0 : OJPEGSubsamplingCorrect(tif);
712 2 : if (sp->readheader_done == 0)
713 : {
714 2 : if (OJPEGReadHeaderInfo(tif) == 0)
715 1 : return (0);
716 : }
717 1 : if (sp->sos_end[s].log == 0)
718 : {
719 0 : if (OJPEGReadSecondarySos(tif, s) == 0)
720 0 : return (0);
721 : }
722 1 : if (isTiled(tif))
723 1 : m = tif->tif_dir.td_curtile;
724 : else
725 0 : m = tif->tif_dir.td_curstrip;
726 1 : if ((sp->writeheader_done != 0) &&
727 0 : ((sp->write_cursample != s) || (sp->write_curstrile > m)))
728 : {
729 0 : if (sp->libjpeg_session_active != 0)
730 0 : OJPEGLibjpegSessionAbort(tif);
731 0 : sp->writeheader_done = 0;
732 : }
733 1 : if (sp->writeheader_done == 0)
734 : {
735 1 : sp->plane_sample_offset = (uint8_t)s;
736 1 : sp->write_cursample = s;
737 1 : sp->write_curstrile = s * tif->tif_dir.td_stripsperimage;
738 1 : if ((sp->in_buffer_file_pos_log == 0) ||
739 0 : (sp->in_buffer_file_pos - sp->in_buffer_togo !=
740 0 : sp->sos_end[s].in_buffer_file_pos))
741 : {
742 1 : sp->in_buffer_source = sp->sos_end[s].in_buffer_source;
743 1 : sp->in_buffer_next_strile = sp->sos_end[s].in_buffer_next_strile;
744 1 : sp->in_buffer_file_pos = sp->sos_end[s].in_buffer_file_pos;
745 1 : sp->in_buffer_file_pos_log = 0;
746 1 : sp->in_buffer_file_togo = sp->sos_end[s].in_buffer_file_togo;
747 1 : sp->in_buffer_togo = 0;
748 1 : sp->in_buffer_cur = 0;
749 : }
750 1 : if (OJPEGWriteHeaderInfo(tif) == 0)
751 0 : return (0);
752 : }
753 :
754 1 : sp->subsampling_convert_state = 0;
755 :
756 1 : while (sp->write_curstrile < m)
757 : {
758 0 : if (sp->libjpeg_jpeg_query_style == 0)
759 : {
760 0 : if (OJPEGPreDecodeSkipRaw(tif) == 0)
761 0 : return (0);
762 : }
763 : else
764 : {
765 0 : if (OJPEGPreDecodeSkipScanlines(tif) == 0)
766 0 : return (0);
767 : }
768 0 : sp->write_curstrile++;
769 : }
770 1 : sp->decoder_ok = 1;
771 1 : return (1);
772 : }
773 :
774 0 : static int OJPEGPreDecodeSkipRaw(TIFF *tif)
775 : {
776 0 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
777 : uint32_t m;
778 0 : m = sp->lines_per_strile;
779 0 : if (sp->subsampling_convert_state != 0)
780 : {
781 0 : if (sp->subsampling_convert_clines - sp->subsampling_convert_state >= m)
782 : {
783 0 : sp->subsampling_convert_state += m;
784 0 : if (sp->subsampling_convert_state == sp->subsampling_convert_clines)
785 0 : sp->subsampling_convert_state = 0;
786 0 : return (1);
787 : }
788 0 : m -= sp->subsampling_convert_clines - sp->subsampling_convert_state;
789 0 : sp->subsampling_convert_state = 0;
790 0 : sp->error_in_raw_data_decoding = 0;
791 : }
792 0 : while (m >= sp->subsampling_convert_clines)
793 : {
794 0 : if (jpeg_read_raw_data_encap(sp, &(sp->libjpeg_jpeg_decompress_struct),
795 0 : sp->subsampling_convert_ycbcrimage,
796 0 : (uint32_t)sp->subsampling_ver * 8) == 0)
797 0 : return (0);
798 0 : m -= sp->subsampling_convert_clines;
799 : }
800 0 : if (m > 0)
801 : {
802 0 : if (jpeg_read_raw_data_encap(sp, &(sp->libjpeg_jpeg_decompress_struct),
803 0 : sp->subsampling_convert_ycbcrimage,
804 0 : (uint32_t)sp->subsampling_ver * 8) == 0)
805 0 : return (0);
806 0 : sp->subsampling_convert_state = m;
807 : }
808 0 : return (1);
809 : }
810 :
811 0 : static int OJPEGPreDecodeSkipScanlines(TIFF *tif)
812 : {
813 : static const char module[] = "OJPEGPreDecodeSkipScanlines";
814 0 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
815 : uint32_t m;
816 0 : if (sp->skip_buffer == NULL)
817 : {
818 0 : sp->skip_buffer = (uint8_t *)_TIFFmallocExt(tif, sp->bytes_per_line);
819 0 : if (sp->skip_buffer == NULL)
820 : {
821 0 : TIFFErrorExtR(tif, module, "Out of memory");
822 0 : return (0);
823 : }
824 : }
825 0 : for (m = 0; m < sp->lines_per_strile; m++)
826 : {
827 0 : if (jpeg_read_scanlines_encap(sp, &(sp->libjpeg_jpeg_decompress_struct),
828 0 : &sp->skip_buffer, 1) == 0)
829 0 : return (0);
830 : }
831 0 : return (1);
832 : }
833 :
834 1 : static int OJPEGDecode(TIFF *tif, uint8_t *buf, tmsize_t cc, uint16_t s)
835 : {
836 : static const char module[] = "OJPEGDecode";
837 1 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
838 : (void)s;
839 1 : if (!sp->decoder_ok)
840 : {
841 0 : memset(buf, 0, (size_t)cc);
842 0 : TIFFErrorExtR(tif, module,
843 : "Cannot decode: decoder not correctly initialized");
844 0 : return 0;
845 : }
846 1 : if (sp->libjpeg_session_active == 0)
847 : {
848 0 : memset(buf, 0, (size_t)cc);
849 : /* This should normally not happen, except that it does when */
850 : /* using TIFFReadScanline() which calls OJPEGPostDecode() for */
851 : /* each scanline, which assumes that a whole strile was read */
852 : /* and may thus incorrectly consider it has read the whole image,
853 : * causing */
854 : /* OJPEGLibjpegSessionAbort() to be called prematurely. */
855 : /* Triggered by https://gitlab.com/libtiff/libtiff/-/issues/337 */
856 0 : TIFFErrorExtR(tif, module,
857 : "Cannot decode: libjpeg_session_active == 0");
858 0 : return 0;
859 : }
860 1 : if (sp->error_in_raw_data_decoding)
861 : {
862 0 : memset(buf, 0, (size_t)cc);
863 0 : return 0;
864 : }
865 1 : if (sp->libjpeg_jpeg_query_style == 0)
866 : {
867 1 : if (OJPEGDecodeRaw(tif, buf, cc) == 0)
868 : {
869 0 : memset(buf, 0, (size_t)cc);
870 0 : return (0);
871 : }
872 : }
873 : else
874 : {
875 0 : if (OJPEGDecodeScanlines(tif, buf, cc) == 0)
876 : {
877 0 : memset(buf, 0, (size_t)cc);
878 0 : return (0);
879 : }
880 : }
881 1 : return (1);
882 : }
883 :
884 1 : static int OJPEGDecodeRaw(TIFF *tif, uint8_t *buf, tmsize_t cc)
885 : {
886 : static const char module[] = "OJPEGDecodeRaw";
887 1 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
888 : uint8_t *m;
889 : tmsize_t n;
890 : uint8_t *oy;
891 : uint8_t *ocb;
892 : uint8_t *ocr;
893 : uint8_t *p;
894 : uint32_t q;
895 : uint8_t *r;
896 : uint8_t sx, sy;
897 1 : if (cc % sp->bytes_per_line != 0)
898 : {
899 0 : TIFFErrorExtR(tif, module, "Fractional scanline not read");
900 0 : return (0);
901 : }
902 1 : assert(cc > 0);
903 1 : m = buf;
904 1 : n = cc;
905 : do
906 : {
907 112 : if (sp->subsampling_convert_state == 0)
908 : {
909 14 : if (jpeg_read_raw_data_encap(
910 : sp, &(sp->libjpeg_jpeg_decompress_struct),
911 14 : sp->subsampling_convert_ycbcrimage,
912 14 : (uint32_t)sp->subsampling_ver * 8) == 0)
913 : {
914 0 : sp->error_in_raw_data_decoding = 1;
915 0 : return (0);
916 : }
917 : }
918 112 : oy = sp->subsampling_convert_ybuf +
919 112 : sp->subsampling_convert_state * sp->subsampling_ver *
920 112 : sp->subsampling_convert_ylinelen;
921 112 : ocb = sp->subsampling_convert_cbbuf +
922 112 : sp->subsampling_convert_state * sp->subsampling_convert_clinelen;
923 112 : ocr = sp->subsampling_convert_crbuf +
924 112 : sp->subsampling_convert_state * sp->subsampling_convert_clinelen;
925 112 : p = m;
926 13552 : for (q = 0; q < sp->subsampling_convert_clinelenout; q++)
927 : {
928 13440 : r = oy;
929 40320 : for (sy = 0; sy < sp->subsampling_ver; sy++)
930 : {
931 80640 : for (sx = 0; sx < sp->subsampling_hor; sx++)
932 53760 : *p++ = *r++;
933 26880 : r += sp->subsampling_convert_ylinelen - sp->subsampling_hor;
934 : }
935 13440 : oy += sp->subsampling_hor;
936 13440 : *p++ = *ocb++;
937 13440 : *p++ = *ocr++;
938 : }
939 112 : sp->subsampling_convert_state++;
940 112 : if (sp->subsampling_convert_state == sp->subsampling_convert_clines)
941 14 : sp->subsampling_convert_state = 0;
942 112 : m += sp->bytes_per_line;
943 112 : n -= sp->bytes_per_line;
944 112 : } while (n > 0);
945 1 : return (1);
946 : }
947 :
948 0 : static int OJPEGDecodeScanlines(TIFF *tif, uint8_t *buf, tmsize_t cc)
949 : {
950 : static const char module[] = "OJPEGDecodeScanlines";
951 0 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
952 : uint8_t *m;
953 : tmsize_t n;
954 0 : if (cc % sp->bytes_per_line != 0)
955 : {
956 0 : TIFFErrorExtR(tif, module, "Fractional scanline not read");
957 0 : return (0);
958 : }
959 0 : assert(cc > 0);
960 0 : m = buf;
961 0 : n = cc;
962 : do
963 : {
964 0 : if (jpeg_read_scanlines_encap(sp, &(sp->libjpeg_jpeg_decompress_struct),
965 : &m, 1) == 0)
966 0 : return (0);
967 0 : m += sp->bytes_per_line;
968 0 : n -= sp->bytes_per_line;
969 0 : } while (n > 0);
970 0 : return (1);
971 : }
972 :
973 0 : static void OJPEGPostDecode(TIFF *tif, uint8_t *buf, tmsize_t cc)
974 : {
975 0 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
976 : (void)buf;
977 : (void)cc;
978 : /* This function somehow incorrectly assumes that a whole strile was read,
979 : */
980 : /* which is not true when TIFFReadScanline() is called, */
981 : /* and may thus incorrectly consider it has read the whole image, causing */
982 : /* OJPEGLibjpegSessionAbort() to be called prematurely. */
983 : /* So this logic should be fixed to take into account cc, or disable */
984 : /* the scan line reading interface. */
985 : /* Triggered by https://gitlab.com/libtiff/libtiff/-/issues/337 */
986 0 : sp->write_curstrile++;
987 0 : if (sp->write_curstrile % tif->tif_dir.td_stripsperimage == 0)
988 : {
989 0 : assert(sp->libjpeg_session_active != 0);
990 0 : OJPEGLibjpegSessionAbort(tif);
991 0 : sp->writeheader_done = 0;
992 : }
993 0 : }
994 :
995 0 : static int OJPEGSetupEncode(TIFF *tif)
996 : {
997 : static const char module[] = "OJPEGSetupEncode";
998 0 : TIFFErrorExtR(
999 : tif, module,
1000 : "OJPEG encoding not supported; use new-style JPEG compression instead");
1001 0 : return (0);
1002 : }
1003 :
1004 0 : static int OJPEGPreEncode(TIFF *tif, uint16_t s)
1005 : {
1006 : static const char module[] = "OJPEGPreEncode";
1007 : (void)s;
1008 0 : TIFFErrorExtR(
1009 : tif, module,
1010 : "OJPEG encoding not supported; use new-style JPEG compression instead");
1011 0 : return (0);
1012 : }
1013 :
1014 0 : static int OJPEGEncode(TIFF *tif, uint8_t *buf, tmsize_t cc, uint16_t s)
1015 : {
1016 : static const char module[] = "OJPEGEncode";
1017 : (void)buf;
1018 : (void)cc;
1019 : (void)s;
1020 0 : TIFFErrorExtR(
1021 : tif, module,
1022 : "OJPEG encoding not supported; use new-style JPEG compression instead");
1023 0 : return (0);
1024 : }
1025 :
1026 0 : static int OJPEGPostEncode(TIFF *tif)
1027 : {
1028 : static const char module[] = "OJPEGPostEncode";
1029 0 : TIFFErrorExtR(
1030 : tif, module,
1031 : "OJPEG encoding not supported; use new-style JPEG compression instead");
1032 0 : return (0);
1033 : }
1034 :
1035 2 : static void OJPEGCleanup(TIFF *tif)
1036 : {
1037 2 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
1038 2 : if (sp != 0)
1039 : {
1040 2 : tif->tif_tagmethods.vgetfield = sp->vgetparent;
1041 2 : tif->tif_tagmethods.vsetfield = sp->vsetparent;
1042 2 : tif->tif_tagmethods.printdir = sp->printdir;
1043 2 : if (sp->qtable[0] != 0)
1044 1 : _TIFFfreeExt(tif, sp->qtable[0]);
1045 2 : if (sp->qtable[1] != 0)
1046 1 : _TIFFfreeExt(tif, sp->qtable[1]);
1047 2 : if (sp->qtable[2] != 0)
1048 1 : _TIFFfreeExt(tif, sp->qtable[2]);
1049 2 : if (sp->qtable[3] != 0)
1050 0 : _TIFFfreeExt(tif, sp->qtable[3]);
1051 2 : if (sp->dctable[0] != 0)
1052 1 : _TIFFfreeExt(tif, sp->dctable[0]);
1053 2 : if (sp->dctable[1] != 0)
1054 1 : _TIFFfreeExt(tif, sp->dctable[1]);
1055 2 : if (sp->dctable[2] != 0)
1056 1 : _TIFFfreeExt(tif, sp->dctable[2]);
1057 2 : if (sp->dctable[3] != 0)
1058 0 : _TIFFfreeExt(tif, sp->dctable[3]);
1059 2 : if (sp->actable[0] != 0)
1060 1 : _TIFFfreeExt(tif, sp->actable[0]);
1061 2 : if (sp->actable[1] != 0)
1062 1 : _TIFFfreeExt(tif, sp->actable[1]);
1063 2 : if (sp->actable[2] != 0)
1064 1 : _TIFFfreeExt(tif, sp->actable[2]);
1065 2 : if (sp->actable[3] != 0)
1066 0 : _TIFFfreeExt(tif, sp->actable[3]);
1067 2 : if (sp->libjpeg_session_active != 0)
1068 1 : OJPEGLibjpegSessionAbort(tif);
1069 2 : if (sp->subsampling_convert_ycbcrbuf != 0)
1070 1 : _TIFFfreeExt(tif, sp->subsampling_convert_ycbcrbuf);
1071 2 : if (sp->subsampling_convert_ycbcrimage != 0)
1072 1 : _TIFFfreeExt(tif, sp->subsampling_convert_ycbcrimage);
1073 2 : if (sp->skip_buffer != 0)
1074 0 : _TIFFfreeExt(tif, sp->skip_buffer);
1075 2 : _TIFFfreeExt(tif, sp);
1076 2 : tif->tif_data = NULL;
1077 2 : _TIFFSetDefaultCompressionState(tif);
1078 : }
1079 2 : }
1080 :
1081 2 : static void OJPEGSubsamplingCorrect(TIFF *tif)
1082 : {
1083 : static const char module[] = "OJPEGSubsamplingCorrect";
1084 2 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
1085 : uint8_t mh;
1086 : uint8_t mv;
1087 :
1088 2 : assert(sp->subsamplingcorrect_done == 0);
1089 2 : if ((tif->tif_dir.td_samplesperpixel != 3) ||
1090 2 : ((tif->tif_dir.td_photometric != PHOTOMETRIC_YCBCR) &&
1091 0 : (tif->tif_dir.td_photometric != PHOTOMETRIC_ITULAB)))
1092 : {
1093 0 : if (sp->subsampling_tag != 0)
1094 0 : TIFFWarningExtR(tif, module,
1095 : "Subsampling tag not appropriate for this "
1096 : "Photometric and/or SamplesPerPixel");
1097 0 : sp->subsampling_hor = 1;
1098 0 : sp->subsampling_ver = 1;
1099 0 : sp->subsampling_force_desubsampling_inside_decompression = 0;
1100 : }
1101 : else
1102 : {
1103 2 : sp->subsamplingcorrect_done = 1;
1104 2 : mh = sp->subsampling_hor;
1105 2 : mv = sp->subsampling_ver;
1106 2 : sp->subsamplingcorrect = 1;
1107 2 : OJPEGReadHeaderInfoSec(tif);
1108 2 : if (sp->subsampling_force_desubsampling_inside_decompression != 0)
1109 : {
1110 0 : sp->subsampling_hor = 1;
1111 0 : sp->subsampling_ver = 1;
1112 : }
1113 2 : sp->subsamplingcorrect = 0;
1114 2 : if (((sp->subsampling_hor != mh) || (sp->subsampling_ver != mv)) &&
1115 0 : (sp->subsampling_force_desubsampling_inside_decompression == 0))
1116 : {
1117 0 : if (sp->subsampling_tag == 0)
1118 0 : TIFFWarningExtR(
1119 : tif, module,
1120 : "Subsampling tag is not set, yet subsampling inside JPEG "
1121 : "data [%" PRIu8 ",%" PRIu8
1122 : "] does not match default values [2,2]; assuming "
1123 : "subsampling inside JPEG data is correct",
1124 0 : sp->subsampling_hor, sp->subsampling_ver);
1125 : else
1126 0 : TIFFWarningExtR(
1127 : tif, module,
1128 : "Subsampling inside JPEG data [%" PRIu8 ",%" PRIu8
1129 : "] does not match subsampling tag values [%" PRIu8
1130 : ",%" PRIu8
1131 : "]; assuming subsampling inside JPEG data is correct",
1132 0 : sp->subsampling_hor, sp->subsampling_ver, mh, mv);
1133 : }
1134 2 : if (sp->subsampling_force_desubsampling_inside_decompression != 0)
1135 : {
1136 0 : if (sp->subsampling_tag == 0)
1137 0 : TIFFWarningExtR(
1138 : tif, module,
1139 : "Subsampling tag is not set, yet subsampling inside JPEG "
1140 : "data does not match default values [2,2] (nor any other "
1141 : "values allowed in TIFF); assuming subsampling inside JPEG "
1142 : "data is correct and desubsampling inside JPEG "
1143 : "decompression");
1144 : else
1145 0 : TIFFWarningExtR(
1146 : tif, module,
1147 : "Subsampling inside JPEG data does not match subsampling "
1148 : "tag values [%" PRIu8 ",%" PRIu8
1149 : "] (nor any other values allowed in TIFF); assuming "
1150 : "subsampling inside JPEG data is correct and desubsampling "
1151 : "inside JPEG decompression",
1152 : mh, mv);
1153 : }
1154 2 : if (sp->subsampling_force_desubsampling_inside_decompression == 0)
1155 : {
1156 2 : if (sp->subsampling_hor < sp->subsampling_ver)
1157 0 : TIFFWarningExtR(tif, module,
1158 : "Subsampling values [%" PRIu8 ",%" PRIu8
1159 : "] are not allowed in TIFF",
1160 0 : sp->subsampling_hor, sp->subsampling_ver);
1161 : }
1162 : }
1163 2 : sp->subsamplingcorrect_done = 1;
1164 2 : }
1165 :
1166 2 : static int OJPEGReadHeaderInfo(TIFF *tif)
1167 : {
1168 : static const char module[] = "OJPEGReadHeaderInfo";
1169 2 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
1170 2 : assert(sp->readheader_done == 0);
1171 2 : sp->image_width = tif->tif_dir.td_imagewidth;
1172 2 : sp->image_length = tif->tif_dir.td_imagelength;
1173 2 : if (isTiled(tif))
1174 : {
1175 2 : sp->strile_width = tif->tif_dir.td_tilewidth;
1176 2 : sp->strile_length = tif->tif_dir.td_tilelength;
1177 2 : sp->strile_length_total =
1178 2 : ((sp->image_length + sp->strile_length - 1) / sp->strile_length) *
1179 2 : sp->strile_length;
1180 : }
1181 : else
1182 : {
1183 0 : sp->strile_width = sp->image_width;
1184 0 : sp->strile_length = tif->tif_dir.td_rowsperstrip;
1185 0 : if (sp->strile_length == (uint32_t)-1)
1186 0 : sp->strile_length = sp->image_length;
1187 0 : sp->strile_length_total = sp->image_length;
1188 : }
1189 2 : if (tif->tif_dir.td_samplesperpixel == 1)
1190 : {
1191 0 : sp->samples_per_pixel = 1;
1192 0 : sp->plane_sample_offset = 0;
1193 0 : sp->samples_per_pixel_per_plane = sp->samples_per_pixel;
1194 0 : sp->subsampling_hor = 1;
1195 0 : sp->subsampling_ver = 1;
1196 : }
1197 : else
1198 : {
1199 2 : if (tif->tif_dir.td_samplesperpixel != 3)
1200 : {
1201 0 : TIFFErrorExtR(tif, module,
1202 : "SamplesPerPixel %" PRIu8
1203 : " not supported for this compression scheme",
1204 0 : sp->samples_per_pixel);
1205 0 : return (0);
1206 : }
1207 2 : sp->samples_per_pixel = 3;
1208 2 : sp->plane_sample_offset = 0;
1209 2 : if (tif->tif_dir.td_planarconfig == PLANARCONFIG_CONTIG)
1210 2 : sp->samples_per_pixel_per_plane = 3;
1211 : else
1212 0 : sp->samples_per_pixel_per_plane = 1;
1213 : }
1214 2 : if (sp->strile_length < sp->image_length)
1215 : {
1216 0 : if (((sp->subsampling_hor != 1) && (sp->subsampling_hor != 2) &&
1217 0 : (sp->subsampling_hor != 4)) ||
1218 0 : ((sp->subsampling_ver != 1) && (sp->subsampling_ver != 2) &&
1219 0 : (sp->subsampling_ver != 4)))
1220 : {
1221 0 : TIFFErrorExtR(tif, module, "Invalid subsampling values");
1222 0 : return (0);
1223 : }
1224 0 : if (sp->strile_length % ((uint32_t)sp->subsampling_ver * 8) != 0)
1225 : {
1226 0 : TIFFErrorExtR(tif, module,
1227 : "Incompatible vertical subsampling and image "
1228 : "strip/tile length");
1229 0 : return (0);
1230 : }
1231 0 : sp->restart_interval =
1232 0 : (uint16_t)(((sp->strile_width + (uint32_t)sp->subsampling_hor * 8 -
1233 0 : 1) /
1234 0 : ((uint32_t)sp->subsampling_hor * 8)) *
1235 0 : (sp->strile_length /
1236 0 : ((uint32_t)sp->subsampling_ver * 8)));
1237 : }
1238 2 : if (OJPEGReadHeaderInfoSec(tif) == 0)
1239 1 : return (0);
1240 1 : sp->sos_end[0].log = 1;
1241 1 : sp->sos_end[0].in_buffer_source = sp->in_buffer_source;
1242 1 : sp->sos_end[0].in_buffer_next_strile = sp->in_buffer_next_strile;
1243 1 : sp->sos_end[0].in_buffer_file_pos =
1244 1 : sp->in_buffer_file_pos - sp->in_buffer_togo;
1245 1 : sp->sos_end[0].in_buffer_file_togo =
1246 1 : sp->in_buffer_file_togo + sp->in_buffer_togo;
1247 1 : sp->readheader_done = 1;
1248 1 : return (1);
1249 : }
1250 :
1251 0 : static int OJPEGReadSecondarySos(TIFF *tif, uint16_t s)
1252 : {
1253 0 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
1254 : uint8_t m;
1255 0 : assert(s > 0);
1256 0 : assert(s < 3);
1257 0 : assert(sp->sos_end[0].log != 0);
1258 0 : assert(sp->sos_end[s].log == 0);
1259 0 : sp->plane_sample_offset = (uint8_t)(s - 1);
1260 0 : while (sp->sos_end[sp->plane_sample_offset].log == 0)
1261 0 : sp->plane_sample_offset--;
1262 0 : sp->in_buffer_source =
1263 0 : sp->sos_end[sp->plane_sample_offset].in_buffer_source;
1264 0 : sp->in_buffer_next_strile =
1265 0 : sp->sos_end[sp->plane_sample_offset].in_buffer_next_strile;
1266 0 : sp->in_buffer_file_pos =
1267 0 : sp->sos_end[sp->plane_sample_offset].in_buffer_file_pos;
1268 0 : sp->in_buffer_file_pos_log = 0;
1269 0 : sp->in_buffer_file_togo =
1270 0 : sp->sos_end[sp->plane_sample_offset].in_buffer_file_togo;
1271 0 : sp->in_buffer_togo = 0;
1272 0 : sp->in_buffer_cur = 0;
1273 0 : while (sp->plane_sample_offset < s)
1274 : {
1275 : do
1276 : {
1277 0 : if (OJPEGReadByte(sp, &m) == 0)
1278 0 : return (0);
1279 0 : if (m == 255)
1280 : {
1281 : do
1282 : {
1283 0 : if (OJPEGReadByte(sp, &m) == 0)
1284 0 : return (0);
1285 0 : if (m != 255)
1286 0 : break;
1287 : } while (1);
1288 0 : if (m == JPEG_MARKER_SOS)
1289 0 : break;
1290 : }
1291 : } while (1);
1292 0 : sp->plane_sample_offset++;
1293 0 : if (OJPEGReadHeaderInfoSecStreamSos(tif) == 0)
1294 0 : return (0);
1295 0 : sp->sos_end[sp->plane_sample_offset].log = 1;
1296 0 : sp->sos_end[sp->plane_sample_offset].in_buffer_source =
1297 0 : sp->in_buffer_source;
1298 0 : sp->sos_end[sp->plane_sample_offset].in_buffer_next_strile =
1299 0 : sp->in_buffer_next_strile;
1300 0 : sp->sos_end[sp->plane_sample_offset].in_buffer_file_pos =
1301 0 : sp->in_buffer_file_pos - sp->in_buffer_togo;
1302 0 : sp->sos_end[sp->plane_sample_offset].in_buffer_file_togo =
1303 0 : sp->in_buffer_file_togo + sp->in_buffer_togo;
1304 : }
1305 0 : return (1);
1306 : }
1307 :
1308 1 : static int OJPEGWriteHeaderInfo(TIFF *tif)
1309 : {
1310 : static const char module[] = "OJPEGWriteHeaderInfo";
1311 1 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
1312 : uint8_t **m;
1313 : uint32_t n;
1314 : /* if a previous attempt failed, don't try again */
1315 1 : if (sp->libjpeg_session_active != 0)
1316 0 : return 0;
1317 1 : sp->out_state = ososSoi;
1318 1 : sp->restart_index = 0;
1319 1 : jpeg_std_error(&(sp->libjpeg_jpeg_error_mgr));
1320 1 : sp->libjpeg_jpeg_error_mgr.output_message =
1321 : OJPEGLibjpegJpegErrorMgrOutputMessage;
1322 1 : sp->libjpeg_jpeg_error_mgr.error_exit = OJPEGLibjpegJpegErrorMgrErrorExit;
1323 1 : sp->libjpeg_jpeg_decompress_struct.err = &(sp->libjpeg_jpeg_error_mgr);
1324 1 : sp->libjpeg_jpeg_decompress_struct.client_data = (void *)tif;
1325 1 : if (jpeg_create_decompress_encap(
1326 : sp, &(sp->libjpeg_jpeg_decompress_struct)) == 0)
1327 0 : return (0);
1328 1 : sp->libjpeg_session_active = 1;
1329 1 : sp->libjpeg_jpeg_source_mgr.bytes_in_buffer = 0;
1330 1 : sp->libjpeg_jpeg_source_mgr.init_source =
1331 : OJPEGLibjpegJpegSourceMgrInitSource;
1332 1 : sp->libjpeg_jpeg_source_mgr.fill_input_buffer =
1333 : OJPEGLibjpegJpegSourceMgrFillInputBuffer;
1334 1 : sp->libjpeg_jpeg_source_mgr.skip_input_data =
1335 : OJPEGLibjpegJpegSourceMgrSkipInputData;
1336 1 : sp->libjpeg_jpeg_source_mgr.resync_to_restart =
1337 : OJPEGLibjpegJpegSourceMgrResyncToRestart;
1338 1 : sp->libjpeg_jpeg_source_mgr.term_source =
1339 : OJPEGLibjpegJpegSourceMgrTermSource;
1340 1 : sp->libjpeg_jpeg_decompress_struct.src = &(sp->libjpeg_jpeg_source_mgr);
1341 1 : if (jpeg_read_header_encap(sp, &(sp->libjpeg_jpeg_decompress_struct), 1) ==
1342 : 0)
1343 0 : return (0);
1344 1 : if ((sp->subsampling_force_desubsampling_inside_decompression == 0) &&
1345 1 : (sp->samples_per_pixel_per_plane > 1))
1346 : {
1347 1 : sp->libjpeg_jpeg_decompress_struct.raw_data_out = 1;
1348 : #if JPEG_LIB_VERSION >= 70
1349 1 : sp->libjpeg_jpeg_decompress_struct.do_fancy_upsampling = FALSE;
1350 : #endif
1351 1 : sp->libjpeg_jpeg_query_style = 0;
1352 1 : if (sp->subsampling_convert_log == 0)
1353 : {
1354 1 : assert(sp->subsampling_convert_ycbcrbuf == 0);
1355 1 : assert(sp->subsampling_convert_ycbcrimage == 0);
1356 : /* Check for division by zero. */
1357 1 : if (sp->subsampling_hor == 0 || sp->subsampling_ver == 0)
1358 0 : return (0);
1359 : /* Check for potential overflow in subsampling_convert_ylinelen
1360 : * computation.
1361 : */
1362 1 : if (sp->strile_width >
1363 1 : UINT32_MAX - ((uint32_t)sp->subsampling_hor * 8 - 1))
1364 0 : return (0);
1365 1 : sp->subsampling_convert_ylinelen =
1366 1 : ((sp->strile_width + (uint32_t)sp->subsampling_hor * 8 - 1) /
1367 1 : ((uint32_t)sp->subsampling_hor * 8) *
1368 1 : ((uint32_t)sp->subsampling_hor * 8));
1369 1 : sp->subsampling_convert_ylines = (uint32_t)sp->subsampling_ver * 8;
1370 1 : sp->subsampling_convert_clinelen =
1371 1 : sp->subsampling_convert_ylinelen / sp->subsampling_hor;
1372 1 : sp->subsampling_convert_clines = 8;
1373 : /* Check for potential overflow in buffer length computations.
1374 : * Use 64-bit intermediates to detect uint32_t overflow in
1375 : * ylinelen * ylines, clinelen * clines, and their sum.
1376 : */
1377 : {
1378 1 : uint64_t ybuflen64 =
1379 1 : (uint64_t)sp->subsampling_convert_ylinelen *
1380 1 : sp->subsampling_convert_ylines;
1381 1 : uint64_t cbuflen64 =
1382 1 : (uint64_t)sp->subsampling_convert_clinelen *
1383 1 : sp->subsampling_convert_clines;
1384 1 : uint64_t ycbcrbuflen64 = ybuflen64 + 2 * cbuflen64;
1385 1 : if (ybuflen64 > UINT32_MAX || cbuflen64 > UINT32_MAX ||
1386 : ycbcrbuflen64 > UINT32_MAX)
1387 : {
1388 0 : TIFFErrorExtR(tif, module,
1389 : "Integer overflow in OJPEG buffer size");
1390 0 : return (0);
1391 : }
1392 1 : sp->subsampling_convert_ybuflen = (uint32_t)ybuflen64;
1393 1 : sp->subsampling_convert_cbuflen = (uint32_t)cbuflen64;
1394 1 : sp->subsampling_convert_ycbcrbuflen = (uint32_t)ycbcrbuflen64;
1395 : }
1396 : /* The calloc is not normally necessary, except in some edge/broken
1397 : * cases */
1398 : /* for example for a tiled image of height 1 with a tile height of 1
1399 : * and subsampling_hor=subsampling_ver=2 */
1400 : /* In that case, libjpeg will only fill the 8 first lines of the 16
1401 : * lines */
1402 : /* See https://bugs.chromium.org/p/oss-fuzz/issues/detail?id=16844
1403 : */
1404 : /* Even if this case is allowed (?), its handling is broken because
1405 : * OJPEGPreDecode() should also likely */
1406 : /* reset subsampling_convert_state to 0 when changing tile. */
1407 2 : sp->subsampling_convert_ycbcrbuf = (uint8_t *)_TIFFcallocExt(
1408 1 : tif, 1, sp->subsampling_convert_ycbcrbuflen);
1409 1 : if (sp->subsampling_convert_ycbcrbuf == 0)
1410 : {
1411 0 : TIFFErrorExtR(tif, module, "Out of memory");
1412 0 : return (0);
1413 : }
1414 1 : sp->subsampling_convert_ybuf = sp->subsampling_convert_ycbcrbuf;
1415 1 : sp->subsampling_convert_cbbuf =
1416 1 : sp->subsampling_convert_ybuf + sp->subsampling_convert_ybuflen;
1417 1 : sp->subsampling_convert_crbuf =
1418 1 : sp->subsampling_convert_cbbuf + sp->subsampling_convert_cbuflen;
1419 1 : sp->subsampling_convert_ycbcrimagelen =
1420 1 : 3 + sp->subsampling_convert_ylines +
1421 1 : 2 * sp->subsampling_convert_clines;
1422 2 : sp->subsampling_convert_ycbcrimage = (uint8_t **)_TIFFmallocExt(
1423 1 : tif, (tmsize_t)((size_t)sp->subsampling_convert_ycbcrimagelen *
1424 : sizeof(uint8_t *)));
1425 1 : if (sp->subsampling_convert_ycbcrimage == 0)
1426 : {
1427 0 : TIFFErrorExtR(tif, module, "Out of memory");
1428 0 : return (0);
1429 : }
1430 1 : m = sp->subsampling_convert_ycbcrimage;
1431 1 : *m++ = (uint8_t *)(sp->subsampling_convert_ycbcrimage + 3);
1432 1 : *m++ = (uint8_t *)(sp->subsampling_convert_ycbcrimage + 3 +
1433 1 : sp->subsampling_convert_ylines);
1434 1 : *m++ = (uint8_t *)(sp->subsampling_convert_ycbcrimage + 3 +
1435 1 : sp->subsampling_convert_ylines +
1436 1 : sp->subsampling_convert_clines);
1437 17 : for (n = 0; n < sp->subsampling_convert_ylines; n++)
1438 16 : *m++ = sp->subsampling_convert_ybuf +
1439 16 : n * sp->subsampling_convert_ylinelen;
1440 9 : for (n = 0; n < sp->subsampling_convert_clines; n++)
1441 8 : *m++ = sp->subsampling_convert_cbbuf +
1442 8 : n * sp->subsampling_convert_clinelen;
1443 9 : for (n = 0; n < sp->subsampling_convert_clines; n++)
1444 8 : *m++ = sp->subsampling_convert_crbuf +
1445 8 : n * sp->subsampling_convert_clinelen;
1446 1 : sp->subsampling_convert_clinelenout =
1447 2 : sp->strile_width / sp->subsampling_hor +
1448 1 : ((sp->strile_width % sp->subsampling_hor) != 0 ? 1 : 0);
1449 1 : sp->subsampling_convert_state = 0;
1450 1 : sp->error_in_raw_data_decoding = 0;
1451 :
1452 1 : const uint64_t bpl =
1453 1 : (uint64_t)sp->subsampling_convert_clinelenout *
1454 1 : ((uint64_t)sp->subsampling_ver * sp->subsampling_hor + 2);
1455 1 : if (bpl > UINT32_MAX)
1456 0 : return (0);
1457 1 : sp->bytes_per_line = (uint32_t)bpl;
1458 :
1459 1 : sp->lines_per_strile =
1460 2 : sp->strile_length / sp->subsampling_ver +
1461 1 : ((sp->strile_length % sp->subsampling_ver) != 0 ? 1 : 0);
1462 1 : sp->subsampling_convert_log = 1;
1463 : }
1464 : }
1465 : else
1466 : {
1467 0 : sp->libjpeg_jpeg_decompress_struct.jpeg_color_space = JCS_UNKNOWN;
1468 0 : sp->libjpeg_jpeg_decompress_struct.out_color_space = JCS_UNKNOWN;
1469 0 : sp->libjpeg_jpeg_query_style = 1;
1470 0 : sp->bytes_per_line =
1471 0 : _TIFFMultiply32(tif, sp->samples_per_pixel_per_plane,
1472 : sp->strile_width, "OJPEGWriteHeaderInfo");
1473 0 : if (sp->bytes_per_line == 0)
1474 0 : return (0);
1475 0 : sp->lines_per_strile = sp->strile_length;
1476 : }
1477 1 : if (jpeg_start_decompress_encap(sp,
1478 : &(sp->libjpeg_jpeg_decompress_struct)) == 0)
1479 0 : return (0);
1480 1 : if (sp->libjpeg_jpeg_decompress_struct.image_width != sp->strile_width)
1481 : {
1482 0 : TIFFErrorExtR(tif, module,
1483 : "jpeg_start_decompress() returned image_width = %u, "
1484 : "expected %" PRIu32,
1485 : sp->libjpeg_jpeg_decompress_struct.image_width,
1486 : sp->strile_width);
1487 0 : return 0;
1488 : }
1489 1 : if (sp->libjpeg_jpeg_decompress_struct.max_h_samp_factor !=
1490 1 : sp->subsampling_hor ||
1491 1 : sp->libjpeg_jpeg_decompress_struct.max_v_samp_factor !=
1492 1 : sp->subsampling_ver)
1493 : {
1494 0 : TIFFErrorExtR(tif, module,
1495 : "jpeg_start_decompress() returned max_h_samp_factor = %d "
1496 : "and max_v_samp_factor = %d, expected %" PRIu8
1497 : " and %" PRIu8,
1498 : sp->libjpeg_jpeg_decompress_struct.max_h_samp_factor,
1499 : sp->libjpeg_jpeg_decompress_struct.max_v_samp_factor,
1500 0 : sp->subsampling_hor, sp->subsampling_ver);
1501 0 : return 0;
1502 : }
1503 :
1504 1 : sp->writeheader_done = 1;
1505 1 : return (1);
1506 : }
1507 :
1508 1 : static void OJPEGLibjpegSessionAbort(TIFF *tif)
1509 : {
1510 1 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
1511 1 : assert(sp->libjpeg_session_active != 0);
1512 1 : jpeg_destroy(
1513 1 : (tiff_ojpeg_common_struct *)(&(sp->libjpeg_jpeg_decompress_struct)));
1514 1 : sp->libjpeg_session_active = 0;
1515 1 : }
1516 :
1517 4 : static int OJPEGReadHeaderInfoSec(TIFF *tif)
1518 : {
1519 : static const char module[] = "OJPEGReadHeaderInfoSec";
1520 4 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
1521 : uint8_t m;
1522 : uint16_t n;
1523 : uint8_t o;
1524 4 : if (sp->file_size == 0)
1525 2 : sp->file_size = TIFFGetFileSize(tif);
1526 4 : if (sp->jpeg_interchange_format != 0)
1527 : {
1528 0 : if (sp->jpeg_interchange_format >= sp->file_size)
1529 : {
1530 0 : sp->jpeg_interchange_format = 0;
1531 0 : sp->jpeg_interchange_format_length = 0;
1532 : }
1533 : else
1534 : {
1535 0 : if ((sp->jpeg_interchange_format_length == 0) ||
1536 0 : (sp->jpeg_interchange_format >
1537 0 : UINT64_MAX - sp->jpeg_interchange_format_length) ||
1538 0 : (sp->jpeg_interchange_format +
1539 0 : sp->jpeg_interchange_format_length >
1540 0 : sp->file_size))
1541 0 : sp->jpeg_interchange_format_length =
1542 0 : sp->file_size - sp->jpeg_interchange_format;
1543 : }
1544 : }
1545 4 : sp->in_buffer_source = osibsNotSetYet;
1546 4 : sp->in_buffer_next_strile = 0;
1547 4 : sp->in_buffer_strile_count = tif->tif_dir.td_nstrips;
1548 4 : sp->in_buffer_file_togo = 0;
1549 4 : sp->in_buffer_togo = 0;
1550 : do
1551 : {
1552 4 : if (OJPEGReadBytePeek(sp, &m) == 0)
1553 2 : return (0);
1554 2 : if (m != 255)
1555 2 : break;
1556 0 : OJPEGReadByteAdvance(sp);
1557 : do
1558 : {
1559 0 : if (OJPEGReadByte(sp, &m) == 0)
1560 0 : return (0);
1561 0 : } while (m == 255);
1562 0 : switch (m)
1563 : {
1564 0 : case JPEG_MARKER_SOI:
1565 : /* this type of marker has no data, and should be skipped */
1566 0 : break;
1567 0 : case JPEG_MARKER_COM:
1568 : case JPEG_MARKER_APP0:
1569 : case JPEG_MARKER_APP0 + 1:
1570 : case JPEG_MARKER_APP0 + 2:
1571 : case JPEG_MARKER_APP0 + 3:
1572 : case JPEG_MARKER_APP0 + 4:
1573 : case JPEG_MARKER_APP0 + 5:
1574 : case JPEG_MARKER_APP0 + 6:
1575 : case JPEG_MARKER_APP0 + 7:
1576 : case JPEG_MARKER_APP0 + 8:
1577 : case JPEG_MARKER_APP0 + 9:
1578 : case JPEG_MARKER_APP0 + 10:
1579 : case JPEG_MARKER_APP0 + 11:
1580 : case JPEG_MARKER_APP0 + 12:
1581 : case JPEG_MARKER_APP0 + 13:
1582 : case JPEG_MARKER_APP0 + 14:
1583 : case JPEG_MARKER_APP0 + 15:
1584 : /* this type of marker has data, but it has no use to us (and no
1585 : * place here) and should be skipped */
1586 0 : if (OJPEGReadWord(sp, &n) == 0)
1587 0 : return (0);
1588 0 : if (n < 2)
1589 : {
1590 0 : if (sp->subsamplingcorrect == 0)
1591 0 : TIFFErrorExtR(tif, module, "Corrupt JPEG data");
1592 0 : return (0);
1593 : }
1594 0 : if (n > 2)
1595 0 : OJPEGReadSkip(sp, (uint16_t)(n - 2));
1596 0 : break;
1597 0 : case JPEG_MARKER_DRI:
1598 0 : if (OJPEGReadHeaderInfoSecStreamDri(tif) == 0)
1599 0 : return (0);
1600 0 : break;
1601 0 : case JPEG_MARKER_DQT:
1602 0 : if (OJPEGReadHeaderInfoSecStreamDqt(tif) == 0)
1603 0 : return (0);
1604 0 : break;
1605 0 : case JPEG_MARKER_DHT:
1606 0 : if (OJPEGReadHeaderInfoSecStreamDht(tif) == 0)
1607 0 : return (0);
1608 0 : break;
1609 0 : case JPEG_MARKER_SOF0:
1610 : case JPEG_MARKER_SOF1:
1611 : case JPEG_MARKER_SOF3:
1612 0 : if (OJPEGReadHeaderInfoSecStreamSof(tif, m) == 0)
1613 0 : return (0);
1614 0 : if (sp->subsamplingcorrect != 0)
1615 0 : return (1);
1616 0 : break;
1617 0 : case JPEG_MARKER_SOS:
1618 0 : if (sp->subsamplingcorrect != 0)
1619 0 : return (1);
1620 0 : assert(sp->plane_sample_offset == 0);
1621 0 : if (OJPEGReadHeaderInfoSecStreamSos(tif) == 0)
1622 0 : return (0);
1623 0 : break;
1624 0 : default:
1625 0 : TIFFErrorExtR(tif, module,
1626 : "Unknown marker type %" PRIu8 " in JPEG data", m);
1627 0 : return (0);
1628 : }
1629 0 : } while (m != JPEG_MARKER_SOS);
1630 2 : if (sp->subsamplingcorrect)
1631 1 : return (1);
1632 1 : if (sp->sof_log == 0)
1633 : {
1634 1 : if (OJPEGReadHeaderInfoSecTablesQTable(tif) == 0)
1635 0 : return (0);
1636 1 : sp->sof_marker_id = JPEG_MARKER_SOF0;
1637 4 : for (o = 0; o < sp->samples_per_pixel; o++)
1638 3 : sp->sof_c[o] = (uint8_t)o;
1639 1 : sp->sof_hv[0] =
1640 1 : (uint8_t)((sp->subsampling_hor << 4) | sp->subsampling_ver);
1641 3 : for (o = 1; o < sp->samples_per_pixel; o++)
1642 2 : sp->sof_hv[o] = 17;
1643 1 : sp->sof_x = sp->strile_width;
1644 1 : sp->sof_y = sp->strile_length_total;
1645 1 : sp->sof_log = 1;
1646 1 : if (OJPEGReadHeaderInfoSecTablesDcTable(tif) == 0)
1647 0 : return (0);
1648 1 : if (OJPEGReadHeaderInfoSecTablesAcTable(tif) == 0)
1649 0 : return (0);
1650 3 : for (o = 1; o < sp->samples_per_pixel; o++)
1651 2 : sp->sos_cs[o] = o;
1652 : }
1653 1 : return (1);
1654 : }
1655 :
1656 0 : static int OJPEGReadHeaderInfoSecStreamDri(TIFF *tif)
1657 : {
1658 : /* This could easily cause trouble in some cases... but no such cases have
1659 : occurred so far */
1660 : static const char module[] = "OJPEGReadHeaderInfoSecStreamDri";
1661 0 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
1662 : uint16_t m;
1663 0 : if (OJPEGReadWord(sp, &m) == 0)
1664 0 : return (0);
1665 0 : if (m != 4)
1666 : {
1667 0 : TIFFErrorExtR(tif, module, "Corrupt DRI marker in JPEG data");
1668 0 : return (0);
1669 : }
1670 0 : if (OJPEGReadWord(sp, &m) == 0)
1671 0 : return (0);
1672 0 : sp->restart_interval = m;
1673 0 : return (1);
1674 : }
1675 :
1676 0 : static int OJPEGReadHeaderInfoSecStreamDqt(TIFF *tif)
1677 : {
1678 : /* this is a table marker, and it is to be saved as a whole for exact
1679 : * pushing on the jpeg stream later on */
1680 : static const char module[] = "OJPEGReadHeaderInfoSecStreamDqt";
1681 0 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
1682 : uint16_t m;
1683 : uint32_t na;
1684 : uint8_t *nb;
1685 : uint8_t o;
1686 0 : if (OJPEGReadWord(sp, &m) == 0)
1687 0 : return (0);
1688 0 : if (m <= 2)
1689 : {
1690 0 : if (sp->subsamplingcorrect == 0)
1691 0 : TIFFErrorExtR(tif, module, "Corrupt DQT marker in JPEG data");
1692 0 : return (0);
1693 : }
1694 0 : if (sp->subsamplingcorrect != 0)
1695 0 : OJPEGReadSkip(sp, (uint16_t)(m - 2));
1696 : else
1697 : {
1698 0 : m = (uint16_t)(m - 2);
1699 : do
1700 : {
1701 0 : if (m < 65)
1702 : {
1703 0 : TIFFErrorExtR(tif, module, "Corrupt DQT marker in JPEG data");
1704 0 : return (0);
1705 : }
1706 0 : na = sizeof(uint32_t) + 69;
1707 0 : nb = (uint8_t *)_TIFFmallocExt(tif, na);
1708 0 : if (nb == 0)
1709 : {
1710 0 : TIFFErrorExtR(tif, module, "Out of memory");
1711 0 : return (0);
1712 : }
1713 0 : *(uint32_t *)nb = na;
1714 0 : nb[sizeof(uint32_t)] = 255;
1715 0 : nb[sizeof(uint32_t) + 1] = JPEG_MARKER_DQT;
1716 0 : nb[sizeof(uint32_t) + 2] = 0;
1717 0 : nb[sizeof(uint32_t) + 3] = 67;
1718 0 : if (OJPEGReadBlock(sp, 65, &nb[sizeof(uint32_t) + 4]) == 0)
1719 : {
1720 0 : _TIFFfreeExt(tif, nb);
1721 0 : return (0);
1722 : }
1723 0 : o = nb[sizeof(uint32_t) + 4] & 15;
1724 0 : if (3 < o)
1725 : {
1726 0 : TIFFErrorExtR(tif, module, "Corrupt DQT marker in JPEG data");
1727 0 : _TIFFfreeExt(tif, nb);
1728 0 : return (0);
1729 : }
1730 0 : if (sp->qtable[o] != 0)
1731 0 : _TIFFfreeExt(tif, sp->qtable[o]);
1732 0 : sp->qtable[o] = nb;
1733 0 : m = (uint16_t)(m - 65);
1734 0 : } while (m > 0);
1735 : }
1736 0 : return (1);
1737 : }
1738 :
1739 0 : static int OJPEGReadHeaderInfoSecStreamDht(TIFF *tif)
1740 : {
1741 : /* this is a table marker, and it is to be saved as a whole for exact
1742 : * pushing on the jpeg stream later on */
1743 : /* TODO: the following assumes there is only one table in this marker... but
1744 : * i'm not quite sure that assumption is guaranteed correct */
1745 : static const char module[] = "OJPEGReadHeaderInfoSecStreamDht";
1746 0 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
1747 : uint16_t m;
1748 : uint32_t na;
1749 : uint8_t *nb;
1750 : uint8_t o;
1751 0 : if (OJPEGReadWord(sp, &m) == 0)
1752 0 : return (0);
1753 0 : if (m <= 2)
1754 : {
1755 0 : if (sp->subsamplingcorrect == 0)
1756 0 : TIFFErrorExtR(tif, module, "Corrupt DHT marker in JPEG data");
1757 0 : return (0);
1758 : }
1759 0 : if (sp->subsamplingcorrect != 0)
1760 : {
1761 0 : OJPEGReadSkip(sp, (uint16_t)(m - 2));
1762 : }
1763 : else
1764 : {
1765 0 : na = (uint32_t)(sizeof(uint32_t) + 2 + m);
1766 0 : nb = (uint8_t *)_TIFFmallocExt(tif, na);
1767 0 : if (nb == 0)
1768 : {
1769 0 : TIFFErrorExtR(tif, module, "Out of memory");
1770 0 : return (0);
1771 : }
1772 0 : *(uint32_t *)nb = na;
1773 0 : nb[sizeof(uint32_t)] = 255;
1774 0 : nb[sizeof(uint32_t) + 1] = JPEG_MARKER_DHT;
1775 0 : nb[sizeof(uint32_t) + 2] = (uint8_t)(m >> 8);
1776 0 : nb[sizeof(uint32_t) + 3] = (uint8_t)(m & 255);
1777 0 : if (OJPEGReadBlock(sp, (uint16_t)(m - 2), &nb[sizeof(uint32_t) + 4]) ==
1778 : 0)
1779 : {
1780 0 : _TIFFfreeExt(tif, nb);
1781 0 : return (0);
1782 : }
1783 0 : o = nb[sizeof(uint32_t) + 4];
1784 0 : if ((o & 240) == 0)
1785 : {
1786 0 : if (3 < o)
1787 : {
1788 0 : TIFFErrorExtR(tif, module, "Corrupt DHT marker in JPEG data");
1789 0 : _TIFFfreeExt(tif, nb);
1790 0 : return (0);
1791 : }
1792 0 : if (sp->dctable[o] != 0)
1793 0 : _TIFFfreeExt(tif, sp->dctable[o]);
1794 0 : sp->dctable[o] = nb;
1795 : }
1796 : else
1797 : {
1798 0 : if ((o & 240) != 16)
1799 : {
1800 0 : TIFFErrorExtR(tif, module, "Corrupt DHT marker in JPEG data");
1801 0 : _TIFFfreeExt(tif, nb);
1802 0 : return (0);
1803 : }
1804 0 : o &= 15;
1805 0 : if (3 < o)
1806 : {
1807 0 : TIFFErrorExtR(tif, module, "Corrupt DHT marker in JPEG data");
1808 0 : _TIFFfreeExt(tif, nb);
1809 0 : return (0);
1810 : }
1811 0 : if (sp->actable[o] != 0)
1812 0 : _TIFFfreeExt(tif, sp->actable[o]);
1813 0 : sp->actable[o] = nb;
1814 : }
1815 : }
1816 0 : return (1);
1817 : }
1818 :
1819 0 : static int OJPEGReadHeaderInfoSecStreamSof(TIFF *tif, uint8_t marker_id)
1820 : {
1821 : /* this marker needs to be checked, and part of its data needs to be saved
1822 : * for regeneration later on */
1823 : static const char module[] = "OJPEGReadHeaderInfoSecStreamSof";
1824 0 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
1825 : uint16_t m;
1826 : uint16_t n;
1827 : uint8_t o;
1828 : uint16_t p;
1829 : uint16_t q;
1830 0 : if (sp->sof_log != 0)
1831 : {
1832 0 : TIFFErrorExtR(tif, module, "Corrupt JPEG data");
1833 0 : return (0);
1834 : }
1835 0 : if (sp->subsamplingcorrect == 0)
1836 0 : sp->sof_marker_id = marker_id;
1837 : /* Lf: data length */
1838 0 : if (OJPEGReadWord(sp, &m) == 0)
1839 0 : return (0);
1840 0 : if (m < 11)
1841 : {
1842 0 : if (sp->subsamplingcorrect == 0)
1843 0 : TIFFErrorExtR(tif, module, "Corrupt SOF marker in JPEG data");
1844 0 : return (0);
1845 : }
1846 0 : m = (uint16_t)(m - 8);
1847 0 : if (m % 3 != 0)
1848 : {
1849 0 : if (sp->subsamplingcorrect == 0)
1850 0 : TIFFErrorExtR(tif, module, "Corrupt SOF marker in JPEG data");
1851 0 : return (0);
1852 : }
1853 0 : n = m / 3;
1854 0 : if (sp->subsamplingcorrect == 0)
1855 : {
1856 0 : if (n != sp->samples_per_pixel)
1857 : {
1858 0 : TIFFErrorExtR(
1859 : tif, module,
1860 : "JPEG compressed data indicates unexpected number of samples");
1861 0 : return (0);
1862 : }
1863 : }
1864 : /* P: Sample precision */
1865 0 : if (OJPEGReadByte(sp, &o) == 0)
1866 0 : return (0);
1867 0 : if (o != 8)
1868 : {
1869 0 : if (sp->subsamplingcorrect == 0)
1870 0 : TIFFErrorExtR(tif, module,
1871 : "JPEG compressed data indicates unexpected number of "
1872 : "bits per sample");
1873 0 : return (0);
1874 : }
1875 : /* Y: Number of lines, X: Number of samples per line */
1876 0 : if (sp->subsamplingcorrect)
1877 0 : OJPEGReadSkip(sp, 4);
1878 : else
1879 : {
1880 : /* Y: Number of lines */
1881 0 : if (OJPEGReadWord(sp, &p) == 0)
1882 0 : return (0);
1883 0 : if (((uint32_t)p < sp->image_length) &&
1884 0 : ((uint32_t)p < sp->strile_length_total))
1885 : {
1886 0 : TIFFErrorExtR(tif, module,
1887 : "JPEG compressed data indicates unexpected height");
1888 0 : return (0);
1889 : }
1890 0 : sp->sof_y = p;
1891 : /* X: Number of samples per line */
1892 0 : if (OJPEGReadWord(sp, &p) == 0)
1893 0 : return (0);
1894 0 : if (((uint32_t)p < sp->image_width) && ((uint32_t)p < sp->strile_width))
1895 : {
1896 0 : TIFFErrorExtR(tif, module,
1897 : "JPEG compressed data indicates unexpected width");
1898 0 : return (0);
1899 : }
1900 0 : if ((uint32_t)p > sp->strile_width)
1901 : {
1902 0 : TIFFErrorExtR(tif, module,
1903 : "JPEG compressed data image width exceeds expected "
1904 : "image width");
1905 0 : return (0);
1906 : }
1907 0 : sp->sof_x = p;
1908 : }
1909 : /* Nf: Number of image components in frame */
1910 0 : if (OJPEGReadByte(sp, &o) == 0)
1911 0 : return (0);
1912 0 : if (o != n)
1913 : {
1914 0 : if (sp->subsamplingcorrect == 0)
1915 0 : TIFFErrorExtR(tif, module, "Corrupt SOF marker in JPEG data");
1916 0 : return (0);
1917 : }
1918 : /* per component stuff */
1919 : /* TODO: double-check that flow implies that n cannot be as big as to make
1920 : * us overflow sof_c, sof_hv and sof_tq arrays */
1921 0 : for (q = 0; q < n; q++)
1922 : {
1923 : /* C: Component identifier */
1924 0 : if (OJPEGReadByte(sp, &o) == 0)
1925 0 : return (0);
1926 0 : if (sp->subsamplingcorrect == 0)
1927 0 : sp->sof_c[q] = o;
1928 : /* H: Horizontal sampling factor, and V: Vertical sampling factor */
1929 0 : if (OJPEGReadByte(sp, &o) == 0)
1930 0 : return (0);
1931 0 : if (sp->subsamplingcorrect != 0)
1932 : {
1933 0 : if (q == 0)
1934 : {
1935 0 : sp->subsampling_hor = (o >> 4);
1936 0 : sp->subsampling_ver = (o & 15);
1937 0 : if (((sp->subsampling_hor != 1) && (sp->subsampling_hor != 2) &&
1938 0 : (sp->subsampling_hor != 4)) ||
1939 0 : ((sp->subsampling_ver != 1) && (sp->subsampling_ver != 2) &&
1940 0 : (sp->subsampling_ver != 4)))
1941 0 : sp->subsampling_force_desubsampling_inside_decompression =
1942 : 1;
1943 : }
1944 : else
1945 : {
1946 0 : if (o != 17)
1947 0 : sp->subsampling_force_desubsampling_inside_decompression =
1948 : 1;
1949 : }
1950 : }
1951 : else
1952 : {
1953 0 : sp->sof_hv[q] = o;
1954 0 : if (sp->subsampling_force_desubsampling_inside_decompression == 0)
1955 : {
1956 0 : if (q == 0)
1957 : {
1958 0 : if (o != ((sp->subsampling_hor << 4) | sp->subsampling_ver))
1959 : {
1960 0 : TIFFErrorExtR(tif, module,
1961 : "JPEG compressed data indicates "
1962 : "unexpected subsampling values");
1963 0 : return (0);
1964 : }
1965 : }
1966 : else
1967 : {
1968 0 : if (o != 17)
1969 : {
1970 0 : TIFFErrorExtR(tif, module,
1971 : "JPEG compressed data indicates "
1972 : "unexpected subsampling values");
1973 0 : return (0);
1974 : }
1975 : }
1976 : }
1977 : }
1978 : /* Tq: Quantization table destination selector */
1979 0 : if (OJPEGReadByte(sp, &o) == 0)
1980 0 : return (0);
1981 0 : if (sp->subsamplingcorrect == 0)
1982 0 : sp->sof_tq[q] = o;
1983 : }
1984 0 : if (sp->subsamplingcorrect == 0)
1985 0 : sp->sof_log = 1;
1986 0 : return (1);
1987 : }
1988 :
1989 0 : static int OJPEGReadHeaderInfoSecStreamSos(TIFF *tif)
1990 : {
1991 : /* this marker needs to be checked, and part of its data needs to be saved
1992 : * for regeneration later on */
1993 : static const char module[] = "OJPEGReadHeaderInfoSecStreamSos";
1994 0 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
1995 : uint16_t m;
1996 : uint8_t n;
1997 : uint8_t o;
1998 0 : assert(sp->subsamplingcorrect == 0);
1999 0 : if (sp->sof_log == 0)
2000 : {
2001 0 : TIFFErrorExtR(tif, module, "Corrupt SOS marker in JPEG data");
2002 0 : return (0);
2003 : }
2004 : /* Ls */
2005 0 : if (OJPEGReadWord(sp, &m) == 0)
2006 0 : return (0);
2007 0 : if (m != 6 + sp->samples_per_pixel_per_plane * 2)
2008 : {
2009 0 : TIFFErrorExtR(tif, module, "Corrupt SOS marker in JPEG data");
2010 0 : return (0);
2011 : }
2012 : /* Ns */
2013 0 : if (OJPEGReadByte(sp, &n) == 0)
2014 0 : return (0);
2015 0 : if (n != sp->samples_per_pixel_per_plane)
2016 : {
2017 0 : TIFFErrorExtR(tif, module, "Corrupt SOS marker in JPEG data");
2018 0 : return (0);
2019 : }
2020 : /* Cs, Td, and Ta */
2021 0 : for (o = 0; o < sp->samples_per_pixel_per_plane; o++)
2022 : {
2023 : /* Cs */
2024 0 : if (OJPEGReadByte(sp, &n) == 0)
2025 0 : return (0);
2026 0 : sp->sos_cs[sp->plane_sample_offset + o] = n;
2027 : /* Td and Ta */
2028 0 : if (OJPEGReadByte(sp, &n) == 0)
2029 0 : return (0);
2030 0 : sp->sos_tda[sp->plane_sample_offset + o] = n;
2031 : }
2032 : /* skip Ss, Se, Ah, en Al -> no check, as per Tom Lane recommendation, as
2033 : * per LibJpeg source */
2034 0 : OJPEGReadSkip(sp, 3);
2035 0 : return (1);
2036 : }
2037 :
2038 1 : static int OJPEGReadHeaderInfoSecTablesQTable(TIFF *tif)
2039 : {
2040 : static const char module[] = "OJPEGReadHeaderInfoSecTablesQTable";
2041 1 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
2042 : uint8_t m;
2043 : uint8_t n;
2044 : uint32_t oa;
2045 : uint8_t *ob;
2046 : uint32_t p;
2047 1 : if (sp->qtable_offset[0] == 0)
2048 : {
2049 0 : TIFFErrorExtR(tif, module, "Missing JPEG tables");
2050 0 : return (0);
2051 : }
2052 1 : sp->in_buffer_file_pos_log = 0;
2053 4 : for (m = 0; m < sp->samples_per_pixel; m++)
2054 : {
2055 3 : if ((sp->qtable_offset[m] != 0) &&
2056 2 : ((m == 0) || (sp->qtable_offset[m] != sp->qtable_offset[m - 1])))
2057 : {
2058 4 : for (n = 0; n < m - 1; n++)
2059 : {
2060 1 : if (sp->qtable_offset[m] == sp->qtable_offset[n])
2061 : {
2062 0 : TIFFErrorExtR(tif, module, "Corrupt JpegQTables tag value");
2063 0 : return (0);
2064 : }
2065 : }
2066 3 : oa = sizeof(uint32_t) + 69;
2067 3 : ob = (uint8_t *)_TIFFmallocExt(tif, oa);
2068 3 : if (ob == 0)
2069 : {
2070 0 : TIFFErrorExtR(tif, module, "Out of memory");
2071 0 : return (0);
2072 : }
2073 3 : *(uint32_t *)ob = oa;
2074 3 : ob[sizeof(uint32_t)] = 255;
2075 3 : ob[sizeof(uint32_t) + 1] = JPEG_MARKER_DQT;
2076 3 : ob[sizeof(uint32_t) + 2] = 0;
2077 3 : ob[sizeof(uint32_t) + 3] = 67;
2078 3 : ob[sizeof(uint32_t) + 4] = m;
2079 3 : TIFFSeekFile(tif, sp->qtable_offset[m], SEEK_SET);
2080 3 : p = (uint32_t)TIFFReadFile(tif, &ob[sizeof(uint32_t) + 5], 64);
2081 3 : if (p != 64)
2082 : {
2083 0 : _TIFFfreeExt(tif, ob);
2084 0 : return (0);
2085 : }
2086 3 : if (sp->qtable[m] != 0)
2087 0 : _TIFFfreeExt(tif, sp->qtable[m]);
2088 3 : sp->qtable[m] = ob;
2089 3 : sp->sof_tq[m] = m;
2090 : }
2091 : else
2092 0 : sp->sof_tq[m] = sp->sof_tq[m - 1];
2093 : }
2094 1 : return (1);
2095 : }
2096 :
2097 1 : static int OJPEGReadHeaderInfoSecTablesDcTable(TIFF *tif)
2098 : {
2099 : static const char module[] = "OJPEGReadHeaderInfoSecTablesDcTable";
2100 1 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
2101 : uint8_t m;
2102 : uint8_t n;
2103 : uint8_t o[16];
2104 : uint32_t p;
2105 : uint32_t q;
2106 : uint32_t ra;
2107 : uint8_t *rb;
2108 1 : if (sp->dctable_offset[0] == 0)
2109 : {
2110 0 : TIFFErrorExtR(tif, module, "Missing JPEG tables");
2111 0 : return (0);
2112 : }
2113 1 : sp->in_buffer_file_pos_log = 0;
2114 4 : for (m = 0; m < sp->samples_per_pixel; m++)
2115 : {
2116 3 : if ((sp->dctable_offset[m] != 0) &&
2117 2 : ((m == 0) || (sp->dctable_offset[m] != sp->dctable_offset[m - 1])))
2118 : {
2119 4 : for (n = 0; n < m - 1; n++)
2120 : {
2121 1 : if (sp->dctable_offset[m] == sp->dctable_offset[n])
2122 : {
2123 0 : TIFFErrorExtR(tif, module,
2124 : "Corrupt JpegDcTables tag value");
2125 0 : return (0);
2126 : }
2127 : }
2128 3 : TIFFSeekFile(tif, sp->dctable_offset[m], SEEK_SET);
2129 3 : p = (uint32_t)TIFFReadFile(tif, o, 16);
2130 3 : if (p != 16)
2131 0 : return (0);
2132 3 : q = 0;
2133 51 : for (n = 0; n < 16; n++)
2134 48 : q += o[n];
2135 3 : ra = (uint32_t)(sizeof(uint32_t) + 21 + q);
2136 3 : rb = (uint8_t *)_TIFFmallocExt(tif, ra);
2137 3 : if (rb == 0)
2138 : {
2139 0 : TIFFErrorExtR(tif, module, "Out of memory");
2140 0 : return (0);
2141 : }
2142 3 : *(uint32_t *)rb = ra;
2143 3 : rb[sizeof(uint32_t)] = 255;
2144 3 : rb[sizeof(uint32_t) + 1] = JPEG_MARKER_DHT;
2145 3 : rb[sizeof(uint32_t) + 2] = (uint8_t)((19 + q) >> 8);
2146 3 : rb[sizeof(uint32_t) + 3] = ((19 + q) & 255);
2147 3 : rb[sizeof(uint32_t) + 4] = m;
2148 51 : for (n = 0; n < 16; n++)
2149 48 : rb[sizeof(uint32_t) + 5 + n] = o[n];
2150 3 : p = (uint32_t)TIFFReadFile(tif, &(rb[sizeof(uint32_t) + 21]), q);
2151 3 : if (p != q)
2152 : {
2153 0 : _TIFFfreeExt(tif, rb);
2154 0 : return (0);
2155 : }
2156 3 : if (sp->dctable[m] != 0)
2157 0 : _TIFFfreeExt(tif, sp->dctable[m]);
2158 3 : sp->dctable[m] = rb;
2159 3 : sp->sos_tda[m] = (uint8_t)(m << 4);
2160 : }
2161 : else
2162 0 : sp->sos_tda[m] = sp->sos_tda[m - 1];
2163 : }
2164 1 : return (1);
2165 : }
2166 :
2167 1 : static int OJPEGReadHeaderInfoSecTablesAcTable(TIFF *tif)
2168 : {
2169 : static const char module[] = "OJPEGReadHeaderInfoSecTablesAcTable";
2170 1 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
2171 : uint8_t m;
2172 : uint8_t n;
2173 : uint8_t o[16];
2174 : uint32_t p;
2175 : uint32_t q;
2176 : uint32_t ra;
2177 : uint8_t *rb;
2178 1 : if (sp->actable_offset[0] == 0)
2179 : {
2180 0 : TIFFErrorExtR(tif, module, "Missing JPEG tables");
2181 0 : return (0);
2182 : }
2183 1 : sp->in_buffer_file_pos_log = 0;
2184 4 : for (m = 0; m < sp->samples_per_pixel; m++)
2185 : {
2186 3 : if ((sp->actable_offset[m] != 0) &&
2187 2 : ((m == 0) || (sp->actable_offset[m] != sp->actable_offset[m - 1])))
2188 : {
2189 4 : for (n = 0; n < m - 1; n++)
2190 : {
2191 1 : if (sp->actable_offset[m] == sp->actable_offset[n])
2192 : {
2193 0 : TIFFErrorExtR(tif, module,
2194 : "Corrupt JpegAcTables tag value");
2195 0 : return (0);
2196 : }
2197 : }
2198 3 : TIFFSeekFile(tif, sp->actable_offset[m], SEEK_SET);
2199 3 : p = (uint32_t)TIFFReadFile(tif, o, 16);
2200 3 : if (p != 16)
2201 0 : return (0);
2202 3 : q = 0;
2203 51 : for (n = 0; n < 16; n++)
2204 48 : q += o[n];
2205 3 : ra = (uint32_t)(sizeof(uint32_t) + 21 + q);
2206 3 : rb = (uint8_t *)_TIFFmallocExt(tif, ra);
2207 3 : if (rb == 0)
2208 : {
2209 0 : TIFFErrorExtR(tif, module, "Out of memory");
2210 0 : return (0);
2211 : }
2212 3 : *(uint32_t *)rb = ra;
2213 3 : rb[sizeof(uint32_t)] = 255;
2214 3 : rb[sizeof(uint32_t) + 1] = JPEG_MARKER_DHT;
2215 3 : rb[sizeof(uint32_t) + 2] = (uint8_t)((19 + q) >> 8);
2216 3 : rb[sizeof(uint32_t) + 3] = ((19 + q) & 255);
2217 3 : rb[sizeof(uint32_t) + 4] = (16 | m);
2218 51 : for (n = 0; n < 16; n++)
2219 48 : rb[sizeof(uint32_t) + 5 + n] = o[n];
2220 3 : p = (uint32_t)TIFFReadFile(tif, &(rb[sizeof(uint32_t) + 21]), q);
2221 3 : if (p != q)
2222 : {
2223 0 : _TIFFfreeExt(tif, rb);
2224 0 : return (0);
2225 : }
2226 3 : if (sp->actable[m] != 0)
2227 0 : _TIFFfreeExt(tif, sp->actable[m]);
2228 3 : sp->actable[m] = rb;
2229 3 : sp->sos_tda[m] = (sp->sos_tda[m] | m);
2230 : }
2231 : else
2232 0 : sp->sos_tda[m] = (sp->sos_tda[m] | (sp->sos_tda[m - 1] & 15));
2233 : }
2234 1 : return (1);
2235 : }
2236 :
2237 22 : static int OJPEGReadBufferFill(OJPEGState *sp)
2238 : {
2239 : uint16_t m;
2240 : tmsize_t n;
2241 : /* TODO: double-check: when subsamplingcorrect is set, no call to
2242 : * TIFFErrorExt or TIFFWarningExt should be made in any other case, seek or
2243 : * read errors should be passed through */
2244 : do
2245 : {
2246 22 : if (sp->in_buffer_file_togo != 0)
2247 : {
2248 6 : if (sp->in_buffer_file_pos_log == 0)
2249 : {
2250 3 : TIFFSeekFile(sp->tif, sp->in_buffer_file_pos, SEEK_SET);
2251 3 : sp->in_buffer_file_pos_log = 1;
2252 : }
2253 6 : m = OJPEG_BUFFER;
2254 6 : if ((uint64_t)m > sp->in_buffer_file_togo)
2255 1 : m = (uint16_t)sp->in_buffer_file_togo;
2256 6 : n = TIFFReadFile(sp->tif, sp->in_buffer, (tmsize_t)m);
2257 6 : if (n <= 0)
2258 0 : return (0);
2259 6 : assert(n > 0);
2260 6 : assert(n <= OJPEG_BUFFER);
2261 6 : assert(n < 65536);
2262 6 : assert((uint64_t)n <= sp->in_buffer_file_togo);
2263 6 : m = (uint16_t)n;
2264 6 : sp->in_buffer_togo = m;
2265 6 : sp->in_buffer_cur = sp->in_buffer;
2266 6 : sp->in_buffer_file_togo -= m;
2267 6 : sp->in_buffer_file_pos += m;
2268 6 : break;
2269 : }
2270 16 : sp->in_buffer_file_pos_log = 0;
2271 16 : switch (sp->in_buffer_source)
2272 : {
2273 4 : case osibsNotSetYet:
2274 4 : if (sp->jpeg_interchange_format != 0)
2275 : {
2276 0 : sp->in_buffer_file_pos = sp->jpeg_interchange_format;
2277 0 : sp->in_buffer_file_togo =
2278 0 : sp->jpeg_interchange_format_length;
2279 : }
2280 4 : sp->in_buffer_source = osibsJpegInterchangeFormat;
2281 4 : break;
2282 4 : case osibsJpegInterchangeFormat:
2283 4 : sp->in_buffer_source = osibsStrile;
2284 4 : break;
2285 6 : case osibsStrile:
2286 6 : if (sp->in_buffer_next_strile == sp->in_buffer_strile_count)
2287 2 : sp->in_buffer_source = osibsEof;
2288 : else
2289 : {
2290 4 : int err = 0;
2291 4 : sp->in_buffer_file_pos = TIFFGetStrileOffsetWithErr(
2292 : sp->tif, sp->in_buffer_next_strile, &err);
2293 4 : if (err)
2294 0 : return 0;
2295 4 : if (sp->in_buffer_file_pos != 0)
2296 : {
2297 4 : uint64_t bytecount = TIFFGetStrileByteCountWithErr(
2298 : sp->tif, sp->in_buffer_next_strile, &err);
2299 4 : if (err)
2300 0 : return 0;
2301 4 : if (sp->in_buffer_file_pos >= sp->file_size)
2302 2 : sp->in_buffer_file_pos = 0;
2303 2 : else if (bytecount == 0)
2304 0 : sp->in_buffer_file_togo =
2305 0 : sp->file_size - sp->in_buffer_file_pos;
2306 : else
2307 : {
2308 2 : sp->in_buffer_file_togo = bytecount;
2309 2 : if (sp->in_buffer_file_togo == 0)
2310 0 : sp->in_buffer_file_pos = 0;
2311 2 : else if (sp->in_buffer_file_pos >
2312 2 : UINT64_MAX - sp->in_buffer_file_togo ||
2313 2 : sp->in_buffer_file_pos +
2314 2 : sp->in_buffer_file_togo >
2315 2 : sp->file_size)
2316 0 : sp->in_buffer_file_togo =
2317 0 : sp->file_size - sp->in_buffer_file_pos;
2318 : }
2319 : }
2320 4 : sp->in_buffer_next_strile++;
2321 : }
2322 6 : break;
2323 2 : case osibsEof:
2324 : default:
2325 2 : return (0);
2326 : }
2327 : } while (1);
2328 6 : return (1);
2329 : }
2330 :
2331 0 : static int OJPEGReadByte(OJPEGState *sp, uint8_t *byte)
2332 : {
2333 0 : if (sp->in_buffer_togo == 0)
2334 : {
2335 0 : if (OJPEGReadBufferFill(sp) == 0)
2336 0 : return (0);
2337 0 : assert(sp->in_buffer_togo > 0);
2338 : }
2339 0 : *byte = *(sp->in_buffer_cur);
2340 0 : sp->in_buffer_cur++;
2341 0 : sp->in_buffer_togo--;
2342 0 : return (1);
2343 : }
2344 :
2345 4 : static int OJPEGReadBytePeek(OJPEGState *sp, uint8_t *byte)
2346 : {
2347 4 : if (sp->in_buffer_togo == 0)
2348 : {
2349 4 : if (OJPEGReadBufferFill(sp) == 0)
2350 2 : return (0);
2351 2 : assert(sp->in_buffer_togo > 0);
2352 : }
2353 2 : *byte = *(sp->in_buffer_cur);
2354 2 : return (1);
2355 : }
2356 :
2357 0 : static void OJPEGReadByteAdvance(OJPEGState *sp)
2358 : {
2359 0 : assert(sp->in_buffer_togo > 0);
2360 0 : sp->in_buffer_cur++;
2361 0 : sp->in_buffer_togo--;
2362 0 : }
2363 :
2364 0 : static int OJPEGReadWord(OJPEGState *sp, uint16_t *word)
2365 : {
2366 : uint8_t m;
2367 0 : if (OJPEGReadByte(sp, &m) == 0)
2368 0 : return (0);
2369 0 : *word = (uint16_t)(m << 8);
2370 0 : if (OJPEGReadByte(sp, &m) == 0)
2371 0 : return (0);
2372 0 : *word |= m;
2373 0 : return (1);
2374 : }
2375 :
2376 0 : static int OJPEGReadBlock(OJPEGState *sp, uint16_t len, void *mem)
2377 : {
2378 : uint16_t mlen;
2379 : uint8_t *mmem;
2380 : uint16_t n;
2381 0 : assert(len > 0);
2382 0 : mlen = len;
2383 0 : mmem = (uint8_t *)mem;
2384 : do
2385 : {
2386 0 : if (sp->in_buffer_togo == 0)
2387 : {
2388 0 : if (OJPEGReadBufferFill(sp) == 0)
2389 0 : return (0);
2390 0 : assert(sp->in_buffer_togo > 0);
2391 : }
2392 0 : n = mlen;
2393 0 : if (n > sp->in_buffer_togo)
2394 0 : n = sp->in_buffer_togo;
2395 0 : _TIFFmemcpy(mmem, sp->in_buffer_cur, n);
2396 0 : sp->in_buffer_cur += n;
2397 0 : sp->in_buffer_togo = (uint16_t)(sp->in_buffer_togo - n);
2398 0 : mlen = (uint16_t)(mlen - n);
2399 0 : mmem += n;
2400 0 : } while (mlen > 0);
2401 0 : return (1);
2402 : }
2403 :
2404 0 : static void OJPEGReadSkip(OJPEGState *sp, uint16_t len)
2405 : {
2406 : uint16_t m;
2407 : uint16_t n;
2408 0 : m = len;
2409 0 : n = m;
2410 0 : if (n > sp->in_buffer_togo)
2411 0 : n = sp->in_buffer_togo;
2412 0 : sp->in_buffer_cur += n;
2413 0 : sp->in_buffer_togo = (uint16_t)(sp->in_buffer_togo - n);
2414 0 : m = (uint16_t)(m - n);
2415 0 : if (m > 0)
2416 : {
2417 0 : assert(sp->in_buffer_togo == 0);
2418 0 : n = m;
2419 0 : if ((uint64_t)n > sp->in_buffer_file_togo)
2420 0 : n = (uint16_t)sp->in_buffer_file_togo;
2421 0 : sp->in_buffer_file_pos += n;
2422 0 : sp->in_buffer_file_togo -= n;
2423 0 : sp->in_buffer_file_pos_log = 0;
2424 : /* we don't skip past jpeginterchangeformat/strile block...
2425 : * if that is asked from us, we're dealing with totally bazurk
2426 : * data anyway, and we've not seen this happening on any
2427 : * testfile, so we might as well likely cause some other
2428 : * meaningless error to be passed at some later time
2429 : */
2430 : }
2431 0 : }
2432 :
2433 17 : static int OJPEGWriteStream(TIFF *tif, void **mem, uint32_t *len)
2434 : {
2435 17 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
2436 17 : *len = 0;
2437 : do
2438 : {
2439 21 : assert(sp->out_state <= ososEoi);
2440 21 : switch (sp->out_state)
2441 : {
2442 1 : case ososSoi:
2443 1 : OJPEGWriteStreamSoi(tif, mem, len);
2444 1 : break;
2445 1 : case ososQTable0:
2446 1 : OJPEGWriteStreamQTable(tif, 0, mem, len);
2447 1 : break;
2448 1 : case ososQTable1:
2449 1 : OJPEGWriteStreamQTable(tif, 1, mem, len);
2450 1 : break;
2451 1 : case ososQTable2:
2452 1 : OJPEGWriteStreamQTable(tif, 2, mem, len);
2453 1 : break;
2454 1 : case ososQTable3:
2455 1 : OJPEGWriteStreamQTable(tif, 3, mem, len);
2456 1 : break;
2457 1 : case ososDcTable0:
2458 1 : OJPEGWriteStreamDcTable(tif, 0, mem, len);
2459 1 : break;
2460 1 : case ososDcTable1:
2461 1 : OJPEGWriteStreamDcTable(tif, 1, mem, len);
2462 1 : break;
2463 1 : case ososDcTable2:
2464 1 : OJPEGWriteStreamDcTable(tif, 2, mem, len);
2465 1 : break;
2466 1 : case ososDcTable3:
2467 1 : OJPEGWriteStreamDcTable(tif, 3, mem, len);
2468 1 : break;
2469 1 : case ososAcTable0:
2470 1 : OJPEGWriteStreamAcTable(tif, 0, mem, len);
2471 1 : break;
2472 1 : case ososAcTable1:
2473 1 : OJPEGWriteStreamAcTable(tif, 1, mem, len);
2474 1 : break;
2475 1 : case ososAcTable2:
2476 1 : OJPEGWriteStreamAcTable(tif, 2, mem, len);
2477 1 : break;
2478 1 : case ososAcTable3:
2479 1 : OJPEGWriteStreamAcTable(tif, 3, mem, len);
2480 1 : break;
2481 1 : case ososDri:
2482 1 : OJPEGWriteStreamDri(tif, mem, len);
2483 1 : break;
2484 1 : case ososSof:
2485 1 : OJPEGWriteStreamSof(tif, mem, len);
2486 1 : break;
2487 1 : case ososSos:
2488 1 : OJPEGWriteStreamSos(tif, mem, len);
2489 1 : break;
2490 4 : case ososCompressed:
2491 4 : if (OJPEGWriteStreamCompressed(tif, mem, len) == 0)
2492 0 : return (0);
2493 4 : break;
2494 0 : case ososRst:
2495 0 : OJPEGWriteStreamRst(tif, mem, len);
2496 0 : break;
2497 1 : case ososEoi:
2498 1 : OJPEGWriteStreamEoi(tif, mem, len);
2499 1 : break;
2500 0 : default:
2501 0 : break;
2502 : }
2503 21 : } while (*len == 0);
2504 17 : return (1);
2505 : }
2506 :
2507 1 : static void OJPEGWriteStreamSoi(TIFF *tif, void **mem, uint32_t *len)
2508 : {
2509 1 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
2510 : assert(OJPEG_BUFFER >= 2);
2511 1 : sp->out_buffer[0] = 255;
2512 1 : sp->out_buffer[1] = JPEG_MARKER_SOI;
2513 1 : *len = 2;
2514 1 : *mem = (void *)sp->out_buffer;
2515 1 : sp->out_state = (OJPEGStateOutState)(sp->out_state + 1);
2516 1 : }
2517 :
2518 4 : static void OJPEGWriteStreamQTable(TIFF *tif, uint8_t table_index, void **mem,
2519 : uint32_t *len)
2520 : {
2521 4 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
2522 4 : if (sp->qtable[table_index] != 0)
2523 : {
2524 3 : *mem = (void *)(sp->qtable[table_index] + sizeof(uint32_t));
2525 3 : *len = (uint32_t)(*((uint32_t *)sp->qtable[table_index]) -
2526 : sizeof(uint32_t));
2527 : }
2528 4 : sp->out_state = (OJPEGStateOutState)(sp->out_state + 1);
2529 4 : }
2530 :
2531 4 : static void OJPEGWriteStreamDcTable(TIFF *tif, uint8_t table_index, void **mem,
2532 : uint32_t *len)
2533 : {
2534 4 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
2535 4 : if (sp->dctable[table_index] != 0)
2536 : {
2537 3 : *mem = (void *)(sp->dctable[table_index] + sizeof(uint32_t));
2538 3 : *len = (uint32_t)(*((uint32_t *)sp->dctable[table_index]) -
2539 : sizeof(uint32_t));
2540 : }
2541 4 : sp->out_state = (OJPEGStateOutState)(sp->out_state + 1);
2542 4 : }
2543 :
2544 4 : static void OJPEGWriteStreamAcTable(TIFF *tif, uint8_t table_index, void **mem,
2545 : uint32_t *len)
2546 : {
2547 4 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
2548 4 : if (sp->actable[table_index] != 0)
2549 : {
2550 3 : *mem = (void *)(sp->actable[table_index] + sizeof(uint32_t));
2551 3 : *len = (uint32_t)(*((uint32_t *)sp->actable[table_index]) -
2552 : sizeof(uint32_t));
2553 : }
2554 4 : sp->out_state = (OJPEGStateOutState)(sp->out_state + 1);
2555 4 : }
2556 :
2557 1 : static void OJPEGWriteStreamDri(TIFF *tif, void **mem, uint32_t *len)
2558 : {
2559 1 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
2560 : assert(OJPEG_BUFFER >= 6);
2561 1 : if (sp->restart_interval != 0)
2562 : {
2563 0 : sp->out_buffer[0] = 255;
2564 0 : sp->out_buffer[1] = JPEG_MARKER_DRI;
2565 0 : sp->out_buffer[2] = 0;
2566 0 : sp->out_buffer[3] = 4;
2567 0 : sp->out_buffer[4] = (uint8_t)(sp->restart_interval >> 8);
2568 0 : sp->out_buffer[5] = (uint8_t)(sp->restart_interval & 255);
2569 0 : *len = 6;
2570 0 : *mem = (void *)sp->out_buffer;
2571 : }
2572 1 : sp->out_state = (OJPEGStateOutState)(sp->out_state + 1);
2573 1 : }
2574 :
2575 1 : static void OJPEGWriteStreamSof(TIFF *tif, void **mem, uint32_t *len)
2576 : {
2577 1 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
2578 : uint8_t m;
2579 1 : assert(OJPEG_BUFFER >= 2 + 8 + sp->samples_per_pixel_per_plane * 3);
2580 1 : assert(255 >= 8 + sp->samples_per_pixel_per_plane * 3);
2581 1 : sp->out_buffer[0] = 255;
2582 1 : sp->out_buffer[1] = sp->sof_marker_id;
2583 : /* Lf */
2584 1 : sp->out_buffer[2] = 0;
2585 1 : sp->out_buffer[3] = (uint8_t)(8 + sp->samples_per_pixel_per_plane * 3);
2586 : /* P */
2587 1 : sp->out_buffer[4] = 8;
2588 : /* Y */
2589 1 : sp->out_buffer[5] = (uint8_t)(sp->sof_y >> 8);
2590 1 : sp->out_buffer[6] = (uint8_t)(sp->sof_y & 255);
2591 : /* X */
2592 1 : sp->out_buffer[7] = (uint8_t)(sp->sof_x >> 8);
2593 1 : sp->out_buffer[8] = (uint8_t)(sp->sof_x & 255);
2594 : /* Nf */
2595 1 : sp->out_buffer[9] = sp->samples_per_pixel_per_plane;
2596 4 : for (m = 0; m < sp->samples_per_pixel_per_plane; m++)
2597 : {
2598 : /* C */
2599 3 : sp->out_buffer[10 + m * 3] = sp->sof_c[sp->plane_sample_offset + m];
2600 : /* H and V */
2601 3 : sp->out_buffer[10 + m * 3 + 1] =
2602 3 : sp->sof_hv[sp->plane_sample_offset + m];
2603 : /* Tq */
2604 3 : sp->out_buffer[10 + m * 3 + 2] =
2605 3 : sp->sof_tq[sp->plane_sample_offset + m];
2606 : }
2607 1 : *len = 10 + (uint32_t)sp->samples_per_pixel_per_plane * 3;
2608 1 : *mem = (void *)sp->out_buffer;
2609 1 : sp->out_state = (OJPEGStateOutState)(sp->out_state + 1);
2610 1 : }
2611 :
2612 1 : static void OJPEGWriteStreamSos(TIFF *tif, void **mem, uint32_t *len)
2613 : {
2614 1 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
2615 : uint8_t m;
2616 1 : assert(OJPEG_BUFFER >= 2 + 6 + sp->samples_per_pixel_per_plane * 2);
2617 1 : assert(255 >= 6 + sp->samples_per_pixel_per_plane * 2);
2618 1 : sp->out_buffer[0] = 255;
2619 1 : sp->out_buffer[1] = JPEG_MARKER_SOS;
2620 : /* Ls */
2621 1 : sp->out_buffer[2] = 0;
2622 1 : sp->out_buffer[3] = (uint8_t)(6 + sp->samples_per_pixel_per_plane * 2);
2623 : /* Ns */
2624 1 : sp->out_buffer[4] = sp->samples_per_pixel_per_plane;
2625 4 : for (m = 0; m < sp->samples_per_pixel_per_plane; m++)
2626 : {
2627 : /* Cs */
2628 3 : sp->out_buffer[5 + m * 2] = sp->sos_cs[sp->plane_sample_offset + m];
2629 : /* Td and Ta */
2630 3 : sp->out_buffer[5 + m * 2 + 1] =
2631 3 : sp->sos_tda[sp->plane_sample_offset + m];
2632 : }
2633 : /* Ss */
2634 1 : sp->out_buffer[5 + sp->samples_per_pixel_per_plane * 2] = 0;
2635 : /* Se */
2636 1 : sp->out_buffer[5 + sp->samples_per_pixel_per_plane * 2 + 1] = 63;
2637 : /* Ah and Al */
2638 1 : sp->out_buffer[5 + sp->samples_per_pixel_per_plane * 2 + 2] = 0;
2639 1 : *len = 8 + (uint32_t)sp->samples_per_pixel_per_plane * 2;
2640 1 : *mem = (void *)sp->out_buffer;
2641 1 : sp->out_state = (OJPEGStateOutState)(sp->out_state + 1);
2642 1 : }
2643 :
2644 4 : static int OJPEGWriteStreamCompressed(TIFF *tif, void **mem, uint32_t *len)
2645 : {
2646 4 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
2647 4 : if (sp->in_buffer_togo == 0)
2648 : {
2649 4 : if (OJPEGReadBufferFill(sp) == 0)
2650 0 : return (0);
2651 4 : assert(sp->in_buffer_togo > 0);
2652 : }
2653 4 : *len = sp->in_buffer_togo;
2654 4 : *mem = (void *)sp->in_buffer_cur;
2655 4 : sp->in_buffer_togo = 0;
2656 4 : if (sp->in_buffer_file_togo == 0)
2657 : {
2658 1 : switch (sp->in_buffer_source)
2659 : {
2660 1 : case osibsStrile:
2661 1 : if (sp->in_buffer_next_strile < sp->in_buffer_strile_count)
2662 0 : sp->out_state = ososRst;
2663 : else
2664 1 : sp->out_state = ososEoi;
2665 1 : break;
2666 0 : case osibsEof:
2667 0 : sp->out_state = ososEoi;
2668 0 : break;
2669 0 : case osibsNotSetYet:
2670 : case osibsJpegInterchangeFormat:
2671 : default:
2672 0 : break;
2673 : }
2674 3 : }
2675 4 : return (1);
2676 : }
2677 :
2678 0 : static void OJPEGWriteStreamRst(TIFF *tif, void **mem, uint32_t *len)
2679 : {
2680 0 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
2681 : assert(OJPEG_BUFFER >= 2);
2682 0 : sp->out_buffer[0] = 255;
2683 0 : sp->out_buffer[1] = (uint8_t)(JPEG_MARKER_RST0 + sp->restart_index);
2684 0 : sp->restart_index++;
2685 0 : if (sp->restart_index == 8)
2686 0 : sp->restart_index = 0;
2687 0 : *len = 2;
2688 0 : *mem = (void *)sp->out_buffer;
2689 0 : sp->out_state = ososCompressed;
2690 0 : }
2691 :
2692 1 : static void OJPEGWriteStreamEoi(TIFF *tif, void **mem, uint32_t *len)
2693 : {
2694 1 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
2695 : assert(OJPEG_BUFFER >= 2);
2696 1 : sp->out_buffer[0] = 255;
2697 1 : sp->out_buffer[1] = JPEG_MARKER_EOI;
2698 1 : *len = 2;
2699 1 : *mem = (void *)sp->out_buffer;
2700 1 : }
2701 :
2702 : #ifndef LIBJPEG_ENCAP_EXTERNAL
2703 1 : static int jpeg_create_decompress_encap(OJPEGState *sp,
2704 : tiff_ojpeg_decompress_struct *cinfo)
2705 : {
2706 1 : if (SETJMP(sp->exit_jmpbuf))
2707 0 : return 0;
2708 : else
2709 : {
2710 1 : jpeg_create_decompress(cinfo);
2711 1 : return 1;
2712 : }
2713 : }
2714 : #endif
2715 :
2716 : #ifndef LIBJPEG_ENCAP_EXTERNAL
2717 1 : static int jpeg_read_header_encap(OJPEGState *sp,
2718 : tiff_ojpeg_decompress_struct *cinfo,
2719 : uint8_t require_image)
2720 : {
2721 1 : if (SETJMP(sp->exit_jmpbuf))
2722 0 : return 0;
2723 : else
2724 : {
2725 1 : jpeg_read_header(cinfo, require_image);
2726 1 : return 1;
2727 : }
2728 : }
2729 : #endif
2730 :
2731 : #ifndef LIBJPEG_ENCAP_EXTERNAL
2732 1 : static int jpeg_start_decompress_encap(OJPEGState *sp,
2733 : tiff_ojpeg_decompress_struct *cinfo)
2734 : {
2735 1 : if (SETJMP(sp->exit_jmpbuf))
2736 0 : return 0;
2737 : else
2738 : {
2739 1 : jpeg_start_decompress(cinfo);
2740 1 : return 1;
2741 : }
2742 : }
2743 : #endif
2744 :
2745 : #ifndef LIBJPEG_ENCAP_EXTERNAL
2746 0 : static int jpeg_read_scanlines_encap(OJPEGState *sp,
2747 : tiff_ojpeg_decompress_struct *cinfo,
2748 : void *scanlines, uint32_t max_lines)
2749 : {
2750 0 : if (SETJMP(sp->exit_jmpbuf))
2751 0 : return 0;
2752 : else
2753 : {
2754 0 : jpeg_read_scanlines(cinfo, (JSAMPARRAY)scanlines, max_lines);
2755 0 : return 1;
2756 : }
2757 : }
2758 : #endif
2759 :
2760 : #ifndef LIBJPEG_ENCAP_EXTERNAL
2761 14 : static int jpeg_read_raw_data_encap(OJPEGState *sp,
2762 : tiff_ojpeg_decompress_struct *cinfo,
2763 : void *data, uint32_t max_lines)
2764 : {
2765 14 : if (SETJMP(sp->exit_jmpbuf))
2766 0 : return 0;
2767 : else
2768 : {
2769 14 : jpeg_read_raw_data(cinfo, (JSAMPIMAGE)data, max_lines);
2770 14 : return 1;
2771 : }
2772 : }
2773 : #endif
2774 :
2775 : #ifndef LIBJPEG_ENCAP_EXTERNAL
2776 0 : static void jpeg_encap_unwind(TIFF *tif)
2777 : {
2778 0 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
2779 0 : LONGJMP(sp->exit_jmpbuf, 1);
2780 : }
2781 : #endif
2782 :
2783 : static void
2784 0 : OJPEGLibjpegJpegErrorMgrOutputMessage(tiff_ojpeg_common_struct *cinfo)
2785 : {
2786 : char buffer[JMSG_LENGTH_MAX];
2787 0 : (*cinfo->err->format_message)(cinfo, buffer);
2788 0 : TIFFWarningExtR(((TIFF *)(cinfo->client_data)), "LibJpeg", "%s", buffer);
2789 0 : }
2790 :
2791 0 : static void OJPEGLibjpegJpegErrorMgrErrorExit(tiff_ojpeg_common_struct *cinfo)
2792 : {
2793 : char buffer[JMSG_LENGTH_MAX];
2794 0 : (*cinfo->err->format_message)(cinfo, buffer);
2795 0 : TIFFErrorExtR(((TIFF *)(cinfo->client_data)), "LibJpeg", "%s", buffer);
2796 0 : jpeg_encap_unwind((TIFF *)(cinfo->client_data));
2797 0 : }
2798 :
2799 : static void
2800 1 : OJPEGLibjpegJpegSourceMgrInitSource(tiff_ojpeg_decompress_struct *cinfo)
2801 : {
2802 : (void)cinfo;
2803 1 : }
2804 :
2805 : static boolean
2806 17 : OJPEGLibjpegJpegSourceMgrFillInputBuffer(tiff_ojpeg_decompress_struct *cinfo)
2807 : {
2808 17 : TIFF *tif = (TIFF *)cinfo->client_data;
2809 17 : OJPEGState *sp = (OJPEGState *)tif->tif_data;
2810 17 : void *mem = 0;
2811 17 : uint32_t len = 0U;
2812 17 : if (OJPEGWriteStream(tif, &mem, &len) == 0)
2813 : {
2814 0 : TIFFErrorExtR(tif, "LibJpeg", "Premature end of JPEG data");
2815 0 : jpeg_encap_unwind(tif);
2816 : }
2817 17 : sp->libjpeg_jpeg_source_mgr.bytes_in_buffer = len;
2818 17 : sp->libjpeg_jpeg_source_mgr.next_input_byte = (const JOCTET *)mem;
2819 17 : return (1);
2820 : }
2821 :
2822 : static void
2823 0 : OJPEGLibjpegJpegSourceMgrSkipInputData(tiff_ojpeg_decompress_struct *cinfo,
2824 : long num_bytes)
2825 : {
2826 0 : TIFF *tif = (TIFF *)cinfo->client_data;
2827 : (void)num_bytes;
2828 0 : TIFFErrorExtR(tif, "LibJpeg", "Unexpected error");
2829 0 : jpeg_encap_unwind(tif);
2830 0 : }
2831 :
2832 : #ifdef _MSC_VER
2833 : #pragma warning(push)
2834 : #pragma warning(disable : 4702) /* unreachable code */
2835 : #endif
2836 : static boolean
2837 0 : OJPEGLibjpegJpegSourceMgrResyncToRestart(tiff_ojpeg_decompress_struct *cinfo,
2838 : int desired)
2839 : {
2840 0 : TIFF *tif = (TIFF *)cinfo->client_data;
2841 : (void)desired;
2842 0 : TIFFErrorExtR(tif, "LibJpeg", "Unexpected error");
2843 0 : jpeg_encap_unwind(tif);
2844 0 : return (0);
2845 : }
2846 : #ifdef _MSC_VER
2847 : #pragma warning(pop)
2848 : #endif
2849 :
2850 : static void
2851 0 : OJPEGLibjpegJpegSourceMgrTermSource(tiff_ojpeg_decompress_struct *cinfo)
2852 : {
2853 : (void)cinfo;
2854 0 : }
2855 :
2856 : #endif
|