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