25
|
1 /*******************************************************************************
|
|
2 * Copyright (c) 2000, 2006 IBM Corporation and others.
|
|
3 * All rights reserved. This program and the accompanying materials
|
|
4 * are made available under the terms of the Eclipse Public License v1.0
|
|
5 * which accompanies this distribution, and is available at
|
|
6 * http://www.eclipse.org/legal/epl-v10.html
|
|
7 *
|
|
8 * Contributors:
|
|
9 * IBM Corporation - initial API and implementation
|
|
10 * Port to the D programming language:
|
|
11 * Frank Benoit <benoit@tionex.de>
|
|
12 *******************************************************************************/
|
|
13 module org.eclipse.swt.internal.image.JPEGDecoder;
|
|
14
|
|
15 import org.eclipse.swt.SWT;
|
|
16 import java.io.InputStream;
|
|
17 import org.eclipse.swt.internal.image.LEDataInputStream;
|
|
18 import org.eclipse.swt.graphics.ImageData;
|
|
19 import org.eclipse.swt.graphics.ImageLoader;
|
|
20 import org.eclipse.swt.graphics.ImageLoaderEvent;
|
|
21 import org.eclipse.swt.graphics.PaletteData;
|
|
22 import org.eclipse.swt.graphics.RGB;
|
|
23 import java.lang.all;
|
|
24
|
|
25 import tango.core.Exception;
|
|
26 import tango.util.Convert;
|
|
27
|
|
28 public class JPEGDecoder {
|
|
29
|
|
30 static const int DCTSIZE = 8;
|
|
31 static const int DCTSIZE2 = 64;
|
|
32 static const int NUM_QUANT_TBLS = 4;
|
|
33 static const int NUM_HUFF_TBLS = 4;
|
|
34 static const int NUM_ARITH_TBLS = 16;
|
|
35 static const int MAX_COMPS_IN_SCAN = 4;
|
|
36 static const int MAX_COMPONENTS = 10;
|
|
37 static const int MAX_SAMP_FACTOR = 4;
|
|
38 static const int D_MAX_BLOCKS_IN_MCU = 10;
|
|
39 static const int HUFF_LOOKAHEAD = 8;
|
|
40 static const int MAX_Q_COMPS = 4;
|
|
41 static const int IFAST_SCALE_BITS = 2;
|
|
42 static const int MAXJSAMPLE = 255;
|
|
43 static const int CENTERJSAMPLE = 128;
|
|
44 static const int MIN_GET_BITS = 32-7;
|
|
45 static const int INPUT_BUFFER_SIZE = 4096;
|
|
46
|
|
47 static const int SCALEBITS = 16; /* speediest right-shift on some machines */
|
|
48 static const int ONE_HALF = 1 << (SCALEBITS-1);
|
|
49
|
|
50 static const int RGB_RED = 2; /* Offset of Red in an RGB scanline element */
|
|
51 static const int RGB_GREEN = 1; /* Offset of Green */
|
|
52 static const int RGB_BLUE = 0; /* Offset of Blue */
|
|
53 static const int RGB_PIXELSIZE = 3;
|
|
54
|
|
55 static const int JBUF_PASS_THRU = 0;
|
|
56 static const int JBUF_SAVE_SOURCE = 1; /* Run source subobject only, save output */
|
|
57 static const int JBUF_CRANK_DEST = 2; /* Run dest subobject only, using saved data */
|
|
58 static const int JBUF_SAVE_AND_PASS = 3;
|
|
59
|
|
60 static const int JPEG_MAX_DIMENSION = 65500;
|
|
61 static const int BITS_IN_JSAMPLE = 8;
|
|
62
|
|
63 static const int JDITHER_NONE = 0; /* no dithering */
|
|
64 static const int JDITHER_ORDERED = 1; /* simple ordered dither */
|
|
65 static const int JDITHER_FS = 2;
|
|
66
|
|
67 static const int JDCT_ISLOW = 0; /* slow but accurate integer algorithm */
|
|
68 static const int JDCT_IFAST = 1; /* faster, less accurate integer method */
|
|
69 static const int JDCT_FLOAT = 2; /* floating-point: accurate, fast on fast HW */
|
|
70 static const int JDCT_DEFAULT = JDCT_ISLOW;
|
|
71
|
|
72 static const int JCS_UNKNOWN = 0; /* error/unspecified */
|
|
73 static const int JCS_GRAYSCALE = 1; /* monochrome */
|
|
74 static const int JCS_RGB = 2; /* red/green/blue */
|
|
75 static const int JCS_YCbCr = 3; /* Y/Cb/Cr (also known as YUV) */
|
|
76 static const int JCS_CMYK = 4; /* C/M/Y/K */
|
|
77 static const int JCS_YCCK = 5; /* Y/Cb/Cr/K */
|
|
78
|
|
79 static const int SAVED_COEFS = 6;
|
|
80 static const int Q01_POS = 1;
|
|
81 static const int Q10_POS = 8;
|
|
82 static const int Q20_POS = 16;
|
|
83 static const int Q11_POS = 9;
|
|
84 static const int Q02_POS = 2;
|
|
85
|
|
86 static const int CTX_PREPARE_FOR_IMCU = 0; /* need to prepare for MCU row */
|
|
87 static const int CTX_PROCESS_IMCU = 1; /* feeding iMCU to postprocessor */
|
|
88 static const int CTX_POSTPONED_ROW = 2; /* feeding postponed row group */
|
|
89
|
|
90 static const int APP0_DATA_LEN = 14; /* Length of interesting data in APP0 */
|
|
91 static const int APP14_DATA_LEN = 12; /* Length of interesting data in APP14 */
|
|
92 static const int APPN_DATA_LEN = 14; /* Must be the largest of the above!! */
|
|
93
|
|
94 /* markers */
|
|
95 static const int M_SOF0 = 0xc0;
|
|
96 static const int M_SOF1 = 0xc1;
|
|
97 static const int M_SOF2 = 0xc2;
|
|
98 static const int M_SOF3 = 0xc3;
|
|
99 static const int M_SOF5 = 0xc5;
|
|
100 static const int M_SOF6 = 0xc6;
|
|
101 static const int M_SOF7 = 0xc7;
|
|
102 static const int M_JPG = 0xc8;
|
|
103 static const int M_SOF9 = 0xc9;
|
|
104 static const int M_SOF10 = 0xca;
|
|
105 static const int M_SOF11 = 0xcb;
|
|
106 static const int M_SOF13 = 0xcd;
|
|
107 static const int M_SOF14 = 0xce;
|
|
108 static const int M_SOF15 = 0xcf;
|
|
109 static const int M_DHT = 0xc4;
|
|
110 static const int M_DAC = 0xcc;
|
|
111 static const int M_RST0 = 0xd0;
|
|
112 static const int M_RST1 = 0xd1;
|
|
113 static const int M_RST2 = 0xd2;
|
|
114 static const int M_RST3 = 0xd3;
|
|
115 static const int M_RST4 = 0xd4;
|
|
116 static const int M_RST5 = 0xd5;
|
|
117 static const int M_RST6 = 0xd6;
|
|
118 static const int M_RST7 = 0xd7;
|
|
119 static const int M_SOI = 0xd8;
|
|
120 static const int M_EOI = 0xd9;
|
|
121 static const int M_SOS = 0xda;
|
|
122 static const int M_DQT = 0xdb;
|
|
123 static const int M_DNL = 0xdc;
|
|
124 static const int M_DRI = 0xdd;
|
|
125 static const int M_DHP = 0xde;
|
|
126 static const int M_EXP = 0xdf;
|
|
127 static const int M_APP0 = 0xe0;
|
|
128 static const int M_APP1 = 0xe1;
|
|
129 static const int M_APP2 = 0xe2;
|
|
130 static const int M_APP3 = 0xe3;
|
|
131 static const int M_APP4 = 0xe4;
|
|
132 static const int M_APP5 = 0xe5;
|
|
133 static const int M_APP6 = 0xe6;
|
|
134 static const int M_APP7 = 0xe7;
|
|
135 static const int M_APP8 = 0xe8;
|
|
136 static const int M_APP9 = 0xe9;
|
|
137 static const int M_APP10 = 0xea;
|
|
138 static const int M_APP11 = 0xeb;
|
|
139 static const int M_APP12 = 0xec;
|
|
140 static const int M_APP13 = 0xed;
|
|
141 static const int M_APP14 = 0xee;
|
|
142 static const int M_APP15 = 0xef;
|
|
143 static const int M_JPG0 = 0xf0;
|
|
144 static const int M_JPG13 = 0xfd;
|
|
145 static const int M_COM = 0xfe;
|
|
146 static const int M_TEM = 0x01;
|
|
147 static const int M_ERROR = 0x100;
|
|
148
|
|
149 /* Values of global_state field (jdapi.c has some dependencies on ordering!) */
|
|
150 static const int CSTATE_START = 100; /* after create_compress */
|
|
151 static const int CSTATE_SCANNING = 101; /* start_compress done, write_scanlines OK */
|
|
152 static const int CSTATE_RAW_OK = 102; /* start_compress done, write_raw_data OK */
|
|
153 static const int CSTATE_WRCOEFS = 103; /* jpeg_write_coefficients done */
|
|
154 static const int DSTATE_START = 200; /* after create_decompress */
|
|
155 static const int DSTATE_INHEADER = 201; /* reading header markers, no SOS yet */
|
|
156 static const int DSTATE_READY = 202; /* found SOS, ready for start_decompress */
|
|
157 static const int DSTATE_PRELOAD = 203; /* reading multiscan file in start_decompress*/
|
|
158 static const int DSTATE_PRESCAN = 204; /* performing dummy pass for 2-pass quant */
|
|
159 static const int DSTATE_SCANNING = 205; /* start_decompress done, read_scanlines OK */
|
|
160 static const int DSTATE_RAW_OK = 206; /* start_decompress done, read_raw_data OK */
|
|
161 static const int DSTATE_BUFIMAGE = 207; /* expecting jpeg_start_output */
|
|
162 static const int DSTATE_BUFPOST = 208; /* looking for SOS/EOI in jpeg_finish_output */
|
|
163 static const int DSTATE_RDCOEFS = 209; /* reading file in jpeg_read_coefficients */
|
|
164 static const int DSTATE_STOPPING = 210; /* looking for EOI in jpeg_finish_decompress */
|
|
165
|
|
166 static const int JPEG_REACHED_SOS = 1; /* Reached start of new scan */
|
|
167 static const int JPEG_REACHED_EOI = 2; /* Reached end of image */
|
|
168 static const int JPEG_ROW_COMPLETED = 3; /* Completed one iMCU row */
|
|
169 static const int JPEG_SCAN_COMPLETED = 4; /* Completed last iMCU row of a scan */
|
|
170
|
|
171 static const int JPEG_SUSPENDED = 0; /* Suspended due to lack of input data */
|
|
172 static const int JPEG_HEADER_OK = 1; /* Found valid image datastream */
|
|
173 static const int JPEG_HEADER_TABLES_ONLY = 2; /* Found valid table-specs-only datastream */
|
|
174
|
|
175 /* Function pointers */
|
|
176 static const int DECOMPRESS_DATA = 0;
|
|
177 static const int DECOMPRESS_SMOOTH_DATA = 1;
|
|
178 static const int DECOMPRESS_ONEPASS = 2;
|
|
179
|
|
180 static const int CONSUME_DATA = 0;
|
|
181 static const int DUMMY_CONSUME_DATA = 1;
|
|
182
|
|
183 static const int PROCESS_DATA_SIMPLE_MAIN = 0;
|
|
184 static const int PROCESS_DATA_CONTEXT_MAIN = 1;
|
|
185 static const int PROCESS_DATA_CRANK_POST = 2;
|
|
186
|
|
187 static const int POST_PROCESS_1PASS = 0;
|
|
188 static const int POST_PROCESS_DATA_UPSAMPLE = 1;
|
|
189
|
|
190 static const int NULL_CONVERT = 0;
|
|
191 static const int GRAYSCALE_CONVERT = 1;
|
|
192 static const int YCC_RGB_CONVERT = 2;
|
|
193 static const int GRAY_RGB_CONVERT = 3;
|
|
194 static const int YCCK_CMYK_CONVERT = 4;
|
|
195
|
|
196 static const int NOOP_UPSAMPLE = 0;
|
|
197 static const int FULLSIZE_UPSAMPLE = 1;
|
|
198 static const int H2V1_FANCY_UPSAMPLE = 2;
|
|
199 static const int H2V1_UPSAMPLE = 3;
|
|
200 static const int H2V2_FANCY_UPSAMPLE = 4;
|
|
201 static const int H2V2_UPSAMPLE = 5;
|
|
202 static const int INT_UPSAMPLE = 6;
|
|
203
|
|
204 static const int INPUT_CONSUME_INPUT = 0;
|
|
205 static const int COEF_CONSUME_INPUT = 1;
|
|
206
|
|
207 static int extend_test[] = /* entry n is 2**(n-1) */
|
|
208 [
|
|
209 0, 0x0001, 0x0002, 0x0004, 0x0008, 0x0010, 0x0020, 0x0040, 0x0080,
|
|
210 0x0100, 0x0200, 0x0400, 0x0800, 0x1000, 0x2000, 0x4000
|
|
211 ];
|
|
212
|
|
213 static int extend_offset[] = /* entry n is (-1 << n) + 1 */
|
|
214 [
|
|
215 0, ((-1)<<1) + 1, ((-1)<<2) + 1, ((-1)<<3) + 1, ((-1)<<4) + 1,
|
|
216 ((-1)<<5) + 1, ((-1)<<6) + 1, ((-1)<<7) + 1, ((-1)<<8) + 1,
|
|
217 ((-1)<<9) + 1, ((-1)<<10) + 1, ((-1)<<11) + 1, ((-1)<<12) + 1,
|
|
218 ((-1)<<13) + 1, ((-1)<<14) + 1, ((-1)<<15) + 1
|
|
219 ];
|
|
220
|
|
221 static int jpeg_natural_order[] = [
|
|
222 0, 1, 8, 16, 9, 2, 3, 10,
|
|
223 17, 24, 32, 25, 18, 11, 4, 5,
|
|
224 12, 19, 26, 33, 40, 48, 41, 34,
|
|
225 27, 20, 13, 6, 7, 14, 21, 28,
|
|
226 35, 42, 49, 56, 57, 50, 43, 36,
|
|
227 29, 22, 15, 23, 30, 37, 44, 51,
|
|
228 58, 59, 52, 45, 38, 31, 39, 46,
|
|
229 53, 60, 61, 54, 47, 55, 62, 63,
|
|
230 63, 63, 63, 63, 63, 63, 63, 63, /* extra entries for safety in decoder */
|
|
231 63, 63, 63, 63, 63, 63, 63, 63
|
|
232 ];
|
|
233
|
|
234 static final class JQUANT_TBL {
|
|
235 /* This array gives the coefficient quantizers in natural array order
|
|
236 * (not the zigzag order in which they are stored in a JPEG DQT marker).
|
|
237 * CAUTION: IJG versions prior to v6a kept this array in zigzag order.
|
|
238 */
|
|
239 short[DCTSIZE2] quantval;// = new short[DCTSIZE2]; /* quantization step for each coefficient */
|
|
240 /* This field is used only during compression. It's initialized false when
|
|
241 * the table is created, and set true when it's been output to the file.
|
|
242 * You could suppress output of a table by setting this to true.
|
|
243 * (See jpeg_suppress_tables for an example.)
|
|
244 */
|
|
245 bool sent_table; /* true when table has been output */
|
|
246 }
|
|
247
|
|
248 static final class JHUFF_TBL {
|
|
249 /* These two fields directly represent the contents of a JPEG DHT marker */
|
|
250 byte[17] bits;// = new byte[17]; /* bits[k] = # of symbols with codes of */
|
|
251 /* length k bits; bits[0] is unused */
|
|
252 byte[256] huffval;// = new byte[256]; /* The symbols, in order of incr code length */
|
|
253 /* This field is used only during compression. It's initialized false when
|
|
254 * the table is created, and set true when it's been output to the file.
|
|
255 * You could suppress output of a table by setting this to true.
|
|
256 * (See jpeg_suppress_tables for an example.)
|
|
257 */
|
|
258 bool sent_table; /* true when table has been output */
|
|
259 }
|
|
260
|
|
261 static final class bitread_perm_state { /* Bitreading state saved across MCUs */
|
|
262 int get_buffer; /* current bit-extraction buffer */
|
|
263 int bits_left; /* # of unused bits in it */
|
|
264 }
|
|
265
|
|
266 static final class bitread_working_state { /* Bitreading working state within an MCU */
|
|
267 /* Current data source location */
|
|
268 /* We need a copy, rather than munging the original, in case of suspension */
|
|
269 byte[] buffer; /* => next byte to read from source */
|
|
270 int bytes_offset;
|
|
271 int bytes_in_buffer; /* # of bytes remaining in source buffer */
|
|
272 /* Bit input buffer --- note these values are kept in register variables,
|
|
273 * not in this struct, inside the inner loops.
|
|
274 */
|
|
275 int get_buffer; /* current bit-extraction buffer */
|
|
276 int bits_left; /* # of unused bits in it */
|
|
277 /* Pointer needed by jpeg_fill_bit_buffer. */
|
|
278 jpeg_decompress_struct cinfo; /* back link to decompress master record */
|
|
279 }
|
|
280
|
|
281 static final class savable_state {
|
|
282 int EOBRUN; //Note that this is only used in the progressive case
|
|
283 int[MAX_COMPS_IN_SCAN] last_dc_val;// = new int[MAX_COMPS_IN_SCAN]; /* last DC coef for each component */
|
|
284 }
|
|
285
|
|
286 static final class d_derived_tbl {
|
|
287 /* Basic tables: (element [0] of each array is unused) */
|
|
288 int[18] maxcode;// = new int[18]; /* largest code of length k (-1 if none) */
|
|
289 /* (maxcode[17] is a sentinel to ensure jpeg_huff_decode terminates) */
|
|
290 int[17] valoffset;// = new int[17]; /* huffval[] offset for codes of length k */
|
|
291 /* valoffset[k] = huffval[] index of 1st symbol of code length k, less
|
|
292 * the smallest code of length k; so given a code of length k, the
|
|
293 * corresponding symbol is huffval[code + valoffset[k]]
|
|
294 */
|
|
295
|
|
296 /* Link to public Huffman table (needed only in jpeg_huff_decode) */
|
|
297 JHUFF_TBL pub;
|
|
298
|
|
299 /* Lookahead tables: indexed by the next HUFF_LOOKAHEAD bits of
|
|
300 * the input data stream. If the next Huffman code is no more
|
|
301 * than HUFF_LOOKAHEAD bits long, we can obtain its length and
|
|
302 * the corresponding symbol directly from these tables.
|
|
303 */
|
|
304 int[1<<HUFF_LOOKAHEAD] look_nbits;// = new int[1<<HUFF_LOOKAHEAD]; /* # bits, or 0 if too long */
|
|
305 byte[1<<HUFF_LOOKAHEAD] look_sym;// = new byte[1<<HUFF_LOOKAHEAD]; /* symbol, or unused */
|
|
306 }
|
|
307
|
|
308 static final class jpeg_d_coef_controller {
|
|
309 int consume_data;
|
|
310 int decompress_data;
|
|
311
|
|
312 /* Pointer to array of coefficient virtual arrays, or null if none */
|
|
313 short[][][] coef_arrays;
|
|
314
|
|
315 /* These variables keep track of the current location of the input side. */
|
|
316 /* cinfo.input_iMCU_row is also used for this. */
|
|
317 int MCU_ctr; /* counts MCUs processed in current row */
|
|
318 int MCU_vert_offset; /* counts MCU rows within iMCU row */
|
|
319 int MCU_rows_per_iMCU_row; /* number of such rows needed */
|
|
320
|
|
321 /* The output side's location is represented by cinfo.output_iMCU_row. */
|
|
322
|
|
323 /* In single-pass modes, it's sufficient to buffer just one MCU.
|
|
324 * We allocate a workspace of D_MAX_BLOCKS_IN_MCU coefficient blocks,
|
|
325 * and let the entropy decoder write into that workspace each time.
|
|
326 * (On 80x86, the workspace is FAR even though it's not really very big;
|
|
327 * this is to keep the module interfaces unchanged when a large coefficient
|
|
328 * buffer is necessary.)
|
|
329 * In multi-pass modes, this array points to the current MCU's blocks
|
|
330 * within the virtual arrays; it is used only by the input side.
|
|
331 */
|
|
332 short[][D_MAX_BLOCKS_IN_MCU] MCU_buffer;// = new short[D_MAX_BLOCKS_IN_MCU][];
|
|
333
|
|
334 /* In multi-pass modes, we need a virtual block array for each component. */
|
|
335 short[][][][MAX_COMPONENTS] whole_image;// = new short[MAX_COMPONENTS][][][];
|
|
336
|
|
337 /* When doing block smoothing, we latch coefficient Al values here */
|
|
338 int[] coef_bits_latch;
|
|
339
|
|
340 short[] workspace;
|
|
341
|
|
342 void start_input_pass (jpeg_decompress_struct cinfo) {
|
|
343 cinfo.input_iMCU_row = 0;
|
|
344 start_iMCU_row(cinfo);
|
|
345 }
|
|
346
|
|
347 /* Reset within-iMCU-row counters for a new row (input side) */
|
|
348 void start_iMCU_row (jpeg_decompress_struct cinfo) {
|
|
349 jpeg_d_coef_controller coef = cinfo.coef;
|
|
350
|
|
351 /* In an interleaved scan, an MCU row is the same as an iMCU row.
|
|
352 * In a noninterleaved scan, an iMCU row has v_samp_factor MCU rows.
|
|
353 * But at the bottom of the image, process only what's left.
|
|
354 */
|
|
355 if (cinfo.comps_in_scan > 1) {
|
|
356 coef.MCU_rows_per_iMCU_row = 1;
|
|
357 } else {
|
|
358 if (cinfo.input_iMCU_row < (cinfo.total_iMCU_rows-1))
|
|
359 coef.MCU_rows_per_iMCU_row = cinfo.cur_comp_info[0].v_samp_factor;
|
|
360 else
|
|
361 coef.MCU_rows_per_iMCU_row = cinfo.cur_comp_info[0].last_row_height;
|
|
362 }
|
|
363
|
|
364 coef.MCU_ctr = 0;
|
|
365 coef.MCU_vert_offset = 0;
|
|
366 }
|
|
367
|
|
368 }
|
|
369
|
|
370 static abstract class jpeg_entropy_decoder {
|
|
371 abstract void start_pass (jpeg_decompress_struct cinfo);
|
|
372 abstract bool decode_mcu (jpeg_decompress_struct cinfo, short[][] MCU_data);
|
|
373
|
|
374 /* This is here to share code between baseline and progressive decoders; */
|
|
375 /* other modules probably should not use it */
|
|
376 bool insufficient_data; /* set true after emitting warning */
|
|
377
|
|
378 bitread_working_state br_state_local;
|
|
379 savable_state state_local;
|
|
380 public this(){
|
|
381 br_state_local = new bitread_working_state();
|
|
382 state_local = new savable_state();
|
|
383 }
|
|
384 }
|
|
385
|
|
386 static final class huff_entropy_decoder : jpeg_entropy_decoder {
|
|
387 bitread_perm_state bitstate;// = new bitread_perm_state(); /* Bit buffer at start of MCU */
|
|
388 savable_state saved;// = new savable_state(); /* Other state at start of MCU */
|
|
389
|
|
390 /* These fields are NOT loaded into local working state. */
|
|
391 int restarts_to_go; /* MCUs left in this restart interval */
|
|
392
|
|
393 /* Pointers to derived tables (these workspaces have image lifespan) */
|
|
394 d_derived_tbl[NUM_HUFF_TBLS] dc_derived_tbls;// = new d_derived_tbl[NUM_HUFF_TBLS];
|
|
395 d_derived_tbl[NUM_HUFF_TBLS] ac_derived_tbls;// = new d_derived_tbl[NUM_HUFF_TBLS];
|
|
396
|
|
397 /* Precalculated info set up by start_pass for use in decode_mcu: */
|
|
398
|
|
399 /* Pointers to derived tables to be used for each block within an MCU */
|
|
400 d_derived_tbl[D_MAX_BLOCKS_IN_MCU] dc_cur_tbls;// = new d_derived_tbl[D_MAX_BLOCKS_IN_MCU];
|
|
401 d_derived_tbl[D_MAX_BLOCKS_IN_MCU] ac_cur_tbls;// = new d_derived_tbl[D_MAX_BLOCKS_IN_MCU];
|
|
402 /* Whether we care about the DC and AC coefficient values for each block */
|
|
403 bool[D_MAX_BLOCKS_IN_MCU] dc_needed;// = new bool[D_MAX_BLOCKS_IN_MCU];
|
|
404 bool[D_MAX_BLOCKS_IN_MCU] ac_needed;// = new bool[D_MAX_BLOCKS_IN_MCU];
|
|
405
|
|
406 public this(){
|
|
407 bitstate = new bitread_perm_state(); /* Bit buffer at start of MCU */
|
|
408 saved = new savable_state(); /* Other state at start of MCU */
|
|
409 }
|
|
410
|
|
411 override void start_pass (jpeg_decompress_struct cinfo) {
|
|
412 start_pass_huff_decoder(cinfo);
|
|
413 }
|
|
414
|
|
415 override bool decode_mcu (jpeg_decompress_struct cinfo, short[][] MCU_data) {
|
|
416 huff_entropy_decoder entropy = this;
|
|
417 int blkn;
|
|
418 // BITREAD_STATE_VARS;
|
|
419 int get_buffer;
|
|
420 int bits_left;
|
|
421 // bitread_working_state br_state = new bitread_working_state();
|
|
422 // savable_state state = new savable_state();
|
|
423 bitread_working_state br_state = br_state_local;
|
|
424 savable_state state = state_local;
|
|
425
|
|
426 /* Process restart marker if needed; may have to suspend */
|
|
427 if (cinfo.restart_interval !is 0) {
|
|
428 if (entropy.restarts_to_go is 0)
|
|
429 if (! process_restart(cinfo))
|
|
430 return false;
|
|
431 }
|
|
432
|
|
433 /* If we've run out of data, just leave the MCU set to zeroes.
|
|
434 * This way, we return uniform gray for the remainder of the segment.
|
|
435 */
|
|
436 if (! entropy.insufficient_data) {
|
|
437
|
|
438 /* Load up working state */
|
|
439 // BITREAD_LOAD_STATE(cinfo,entropy.bitstate);
|
|
440 br_state.cinfo = cinfo;
|
|
441 br_state.buffer = cinfo.buffer;
|
|
442 br_state.bytes_in_buffer = cinfo.bytes_in_buffer;
|
|
443 br_state.bytes_offset = cinfo.bytes_offset;
|
|
444 get_buffer = entropy.bitstate.get_buffer;
|
|
445 bits_left = entropy.bitstate.bits_left;
|
|
446
|
|
447 // ASSIGN_STATE(state, entropy.saved);
|
|
448 state.last_dc_val[0] = entropy.saved.last_dc_val[0];
|
|
449 state.last_dc_val[1] = entropy.saved.last_dc_val[1];
|
|
450 state.last_dc_val[2] = entropy.saved.last_dc_val[2];
|
|
451 state.last_dc_val[3] = entropy.saved.last_dc_val[3];
|
|
452
|
|
453 /* Outer loop handles each block in the MCU */
|
|
454
|
|
455 for (blkn = 0; blkn < cinfo.blocks_in_MCU; blkn++) {
|
|
456 short[] block = MCU_data[blkn];
|
|
457 d_derived_tbl dctbl = entropy.dc_cur_tbls[blkn];
|
|
458 d_derived_tbl actbl = entropy.ac_cur_tbls[blkn];
|
|
459 int s = 0, k, r;
|
|
460
|
|
461 /* Decode a single block's worth of coefficients */
|
|
462
|
|
463 /* Section F.2.2.1: decode the DC coefficient difference */
|
|
464 // HUFF_DECODE(s, br_state, dctbl, return FALSE, label1);
|
|
465 {
|
|
466 int nb = 0, look;
|
|
467 if (bits_left < HUFF_LOOKAHEAD) {
|
|
468 if (!jpeg_fill_bit_buffer(br_state,get_buffer,bits_left, 0)) {
|
|
469 return false;
|
|
470 }
|
|
471 get_buffer = br_state.get_buffer; bits_left = br_state.bits_left;
|
|
472 if (bits_left < HUFF_LOOKAHEAD) {
|
|
473 nb = 1;
|
|
474 // goto slowlabel;
|
|
475 if ((s=jpeg_huff_decode(br_state,get_buffer,bits_left,dctbl,nb)) < 0) {
|
|
476 return false;
|
|
477 }
|
|
478 get_buffer = br_state.get_buffer; bits_left = br_state.bits_left;
|
|
479 }
|
|
480 }
|
|
481 // look = PEEK_BITS(HUFF_LOOKAHEAD);
|
|
482 if (nb !is 1) {
|
|
483 look = (( (get_buffer >> (bits_left - (HUFF_LOOKAHEAD)))) & ((1<<(HUFF_LOOKAHEAD))-1));
|
|
484 if ((nb = dctbl.look_nbits[look]) !is 0) {
|
|
485 // DROP_BITS(nb);
|
|
486 bits_left -= nb;
|
|
487 s = dctbl.look_sym[look] & 0xFF;
|
|
488 } else {
|
|
489 nb = HUFF_LOOKAHEAD+1;
|
|
490 // slowlabel:
|
|
491 if ((s=jpeg_huff_decode(br_state,get_buffer,bits_left,dctbl,nb)) < 0) {
|
|
492 return false;
|
|
493 }
|
|
494 get_buffer = br_state.get_buffer; bits_left = br_state.bits_left;
|
|
495 }
|
|
496 }
|
|
497 }
|
|
498
|
|
499 if (s !is 0) {
|
|
500 // CHECK_BIT_BUFFER(br_state, s, return FALSE);
|
|
501 {
|
|
502 if (bits_left < (s)) {
|
|
503 if (!jpeg_fill_bit_buffer(br_state,get_buffer,bits_left,s)) {
|
|
504 return false;
|
|
505 }
|
|
506 get_buffer = br_state.get_buffer; bits_left = br_state.bits_left;
|
|
507 }
|
|
508 }
|
|
509 // r = GET_BITS(s);
|
|
510 r = (( (get_buffer >> (bits_left -= (s)))) & ((1<<(s))-1));
|
|
511 // s = HUFF_EXTEND(r, s);
|
|
512 s = ((r) < extend_test[s] ? (r) + extend_offset[s] : (r));
|
|
513 }
|
|
514
|
|
515 if (entropy.dc_needed[blkn]) {
|
|
516 /* Convert DC difference to actual value, update last_dc_val */
|
|
517 int ci = cinfo.MCU_membership[blkn];
|
|
518 s += state.last_dc_val[ci];
|
|
519 state.last_dc_val[ci] = s;
|
|
520 /* Output the DC coefficient (assumes jpeg_natural_order[0] = 0) */
|
|
521 block[0] = cast(short) s;
|
|
522 }
|
|
523
|
|
524 if (entropy.ac_needed[blkn]) {
|
|
525
|
|
526 /* Section F.2.2.2: decode the AC coefficients */
|
|
527 /* Since zeroes are skipped, output area must be cleared beforehand */
|
|
528 for (k = 1; k < DCTSIZE2; k++) {
|
|
529 // HUFF_DECODE(s, br_state, actbl, return FALSE, label2);
|
|
530 {
|
|
531 int nb = 0, look;
|
|
532 if (bits_left < HUFF_LOOKAHEAD) {
|
|
533 if (!jpeg_fill_bit_buffer(br_state,get_buffer,bits_left, 0)) {
|
|
534 return false;
|
|
535 }
|
|
536 get_buffer = br_state.get_buffer; bits_left = br_state.bits_left;
|
|
537 if (bits_left < HUFF_LOOKAHEAD) {
|
|
538 nb = 1;
|
|
539 // goto slowlabel;
|
|
540 if ((s=jpeg_huff_decode(br_state,get_buffer,bits_left,actbl,nb)) < 0) {
|
|
541 return false;
|
|
542 }
|
|
543 get_buffer = br_state.get_buffer; bits_left = br_state.bits_left;
|
|
544 }
|
|
545 }
|
|
546 if (nb !is 1) {
|
|
547 // look = PEEK_BITS(HUFF_LOOKAHEAD);
|
|
548 look = (( (get_buffer >> (bits_left - (HUFF_LOOKAHEAD)))) & ((1<<(HUFF_LOOKAHEAD))-1));
|
|
549 if ((nb = actbl.look_nbits[look]) !is 0) {
|
|
550 // DROP_BITS(nb);
|
|
551 bits_left -= (nb);
|
|
552 s = actbl.look_sym[look] & 0xFF;
|
|
553 } else {
|
|
554 nb = HUFF_LOOKAHEAD+1;
|
|
555 // slowlabel:
|
|
556 if ((s=jpeg_huff_decode(br_state,get_buffer,bits_left,actbl,nb)) < 0) {
|
|
557 return false;
|
|
558 }
|
|
559 get_buffer = br_state.get_buffer; bits_left = br_state.bits_left;
|
|
560 }
|
|
561 }
|
|
562 }
|
|
563 r = s >> 4;
|
|
564 s &= 15;
|
|
565
|
|
566 if (s !is 0) {
|
|
567 k += r;
|
|
568 // CHECK_BIT_BUFFER(br_state, s, return FALSE);
|
|
569 {
|
|
570 if (bits_left < (s)) {
|
|
571 if (!jpeg_fill_bit_buffer(br_state, get_buffer, bits_left, s)) {
|
|
572 return false;
|
|
573 }
|
|
574 get_buffer = br_state.get_buffer;
|
|
575 bits_left = br_state.bits_left;
|
|
576 }
|
|
577 }
|
|
578 // r = GET_BITS(s);
|
|
579 r = (((get_buffer >> (bits_left -= (s)))) & ((1 << (s)) - 1));
|
|
580 // s = HUFF_EXTEND(r, s);
|
|
581 s = ((r) < extend_test[s] ? (r) + extend_offset[s] : (r));
|
|
582 /*
|
|
583 * Output coefficient in natural (dezigzagged)
|
|
584 * order. Note: the extra entries in
|
|
585 * jpeg_natural_order[] will save us if k >=
|
|
586 * DCTSIZE2, which could happen if the data is
|
|
587 * corrupted.
|
|
588 */
|
|
589 block[jpeg_natural_order[k]] = cast(short) s;
|
|
590 } else {
|
|
591 if (r !is 15)
|
|
592 break;
|
|
593 k += 15;
|
|
594 }
|
|
595 }
|
|
596
|
|
597 } else {
|
|
598
|
|
599 /* Section F.2.2.2: decode the AC coefficients */
|
|
600 /* In this path we just discard the values */
|
|
601 for (k = 1; k < DCTSIZE2; k++) {
|
|
602 // HUFF_DECODE(s, br_state, actbl, return FALSE, label3);
|
|
603 {
|
|
604 int nb = 0, look;
|
|
605 if (bits_left < HUFF_LOOKAHEAD) {
|
|
606 if (!jpeg_fill_bit_buffer(br_state,get_buffer,bits_left, 0)) {
|
|
607 return false;
|
|
608 }
|
|
609 get_buffer = br_state.get_buffer; bits_left = br_state.bits_left;
|
|
610 if (bits_left < HUFF_LOOKAHEAD) {
|
|
611 nb = 1;
|
|
612 // goto slowlabel;
|
|
613 if ((s=jpeg_huff_decode(br_state,get_buffer,bits_left,actbl,nb)) < 0) {
|
|
614 return false;
|
|
615 }
|
|
616 get_buffer = br_state.get_buffer; bits_left = br_state.bits_left;
|
|
617 }
|
|
618 }
|
|
619 if (nb !is 1) {
|
|
620 // look = PEEK_BITS(HUFF_LOOKAHEAD);
|
|
621 look = (( (get_buffer >> (bits_left - (HUFF_LOOKAHEAD)))) & ((1<<(HUFF_LOOKAHEAD))-1));
|
|
622 if ((nb = actbl.look_nbits[look]) !is 0) {
|
|
623 // DROP_BITS(nb);
|
|
624 bits_left -= (nb);
|
|
625 s = actbl.look_sym[look] & 0xFF;
|
|
626 } else {
|
|
627 nb = HUFF_LOOKAHEAD+1;
|
|
628 // slowlabel:
|
|
629 if ((s=jpeg_huff_decode(br_state,get_buffer,bits_left,actbl,nb)) < 0) {
|
|
630 return false;
|
|
631 }
|
|
632 get_buffer = br_state.get_buffer; bits_left = br_state.bits_left;
|
|
633 }
|
|
634 }
|
|
635 }
|
|
636 r = s >> 4;
|
|
637 s &= 15;
|
|
638
|
|
639 if (s !is 0) {
|
|
640 k += r;
|
|
641 // CHECK_BIT_BUFFER(br_state, s, return FALSE);
|
|
642 {
|
|
643 if (bits_left < (s)) {
|
|
644 if (!jpeg_fill_bit_buffer(br_state,get_buffer,bits_left,s)) {
|
|
645 return false;
|
|
646 }
|
|
647 get_buffer = br_state.get_buffer; bits_left = br_state.bits_left;
|
|
648 }
|
|
649 }
|
|
650 // DROP_BITS(s);
|
|
651 bits_left -= s;
|
|
652 } else {
|
|
653 if (r !is 15)
|
|
654 break;
|
|
655 k += 15;
|
|
656 }
|
|
657 }
|
|
658
|
|
659 }
|
|
660 }
|
|
661
|
|
662 /* Completed MCU, so update state */
|
|
663 // BITREAD_SAVE_STATE(cinfo,entropy.bitstate);
|
|
664 cinfo.buffer = br_state.buffer;
|
|
665 cinfo.bytes_in_buffer = br_state.bytes_in_buffer;
|
|
666 cinfo.bytes_offset = br_state.bytes_offset;
|
|
667 entropy.bitstate.get_buffer = get_buffer;
|
|
668 entropy.bitstate.bits_left = bits_left;
|
|
669 // ASSIGN_STATE(entropy.saved, state);
|
|
670 entropy.saved.last_dc_val[0] = state.last_dc_val[0];
|
|
671 entropy.saved.last_dc_val[1] = state.last_dc_val[1];
|
|
672 entropy.saved.last_dc_val[2] = state.last_dc_val[2];
|
|
673 entropy.saved.last_dc_val[3] = state.last_dc_val[3];
|
|
674 }
|
|
675
|
|
676 /* Account for restart interval (no-op if not using restarts) */
|
|
677 entropy.restarts_to_go--;
|
|
678
|
|
679 return true;
|
|
680 }
|
|
681
|
|
682 void start_pass_huff_decoder (jpeg_decompress_struct cinfo) {
|
|
683 huff_entropy_decoder entropy = this;
|
|
684 int ci, blkn, dctbl, actbl;
|
|
685 jpeg_component_info compptr;
|
|
686
|
|
687 /* Check that the scan parameters Ss, Se, Ah/Al are OK for sequential JPEG.
|
|
688 * This ought to be an error condition, but we make it a warning because
|
|
689 * there are some baseline files out there with all zeroes in these bytes.
|
|
690 */
|
|
691 if (cinfo.Ss !is 0 || cinfo.Se !is DCTSIZE2-1 || cinfo.Ah !is 0 || cinfo.Al !is 0) {
|
|
692 // WARNMS(cinfo, JWRN_NOT_SEQUENTIAL);
|
|
693 }
|
|
694
|
|
695 for (ci = 0; ci < cinfo.comps_in_scan; ci++) {
|
|
696 compptr = cinfo.cur_comp_info[ci];
|
|
697 dctbl = compptr.dc_tbl_no;
|
|
698 actbl = compptr.ac_tbl_no;
|
|
699 /* Compute derived values for Huffman tables */
|
|
700 /* We may do this more than once for a table, but it's not expensive */
|
|
701 jpeg_make_d_derived_tbl(cinfo, true, dctbl, entropy.dc_derived_tbls[dctbl] = new d_derived_tbl());
|
|
702 jpeg_make_d_derived_tbl(cinfo, false, actbl, entropy.ac_derived_tbls[actbl] = new d_derived_tbl());
|
|
703 /* Initialize DC predictions to 0 */
|
|
704 entropy.saved.last_dc_val[ci] = 0;
|
|
705 }
|
|
706
|
|
707 /* Precalculate decoding info for each block in an MCU of this scan */
|
|
708 for (blkn = 0; blkn < cinfo.blocks_in_MCU; blkn++) {
|
|
709 ci = cinfo.MCU_membership[blkn];
|
|
710 compptr = cinfo.cur_comp_info[ci];
|
|
711 /* Precalculate which table to use for each block */
|
|
712 entropy.dc_cur_tbls[blkn] = entropy.dc_derived_tbls[compptr.dc_tbl_no];
|
|
713 entropy.ac_cur_tbls[blkn] = entropy.ac_derived_tbls[compptr.ac_tbl_no];
|
|
714 /* Decide whether we really care about the coefficient values */
|
|
715 if (compptr.component_needed) {
|
|
716 entropy.dc_needed[blkn] = true;
|
|
717 /* we don't need the ACs if producing a 1/8th-size image */
|
|
718 entropy.ac_needed[blkn] = (compptr.DCT_scaled_size > 1);
|
|
719 } else {
|
|
720 entropy.dc_needed[blkn] = entropy.ac_needed[blkn] = false;
|
|
721 }
|
|
722 }
|
|
723
|
|
724 /* Initialize bitread state variables */
|
|
725 entropy.bitstate.bits_left = 0;
|
|
726 entropy.bitstate.get_buffer = 0; /* unnecessary, but keeps Purify quiet */
|
|
727 entropy.insufficient_data = false;
|
|
728
|
|
729 /* Initialize restart counter */
|
|
730 entropy.restarts_to_go = cinfo.restart_interval;
|
|
731 }
|
|
732
|
|
733 bool process_restart (jpeg_decompress_struct cinfo) {
|
|
734 huff_entropy_decoder entropy = this;
|
|
735 int ci;
|
|
736
|
|
737 /* Throw away any unused bits remaining in bit buffer; */
|
|
738 /* include any full bytes in next_marker's count of discarded bytes */
|
|
739 cinfo.marker.discarded_bytes += entropy.bitstate.bits_left / 8;
|
|
740 entropy.bitstate.bits_left = 0;
|
|
741
|
|
742 /* Advance past the RSTn marker */
|
|
743 if (! read_restart_marker (cinfo))
|
|
744 return false;
|
|
745
|
|
746 /* Re-initialize DC predictions to 0 */
|
|
747 for (ci = 0; ci < cinfo.comps_in_scan; ci++)
|
|
748 entropy.saved.last_dc_val[ci] = 0;
|
|
749
|
|
750 /* Reset restart counter */
|
|
751 entropy.restarts_to_go = cinfo.restart_interval;
|
|
752
|
|
753 /* Reset out-of-data flag, unless read_restart_marker left us smack up
|
|
754 * against a marker. In that case we will end up treating the next data
|
|
755 * segment as empty, and we can avoid producing bogus output pixels by
|
|
756 * leaving the flag set.
|
|
757 */
|
|
758 if (cinfo.unread_marker is 0)
|
|
759 entropy.insufficient_data = false;
|
|
760
|
|
761 return true;
|
|
762 }
|
|
763 }
|
|
764
|
|
765 static final class phuff_entropy_decoder : jpeg_entropy_decoder {
|
|
766
|
|
767 /* These fields are loaded into local variables at start of each MCU.
|
|
768 * In case of suspension, we exit WITHOUT updating them.
|
|
769 */
|
|
770 bitread_perm_state bitstate;// = new bitread_perm_state(); /* Bit buffer at start of MCU */
|
|
771 savable_state saved;// = new savable_state(); /* Other state at start of MCU */
|
|
772
|
|
773 /* These fields are NOT loaded into local working state. */
|
|
774 int restarts_to_go; /* MCUs left in this restart interval */
|
|
775
|
|
776 /* Pointers to derived tables (these workspaces have image lifespan) */
|
|
777 d_derived_tbl[NUM_HUFF_TBLS] derived_tbls;// = new d_derived_tbl[NUM_HUFF_TBLS];
|
|
778
|
|
779 d_derived_tbl ac_derived_tbl; /* active table during an AC scan */
|
|
780
|
|
781 int[DCTSIZE2] newnz_pos;// = new int[DCTSIZE2];
|
|
782
|
|
783 public this(){
|
|
784 bitstate = new bitread_perm_state(); /* Bit buffer at start of MCU */
|
|
785 saved = new savable_state(); /* Other state at start of MCU */
|
|
786 }
|
|
787
|
|
788 override void start_pass (jpeg_decompress_struct cinfo) {
|
|
789 start_pass_phuff_decoder(cinfo);
|
|
790 }
|
|
791
|
|
792 override bool decode_mcu (jpeg_decompress_struct cinfo, short[][] MCU_data) {
|
|
793 bool is_DC_band = (cinfo.Ss is 0);
|
|
794 if (cinfo.Ah is 0) {
|
|
795 if (is_DC_band)
|
|
796 return decode_mcu_DC_first(cinfo, MCU_data);
|
|
797 else
|
|
798 return decode_mcu_AC_first(cinfo, MCU_data);
|
|
799 } else {
|
|
800 if (is_DC_band)
|
|
801 return decode_mcu_DC_refine(cinfo, MCU_data);
|
|
802 else
|
|
803 return decode_mcu_AC_refine(cinfo, MCU_data);
|
|
804 }
|
|
805 }
|
|
806
|
|
807 bool decode_mcu_DC_refine (jpeg_decompress_struct cinfo, short[][] MCU_data) {
|
|
808 phuff_entropy_decoder entropy = this;
|
|
809 int p1 = 1 << cinfo.Al; /* 1 in the bit position being coded */
|
|
810 int blkn;
|
|
811 short[] block;
|
|
812 // BITREAD_STATE_VARS;
|
|
813 int get_buffer;
|
|
814 int bits_left;
|
|
815 // bitread_working_state br_state = new bitread_working_state();
|
|
816 bitread_working_state br_state = br_state_local;
|
|
817
|
|
818 /* Process restart marker if needed; may have to suspend */
|
|
819 if (cinfo.restart_interval !is 0) {
|
|
820 if (entropy.restarts_to_go is 0)
|
|
821 if (! process_restart(cinfo))
|
|
822 return false;
|
|
823 }
|
|
824
|
|
825 /* Not worth the cycles to check insufficient_data here,
|
|
826 * since we will not change the data anyway if we read zeroes.
|
|
827 */
|
|
828
|
|
829 /* Load up working state */
|
|
830 // BITREAD_LOAD_STATE(cinfo,entropy.bitstate);
|
|
831 br_state.cinfo = cinfo;
|
|
832 br_state.buffer = cinfo.buffer;
|
|
833 br_state.bytes_in_buffer = cinfo.bytes_in_buffer;
|
|
834 br_state.bytes_offset = cinfo.bytes_offset;
|
|
835 get_buffer = entropy.bitstate.get_buffer;
|
|
836 bits_left = entropy.bitstate.bits_left;
|
|
837
|
|
838 /* Outer loop handles each block in the MCU */
|
|
839
|
|
840 for (blkn = 0; blkn < cinfo.blocks_in_MCU; blkn++) {
|
|
841 block = MCU_data[blkn];
|
|
842
|
|
843 /* Encoded data is simply the next bit of the two's-complement DC value */
|
|
844 // CHECK_BIT_BUFFER(br_state, 1, return FALSE);
|
|
845 {
|
|
846 if (bits_left < (1)) {
|
|
847 if (!jpeg_fill_bit_buffer(br_state,get_buffer,bits_left,1)) {
|
|
848 return false;
|
|
849 }
|
|
850 get_buffer = br_state.get_buffer; bits_left = br_state.bits_left;
|
|
851 }
|
|
852 }
|
|
853 // if (GET_BITS(1))
|
|
854 if ((( (get_buffer >> (bits_left -= (1)))) & ((1<<(1))-1)) !is 0)
|
|
855 block[0] |= p1;
|
|
856 /* Note: since we use |=, repeating the assignment later is safe */
|
|
857 }
|
|
858
|
|
859 /* Completed MCU, so update state */
|
|
860 // BITREAD_SAVE_STATE(cinfo,entropy.bitstate);
|
|
861 cinfo.buffer = br_state.buffer;
|
|
862 cinfo.bytes_in_buffer = br_state.bytes_in_buffer;
|
|
863 cinfo.bytes_offset = br_state.bytes_offset;
|
|
864 entropy.bitstate.get_buffer = get_buffer;
|
|
865 entropy.bitstate.bits_left = bits_left;
|
|
866
|
|
867 /* Account for restart interval (no-op if not using restarts) */
|
|
868 entropy.restarts_to_go--;
|
|
869
|
|
870 return true;
|
|
871
|
|
872 }
|
|
873
|
|
874 bool decode_mcu_AC_refine (jpeg_decompress_struct cinfo, short[][] MCU_data) {
|
|
875 phuff_entropy_decoder entropy = this;
|
|
876 int Se = cinfo.Se;
|
|
877 int p1 = 1 << cinfo.Al; /* 1 in the bit position being coded */
|
|
878 int m1 = (-1) << cinfo.Al; /* -1 in the bit position being coded */
|
|
879 int s = 0, k, r;
|
|
880 int EOBRUN;
|
|
881 short[] block;
|
|
882 short[] thiscoef;
|
|
883 // BITREAD_STATE_VARS;
|
|
884 int get_buffer;
|
|
885 int bits_left;
|
|
886 // bitread_working_state br_state = new bitread_working_state();
|
|
887 bitread_working_state br_state = br_state_local;
|
|
888
|
|
889 d_derived_tbl tbl;
|
|
890 int num_newnz;
|
|
891 int[] newnz_pos = entropy.newnz_pos;
|
|
892
|
|
893 /* Process restart marker if needed; may have to suspend */
|
|
894 if (cinfo.restart_interval !is 0) {
|
|
895 if (entropy.restarts_to_go is 0)
|
|
896 if (! process_restart(cinfo))
|
|
897 return false;
|
|
898 }
|
|
899
|
|
900 /* If we've run out of data, don't modify the MCU.
|
|
901 */
|
|
902 if (! entropy.insufficient_data) {
|
|
903
|
|
904 /* Load up working state */
|
|
905 // BITREAD_LOAD_STATE(cinfo,entropy.bitstate);
|
|
906 br_state.cinfo = cinfo;
|
|
907 br_state.buffer = cinfo.buffer;
|
|
908 br_state.bytes_in_buffer = cinfo.bytes_in_buffer;
|
|
909 br_state.bytes_offset = cinfo.bytes_offset;
|
|
910 get_buffer = entropy.bitstate.get_buffer;
|
|
911 bits_left = entropy.bitstate.bits_left;
|
|
912
|
|
913 EOBRUN = entropy.saved.EOBRUN; /* only part of saved state we need */
|
|
914
|
|
915 /* There is always only one block per MCU */
|
|
916 block = MCU_data[0];
|
|
917 tbl = entropy.ac_derived_tbl;
|
|
918
|
|
919 /* If we are forced to suspend, we must undo the assignments to any newly
|
|
920 * nonzero coefficients in the block, because otherwise we'd get confused
|
|
921 * next time about which coefficients were already nonzero.
|
|
922 * But we need not undo addition of bits to already-nonzero coefficients;
|
|
923 * instead, we can test the current bit to see if we already did it.
|
|
924 */
|
|
925 num_newnz = 0;
|
|
926
|
|
927 /* initialize coefficient loop counter to start of band */
|
|
928 k = cinfo.Ss;
|
|
929
|
|
930 if (EOBRUN is 0) {
|
|
931 for (; k <= Se; k++) {
|
|
932 // HUFF_DECODE(s, br_state, tbl, goto undoit, label3);
|
|
933 {
|
|
934 int nb = 0, look;
|
|
935 if (bits_left < HUFF_LOOKAHEAD) {
|
|
936 if (! jpeg_fill_bit_buffer(br_state,get_buffer,bits_left, 0)) {
|
|
937 // failaction;
|
|
938 while (num_newnz > 0)
|
|
939 block[newnz_pos[--num_newnz]] = 0;
|
|
940
|
|
941 return false;
|
|
942 }
|
|
943 get_buffer = br_state.get_buffer; bits_left = br_state.bits_left;
|
|
944 if (bits_left < HUFF_LOOKAHEAD) {
|
|
945 nb = 1;
|
|
946 // goto slowlabel;
|
|
947 if ((s=jpeg_huff_decode(br_state,get_buffer,bits_left,tbl,nb)) < 0) {
|
|
948 // failaction;
|
|
949 while (num_newnz > 0)
|
|
950 block[newnz_pos[--num_newnz]] = 0;
|
|
951
|
|
952 return false;
|
|
953 }
|
|
954 get_buffer = br_state.get_buffer; bits_left = br_state.bits_left;
|
|
955 }
|
|
956 }
|
|
957 if (nb !is 1) {
|
|
958 // look = PEEK_BITS(HUFF_LOOKAHEAD);
|
|
959 look = (( (get_buffer >> (bits_left - (HUFF_LOOKAHEAD)))) & ((1<<(HUFF_LOOKAHEAD))-1));
|
|
960 if ((nb = tbl.look_nbits[look]) !is 0) {
|
|
961 // DROP_BITS(nb);
|
|
962 bits_left -= nb;
|
|
963 s = tbl.look_sym[look] & 0xFF;
|
|
964 } else {
|
|
965 nb = HUFF_LOOKAHEAD+1;
|
|
966 // slowlabel:
|
|
967 if ((s=jpeg_huff_decode(br_state,get_buffer,bits_left,tbl,nb)) < 0) {
|
|
968 // failaction;
|
|
969 while (num_newnz > 0)
|
|
970 block[newnz_pos[--num_newnz]] = 0;
|
|
971
|
|
972 return false;
|
|
973 }
|
|
974 get_buffer = br_state.get_buffer; bits_left = br_state.bits_left;
|
|
975 }
|
|
976 }
|
|
977 }
|
|
978 r = s >> 4;
|
|
979 s &= 15;
|
|
980 if (s !is 0) {
|
|
981 if (s !is 1) { /* size of new coef should always be 1 */
|
|
982 // WARNMS(cinfo, JWRN_HUFF_BAD_CODE);
|
|
983 }
|
|
984 // CHECK_BIT_BUFFER(br_state, 1, goto undoit);
|
|
985 {
|
|
986 if (bits_left < (1)) {
|
|
987 if (! jpeg_fill_bit_buffer(br_state,get_buffer,bits_left,1)) {
|
|
988 // failaction;
|
|
989 while (num_newnz > 0)
|
|
990 block[newnz_pos[--num_newnz]] = 0;
|
|
991
|
|
992 return false;
|
|
993 }
|
|
994 get_buffer = br_state.get_buffer; bits_left = br_state.bits_left;
|
|
995 }
|
|
996 }
|
|
997 // if (GET_BITS(1))
|
|
998 if ((( (get_buffer >> (bits_left -= (1)))) & ((1<<(1))-1)) !is 0)
|
|
999 s = p1; /* newly nonzero coef is positive */
|
|
1000 else
|
|
1001 s = m1; /* newly nonzero coef is negative */
|
|
1002 } else {
|
|
1003 if (r !is 15) {
|
|
1004 EOBRUN = 1 << r; /* EOBr, run length is 2^r + appended bits */
|
|
1005 if (r !is 0) {
|
|
1006 // CHECK_BIT_BUFFER(br_state, r, goto undoit);
|
|
1007 {
|
|
1008 if (bits_left < (r)) {
|
|
1009 if (!jpeg_fill_bit_buffer(br_state,get_buffer,bits_left,r)) {
|
|
1010 // failaction;
|
|
1011 while (num_newnz > 0)
|
|
1012 block[newnz_pos[--num_newnz]] = 0;
|
|
1013
|
|
1014 return false;
|
|
1015 }
|
|
1016 get_buffer = br_state.get_buffer; bits_left = br_state.bits_left;
|
|
1017 }
|
|
1018 }
|
|
1019 // r = GET_BITS(r);
|
|
1020 r = (( (get_buffer >> (bits_left -= (r)))) & ((1<<(r))-1));
|
|
1021 EOBRUN += r;
|
|
1022 }
|
|
1023 break; /* rest of block is handled by EOB logic */
|
|
1024 }
|
|
1025 /* note s = 0 for processing ZRL */
|
|
1026 }
|
|
1027 /* Advance over already-nonzero coefs and r still-zero coefs,
|
|
1028 * appending correction bits to the nonzeroes. A correction bit is 1
|
|
1029 * if the absolute value of the coefficient must be increased.
|
|
1030 */
|
|
1031 do {
|
|
1032 thiscoef = block;
|
|
1033 int thiscoef_offset = jpeg_natural_order[k];
|
|
1034 if (thiscoef[thiscoef_offset] !is 0) {
|
|
1035 // CHECK_BIT_BUFFER(br_state, 1, goto undoit);
|
|
1036 {
|
|
1037 if (bits_left < (1)) {
|
|
1038 if (!jpeg_fill_bit_buffer(br_state,get_buffer,bits_left,1)) {
|
|
1039 // failaction;
|
|
1040 while (num_newnz > 0)
|
|
1041 block[newnz_pos[--num_newnz]] = 0;
|
|
1042
|
|
1043 return false;
|
|
1044 }
|
|
1045 get_buffer = br_state.get_buffer; bits_left = br_state.bits_left;
|
|
1046 }
|
|
1047 }
|
|
1048 // if (GET_BITS(1)) {
|
|
1049 if ((( (get_buffer >> (bits_left -= (1)))) & ((1<<(1))-1)) !is 0) {
|
|
1050 if ((thiscoef[thiscoef_offset] & p1) is 0) { /* do nothing if already set it */
|
|
1051 if (thiscoef[thiscoef_offset] >= 0)
|
|
1052 thiscoef[thiscoef_offset] += p1;
|
|
1053 else
|
|
1054 thiscoef[thiscoef_offset] += m1;
|
|
1055 }
|
|
1056 }
|
|
1057 } else {
|
|
1058 if (--r < 0)
|
|
1059 break; /* reached target zero coefficient */
|
|
1060 }
|
|
1061 k++;
|
|
1062 } while (k <= Se);
|
|
1063 if (s !is 0) {
|
|
1064 int pos = jpeg_natural_order[k];
|
|
1065 /* Output newly nonzero coefficient */
|
|
1066 block[pos] = cast(short) s;
|
|
1067 /* Remember its position in case we have to suspend */
|
|
1068 newnz_pos[num_newnz++] = pos;
|
|
1069 }
|
|
1070 }
|
|
1071 }
|
|
1072
|
|
1073 if (EOBRUN > 0) {
|
|
1074 /* Scan any remaining coefficient positions after the end-of-band
|
|
1075 * (the last newly nonzero coefficient, if any). Append a correction
|
|
1076 * bit to each already-nonzero coefficient. A correction bit is 1
|
|
1077 * if the absolute value of the coefficient must be increased.
|
|
1078 */
|
|
1079 for (; k <= Se; k++) {
|
|
1080 thiscoef = block;
|
|
1081 int thiscoef_offset = jpeg_natural_order[k];
|
|
1082 if (thiscoef[thiscoef_offset] !is 0) {
|
|
1083 // CHECK_BIT_BUFFER(br_state, 1, goto undoit);
|
|
1084 {
|
|
1085 if (bits_left < (1)) {
|
|
1086 if (! jpeg_fill_bit_buffer(br_state,get_buffer,bits_left,1)) {
|
|
1087 // failaction;
|
|
1088 while (num_newnz > 0)
|
|
1089 block[newnz_pos[--num_newnz]] = 0;
|
|
1090
|
|
1091 return false;
|
|
1092 }
|
|
1093 get_buffer = br_state.get_buffer; bits_left = br_state.bits_left;
|
|
1094 }
|
|
1095 }
|
|
1096 // if (GET_BITS(1)) {
|
|
1097 if ((( (get_buffer >> (bits_left -= (1)))) & ((1<<(1))-1)) !is 0) {
|
|
1098 if ((thiscoef[thiscoef_offset] & p1) is 0) { /* do nothing if already changed it */
|
|
1099 if (thiscoef[thiscoef_offset] >= 0)
|
|
1100 thiscoef[thiscoef_offset] += p1;
|
|
1101 else
|
|
1102 thiscoef[thiscoef_offset] += m1;
|
|
1103 }
|
|
1104 }
|
|
1105 }
|
|
1106 }
|
|
1107 /* Count one block completed in EOB run */
|
|
1108 EOBRUN--;
|
|
1109 }
|
|
1110
|
|
1111 /* Completed MCU, so update state */
|
|
1112 // BITREAD_SAVE_STATE(cinfo,entropy.bitstate);
|
|
1113 cinfo.buffer = br_state.buffer;
|
|
1114 cinfo.bytes_in_buffer = br_state.bytes_in_buffer;
|
|
1115 cinfo.bytes_offset = br_state.bytes_offset;
|
|
1116 entropy.bitstate.get_buffer = get_buffer;
|
|
1117 entropy.bitstate.bits_left = bits_left;
|
|
1118
|
|
1119 entropy.saved.EOBRUN = EOBRUN; /* only part of saved state we need */
|
|
1120 }
|
|
1121
|
|
1122 /* Account for restart interval (no-op if not using restarts) */
|
|
1123 entropy.restarts_to_go--;
|
|
1124
|
|
1125 return true;
|
|
1126
|
|
1127 // undoit:
|
|
1128 // /* Re-zero any output coefficients that we made newly nonzero */
|
|
1129 // while (num_newnz > 0)
|
|
1130 // (*block)[newnz_pos[--num_newnz]] = 0;
|
|
1131 //
|
|
1132 // return false;
|
|
1133
|
|
1134 }
|
|
1135
|
|
1136 bool decode_mcu_AC_first (jpeg_decompress_struct cinfo, short[][] MCU_data) {
|
|
1137 phuff_entropy_decoder entropy = this;
|
|
1138 int Se = cinfo.Se;
|
|
1139 int Al = cinfo.Al;
|
|
1140 int s = 0, k, r;
|
|
1141 int EOBRUN;
|
|
1142 short[] block;
|
|
1143 // BITREAD_STATE_VARS;
|
|
1144 int get_buffer;
|
|
1145 int bits_left;
|
|
1146 // bitread_working_state br_state = new bitread_working_state();
|
|
1147 bitread_working_state br_state = br_state_local;
|
|
1148
|
|
1149 d_derived_tbl tbl;
|
|
1150
|
|
1151 /* Process restart marker if needed; may have to suspend */
|
|
1152 if (cinfo.restart_interval !is 0) {
|
|
1153 if (entropy.restarts_to_go is 0)
|
|
1154 if (! process_restart(cinfo))
|
|
1155 return false;
|
|
1156 }
|
|
1157
|
|
1158 /* If we've run out of data, just leave the MCU set to zeroes.
|
|
1159 * This way, we return uniform gray for the remainder of the segment.
|
|
1160 */
|
|
1161 if (! entropy.insufficient_data) {
|
|
1162
|
|
1163 /* Load up working state.
|
|
1164 * We can avoid loading/saving bitread state if in an EOB run.
|
|
1165 */
|
|
1166 EOBRUN = entropy.saved.EOBRUN; /* only part of saved state we need */
|
|
1167
|
|
1168 /* There is always only one block per MCU */
|
|
1169
|
|
1170 if (EOBRUN > 0) /* if it's a band of zeroes... */
|
|
1171 EOBRUN--; /* ...process it now (we do nothing) */
|
|
1172 else {
|
|
1173 // BITREAD_LOAD_STATE(cinfo,entropy.bitstate);
|
|
1174 br_state.cinfo = cinfo;
|
|
1175 br_state.buffer = cinfo.buffer;
|
|
1176 br_state.bytes_in_buffer = cinfo.bytes_in_buffer;
|
|
1177 br_state.bytes_offset = cinfo.bytes_offset;
|
|
1178 get_buffer = entropy.bitstate.get_buffer;
|
|
1179 bits_left = entropy.bitstate.bits_left;
|
|
1180
|
|
1181 block = MCU_data[0];
|
|
1182 tbl = entropy.ac_derived_tbl;
|
|
1183
|
|
1184 for (k = cinfo.Ss; k <= Se; k++) {
|
|
1185 // HUFF_DECODE(s, br_state, tbl, return FALSE, label2);
|
|
1186 {
|
|
1187 int nb = 0, look;
|
|
1188 if (bits_left < HUFF_LOOKAHEAD) {
|
|
1189 if (! jpeg_fill_bit_buffer(br_state,get_buffer,bits_left, 0)) {
|
|
1190 return false;
|
|
1191 }
|
|
1192 get_buffer = br_state.get_buffer; bits_left = br_state.bits_left;
|
|
1193 if (bits_left < HUFF_LOOKAHEAD) {
|
|
1194 nb = 1;
|
|
1195 // goto slowlabel;
|
|
1196 if ((s=jpeg_huff_decode(br_state,get_buffer,bits_left,tbl,nb)) < 0) {
|
|
1197 return false;
|
|
1198 }
|
|
1199 get_buffer = br_state.get_buffer; bits_left = br_state.bits_left;
|
|
1200 }
|
|
1201 }
|
|
1202 if (nb !is 1) {
|
|
1203 // look = PEEK_BITS(HUFF_LOOKAHEAD);
|
|
1204 look = (( (get_buffer >> (bits_left - (HUFF_LOOKAHEAD)))) & ((1<<(HUFF_LOOKAHEAD))-1));
|
|
1205
|
|
1206 if ((nb = tbl.look_nbits[look]) !is 0) {
|
|
1207 // DROP_BITS(nb);
|
|
1208 bits_left -= nb;
|
|
1209 s = tbl.look_sym[look] & 0xFF;
|
|
1210 } else {
|
|
1211 nb = HUFF_LOOKAHEAD+1;
|
|
1212 // slowlabel:
|
|
1213 if ((s=jpeg_huff_decode(br_state,get_buffer,bits_left,tbl,nb)) < 0) {
|
|
1214 return false;
|
|
1215 }
|
|
1216 get_buffer = br_state.get_buffer; bits_left = br_state.bits_left;
|
|
1217 }
|
|
1218 }
|
|
1219 }
|
|
1220 r = s >> 4;
|
|
1221 s &= 15;
|
|
1222 if (s !is 0) {
|
|
1223 k += r;
|
|
1224 // CHECK_BIT_BUFFER(br_state, s, return FALSE);
|
|
1225 {
|
|
1226 if (bits_left < (s)) {
|
|
1227 if (! jpeg_fill_bit_buffer(br_state,get_buffer,bits_left,s)) {
|
|
1228 return false;
|
|
1229 }
|
|
1230 get_buffer = br_state.get_buffer; bits_left = br_state.bits_left;
|
|
1231 }
|
|
1232 }
|
|
1233 // r = GET_BITS(s);
|
|
1234 r = (( (get_buffer >> (bits_left -= (s)))) & ((1<<(s))-1));
|
|
1235 // s = HUFF_EXTEND(r, s);
|
|
1236 s = ((r) < extend_test[s] ? (r) + extend_offset[s] : (r));
|
|
1237 /* Scale and output coefficient in natural (dezigzagged) order */
|
|
1238 block[jpeg_natural_order[k]] = cast(short) (s << Al);
|
|
1239 } else {
|
|
1240 if (r is 15) { /* ZRL */
|
|
1241 k += 15; /* skip 15 zeroes in band */
|
|
1242 } else { /* EOBr, run length is 2^r + appended bits */
|
|
1243 EOBRUN = 1 << r;
|
|
1244 if (r !is 0) { /* EOBr, r > 0 */
|
|
1245 // CHECK_BIT_BUFFER(br_state, r, return FALSE);
|
|
1246 {
|
|
1247 if (bits_left < (r)) {
|
|
1248 if (! jpeg_fill_bit_buffer(br_state,get_buffer,bits_left,r)) {
|
|
1249 return false;
|
|
1250 }
|
|
1251 get_buffer = br_state.get_buffer; bits_left = br_state.bits_left;
|
|
1252 }
|
|
1253 }
|
|
1254 // r = GET_BITS(r);
|
|
1255 r = (( (get_buffer >> (bits_left -= (r)))) & ((1<<(r))-1));
|
|
1256 EOBRUN += r;
|
|
1257 }
|
|
1258 EOBRUN--; /* this band is processed at this moment */
|
|
1259 break; /* force end-of-band */
|
|
1260 }
|
|
1261 }
|
|
1262 }
|
|
1263
|
|
1264 // BITREAD_SAVE_STATE(cinfo,entropy.bitstate);
|
|
1265 cinfo.buffer = br_state.buffer;
|
|
1266 cinfo.bytes_in_buffer = br_state.bytes_in_buffer;
|
|
1267 cinfo.bytes_offset = br_state.bytes_offset;
|
|
1268 entropy.bitstate.get_buffer = get_buffer;
|
|
1269 entropy.bitstate.bits_left = bits_left;
|
|
1270 }
|
|
1271
|
|
1272 /* Completed MCU, so update state */
|
|
1273 entropy.saved.EOBRUN = EOBRUN; /* only part of saved state we need */
|
|
1274 }
|
|
1275
|
|
1276 /* Account for restart interval (no-op if not using restarts) */
|
|
1277 entropy.restarts_to_go--;
|
|
1278
|
|
1279 return true;
|
|
1280 }
|
|
1281
|
|
1282 bool decode_mcu_DC_first (jpeg_decompress_struct cinfo, short[][] MCU_data) {
|
|
1283 phuff_entropy_decoder entropy = this;
|
|
1284 int Al = cinfo.Al;
|
|
1285 int s = 0, r;
|
|
1286 int blkn, ci;
|
|
1287 short[] block;
|
|
1288 // BITREAD_STATE_VARS;
|
|
1289 int get_buffer;
|
|
1290 int bits_left;
|
|
1291 // bitread_working_state br_state = new bitread_working_state();
|
|
1292 bitread_working_state br_state = br_state_local;
|
|
1293
|
|
1294 // savable_state state = new savable_state();
|
|
1295 savable_state state = state_local;
|
|
1296 d_derived_tbl tbl;
|
|
1297 jpeg_component_info compptr;
|
|
1298
|
|
1299 /* Process restart marker if needed; may have to suspend */
|
|
1300 if (cinfo.restart_interval !is 0) {
|
|
1301 if (entropy.restarts_to_go is 0)
|
|
1302 if (! process_restart(cinfo))
|
|
1303 return false;
|
|
1304 }
|
|
1305
|
|
1306 /* If we've run out of data, just leave the MCU set to zeroes.
|
|
1307 * This way, we return uniform gray for the remainder of the segment.
|
|
1308 */
|
|
1309 if (! entropy.insufficient_data) {
|
|
1310
|
|
1311 /* Load up working state */
|
|
1312 // BITREAD_LOAD_STATE(cinfo,entropy.bitstate);
|
|
1313 br_state.cinfo = cinfo;
|
|
1314 br_state.buffer = cinfo.buffer;
|
|
1315 br_state.bytes_in_buffer = cinfo.bytes_in_buffer;
|
|
1316 br_state.bytes_offset = cinfo.bytes_offset;
|
|
1317 get_buffer = entropy.bitstate.get_buffer;
|
|
1318 bits_left = entropy.bitstate.bits_left;
|
|
1319
|
|
1320 // ASSIGN_STATE(state, entropy.saved);
|
|
1321 state.EOBRUN = entropy.saved.EOBRUN;
|
|
1322 state.last_dc_val[0] = entropy.saved.last_dc_val[0];
|
|
1323 state.last_dc_val[1] = entropy.saved.last_dc_val[1];
|
|
1324 state.last_dc_val[2] = entropy.saved.last_dc_val[2];
|
|
1325 state.last_dc_val[3] = entropy.saved.last_dc_val[3];
|
|
1326
|
|
1327 /* Outer loop handles each block in the MCU */
|
|
1328
|
|
1329 for (blkn = 0; blkn < cinfo.blocks_in_MCU; blkn++) {
|
|
1330 block = MCU_data[blkn];
|
|
1331 ci = cinfo.MCU_membership[blkn];
|
|
1332 compptr = cinfo.cur_comp_info[ci];
|
|
1333 tbl = entropy.derived_tbls[compptr.dc_tbl_no];
|
|
1334
|
|
1335 /* Decode a single block's worth of coefficients */
|
|
1336
|
|
1337 /* Section F.2.2.1: decode the DC coefficient difference */
|
|
1338 // HUFF_DECODE(s, br_state, tbl, return FALSE, label1);
|
|
1339 {
|
|
1340 int nb = 0, look;
|
|
1341 if (bits_left < HUFF_LOOKAHEAD) {
|
|
1342 if (! jpeg_fill_bit_buffer(br_state,get_buffer,bits_left, 0)) {
|
|
1343 return false;
|
|
1344 }
|
|
1345 get_buffer = br_state.get_buffer; bits_left = br_state.bits_left;
|
|
1346 if (bits_left < HUFF_LOOKAHEAD) {
|
|
1347 nb = 1;
|
|
1348 // goto slowlabel;
|
|
1349 if ((s=jpeg_huff_decode(br_state,get_buffer,bits_left,tbl,nb)) < 0) {
|
|
1350 return false;
|
|
1351 }
|
|
1352 get_buffer = br_state.get_buffer; bits_left = br_state.bits_left;
|
|
1353 }
|
|
1354 }
|
|
1355 if (nb !is 1) {
|
|
1356 // look = PEEK_BITS(HUFF_LOOKAHEAD);
|
|
1357 look = (( (get_buffer >> (bits_left - (HUFF_LOOKAHEAD)))) & ((1<<(HUFF_LOOKAHEAD))-1));
|
|
1358
|
|
1359 if ((nb = tbl.look_nbits[look]) !is 0) {
|
|
1360 // DROP_BITS(nb);
|
|
1361 bits_left -= nb;
|
|
1362 s = tbl.look_sym[look] & 0xFF;
|
|
1363 } else {
|
|
1364 nb = HUFF_LOOKAHEAD+1;
|
|
1365 // slowlabel:
|
|
1366 if ((s=jpeg_huff_decode(br_state,get_buffer,bits_left,tbl,nb)) < 0) {
|
|
1367 return false;
|
|
1368 }
|
|
1369 get_buffer = br_state.get_buffer; bits_left = br_state.bits_left;
|
|
1370 }
|
|
1371 }
|
|
1372 }
|
|
1373 if (s !is 0) {
|
|
1374 // CHECK_BIT_BUFFER(br_state, s, return FALSE);
|
|
1375 {
|
|
1376 if (bits_left < (s)) {
|
|
1377 if (! jpeg_fill_bit_buffer(br_state,get_buffer,bits_left,s)) {
|
|
1378 return false;
|
|
1379 }
|
|
1380 get_buffer = br_state.get_buffer; bits_left = br_state.bits_left;
|
|
1381 }
|
|
1382 }
|
|
1383 // r = GET_BITS(s);
|
|
1384 r = (( (get_buffer >> (bits_left -= (s)))) & ((1<<(s))-1));
|
|
1385 // s = HUFF_EXTEND(r, s);
|
|
1386 s = ((r) < extend_test[s] ? (r) + extend_offset[s] : (r));
|
|
1387 }
|
|
1388
|
|
1389 /* Convert DC difference to actual value, update last_dc_val */
|
|
1390 s += state.last_dc_val[ci];
|
|
1391 state.last_dc_val[ci] = s;
|
|
1392 /* Scale and output the coefficient (assumes jpeg_natural_order[0]=0) */
|
|
1393 block[0] = cast(short) (s << Al);
|
|
1394 }
|
|
1395
|
|
1396 /* Completed MCU, so update state */
|
|
1397 // BITREAD_SAVE_STATE(cinfo,entropy.bitstate);
|
|
1398 cinfo.buffer = br_state.buffer;
|
|
1399 cinfo.bytes_in_buffer = br_state.bytes_in_buffer;
|
|
1400 cinfo.bytes_offset = br_state.bytes_offset;
|
|
1401 entropy.bitstate.get_buffer = get_buffer;
|
|
1402 entropy.bitstate.bits_left = bits_left;
|
|
1403 // ASSIGN_STATE(entropy.saved, state);
|
|
1404 entropy.saved.EOBRUN = state.EOBRUN;
|
|
1405 entropy.saved.last_dc_val[0] = state.last_dc_val[0];
|
|
1406 entropy.saved.last_dc_val[1] = state.last_dc_val[1];
|
|
1407 entropy.saved.last_dc_val[2] = state.last_dc_val[2];
|
|
1408 entropy.saved.last_dc_val[3] = state.last_dc_val[3];
|
|
1409 }
|
|
1410
|
|
1411 /* Account for restart interval (no-op if not using restarts) */
|
|
1412 entropy.restarts_to_go--;
|
|
1413
|
|
1414 return true;
|
|
1415 }
|
|
1416
|
|
1417 bool process_restart (jpeg_decompress_struct cinfo) {
|
|
1418 phuff_entropy_decoder entropy = this;
|
|
1419 int ci;
|
|
1420
|
|
1421 /* Throw away any unused bits remaining in bit buffer; */
|
|
1422 /* include any full bytes in next_marker's count of discarded bytes */
|
|
1423 cinfo.marker.discarded_bytes += entropy.bitstate.bits_left / 8;
|
|
1424 entropy.bitstate.bits_left = 0;
|
|
1425
|
|
1426 /* Advance past the RSTn marker */
|
|
1427 if (! read_restart_marker (cinfo))
|
|
1428 return false;
|
|
1429
|
|
1430 /* Re-initialize DC predictions to 0 */
|
|
1431 for (ci = 0; ci < cinfo.comps_in_scan; ci++)
|
|
1432 entropy.saved.last_dc_val[ci] = 0;
|
|
1433 /* Re-init EOB run count, too */
|
|
1434 entropy.saved.EOBRUN = 0;
|
|
1435
|
|
1436 /* Reset restart counter */
|
|
1437 entropy.restarts_to_go = cinfo.restart_interval;
|
|
1438
|
|
1439 /* Reset out-of-data flag, unless read_restart_marker left us smack up
|
|
1440 * against a marker. In that case we will end up treating the next data
|
|
1441 * segment as empty, and we can avoid producing bogus output pixels by
|
|
1442 * leaving the flag set.
|
|
1443 */
|
|
1444 if (cinfo.unread_marker is 0)
|
|
1445 entropy.insufficient_data = false;
|
|
1446
|
|
1447 return true;
|
|
1448 }
|
|
1449
|
|
1450 void start_pass_phuff_decoder (jpeg_decompress_struct cinfo) {
|
|
1451 phuff_entropy_decoder entropy = this;
|
|
1452 bool is_DC_band, bad;
|
|
1453 int ci, coefi, tbl;
|
|
1454 int[] coef_bit_ptr;
|
|
1455 jpeg_component_info compptr;
|
|
1456
|
|
1457 is_DC_band = (cinfo.Ss is 0);
|
|
1458
|
|
1459 /* Validate scan parameters */
|
|
1460 bad = false;
|
|
1461 if (is_DC_band) {
|
|
1462 if (cinfo.Se !is 0)
|
|
1463 bad = true;
|
|
1464 } else {
|
|
1465 /* need not check Ss/Se < 0 since they came from unsigned bytes */
|
|
1466 if (cinfo.Ss > cinfo.Se || cinfo.Se >= DCTSIZE2)
|
|
1467 bad = true;
|
|
1468 /* AC scans may have only one component */
|
|
1469 if (cinfo.comps_in_scan !is 1)
|
|
1470 bad = true;
|
|
1471 }
|
|
1472 if (cinfo.Ah !is 0) {
|
|
1473 /* Successive approximation refinement scan: must have Al = Ah-1. */
|
|
1474 if (cinfo.Al !is cinfo.Ah-1)
|
|
1475 bad = true;
|
|
1476 }
|
|
1477 if (cinfo.Al > 13) /* need not check for < 0 */
|
|
1478 bad = true;
|
|
1479 /* Arguably the maximum Al value should be less than 13 for 8-bit precision,
|
|
1480 * but the spec doesn't say so, and we try to be liberal about what we
|
|
1481 * accept. Note: large Al values could result in out-of-range DC
|
|
1482 * coefficients during early scans, leading to bizarre displays due to
|
|
1483 * overflows in the IDCT math. But we won't crash.
|
|
1484 */
|
|
1485 if (bad)
|
|
1486 error();
|
|
1487 // ERREXIT4(cinfo, JERR_BAD_PROGRESSION, cinfo.Ss, cinfo.Se, cinfo.Ah, cinfo.Al);
|
|
1488 /* Update progression status, and verify that scan order is legal.
|
|
1489 * Note that inter-scan inconsistencies are treated as warnings
|
|
1490 * not fatal errors ... not clear if this is right way to behave.
|
|
1491 */
|
|
1492 for (ci = 0; ci < cinfo.comps_in_scan; ci++) {
|
|
1493 int cindex = cinfo.cur_comp_info[ci].component_index;
|
|
1494 coef_bit_ptr = cinfo.coef_bits[cindex];
|
|
1495 if (!is_DC_band && coef_bit_ptr[0] < 0) {/* AC without prior DC scan */
|
|
1496 // WARNMS2(cinfo, JWRN_BOGUS_PROGRESSION, cindex, 0);
|
|
1497 }
|
|
1498 for (coefi = cinfo.Ss; coefi <= cinfo.Se; coefi++) {
|
|
1499 int expected = (coef_bit_ptr[coefi] < 0) ? 0 : coef_bit_ptr[coefi];
|
|
1500 if (cinfo.Ah !is expected) {
|
|
1501 // WARNMS2(cinfo, JWRN_BOGUS_PROGRESSION, cindex, coefi);
|
|
1502 }
|
|
1503 coef_bit_ptr[coefi] = cinfo.Al;
|
|
1504 }
|
|
1505 }
|
|
1506
|
|
1507 /* Select MCU decoding routine */
|
|
1508 // if (cinfo.Ah is 0) {
|
|
1509 // if (is_DC_band)
|
|
1510 // entropy.pub.decode_mcu = decode_mcu_DC_first;
|
|
1511 // else
|
|
1512 // entropy.pub.decode_mcu = decode_mcu_AC_first;
|
|
1513 // } else {
|
|
1514 // if (is_DC_band)
|
|
1515 // entropy.pub.decode_mcu = decode_mcu_DC_refine;
|
|
1516 // else
|
|
1517 // entropy.pub.decode_mcu = decode_mcu_AC_refine;
|
|
1518 // }
|
|
1519
|
|
1520 for (ci = 0; ci < cinfo.comps_in_scan; ci++) {
|
|
1521 compptr = cinfo.cur_comp_info[ci];
|
|
1522 /* Make sure requested tables are present, and compute derived tables.
|
|
1523 * We may build same derived table more than once, but it's not expensive.
|
|
1524 */
|
|
1525 if (is_DC_band) {
|
|
1526 if (cinfo.Ah is 0) { /* DC refinement needs no table */
|
|
1527 tbl = compptr.dc_tbl_no;
|
|
1528 jpeg_make_d_derived_tbl(cinfo, true, tbl, entropy.derived_tbls[tbl] = new d_derived_tbl());
|
|
1529 }
|
|
1530 } else {
|
|
1531 tbl = compptr.ac_tbl_no;
|
|
1532 jpeg_make_d_derived_tbl(cinfo, false, tbl, entropy.derived_tbls[tbl] = new d_derived_tbl());
|
|
1533 /* remember the single active table */
|
|
1534 entropy.ac_derived_tbl = entropy.derived_tbls[tbl];
|
|
1535 }
|
|
1536 /* Initialize DC predictions to 0 */
|
|
1537 entropy.saved.last_dc_val[ci] = 0;
|
|
1538 }
|
|
1539
|
|
1540 /* Initialize bitread state variables */
|
|
1541 entropy.bitstate.bits_left = 0;
|
|
1542 entropy.bitstate.get_buffer = 0; /* unnecessary, but keeps Purify quiet */
|
|
1543 entropy.insufficient_data = false;
|
|
1544
|
|
1545 /* Initialize private state variables */
|
|
1546 entropy.saved.EOBRUN = 0;
|
|
1547
|
|
1548 /* Initialize restart counter */
|
|
1549 entropy.restarts_to_go = cinfo.restart_interval;
|
|
1550 }
|
|
1551
|
|
1552 }
|
|
1553
|
|
1554 static final class jpeg_component_info {
|
|
1555 /* These values are fixed over the whole image. */
|
|
1556 /* For compression, they must be supplied by parameter setup; */
|
|
1557 /* for decompression, they are read from the SOF marker. */
|
|
1558 int component_id; /* identifier for this component (0..255) */
|
|
1559 int component_index; /* its index in SOF or cinfo.comp_info[] */
|
|
1560 int h_samp_factor; /* horizontal sampling factor (1..4) */
|
|
1561 int v_samp_factor; /* vertical sampling factor (1..4) */
|
|
1562 int quant_tbl_no; /* quantization table selector (0..3) */
|
|
1563 /* These values may vary between scans. */
|
|
1564 /* For compression, they must be supplied by parameter setup; */
|
|
1565 /* for decompression, they are read from the SOS marker. */
|
|
1566 /* The decompressor output side may not use these variables. */
|
|
1567 int dc_tbl_no; /* DC entropy table selector (0..3) */
|
|
1568 int ac_tbl_no; /* AC entropy table selector (0..3) */
|
|
1569
|
|
1570 /* Remaining fields should be treated as private by applications. */
|
|
1571
|
|
1572 /* These values are computed during compression or decompression startup: */
|
|
1573 /* Component's size in DCT blocks.
|
|
1574 * Any dummy blocks added to complete an MCU are not counted; therefore
|
|
1575 * these values do not depend on whether a scan is interleaved or not.
|
|
1576 */
|
|
1577 int width_in_blocks;
|
|
1578 int height_in_blocks;
|
|
1579 /* Size of a DCT block in samples. Always DCTSIZE for compression.
|
|
1580 * For decompression this is the size of the output from one DCT block,
|
|
1581 * reflecting any scaling we choose to apply during the IDCT step.
|
|
1582 * Values of 1,2,4,8 are likely to be supported. Note that different
|
|
1583 * components may receive different IDCT scalings.
|
|
1584 */
|
|
1585 int DCT_scaled_size;
|
|
1586 /* The downsampled dimensions are the component's actual, unpadded number
|
|
1587 * of samples at the main buffer (preprocessing/compression interface), thus
|
|
1588 * downsampled_width = ceil(image_width * Hi/Hmax)
|
|
1589 * and similarly for height. For decompression, IDCT scaling is included, so
|
|
1590 * downsampled_width = ceil(image_width * Hi/Hmax * DCT_scaled_size/DCTSIZE)
|
|
1591 */
|
|
1592 int downsampled_width; /* actual width in samples */
|
|
1593 int downsampled_height; /* actual height in samples */
|
|
1594 /* This flag is used only for decompression. In cases where some of the
|
|
1595 * components will be ignored (eg grayscale output from YCbCr image),
|
|
1596 * we can skip most computations for the unused components.
|
|
1597 */
|
|
1598 bool component_needed; /* do we need the value of this component? */
|
|
1599
|
|
1600 /* These values are computed before starting a scan of the component. */
|
|
1601 /* The decompressor output side may not use these variables. */
|
|
1602 int MCU_width; /* number of blocks per MCU, horizontally */
|
|
1603 int MCU_height; /* number of blocks per MCU, vertically */
|
|
1604 int MCU_blocks; /* MCU_width * MCU_height */
|
|
1605 int MCU_sample_width; /* MCU width in samples, MCU_width*DCT_scaled_size */
|
|
1606 int last_col_width; /* # of non-dummy blocks across in last MCU */
|
|
1607 int last_row_height; /* # of non-dummy blocks down in last MCU */
|
|
1608
|
|
1609 /* Saved quantization table for component; null if none yet saved.
|
|
1610 * See jdinput.c comments about the need for this information.
|
|
1611 * This field is currently used only for decompression.
|
|
1612 */
|
|
1613 JQUANT_TBL quant_table;
|
|
1614
|
|
1615 /* Private per-component storage for DCT or IDCT subsystem. */
|
|
1616 int[] dct_table;
|
|
1617 }
|
|
1618
|
|
1619 static final class jpeg_color_quantizer {
|
|
1620 // JMETHOD(void, start_pass, (j_decompress_ptr cinfo, bool is_pre_scan));
|
|
1621 // JMETHOD(void, color_quantize, (j_decompress_ptr cinfo,
|
|
1622 // JSAMPARRAY input_buf, JSAMPARRAY output_buf,
|
|
1623 // int num_rows));
|
|
1624 // JMETHOD(void, finish_pass, (j_decompress_ptr cinfo));
|
|
1625 // JMETHOD(void, new_color_map, (j_decompress_ptr cinfo));
|
|
1626
|
|
1627 /* Initially allocated colormap is saved here */
|
|
1628 int[][] sv_colormap; /* The color map as a 2-D pixel array */
|
|
1629 int sv_actual; /* number of entries in use */
|
|
1630
|
|
1631 int[][] colorindex; /* Precomputed mapping for speed */
|
|
1632 /* colorindex[i][j] = index of color closest to pixel value j in component i,
|
|
1633 * premultiplied as described above. Since colormap indexes must fit into
|
|
1634 * JSAMPLEs, the entries of this array will too.
|
|
1635 */
|
|
1636 bool is_padded; /* is the colorindex padded for odither? */
|
|
1637
|
|
1638 int[MAX_Q_COMPS] Ncolors;// = new int [MAX_Q_COMPS]; /* # of values alloced to each component */
|
|
1639
|
|
1640 /* Variables for ordered dithering */
|
|
1641 int row_index; /* cur row's vertical index in dither matrix */
|
|
1642 // ODITHER_MATRIX_PTR odither[MAX_Q_COMPS]; /* one dither array per component */
|
|
1643
|
|
1644 /* Variables for Floyd-Steinberg dithering */
|
|
1645 // FSERRPTR fserrors[MAX_Q_COMPS]; /* accumulated errors */
|
|
1646 bool on_odd_row;
|
|
1647
|
|
1648 void start_pass (jpeg_decompress_struct cinfo, bool is_pre_scan) {
|
|
1649 error();
|
|
1650 }
|
|
1651 }
|
|
1652
|
|
1653 static final class jpeg_upsampler {
|
|
1654 // JMETHOD(void, start_pass, (j_decompress_ptr cinfo));
|
|
1655 // JMETHOD(void, upsample, (j_decompress_ptr cinfo,
|
|
1656 // JSAMPIMAGE input_buf,
|
|
1657 // JDIMENSION *in_row_group_ctr,
|
|
1658 // JDIMENSION in_row_groups_avail,
|
|
1659 // JSAMPARRAY output_buf,
|
|
1660 // JDIMENSION *out_row_ctr,
|
|
1661 // JDIMENSION out_rows_avail));
|
|
1662
|
|
1663 bool need_context_rows; /* TRUE if need rows above & below */
|
|
1664
|
|
1665 /* Color conversion buffer. When using separate upsampling and color
|
|
1666 * conversion steps, this buffer holds one upsampled row group until it
|
|
1667 * has been color converted and output.
|
|
1668 * Note: we do not allocate any storage for component(s) which are full-size,
|
|
1669 * ie do not need rescaling. The corresponding entry of color_buf[] is
|
|
1670 * simply set to point to the input data array, thereby avoiding copying.
|
|
1671 */
|
|
1672 byte[][][MAX_COMPONENTS] color_buf;// = new byte[MAX_COMPONENTS][][];
|
|
1673 int[MAX_COMPONENTS] color_buf_offset;// = new int[MAX_COMPONENTS];
|
|
1674
|
|
1675 /* Per-component upsampling method pointers */
|
|
1676 int[MAX_COMPONENTS] methods;// = new int[MAX_COMPONENTS];
|
|
1677
|
|
1678 int next_row_out; /* counts rows emitted from color_buf */
|
|
1679 int rows_to_go; /* counts rows remaining in image */
|
|
1680
|
|
1681 /* Height of an input row group for each component. */
|
|
1682 int[MAX_COMPONENTS] rowgroup_height;// = new int[MAX_COMPONENTS];
|
|
1683
|
|
1684 /* These arrays save pixel expansion factors so that int_expand need not
|
|
1685 * recompute them each time. They are unused for other upsampling methods.
|
|
1686 */
|
|
1687 byte[MAX_COMPONENTS] h_expand;// = new byte[MAX_COMPONENTS];
|
|
1688 byte[MAX_COMPONENTS] v_expand;// = new byte[MAX_COMPONENTS];
|
|
1689
|
|
1690 void start_pass (jpeg_decompress_struct cinfo) {
|
|
1691 jpeg_upsampler upsample = cinfo.upsample;
|
|
1692
|
|
1693 /* Mark the conversion buffer empty */
|
|
1694 upsample.next_row_out = cinfo.max_v_samp_factor;
|
|
1695 /* Initialize total-height counter for detecting bottom of image */
|
|
1696 upsample.rows_to_go = cinfo.output_height;
|
|
1697 }
|
|
1698
|
|
1699 }
|
|
1700
|
|
1701 static final class jpeg_marker_reader {
|
|
1702 /* Read a restart marker --- exported for use by entropy decoder only */
|
|
1703 // jpeg_marker_parser_method read_restart_marker;
|
|
1704
|
|
1705 /* State of marker reader --- nominally internal, but applications
|
|
1706 * supplying COM or APPn handlers might like to know the state.
|
|
1707 */
|
|
1708 bool saw_SOI; /* found SOI? */
|
|
1709 bool saw_SOF; /* found SOF? */
|
|
1710 int next_restart_num; /* next restart number expected (0-7) */
|
|
1711 int discarded_bytes; /* # of bytes skipped looking for a marker */
|
|
1712
|
|
1713 /* Application-overridable marker processing methods */
|
|
1714 // jpeg_marker_parser_method process_COM;
|
|
1715 // jpeg_marker_parser_method process_APPn[16];
|
|
1716
|
|
1717 /* Limit on marker data length to save for each marker type */
|
|
1718 int length_limit_COM;
|
|
1719 int[16] length_limit_APPn;// = new int[16];
|
|
1720
|
|
1721 /* Status of COM/APPn marker saving */
|
|
1722 // jpeg_marker_reader cur_marker; /* null if not processing a marker */
|
|
1723 // int bytes_read; /* data bytes read so far in marker */
|
|
1724 /* Note: cur_marker is not linked into marker_list until it's all read. */
|
|
1725 }
|
|
1726
|
|
1727
|
|
1728 static final class jpeg_d_main_controller {
|
|
1729 // JMETHOD(void, start_pass, (j_decompress_ptr cinfo, J_BUF_MODE pass_mode));
|
|
1730 int process_data;
|
|
1731
|
|
1732 /* Pointer to allocated workspace (M or M+2 row groups). */
|
|
1733 byte[][][MAX_COMPONENTS] buffer;// = new byte[MAX_COMPONENTS][][];
|
|
1734 int[MAX_COMPONENTS] buffer_offset;// = new int[MAX_COMPONENTS];
|
|
1735
|
|
1736 bool buffer_full; /* Have we gotten an iMCU row from decoder? */
|
|
1737 int[1] rowgroup_ctr;// = new int[1]; /* counts row groups output to postprocessor */
|
|
1738
|
|
1739 /* Remaining fields are only used in the context case. */
|
|
1740
|
|
1741 /* These are the master pointers to the funny-order pointer lists. */
|
|
1742 byte[][][][2] xbuffer;// = new byte[2][][][]; /* pointers to weird pointer lists */
|
|
1743 int[][2] xbuffer_offset;// = new int[2][];
|
|
1744
|
|
1745 int whichptr; /* indicates which pointer set is now in use */
|
|
1746 int context_state; /* process_data state machine status */
|
|
1747 int rowgroups_avail; /* row groups available to postprocessor */
|
|
1748 int iMCU_row_ctr; /* counts iMCU rows to detect image top/bot */
|
|
1749
|
|
1750 void start_pass (jpeg_decompress_struct cinfo, int pass_mode) {
|
|
1751 jpeg_d_main_controller main = cinfo.main;
|
|
1752
|
|
1753 switch (pass_mode) {
|
|
1754 case JBUF_PASS_THRU:
|
|
1755 if (cinfo.upsample.need_context_rows) {
|
|
1756 main.process_data = PROCESS_DATA_CONTEXT_MAIN;
|
|
1757 make_funny_pointers(cinfo); /* Create the xbuffer[] lists */
|
|
1758 main.whichptr = 0; /* Read first iMCU row into xbuffer[0] */
|
|
1759 main.context_state = CTX_PREPARE_FOR_IMCU;
|
|
1760 main.iMCU_row_ctr = 0;
|
|
1761 } else {
|
|
1762 /* Simple case with no context needed */
|
|
1763 main.process_data = PROCESS_DATA_SIMPLE_MAIN;
|
|
1764 }
|
|
1765 main.buffer_full = false; /* Mark buffer empty */
|
|
1766 main.rowgroup_ctr[0] = 0;
|
|
1767 break;
|
|
1768 // #ifdef QUANT_2PASS_SUPPORTED
|
|
1769 // case JBUF_CRANK_DEST:
|
|
1770 // /* For last pass of 2-pass quantization, just crank the postprocessor */
|
|
1771 // main.process_data = PROCESS_DATA_CRANK_POST;
|
|
1772 // break;
|
|
1773 // #endif
|
|
1774 default:
|
|
1775 error();
|
|
1776 // ERREXIT(cinfo, JERR_BAD_BUFFER_MODE);
|
|
1777 break;
|
|
1778 }
|
|
1779 }
|
|
1780
|
|
1781 }
|
|
1782
|
|
1783 static final class jpeg_decomp_master {
|
|
1784 // JMETHOD(void, prepare_for_output_pass, (j_decompress_ptr cinfo));
|
|
1785 // JMETHOD(void, finish_output_pass, (j_decompress_ptr cinfo));
|
|
1786
|
|
1787 /* State variables made visible to other modules */
|
|
1788 bool is_dummy_pass;
|
|
1789
|
|
1790 int pass_number; /* # of passes completed */
|
|
1791
|
|
1792 bool using_merged_upsample; /* true if using merged upsample/cconvert */
|
|
1793
|
|
1794 /* Saved references to initialized quantizer modules,
|
|
1795 * in case we need to switch modes.
|
|
1796 */
|
|
1797 jpeg_color_quantizer quantizer_1pass;
|
|
1798 jpeg_color_quantizer quantizer_2pass;
|
|
1799 }
|
|
1800
|
|
1801 static final class jpeg_inverse_dct {
|
|
1802 // JMETHOD(void, start_pass, (j_decompress_ptr cinfo));
|
|
1803 // /* It is useful to allow each component to have a separate IDCT method. */
|
|
1804 // inverse_DCT_method_ptr inverse_DCT[MAX_COMPONENTS];
|
|
1805 int[MAX_COMPONENTS] cur_method;// = new int[MAX_COMPONENTS];
|
|
1806
|
|
1807 void start_pass (jpeg_decompress_struct cinfo) {
|
|
1808 jpeg_inverse_dct idct = cinfo.idct;
|
|
1809 int ci, i;
|
|
1810 jpeg_component_info compptr;
|
|
1811 int method = 0;
|
|
1812 // inverse_DCT_method_ptr method_ptr = NULL;
|
|
1813 JQUANT_TBL qtbl;
|
|
1814
|
|
1815 for (ci = 0; ci < cinfo.num_components; ci++) {
|
|
1816 compptr = cinfo.comp_info[ci];
|
|
1817 /* Select the proper IDCT routine for this component's scaling */
|
|
1818 switch (compptr.DCT_scaled_size) {
|
|
1819 // #ifdef IDCT_SCALING_SUPPORTED
|
|
1820 // case 1:
|
|
1821 // method_ptr = jpeg_idct_1x1;
|
|
1822 // method = JDCT_ISLOW; /* jidctred uses islow-style table */
|
|
1823 // break;
|
|
1824 // case 2:
|
|
1825 // method_ptr = jpeg_idct_2x2;
|
|
1826 // method = JDCT_ISLOW; /* jidctred uses islow-style table */
|
|
1827 // break;
|
|
1828 // case 4:
|
|
1829 // method_ptr = jpeg_idct_4x4;
|
|
1830 // method = JDCT_ISLOW; /* jidctred uses islow-style table */
|
|
1831 // break;
|
|
1832 // #endif
|
|
1833 case DCTSIZE:
|
|
1834 switch (cinfo.dct_method) {
|
|
1835 // #ifdef DCT_ISLOW_SUPPORTED
|
|
1836 case JDCT_ISLOW:
|
|
1837 // method_ptr = jpeg_idct_islow;
|
|
1838 method = JDCT_ISLOW;
|
|
1839 break;
|
|
1840 // #endif
|
|
1841 // #ifdef DCT_IFAST_SUPPORTED
|
|
1842 // case JDCT_IFAST:
|
|
1843 // method_ptr = jpeg_idct_ifast;
|
|
1844 // method = JDCT_IFAST;
|
|
1845 // break;
|
|
1846 // #endif
|
|
1847 // #ifdef DCT_FLOAT_SUPPORTED
|
|
1848 // case JDCT_FLOAT:
|
|
1849 // method_ptr = jpeg_idct_float;
|
|
1850 // method = JDCT_FLOAT;
|
|
1851 // break;
|
|
1852 // #endif
|
|
1853 default:
|
|
1854 error();
|
|
1855 // ERREXIT(cinfo, JERR_NOT_COMPILED);
|
|
1856 break;
|
|
1857 }
|
|
1858 break;
|
|
1859 default:
|
|
1860 error();
|
|
1861 // ERREXIT1(cinfo, JERR_BAD_DCTSIZE, compptr.DCT_scaled_size);
|
|
1862 break;
|
|
1863 }
|
|
1864 // idct.inverse_DCT[ci] = method_ptr;
|
|
1865 /* Create multiplier table from quant table.
|
|
1866 * However, we can skip this if the component is uninteresting
|
|
1867 * or if we already built the table. Also, if no quant table
|
|
1868 * has yet been saved for the component, we leave the
|
|
1869 * multiplier table all-zero; we'll be reading zeroes from the
|
|
1870 * coefficient controller's buffer anyway.
|
|
1871 */
|
|
1872 if (! compptr.component_needed || idct.cur_method[ci] is method)
|
|
1873 continue;
|
|
1874 qtbl = compptr.quant_table;
|
|
1875 if (qtbl is null) /* happens if no data yet for component */
|
|
1876 continue;
|
|
1877 idct.cur_method[ci] = method;
|
|
1878 switch (method) {
|
|
1879 // #ifdef PROVIDE_ISLOW_TABLES
|
|
1880 case JDCT_ISLOW:
|
|
1881 {
|
|
1882 /* For LL&M IDCT method, multipliers are equal to raw quantization
|
|
1883 * coefficients, but are stored as ints to ensure access efficiency.
|
|
1884 */
|
|
1885 int[] ismtbl = compptr.dct_table;
|
|
1886 for (i = 0; i < DCTSIZE2; i++) {
|
|
1887 ismtbl[i] = qtbl.quantval[i];
|
|
1888 }
|
|
1889 }
|
|
1890 break;
|
|
1891 // #endif
|
|
1892 // #ifdef DCT_IFAST_SUPPORTED
|
|
1893 // case JDCT_IFAST:
|
|
1894 // {
|
|
1895 // /* For AA&N IDCT method, multipliers are equal to quantization
|
|
1896 // * coefficients scaled by scalefactor[row]*scalefactor[col], where
|
|
1897 // * scalefactor[0] = 1
|
|
1898 // * scalefactor[k] = cos(k*PI/16) * sqrt(2) for k=1..7
|
|
1899 // * For integer operation, the multiplier table is to be scaled by
|
|
1900 // * IFAST_SCALE_BITS.
|
|
1901 // */
|
|
1902 // int[] ifmtbl = compptr.dct_table;
|
|
1903 // short aanscales[] = {
|
|
1904 // /* precomputed values scaled up by 14 bits */
|
|
1905 // 16384, 22725, 21407, 19266, 16384, 12873, 8867, 4520,
|
|
1906 // 22725, 31521, 29692, 26722, 22725, 17855, 12299, 6270,
|
|
1907 // 21407, 29692, 27969, 25172, 21407, 16819, 11585, 5906,
|
|
1908 // 19266, 26722, 25172, 22654, 19266, 15137, 10426, 5315,
|
|
1909 // 16384, 22725, 21407, 19266, 16384, 12873, 8867, 4520,
|
|
1910 // 12873, 17855, 16819, 15137, 12873, 10114, 6967, 3552,
|
|
1911 // 8867, 12299, 11585, 10426, 8867, 6967, 4799, 2446,
|
|
1912 // 4520, 6270, 5906, 5315, 4520, 3552, 2446, 1247
|
|
1913 // };
|
|
1914 // SHIFT_TEMPS
|
|
1915 //
|
|
1916 // for (i = 0; i < DCTSIZE2; i++) {
|
|
1917 // ifmtbl[i] = DESCALE(MULTIPLY16V16( qtbl.quantval[i], aanscales[i]), CONST_BITS-IFAST_SCALE_BITS);
|
|
1918 // }
|
|
1919 // }
|
|
1920 // break;
|
|
1921 // #endif
|
|
1922 // #ifdef DCT_FLOAT_SUPPORTED
|
|
1923 // case JDCT_FLOAT:
|
|
1924 // {
|
|
1925 // /* For float AA&N IDCT method, multipliers are equal to quantization
|
|
1926 // * coefficients scaled by scalefactor[row]*scalefactor[col], where
|
|
1927 // * scalefactor[0] = 1
|
|
1928 // * scalefactor[k] = cos(k*PI/16) * sqrt(2) for k=1..7
|
|
1929 // */
|
|
1930 // FLOAT_MULT_TYPE * fmtbl = (FLOAT_MULT_TYPE *) compptr.dct_table;
|
|
1931 // int row, col;
|
|
1932 // static const double aanscalefactor[DCTSIZE] = {
|
|
1933 // 1.0, 1.387039845, 1.306562965, 1.175875602,
|
|
1934 // 1.0, 0.785694958, 0.541196100, 0.275899379
|
|
1935 // };
|
|
1936 //
|
|
1937 // i = 0;
|
|
1938 // for (row = 0; row < DCTSIZE; row++) {
|
|
1939 // for (col = 0; col < DCTSIZE; col++) {
|
|
1940 // fmtbl[i] = (FLOAT_MULT_TYPE)
|
|
1941 // ((double) qtbl.quantval[i] *
|
|
1942 // aanscalefactor[row] * aanscalefactor[col]);
|
|
1943 // i++;
|
|
1944 // }
|
|
1945 // }
|
|
1946 // }
|
|
1947 // break;
|
|
1948 // #endif
|
|
1949 default:
|
|
1950 error();
|
|
1951 // ERREXIT(cinfo, JERR_NOT_COMPILED);
|
|
1952 break;
|
|
1953 }
|
|
1954 }
|
|
1955 }
|
|
1956 }
|
|
1957
|
|
1958 static final class jpeg_input_controller {
|
|
1959 int consume_input;
|
|
1960 bool has_multiple_scans; /* True if file has multiple scans */
|
|
1961 bool eoi_reached;
|
|
1962
|
|
1963 bool inheaders; /* true until first SOS is reached */
|
|
1964 }
|
|
1965
|
|
1966 static final class jpeg_color_deconverter {
|
|
1967 // JMETHOD(void, start_pass, (j_decompress_ptr cinfo));
|
|
1968 int color_convert;
|
|
1969
|
|
1970 /* Private state for YCC.RGB conversion */
|
|
1971 int[] Cr_r_tab; /* => table for Cr to R conversion */
|
|
1972 int[] Cb_b_tab; /* => table for Cb to B conversion */
|
|
1973 int[] Cr_g_tab; /* => table for Cr to G conversion */
|
|
1974 int[] Cb_g_tab; /* => table for Cb to G conversion */
|
|
1975
|
|
1976 void start_pass (jpeg_decompress_struct cinfo) {
|
|
1977 /* no work needed */
|
|
1978 }
|
|
1979
|
|
1980 }
|
|
1981
|
|
1982 static final class jpeg_d_post_controller {
|
|
1983 // JMETHOD(void, start_pass, (j_decompress_ptr cinfo, J_BUF_MODE pass_mode));
|
|
1984 int post_process_data;
|
|
1985
|
|
1986 /* Color quantization source buffer: this holds output data from
|
|
1987 * the upsample/color conversion step to be passed to the quantizer.
|
|
1988 * For two-pass color quantization, we need a full-image buffer;
|
|
1989 * for one-pass operation, a strip buffer is sufficient.
|
|
1990 */
|
|
1991 int[] whole_image; /* virtual array, or NULL if one-pass */
|
|
1992 int[][] buffer; /* strip buffer, or current strip of virtual */
|
|
1993 int strip_height; /* buffer size in rows */
|
|
1994 /* for two-pass mode only: */
|
|
1995 int starting_row; /* row # of first row in current strip */
|
|
1996 int next_row; /* index of next row to fill/empty in strip */
|
|
1997
|
|
1998 void start_pass (jpeg_decompress_struct cinfo, int pass_mode) {
|
|
1999 jpeg_d_post_controller post = cinfo.post;
|
|
2000
|
|
2001 switch (pass_mode) {
|
|
2002 case JBUF_PASS_THRU:
|
|
2003 if (cinfo.quantize_colors) {
|
|
2004 error(SWT.ERROR_NOT_IMPLEMENTED);
|
|
2005 // /* Single-pass processing with color quantization. */
|
|
2006 // post.post_process_data = POST_PROCESS_1PASS;
|
|
2007 // /* We could be doing buffered-image output before starting a 2-pass
|
|
2008 // * color quantization; in that case, jinit_d_post_controller did not
|
|
2009 // * allocate a strip buffer. Use the virtual-array buffer as workspace.
|
|
2010 // */
|
|
2011 // if (post.buffer is null) {
|
|
2012 // post.buffer = (*cinfo.mem.access_virt_sarray)
|
|
2013 // ((j_common_ptr) cinfo, post.whole_image,
|
|
2014 // (JDIMENSION) 0, post.strip_height, TRUE);
|
|
2015 // }
|
|
2016 } else {
|
|
2017 /* For single-pass processing without color quantization,
|
|
2018 * I have no work to do; just call the upsampler directly.
|
|
2019 */
|
|
2020 post.post_process_data = POST_PROCESS_DATA_UPSAMPLE;
|
|
2021 }
|
|
2022 break;
|
|
2023 // #ifdef QUANT_2PASS_SUPPORTED
|
|
2024 // case JBUF_SAVE_AND_PASS:
|
|
2025 // /* First pass of 2-pass quantization */
|
|
2026 // if (post.whole_image is NULL)
|
|
2027 // ERREXIT(cinfo, JERR_BAD_BUFFER_MODE);
|
|
2028 // post.pub.post_process_data = post_process_prepass;
|
|
2029 // break;
|
|
2030 // case JBUF_CRANK_DEST:
|
|
2031 // /* Second pass of 2-pass quantization */
|
|
2032 // if (post.whole_image is NULL)
|
|
2033 // ERREXIT(cinfo, JERR_BAD_BUFFER_MODE);
|
|
2034 // post.pub.post_process_data = post_process_2pass;
|
|
2035 // break;
|
|
2036 // #endif /* QUANT_2PASS_SUPPORTED */
|
|
2037 default:
|
|
2038 error();
|
|
2039 // ERREXIT(cinfo, JERR_BAD_BUFFER_MODE);
|
|
2040 break;
|
|
2041 }
|
|
2042 post.starting_row = post.next_row = 0;
|
|
2043 }
|
|
2044
|
|
2045 }
|
|
2046
|
|
2047 static final class jpeg_decompress_struct {
|
|
2048 // jpeg_error_mgr * err; /* Error handler module */\
|
|
2049 // struct jpeg_memory_mgr * mem; /* Memory manager module */\
|
|
2050 // struct jpeg_progress_mgr * progress; /* Progress monitor, or null if none */\
|
|
2051 // void * client_data; /* Available for use by application */\
|
|
2052 bool is_decompressor; /* So common code can tell which is which */
|
|
2053 int global_state; /* For checking call sequence validity */
|
|
2054
|
|
2055 // /* Source of compressed data */
|
|
2056 // struct jpeg_source_mgr * src;
|
|
2057 InputStream inputStream;
|
|
2058 byte[] buffer;
|
|
2059 int bytes_in_buffer;
|
|
2060 int bytes_offset;
|
|
2061 bool start_of_file;
|
|
2062
|
|
2063 /* Basic description of image --- filled in by jpeg_read_header(). */
|
|
2064 /* Application may inspect these values to decide how to process image. */
|
|
2065
|
|
2066 int image_width; /* nominal image width (from SOF marker) */
|
|
2067 int image_height; /* nominal image height */
|
|
2068 int num_components; /* # of color components in JPEG image */
|
|
2069 int jpeg_color_space; /* colorspace of JPEG image */
|
|
2070
|
|
2071 /* Decompression processing parameters --- these fields must be set before
|
|
2072 * calling jpeg_start_decompress(). Note that jpeg_read_header() initializes
|
|
2073 * them to default values.
|
|
2074 */
|
|
2075
|
|
2076 int out_color_space; /* colorspace for output */
|
|
2077
|
|
2078 int scale_num, scale_denom; /* fraction by which to scale image */
|
|
2079
|
|
2080 double output_gamma; /* image gamma wanted in output */
|
|
2081
|
|
2082 bool buffered_image; /* true=multiple output passes */
|
|
2083 bool raw_data_out; /* true=downsampled data wanted */
|
|
2084
|
|
2085 int dct_method; /* IDCT algorithm selector */
|
|
2086 bool do_fancy_upsampling; /* true=apply fancy upsampling */
|
|
2087 bool do_block_smoothing; /* true=apply interblock smoothing */
|
|
2088
|
|
2089 bool quantize_colors; /* true=colormapped output wanted */
|
|
2090 /* the following are ignored if not quantize_colors: */
|
|
2091 int dither_mode; /* type of color dithering to use */
|
|
2092 bool two_pass_quantize; /* true=use two-pass color quantization */
|
|
2093 int desired_number_of_colors; /* max # colors to use in created colormap */
|
|
2094 /* these are significant only in buffered-image mode: */
|
|
2095 bool enable_1pass_quant; /* enable future use of 1-pass quantizer */
|
|
2096 bool enable_external_quant;/* enable future use of external colormap */
|
|
2097 bool enable_2pass_quant; /* enable future use of 2-pass quantizer */
|
|
2098
|
|
2099 /* Description of actual output image that will be returned to application.
|
|
2100 * These fields are computed by jpeg_start_decompress().
|
|
2101 * You can also use jpeg_calc_output_dimensions() to determine these values
|
|
2102 * in advance of calling jpeg_start_decompress().
|
|
2103 */
|
|
2104
|
|
2105 int output_width; /* scaled image width */
|
|
2106 int output_height; /* scaled image height */
|
|
2107 int out_color_components; /* # of color components in out_color_space */
|
|
2108 int output_components; /* # of color components returned */
|
|
2109 /* output_components is 1 (a colormap index) when quantizing colors;
|
|
2110 * otherwise it equals out_color_components.
|
|
2111 */
|
|
2112 int rec_outbuf_height; /* min recommended height of scanline buffer */
|
|
2113 /* If the buffer passed to jpeg_read_scanlines() is less than this many rows
|
|
2114 * high, space and time will be wasted due to unnecessary data copying.
|
|
2115 * Usually rec_outbuf_height will be 1 or 2, at most 4.
|
|
2116 */
|
|
2117
|
|
2118 /* When quantizing colors, the output colormap is described by these fields.
|
|
2119 * The application can supply a colormap by setting colormap non-null before
|
|
2120 * calling jpeg_start_decompress; otherwise a colormap is created during
|
|
2121 * jpeg_start_decompress or jpeg_start_output.
|
|
2122 * The map has out_color_components rows and actual_number_of_colors columns.
|
|
2123 */
|
|
2124 int actual_number_of_colors; /* number of entries in use */
|
|
2125 int[] colormap; /* The color map as a 2-D pixel array */
|
|
2126
|
|
2127 /* State variables: these variables indicate the progress of decompression.
|
|
2128 * The application may examine these but must not modify them.
|
|
2129 */
|
|
2130
|
|
2131 /* Row index of next scanline to be read from jpeg_read_scanlines().
|
|
2132 * Application may use this to control its processing loop, e.g.,
|
|
2133 * "while (output_scanline < output_height)".
|
|
2134 */
|
|
2135 int output_scanline; /* 0 .. output_height-1 */
|
|
2136
|
|
2137 /* Current input scan number and number of iMCU rows completed in scan.
|
|
2138 * These indicate the progress of the decompressor input side.
|
|
2139 */
|
|
2140 int input_scan_number; /* Number of SOS markers seen so far */
|
|
2141 int input_iMCU_row; /* Number of iMCU rows completed */
|
|
2142
|
|
2143 /* The "output scan number" is the notional scan being displayed by the
|
|
2144 * output side. The decompressor will not allow output scan/row number
|
|
2145 * to get ahead of input scan/row, but it can fall arbitrarily far behind.
|
|
2146 */
|
|
2147 int output_scan_number; /* Nominal scan number being displayed */
|
|
2148 int output_iMCU_row; /* Number of iMCU rows read */
|
|
2149
|
|
2150 /* Current progression status. coef_bits[c][i] indicates the precision
|
|
2151 * with which component c's DCT coefficient i (in zigzag order) is known.
|
|
2152 * It is -1 when no data has yet been received, otherwise it is the point
|
|
2153 * transform (shift) value for the most recent scan of the coefficient
|
|
2154 * (thus, 0 at completion of the progression).
|
|
2155 * This pointer is null when reading a non-progressive file.
|
|
2156 */
|
|
2157 int[][] coef_bits; /* -1 or current Al value for each coef */
|
|
2158
|
|
2159 /* Internal JPEG parameters --- the application usually need not look at
|
|
2160 * these fields. Note that the decompressor output side may not use
|
|
2161 * any parameters that can change between scans.
|
|
2162 */
|
|
2163
|
|
2164 /* Quantization and Huffman tables are carried forward across input
|
|
2165 * datastreams when processing abbreviated JPEG datastreams.
|
|
2166 */
|
|
2167
|
|
2168 JQUANT_TBL[NUM_QUANT_TBLS] quant_tbl_ptrs;// = new JQUANT_TBL[NUM_QUANT_TBLS];
|
|
2169 /* ptrs to coefficient quantization tables, or null if not defined */
|
|
2170
|
|
2171 JHUFF_TBL[NUM_HUFF_TBLS] dc_huff_tbl_ptrs;// = new JHUFF_TBL[NUM_HUFF_TBLS];
|
|
2172 JHUFF_TBL[NUM_HUFF_TBLS] ac_huff_tbl_ptrs;// = new JHUFF_TBL[NUM_HUFF_TBLS];
|
|
2173 /* ptrs to Huffman coding tables, or null if not defined */
|
|
2174
|
|
2175 /* These parameters are never carried across datastreams, since they
|
|
2176 * are given in SOF/SOS markers or defined to be reset by SOI.
|
|
2177 */
|
|
2178
|
|
2179 int data_precision; /* bits of precision in image data */
|
|
2180
|
|
2181 jpeg_component_info[] comp_info;
|
|
2182 /* comp_info[i] describes component that appears i'th in SOF */
|
|
2183
|
|
2184 bool progressive_mode; /* true if SOFn specifies progressive mode */
|
|
2185 bool arith_code; /* true=arithmetic coding, false=Huffman */
|
|
2186
|
|
2187 byte[NUM_ARITH_TBLS] arith_dc_L;// = new byte[NUM_ARITH_TBLS]; /* L values for DC arith-coding tables */
|
|
2188 byte[NUM_ARITH_TBLS] arith_dc_U;// = new byte[NUM_ARITH_TBLS]; /* U values for DC arith-coding tables */
|
|
2189 byte[NUM_ARITH_TBLS] arith_ac_K;// = new byte[NUM_ARITH_TBLS]; /* Kx values for AC arith-coding tables */
|
|
2190
|
|
2191 int restart_interval; /* MCUs per restart interval, or 0 for no restart */
|
|
2192
|
|
2193 /* These fields record data obtained from optional markers recognized by
|
|
2194 * the JPEG library.
|
|
2195 */
|
|
2196 bool saw_JFIF_marker; /* true iff a JFIF APP0 marker was found */
|
|
2197 /* Data copied from JFIF marker; only valid if saw_JFIF_marker is true: */
|
|
2198 byte JFIF_major_version; /* JFIF version number */
|
|
2199 byte JFIF_minor_version;
|
|
2200 byte density_unit; /* JFIF code for pixel size units */
|
|
2201 short X_density; /* Horizontal pixel density */
|
|
2202 short Y_density; /* Vertical pixel density */
|
|
2203 bool saw_Adobe_marker; /* true iff an Adobe APP14 marker was found */
|
|
2204 byte Adobe_transform; /* Color transform code from Adobe marker */
|
|
2205
|
|
2206 bool CCIR601_sampling; /* true=first samples are cosited */
|
|
2207
|
|
2208 /* Aside from the specific data retained from APPn markers known to the
|
|
2209 * library, the uninterpreted contents of any or all APPn and COM markers
|
|
2210 * can be saved in a list for examination by the application.
|
|
2211 */
|
|
2212 jpeg_marker_reader marker_list; /* Head of list of saved markers */
|
|
2213
|
|
2214 /* Remaining fields are known throughout decompressor, but generally
|
|
2215 * should not be touched by a surrounding application.
|
|
2216 */
|
|
2217
|
|
2218 /*
|
|
2219 * These fields are computed during decompression startup
|
|
2220 */
|
|
2221 int max_h_samp_factor; /* largest h_samp_factor */
|
|
2222 int max_v_samp_factor; /* largest v_samp_factor */
|
|
2223
|
|
2224 int min_DCT_scaled_size; /* smallest DCT_scaled_size of any component */
|
|
2225
|
|
2226 int total_iMCU_rows; /* # of iMCU rows in image */
|
|
2227 /* The coefficient controller's input and output progress is measured in
|
|
2228 * units of "iMCU" (interleaved MCU) rows. These are the same as MCU rows
|
|
2229 * in fully interleaved JPEG scans, but are used whether the scan is
|
|
2230 * interleaved or not. We define an iMCU row as v_samp_factor DCT block
|
|
2231 * rows of each component. Therefore, the IDCT output contains
|
|
2232 * v_samp_factor*DCT_scaled_size sample rows of a component per iMCU row.
|
|
2233 */
|
|
2234
|
|
2235 byte[] sample_range_limit; /* table for fast range-limiting */
|
|
2236 int sample_range_limit_offset;
|
|
2237
|
|
2238 /*
|
|
2239 * These fields are valid during any one scan.
|
|
2240 * They describe the components and MCUs actually appearing in the scan.
|
|
2241 * Note that the decompressor output side must not use these fields.
|
|
2242 */
|
|
2243 int comps_in_scan; /* # of JPEG components in this scan */
|
|
2244 jpeg_component_info[MAX_COMPS_IN_SCAN] cur_comp_info;// = new jpeg_component_info[MAX_COMPS_IN_SCAN];
|
|
2245 /* *cur_comp_info[i] describes component that appears i'th in SOS */
|
|
2246
|
|
2247 int MCUs_per_row; /* # of MCUs across the image */
|
|
2248 int MCU_rows_in_scan; /* # of MCU rows in the image */
|
|
2249
|
|
2250 int blocks_in_MCU; /* # of DCT blocks per MCU */
|
|
2251 int[D_MAX_BLOCKS_IN_MCU] MCU_membership;// = new int[D_MAX_BLOCKS_IN_MCU];
|
|
2252 /* MCU_membership[i] is index in cur_comp_info of component owning */
|
|
2253 /* i'th block in an MCU */
|
|
2254
|
|
2255 int Ss, Se, Ah, Al; /* progressive JPEG parameters for scan */
|
|
2256
|
|
2257 /* This field is shared between entropy decoder and marker parser.
|
|
2258 * It is either zero or the code of a JPEG marker that has been
|
|
2259 * read from the data source, but has not yet been processed.
|
|
2260 */
|
|
2261 int unread_marker;
|
|
2262
|
|
2263 int[DCTSIZE2] workspace;// = new int[DCTSIZE2];
|
|
2264 int[1] row_ctr;// = new int[1];
|
|
2265
|
|
2266 /*
|
|
2267 * Links to decompression subobjects (methods, private variables of modules)
|
|
2268 */
|
|
2269 jpeg_decomp_master master;
|
|
2270 jpeg_d_main_controller main;
|
|
2271 jpeg_d_coef_controller coef;
|
|
2272 jpeg_d_post_controller post;
|
|
2273 jpeg_input_controller inputctl;
|
|
2274 jpeg_marker_reader marker;
|
|
2275 jpeg_entropy_decoder entropy;
|
|
2276 jpeg_inverse_dct idct;
|
|
2277 jpeg_upsampler upsample;
|
|
2278 jpeg_color_deconverter cconvert;
|
|
2279 jpeg_color_quantizer cquantize;
|
|
2280 }
|
|
2281
|
|
2282 static void error() {
|
|
2283 SWT.error(SWT.ERROR_INVALID_IMAGE);
|
|
2284 }
|
|
2285
|
|
2286 static void error(int code) {
|
|
2287 SWT.error(code);
|
|
2288 }
|
|
2289
|
|
2290 static void error(String msg) {
|
|
2291 SWT.error(SWT.ERROR_INVALID_IMAGE, null, msg);
|
|
2292 }
|
|
2293
|
|
2294 static void jinit_marker_reader (jpeg_decompress_struct cinfo) {
|
|
2295 jpeg_marker_reader marker = cinfo.marker = new jpeg_marker_reader();
|
|
2296 // int i;
|
|
2297
|
|
2298 /* Initialize COM/APPn processing.
|
|
2299 * By default, we examine and then discard APP0 and APP14,
|
|
2300 * but simply discard COM and all other APPn.
|
|
2301 */
|
|
2302 // marker.process_COM = skip_variable;
|
|
2303 marker.length_limit_COM = 0;
|
|
2304 // for (i = 0; i < 16; i++) {
|
|
2305 // marker.process_APPn[i] = skip_variable;
|
|
2306 // marker.length_limit_APPn[i] = 0;
|
|
2307 // }
|
|
2308 // marker.process_APPn[0] = get_interesting_appn;
|
|
2309 // marker.process_APPn[14] = get_interesting_appn;
|
|
2310 /* Reset marker processing state */
|
|
2311 reset_marker_reader(cinfo);
|
|
2312 }
|
|
2313
|
|
2314 static void jinit_d_coef_controller (jpeg_decompress_struct cinfo, bool need_full_buffer) {
|
|
2315 jpeg_d_coef_controller coef = new jpeg_d_coef_controller();
|
|
2316 cinfo.coef = coef;
|
|
2317 // coef.pub.start_input_pass = start_input_pass;
|
|
2318 // coef.pub.start_output_pass = start_output_pass;
|
|
2319 coef.coef_bits_latch = null;
|
|
2320
|
|
2321 /* Create the coefficient buffer. */
|
|
2322 if (need_full_buffer) {
|
|
2323 //#ifdef D_MULTISCAN_FILES_SUPPORTED
|
|
2324 /* Allocate a full-image virtual array for each component, */
|
|
2325 /* padded to a multiple of samp_factor DCT blocks in each direction. */
|
|
2326 /* Note we ask for a pre-zeroed array. */
|
|
2327 int ci, access_rows;
|
|
2328 jpeg_component_info compptr;
|
|
2329
|
|
2330 for (ci = 0; ci < cinfo.num_components; ci++) {
|
|
2331 compptr = cinfo.comp_info[ci];
|
|
2332 access_rows = compptr.v_samp_factor;
|
|
2333 //#ifdef BLOCK_SMOOTHING_SUPPORTED
|
|
2334 /* If block smoothing could be used, need a bigger window */
|
|
2335 if (cinfo.progressive_mode)
|
|
2336 access_rows *= 3;
|
|
2337 //#endif
|
|
2338 coef.whole_image[ci] =
|
|
2339 new short[][][](
|
|
2340 cast(int)jround_up( compptr.height_in_blocks, compptr.v_samp_factor),
|
|
2341 cast(int)jround_up( compptr.width_in_blocks, compptr.h_samp_factor),
|
|
2342 DCTSIZE2
|
|
2343 );
|
|
2344 }
|
|
2345 // coef.consume_data = consume_data;
|
|
2346 coef.decompress_data = DECOMPRESS_DATA;
|
|
2347 coef.coef_arrays = coef.whole_image[0]; /* link to virtual arrays */
|
|
2348 // #else
|
|
2349 // ERREXIT(cinfo, JERR_NOT_COMPILED);
|
|
2350 // #endif
|
|
2351 } else {
|
|
2352 /* We only need a single-MCU buffer. */
|
|
2353 foreach( inout el; coef.MCU_buffer ){
|
|
2354 el = new short[](DCTSIZE2);
|
|
2355 }
|
|
2356 // coef.consume_data = dummy_consume_data;
|
|
2357 coef.decompress_data = DECOMPRESS_ONEPASS;
|
|
2358 coef.coef_arrays = null; /* flag for no virtual arrays */
|
|
2359 }
|
|
2360 }
|
|
2361
|
|
2362 static void start_output_pass (jpeg_decompress_struct cinfo) {
|
|
2363 //#ifdef BLOCK_SMOOTHING_SUPPORTED
|
|
2364 jpeg_d_coef_controller coef = cinfo.coef;
|
|
2365
|
|
2366 /* If multipass, check to see whether to use block smoothing on this pass */
|
|
2367 if (coef.coef_arrays !is null) {
|
|
2368 if (cinfo.do_block_smoothing && smoothing_ok(cinfo))
|
|
2369 coef.decompress_data = DECOMPRESS_SMOOTH_DATA;
|
|
2370 else
|
|
2371 coef.decompress_data = DECOMPRESS_DATA;
|
|
2372 }
|
|
2373 //#endif
|
|
2374 cinfo.output_iMCU_row = 0;
|
|
2375 }
|
|
2376
|
|
2377 static void jpeg_create_decompress(jpeg_decompress_struct cinfo) {
|
|
2378 cinfo.is_decompressor = true;
|
|
2379
|
|
2380
|
|
2381 /* Initialize marker processor so application can override methods
|
|
2382 * for COM, APPn markers before calling jpeg_read_header.
|
|
2383 */
|
|
2384 cinfo.marker_list = null;
|
|
2385 jinit_marker_reader(cinfo);
|
|
2386
|
|
2387 /* And initialize the overall input controller. */
|
|
2388 jinit_input_controller(cinfo);
|
|
2389
|
|
2390 /* OK, I'm ready */
|
|
2391 cinfo.global_state = DSTATE_START;
|
|
2392 }
|
|
2393
|
|
2394 static void jpeg_calc_output_dimensions (jpeg_decompress_struct cinfo)
|
|
2395 /* Do computations that are needed before master selection phase */
|
|
2396 {
|
|
2397 //#ifdef IDCT_SCALING_SUPPORTED
|
|
2398 // int ci;
|
|
2399 // jpeg_component_info compptr;
|
|
2400 //#endif
|
|
2401
|
|
2402 /* Prevent application from calling me at wrong times */
|
|
2403 if (cinfo.global_state !is DSTATE_READY)
|
|
2404 error();
|
|
2405 // ERREXIT1(cinfo, JERR_BAD_STATE, cinfo.global_state);
|
|
2406
|
|
2407 //#ifdef IDCT_SCALING_SUPPORTED
|
|
2408 //
|
|
2409 // /* Compute actual output image dimensions and DCT scaling choices. */
|
|
2410 // if (cinfo.scale_num * 8 <= cinfo.scale_denom) {
|
|
2411 // /* Provide 1/8 scaling */
|
|
2412 // cinfo.output_width = cast(int)
|
|
2413 // jdiv_round_up(cinfo.image_width, 8L);
|
|
2414 // cinfo.output_height = cast(int)
|
|
2415 // jdiv_round_up(cinfo.image_height, 8L);
|
|
2416 // cinfo.min_DCT_scaled_size = 1;
|
|
2417 // } else if (cinfo.scale_num * 4 <= cinfo.scale_denom) {
|
|
2418 // /* Provide 1/4 scaling */
|
|
2419 // cinfo.output_width = cast(int)
|
|
2420 // jdiv_round_up(cinfo.image_width, 4L);
|
|
2421 // cinfo.output_height = cast(int)
|
|
2422 // jdiv_round_up(cinfo.image_height, 4L);
|
|
2423 // cinfo.min_DCT_scaled_size = 2;
|
|
2424 // } else if (cinfo.scale_num * 2 <= cinfo.scale_denom) {
|
|
2425 // /* Provide 1/2 scaling */
|
|
2426 // cinfo.output_width = cast(int)
|
|
2427 // jdiv_round_up(cinfo.image_width, 2L);
|
|
2428 // cinfo.output_height = cast(int)
|
|
2429 // jdiv_round_up(cinfo.image_height, 2L);
|
|
2430 // cinfo.min_DCT_scaled_size = 4;
|
|
2431 // } else {
|
|
2432 // /* Provide 1/1 scaling */
|
|
2433 // cinfo.output_width = cinfo.image_width;
|
|
2434 // cinfo.output_height = cinfo.image_height;
|
|
2435 // cinfo.min_DCT_scaled_size = DCTSIZE;
|
|
2436 // }
|
|
2437 // /* In selecting the actual DCT scaling for each component, we try to
|
|
2438 // * scale up the chroma components via IDCT scaling rather than upsampling.
|
|
2439 // * This saves time if the upsampler gets to use 1:1 scaling.
|
|
2440 // * Note this code assumes that the supported DCT scalings are powers of 2.
|
|
2441 // */
|
|
2442 // for (ci = 0; ci < cinfo.num_components; ci++) {
|
|
2443 // compptr = cinfo.comp_info[ci];
|
|
2444 // int ssize = cinfo.min_DCT_scaled_size;
|
|
2445 // while (ssize < DCTSIZE &&
|
|
2446 // (compptr.h_samp_factor * ssize * 2 <= cinfo.max_h_samp_factor * cinfo.min_DCT_scaled_size) &&
|
|
2447 // (compptr.v_samp_factor * ssize * 2 <= cinfo.max_v_samp_factor * cinfo.min_DCT_scaled_size))
|
|
2448 // {
|
|
2449 // ssize = ssize * 2;
|
|
2450 // }
|
|
2451 // compptr.DCT_scaled_size = ssize;
|
|
2452 // }
|
|
2453 //
|
|
2454 // /* Recompute downsampled dimensions of components;
|
|
2455 // * application needs to know these if using raw downsampled data.
|
|
2456 // */
|
|
2457 // for (ci = 0; ci < cinfo.num_components; ci++) {
|
|
2458 // compptr = cinfo.comp_info[ci];
|
|
2459 // /* Size in samples, after IDCT scaling */
|
|
2460 // compptr.downsampled_width = cast(int)
|
|
2461 // jdiv_round_up(cast(long) cinfo.image_width * cast(long) (compptr.h_samp_factor * compptr.DCT_scaled_size),
|
|
2462 // (cinfo.max_h_samp_factor * DCTSIZE));
|
|
2463 // compptr.downsampled_height = cast(int)
|
|
2464 // jdiv_round_up(cast(long) cinfo.image_height * cast(long) (compptr.v_samp_factor * compptr.DCT_scaled_size),
|
|
2465 // (cinfo.max_v_samp_factor * DCTSIZE));
|
|
2466 // }
|
|
2467 //
|
|
2468 //#else /* !IDCT_SCALING_SUPPORTED */
|
|
2469
|
|
2470 /* Hardwire it to "no scaling" */
|
|
2471 cinfo.output_width = cinfo.image_width;
|
|
2472 cinfo.output_height = cinfo.image_height;
|
|
2473 /* jdinput.c has already initialized DCT_scaled_size to DCTSIZE,
|
|
2474 * and has computed unscaled downsampled_width and downsampled_height.
|
|
2475 */
|
|
2476
|
|
2477 //#endif /* IDCT_SCALING_SUPPORTED */
|
|
2478
|
|
2479 /* Report number of components in selected colorspace. */
|
|
2480 /* Probably this should be in the color conversion module... */
|
|
2481 switch (cinfo.out_color_space) {
|
|
2482 case JCS_GRAYSCALE:
|
|
2483 cinfo.out_color_components = 1;
|
|
2484 break;
|
|
2485 case JCS_RGB:
|
|
2486 if (RGB_PIXELSIZE !is 3) {
|
|
2487 cinfo.out_color_components = RGB_PIXELSIZE;
|
|
2488 break;
|
|
2489 }
|
|
2490 //FALLTHROUGH
|
|
2491 case JCS_YCbCr:
|
|
2492 cinfo.out_color_components = 3;
|
|
2493 break;
|
|
2494 case JCS_CMYK:
|
|
2495 case JCS_YCCK:
|
|
2496 cinfo.out_color_components = 4;
|
|
2497 break;
|
|
2498 default: /* else must be same colorspace as in file */
|
|
2499 cinfo.out_color_components = cinfo.num_components;
|
|
2500 break;
|
|
2501 }
|
|
2502 cinfo.output_components = (cinfo.quantize_colors ? 1 : cinfo.out_color_components);
|
|
2503
|
|
2504 /* See if upsampler will want to emit more than one row at a time */
|
|
2505 if (use_merged_upsample(cinfo))
|
|
2506 cinfo.rec_outbuf_height = cinfo.max_v_samp_factor;
|
|
2507 else
|
|
2508 cinfo.rec_outbuf_height = 1;
|
|
2509 }
|
|
2510
|
|
2511 static bool use_merged_upsample (jpeg_decompress_struct cinfo) {
|
|
2512 //#ifdef UPSAMPLE_MERGING_SUPPORTED
|
|
2513 /* Merging is the equivalent of plain box-filter upsampling */
|
|
2514 if (cinfo.do_fancy_upsampling || cinfo.CCIR601_sampling)
|
|
2515 return false;
|
|
2516 /* jdmerge.c only supports YCC=>RGB color conversion */
|
|
2517 if (cinfo.jpeg_color_space !is JCS_YCbCr || cinfo.num_components !is 3 ||
|
|
2518 cinfo.out_color_space !is JCS_RGB ||
|
|
2519 cinfo.out_color_components !is RGB_PIXELSIZE)
|
|
2520 return false;
|
|
2521 /* and it only handles 2h1v or 2h2v sampling ratios */
|
|
2522 if (cinfo.comp_info[0].h_samp_factor !is 2 ||
|
|
2523 cinfo.comp_info[1].h_samp_factor !is 1 ||
|
|
2524 cinfo.comp_info[2].h_samp_factor !is 1 ||
|
|
2525 cinfo.comp_info[0].v_samp_factor > 2 ||
|
|
2526 cinfo.comp_info[1].v_samp_factor !is 1 ||
|
|
2527 cinfo.comp_info[2].v_samp_factor !is 1)
|
|
2528 return false;
|
|
2529 /* furthermore, it doesn't work if we've scaled the IDCTs differently */
|
|
2530 if (cinfo.comp_info[0].DCT_scaled_size !is cinfo.min_DCT_scaled_size ||
|
|
2531 cinfo.comp_info[1].DCT_scaled_size !is cinfo.min_DCT_scaled_size ||
|
|
2532 cinfo.comp_info[2].DCT_scaled_size !is cinfo.min_DCT_scaled_size)
|
|
2533 return false;
|
|
2534 /* ??? also need to test for upsample-time rescaling, when & if supported */
|
|
2535 return true; /* by golly, it'll work... */
|
|
2536 //#else
|
|
2537 // return false;
|
|
2538 //#endif
|
|
2539 }
|
|
2540
|
|
2541 static void prepare_range_limit_table (jpeg_decompress_struct cinfo)
|
|
2542 /* Allocate and fill in the sample_range_limit table */
|
|
2543 {
|
|
2544 byte[] table;
|
|
2545 int i;
|
|
2546
|
|
2547 table = new byte[5 * (MAXJSAMPLE+1) + CENTERJSAMPLE];
|
|
2548 int offset = (MAXJSAMPLE+1); /* allow negative subscripts of simple table */
|
|
2549 cinfo.sample_range_limit_offset = offset;
|
|
2550 cinfo.sample_range_limit = table;
|
|
2551 /* First segment of "simple" table: limit[x] = 0 for x < 0 */
|
|
2552 /* Main part of "simple" table: limit[x] = x */
|
|
2553 for (i = 0; i <= MAXJSAMPLE; i++)
|
|
2554 table[i + offset] = cast(byte)i;
|
|
2555 offset += CENTERJSAMPLE; /* Point to where post-IDCT table starts */
|
|
2556 /* End of simple table, rest of first half of post-IDCT table */
|
|
2557 for (i = CENTERJSAMPLE; i < 2*(MAXJSAMPLE+1); i++)
|
|
2558 table[i+offset] = cast(byte)MAXJSAMPLE;
|
|
2559 /* Second half of post-IDCT table */
|
|
2560 System.arraycopy(cinfo.sample_range_limit, cinfo.sample_range_limit_offset, table, offset + (4 * (MAXJSAMPLE+1) - CENTERJSAMPLE), CENTERJSAMPLE);
|
|
2561 }
|
|
2562
|
|
2563 static void build_ycc_rgb_table (jpeg_decompress_struct cinfo) {
|
|
2564 jpeg_color_deconverter cconvert = cinfo.cconvert;
|
|
2565 int i;
|
|
2566 int x;
|
|
2567 // SHIFT_TEMPS
|
|
2568
|
|
2569 cconvert.Cr_r_tab = new int[MAXJSAMPLE+1];
|
|
2570 cconvert.Cb_b_tab = new int[MAXJSAMPLE+1];
|
|
2571 cconvert.Cr_g_tab = new int[MAXJSAMPLE+1];
|
|
2572 cconvert.Cb_g_tab = new int[MAXJSAMPLE+1];
|
|
2573
|
|
2574 for (i = 0, x = -CENTERJSAMPLE; i <= MAXJSAMPLE; i++, x++) {
|
|
2575 /* i is the actual input pixel value, in the range 0..MAXJSAMPLE */
|
|
2576 /* The Cb or Cr value we are thinking of is x = i - CENTERJSAMPLE */
|
|
2577 /* Cr=>R value is nearest int to 1.40200 * x */
|
|
2578 cconvert.Cr_r_tab[i] = (cast(int)(1.40200f * (1<<SCALEBITS) + 0.5f) * x + ONE_HALF) >> SCALEBITS;
|
|
2579 /* Cb=>B value is nearest int to 1.77200 * x */
|
|
2580 cconvert.Cb_b_tab[i] = (cast(int)(1.77200f * (1<<SCALEBITS) + 0.5f) * x + ONE_HALF) >> SCALEBITS;
|
|
2581 /* Cr=>G value is scaled-up -0.71414 * x */
|
|
2582 cconvert.Cr_g_tab[i] = (cast(int)(- (0.71414f * (1<<SCALEBITS) + 0.5f)) * x);
|
|
2583 /* Cb=>G value is scaled-up -0.34414 * x */
|
|
2584 /* We also add in ONE_HALF so that need not do it in inner loop */
|
|
2585 cconvert.Cb_g_tab[i] = (cast(int)(- (0.34414f* (1<<SCALEBITS) + 0.5f)) * x + ONE_HALF);
|
|
2586 }
|
|
2587 }
|
|
2588
|
|
2589 static void jinit_color_deconverter (jpeg_decompress_struct cinfo) {
|
|
2590 jpeg_color_deconverter cconvert = cinfo.cconvert = new jpeg_color_deconverter();
|
|
2591 // cconvert.start_pass = start_pass_dcolor;
|
|
2592
|
|
2593 /* Make sure num_components agrees with jpeg_color_space */
|
|
2594 switch (cinfo.jpeg_color_space) {
|
|
2595 case JCS_GRAYSCALE:
|
|
2596 if (cinfo.num_components !is 1)
|
|
2597 error();
|
|
2598 // ERREXIT(cinfo, JERR_BAD_J_COLORSPACE);
|
|
2599 break;
|
|
2600
|
|
2601 case JCS_RGB:
|
|
2602 case JCS_YCbCr:
|
|
2603 if (cinfo.num_components !is 3)
|
|
2604 error();
|
|
2605 // ERREXIT(cinfo, JERR_BAD_J_COLORSPACE);
|
|
2606 break;
|
|
2607
|
|
2608 case JCS_CMYK:
|
|
2609 case JCS_YCCK:
|
|
2610 if (cinfo.num_components !is 4)
|
|
2611 error();
|
|
2612 // ERREXIT(cinfo, JERR_BAD_J_COLORSPACE);
|
|
2613 break;
|
|
2614
|
|
2615 default: /* JCS_UNKNOWN can be anything */
|
|
2616 if (cinfo.num_components < 1)
|
|
2617 error();
|
|
2618 // ERREXIT(cinfo, JERR_BAD_J_COLORSPACE);
|
|
2619 break;
|
|
2620 }
|
|
2621
|
|
2622 /* Set out_color_components and conversion method based on requested space.
|
|
2623 * Also clear the component_needed flags for any unused components,
|
|
2624 * so that earlier pipeline stages can avoid useless computation.
|
|
2625 */
|
|
2626
|
|
2627 int ci;
|
|
2628 switch (cinfo.out_color_space) {
|
|
2629 case JCS_GRAYSCALE:
|
|
2630 cinfo.out_color_components = 1;
|
|
2631 if (cinfo.jpeg_color_space is JCS_GRAYSCALE || cinfo.jpeg_color_space is JCS_YCbCr) {
|
|
2632 cconvert.color_convert = GRAYSCALE_CONVERT;
|
|
2633 /* For color.grayscale conversion, only the Y (0) component is needed */
|
|
2634 for (ci = 1; ci < cinfo.num_components; ci++)
|
|
2635 cinfo.comp_info[ci].component_needed = false;
|
|
2636 } else
|
|
2637 error();
|
|
2638 // ERREXIT(cinfo, JERR_CONVERSION_NOTIMPL);
|
|
2639 break;
|
|
2640
|
|
2641 case JCS_RGB:
|
|
2642 cinfo.out_color_components = RGB_PIXELSIZE;
|
|
2643 if (cinfo.jpeg_color_space is JCS_YCbCr) {
|
|
2644 cconvert.color_convert = YCC_RGB_CONVERT;
|
|
2645 build_ycc_rgb_table(cinfo);
|
|
2646 } else if (cinfo.jpeg_color_space is JCS_GRAYSCALE) {
|
|
2647 cconvert.color_convert = GRAY_RGB_CONVERT;
|
|
2648 } else if (cinfo.jpeg_color_space is JCS_RGB && RGB_PIXELSIZE is 3) {
|
|
2649 cconvert.color_convert = NULL_CONVERT;
|
|
2650 } else
|
|
2651 error();
|
|
2652 // ERREXIT(cinfo, JERR_CONVERSION_NOTIMPL);
|
|
2653 break;
|
|
2654
|
|
2655 case JCS_CMYK:
|
|
2656 cinfo.out_color_components = 4;
|
|
2657 if (cinfo.jpeg_color_space is JCS_YCCK) {
|
|
2658 cconvert.color_convert = YCCK_CMYK_CONVERT;
|
|
2659 build_ycc_rgb_table(cinfo);
|
|
2660 } else if (cinfo.jpeg_color_space is JCS_CMYK) {
|
|
2661 cconvert.color_convert = NULL_CONVERT;
|
|
2662 } else
|
|
2663 error();
|
|
2664 // ERREXIT(cinfo, JERR_CONVERSION_NOTIMPL);
|
|
2665 break;
|
|
2666
|
|
2667 default:
|
|
2668 /* Permit null conversion to same output space */
|
|
2669 if (cinfo.out_color_space is cinfo.jpeg_color_space) {
|
|
2670 cinfo.out_color_components = cinfo.num_components;
|
|
2671 cconvert.color_convert = NULL_CONVERT;
|
|
2672 } else /* unsupported non-null conversion */
|
|
2673 error();
|
|
2674 // ERREXIT(cinfo, JERR_CONVERSION_NOTIMPL);
|
|
2675 break;
|
|
2676 }
|
|
2677
|
|
2678 if (cinfo.quantize_colors)
|
|
2679 cinfo.output_components = 1; /* single colormapped output component */
|
|
2680 else
|
|
2681 cinfo.output_components = cinfo.out_color_components;
|
|
2682 }
|
|
2683
|
|
2684 static void jinit_d_post_controller (jpeg_decompress_struct cinfo, bool need_full_buffer) {
|
|
2685 jpeg_d_post_controller post = cinfo.post = new jpeg_d_post_controller();
|
|
2686 // post.pub.start_pass = start_pass_dpost;
|
|
2687 post.whole_image = null; /* flag for no virtual arrays */
|
|
2688 post.buffer = null; /* flag for no strip buffer */
|
|
2689
|
|
2690 /* Create the quantization buffer, if needed */
|
|
2691 if (cinfo.quantize_colors) {
|
|
2692 error(SWT.ERROR_NOT_IMPLEMENTED);
|
|
2693 // /* The buffer strip height is max_v_samp_factor, which is typically
|
|
2694 // * an efficient number of rows for upsampling to return.
|
|
2695 // * (In the presence of output rescaling, we might want to be smarter?)
|
|
2696 // */
|
|
2697 // post.strip_height = cinfo.max_v_samp_factor;
|
|
2698 // if (need_full_buffer) {
|
|
2699 // /* Two-pass color quantization: need full-image storage. */
|
|
2700 // /* We round up the number of rows to a multiple of the strip height. */
|
|
2701 //#ifdef QUANT_2PASS_SUPPORTED
|
|
2702 // post.whole_image = (*cinfo.mem.request_virt_sarray)
|
|
2703 // ((j_common_ptr) cinfo, JPOOL_IMAGE, FALSE,
|
|
2704 // cinfo.output_width * cinfo.out_color_components,
|
|
2705 // (JDIMENSION) jround_up(cast(long) cinfo.output_height,
|
|
2706 // cast(long) post.strip_height),
|
|
2707 // post.strip_height);
|
|
2708 //#else
|
|
2709 // ERREXIT(cinfo, JERR_BAD_BUFFER_MODE);
|
|
2710 //#endif /* QUANT_2PASS_SUPPORTED */
|
|
2711 // } else {
|
|
2712 // /* One-pass color quantization: just make a strip buffer. */
|
|
2713 // post.buffer = (*cinfo.mem.alloc_sarray)
|
|
2714 // ((j_common_ptr) cinfo, JPOOL_IMAGE,
|
|
2715 // cinfo.output_width * cinfo.out_color_components,
|
|
2716 // post.strip_height);
|
|
2717 // }
|
|
2718 }
|
|
2719 }
|
|
2720
|
|
2721 static void make_funny_pointers (jpeg_decompress_struct cinfo)
|
|
2722 /* Create the funny pointer lists discussed in the comments above.
|
|
2723 * The actual workspace is already allocated (in main.buffer),
|
|
2724 * and the space for the pointer lists is allocated too.
|
|
2725 * This routine just fills in the curiously ordered lists.
|
|
2726 * This will be repeated at the beginning of each pass.
|
|
2727 */
|
|
2728 {
|
|
2729 jpeg_d_main_controller main = cinfo.main;
|
|
2730 int ci, i, rgroup;
|
|
2731 int M = cinfo.min_DCT_scaled_size;
|
|
2732 jpeg_component_info compptr;
|
|
2733 byte[][] buf, xbuf0, xbuf1;
|
|
2734
|
|
2735 for (ci = 0; ci < cinfo.num_components; ci++) {
|
|
2736 compptr = cinfo.comp_info[ci];
|
|
2737 rgroup = (compptr.v_samp_factor * compptr.DCT_scaled_size) /
|
|
2738 cinfo.min_DCT_scaled_size; /* height of a row group of component */
|
|
2739 xbuf0 = main.xbuffer[0][ci];
|
|
2740 int xbuf0_offset = main.xbuffer_offset[0][ci];
|
|
2741 xbuf1 = main.xbuffer[1][ci];
|
|
2742 int xbuf1_offset = main.xbuffer_offset[1][ci];
|
|
2743 /* First copy the workspace pointers as-is */
|
|
2744 buf = main.buffer[ci];
|
|
2745 for (i = 0; i < rgroup * (M + 2); i++) {
|
|
2746 xbuf0[i + xbuf0_offset] = xbuf1[i + xbuf1_offset] = buf[i];
|
|
2747 }
|
|
2748 /* In the second list, put the last four row groups in swapped order */
|
|
2749 for (i = 0; i < rgroup * 2; i++) {
|
|
2750 xbuf1[rgroup*(M-2) + i + xbuf1_offset] = buf[rgroup*M + i];
|
|
2751 xbuf1[rgroup*M + i + xbuf1_offset] = buf[rgroup*(M-2) + i];
|
|
2752 }
|
|
2753 /* The wraparound pointers at top and bottom will be filled later
|
|
2754 * (see set_wraparound_pointers, below). Initially we want the "above"
|
|
2755 * pointers to duplicate the first actual data line. This only needs
|
|
2756 * to happen in xbuffer[0].
|
|
2757 */
|
|
2758 for (i = 0; i < rgroup; i++) {
|
|
2759 xbuf0[i - rgroup + xbuf0_offset] = xbuf0[0 + xbuf0_offset];
|
|
2760 }
|
|
2761 }
|
|
2762 }
|
|
2763
|
|
2764 static void alloc_funny_pointers (jpeg_decompress_struct cinfo)
|
|
2765 /* Allocate space for the funny pointer lists.
|
|
2766 * This is done only once, not once per pass.
|
|
2767 */
|
|
2768 {
|
|
2769 jpeg_d_main_controller main = cinfo.main;
|
|
2770 int ci, rgroup;
|
|
2771 int M = cinfo.min_DCT_scaled_size;
|
|
2772 jpeg_component_info compptr;
|
|
2773 byte[][] xbuf;
|
|
2774
|
|
2775 /* Get top-level space for component array pointers.
|
|
2776 * We alloc both arrays with one call to save a few cycles.
|
|
2777 */
|
|
2778 main.xbuffer[0] = new byte[][][](cinfo.num_components);
|
|
2779 main.xbuffer[1] = new byte[][][](cinfo.num_components);
|
|
2780 main.xbuffer_offset[0] = new int[](cinfo.num_components);
|
|
2781 main.xbuffer_offset[1] = new int[](cinfo.num_components);
|
|
2782
|
|
2783 for (ci = 0; ci < cinfo.num_components; ci++) {
|
|
2784 compptr = cinfo.comp_info[ci];
|
|
2785 rgroup = (compptr.v_samp_factor * compptr.DCT_scaled_size) / cinfo.min_DCT_scaled_size; /* height of a row group of component */
|
|
2786 /* Get space for pointer lists --- M+4 row groups in each list.
|
|
2787 * We alloc both pointer lists with one call to save a few cycles.
|
|
2788 */
|
|
2789 xbuf = new byte[][](2 * (rgroup * (M + 4)));
|
|
2790 int offset = rgroup;
|
|
2791 main.xbuffer_offset[0][ci] = offset;
|
|
2792 main.xbuffer[0][ci] = xbuf;
|
|
2793 offset += rgroup * (M + 4);
|
|
2794 main.xbuffer_offset[1][ci] = offset;
|
|
2795 main.xbuffer[1][ci] = xbuf;
|
|
2796 }
|
|
2797 }
|
|
2798
|
|
2799
|
|
2800 static void jinit_d_main_controller (jpeg_decompress_struct cinfo, bool need_full_buffer) {
|
|
2801 int ci, rgroup, ngroups;
|
|
2802 jpeg_component_info compptr;
|
|
2803
|
|
2804 jpeg_d_main_controller main = cinfo.main = new jpeg_d_main_controller();
|
|
2805 // main.pub.start_pass = start_pass_main;
|
|
2806
|
|
2807 if (need_full_buffer) /* shouldn't happen */
|
|
2808 error();
|
|
2809 // ERREXIT(cinfo, JERR_BAD_BUFFER_MODE);
|
|
2810
|
|
2811 /* Allocate the workspace.
|
|
2812 * ngroups is the number of row groups we need.
|
|
2813 */
|
|
2814 if (cinfo.upsample.need_context_rows) {
|
|
2815 if (cinfo.min_DCT_scaled_size < 2) /* unsupported, see comments above */
|
|
2816 error();
|
|
2817 // ERREXIT(cinfo, JERR_NOTIMPL);
|
|
2818 alloc_funny_pointers(cinfo); /* Alloc space for xbuffer[] lists */
|
|
2819 ngroups = cinfo.min_DCT_scaled_size + 2;
|
|
2820 } else {
|
|
2821 ngroups = cinfo.min_DCT_scaled_size;
|
|
2822 }
|
|
2823
|
|
2824 for (ci = 0; ci < cinfo.num_components; ci++) {
|
|
2825 compptr = cinfo.comp_info[ci];
|
|
2826 rgroup = (compptr.v_samp_factor * compptr.DCT_scaled_size) / cinfo.min_DCT_scaled_size; /* height of a row group of component */
|
|
2827 main.buffer[ci] = new byte[][]( rgroup * ngroups, compptr.width_in_blocks * compptr.DCT_scaled_size );
|
|
2828 }
|
|
2829 }
|
|
2830
|
|
2831 static long jround_up (long a, long b)
|
|
2832 /* Compute a rounded up to next multiple of b, ie, ceil(a/b)*b */
|
|
2833 /* Assumes a >= 0, b > 0 */
|
|
2834 {
|
|
2835 a += b - 1L;
|
|
2836 return a - (a % b);
|
|
2837 }
|
|
2838
|
|
2839 static void jinit_upsampler (jpeg_decompress_struct cinfo) {
|
|
2840 int ci;
|
|
2841 jpeg_component_info compptr;
|
|
2842 bool need_buffer, do_fancy;
|
|
2843 int h_in_group, v_in_group, h_out_group, v_out_group;
|
|
2844
|
|
2845 jpeg_upsampler upsample = new jpeg_upsampler();
|
|
2846 cinfo.upsample = upsample;
|
|
2847 // upsample.start_pass = start_pass_upsample;
|
|
2848 // upsample.upsample = sep_upsample;
|
|
2849 upsample.need_context_rows = false; /* until we find out differently */
|
|
2850
|
|
2851 if (cinfo.CCIR601_sampling) /* this isn't supported */
|
|
2852 error();
|
|
2853 // ERREXIT(cinfo, JERR_CCIR601_NOTIMPL);
|
|
2854
|
|
2855 /* jdmainct.c doesn't support context rows when min_DCT_scaled_size = 1,
|
|
2856 * so don't ask for it.
|
|
2857 */
|
|
2858 do_fancy = cinfo.do_fancy_upsampling && cinfo.min_DCT_scaled_size > 1;
|
|
2859
|
|
2860 /* Verify we can handle the sampling factors, select per-component methods,
|
|
2861 * and create storage as needed.
|
|
2862 */
|
|
2863 for (ci = 0; ci < cinfo.num_components; ci++) {
|
|
2864 compptr = cinfo.comp_info[ci];
|
|
2865 /* Compute size of an "input group" after IDCT scaling. This many samples
|
|
2866 * are to be converted to max_h_samp_factor * max_v_samp_factor pixels.
|
|
2867 */
|
|
2868 h_in_group = (compptr.h_samp_factor * compptr.DCT_scaled_size) /
|
|
2869 cinfo.min_DCT_scaled_size;
|
|
2870 v_in_group = (compptr.v_samp_factor * compptr.DCT_scaled_size) /
|
|
2871 cinfo.min_DCT_scaled_size;
|
|
2872 h_out_group = cinfo.max_h_samp_factor;
|
|
2873 v_out_group = cinfo.max_v_samp_factor;
|
|
2874 upsample.rowgroup_height[ci] = v_in_group; /* save for use later */
|
|
2875 need_buffer = true;
|
|
2876 if (! compptr.component_needed) {
|
|
2877 /* Don't bother to upsample an uninteresting component. */
|
|
2878 upsample.methods[ci] = NOOP_UPSAMPLE;
|
|
2879 need_buffer = false;
|
|
2880 } else if (h_in_group is h_out_group && v_in_group is v_out_group) {
|
|
2881 /* Fullsize components can be processed without any work. */
|
|
2882 upsample.methods[ci] = FULLSIZE_UPSAMPLE;
|
|
2883 need_buffer = false;
|
|
2884 } else if (h_in_group * 2 is h_out_group && v_in_group is v_out_group) {
|
|
2885 /* Special cases for 2h1v upsampling */
|
|
2886 if (do_fancy && compptr.downsampled_width > 2)
|
|
2887 upsample.methods[ci] = H2V1_FANCY_UPSAMPLE;
|
|
2888 else
|
|
2889 upsample.methods[ci] = H2V1_UPSAMPLE;
|
|
2890 } else if (h_in_group * 2 is h_out_group && v_in_group * 2 is v_out_group) {
|
|
2891 /* Special cases for 2h2v upsampling */
|
|
2892 if (do_fancy && compptr.downsampled_width > 2) {
|
|
2893 upsample.methods[ci] = H2V2_FANCY_UPSAMPLE;
|
|
2894 upsample.need_context_rows = true;
|
|
2895 } else
|
|
2896 upsample.methods[ci] = H2V2_UPSAMPLE;
|
|
2897 } else if ((h_out_group % h_in_group) is 0 && (v_out_group % v_in_group) is 0) {
|
|
2898 /* Generic integral-factors upsampling method */
|
|
2899 upsample.methods[ci] = INT_UPSAMPLE;
|
|
2900 upsample.h_expand[ci] = cast(byte) (h_out_group / h_in_group);
|
|
2901 upsample.v_expand[ci] = cast(byte) (v_out_group / v_in_group);
|
|
2902 } else
|
|
2903 error();
|
|
2904 // ERREXIT(cinfo, JERR_FRACT_SAMPLE_NOTIMPL);
|
|
2905 if (need_buffer) {
|
|
2906 upsample.color_buf[ci] = new byte[][]( cinfo.max_v_samp_factor,
|
|
2907 cast(int) jround_up(cinfo.output_width, cinfo.max_h_samp_factor));
|
|
2908 }
|
|
2909 }
|
|
2910 }
|
|
2911
|
|
2912 static void jinit_phuff_decoder (jpeg_decompress_struct cinfo) {
|
|
2913 int[][] coef_bit_ptr;
|
|
2914 int ci, i;
|
|
2915
|
|
2916 cinfo.entropy = new phuff_entropy_decoder();
|
|
2917 // entropy.pub.start_pass = start_pass_phuff_decoder;
|
|
2918
|
|
2919 /* Create progression status table */
|
|
2920 cinfo.coef_bits = new int[][]( cinfo.num_components, DCTSIZE2 );
|
|
2921 coef_bit_ptr = cinfo.coef_bits;
|
|
2922 for (ci = 0; ci < cinfo.num_components; ci++)
|
|
2923 for (i = 0; i < DCTSIZE2; i++)
|
|
2924 coef_bit_ptr[ci][i] = -1;
|
|
2925 }
|
|
2926
|
|
2927
|
|
2928 static void jinit_huff_decoder (jpeg_decompress_struct cinfo) {
|
|
2929
|
|
2930 cinfo.entropy = new huff_entropy_decoder();
|
|
2931 // entropy.pub.start_pass = start_pass_huff_decoder;
|
|
2932 // entropy.pub.decode_mcu = decode_mcu;
|
|
2933
|
|
2934 }
|
|
2935
|
|
2936 static void jinit_inverse_dct (jpeg_decompress_struct cinfo) {
|
|
2937 int ci;
|
|
2938 jpeg_component_info compptr;
|
|
2939
|
|
2940 jpeg_inverse_dct idct = cinfo.idct = new jpeg_inverse_dct();
|
|
2941 // idct.pub.start_pass = start_pass;
|
|
2942
|
|
2943 for (ci = 0; ci < cinfo.num_components; ci++) {
|
|
2944 compptr = cinfo.comp_info[ci];
|
|
2945 /* Allocate and pre-zero a multiplier table for each component */
|
|
2946 compptr.dct_table = new int[DCTSIZE2];
|
|
2947 /* Mark multiplier table not yet set up for any method */
|
|
2948 idct.cur_method[ci] = -1;
|
|
2949 }
|
|
2950 }
|
|
2951
|
|
2952 static final int CONST_BITS = 13;
|
|
2953 static final int PASS1_BITS = 2;
|
|
2954 static final int RANGE_MASK =(MAXJSAMPLE * 4 + 3);
|
|
2955 static void jpeg_idct_islow (jpeg_decompress_struct cinfo, jpeg_component_info compptr,
|
|
2956 short[] coef_block,
|
|
2957 byte[][] output_buf, int output_buf_offset, int output_col)
|
|
2958 {
|
|
2959 int tmp0, tmp1, tmp2, tmp3;
|
|
2960 int tmp10, tmp11, tmp12, tmp13;
|
|
2961 int z1, z2, z3, z4, z5;
|
|
2962 short[] inptr;
|
|
2963 int[] quantptr;
|
|
2964 int[] wsptr;
|
|
2965 byte[] outptr;
|
|
2966 byte[] range_limit = cinfo.sample_range_limit;
|
|
2967 int range_limit_offset = cinfo.sample_range_limit_offset + CENTERJSAMPLE;
|
|
2968 int ctr;
|
|
2969 int[] workspace = cinfo.workspace; /* buffers data between passes */
|
|
2970 // SHIFT_TEMPS
|
|
2971
|
|
2972 /* Pass 1: process columns from input, store into work array. */
|
|
2973 /* Note results are scaled up by sqrt(8) compared to a true IDCT; */
|
|
2974 /* furthermore, we scale the results by 2**PASS1_BITS. */
|
|
2975
|
|
2976 inptr = coef_block;
|
|
2977 quantptr = compptr.dct_table;
|
|
2978 wsptr = workspace;
|
|
2979 int inptr_offset = 0, quantptr_offset = 0, wsptr_offset = 0;
|
|
2980 for (ctr = DCTSIZE; ctr > 0; ctr--) {
|
|
2981 /* Due to quantization, we will usually find that many of the input
|
|
2982 * coefficients are zero, especially the AC terms. We can exploit this
|
|
2983 * by short-circuiting the IDCT calculation for any column in which all
|
|
2984 * the AC terms are zero. In that case each output is equal to the
|
|
2985 * DC coefficient (with scale factor as needed).
|
|
2986 * With typical images and quantization tables, half or more of the
|
|
2987 * column DCT calculations can be simplified this way.
|
|
2988 */
|
|
2989
|
|
2990 if (inptr[DCTSIZE*1+inptr_offset] is 0 && inptr[DCTSIZE*2+inptr_offset] is 0 &&
|
|
2991 inptr[DCTSIZE*3+inptr_offset] is 0 && inptr[DCTSIZE*4+inptr_offset] is 0 &&
|
|
2992 inptr[DCTSIZE*5+inptr_offset] is 0 && inptr[DCTSIZE*6+inptr_offset] is 0 &&
|
|
2993 inptr[DCTSIZE*7+inptr_offset] is 0)
|
|
2994 {
|
|
2995 /* AC terms all zero */
|
|
2996 int dcval = ((inptr[DCTSIZE*0+inptr_offset]) * quantptr[DCTSIZE*0+quantptr_offset]) << PASS1_BITS;
|
|
2997
|
|
2998 wsptr[DCTSIZE*0+wsptr_offset] = dcval;
|
|
2999 wsptr[DCTSIZE*1+wsptr_offset] = dcval;
|
|
3000 wsptr[DCTSIZE*2+wsptr_offset] = dcval;
|
|
3001 wsptr[DCTSIZE*3+wsptr_offset] = dcval;
|
|
3002 wsptr[DCTSIZE*4+wsptr_offset] = dcval;
|
|
3003 wsptr[DCTSIZE*5+wsptr_offset] = dcval;
|
|
3004 wsptr[DCTSIZE*6+wsptr_offset] = dcval;
|
|
3005 wsptr[DCTSIZE*7+wsptr_offset] = dcval;
|
|
3006
|
|
3007 inptr_offset++; /* advance pointers to next column */
|
|
3008 quantptr_offset++;
|
|
3009 wsptr_offset++;
|
|
3010 continue;
|
|
3011 }
|
|
3012
|
|
3013 /* Even part: reverse the even part of the forward DCT. */
|
|
3014 /* The rotator is sqrt(2)*c(-6). */
|
|
3015
|
|
3016 z2 = ((inptr[DCTSIZE*2+inptr_offset]) * quantptr[DCTSIZE*2+quantptr_offset]);
|
|
3017 z3 = ((inptr[DCTSIZE*6+inptr_offset]) * quantptr[DCTSIZE*6+quantptr_offset]);
|
|
3018
|
|
3019 z1 = ((z2 + z3) * 4433/*FIX_0_541196100*/);
|
|
3020 tmp2 = z1 + (z3 * - 15137/*FIX_1_847759065*/);
|
|
3021 tmp3 = z1 + (z2 * 6270/*FIX_0_765366865*/);
|
|
3022
|
|
3023 z2 = ((inptr[DCTSIZE*0+inptr_offset]) * quantptr[DCTSIZE*0+quantptr_offset]);
|
|
3024 z3 = ((inptr[DCTSIZE*4+inptr_offset]) * quantptr[DCTSIZE*4+quantptr_offset]);
|
|
3025
|
|
3026 tmp0 = (z2 + z3) << CONST_BITS;
|
|
3027 tmp1 = (z2 - z3) << CONST_BITS;
|
|
3028
|
|
3029 tmp10 = tmp0 + tmp3;
|
|
3030 tmp13 = tmp0 - tmp3;
|
|
3031 tmp11 = tmp1 + tmp2;
|
|
3032 tmp12 = tmp1 - tmp2;
|
|
3033
|
|
3034 /* Odd part per figure 8; the matrix is unitary and hence its
|
|
3035 * transpose is its inverse. i0..i3 are y7,y5,y3,y1 respectively.
|
|
3036 */
|
|
3037
|
|
3038 tmp0 = ((inptr[DCTSIZE*7+inptr_offset]) * quantptr[DCTSIZE*7+quantptr_offset]);
|
|
3039 tmp1 = ((inptr[DCTSIZE*5+inptr_offset]) * quantptr[DCTSIZE*5+quantptr_offset]);
|
|
3040 tmp2 = ((inptr[DCTSIZE*3+inptr_offset]) * quantptr[DCTSIZE*3+quantptr_offset]);
|
|
3041 tmp3 = ((inptr[DCTSIZE*1+inptr_offset]) * quantptr[DCTSIZE*1+quantptr_offset]);
|
|
3042
|
|
3043 z1 = tmp0 + tmp3;
|
|
3044 z2 = tmp1 + tmp2;
|
|
3045 z3 = tmp0 + tmp2;
|
|
3046 z4 = tmp1 + tmp3;
|
|
3047 z5 = ((z3 + z4) * 9633/*FIX_1_175875602*/); /* sqrt(2) * c3 */
|
|
3048
|
|
3049 tmp0 = (tmp0 * 2446/*FIX_0_298631336*/); /* sqrt(2) * (-c1+c3+c5-c7) */
|
|
3050 tmp1 = (tmp1 * 16819/*FIX_2_053119869*/); /* sqrt(2) * ( c1+c3-c5+c7) */
|
|
3051 tmp2 = (tmp2 * 25172/*FIX_3_072711026*/); /* sqrt(2) * ( c1+c3+c5-c7) */
|
|
3052 tmp3 = (tmp3 * 12299/*FIX_1_501321110*/); /* sqrt(2) * ( c1+c3-c5-c7) */
|
|
3053 z1 = (z1 * - 7373/*FIX_0_899976223*/); /* sqrt(2) * (c7-c3) */
|
|
3054 z2 = (z2 * - 20995/*FIX_2_562915447*/); /* sqrt(2) * (-c1-c3) */
|
|
3055 z3 = (z3 * - 16069/*FIX_1_961570560*/); /* sqrt(2) * (-c3-c5) */
|
|
3056 z4 = (z4 * - 3196/*FIX_0_390180644*/); /* sqrt(2) * (c5-c3) */
|
|
3057
|
|
3058 z3 += z5;
|
|
3059 z4 += z5;
|
|
3060
|
|
3061 tmp0 += z1 + z3;
|
|
3062 tmp1 += z2 + z4;
|
|
3063 tmp2 += z2 + z3;
|
|
3064 tmp3 += z1 + z4;
|
|
3065
|
|
3066 /* Final output stage: inputs are tmp10..tmp13, tmp0..tmp3 */
|
|
3067
|
|
3068 // #define DESCALE(x,n) RIGHT_SHIFT((x) + (ONE << ((n)-1)), n)
|
|
3069 wsptr[DCTSIZE*0+wsptr_offset] = (((tmp10 + tmp3) + (1 << ((CONST_BITS-PASS1_BITS)-1))) >> (CONST_BITS-PASS1_BITS));
|
|
3070 wsptr[DCTSIZE*7+wsptr_offset] = (((tmp10 - tmp3) + (1 << ((CONST_BITS-PASS1_BITS)-1))) >> (CONST_BITS-PASS1_BITS));
|
|
3071 wsptr[DCTSIZE*1+wsptr_offset] = (((tmp11 + tmp2) + (1 << ((CONST_BITS-PASS1_BITS)-1))) >> (CONST_BITS-PASS1_BITS));
|
|
3072 wsptr[DCTSIZE*6+wsptr_offset] = (((tmp11 - tmp2) + (1 << ((CONST_BITS-PASS1_BITS)-1))) >> (CONST_BITS-PASS1_BITS));
|
|
3073 wsptr[DCTSIZE*2+wsptr_offset] = (((tmp12 + tmp1) + (1 << ((CONST_BITS-PASS1_BITS)-1))) >> (CONST_BITS-PASS1_BITS));
|
|
3074 wsptr[DCTSIZE*5+wsptr_offset] = (((tmp12 - tmp1) + (1 << ((CONST_BITS-PASS1_BITS)-1))) >> (CONST_BITS-PASS1_BITS));
|
|
3075 wsptr[DCTSIZE*3+wsptr_offset] = (((tmp13 + tmp0) + (1 << ((CONST_BITS-PASS1_BITS)-1))) >> (CONST_BITS-PASS1_BITS));
|
|
3076 wsptr[DCTSIZE*4+wsptr_offset] = (((tmp13 - tmp0) + (1 << ((CONST_BITS-PASS1_BITS)-1))) >> (CONST_BITS-PASS1_BITS));
|
|
3077
|
|
3078 inptr_offset++; /* advance pointers to next column */
|
|
3079 quantptr_offset++;
|
|
3080 wsptr_offset++;
|
|
3081 }
|
|
3082
|
|
3083
|
|
3084 /* Pass 2: process rows from work array, store into output array. */
|
|
3085 /* Note that we must descale the results by a factor of 8 is 2**3, */
|
|
3086 /* and also undo the PASS1_BITS scaling. */
|
|
3087
|
|
3088 int outptr_offset = 0;
|
|
3089 wsptr = workspace;
|
|
3090 wsptr_offset =0;
|
|
3091 for (ctr = 0; ctr < DCTSIZE; ctr++) {
|
|
3092 outptr = output_buf[ctr+output_buf_offset];
|
|
3093 outptr_offset = output_col;
|
|
3094 /* Rows of zeroes can be exploited in the same way as we did with columns.
|
|
3095 * However, the column calculation has created many nonzero AC terms, so
|
|
3096 * the simplification applies less often (typically 5% to 10% of the time).
|
|
3097 * On machines with very fast multiplication, it's possible that the
|
|
3098 * test takes more time than it's worth. In that case this section
|
|
3099 * may be commented out.
|
|
3100 */
|
|
3101
|
|
3102 //#ifndef NO_ZERO_ROW_TEST
|
|
3103 if (wsptr[1+wsptr_offset] is 0 && wsptr[2+wsptr_offset] is 0 && wsptr[3+wsptr_offset] is 0 && wsptr[4+wsptr_offset] is 0 &&
|
|
3104 wsptr[5+wsptr_offset] is 0 && wsptr[6+wsptr_offset] is 0 && wsptr[7+wsptr_offset] is 0)
|
|
3105 {
|
|
3106 /* AC terms all zero */
|
|
3107 // #define DESCALE(x,n) RIGHT_SHIFT((x) + (ONE << ((n)-1)), n)
|
|
3108 byte dcval = range_limit[range_limit_offset + ((((wsptr[0+wsptr_offset]) + (1 << ((PASS1_BITS+3)-1))) >> PASS1_BITS+3)
|
|
3109 & RANGE_MASK)];
|
|
3110
|
|
3111 outptr[0+outptr_offset] = dcval;
|
|
3112 outptr[1+outptr_offset] = dcval;
|
|
3113 outptr[2+outptr_offset] = dcval;
|
|
3114 outptr[3+outptr_offset] = dcval;
|
|
3115 outptr[4+outptr_offset] = dcval;
|
|
3116 outptr[5+outptr_offset] = dcval;
|
|
3117 outptr[6+outptr_offset] = dcval;
|
|
3118 outptr[7+outptr_offset] = dcval;
|
|
3119
|
|
3120 wsptr_offset += DCTSIZE; /* advance pointer to next row */
|
|
3121 continue;
|
|
3122 }
|
|
3123 //#endif
|
|
3124
|
|
3125 /* Even part: reverse the even part of the forward DCT. */
|
|
3126 /* The rotator is sqrt(2)*c(-6). */
|
|
3127
|
|
3128 z2 = wsptr[2+wsptr_offset];
|
|
3129 z3 = wsptr[6+wsptr_offset];
|
|
3130
|
|
3131 z1 = ((z2 + z3) * 4433/*FIX_0_541196100*/);
|
|
3132 tmp2 = z1 + (z3 * - 15137/*FIX_1_847759065*/);
|
|
3133 tmp3 = z1 + (z2 * 6270/*FIX_0_765366865*/);
|
|
3134
|
|
3135 tmp0 = (wsptr[0+wsptr_offset] + wsptr[4+wsptr_offset]) << CONST_BITS;
|
|
3136 tmp1 = (wsptr[0+wsptr_offset] - wsptr[4+wsptr_offset]) << CONST_BITS;
|
|
3137
|
|
3138 tmp10 = tmp0 + tmp3;
|
|
3139 tmp13 = tmp0 - tmp3;
|
|
3140 tmp11 = tmp1 + tmp2;
|
|
3141 tmp12 = tmp1 - tmp2;
|
|
3142
|
|
3143 /* Odd part per figure 8; the matrix is unitary and hence its
|
|
3144 * transpose is its inverse. i0..i3 are y7,y5,y3,y1 respectively.
|
|
3145 */
|
|
3146
|
|
3147 tmp0 = wsptr[7+wsptr_offset];
|
|
3148 tmp1 = wsptr[5+wsptr_offset];
|
|
3149 tmp2 = wsptr[3+wsptr_offset];
|
|
3150 tmp3 = wsptr[1+wsptr_offset];
|
|
3151
|
|
3152 z1 = tmp0 + tmp3;
|
|
3153 z2 = tmp1 + tmp2;
|
|
3154 z3 = tmp0 + tmp2;
|
|
3155 z4 = tmp1 + tmp3;
|
|
3156 z5 = ((z3 + z4) * 9633/*FIX_1_175875602*/); /* sqrt(2) * c3 */
|
|
3157
|
|
3158 tmp0 = (tmp0 * 2446/*FIX_0_298631336*/); /* sqrt(2) * (-c1+c3+c5-c7) */
|
|
3159 tmp1 = (tmp1 * 16819/*FIX_2_053119869*/); /* sqrt(2) * ( c1+c3-c5+c7) */
|
|
3160 tmp2 = (tmp2 * 25172/*FIX_3_072711026*/); /* sqrt(2) * ( c1+c3+c5-c7) */
|
|
3161 tmp3 = (tmp3 * 12299/*FIX_1_501321110*/); /* sqrt(2) * ( c1+c3-c5-c7) */
|
|
3162 z1 = (z1 * - 7373/*FIX_0_899976223*/); /* sqrt(2) * (c7-c3) */
|
|
3163 z2 = (z2 * - 20995/*FIX_2_562915447*/); /* sqrt(2) * (-c1-c3) */
|
|
3164 z3 = (z3 * - 16069/*FIX_1_961570560*/); /* sqrt(2) * (-c3-c5) */
|
|
3165 z4 = (z4 * - 3196/*FIX_0_390180644*/); /* sqrt(2) * (c5-c3) */
|
|
3166
|
|
3167 z3 += z5;
|
|
3168 z4 += z5;
|
|
3169
|
|
3170 tmp0 += z1 + z3;
|
|
3171 tmp1 += z2 + z4;
|
|
3172 tmp2 += z2 + z3;
|
|
3173 tmp3 += z1 + z4;
|
|
3174
|
|
3175 /* Final output stage: inputs are tmp10..tmp13, tmp0..tmp3 */
|
|
3176
|
|
3177
|
|
3178 // #define DESCALE(x,n) RIGHT_SHIFT((x) + (ONE << ((n)-1)), n)
|
|
3179 outptr[0+outptr_offset] = range_limit[range_limit_offset + ((((tmp10 + tmp3) + (1 << ((CONST_BITS+PASS1_BITS+3)-1))) >>
|
|
3180 CONST_BITS+PASS1_BITS+3)
|
|
3181 & RANGE_MASK)];
|
|
3182 outptr[7+outptr_offset] = range_limit[range_limit_offset + ((((tmp10 - tmp3) + (1 << ((CONST_BITS+PASS1_BITS+3)-1))) >>
|
|
3183 CONST_BITS+PASS1_BITS+3)
|
|
3184 & RANGE_MASK)];
|
|
3185 outptr[1+outptr_offset] = range_limit[range_limit_offset + ((((tmp11 + tmp2) + (1 << ((CONST_BITS+PASS1_BITS+3)-1))) >>
|
|
3186 CONST_BITS+PASS1_BITS+3)
|
|
3187 & RANGE_MASK)];
|
|
3188 outptr[6+outptr_offset] = range_limit[range_limit_offset + ((((tmp11 - tmp2) + (1 << ((CONST_BITS+PASS1_BITS+3)-1))) >>
|
|
3189 CONST_BITS+PASS1_BITS+3)
|
|
3190 & RANGE_MASK)];
|
|
3191 outptr[2+outptr_offset] = range_limit[range_limit_offset + ((((tmp12 + tmp1) + (1 << ((CONST_BITS+PASS1_BITS+3)-1))) >>
|
|
3192 CONST_BITS+PASS1_BITS+3)
|
|
3193 & RANGE_MASK)];
|
|
3194 outptr[5+outptr_offset] = range_limit[range_limit_offset + ((((tmp12 - tmp1) + (1 << ((CONST_BITS+PASS1_BITS+3)-1))) >>
|
|
3195 CONST_BITS+PASS1_BITS+3)
|
|
3196 & RANGE_MASK)];
|
|
3197 outptr[3+outptr_offset] = range_limit[range_limit_offset + ((((tmp13 + tmp0) + (1 << ((CONST_BITS+PASS1_BITS+3)-1))) >>
|
|
3198 CONST_BITS+PASS1_BITS+3)
|
|
3199 & RANGE_MASK)];
|
|
3200 outptr[4+outptr_offset] = range_limit[range_limit_offset + ((((tmp13 - tmp0) + (1 << ((CONST_BITS+PASS1_BITS+3)-1))) >>
|
|
3201 CONST_BITS+PASS1_BITS+3)
|
|
3202 & RANGE_MASK)];
|
|
3203
|
|
3204 wsptr_offset += DCTSIZE; /* advance pointer to next row */
|
|
3205 }
|
|
3206 }
|
|
3207
|
|
3208 static void upsample (jpeg_decompress_struct cinfo,
|
|
3209 byte[][][] input_buf, int[] input_buf_offset, int[] in_row_group_ctr,
|
|
3210 int in_row_groups_avail,
|
|
3211 byte[][] output_buf, int[] out_row_ctr,
|
|
3212 int out_rows_avail)
|
|
3213 {
|
|
3214 sep_upsample(cinfo, input_buf, input_buf_offset, in_row_group_ctr, in_row_groups_avail, output_buf, out_row_ctr, out_rows_avail);
|
|
3215 }
|
|
3216
|
|
3217 static bool smoothing_ok (jpeg_decompress_struct cinfo) {
|
|
3218 jpeg_d_coef_controller coef = cinfo.coef;
|
|
3219 bool smoothing_useful = false;
|
|
3220 int ci, coefi;
|
|
3221 jpeg_component_info compptr;
|
|
3222 JQUANT_TBL qtable;
|
|
3223 int[] coef_bits;
|
|
3224 int[] coef_bits_latch;
|
|
3225
|
|
3226 if (! cinfo.progressive_mode || cinfo.coef_bits is null)
|
|
3227 return false;
|
|
3228
|
|
3229 /* Allocate latch area if not already done */
|
|
3230 if (coef.coef_bits_latch is null)
|
|
3231 coef.coef_bits_latch = new int[cinfo.num_components * SAVED_COEFS];
|
|
3232 coef_bits_latch = coef.coef_bits_latch;
|
|
3233 int coef_bits_latch_offset = 0;
|
|
3234
|
|
3235 for (ci = 0; ci < cinfo.num_components; ci++) {
|
|
3236 compptr = cinfo.comp_info[ci];
|
|
3237 /* All components' quantization values must already be latched. */
|
|
3238 if ((qtable = compptr.quant_table) is null)
|
|
3239 return false;
|
|
3240 /* Verify DC & first 5 AC quantizers are nonzero to avoid zero-divide. */
|
|
3241 if (qtable.quantval[0] is 0 ||
|
|
3242 qtable.quantval[Q01_POS] is 0 ||
|
|
3243 qtable.quantval[Q10_POS] is 0 ||
|
|
3244 qtable.quantval[Q20_POS] is 0 ||
|
|
3245 qtable.quantval[Q11_POS] is 0 ||
|
|
3246 qtable.quantval[Q02_POS] is 0)
|
|
3247 return false;
|
|
3248 /* DC values must be at least partly known for all components. */
|
|
3249 coef_bits = cinfo.coef_bits[ci];
|
|
3250 if (coef_bits[0] < 0)
|
|
3251 return false;
|
|
3252 /* Block smoothing is helpful if some AC coefficients remain inaccurate. */
|
|
3253 for (coefi = 1; coefi <= 5; coefi++) {
|
|
3254 coef_bits_latch[coefi+coef_bits_latch_offset] = coef_bits[coefi];
|
|
3255 if (coef_bits[coefi] !is 0)
|
|
3256 smoothing_useful = true;
|
|
3257 }
|
|
3258 coef_bits_latch_offset += SAVED_COEFS;
|
|
3259 }
|
|
3260
|
|
3261 return smoothing_useful;
|
|
3262 }
|
|
3263
|
|
3264 static void master_selection (jpeg_decompress_struct cinfo) {
|
|
3265 jpeg_decomp_master master = cinfo.master;
|
|
3266 bool use_c_buffer;
|
|
3267 long samplesperrow;
|
|
3268 int jd_samplesperrow;
|
|
3269
|
|
3270 /* Initialize dimensions and other stuff */
|
|
3271 jpeg_calc_output_dimensions(cinfo);
|
|
3272 prepare_range_limit_table(cinfo);
|
|
3273
|
|
3274 /* Width of an output scanline must be representable as JDIMENSION. */
|
|
3275 samplesperrow = cast(long) cinfo.output_width * cast(long) cinfo.out_color_components;
|
|
3276 jd_samplesperrow = cast(int) samplesperrow;
|
|
3277 if ( jd_samplesperrow !is samplesperrow)
|
|
3278 error();
|
|
3279 // ERREXIT(cinfo, JERR_WIDTH_OVERFLOW);
|
|
3280
|
|
3281 /* Initialize my private state */
|
|
3282 master.pass_number = 0;
|
|
3283 master.using_merged_upsample = use_merged_upsample(cinfo);
|
|
3284
|
|
3285 /* Color quantizer selection */
|
|
3286 master.quantizer_1pass = null;
|
|
3287 master.quantizer_2pass = null;
|
|
3288 /* No mode changes if not using buffered-image mode. */
|
|
3289 if (! cinfo.quantize_colors || ! cinfo.buffered_image) {
|
|
3290 cinfo.enable_1pass_quant = false;
|
|
3291 cinfo.enable_external_quant = false;
|
|
3292 cinfo.enable_2pass_quant = false;
|
|
3293 }
|
|
3294 if (cinfo.quantize_colors) {
|
|
3295 error(SWT.ERROR_NOT_IMPLEMENTED);
|
|
3296 // if (cinfo.raw_data_out)
|
|
3297 // ERREXIT(cinfo, JERR_NOTIMPL);
|
|
3298 // /* 2-pass quantizer only works in 3-component color space. */
|
|
3299 // if (cinfo.out_color_components !is 3) {
|
|
3300 // cinfo.enable_1pass_quant = true;
|
|
3301 // cinfo.enable_external_quant = false;
|
|
3302 // cinfo.enable_2pass_quant = false;
|
|
3303 // cinfo.colormap = null;
|
|
3304 // } else if (cinfo.colormap !is null) {
|
|
3305 // cinfo.enable_external_quant = true;
|
|
3306 // } else if (cinfo.two_pass_quantize) {
|
|
3307 // cinfo.enable_2pass_quant = true;
|
|
3308 // } else {
|
|
3309 // cinfo.enable_1pass_quant = true;
|
|
3310 // }
|
|
3311 //
|
|
3312 // if (cinfo.enable_1pass_quant) {
|
|
3313 //#ifdef QUANT_1PASS_SUPPORTED
|
|
3314 // jinit_1pass_quantizer(cinfo);
|
|
3315 // master.quantizer_1pass = cinfo.cquantize;
|
|
3316 //#else
|
|
3317 // ERREXIT(cinfo, JERR_NOT_COMPILED);
|
|
3318 //#endif
|
|
3319 // }
|
|
3320 //
|
|
3321 // /* We use the 2-pass code to map to external colormaps. */
|
|
3322 // if (cinfo.enable_2pass_quant || cinfo.enable_external_quant) {
|
|
3323 //#ifdef QUANT_2PASS_SUPPORTED
|
|
3324 // jinit_2pass_quantizer(cinfo);
|
|
3325 // master.quantizer_2pass = cinfo.cquantize;
|
|
3326 //#else
|
|
3327 // ERREXIT(cinfo, JERR_NOT_COMPILED);
|
|
3328 //#endif
|
|
3329 // }
|
|
3330 // /* If both quantizers are initialized, the 2-pass one is left active;
|
|
3331 // * this is necessary for starting with quantization to an external map.
|
|
3332 // */
|
|
3333 }
|
|
3334
|
|
3335 /* Post-processing: in particular, color conversion first */
|
|
3336 if (! cinfo.raw_data_out) {
|
|
3337 if (master.using_merged_upsample) {
|
|
3338 //#ifdef UPSAMPLE_MERGING_SUPPORTED
|
|
3339 // jinit_merged_upsampler(cinfo); /* does color conversion too */
|
|
3340 //#else
|
|
3341 error();
|
|
3342 // ERREXIT(cinfo, JERR_NOT_COMPILED);
|
|
3343 //#endif
|
|
3344 } else {
|
|
3345 jinit_color_deconverter(cinfo);
|
|
3346 jinit_upsampler(cinfo);
|
|
3347 }
|
|
3348 jinit_d_post_controller(cinfo, cinfo.enable_2pass_quant);
|
|
3349 }
|
|
3350 /* Inverse DCT */
|
|
3351 jinit_inverse_dct(cinfo);
|
|
3352 /* Entropy decoding: either Huffman or arithmetic coding. */
|
|
3353 if (cinfo.arith_code) {
|
|
3354 error();
|
|
3355 // ERREXIT(cinfo, JERR_ARITH_NOTIMPL);
|
|
3356 } else {
|
|
3357 if (cinfo.progressive_mode) {
|
|
3358 //#ifdef D_PROGRESSIVE_SUPPORTED
|
|
3359 jinit_phuff_decoder(cinfo);
|
|
3360 //#else
|
|
3361 // ERREXIT(cinfo, JERR_NOT_COMPILED);
|
|
3362 //#endif
|
|
3363 } else
|
|
3364 jinit_huff_decoder(cinfo);
|
|
3365 }
|
|
3366
|
|
3367 /* Initialize principal buffer controllers. */
|
|
3368 use_c_buffer = cinfo.inputctl.has_multiple_scans || cinfo.buffered_image;
|
|
3369 jinit_d_coef_controller(cinfo, use_c_buffer);
|
|
3370
|
|
3371 if (! cinfo.raw_data_out)
|
|
3372 jinit_d_main_controller(cinfo, false /* never need full buffer here */);
|
|
3373
|
|
3374 /* Initialize input side of decompressor to consume first scan. */
|
|
3375 start_input_pass (cinfo);
|
|
3376
|
|
3377 //#ifdef D_MULTISCAN_FILES_SUPPORTED
|
|
3378 /* If jpeg_start_decompress will read the whole file, initialize
|
|
3379 * progress monitoring appropriately. The input step is counted
|
|
3380 * as one pass.
|
|
3381 */
|
|
3382 // if (cinfo.progress !is null && ! cinfo.buffered_image &&
|
|
3383 // cinfo.inputctl.has_multiple_scans) {
|
|
3384 // int nscans;
|
|
3385 // /* Estimate number of scans to set pass_limit. */
|
|
3386 // if (cinfo.progressive_mode) {
|
|
3387 // /* Arbitrarily estimate 2 interleaved DC scans + 3 AC scans/component. */
|
|
3388 // nscans = 2 + 3 * cinfo.num_components;
|
|
3389 // } else {
|
|
3390 // /* For a nonprogressive multiscan file, estimate 1 scan per component. */
|
|
3391 // nscans = cinfo.num_components;
|
|
3392 // }
|
|
3393 // cinfo.progress.pass_counter = 0L;
|
|
3394 // cinfo.progress.pass_limit = cast(long) cinfo.total_iMCU_rows * nscans;
|
|
3395 // cinfo.progress.completed_passes = 0;
|
|
3396 // cinfo.progress.total_passes = (cinfo.enable_2pass_quant ? 3 : 2);
|
|
3397 // /* Count the input pass as done */
|
|
3398 // master.pass_number++;
|
|
3399 // }
|
|
3400 //#endif /* D_MULTISCAN_FILES_SUPPORTED */
|
|
3401 }
|
|
3402
|
|
3403 static void jinit_master_decompress (jpeg_decompress_struct cinfo) {
|
|
3404 jpeg_decomp_master master = new jpeg_decomp_master();
|
|
3405 cinfo.master = master;
|
|
3406 // master.prepare_for_output_pass = prepare_for_output_pass;
|
|
3407 // master.finish_output_pass = finish_output_pass;
|
|
3408
|
|
3409 master.is_dummy_pass = false;
|
|
3410
|
|
3411 master_selection(cinfo);
|
|
3412 }
|
|
3413
|
|
3414 static void
|
|
3415 jcopy_sample_rows (byte[][] input_array, int source_row,
|
|
3416 byte[][] output_array, int dest_row,
|
|
3417 int num_rows, int num_cols)
|
|
3418 /* Copy some rows of samples from one place to another.
|
|
3419 * num_rows rows are copied from input_array[source_row++]
|
|
3420 * to output_array[dest_row++]; these areas may overlap for duplication.
|
|
3421 * The source and destination arrays must be at least as wide as num_cols.
|
|
3422 */
|
|
3423 {
|
|
3424 byte[] inptr, outptr;
|
|
3425 int count = num_cols;
|
|
3426 int row;
|
|
3427
|
|
3428 int input_array_offset = source_row;
|
|
3429 int output_array_offset = dest_row;
|
|
3430
|
|
3431 for (row = num_rows; row > 0; row--) {
|
|
3432 inptr = input_array[input_array_offset++];
|
|
3433 outptr = output_array[output_array_offset++];
|
|
3434 System.arraycopy(inptr, 0, outptr, 0, count);
|
|
3435 }
|
|
3436 }
|
|
3437
|
|
3438 static bool jpeg_start_decompress (jpeg_decompress_struct cinfo) {
|
|
3439 if (cinfo.global_state is DSTATE_READY) {
|
|
3440 /* First call: initialize master control, select active modules */
|
|
3441 jinit_master_decompress(cinfo);
|
|
3442 if (cinfo.buffered_image) {
|
|
3443 /* No more work here; expecting jpeg_start_output next */
|
|
3444 cinfo.global_state = DSTATE_BUFIMAGE;
|
|
3445 return true;
|
|
3446 }
|
|
3447 cinfo.global_state = DSTATE_PRELOAD;
|
|
3448 }
|
|
3449 if (cinfo.global_state is DSTATE_PRELOAD) {
|
|
3450 /* If file has multiple scans, absorb them all into the coef buffer */
|
|
3451 if (cinfo.inputctl.has_multiple_scans) {
|
|
3452 //#ifdef D_MULTISCAN_FILES_SUPPORTED
|
|
3453 for (;;) {
|
|
3454 int retcode;
|
|
3455 /* Call progress monitor hook if present */
|
|
3456 // if (cinfo.progress !is null)
|
|
3457 // (*cinfo.progress.progress_monitor) ((j_common_ptr) cinfo);
|
|
3458 /* Absorb some more input */
|
|
3459 retcode = consume_input (cinfo);
|
|
3460 if (retcode is JPEG_SUSPENDED)
|
|
3461 return false;
|
|
3462 if (retcode is JPEG_REACHED_EOI)
|
|
3463 break;
|
|
3464 /* Advance progress counter if appropriate */
|
|
3465 // if (cinfo.progress !is null && (retcode is JPEG_ROW_COMPLETED || retcode is JPEG_REACHED_SOS)) {
|
|
3466 // if (++cinfo.progress.pass_counter >= cinfo.progress.pass_limit) {
|
|
3467 // /* jdmaster underestimated number of scans; ratchet up one scan */
|
|
3468 // cinfo.progress.pass_limit += cast(long) cinfo.total_iMCU_rows;
|
|
3469 // }
|
|
3470 // }
|
|
3471 }
|
|
3472 //#else
|
|
3473 // ERREXIT(cinfo, JERR_NOT_COMPILED);
|
|
3474 //#endif /* D_MULTISCAN_FILES_SUPPORTED */
|
|
3475 }
|
|
3476 cinfo.output_scan_number = cinfo.input_scan_number;
|
|
3477 } else if (cinfo.global_state !is DSTATE_PRESCAN)
|
|
3478 error();
|
|
3479 // ERREXIT1(cinfo, JERR_BAD_STATE, cinfo.global_state);
|
|
3480 /* Perform any dummy output passes, and set up for the final pass */
|
|
3481 return output_pass_setup(cinfo);
|
|
3482 }
|
|
3483
|
|
3484 static void prepare_for_output_pass (jpeg_decompress_struct cinfo) {
|
|
3485 jpeg_decomp_master master = cinfo.master;
|
|
3486
|
|
3487 if (master.is_dummy_pass) {
|
|
3488 //#ifdef QUANT_2PASS_SUPPORTED
|
|
3489 // /* Final pass of 2-pass quantization */
|
|
3490 // master.pub.is_dummy_pass = FALSE;
|
|
3491 // (*cinfo.cquantize.start_pass) (cinfo, FALSE);
|
|
3492 // (*cinfo.post.start_pass) (cinfo, JBUF_CRANK_DEST);
|
|
3493 // (*cinfo.main.start_pass) (cinfo, JBUF_CRANK_DEST);
|
|
3494 //#else
|
|
3495 error(SWT.ERROR_NOT_IMPLEMENTED);
|
|
3496 // ERREXIT(cinfo, JERR_NOT_COMPILED);
|
|
3497 //#endif /* QUANT_2PASS_SUPPORTED */
|
|
3498 } else {
|
|
3499 if (cinfo.quantize_colors && cinfo.colormap is null) {
|
|
3500 /* Select new quantization method */
|
|
3501 if (cinfo.two_pass_quantize && cinfo.enable_2pass_quant) {
|
|
3502 cinfo.cquantize = master.quantizer_2pass;
|
|
3503 master.is_dummy_pass = true;
|
|
3504 } else if (cinfo.enable_1pass_quant) {
|
|
3505 cinfo.cquantize = master.quantizer_1pass;
|
|
3506 } else {
|
|
3507 error();
|
|
3508 // ERREXIT(cinfo, JERR_MODE_CHANGE);
|
|
3509 }
|
|
3510 }
|
|
3511 cinfo.idct.start_pass (cinfo);
|
|
3512 start_output_pass (cinfo);
|
|
3513 if (! cinfo.raw_data_out) {
|
|
3514 if (! master.using_merged_upsample)
|
|
3515 cinfo.cconvert.start_pass (cinfo);
|
|
3516 cinfo.upsample.start_pass (cinfo);
|
|
3517 if (cinfo.quantize_colors)
|
|
3518 cinfo.cquantize.start_pass (cinfo, master.is_dummy_pass);
|
|
3519 cinfo.post.start_pass (cinfo, (master.is_dummy_pass ? JBUF_SAVE_AND_PASS : JBUF_PASS_THRU));
|
|
3520 cinfo.main.start_pass (cinfo, JBUF_PASS_THRU);
|
|
3521 }
|
|
3522 }
|
|
3523
|
|
3524 // /* Set up progress monitor's pass info if present */
|
|
3525 // if (cinfo.progress !is NULL) {
|
|
3526 // cinfo.progress.completed_passes = master.pass_number;
|
|
3527 // cinfo.progress.total_passes = master.pass_number +
|
|
3528 // (master.pub.is_dummy_pass ? 2 : 1);
|
|
3529 // /* In buffered-image mode, we assume one more output pass if EOI not
|
|
3530 // * yet reached, but no more passes if EOI has been reached.
|
|
3531 // */
|
|
3532 // if (cinfo.buffered_image && ! cinfo.inputctl.eoi_reached) {
|
|
3533 // cinfo.progress.total_passes += (cinfo.enable_2pass_quant ? 2 : 1);
|
|
3534 // }
|
|
3535 // }
|
|
3536 }
|
|
3537
|
|
3538
|
|
3539 static bool jpeg_resync_to_restart (jpeg_decompress_struct cinfo, int desired) {
|
|
3540 int marker = cinfo.unread_marker;
|
|
3541 int action = 1;
|
|
3542
|
|
3543 /* Always put up a warning. */
|
|
3544 // WARNMS2(cinfo, JWRN_MUST_RESYNC, marker, desired);
|
|
3545
|
|
3546 /* Outer loop handles repeated decision after scanning forward. */
|
|
3547 for (;;) {
|
|
3548 if (marker < M_SOF0)
|
|
3549 action = 2; /* invalid marker */
|
|
3550 else if (marker < M_RST0 || marker > M_RST7)
|
|
3551 action = 3; /* valid non-restart marker */
|
|
3552 else {
|
|
3553 if (marker is (M_RST0 + ((desired+1) & 7)) || marker is ( M_RST0 + ((desired+2) & 7)))
|
|
3554 action = 3; /* one of the next two expected restarts */
|
|
3555 else if (marker is (M_RST0 + ((desired-1) & 7)) || marker is ( M_RST0 + ((desired-2) & 7)))
|
|
3556 action = 2; /* a prior restart, so advance */
|
|
3557 else
|
|
3558 action = 1; /* desired restart or too far away */
|
|
3559 }
|
|
3560 // TRACEMS2(cinfo, 4, JTRC_RECOVERY_ACTION, marker, action);
|
|
3561 switch (action) {
|
|
3562 case 1:
|
|
3563 /* Discard marker and let entropy decoder resume processing. */
|
|
3564 cinfo.unread_marker = 0;
|
|
3565 return true;
|
|
3566 case 2:
|
|
3567 /* Scan to the next marker, and repeat the decision loop. */
|
|
3568 if (! next_marker(cinfo))
|
|
3569 return false;
|
|
3570 marker = cinfo.unread_marker;
|
|
3571 break;
|
|
3572 case 3:
|
|
3573 /* Return without advancing past this marker. */
|
|
3574 /* Entropy decoder will be forced to process an empty segment. */
|
|
3575 return true;
|
|
3576 default:
|
|
3577 }
|
|
3578 } /* end loop */
|
|
3579 }
|
|
3580
|
|
3581 static bool read_restart_marker (jpeg_decompress_struct cinfo) {
|
|
3582 /* Obtain a marker unless we already did. */
|
|
3583 /* Note that next_marker will complain if it skips any data. */
|
|
3584 if (cinfo.unread_marker is 0) {
|
|
3585 if (! next_marker(cinfo))
|
|
3586 return false;
|
|
3587 }
|
|
3588
|
|
3589 if (cinfo.unread_marker is (M_RST0 + cinfo.marker.next_restart_num)) {
|
|
3590 /* Normal case --- swallow the marker and let entropy decoder continue */
|
|
3591 // TRACEMS1(cinfo, 3, JTRC_RST, cinfo.marker.next_restart_num);
|
|
3592 cinfo.unread_marker = 0;
|
|
3593 } else {
|
|
3594 /* Uh-oh, the restart markers have been messed up. */
|
|
3595 /* Let the data source manager determine how to resync. */
|
|
3596 if (! jpeg_resync_to_restart (cinfo, cinfo.marker.next_restart_num))
|
|
3597 return false;
|
|
3598 }
|
|
3599
|
|
3600 /* Update next-restart state */
|
|
3601 cinfo.marker.next_restart_num = (cinfo.marker.next_restart_num + 1) & 7;
|
|
3602
|
|
3603 return true;
|
|
3604 }
|
|
3605
|
|
3606 static bool jpeg_fill_bit_buffer (bitread_working_state state, int get_buffer, int bits_left, int nbits)
|
|
3607 /* Load up the bit buffer to a depth of at least nbits */
|
|
3608 {
|
|
3609 /* Copy heavily used state fields into locals (hopefully registers) */
|
|
3610 byte[] buffer = state.buffer;
|
|
3611 int bytes_in_buffer = state.bytes_in_buffer;
|
|
3612 int bytes_offset = state.bytes_offset;
|
|
3613 jpeg_decompress_struct cinfo = state.cinfo;
|
|
3614
|
|
3615 /* Attempt to load at least MIN_GET_BITS bits into get_buffer. */
|
|
3616 /* (It is assumed that no request will be for more than that many bits.) */
|
|
3617 /* We fail to do so only if we hit a marker or are forced to suspend. */
|
|
3618
|
|
3619 if (cinfo.unread_marker is 0) { /* cannot advance past a marker */
|
|
3620 while (bits_left < MIN_GET_BITS) {
|
|
3621 int c;
|
|
3622
|
|
3623 /* Attempt to read a byte */
|
|
3624 if (bytes_offset is bytes_in_buffer) {
|
|
3625 if (! fill_input_buffer (cinfo))
|
|
3626 return false;
|
|
3627 buffer = cinfo.buffer;
|
|
3628 bytes_in_buffer = cinfo.bytes_in_buffer;
|
|
3629 bytes_offset = cinfo.bytes_offset;
|
|
3630 }
|
|
3631 c = buffer[bytes_offset++] & 0xFF;
|
|
3632
|
|
3633 /* If it's 0xFF, check and discard stuffed zero byte */
|
|
3634 if (c is 0xFF) {
|
|
3635 /* Loop here to discard any padding FF's on terminating marker,
|
|
3636 * so that we can save a valid unread_marker value. NOTE: we will
|
|
3637 * accept multiple FF's followed by a 0 as meaning a single FF data
|
|
3638 * byte. This data pattern is not valid according to the standard.
|
|
3639 */
|
|
3640 do {
|
|
3641 if (bytes_offset is bytes_in_buffer) {
|
|
3642 if (! fill_input_buffer (cinfo))
|
|
3643 return false;
|
|
3644 buffer = cinfo.buffer;
|
|
3645 bytes_in_buffer = cinfo.bytes_in_buffer;
|
|
3646 bytes_offset = cinfo.bytes_offset;
|
|
3647 }
|
|
3648 c = buffer[bytes_offset++] & 0xFF;
|
|
3649 } while (c is 0xFF);
|
|
3650
|
|
3651 if (c is 0) {
|
|
3652 /* Found FF/00, which represents an FF data byte */
|
|
3653 c = 0xFF;
|
|
3654 } else {
|
|
3655 /* Oops, it's actually a marker indicating end of compressed data.
|
|
3656 * Save the marker code for later use.
|
|
3657 * Fine point: it might appear that we should save the marker into
|
|
3658 * bitread working state, not straight into permanent state. But
|
|
3659 * once we have hit a marker, we cannot need to suspend within the
|
|
3660 * current MCU, because we will read no more bytes from the data
|
|
3661 * source. So it is OK to update permanent state right away.
|
|
3662 */
|
|
3663 cinfo.unread_marker = c;
|
|
3664 /* See if we need to insert some fake zero bits. */
|
|
3665 // goto no_more_bytes;
|
|
3666 if (nbits > bits_left) {
|
|
3667 /* Uh-oh. Report corrupted data to user and stuff zeroes into
|
|
3668 * the data stream, so that we can produce some kind of image.
|
|
3669 * We use a nonvolatile flag to ensure that only one warning message
|
|
3670 * appears per data segment.
|
|
3671 */
|
|
3672 if (! cinfo.entropy.insufficient_data) {
|
|
3673 // WARNMS(cinfo, JWRN_HIT_MARKER);
|
|
3674 cinfo.entropy.insufficient_data = true;
|
|
3675 }
|
|
3676 /* Fill the buffer with zero bits */
|
|
3677 get_buffer <<= MIN_GET_BITS - bits_left;
|
|
3678 bits_left = MIN_GET_BITS;
|
|
3679 }
|
|
3680
|
|
3681 /* Unload the local registers */
|
|
3682 state.buffer = buffer;
|
|
3683 state.bytes_in_buffer = bytes_in_buffer;
|
|
3684 state.bytes_offset = bytes_offset;
|
|
3685 state.get_buffer = get_buffer;
|
|
3686 state.bits_left = bits_left;
|
|
3687
|
|
3688 return true;
|
|
3689
|
|
3690 }
|
|
3691 }
|
|
3692
|
|
3693 /* OK, load c into get_buffer */
|
|
3694 get_buffer = (get_buffer << 8) | c;
|
|
3695 bits_left += 8;
|
|
3696 } /* end while */
|
|
3697 } else {
|
|
3698 // no_more_bytes:
|
|
3699 /* We get here if we've read the marker that terminates the compressed
|
|
3700 * data segment. There should be enough bits in the buffer register
|
|
3701 * to satisfy the request; if so, no problem.
|
|
3702 */
|
|
3703 if (nbits > bits_left) {
|
|
3704 /* Uh-oh. Report corrupted data to user and stuff zeroes into
|
|
3705 * the data stream, so that we can produce some kind of image.
|
|
3706 * We use a nonvolatile flag to ensure that only one warning message
|
|
3707 * appears per data segment.
|
|
3708 */
|
|
3709 if (! cinfo.entropy.insufficient_data) {
|
|
3710 // WARNMS(cinfo, JWRN_HIT_MARKER);
|
|
3711 cinfo.entropy.insufficient_data = true;
|
|
3712 }
|
|
3713 /* Fill the buffer with zero bits */
|
|
3714 get_buffer <<= MIN_GET_BITS - bits_left;
|
|
3715 bits_left = MIN_GET_BITS;
|
|
3716 }
|
|
3717 }
|
|
3718
|
|
3719 /* Unload the local registers */
|
|
3720 state.buffer = buffer;
|
|
3721 state.bytes_in_buffer = bytes_in_buffer;
|
|
3722 state.bytes_offset = bytes_offset;
|
|
3723 state.get_buffer = get_buffer;
|
|
3724 state.bits_left = bits_left;
|
|
3725
|
|
3726 return true;
|
|
3727 }
|
|
3728
|
|
3729 static int jpeg_huff_decode (bitread_working_state state, int get_buffer, int bits_left, d_derived_tbl htbl, int min_bits) {
|
|
3730 int l = min_bits;
|
|
3731 int code;
|
|
3732
|
|
3733 /* HUFF_DECODE has determined that the code is at least min_bits */
|
|
3734 /* bits long, so fetch that many bits in one swoop. */
|
|
3735
|
|
3736 // CHECK_BIT_BUFFER(*state, l, return -1);
|
|
3737 {
|
|
3738 if (bits_left < (l)) {
|
|
3739 if (! jpeg_fill_bit_buffer(state,get_buffer,bits_left,l)) {
|
|
3740 return -1;
|
|
3741 }
|
|
3742 get_buffer = state.get_buffer; bits_left = state.bits_left;
|
|
3743 }
|
|
3744 }
|
|
3745 // code = GET_BITS(l);
|
|
3746 code = (( (get_buffer >> (bits_left -= (l)))) & ((1<<(l))-1));
|
|
3747
|
|
3748 /* Collect the rest of the Huffman code one bit at a time. */
|
|
3749 /* This is per Figure F.16 in the JPEG spec. */
|
|
3750
|
|
3751 while (code > htbl.maxcode[l]) {
|
|
3752 code <<= 1;
|
|
3753 // CHECK_BIT_BUFFER(*state, 1, return -1);
|
|
3754 {
|
|
3755 if (bits_left < (1)) {
|
|
3756 if (! jpeg_fill_bit_buffer(state,get_buffer,bits_left,1)) {
|
|
3757 return -1;
|
|
3758 }
|
|
3759 get_buffer = state.get_buffer; bits_left = state.bits_left;
|
|
3760 }
|
|
3761 }
|
|
3762 // code |= GET_BITS(1);
|
|
3763 code |= (( (get_buffer >> (bits_left -= (1)))) & ((1<<(1))-1));
|
|
3764 l++;
|
|
3765 }
|
|
3766
|
|
3767 /* Unload the local registers */
|
|
3768 state.get_buffer = get_buffer;
|
|
3769 state.bits_left = bits_left;
|
|
3770
|
|
3771 /* With garbage input we may reach the sentinel value l = 17. */
|
|
3772
|
|
3773 if (l > 16) {
|
|
3774 // WARNMS(state.cinfo, JWRN_HUFF_BAD_CODE);
|
|
3775 return 0; /* fake a zero as the safest result */
|
|
3776 }
|
|
3777
|
|
3778 return htbl.pub.huffval[ (code + htbl.valoffset[l]) ] & 0xFF;
|
|
3779 }
|
|
3780
|
|
3781 static int decompress_onepass (jpeg_decompress_struct cinfo, byte[][][] output_buf, int[] output_buf_offset) {
|
|
3782 jpeg_d_coef_controller coef = cinfo.coef;
|
|
3783 int MCU_col_num; /* index of current MCU within row */
|
|
3784 int last_MCU_col = cinfo.MCUs_per_row - 1;
|
|
3785 int last_iMCU_row = cinfo.total_iMCU_rows - 1;
|
|
3786 int blkn, ci, xindex, yindex, yoffset, useful_width;
|
|
3787 byte[][] output_ptr;
|
|
3788 int start_col, output_col;
|
|
3789 jpeg_component_info compptr;
|
|
3790 // inverse_DCT_method_ptr inverse_DCT;
|
|
3791
|
|
3792 /* Loop to process as much as one whole iMCU row */
|
|
3793 for (yoffset = coef.MCU_vert_offset; yoffset < coef.MCU_rows_per_iMCU_row; yoffset++) {
|
|
3794 for (MCU_col_num = coef.MCU_ctr; MCU_col_num <= last_MCU_col; MCU_col_num++) {
|
|
3795 /* Try to fetch an MCU. Entropy decoder expects buffer to be zeroed. */
|
|
3796 for (int i = 0; i < cinfo.blocks_in_MCU; i++) {
|
|
3797 short[] blk = coef.MCU_buffer[i];
|
|
3798 for (int j = 0; j < blk.length; j++) {
|
|
3799 blk[j] = 0;
|
|
3800 }
|
|
3801 }
|
|
3802 if (! cinfo.entropy.decode_mcu (cinfo, coef.MCU_buffer)) {
|
|
3803 /* Suspension forced; update state counters and exit */
|
|
3804 coef.MCU_vert_offset = yoffset;
|
|
3805 coef.MCU_ctr = MCU_col_num;
|
|
3806 return JPEG_SUSPENDED;
|
|
3807 }
|
|
3808 /* Determine where data should go in output_buf and do the IDCT thing.
|
|
3809 * We skip dummy blocks at the right and bottom edges (but blkn gets
|
|
3810 * incremented past them!). Note the inner loop relies on having
|
|
3811 * allocated the MCU_buffer[] blocks sequentially.
|
|
3812 */
|
|
3813 blkn = 0; /* index of current DCT block within MCU */
|
|
3814 for (ci = 0; ci < cinfo.comps_in_scan; ci++) {
|
|
3815 compptr = cinfo.cur_comp_info[ci];
|
|
3816 /* Don't bother to IDCT an uninteresting component. */
|
|
3817 if (! compptr.component_needed) {
|
|
3818 blkn += compptr.MCU_blocks;
|
|
3819 continue;
|
|
3820 }
|
|
3821 // inverse_DCT = cinfo.idct.inverse_DCT[compptr.component_index];
|
|
3822 useful_width = (MCU_col_num < last_MCU_col) ? compptr.MCU_width : compptr.last_col_width;
|
|
3823 output_ptr = output_buf[compptr.component_index];
|
|
3824 int output_ptr_offset = output_buf_offset[compptr.component_index] + yoffset * compptr.DCT_scaled_size;
|
|
3825 start_col = MCU_col_num * compptr.MCU_sample_width;
|
|
3826 for (yindex = 0; yindex < compptr.MCU_height; yindex++) {
|
|
3827 if (cinfo.input_iMCU_row < last_iMCU_row || yoffset+yindex < compptr.last_row_height) {
|
|
3828 output_col = start_col;
|
|
3829 for (xindex = 0; xindex < useful_width; xindex++) {
|
|
3830 jpeg_idct_islow(cinfo, compptr, coef.MCU_buffer[blkn+xindex], output_ptr, output_ptr_offset, output_col);
|
|
3831 output_col += compptr.DCT_scaled_size;
|
|
3832 }
|
|
3833 }
|
|
3834 blkn += compptr.MCU_width;
|
|
3835 output_ptr_offset += compptr.DCT_scaled_size;
|
|
3836 }
|
|
3837 }
|
|
3838 }
|
|
3839 /* Completed an MCU row, but perhaps not an iMCU row */
|
|
3840 coef.MCU_ctr = 0;
|
|
3841 }
|
|
3842 /* Completed the iMCU row, advance counters for next one */
|
|
3843 cinfo.output_iMCU_row++;
|
|
3844 if (++(cinfo.input_iMCU_row) < cinfo.total_iMCU_rows) {
|
|
3845 coef.start_iMCU_row(cinfo);
|
|
3846 return JPEG_ROW_COMPLETED;
|
|
3847 }
|
|
3848 /* Completed the scan */
|
|
3849 finish_input_pass (cinfo);
|
|
3850 return JPEG_SCAN_COMPLETED;
|
|
3851 }
|
|
3852
|
|
3853 static int decompress_smooth_data (jpeg_decompress_struct cinfo, byte[][][] output_buf, int[] output_buf_offset) {
|
|
3854 jpeg_d_coef_controller coef = cinfo.coef;
|
|
3855 int last_iMCU_row = cinfo.total_iMCU_rows - 1;
|
|
3856 int block_num, last_block_column;
|
|
3857 int ci, block_row, block_rows, access_rows;
|
|
3858 short[][][] buffer;
|
|
3859 short[][] buffer_ptr, prev_block_row, next_block_row;
|
|
3860 byte[][] output_ptr;
|
|
3861 int output_col;
|
|
3862 jpeg_component_info compptr;
|
|
3863 // inverse_DCT_method_ptr inverse_DCT;
|
|
3864 bool first_row, last_row;
|
|
3865 short[] workspace = coef.workspace;
|
|
3866 if (workspace is null) workspace = coef.workspace = new short[DCTSIZE2];
|
|
3867 int[] coef_bits;
|
|
3868 JQUANT_TBL quanttbl;
|
|
3869 int Q00,Q01,Q02,Q10,Q11,Q20, num;
|
|
3870 int DC1,DC2,DC3,DC4,DC5,DC6,DC7,DC8,DC9;
|
|
3871 int Al, pred;
|
|
3872
|
|
3873 /* Force some input to be done if we are getting ahead of the input. */
|
|
3874 while (cinfo.input_scan_number <= cinfo.output_scan_number && ! cinfo.inputctl.eoi_reached) {
|
|
3875 if (cinfo.input_scan_number is cinfo.output_scan_number) {
|
|
3876 /* If input is working on current scan, we ordinarily want it to
|
|
3877 * have completed the current row. But if input scan is DC,
|
|
3878 * we want it to keep one row ahead so that next block row's DC
|
|
3879 * values are up to date.
|
|
3880 */
|
|
3881 int delta = (cinfo.Ss is 0) ? 1 : 0;
|
|
3882 if (cinfo.input_iMCU_row > cinfo.output_iMCU_row+delta)
|
|
3883 break;
|
|
3884 }
|
|
3885 if (consume_input(cinfo) is JPEG_SUSPENDED)
|
|
3886 return JPEG_SUSPENDED;
|
|
3887 }
|
|
3888
|
|
3889 /* OK, output from the virtual arrays. */
|
|
3890 for (ci = 0; ci < cinfo.num_components; ci++) {
|
|
3891 compptr = cinfo.comp_info[ci];
|
|
3892 /* Don't bother to IDCT an uninteresting component. */
|
|
3893 if (! compptr.component_needed)
|
|
3894 continue;
|
|
3895 /* Count non-dummy DCT block rows in this iMCU row. */
|
|
3896 if (cinfo.output_iMCU_row < last_iMCU_row) {
|
|
3897 block_rows = compptr.v_samp_factor;
|
|
3898 access_rows = block_rows * 2; /* this and next iMCU row */
|
|
3899 last_row = false;
|
|
3900 } else {
|
|
3901 /* NB: can't use last_row_height here; it is input-side-dependent! */
|
|
3902 block_rows = (compptr.height_in_blocks % compptr.v_samp_factor);
|
|
3903 if (block_rows is 0) block_rows = compptr.v_samp_factor;
|
|
3904 access_rows = block_rows; /* this iMCU row only */
|
|
3905 last_row = true;
|
|
3906 }
|
|
3907 /* Align the virtual buffer for this component. */
|
|
3908 int buffer_offset;
|
|
3909 if (cinfo.output_iMCU_row > 0) {
|
|
3910 access_rows += compptr.v_samp_factor; /* prior iMCU row too */
|
|
3911 buffer = coef.whole_image[ci];
|
|
3912 buffer_offset = (cinfo.output_iMCU_row - 1) * compptr.v_samp_factor;
|
|
3913 buffer_offset += compptr.v_samp_factor; /* point to current iMCU row */
|
|
3914 first_row = false;
|
|
3915 } else {
|
|
3916 buffer = coef.whole_image[ci];
|
|
3917 buffer_offset = 0;
|
|
3918 first_row = true;
|
|
3919 }
|
|
3920 /* Fetch component-dependent info */
|
|
3921 coef_bits = coef.coef_bits_latch;
|
|
3922 int coef_offset = (ci * SAVED_COEFS);
|
|
3923 quanttbl = compptr.quant_table;
|
|
3924 Q00 = quanttbl.quantval[0];
|
|
3925 Q01 = quanttbl.quantval[Q01_POS];
|
|
3926 Q10 = quanttbl.quantval[Q10_POS];
|
|
3927 Q20 = quanttbl.quantval[Q20_POS];
|
|
3928 Q11 = quanttbl.quantval[Q11_POS];
|
|
3929 Q02 = quanttbl.quantval[Q02_POS];
|
|
3930 // inverse_DCT = cinfo.idct.inverse_DCT[ci];
|
|
3931 output_ptr = output_buf[ci];
|
|
3932 int output_ptr_offset = output_buf_offset[ci];
|
|
3933 /* Loop over all DCT blocks to be processed. */
|
|
3934 for (block_row = 0; block_row < block_rows; block_row++) {
|
|
3935 buffer_ptr = buffer[block_row+buffer_offset];
|
|
3936 int buffer_ptr_offset = 0, prev_block_row_offset = 0, next_block_row_offset = 0;
|
|
3937 if (first_row && block_row is 0) {
|
|
3938 prev_block_row = buffer_ptr;
|
|
3939 prev_block_row_offset = buffer_ptr_offset;
|
|
3940 } else {
|
|
3941 prev_block_row = buffer[block_row-1+buffer_offset];
|
|
3942 prev_block_row_offset = 0;
|
|
3943 }
|
|
3944 if (last_row && block_row is block_rows-1) {
|
|
3945 next_block_row = buffer_ptr;
|
|
3946 next_block_row_offset = buffer_ptr_offset;
|
|
3947 } else {
|
|
3948 next_block_row = buffer[block_row+1+buffer_offset];
|
|
3949 next_block_row_offset = 0;
|
|
3950 }
|
|
3951 /* We fetch the surrounding DC values using a sliding-register approach.
|
|
3952 * Initialize all nine here so as to do the right thing on narrow pics.
|
|
3953 */
|
|
3954 DC1 = DC2 = DC3 = prev_block_row[0+prev_block_row_offset][0];
|
|
3955 DC4 = DC5 = DC6 = buffer_ptr[0+buffer_ptr_offset][0];
|
|
3956 DC7 = DC8 = DC9 = next_block_row[0+next_block_row_offset][0];
|
|
3957 output_col = 0;
|
|
3958 last_block_column = compptr.width_in_blocks - 1;
|
|
3959 for (block_num = 0; block_num <= last_block_column; block_num++) {
|
|
3960 /* Fetch current DCT block into workspace so we can modify it. */
|
|
3961 // jcopy_block_row(buffer_ptr, workspace, 1);
|
|
3962 System.arraycopy(buffer_ptr[buffer_ptr_offset], 0, workspace, 0, workspace.length);
|
|
3963 /* Update DC values */
|
|
3964 if (block_num < last_block_column) {
|
|
3965 DC3 = prev_block_row[1+prev_block_row_offset][0];
|
|
3966 DC6 = buffer_ptr[1+buffer_ptr_offset][0];
|
|
3967 DC9 = next_block_row[1+next_block_row_offset][0];
|
|
3968 }
|
|
3969 /* Compute coefficient estimates per K.8.
|
|
3970 * An estimate is applied only if coefficient is still zero,
|
|
3971 * and is not known to be fully accurate.
|
|
3972 */
|
|
3973 /* AC01 */
|
|
3974 if ((Al=coef_bits[1+coef_offset]) !is 0 && workspace[1] is 0) {
|
|
3975 num = 36 * Q00 * (DC4 - DC6);
|
|
3976 if (num >= 0) {
|
|
3977 pred = (((Q01<<7) + num) / (Q01<<8));
|
|
3978 if (Al > 0 && pred >= (1<<Al))
|
|
3979 pred = (1<<Al)-1;
|
|
3980 } else {
|
|
3981 pred = (((Q01<<7) - num) / (Q01<<8));
|
|
3982 if (Al > 0 && pred >= (1<<Al))
|
|
3983 pred = (1<<Al)-1;
|
|
3984 pred = -pred;
|
|
3985 }
|
|
3986 workspace[1] = cast(short) pred;
|
|
3987 }
|
|
3988 /* AC10 */
|
|
3989 if ((Al=coef_bits[2+coef_offset]) !is 0 && workspace[8] is 0) {
|
|
3990 num = 36 * Q00 * (DC2 - DC8);
|
|
3991 if (num >= 0) {
|
|
3992 pred = (((Q10<<7) + num) / (Q10<<8));
|
|
3993 if (Al > 0 && pred >= (1<<Al))
|
|
3994 pred = (1<<Al)-1;
|
|
3995 } else {
|
|
3996 pred = (((Q10<<7) - num) / (Q10<<8));
|
|
3997 if (Al > 0 && pred >= (1<<Al))
|
|
3998 pred = (1<<Al)-1;
|
|
3999 pred = -pred;
|
|
4000 }
|
|
4001 workspace[8] = cast(short) pred;
|
|
4002 }
|
|
4003 /* AC20 */
|
|
4004 if ((Al=coef_bits[3+coef_offset]) !is 0 && workspace[16] is 0) {
|
|
4005 num = 9 * Q00 * (DC2 + DC8 - 2*DC5);
|
|
4006 if (num >= 0) {
|
|
4007 pred = (((Q20<<7) + num) / (Q20<<8));
|
|
4008 if (Al > 0 && pred >= (1<<Al))
|
|
4009 pred = (1<<Al)-1;
|
|
4010 } else {
|
|
4011 pred = (((Q20<<7) - num) / (Q20<<8));
|
|
4012 if (Al > 0 && pred >= (1<<Al))
|
|
4013 pred = (1<<Al)-1;
|
|
4014 pred = -pred;
|
|
4015 }
|
|
4016 workspace[16] = cast(short) pred;
|
|
4017 }
|
|
4018 /* AC11 */
|
|
4019 if ((Al=coef_bits[4+coef_offset]) !is 0 && workspace[9] is 0) {
|
|
4020 num = 5 * Q00 * (DC1 - DC3 - DC7 + DC9);
|
|
4021 if (num >= 0) {
|
|
4022 pred = (((Q11<<7) + num) / (Q11<<8));
|
|
4023 if (Al > 0 && pred >= (1<<Al))
|
|
4024 pred = (1<<Al)-1;
|
|
4025 } else {
|
|
4026 pred = (((Q11<<7) - num) / (Q11<<8));
|
|
4027 if (Al > 0 && pred >= (1<<Al))
|
|
4028 pred = (1<<Al)-1;
|
|
4029 pred = -pred;
|
|
4030 }
|
|
4031 workspace[9] = cast(short) pred;
|
|
4032 }
|
|
4033 /* AC02 */
|
|
4034 if ((Al=coef_bits[5+coef_offset]) !is 0 && workspace[2] is 0) {
|
|
4035 num = 9 * Q00 * (DC4 + DC6 - 2*DC5);
|
|
4036 if (num >= 0) {
|
|
4037 pred = (((Q02<<7) + num) / (Q02<<8));
|
|
4038 if (Al > 0 && pred >= (1<<Al))
|
|
4039 pred = (1<<Al)-1;
|
|
4040 } else {
|
|
4041 pred = (((Q02<<7) - num) / (Q02<<8));
|
|
4042 if (Al > 0 && pred >= (1<<Al))
|
|
4043 pred = (1<<Al)-1;
|
|
4044 pred = -pred;
|
|
4045 }
|
|
4046 workspace[2] = cast(short) pred;
|
|
4047 }
|
|
4048 /* OK, do the IDCT */
|
|
4049 jpeg_idct_islow(cinfo, compptr, workspace, output_ptr, output_ptr_offset, output_col);
|
|
4050 /* Advance for next column */
|
|
4051 DC1 = DC2; DC2 = DC3;
|
|
4052 DC4 = DC5; DC5 = DC6;
|
|
4053 DC7 = DC8; DC8 = DC9;
|
|
4054 buffer_ptr_offset++; prev_block_row_offset++; next_block_row_offset++;
|
|
4055 output_col += compptr.DCT_scaled_size;
|
|
4056 }
|
|
4057 output_ptr_offset += compptr.DCT_scaled_size;
|
|
4058 }
|
|
4059 }
|
|
4060
|
|
4061 if (++(cinfo.output_iMCU_row) < cinfo.total_iMCU_rows)
|
|
4062 return JPEG_ROW_COMPLETED;
|
|
4063 return JPEG_SCAN_COMPLETED;
|
|
4064 }
|
|
4065
|
|
4066 static int decompress_data (jpeg_decompress_struct cinfo, byte[][][] output_buf, int[] output_buf_offset) {
|
|
4067 jpeg_d_coef_controller coef = cinfo.coef;
|
|
4068 int last_iMCU_row = cinfo.total_iMCU_rows - 1;
|
|
4069 int block_num;
|
|
4070 int ci, block_row, block_rows;
|
|
4071 short[][][] buffer;
|
|
4072 short[][] buffer_ptr;
|
|
4073 byte[][] output_ptr;
|
|
4074 int output_col;
|
|
4075 jpeg_component_info compptr;
|
|
4076 // inverse_DCT_method_ptr inverse_DCT;
|
|
4077
|
|
4078 /* Force some input to be done if we are getting ahead of the input. */
|
|
4079 while (cinfo.input_scan_number < cinfo.output_scan_number ||
|
|
4080 (cinfo.input_scan_number is cinfo.output_scan_number &&
|
|
4081 cinfo.input_iMCU_row <= cinfo.output_iMCU_row))
|
|
4082 {
|
|
4083 if (consume_input(cinfo) is JPEG_SUSPENDED)
|
|
4084 return JPEG_SUSPENDED;
|
|
4085 }
|
|
4086
|
|
4087 /* OK, output from the virtual arrays. */
|
|
4088 for (ci = 0; ci < cinfo.num_components; ci++) {
|
|
4089 compptr = cinfo.comp_info[ci];
|
|
4090 /* Don't bother to IDCT an uninteresting component. */
|
|
4091 if (! compptr.component_needed)
|
|
4092 continue;
|
|
4093 /* Align the virtual buffer for this component. */
|
|
4094 buffer = coef.whole_image[ci];
|
|
4095 int buffer_offset = cinfo.output_iMCU_row * compptr.v_samp_factor;
|
|
4096 /* Count non-dummy DCT block rows in this iMCU row. */
|
|
4097 if (cinfo.output_iMCU_row < last_iMCU_row)
|
|
4098 block_rows = compptr.v_samp_factor;
|
|
4099 else {
|
|
4100 /* NB: can't use last_row_height here; it is input-side-dependent! */
|
|
4101 block_rows = (compptr.height_in_blocks % compptr.v_samp_factor);
|
|
4102 if (block_rows is 0) block_rows = compptr.v_samp_factor;
|
|
4103 }
|
|
4104 // inverse_DCT = cinfo.idct.inverse_DCT[ci];
|
|
4105 output_ptr = output_buf[ci];
|
|
4106 int output_ptr_offset = output_buf_offset[ci];
|
|
4107 /* Loop over all DCT blocks to be processed. */
|
|
4108 for (block_row = 0; block_row < block_rows; block_row++) {
|
|
4109 buffer_ptr = buffer[block_row+buffer_offset];
|
|
4110 int buffer_ptr_offset = 0;
|
|
4111 output_col = 0;
|
|
4112 for (block_num = 0; block_num < compptr.width_in_blocks; block_num++) {
|
|
4113 jpeg_idct_islow(cinfo, compptr, buffer_ptr[buffer_ptr_offset], output_ptr, output_ptr_offset, output_col);
|
|
4114
|
|
4115 buffer_ptr_offset++;
|
|
4116 output_col += compptr.DCT_scaled_size;
|
|
4117 }
|
|
4118 output_ptr_offset += compptr.DCT_scaled_size;
|
|
4119 }
|
|
4120 }
|
|
4121
|
|
4122 if (++(cinfo.output_iMCU_row) < cinfo.total_iMCU_rows)
|
|
4123 return JPEG_ROW_COMPLETED;
|
|
4124 return JPEG_SCAN_COMPLETED;
|
|
4125 }
|
|
4126
|
|
4127 static void post_process_data (jpeg_decompress_struct cinfo,
|
|
4128 byte[][][] input_buf, int[] input_buf_offset, int[] in_row_group_ctr,
|
|
4129 int in_row_groups_avail,
|
|
4130 byte[][] output_buf, int[] out_row_ctr,
|
|
4131 int out_rows_avail)
|
|
4132 {
|
|
4133 upsample(cinfo, input_buf, input_buf_offset, in_row_group_ctr, in_row_groups_avail, output_buf, out_row_ctr, out_rows_avail);
|
|
4134 }
|
|
4135
|
|
4136 static void set_bottom_pointers (jpeg_decompress_struct cinfo)
|
|
4137 /* Change the pointer lists to duplicate the last sample row at the bottom
|
|
4138 * of the image. whichptr indicates which xbuffer holds the final iMCU row.
|
|
4139 * Also sets rowgroups_avail to indicate number of nondummy row groups in row.
|
|
4140 */
|
|
4141 {
|
|
4142 jpeg_d_main_controller main = cinfo.main;
|
|
4143 int ci, i, rgroup, iMCUheight, rows_left;
|
|
4144 jpeg_component_info compptr;
|
|
4145 byte[][] xbuf;
|
|
4146
|
|
4147 for (ci = 0; ci < cinfo.num_components; ci++) {
|
|
4148 compptr = cinfo.comp_info[ci];
|
|
4149 /* Count sample rows in one iMCU row and in one row group */
|
|
4150 iMCUheight = compptr.v_samp_factor * compptr.DCT_scaled_size;
|
|
4151 rgroup = iMCUheight / cinfo.min_DCT_scaled_size;
|
|
4152 /* Count nondummy sample rows remaining for this component */
|
|
4153 rows_left = (compptr.downsampled_height % iMCUheight);
|
|
4154 if (rows_left is 0) rows_left = iMCUheight;
|
|
4155 /* Count nondummy row groups. Should get same answer for each component,
|
|
4156 * so we need only do it once.
|
|
4157 */
|
|
4158 if (ci is 0) {
|
|
4159 main.rowgroups_avail = ((rows_left-1) / rgroup + 1);
|
|
4160 }
|
|
4161 /* Duplicate the last real sample row rgroup*2 times; this pads out the
|
|
4162 * last partial rowgroup and ensures at least one full rowgroup of context.
|
|
4163 */
|
|
4164 xbuf = main.xbuffer[main.whichptr][ci];
|
|
4165 int xbuf_offset = main.xbuffer_offset[main.whichptr][ci];
|
|
4166 for (i = 0; i < rgroup * 2; i++) {
|
|
4167 xbuf[rows_left + i + xbuf_offset] = xbuf[rows_left-1 + xbuf_offset];
|
|
4168 }
|
|
4169 }
|
|
4170 }
|
|
4171
|
|
4172 static void set_wraparound_pointers (jpeg_decompress_struct cinfo)
|
|
4173 /* Set up the "wraparound" pointers at top and bottom of the pointer lists.
|
|
4174 * This changes the pointer list state from top-of-image to the normal state.
|
|
4175 */
|
|
4176 {
|
|
4177 jpeg_d_main_controller main = cinfo.main;
|
|
4178 int ci, i, rgroup;
|
|
4179 int M = cinfo.min_DCT_scaled_size;
|
|
4180 jpeg_component_info compptr;
|
|
4181 byte[][] xbuf0, xbuf1;
|
|
4182
|
|
4183 for (ci = 0; ci < cinfo.num_components; ci++) {
|
|
4184 compptr = cinfo.comp_info[ci];
|
|
4185 rgroup = (compptr.v_samp_factor * compptr.DCT_scaled_size) / cinfo.min_DCT_scaled_size; /* height of a row group of component */
|
|
4186 xbuf0 = main.xbuffer[0][ci];
|
|
4187 int xbuf0_offset = main.xbuffer_offset[0][ci];
|
|
4188 xbuf1 = main.xbuffer[1][ci];
|
|
4189 int xbuf1_offset = main.xbuffer_offset[1][ci];
|
|
4190 for (i = 0; i < rgroup; i++) {
|
|
4191 xbuf0[i - rgroup + xbuf0_offset] = xbuf0[rgroup*(M+1) + i + xbuf0_offset];
|
|
4192 xbuf1[i - rgroup + xbuf1_offset] = xbuf1[rgroup*(M+1) + i + xbuf1_offset];
|
|
4193 xbuf0[rgroup*(M+2) + i + xbuf0_offset] = xbuf0[i + xbuf0_offset];
|
|
4194 xbuf1[rgroup*(M+2) + i + xbuf1_offset] = xbuf1[i + xbuf1_offset];
|
|
4195 }
|
|
4196 }
|
|
4197 }
|
|
4198
|
|
4199 static void process_data_crank_post (jpeg_decompress_struct cinfo,
|
|
4200 byte[][] output_buf, int[] out_row_ctr,
|
|
4201 int out_rows_avail)
|
|
4202 {
|
|
4203 error();
|
|
4204 }
|
|
4205
|
|
4206 static void process_data_context_main (jpeg_decompress_struct cinfo,
|
|
4207 byte[][] output_buf, int[] out_row_ctr,
|
|
4208 int out_rows_avail)
|
|
4209 {
|
|
4210 jpeg_d_main_controller main = cinfo.main;
|
|
4211
|
|
4212 /* Read input data if we haven't filled the main buffer yet */
|
|
4213 if (! main.buffer_full) {
|
|
4214 int result;
|
|
4215 switch (cinfo.coef.decompress_data) {
|
|
4216 case DECOMPRESS_DATA:
|
|
4217 result = decompress_data(cinfo, main.xbuffer[main.whichptr], main.xbuffer_offset[main.whichptr]);
|
|
4218 break;
|
|
4219 case DECOMPRESS_SMOOTH_DATA:
|
|
4220 result = decompress_smooth_data(cinfo, main.xbuffer[main.whichptr], main.xbuffer_offset[main.whichptr]);
|
|
4221 break;
|
|
4222 case DECOMPRESS_ONEPASS:
|
|
4223 result = decompress_onepass(cinfo, main.xbuffer[main.whichptr], main.xbuffer_offset[main.whichptr]);
|
|
4224 break;
|
|
4225 default: result = 0;
|
|
4226 }
|
|
4227 if (result is 0)
|
|
4228 return; /* suspension forced, can do nothing more */
|
|
4229 main.buffer_full = true; /* OK, we have an iMCU row to work with */
|
|
4230 main.iMCU_row_ctr++; /* count rows received */
|
|
4231 }
|
|
4232
|
|
4233 /* Postprocessor typically will not swallow all the input data it is handed
|
|
4234 * in one call (due to filling the output buffer first). Must be prepared
|
|
4235 * to exit and restart. This switch lets us keep track of how far we got.
|
|
4236 * Note that each case falls through to the next on successful completion.
|
|
4237 */
|
|
4238 switch (main.context_state) {
|
|
4239 case CTX_POSTPONED_ROW:
|
|
4240 /* Call postprocessor using previously set pointers for postponed row */
|
|
4241 post_process_data (cinfo, main.xbuffer[main.whichptr], main.xbuffer_offset[main.whichptr], main.rowgroup_ctr, main.rowgroups_avail, output_buf, out_row_ctr, out_rows_avail);
|
|
4242 if (main.rowgroup_ctr[0] < main.rowgroups_avail)
|
|
4243 return; /* Need to suspend */
|
|
4244 main.context_state = CTX_PREPARE_FOR_IMCU;
|
|
4245 if (out_row_ctr[0] >= out_rows_avail)
|
|
4246 return; /* Postprocessor exactly filled output buf */
|
|
4247 /*FALLTHROUGH*/
|
|
4248 case CTX_PREPARE_FOR_IMCU:
|
|
4249 /* Prepare to process first M-1 row groups of this iMCU row */
|
|
4250 main.rowgroup_ctr[0] = 0;
|
|
4251 main.rowgroups_avail = (cinfo.min_DCT_scaled_size - 1);
|
|
4252 /* Check for bottom of image: if so, tweak pointers to "duplicate"
|
|
4253 * the last sample row, and adjust rowgroups_avail to ignore padding rows.
|
|
4254 */
|
|
4255 if (main.iMCU_row_ctr is cinfo.total_iMCU_rows)
|
|
4256 set_bottom_pointers(cinfo);
|
|
4257 main.context_state = CTX_PROCESS_IMCU;
|
|
4258 /*FALLTHROUGH*/
|
|
4259 case CTX_PROCESS_IMCU:
|
|
4260 /* Call postprocessor using previously set pointers */
|
|
4261 post_process_data (cinfo, main.xbuffer[main.whichptr], main.xbuffer_offset[main.whichptr], main.rowgroup_ctr, main.rowgroups_avail, output_buf, out_row_ctr, out_rows_avail);
|
|
4262 if (main.rowgroup_ctr[0] < main.rowgroups_avail)
|
|
4263 return; /* Need to suspend */
|
|
4264 /* After the first iMCU, change wraparound pointers to normal state */
|
|
4265 if (main.iMCU_row_ctr is 1)
|
|
4266 set_wraparound_pointers(cinfo);
|
|
4267 /* Prepare to load new iMCU row using other xbuffer list */
|
|
4268 main.whichptr ^= 1; /* 0=>1 or 1=>0 */
|
|
4269 main.buffer_full = false;
|
|
4270 /* Still need to process last row group of this iMCU row, */
|
|
4271 /* which is saved at index M+1 of the other xbuffer */
|
|
4272 main.rowgroup_ctr[0] = (cinfo.min_DCT_scaled_size + 1);
|
|
4273 main.rowgroups_avail = (cinfo.min_DCT_scaled_size + 2);
|
|
4274 main.context_state = CTX_POSTPONED_ROW;
|
|
4275 default:
|
|
4276 }
|
|
4277 }
|
|
4278
|
|
4279 static void process_data_simple_main (jpeg_decompress_struct cinfo, byte[][] output_buf, int[] out_row_ctr, int out_rows_avail) {
|
|
4280 jpeg_d_main_controller main = cinfo.main;
|
|
4281 int rowgroups_avail;
|
|
4282
|
|
4283 /* Read input data if we haven't filled the main buffer yet */
|
|
4284 if (! main.buffer_full) {
|
|
4285 int result;
|
|
4286 switch (cinfo.coef.decompress_data) {
|
|
4287 case DECOMPRESS_DATA:
|
|
4288 result = decompress_data(cinfo, main.buffer, main.buffer_offset);
|
|
4289 break;
|
|
4290 case DECOMPRESS_SMOOTH_DATA:
|
|
4291 result = decompress_smooth_data(cinfo, main.buffer, main.buffer_offset);
|
|
4292 break;
|
|
4293 case DECOMPRESS_ONEPASS:
|
|
4294 result = decompress_onepass(cinfo, main.buffer, main.buffer_offset);
|
|
4295 break;
|
|
4296 default: result = 0;
|
|
4297 }
|
|
4298 if (result is 0)
|
|
4299 return; /* suspension forced, can do nothing more */
|
|
4300 main.buffer_full = true; /* OK, we have an iMCU row to work with */
|
|
4301 }
|
|
4302
|
|
4303 /* There are always min_DCT_scaled_size row groups in an iMCU row. */
|
|
4304 rowgroups_avail = cinfo.min_DCT_scaled_size;
|
|
4305 /* Note: at the bottom of the image, we may pass extra garbage row groups
|
|
4306 * to the postprocessor. The postprocessor has to check for bottom
|
|
4307 * of image anyway (at row resolution), so no point in us doing it too.
|
|
4308 */
|
|
4309
|
|
4310 /* Feed the postprocessor */
|
|
4311 post_process_data (cinfo, main.buffer, main.buffer_offset, main.rowgroup_ctr, rowgroups_avail, output_buf, out_row_ctr, out_rows_avail);
|
|
4312
|
|
4313 /* Has postprocessor consumed all the data yet? If so, mark buffer empty */
|
|
4314 if (main.rowgroup_ctr[0] >= rowgroups_avail) {
|
|
4315 main.buffer_full = false;
|
|
4316 main.rowgroup_ctr[0] = 0;
|
|
4317 }
|
|
4318 }
|
|
4319
|
|
4320 static int jpeg_read_scanlines (jpeg_decompress_struct cinfo, byte[][] scanlines, int max_lines) {
|
|
4321
|
|
4322 if (cinfo.global_state !is DSTATE_SCANNING)
|
|
4323 error();
|
|
4324 // ERREXIT1(cinfo, JERR_BAD_STATE, cinfo.global_state);
|
|
4325 if (cinfo.output_scanline >= cinfo.output_height) {
|
|
4326 // WARNMS(cinfo, JWRN_TOO_MUCH_DATA);
|
|
4327 return 0;
|
|
4328 }
|
|
4329
|
|
4330 /* Call progress monitor hook if present */
|
|
4331 // if (cinfo.progress !is NULL) {
|
|
4332 // cinfo.progress.pass_counter = cast(long) cinfo.output_scanline;
|
|
4333 // cinfo.progress.pass_limit = cast(long) cinfo.output_height;
|
|
4334 // (*cinfo.progress.progress_monitor) ((j_common_ptr) cinfo);
|
|
4335 // }
|
|
4336
|
|
4337 /* Process some data */
|
|
4338 cinfo.row_ctr[0] = 0;
|
|
4339 switch (cinfo.main.process_data) {
|
|
4340 case PROCESS_DATA_SIMPLE_MAIN:
|
|
4341 process_data_simple_main (cinfo, scanlines, cinfo.row_ctr, max_lines);
|
|
4342 break;
|
|
4343 case PROCESS_DATA_CONTEXT_MAIN:
|
|
4344 process_data_context_main (cinfo, scanlines, cinfo.row_ctr, max_lines);
|
|
4345 break;
|
|
4346 case PROCESS_DATA_CRANK_POST:
|
|
4347 process_data_crank_post (cinfo, scanlines, cinfo.row_ctr, max_lines);
|
|
4348 break;
|
|
4349 default: error();
|
|
4350 }
|
|
4351 cinfo.output_scanline += cinfo.row_ctr[0];
|
|
4352 return cinfo.row_ctr[0];
|
|
4353 }
|
|
4354
|
|
4355
|
|
4356 static bool output_pass_setup (jpeg_decompress_struct cinfo) {
|
|
4357 if (cinfo.global_state !is DSTATE_PRESCAN) {
|
|
4358 /* First call: do pass setup */
|
|
4359 prepare_for_output_pass (cinfo);
|
|
4360 cinfo.output_scanline = 0;
|
|
4361 cinfo.global_state = DSTATE_PRESCAN;
|
|
4362 }
|
|
4363 /* Loop over any required dummy passes */
|
|
4364 while (cinfo.master.is_dummy_pass) {
|
|
4365 error();
|
|
4366 //#ifdef QUANT_2PASS_SUPPORTED
|
|
4367 // /* Crank through the dummy pass */
|
|
4368 // while (cinfo.output_scanline < cinfo.output_height) {
|
|
4369 // JDIMENSION last_scanline;
|
|
4370 // /* Call progress monitor hook if present */
|
|
4371 // if (cinfo.progress !is NULL) {
|
|
4372 // cinfo.progress.pass_counter = cast(long) cinfo.output_scanline;
|
|
4373 // cinfo.progress.pass_limit = cast(long) cinfo.output_height;
|
|
4374 // (*cinfo.progress.progress_monitor) ((j_common_ptr) cinfo);
|
|
4375 // }
|
|
4376 // /* Process some data */
|
|
4377 // last_scanline = cinfo.output_scanline;
|
|
4378 // (*cinfo.main.process_data) (cinfo, (JSAMPARRAY) NULL,
|
|
4379 // &cinfo.output_scanline, (JDIMENSION) 0);
|
|
4380 // if (cinfo.output_scanline is last_scanline)
|
|
4381 // return FALSE; /* No progress made, must suspend */
|
|
4382 // }
|
|
4383 // /* Finish up dummy pass, and set up for another one */
|
|
4384 // (*cinfo.master.finish_output_pass) (cinfo);
|
|
4385 // (*cinfo.master.prepare_for_output_pass) (cinfo);
|
|
4386 // cinfo.output_scanline = 0;
|
|
4387 //#else
|
|
4388 // ERREXIT(cinfo, JERR_NOT_COMPILED);
|
|
4389 //#endif /* QUANT_2PASS_SUPPORTED */
|
|
4390 }
|
|
4391 /* Ready for application to drive output pass through
|
|
4392 * jpeg_read_scanlines or jpeg_read_raw_data.
|
|
4393 */
|
|
4394 cinfo.global_state = cinfo.raw_data_out ? DSTATE_RAW_OK : DSTATE_SCANNING;
|
|
4395 return true;
|
|
4396 }
|
|
4397
|
|
4398 static bool get_dht (jpeg_decompress_struct cinfo)
|
|
4399 /* Process a DHT marker */
|
|
4400 {
|
|
4401 int length;
|
|
4402 byte[] bits = new byte[17];
|
|
4403 byte[] huffval = new byte[256];
|
|
4404 int i, index, count;
|
|
4405 JHUFF_TBL htblptr;
|
|
4406
|
|
4407 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4408 length = (cinfo.buffer[cinfo.bytes_offset++] & 0xFF) << 8;
|
|
4409 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4410 length |= cinfo.buffer[cinfo.bytes_offset++] & 0xFF;
|
|
4411 length -= 2;
|
|
4412
|
|
4413 while (length > 16) {
|
|
4414 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4415 index = cinfo.buffer[cinfo.bytes_offset++] & 0xFF;
|
|
4416
|
|
4417 // TRACEMS1(cinfo, 1, JTRC_DHT, index);
|
|
4418
|
|
4419 bits[0] = 0;
|
|
4420 count = 0;
|
|
4421 for (i = 1; i <= 16; i++) {
|
|
4422 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4423 bits[i] = cinfo.buffer[cinfo.bytes_offset++];
|
|
4424 count += bits[i] & 0xFF;
|
|
4425 }
|
|
4426
|
|
4427 length -= 1 + 16;
|
|
4428
|
|
4429 // TRACEMS8(cinfo, 2, JTRC_HUFFBITS,
|
|
4430 // bits[1], bits[2], bits[3], bits[4],
|
|
4431 // bits[5], bits[6], bits[7], bits[8]);
|
|
4432 // TRACEMS8(cinfo, 2, JTRC_HUFFBITS,
|
|
4433 // bits[9], bits[10], bits[11], bits[12],
|
|
4434 // bits[13], bits[14], bits[15], bits[16]);
|
|
4435
|
|
4436 /* Here we just do minimal validation of the counts to avoid walking
|
|
4437 * off the end of our table space. jdhuff.c will check more carefully.
|
|
4438 */
|
|
4439 if (count > 256 || (count) > length)
|
|
4440 error();
|
|
4441 // ERREXIT(cinfo, JERR_BAD_HUFF_TABLE);
|
|
4442
|
|
4443 for (i = 0; i < count; i++) {
|
|
4444 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4445 huffval[i] = cinfo.buffer[cinfo.bytes_offset++];
|
|
4446 }
|
|
4447
|
|
4448 length -= count;
|
|
4449
|
|
4450 if ((index & 0x10) !is 0) { /* AC table definition */
|
|
4451 index -= 0x10;
|
|
4452 htblptr = cinfo.ac_huff_tbl_ptrs[index] = new JHUFF_TBL();
|
|
4453 } else { /* DC table definition */
|
|
4454 htblptr = cinfo.dc_huff_tbl_ptrs[index] = new JHUFF_TBL();
|
|
4455 }
|
|
4456
|
|
4457 if (index < 0 || index >= NUM_HUFF_TBLS)
|
|
4458 error();
|
|
4459 // ERREXIT1(cinfo, JERR_DHT_INDEX, index);
|
|
4460
|
|
4461 System.arraycopy(bits, 0, htblptr.bits, 0, bits.length);
|
|
4462 System.arraycopy(huffval, 0, htblptr.huffval, 0, huffval.length);
|
|
4463 }
|
|
4464
|
|
4465 if (length !is 0)
|
|
4466 error();
|
|
4467 // ERREXIT(cinfo, JERR_BAD_LENGTH);
|
|
4468
|
|
4469 return true;
|
|
4470 }
|
|
4471
|
|
4472
|
|
4473 static bool get_dqt (jpeg_decompress_struct cinfo)
|
|
4474 /* Process a DQT marker */
|
|
4475 {
|
|
4476 int length;
|
|
4477 int n, i, prec;
|
|
4478 int tmp;
|
|
4479 JQUANT_TBL quant_ptr;
|
|
4480
|
|
4481 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4482 length = (cinfo.buffer[cinfo.bytes_offset++] & 0xFF) << 8;
|
|
4483 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4484 length |= cinfo.buffer[cinfo.bytes_offset++] & 0xFF;
|
|
4485 length -= 2;
|
|
4486
|
|
4487 while (length > 0) {
|
|
4488 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4489 n = cinfo.buffer[cinfo.bytes_offset++] & 0xFF;
|
|
4490 prec = n >> 4;
|
|
4491 n &= 0x0F;
|
|
4492
|
|
4493 // TRACEMS2(cinfo, 1, JTRC_DQT, n, prec);
|
|
4494
|
|
4495 if (n >= NUM_QUANT_TBLS)
|
|
4496 error();
|
|
4497 // ERREXIT1(cinfo, JERR_DQT_INDEX, n);
|
|
4498
|
|
4499 if (cinfo.quant_tbl_ptrs[n] is null)
|
|
4500 cinfo.quant_tbl_ptrs[n] = new JQUANT_TBL();
|
|
4501 quant_ptr = cinfo.quant_tbl_ptrs[n];
|
|
4502
|
|
4503 for (i = 0; i < DCTSIZE2; i++) {
|
|
4504 if (prec !is 0) {
|
|
4505 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4506 tmp = (cinfo.buffer[cinfo.bytes_offset++] & 0xFF) << 8;
|
|
4507 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4508 tmp |= cinfo.buffer[cinfo.bytes_offset++] & 0xFF;
|
|
4509 } else {
|
|
4510 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4511 tmp = cinfo.buffer[cinfo.bytes_offset++] & 0xFF;
|
|
4512 }
|
|
4513 /* We convert the zigzag-order table to natural array order. */
|
|
4514 quant_ptr.quantval[jpeg_natural_order[i]] = cast(short) tmp;
|
|
4515 }
|
|
4516
|
|
4517 // if (cinfo.err.trace_level >= 2) {
|
|
4518 // for (i = 0; i < DCTSIZE2; i += 8) {
|
|
4519 // TRACEMS8(cinfo, 2, JTRC_QUANTVALS,
|
|
4520 // quant_ptr.quantval[i], quant_ptr.quantval[i+1],
|
|
4521 // quant_ptr.quantval[i+2], quant_ptr.quantval[i+3],
|
|
4522 // quant_ptr.quantval[i+4], quant_ptr.quantval[i+5],
|
|
4523 // quant_ptr.quantval[i+6], quant_ptr.quantval[i+7]);
|
|
4524 // }
|
|
4525 // }
|
|
4526
|
|
4527 length -= (DCTSIZE2+1);
|
|
4528 if (prec !is 0) length -= DCTSIZE2;
|
|
4529 }
|
|
4530
|
|
4531 if (length !is 0)
|
|
4532 error();
|
|
4533 // ERREXIT(cinfo, JERR_BAD_LENGTH);
|
|
4534
|
|
4535 return true;
|
|
4536 }
|
|
4537
|
|
4538 static bool get_dri (jpeg_decompress_struct cinfo)
|
|
4539 /* Process a DRI marker */
|
|
4540 {
|
|
4541 int length;
|
|
4542 int tmp;
|
|
4543
|
|
4544 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4545 length = (cinfo.buffer[cinfo.bytes_offset++] & 0xFF) << 8;
|
|
4546 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4547 length |= cinfo.buffer[cinfo.bytes_offset++] & 0xFF;
|
|
4548
|
|
4549 if (length !is 4)
|
|
4550 error();
|
|
4551 // ERREXIT(cinfo, JERR_BAD_LENGTH);
|
|
4552
|
|
4553 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4554 tmp = (cinfo.buffer[cinfo.bytes_offset++] & 0xFF) << 8;
|
|
4555 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4556 tmp |= cinfo.buffer[cinfo.bytes_offset++] & 0xFF;
|
|
4557
|
|
4558 // TRACEMS1(cinfo, 1, JTRC_DRI, tmp);
|
|
4559
|
|
4560 cinfo.restart_interval = tmp;
|
|
4561
|
|
4562 return true;
|
|
4563 }
|
|
4564
|
|
4565 static bool get_dac (jpeg_decompress_struct cinfo)
|
|
4566 /* Process a DAC marker */
|
|
4567 {
|
|
4568 int length;
|
|
4569 int index, val;
|
|
4570 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4571 length = (cinfo.buffer[cinfo.bytes_offset++] & 0xFF) << 8;
|
|
4572 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4573 length |= cinfo.buffer[cinfo.bytes_offset++] & 0xFF;
|
|
4574 length -= 2;
|
|
4575
|
|
4576 while (length > 0) {
|
|
4577 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4578 index = cinfo.buffer[cinfo.bytes_offset++] & 0xFF;
|
|
4579 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4580 val = cinfo.buffer[cinfo.bytes_offset++] & 0xFF;
|
|
4581
|
|
4582 length -= 2;
|
|
4583
|
|
4584 // TRACEMS2(cinfo, 1, JTRC_DAC, index, val);
|
|
4585
|
|
4586 if (index < 0 || index >= (2*NUM_ARITH_TBLS))
|
|
4587 error();
|
|
4588 // ERREXIT1(cinfo, JERR_DAC_INDEX, index);
|
|
4589
|
|
4590 if (index >= NUM_ARITH_TBLS) { /* define AC table */
|
|
4591 cinfo.arith_ac_K[index-NUM_ARITH_TBLS] = cast(byte) val;
|
|
4592 } else { /* define DC table */
|
|
4593 cinfo.arith_dc_L[index] = cast(byte) (val & 0x0F);
|
|
4594 cinfo.arith_dc_U[index] = cast(byte) (val >> 4);
|
|
4595 if (cinfo.arith_dc_L[index] > cinfo.arith_dc_U[index])
|
|
4596 error();
|
|
4597 // ERREXIT1(cinfo, JERR_DAC_VALUE, val);
|
|
4598 }
|
|
4599 }
|
|
4600
|
|
4601 if (length !is 0)
|
|
4602 error();
|
|
4603 // ERREXIT(cinfo, JERR_BAD_LENGTH);
|
|
4604
|
|
4605 return true;
|
|
4606 }
|
|
4607
|
|
4608
|
|
4609 static bool get_sos (jpeg_decompress_struct cinfo)
|
|
4610 /* Process a SOS marker */
|
|
4611 {
|
|
4612 int length;
|
|
4613 int i, ci, n, c, cc;
|
|
4614 jpeg_component_info compptr = null;
|
|
4615
|
|
4616 if (! cinfo.marker.saw_SOF)
|
|
4617 error();
|
|
4618 // ERREXIT(cinfo, JERR_SOS_NO_SOF);
|
|
4619
|
|
4620 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4621 length = (cinfo.buffer[cinfo.bytes_offset++] & 0xFF) << 8;
|
|
4622 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4623 length |= cinfo.buffer[cinfo.bytes_offset++] & 0xFF;
|
|
4624
|
|
4625 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4626 n = cinfo.buffer[cinfo.bytes_offset++] & 0xFF;
|
|
4627
|
|
4628 // TRACEMS1(cinfo, 1, JTRC_SOS, n);
|
|
4629
|
|
4630 if (length !is (n * 2 + 6) || n < 1 || n > MAX_COMPS_IN_SCAN)
|
|
4631 error();
|
|
4632 // ERREXIT(cinfo, JERR_BAD_LENGTH);
|
|
4633
|
|
4634 cinfo.comps_in_scan = n;
|
|
4635
|
|
4636 /* Collect the component-spec parameters */
|
|
4637
|
|
4638 for (i = 0; i < n; i++) {
|
|
4639 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4640 cc = cinfo.buffer[cinfo.bytes_offset++] & 0xFF;
|
|
4641 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4642 c = cinfo.buffer[cinfo.bytes_offset++] & 0xFF;
|
|
4643
|
|
4644 for (ci = 0; ci < cinfo.num_components; ci++) {
|
|
4645 compptr = cinfo.comp_info[ci];
|
|
4646 if (cc is compptr.component_id)
|
|
4647 break;
|
|
4648 }
|
|
4649
|
|
4650 if (ci is cinfo.num_components)
|
|
4651 error();
|
|
4652 // ERREXIT1(cinfo, JERR_BAD_COMPONENT_ID, cc);
|
|
4653
|
|
4654 cinfo.cur_comp_info[i] = compptr;
|
|
4655 compptr.dc_tbl_no = (c >> 4) & 15;
|
|
4656 compptr.ac_tbl_no = (c ) & 15;
|
|
4657
|
|
4658 // TRACEMS3(cinfo, 1, JTRC_SOS_COMPONENT, cc, compptr.dc_tbl_no, compptr.ac_tbl_no);
|
|
4659 }
|
|
4660
|
|
4661 /* Collect the additional scan parameters Ss, Se, Ah/Al. */
|
|
4662 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4663 c = cinfo.buffer[cinfo.bytes_offset++] & 0xFF;
|
|
4664 cinfo.Ss = c;
|
|
4665 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4666 c = cinfo.buffer[cinfo.bytes_offset++] & 0xFF;
|
|
4667 cinfo.Se = c;
|
|
4668 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4669 c = cinfo.buffer[cinfo.bytes_offset++] & 0xFF;
|
|
4670 cinfo.Ah = (c >> 4) & 15;
|
|
4671 cinfo.Al = (c ) & 15;
|
|
4672
|
|
4673 // TRACEMS4(cinfo, 1, JTRC_SOS_PARAMS, cinfo.Ss, cinfo.Se, cinfo.Ah, cinfo.Al);
|
|
4674
|
|
4675 /* Prepare to scan data & restart markers */
|
|
4676 cinfo.marker.next_restart_num = 0;
|
|
4677
|
|
4678 /* Count another SOS marker */
|
|
4679 cinfo.input_scan_number++;
|
|
4680
|
|
4681 return true;
|
|
4682 }
|
|
4683
|
|
4684 static bool get_sof (jpeg_decompress_struct cinfo, bool is_prog, bool is_arith) {
|
|
4685 int length;
|
|
4686 int c, ci;
|
|
4687
|
|
4688 cinfo.progressive_mode = is_prog;
|
|
4689 cinfo.arith_code = is_arith;
|
|
4690
|
|
4691 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4692 length = (cinfo.buffer[cinfo.bytes_offset++] & 0xFF) << 8;
|
|
4693 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4694 length |= cinfo.buffer[cinfo.bytes_offset++] & 0xFF;
|
|
4695
|
|
4696 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4697 cinfo.data_precision = cinfo.buffer[cinfo.bytes_offset++] & 0xFF;
|
|
4698
|
|
4699 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4700 cinfo.image_height = (cinfo.buffer[cinfo.bytes_offset++] & 0xFF) << 8;
|
|
4701 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4702 cinfo.image_height |= cinfo.buffer[cinfo.bytes_offset++] & 0xFF;
|
|
4703
|
|
4704 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4705 cinfo.image_width = (cinfo.buffer[cinfo.bytes_offset++] & 0xFF) << 8;
|
|
4706 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4707 cinfo.image_width |= cinfo.buffer[cinfo.bytes_offset++] & 0xFF;
|
|
4708
|
|
4709 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4710 cinfo.num_components = cinfo.buffer[cinfo.bytes_offset++] & 0xFF;
|
|
4711
|
|
4712 length -= 8;
|
|
4713
|
|
4714 // TRACEMS4(cinfo, 1, JTRC_SOF, cinfo.unread_marker,
|
|
4715 // cast(int) cinfo.image_width, cast(int) cinfo.image_height,
|
|
4716 // cinfo.num_components);
|
|
4717
|
|
4718 if (cinfo.marker.saw_SOF)
|
|
4719 error();
|
|
4720 // ERREXIT(cinfo, JERR_SOF_DUPLICATE);
|
|
4721
|
|
4722 /* We don't support files in which the image height is initially specified */
|
|
4723 /* as 0 and is later redefined by DNL. As long as we have to check that, */
|
|
4724 /* might as well have a general sanity check. */
|
|
4725 if (cinfo.image_height <= 0 || cinfo.image_width <= 0 || cinfo.num_components <= 0)
|
|
4726 error();
|
|
4727 // ERREXIT(cinfo, JERR_EMPTY_IMAGE);
|
|
4728
|
|
4729 if (length !is (cinfo.num_components * 3))
|
|
4730 error();
|
|
4731 // ERREXIT(cinfo, JERR_BAD_LENGTH);
|
|
4732
|
|
4733 if (cinfo.comp_info is null) /* do only once, even if suspend */
|
|
4734 cinfo.comp_info = new jpeg_component_info[cinfo.num_components];
|
|
4735
|
|
4736 for (ci = 0; ci < cinfo.num_components; ci++) {
|
|
4737 jpeg_component_info compptr = cinfo.comp_info[ci] = new jpeg_component_info();
|
|
4738 compptr.component_index = ci;
|
|
4739 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4740 compptr.component_id = cinfo.buffer[cinfo.bytes_offset++] & 0xFF;
|
|
4741 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4742 c = cinfo.buffer[cinfo.bytes_offset++] & 0xFF;
|
|
4743 compptr.h_samp_factor = (c >> 4) & 15;
|
|
4744 compptr.v_samp_factor = (c ) & 15;
|
|
4745 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
4746 compptr.quant_tbl_no = cinfo.buffer[cinfo.bytes_offset++] & 0xFF;
|
|
4747
|
|
4748 // TRACEMS4(cinfo, 1, JTRC_SOF_COMPONENT,
|
|
4749 // compptr.component_id, compptr.h_samp_factor,
|
|
4750 // compptr.v_samp_factor, compptr.quant_tbl_no);
|
|
4751 }
|
|
4752
|
|
4753 cinfo.marker.saw_SOF = true;
|
|
4754
|
|
4755 return true;
|
|
4756 }
|
|
4757
|
|
4758 static void sep_upsample (jpeg_decompress_struct cinfo, byte[][][] input_buf, int[] input_buf_offset,
|
|
4759 int[] in_row_group_ctr, int in_row_groups_avail,
|
|
4760 byte[][] output_buf, int[] out_row_ctr, int out_rows_avail)
|
|
4761 {
|
|
4762 jpeg_upsampler upsample = cinfo.upsample;
|
|
4763 int ci;
|
|
4764 jpeg_component_info compptr;
|
|
4765 int num_rows;
|
|
4766
|
|
4767 /* Fill the conversion buffer, if it's empty */
|
|
4768 if (upsample.next_row_out >= cinfo.max_v_samp_factor) {
|
|
4769 for (ci = 0; ci < cinfo.num_components; ci++) {
|
|
4770 compptr = cinfo.comp_info[ci];
|
|
4771 /* Invoke per-component upsample method. Notice we pass a POINTER
|
|
4772 * to color_buf[ci], so that fullsize_upsample can change it.
|
|
4773 */
|
|
4774 int offset = input_buf_offset[ci] + (in_row_group_ctr[0] * upsample.rowgroup_height[ci]);
|
|
4775 switch (upsample.methods[ci]) {
|
|
4776 case NOOP_UPSAMPLE: noop_upsample(cinfo, compptr, input_buf[ci], offset, upsample.color_buf, upsample.color_buf_offset, ci); break;
|
|
4777 case FULLSIZE_UPSAMPLE: fullsize_upsample(cinfo, compptr, input_buf[ci], offset, upsample.color_buf, upsample.color_buf_offset, ci); break;
|
|
4778 case H2V1_FANCY_UPSAMPLE: h2v1_fancy_upsample(cinfo, compptr, input_buf[ci], offset, upsample.color_buf, upsample.color_buf_offset, ci); break;
|
|
4779 case H2V1_UPSAMPLE: h2v1_upsample(cinfo, compptr, input_buf[ci], offset, upsample.color_buf, upsample.color_buf_offset, ci); break;
|
|
4780 case H2V2_FANCY_UPSAMPLE: h2v2_fancy_upsample(cinfo, compptr, input_buf[ci], offset, upsample.color_buf, upsample.color_buf_offset, ci); break;
|
|
4781 case H2V2_UPSAMPLE: h2v2_upsample(cinfo, compptr, input_buf[ci], offset, upsample.color_buf, upsample.color_buf_offset, ci); break;
|
|
4782 case INT_UPSAMPLE: int_upsample(cinfo, compptr, input_buf[ci], offset, upsample.color_buf, upsample.color_buf_offset, ci); break;
|
|
4783 default:
|
|
4784 }
|
|
4785 }
|
|
4786 upsample.next_row_out = 0;
|
|
4787 }
|
|
4788
|
|
4789 /* Color-convert and emit rows */
|
|
4790
|
|
4791 /* How many we have in the buffer: */
|
|
4792 num_rows = (cinfo.max_v_samp_factor - upsample.next_row_out);
|
|
4793 /* Not more than the distance to the end of the image. Need this test
|
|
4794 * in case the image height is not a multiple of max_v_samp_factor:
|
|
4795 */
|
|
4796 if (num_rows > upsample.rows_to_go)
|
|
4797 num_rows = upsample.rows_to_go;
|
|
4798 /* And not more than what the client can accept: */
|
|
4799 out_rows_avail -= out_row_ctr[0];
|
|
4800 if (num_rows > out_rows_avail)
|
|
4801 num_rows = out_rows_avail;
|
|
4802
|
|
4803 switch (cinfo.cconvert.color_convert) {
|
|
4804 case NULL_CONVERT: null_convert (cinfo, upsample.color_buf, upsample.color_buf_offset, upsample.next_row_out, output_buf, out_row_ctr[0], num_rows); break;
|
|
4805 case GRAYSCALE_CONVERT: grayscale_convert (cinfo, upsample.color_buf, upsample.color_buf_offset, upsample.next_row_out, output_buf, out_row_ctr[0], num_rows); break;
|
|
4806 case YCC_RGB_CONVERT: ycc_rgb_convert (cinfo, upsample.color_buf, upsample.color_buf_offset, upsample.next_row_out, output_buf, out_row_ctr[0], num_rows); break;
|
|
4807 case GRAY_RGB_CONVERT: gray_rgb_convert (cinfo, upsample.color_buf, upsample.color_buf_offset, upsample.next_row_out, output_buf, out_row_ctr[0], num_rows); break;
|
|
4808 case YCCK_CMYK_CONVERT: error(); break;
|
|
4809 default:
|
|
4810 }
|
|
4811
|
|
4812 /* Adjust counts */
|
|
4813 out_row_ctr[0] += num_rows;
|
|
4814 upsample.rows_to_go -= num_rows;
|
|
4815 upsample.next_row_out += num_rows;
|
|
4816 /* When the buffer is emptied, declare this input row group consumed */
|
|
4817 if (upsample.next_row_out >= cinfo.max_v_samp_factor) {
|
|
4818 in_row_group_ctr[0]++;
|
|
4819 }
|
|
4820 }
|
|
4821
|
|
4822 static void noop_upsample (jpeg_decompress_struct cinfo, jpeg_component_info compptr,
|
|
4823 byte[][] input_data, int input_data_offset, byte[][][] output_data_ptr, int[] output_data_offset, int output_data_index)
|
|
4824 {
|
|
4825 output_data_ptr[output_data_index] = null; /* safety check */
|
|
4826 }
|
|
4827
|
|
4828 static void fullsize_upsample (jpeg_decompress_struct cinfo, jpeg_component_info compptr,
|
|
4829 byte[][] input_data, int input_data_offset, byte[][][] output_data_ptr, int[] output_data_offset, int output_data_index)
|
|
4830 {
|
|
4831 output_data_ptr[output_data_index] = input_data;
|
|
4832 output_data_offset[output_data_index] = input_data_offset;
|
|
4833 }
|
|
4834
|
|
4835 static void h2v1_upsample (jpeg_decompress_struct cinfo, jpeg_component_info compptr,
|
|
4836 byte[][] input_data, int input_data_offset, byte[][][] output_data_ptr, int[] output_data_offset, int output_data_index)
|
|
4837 {
|
|
4838 byte[][] output_data = output_data_ptr[output_data_index];
|
|
4839 byte[] inptr, outptr;
|
|
4840 byte invalue;
|
|
4841 int outend;
|
|
4842 int inrow;
|
|
4843 output_data_offset[output_data_index] = 0;
|
|
4844
|
|
4845 for (inrow = 0; inrow < cinfo.max_v_samp_factor; inrow++) {
|
|
4846 inptr = input_data[inrow+input_data_offset];
|
|
4847 outptr = output_data[inrow];
|
|
4848 int inptr_offset = 0, outptr_offset = 0;
|
|
4849 outend = outptr_offset + cinfo.output_width;
|
|
4850 while (outptr_offset < outend) {
|
|
4851 invalue = inptr[inptr_offset++]; /* don't need GETJSAMPLE() here */
|
|
4852 outptr[outptr_offset++] = invalue;
|
|
4853 outptr[outptr_offset++] = invalue;
|
|
4854 }
|
|
4855 }
|
|
4856 }
|
|
4857
|
|
4858 static void h2v2_upsample (jpeg_decompress_struct cinfo, jpeg_component_info compptr,
|
|
4859 byte[][] input_data, int input_data_offset, byte[][][] output_data_ptr, int[] output_data_offset, int output_data_index)
|
|
4860 {
|
|
4861 byte[][] output_data = output_data_ptr[output_data_index];
|
|
4862 byte[] inptr, outptr;
|
|
4863 byte invalue;
|
|
4864 int outend;
|
|
4865 int inrow, outrow;
|
|
4866 output_data_offset[output_data_index] = 0;
|
|
4867
|
|
4868 inrow = outrow = 0;
|
|
4869 while (outrow < cinfo.max_v_samp_factor) {
|
|
4870 inptr = input_data[inrow+input_data_offset];
|
|
4871 outptr = output_data[outrow];
|
|
4872 int inptr_offset = 0, outptr_offset = 0;
|
|
4873 outend = outptr_offset + cinfo.output_width;
|
|
4874 while (outptr_offset < outend) {
|
|
4875 invalue = inptr[inptr_offset++]; /* don't need GETJSAMPLE() here */
|
|
4876 outptr[outptr_offset++] = invalue;
|
|
4877 outptr[outptr_offset++] = invalue;
|
|
4878 }
|
|
4879 jcopy_sample_rows(output_data, outrow, output_data, outrow+1, 1, cinfo.output_width);
|
|
4880 inrow++;
|
|
4881 outrow += 2;
|
|
4882 }
|
|
4883 }
|
|
4884
|
|
4885 static void h2v1_fancy_upsample (jpeg_decompress_struct cinfo, jpeg_component_info compptr,
|
|
4886 byte[][] input_data, int input_data_offset, byte[][][] output_data_ptr, int[] output_data_offset, int output_data_index)
|
|
4887 {
|
|
4888 byte[][] output_data = output_data_ptr[output_data_index];
|
|
4889 byte[] inptr, outptr;
|
|
4890 int invalue;
|
|
4891 int colctr;
|
|
4892 int inrow;
|
|
4893 output_data_offset[output_data_index] = 0;
|
|
4894
|
|
4895 for (inrow = 0; inrow < cinfo.max_v_samp_factor; inrow++) {
|
|
4896 inptr = input_data[inrow+input_data_offset];
|
|
4897 outptr = output_data[inrow];
|
|
4898 int inptr_offset = 0, outptr_offset = 0;
|
|
4899 /* Special case for first column */
|
|
4900 invalue = inptr[inptr_offset++] & 0xFF;
|
|
4901 outptr[outptr_offset++] = cast(byte) invalue;
|
|
4902 outptr[outptr_offset++] = cast(byte) ((invalue * 3 + (inptr[inptr_offset] & 0xFF) + 2) >> 2);
|
|
4903
|
|
4904 for (colctr = compptr.downsampled_width - 2; colctr > 0; colctr--) {
|
|
4905 /* General case: 3/4 * nearer pixel + 1/4 * further pixel */
|
|
4906 invalue = (inptr[inptr_offset++] & 0xFF) * 3;
|
|
4907 outptr[outptr_offset++] = cast(byte) ((invalue + (inptr[inptr_offset-2] & 0xFF) + 1) >> 2);
|
|
4908 outptr[outptr_offset++] = cast(byte) ((invalue + (inptr[inptr_offset] & 0xFF) + 2) >> 2);
|
|
4909 }
|
|
4910
|
|
4911 /* Special case for last column */
|
|
4912 invalue = (inptr[inptr_offset] & 0xFF);
|
|
4913 outptr[outptr_offset++] = cast(byte) ((invalue * 3 + (inptr[inptr_offset-1] & 0xFF) + 1) >> 2);
|
|
4914 outptr[outptr_offset++] = cast(byte) invalue;
|
|
4915 }
|
|
4916 }
|
|
4917
|
|
4918 static void h2v2_fancy_upsample (jpeg_decompress_struct cinfo, jpeg_component_info compptr,
|
|
4919 byte[][] input_data, int input_data_offset, byte[][][] output_data_ptr, int[] output_data_offset, int output_data_index)
|
|
4920 {
|
|
4921 byte[][] output_data = output_data_ptr[output_data_index];
|
|
4922 byte[] inptr0, inptr1, outptr;
|
|
4923 int thiscolsum, lastcolsum, nextcolsum;
|
|
4924 int colctr;
|
|
4925 int inrow, outrow, v;
|
|
4926 output_data_offset[output_data_index] = 0;
|
|
4927
|
|
4928 inrow = outrow = 0;
|
|
4929 while (outrow < cinfo.max_v_samp_factor) {
|
|
4930 for (v = 0; v < 2; v++) {
|
|
4931 /* inptr0 points to nearest input row, inptr1 points to next nearest */
|
|
4932 inptr0 = input_data[inrow+input_data_offset];
|
|
4933 if (v is 0) /* next nearest is row above */
|
|
4934 inptr1 = input_data[inrow-1+input_data_offset];
|
|
4935 else /* next nearest is row below */
|
|
4936 inptr1 = input_data[inrow+1+input_data_offset];
|
|
4937 outptr = output_data[outrow++];
|
|
4938
|
|
4939 int inptr0_offset = 0, inptr1_offset = 0, outptr_offset = 0;
|
|
4940
|
|
4941 /* Special case for first column */
|
|
4942 thiscolsum = (inptr0[inptr0_offset++] & 0xFF) * 3 + (inptr1[inptr1_offset++] & 0xFF);
|
|
4943 nextcolsum = (inptr0[inptr0_offset++] & 0xFF) * 3 + (inptr1[inptr1_offset++] & 0xFF);
|
|
4944 outptr[outptr_offset++] = cast(byte) ((thiscolsum * 4 + 8) >> 4);
|
|
4945 outptr[outptr_offset++] = cast(byte) ((thiscolsum * 3 + nextcolsum + 7) >> 4);
|
|
4946 lastcolsum = thiscolsum; thiscolsum = nextcolsum;
|
|
4947
|
|
4948 for (colctr = compptr.downsampled_width - 2; colctr > 0; colctr--) {
|
|
4949 /* General case: 3/4 * nearer pixel + 1/4 * further pixel in each */
|
|
4950 /* dimension, thus 9/16, 3/16, 3/16, 1/16 overall */
|
|
4951 nextcolsum = (inptr0[inptr0_offset++] & 0xFF) * 3 + (inptr1[inptr1_offset++] & 0xFF);
|
|
4952 outptr[outptr_offset++] = cast(byte) ((thiscolsum * 3 + lastcolsum + 8) >> 4);
|
|
4953 outptr[outptr_offset++] = cast(byte) ((thiscolsum * 3 + nextcolsum + 7) >> 4);
|
|
4954 lastcolsum = thiscolsum; thiscolsum = nextcolsum;
|
|
4955 }
|
|
4956
|
|
4957 /* Special case for last column */
|
|
4958 outptr[outptr_offset++] = cast(byte) ((thiscolsum * 3 + lastcolsum + 8) >> 4);
|
|
4959 outptr[outptr_offset++] = cast(byte) ((thiscolsum * 4 + 7) >> 4);
|
|
4960 }
|
|
4961 inrow++;
|
|
4962 }
|
|
4963 }
|
|
4964
|
|
4965 static void int_upsample (jpeg_decompress_struct cinfo, jpeg_component_info compptr,
|
|
4966 byte[][] input_data, int input_data_offset, byte[][][] output_data_ptr, int[] output_data_offset, int output_data_index)
|
|
4967 {
|
|
4968 jpeg_upsampler upsample = cinfo.upsample;
|
|
4969 byte[][] output_data = output_data_ptr[output_data_index];
|
|
4970 byte[] inptr, outptr;
|
|
4971 byte invalue;
|
|
4972 int h;
|
|
4973 int outend;
|
|
4974 int h_expand, v_expand;
|
|
4975 int inrow, outrow;
|
|
4976 output_data_offset[output_data_index] = 0;
|
|
4977
|
|
4978 h_expand = upsample.h_expand[compptr.component_index];
|
|
4979 v_expand = upsample.v_expand[compptr.component_index];
|
|
4980
|
|
4981 inrow = outrow = 0;
|
|
4982 while (outrow < cinfo.max_v_samp_factor) {
|
|
4983 /* Generate one output row with proper horizontal expansion */
|
|
4984 inptr = input_data[inrow+input_data_offset];
|
|
4985 int inptr_offset = 0;
|
|
4986 outptr = output_data[outrow];
|
|
4987 int outptr_offset = 0;
|
|
4988 outend = outptr_offset + cinfo.output_width;
|
|
4989 while (outptr_offset < outend) {
|
|
4990 invalue = inptr[inptr_offset++]; /* don't need GETJSAMPLE() here */
|
|
4991 for (h = h_expand; h > 0; h--) {
|
|
4992 outptr[outptr_offset++] = invalue;
|
|
4993 }
|
|
4994 }
|
|
4995 /* Generate any additional output rows by duplicating the first one */
|
|
4996 if (v_expand > 1) {
|
|
4997 jcopy_sample_rows(output_data, outrow, output_data, outrow+1, v_expand-1, cinfo.output_width);
|
|
4998 }
|
|
4999 inrow++;
|
|
5000 outrow += v_expand;
|
|
5001 }
|
|
5002 }
|
|
5003
|
|
5004 static void null_convert (jpeg_decompress_struct cinfo,
|
|
5005 byte[][][] input_buf, int[] input_buf_offset, int input_row,
|
|
5006 byte[][] output_buf, int output_buf_offset, int num_rows)
|
|
5007 {
|
|
5008 byte[] inptr, outptr;
|
|
5009 int count;
|
|
5010 int num_components = cinfo.num_components;
|
|
5011 int num_cols = cinfo.output_width;
|
|
5012 int ci;
|
|
5013
|
|
5014 while (--num_rows >= 0) {
|
|
5015 for (ci = 0; ci < num_components; ci++) {
|
|
5016 inptr = input_buf[ci][input_row+input_buf_offset[0]];
|
|
5017 outptr = output_buf[output_buf_offset];
|
|
5018 /* BGR instead of RGB */
|
|
5019 int offset = 0;
|
|
5020 switch (ci) {
|
|
5021 case 2: offset = RGB_BLUE; break;
|
|
5022 case 1: offset = RGB_GREEN; break;
|
|
5023 case 0: offset = RGB_RED; break;
|
|
5024 default:
|
|
5025 }
|
|
5026 int outptr_offset = offset, inptr_offset = 0;
|
|
5027 for (count = num_cols; count > 0; count--) {
|
|
5028 outptr[outptr_offset] = inptr[inptr_offset++]; /* needn't bother with GETJSAMPLE() here */
|
|
5029 outptr_offset += num_components;
|
|
5030 }
|
|
5031 }
|
|
5032 input_row++;
|
|
5033 output_buf_offset++;
|
|
5034 }
|
|
5035 }
|
|
5036
|
|
5037 static void grayscale_convert (jpeg_decompress_struct cinfo,
|
|
5038 byte[][][] input_buf, int[] input_buf_offset, int input_row,
|
|
5039 byte[][] output_buf, int output_buf_offset, int num_rows)
|
|
5040 {
|
|
5041 jcopy_sample_rows(input_buf[0], input_row+input_buf_offset[0], output_buf, output_buf_offset,
|
|
5042 num_rows, cinfo.output_width);
|
|
5043 }
|
|
5044
|
|
5045 static void gray_rgb_convert (jpeg_decompress_struct cinfo,
|
|
5046 byte[][][] input_buf, int[] input_buf_offset, int input_row,
|
|
5047 byte[][] output_buf, int output_buf_offset, int num_rows)
|
|
5048 {
|
|
5049 byte[] inptr, outptr;
|
|
5050 int col;
|
|
5051 int num_cols = cinfo.output_width;
|
|
5052
|
|
5053 while (--num_rows >= 0) {
|
|
5054 inptr = input_buf[0][input_row+++input_buf_offset[0]];
|
|
5055 outptr = output_buf[output_buf_offset++];
|
|
5056 int outptr_offset = 0;
|
|
5057 for (col = 0; col < num_cols; col++) {
|
|
5058 /* We can dispense with GETJSAMPLE() here */
|
|
5059 outptr[RGB_RED+outptr_offset] = outptr[RGB_GREEN+outptr_offset] = outptr[RGB_BLUE+outptr_offset] = inptr[col];
|
|
5060 outptr_offset += RGB_PIXELSIZE;
|
|
5061 }
|
|
5062 }
|
|
5063 }
|
|
5064
|
|
5065 static void ycc_rgb_convert (jpeg_decompress_struct cinfo,
|
|
5066 byte[][][] input_buf, int[] input_buf_offset, int input_row,
|
|
5067 byte[][] output_buf, int output_buf_offset, int num_rows)
|
|
5068 {
|
|
5069 jpeg_color_deconverter cconvert = cinfo.cconvert;
|
|
5070 int y, cb, cr;
|
|
5071 byte[] outptr;
|
|
5072 byte[] inptr0, inptr1, inptr2;
|
|
5073 int col;
|
|
5074 int num_cols = cinfo.output_width;
|
|
5075 /* copy these pointers into registers if possible */
|
|
5076 byte[] range_limit = cinfo.sample_range_limit;
|
|
5077 int range_limit_offset = cinfo.sample_range_limit_offset;
|
|
5078 int[] Crrtab = cconvert.Cr_r_tab;
|
|
5079 int[] Cbbtab = cconvert.Cb_b_tab;
|
|
5080 int[] Crgtab = cconvert.Cr_g_tab;
|
|
5081 int[] Cbgtab = cconvert.Cb_g_tab;
|
|
5082 // SHIFT_TEMPS
|
|
5083
|
|
5084 while (--num_rows >= 0) {
|
|
5085 inptr0 = input_buf[0][input_row+input_buf_offset[0]];
|
|
5086 inptr1 = input_buf[1][input_row+input_buf_offset[1]];
|
|
5087 inptr2 = input_buf[2][input_row+input_buf_offset[2]];
|
|
5088 input_row++;
|
|
5089 outptr = output_buf[output_buf_offset++];
|
|
5090 int outptr_offset = 0;
|
|
5091 for (col = 0; col < num_cols; col++) {
|
|
5092 y = (inptr0[col] & 0xFF);
|
|
5093 cb = (inptr1[col] & 0xFF);
|
|
5094 cr = (inptr2[col] & 0xFF);
|
|
5095 /* Range-limiting is essential due to noise introduced by DCT losses. */
|
|
5096 outptr[outptr_offset + RGB_RED] = range_limit[y + Crrtab[cr] + range_limit_offset];
|
|
5097 outptr[outptr_offset + RGB_GREEN] = range_limit[y + ((Cbgtab[cb] + Crgtab[cr]>>SCALEBITS)) + range_limit_offset];
|
|
5098 outptr[outptr_offset + RGB_BLUE] = range_limit[y + Cbbtab[cb] + range_limit_offset];
|
|
5099 outptr_offset += RGB_PIXELSIZE;
|
|
5100 }
|
|
5101 }
|
|
5102 }
|
|
5103
|
|
5104 static bool process_APPn(int n, jpeg_decompress_struct cinfo) {
|
|
5105 if (n is 0 || n is 14) {
|
|
5106 return get_interesting_appn(cinfo);
|
|
5107 }
|
|
5108 return skip_variable(cinfo);
|
|
5109 }
|
|
5110
|
|
5111 static bool process_COM(jpeg_decompress_struct cinfo) {
|
|
5112 return skip_variable(cinfo);
|
|
5113 }
|
|
5114
|
|
5115 static void skip_input_data (jpeg_decompress_struct cinfo, int num_bytes) {
|
|
5116 if (num_bytes > 0) {
|
|
5117 while (num_bytes > cinfo.bytes_in_buffer - cinfo.bytes_offset) {
|
|
5118 num_bytes -= cinfo.bytes_in_buffer - cinfo.bytes_offset;
|
|
5119 if (!fill_input_buffer(cinfo)) error();
|
|
5120 /* note we assume that fill_input_buffer will never return FALSE,
|
|
5121 * so suspension need not be handled.
|
|
5122 */
|
|
5123 }
|
|
5124 cinfo.bytes_offset += num_bytes;
|
|
5125 }
|
|
5126 }
|
|
5127
|
|
5128 static bool skip_variable (jpeg_decompress_struct cinfo)
|
|
5129 /* Skip over an unknown or uninteresting variable-length marker */
|
|
5130 {
|
|
5131 int length;
|
|
5132
|
|
5133 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
5134 length = (cinfo.buffer[cinfo.bytes_offset++] & 0xFF) << 8;
|
|
5135 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
5136 length |= cinfo.buffer[cinfo.bytes_offset++] & 0xFF;
|
|
5137
|
|
5138 length -= 2;
|
|
5139
|
|
5140 // TRACEMS2(cinfo, 1, JTRC_MISC_MARKER, cinfo.unread_marker, cast(int) length);
|
|
5141
|
|
5142 if (length > 0) {
|
|
5143 skip_input_data (cinfo, length);
|
|
5144 }
|
|
5145
|
|
5146 return true;
|
|
5147 }
|
|
5148
|
|
5149 static bool get_interesting_appn (jpeg_decompress_struct cinfo)
|
|
5150 /* Process an APP0 or APP14 marker without saving it */
|
|
5151 {
|
|
5152 int length;
|
|
5153 byte[] b = new byte[APPN_DATA_LEN];
|
|
5154 int i, numtoread;
|
|
5155
|
|
5156 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
5157 length = (cinfo.buffer[cinfo.bytes_offset++] & 0xFF) << 8;
|
|
5158 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
5159 length |= cinfo.buffer[cinfo.bytes_offset++] & 0xFF;
|
|
5160 length -= 2;
|
|
5161
|
|
5162 /* get the interesting part of the marker data */
|
|
5163 if (length >= APPN_DATA_LEN)
|
|
5164 numtoread = APPN_DATA_LEN;
|
|
5165 else if (length > 0)
|
|
5166 numtoread = length;
|
|
5167 else
|
|
5168 numtoread = 0;
|
|
5169 for (i = 0; i < numtoread; i++) {
|
|
5170 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
5171 b[i] = cinfo.buffer[cinfo.bytes_offset++];
|
|
5172 }
|
|
5173 length -= numtoread;
|
|
5174
|
|
5175 /* process it */
|
|
5176 switch (cinfo.unread_marker) {
|
|
5177 case M_APP0:
|
|
5178 examine_app0(cinfo, b, numtoread, length);
|
|
5179 break;
|
|
5180 case M_APP14:
|
|
5181 examine_app14(cinfo, b, numtoread, length);
|
|
5182 break;
|
|
5183 default:
|
|
5184 /* can't get here unless jpeg_save_markers chooses wrong processor */
|
|
5185 error();
|
|
5186 // ERREXIT1(cinfo, JERR_UNKNOWN_MARKER, cinfo.unread_marker);
|
|
5187 break;
|
|
5188 }
|
|
5189
|
|
5190 /* skip any remaining data -- could be lots */
|
|
5191 if (length > 0)
|
|
5192 skip_input_data (cinfo, length);
|
|
5193
|
|
5194 return true;
|
|
5195 }
|
|
5196
|
|
5197 static void examine_app0 (jpeg_decompress_struct cinfo, byte[] data, int datalen, int remaining)
|
|
5198 /* Examine first few bytes from an APP0.
|
|
5199 * Take appropriate action if it is a JFIF marker.
|
|
5200 * datalen is # of bytes at data[], remaining is length of rest of marker data.
|
|
5201 */
|
|
5202 {
|
|
5203 int totallen = datalen + remaining;
|
|
5204
|
|
5205 if (datalen >= APP0_DATA_LEN &&
|
|
5206 (data[0] & 0xFF) is 0x4A &&
|
|
5207 (data[1] & 0xFF) is 0x46 &&
|
|
5208 (data[2] & 0xFF) is 0x49 &&
|
|
5209 (data[3] & 0xFF) is 0x46 &&
|
|
5210 (data[4] & 0xFF) is 0)
|
|
5211 {
|
|
5212 /* Found JFIF APP0 marker: save info */
|
|
5213 cinfo.saw_JFIF_marker = true;
|
|
5214 cinfo.JFIF_major_version = (data[5]);
|
|
5215 cinfo.JFIF_minor_version = cast(byte)(data[6] & 0xFF);
|
|
5216 cinfo.density_unit = cast(byte)(data[7] & 0xFF);
|
|
5217 cinfo.X_density = cast(short)(((data[8] & 0xFF) << 8) + (data[9] & 0xFF));
|
|
5218 cinfo.Y_density = cast(short)(((data[10] & 0xFF) << 8) + (data[11] & 0xFF));
|
|
5219 /* Check version.
|
|
5220 * Major version must be 1, anything else signals an incompatible change.
|
|
5221 * (We used to treat this as an error, but now it's a nonfatal warning,
|
|
5222 * because some bozo at Hijaak couldn't read the spec.)
|
|
5223 * Minor version should be 0..2, but process anyway if newer.
|
|
5224 */
|
|
5225 if (cinfo.JFIF_major_version !is 1) {
|
|
5226 // WARNMS2(cinfo, JWRN_JFIF_MAJOR,
|
|
5227 // cinfo.JFIF_major_version, cinfo.JFIF_minor_version);
|
|
5228 }
|
|
5229 /* Generate trace messages */
|
|
5230 // TRACEMS5(cinfo, 1, JTRC_JFIF,
|
|
5231 // cinfo.JFIF_major_version, cinfo.JFIF_minor_version,
|
|
5232 // cinfo.X_density, cinfo.Y_density, cinfo.density_unit);
|
|
5233 /* Validate thumbnail dimensions and issue appropriate messages */
|
|
5234 if (((data[12] & 0xFF) | (data[13]) & 0xFF) !is 0) {
|
|
5235 // TRACEMS2(cinfo, 1, JTRC_JFIF_THUMBNAIL,
|
|
5236 // GETJOCTET(data[12]), GETJOCTET(data[13]));
|
|
5237 }
|
|
5238 totallen -= APP0_DATA_LEN;
|
|
5239 if (totallen !is ((data[12] & 0xFF) * (data[13] & 0xFF) * 3)) {
|
|
5240 // TRACEMS1(cinfo, 1, JTRC_JFIF_BADTHUMBNAILSIZE, cast(int) totallen);
|
|
5241 }
|
|
5242 } else if (datalen >= 6 &&
|
|
5243 (data[0] & 0xFF) is 0x4A &&
|
|
5244 (data[1] & 0xFF) is 0x46 &&
|
|
5245 (data[2] & 0xFF) is 0x58 &&
|
|
5246 (data[3] & 0xFF) is 0x58 &&
|
|
5247 (data[4] & 0xFF) is 0)
|
|
5248 {
|
|
5249 /* Found JFIF "JFXX" extension APP0 marker */
|
|
5250 /* The library doesn't actually do anything with these,
|
|
5251 * but we try to produce a helpful trace message.
|
|
5252 */
|
|
5253 switch ((data[5]) & 0xFF) {
|
|
5254 case 0x10:
|
|
5255 // TRACEMS1(cinfo, 1, JTRC_THUMB_JPEG, cast(int) totallen);
|
|
5256 break;
|
|
5257 case 0x11:
|
|
5258 // TRACEMS1(cinfo, 1, JTRC_THUMB_PALETTE, cast(int) totallen);
|
|
5259 break;
|
|
5260 case 0x13:
|
|
5261 // TRACEMS1(cinfo, 1, JTRC_THUMB_RGB, cast(int) totallen);
|
|
5262 break;
|
|
5263 default:
|
|
5264 // TRACEMS2(cinfo, 1, JTRC_JFIF_EXTENSION, GETJOCTET(data[5]), cast(int) totallen);
|
|
5265 break;
|
|
5266 }
|
|
5267 } else {
|
|
5268 /* Start of APP0 does not match "JFIF" or "JFXX", or too short */
|
|
5269 // TRACEMS1(cinfo, 1, JTRC_APP0, cast(int) totallen);
|
|
5270 }
|
|
5271 }
|
|
5272
|
|
5273 static void examine_app14 (jpeg_decompress_struct cinfo, byte[] data, int datalen, int remaining)
|
|
5274 /* Examine first few bytes from an APP14.
|
|
5275 * Take appropriate action if it is an Adobe marker.
|
|
5276 * datalen is # of bytes at data[], remaining is length of rest of marker data.
|
|
5277 */
|
|
5278 {
|
|
5279 int /*version, flags0, flags1, */transform;
|
|
5280
|
|
5281 if (datalen >= APP14_DATA_LEN &&
|
|
5282 (data[0] & 0xFF) is 0x41 &&
|
|
5283 (data[1] & 0xFF) is 0x64 &&
|
|
5284 (data[2] & 0xFF) is 0x6F &&
|
|
5285 (data[3] & 0xFF) is 0x62 &&
|
|
5286 (data[4] & 0xFF) is 0x65)
|
|
5287 {
|
|
5288 /* Found Adobe APP14 marker */
|
|
5289 // version = ((data[5] & 0xFF) << 8) + (data[6] & 0xFF);
|
|
5290 // flags0 = ((data[7] & 0xFF) << 8) + (data[8] & 0xFF);
|
|
5291 // flags1 = ((data[9] & 0xFF) << 8) + (data[10] & 0xFF);
|
|
5292 transform = (data[11] & 0xFF);
|
|
5293 // TRACEMS4(cinfo, 1, JTRC_ADOBE, version, flags0, flags1, transform);
|
|
5294 cinfo.saw_Adobe_marker = true;
|
|
5295 cinfo.Adobe_transform = cast(byte) transform;
|
|
5296 } else {
|
|
5297 /* Start of APP14 does not match "Adobe", or too short */
|
|
5298 // TRACEMS1(cinfo, 1, JTRC_APP14, cast(int) (datalen + remaining));
|
|
5299 }
|
|
5300 }
|
|
5301
|
|
5302 static bool get_soi (jpeg_decompress_struct cinfo) /* Process an SOI marker */ {
|
|
5303 int i;
|
|
5304
|
|
5305 // TRACEMS(cinfo, 1, JTRC_SOI);
|
|
5306
|
|
5307 if (cinfo.marker.saw_SOI)
|
|
5308 error();
|
|
5309 // ERREXIT(cinfo, JERR_SOI_DUPLICATE);
|
|
5310
|
|
5311 /* Reset all parameters that are defined to be reset by SOI */
|
|
5312
|
|
5313 for (i = 0; i < NUM_ARITH_TBLS; i++) {
|
|
5314 cinfo.arith_dc_L[i] = 0;
|
|
5315 cinfo.arith_dc_U[i] = 1;
|
|
5316 cinfo.arith_ac_K[i] = 5;
|
|
5317 }
|
|
5318 cinfo.restart_interval = 0;
|
|
5319
|
|
5320 /* Set initial assumptions for colorspace etc */
|
|
5321
|
|
5322 cinfo.jpeg_color_space = JCS_UNKNOWN;
|
|
5323 cinfo.CCIR601_sampling = false; /* Assume non-CCIR sampling??? */
|
|
5324
|
|
5325 cinfo.saw_JFIF_marker = false;
|
|
5326 cinfo.JFIF_major_version = 1; /* set default JFIF APP0 values */
|
|
5327 cinfo.JFIF_minor_version = 1;
|
|
5328 cinfo.density_unit = 0;
|
|
5329 cinfo.X_density = 1;
|
|
5330 cinfo.Y_density = 1;
|
|
5331 cinfo.saw_Adobe_marker = false;
|
|
5332 cinfo.Adobe_transform = 0;
|
|
5333
|
|
5334 cinfo.marker.saw_SOI = true;
|
|
5335
|
|
5336 return true;
|
|
5337 }
|
|
5338
|
|
5339 static void jinit_input_controller (jpeg_decompress_struct cinfo)
|
|
5340 {
|
|
5341 /* Initialize state: can't use reset_input_controller since we don't
|
|
5342 * want to try to reset other modules yet.
|
|
5343 */
|
|
5344 jpeg_input_controller inputctl = cinfo.inputctl = new jpeg_input_controller();
|
|
5345 inputctl.has_multiple_scans = false; /* "unknown" would be better */
|
|
5346 inputctl.eoi_reached = false;
|
|
5347 inputctl.inheaders = true;
|
|
5348 }
|
|
5349
|
|
5350 static void reset_marker_reader (jpeg_decompress_struct cinfo) {
|
|
5351 jpeg_marker_reader marker = cinfo.marker;
|
|
5352
|
|
5353 cinfo.comp_info = null; /* until allocated by get_sof */
|
|
5354 cinfo.input_scan_number = 0; /* no SOS seen yet */
|
|
5355 cinfo.unread_marker = 0; /* no pending marker */
|
|
5356 marker.saw_SOI = false; /* set internal state too */
|
|
5357 marker.saw_SOF = false;
|
|
5358 marker.discarded_bytes = 0;
|
|
5359 // marker.cur_marker = null;
|
|
5360 }
|
|
5361
|
|
5362 static void reset_input_controller (jpeg_decompress_struct cinfo) {
|
|
5363 jpeg_input_controller inputctl = cinfo.inputctl;
|
|
5364
|
|
5365 inputctl.has_multiple_scans = false; /* "unknown" would be better */
|
|
5366 inputctl.eoi_reached = false;
|
|
5367 inputctl.inheaders = true;
|
|
5368 /* Reset other modules */
|
|
5369 reset_marker_reader (cinfo);
|
|
5370 /* Reset progression state -- would be cleaner if entropy decoder did this */
|
|
5371 cinfo.coef_bits = null;
|
|
5372 }
|
|
5373
|
|
5374 static void finish_output_pass (jpeg_decompress_struct cinfo) {
|
|
5375 jpeg_decomp_master master = cinfo.master;
|
|
5376
|
|
5377 if (cinfo.quantize_colors) {
|
|
5378 error(SWT.ERROR_NOT_IMPLEMENTED);
|
|
5379 // (*cinfo.cquantize.finish_pass) (cinfo);
|
|
5380 }
|
|
5381 master.pass_number++;
|
|
5382 }
|
|
5383
|
|
5384 static void jpeg_destroy (jpeg_decompress_struct cinfo) {
|
|
5385 /* We need only tell the memory manager to release everything. */
|
|
5386 /* NB: mem pointer is NULL if memory mgr failed to initialize. */
|
|
5387 // if (cinfo.mem !is NULL)
|
|
5388 // (*cinfo.mem.self_destruct) (cinfo);
|
|
5389 // cinfo.mem = NULL; /* be safe if jpeg_destroy is called twice */
|
|
5390 cinfo.global_state = 0; /* mark it destroyed */
|
|
5391 }
|
|
5392
|
|
5393 static void jpeg_destroy_decompress (jpeg_decompress_struct cinfo) {
|
|
5394 jpeg_destroy(cinfo); /* use common routine */
|
|
5395 }
|
|
5396
|
|
5397 static bool jpeg_input_complete (jpeg_decompress_struct cinfo) {
|
|
5398 /* Check for valid jpeg object */
|
|
5399 if (cinfo.global_state < DSTATE_START || cinfo.global_state > DSTATE_STOPPING)
|
|
5400 error();
|
|
5401 // ERREXIT1(cinfo, JERR_BAD_STATE, cinfo.global_state);
|
|
5402 return cinfo.inputctl.eoi_reached;
|
|
5403 }
|
|
5404
|
|
5405 static bool jpeg_start_output (jpeg_decompress_struct cinfo, int scan_number) {
|
|
5406 if (cinfo.global_state !is DSTATE_BUFIMAGE && cinfo.global_state !is DSTATE_PRESCAN)
|
|
5407 error();
|
|
5408 // ERREXIT1(cinfo, JERR_BAD_STATE, cinfo.global_state);
|
|
5409 /* Limit scan number to valid range */
|
|
5410 if (scan_number <= 0)
|
|
5411 scan_number = 1;
|
|
5412 if (cinfo.inputctl.eoi_reached && scan_number > cinfo.input_scan_number)
|
|
5413 scan_number = cinfo.input_scan_number;
|
|
5414 cinfo.output_scan_number = scan_number;
|
|
5415 /* Perform any dummy output passes, and set up for the real pass */
|
|
5416 return output_pass_setup(cinfo);
|
|
5417 }
|
|
5418
|
|
5419 static bool jpeg_finish_output (jpeg_decompress_struct cinfo) {
|
|
5420 if ((cinfo.global_state is DSTATE_SCANNING || cinfo.global_state is DSTATE_RAW_OK) && cinfo.buffered_image) {
|
|
5421 /* Terminate this pass. */
|
|
5422 /* We do not require the whole pass to have been completed. */
|
|
5423 finish_output_pass (cinfo);
|
|
5424 cinfo.global_state = DSTATE_BUFPOST;
|
|
5425 } else if (cinfo.global_state !is DSTATE_BUFPOST) {
|
|
5426 /* BUFPOST = repeat call after a suspension, anything else is error */
|
|
5427 error();
|
|
5428 // ERREXIT1(cinfo, JERR_BAD_STATE, cinfo.global_state);
|
|
5429 }
|
|
5430 /* Read markers looking for SOS or EOI */
|
|
5431 while (cinfo.input_scan_number <= cinfo.output_scan_number && !cinfo.inputctl.eoi_reached) {
|
|
5432 if (consume_input (cinfo) is JPEG_SUSPENDED)
|
|
5433 return false; /* Suspend, come back later */
|
|
5434 }
|
|
5435 cinfo.global_state = DSTATE_BUFIMAGE;
|
|
5436 return true;
|
|
5437 }
|
|
5438
|
|
5439 static bool jpeg_finish_decompress (jpeg_decompress_struct cinfo) {
|
|
5440 if ((cinfo.global_state is DSTATE_SCANNING || cinfo.global_state is DSTATE_RAW_OK) && ! cinfo.buffered_image) {
|
|
5441 /* Terminate final pass of non-buffered mode */
|
|
5442 if (cinfo.output_scanline < cinfo.output_height)
|
|
5443 error();
|
|
5444 // ERREXIT(cinfo, JERR_TOO_LITTLE_DATA);
|
|
5445 finish_output_pass (cinfo);
|
|
5446 cinfo.global_state = DSTATE_STOPPING;
|
|
5447 } else if (cinfo.global_state is DSTATE_BUFIMAGE) {
|
|
5448 /* Finishing after a buffered-image operation */
|
|
5449 cinfo.global_state = DSTATE_STOPPING;
|
|
5450 } else if (cinfo.global_state !is DSTATE_STOPPING) {
|
|
5451 /* STOPPING = repeat call after a suspension, anything else is error */
|
|
5452 error();
|
|
5453 // ERREXIT1(cinfo, JERR_BAD_STATE, cinfo.global_state);
|
|
5454 }
|
|
5455 /* Read until EOI */
|
|
5456 while (! cinfo.inputctl.eoi_reached) {
|
|
5457 if (consume_input (cinfo) is JPEG_SUSPENDED)
|
|
5458 return false; /* Suspend, come back later */
|
|
5459 }
|
|
5460 /* Do final cleanup */
|
|
5461 // (*cinfo.src.term_source) (cinfo);
|
|
5462 /* We can use jpeg_abort to release memory and reset global_state */
|
|
5463 jpeg_abort(cinfo);
|
|
5464 return true;
|
|
5465 }
|
|
5466
|
|
5467
|
|
5468 static int jpeg_read_header (jpeg_decompress_struct cinfo, bool require_image) {
|
|
5469 int retcode;
|
|
5470
|
|
5471 if (cinfo.global_state !is DSTATE_START && cinfo.global_state !is DSTATE_INHEADER)
|
|
5472 error();
|
|
5473 // ERREXIT1(cinfo, JERR_BAD_STATE, cinfo.global_state);
|
|
5474
|
|
5475 retcode = jpeg_consume_input(cinfo);
|
|
5476
|
|
5477 switch (retcode) {
|
|
5478 case JPEG_REACHED_SOS:
|
|
5479 retcode = JPEG_HEADER_OK;
|
|
5480 break;
|
|
5481 case JPEG_REACHED_EOI:
|
|
5482 if (require_image) /* Complain if application wanted an image */
|
|
5483 error();
|
|
5484 // ERREXIT(cinfo, JERR_NO_IMAGE);
|
|
5485 /* Reset to start state; it would be safer to require the application to
|
|
5486 * call jpeg_abort, but we can't change it now for compatibility reasons.
|
|
5487 * A side effect is to free any temporary memory (there shouldn't be any).
|
|
5488 */
|
|
5489 jpeg_abort(cinfo); /* sets state = DSTATE_START */
|
|
5490 retcode = JPEG_HEADER_TABLES_ONLY;
|
|
5491 break;
|
|
5492 case JPEG_SUSPENDED:
|
|
5493 /* no work */
|
|
5494 break;
|
|
5495 default:
|
|
5496 }
|
|
5497
|
|
5498 return retcode;
|
|
5499 }
|
|
5500
|
|
5501 static int dummy_consume_data (jpeg_decompress_struct cinfo) {
|
|
5502 return JPEG_SUSPENDED; /* Always indicate nothing was done */
|
|
5503 }
|
|
5504
|
|
5505 static int consume_data (jpeg_decompress_struct cinfo) {
|
|
5506 jpeg_d_coef_controller coef = cinfo.coef;
|
|
5507 int MCU_col_num; /* index of current MCU within row */
|
|
5508 int blkn, ci, xindex, yindex, yoffset;
|
|
5509 int start_col;
|
|
5510 // short[][][][] buffer = new short[MAX_COMPS_IN_SCAN][][][];
|
|
5511 short[][] buffer_ptr;
|
|
5512 jpeg_component_info compptr;
|
|
5513
|
|
5514 // /* Align the virtual buffers for the components used in this scan. */
|
|
5515 // for (ci = 0; ci < cinfo.comps_in_scan; ci++) {
|
|
5516 // compptr = cinfo.cur_comp_info[ci];
|
|
5517 // buffer[ci] = coef.whole_image[compptr.component_index];
|
|
5518 // /* Note: entropy decoder expects buffer to be zeroed,
|
|
5519 // * but this is handled automatically by the memory manager
|
|
5520 // * because we requested a pre-zeroed array.
|
|
5521 // */
|
|
5522 // }
|
|
5523
|
|
5524 /* Loop to process one whole iMCU row */
|
|
5525 for (yoffset = coef.MCU_vert_offset; yoffset < coef.MCU_rows_per_iMCU_row; yoffset++) {
|
|
5526 for (MCU_col_num = coef.MCU_ctr; MCU_col_num < cinfo.MCUs_per_row; MCU_col_num++) {
|
|
5527 /* Construct list of pointers to DCT blocks belonging to this MCU */
|
|
5528 blkn = 0; /* index of current DCT block within MCU */
|
|
5529 for (ci = 0; ci < cinfo.comps_in_scan; ci++) {
|
|
5530 compptr = cinfo.cur_comp_info[ci];
|
|
5531 start_col = MCU_col_num * compptr.MCU_width;
|
|
5532 for (yindex = 0; yindex < compptr.MCU_height; yindex++) {
|
|
5533 // buffer_ptr = buffer[ci][yindex+yoffset] + start_col;
|
|
5534 buffer_ptr = coef.whole_image[compptr.component_index][yindex+yoffset+cinfo.input_iMCU_row*compptr.v_samp_factor];
|
|
5535 int buffer_ptr_offset = start_col;
|
|
5536 for (xindex = 0; xindex < compptr.MCU_width; xindex++) {
|
|
5537 coef.MCU_buffer[blkn++] = buffer_ptr[buffer_ptr_offset++];
|
|
5538 }
|
|
5539 }
|
|
5540 }
|
|
5541 /* Try to fetch the MCU. */
|
|
5542 if (! cinfo.entropy.decode_mcu (cinfo, coef.MCU_buffer)) {
|
|
5543 /* Suspension forced; update state counters and exit */
|
|
5544 coef.MCU_vert_offset = yoffset;
|
|
5545 coef.MCU_ctr = MCU_col_num;
|
|
5546 return JPEG_SUSPENDED;
|
|
5547 }
|
|
5548 }
|
|
5549 /* Completed an MCU row, but perhaps not an iMCU row */
|
|
5550 coef.MCU_ctr = 0;
|
|
5551 }
|
|
5552 /* Completed the iMCU row, advance counters for next one */
|
|
5553 if (++(cinfo.input_iMCU_row) < cinfo.total_iMCU_rows) {
|
|
5554 coef.start_iMCU_row(cinfo);
|
|
5555 return JPEG_ROW_COMPLETED;
|
|
5556 }
|
|
5557 /* Completed the scan */
|
|
5558 finish_input_pass (cinfo);
|
|
5559 return JPEG_SCAN_COMPLETED;
|
|
5560 }
|
|
5561
|
|
5562 static int consume_input (jpeg_decompress_struct cinfo) {
|
|
5563 switch (cinfo.inputctl.consume_input) {
|
|
5564 case COEF_CONSUME_INPUT:
|
|
5565 switch (cinfo.coef.consume_data) {
|
|
5566 case CONSUME_DATA: return consume_data(cinfo);
|
|
5567 case DUMMY_CONSUME_DATA: return dummy_consume_data(cinfo);
|
|
5568 default: error();
|
|
5569 }
|
|
5570 break;
|
|
5571 case INPUT_CONSUME_INPUT:
|
|
5572 return consume_markers(cinfo);
|
|
5573 default:
|
|
5574 error();
|
|
5575 }
|
|
5576 return 0;
|
|
5577 }
|
|
5578
|
|
5579 static bool fill_input_buffer(jpeg_decompress_struct cinfo) {
|
|
5580 try {
|
|
5581 InputStream inputStream = cinfo.inputStream;
|
|
5582 int nbytes = inputStream.read(cinfo.buffer);
|
|
5583 if (nbytes <= 0) {
|
|
5584 if (cinfo.start_of_file) /* Treat empty input file as fatal error */
|
|
5585 error();
|
|
5586 // ERREXIT(cinfo, JERR_INPUT_EMPTY);
|
|
5587 // WARNMS(cinfo, JWRN_JPEG_EOF);
|
|
5588 /* Insert a fake EOI marker */
|
|
5589 cinfo.buffer[0] = cast(byte)0xFF;
|
|
5590 cinfo.buffer[1] = cast(byte)M_EOI;
|
|
5591 nbytes = 2;
|
|
5592 }
|
|
5593 cinfo.bytes_in_buffer = nbytes;
|
|
5594 cinfo.bytes_offset = 0;
|
|
5595 cinfo.start_of_file = false;
|
|
5596 } catch (IOException e) {
|
|
5597 error(SWT.ERROR_IO);
|
|
5598 return false;
|
|
5599 }
|
|
5600 return true;
|
|
5601 }
|
|
5602
|
|
5603 static bool first_marker (jpeg_decompress_struct cinfo) {
|
|
5604 /* Like next_marker, but used to obtain the initial SOI marker. */
|
|
5605 /* For this marker, we do not allow preceding garbage or fill; otherwise,
|
|
5606 * we might well scan an entire input file before realizing it ain't JPEG.
|
|
5607 * If an application wants to process non-JFIF files, it must seek to the
|
|
5608 * SOI before calling the JPEG library.
|
|
5609 */
|
|
5610 int c, c2;
|
|
5611
|
|
5612 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
5613 c = cinfo.buffer[cinfo.bytes_offset++] & 0xFF;
|
|
5614 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
5615 c2 = cinfo.buffer[cinfo.bytes_offset++] & 0xFF;
|
|
5616 if (c !is 0xFF || c2 !is M_SOI)
|
|
5617 error();
|
|
5618 // ERREXIT2(cinfo, JERR_NO_SOI, c, c2);
|
|
5619
|
|
5620 cinfo.unread_marker = c2;
|
|
5621
|
|
5622 return true;
|
|
5623 }
|
|
5624
|
|
5625 static bool next_marker (jpeg_decompress_struct cinfo) {
|
|
5626 int c;
|
|
5627
|
|
5628 for (;;) {
|
|
5629 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
5630 c = cinfo.buffer[cinfo.bytes_offset++] & 0xFF;
|
|
5631 /* Skip any non-FF bytes.
|
|
5632 * This may look a bit inefficient, but it will not occur in a valid file.
|
|
5633 * We sync after each discarded byte so that a suspending data source
|
|
5634 * can discard the byte from its buffer.
|
|
5635 */
|
|
5636 while (c !is 0xFF) {
|
|
5637 cinfo.marker.discarded_bytes++;
|
|
5638 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
5639 c = cinfo.buffer[cinfo.bytes_offset++] & 0xFF;
|
|
5640 }
|
|
5641 /* This loop swallows any duplicate FF bytes. Extra FFs are legal as
|
|
5642 * pad bytes, so don't count them in discarded_bytes. We assume there
|
|
5643 * will not be so many consecutive FF bytes as to overflow a suspending
|
|
5644 * data source's input buffer.
|
|
5645 */
|
|
5646 do {
|
|
5647 if (cinfo.bytes_offset is cinfo.bytes_in_buffer) fill_input_buffer(cinfo);
|
|
5648 c = cinfo.buffer[cinfo.bytes_offset++] & 0xFF;
|
|
5649 } while (c is 0xFF);
|
|
5650 if (c !is 0)
|
|
5651 break; /* found a valid marker, exit loop */
|
|
5652 /* Reach here if we found a stuffed-zero data sequence (FF/00).
|
|
5653 * Discard it and loop back to try again.
|
|
5654 */
|
|
5655 cinfo.marker.discarded_bytes += 2;
|
|
5656 }
|
|
5657
|
|
5658 if (cinfo.marker.discarded_bytes !is 0) {
|
|
5659 // WARNMS2(cinfo, JWRN_EXTRANEOUS_DATA, cinfo.marker.discarded_bytes, c);
|
|
5660 cinfo.marker.discarded_bytes = 0;
|
|
5661 }
|
|
5662
|
|
5663 cinfo.unread_marker = c;
|
|
5664
|
|
5665 return true;
|
|
5666 }
|
|
5667
|
|
5668 static int read_markers (jpeg_decompress_struct cinfo) {
|
|
5669 /* Outer loop repeats once for each marker. */
|
|
5670 for (;;) {
|
|
5671 /* Collect the marker proper, unless we already did. */
|
|
5672 /* NB: first_marker() enforces the requirement that SOI appear first. */
|
|
5673 if (cinfo.unread_marker is 0) {
|
|
5674 if (! cinfo.marker.saw_SOI) {
|
|
5675 if (! first_marker(cinfo))
|
|
5676 return JPEG_SUSPENDED;
|
|
5677 } else {
|
|
5678 if (! next_marker(cinfo))
|
|
5679 return JPEG_SUSPENDED;
|
|
5680 }
|
|
5681 }
|
|
5682 /* At this point cinfo.unread_marker contains the marker code and the
|
|
5683 * input point is just past the marker proper, but before any parameters.
|
|
5684 * A suspension will cause us to return with this state still true.
|
|
5685 */
|
|
5686 switch (cinfo.unread_marker) {
|
|
5687 case M_SOI:
|
|
5688 if (! get_soi(cinfo))
|
|
5689 return JPEG_SUSPENDED;
|
|
5690 break;
|
|
5691
|
|
5692 case M_SOF0: /* Baseline */
|
|
5693 case M_SOF1: /* Extended sequential, Huffman */
|
|
5694 if (! get_sof(cinfo, false, false))
|
|
5695 return JPEG_SUSPENDED;
|
|
5696 break;
|
|
5697
|
|
5698 case M_SOF2: /* Progressive, Huffman */
|
|
5699 if (! get_sof(cinfo, true, false))
|
|
5700 return JPEG_SUSPENDED;
|
|
5701 break;
|
|
5702
|
|
5703 case M_SOF9: /* Extended sequential, arithmetic */
|
|
5704 if (! get_sof(cinfo, false, true))
|
|
5705 return JPEG_SUSPENDED;
|
|
5706 break;
|
|
5707
|
|
5708 case M_SOF10: /* Progressive, arithmetic */
|
|
5709 if (! get_sof(cinfo, true, true))
|
|
5710 return JPEG_SUSPENDED;
|
|
5711 break;
|
|
5712
|
|
5713 /* Currently unsupported SOFn types */
|
|
5714 case M_SOF3: /* Lossless, Huffman */
|
|
5715 case M_SOF5: /* Differential sequential, Huffman */
|
|
5716 case M_SOF6: /* Differential progressive, Huffman */
|
|
5717 case M_SOF7: /* Differential lossless, Huffman */
|
|
5718 case M_JPG: /* Reserved for JPEG extensions */
|
|
5719 case M_SOF11: /* Lossless, arithmetic */
|
|
5720 case M_SOF13: /* Differential sequential, arithmetic */
|
|
5721 case M_SOF14: /* Differential progressive, arithmetic */
|
|
5722 case M_SOF15: /* Differential lossless, arithmetic */
|
|
5723 error();
|
|
5724 // ERREXIT1(cinfo, JERR_SOF_UNSUPPORTED, cinfo.unread_marker);
|
|
5725 break;
|
|
5726
|
|
5727 case M_SOS:
|
|
5728 if (! get_sos(cinfo))
|
|
5729 return JPEG_SUSPENDED;
|
|
5730 cinfo.unread_marker = 0; /* processed the marker */
|
|
5731 return JPEG_REACHED_SOS;
|
|
5732
|
|
5733 case M_EOI:
|
|
5734 // TRACEMS(cinfo, 1, JTRC_EOI);
|
|
5735 cinfo.unread_marker = 0; /* processed the marker */
|
|
5736 return JPEG_REACHED_EOI;
|
|
5737
|
|
5738 case M_DAC:
|
|
5739 if (! get_dac(cinfo))
|
|
5740 return JPEG_SUSPENDED;
|
|
5741 break;
|
|
5742
|
|
5743 case M_DHT:
|
|
5744 if (! get_dht(cinfo))
|
|
5745 return JPEG_SUSPENDED;
|
|
5746 break;
|
|
5747
|
|
5748 case M_DQT:
|
|
5749 if (! get_dqt(cinfo))
|
|
5750 return JPEG_SUSPENDED;
|
|
5751 break;
|
|
5752
|
|
5753 case M_DRI:
|
|
5754 if (! get_dri(cinfo))
|
|
5755 return JPEG_SUSPENDED;
|
|
5756 break;
|
|
5757
|
|
5758 case M_APP0:
|
|
5759 case M_APP1:
|
|
5760 case M_APP2:
|
|
5761 case M_APP3:
|
|
5762 case M_APP4:
|
|
5763 case M_APP5:
|
|
5764 case M_APP6:
|
|
5765 case M_APP7:
|
|
5766 case M_APP8:
|
|
5767 case M_APP9:
|
|
5768 case M_APP10:
|
|
5769 case M_APP11:
|
|
5770 case M_APP12:
|
|
5771 case M_APP13:
|
|
5772 case M_APP14:
|
|
5773 case M_APP15:
|
|
5774 if (! process_APPn(cinfo.unread_marker - M_APP0, cinfo))
|
|
5775 return JPEG_SUSPENDED;
|
|
5776 break;
|
|
5777
|
|
5778 case M_COM:
|
|
5779 if (! process_COM(cinfo))
|
|
5780 return JPEG_SUSPENDED;
|
|
5781 break;
|
|
5782
|
|
5783 case M_RST0: /* these are all parameterless */
|
|
5784 case M_RST1:
|
|
5785 case M_RST2:
|
|
5786 case M_RST3:
|
|
5787 case M_RST4:
|
|
5788 case M_RST5:
|
|
5789 case M_RST6:
|
|
5790 case M_RST7:
|
|
5791 case M_TEM:
|
|
5792 // TRACEMS1(cinfo, 1, JTRC_PARMLESS_MARKER, cinfo.unread_marker);
|
|
5793 break;
|
|
5794
|
|
5795 case M_DNL: /* Ignore DNL ... perhaps the wrong thing */
|
|
5796 if (! skip_variable(cinfo))
|
|
5797 return JPEG_SUSPENDED;
|
|
5798 break;
|
|
5799
|
|
5800 default: /* must be DHP, EXP, JPGn, or RESn */
|
|
5801 /* For now, we treat the reserved markers as fatal errors since they are
|
|
5802 * likely to be used to signal incompatible JPEG Part 3 extensions.
|
|
5803 * Once the JPEG 3 version-number marker is well defined, this code
|
|
5804 * ought to change!
|
|
5805 */
|
|
5806 error();
|
|
5807 // ERREXIT1(cinfo, JERR_UNKNOWN_MARKER, cinfo.unread_marker);
|
|
5808 break;
|
|
5809 }
|
|
5810 /* Successfully processed marker, so reset state variable */
|
|
5811 cinfo.unread_marker = 0;
|
|
5812 } /* end loop */
|
|
5813 }
|
|
5814
|
|
5815 static long jdiv_round_up (long a, long b)
|
|
5816 /* Compute a/b rounded up to next integer, ie, ceil(a/b) */
|
|
5817 /* Assumes a >= 0, b > 0 */
|
|
5818 {
|
|
5819 return (a + b - 1) / b;
|
|
5820 }
|
|
5821
|
|
5822 static void initial_setup (jpeg_decompress_struct cinfo)
|
|
5823 /* Called once, when first SOS marker is reached */
|
|
5824 {
|
|
5825 int ci;
|
|
5826 jpeg_component_info compptr;
|
|
5827
|
|
5828 /* Make sure image isn't bigger than I can handle */
|
|
5829 if (cinfo.image_height > JPEG_MAX_DIMENSION || cinfo.image_width > JPEG_MAX_DIMENSION)
|
|
5830 error();
|
|
5831 // ERREXIT1(cinfo, JERR_IMAGE_TOO_BIG, (unsigned int) JPEG_MAX_DIMENSION);
|
|
5832
|
|
5833 /* For now, precision must match compiled-in value... */
|
|
5834 if (cinfo.data_precision !is BITS_IN_JSAMPLE)
|
|
5835 error(" [data precision=" ~ to!(String)(cinfo.data_precision) ~ "]");
|
|
5836 // ERREXIT1(cinfo, JERR_BAD_PRECISION, cinfo.data_precision);
|
|
5837
|
|
5838 /* Check that number of components won't exceed internal array sizes */
|
|
5839 if (cinfo.num_components > MAX_COMPONENTS)
|
|
5840 error();
|
|
5841 // ERREXIT2(cinfo, JERR_COMPONENT_COUNT, cinfo.num_components, MAX_COMPONENTS);
|
|
5842
|
|
5843 /* Compute maximum sampling factors; check factor validity */
|
|
5844 cinfo.max_h_samp_factor = 1;
|
|
5845 cinfo.max_v_samp_factor = 1;
|
|
5846 for (ci = 0; ci < cinfo.num_components; ci++) {
|
|
5847 compptr = cinfo.comp_info[ci];
|
|
5848 if (compptr.h_samp_factor<=0 || compptr.h_samp_factor>MAX_SAMP_FACTOR || compptr.v_samp_factor<=0 || compptr.v_samp_factor>MAX_SAMP_FACTOR)
|
|
5849 error();
|
|
5850 // ERREXIT(cinfo, JERR_BAD_SAMPLING);
|
|
5851 cinfo.max_h_samp_factor = Math.max(cinfo.max_h_samp_factor, compptr.h_samp_factor);
|
|
5852 cinfo.max_v_samp_factor = Math.max(cinfo.max_v_samp_factor, compptr.v_samp_factor);
|
|
5853 }
|
|
5854
|
|
5855 /* We initialize DCT_scaled_size and min_DCT_scaled_size to DCTSIZE.
|
|
5856 * In the full decompressor, this will be overridden by jdmaster.c;
|
|
5857 * but in the transcoder, jdmaster.c is not used, so we must do it here.
|
|
5858 */
|
|
5859 cinfo.min_DCT_scaled_size = DCTSIZE;
|
|
5860
|
|
5861 /* Compute dimensions of components */
|
|
5862 for (ci = 0; ci < cinfo.num_components; ci++) {
|
|
5863 compptr = cinfo.comp_info[ci];
|
|
5864 compptr.DCT_scaled_size = DCTSIZE;
|
|
5865 /* Size in DCT blocks */
|
|
5866 compptr.width_in_blocks = cast(int)jdiv_round_up(cast(long) cinfo.image_width * cast(long) compptr.h_samp_factor, (cinfo.max_h_samp_factor * DCTSIZE));
|
|
5867 compptr.height_in_blocks = cast(int)jdiv_round_up(cast(long) cinfo.image_height * cast(long) compptr.v_samp_factor, (cinfo.max_v_samp_factor * DCTSIZE));
|
|
5868 /* downsampled_width and downsampled_height will also be overridden by
|
|
5869 * jdmaster.c if we are doing full decompression. The transcoder library
|
|
5870 * doesn't use these values, but the calling application might.
|
|
5871 */
|
|
5872 /* Size in samples */
|
|
5873 compptr.downsampled_width = cast(int)jdiv_round_up(cast(long) cinfo.image_width * cast(long) compptr.h_samp_factor, cinfo.max_h_samp_factor);
|
|
5874 compptr.downsampled_height = cast(int)jdiv_round_up(cast(long) cinfo.image_height * cast(long) compptr.v_samp_factor, cinfo.max_v_samp_factor);
|
|
5875 /* Mark component needed, until color conversion says otherwise */
|
|
5876 compptr.component_needed = true;
|
|
5877 /* Mark no quantization table yet saved for component */
|
|
5878 compptr.quant_table = null;
|
|
5879 }
|
|
5880
|
|
5881 /* Compute number of fully interleaved MCU rows. */
|
|
5882 cinfo.total_iMCU_rows = cast(int)jdiv_round_up( cinfo.image_height, (cinfo.max_v_samp_factor*DCTSIZE));
|
|
5883
|
|
5884 /* Decide whether file contains multiple scans */
|
|
5885 if (cinfo.comps_in_scan < cinfo.num_components || cinfo.progressive_mode)
|
|
5886 cinfo.inputctl.has_multiple_scans = true;
|
|
5887 else
|
|
5888 cinfo.inputctl.has_multiple_scans = false;
|
|
5889 }
|
|
5890
|
|
5891
|
|
5892 static void per_scan_setup (jpeg_decompress_struct cinfo)
|
|
5893 /* Do computations that are needed before processing a JPEG scan */
|
|
5894 /* cinfo.comps_in_scan and cinfo.cur_comp_info[] were set from SOS marker */
|
|
5895 {
|
|
5896 int ci, mcublks, tmp = 0;
|
|
5897 jpeg_component_info compptr;
|
|
5898
|
|
5899 if (cinfo.comps_in_scan is 1) {
|
|
5900
|
|
5901 /* Noninterleaved (single-component) scan */
|
|
5902 compptr = cinfo.cur_comp_info[0];
|
|
5903
|
|
5904 /* Overall image size in MCUs */
|
|
5905 cinfo.MCUs_per_row = compptr.width_in_blocks;
|
|
5906 cinfo.MCU_rows_in_scan = compptr.height_in_blocks;
|
|
5907
|
|
5908 /* For noninterleaved scan, always one block per MCU */
|
|
5909 compptr.MCU_width = 1;
|
|
5910 compptr.MCU_height = 1;
|
|
5911 compptr.MCU_blocks = 1;
|
|
5912 compptr.MCU_sample_width = compptr.DCT_scaled_size;
|
|
5913 compptr.last_col_width = 1;
|
|
5914 /* For noninterleaved scans, it is convenient to define last_row_height
|
|
5915 * as the number of block rows present in the last iMCU row.
|
|
5916 */
|
|
5917 tmp = (compptr.height_in_blocks % compptr.v_samp_factor);
|
|
5918 if (tmp is 0) tmp = compptr.v_samp_factor;
|
|
5919 compptr.last_row_height = tmp;
|
|
5920
|
|
5921 /* Prepare array describing MCU composition */
|
|
5922 cinfo.blocks_in_MCU = 1;
|
|
5923 cinfo.MCU_membership[0] = 0;
|
|
5924
|
|
5925 } else {
|
|
5926
|
|
5927 /* Interleaved (multi-component) scan */
|
|
5928 if (cinfo.comps_in_scan <= 0 || cinfo.comps_in_scan > MAX_COMPS_IN_SCAN)
|
|
5929 error();
|
|
5930 // ERREXIT2(cinfo, JERR_COMPONENT_COUNT, cinfo.comps_in_scan, MAX_COMPS_IN_SCAN);
|
|
5931
|
|
5932 /* Overall image size in MCUs */
|
|
5933 cinfo.MCUs_per_row = cast(int)jdiv_round_up( cinfo.image_width, (cinfo.max_h_samp_factor*DCTSIZE));
|
|
5934 cinfo.MCU_rows_in_scan = cast(int)jdiv_round_up( cinfo.image_height, (cinfo.max_v_samp_factor*DCTSIZE));
|
|
5935
|
|
5936 cinfo.blocks_in_MCU = 0;
|
|
5937
|
|
5938 for (ci = 0; ci < cinfo.comps_in_scan; ci++) {
|
|
5939 compptr = cinfo.cur_comp_info[ci];
|
|
5940 /* Sampling factors give # of blocks of component in each MCU */
|
|
5941 compptr.MCU_width = compptr.h_samp_factor;
|
|
5942 compptr.MCU_height = compptr.v_samp_factor;
|
|
5943 compptr.MCU_blocks = compptr.MCU_width * compptr.MCU_height;
|
|
5944 compptr.MCU_sample_width = compptr.MCU_width * compptr.DCT_scaled_size;
|
|
5945 /* Figure number of non-dummy blocks in last MCU column & row */
|
|
5946 tmp = (compptr.width_in_blocks % compptr.MCU_width);
|
|
5947 if (tmp is 0) tmp = compptr.MCU_width;
|
|
5948 compptr.last_col_width = tmp;
|
|
5949 tmp = (compptr.height_in_blocks % compptr.MCU_height);
|
|
5950 if (tmp is 0) tmp = compptr.MCU_height;
|
|
5951 compptr.last_row_height = tmp;
|
|
5952 /* Prepare array describing MCU composition */
|
|
5953 mcublks = compptr.MCU_blocks;
|
|
5954 if (cinfo.blocks_in_MCU + mcublks > D_MAX_BLOCKS_IN_MCU)
|
|
5955 error();
|
|
5956 // ERREXIT(cinfo, JERR_BAD_MCU_SIZE);
|
|
5957 while (mcublks-- > 0) {
|
|
5958 cinfo.MCU_membership[cinfo.blocks_in_MCU++] = ci;
|
|
5959 }
|
|
5960 }
|
|
5961
|
|
5962 }
|
|
5963 }
|
|
5964
|
|
5965 static void latch_quant_tables (jpeg_decompress_struct cinfo) {
|
|
5966 int ci, qtblno;
|
|
5967 jpeg_component_info compptr;
|
|
5968 JQUANT_TBL qtbl;
|
|
5969
|
|
5970 for (ci = 0; ci < cinfo.comps_in_scan; ci++) {
|
|
5971 compptr = cinfo.cur_comp_info[ci];
|
|
5972 /* No work if we already saved Q-table for this component */
|
|
5973 if (compptr.quant_table !is null)
|
|
5974 continue;
|
|
5975 /* Make sure specified quantization table is present */
|
|
5976 qtblno = compptr.quant_tbl_no;
|
|
5977 if (qtblno < 0 || qtblno >= NUM_QUANT_TBLS || cinfo.quant_tbl_ptrs[qtblno] is null)
|
|
5978 error();
|
|
5979 // ERREXIT1(cinfo, JERR_NO_QUANT_TABLE, qtblno);
|
|
5980 /* OK, save away the quantization table */
|
|
5981 qtbl = new JQUANT_TBL();
|
|
5982 System.arraycopy(cinfo.quant_tbl_ptrs[qtblno].quantval, 0, qtbl.quantval, 0, qtbl.quantval.length);
|
|
5983 qtbl.sent_table = cinfo.quant_tbl_ptrs[qtblno].sent_table;
|
|
5984 compptr.quant_table = qtbl;
|
|
5985 }
|
|
5986 }
|
|
5987
|
|
5988 static void jpeg_make_d_derived_tbl (jpeg_decompress_struct cinfo, bool isDC, int tblno, d_derived_tbl dtbl) {
|
|
5989 JHUFF_TBL htbl;
|
|
5990 int p, i = 0, l, si, numsymbols;
|
|
5991 int lookbits, ctr;
|
|
5992 byte[] huffsize = new byte[257];
|
|
5993 int[] huffcode = new int[257];
|
|
5994 int code;
|
|
5995
|
|
5996 /* Note that huffsize[] and huffcode[] are filled in code-length order,
|
|
5997 * paralleling the order of the symbols themselves in htbl.huffval[].
|
|
5998 */
|
|
5999
|
|
6000 /* Find the input Huffman table */
|
|
6001 if (tblno < 0 || tblno >= NUM_HUFF_TBLS)
|
|
6002 error();
|
|
6003 // ERREXIT1(cinfo, JERR_NO_HUFF_TABLE, tblno);
|
|
6004 htbl = isDC ? cinfo.dc_huff_tbl_ptrs[tblno] : cinfo.ac_huff_tbl_ptrs[tblno];
|
|
6005 if (htbl is null)
|
|
6006 error();
|
|
6007 // ERREXIT1(cinfo, JERR_NO_HUFF_TABLE, tblno);
|
|
6008
|
|
6009 /* Allocate a workspace if we haven't already done so. */
|
|
6010 dtbl.pub = htbl; /* fill in back link */
|
|
6011
|
|
6012 /* Figure C.1: make table of Huffman code length for each symbol */
|
|
6013
|
|
6014 p = 0;
|
|
6015 for (l = 1; l <= 16; l++) {
|
|
6016 i = htbl.bits[l] & 0xFF;
|
|
6017 if (i < 0 || p + i > 256) /* protect against table overrun */
|
|
6018 error();
|
|
6019 // ERREXIT(cinfo, JERR_BAD_HUFF_TABLE);
|
|
6020 while (i-- !is 0)
|
|
6021 huffsize[p++] = cast(byte) l;
|
|
6022 }
|
|
6023 huffsize[p] = 0;
|
|
6024 numsymbols = p;
|
|
6025
|
|
6026 /* Figure C.2: generate the codes themselves */
|
|
6027 /* We also validate that the counts represent a legal Huffman code tree. */
|
|
6028
|
|
6029 code = 0;
|
|
6030 si = huffsize[0];
|
|
6031 p = 0;
|
|
6032 while ( huffsize[p] !is 0) {
|
|
6033 while (( huffsize[p]) is si) {
|
|
6034 huffcode[p++] = code;
|
|
6035 code++;
|
|
6036 }
|
|
6037 /* code is now 1 more than the last code used for codelength si; but
|
|
6038 * it must still fit in si bits, since no code is allowed to be all ones.
|
|
6039 */
|
|
6040 if (( code) >= (( 1) << si))
|
|
6041 error();
|
|
6042 // ERREXIT(cinfo, JERR_BAD_HUFF_TABLE);
|
|
6043 code <<= 1;
|
|
6044 si++;
|
|
6045 }
|
|
6046
|
|
6047 /* Figure F.15: generate decoding tables for bit-sequential decoding */
|
|
6048
|
|
6049 p = 0;
|
|
6050 for (l = 1; l <= 16; l++) {
|
|
6051 if ((htbl.bits[l] & 0xFF) !is 0) {
|
|
6052 /* valoffset[l] = huffval[] index of 1st symbol of code length l,
|
|
6053 * minus the minimum code of length l
|
|
6054 */
|
|
6055 dtbl.valoffset[l] = p - huffcode[p];
|
|
6056 p += (htbl.bits[l] & 0xFF);
|
|
6057 dtbl.maxcode[l] = huffcode[p-1]; /* maximum code of length l */
|
|
6058 } else {
|
|
6059 dtbl.maxcode[l] = -1; /* -1 if no codes of this length */
|
|
6060 }
|
|
6061 }
|
|
6062 dtbl.maxcode[17] = 0xFFFFF; /* ensures jpeg_huff_decode terminates */
|
|
6063
|
|
6064 /* Compute lookahead tables to speed up decoding.
|
|
6065 * First we set all the table entries to 0, indicating "too long";
|
|
6066 * then we iterate through the Huffman codes that are short enough and
|
|
6067 * fill in all the entries that correspond to bit sequences starting
|
|
6068 * with that code.
|
|
6069 */
|
|
6070
|
|
6071 for (int j = 0; j < dtbl.look_nbits.length; j++) {
|
|
6072 dtbl.look_nbits[j] = 0;
|
|
6073 }
|
|
6074
|
|
6075 p = 0;
|
|
6076 for (l = 1; l <= HUFF_LOOKAHEAD; l++) {
|
|
6077 for (i = 1; i <= (htbl.bits[l] & 0xFF); i++, p++) {
|
|
6078 /* l = current code's length, p = its index in huffcode[] & huffval[]. */
|
|
6079 /* Generate left-justified code followed by all possible bit sequences */
|
|
6080 lookbits = huffcode[p] << (HUFF_LOOKAHEAD-l);
|
|
6081 for (ctr = 1 << (HUFF_LOOKAHEAD-l); ctr > 0; ctr--) {
|
|
6082 dtbl.look_nbits[lookbits] = l;
|
|
6083 dtbl.look_sym[lookbits] = htbl.huffval[p];
|
|
6084 lookbits++;
|
|
6085 }
|
|
6086 }
|
|
6087 }
|
|
6088
|
|
6089 /* Validate symbols as being reasonable.
|
|
6090 * For AC tables, we make no check, but accept all byte values 0..255.
|
|
6091 * For DC tables, we require the symbols to be in range 0..15.
|
|
6092 * (Tighter bounds could be applied depending on the data depth and mode,
|
|
6093 * but this is sufficient to ensure safe decoding.)
|
|
6094 */
|
|
6095 if (isDC) {
|
|
6096 for (i = 0; i < numsymbols; i++) {
|
|
6097 int sym = htbl.huffval[i] & 0xFF;
|
|
6098 if (sym < 0 || sym > 15)
|
|
6099 error();
|
|
6100 // ERREXIT(cinfo, JERR_BAD_HUFF_TABLE);
|
|
6101 }
|
|
6102 }
|
|
6103 }
|
|
6104
|
|
6105 static void start_input_pass (jpeg_decompress_struct cinfo) {
|
|
6106 per_scan_setup(cinfo);
|
|
6107 latch_quant_tables(cinfo);
|
|
6108 cinfo.entropy.start_pass(cinfo);
|
|
6109 cinfo.coef.start_input_pass (cinfo);
|
|
6110 cinfo.inputctl.consume_input = COEF_CONSUME_INPUT;
|
|
6111 }
|
|
6112
|
|
6113 static void finish_input_pass (jpeg_decompress_struct cinfo) {
|
|
6114 cinfo.inputctl.consume_input = INPUT_CONSUME_INPUT;
|
|
6115 }
|
|
6116
|
|
6117 static int consume_markers (jpeg_decompress_struct cinfo) {
|
|
6118 jpeg_input_controller inputctl = cinfo.inputctl;
|
|
6119 int val;
|
|
6120
|
|
6121 if (inputctl.eoi_reached) /* After hitting EOI, read no further */
|
|
6122 return JPEG_REACHED_EOI;
|
|
6123
|
|
6124 val = read_markers (cinfo);
|
|
6125
|
|
6126 switch (val) {
|
|
6127 case JPEG_REACHED_SOS: /* Found SOS */
|
|
6128 if (inputctl.inheaders) { /* 1st SOS */
|
|
6129 initial_setup(cinfo);
|
|
6130 inputctl.inheaders = false;
|
|
6131 /* Note: start_input_pass must be called by jdmaster.c
|
|
6132 * before any more input can be consumed. jdapimin.c is
|
|
6133 * responsible for enforcing this sequencing.
|
|
6134 */
|
|
6135 } else { /* 2nd or later SOS marker */
|
|
6136 if (! inputctl.has_multiple_scans)
|
|
6137 error();
|
|
6138 // ERREXIT(cinfo, JERR_EOI_EXPECTED); /* Oops, I wasn't expecting this! */
|
|
6139 start_input_pass(cinfo);
|
|
6140 }
|
|
6141 break;
|
|
6142 case JPEG_REACHED_EOI: /* Found EOI */
|
|
6143 inputctl.eoi_reached = true;
|
|
6144 if (inputctl.inheaders) { /* Tables-only datastream, apparently */
|
|
6145 if (cinfo.marker.saw_SOF)
|
|
6146 error();
|
|
6147 // ERREXIT(cinfo, JERR_SOF_NO_SOS);
|
|
6148 } else {
|
|
6149 /* Prevent infinite loop in coef ctlr's decompress_data routine
|
|
6150 * if user set output_scan_number larger than number of scans.
|
|
6151 */
|
|
6152 if (cinfo.output_scan_number > cinfo.input_scan_number)
|
|
6153 cinfo.output_scan_number = cinfo.input_scan_number;
|
|
6154 }
|
|
6155 break;
|
|
6156 case JPEG_SUSPENDED:
|
|
6157 break;
|
|
6158 default:
|
|
6159 }
|
|
6160
|
|
6161 return val;
|
|
6162 }
|
|
6163
|
|
6164 static void default_decompress_parms (jpeg_decompress_struct cinfo) {
|
|
6165 /* Guess the input colorspace, and set output colorspace accordingly. */
|
|
6166 /* (Wish JPEG committee had provided a real way to specify this...) */
|
|
6167 /* Note application may override our guesses. */
|
|
6168 switch (cinfo.num_components) {
|
|
6169 case 1:
|
|
6170 cinfo.jpeg_color_space = JCS_GRAYSCALE;
|
|
6171 cinfo.out_color_space = JCS_GRAYSCALE;
|
|
6172 break;
|
|
6173
|
|
6174 case 3:
|
|
6175 if (cinfo.saw_JFIF_marker) {
|
|
6176 cinfo.jpeg_color_space = JCS_YCbCr; /* JFIF implies YCbCr */
|
|
6177 } else if (cinfo.saw_Adobe_marker) {
|
|
6178 switch (cinfo.Adobe_transform) {
|
|
6179 case 0:
|
|
6180 cinfo.jpeg_color_space = JCS_RGB;
|
|
6181 break;
|
|
6182 case 1:
|
|
6183 cinfo.jpeg_color_space = JCS_YCbCr;
|
|
6184 break;
|
|
6185 default:
|
|
6186 // WARNMS1(cinfo, JWRN_ADOBE_XFORM, cinfo.Adobe_transform);
|
|
6187 cinfo.jpeg_color_space = JCS_YCbCr; /* assume it's YCbCr */
|
|
6188 break;
|
|
6189 }
|
|
6190 } else {
|
|
6191 /* Saw no special markers, try to guess from the component IDs */
|
|
6192 int cid0 = cinfo.comp_info[0].component_id;
|
|
6193 int cid1 = cinfo.comp_info[1].component_id;
|
|
6194 int cid2 = cinfo.comp_info[2].component_id;
|
|
6195
|
|
6196 if (cid0 is 1 && cid1 is 2 && cid2 is 3)
|
|
6197 cinfo.jpeg_color_space = JCS_YCbCr; /* assume JFIF w/out marker */
|
|
6198 else if (cid0 is 82 && cid1 is 71 && cid2 is 66)
|
|
6199 cinfo.jpeg_color_space = JCS_RGB; /* ASCII 'R', 'G', 'B' */
|
|
6200 else {
|
|
6201 // TRACEMS3(cinfo, 1, JTRC_UNKNOWN_IDS, cid0, cid1, cid2);
|
|
6202 cinfo.jpeg_color_space = JCS_YCbCr; /* assume it's YCbCr */
|
|
6203 }
|
|
6204 }
|
|
6205 /* Always guess RGB is proper output colorspace. */
|
|
6206 cinfo.out_color_space = JCS_RGB;
|
|
6207 break;
|
|
6208
|
|
6209 case 4:
|
|
6210 if (cinfo.saw_Adobe_marker) {
|
|
6211 switch (cinfo.Adobe_transform) {
|
|
6212 case 0:
|
|
6213 cinfo.jpeg_color_space = JCS_CMYK;
|
|
6214 break;
|
|
6215 case 2:
|
|
6216 cinfo.jpeg_color_space = JCS_YCCK;
|
|
6217 break;
|
|
6218 default:
|
|
6219 // WARNMS1(cinfo, JWRN_ADOBE_XFORM, cinfo.Adobe_transform);
|
|
6220 cinfo.jpeg_color_space = JCS_YCCK; /* assume it's YCCK */
|
|
6221 break;
|
|
6222 }
|
|
6223 } else {
|
|
6224 /* No special markers, assume straight CMYK. */
|
|
6225 cinfo.jpeg_color_space = JCS_CMYK;
|
|
6226 }
|
|
6227 cinfo.out_color_space = JCS_CMYK;
|
|
6228 break;
|
|
6229
|
|
6230 default:
|
|
6231 cinfo.jpeg_color_space = JCS_UNKNOWN;
|
|
6232 cinfo.out_color_space = JCS_UNKNOWN;
|
|
6233 break;
|
|
6234 }
|
|
6235
|
|
6236 /* Set defaults for other decompression parameters. */
|
|
6237 cinfo.scale_num = 1; /* 1:1 scaling */
|
|
6238 cinfo.scale_denom = 1;
|
|
6239 cinfo.output_gamma = 1.0;
|
|
6240 cinfo.buffered_image = false;
|
|
6241 cinfo.raw_data_out = false;
|
|
6242 cinfo.dct_method = JDCT_DEFAULT;
|
|
6243 cinfo.do_fancy_upsampling = true;
|
|
6244 cinfo.do_block_smoothing = true;
|
|
6245 cinfo.quantize_colors = false;
|
|
6246 /* We set these in case application only sets quantize_colors. */
|
|
6247 cinfo.dither_mode = JDITHER_FS;
|
|
6248 cinfo.two_pass_quantize = true;
|
|
6249 cinfo.desired_number_of_colors = 256;
|
|
6250 cinfo.colormap = null;
|
|
6251 /* Initialize for no mode change in buffered-image mode. */
|
|
6252 cinfo.enable_1pass_quant = false;
|
|
6253 cinfo.enable_external_quant = false;
|
|
6254 cinfo.enable_2pass_quant = false;
|
|
6255 }
|
|
6256
|
|
6257 static void init_source(jpeg_decompress_struct cinfo) {
|
|
6258 cinfo.buffer = new byte[INPUT_BUFFER_SIZE];
|
|
6259 cinfo.bytes_in_buffer = 0;
|
|
6260 cinfo.bytes_offset = 0;
|
|
6261 cinfo.start_of_file = true;
|
|
6262 }
|
|
6263
|
|
6264 static int jpeg_consume_input (jpeg_decompress_struct cinfo) {
|
|
6265 int retcode = JPEG_SUSPENDED;
|
|
6266
|
|
6267 /* NB: every possible DSTATE value should be listed in this switch */
|
|
6268 switch (cinfo.global_state) {
|
|
6269 case DSTATE_START:
|
|
6270 /* Start-of-datastream actions: reset appropriate modules */
|
|
6271 reset_input_controller(cinfo);
|
|
6272 /* Initialize application's data source module */
|
|
6273 init_source (cinfo);
|
|
6274 cinfo.global_state = DSTATE_INHEADER;
|
|
6275 /*FALLTHROUGH*/
|
|
6276 case DSTATE_INHEADER:
|
|
6277 retcode = consume_input(cinfo);
|
|
6278 if (retcode is JPEG_REACHED_SOS) { /* Found SOS, prepare to decompress */
|
|
6279 /* Set up default parameters based on header data */
|
|
6280 default_decompress_parms(cinfo);
|
|
6281 /* Set global state: ready for start_decompress */
|
|
6282 cinfo.global_state = DSTATE_READY;
|
|
6283 }
|
|
6284 break;
|
|
6285 case DSTATE_READY:
|
|
6286 /* Can't advance past first SOS until start_decompress is called */
|
|
6287 retcode = JPEG_REACHED_SOS;
|
|
6288 break;
|
|
6289 case DSTATE_PRELOAD:
|
|
6290 case DSTATE_PRESCAN:
|
|
6291 case DSTATE_SCANNING:
|
|
6292 case DSTATE_RAW_OK:
|
|
6293 case DSTATE_BUFIMAGE:
|
|
6294 case DSTATE_BUFPOST:
|
|
6295 case DSTATE_STOPPING:
|
|
6296 retcode = consume_input (cinfo);
|
|
6297 break;
|
|
6298 default:
|
|
6299 error();
|
|
6300 // ERREXIT1(cinfo, JERR_BAD_STATE, cinfo.global_state);
|
|
6301 }
|
|
6302 return retcode;
|
|
6303 }
|
|
6304
|
|
6305
|
|
6306 static void jpeg_abort (jpeg_decompress_struct cinfo) {
|
|
6307 // int pool;
|
|
6308 //
|
|
6309 // /* Releasing pools in reverse order might help avoid fragmentation
|
|
6310 // * with some (brain-damaged) malloc libraries.
|
|
6311 // */
|
|
6312 // for (pool = JPOOL_NUMPOOLS-1; pool > JPOOL_PERMANENT; pool--) {
|
|
6313 // (*cinfo.mem.free_pool) (cinfo, pool);
|
|
6314 // }
|
|
6315
|
|
6316 /* Reset overall state for possible reuse of object */
|
|
6317 if (cinfo.is_decompressor) {
|
|
6318 cinfo.global_state = DSTATE_START;
|
|
6319 /* Try to keep application from accessing now-deleted marker list.
|
|
6320 * A bit kludgy to do it here, but this is the most central place.
|
|
6321 */
|
|
6322 // ((j_decompress_ptr) cinfo).marker_list = null;
|
|
6323 } else {
|
|
6324 cinfo.global_state = CSTATE_START;
|
|
6325 }
|
|
6326 }
|
|
6327
|
|
6328
|
|
6329 static bool isFileFormat(LEDataInputStream stream) {
|
|
6330 try {
|
|
6331 byte[] buffer = new byte[2];
|
|
6332 stream.read(buffer);
|
|
6333 stream.unread(buffer);
|
|
6334 return (buffer[0] & 0xFF) is 0xFF && (buffer[1] & 0xFF) is M_SOI;
|
|
6335 } catch (Exception e) {
|
|
6336 return false;
|
|
6337 }
|
|
6338 }
|
|
6339
|
|
6340 static ImageData[] loadFromByteStream(InputStream inputStream, ImageLoader loader) {
|
|
6341 jpeg_decompress_struct cinfo = new jpeg_decompress_struct();
|
|
6342 cinfo.inputStream = inputStream;
|
|
6343 jpeg_create_decompress(cinfo);
|
|
6344 jpeg_read_header(cinfo, true);
|
|
6345 cinfo.buffered_image = cinfo.progressive_mode && loader.hasListeners();
|
|
6346 jpeg_start_decompress(cinfo);
|
|
6347 PaletteData palette = null;
|
|
6348 switch (cinfo.out_color_space) {
|
|
6349 case JCS_RGB:
|
|
6350 palette = new PaletteData(0xFF, 0xFF00, 0xFF0000);
|
|
6351 break;
|
|
6352 case JCS_GRAYSCALE:
|
|
6353 RGB[] colors = new RGB[256];
|
|
6354 for (int i = 0; i < colors.length; i++) {
|
|
6355 colors[i] = new RGB(i, i, i);
|
|
6356 }
|
|
6357 palette = new PaletteData(colors);
|
|
6358 break;
|
|
6359 default:
|
|
6360 error();
|
|
6361 }
|
|
6362 int scanlinePad = 4;
|
|
6363 int row_stride = (((cinfo.output_width * cinfo.out_color_components * 8 + 7) / 8) + (scanlinePad - 1)) / scanlinePad * scanlinePad;
|
|
6364 byte[][] buffer = new byte[][]( 1, row_stride );
|
|
6365 byte[] data = new byte[row_stride * cinfo.output_height];
|
|
6366 ImageData imageData = ImageData.internal_new(
|
|
6367 cinfo.output_width, cinfo.output_height, palette.isDirect ? 24 : 8, palette, scanlinePad, data,
|
|
6368 0, null, null, -1, -1, SWT.IMAGE_JPEG, 0, 0, 0, 0);
|
|
6369 if (cinfo.buffered_image) {
|
|
6370 bool done;
|
|
6371 do {
|
|
6372 int incrementCount = cinfo.input_scan_number - 1;
|
|
6373 jpeg_start_output(cinfo, cinfo.input_scan_number);
|
|
6374 while (cinfo.output_scanline < cinfo.output_height) {
|
|
6375 int offset = row_stride * cinfo.output_scanline;
|
|
6376 jpeg_read_scanlines(cinfo, buffer, 1);
|
|
6377 System.arraycopy(buffer[0], 0, data, offset, row_stride);
|
|
6378 }
|
|
6379 jpeg_finish_output(cinfo);
|
|
6380 loader.notifyListeners(new ImageLoaderEvent(loader, cast(ImageData)imageData.clone(), incrementCount, done = jpeg_input_complete(cinfo)));
|
|
6381 } while (!done);
|
|
6382 } else {
|
|
6383 while (cinfo.output_scanline < cinfo.output_height) {
|
|
6384 int offset = row_stride * cinfo.output_scanline;
|
|
6385 jpeg_read_scanlines(cinfo, buffer, 1);
|
|
6386 System.arraycopy(buffer[0], 0, data, offset, row_stride);
|
|
6387 }
|
|
6388 }
|
|
6389 jpeg_finish_decompress(cinfo);
|
|
6390 jpeg_destroy_decompress(cinfo);
|
|
6391 return [imageData];
|
|
6392 }
|
|
6393
|
|
6394 }
|