Path: blob/master/thirdparty/libjpeg-turbo/src/jdatasrc-tj.c
9904 views
/*1* jdatasrc-tj.c2*3* This file was part of the Independent JPEG Group's software:4* Copyright (C) 1994-1996, Thomas G. Lane.5* Modified 2009-2011 by Guido Vollbeding.6* libjpeg-turbo Modifications:7* Copyright (C) 2011, 2016, 2019, 2023, D. R. Commander.8* For conditions of distribution and use, see the accompanying README.ijg9* file.10*11* This file contains decompression data source routines for the case of12* reading JPEG data from memory or from a file (or any stdio stream).13* While these routines are sufficient for most applications,14* some will want to use a different source manager.15* IMPORTANT: we assume that fread() will correctly transcribe an array of16* JOCTETs from 8-bit-wide elements on external storage. If char is wider17* than 8 bits on your machine, you may need to do some tweaking.18*/1920/* this is not a core library module, so it doesn't define JPEG_INTERNALS */21#include "jinclude.h"22#include "jpeglib.h"23#include "jerror.h"2425void jpeg_mem_src_tj(j_decompress_ptr cinfo, const unsigned char *inbuffer,26size_t insize);272829/*30* Initialize source --- called by jpeg_read_header31* before any data is actually read.32*/3334METHODDEF(void)35init_mem_source(j_decompress_ptr cinfo)36{37/* no work necessary here */38}394041/*42* Fill the input buffer --- called whenever buffer is emptied.43*44* In typical applications, this should read fresh data into the buffer45* (ignoring the current state of next_input_byte & bytes_in_buffer),46* reset the pointer & count to the start of the buffer, and return TRUE47* indicating that the buffer has been reloaded. It is not necessary to48* fill the buffer entirely, only to obtain at least one more byte.49*50* There is no such thing as an EOF return. If the end of the file has been51* reached, the routine has a choice of ERREXIT() or inserting fake data into52* the buffer. In most cases, generating a warning message and inserting a53* fake EOI marker is the best course of action --- this will allow the54* decompressor to output however much of the image is there. However,55* the resulting error message is misleading if the real problem is an empty56* input file, so we handle that case specially.57*58* In applications that need to be able to suspend compression due to input59* not being available yet, a FALSE return indicates that no more data can be60* obtained right now, but more may be forthcoming later. In this situation,61* the decompressor will return to its caller (with an indication of the62* number of scanlines it has read, if any). The application should resume63* decompression after it has loaded more data into the input buffer. Note64* that there are substantial restrictions on the use of suspension --- see65* the documentation.66*67* When suspending, the decompressor will back up to a convenient restart point68* (typically the start of the current MCU). next_input_byte & bytes_in_buffer69* indicate where the restart point will be if the current call returns FALSE.70* Data beyond this point must be rescanned after resumption, so move it to71* the front of the buffer rather than discarding it.72*/7374METHODDEF(boolean)75fill_mem_input_buffer(j_decompress_ptr cinfo)76{77static const JOCTET mybuffer[4] = {78(JOCTET)0xFF, (JOCTET)JPEG_EOI, 0, 079};8081/* The whole JPEG data is expected to reside in the supplied memory82* buffer, so any request for more data beyond the given buffer size83* is treated as an error.84*/85WARNMS(cinfo, JWRN_JPEG_EOF);8687/* Insert a fake EOI marker */8889cinfo->src->next_input_byte = mybuffer;90cinfo->src->bytes_in_buffer = 2;9192return TRUE;93}949596/*97* Skip data --- used to skip over a potentially large amount of98* uninteresting data (such as an APPn marker).99*100* Writers of suspendable-input applications must note that skip_input_data101* is not granted the right to give a suspension return. If the skip extends102* beyond the data currently in the buffer, the buffer can be marked empty so103* that the next read will cause a fill_input_buffer call that can suspend.104* Arranging for additional bytes to be discarded before reloading the input105* buffer is the application writer's problem.106*/107108METHODDEF(void)109skip_input_data(j_decompress_ptr cinfo, long num_bytes)110{111struct jpeg_source_mgr *src = cinfo->src;112113/* Just a dumb implementation for now. Could use fseek() except114* it doesn't work on pipes. Not clear that being smart is worth115* any trouble anyway --- large skips are infrequent.116*/117if (num_bytes > 0) {118while (num_bytes > (long)src->bytes_in_buffer) {119num_bytes -= (long)src->bytes_in_buffer;120(void)(*src->fill_input_buffer) (cinfo);121/* note we assume that fill_input_buffer will never return FALSE,122* so suspension need not be handled.123*/124}125src->next_input_byte += (size_t)num_bytes;126src->bytes_in_buffer -= (size_t)num_bytes;127}128}129130131/*132* An additional method that can be provided by data source modules is the133* resync_to_restart method for error recovery in the presence of RST markers.134* For the moment, this source module just uses the default resync method135* provided by the JPEG library. That method assumes that no backtracking136* is possible.137*/138139140/*141* Terminate source --- called by jpeg_finish_decompress142* after all data has been read. Often a no-op.143*144* NB: *not* called by jpeg_abort or jpeg_destroy; surrounding145* application must deal with any cleanup that should happen even146* for error exit.147*/148149METHODDEF(void)150term_source(j_decompress_ptr cinfo)151{152/* no work necessary here */153}154155156/*157* Prepare for input from a supplied memory buffer.158* The buffer must contain the whole JPEG data.159*/160161GLOBAL(void)162jpeg_mem_src_tj(j_decompress_ptr cinfo, const unsigned char *inbuffer,163size_t insize)164{165struct jpeg_source_mgr *src;166167if (inbuffer == NULL || insize == 0) /* Treat empty input as fatal error */168ERREXIT(cinfo, JERR_INPUT_EMPTY);169170/* The source object is made permanent so that a series of JPEG images171* can be read from the same buffer by calling jpeg_mem_src only before172* the first one.173*/174if (cinfo->src == NULL) { /* first time for this JPEG object? */175cinfo->src = (struct jpeg_source_mgr *)176(*cinfo->mem->alloc_small) ((j_common_ptr)cinfo, JPOOL_PERMANENT,177sizeof(struct jpeg_source_mgr));178} else if (cinfo->src->init_source != init_mem_source) {179/* It is unsafe to reuse the existing source manager unless it was created180* by this function.181*/182ERREXIT(cinfo, JERR_BUFFER_SIZE);183}184185src = cinfo->src;186src->init_source = init_mem_source;187src->fill_input_buffer = fill_mem_input_buffer;188src->skip_input_data = skip_input_data;189src->resync_to_restart = jpeg_resync_to_restart; /* use default method */190src->term_source = term_source;191src->bytes_in_buffer = insize;192src->next_input_byte = (const JOCTET *)inbuffer;193}194195196