1 /* Linux driver for Philips webcam
2 Decompression for chipset version 2 et 3
3 (C) 2004-2006 Luc Saillard (luc@saillard.org)
5 NOTE: this version of pwc is an unofficial (modified) release of pwc & pcwx
6 driver and thus may have bugs that are not present in the original version.
7 Please send bug reports and support requests to <luc@saillard.org>.
8 The decompression routines have been implemented by reverse-engineering the
9 Nemosoft binary pwcx module. Caveat emptor.
11 This program is free software; you can redistribute it and/or modify
12 it under the terms of the GNU General Public License as published by
13 the Free Software Foundation; either version 2 of the License, or
14 (at your option) any later version.
16 This program is distributed in the hope that it will be useful,
17 but WITHOUT ANY WARRANTY; without even the implied warranty of
18 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19 GNU General Public License for more details.
21 You should have received a copy of the GNU General Public License
22 along with this program; if not, write to the Free Software
23 Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
27 #include "pwc-timon.h"
28 #include "pwc-kiara.h"
29 #include "pwc-dec23.h"
30 #include <media/pwc-ioctl.h>
32 #include <linux/string.h>
35 * USE_LOOKUP_TABLE_TO_CLAMP
36 * 0: use a C version of this tests: { a<0?0:(a>255?255:a) }
37 * 1: use a faster lookup table for cpu with a big cache (intel)
39 #define USE_LOOKUP_TABLE_TO_CLAMP 1
41 * UNROLL_LOOP_FOR_COPYING_BLOCK
42 * 0: use a loop for a smaller code (but little slower)
43 * 1: when unrolling the loop, gcc produces some faster code (perhaps only
44 * valid for intel processor class). Activating this option, automaticaly
45 * activate USE_LOOKUP_TABLE_TO_CLAMP
47 #define UNROLL_LOOP_FOR_COPY 1
48 #if UNROLL_LOOP_FOR_COPY
49 # undef USE_LOOKUP_TABLE_TO_CLAMP
50 # define USE_LOOKUP_TABLE_TO_CLAMP 1
54 * ENABLE_BAYER_DECODER
55 * 0: bayer decoder is not build (save some space)
56 * 1: bayer decoder is build and can be used
58 #define ENABLE_BAYER_DECODER 0
60 static void build_subblock_pattern(struct pwc_dec23_private *pdec)
62 static const unsigned int initial_values[12] = {
63 -0x526500, -0x221200, 0x221200, 0x526500,
65 -0x6db480, -0x2d5d00, 0x2d5d00, 0x6db480,
69 static const unsigned int values_derivated[12] = {
70 0xa4ca, 0x4424, -0x4424, -0xa4ca,
72 0xdb69, 0x5aba, -0x5aba, -0xdb69,
75 unsigned int temp_values[12];
78 memcpy(temp_values, initial_values, sizeof(initial_values));
79 for (i = 0; i < 256; i++) {
80 for (j = 0; j < 12; j++) {
81 pdec->table_subblock[i][j] = temp_values[j];
82 temp_values[j] += values_derivated[j];
87 static void build_bit_powermask_table(struct pwc_dec23_private *pdec)
90 unsigned int bit, byte, mask, val;
91 unsigned int bitpower = 1;
93 for (bit = 0; bit < 8; bit++) {
95 p = pdec->table_bitpowermask[bit];
96 for (byte = 0; byte < 256; byte++) {
107 static void build_table_color(const unsigned int romtable[16][8],
108 unsigned char p0004[16][1024],
109 unsigned char p8004[16][256])
111 int compression_mode, j, k, bit, pw;
112 unsigned char *p0, *p8;
113 const unsigned int *r;
115 /* We have 16 compressions tables */
116 for (compression_mode = 0; compression_mode < 16; compression_mode++) {
117 p0 = p0004[compression_mode];
118 p8 = p8004[compression_mode];
119 r = romtable[compression_mode];
121 for (j = 0; j < 8; j++, r++, p0 += 128) {
123 for (k = 0; k < 16; k++) {
126 else if (k >= 1 && k < 3)
127 bit = (r[0] >> 15) & 7;
128 else if (k >= 3 && k < 6)
129 bit = (r[0] >> 12) & 7;
130 else if (k >= 6 && k < 10)
131 bit = (r[0] >> 9) & 7;
132 else if (k >= 10 && k < 13)
133 bit = (r[0] >> 6) & 7;
134 else if (k >= 13 && k < 15)
135 bit = (r[0] >> 3) & 7;
145 p0[k + 0x00] = (1 * pw) + 0x80;
146 p0[k + 0x10] = (2 * pw) + 0x80;
147 p0[k + 0x20] = (3 * pw) + 0x80;
148 p0[k + 0x30] = (4 * pw) + 0x80;
149 p0[k + 0x40] = (-1 * pw) + 0x80;
150 p0[k + 0x50] = (-2 * pw) + 0x80;
151 p0[k + 0x60] = (-3 * pw) + 0x80;
152 p0[k + 0x70] = (-4 * pw) + 0x80;
153 } /* end of for (k=0; k<16; k++, p8++) */
154 } /* end of for (j=0; j<8; j++ , table++) */
155 } /* end of foreach compression_mode */
161 static void fill_table_dc00_d800(struct pwc_dec23_private *pdec)
164 #define ONE_HALF (1UL << (SCALEBITS - 1))
166 unsigned int offset1 = ONE_HALF;
167 unsigned int offset2 = 0x0000;
169 for (i=0; i<256; i++) {
170 pdec->table_dc00[i] = offset1 & ~(ONE_HALF);
171 pdec->table_d800[i] = offset2;
179 * To decode the stream:
180 * if look_bits(2) == 0: # op == 2 in the lookup table
183 * elif look_bits(3) == 7: # op == 1 in the lookup table
187 * else: # op == 0 in the lookup table
190 * For speedup processing, we build a lookup table and we takes the first 6 bits.
193 * unsigned char op; // operation to execute
194 * unsigned char bits; // bits use to perform operation
195 * unsigned char offset1; // offset to add to access in the table_0004 % 16
196 * unsigned char offset2; // offset to add to access in the table_0004
199 * How to build this table ?
200 * op == 2 when (i%4)==0
201 * op == 1 when (i%8)==7
205 static const unsigned char hash_table_ops[64*4] = {
206 0x02, 0x00, 0x00, 0x00,
207 0x00, 0x03, 0x01, 0x00,
208 0x00, 0x04, 0x01, 0x10,
209 0x00, 0x06, 0x01, 0x30,
210 0x02, 0x00, 0x00, 0x00,
211 0x00, 0x03, 0x01, 0x40,
212 0x00, 0x05, 0x01, 0x20,
213 0x01, 0x00, 0x00, 0x00,
214 0x02, 0x00, 0x00, 0x00,
215 0x00, 0x03, 0x01, 0x00,
216 0x00, 0x04, 0x01, 0x50,
217 0x00, 0x05, 0x02, 0x00,
218 0x02, 0x00, 0x00, 0x00,
219 0x00, 0x03, 0x01, 0x40,
220 0x00, 0x05, 0x03, 0x00,
221 0x01, 0x00, 0x00, 0x00,
222 0x02, 0x00, 0x00, 0x00,
223 0x00, 0x03, 0x01, 0x00,
224 0x00, 0x04, 0x01, 0x10,
225 0x00, 0x06, 0x02, 0x10,
226 0x02, 0x00, 0x00, 0x00,
227 0x00, 0x03, 0x01, 0x40,
228 0x00, 0x05, 0x01, 0x60,
229 0x01, 0x00, 0x00, 0x00,
230 0x02, 0x00, 0x00, 0x00,
231 0x00, 0x03, 0x01, 0x00,
232 0x00, 0x04, 0x01, 0x50,
233 0x00, 0x05, 0x02, 0x40,
234 0x02, 0x00, 0x00, 0x00,
235 0x00, 0x03, 0x01, 0x40,
236 0x00, 0x05, 0x03, 0x40,
237 0x01, 0x00, 0x00, 0x00,
238 0x02, 0x00, 0x00, 0x00,
239 0x00, 0x03, 0x01, 0x00,
240 0x00, 0x04, 0x01, 0x10,
241 0x00, 0x06, 0x01, 0x70,
242 0x02, 0x00, 0x00, 0x00,
243 0x00, 0x03, 0x01, 0x40,
244 0x00, 0x05, 0x01, 0x20,
245 0x01, 0x00, 0x00, 0x00,
246 0x02, 0x00, 0x00, 0x00,
247 0x00, 0x03, 0x01, 0x00,
248 0x00, 0x04, 0x01, 0x50,
249 0x00, 0x05, 0x02, 0x00,
250 0x02, 0x00, 0x00, 0x00,
251 0x00, 0x03, 0x01, 0x40,
252 0x00, 0x05, 0x03, 0x00,
253 0x01, 0x00, 0x00, 0x00,
254 0x02, 0x00, 0x00, 0x00,
255 0x00, 0x03, 0x01, 0x00,
256 0x00, 0x04, 0x01, 0x10,
257 0x00, 0x06, 0x02, 0x50,
258 0x02, 0x00, 0x00, 0x00,
259 0x00, 0x03, 0x01, 0x40,
260 0x00, 0x05, 0x01, 0x60,
261 0x01, 0x00, 0x00, 0x00,
262 0x02, 0x00, 0x00, 0x00,
263 0x00, 0x03, 0x01, 0x00,
264 0x00, 0x04, 0x01, 0x50,
265 0x00, 0x05, 0x02, 0x40,
266 0x02, 0x00, 0x00, 0x00,
267 0x00, 0x03, 0x01, 0x40,
268 0x00, 0x05, 0x03, 0x40,
269 0x01, 0x00, 0x00, 0x00
275 static const unsigned int MulIdx[16][16] = {
276 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,},
277 {0, 1, 2, 3, 0, 1, 2, 3, 0, 1, 2, 3, 0, 1, 2, 3,},
278 {0, 0, 0, 0, 1, 1, 1, 1, 2, 2, 2, 2, 3, 3, 3, 3,},
279 {4, 4, 4, 4, 5, 5, 5, 5, 5, 5, 5, 5, 4, 4, 4, 4,},
280 {6, 7, 8, 9, 7, 10, 11, 8, 8, 11, 10, 7, 9, 8, 7, 6,},
281 {4, 5, 5, 4, 4, 5, 5, 4, 4, 5, 5, 4, 4, 5, 5, 4,},
282 {1, 3, 0, 2, 1, 3, 0, 2, 1, 3, 0, 2, 1, 3, 0, 2,},
283 {0, 3, 3, 0, 1, 2, 2, 1, 2, 1, 1, 2, 3, 0, 0, 3,},
284 {0, 1, 2, 3, 3, 2, 1, 0, 3, 2, 1, 0, 0, 1, 2, 3,},
285 {1, 1, 1, 1, 3, 3, 3, 3, 0, 0, 0, 0, 2, 2, 2, 2,},
286 {7, 10, 11, 8, 9, 8, 7, 6, 6, 7, 8, 9, 8, 11, 10, 7,},
287 {4, 5, 5, 4, 5, 4, 4, 5, 5, 4, 4, 5, 4, 5, 5, 4,},
288 {7, 9, 6, 8, 10, 8, 7, 11, 11, 7, 8, 10, 8, 6, 9, 7,},
289 {1, 3, 0, 2, 2, 0, 3, 1, 2, 0, 3, 1, 1, 3, 0, 2,},
290 {1, 2, 2, 1, 3, 0, 0, 3, 0, 3, 3, 0, 2, 1, 1, 2,},
291 {10, 8, 7, 11, 8, 6, 9, 7, 7, 9, 6, 8, 11, 7, 8, 10}
294 #if USE_LOOKUP_TABLE_TO_CLAMP
295 #define MAX_OUTER_CROP_VALUE (512)
296 static unsigned char pwc_crop_table[256 + 2*MAX_OUTER_CROP_VALUE];
297 #define CLAMP(x) (pwc_crop_table[MAX_OUTER_CROP_VALUE+(x)])
299 #define CLAMP(x) ((x)>255?255:((x)<0?0:x))
303 /* If the type or the command change, we rebuild the lookup table */
304 int pwc_dec23_init(struct pwc_device *pwc, int type, unsigned char *cmd)
306 int flags, version, shift, i;
307 struct pwc_dec23_private *pdec;
309 if (pwc->decompress_data == NULL) {
310 pdec = kmalloc(sizeof(struct pwc_dec23_private), GFP_KERNEL);
313 pwc->decompress_data = pdec;
315 pdec = pwc->decompress_data;
317 if (DEVICE_USE_CODEC3(type)) {
318 flags = cmd[2] & 0x18;
320 pdec->nbits = 7; /* More bits, mean more bits to encode the stream, but better quality */
321 else if (flags == 0x10)
326 version = cmd[2] >> 5;
327 build_table_color(KiaraRomTable[version][0], pdec->table_0004_pass1, pdec->table_8004_pass1);
328 build_table_color(KiaraRomTable[version][1], pdec->table_0004_pass2, pdec->table_8004_pass2);
340 version = cmd[2] >> 3;
341 build_table_color(TimonRomTable[version][0], pdec->table_0004_pass1, pdec->table_8004_pass1);
342 build_table_color(TimonRomTable[version][1], pdec->table_0004_pass2, pdec->table_8004_pass2);
345 /* Informations can be coded on a variable number of bits but never less than 8 */
346 shift = 8 - pdec->nbits;
347 pdec->scalebits = SCALEBITS - shift;
348 pdec->nbitsmask = 0xFF >> shift;
350 fill_table_dc00_d800(pdec);
351 build_subblock_pattern(pdec);
352 build_bit_powermask_table(pdec);
354 #if USE_LOOKUP_TABLE_TO_CLAMP
355 /* Build the static table to clamp value [0-255] */
356 for (i=0;i<MAX_OUTER_CROP_VALUE;i++)
357 pwc_crop_table[i] = 0;
358 for (i=0; i<256; i++)
359 pwc_crop_table[MAX_OUTER_CROP_VALUE+i] = i;
360 for (i=0; i<MAX_OUTER_CROP_VALUE; i++)
361 pwc_crop_table[MAX_OUTER_CROP_VALUE+256+i] = 255;
368 * Copy the 4x4 image block to Y plane buffer
370 static void copy_image_block_Y(const int *src, unsigned char *dst, unsigned int bytes_per_line, unsigned int scalebits)
372 #if UNROLL_LOOP_FOR_COPY
373 const unsigned char *cm = pwc_crop_table+MAX_OUTER_CROP_VALUE;
375 unsigned char *d = dst;
377 *d++ = cm[c[0] >> scalebits];
378 *d++ = cm[c[1] >> scalebits];
379 *d++ = cm[c[2] >> scalebits];
380 *d++ = cm[c[3] >> scalebits];
382 d = dst + bytes_per_line;
383 *d++ = cm[c[4] >> scalebits];
384 *d++ = cm[c[5] >> scalebits];
385 *d++ = cm[c[6] >> scalebits];
386 *d++ = cm[c[7] >> scalebits];
388 d = dst + bytes_per_line*2;
389 *d++ = cm[c[8] >> scalebits];
390 *d++ = cm[c[9] >> scalebits];
391 *d++ = cm[c[10] >> scalebits];
392 *d++ = cm[c[11] >> scalebits];
394 d = dst + bytes_per_line*3;
395 *d++ = cm[c[12] >> scalebits];
396 *d++ = cm[c[13] >> scalebits];
397 *d++ = cm[c[14] >> scalebits];
398 *d++ = cm[c[15] >> scalebits];
402 unsigned char *d = dst;
403 for (i = 0; i < 4; i++, c++)
404 *d++ = CLAMP((*c) >> scalebits);
406 d = dst + bytes_per_line;
407 for (i = 0; i < 4; i++, c++)
408 *d++ = CLAMP((*c) >> scalebits);
410 d = dst + bytes_per_line*2;
411 for (i = 0; i < 4; i++, c++)
412 *d++ = CLAMP((*c) >> scalebits);
414 d = dst + bytes_per_line*3;
415 for (i = 0; i < 4; i++, c++)
416 *d++ = CLAMP((*c) >> scalebits);
421 * Copy the 4x4 image block to a CrCb plane buffer
424 static void copy_image_block_CrCb(const int *src, unsigned char *dst, unsigned int bytes_per_line, unsigned int scalebits)
426 #if UNROLL_LOOP_FOR_COPY
427 /* Unroll all loops */
428 const unsigned char *cm = pwc_crop_table+MAX_OUTER_CROP_VALUE;
430 unsigned char *d = dst;
432 *d++ = cm[c[0] >> scalebits];
433 *d++ = cm[c[4] >> scalebits];
434 *d++ = cm[c[1] >> scalebits];
435 *d++ = cm[c[5] >> scalebits];
436 *d++ = cm[c[2] >> scalebits];
437 *d++ = cm[c[6] >> scalebits];
438 *d++ = cm[c[3] >> scalebits];
439 *d++ = cm[c[7] >> scalebits];
441 d = dst + bytes_per_line;
442 *d++ = cm[c[12] >> scalebits];
443 *d++ = cm[c[8] >> scalebits];
444 *d++ = cm[c[13] >> scalebits];
445 *d++ = cm[c[9] >> scalebits];
446 *d++ = cm[c[14] >> scalebits];
447 *d++ = cm[c[10] >> scalebits];
448 *d++ = cm[c[15] >> scalebits];
449 *d++ = cm[c[11] >> scalebits];
453 const int *c2 = src + 4;
454 unsigned char *d = dst;
456 for (i = 0; i < 4; i++, c1++, c2++) {
457 *d++ = CLAMP((*c1) >> scalebits);
458 *d++ = CLAMP((*c2) >> scalebits);
461 d = dst + bytes_per_line;
462 for (i = 0; i < 4; i++, c1++, c2++) {
463 *d++ = CLAMP((*c1) >> scalebits);
464 *d++ = CLAMP((*c2) >> scalebits);
469 #if ENABLE_BAYER_DECODER
472 * . G . G . G . G . G . G . G
473 * . . . . . . . . . . . . . .
474 * . G . G . G . G . G . G . G
475 * . . . . . . . . . . . . . .
477 * . . . . . . . . . . . . . .
478 * G . G . G . G . G . G . G .
479 * . . . . . . . . . . . . . .
480 * G . G . G . G . G . G . G .
482 static void copy_image_block_Green(const int *src, unsigned char *dst, unsigned int bytes_per_line, unsigned int scalebits)
484 #if UNROLL_LOOP_FOR_COPY
485 /* Unroll all loops */
486 const unsigned char *cm = pwc_crop_table+MAX_OUTER_CROP_VALUE;
487 unsigned char *d = dst;
490 d[0] = cm[c[0] >> scalebits];
491 d[2] = cm[c[1] >> scalebits];
492 d[4] = cm[c[2] >> scalebits];
493 d[6] = cm[c[3] >> scalebits];
494 d[8] = cm[c[4] >> scalebits];
495 d[10] = cm[c[5] >> scalebits];
496 d[12] = cm[c[6] >> scalebits];
497 d[14] = cm[c[7] >> scalebits];
499 d = dst + bytes_per_line;
500 d[0] = cm[c[8] >> scalebits];
501 d[2] = cm[c[9] >> scalebits];
502 d[4] = cm[c[10] >> scalebits];
503 d[6] = cm[c[11] >> scalebits];
504 d[8] = cm[c[12] >> scalebits];
505 d[10] = cm[c[13] >> scalebits];
506 d[12] = cm[c[14] >> scalebits];
507 d[14] = cm[c[15] >> scalebits];
514 for (i = 0; i < 8; i++, c++)
515 d[i*2] = CLAMP((*c) >> scalebits);
517 d = dst + bytes_per_line;
518 for (i = 0; i < 8; i++, c++)
519 d[i*2] = CLAMP((*c) >> scalebits);
524 #if ENABLE_BAYER_DECODER
532 static void copy_image_block_RedBlue(const int *src, unsigned char *dst, unsigned int bytes_per_line, unsigned int scalebits)
534 #if UNROLL_LOOP_FOR_COPY
535 /* Unroll all loops */
536 const unsigned char *cm = pwc_crop_table+MAX_OUTER_CROP_VALUE;
537 unsigned char *d = dst;
540 d[0] = cm[c[0] >> scalebits];
541 d[2] = cm[c[1] >> scalebits];
542 d[4] = cm[c[2] >> scalebits];
543 d[6] = cm[c[3] >> scalebits];
545 d = dst + bytes_per_line;
546 d[1] = cm[c[4] >> scalebits];
547 d[3] = cm[c[5] >> scalebits];
548 d[5] = cm[c[6] >> scalebits];
549 d[7] = cm[c[7] >> scalebits];
551 d = dst + bytes_per_line*2;
552 d[0] = cm[c[8] >> scalebits];
553 d[2] = cm[c[9] >> scalebits];
554 d[4] = cm[c[10] >> scalebits];
555 d[6] = cm[c[11] >> scalebits];
557 d = dst + bytes_per_line*3;
558 d[1] = cm[c[12] >> scalebits];
559 d[3] = cm[c[13] >> scalebits];
560 d[5] = cm[c[14] >> scalebits];
561 d[7] = cm[c[15] >> scalebits];
568 for (i = 0; i < 4; i++, c++)
569 d[i*2] = CLAMP((*c) >> scalebits);
571 d = dst + bytes_per_line;
572 for (i = 0; i < 4; i++, c++)
573 d[i*2+1] = CLAMP((*c) >> scalebits);
575 d = dst + bytes_per_line*2;
576 for (i = 0; i < 4; i++, c++)
577 d[i*2] = CLAMP((*c) >> scalebits);
579 d = dst + bytes_per_line*3;
580 for (i = 0; i < 4; i++, c++)
581 d[i*2+1] = CLAMP((*c) >> scalebits);
587 * To manage the stream, we keep bits in a 32 bits register.
588 * fill_nbits(n): fill the reservoir with at least n bits
589 * skip_bits(n): discard n bits from the reservoir
590 * get_bits(n): fill the reservoir, returns the first n bits and discard the
591 * bits from the reservoir.
592 * __get_nbits(n): faster version of get_bits(n), but asumes that the reservoir
593 * contains at least n bits. bits returned is discarded.
595 #define fill_nbits(pdec, nbits_wanted) do { \
596 while (pdec->nbits_in_reservoir<(nbits_wanted)) \
598 pdec->reservoir |= (*(pdec->stream)++) << (pdec->nbits_in_reservoir); \
599 pdec->nbits_in_reservoir += 8; \
603 #define skip_nbits(pdec, nbits_to_skip) do { \
604 pdec->reservoir >>= (nbits_to_skip); \
605 pdec->nbits_in_reservoir -= (nbits_to_skip); \
608 #define get_nbits(pdec, nbits_wanted, result) do { \
609 fill_nbits(pdec, nbits_wanted); \
610 result = (pdec->reservoir) & ((1U<<(nbits_wanted))-1); \
611 skip_nbits(pdec, nbits_wanted); \
614 #define __get_nbits(pdec, nbits_wanted, result) do { \
615 result = (pdec->reservoir) & ((1U<<(nbits_wanted))-1); \
616 skip_nbits(pdec, nbits_wanted); \
619 #define look_nbits(pdec, nbits_wanted) \
620 ((pdec->reservoir) & ((1U<<(nbits_wanted))-1))
623 * Decode a 4x4 pixel block
625 static void decode_block(struct pwc_dec23_private *pdec,
626 const unsigned char *ptable0004,
627 const unsigned char *ptable8004)
629 unsigned int primary_color;
630 unsigned int channel_v, offset1, op;
633 fill_nbits(pdec, 16);
634 __get_nbits(pdec, pdec->nbits, primary_color);
636 if (look_nbits(pdec,2) == 0) {
638 /* Very simple, the color is the same for all pixels of the square */
639 for (i = 0; i < 16; i++)
640 pdec->temp_colors[i] = pdec->table_dc00[primary_color];
645 /* This block is encoded with small pattern */
646 for (i = 0; i < 16; i++)
647 pdec->temp_colors[i] = pdec->table_d800[primary_color];
649 __get_nbits(pdec, 3, channel_v);
650 channel_v = ((channel_v & 1) << 2) | (channel_v & 2) | ((channel_v & 4) >> 2);
652 ptable0004 += (channel_v * 128);
653 ptable8004 += (channel_v * 32);
658 unsigned int htable_idx, rows = 0;
659 const unsigned int *block;
662 * xx == 00 :=> end of the block def, remove the two bits from the stream
664 * yxx == any other value
667 fill_nbits(pdec, 16);
668 htable_idx = look_nbits(pdec, 6);
669 op = hash_table_ops[htable_idx * 4];
674 } else if (op == 1) {
675 /* 15bits [ xxxx xxxx yyyy 111 ]
676 * yyy => offset in the table8004
677 * xxx => offset in the tabled004 (tree)
679 unsigned int mask, shift;
680 unsigned int nbits, col1;
684 /* offset1 += yyyy */
685 __get_nbits(pdec, 4, yyyy);
688 nbits = ptable8004[offset1 * 2];
690 /* col1 = xxxx xxxx */
691 __get_nbits(pdec, nbits+1, col1);
694 mask = pdec->table_bitpowermask[nbits][col1];
695 shift = ptable8004[offset1 * 2 + 1];
696 rows = ((mask << shift) + 0x80) & 0xFF;
698 block = pdec->table_subblock[rows];
699 for (i = 0; i < 16; i++)
700 pdec->temp_colors[i] += block[MulIdx[offset1][i]];
704 * offset1 is coded on 3 bits
708 offset1 += hash_table_ops [htable_idx * 4 + 2];
711 rows = ptable0004[offset1 + hash_table_ops [htable_idx * 4 + 3]];
712 block = pdec->table_subblock[rows];
713 for (i = 0; i < 16; i++)
714 pdec->temp_colors[i] += block[MulIdx[offset1][i]];
716 shift = hash_table_ops[htable_idx * 4 + 1];
717 skip_nbits(pdec, shift);
724 static void DecompressBand23(struct pwc_dec23_private *pdec,
725 const unsigned char *rawyuv,
726 unsigned char *planar_y,
727 unsigned char *planar_u,
728 unsigned char *planar_v,
729 unsigned int compressed_image_width,
730 unsigned int real_image_width)
732 int compression_index, nblocks;
733 const unsigned char *ptable0004;
734 const unsigned char *ptable8004;
737 pdec->nbits_in_reservoir = 0;
738 pdec->stream = rawyuv + 1; /* The first byte of the stream is skipped */
740 get_nbits(pdec, 4, compression_index);
742 /* pass 1: uncompress Y component */
743 nblocks = compressed_image_width / 4;
745 ptable0004 = pdec->table_0004_pass1[compression_index];
746 ptable8004 = pdec->table_8004_pass1[compression_index];
748 /* Each block decode a square of 4x4 */
750 decode_block(pdec, ptable0004, ptable8004);
751 copy_image_block_Y(pdec->temp_colors, planar_y, real_image_width, pdec->scalebits);
756 /* pass 2: uncompress UV component */
757 nblocks = compressed_image_width / 8;
759 ptable0004 = pdec->table_0004_pass2[compression_index];
760 ptable8004 = pdec->table_8004_pass2[compression_index];
762 /* Each block decode a square of 4x4 */
764 decode_block(pdec, ptable0004, ptable8004);
765 copy_image_block_CrCb(pdec->temp_colors, planar_u, real_image_width/2, pdec->scalebits);
767 decode_block(pdec, ptable0004, ptable8004);
768 copy_image_block_CrCb(pdec->temp_colors, planar_v, real_image_width/2, pdec->scalebits);
777 #if ENABLE_BAYER_DECODER
779 * Size need to be a multiple of 8 in width
781 * Return a block of four line encoded like this:
783 * G R G R G R G R G R G R G R G R
784 * B G B G B G B G B G B G B G B G
785 * G R G R G R G R G R G R G R G R
786 * B G B G B G B G B G B G B G B G
789 static void DecompressBandBayer(struct pwc_dec23_private *pdec,
790 const unsigned char *rawyuv,
791 unsigned char *rgbbayer,
792 unsigned int compressed_image_width,
793 unsigned int real_image_width)
795 int compression_index, nblocks;
796 const unsigned char *ptable0004;
797 const unsigned char *ptable8004;
801 pdec->nbits_in_reservoir = 0;
802 pdec->stream = rawyuv + 1; /* The first byte of the stream is skipped */
804 get_nbits(pdec, 4, compression_index);
806 /* pass 1: uncompress RB component */
807 nblocks = compressed_image_width / 4;
809 ptable0004 = pdec->table_0004_pass1[compression_index];
810 ptable8004 = pdec->table_8004_pass1[compression_index];
813 /* Each block decode a square of 4x4 */
815 decode_block(pdec, ptable0004, ptable8004);
816 copy_image_block_RedBlue(pdec->temp_colors, rgbbayer, real_image_width, pdec->scalebits);
821 /* pass 2: uncompress G component */
822 nblocks = compressed_image_width / 8;
824 ptable0004 = pdec->table_0004_pass2[compression_index];
825 ptable8004 = pdec->table_8004_pass2[compression_index];
827 /* Each block decode a square of 4x4 */
829 decode_block(pdec, ptable0004, ptable8004);
830 copy_image_block_Green(pdec->temp_colors, rgbbayer+1, real_image_width, pdec->scalebits);
832 decode_block(pdec, ptable0004, ptable8004);
833 copy_image_block_Green(pdec->temp_colors, rgbbayer+real_image_width, real_image_width, pdec->scalebits);
844 * Uncompress a pwc23 buffer.
846 * pwc.view: size of the image wanted
847 * pwc.image: size of the image returned by the camera
848 * pwc.offset: (x,y) to displayer image in the view
852 * flags: PWCX_FLAG_PLANAR or PWCX_FLAG_BAYER
854 void pwc_dec23_decompress(const struct pwc_device *pwc,
859 int bandlines_left, stride, bytes_per_block;
861 bandlines_left = pwc->image.y / 4;
862 bytes_per_block = pwc->view.x * 4;
864 if (flags & PWCX_FLAG_BAYER) {
865 #if ENABLE_BAYER_DECODER
866 /* RGB Bayer format */
867 unsigned char *rgbout;
869 stride = pwc->view.x * pwc->offset.y;
870 rgbout = dst + stride + pwc->offset.x;
873 while (bandlines_left--) {
875 DecompressBandBayer(pwc->decompress_data,
878 pwc->image.x, pwc->view.x);
880 src += pwc->vbandlength;
881 rgbout += bytes_per_block;
885 memset(dst, 0, pwc->view.x * pwc->view.y);
889 /* YUV420P image format */
890 unsigned char *pout_planar_y;
891 unsigned char *pout_planar_u;
892 unsigned char *pout_planar_v;
893 unsigned int plane_size;
895 plane_size = pwc->view.x * pwc->view.y;
897 /* offset in Y plane */
898 stride = pwc->view.x * pwc->offset.y;
899 pout_planar_y = dst + stride + pwc->offset.x;
901 /* offsets in U/V planes */
902 stride = (pwc->view.x * pwc->offset.y) / 4 + pwc->offset.x / 2;
903 pout_planar_u = dst + plane_size + stride;
904 pout_planar_v = dst + plane_size + plane_size / 4 + stride;
906 while (bandlines_left--) {
908 DecompressBand23(pwc->decompress_data,
910 pout_planar_y, pout_planar_u, pout_planar_v,
911 pwc->image.x, pwc->view.x);
912 src += pwc->vbandlength;
913 pout_planar_y += bytes_per_block;
914 pout_planar_u += pwc->view.x;
915 pout_planar_v += pwc->view.x;
923 void pwc_dec23_exit(void)
930 * Allocate a private structure used by lookup table.
931 * You must call kfree() to free the memory allocated.
933 int pwc_dec23_alloc(struct pwc_device *pwc)
935 pwc->decompress_data = kmalloc(sizeof(struct pwc_dec23_private), GFP_KERNEL);
936 if (pwc->decompress_data == NULL)
941 /* vim: set cino= formatoptions=croql cindent shiftwidth=8 tabstop=8: */