LCOV - code coverage report
Current view: directory - frmts/gtiff/libtiff - tif_ojpeg.c (source / functions) Found Hit Coverage
Test: gdal_filtered.info Lines: 1219 0 0.0 %
Date: 2010-01-09 Functions: 63 0 0.0 %

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

Generated by: LCOV version 1.7