1 /* We would like to embed this inside libv4l, but we cannot as I've failed
2    to contact Mark W. McClelland to get permission to relicense this,
3    so this lives in an external (GPL licensed) helper */
4 
5 /* OV518 Decompression Support Module (No-MMX version)
6  *
7  * Copyright (c) 2002-2003 Mark W. McClelland. All rights reserved.
8  * http://alpha.dyndns.org/ov511/
9  *
10  * Fast integer iDCT by Yuri van Oers <yvanoers AT xs4all.nl>
11  * Original OV511 decompression code Copyright 1998-2000 OmniVision Technologies
12  *
13  * This program is free software; you can redistribute it and/or modify it
14  * under the terms of the GNU General Public License as published by the
15  * Free Software Foundation; version 2 of the License.
16  */
17 
18 #include <limits.h>
19 #include <string.h>
20 #include <unistd.h>
21 #include "helper-funcs.h"
22 
23 /******************************************************************************
24  * Compile-time Options
25  ******************************************************************************/
26 
27 /* Defining APPROXIMATE_MUL_BY_SHIFT increases performance by approximation
28  * the multiplications by shifts. I think there's no change in the
29  * calculated picture, but I'm not sure, so the choice is still in here. */
30 #undef APPROXIMATE_MUL_BY_SHIFT
31 
32 /******************************************************************************
33  * Local Data Types
34  ******************************************************************************/
35 
36 /* Make sure this remains naturally aligned and 2^n bytes in size */
37 struct tree_node {
38 	short left;		/* Pointer to left child node */
39 	short right;		/* Pointer to right child node */
40 	signed char depth;	/* Depth (starting at 1) if leaf, else -1 */
41 	signed char coeffbits;	/* Size of coefficient data, or zero if none */
42 	signed char skip;	/* Number of zero coefficients. Unused w/ DC */
43 	char padding;		/* Pad out to 8 bytes */
44 };
45 
46 struct comp_info {
47 	int bytes;		/* Number of processed input bytes */
48 	int bits;		/* Number of unprocessed input bits */
49 	int rawLen;		/* Total number of bytes in input buffer */
50 	unsigned char *qt;	/* Current quantization table */
51 };
52 
53 /******************************************************************************
54  * Constant Data Definitions
55  ******************************************************************************/
56 
57 /* Zig-Zag Table */
58 static const unsigned char ZigZag518[] = {
59 	0x00, 0x02, 0x03, 0x09,
60 	0x01, 0x04, 0x08, 0x0a,
61 	0x05, 0x07, 0x0b, 0x11,
62 	0x06, 0x0c, 0x10, 0x12,
63 	0x0d, 0x0f, 0x13, 0x19,
64 	0x0e, 0x14, 0x18, 0x1a,
65 	0x15, 0x17, 0x1b, 0x1e,
66 	0x16, 0x1c, 0x1d, 0x1f
67 };
68 
69 /* Huffman trees */
70 
71 static const struct tree_node treeYAC[] = {
72 	{  1,   4, -1,  0, -1}, {  2,   3, -1,  0, -1},
73 	{ -1,  -1,  2,  1,  0}, { -1,  -1,  2,  2,  0},
74 	{  5,   9, -1,  0, -1}, {  6,   7, -1,  0, -1},
75 	{ -1,  -1,  3,  3,  0}, {323,   8, -1,  0, -1},
76 	{ -1,  -1,  4,  4,  0}, { 10,  13, -1,  0, -1},
77 	{ 38,  11, -1,  0, -1}, { 12,  39, -1,  0, -1},
78 	{ -1,  -1,  5,  5,  0}, { 59,  14, -1,  0, -1},
79 	{ 15,  18, -1,  0, -1}, { 16, 113, -1,  0, -1},
80 	{ 17,  40, -1,  0, -1}, { -1,  -1,  7,  6,  0},
81 	{ 19,  22, -1,  0, -1}, { 20,  41, -1,  0, -1},
82 	{ 21,  61, -1,  0, -1}, { -1,  -1,  8,  7,  0},
83 	{ 23,  27, -1,  0, -1}, {169,  24, -1,  0, -1},
84 	{208,  25, -1,  0, -1}, { 26,  62, -1,  0, -1},
85 	{ -1,  -1, 10,  8,  0}, { 44,  28, -1,  0, -1},
86 	{ 63,  29, -1,  0, -1}, { 30, 191, -1,  0, -1},
87 	{ 31, 119, -1,  0, -1}, { 32,  82, -1,  0, -1},
88 	{ 33,  55, -1,  0, -1}, { 34,  48, -1,  0, -1},
89 	{171,  35, -1,  0, -1}, { 36,  37, -1,  0, -1},
90 	{ -1,  -1, 16,  9,  0}, { -1,  -1, 16, 10,  0},
91 	{ -1,  -1,  4,  1,  1}, { -1,  -1,  5,  2,  1},
92 	{ -1,  -1,  7,  3,  1}, {151,  42, -1,  0, -1},
93 	{ 43,  79, -1,  0, -1}, { -1,  -1,  9,  4,  1},
94 	{ 96,  45, -1,  0, -1}, {246,  46, -1,  0, -1},
95 	{ 47, 115, -1,  0, -1}, { -1,  -1, 11,  5,  1},
96 	{ 49,  52, -1,  0, -1}, { 50,  51, -1,  0, -1},
97 	{ -1,  -1, 16,  6,  1}, { -1,  -1, 16,  7,  1},
98 	{ 53,  54, -1,  0, -1}, { -1,  -1, 16,  8,  1},
99 	{ -1,  -1, 16,  9,  1}, { 56,  71, -1,  0, -1},
100 	{ 57,  68, -1,  0, -1}, { 58,  67, -1,  0, -1},
101 	{ -1,  -1, 16, 10,  1}, { 60,  77, -1,  0, -1},
102 	{ -1,  -1,  5,  1,  2}, { -1,  -1,  8,  2,  2},
103 	{ -1,  -1, 10,  3,  2}, {265,  64, -1,  0, -1},
104 	{ 65, 134, -1,  0, -1}, { 66,  80, -1,  0, -1},
105 	{ -1,  -1, 12,  4,  2}, { -1,  -1, 16,  5,  2},
106 	{ 69,  70, -1,  0, -1}, { -1,  -1, 16,  6,  2},
107 	{ -1,  -1, 16,  7,  2}, { 72,  75, -1,  0, -1},
108 	{ 73,  74, -1,  0, -1}, { -1,  -1, 16,  8,  2},
109 	{ -1,  -1, 16,  9,  2}, { 76,  81, -1,  0, -1},
110 	{ -1,  -1, 16, 10,  2}, { 78,  95, -1,  0, -1},
111 	{ -1,  -1,  6,  1,  3}, { -1,  -1,  9,  2,  3},
112 	{ -1,  -1, 12,  3,  3}, { -1,  -1, 16,  4,  3},
113 	{ 83, 101, -1,  0, -1}, { 84,  91, -1,  0, -1},
114 	{ 85,  88, -1,  0, -1}, { 86,  87, -1,  0, -1},
115 	{ -1,  -1, 16,  5,  3}, { -1,  -1, 16,  6,  3},
116 	{ 89,  90, -1,  0, -1}, { -1,  -1, 16,  7,  3},
117 	{ -1,  -1, 16,  8,  3}, { 92,  98, -1,  0, -1},
118 	{ 93,  94, -1,  0, -1}, { -1,  -1, 16,  9,  3},
119 	{ -1,  -1, 16, 10,  3}, { -1,  -1,  6,  1,  4},
120 	{ 97, 225, -1,  0, -1}, { -1,  -1, 10,  2,  4},
121 	{ 99, 100, -1,  0, -1}, { -1,  -1, 16,  3,  4},
122 	{ -1,  -1, 16,  4,  4}, {102, 109, -1,  0, -1},
123 	{103, 106, -1,  0, -1}, {104, 105, -1,  0, -1},
124 	{ -1,  -1, 16,  5,  4}, { -1,  -1, 16,  6,  4},
125 	{107, 108, -1,  0, -1}, { -1,  -1, 16,  7,  4},
126 	{ -1,  -1, 16,  8,  4}, {110, 116, -1,  0, -1},
127 	{111, 112, -1,  0, -1}, { -1,  -1, 16,  9,  4},
128 	{ -1,  -1, 16, 10,  4}, {114, 133, -1,  0, -1},
129 	{ -1,  -1,  7,  1,  5}, { -1,  -1, 11,  2,  5},
130 	{117, 118, -1,  0, -1}, { -1,  -1, 16,  3,  5},
131 	{ -1,  -1, 16,  4,  5}, {120, 156, -1,  0, -1},
132 	{121, 139, -1,  0, -1}, {122, 129, -1,  0, -1},
133 	{123, 126, -1,  0, -1}, {124, 125, -1,  0, -1},
134 	{ -1,  -1, 16,  5,  5}, { -1,  -1, 16,  6,  5},
135 	{127, 128, -1,  0, -1}, { -1,  -1, 16,  7,  5},
136 	{ -1,  -1, 16,  8,  5}, {130, 136, -1,  0, -1},
137 	{131, 132, -1,  0, -1}, { -1,  -1, 16,  9,  5},
138 	{ -1,  -1, 16, 10,  5}, { -1,  -1,  7,  1,  6},
139 	{135, 152, -1,  0, -1}, { -1,  -1, 12,  2,  6},
140 	{137, 138, -1,  0, -1}, { -1,  -1, 16,  3,  6},
141 	{ -1,  -1, 16,  4,  6}, {140, 147, -1,  0, -1},
142 	{141, 144, -1,  0, -1}, {142, 143, -1,  0, -1},
143 	{ -1,  -1, 16,  5,  6}, { -1,  -1, 16,  6,  6},
144 	{145, 146, -1,  0, -1}, { -1,  -1, 16,  7,  6},
145 	{ -1,  -1, 16,  8,  6}, {148, 153, -1,  0, -1},
146 	{149, 150, -1,  0, -1}, { -1,  -1, 16,  9,  6},
147 	{ -1,  -1, 16, 10,  6}, { -1,  -1,  8,  1,  7},
148 	{ -1,  -1, 12,  2,  7}, {154, 155, -1,  0, -1},
149 	{ -1,  -1, 16,  3,  7}, { -1,  -1, 16,  4,  7},
150 	{157, 175, -1,  0, -1}, {158, 165, -1,  0, -1},
151 	{159, 162, -1,  0, -1}, {160, 161, -1,  0, -1},
152 	{ -1,  -1, 16,  5,  7}, { -1,  -1, 16,  6,  7},
153 	{163, 164, -1,  0, -1}, { -1,  -1, 16,  7,  7},
154 	{ -1,  -1, 16,  8,  7}, {166, 172, -1,  0, -1},
155 	{167, 168, -1,  0, -1}, { -1,  -1, 16,  9,  7},
156 	{ -1,  -1, 16, 10,  7}, {170, 187, -1,  0, -1},
157 	{ -1,  -1,  9,  1,  8}, { -1,  -1, 15,  2,  8},
158 	{173, 174, -1,  0, -1}, { -1,  -1, 16,  3,  8},
159 	{ -1,  -1, 16,  4,  8}, {176, 183, -1,  0, -1},
160 	{177, 180, -1,  0, -1}, {178, 179, -1,  0, -1},
161 	{ -1,  -1, 16,  5,  8}, { -1,  -1, 16,  6,  8},
162 	{181, 182, -1,  0, -1}, { -1,  -1, 16,  7,  8},
163 	{ -1,  -1, 16,  8,  8}, {184, 188, -1,  0, -1},
164 	{185, 186, -1,  0, -1}, { -1,  -1, 16,  9,  8},
165 	{ -1,  -1, 16, 10,  8}, { -1,  -1,  9,  1,  9},
166 	{189, 190, -1,  0, -1}, { -1,  -1, 16,  2,  9},
167 	{ -1,  -1, 16,  3,  9}, {192, 258, -1,  0, -1},
168 	{193, 226, -1,  0, -1}, {194, 210, -1,  0, -1},
169 	{195, 202, -1,  0, -1}, {196, 199, -1,  0, -1},
170 	{197, 198, -1,  0, -1}, { -1,  -1, 16,  4,  9},
171 	{ -1,  -1, 16,  5,  9}, {200, 201, -1,  0, -1},
172 	{ -1,  -1, 16,  6,  9}, { -1,  -1, 16,  7,  9},
173 	{203, 206, -1,  0, -1}, {204, 205, -1,  0, -1},
174 	{ -1,  -1, 16,  8,  9}, { -1,  -1, 16,  9,  9},
175 	{207, 209, -1,  0, -1}, { -1,  -1, 16, 10,  9},
176 	{ -1,  -1,  9,  1, 10}, { -1,  -1, 16,  2, 10},
177 	{211, 218, -1,  0, -1}, {212, 215, -1,  0, -1},
178 	{213, 214, -1,  0, -1}, { -1,  -1, 16,  3, 10},
179 	{ -1,  -1, 16,  4, 10}, {216, 217, -1,  0, -1},
180 	{ -1,  -1, 16,  5, 10}, { -1,  -1, 16,  6, 10},
181 	{219, 222, -1,  0, -1}, {220, 221, -1,  0, -1},
182 	{ -1,  -1, 16,  7, 10}, { -1,  -1, 16,  8, 10},
183 	{223, 224, -1,  0, -1}, { -1,  -1, 16,  9, 10},
184 	{ -1,  -1, 16, 10, 10}, { -1,  -1, 10,  1, 11},
185 	{227, 242, -1,  0, -1}, {228, 235, -1,  0, -1},
186 	{229, 232, -1,  0, -1}, {230, 231, -1,  0, -1},
187 	{ -1,  -1, 16,  2, 11}, { -1,  -1, 16,  3, 11},
188 	{233, 234, -1,  0, -1}, { -1,  -1, 16,  4, 11},
189 	{ -1,  -1, 16,  5, 11}, {236, 239, -1,  0, -1},
190 	{237, 238, -1,  0, -1}, { -1,  -1, 16,  6, 11},
191 	{ -1,  -1, 16,  7, 11}, {240, 241, -1,  0, -1},
192 	{ -1,  -1, 16,  8, 11}, { -1,  -1, 16,  9, 11},
193 	{243, 251, -1,  0, -1}, {244, 248, -1,  0, -1},
194 	{245, 247, -1,  0, -1}, { -1,  -1, 16, 10, 11},
195 	{ -1,  -1, 10,  1, 12}, { -1,  -1, 16,  2, 12},
196 	{249, 250, -1,  0, -1}, { -1,  -1, 16,  3, 12},
197 	{ -1,  -1, 16,  4, 12}, {252, 255, -1,  0, -1},
198 	{253, 254, -1,  0, -1}, { -1,  -1, 16,  5, 12},
199 	{ -1,  -1, 16,  6, 12}, {256, 257, -1,  0, -1},
200 	{ -1,  -1, 16,  7, 12}, { -1,  -1, 16,  8, 12},
201 	{259, 292, -1,  0, -1}, {260, 277, -1,  0, -1},
202 	{261, 270, -1,  0, -1}, {262, 267, -1,  0, -1},
203 	{263, 264, -1,  0, -1}, { -1,  -1, 16,  9, 12},
204 	{ -1,  -1, 16, 10, 12}, {266, 322, -1,  0, -1},
205 	{ -1,  -1, 11,  1, 13}, {268, 269, -1,  0, -1},
206 	{ -1,  -1, 16,  2, 13}, { -1,  -1, 16,  3, 13},
207 	{271, 274, -1,  0, -1}, {272, 273, -1,  0, -1},
208 	{ -1,  -1, 16,  4, 13}, { -1,  -1, 16,  5, 13},
209 	{275, 276, -1,  0, -1}, { -1,  -1, 16,  6, 13},
210 	{ -1,  -1, 16,  7, 13}, {278, 285, -1,  0, -1},
211 	{279, 282, -1,  0, -1}, {280, 281, -1,  0, -1},
212 	{ -1,  -1, 16,  8, 13}, { -1,  -1, 16,  9, 13},
213 	{283, 284, -1,  0, -1}, { -1,  -1, 16, 10, 13},
214 	{ -1,  -1, 16,  1, 14}, {286, 289, -1,  0, -1},
215 	{287, 288, -1,  0, -1}, { -1,  -1, 16,  2, 14},
216 	{ -1,  -1, 16,  3, 14}, {290, 291, -1,  0, -1},
217 	{ -1,  -1, 16,  4, 14}, { -1,  -1, 16,  5, 14},
218 	{293, 308, -1,  0, -1}, {294, 301, -1,  0, -1},
219 	{295, 298, -1,  0, -1}, {296, 297, -1,  0, -1},
220 	{ -1,  -1, 16,  6, 14}, { -1,  -1, 16,  7, 14},
221 	{299, 300, -1,  0, -1}, { -1,  -1, 16,  8, 14},
222 	{ -1,  -1, 16,  9, 14}, {302, 305, -1,  0, -1},
223 	{303, 304, -1,  0, -1}, { -1,  -1, 16, 10, 14},
224 	{ -1,  -1, 16,  1, 15}, {306, 307, -1,  0, -1},
225 	{ -1,  -1, 16,  2, 15}, { -1,  -1, 16,  3, 15},
226 	{309, 316, -1,  0, -1}, {310, 313, -1,  0, -1},
227 	{311, 312, -1,  0, -1}, { -1,  -1, 16,  4, 15},
228 	{ -1,  -1, 16,  5, 15}, {314, 315, -1,  0, -1},
229 	{ -1,  -1, 16,  6, 15}, { -1,  -1, 16,  7, 15},
230 	{317, 320, -1,  0, -1}, {318, 319, -1,  0, -1},
231 	{ -1,  -1, 16,  8, 15}, { -1,  -1, 16,  9, 15},
232 	{321,  -1, -1,  0, -1}, { -1,  -1, 16, 10, 15},
233 	{ -1,  -1, 11,  0, 16}, { -1,  -1,  4,  0, -1},
234 };
235 
236 static const struct tree_node treeUVAC[] = {
237 	{  1,   3, -1,  0, -1}, {323,   2, -1,  0, -1},
238 	{ -1,  -1,  2,  1,  0}, {  4,   8, -1,  0, -1},
239 	{  5,   6, -1,  0, -1}, { -1,  -1,  3,  2,  0},
240 	{  7,  37, -1,  0, -1}, { -1,  -1,  4,  3,  0},
241 	{  9,  13, -1,  0, -1}, { 10,  60, -1,  0, -1},
242 	{ 11,  12, -1,  0, -1}, { -1,  -1,  5,  4,  0},
243 	{ -1,  -1,  5,  5,  0}, { 14,  17, -1,  0, -1},
244 	{ 15,  97, -1,  0, -1}, { 16,  38, -1,  0, -1},
245 	{ -1,  -1,  6,  6,  0}, { 18,  21, -1,  0, -1},
246 	{ 19,  39, -1,  0, -1}, { 20, 135, -1,  0, -1},
247 	{ -1,  -1,  7,  7,  0}, { 22,  26, -1,  0, -1},
248 	{ 82,  23, -1,  0, -1}, { 24,  99, -1,  0, -1},
249 	{ 25,  42, -1,  0, -1}, { -1,  -1,  9,  8,  0},
250 	{ 27,  31, -1,  0, -1}, {211,  28, -1,  0, -1},
251 	{248,  29, -1,  0, -1}, { 30,  63, -1,  0, -1},
252 	{ -1,  -1, 10,  9,  0}, { 43,  32, -1,  0, -1},
253 	{ 33,  48, -1,  0, -1}, {153,  34, -1,  0, -1},
254 	{ 35,  64, -1,  0, -1}, { 36,  47, -1,  0, -1},
255 	{ -1,  -1, 12, 10,  0}, { -1,  -1,  4,  1,  1},
256 	{ -1,  -1,  6,  2,  1}, {152,  40, -1,  0, -1},
257 	{ 41,  62, -1,  0, -1}, { -1,  -1,  8,  3,  1},
258 	{ -1,  -1,  9,  4,  1}, { 84,  44, -1,  0, -1},
259 	{322,  45, -1,  0, -1}, { 46, 136, -1,  0, -1},
260 	{ -1,  -1, 11,  5,  1}, { -1,  -1, 12,  6,  1},
261 	{ 49, 189, -1,  0, -1}, { 50, 119, -1,  0, -1},
262 	{ 51,  76, -1,  0, -1}, { 66,  52, -1,  0, -1},
263 	{ 53,  69, -1,  0, -1}, { 54,  57, -1,  0, -1},
264 	{ 55,  56, -1,  0, -1}, { -1,  -1, 16,  7,  1},
265 	{ -1,  -1, 16,  8,  1}, { 58,  59, -1,  0, -1},
266 	{ -1,  -1, 16,  9,  1}, { -1,  -1, 16, 10,  1},
267 	{ 61,  81, -1,  0, -1}, { -1,  -1,  5,  1,  2},
268 	{ -1,  -1,  8,  2,  2}, { -1,  -1, 10,  3,  2},
269 	{ 65,  86, -1,  0, -1}, { -1,  -1, 12,  4,  2},
270 	{286,  67, -1,  0, -1}, { 68, 304, -1,  0, -1},
271 	{ -1,  -1, 15,  5,  2}, { 70,  73, -1,  0, -1},
272 	{ 71,  72, -1,  0, -1}, { -1,  -1, 16,  6,  2},
273 	{ -1,  -1, 16,  7,  2}, { 74,  75, -1,  0, -1},
274 	{ -1,  -1, 16,  8,  2}, { -1,  -1, 16,  9,  2},
275 	{ 77, 102, -1,  0, -1}, { 78,  91, -1,  0, -1},
276 	{ 79,  88, -1,  0, -1}, { 80,  87, -1,  0, -1},
277 	{ -1,  -1, 16, 10,  2}, { -1,  -1,  5,  1,  3},
278 	{ 83, 171, -1,  0, -1}, { -1,  -1,  8,  2,  3},
279 	{ 85, 117, -1,  0, -1}, { -1,  -1, 10,  3,  3},
280 	{ -1,  -1, 12,  4,  3}, { -1,  -1, 16,  5,  3},
281 	{ 89,  90, -1,  0, -1}, { -1,  -1, 16,  6,  3},
282 	{ -1,  -1, 16,  7,  3}, { 92,  95, -1,  0, -1},
283 	{ 93,  94, -1,  0, -1}, { -1,  -1, 16,  8,  3},
284 	{ -1,  -1, 16,  9,  3}, { 96, 101, -1,  0, -1},
285 	{ -1,  -1, 16, 10,  3}, { 98, 116, -1,  0, -1},
286 	{ -1,  -1,  6,  1,  4}, {100, 188, -1,  0, -1},
287 	{ -1,  -1,  9,  2,  4}, { -1,  -1, 16,  3,  4},
288 	{103, 110, -1,  0, -1}, {104, 107, -1,  0, -1},
289 	{105, 106, -1,  0, -1}, { -1,  -1, 16,  4,  4},
290 	{ -1,  -1, 16,  5,  4}, {108, 109, -1,  0, -1},
291 	{ -1,  -1, 16,  6,  4}, { -1,  -1, 16,  7,  4},
292 	{111, 114, -1,  0, -1}, {112, 113, -1,  0, -1},
293 	{ -1,  -1, 16,  8,  4}, { -1,  -1, 16,  9,  4},
294 	{115, 118, -1,  0, -1}, { -1,  -1, 16, 10,  4},
295 	{ -1,  -1,  6,  1,  5}, { -1,  -1, 10,  2,  5},
296 	{ -1,  -1, 16,  3,  5}, {120, 156, -1,  0, -1},
297 	{121, 138, -1,  0, -1}, {122, 129, -1,  0, -1},
298 	{123, 126, -1,  0, -1}, {124, 125, -1,  0, -1},
299 	{ -1,  -1, 16,  4,  5}, { -1,  -1, 16,  5,  5},
300 	{127, 128, -1,  0, -1}, { -1,  -1, 16,  6,  5},
301 	{ -1,  -1, 16,  7,  5}, {130, 133, -1,  0, -1},
302 	{131, 132, -1,  0, -1}, { -1,  -1, 16,  8,  5},
303 	{ -1,  -1, 16,  9,  5}, {134, 137, -1,  0, -1},
304 	{ -1,  -1, 16, 10,  5}, { -1,  -1,  7,  1,  6},
305 	{ -1,  -1, 11,  2,  6}, { -1,  -1, 16,  3,  6},
306 	{139, 146, -1,  0, -1}, {140, 143, -1,  0, -1},
307 	{141, 142, -1,  0, -1}, { -1,  -1, 16,  4,  6},
308 	{ -1,  -1, 16,  5,  6}, {144, 145, -1,  0, -1},
309 	{ -1,  -1, 16,  6,  6}, { -1,  -1, 16,  7,  6},
310 	{147, 150, -1,  0, -1}, {148, 149, -1,  0, -1},
311 	{ -1,  -1, 16,  8,  6}, { -1,  -1, 16,  9,  6},
312 	{151, 155, -1,  0, -1}, { -1,  -1, 16, 10,  6},
313 	{ -1,  -1,  7,  1,  7}, {154, 267, -1,  0, -1},
314 	{ -1,  -1, 11,  2,  7}, { -1,  -1, 16,  3,  7},
315 	{157, 173, -1,  0, -1}, {158, 165, -1,  0, -1},
316 	{159, 162, -1,  0, -1}, {160, 161, -1,  0, -1},
317 	{ -1,  -1, 16,  4,  7}, { -1,  -1, 16,  5,  7},
318 	{163, 164, -1,  0, -1}, { -1,  -1, 16,  6,  7},
319 	{ -1,  -1, 16,  7,  7}, {166, 169, -1,  0, -1},
320 	{167, 168, -1,  0, -1}, { -1,  -1, 16,  8,  7},
321 	{ -1,  -1, 16,  9,  7}, {170, 172, -1,  0, -1},
322 	{ -1,  -1, 16, 10,  7}, { -1,  -1,  8,  1,  8},
323 	{ -1,  -1, 16,  2,  8}, {174, 181, -1,  0, -1},
324 	{175, 178, -1,  0, -1}, {176, 177, -1,  0, -1},
325 	{ -1,  -1, 16,  3,  8}, { -1,  -1, 16,  4,  8},
326 	{179, 180, -1,  0, -1}, { -1,  -1, 16,  5,  8},
327 	{ -1,  -1, 16,  6,  8}, {182, 185, -1,  0, -1},
328 	{183, 184, -1,  0, -1}, { -1,  -1, 16,  7,  8},
329 	{ -1,  -1, 16,  8,  8}, {186, 187, -1,  0, -1},
330 	{ -1,  -1, 16,  9,  8}, { -1,  -1, 16, 10,  8},
331 	{ -1,  -1,  9,  1,  9}, {190, 257, -1,  0, -1},
332 	{191, 224, -1,  0, -1}, {192, 207, -1,  0, -1},
333 	{193, 200, -1,  0, -1}, {194, 197, -1,  0, -1},
334 	{195, 196, -1,  0, -1}, { -1,  -1, 16,  2,  9},
335 	{ -1,  -1, 16,  3,  9}, {198, 199, -1,  0, -1},
336 	{ -1,  -1, 16,  4,  9}, { -1,  -1, 16,  5,  9},
337 	{201, 204, -1,  0, -1}, {202, 203, -1,  0, -1},
338 	{ -1,  -1, 16,  6,  9}, { -1,  -1, 16,  7,  9},
339 	{205, 206, -1,  0, -1}, { -1,  -1, 16,  8,  9},
340 	{ -1,  -1, 16,  9,  9}, {208, 217, -1,  0, -1},
341 	{209, 214, -1,  0, -1}, {210, 213, -1,  0, -1},
342 	{ -1,  -1, 16, 10,  9}, {212, 230, -1,  0, -1},
343 	{ -1,  -1,  9,  1, 10}, { -1,  -1, 16,  2, 10},
344 	{215, 216, -1,  0, -1}, { -1,  -1, 16,  3, 10},
345 	{ -1,  -1, 16,  4, 10}, {218, 221, -1,  0, -1},
346 	{219, 220, -1,  0, -1}, { -1,  -1, 16,  5, 10},
347 	{ -1,  -1, 16,  6, 10}, {222, 223, -1,  0, -1},
348 	{ -1,  -1, 16,  7, 10}, { -1,  -1, 16,  8, 10},
349 	{225, 241, -1,  0, -1}, {226, 234, -1,  0, -1},
350 	{227, 231, -1,  0, -1}, {228, 229, -1,  0, -1},
351 	{ -1,  -1, 16,  9, 10}, { -1,  -1, 16, 10, 10},
352 	{ -1,  -1,  9,  1, 11}, {232, 233, -1,  0, -1},
353 	{ -1,  -1, 16,  2, 11}, { -1,  -1, 16,  3, 11},
354 	{235, 238, -1,  0, -1}, {236, 237, -1,  0, -1},
355 	{ -1,  -1, 16,  4, 11}, { -1,  -1, 16,  5, 11},
356 	{239, 240, -1,  0, -1}, { -1,  -1, 16,  6, 11},
357 	{ -1,  -1, 16,  7, 11}, {242, 250, -1,  0, -1},
358 	{243, 246, -1,  0, -1}, {244, 245, -1,  0, -1},
359 	{ -1,  -1, 16,  8, 11}, { -1,  -1, 16,  9, 11},
360 	{247, 249, -1,  0, -1}, { -1,  -1, 16, 10, 11},
361 	{ -1,  -1,  9,  1, 12}, { -1,  -1, 16,  2, 12},
362 	{251, 254, -1,  0, -1}, {252, 253, -1,  0, -1},
363 	{ -1,  -1, 16,  3, 12}, { -1,  -1, 16,  4, 12},
364 	{255, 256, -1,  0, -1}, { -1,  -1, 16,  5, 12},
365 	{ -1,  -1, 16,  6, 12}, {258, 291, -1,  0, -1},
366 	{259, 275, -1,  0, -1}, {260, 268, -1,  0, -1},
367 	{261, 264, -1,  0, -1}, {262, 263, -1,  0, -1},
368 	{ -1,  -1, 16,  7, 12}, { -1,  -1, 16,  8, 12},
369 	{265, 266, -1,  0, -1}, { -1,  -1, 16,  9, 12},
370 	{ -1,  -1, 16, 10, 12}, { -1,  -1, 11,  1, 13},
371 	{269, 272, -1,  0, -1}, {270, 271, -1,  0, -1},
372 	{ -1,  -1, 16,  2, 13}, { -1,  -1, 16,  3, 13},
373 	{273, 274, -1,  0, -1}, { -1,  -1, 16,  4, 13},
374 	{ -1,  -1, 16,  5, 13}, {276, 283, -1,  0, -1},
375 	{277, 280, -1,  0, -1}, {278, 279, -1,  0, -1},
376 	{ -1,  -1, 16,  6, 13}, { -1,  -1, 16,  7, 13},
377 	{281, 282, -1,  0, -1}, { -1,  -1, 16,  8, 13},
378 	{ -1,  -1, 16,  9, 13}, {284, 288, -1,  0, -1},
379 	{285, 287, -1,  0, -1}, { -1,  -1, 16, 10, 13},
380 	{ -1,  -1, 14,  1, 14}, { -1,  -1, 16,  2, 14},
381 	{289, 290, -1,  0, -1}, { -1,  -1, 16,  3, 14},
382 	{ -1,  -1, 16,  4, 14}, {292, 308, -1,  0, -1},
383 	{293, 300, -1,  0, -1}, {294, 297, -1,  0, -1},
384 	{295, 296, -1,  0, -1}, { -1,  -1, 16,  5, 14},
385 	{ -1,  -1, 16,  6, 14}, {298, 299, -1,  0, -1},
386 	{ -1,  -1, 16,  7, 14}, { -1,  -1, 16,  8, 14},
387 	{301, 305, -1,  0, -1}, {302, 303, -1,  0, -1},
388 	{ -1,  -1, 16,  9, 14}, { -1,  -1, 16, 10, 14},
389 	{ -1,  -1, 15,  1, 15}, {306, 307, -1,  0, -1},
390 	{ -1,  -1, 16,  2, 15}, { -1,  -1, 16,  3, 15},
391 	{309, 316, -1,  0, -1}, {310, 313, -1,  0, -1},
392 	{311, 312, -1,  0, -1}, { -1,  -1, 16,  4, 15},
393 	{ -1,  -1, 16,  5, 15}, {314, 315, -1,  0, -1},
394 	{ -1,  -1, 16,  6, 15}, { -1,  -1, 16,  7, 15},
395 	{317, 320, -1,  0, -1}, {318, 319, -1,  0, -1},
396 	{ -1,  -1, 16,  8, 15}, { -1,  -1, 16,  9, 15},
397 	{321,  -1, -1,  0, -1}, { -1,  -1, 16, 10, 15},
398 	{ -1,  -1, 10,  0, 16}, { -1,  -1,  2,  0, -1},
399 };
400 
401 static const struct tree_node treeYDC[] = {
402 	{  1,   6, -1,  0}, {  2,   3, -1,  0},
403 	{ -1,  -1,  2,  0}, {  4,   5, -1,  0},
404 	{ -1,  -1,  3,  1}, { -1,  -1,  3,  2},
405 	{  7,  10, -1,  0}, {  8,   9, -1,  0},
406 	{ -1,  -1,  3,  3}, { -1,  -1,  3,  4},
407 	{ 11,  12, -1,  0}, { -1,  -1,  3,  5},
408 	{ 13,  14, -1,  0}, { -1,  -1,  4,  6},
409 	{ 15,  16, -1,  0}, { -1,  -1,  5,  7},
410 	{ 17,  18, -1,  0}, { -1,  -1,  6,  8},
411 	{ 19,  20, -1,  0}, { -1,  -1,  7,  9},
412 	{ 21,  22, -1,  0}, { -1,  -1,  8, 10},
413 	{ 23,  -1, -1,  0}, { -1,  -1,  9, 11},
414 };
415 
416 static const struct tree_node treeUVDC[] = {
417 	{  1,   4, -1,  0}, {  2,   3, -1,  0},
418 	{ -1,  -1,  2,  0}, { -1,  -1,  2,  1},
419 	{  5,   6, -1,  0}, { -1,  -1,  2,  2},
420 	{  7,   8, -1,  0}, { -1,  -1,  3,  3},
421 	{  9,  10, -1,  0}, { -1,  -1,  4,  4},
422 	{ 11,  12, -1,  0}, { -1,  -1,  5,  5},
423 	{ 13,  14, -1,  0}, { -1,  -1,  6,  6},
424 	{ 15,  16, -1,  0}, { -1,  -1,  7,  7},
425 	{ 17,  18, -1,  0}, { -1,  -1,  8,  8},
426 	{ 19,  20, -1,  0}, { -1,  -1,  9,  9},
427 	{ 21,  22, -1,  0}, { -1,  -1, 10, 10},
428 	{ 23,  -1, -1,  0}, { -1,  -1, 11, 11},
429 };
430 
431 /******************************************************************************
432  * Huffman Decoder
433  ******************************************************************************/
434 
435 /* Note: There is no penalty for passing the tree as an argument, since dummy
436  * args are passed anyway (to maintain 16-byte stack alignment), and since the
437  * address is loaded into a register either way. */
438 
439 /* If no node is found, coeffbits and skip will not be modified */
440 /* Return: Depth of node found, or -1 if invalid input code */
441 static int
getNodeAC(unsigned int in,signed char * coeffbits,signed char * skip,const struct tree_node * tree)442 getNodeAC(unsigned int in, signed char *coeffbits, signed char *skip,
443 		const struct tree_node *tree)
444 {
445 	int node = 0;
446 	int i = 0;
447 	int depth;
448 
449 	do {
450 		if ((in & 0x80000000) == 0)
451 			node = tree[node].left;
452 		else
453 			node = tree[node].right;
454 
455 		if (node == -1)
456 			break;
457 
458 		depth = tree[node].depth;
459 
460 		/* Is it a leaf? If not, branch downward */
461 		if (depth != -1) {
462 			*coeffbits = tree[node].coeffbits;
463 			*skip = tree[node].skip;
464 			return depth;
465 		}
466 
467 		in <<= 1;
468 		++i;
469 	} while (i <= 15);
470 
471 	return -1;
472 }
473 
474 /* If no node is found, coeffbits will not be modified */
475 /* Return: Depth of node found, or -1 if invalid input code */
476 static int
getNodeDC(unsigned int in,signed char * coeffbits,const struct tree_node * tree)477 getNodeDC(unsigned int in, signed char *coeffbits, const struct tree_node *tree)
478 {
479 	int node = 0;
480 	int i = 0;
481 	int depth;
482 
483 	do {
484 		if ((in & 0x80000000) == 0)
485 			node = tree[node].left;
486 		else
487 			node = tree[node].right;
488 
489 		if (node == -1)
490 			break;
491 
492 		depth = tree[node].depth;
493 
494 		/* Is it a leaf? If not, branch downward */
495 		if (depth != -1) {
496 			*coeffbits = tree[node].coeffbits;
497 			return depth;
498 		}
499 
500 		in <<= 1;
501 		++i;
502 	} while (i <= 15);
503 
504 	return -1;
505 }
506 
507 static inline unsigned int
getBytes(int * rawData,struct comp_info * cinfo)508 getBytes(int *rawData, struct comp_info *cinfo)
509 {
510 	int bufLen = cinfo->rawLen;
511 	int bits = cinfo->bits;
512 	int bytes = cinfo->bytes;
513 	unsigned char *in = bytes + (unsigned char *) rawData;
514 	unsigned char b1, b2, b3, b4, b5;
515 	unsigned int packedIn;
516 
517 	/* Pull 5 bytes out of raw data */
518 	if (bytes < bufLen - 4) {
519 		b1 = in[0];
520 		b2 = in[1];
521 		b3 = in[2];
522 		b4 = in[3];
523 		b5 = in[4];
524 	} else {
525 		if (bytes < bufLen - 3) {
526 			b1 = in[0];
527 			b2 = in[1];
528 			b3 = in[2];
529 			b4 = in[3];
530 		} else {
531 			if (bytes < bufLen - 2) {
532 				b1 = in[0];
533 				b2 = in[1];
534 				b3 = in[2];
535 			} else {
536 				if (bytes < bufLen - 1) {
537 					b1 = in[0];
538 					b2 = in[1];
539 				} else {
540 					if (bytes <= bufLen)
541 						b1 = in[0];
542 					else
543 						b1 = 0;
544 					b2 = 0;
545 				}
546 				b3 = 0;
547 			}
548 			b4 = 0;
549 		}
550 		b5 = 0;
551 	}
552 
553 	/* Pack the bytes */
554 	packedIn  = b1 << 24;
555 	packedIn += b2 << 16;
556 	packedIn += b3 << 8;
557 	packedIn += b4;
558 
559 	if (bits != 0) {
560 		packedIn = packedIn << bits;
561 		packedIn += b5 >> (8 - bits);
562 	}
563 
564 	return packedIn;
565 }
566 
567 static int
getACCoefficient(int * rawData,int * coeff,struct comp_info * cinfo,const struct tree_node * tree)568 getACCoefficient(int *rawData, int *coeff, struct comp_info *cinfo,
569 		const struct tree_node *tree)
570 {
571 	int input, bits, bytes, tmp_c;
572 	signed char coeffbits = 0;
573 	signed char skip = 0;
574 
575 	input = getBytes(rawData, cinfo);
576 	bits = getNodeAC(input, &coeffbits, &skip, tree);
577 
578 	if (coeffbits) {
579 		input = input << (bits - 1);
580 		input &= 0x7fffffff;
581 		if (!(input & 0x40000000))
582 			input |= 0x80000000;
583 
584 		tmp_c = input >> (31 - coeffbits);
585 		if (tmp_c < 0)
586 			tmp_c++;
587 		*coeff = tmp_c;
588 
589 		bits += coeffbits;
590 	}
591 
592 	bytes = (bits + cinfo->bits) >> 3;
593 	cinfo->bytes += bytes;
594 	cinfo->bits += bits - (bytes << 3);
595 
596 	return skip;
597 }
598 
599 static void
getDCCoefficient(int * rawData,int * coeff,struct comp_info * cinfo,const struct tree_node * tree)600 getDCCoefficient(int *rawData, int *coeff, struct comp_info *cinfo,
601 		const struct tree_node *tree)
602 {
603 	int input, bits, bytes, tmp_c;
604 	signed char coeffbits = 0;
605 
606 	input = getBytes(rawData, cinfo);
607 	bits = getNodeDC(input, &coeffbits, tree);
608 
609 	if (bits == -1) {
610 		bits = 1;	/* Try to re-sync at the next bit */
611 		*coeff = 0;	/* Indicates no change from last DC */
612 	} else {
613 
614 		input = input << (bits - 1);
615 		input &= 0x7fffffff;
616 		if (!(input & 0x40000000))
617 			input |= 0x80000000;
618 
619 		tmp_c = input >> (31 - coeffbits);
620 		if (tmp_c < 0)
621 			tmp_c++;
622 		*coeff = tmp_c;
623 
624 		bits += coeffbits;
625 	}
626 
627 	bytes = (bits + cinfo->bits) >> 3;
628 	cinfo->bytes += bytes;
629 	cinfo->bits += bits - (bytes << 3);
630 }
631 
632 /* For AC coefficients, here is what the "skip" value means:
633  *   -1: Either the 8x4 block has ended, or the decoding failed.
634  *    0: Use the returned coeff. Don't skip anything.
635  * 1-15: The next <skip> coeffs are zero. The returned coeff is used.
636  *   16: The next 16 coeffs are zero. The returned coeff is ignored.
637  *
638  * You must ensure that the C[] array not be overrun, or stack corruption will
639  * result.
640  */
641 static void
huffmanDecoderY(int * C,int * pIn,struct comp_info * cinfo)642 huffmanDecoderY(int *C, int *pIn, struct comp_info *cinfo)
643 {
644 	int coeff = 0;
645 	int i = 1;
646 	int k, skip;
647 
648 	getDCCoefficient(pIn, C, cinfo, treeYDC);
649 
650 	i = 1;
651 	do {
652 		skip = getACCoefficient(pIn, &coeff, cinfo, treeYAC);
653 
654 		if (skip == -1) {
655 			break;
656 		}
657 		if (skip == 0) {
658 			C[i++] = coeff;
659 		} else if (skip == 16) {
660 			k = 16;
661 			if (i > 16)
662 				k = 32 - i;
663 
664 			while (k--)
665 				C[i++] = 0;
666 		} else {
667 			k = skip;
668 			if (skip > 31 - i)
669 				k = 31 - i;
670 
671 			while (k--)
672 				C[i++] = 0;
673 
674 			C[i++] = coeff;
675 		}
676 	} while (i <= 31);
677 
678 	if (skip == -1)
679 		while (i <= 31)
680 			C[i++] = 0;
681 	else
682 		getACCoefficient(pIn, &coeff, cinfo, treeYAC);
683 }
684 
685 /* Same as huffmanDecoderY, except for the tables used */
686 static void
huffmanDecoderUV(int * C,int * pIn,struct comp_info * cinfo)687 huffmanDecoderUV(int *C, int *pIn, struct comp_info *cinfo)
688 {
689 	int coeff = 0;
690 	int i = 1;
691 	int k, skip;
692 
693 	getDCCoefficient(pIn, C, cinfo, treeUVDC);
694 
695 	i = 1;
696 	do {
697 		skip = getACCoefficient(pIn, &coeff, cinfo, treeUVAC);
698 
699 		if (skip == -1) {
700 			break;
701 		}
702 		if (skip == 0) {
703 			C[i++] = coeff;
704 		} else if (skip == 16) {
705 			k = 16;
706 			if (i > 16)
707 				k = 32 - i;
708 
709 			while (k--)
710 				C[i++] = 0;
711 		} else {
712 			k = skip;
713 			if (skip > 31 - i)
714 				k = 31 - i;
715 
716 			while (k--)
717 				C[i++] = 0;
718 
719 			C[i++] = coeff;
720 		}
721 	} while (i <= 31);
722 
723 	if (skip == -1)
724 		while (i <= 31)
725 			C[i++] = 0;
726 	else
727 		getACCoefficient(pIn, &coeff, cinfo, treeUVAC);
728 }
729 
730 /******************************************************************************
731  * iDCT Functions
732  ******************************************************************************/
733 
734 #ifndef APPROXIMATE_MUL_BY_SHIFT
735 
736 #define IDCT_MESSAGE "iDCT with multiply"
737 
738 #define TIMES_16382(u)	((u) ? 16382 * (u) : 0)
739 #define TIMES_23168(u)	((u) ? 23168 * (u) : 0)
740 #define TIMES_30270(u)	((u) ? 30270 * (u) : 0)
741 #define TIMES_41986(u)	((u) ? 41986 * (u) : 0)
742 #define TIMES_35594(u)	((u) ? 35594 * (u) : 0)
743 #define TIMES_23783(u)	((u) ? 23783 * (u) : 0)
744 #define TIMES_8351(u)	((u) ? 8351  * (u) : 0)
745 #define TIMES_17391(u)	((u) ? 17391 * (u) : 0)
746 #define TIMES_14743(u)	((u) ? 14743 * (u) : 0)
747 #define TIMES_9851(u)	((u) ? 9851  * (u) : 0)
748 #define TIMES_3459(u)	((u) ? 3459  * (u) : 0)
749 #define TIMES_32134(u)	((u) ? 32134 * (u) : 0)
750 #define TIMES_27242(u)	((u) ? 27242 * (u) : 0)
751 #define TIMES_18202(u)	((u) ? 18202 * (u) : 0)
752 #define TIMES_6392(u)	((u) ? 6392  * (u) : 0)
753 #define TIMES_39550(u)	((u) ? 39550 * (u) : 0)
754 #define TIMES_6785(u)	((u) ? 6785  * (u) : 0)
755 #define TIMES_12538(u)	((u) ? 12538 * (u) : 0)
756 
757 #else
758 
759 #define IDCT_MESSAGE "iDCT with shift"
760 
761 #define TIMES_16382(u) ((u) ? x = (u), (x << 14) - (x << 1) : 0)
762 #define TIMES_23168(u) ((u) ? x = (u), (x << 14) + (x << 12) + (x << 11) + (x << 9) : 0)
763 #define TIMES_30270(u) ((u) ? x = (u), (x << 15) - (x << 11) : 0)
764 #define TIMES_41986(u) ((u) ? x = (u), (x << 15) + (x << 13) + (x << 10) : 0)
765 #define TIMES_35594(u) ((u) ? x = (u), (x << 15) + (x << 11) + (x << 9) + (x << 8) : 0)
766 #define TIMES_23783(u) ((u) ? x = (u), (x << 14) + (x << 13) - (x << 9) - (x << 8) : 0)
767 #define TIMES_8351(u)  ((u) ? x = (u), (x << 13) : 0)
768 #define TIMES_17391(u) ((u) ? x = (u), (x << 14) + (x << 10) : 0)
769 #define TIMES_14743(u) ((u) ? x = (u), (x << 14) - (x << 10) - (x << 9) : 0)
770 #define TIMES_9851(u)  ((u) ? x = (u), (x << 13) + (x << 10) + (x << 9) : 0)
771 #define TIMES_3459(u)  ((u) ? x = (u), (x << 12) - (x << 9) : 0)
772 #define TIMES_32134(u) ((u) ? x = (u), (x << 15) - (x << 9) : 0)
773 #define TIMES_27242(u) ((u) ? x = (u), (x << 14) + (x << 13) + (x << 11) + (x << 9) : 0)
774 #define TIMES_18202(u) ((u) ? x = (u), (x << 14) + (x << 11) - (x << 8) : 0)
775 #define TIMES_6392(u)  ((u) ? x = (u), (x << 13) - (x << 11) + (x << 8) : 0)
776 #define TIMES_39550(u) ((u) ? x = (u), (x << 15) + (x << 12) + (x << 11) + (x << 9) : 0)
777 #define TIMES_6785(u)  ((u) ? x = (u), (x << 12) + (x << 11) + (x << 9) : 0)
778 #define TIMES_12538(u) ((u) ? x = (u), (x << 13) + (x << 12) + (x << 8) : 0)
779 
780 /*
781  * The variables C0, C4, C16 and C20 can also be removed from the algorithm
782  * if APPROXIMATE_MUL_BY_SHIFTS is defined. They store correction values
783  * and can be considered insignificant.
784  */
785 
786 #endif
787 
788 static void
DCT_8x4(int * coeff,unsigned char * out)789 DCT_8x4(int *coeff, unsigned char *out)
790 	/* pre: coeff == coefficients
791 	   post: coeff != coefficients
792 	 ** DO NOT ASSUME coeff TO BE THE SAME BEFORE AND AFTER CALLING THIS FUNCTION!
793 	 */
794 {
795 	register int base, val1, val2, val3;
796 	int tmp1, tmp2;
797 	int C4, C16, C20;
798 	int C2_18, C6_22, C1_17, C3_19, C5_21, C7_23;
799 	register int t;
800 #ifdef APPROXIMATE_MUL_BY_SHIFT
801 	register int x;
802 #endif
803 
804 	C4 = coeff[4];
805 	C16 = coeff[16];
806 	C20 = coeff[20];
807 
808 	coeff[0] = TIMES_23168(coeff[0]);
809 	coeff[4] = TIMES_23168(coeff[4]);
810 	coeff[16] = TIMES_23168(coeff[16]);
811 	coeff[20] = TIMES_23168(coeff[20]);
812 
813 	C2_18 = coeff[2] + coeff[18];
814 	C6_22 = coeff[6] + coeff[22];
815 	C1_17 = coeff[1] + coeff[17];
816 	C3_19 = coeff[3] + coeff[19];
817 	C5_21 = coeff[5] + coeff[21];
818 	C7_23 = coeff[7] + coeff[23];
819 
820 	// 0,7,25,32
821 
822 	base = 0x1000000;
823 	base += coeff[0] + coeff[4] + coeff[16] + coeff[20];
824 	base += TIMES_30270(C2_18);
825 	base += TIMES_12538(C6_22);
826 
827 	val1 = TIMES_41986(coeff[9]);
828 	val1 += TIMES_35594(coeff[11]);
829 	val1 += TIMES_23783(coeff[13]);
830 	val1 += TIMES_8351(coeff[15]);
831 	val1 += TIMES_17391(coeff[25]);
832 	val1 += TIMES_14743(coeff[27]);
833 	val1 += TIMES_9851(coeff[29]);
834 	val1 += TIMES_3459(coeff[31]);
835 
836 	val2 = TIMES_32134(C1_17);
837 	val2 += TIMES_27242(C3_19);
838 	val2 += TIMES_18202(C5_21);
839 	val2 += TIMES_6392(C7_23);
840 
841 	val3 = TIMES_39550(coeff[10]);
842 	val3 += TIMES_16382(coeff[14] + coeff[26]);
843 	val3 += TIMES_6785(coeff[30]);
844 	val3 += TIMES_30270(coeff[8] + coeff[12]);
845 	val3 += TIMES_12538(coeff[24] + coeff[28]);
846 
847 	t = (base + val1 + val2 + val3) >> 17;
848 	out[0] = t & 0xFFFFFF00 ? t < 0 ? 0 : 255 : (unsigned char)t;
849 	t = (base - val1 - val2 + val3 - C4 - C20) >> 17;
850 	out[7] = t & 0xFFFFFF00 ? t < 0 ? 0 : 255 : (unsigned char)t;
851 	t = (base - val1 + val2 - val3 - C16 - C20) >> 17;
852 	out[24] = t & 0xFFFFFF00 ? t < 0 ? 0 : 255 : (unsigned char)t;
853 	t = (base + val1 - val2 - val3 - C4 - C16 - C20) >> 17;
854 	out[31] = t & 0xFFFFFF00 ? t < 0 ? 0 : 255 : (unsigned char)t;
855 
856 	//1,6,25,30
857 
858 	base = 0x1000000;
859 	base += coeff[0] - coeff[4] + coeff[16] - coeff[20];
860 	base += TIMES_12538(C2_18);
861 	base -= TIMES_30270(C6_22);
862 
863 	val1 = TIMES_35594(coeff[9]);
864 	val1 -= TIMES_8351(coeff[11]);
865 	val1 -= TIMES_41986(coeff[13]);
866 	val1 -= TIMES_23783(coeff[15]);
867 	val1 -= TIMES_14743(coeff[25]);
868 	val1 -= TIMES_3459(coeff[27]);
869 	val1 -= TIMES_17391(coeff[29]);
870 	val1 -= TIMES_9851(coeff[31]);
871 
872 	val2 = TIMES_27242(C1_17);
873 	val2 -= TIMES_6392(C3_19);
874 	val2 -= TIMES_32134(C5_21);
875 	val2 -= TIMES_18202(C7_23);
876 
877 	val3 = TIMES_16382(coeff[10] - coeff[30]);
878 	val3 -= TIMES_39550(coeff[14]);
879 	val3 += TIMES_6785(coeff[26]);
880 	val3 += TIMES_12538(coeff[24] - coeff[28]);
881 	val3 += TIMES_30270(coeff[8] - coeff[12]);
882 
883 	t = (base + val1 + val2 + val3 + C4 + C20) >> 17;
884 	out[1] = t & 0xFFFFFF00 ? t < 0 ? 0 : 255 : (unsigned char)t;
885 	t = (base - val1 - val2 + val3) >> 17;
886 	out[6] = t & 0xFFFFFF00 ? t < 0 ? 0 : 255 : (unsigned char)t;
887 	t = (base - val1 + val2 - val3 + C4 - C16 + C20) >> 17;
888 	out[25] = t & 0xFFFFFF00 ? t < 0 ? 0 : 255 : (unsigned char)t;
889 	t = (base + val1 - val2 - val3 + C20) >> 17;
890 	out[30] = t & 0xFFFFFF00 ? t < 0 ? 0 : 255 : (unsigned char)t;
891 
892 	//2,5,26,29
893 
894 	base = 0x1000000;
895 	base += coeff[0] - coeff[4] + coeff[16] - coeff[20];
896 	base -= TIMES_12538(C2_18);
897 	base += TIMES_30270(C6_22);
898 
899 	val1 = TIMES_23783(coeff[9]);
900 	val1 -= TIMES_41986(coeff[11]);
901 	val1 += TIMES_8351(coeff[13]);
902 	val1 += TIMES_35594(coeff[15]);
903 	val1 += TIMES_9851(coeff[25]);
904 	val1 -= TIMES_17391(coeff[27]);
905 	val1 += TIMES_3459(coeff[29]);
906 	val1 += TIMES_14743(coeff[31]);
907 
908 	val2 = TIMES_18202(C1_17);
909 	val2 -= TIMES_32134(C3_19);
910 	val2 += TIMES_6392(C5_21);
911 	val2 += TIMES_27242(C7_23);
912 
913 	val3 = -TIMES_16382(coeff[10] - coeff[30]);
914 	val3 += TIMES_39550(coeff[14]);
915 	val3 -= TIMES_6785(coeff[26]);
916 	val3 += TIMES_12538(coeff[24] - coeff[28]);
917 	val3 += TIMES_30270(coeff[8] - coeff[12]);
918 
919 	t = (base + val1 + val2 + val3) >> 17;
920 	out[2] = t & 0xFFFFFF00 ? t < 0 ? 0 : 255 : (unsigned char)t;
921 	t = (base - val1 - val2 + val3) >> 17;
922 	out[5] = t & 0xFFFFFF00 ? t < 0 ? 0 : 255 : (unsigned char)t;
923 	t = (base - val1 + val2 - val3 - C16) >> 17;
924 	out[26] = t & 0xFFFFFF00 ? t < 0 ? 0 : 255 : (unsigned char)t;
925 	t = (base + val1 - val2 - val3 + C4 - C16 + C20) >> 17;
926 	out[29] = t & 0xFFFFFF00 ? t < 0 ? 0 : 255 : (unsigned char)t;
927 
928 	//3,4,27,28
929 
930 	base = 0x1000000;
931 	base += coeff[0] + coeff[4] + coeff[16] + coeff[20];
932 	base -= TIMES_30270(C2_18);
933 	base -= TIMES_12538(C6_22);
934 
935 	val1 = TIMES_8351(coeff[9]);
936 	val1 -= TIMES_23783(coeff[11]);
937 	val1 += TIMES_35594(coeff[13]);
938 	val1 += TIMES_3459(coeff[25]);
939 	val1 -= TIMES_9851(coeff[27]);
940 	val1 += TIMES_14743(coeff[29]);
941 
942 	val2 = TIMES_6392(C1_17);
943 	val2 -= TIMES_18202(C3_19);
944 	val2 += TIMES_27242(C5_21);
945 
946 	val3 = -TIMES_39550(coeff[10]);
947 	val3 += TIMES_16382(coeff[14] + coeff[26]);
948 	val3 -= TIMES_6785(coeff[30]);
949 	val3 += TIMES_30270(coeff[8] + coeff[12]);
950 	val3 += TIMES_12538(coeff[24] + coeff[28]);
951 
952 	tmp1 = TIMES_32134(C7_23);
953 	tmp2 = TIMES_41986(coeff[15]) + TIMES_17391(coeff[31]);
954 
955 	t = (base + val1 + val2 + val3 - tmp1 - tmp2 - C4 - C20) >> 17;
956 	out[3] = t & 0xFFFFFF00 ? t < 0 ? 0 : 255 : (unsigned char)t;
957 	t = (base - val1 - val2 + val3) >> 17;
958 	out[4] = t & 0xFFFFFF00 ? t < 0 ? 0 : 255 : (unsigned char)t;
959 	t = (base - val1 + val2 - val3 - tmp1 + tmp2) >> 17;
960 	out[27] = t & 0xFFFFFF00 ? t < 0 ? 0 : 255 : (unsigned char)t;
961 	t = (base + val1 - val2 - val3 - C16 - C20) >> 17;
962 	out[28] = t & 0xFFFFFF00 ? t < 0 ? 0 : 255 : (unsigned char)t;
963 
964 	// Second half
965 	C2_18 = coeff[2] - coeff[18];
966 	C6_22 = coeff[6] - coeff[22];
967 	C1_17 = coeff[1] - coeff[17];
968 	C3_19 = coeff[3] - coeff[19];
969 	C5_21 = coeff[5] - coeff[21];
970 	C7_23 = coeff[7] - coeff[23];
971 
972 	// 8,15,16,23
973 
974 	base = 0x1000000;
975 	base += coeff[0] + coeff[4] - coeff[16] - coeff[20];
976 	base += TIMES_30270(C2_18);
977 	base += TIMES_12538(C6_22);
978 
979 	val1 = TIMES_17391(coeff[9]);
980 	val1 += TIMES_14743(coeff[11]);
981 	val1 += TIMES_9851(coeff[13]);
982 	val1 += TIMES_3459(coeff[15]);
983 	val1 -= TIMES_41986(coeff[25]);
984 	val1 -= TIMES_35594(coeff[27]);
985 	val1 -= TIMES_23783(coeff[29]);
986 	val1 -= TIMES_8351(coeff[31]);
987 
988 	val2 = TIMES_32134(C1_17);
989 	val2 += TIMES_27242(C3_19);
990 	val2 += TIMES_18202(C5_21);
991 	val2 += TIMES_6392(C7_23);
992 
993 	val3 = TIMES_16382(coeff[10] - coeff[30]);
994 	val3 += TIMES_6785(coeff[14]);
995 	val3 -= TIMES_39550(coeff[26]);
996 	val3 -= TIMES_30270(coeff[24] + coeff[28]);
997 	val3 += TIMES_12538(coeff[8] + coeff[12]);
998 
999 	t = (base + val1 + val2 + val3) >> 17;
1000 	out[8] = t & 0xFFFFFF00 ? t < 0 ? 0 : 255 : (unsigned char)t;
1001 	t = (base - val1 - val2 + val3 - C4 + C16 + C20) >> 17;
1002 	out[15] = t & 0xFFFFFF00 ? t < 0 ? 0 : 255 : (unsigned char)t;
1003 	t = (base - val1 + val2 - val3) >> 17;
1004 	out[16] = t & 0xFFFFFF00 ? t < 0 ? 0 : 255 : (unsigned char)t;
1005 	t = (base + val1 - val2 - val3 - C4 + C20) >> 17;
1006 	out[23] = t & 0xFFFFFF00 ? t < 0 ? 0 : 255 : (unsigned char)t;
1007 
1008 	//9,14,17,22
1009 
1010 	base = 0x1000000;
1011 	base += coeff[0] - coeff[4] - coeff[16] + coeff[20];
1012 	base += TIMES_12538(C2_18);
1013 	base -= TIMES_30270(C6_22);
1014 
1015 	val1 = TIMES_14743(coeff[9]);
1016 	val1 -= TIMES_3459(coeff[11]);
1017 	val1 -= TIMES_17391(coeff[13]);
1018 	val1 -= TIMES_9851(coeff[15]);
1019 	val1 -= TIMES_35594(coeff[25]);
1020 	val1 += TIMES_8351(coeff[27]);
1021 	val1 += TIMES_41986(coeff[29]);
1022 	val1 += TIMES_23783(coeff[31]);
1023 
1024 	val2 = TIMES_27242(C1_17);
1025 	val2 -= TIMES_6392(C3_19);
1026 	val2 -= TIMES_32134(C5_21);
1027 	val2 -= TIMES_18202(C7_23);
1028 
1029 	val3 = TIMES_6785(coeff[10]);
1030 	val3 -= TIMES_16382(coeff[14] + coeff[26]);
1031 	val3 += TIMES_39550(coeff[30]);
1032 	val3 += TIMES_12538(coeff[8] - coeff[12]);
1033 	val3 -= TIMES_30270(coeff[24] - coeff[28]);
1034 
1035 	t = (base + val1 + val2 + val3 + C4 + C16 - C20) >> 17;
1036 	out[9] = t & 0xFFFFFF00 ? t < 0 ? 0 : 255 : (unsigned char)t;
1037 	t = (base - val1 - val2 + val3 + C16) >> 17;
1038 	out[14] = t & 0xFFFFFF00 ? t < 0 ? 0 : 255 : (unsigned char)t;
1039 	t = (base - val1 + val2 - val3 + C4) >> 17;
1040 	out[17] = t & 0xFFFFFF00 ? t < 0 ? 0 : 255 : (unsigned char)t;
1041 	t = (base + val1 - val2 - val3) >> 17;
1042 	out[22] = t & 0xFFFFFF00 ? t < 0 ? 0 : 255 : (unsigned char)t;
1043 
1044 	//10,13,18,21
1045 
1046 	base = 0x1000000;
1047 	base += coeff[0] - coeff[4] - coeff[16] + coeff[20];
1048 	base -= TIMES_12538(C2_18);
1049 	base += TIMES_30270(C6_22);
1050 
1051 	val1 = TIMES_9851(coeff[9]);
1052 	val1 -= TIMES_17391(coeff[11]);
1053 	val1 += TIMES_3459(coeff[13]);
1054 	val1 += TIMES_14743(coeff[15]);
1055 	val1 -= TIMES_23783(coeff[25]);
1056 	val1 += TIMES_41986(coeff[27]);
1057 	val1 -= TIMES_8351(coeff[29]);
1058 	val1 -= TIMES_35594(coeff[31]);
1059 
1060 	val2 = TIMES_18202(C1_17);
1061 	val2 -= TIMES_32134(C3_19);
1062 	val2 += TIMES_6392(C5_21);
1063 	val2 += TIMES_27242(C7_23);
1064 
1065 	val3 = -TIMES_6785(coeff[10]);
1066 	val3 += TIMES_16382(coeff[14] + coeff[26]);
1067 	val3 -= TIMES_39550(coeff[30]);
1068 	val3 += TIMES_12538(coeff[8] - coeff[12]);
1069 	val3 -= TIMES_30270(coeff[24] - coeff[28]);
1070 
1071 	t = (base + val1 + val2 + val3) >> 17;
1072 	out[10] = t & 0xFFFFFF00 ? t < 0 ? 0 : 255 : (unsigned char)t;
1073 	t = (base - val1 - val2 + val3 + C4 + C16 - C20) >> 17;
1074 	out[13] = t & 0xFFFFFF00 ? t < 0 ? 0 : 255 : (unsigned char)t;
1075 	t = (base - val1 + val2 - val3) >> 17;
1076 	out[18] = t & 0xFFFFFF00 ? t < 0 ? 0 : 255 : (unsigned char)t;
1077 	t = (base + val1 - val2 - val3 + C4) >> 17;
1078 	out[21] = t & 0xFFFFFF00 ? t < 0 ? 0 : 255 : (unsigned char)t;
1079 
1080 	// 11,12,19,20
1081 
1082 	base = 0x1000000;
1083 	base += coeff[0] + coeff[4] - coeff[16] - coeff[20];
1084 	base -= TIMES_30270(C2_18);
1085 	base -= TIMES_12538(C6_22);
1086 
1087 	val1 = TIMES_3459(coeff[9]);
1088 	val1 -= TIMES_9851(coeff[11]);
1089 	val1 += TIMES_14743(coeff[13]);
1090 	val1 -= TIMES_8351(coeff[25]);
1091 	val1 += TIMES_23783(coeff[27]);
1092 	val1 -= TIMES_35594(coeff[29]);
1093 
1094 	val2 = TIMES_6392(C1_17);
1095 	val2 -= TIMES_18202(C3_19);
1096 	val2 += TIMES_27242(C5_21);
1097 
1098 	val3 = -TIMES_16382(coeff[10] - coeff[30]);
1099 	val3 -= TIMES_6785(coeff[14]);
1100 	val3 += TIMES_39550(coeff[26]);
1101 	val3 -= TIMES_30270(coeff[24] + coeff[28]);
1102 	val3 += TIMES_12538(coeff[8] + coeff[12]);
1103 
1104 	tmp1 = TIMES_32134(C7_23);
1105 	tmp2 = -TIMES_17391(coeff[15]) + TIMES_41986(coeff[31]);
1106 
1107 	t = (base + val1 + val2 + val3 - tmp1 + tmp2 + C16 + C20) >> 17;
1108 	out[11] = t & 0xFFFFFF00 ? t < 0 ? 0 : 255 : (unsigned char)t;
1109 	t = (base - val1 - val2 + val3 + C16 + C20) >> 17;
1110 	out[12] = t & 0xFFFFFF00 ? t < 0 ? 0 : 255 : (unsigned char)t;
1111 	t = (base - val1 + val2 - val3 - tmp1 - tmp2 - C4 + C20) >> 17;
1112 	out[19] = t & 0xFFFFFF00 ? t < 0 ? 0 : 255 : (unsigned char)t;
1113 	t = (base + val1 - val2 - val3) >> 17;
1114 	out[20] = t & 0xFFFFFF00 ? t < 0 ? 0 : 255 : (unsigned char)t;
1115 }
1116 
1117 #undef TIMES_16382
1118 #undef TIMES_23168
1119 #undef TIMES_30270
1120 #undef TIMES_41986
1121 #undef TIMES_35594
1122 #undef TIMES_23783
1123 #undef TIMES_8351
1124 #undef TIMES_17391
1125 #undef TIMES_14743
1126 #undef TIMES_9851
1127 #undef TIMES_3459
1128 #undef TIMES_32134
1129 #undef TIMES_27242
1130 #undef TIMES_18202
1131 #undef TIMES_6392
1132 #undef TIMES_39550
1133 #undef TIMES_6785
1134 #undef TIMES_12538
1135 
1136 /******************************************************************************
1137  * Main Decoder Functions
1138  ******************************************************************************/
1139 
1140 /* This function handles the decompression of a single 8x4 block. It is
1141  * independent of the palette (YUV422, YUV420, YUV400, GBR422...). cinfo->bytes
1142  * determines the positin in the input buffer.
1143  */
1144 static int
decompress8x4(unsigned char * pOut,unsigned char * pIn,int * lastDC,int uvFlag,struct comp_info * cinfo)1145 decompress8x4(unsigned char	*pOut,
1146 		unsigned char	*pIn,
1147 		int		*lastDC,
1148 		int		uvFlag,
1149 		struct comp_info	*cinfo)
1150 {
1151 	int i, x, y, dc;
1152 	int coeffs[32];
1153 	int deZigZag[32];
1154 	int *dest;
1155 	int *src;
1156 	unsigned char *qt = cinfo->qt;
1157 
1158 	if (!uvFlag) {
1159 		huffmanDecoderY(coeffs, (int *)pIn, cinfo);
1160 
1161 		/* iDPCM and dequantize first coefficient */
1162 		dc = (*lastDC) + coeffs[0];
1163 		coeffs[0] = dc * (qt[0] + 1);
1164 		*lastDC = dc;
1165 
1166 		/* ...and the second coefficient */
1167 		coeffs[1] = ((qt[1] + 1) * coeffs[1]) >> 1;
1168 
1169 		/* Dequantize, starting at 3rd element */
1170 		for (i = 2; i < 32; i++)
1171 			coeffs[i] = (qt[i] + 1) * coeffs[i];
1172 	} else {
1173 		huffmanDecoderUV(coeffs, (int *)pIn, cinfo);
1174 
1175 		/* iDPCM */
1176 		dc = (*lastDC) + coeffs[0];
1177 		coeffs[0] = dc;
1178 		*lastDC = dc;
1179 
1180 		/* Dequantize */
1181 		for (i = 0; i < 32; i++)
1182 			coeffs[i] = (qt[32 + i] + 1) * coeffs[i];
1183 	}
1184 
1185 	/* Dezigzag */
1186 	for (i = 0; i < 32; i++)
1187 		deZigZag[i] = coeffs[ZigZag518[i]];
1188 
1189 	/* Transpose the dezigzagged coefficient matrix */
1190 	src = deZigZag;
1191 	dest = coeffs;
1192 	for (y = 0; y <= 3; ++y) {
1193 		for (x = 0; x <= 7; ++x)
1194 			dest[x] = src[x * 4];
1195 		src += 1;
1196 		dest += 8;
1197 	}
1198 
1199 	/* Do the inverse DCT transform */
1200 	DCT_8x4(coeffs, pOut);
1201 
1202 	return 0;	/* Always returns 0 */
1203 }
1204 
1205 static inline void
copyBlock(unsigned char * src,unsigned char * dest,int destInc)1206 copyBlock(unsigned char *src, unsigned char *dest, int destInc)
1207 {
1208 	int i;
1209 	unsigned int *pSrc, *pDest;
1210 
1211 	for (i = 0; i <= 3; i++) {
1212 		pSrc = (unsigned int *) src;
1213 		pDest = (unsigned int *) dest;
1214 		pDest[0] = pSrc[0];
1215 		pDest[1] = pSrc[1];
1216 		src += 8;
1217 		dest += destInc;
1218 	}
1219 }
1220 
1221 #if 0
1222 static inline int
1223 decompress400NoMMXOV518(unsigned char	 *pIn,
1224 		unsigned char	 *pOut,
1225 		unsigned char	 *pTmp,
1226 		const int	 w,
1227 		const int	 h,
1228 		const int	 numpix,
1229 		struct comp_info *cinfo)
1230 {
1231 	int iOutY, x, y;
1232 	int lastYDC = 0;
1233 
1234 	/* Start Y loop */
1235 	y = 0;
1236 	do {
1237 		iOutY = w * y;
1238 		x = 0;
1239 		do {
1240 			decompress8x4(pTmp, pIn, &lastYDC, 0, cinfo);
1241 			copyBlock(pTmp, pOut + iOutY, w);
1242 			iOutY += 8;
1243 			x += 8;
1244 		} while (x < w);
1245 		y += 4;
1246 	} while (y < h);
1247 
1248 	/* Did we decode too much? */
1249 	if (cinfo->bytes > cinfo->rawLen + 897)
1250 		return 1;
1251 
1252 	/* Did we decode enough? */
1253 	if (cinfo->bytes >= cinfo->rawLen - 897)
1254 		return 0;
1255 	else
1256 		return 1;
1257 }
1258 #endif
1259 
1260 static inline int
decompress420NoMMXOV518(unsigned char * pIn,unsigned char * pOut,unsigned char * pTmp,const int w,const int h,const int numpix,struct comp_info * cinfo,int yvu)1261 decompress420NoMMXOV518(unsigned char	 *pIn,
1262 		unsigned char	 *pOut,
1263 		unsigned char	 *pTmp,
1264 		const int	 w,
1265 		const int	 h,
1266 		const int	 numpix,
1267 		struct comp_info *cinfo,
1268 		int yvu)
1269 {
1270 	unsigned char *pOutU, *pOutV;
1271 	int iOutY, iOutU, iOutV, x, y;
1272 	int lastYDC = 0;
1273 	int lastUDC = 0;
1274 	int lastVDC = 0;
1275 
1276 	if (yvu) {
1277 		pOutV = pOut + numpix;
1278 		pOutU = pOutV + numpix / 4;
1279 	} else {
1280 		pOutU = pOut + numpix;
1281 		pOutV = pOutU + numpix / 4;
1282 	}
1283 
1284 	/* Start Y loop */
1285 	y = 0;
1286 	do {
1287 		iOutY = w * y;
1288 		iOutV = iOutU = iOutY / 4;
1289 
1290 		x = 0;
1291 		do {
1292 			decompress8x4(pTmp, pIn, &lastYDC, 0, cinfo);
1293 			copyBlock(pTmp, pOut + iOutY, w);
1294 			iOutY += 8;
1295 			x += 8;
1296 		} while (x < w);
1297 
1298 
1299 
1300 		iOutY = w * (y + 4);
1301 		x = 0;
1302 		do {
1303 			decompress8x4(pTmp, pIn, &lastUDC, 1, cinfo);
1304 			copyBlock(pTmp, pOutU + iOutU, w/2);
1305 			iOutU += 8;
1306 
1307 			decompress8x4(pTmp, pIn, &lastVDC, 1, cinfo);
1308 			copyBlock(pTmp, pOutV + iOutV, w/2);
1309 			iOutV += 8;
1310 
1311 			decompress8x4(pTmp, pIn, &lastYDC, 0, cinfo);
1312 			copyBlock(pTmp, pOut + iOutY, w);
1313 			iOutY += 8;
1314 
1315 			decompress8x4(pTmp, pIn, &lastYDC, 0, cinfo);
1316 			copyBlock(pTmp, pOut + iOutY, w);
1317 			iOutY += 8;
1318 
1319 			x += 16;
1320 		} while (x < w);
1321 
1322 		y += 8;
1323 	} while (y < h);
1324 
1325 	/* Did we decode too much? */
1326 	if (cinfo->bytes > cinfo->rawLen + 897)
1327 		return 1;
1328 
1329 	/* Did we decode enough? */
1330 	if (cinfo->bytes >= cinfo->rawLen - (897 + 64))
1331 		return 0;
1332 
1333 	return 1;
1334 }
1335 
1336 /* Get quantization tables from input
1337  * Returns: <0 if error, or >=0 otherwise */
1338 static int
get_qt_dynamic(unsigned char * pIn,struct comp_info * cinfo)1339 get_qt_dynamic(unsigned char *pIn, struct comp_info *cinfo)
1340 {
1341 	int rawLen = cinfo->rawLen;
1342 
1343 	/* Make sure input is actually big enough to hold trailer */
1344 	if (rawLen < 72)
1345 		return -1;
1346 
1347 	cinfo->qt = pIn + rawLen - 64;
1348 
1349 	return 0;
1350 }
1351 
1352 /* Remove all 0 blocks from input */
remove0blocks(unsigned char * pIn,int * inSize)1353 static void remove0blocks(unsigned char *pIn, int *inSize)
1354 {
1355 	long long *in = (long long *)pIn;
1356 	long long *out = (long long *)pIn;
1357 	int i;
1358 
1359 	for (i = 0; i < *inSize; i += 8, in++)
1360 		/* Skip 8 byte blocks of all 0 */
1361 		if (*in)
1362 			*out++ = *in;
1363 
1364 	*inSize -= (in - out) * 8;
1365 }
1366 
1367 #if 0 /* not used */
1368 /* Input format is raw isoc. data (with intact SOF header, packet numbers
1369  * stripped, and all-zero blocks removed).
1370  * Output format is planar YUV400
1371  * Returns uncompressed data length if success, or zero if error
1372  */
1373 static int
1374 Decompress400(unsigned char *pIn,
1375 		unsigned char *pOut,
1376 		int	     w,
1377 		int	     h,
1378 		int	     inSize)
1379 {
1380 	struct comp_info cinfo;
1381 	int numpix = w * h;
1382 	unsigned char pTmp[32];
1383 
1384 	remove0blocks(pIn, &inSize);
1385 
1386 	cinfo.bytes = 0;
1387 	cinfo.bits = 0;
1388 	cinfo.rawLen = inSize;
1389 
1390 	if (get_qt_dynamic(pIn, &cinfo) < 0)
1391 		return 0;
1392 
1393 	/* Decompress, skipping the 8-byte SOF header */
1394 	if (decompress400NoMMXOV518(pIn + 8, pOut, pTmp, w, h, numpix, &cinfo))
1395 		/*		return 0; */
1396 		; /* Don't return error yet */
1397 
1398 	return numpix;
1399 }
1400 #endif
1401 
1402 /* Input format is raw isoc. data (with intact SOF header, packet numbers
1403  * stripped, and all-zero blocks removed).
1404  * Output format is planar YUV420
1405  * Returns uncompressed data length if success, or zero if error
1406  */
v4lconvert_ov518_to_yuv420(unsigned char * src,unsigned char * dst,int w,int h,int yvu,int inSize)1407 static int v4lconvert_ov518_to_yuv420(unsigned char *src, unsigned char *dst,
1408 		int w, int h, int yvu, int inSize)
1409 {
1410 	struct comp_info cinfo;
1411 	int numpix = w * h;
1412 	unsigned char pTmp[32];
1413 
1414 	remove0blocks(src, &inSize);
1415 
1416 	cinfo.bytes = 0;
1417 	cinfo.bits = 0;
1418 	cinfo.rawLen = inSize;
1419 
1420 	if (get_qt_dynamic(src, &cinfo) < 0)
1421 		return -1;
1422 
1423 	/* Decompress, skipping the 8-byte SOF header */
1424 	if (decompress420NoMMXOV518(src + 8, dst, pTmp, w, h, numpix, &cinfo, yvu))
1425 		return -1;
1426 
1427 	return 0;
1428 }
1429 
main(int argc,char * argv[])1430 int main(int argc, char *argv[])
1431 {
1432 	int width, height, yvu, src_size, dest_size;
1433 	unsigned char src_buf[200000];
1434 	unsigned char dest_buf[500000];
1435 
1436 	while (1) {
1437 		if (v4lconvert_helper_read(STDIN_FILENO, &width, sizeof(int), argv[0]))
1438 			return 1; /* Erm, no way to recover without loosing sync with libv4l */
1439 
1440 		if (v4lconvert_helper_read(STDIN_FILENO, &height, sizeof(int), argv[0]))
1441 			return 1; /* Erm, no way to recover without loosing sync with libv4l */
1442 
1443 		if (v4lconvert_helper_read(STDIN_FILENO, &yvu, sizeof(int), argv[0]))
1444 			return 1; /* Erm, no way to recover without loosing sync with libv4l */
1445 
1446 		if (v4lconvert_helper_read(STDIN_FILENO, &src_size, sizeof(int), argv[0]))
1447 			return 1; /* Erm, no way to recover without loosing sync with libv4l */
1448 
1449 		if (src_size > sizeof(src_buf)) {
1450 			fprintf(stderr, "%s: error: src_buf too small, need: %d\n",
1451 					argv[0], src_size);
1452 			return 2;
1453 		}
1454 
1455 		if (v4lconvert_helper_read(STDIN_FILENO, src_buf, src_size, argv[0]))
1456 			return 1; /* Erm, no way to recover without loosing sync with libv4l */
1457 
1458 
1459 		dest_size = width * height * 3 / 2;
1460 		if (width <= 0 || width > SHRT_MAX || height <= 0 || height > SHRT_MAX) {
1461 			fprintf(stderr, "%s: error: width or height out of bounds\n",
1462 					argv[0]);
1463 			dest_size = -1;
1464 		} else if (dest_size > sizeof(dest_buf)) {
1465 			fprintf(stderr, "%s: error: dest_buf too small, need: %d\n",
1466 					argv[0], dest_size);
1467 			dest_size = -1;
1468 		} else if (v4lconvert_ov518_to_yuv420(src_buf, dest_buf, width, height,
1469 					yvu, src_size))
1470 			dest_size = -1;
1471 
1472 		if (v4lconvert_helper_write(STDOUT_FILENO, &dest_size, sizeof(int),
1473 					argv[0]))
1474 			return 1; /* Erm, no way to recover without loosing sync with libv4l */
1475 
1476 		if (dest_size == -1)
1477 			continue;
1478 
1479 		if (v4lconvert_helper_write(STDOUT_FILENO, dest_buf, dest_size, argv[0]))
1480 			return 1; /* Erm, no way to recover without loosing sync with libv4l */
1481 	}
1482 }
1483