Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(63)

Side by Side Diff: source/libvpx/vp9/common/vp9_reconintra4x4.c

Issue 11555023: libvpx: Add VP9 decoder. (Closed) Base URL: svn://chrome-svn/chrome/trunk/deps/third_party/libvpx/
Patch Set: Created 8 years ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
Property Changes:
Added: svn:eol-style
+ LF
OLDNEW
(Empty)
1 /*
2 * Copyright (c) 2010 The WebM project authors. All Rights Reserved.
3 *
4 * Use of this source code is governed by a BSD-style license
5 * that can be found in the LICENSE file in the root of the source
6 * tree. An additional intellectual property rights grant can be found
7 * in the file PATENTS. All contributing project authors may
8 * be found in the AUTHORS file in the root of the source tree.
9 */
10
11
12 #include "vpx_ports/config.h"
13 #include "vpx_mem/vpx_mem.h"
14 #include "vp9/common/vp9_reconintra.h"
15 #include "vp9_rtcd.h"
16
17 #if CONFIG_NEWBINTRAMODES
18 static int find_grad_measure(unsigned char *x, int stride, int n, int t,
19 int dx, int dy) {
20 int i, j;
21 int count = 0, gsum = 0, gdiv;
22 /* TODO: Make this code more efficient by breaking up into two loops */
23 for (i = -t; i < n; ++i)
24 for (j = -t; j < n; ++j) {
25 int g;
26 if (i >= 0 && j >= 0) continue;
27 if (i + dy >= 0 && j + dx >= 0) continue;
28 if (i + dy < -t || i + dy >= n || j + dx < -t || j + dx >= n) continue;
29 g = abs(x[(i + dy) * stride + j + dx] - x[i * stride + j]);
30 gsum += g * g;
31 count++;
32 }
33 gdiv = (dx * dx + dy * dy) * count;
34 return ((gsum << 8) + (gdiv >> 1)) / gdiv;
35 }
36
37 #if CONTEXT_PRED_REPLACEMENTS == 6
38 B_PREDICTION_MODE vp9_find_dominant_direction(
39 unsigned char *ptr, int stride, int n) {
40 int g[8], i, imin, imax;
41 g[1] = find_grad_measure(ptr, stride, n, 4, 2, 1);
42 g[2] = find_grad_measure(ptr, stride, n, 4, 1, 1);
43 g[3] = find_grad_measure(ptr, stride, n, 4, 1, 2);
44 g[5] = find_grad_measure(ptr, stride, n, 4, -1, 2);
45 g[6] = find_grad_measure(ptr, stride, n, 4, -1, 1);
46 g[7] = find_grad_measure(ptr, stride, n, 4, -2, 1);
47 imin = 1;
48 for (i = 2; i < 8; i += 1 + (i == 3))
49 imin = (g[i] < g[imin] ? i : imin);
50 imax = 1;
51 for (i = 2; i < 8; i += 1 + (i == 3))
52 imax = (g[i] > g[imax] ? i : imax);
53 /*
54 printf("%d %d %d %d %d %d = %d %d\n",
55 g[1], g[2], g[3], g[5], g[6], g[7], imin, imax);
56 */
57 switch (imin) {
58 case 1:
59 return B_HD_PRED;
60 case 2:
61 return B_RD_PRED;
62 case 3:
63 return B_VR_PRED;
64 case 5:
65 return B_VL_PRED;
66 case 6:
67 return B_LD_PRED;
68 case 7:
69 return B_HU_PRED;
70 default:
71 assert(0);
72 }
73 }
74 #elif CONTEXT_PRED_REPLACEMENTS == 4
75 B_PREDICTION_MODE vp9_find_dominant_direction(
76 unsigned char *ptr, int stride, int n) {
77 int g[8], i, imin, imax;
78 g[1] = find_grad_measure(ptr, stride, n, 4, 2, 1);
79 g[3] = find_grad_measure(ptr, stride, n, 4, 1, 2);
80 g[5] = find_grad_measure(ptr, stride, n, 4, -1, 2);
81 g[7] = find_grad_measure(ptr, stride, n, 4, -2, 1);
82 imin = 1;
83 for (i = 3; i < 8; i+=2)
84 imin = (g[i] < g[imin] ? i : imin);
85 imax = 1;
86 for (i = 3; i < 8; i+=2)
87 imax = (g[i] > g[imax] ? i : imax);
88 /*
89 printf("%d %d %d %d = %d %d\n",
90 g[1], g[3], g[5], g[7], imin, imax);
91 */
92 switch (imin) {
93 case 1:
94 return B_HD_PRED;
95 case 3:
96 return B_VR_PRED;
97 case 5:
98 return B_VL_PRED;
99 case 7:
100 return B_HU_PRED;
101 default:
102 assert(0);
103 }
104 }
105 #elif CONTEXT_PRED_REPLACEMENTS == 0
106 B_PREDICTION_MODE vp9_find_dominant_direction(
107 unsigned char *ptr, int stride, int n) {
108 int g[8], i, imin, imax;
109 g[0] = find_grad_measure(ptr, stride, n, 4, 1, 0);
110 g[1] = find_grad_measure(ptr, stride, n, 4, 2, 1);
111 g[2] = find_grad_measure(ptr, stride, n, 4, 1, 1);
112 g[3] = find_grad_measure(ptr, stride, n, 4, 1, 2);
113 g[4] = find_grad_measure(ptr, stride, n, 4, 0, 1);
114 g[5] = find_grad_measure(ptr, stride, n, 4, -1, 2);
115 g[6] = find_grad_measure(ptr, stride, n, 4, -1, 1);
116 g[7] = find_grad_measure(ptr, stride, n, 4, -2, 1);
117 imax = 0;
118 for (i = 1; i < 8; i++)
119 imax = (g[i] > g[imax] ? i : imax);
120 imin = 0;
121 for (i = 1; i < 8; i++)
122 imin = (g[i] < g[imin] ? i : imin);
123
124 switch (imin) {
125 case 0:
126 return B_HE_PRED;
127 case 1:
128 return B_HD_PRED;
129 case 2:
130 return B_RD_PRED;
131 case 3:
132 return B_VR_PRED;
133 case 4:
134 return B_VE_PRED;
135 case 5:
136 return B_VL_PRED;
137 case 6:
138 return B_LD_PRED;
139 case 7:
140 return B_HU_PRED;
141 default:
142 assert(0);
143 }
144 }
145 #endif
146
147 B_PREDICTION_MODE vp9_find_bpred_context(BLOCKD *x) {
148 unsigned char *ptr = *(x->base_dst) + x->dst;
149 int stride = x->dst_stride;
150 return vp9_find_dominant_direction(ptr, stride, 4);
151 }
152 #endif
153
154 void vp9_intra4x4_predict(BLOCKD *x,
155 int b_mode,
156 unsigned char *predictor) {
157 int i, r, c;
158
159 unsigned char *Above = *(x->base_dst) + x->dst - x->dst_stride;
160 unsigned char Left[4];
161 unsigned char top_left = Above[-1];
162
163 Left[0] = (*(x->base_dst))[x->dst - 1];
164 Left[1] = (*(x->base_dst))[x->dst - 1 + x->dst_stride];
165 Left[2] = (*(x->base_dst))[x->dst - 1 + 2 * x->dst_stride];
166 Left[3] = (*(x->base_dst))[x->dst - 1 + 3 * x->dst_stride];
167
168 #if CONFIG_NEWBINTRAMODES
169 if (b_mode == B_CONTEXT_PRED)
170 b_mode = x->bmi.as_mode.context;
171 #endif
172
173 switch (b_mode) {
174 case B_DC_PRED: {
175 int expected_dc = 0;
176
177 for (i = 0; i < 4; i++) {
178 expected_dc += Above[i];
179 expected_dc += Left[i];
180 }
181
182 expected_dc = (expected_dc + 4) >> 3;
183
184 for (r = 0; r < 4; r++) {
185 for (c = 0; c < 4; c++) {
186 predictor[c] = expected_dc;
187 }
188
189 predictor += 16;
190 }
191 }
192 break;
193 case B_TM_PRED: {
194 /* prediction similar to true_motion prediction */
195 for (r = 0; r < 4; r++) {
196 for (c = 0; c < 4; c++) {
197 int pred = Above[c] - top_left + Left[r];
198
199 if (pred < 0)
200 pred = 0;
201
202 if (pred > 255)
203 pred = 255;
204
205 predictor[c] = pred;
206 }
207
208 predictor += 16;
209 }
210 }
211 break;
212
213 case B_VE_PRED: {
214
215 unsigned int ap[4];
216 ap[0] = Above[0];
217 ap[1] = Above[1];
218 ap[2] = Above[2];
219 ap[3] = Above[3];
220
221 for (r = 0; r < 4; r++) {
222 for (c = 0; c < 4; c++) {
223
224 predictor[c] = ap[c];
225 }
226
227 predictor += 16;
228 }
229
230 }
231 break;
232
233
234 case B_HE_PRED: {
235
236 unsigned int lp[4];
237 lp[0] = Left[0];
238 lp[1] = Left[1];
239 lp[2] = Left[2];
240 lp[3] = Left[3];
241
242 for (r = 0; r < 4; r++) {
243 for (c = 0; c < 4; c++) {
244 predictor[c] = lp[r];
245 }
246
247 predictor += 16;
248 }
249 }
250 break;
251 case B_LD_PRED: {
252 unsigned char *ptr = Above;
253 predictor[0 * 16 + 0] = (ptr[0] + ptr[1] * 2 + ptr[2] + 2) >> 2;
254 predictor[0 * 16 + 1] =
255 predictor[1 * 16 + 0] = (ptr[1] + ptr[2] * 2 + ptr[3] + 2) >> 2;
256 predictor[0 * 16 + 2] =
257 predictor[1 * 16 + 1] =
258 predictor[2 * 16 + 0] = (ptr[2] + ptr[3] * 2 + ptr[4] + 2) >> 2;
259 predictor[0 * 16 + 3] =
260 predictor[1 * 16 + 2] =
261 predictor[2 * 16 + 1] =
262 predictor[3 * 16 + 0] = (ptr[3] + ptr[4] * 2 + ptr[5] + 2) >> 2;
263 predictor[1 * 16 + 3] =
264 predictor[2 * 16 + 2] =
265 predictor[3 * 16 + 1] = (ptr[4] + ptr[5] * 2 + ptr[6] + 2) >> 2;
266 predictor[2 * 16 + 3] =
267 predictor[3 * 16 + 2] = (ptr[5] + ptr[6] * 2 + ptr[7] + 2) >> 2;
268 predictor[3 * 16 + 3] = (ptr[6] + ptr[7] * 2 + ptr[7] + 2) >> 2;
269
270 }
271 break;
272 case B_RD_PRED: {
273
274 unsigned char pp[9];
275
276 pp[0] = Left[3];
277 pp[1] = Left[2];
278 pp[2] = Left[1];
279 pp[3] = Left[0];
280 pp[4] = top_left;
281 pp[5] = Above[0];
282 pp[6] = Above[1];
283 pp[7] = Above[2];
284 pp[8] = Above[3];
285
286 predictor[3 * 16 + 0] = (pp[0] + pp[1] * 2 + pp[2] + 2) >> 2;
287 predictor[3 * 16 + 1] =
288 predictor[2 * 16 + 0] = (pp[1] + pp[2] * 2 + pp[3] + 2) >> 2;
289 predictor[3 * 16 + 2] =
290 predictor[2 * 16 + 1] =
291 predictor[1 * 16 + 0] = (pp[2] + pp[3] * 2 + pp[4] + 2) >> 2;
292 predictor[3 * 16 + 3] =
293 predictor[2 * 16 + 2] =
294 predictor[1 * 16 + 1] =
295 predictor[0 * 16 + 0] = (pp[3] + pp[4] * 2 + pp[5] + 2) >> 2;
296 predictor[2 * 16 + 3] =
297 predictor[1 * 16 + 2] =
298 predictor[0 * 16 + 1] = (pp[4] + pp[5] * 2 + pp[6] + 2) >> 2;
299 predictor[1 * 16 + 3] =
300 predictor[0 * 16 + 2] = (pp[5] + pp[6] * 2 + pp[7] + 2) >> 2;
301 predictor[0 * 16 + 3] = (pp[6] + pp[7] * 2 + pp[8] + 2) >> 2;
302
303 }
304 break;
305 case B_VR_PRED: {
306
307 unsigned char pp[9];
308
309 pp[0] = Left[3];
310 pp[1] = Left[2];
311 pp[2] = Left[1];
312 pp[3] = Left[0];
313 pp[4] = top_left;
314 pp[5] = Above[0];
315 pp[6] = Above[1];
316 pp[7] = Above[2];
317 pp[8] = Above[3];
318
319
320 predictor[3 * 16 + 0] = (pp[1] + pp[2] * 2 + pp[3] + 2) >> 2;
321 predictor[2 * 16 + 0] = (pp[2] + pp[3] * 2 + pp[4] + 2) >> 2;
322 predictor[3 * 16 + 1] =
323 predictor[1 * 16 + 0] = (pp[3] + pp[4] * 2 + pp[5] + 2) >> 2;
324 predictor[2 * 16 + 1] =
325 predictor[0 * 16 + 0] = (pp[4] + pp[5] + 1) >> 1;
326 predictor[3 * 16 + 2] =
327 predictor[1 * 16 + 1] = (pp[4] + pp[5] * 2 + pp[6] + 2) >> 2;
328 predictor[2 * 16 + 2] =
329 predictor[0 * 16 + 1] = (pp[5] + pp[6] + 1) >> 1;
330 predictor[3 * 16 + 3] =
331 predictor[1 * 16 + 2] = (pp[5] + pp[6] * 2 + pp[7] + 2) >> 2;
332 predictor[2 * 16 + 3] =
333 predictor[0 * 16 + 2] = (pp[6] + pp[7] + 1) >> 1;
334 predictor[1 * 16 + 3] = (pp[6] + pp[7] * 2 + pp[8] + 2) >> 2;
335 predictor[0 * 16 + 3] = (pp[7] + pp[8] + 1) >> 1;
336
337 }
338 break;
339 case B_VL_PRED: {
340
341 unsigned char *pp = Above;
342
343 predictor[0 * 16 + 0] = (pp[0] + pp[1] + 1) >> 1;
344 predictor[1 * 16 + 0] = (pp[0] + pp[1] * 2 + pp[2] + 2) >> 2;
345 predictor[2 * 16 + 0] =
346 predictor[0 * 16 + 1] = (pp[1] + pp[2] + 1) >> 1;
347 predictor[1 * 16 + 1] =
348 predictor[3 * 16 + 0] = (pp[1] + pp[2] * 2 + pp[3] + 2) >> 2;
349 predictor[2 * 16 + 1] =
350 predictor[0 * 16 + 2] = (pp[2] + pp[3] + 1) >> 1;
351 predictor[3 * 16 + 1] =
352 predictor[1 * 16 + 2] = (pp[2] + pp[3] * 2 + pp[4] + 2) >> 2;
353 predictor[0 * 16 + 3] =
354 predictor[2 * 16 + 2] = (pp[3] + pp[4] + 1) >> 1;
355 predictor[1 * 16 + 3] =
356 predictor[3 * 16 + 2] = (pp[3] + pp[4] * 2 + pp[5] + 2) >> 2;
357 predictor[2 * 16 + 3] = (pp[4] + pp[5] * 2 + pp[6] + 2) >> 2;
358 predictor[3 * 16 + 3] = (pp[5] + pp[6] * 2 + pp[7] + 2) >> 2;
359 }
360 break;
361
362 case B_HD_PRED: {
363 unsigned char pp[9];
364 pp[0] = Left[3];
365 pp[1] = Left[2];
366 pp[2] = Left[1];
367 pp[3] = Left[0];
368 pp[4] = top_left;
369 pp[5] = Above[0];
370 pp[6] = Above[1];
371 pp[7] = Above[2];
372 pp[8] = Above[3];
373
374
375 predictor[3 * 16 + 0] = (pp[0] + pp[1] + 1) >> 1;
376 predictor[3 * 16 + 1] = (pp[0] + pp[1] * 2 + pp[2] + 2) >> 2;
377 predictor[2 * 16 + 0] =
378 predictor[3 * 16 + 2] = (pp[1] + pp[2] + 1) >> 1;
379 predictor[2 * 16 + 1] =
380 predictor[3 * 16 + 3] = (pp[1] + pp[2] * 2 + pp[3] + 2) >> 2;
381 predictor[2 * 16 + 2] =
382 predictor[1 * 16 + 0] = (pp[2] + pp[3] + 1) >> 1;
383 predictor[2 * 16 + 3] =
384 predictor[1 * 16 + 1] = (pp[2] + pp[3] * 2 + pp[4] + 2) >> 2;
385 predictor[1 * 16 + 2] =
386 predictor[0 * 16 + 0] = (pp[3] + pp[4] + 1) >> 1;
387 predictor[1 * 16 + 3] =
388 predictor[0 * 16 + 1] = (pp[3] + pp[4] * 2 + pp[5] + 2) >> 2;
389 predictor[0 * 16 + 2] = (pp[4] + pp[5] * 2 + pp[6] + 2) >> 2;
390 predictor[0 * 16 + 3] = (pp[5] + pp[6] * 2 + pp[7] + 2) >> 2;
391 }
392 break;
393
394
395 case B_HU_PRED: {
396 unsigned char *pp = Left;
397 predictor[0 * 16 + 0] = (pp[0] + pp[1] + 1) >> 1;
398 predictor[0 * 16 + 1] = (pp[0] + pp[1] * 2 + pp[2] + 2) >> 2;
399 predictor[0 * 16 + 2] =
400 predictor[1 * 16 + 0] = (pp[1] + pp[2] + 1) >> 1;
401 predictor[0 * 16 + 3] =
402 predictor[1 * 16 + 1] = (pp[1] + pp[2] * 2 + pp[3] + 2) >> 2;
403 predictor[1 * 16 + 2] =
404 predictor[2 * 16 + 0] = (pp[2] + pp[3] + 1) >> 1;
405 predictor[1 * 16 + 3] =
406 predictor[2 * 16 + 1] = (pp[2] + pp[3] * 2 + pp[3] + 2) >> 2;
407 predictor[2 * 16 + 2] =
408 predictor[2 * 16 + 3] =
409 predictor[3 * 16 + 0] =
410 predictor[3 * 16 + 1] =
411 predictor[3 * 16 + 2] =
412 predictor[3 * 16 + 3] = pp[3];
413 }
414 break;
415
416 #if CONFIG_NEWBINTRAMODES
417 case B_CONTEXT_PRED:
418 break;
419 /*
420 case B_CORNER_PRED:
421 corner_predictor(predictor, 16, 4, Above, Left);
422 break;
423 */
424 #endif
425 }
426 }
427
428 #if CONFIG_COMP_INTRA_PRED
429 void vp9_comp_intra4x4_predict_c(BLOCKD *x,
430 int b_mode, int b_mode2,
431 unsigned char *out_predictor) {
432 unsigned char predictor[2][4 * 16];
433 int i, j;
434
435 vp9_intra4x4_predict(x, b_mode, predictor[0]);
436 vp9_intra4x4_predict(x, b_mode2, predictor[1]);
437
438 for (i = 0; i < 16 * 4; i += 16) {
439 for (j = i; j < i + 4; j++) {
440 out_predictor[j] = (predictor[0][j] + predictor[1][j] + 1) >> 1;
441 }
442 }
443 }
444 #endif
445
446 /* copy 4 bytes from the above right down so that the 4x4 prediction modes using pixels above and
447 * to the right prediction have filled in pixels to use.
448 */
449 void vp9_intra_prediction_down_copy(MACROBLOCKD *xd) {
450 int extend_edge = (xd->mb_to_right_edge == 0 && xd->mb_index < 2);
451 unsigned char *above_right = *(xd->block[0].base_dst) + xd->block[0].dst -
452 xd->block[0].dst_stride + 16;
453 unsigned int *src_ptr = (unsigned int *)
454 (above_right - (xd->mb_index == 3 ? 16 * xd->block[0].dst_stride : 0));
455
456 unsigned int *dst_ptr0 = (unsigned int *)above_right;
457 unsigned int *dst_ptr1 =
458 (unsigned int *)(above_right + 4 * xd->block[0].dst_stride);
459 unsigned int *dst_ptr2 =
460 (unsigned int *)(above_right + 8 * xd->block[0].dst_stride);
461 unsigned int *dst_ptr3 =
462 (unsigned int *)(above_right + 12 * xd->block[0].dst_stride);
463
464 if (extend_edge) {
465 *src_ptr = ((uint8_t *) src_ptr)[-1] * 0x01010101U;
466 }
467
468 *dst_ptr0 = *src_ptr;
469 *dst_ptr1 = *src_ptr;
470 *dst_ptr2 = *src_ptr;
471 *dst_ptr3 = *src_ptr;
472 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698