diff options
Diffstat (limited to 'xc/programs/Xserver/XIE/mixie/jpeg/jrdjfif.c')
-rw-r--r-- | xc/programs/Xserver/XIE/mixie/jpeg/jrdjfif.c | 1619 |
1 files changed, 1619 insertions, 0 deletions
diff --git a/xc/programs/Xserver/XIE/mixie/jpeg/jrdjfif.c b/xc/programs/Xserver/XIE/mixie/jpeg/jrdjfif.c new file mode 100644 index 000000000..6f50f7901 --- /dev/null +++ b/xc/programs/Xserver/XIE/mixie/jpeg/jrdjfif.c @@ -0,0 +1,1619 @@ +/* $TOG: jrdjfif.c /main/6 1998/02/09 16:20:33 kaleb $ */ +/* AGE Logic - Oct 15 1995 - Larry Hare */ +/* Module jrdjfif.c */ + +/**************************************************************************** + +Copyright 1993, 1994, 1998 The Open Group + +All Rights Reserved. + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN +AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN +CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + +Except as contained in this notice, the name of The Open Group shall not be +used in advertising or otherwise to promote the sale, use or other dealings +in this Software without prior written authorization from The Open Group. + + + NOTICE + +This software is being provided by AGE Logic, Inc. under the +following license. By obtaining, using and/or copying this software, +you agree that you have read, understood, and will comply with these +terms and conditions: + + Permission to use, copy, modify, distribute and sell this + software and its documentation for any purpose and without + fee or royalty and to grant others any or all rights granted + herein is hereby granted, provided that you agree to comply + with the following copyright notice and statements, including + the disclaimer, and that the same appears on all copies and + derivative works of the software and documentation you make. + + "Copyright 1993, 1994 by AGE Logic, Inc." + + THIS SOFTWARE IS PROVIDED "AS IS". AGE LOGIC MAKES NO + REPRESENTATIONS OR WARRANTIES, EXPRESS OR IMPLIED. By way of + example, but not limitation, AGE LOGIC MAKE NO + REPRESENTATIONS OR WARRANTIES OF MERCHANTABILITY OR FITNESS + FOR ANY PARTICULAR PURPOSE OR THAT THE SOFTWARE DOES NOT + INFRINGE THIRD-PARTY PROPRIETARY RIGHTS. AGE LOGIC + SHALL BEAR NO LIABILITY FOR ANY USE OF THIS SOFTWARE. IN NO + EVENT SHALL EITHER PARTY BE LIABLE FOR ANY INDIRECT, + INCIDENTAL, SPECIAL, OR CONSEQUENTIAL DAMAGES, INCLUDING LOSS + OF PROFITS, REVENUE, DATA OR USE, INCURRED BY EITHER PARTY OR + ANY THIRD PARTY, WHETHER IN AN ACTION IN CONTRACT OR TORT OR + BASED ON A WARRANTY, EVEN IF AGE LOGIC LICENSEES + HEREUNDER HAVE BEEN ADVISED OF THE POSSIBILITY OF SUCH + DAMAGES. + + The name of AGE Logic, Inc. may not be used in + advertising or publicity pertaining to this software without + specific, written prior permission from AGE Logic. + + Title to this software shall at all times remain with AGE + Logic, Inc. +***************************************************************************** + + Gary Rogers, AGE Logic, Inc., October 1993 + +****************************************************************************/ +/* $XFree86: xc/programs/Xserver/XIE/mixie/jpeg/jrdjfif.c,v 1.3 1998/10/04 09:36:23 dawes Exp $ */ + +/* + * jrdjfif.c + * + * Copyright (C) 1991, 1992, Thomas G. Lane. + * This file is part of the Independent JPEG Group's software. + * For conditions of distribution and use, see the accompanying README file. + * + * This file contains routines to decode standard JPEG file headers/markers. + * This code will handle "raw JPEG" and JFIF-convention JPEG files. + * + * You can also use this module to decode a raw-JPEG or JFIF-standard data + * stream that is embedded within a larger file. To do that, you must + * position the file to the JPEG SOI marker (0xFF/0xD8) that begins the + * data sequence to be decoded. If nothing better is possible, you can scan + * the file until you see the SOI marker, then use JUNGETC to push it back. + * + * This module relies on the JGETC macro and the read_jpeg_data method (which + * is provided by the user interface) to read from the JPEG data stream. + * Therefore, this module is not dependent on any particular assumption about + * the data source; it need not be a stdio stream at all. (This fact does + * NOT carry over to more complex JPEG file formats such as JPEG-in-TIFF; + * those format control modules may well need to assume stdio input.) + * + * These routines are invoked via the methods read_file_header, + * read_scan_header, read_jpeg_data, read_scan_trailer, and read_file_trailer. + */ + +#include "jinclude.h" +#include "macro.h" + +#ifdef JFIF_SUPPORTED + +#ifdef XIE_SUPPORTED +#define M_EOB -1 +#define M_SOF0 0xc0 +#define M_SOF1 0xc1 +#define M_SOF2 0xc2 +#define M_SOF3 0xc3 + +#define M_SOF5 0xc5 +#define M_SOF6 0xc6 +#define M_SOF7 0xc7 + +#define M_JPG 0xc8 +#define M_SOF9 0xc9 +#define M_SOF10 0xca +#define M_SOF11 0xcb + +#define M_SOF13 0xcd +#define M_SOF14 0xce +#define M_SOF15 0xcf + +#define M_DHT 0xc4 + +#define M_DAC 0xcc + +#define M_RST0 0xd0 +#define M_RST1 0xd1 +#define M_RST2 0xd2 +#define M_RST3 0xd3 +#define M_RST4 0xd4 +#define M_RST5 0xd5 +#define M_RST6 0xd6 +#define M_RST7 0xd7 + +#define M_SOI 0xd8 +#define M_EOI 0xd9 +#define M_SOS 0xda +#define M_DQT 0xdb +#define M_DNL 0xdc +#define M_DRI 0xdd +#define M_DHP 0xde +#define M_EXP 0xdf + +#define M_APP0 0xe0 +#define M_APP15 0xef + +#define M_JPG0 0xf0 +#define M_JPG13 0xfd +#define M_COM 0xfe + +#define M_TEM 0x01 + +#define M_ERROR 0x100 +#else +typedef enum { /* JPEG marker codes */ + M_SOF0 = 0xc0, + M_SOF1 = 0xc1, + M_SOF2 = 0xc2, + M_SOF3 = 0xc3, + + M_SOF5 = 0xc5, + M_SOF6 = 0xc6, + M_SOF7 = 0xc7, + + M_JPG = 0xc8, + M_SOF9 = 0xc9, + M_SOF10 = 0xca, + M_SOF11 = 0xcb, + + M_SOF13 = 0xcd, + M_SOF14 = 0xce, + M_SOF15 = 0xcf, + + M_DHT = 0xc4, + + M_DAC = 0xcc, + + M_RST0 = 0xd0, + M_RST1 = 0xd1, + M_RST2 = 0xd2, + M_RST3 = 0xd3, + M_RST4 = 0xd4, + M_RST5 = 0xd5, + M_RST6 = 0xd6, + M_RST7 = 0xd7, + + M_SOI = 0xd8, + M_EOI = 0xd9, + M_SOS = 0xda, + M_DQT = 0xdb, + M_DNL = 0xdc, + M_DRI = 0xdd, + M_DHP = 0xde, + M_EXP = 0xdf, + + M_APP0 = 0xe0, + M_APP15 = 0xef, + + M_JPG0 = 0xf0, + M_JPG13 = 0xfd, + M_COM = 0xfe, + + M_TEM = 0x01, + + M_ERROR = 0x100 +} JPEG_MARKER; +#endif /* XIE_SUPPORTED */ + + +/* + * Reload the input buffer after it's been emptied, and return the next byte. + * This is exported for direct use by the entropy decoder. + * See the JGETC macro for calling conditions. Note in particular that + * read_jpeg_data may NOT return EOF. If no more data is available, it must + * exit via ERREXIT, or perhaps synthesize fake data (such as an RST marker). + * For error recovery purposes, synthesizing an EOI marker is probably best. + * + * For this header control module, read_jpeg_data is supplied by the + * user interface. However, header formats that require random access + * to the input file would need to supply their own code. This code is + * left here to indicate what is required. + */ + +#ifndef XIE_SUPPORTED +#if NOTDEF /* not needed in this module */ + +METHODDEF int +read_jpeg_data (decompress_info_ptr cinfo) +{ + cinfo->next_input_byte = cinfo->input_buffer + MIN_UNGET; + + cinfo->bytes_in_buffer = (int) JFREAD(cinfo->input_file, + cinfo->next_input_byte, + JPEG_BUF_SIZE); + + if (cinfo->bytes_in_buffer <= 0) { + WARNMS(cinfo->emethods, "Premature EOF in JPEG file"); + cinfo->next_input_byte[0] = (char) 0xFF; + cinfo->next_input_byte[1] = (char) M_EOI; + cinfo->bytes_in_buffer = 2; + } + + return JGETC(cinfo); +} + +#endif +#endif /* XIE_SUPPORTED */ + + +/* + * Routines to parse JPEG markers & save away the useful info. + */ + + +LOCAL INT32 +#ifdef XIE_SUPPORTED +#if NeedFunctionPrototypes +get_2bytes (decompress_info_ptr cinfo) +#else +get_2bytes (cinfo) + decompress_info_ptr cinfo; +#endif /* NeedFunctionPrototypes */ +#else +get_2bytes (decompress_info_ptr cinfo) +#endif /* XIE_SUPPORTED */ +/* Get a 2-byte unsigned integer (e.g., a marker parameter length field) */ +{ + INT32 a; +#ifdef XIE_SUPPORTED + INT32 b; + if ((a = JGETC(cinfo)) < 0) + return(-1); + if ((b = JGETC(cinfo)) < 0) + return(-1); + return (a << 8) + b; +#else + a = JGETC(cinfo); + return (a << 8) + JGETC(cinfo); +#endif /* XIE_SUPPORTED */ +} + + +#ifdef XIE_SUPPORTED +LOCAL int +#if NeedFunctionPrototypes +skip_variable (decompress_info_ptr cinfo, int code) +#else +skip_variable (cinfo, code) + decompress_info_ptr cinfo; + int code; +#endif /* NeedFunctionPrototypes */ +#else +LOCAL void +skip_variable (decompress_info_ptr cinfo, int code) +#endif /* XIE_SUPPORTED */ +/* Skip over an unknown or uninteresting variable-length marker */ +{ + INT32 length; + + length = get_2bytes(cinfo); +#ifdef XIE_SUPPORTED + if (length < 0) + return(-1); +#else + TRACEMS2(cinfo->emethods, 1, + "Skipping marker 0x%02x, length %u", code, (int) length); +#endif /* XIE_SUPPORTED */ + + for (length -= 2; length > 0; length--) +#ifdef XIE_SUPPORTED + if (JGETC(cinfo) < 0) + return(-1); +#else + (void) JGETC(cinfo); +#endif /* XIE_SUPPORTED */ + +#ifdef XIE_SUPPORTED + return(0); +#endif /* XIE_SUPPORTED */ +} + + +#ifdef XIE_SUPPORTED +LOCAL int +#if NeedFunctionPrototypes +get_dht (decompress_info_ptr cinfo) +#else +get_dht (cinfo) + decompress_info_ptr cinfo; +#endif /* NeedFunctionPrototypes */ +#else +LOCAL void +get_dht (decompress_info_ptr cinfo) +#endif /* XIE_SUPPORTED */ +/* Process a DHT marker */ +{ + INT32 length; + UINT8 bits[17]; + UINT8 huffval[256]; + int i, index, count; + HUFF_TBL **htblptr; +#ifdef XIE_SUPPORTED + int j; +#endif /* XIE_SUPPORTED */ + +#ifdef XIE_SUPPORTED + if ((length = get_2bytes(cinfo)) < 0) + return(-1); + length -= 2; +#else + length = get_2bytes(cinfo)-2; +#endif /* XIE_SUPPORTED */ + + + while (length > 0) { + index = JGETC(cinfo); +#ifdef XIE_SUPPORTED + if (index < 0) + return(-1); +#else + TRACEMS1(cinfo->emethods, 1, "Define Huffman Table 0x%02x", index); +#endif /* XIE_SUPPORTED */ + + bits[0] = 0; + count = 0; + for (i = 1; i <= 16; i++) { +#ifdef XIE_SUPPORTED + if ((j = JGETC(cinfo)) < 0) + return(-1); + bits[i] = (UINT8) j; +#else + bits[i] = (UINT8) JGETC(cinfo); +#endif /* XIE_SUPPORTED */ + count += bits[i]; + } + +#ifndef XIE_SUPPORTED + TRACEMS8(cinfo->emethods, 2, " %3d %3d %3d %3d %3d %3d %3d %3d", + bits[1], bits[2], bits[3], bits[4], + bits[5], bits[6], bits[7], bits[8]); + TRACEMS8(cinfo->emethods, 2, " %3d %3d %3d %3d %3d %3d %3d %3d", + bits[9], bits[10], bits[11], bits[12], + bits[13], bits[14], bits[15], bits[16]); +#endif /* XIE_SUPPORTED */ + + if (count > 256) +#ifdef XIE_SUPPORTED + return(XIE_ERR); +#else + ERREXIT(cinfo->emethods, "Bogus DHT counts"); +#endif /* XIE_SUPPORTED */ + + for (i = 0; i < count; i++) { +#ifdef XIE_SUPPORTED + if ((j = JGETC(cinfo)) < 0) + return(-1); + huffval[i] = (UINT8) j; +#else + huffval[i] = (UINT8) JGETC(cinfo); +#endif /* XIE_SUPPORTED */ + } + + length -= 1 + 16 + count; + + if (index & 0x10) { /* AC table definition */ + index -= 0x10; + htblptr = &cinfo->ac_huff_tbl_ptrs[index]; + } else { /* DC table definition */ + htblptr = &cinfo->dc_huff_tbl_ptrs[index]; + } + + if (index < 0 || index >= NUM_HUFF_TBLS) +#ifdef XIE_SUPPORTED + return(XIE_ERR); +#else + ERREXIT1(cinfo->emethods, "Bogus DHT index %d", index); +#endif /* XIE_SUPPORTED */ + +#ifdef XIE_SUPPORTED + if (*htblptr == NULL) + *htblptr = (HUFF_TBL *) (*cinfo->emethods->d_alloc_small) + (cinfo, SIZEOF(HUFF_TBL)); + if (*htblptr == (HUFF_TBL *) NULL) + return(XIE_ERR); +#else + if (*htblptr == NULL) + *htblptr = (HUFF_TBL *) (*cinfo->emethods->alloc_small) (SIZEOF(HUFF_TBL)); +#endif /* XIE_SUPPORTED */ + + MEMCOPY((*htblptr)->bits, bits, SIZEOF((*htblptr)->bits)); + MEMCOPY((*htblptr)->huffval, huffval, SIZEOF((*htblptr)->huffval)); + } +#ifdef XIE_SUPPORTED + return(0); +#endif /* XIE_SUPPORTED */ +} + + +#ifdef XIE_SUPPORTED +LOCAL int +#if NeedFunctionPrototypes +get_dac (decompress_info_ptr cinfo) +#else +get_dac (cinfo) + decompress_info_ptr cinfo; +#endif /* NeedFunctionPrototypes */ +#else +LOCAL void +get_dac (decompress_info_ptr cinfo) +#endif /* XIE_SUPPORTED */ +/* Process a DAC marker */ +{ + INT32 length; + int index, val; + +#ifdef XIE_SUPPORTED + if ((length = get_2bytes(cinfo)) < 0) + return(-1); + length -= 2; +#else + length = get_2bytes(cinfo)-2; +#endif /* XIE_SUPPORTED */ + + while (length > 0) { + index = JGETC(cinfo); +#ifdef XIE_SUPPORTED + if (index < 0) + return(-1); +#endif /* XIE_SUPPORTED */ + val = JGETC(cinfo); +#ifdef XIE_SUPPORTED + if (val < 0) + return(-1); +#else + TRACEMS2(cinfo->emethods, 1, + "Define Arithmetic Table 0x%02x: 0x%02x", index, val); +#endif /* XIE_SUPPORTED */ + + if (index < 0 || index >= (2*NUM_ARITH_TBLS)) +#ifdef XIE_SUPPORTED + return(XIE_ERR); +#else + ERREXIT1(cinfo->emethods, "Bogus DAC index %d", index); +#endif /* XIE_SUPPORTED */ + + if (index >= NUM_ARITH_TBLS) { /* define AC table */ + cinfo->arith_ac_K[index-NUM_ARITH_TBLS] = (UINT8) val; + } else { /* define DC table */ + cinfo->arith_dc_L[index] = (UINT8) (val & 0x0F); + cinfo->arith_dc_U[index] = (UINT8) (val >> 4); + if (cinfo->arith_dc_L[index] > cinfo->arith_dc_U[index]) +#ifdef XIE_SUPPORTED + return(XIE_ERR); +#else + ERREXIT1(cinfo->emethods, "Bogus DAC value 0x%x", val); +#endif /* XIE_SUPPORTED */ + } + + length -= 2; + } +#ifdef XIE_SUPPORTED + return(0); +#endif /* XIE_SUPPORTED */ +} + + +#ifdef XIE_SUPPORTED +LOCAL int +#if NeedFunctionPrototypes +get_dqt (decompress_info_ptr cinfo) +#else +get_dqt (cinfo) + decompress_info_ptr cinfo; +#endif /* NeedFunctionPrototypes */ +#else +LOCAL void +get_dqt (decompress_info_ptr cinfo) +#endif /* XIE_SUPPORTED */ +/* Process a DQT marker */ +{ + INT32 length; + int n, i, prec; + UINT16 tmp; + QUANT_TBL_PTR quant_ptr; +#ifdef XIE_SUPPORTED + int j; +#endif /* XIE_SUPPORTED */ + +#ifdef XIE_SUPPORTED + if ((length = get_2bytes(cinfo)) < 0) + return(-1); + length -= 2; +#else + length = get_2bytes(cinfo)-2; +#endif /* XIE_SUPPORTED */ + + while (length > 0) { + n = JGETC(cinfo); +#ifdef XIE_SUPPORTED + if (n < 0) + return(-1); +#endif /* XIE_SUPPORTED */ + prec = n >> 4; + n &= 0x0F; + +#ifndef XIE_SUPPORTED + TRACEMS2(cinfo->emethods, 1, + "Define Quantization Table %d precision %d", n, prec); +#endif /* XIE_SUPPORTED */ + + if (n >= NUM_QUANT_TBLS) +#ifdef XIE_SUPPORTED + return(XIE_ERR); +#else + ERREXIT1(cinfo->emethods, "Bogus table number %d", n); +#endif /* XIE_SUPPORTED */ + +#ifdef XIE_SUPPORTED + if (cinfo->quant_tbl_ptrs[n] == NULL) + cinfo->quant_tbl_ptrs[n] = (QUANT_TBL_PTR) + (*cinfo->emethods->d_alloc_small) (cinfo, SIZEOF(QUANT_TBL)); + if (cinfo->quant_tbl_ptrs[n] == (QUANT_TBL_PTR) NULL) + return(XIE_ERR); +#else + if (cinfo->quant_tbl_ptrs[n] == NULL) + cinfo->quant_tbl_ptrs[n] = (QUANT_TBL_PTR) + (*cinfo->emethods->alloc_small) (SIZEOF(QUANT_TBL)); +#endif /* XIE_SUPPORTED */ + quant_ptr = cinfo->quant_tbl_ptrs[n]; + + for (i = 0; i < DCTSIZE2; i++) { +#ifdef XIE_SUPPORTED + j = JGETC(cinfo); + if (j < 0) + return(-1); + tmp = (UINT16) j; +#else + tmp = JGETC(cinfo); +#endif /* XIE_SUPPORTED */ + if (prec) { +#ifdef XIE_SUPPORTED + if ((j = JGETC(cinfo)) < 0) + return(-1); + tmp = (tmp<<8) + j; +#else + tmp = (tmp<<8) + JGETC(cinfo); +#endif /* XIE_SUPPORTED */ + } + quant_ptr[i] = tmp; + } + +#ifndef XIE_SUPPORTED + for (i = 0; i < DCTSIZE2; i += 8) { + TRACEMS8(cinfo->emethods, 2, " %4u %4u %4u %4u %4u %4u %4u %4u", + quant_ptr[i ], quant_ptr[i+1], quant_ptr[i+2], quant_ptr[i+3], + quant_ptr[i+4], quant_ptr[i+5], quant_ptr[i+6], quant_ptr[i+7]); + } +#endif /* XIE_SUPPORTED */ + + length -= DCTSIZE2+1; + if (prec) length -= DCTSIZE2; + } +#ifdef XIE_SUPPORTED + return(0); +#endif /* XIE_SUPPORTED */ +} + + +#ifdef XIE_SUPPORTED +LOCAL int +#if NeedFunctionPrototypes +get_dri (decompress_info_ptr cinfo) +#else +get_dri (cinfo) + decompress_info_ptr cinfo; +#endif /* NeedFunctionPrototypes */ +#else +LOCAL void +get_dri (decompress_info_ptr cinfo) +#endif /* XIE_SUPPORTED */ +/* Process a DRI marker */ +{ +#ifdef XIE_SUPPORTED + INT32 j; +#endif /* XIE_SUPPORTED */ + if (get_2bytes(cinfo) != 4) +#ifdef XIE_SUPPORTED + return(XIE_ERR); +#else + ERREXIT(cinfo->emethods, "Bogus length in DRI"); +#endif /* XIE_SUPPORTED */ + +#ifdef XIE_SUPPORTED + if ((j = get_2bytes(cinfo)) < 0) + return(-1); + cinfo->restart_interval = (UINT16) j; + + return(0); +#else + cinfo->restart_interval = (UINT16) get_2bytes(cinfo); + + TRACEMS1(cinfo->emethods, 1, + "Define Restart Interval %u", cinfo->restart_interval); +#endif /* XIE_SUPPORTED */ +} + + +#ifdef XIE_SUPPORTED +LOCAL int +#if NeedFunctionPrototypes +get_app0 (decompress_info_ptr cinfo) +#else +get_app0 (cinfo) + decompress_info_ptr cinfo; +#endif /* NeedFunctionPrototypes */ +#else +LOCAL void +get_app0 (decompress_info_ptr cinfo) +#endif /* XIE_SUPPORTED */ +/* Process an APP0 marker */ +{ +#define JFIF_LEN 14 + INT32 length; + UINT8 b[JFIF_LEN]; + int buffp; +#ifdef XIE_SUPPORTED + int j; +#endif /* XIE_SUPPORTED */ + +#ifdef XIE_SUPPORTED + if ((length = get_2bytes(cinfo)) < 0) + return(-1); + length -= 2; +#else + length = get_2bytes(cinfo)-2; +#endif /* XIE_SUPPORTED */ + + /* See if a JFIF APP0 marker is present */ + + if (length >= JFIF_LEN) { + for (buffp = 0; buffp < JFIF_LEN; buffp++) { +#ifdef XIE_SUPPORTED + if ((j = JGETC(cinfo)) < 0) + return(-1); + b[buffp] = (UINT8) j; +#else + b[buffp] = (UINT8) JGETC(cinfo); +#endif /* XIE_SUPPORTED */ + } + length -= JFIF_LEN; + + if (b[0]==0x4A && b[1]==0x46 && b[2]==0x49 && b[3]==0x46 && b[4]==0) { + /* Found JFIF APP0 marker: check version */ + /* Major version must be 1 */ + if (b[5] != 1) +#ifdef XIE_SUPPORTED + return(XIE_ERR); +#else + ERREXIT2(cinfo->emethods, "Unsupported JFIF revision number %d.%02d", + b[5], b[6]); + /* Minor version should be 0..2, but try to process anyway if newer */ + if (b[6] > 2) + TRACEMS2(cinfo->emethods, 1, "Warning: unknown JFIF revision number %d.%02d", + b[5], b[6]); +#endif /* XIE_SUPPORTED */ + /* Save info */ + cinfo->density_unit = b[7]; + cinfo->X_density = (b[8] << 8) + b[9]; + cinfo->Y_density = (b[10] << 8) + b[11]; + /* Assume colorspace is YCbCr, unless UI has overridden me */ + if (cinfo->jpeg_color_space == CS_UNKNOWN) + cinfo->jpeg_color_space = CS_YCbCr; +#ifndef XIE_SUPPORTED + TRACEMS3(cinfo->emethods, 1, "JFIF APP0 marker, density %dx%d %d", + cinfo->X_density, cinfo->Y_density, cinfo->density_unit); + if (b[12] | b[13]) + TRACEMS2(cinfo->emethods, 1, " with %d x %d thumbnail image", + b[12], b[13]); + if (length != ((INT32) b[12] * (INT32) b[13] * (INT32) 3)) + TRACEMS1(cinfo->emethods, 1, + "Warning: thumbnail image size does not match data length %u", + (int) length); +#endif /* XIE_SUPPORTED */ + } else { +#ifndef XIE_SUPPORTED + TRACEMS1(cinfo->emethods, 1, "Unknown APP0 marker (not JFIF), length %u", + (int) length + JFIF_LEN); +#endif /* XIE_SUPPORTED */ + } + } else { +#ifndef XIE_SUPPORTED + TRACEMS1(cinfo->emethods, 1, "Short APP0 marker, length %u", (int) length); +#endif /* XIE_SUPPORTED */ + } + + while (length-- > 0) /* skip any remaining data */ +#ifdef XIE_SUPPORTED + if (JGETC(cinfo) < 0) + return(-1); +#else + (void) JGETC(cinfo); +#endif /* XIE_SUPPORTED */ + +#ifdef XIE_SUPPORTED + return(0); +#endif /* XIE_SUPPORTED */ +} + +#ifdef XIE_SUPPORTED +LOCAL int +#if NeedFunctionPrototypes +get_com (decompress_info_ptr cinfo) +#else +get_com (cinfo) + decompress_info_ptr cinfo; +#endif /* NeedFunctionPrototypes */ +#else +LOCAL void +get_com (decompress_info_ptr cinfo) +#endif /* XIE_SUPPORTED */ +/* Process a COM marker */ +/* Actually we just pass this off to an application-supplied routine */ +{ + INT32 length; + +#ifdef XIE_SUPPORTED + if ((length = get_2bytes(cinfo)) < 0) + return(-1); + length -= 2; +#else + length = get_2bytes(cinfo) - 2; + + TRACEMS1(cinfo->emethods, 1, "Comment, length %u", (int) length); +#endif /* XIE_SUPPORTED */ + + (*cinfo->methods->process_comment) (cinfo, (long) length); + +#ifdef XIE_SUPPORTED + return(0); +#endif /* XIE_SUPPORTED */ +} + +#ifdef XIE_SUPPORTED +LOCAL int +#if NeedFunctionPrototypes +get_sof (decompress_info_ptr cinfo, int code) +#else +get_sof (cinfo, code) + decompress_info_ptr cinfo; + int code; +#endif /* NeedFunctionPrototypes */ +#else +LOCAL void +get_sof (decompress_info_ptr cinfo, int code) +#endif /* XIE_SUPPORTED */ +/* Process a SOFn marker */ +{ + INT32 length; + short ci; + int c; + jpeg_component_info * compptr; +#ifdef XIE_SUPPORTED + int j; + INT32 k; +#endif /* XIE_SUPPORTED */ + + length = get_2bytes(cinfo); +#ifdef XIE_SUPPORTED + if (length < 0) + return(-1); +#endif /* XIE_SUPPORTED */ + +#ifdef XIE_SUPPORTED + if ((j = JGETC(cinfo)) < 0) + return(-1); + cinfo->data_precision = j; + if ((k = get_2bytes(cinfo)) < 0) + return(-1); + cinfo->image_height = k; + if ((k = get_2bytes(cinfo)) < 0) + return(-1); + cinfo->image_width = k; + if ((j = JGETC(cinfo)) < 0) + return(-1); + cinfo->num_components = j; +#else + cinfo->data_precision = JGETC(cinfo); + cinfo->image_height = get_2bytes(cinfo); + cinfo->image_width = get_2bytes(cinfo); + cinfo->num_components = JGETC(cinfo); + + TRACEMS4(cinfo->emethods, 1, + "Start Of Frame 0x%02x: width=%u, height=%u, components=%d", + code, (int) cinfo->image_width, (int) cinfo->image_height, + cinfo->num_components); +#endif /* XIE_SUPPORTED */ + + /* We don't support files in which the image height is initially specified */ + /* as 0 and is later redefined by DNL. As long as we have to check that, */ + /* might as well have a general sanity check. */ + if (cinfo->image_height <= 0 || cinfo->image_width <= 0 + || cinfo->num_components <= 0) +#ifdef XIE_SUPPORTED + return(XIE_ERR); +#else + ERREXIT(cinfo->emethods, "Empty JPEG image (DNL not supported)"); +#endif /* XIE_SUPPORTED */ + +#ifdef EIGHT_BIT_SAMPLES + if (cinfo->data_precision != 8) +#ifdef XIE_SUPPORTED + return(XIE_ERR); +#else + ERREXIT(cinfo->emethods, "Unsupported JPEG data precision"); +#endif /* XIE_SUPPORTED */ +#endif +#ifdef TWELVE_BIT_SAMPLES + if (cinfo->data_precision != 12) /* this needs more thought?? */ +#ifdef XIE_SUPPORTED + return(XIE_ERR); +#else + ERREXIT(cinfo->emethods, "Unsupported JPEG data precision"); +#endif /* XIE_SUPPORTED */ +#endif +#ifdef SIXTEEN_BIT_SAMPLES + if (cinfo->data_precision != 16) /* this needs more thought?? */ +#ifdef XIE_SUPPORTED + return(XIE_ERR); +#else + ERREXIT(cinfo->emethods, "Unsupported JPEG data precision"); +#endif /* XIE_SUPPORTED */ +#endif + + if (length != (cinfo->num_components * 3 + 8)) +#ifdef XIE_SUPPORTED + return(XIE_ERR); +#else + ERREXIT(cinfo->emethods, "Bogus SOF length"); +#endif /* XIE_SUPPORTED */ + +#ifdef XIE_SUPPORTED + cinfo->comp_info = (jpeg_component_info *) (*cinfo->emethods->d_alloc_small) + (cinfo, (cinfo->num_components * SIZEOF(jpeg_component_info))); + if (cinfo->comp_info == (jpeg_component_info *) NULL) + return(XIE_ERR); +#else + cinfo->comp_info = (jpeg_component_info *) (*cinfo->emethods->alloc_small) + (cinfo->num_components * SIZEOF(jpeg_component_info)); +#endif /* XIE_SUPPORTED */ + + for (ci = 0; ci < cinfo->num_components; ci++) { + compptr = &cinfo->comp_info[ci]; + compptr->component_index = ci; +#ifdef XIE_SUPPORTED + if ((j = JGETC(cinfo)) < 0) + return(-1); + compptr->component_id = j; + if ((c = JGETC(cinfo)) < 0) + return(-1); + compptr->h_samp_factor = (c >> 4) & 15; + compptr->v_samp_factor = (c ) & 15; + if ((j = JGETC(cinfo)) < 0) + return(-1); + compptr->quant_tbl_no = j; +#else + compptr->component_id = JGETC(cinfo); + c = JGETC(cinfo); + compptr->h_samp_factor = (c >> 4) & 15; + compptr->v_samp_factor = (c ) & 15; + compptr->quant_tbl_no = JGETC(cinfo); + + TRACEMS4(cinfo->emethods, 1, " Component %d: %dhx%dv q=%d", + compptr->component_id, compptr->h_samp_factor, + compptr->v_samp_factor, compptr->quant_tbl_no); +#endif /* XIE_SUPPORTED */ + } +#ifdef XIE_SUPPORTED + return(0); +#endif /* XIE_SUPPORTED */ +} + + +#ifdef XIE_SUPPORTED +LOCAL int +#if NeedFunctionPrototypes +get_sos (decompress_info_ptr cinfo) +#else +get_sos (cinfo) + decompress_info_ptr cinfo; +#endif /* NeedFunctionPrototypes */ +#else +LOCAL void +get_sos (decompress_info_ptr cinfo) +#endif /* XIE_SUPPORTED */ +/* Process a SOS marker */ +{ + INT32 length; + int i, ci, n, c, cc; + jpeg_component_info * compptr; + + length = get_2bytes(cinfo); +#ifdef XIE_SUPPORTED + if (length < 0) + return(-1); +#endif /* XIE_SUPPORTED */ + + n = JGETC(cinfo); /* Number of components */ +#ifdef XIE_SUPPORTED + if (n < 0) + return(-1); +#endif /* XIE_SUPPORTED */ + cinfo->comps_in_scan = n; + length -= 3; + + if (length != (n * 2 + 3) || n < 1 || n > MAX_COMPS_IN_SCAN) +#ifdef XIE_SUPPORTED + return(XIE_ERR); +#else + ERREXIT(cinfo->emethods, "Bogus SOS length"); + + TRACEMS1(cinfo->emethods, 1, "Start Of Scan: %d components", n); +#endif /* XIE_SUPPORTED */ + + for (i = 0; i < n; i++) { + cc = JGETC(cinfo); +#ifdef XIE_SUPPORTED + if (cc < 0) + return(-1); +#endif /* XIE_SUPPORTED */ + c = JGETC(cinfo); +#ifdef XIE_SUPPORTED + if (c < 0) + return(-1); +#endif /* XIE_SUPPORTED */ + length -= 2; + + for (ci = 0; ci < cinfo->num_components; ci++) + if (cc == cinfo->comp_info[ci].component_id) + break; + + if (ci >= cinfo->num_components) +#ifdef XIE_SUPPORTED + return(XIE_ERR); +#else + ERREXIT(cinfo->emethods, "Invalid component number in SOS"); +#endif /* XIE_SUPPORTED */ + + compptr = &cinfo->comp_info[ci]; + cinfo->cur_comp_info[i] = compptr; + compptr->dc_tbl_no = (c >> 4) & 15; + compptr->ac_tbl_no = (c ) & 15; + +#ifndef XIE_SUPPORTED + TRACEMS3(cinfo->emethods, 1, " c%d: [dc=%d ac=%d]", cc, + compptr->dc_tbl_no, compptr->ac_tbl_no); +#endif /* XIE_SUPPORTED */ + } + + while (length > 0) { +#ifdef XIE_SUPPORTED + if (JGETC(cinfo) < 0) + return(-1); +#else + (void) JGETC(cinfo); +#endif /* XIE_SUPPORTED */ + length--; + } +#ifdef XIE_SUPPORTED + return(0); +#endif /* XIE_SUPPORTED */ +} + + +LOCAL void +#ifdef XIE_SUPPORTED +#if NeedFunctionPrototypes +get_soi (decompress_info_ptr cinfo) +#else +get_soi (cinfo) + decompress_info_ptr cinfo; +#endif /* NeedFunctionPrototypes */ +/* Process an SOI marker */ +{ + int i; + +#else +get_soi (decompress_info_ptr cinfo) +/* Process an SOI marker */ +{ + int i; + + TRACEMS(cinfo->emethods, 1, "Start of Image"); +#endif /* XIE_SUPPORTED */ + + /* Reset all parameters that are defined to be reset by SOI */ + + for (i = 0; i < NUM_ARITH_TBLS; i++) { + cinfo->arith_dc_L[i] = 0; + cinfo->arith_dc_U[i] = 1; + cinfo->arith_ac_K[i] = 5; + } + cinfo->restart_interval = 0; + + cinfo->density_unit = 0; /* set default JFIF APP0 values */ + cinfo->X_density = 1; + cinfo->Y_density = 1; + + cinfo->CCIR601_sampling = FALSE; /* Assume non-CCIR sampling */ +} + + +LOCAL int +#ifdef XIE_SUPPORTED +#if NeedFunctionPrototypes +next_marker (decompress_info_ptr cinfo) +#else +next_marker (cinfo) + decompress_info_ptr cinfo; +#endif /* NeedFunctionPrototypes */ +#else +next_marker (decompress_info_ptr cinfo) +#endif /* XIE_SUPPORTED */ +/* Find the next JPEG marker */ +/* Note that the output might not be a valid marker code, */ +/* but it will never be 0 or FF */ +{ + int c, nbytes; + +#ifdef XIE_SUPPORTED + /* Save the location of the next marker (for restart) */ + cinfo->XIEnext_input_byte = cinfo->next_input_byte; + cinfo->XIEbytes_in_buffer = cinfo->bytes_in_buffer; +#endif /* XIE_SUPPORTED */ + nbytes = 0; + do { + do { /* skip any non-FF bytes */ + nbytes++; + c = JGETC(cinfo); +#ifdef XIE_SUPPORTED + if (c < 0) + return(-1); +#endif /* XIE_SUPPORTED */ + } while (c != 0xFF); + do { /* skip any duplicate FFs */ + /* we don't increment nbytes here since extra FFs are legal */ + c = JGETC(cinfo); +#ifdef XIE_SUPPORTED + if (c < 0) + return(-1); +#endif /* XIE_SUPPORTED */ + } while (c == 0xFF); + } while (c == 0); /* repeat if it was a stuffed FF/00 */ + +#ifndef XIE_SUPPORTED + if (nbytes != 1) + WARNMS2(cinfo->emethods, + "Corrupt JPEG data: %d extraneous bytes before marker 0x%02x", + nbytes-1, c); +#endif /* XIE_SUPPORTED */ + + return c; +} + + +#ifdef XIE_SUPPORTED +LOCAL int +#if NeedFunctionPrototypes +process_tables (decompress_info_ptr cinfo) +#else +process_tables (cinfo) + decompress_info_ptr cinfo; +#endif /* NeedFunctionPrototypes */ +/* Scan and process JPEG markers that can appear in any order */ +/* Return when an SOI, EOI, SOFn, or SOS is found */ +{ + int status; +#else +LOCAL JPEG_MARKER +process_tables (decompress_info_ptr cinfo) +/* Scan and process JPEG markers that can appear in any order */ +/* Return when an SOI, EOI, SOFn, or SOS is found */ +{ +#endif /* XIE_SUPPORTED */ + int c; + + while (TRUE) { + c = next_marker(cinfo); +#ifdef XIE_SUPPORTED + if (c < 0) + return(-1); +#endif /* XIE_SUPPORTED */ + + switch (c) { + case M_SOF0: + case M_SOF1: + case M_SOF2: + case M_SOF3: + case M_SOF5: + case M_SOF6: + case M_SOF7: + case M_JPG: + case M_SOF9: + case M_SOF10: + case M_SOF11: + case M_SOF13: + case M_SOF14: + case M_SOF15: + case M_SOI: + case M_EOI: + case M_SOS: +#ifdef XIE_SUPPORTED + return (c); +#else + return ((JPEG_MARKER) c); +#endif /* XIE_SUPPORTED */ + + case M_DHT: +#ifdef XIE_SUPPORTED + if ((status = get_dht(cinfo)) < 0) + return(status); +#else + get_dht(cinfo); +#endif /* XIE_SUPPORTED */ + break; + + case M_DAC: +#ifdef XIE_SUPPORTED + if ((status = get_dac(cinfo)) < 0) + return(status); +#else + get_dac(cinfo); +#endif /* XIE_SUPPORTED */ + break; + + case M_DQT: +#ifdef XIE_SUPPORTED + if ((status = get_dqt(cinfo)) < 0) + return(status); +#else + get_dqt(cinfo); +#endif /* XIE_SUPPORTED */ + break; + + case M_DRI: +#ifdef XIE_SUPPORTED + if ((status = get_dri(cinfo)) < 0) + return(status); +#else + get_dri(cinfo); +#endif /* XIE_SUPPORTED */ + break; + + case M_APP0: +#ifdef XIE_SUPPORTED + if ((status = get_app0(cinfo)) < 0) + return(status); +#else + get_app0(cinfo); +#endif /* XIE_SUPPORTED */ + break; + + case M_COM: +#ifdef XIE_SUPPORTED + if ((status = get_com(cinfo)) < 0) + return(status); +#else + get_com(cinfo); +#endif /* XIE_SUPPORTED */ + break; + + case M_RST0: /* these are all parameterless */ + case M_RST1: + case M_RST2: + case M_RST3: + case M_RST4: + case M_RST5: + case M_RST6: + case M_RST7: + case M_TEM: +#ifndef XIE_SUPPORTED + TRACEMS1(cinfo->emethods, 1, "Unexpected marker 0x%02x", c); +#endif /* XIE_SUPPORTED */ + break; + + default: /* must be DNL, DHP, EXP, APPn, JPGn, COM, or RESn */ +#ifdef XIE_SUPPORTED + if (skip_variable(cinfo, c) < 0) + return(-1); +#else + skip_variable(cinfo, c); +#endif /* XIE_SUPPORTED */ + break; + } + } +} + + + +/* + * Initialize and read the file header (everything through the SOF marker). + */ + +#ifdef XIE_SUPPORTED +METHODDEF int +#if NeedFunctionPrototypes +read_file_header (decompress_info_ptr cinfo) +#else +read_file_header (cinfo) + decompress_info_ptr cinfo; +#endif /* NeedFunctionPrototypes */ +{ + int i, j; + int status; +#else +METHODDEF void +read_file_header (decompress_info_ptr cinfo) +{ +#endif /* XIE_SUPPORTED */ + int c; + + /* Demand an SOI marker at the start of the file --- otherwise it's + * probably not a JPEG file at all. If the user interface wants to support + * nonstandard headers in front of the SOI, it must skip over them itself + * before calling jpeg_decompress(). + */ +#ifdef XIE_SUPPORTED + if (cinfo->XIErestart != XIE_RRFH) { /* don't read signature bytes on restart */ + if ((i = JGETC(cinfo)) < 0) + return(-1); + if ((j = JGETC(cinfo)) < 0) + return(-1); + if (i != 0xFF || j != M_SOI) + return(XIE_ERR); + + get_soi(cinfo); /* OK, process SOI */ + } +#else + if (JGETC(cinfo) != 0xFF || JGETC(cinfo) != M_SOI) + ERREXIT(cinfo->emethods, "Not a JPEG file"); + + get_soi(cinfo); /* OK, process SOI */ +#endif /* XIE_SUPPORTED */ + + /* Process markers until SOF */ + c = process_tables(cinfo); +#ifdef XIE_SUPPORTED + if (c < 0) + return(c); +#endif /* XIE_SUPPORTED */ + + switch (c) { + case M_SOF0: + case M_SOF1: +#ifdef XIE_SUPPORTED + if ((status = get_sof(cinfo, c)) < 0) + return(status); +#else + get_sof(cinfo, c); +#endif /* XIE_SUPPORTED */ + cinfo->arith_code = FALSE; + break; + + case M_SOF9: +#ifdef XIE_SUPPORTED + if ((status = get_sof(cinfo, c)) < 0) + return(status); +#else + get_sof(cinfo, c); +#endif /* XIE_SUPPORTED */ + cinfo->arith_code = TRUE; + break; + + default: +#ifdef XIE_SUPPORTED + return(XIE_ERR); +#else + ERREXIT1(cinfo->emethods, "Unsupported SOF marker type 0x%02x", c); +#endif /* XIE_SUPPORTED */ + break; + } + + /* Figure out what colorspace we have */ + /* (too bad the JPEG committee didn't provide a real way to specify this) */ + + switch (cinfo->num_components) { + case 1: + cinfo->jpeg_color_space = CS_GRAYSCALE; + break; + + case 3: + /* if we saw a JFIF marker, leave it set to YCbCr; */ + /* also leave it alone if UI has provided a value */ + if (cinfo->jpeg_color_space == CS_UNKNOWN) { + short cid0 = cinfo->comp_info[0].component_id; + short cid1 = cinfo->comp_info[1].component_id; + short cid2 = cinfo->comp_info[2].component_id; + + if (cid0 == 1 && cid1 == 2 && cid2 == 3) + cinfo->jpeg_color_space = CS_YCbCr; /* assume it's JFIF w/out marker */ + else if (cid0 == 1 && cid1 == 4 && cid2 == 5) + cinfo->jpeg_color_space = CS_YIQ; /* prototype's YIQ matrix */ + else { +#ifndef XIE_SUPPORTED + TRACEMS3(cinfo->emethods, 1, + "Unrecognized component IDs %d %d %d, assuming YCbCr", + cid0, cid1, cid2); +#endif /* XIE_SUPPORTED */ + cinfo->jpeg_color_space = CS_YCbCr; + } + } + break; + + case 4: + cinfo->jpeg_color_space = CS_CMYK; + break; + + default: + cinfo->jpeg_color_space = CS_UNKNOWN; + break; + } +#ifdef XIE_SUPPORTED + return(0); +#endif /* XIE_SUPPORTED */ +} + + +/* + * Read the start of a scan (everything through the SOS marker). + * Return TRUE if find SOS, FALSE if find EOI. + */ + +#ifdef XIE_SUPPORTED +METHODDEF int +#if NeedFunctionPrototypes +read_scan_header (decompress_info_ptr cinfo) +#else +read_scan_header (cinfo) + decompress_info_ptr cinfo; +#endif /* NeedFunctionPrototypes */ +#else +METHODDEF boolean +read_scan_header (decompress_info_ptr cinfo) +#endif /* XIE_SUPPORTED */ +{ + int c; + + /* Process markers until SOS or EOI */ + c = process_tables(cinfo); +#ifdef XIE_SUPPORTED + if (c < 0) + return(c); +#endif /* XIE_SUPPORTED */ + + switch (c) { + case M_SOS: +#ifdef XIE_SUPPORTED + return(get_sos(cinfo)); /* 0, OK; -1, read error */ +#else + get_sos(cinfo); + return TRUE; +#endif /* XIE_SUPPORTED */ + + case M_EOI: +#ifndef XIE_SUPPORTED + TRACEMS(cinfo->emethods, 1, "End Of Image"); +#endif /* XIE_SUPPORTED */ + return FALSE; + + default: +#ifdef XIE_SUPPORTED + return(XIE_ERR); +#else + ERREXIT1(cinfo->emethods, "Unexpected marker 0x%02x", c); +#endif /* XIE_SUPPORTED */ + break; + } +#ifdef XIE_SUPPORTED + return(0); +#else + return FALSE; /* keeps lint happy */ +#endif /* XIE_SUPPORTED */ +} + + +/* + * The entropy decoder calls this routine if it finds a marker other than + * the restart marker it was expecting. (This code is *not* used unless + * a nonzero restart interval has been declared.) The passed parameter is + * the marker code actually found (might be anything, except 0 or FF). + * The desired restart marker is that indicated by cinfo->next_restart_num. + * This routine is supposed to apply whatever error recovery strategy seems + * appropriate in order to position the input stream to the next data segment. + * For some file formats (eg, TIFF) extra information such as tile boundary + * pointers may be available to help in this decision. + * + * This implementation is substantially constrained by wanting to treat the + * input as a data stream; this means we can't back up. (For instance, we + * generally can't fseek() if the input is a Unix pipe.) Therefore, we have + * only the following actions to work with: + * 1. Do nothing, let the entropy decoder resume at next byte of file. + * 2. Read forward until we find another marker, discarding intervening + * data. (In theory we could look ahead within the current bufferload, + * without having to discard data if we don't find the desired marker. + * This idea is not implemented here, in part because it makes behavior + * dependent on buffer size and chance buffer-boundary positions.) + * 3. Push back the passed marker (with JUNGETC). This will cause the + * entropy decoder to process an empty data segment, inserting dummy + * zeroes, and then re-read the marker we pushed back. + * #2 is appropriate if we think the desired marker lies ahead, while #3 is + * appropriate if the found marker is a future restart marker (indicating + * that we have missed the desired restart marker, probably because it got + * corrupted). + + * We apply #2 or #3 if the found marker is a restart marker no more than + * two counts behind or ahead of the expected one. We also apply #2 if the + * found marker is not a legal JPEG marker code (it's certainly bogus data). + * If the found marker is a restart marker more than 2 counts away, we do #1 + * (too much risk that the marker is erroneous; with luck we will be able to + * resync at some future point). + * For any valid non-restart JPEG marker, we apply #3. This keeps us from + * overrunning the end of a scan. An implementation limited to single-scan + * files might find it better to apply #2 for markers other than EOI, since + * any other marker would have to be bogus data in that case. + */ + +#ifdef XIE_SUPPORTED +METHODDEF int +#if NeedFunctionPrototypes +resync_to_restart (decompress_info_ptr cinfo, int marker) +#else +resync_to_restart (cinfo, marker) + decompress_info_ptr cinfo; + int marker; +#endif /* NeedFunctionPrototypes */ +#else +METHODDEF void +resync_to_restart (decompress_info_ptr cinfo, int marker) +#endif /* XIE_SUPPORTED */ +{ + int desired = cinfo->next_restart_num; + int action = 1; + + /* Always put up a warning. */ +#ifndef XIE_SUPPORTED + WARNMS2(cinfo->emethods, + "Corrupt JPEG data: found 0x%02x marker instead of RST%d", + marker, desired); +#endif /* XIE_SUPPORTED */ + /* Outer loop handles repeated decision after scanning forward. */ + for (;;) { + if (marker < (int) M_SOF0) + action = 2; /* invalid marker */ + else if (marker < (int) M_RST0 || marker > (int) M_RST7) + action = 3; /* valid non-restart marker */ + else { + if (marker == ((int) M_RST0 + ((desired+1) & 7)) || + marker == ((int) M_RST0 + ((desired+2) & 7))) + action = 3; /* one of the next two expected restarts */ + else if (marker == ((int) M_RST0 + ((desired-1) & 7)) || + marker == ((int) M_RST0 + ((desired-2) & 7))) + action = 2; /* a prior restart, so advance */ + else + action = 1; /* desired restart or too far away */ + } +#ifndef XIE_SUPPORTED + TRACEMS2(cinfo->emethods, 4, + "At marker 0x%02x, recovery action %d", marker, action); +#endif /* XIE_SUPPORTED */ + switch (action) { + case 1: + /* Let entropy decoder resume processing. */ +#ifdef XIE_SUPPORTED + return(0); +#else + return; +#endif /* XIE_SUPPORTED */ + case 2: + /* Scan to the next marker, and repeat the decision loop. */ + marker = next_marker(cinfo); +#ifdef XIE_SUPPORTED + if (marker < 0) + return(-1); +#endif /* XIE_SUPPORTED */ + break; + case 3: + /* Put back this marker & return. */ + /* Entropy decoder will be forced to process an empty segment. */ + JUNGETC(marker, cinfo); + JUNGETC(0xFF, cinfo); +#ifdef XIE_SUPPORTED + return(0); +#else + return; +#endif /* XIE_SUPPORTED */ + } + } +} + + +/* + * Finish up after a compressed scan (series of read_jpeg_data calls); + * prepare for another read_scan_header call. + */ + +#ifndef XIE_SUPPORTED +METHODDEF void +#ifdef XIE_SUPPORTED +#if NeedFunctionPrototypes +read_scan_trailer (decompress_info_ptr cinfo) +#else +read_scan_trailer (cinfo) + decompress_info_ptr cinfo; +#endif /* NeedFunctionPrototypes */ +#else +read_scan_trailer (decompress_info_ptr cinfo) +#endif /* XIE_SUPPORTED */ +{ + /* no work needed */ +} +#endif /* XIE_SUPPORTED */ + +/* + * Finish up at the end of the file. + */ + +#ifndef XIE_SUPPORTED +METHODDEF void +#ifdef XIE_SUPPORTED +#if NeedFunctionPrototypes +read_file_trailer (decompress_info_ptr cinfo) +#else +read_file_trailer (cinfo) + decompress_info_ptr cinfo; +#endif /* NeedFunctionPrototypes */ +#else +read_file_trailer (decompress_info_ptr cinfo) +#endif /* XIE_SUPPORTED */ +{ + /* no work needed */ +} +#endif /* XIE_SUPPORTED */ + +/* + * The method selection routine for standard JPEG header reading. + * Note that this must be called by the user interface before calling + * jpeg_decompress. When a non-JFIF file is to be decompressed (TIFF, + * perhaps), the user interface must discover the file type and call + * the appropriate method selection routine. + */ + +GLOBAL void +#ifdef XIE_SUPPORTED +#if NeedFunctionPrototypes +jselrjfif (decompress_info_ptr cinfo) +#else +jselrjfif (cinfo) + decompress_info_ptr cinfo; +#endif /* NeedFunctionPrototypes */ +#else +jselrjfif (decompress_info_ptr cinfo) +#endif /* XIE_SUPPORTED */ +{ + cinfo->methods->read_file_header = read_file_header; + cinfo->methods->read_scan_header = read_scan_header; + /* For JFIF/raw-JPEG format, the user interface supplies read_jpeg_data. */ +#ifndef XIE_SUPPORTED +#if NOTDEF + cinfo->methods->read_jpeg_data = read_jpeg_data; +#endif +#endif /* XIE_SUPPORTED */ + cinfo->methods->resync_to_restart = resync_to_restart; +#ifndef XIE_SUPPORTED + cinfo->methods->read_scan_trailer = read_scan_trailer; + cinfo->methods->read_file_trailer = read_file_trailer; +#endif /* XIE_SUPPORTED */ +} + +#endif /* JFIF_SUPPORTED */ |