Coverage Report

Created: 2026-06-30 07:05

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