aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/linden/indra/llmessage/patch_code.cpp
diff options
context:
space:
mode:
authorJacek Antonelli2008-08-15 23:44:46 -0500
committerJacek Antonelli2008-08-15 23:44:46 -0500
commit38d6d37f2d982fa959e9e8a4a3f7e1ccfad7b5d4 (patch)
treeadca584755d22ca041a2dbfc35d4eca01f70b32c /linden/indra/llmessage/patch_code.cpp
parentREADME.txt (diff)
downloadmeta-impy-38d6d37f2d982fa959e9e8a4a3f7e1ccfad7b5d4.zip
meta-impy-38d6d37f2d982fa959e9e8a4a3f7e1ccfad7b5d4.tar.gz
meta-impy-38d6d37f2d982fa959e9e8a4a3f7e1ccfad7b5d4.tar.bz2
meta-impy-38d6d37f2d982fa959e9e8a4a3f7e1ccfad7b5d4.tar.xz
Second Life viewer sources 1.13.2.12
Diffstat (limited to 'linden/indra/llmessage/patch_code.cpp')
-rw-r--r--linden/indra/llmessage/patch_code.cpp409
1 files changed, 409 insertions, 0 deletions
diff --git a/linden/indra/llmessage/patch_code.cpp b/linden/indra/llmessage/patch_code.cpp
new file mode 100644
index 0000000..3eb2be6
--- /dev/null
+++ b/linden/indra/llmessage/patch_code.cpp
@@ -0,0 +1,409 @@
1/**
2 * @file patch_code.cpp
3 * @brief Encode patch DCT data into bitcode.
4 *
5 * Copyright (c) 2000-2007, Linden Research, Inc.
6 *
7 * The source code in this file ("Source Code") is provided by Linden Lab
8 * to you under the terms of the GNU General Public License, version 2.0
9 * ("GPL"), unless you have obtained a separate licensing agreement
10 * ("Other License"), formally executed by you and Linden Lab. Terms of
11 * the GPL can be found in doc/GPL-license.txt in this distribution, or
12 * online at http://secondlife.com/developers/opensource/gplv2
13 *
14 * There are special exceptions to the terms and conditions of the GPL as
15 * it is applied to this Source Code. View the full text of the exception
16 * in the file doc/FLOSS-exception.txt in this software distribution, or
17 * online at http://secondlife.com/developers/opensource/flossexception
18 *
19 * By copying, modifying or distributing this software, you acknowledge
20 * that you have read and understood your obligations described above,
21 * and agree to abide by those obligations.
22 *
23 * ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO
24 * WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY,
25 * COMPLETENESS OR PERFORMANCE.
26 */
27
28#include "linden_common.h"
29
30#include "llmath.h"
31//#include "vmath.h"
32#include "v3math.h"
33#include "patch_dct.h"
34#include "patch_code.h"
35#include "bitpack.h"
36
37U32 gPatchSize, gWordBits;
38
39void init_patch_coding(LLBitPack &bitpack)
40{
41 bitpack.resetBitPacking();
42}
43
44void code_patch_group_header(LLBitPack &bitpack, LLGroupHeader *gopp)
45{
46#ifdef LL_BIG_ENDIAN
47 U8 *stride = (U8 *)&gopp->stride;
48 bitpack.bitPack(&(stride[1]), 8);
49 bitpack.bitPack(&(stride[0]), 8);
50#else
51 bitpack.bitPack((U8 *)&gopp->stride, 16);
52#endif
53 bitpack.bitPack((U8 *)&gopp->patch_size, 8);
54 bitpack.bitPack((U8 *)&gopp->layer_type, 8);
55
56 gPatchSize = gopp->patch_size;
57}
58
59void code_patch_header(LLBitPack &bitpack, LLPatchHeader *ph, S32 *patch)
60{
61 S32 i, j, temp, patch_size = gPatchSize, wbits = (ph->quant_wbits & 0xf) + 2;
62 U32 max_wbits = wbits + 5, min_wbits = wbits>>1;
63
64 wbits = min_wbits;
65
66 for (i = 0; i < (int) patch_size*patch_size; i++)
67 {
68 temp = patch[i];
69 if (temp)
70 {
71 if (temp < 0)
72 temp *= -1;
73 for (j = max_wbits; j > (int) min_wbits; j--)
74 {
75 if (temp & (1<<j))
76 {
77 if (j > wbits)
78 wbits = j;
79 break;
80 }
81 }
82 }
83 }
84
85 wbits += 1;
86
87 ph->quant_wbits &= 0xf0;
88
89 if ( (wbits > 17)
90 ||(wbits < 2))
91 {
92 llerrs << "Bits needed per word in code_patch_header out of legal range. Adjust compression quatization." << llendl;
93 }
94
95 ph->quant_wbits |= (wbits - 2);
96
97 bitpack.bitPack((U8 *)&ph->quant_wbits, 8);
98#ifdef LL_BIG_ENDIAN
99 U8 *offset = (U8 *)&ph->dc_offset;
100 bitpack.bitPack(&(offset[3]), 8);
101 bitpack.bitPack(&(offset[2]), 8);
102 bitpack.bitPack(&(offset[1]), 8);
103 bitpack.bitPack(&(offset[0]), 8);
104#else
105 bitpack.bitPack((U8 *)&ph->dc_offset, 32);
106#endif
107#ifdef LL_BIG_ENDIAN
108 U8 *range = (U8 *)&ph->range;
109 bitpack.bitPack(&(range[1]), 8);
110 bitpack.bitPack(&(range[0]), 8);
111#else
112 bitpack.bitPack((U8 *)&ph->range, 16);
113#endif
114#ifdef LL_BIG_ENDIAN
115 U8 *ids = (U8 *)&ph->patchids;
116 bitpack.bitPack(&(ids[1]), 8);
117 bitpack.bitPack(&(ids[0]), 2);
118#else
119 bitpack.bitPack((U8 *)&ph->patchids, 10);
120#endif
121
122 gWordBits = wbits;
123}
124
125void code_end_of_data(LLBitPack &bitpack)
126{
127 bitpack.bitPack((U8 *)&END_OF_PATCHES, 8);
128}
129
130void code_patch(LLBitPack &bitpack, S32 *patch, S32 postquant)
131{
132 S32 i, j, patch_size = gPatchSize, wbits = gWordBits;
133 S32 temp;
134 BOOL b_eob;
135
136 if ( (postquant > patch_size*patch_size)
137 ||(postquant < 0))
138 {
139 llerrs << "Bad postquant in code_patch!" << llendl;
140 }
141
142 if (postquant)
143 patch[patch_size*patch_size - postquant] = 0;
144
145 for (i = 0; i < patch_size*patch_size; i++)
146 {
147 b_eob = FALSE;
148 temp = patch[i];
149 if (!temp)
150 {
151 b_eob = TRUE;
152 for (j = i; j < patch_size*patch_size - postquant; j++)
153 {
154 if (patch[j])
155 {
156 b_eob = FALSE;
157 break;
158 }
159 }
160 if (b_eob)
161 {
162 bitpack.bitPack((U8 *)&ZERO_EOB, 2);
163 return;
164 }
165 else
166 {
167 bitpack.bitPack((U8 *)&ZERO_CODE, 1);
168 }
169 }
170 else
171 {
172 if (temp < 0)
173 {
174 temp *= -1;
175 if (temp > (1<<wbits))
176 {
177 temp = (1<<wbits);
178// printf("patch quatization exceeding allowable bits!");
179 }
180 bitpack.bitPack((U8 *)&NEGATIVE_VALUE, 3);
181 bitpack.bitPack((U8 *)&temp, wbits);
182 }
183 else
184 {
185 if (temp > (1<<wbits))
186 {
187 temp = (1<<wbits);
188// printf("patch quatization exceeding allowable bits!");
189 }
190 bitpack.bitPack((U8 *)&POSITIVE_VALUE, 3);
191 bitpack.bitPack((U8 *)&temp, wbits);
192 }
193 }
194 }
195}
196
197
198void end_patch_coding(LLBitPack &bitpack)
199{
200 bitpack.flushBitPack();
201}
202
203void init_patch_decoding(LLBitPack &bitpack)
204{
205 bitpack.resetBitPacking();
206}
207
208void decode_patch_group_header(LLBitPack &bitpack, LLGroupHeader *gopp)
209{
210 U16 retvalu16;
211
212 retvalu16 = 0;
213#ifdef LL_BIG_ENDIAN
214 U8 *ret = (U8 *)&retvalu16;
215 bitpack.bitUnpack(&(ret[1]), 8);
216 bitpack.bitUnpack(&(ret[0]), 8);
217#else
218 bitpack.bitUnpack((U8 *)&retvalu16, 16);
219#endif
220 gopp->stride = retvalu16;
221
222 U8 retvalu8 = 0;
223 bitpack.bitUnpack(&retvalu8, 8);
224 gopp->patch_size = retvalu8;
225
226 retvalu8 = 0;
227 bitpack.bitUnpack(&retvalu8, 8);
228 gopp->layer_type = retvalu8;
229
230 gPatchSize = gopp->patch_size;
231}
232
233void decode_patch_header(LLBitPack &bitpack, LLPatchHeader *ph)
234{
235 U8 retvalu8;
236
237 retvalu8 = 0;
238 bitpack.bitUnpack(&retvalu8, 8);
239 ph->quant_wbits = retvalu8;
240
241 if (END_OF_PATCHES == ph->quant_wbits)
242 {
243 // End of data, blitz the rest.
244 ph->dc_offset = 0;
245 ph->range = 0;
246 ph->patchids = 0;
247 return;
248 }
249
250 U32 retvalu32 = 0;
251#ifdef LL_BIG_ENDIAN
252 U8 *ret = (U8 *)&retvalu32;
253 bitpack.bitUnpack(&(ret[3]), 8);
254 bitpack.bitUnpack(&(ret[2]), 8);
255 bitpack.bitUnpack(&(ret[1]), 8);
256 bitpack.bitUnpack(&(ret[0]), 8);
257#else
258 bitpack.bitUnpack((U8 *)&retvalu32, 32);
259#endif
260 ph->dc_offset = *(F32 *)&retvalu32;
261
262 U16 retvalu16 = 0;
263#ifdef LL_BIG_ENDIAN
264 ret = (U8 *)&retvalu16;
265 bitpack.bitUnpack(&(ret[1]), 8);
266 bitpack.bitUnpack(&(ret[0]), 8);
267#else
268 bitpack.bitUnpack((U8 *)&retvalu16, 16);
269#endif
270 ph->range = retvalu16;
271
272 retvalu16 = 0;
273#ifdef LL_BIG_ENDIAN
274 ret = (U8 *)&retvalu16;
275 bitpack.bitUnpack(&(ret[1]), 8);
276 bitpack.bitUnpack(&(ret[0]), 2);
277#else
278 bitpack.bitUnpack((U8 *)&retvalu16, 10);
279#endif
280 ph->patchids = retvalu16;
281
282 gWordBits = (ph->quant_wbits & 0xf) + 2;
283}
284
285void decode_patch(LLBitPack &bitpack, S32 *patches)
286{
287#ifdef LL_BIG_ENDIAN
288 S32 i, j, patch_size = gPatchSize, wbits = gWordBits;
289 U8 tempu8;
290 U16 tempu16;
291 U32 tempu32;
292 for (i = 0; i < patch_size*patch_size; i++)
293 {
294 bitpack.bitUnpack((U8 *)&tempu8, 1);
295 if (tempu8)
296 {
297 // either 0 EOB or Value
298 bitpack.bitUnpack((U8 *)&tempu8, 1);
299 if (tempu8)
300 {
301 // value
302 bitpack.bitUnpack((U8 *)&tempu8, 1);
303 if (tempu8)
304 {
305 // negative
306 patches[i] = -1;
307 }
308 else
309 {
310 // positive
311 patches[i] = 1;
312 }
313 if (wbits <= 8)
314 {
315 bitpack.bitUnpack((U8 *)&tempu8, wbits);
316 patches[i] *= tempu8;
317 }
318 else if (wbits <= 16)
319 {
320 tempu16 = 0;
321 U8 *ret = (U8 *)&tempu16;
322 bitpack.bitUnpack(&(ret[1]), 8);
323 bitpack.bitUnpack(&(ret[0]), wbits - 8);
324 patches[i] *= tempu16;
325 }
326 else if (wbits <= 24)
327 {
328 tempu32 = 0;
329 U8 *ret = (U8 *)&tempu32;
330 bitpack.bitUnpack(&(ret[2]), 8);
331 bitpack.bitUnpack(&(ret[1]), 8);
332 bitpack.bitUnpack(&(ret[0]), wbits - 16);
333 patches[i] *= tempu32;
334 }
335 else if (wbits <= 32)
336 {
337 tempu32 = 0;
338 U8 *ret = (U8 *)&tempu32;
339 bitpack.bitUnpack(&(ret[3]), 8);
340 bitpack.bitUnpack(&(ret[2]), 8);
341 bitpack.bitUnpack(&(ret[1]), 8);
342 bitpack.bitUnpack(&(ret[0]), wbits - 24);
343 patches[i] *= tempu32;
344 }
345 }
346 else
347 {
348 for (j = i; j < patch_size*patch_size; j++)
349 {
350 patches[j] = 0;
351 }
352 return;
353 }
354 }
355 else
356 {
357 patches[i] = 0;
358 }
359 }
360#else
361 S32 i, j, patch_size = gPatchSize, wbits = gWordBits;
362 U32 temp;
363 for (i = 0; i < patch_size*patch_size; i++)
364 {
365 temp = 0;
366 bitpack.bitUnpack((U8 *)&temp, 1);
367 if (temp)
368 {
369 // either 0 EOB or Value
370 temp = 0;
371 bitpack.bitUnpack((U8 *)&temp, 1);
372 if (temp)
373 {
374 // value
375 temp = 0;
376 bitpack.bitUnpack((U8 *)&temp, 1);
377 if (temp)
378 {
379 // negative
380 temp = 0;
381 bitpack.bitUnpack((U8 *)&temp, wbits);
382 patches[i] = temp;
383 patches[i] *= -1;
384 }
385 else
386 {
387 // positive
388 temp = 0;
389 bitpack.bitUnpack((U8 *)&temp, wbits);
390 patches[i] = temp;
391 }
392 }
393 else
394 {
395 for (j = i; j < patch_size*patch_size; j++)
396 {
397 patches[j] = 0;
398 }
399 return;
400 }
401 }
402 else
403 {
404 patches[i] = 0;
405 }
406 }
407#endif
408}
409