5 unsigned num_codes[17]; /* BITS */
6 unsigned char codes[256]; /* HUFFVAL */
9 unsigned huffsize[256];
10 unsigned huffcode[256];
15 struct huffman_table huffman_tables[2][4];
21 struct mem_stream streams[128];
23 void *xmalloc(size_t size)
25 void *buf = malloc(size);
36 unsigned char mygetc()
42 fprintf(stderr, "Error: Unexpected end of file.\n");
50 return ((unsigned char)ch);
53 void putchar_stream(int stream, unsigned char ch)
55 int used = streams[stream].used;
57 if (streams[stream].used == streams[stream].room) {
58 streams[stream].room <<= 1;
59 streams[stream].buf = (unsigned char *)realloc(streams[stream].buf, streams[stream].room);
62 streams[stream].buf[streams[stream].used++] = ch;
65 void flush_stream(int stream)
67 fwrite(streams[stream].buf, streams[stream].used, 1, stdout);
68 streams[stream].used = 0;
71 unsigned char mygetc_limit(unsigned *len)
74 fprintf(stderr, "Error: Premature end of segment\n");
81 unsigned read_length()
83 unsigned char len1 = mygetc();
84 unsigned char len2 = mygetc();
85 unsigned len = (len1 << 8) | len2;
88 fprintf(stderr, "Error: Got length %u, expected at least 2\n", len);
95 void copy_segment(unsigned char marker_code)
97 unsigned len = read_length();
100 /* marker segment header */
102 putchar(marker_code);
106 for (i = 0; i < len - 2; ++i) {
111 void read_huffman_tables()
113 unsigned len = read_length() - 2;
121 unsigned char tc_th = mygetc_limit(&len);
122 unsigned table_class = tc_th >> 4;
123 unsigned table_dest = tc_th & 0x0f;
124 unsigned i, j, k, si;
125 struct huffman_table *tbl;
127 if (table_class != 0 && table_class != 1) {
128 fprintf(stderr, "Error: Unknown table class %u\n", table_class);
131 if (table_dest >= 4) {
132 fprintf(stderr, "Error: Unknown table destination %u\n", table_dest);
137 tbl = &huffman_tables[table_class][table_dest];
139 for (i = 0; i < 16; ++i) {
140 tbl->num_codes[i] = mygetc_limit(&len);
141 putchar(tbl->num_codes[i]);
142 fprintf(stderr, "%u ", tbl->num_codes[i]);
144 fprintf(stderr, "\ndumping tc=%u td=%u\n", table_class, table_dest);
145 for (i = 0, k = 0; i < 16; ++i) {
146 for (j = 0; j < tbl->num_codes[i]; ++j, ++k) {
147 tbl->codes[k] = mygetc_limit(&len);
148 putchar(tbl->codes[k]);
149 fprintf(stderr, "%u: len=%u, ind=%u: code=0x%02x\n", k, i+1, j, tbl->codes[k]);
153 /* generate derived tables */
155 /* generate_size_table (figure C.1) */
157 for (i = 0; i < 16; ++i) {
158 for (j = 0; j < tbl->num_codes[i]; ++j, ++k) {
159 tbl->huffsize[k] = i+1;
162 tbl->huffsize[k] = 0;
163 fprintf(stderr, "k=%u\n", k);
165 /* generate_code_table (figure C.2) */
166 si = tbl->huffsize[0];
167 for (i = 0, j = 0;; ) {
168 fprintf(stderr, "%u = %u [si=%u]\n", i, j, si);
170 tbl->huffcode[i++] = j++;
171 if (tbl->huffsize[i] == si) {
175 if (tbl->huffsize[i] == 0) {
181 } while (++si != tbl->huffsize[i]);
184 /* decoder_tables (figure F.15) */
185 for (i = 0, j = 0; i < 16; ++i) {
186 if (tbl->num_codes[i] == 0) {
187 tbl->maxcode[i] = -1;
192 //fprintf(stderr, "minind=%u\n", j);
193 tbl->mincode[i] = tbl->huffcode[j];
194 j += tbl->num_codes[i];
195 //fprintf(stderr, "maxind=%u\n", j-1);
196 tbl->maxcode[i] = tbl->huffcode[j - 1];
198 //fprintf(stderr, "%u: min=%u, max=%u\n", i, tbl->mincode[i], tbl->maxcode[i]);
207 /* procedure NEXTBIT */
208 unsigned get_bit(unsigned *bits_available, unsigned char *bit_reservoir)
212 if (*bits_available == 0) {
213 *bit_reservoir = mygetc();
214 //fprintf(stderr, "Read byte (0x%02x)\n", *bit_reservoir);
215 if (*bit_reservoir == 0xff) {
216 unsigned char ch = mygetc();
219 for (i = 0; i < 128; ++i) {
223 fprintf(stderr, "Error: Couldn't handle marker 0x%02x\n", ch);
226 //fprintf(stderr, "Read stuff byte (%u)\n", ch);
232 bit = *bit_reservoir >> 7;
233 *bit_reservoir = (*bit_reservoir & 0x7f) << 1;
236 //fprintf(stderr, "%u\n", bit);
241 /* procedure DECODE (figure F.16) */
242 unsigned char get_huffman_byte(unsigned *bits_available, unsigned char *bit_reservoir, struct huffman_table* huff_tbl)
244 unsigned code = get_bit(bits_available, bit_reservoir);
247 while (code > huff_tbl->maxcode[i - 1] || huff_tbl->maxcode[i - 1] == -1) {
248 code = (code << 1) | get_bit(bits_available, bit_reservoir);
252 fprintf(stderr, "Error in Huffman decoding: Too long code (%x).numch=%u\n", code, numch);
257 /*fprintf(stderr, "h=%d => code=0x%02x\n", huff_tbl->valptr[i - 1] + code - huff_tbl->mincode[i - 1],
258 huff_tbl->codes[huff_tbl->valptr[i - 1] + code - huff_tbl->mincode[i - 1]]);*/
259 return huff_tbl->codes[huff_tbl->valptr[i - 1] + code - huff_tbl->mincode[i - 1]];
262 /* procedure RECEIVE */
263 unsigned get_bits(unsigned num_bits, unsigned *bits_available, unsigned char *bit_reservoir)
267 for (i = 0; i < num_bits; ++i) {
269 val |= get_bit(bits_available, bit_reservoir);
275 /* procedure EXTEND (figure F.12) */
276 unsigned extend(int val, int bits)
278 if (val < (1 << (bits - 1))) {
279 return val + (-1 << bits) + 1;
287 unsigned len = read_length() - 2;
288 unsigned bits_available;
289 unsigned char bit_reservoir;
290 unsigned num_components = mygetc_limit(&len);
292 unsigned component_num[256];
293 unsigned dc_huffman_table[256], ac_huffman_table[256];
294 unsigned ss, se, ah_al;
298 for (i = 0; i < num_components; ++i) {
300 component_num[i] = mygetc_limit(&len);
301 td_ta = mygetc_limit(&len);
302 dc_huffman_table[i] = td_ta >> 4;
303 ac_huffman_table[i] = td_ta & 0x0f;
308 for (j = 0; j < 64; ++j) {
314 ss = mygetc_limit(&len);
315 se = mygetc_limit(&len);
316 ah_al = mygetc_limit(&len);
319 fprintf(stderr, "Error: %u unused bytes at end of SOS segment\n", len);
325 //fprintf(stderr, "\n");
328 for (c = 0; c < num_components; ++c) {
330 /*fprintf(stderr, "coeff %u\n", c);
331 fprintf(stderr, "getting dc (table %u)\n", dc_huffman_table[c]); */
333 /* decode DC component */
334 unsigned char dc_category = get_huffman_byte(&bits_available, &bit_reservoir, &huffman_tables[0][dc_huffman_table[c]]);
338 dc_diff = get_bits(dc_category, &bits_available, &bit_reservoir);
339 last_dc[c] += extend(dc_diff, dc_category);
341 /*putchar_stream(0, last_dc[c] >> 8);
342 putchar_stream(0, last_dc[c] & 0xff); */
343 putchar_stream(0, dc_diff >> 8);
344 putchar_stream(0, dc_diff & 0xff);
346 for (i = 0; i < 63; ++i) {
350 for (i = 0; i < 63; ++i) {
351 unsigned char rs = get_huffman_byte(&bits_available, &bit_reservoir, &huffman_tables[1][ac_huffman_table[c]]);
352 unsigned char r = rs >> 4;
353 unsigned char s = rs & 0xf;
360 /* 16 zero coefficients */
366 zz[i] = extend(get_bits(s, &bits_available, &bit_reservoir), s);
369 for (i = 0; i < 63; ++i) {
381 putchar_stream(s * 2 + 2, m >> 8);
382 putchar_stream(s * 2 + 3, m & 0xff);
391 for (i = 0; i < 128; ++i) {
392 streams[i].buf = (unsigned char *)malloc(4096);
394 streams[i].room = 4096;
398 unsigned char m1 = mygetc();
399 unsigned char m2 = mygetc();
402 fprintf(stderr, "Error: Expected marker (0xff), got 0x%02x\n", m1);
423 /* APP0 through APPF */
427 /* SOF0 (baseline DCT, Huffman encoded) */
436 /* DHT (define Huffman tables) */
437 read_huffman_tables();
440 /* SOS (start of scan) */
444 fprintf(stderr, "Error: Unknown marker 0x%02x\n", m2);