Main MRPT website > C++ reference for MRPT 1.9.9
jdmarker.cpp
Go to the documentation of this file.
1 /* +------------------------------------------------------------------------+
2  | Mobile Robot Programming Toolkit (MRPT) |
3  | http://www.mrpt.org/ |
4  | |
5  | Copyright (c) 2005-2017, Individual contributors, see AUTHORS file |
6  | See: http://www.mrpt.org/Authors - All rights reserved. |
7  | Released under BSD License. See details in http://www.mrpt.org/License |
8  +------------------------------------------------------------------------+ */
9 
10 #define JPEG_INTERNALS
11 #include "jinclude.h"
12 #include "mrpt_jpeglib.h"
13 
14 typedef enum { /* JPEG marker codes */
15  M_SOF0 = 0xc0,
16  M_SOF1 = 0xc1,
17  M_SOF2 = 0xc2,
18  M_SOF3 = 0xc3,
19 
20  M_SOF5 = 0xc5,
21  M_SOF6 = 0xc6,
22  M_SOF7 = 0xc7,
23 
24  M_JPG = 0xc8,
25  M_SOF9 = 0xc9,
26  M_SOF10 = 0xca,
27  M_SOF11 = 0xcb,
28 
29  M_SOF13 = 0xcd,
30  M_SOF14 = 0xce,
31  M_SOF15 = 0xcf,
32 
33  M_DHT = 0xc4,
34 
35  M_DAC = 0xcc,
36 
37  M_RST0 = 0xd0,
38  M_RST1 = 0xd1,
39  M_RST2 = 0xd2,
40  M_RST3 = 0xd3,
41  M_RST4 = 0xd4,
42  M_RST5 = 0xd5,
43  M_RST6 = 0xd6,
44  M_RST7 = 0xd7,
45 
46  M_SOI = 0xd8,
47  M_EOI = 0xd9,
48  M_SOS = 0xda,
49  M_DQT = 0xdb,
50  M_DNL = 0xdc,
51  M_DRI = 0xdd,
52  M_DHP = 0xde,
53  M_EXP = 0xdf,
54 
55  M_APP0 = 0xe0,
56  M_APP1 = 0xe1,
57  M_APP2 = 0xe2,
58  M_APP3 = 0xe3,
59  M_APP4 = 0xe4,
60  M_APP5 = 0xe5,
61  M_APP6 = 0xe6,
62  M_APP7 = 0xe7,
63  M_APP8 = 0xe8,
64  M_APP9 = 0xe9,
65  M_APP10 = 0xea,
66  M_APP11 = 0xeb,
67  M_APP12 = 0xec,
68  M_APP13 = 0xed,
69  M_APP14 = 0xee,
70  M_APP15 = 0xef,
71 
72  M_JPG0 = 0xf0,
73  M_JPG13 = 0xfd,
74  M_COM = 0xfe,
75 
76  M_TEM = 0x01,
77 
78  M_ERROR = 0x100
79 } JPEG_MARKER;
80 
81 /* Private state */
82 
83 typedef struct
84 {
85  struct jpeg_marker_reader pub; /* public fields */
86 
87  /* Application-overridable marker processing methods */
88  jpeg_marker_parser_method process_COM;
89  jpeg_marker_parser_method process_APPn[16];
90 
91  /* Limit on marker data length to save for each marker type */
92  unsigned int length_limit_COM;
93  unsigned int length_limit_APPn[16];
94 
95  /* Status of COM/APPn marker saving */
96  jpeg_saved_marker_ptr cur_marker; /* nullptr if not processing a marker */
97  unsigned int bytes_read; /* data bytes read so far in marker */
98  /* Note: cur_marker is not linked into marker_list until it's all read. */
100 
102 
103 /*
104  * Macros for fetching data from the data source module.
105  *
106  * At all times, cinfo->src->next_input_byte and ->bytes_in_buffer reflect
107  * the current restart point; we update them only when we have reached a
108  * suitable place to restart if a suspension occurs.
109  */
110 
111 /* Declare and initialize local copies of input pointer/count */
112 #define INPUT_VARS(cinfo) \
113  struct jpeg_source_mgr* datasrc = (cinfo)->src; \
114  const JOCTET* next_input_byte = datasrc->next_input_byte; \
115  size_t bytes_in_buffer = datasrc->bytes_in_buffer
116 
117 /* Unload the local copies --- do this only at a restart boundary */
118 #define INPUT_SYNC(cinfo) \
119  (datasrc->next_input_byte = next_input_byte, \
120  datasrc->bytes_in_buffer = bytes_in_buffer)
121 
122 /* Reload the local copies --- used only in MAKE_BYTE_AVAIL */
123 #define INPUT_RELOAD(cinfo) \
124  (next_input_byte = datasrc->next_input_byte, \
125  bytes_in_buffer = datasrc->bytes_in_buffer)
126 
127 /* Internal macro for INPUT_BYTE and INPUT_2BYTES: make a byte available.
128  * Note we do *not* do INPUT_SYNC before calling fill_input_buffer,
129  * but we must reload the local copies after a successful fill.
130  */
131 #define MAKE_BYTE_AVAIL(cinfo, action) \
132  if (bytes_in_buffer == 0) \
133  { \
134  if (!(*datasrc->fill_input_buffer)(cinfo)) \
135  { \
136  action; \
137  } \
138  INPUT_RELOAD(cinfo); \
139  }
140 
141 /* Read a byte into variable V.
142  * If must suspend, take the specified action (typically "return FALSE").
143  */
144 #define INPUT_BYTE(cinfo, V, action) \
145  MAKESTMT( \
146  MAKE_BYTE_AVAIL(cinfo, action); bytes_in_buffer--; \
147  V = GETJOCTET(*next_input_byte++);)
148 
149 /* As above, but read two bytes interpreted as an unsigned 16-bit integer.
150  * V should be declared unsigned int or perhaps INT32.
151  */
152 #define INPUT_2BYTES(cinfo, V, action) \
153  MAKESTMT( \
154  MAKE_BYTE_AVAIL(cinfo, action); bytes_in_buffer--; \
155  V = ((unsigned int)GETJOCTET(*next_input_byte++)) << 8; \
156  MAKE_BYTE_AVAIL(cinfo, action); bytes_in_buffer--; \
157  V += GETJOCTET(*next_input_byte++);)
158 
159 /*
160  * Routines to process JPEG markers.
161  *
162  * Entry condition: JPEG marker itself has been read and its code saved
163  * in cinfo->unread_marker; input restart point is just after the marker.
164  *
165  * Exit: if return TRUE, have read and processed any parameters, and have
166  * updated the restart point to point after the parameters.
167  * If return FALSE, was forced to suspend before reaching end of
168  * marker parameters; restart point has not been moved. Same routine
169  * will be called again after application supplies more input data.
170  *
171  * This approach to suspension assumes that all of a marker's parameters
172  * can fit into a single input bufferload. This should hold for "normal"
173  * markers. Some COM/APPn markers might have large parameter segments
174  * that might not fit. If we are simply dropping such a marker, we use
175  * skip_input_data to get past it, and thereby put the problem on the
176  * source manager's shoulders. If we are saving the marker's contents
177  * into memory, we use a slightly different convention: when forced to
178  * suspend, the marker processor updates the restart point to the end of
179  * what it's consumed (ie, the end of the buffer) before returning FALSE.
180  * On resumption, cinfo->unread_marker still contains the marker code,
181  * but the data source will point to the next chunk of marker data.
182  * The marker processor must retain internal state to deal with this.
183  *
184  * Note that we don't bother to avoid duplicate trace messages if a
185  * suspension occurs within marker parameters. Other side effects
186  * require more care.
187  */
188 
189 LOCAL(boolean)
191 /* Process an SOI marker */
192 {
193  int i;
194 
195  TRACEMS(cinfo, 1, JTRC_SOI);
196 
197  if (cinfo->marker->saw_SOI) ERREXIT(cinfo, JERR_SOI_DUPLICATE);
198 
199  /* Reset all parameters that are defined to be reset by SOI */
200 
201  for (i = 0; i < NUM_ARITH_TBLS; i++)
202  {
203  cinfo->arith_dc_L[i] = 0;
204  cinfo->arith_dc_U[i] = 1;
205  cinfo->arith_ac_K[i] = 5;
206  }
207  cinfo->restart_interval = 0;
208 
209  /* Set initial assumptions for colorspace etc */
210 
211  cinfo->jpeg_color_space = JCS_UNKNOWN;
212  cinfo->CCIR601_sampling = FALSE; /* Assume non-CCIR sampling??? */
213 
214  cinfo->saw_JFIF_marker = FALSE;
215  cinfo->JFIF_major_version = 1; /* set default JFIF APP0 values */
216  cinfo->JFIF_minor_version = 1;
217  cinfo->density_unit = 0;
218  cinfo->X_density = 1;
219  cinfo->Y_density = 1;
220  cinfo->saw_Adobe_marker = FALSE;
221  cinfo->Adobe_transform = 0;
222 
223  cinfo->marker->saw_SOI = TRUE;
224 
225  return TRUE;
226 }
227 
228 LOCAL(boolean)
229 get_sof(j_decompress_ptr cinfo, boolean is_prog, boolean is_arith)
230 /* Process a SOFn marker */
231 {
232  INT32 length;
233  int c, ci;
235  INPUT_VARS(cinfo);
236 
237  cinfo->progressive_mode = is_prog;
238  cinfo->arith_code = is_arith;
239 
240  INPUT_2BYTES(cinfo, length, return FALSE);
241 
242  INPUT_BYTE(cinfo, cinfo->data_precision, return FALSE);
243  INPUT_2BYTES(cinfo, cinfo->image_height, return FALSE);
244  INPUT_2BYTES(cinfo, cinfo->image_width, return FALSE);
245  INPUT_BYTE(cinfo, cinfo->num_components, return FALSE);
246 
247  length -= 8;
248 
249  TRACEMS4(
250  cinfo, 1, JTRC_SOF, cinfo->unread_marker, (int)cinfo->image_width,
251  (int)cinfo->image_height, cinfo->num_components);
252 
253  if (cinfo->marker->saw_SOF) ERREXIT(cinfo, JERR_SOF_DUPLICATE);
254 
255  /* We don't support files in which the image height is initially specified
256  */
257  /* as 0 and is later redefined by DNL. As long as we have to check that, */
258  /* might as well have a general sanity check. */
259  if (cinfo->image_height <= 0 || cinfo->image_width <= 0 ||
260  cinfo->num_components <= 0)
261  ERREXIT(cinfo, JERR_EMPTY_IMAGE);
262 
263  if (length != (cinfo->num_components * 3)) ERREXIT(cinfo, JERR_BAD_LENGTH);
264 
265  if (cinfo->comp_info == nullptr) /* do only once, even if suspend */
266  cinfo->comp_info = (jpeg_component_info*)(*cinfo->mem->alloc_small)(
267  (j_common_ptr)cinfo, JPOOL_IMAGE,
268  cinfo->num_components * SIZEOF(jpeg_component_info));
269 
270  for (ci = 0, compptr = cinfo->comp_info; ci < cinfo->num_components;
271  ci++, compptr++)
272  {
273  compptr->component_index = ci;
274  INPUT_BYTE(cinfo, compptr->component_id, return FALSE);
275  INPUT_BYTE(cinfo, c, return FALSE);
276  compptr->h_samp_factor = (c >> 4) & 15;
277  compptr->v_samp_factor = (c)&15;
278  INPUT_BYTE(cinfo, compptr->quant_tbl_no, return FALSE);
279 
280  TRACEMS4(
281  cinfo, 1, JTRC_SOF_COMPONENT, compptr->component_id,
284  }
285 
286  cinfo->marker->saw_SOF = TRUE;
287 
288  INPUT_SYNC(cinfo);
289  return TRUE;
290 }
291 
292 LOCAL(boolean)
294 /* Process a SOS marker */
295 {
296  INT32 length;
297  int i, ci, n, c, cc;
299  INPUT_VARS(cinfo);
300 
301  if (!cinfo->marker->saw_SOF) ERREXIT(cinfo, JERR_SOS_NO_SOF);
302 
303  INPUT_2BYTES(cinfo, length, return FALSE);
304 
305  INPUT_BYTE(cinfo, n, return FALSE); /* Number of components */
306 
307  TRACEMS1(cinfo, 1, JTRC_SOS, n);
308 
309  if (length != (n * 2 + 6) || n < 1 || n > MAX_COMPS_IN_SCAN)
310  ERREXIT(cinfo, JERR_BAD_LENGTH);
311 
312  cinfo->comps_in_scan = n;
313 
314  /* Collect the component-spec parameters */
315 
316  for (i = 0; i < n; i++)
317  {
318  INPUT_BYTE(cinfo, cc, return FALSE);
319  INPUT_BYTE(cinfo, c, return FALSE);
320 
321  for (ci = 0, compptr = cinfo->comp_info; ci < cinfo->num_components;
322  ci++, compptr++)
323  {
324  if (cc == compptr->component_id) goto id_found;
325  }
326 
327  ERREXIT1(cinfo, JERR_BAD_COMPONENT_ID, cc);
328 
329  id_found:
330 
331  cinfo->cur_comp_info[i] = compptr;
332  compptr->dc_tbl_no = (c >> 4) & 15;
333  compptr->ac_tbl_no = (c)&15;
334 
335  TRACEMS3(
336  cinfo, 1, JTRC_SOS_COMPONENT, cc, compptr->dc_tbl_no,
337  compptr->ac_tbl_no);
338  }
339 
340  /* Collect the additional scan parameters Ss, Se, Ah/Al. */
341  INPUT_BYTE(cinfo, c, return FALSE);
342  cinfo->Ss = c;
343  INPUT_BYTE(cinfo, c, return FALSE);
344  cinfo->Se = c;
345  INPUT_BYTE(cinfo, c, return FALSE);
346  cinfo->Ah = (c >> 4) & 15;
347  cinfo->Al = (c)&15;
348 
349  TRACEMS4(
350  cinfo, 1, JTRC_SOS_PARAMS, cinfo->Ss, cinfo->Se, cinfo->Ah, cinfo->Al);
351 
352  /* Prepare to scan data & restart markers */
353  cinfo->marker->next_restart_num = 0;
354 
355  /* Count another SOS marker */
356  cinfo->input_scan_number++;
357 
358  INPUT_SYNC(cinfo);
359  return TRUE;
360 }
361 
362 #ifdef D_ARITH_CODING_SUPPORTED
363 
364 LOCAL(boolean)
366 /* Process a DAC marker */
367 {
368  INT32 length;
369  int index, val;
370  INPUT_VARS(cinfo);
371 
372  INPUT_2BYTES(cinfo, length, return FALSE);
373  length -= 2;
374 
375  while (length > 0)
376  {
377  INPUT_BYTE(cinfo, index, return FALSE);
378  INPUT_BYTE(cinfo, val, return FALSE);
379 
380  length -= 2;
381 
382  TRACEMS2(cinfo, 1, JTRC_DAC, index, val);
383 
385  ERREXIT1(cinfo, JERR_DAC_INDEX, index);
386 
387  if (index >= NUM_ARITH_TBLS)
388  { /* define AC table */
389  cinfo->arith_ac_K[index - NUM_ARITH_TBLS] = (UINT8)val;
390  }
391  else
392  { /* define DC table */
393  cinfo->arith_dc_L[index] = (UINT8)(val & 0x0F);
394  cinfo->arith_dc_U[index] = (UINT8)(val >> 4);
395  if (cinfo->arith_dc_L[index] > cinfo->arith_dc_U[index])
396  ERREXIT1(cinfo, JERR_DAC_VALUE, val);
397  }
398  }
399 
400  if (length != 0) ERREXIT(cinfo, JERR_BAD_LENGTH);
401 
402  INPUT_SYNC(cinfo);
403  return TRUE;
404 }
405 
406 #else /* ! D_ARITH_CODING_SUPPORTED */
407 
408 #define get_dac(cinfo) skip_variable(cinfo)
409 
410 #endif /* D_ARITH_CODING_SUPPORTED */
411 
412 LOCAL(boolean)
414 /* Process a DHT marker */
415 {
416  INT32 length;
417  UINT8 bits[17];
418  UINT8 huffval[256];
419  int i, index, count;
420  JHUFF_TBL** htblptr;
421  INPUT_VARS(cinfo);
422 
423  INPUT_2BYTES(cinfo, length, return FALSE);
424  length -= 2;
425 
426  while (length > 16)
427  {
428  INPUT_BYTE(cinfo, index, return FALSE);
429 
430  TRACEMS1(cinfo, 1, JTRC_DHT, index);
431 
432  bits[0] = 0;
433  count = 0;
434  for (i = 1; i <= 16; i++)
435  {
436  INPUT_BYTE(cinfo, bits[i], return FALSE);
437  count += bits[i];
438  }
439 
440  length -= 1 + 16;
441 
442  TRACEMS8(
443  cinfo, 2, JTRC_HUFFBITS, bits[1], bits[2], bits[3], bits[4],
444  bits[5], bits[6], bits[7], bits[8]);
445  TRACEMS8(
446  cinfo, 2, JTRC_HUFFBITS, bits[9], bits[10], bits[11], bits[12],
447  bits[13], bits[14], bits[15], bits[16]);
448 
449  /* Here we just do minimal validation of the counts to avoid walking
450  * off the end of our table space. jdhuff.c will check more carefully.
451  */
452  if (count > 256 || ((INT32)count) > length)
453  ERREXIT(cinfo, JERR_BAD_HUFF_TABLE);
454 
455  for (i = 0; i < count; i++) INPUT_BYTE(cinfo, huffval[i], return FALSE);
456 
457  length -= count;
458 
459  if (index & 0x10)
460  { /* AC table definition */
461  index -= 0x10;
462  htblptr = &cinfo->ac_huff_tbl_ptrs[index];
463  }
464  else
465  { /* DC table definition */
466  htblptr = &cinfo->dc_huff_tbl_ptrs[index];
467  }
468 
470  ERREXIT1(cinfo, JERR_DHT_INDEX, index);
471 
472  if (*htblptr == nullptr)
473  *htblptr = jpeg_alloc_huff_table((j_common_ptr)cinfo);
474 
475  MEMCOPY((*htblptr)->bits, bits, SIZEOF((*htblptr)->bits));
476  MEMCOPY((*htblptr)->huffval, huffval, SIZEOF((*htblptr)->huffval));
477  }
478 
479  if (length != 0) ERREXIT(cinfo, JERR_BAD_LENGTH);
480 
481  INPUT_SYNC(cinfo);
482  return TRUE;
483 }
484 
485 LOCAL(boolean)
487 /* Process a DQT marker */
488 {
489  INT32 length;
490  int n, i, prec;
491  unsigned int tmp;
492  JQUANT_TBL* quant_ptr;
493  INPUT_VARS(cinfo);
494 
495  INPUT_2BYTES(cinfo, length, return FALSE);
496  length -= 2;
497 
498  while (length > 0)
499  {
500  INPUT_BYTE(cinfo, n, return FALSE);
501  prec = n >> 4;
502  n &= 0x0F;
503 
504  TRACEMS2(cinfo, 1, JTRC_DQT, n, prec);
505 
506  if (n >= NUM_QUANT_TBLS) ERREXIT1(cinfo, JERR_DQT_INDEX, n);
507 
508  if (cinfo->quant_tbl_ptrs[n] == nullptr)
509  cinfo->quant_tbl_ptrs[n] =
511  quant_ptr = cinfo->quant_tbl_ptrs[n];
512 
513  for (i = 0; i < DCTSIZE2; i++)
514  {
515  if (prec)
516  INPUT_2BYTES(cinfo, tmp, return FALSE);
517  else
518  INPUT_BYTE(cinfo, tmp, return FALSE);
519  /* We convert the zigzag-order table to natural array order. */
520  quant_ptr->quantval[jpeg_natural_order[i]] = (UINT16)tmp;
521  }
522 
523  if (cinfo->err->trace_level >= 2)
524  {
525  for (i = 0; i < DCTSIZE2; i += 8)
526  {
527  TRACEMS8(
528  cinfo, 2, JTRC_QUANTVALS, quant_ptr->quantval[i],
529  quant_ptr->quantval[i + 1], quant_ptr->quantval[i + 2],
530  quant_ptr->quantval[i + 3], quant_ptr->quantval[i + 4],
531  quant_ptr->quantval[i + 5], quant_ptr->quantval[i + 6],
532  quant_ptr->quantval[i + 7]);
533  }
534  }
535 
536  length -= DCTSIZE2 + 1;
537  if (prec) length -= DCTSIZE2;
538  }
539 
540  if (length != 0) ERREXIT(cinfo, JERR_BAD_LENGTH);
541 
542  INPUT_SYNC(cinfo);
543  return TRUE;
544 }
545 
546 LOCAL(boolean)
548 /* Process a DRI marker */
549 {
550  INT32 length;
551  unsigned int tmp;
552  INPUT_VARS(cinfo);
553 
554  INPUT_2BYTES(cinfo, length, return FALSE);
555 
556  if (length != 4) ERREXIT(cinfo, JERR_BAD_LENGTH);
557 
558  INPUT_2BYTES(cinfo, tmp, return FALSE);
559 
560  TRACEMS1(cinfo, 1, JTRC_DRI, tmp);
561 
562  cinfo->restart_interval = tmp;
563 
564  INPUT_SYNC(cinfo);
565  return TRUE;
566 }
567 
568 /*
569  * Routines for processing APPn and COM markers.
570  * These are either saved in memory or discarded, per application request.
571  * APP0 and APP14 are specially checked to see if they are
572  * JFIF and Adobe markers, respectively.
573  */
574 
575 #define APP0_DATA_LEN 14 /* Length of interesting data in APP0 */
576 #define APP14_DATA_LEN 12 /* Length of interesting data in APP14 */
577 #define APPN_DATA_LEN 14 /* Must be the largest of the above!! */
578 
579 LOCAL(void)
581  j_decompress_ptr cinfo, JOCTET FAR* data, unsigned int datalen,
582  INT32 remaining)
583 /* Examine first few bytes from an APP0.
584  * Take appropriate action if it is a JFIF marker.
585  * datalen is # of bytes at data[], remaining is length of rest of marker data.
586  */
587 {
588  INT32 totallen = (INT32)datalen + remaining;
589 
590  if (datalen >= APP0_DATA_LEN && GETJOCTET(data[0]) == 0x4A &&
591  GETJOCTET(data[1]) == 0x46 && GETJOCTET(data[2]) == 0x49 &&
592  GETJOCTET(data[3]) == 0x46 && GETJOCTET(data[4]) == 0)
593  {
594  /* Found JFIF APP0 marker: save info */
595  cinfo->saw_JFIF_marker = TRUE;
596  cinfo->JFIF_major_version = GETJOCTET(data[5]);
597  cinfo->JFIF_minor_version = GETJOCTET(data[6]);
598  cinfo->density_unit = GETJOCTET(data[7]);
599  cinfo->X_density = (GETJOCTET(data[8]) << 8) + GETJOCTET(data[9]);
600  cinfo->Y_density = (GETJOCTET(data[10]) << 8) + GETJOCTET(data[11]);
601  /* Check version.
602  * Major version must be 1, anything else signals an incompatible
603  * change.
604  * (We used to treat this as an error, but now it's a nonfatal warning,
605  * because some bozo at Hijaak couldn't read the spec.)
606  * Minor version should be 0..2, but process anyway if newer.
607  */
608  if (cinfo->JFIF_major_version != 1)
609  WARNMS2(
610  cinfo, JWRN_JFIF_MAJOR, cinfo->JFIF_major_version,
611  cinfo->JFIF_minor_version);
612  /* Generate trace messages */
613  TRACEMS5(
614  cinfo, 1, JTRC_JFIF, cinfo->JFIF_major_version,
615  cinfo->JFIF_minor_version, cinfo->X_density, cinfo->Y_density,
616  cinfo->density_unit);
617  /* Validate thumbnail dimensions and issue appropriate messages */
618  if (GETJOCTET(data[12]) | GETJOCTET(data[13]))
619  TRACEMS2(
620  cinfo, 1, JTRC_JFIF_THUMBNAIL, GETJOCTET(data[12]),
621  GETJOCTET(data[13]));
622  totallen -= APP0_DATA_LEN;
623  if (totallen != ((INT32)GETJOCTET(data[12]) *
624  (INT32)GETJOCTET(data[13]) * (INT32)3))
625  TRACEMS1(cinfo, 1, JTRC_JFIF_BADTHUMBNAILSIZE, (int)totallen);
626  }
627  else if (
628  datalen >= 6 && GETJOCTET(data[0]) == 0x4A &&
629  GETJOCTET(data[1]) == 0x46 && GETJOCTET(data[2]) == 0x58 &&
630  GETJOCTET(data[3]) == 0x58 && GETJOCTET(data[4]) == 0)
631  {
632  /* Found JFIF "JFXX" extension APP0 marker */
633  /* The library doesn't actually do anything with these,
634  * but we try to produce a helpful trace message.
635  */
636  switch (GETJOCTET(data[5]))
637  {
638  case 0x10:
639  TRACEMS1(cinfo, 1, JTRC_THUMB_JPEG, (int)totallen);
640  break;
641  case 0x11:
642  TRACEMS1(cinfo, 1, JTRC_THUMB_PALETTE, (int)totallen);
643  break;
644  case 0x13:
645  TRACEMS1(cinfo, 1, JTRC_THUMB_RGB, (int)totallen);
646  break;
647  default:
648  TRACEMS2(
649  cinfo, 1, JTRC_JFIF_EXTENSION, GETJOCTET(data[5]),
650  (int)totallen);
651  break;
652  }
653  }
654  else
655  {
656  /* Start of APP0 does not match "JFIF" or "JFXX", or too short */
657  TRACEMS1(cinfo, 1, JTRC_APP0, (int)totallen);
658  }
659 }
660 
661 LOCAL(void)
663  j_decompress_ptr cinfo, JOCTET FAR* data, unsigned int datalen,
664  INT32 remaining)
665 /* Examine first few bytes from an APP14.
666  * Take appropriate action if it is an Adobe marker.
667  * datalen is # of bytes at data[], remaining is length of rest of marker data.
668  */
669 {
670  unsigned int version, flags0, flags1, transform;
671 
672  if (datalen >= APP14_DATA_LEN && GETJOCTET(data[0]) == 0x41 &&
673  GETJOCTET(data[1]) == 0x64 && GETJOCTET(data[2]) == 0x6F &&
674  GETJOCTET(data[3]) == 0x62 && GETJOCTET(data[4]) == 0x65)
675  {
676  /* Found Adobe APP14 marker */
677  version = (GETJOCTET(data[5]) << 8) + GETJOCTET(data[6]);
678  flags0 = (GETJOCTET(data[7]) << 8) + GETJOCTET(data[8]);
679  flags1 = (GETJOCTET(data[9]) << 8) + GETJOCTET(data[10]);
680  transform = GETJOCTET(data[11]);
681  TRACEMS4(cinfo, 1, JTRC_ADOBE, version, flags0, flags1, transform);
682  cinfo->saw_Adobe_marker = TRUE;
683  cinfo->Adobe_transform = (UINT8)transform;
684  }
685  else
686  {
687  /* Start of APP14 does not match "Adobe", or too short */
688  TRACEMS1(cinfo, 1, JTRC_APP14, (int)(datalen + remaining));
689  }
690 }
691 
692 METHODDEF(boolean)
694 /* Process an APP0 or APP14 marker without saving it */
695 {
696  INT32 length;
698  unsigned int i, numtoread;
699  INPUT_VARS(cinfo);
700 
701  INPUT_2BYTES(cinfo, length, return FALSE);
702  length -= 2;
703 
704  /* get the interesting part of the marker data */
705  if (length >= APPN_DATA_LEN)
706  numtoread = APPN_DATA_LEN;
707  else if (length > 0)
708  numtoread = (unsigned int)length;
709  else
710  numtoread = 0;
711  for (i = 0; i < numtoread; i++) INPUT_BYTE(cinfo, b[i], return FALSE);
712  length -= numtoread;
713 
714  /* process it */
715  switch (cinfo->unread_marker)
716  {
717  case M_APP0:
718  examine_app0(cinfo, (JOCTET FAR*)b, numtoread, length);
719  break;
720  case M_APP14:
721  examine_app14(cinfo, (JOCTET FAR*)b, numtoread, length);
722  break;
723  default:
724  /* can't get here unless jpeg_save_markers chooses wrong processor
725  */
726  ERREXIT1(cinfo, JERR_UNKNOWN_MARKER, cinfo->unread_marker);
727  break;
728  }
729 
730  /* skip any remaining data -- could be lots */
731  INPUT_SYNC(cinfo);
732  if (length > 0) (*cinfo->src->skip_input_data)(cinfo, (long)length);
733 
734  return TRUE;
735 }
736 
737 #ifdef SAVE_MARKERS_SUPPORTED
738 
739 METHODDEF(boolean)
741 /* Save an APPn or COM marker into the marker list */
742 {
743  my_marker_ptr marker = (my_marker_ptr)cinfo->marker;
744  jpeg_saved_marker_ptr cur_marker = marker->cur_marker;
745  unsigned int bytes_read, data_length;
746  JOCTET FAR* data;
747  INT32 length = 0;
748  INPUT_VARS(cinfo);
749 
750  if (cur_marker == nullptr)
751  {
752  /* begin reading a marker */
753  INPUT_2BYTES(cinfo, length, return FALSE);
754  length -= 2;
755  if (length >= 0)
756  { /* watch out for bogus length word */
757  /* figure out how much we want to save */
758  unsigned int limit;
759  if (cinfo->unread_marker == (int)M_COM)
760  limit = marker->length_limit_COM;
761  else
762  limit =
763  marker
764  ->length_limit_APPn[cinfo->unread_marker - (int)M_APP0];
765  if ((unsigned int)length < limit) limit = (unsigned int)length;
766  /* allocate and initialize the marker item */
767  cur_marker = (jpeg_saved_marker_ptr)(*cinfo->mem->alloc_large)(
768  (j_common_ptr)cinfo, JPOOL_IMAGE,
769  SIZEOF(struct jpeg_marker_struct) + limit);
770  cur_marker->next = nullptr;
771  cur_marker->marker = (UINT8)cinfo->unread_marker;
772  cur_marker->original_length = (unsigned int)length;
773  cur_marker->data_length = limit;
774  /* data area is just beyond the jpeg_marker_struct */
775  data = cur_marker->data = (JOCTET FAR*)(cur_marker + 1);
776  marker->cur_marker = cur_marker;
777  marker->bytes_read = 0;
778  bytes_read = 0;
779  data_length = limit;
780  }
781  else
782  {
783  /* deal with bogus length word */
784  bytes_read = data_length = 0;
785  data = nullptr;
786  }
787  }
788  else
789  {
790  /* resume reading a marker */
791  bytes_read = marker->bytes_read;
792  data_length = cur_marker->data_length;
793  data = cur_marker->data + bytes_read;
794  }
795 
796  while (bytes_read < data_length)
797  {
798  INPUT_SYNC(cinfo); /* move the restart point to here */
799  marker->bytes_read = bytes_read;
800  /* If there's not at least one byte in buffer, suspend */
801  MAKE_BYTE_AVAIL(cinfo, return FALSE);
802  /* Copy bytes with reasonable rapidity */
803  while (bytes_read < data_length && bytes_in_buffer > 0)
804  {
805  *data++ = *next_input_byte++;
806  bytes_in_buffer--;
807  bytes_read++;
808  }
809  }
810 
811  /* Done reading what we want to read */
812  if (cur_marker != nullptr)
813  { /* will be nullptr if bogus length word */
814  /* Add new marker to end of list */
815  if (cinfo->marker_list == nullptr)
816  {
817  cinfo->marker_list = cur_marker;
818  }
819  else
820  {
821  jpeg_saved_marker_ptr prev = cinfo->marker_list;
822  while (prev->next != nullptr) prev = prev->next;
823  prev->next = cur_marker;
824  }
825  /* Reset pointer & calc remaining data length */
826  data = cur_marker->data;
827  length = cur_marker->original_length - data_length;
828  }
829  /* Reset to initial state for next marker */
830  marker->cur_marker = nullptr;
831 
832  /* Process the marker if interesting; else just make a generic trace msg */
833  switch (cinfo->unread_marker)
834  {
835  case M_APP0:
836  examine_app0(cinfo, data, data_length, length);
837  break;
838  case M_APP14:
839  examine_app14(cinfo, data, data_length, length);
840  break;
841  default:
842  TRACEMS2(
843  cinfo, 1, JTRC_MISC_MARKER, cinfo->unread_marker,
844  (int)(data_length + length));
845  break;
846  }
847 
848  /* skip any remaining data -- could be lots */
849  INPUT_SYNC(cinfo); /* do before skip_input_data */
850  if (length > 0) (*cinfo->src->skip_input_data)(cinfo, (long)length);
851 
852  return TRUE;
853 }
854 
855 #endif /* SAVE_MARKERS_SUPPORTED */
856 
857 METHODDEF(boolean)
859 /* Skip over an unknown or uninteresting variable-length marker */
860 {
861  INT32 length;
862  INPUT_VARS(cinfo);
863 
864  INPUT_2BYTES(cinfo, length, return FALSE);
865  length -= 2;
866 
867  TRACEMS2(cinfo, 1, JTRC_MISC_MARKER, cinfo->unread_marker, (int)length);
868 
869  INPUT_SYNC(cinfo); /* do before skip_input_data */
870  if (length > 0) (*cinfo->src->skip_input_data)(cinfo, (long)length);
871 
872  return TRUE;
873 }
874 
875 /*
876  * Find the next JPEG marker, save it in cinfo->unread_marker.
877  * Returns FALSE if had to suspend before reaching a marker;
878  * in that case cinfo->unread_marker is unchanged.
879  *
880  * Note that the result might not be a valid marker code,
881  * but it will never be 0 or FF.
882  */
883 
884 LOCAL(boolean)
886 {
887  int c;
888  INPUT_VARS(cinfo);
889 
890  for (;;)
891  {
892  INPUT_BYTE(cinfo, c, return FALSE);
893  /* Skip any non-FF bytes.
894  * This may look a bit inefficient, but it will not occur in a valid
895  * file.
896  * We sync after each discarded byte so that a suspending data source
897  * can discard the byte from its buffer.
898  */
899  while (c != 0xFF)
900  {
901  cinfo->marker->discarded_bytes++;
902  INPUT_SYNC(cinfo);
903  INPUT_BYTE(cinfo, c, return FALSE);
904  }
905  /* This loop swallows any duplicate FF bytes. Extra FFs are legal as
906  * pad bytes, so don't count them in discarded_bytes. We assume there
907  * will not be so many consecutive FF bytes as to overflow a suspending
908  * data source's input buffer.
909  */
910  do
911  {
912  INPUT_BYTE(cinfo, c, return FALSE);
913  } while (c == 0xFF);
914  if (c != 0) break; /* found a valid marker, exit loop */
915  /* Reach here if we found a stuffed-zero data sequence (FF/00).
916  * Discard it and loop back to try again.
917  */
918  cinfo->marker->discarded_bytes += 2;
919  INPUT_SYNC(cinfo);
920  }
921 
922  if (cinfo->marker->discarded_bytes != 0)
923  {
924  WARNMS2(cinfo, JWRN_EXTRANEOUS_DATA, cinfo->marker->discarded_bytes, c);
925  cinfo->marker->discarded_bytes = 0;
926  }
927 
928  cinfo->unread_marker = c;
929 
930  INPUT_SYNC(cinfo);
931  return TRUE;
932 }
933 
934 LOCAL(boolean)
936 /* Like next_marker, but used to obtain the initial SOI marker. */
937 /* For this marker, we do not allow preceding garbage or fill; otherwise,
938  * we might well scan an entire input file before realizing it ain't JPEG.
939  * If an application wants to process non-JFIF files, it must seek to the
940  * SOI before calling the JPEG library.
941  */
942 {
943  int c, c2;
944  INPUT_VARS(cinfo);
945 
946  INPUT_BYTE(cinfo, c, return FALSE);
947  INPUT_BYTE(cinfo, c2, return FALSE);
948  if (c != 0xFF || c2 != (int)M_SOI) ERREXIT2(cinfo, JERR_NO_SOI, c, c2);
949 
950  cinfo->unread_marker = c2;
951 
952  INPUT_SYNC(cinfo);
953  return TRUE;
954 }
955 
956 /*
957  * Read markers until SOS or EOI.
958  *
959  * Returns same codes as are defined for jpeg_consume_input:
960  * JPEG_SUSPENDED, JPEG_REACHED_SOS, or JPEG_REACHED_EOI.
961  */
962 
963 METHODDEF(int)
965 {
966  /* Outer loop repeats once for each marker. */
967  for (;;)
968  {
969  /* Collect the marker proper, unless we already did. */
970  /* NB: first_marker() enforces the requirement that SOI appear first. */
971  if (cinfo->unread_marker == 0)
972  {
973  if (!cinfo->marker->saw_SOI)
974  {
975  if (!first_marker(cinfo)) return JPEG_SUSPENDED;
976  }
977  else
978  {
979  if (!next_marker(cinfo)) return JPEG_SUSPENDED;
980  }
981  }
982  /* At this point cinfo->unread_marker contains the marker code and the
983  * input point is just past the marker proper, but before any
984  * parameters.
985  * A suspension will cause us to return with this state still true.
986  */
987  switch (cinfo->unread_marker)
988  {
989  case M_SOI:
990  if (!get_soi(cinfo)) return JPEG_SUSPENDED;
991  break;
992 
993  case M_SOF0: /* Baseline */
994  case M_SOF1: /* Extended sequential, Huffman */
995  if (!get_sof(cinfo, FALSE, FALSE)) return JPEG_SUSPENDED;
996  break;
997 
998  case M_SOF2: /* Progressive, Huffman */
999  if (!get_sof(cinfo, TRUE, FALSE)) return JPEG_SUSPENDED;
1000  break;
1001 
1002  case M_SOF9: /* Extended sequential, arithmetic */
1003  if (!get_sof(cinfo, FALSE, TRUE)) return JPEG_SUSPENDED;
1004  break;
1005 
1006  case M_SOF10: /* Progressive, arithmetic */
1007  if (!get_sof(cinfo, TRUE, TRUE)) return JPEG_SUSPENDED;
1008  break;
1009 
1010  /* Currently unsupported SOFn types */
1011  case M_SOF3: /* Lossless, Huffman */
1012  case M_SOF5: /* Differential sequential, Huffman */
1013  case M_SOF6: /* Differential progressive, Huffman */
1014  case M_SOF7: /* Differential lossless, Huffman */
1015  case M_JPG: /* Reserved for JPEG extensions */
1016  case M_SOF11: /* Lossless, arithmetic */
1017  case M_SOF13: /* Differential sequential, arithmetic */
1018  case M_SOF14: /* Differential progressive, arithmetic */
1019  case M_SOF15: /* Differential lossless, arithmetic */
1020  ERREXIT1(cinfo, JERR_SOF_UNSUPPORTED, cinfo->unread_marker);
1021  break;
1022 
1023  case M_SOS:
1024  if (!get_sos(cinfo)) return JPEG_SUSPENDED;
1025  cinfo->unread_marker = 0; /* processed the marker */
1026  return JPEG_REACHED_SOS;
1027 
1028  case M_EOI:
1029  TRACEMS(cinfo, 1, JTRC_EOI);
1030  cinfo->unread_marker = 0; /* processed the marker */
1031  return JPEG_REACHED_EOI;
1032 
1033  case M_DAC:
1034  if (!get_dac(cinfo)) return JPEG_SUSPENDED;
1035  break;
1036 
1037  case M_DHT:
1038  if (!get_dht(cinfo)) return JPEG_SUSPENDED;
1039  break;
1040 
1041  case M_DQT:
1042  if (!get_dqt(cinfo)) return JPEG_SUSPENDED;
1043  break;
1044 
1045  case M_DRI:
1046  if (!get_dri(cinfo)) return JPEG_SUSPENDED;
1047  break;
1048 
1049  case M_APP0:
1050  case M_APP1:
1051  case M_APP2:
1052  case M_APP3:
1053  case M_APP4:
1054  case M_APP5:
1055  case M_APP6:
1056  case M_APP7:
1057  case M_APP8:
1058  case M_APP9:
1059  case M_APP10:
1060  case M_APP11:
1061  case M_APP12:
1062  case M_APP13:
1063  case M_APP14:
1064  case M_APP15:
1065  if (!(*((my_marker_ptr)cinfo->marker)
1066  ->process_APPn[cinfo->unread_marker - (int)M_APP0])(
1067  cinfo))
1068  return JPEG_SUSPENDED;
1069  break;
1070 
1071  case M_COM:
1072  if (!(*((my_marker_ptr)cinfo->marker)->process_COM)(cinfo))
1073  return JPEG_SUSPENDED;
1074  break;
1075 
1076  case M_RST0: /* these are all parameterless */
1077  case M_RST1:
1078  case M_RST2:
1079  case M_RST3:
1080  case M_RST4:
1081  case M_RST5:
1082  case M_RST6:
1083  case M_RST7:
1084  case M_TEM:
1085  TRACEMS1(cinfo, 1, JTRC_PARMLESS_MARKER, cinfo->unread_marker);
1086  break;
1087 
1088  case M_DNL: /* Ignore DNL ... perhaps the wrong thing */
1089  if (!skip_variable(cinfo)) return JPEG_SUSPENDED;
1090  break;
1091 
1092  default: /* must be DHP, EXP, JPGn, or RESn */
1093  /* For now, we treat the reserved markers as fatal errors since
1094  * they are
1095  * likely to be used to signal incompatible JPEG Part 3
1096  * extensions.
1097  * Once the JPEG 3 version-number marker is well defined, this
1098  * code
1099  * ought to change!
1100  */
1101  ERREXIT1(cinfo, JERR_UNKNOWN_MARKER, cinfo->unread_marker);
1102  break;
1103  }
1104  /* Successfully processed marker, so reset state variable */
1105  cinfo->unread_marker = 0;
1106  } /* end loop */
1107 }
1108 
1109 /*
1110  * Read a restart marker, which is expected to appear next in the datastream;
1111  * if the marker is not there, take appropriate recovery action.
1112  * Returns FALSE if suspension is required.
1113  *
1114  * This is called by the entropy decoder after it has read an appropriate
1115  * number of MCUs. cinfo->unread_marker may be nonzero if the entropy decoder
1116  * has already read a marker from the data source. Under normal conditions
1117  * cinfo->unread_marker will be reset to 0 before returning; if not reset,
1118  * it holds a marker which the decoder will be unable to read past.
1119  */
1120 
1121 METHODDEF(boolean)
1123 {
1124  /* Obtain a marker unless we already did. */
1125  /* Note that next_marker will complain if it skips any data. */
1126  if (cinfo->unread_marker == 0)
1127  {
1128  if (!next_marker(cinfo)) return FALSE;
1129  }
1130 
1131  if (cinfo->unread_marker == ((int)M_RST0 + cinfo->marker->next_restart_num))
1132  {
1133  /* Normal case --- swallow the marker and let entropy decoder continue
1134  */
1135  TRACEMS1(cinfo, 3, JTRC_RST, cinfo->marker->next_restart_num);
1136  cinfo->unread_marker = 0;
1137  }
1138  else
1139  {
1140  /* Uh-oh, the restart markers have been messed up. */
1141  /* Let the data source manager determine how to resync. */
1142  if (!(*cinfo->src->resync_to_restart)(
1143  cinfo, cinfo->marker->next_restart_num))
1144  return FALSE;
1145  }
1146 
1147  /* Update next-restart state */
1148  cinfo->marker->next_restart_num = (cinfo->marker->next_restart_num + 1) & 7;
1149 
1150  return TRUE;
1151 }
1152 
1153 /*
1154  * This is the default resync_to_restart method for data source managers
1155  * to use if they don't have any better approach. Some data source managers
1156  * may be able to back up, or may have additional knowledge about the data
1157  * which permits a more intelligent recovery strategy; such managers would
1158  * presumably supply their own resync method.
1159  *
1160  * read_restart_marker calls resync_to_restart if it finds a marker other than
1161  * the restart marker it was expecting. (This code is *not* used unless
1162  * a nonzero restart interval has been declared.) cinfo->unread_marker is
1163  * the marker code actually found (might be anything, except 0 or FF).
1164  * The desired restart marker number (0..7) is passed as a parameter.
1165  * This routine is supposed to apply whatever error recovery strategy seems
1166  * appropriate in order to position the input stream to the next data segment.
1167  * Note that cinfo->unread_marker is treated as a marker appearing before
1168  * the current data-source input point; usually it should be reset to zero
1169  * before returning.
1170  * Returns FALSE if suspension is required.
1171  *
1172  * This implementation is substantially constrained by wanting to treat the
1173  * input as a data stream; this means we can't back up. Therefore, we have
1174  * only the following actions to work with:
1175  * 1. Simply discard the marker and let the entropy decoder resume at next
1176  * byte of file.
1177  * 2. Read forward until we find another marker, discarding intervening
1178  * data. (In theory we could look ahead within the current bufferload,
1179  * without having to discard data if we don't find the desired marker.
1180  * This idea is not implemented here, in part because it makes behavior
1181  * dependent on buffer size and chance buffer-boundary positions.)
1182  * 3. Leave the marker unread (by failing to zero cinfo->unread_marker).
1183  * This will cause the entropy decoder to process an empty data segment,
1184  * inserting dummy zeroes, and then we will reprocess the marker.
1185  *
1186  * #2 is appropriate if we think the desired marker lies ahead, while #3 is
1187  * appropriate if the found marker is a future restart marker (indicating
1188  * that we have missed the desired restart marker, probably because it got
1189  * corrupted).
1190  * We apply #2 or #3 if the found marker is a restart marker no more than
1191  * two counts behind or ahead of the expected one. We also apply #2 if the
1192  * found marker is not a legal JPEG marker code (it's certainly bogus data).
1193  * If the found marker is a restart marker more than 2 counts away, we do #1
1194  * (too much risk that the marker is erroneous; with luck we will be able to
1195  * resync at some future point).
1196  * For any valid non-restart JPEG marker, we apply #3. This keeps us from
1197  * overrunning the end of a scan. An implementation limited to single-scan
1198  * files might find it better to apply #2 for markers other than EOI, since
1199  * any other marker would have to be bogus data in that case.
1200  */
1201 
1202 GLOBAL(boolean)
1204 {
1205  int marker = cinfo->unread_marker;
1206  int action = 1;
1207 
1208  /* Always put up a warning. */
1209  WARNMS2(cinfo, JWRN_MUST_RESYNC, marker, desired);
1210 
1211  /* Outer loop handles repeated decision after scanning forward. */
1212  for (;;)
1213  {
1214  if (marker < (int)M_SOF0)
1215  action = 2; /* invalid marker */
1216  else if (marker < (int)M_RST0 || marker > (int)M_RST7)
1217  action = 3; /* valid non-restart marker */
1218  else
1219  {
1220  if (marker == ((int)M_RST0 + ((desired + 1) & 7)) ||
1221  marker == ((int)M_RST0 + ((desired + 2) & 7)))
1222  action = 3; /* one of the next two expected restarts */
1223  else if (
1224  marker == ((int)M_RST0 + ((desired - 1) & 7)) ||
1225  marker == ((int)M_RST0 + ((desired - 2) & 7)))
1226  action = 2; /* a prior restart, so advance */
1227  else
1228  action = 1; /* desired restart or too far away */
1229  }
1230  TRACEMS2(cinfo, 4, JTRC_RECOVERY_ACTION, marker, action);
1231  switch (action)
1232  {
1233  case 1:
1234  /* Discard marker and let entropy decoder resume processing. */
1235  cinfo->unread_marker = 0;
1236  return TRUE;
1237  case 2:
1238  /* Scan to the next marker, and repeat the decision loop. */
1239  if (!next_marker(cinfo)) return FALSE;
1240  marker = cinfo->unread_marker;
1241  break;
1242  case 3:
1243  /* Return without advancing past this marker. */
1244  /* Entropy decoder will be forced to process an empty segment.
1245  */
1246  return TRUE;
1247  }
1248  } /* end loop */
1249 }
1250 
1251 /*
1252  * Reset marker processing state to begin a fresh datastream.
1253  */
1254 
1255 METHODDEF(void)
1257 {
1258  my_marker_ptr marker = (my_marker_ptr)cinfo->marker;
1259 
1260  cinfo->comp_info = nullptr; /* until allocated by get_sof */
1261  cinfo->input_scan_number = 0; /* no SOS seen yet */
1262  cinfo->unread_marker = 0; /* no pending marker */
1263  marker->pub.saw_SOI = FALSE; /* set internal state too */
1264  marker->pub.saw_SOF = FALSE;
1265  marker->pub.discarded_bytes = 0;
1266  marker->cur_marker = nullptr;
1267 }
1268 
1269 /*
1270  * Initialize the marker reader module.
1271  * This is called only once, when the decompression object is created.
1272  */
1273 
1274 GLOBAL(void)
1276 {
1277  my_marker_ptr marker;
1278  int i;
1279 
1280  /* Create subobject in permanent pool */
1281  marker = (my_marker_ptr)(*cinfo->mem->alloc_small)(
1283  cinfo->marker = (struct jpeg_marker_reader*)marker;
1284  /* Initialize public method pointers */
1285  marker->pub.reset_marker_reader = reset_marker_reader;
1286  marker->pub.read_markers = read_markers;
1287  marker->pub.read_restart_marker = read_restart_marker;
1288  /* Initialize COM/APPn processing.
1289  * By default, we examine and then discard APP0 and APP14,
1290  * but simply discard COM and all other APPn.
1291  */
1292  marker->process_COM = skip_variable;
1293  marker->length_limit_COM = 0;
1294  for (i = 0; i < 16; i++)
1295  {
1296  marker->process_APPn[i] = skip_variable;
1297  marker->length_limit_APPn[i] = 0;
1298  }
1299  marker->process_APPn[0] = get_interesting_appn;
1300  marker->process_APPn[14] = get_interesting_appn;
1301  /* Reset marker processing state */
1302  reset_marker_reader(cinfo);
1303 }
1304 
1305 /*
1306  * Control saving of COM and APPn markers into marker_list.
1307  */
1308 
1309 #ifdef SAVE_MARKERS_SUPPORTED
1310 
1311 GLOBAL(void)
1313  j_decompress_ptr cinfo, int marker_code, unsigned int length_limit)
1314 {
1315  my_marker_ptr marker = (my_marker_ptr)cinfo->marker;
1316  long maxlength;
1317  jpeg_marker_parser_method processor;
1318 
1319  /* Length limit mustn't be larger than what we can allocate
1320  * (should only be a concern in a 16-bit environment).
1321  */
1322  maxlength = cinfo->mem->max_alloc_chunk - SIZEOF(struct jpeg_marker_struct);
1323  if (((long)length_limit) > maxlength)
1324  length_limit = (unsigned int)maxlength;
1325 
1326  /* Choose processor routine to use.
1327  * APP0/APP14 have special requirements.
1328  */
1329  if (length_limit)
1330  {
1331  processor = save_marker;
1332  /* If saving APP0/APP14, save at least enough for our internal use. */
1333  if (marker_code == (int)M_APP0 && length_limit < APP0_DATA_LEN)
1334  length_limit = APP0_DATA_LEN;
1335  else if (marker_code == (int)M_APP14 && length_limit < APP14_DATA_LEN)
1336  length_limit = APP14_DATA_LEN;
1337  }
1338  else
1339  {
1340  processor = skip_variable;
1341  /* If discarding APP0/APP14, use our regular on-the-fly processor. */
1342  if (marker_code == (int)M_APP0 || marker_code == (int)M_APP14)
1343  processor = get_interesting_appn;
1344  }
1345 
1346  if (marker_code == (int)M_COM)
1347  {
1348  marker->process_COM = processor;
1349  marker->length_limit_COM = length_limit;
1350  }
1351  else if (marker_code >= (int)M_APP0 && marker_code <= (int)M_APP15)
1352  {
1353  marker->process_APPn[marker_code - (int)M_APP0] = processor;
1354  marker->length_limit_APPn[marker_code - (int)M_APP0] = length_limit;
1355  }
1356  else
1357  ERREXIT1(cinfo, JERR_UNKNOWN_MARKER, marker_code);
1358 }
1359 
1360 #endif /* SAVE_MARKERS_SUPPORTED */
1361 
1362 /*
1363  * Install a special processing method for COM or APPn markers.
1364  */
1365 
1366 GLOBAL(void)
1368  j_decompress_ptr cinfo, int marker_code, jpeg_marker_parser_method routine)
1369 {
1370  my_marker_ptr marker = (my_marker_ptr)cinfo->marker;
1371 
1372  if (marker_code == (int)M_COM)
1373  marker->process_COM = routine;
1374  else if (marker_code >= (int)M_APP0 && marker_code <= (int)M_APP15)
1375  marker->process_APPn[marker_code - (int)M_APP0] = routine;
1376  else
1377  ERREXIT1(cinfo, JERR_UNKNOWN_MARKER, marker_code);
1378 }
#define INPUT_VARS(cinfo)
Definition: jdmarker.cpp:112
jinit_marker_reader(j_decompress_ptr cinfo)
Definition: jdmarker.cpp:1275
#define INPUT_2BYTES(cinfo, V, action)
Definition: jdmarker.cpp:152
GLuint GLuint GLsizei count
Definition: glext.h:3528
UINT16 quantval[DCTSIZE2]
Definition: mrpt_jpeglib.h:81
get_sof(j_decompress_ptr cinfo, boolean is_prog, boolean is_arith)
Definition: jdmarker.cpp:229
first_marker(j_decompress_ptr cinfo)
Definition: jdmarker.cpp:935
skip_variable(j_decompress_ptr cinfo)
Definition: jdmarker.cpp:858
#define GETJOCTET(value)
Definition: jmorecfg.h:110
#define MAX_COMPS_IN_SCAN
Definition: mrpt_jpeglib.h:41
#define JPOOL_PERMANENT
Definition: mrpt_jpeglib.h:749
UINT8 arith_dc_U[NUM_ARITH_TBLS]
Definition: mrpt_jpeglib.h:544
const int jpeg_natural_order[]
Definition: jutils.cpp:48
GLenum GLsizei n
Definition: glext.h:5074
struct jpeg_common_struct * j_common_ptr
Definition: mrpt_jpeglib.h:258
#define ERREXIT(cinfo, code)
Definition: jerror.h:451
#define TRACEMS2(cinfo, lvl, code, p1, p2)
Definition: jerror.h:500
#define SIZEOF(object)
Definition: jinclude.h:74
#define NUM_ARITH_TBLS
Definition: mrpt_jpeglib.h:40
struct jpeg_marker_struct FAR * jpeg_saved_marker_ptr
Definition: mrpt_jpeglib.h:187
read_markers(j_decompress_ptr cinfo)
Definition: jdmarker.cpp:964
my_marker_reader * my_marker_ptr
Definition: jdmarker.cpp:101
long INT32
Definition: jmorecfg.h:151
#define INPUT_BYTE(cinfo, V, action)
Definition: jdmarker.cpp:144
GLint limit
Definition: glext.h:8188
UINT8 arith_dc_L[NUM_ARITH_TBLS]
Definition: mrpt_jpeglib.h:543
#define TRACEMS(cinfo, lvl, code)
Definition: jerror.h:494
get_sos(j_decompress_ptr cinfo)
Definition: jdmarker.cpp:293
#define WARNMS2(cinfo, code, p1, p2)
Definition: jerror.h:488
jpeg_resync_to_restart(j_decompress_ptr cinfo, int desired)
Definition: jdmarker.cpp:1203
#define APP14_DATA_LEN
Definition: jdmarker.cpp:576
UINT8 arith_ac_K[NUM_ARITH_TBLS]
Definition: mrpt_jpeglib.h:545
#define TRACEMS1(cinfo, lvl, code, p1)
Definition: jerror.h:497
#define MEMCOPY(dest, src, size)
Definition: jinclude.h:61
read_restart_marker(j_decompress_ptr cinfo)
Definition: jdmarker.cpp:1122
GLuint index
Definition: glext.h:4054
const GLubyte * c
Definition: glext.h:6313
#define FALSE
Definition: jmorecfg.h:216
short UINT8
Definition: jmorecfg.h:130
#define TRACEMS5(cinfo, lvl, code, p1, p2, p3, p4, p5)
Definition: jerror.h:514
#define JPEG_REACHED_EOI
Definition: mrpt_jpeglib.h:998
#define JPOOL_IMAGE
Definition: mrpt_jpeglib.h:750
#define LOCAL(type)
Definition: jmorecfg.h:175
save_marker(j_decompress_ptr cinfo)
Definition: jdmarker.cpp:740
#define APP0_DATA_LEN
Definition: jdmarker.cpp:575
int val
Definition: mrpt_jpeglib.h:955
GLubyte GLubyte b
Definition: glext.h:6279
#define APPN_DATA_LEN
Definition: jdmarker.cpp:577
jpeg_alloc_huff_table(j_common_ptr cinfo)
Definition: jcomapi.cpp:94
examine_app0(j_decompress_ptr cinfo, JOCTET FAR *data, unsigned int datalen, INT32 remaining)
Definition: jdmarker.cpp:580
#define DCTSIZE2
Definition: mrpt_jpeglib.h:37
jpeg_marker_parser_method process_COM
Definition: jdmarker.cpp:88
reset_marker_reader(j_decompress_ptr cinfo)
Definition: jdmarker.cpp:1256
#define NUM_HUFF_TBLS
Definition: mrpt_jpeglib.h:39
get_dht(j_decompress_ptr cinfo)
Definition: jdmarker.cpp:413
#define JPEG_SUSPENDED
Definition: mrpt_jpeglib.h:964
#define TRUE
Definition: jmorecfg.h:219
jpeg_alloc_quant_table(j_common_ptr cinfo)
Definition: jcomapi.cpp:83
unsigned int UINT16
Definition: jmorecfg.h:139
#define ERREXIT1(cinfo, code, p1)
Definition: jerror.h:454
get_dqt(j_decompress_ptr cinfo)
Definition: jdmarker.cpp:486
JPEG_MARKER
Definition: jdmarker.cpp:14
jpeg_save_markers(j_decompress_ptr cinfo, int marker_code, unsigned int length_limit)
Definition: jdmarker.cpp:1312
#define GLOBAL(type)
Definition: jmorecfg.h:177
next_marker(j_decompress_ptr cinfo)
Definition: jdmarker.cpp:885
#define METHODDEF(type)
Definition: jmorecfg.h:173
GLuint GLsizei GLsizei * length
Definition: glext.h:4064
#define NUM_QUANT_TBLS
Definition: mrpt_jpeglib.h:38
#define MAKE_BYTE_AVAIL(cinfo, action)
Definition: jdmarker.cpp:131
#define JPEG_REACHED_SOS
Definition: mrpt_jpeglib.h:997
get_dri(j_decompress_ptr cinfo)
Definition: jdmarker.cpp:547
#define TRACEMS8(cinfo, lvl, code, p1, p2, p3, p4, p5, p6, p7, p8)
Definition: jerror.h:520
get_soi(j_decompress_ptr cinfo)
Definition: jdmarker.cpp:190
struct jpeg_marker_writer pub
Definition: jcmarker.cpp:85
#define get_dac(cinfo)
Definition: jdmarker.cpp:408
#define TRACEMS3(cinfo, lvl, code, p1, p2, p3)
Definition: jerror.h:504
jpeg_saved_marker_ptr cur_marker
Definition: jdmarker.cpp:96
#define TRACEMS4(cinfo, lvl, code, p1, p2, p3, p4)
Definition: jerror.h:509
#define FAR
Definition: zconf.h:262
jpeg_set_marker_processor(j_decompress_ptr cinfo, int marker_code, jpeg_marker_parser_method routine)
Definition: jdmarker.cpp:1367
char JOCTET
Definition: jmorecfg.h:106
GLuint GLenum GLenum transform
Definition: glext.h:6975
#define ERREXIT2(cinfo, code, p1, p2)
Definition: jerror.h:457
GLsizei GLsizei GLenum GLenum const GLvoid * data
Definition: glext.h:3546
unsigned int length_limit_COM
Definition: jdmarker.cpp:92
#define INPUT_SYNC(cinfo)
Definition: jdmarker.cpp:118
examine_app14(j_decompress_ptr cinfo, JOCTET FAR *data, unsigned int datalen, INT32 remaining)
Definition: jdmarker.cpp:662
jpeg_component_info * compptr
Definition: jidctflt.cpp:36
unsigned int bytes_read
Definition: jdmarker.cpp:97
get_interesting_appn(j_decompress_ptr cinfo)
Definition: jdmarker.cpp:693



Page generated by Doxygen 1.8.14 for MRPT 1.9.9 Git: ae4571287 Thu Nov 23 00:06:53 2017 +0100 at dom oct 27 23:51:55 CET 2019