annotate vp56.c @ 7778:e31b0b920475 libavcodec

theoradec: skip decoding of uncoded MV in 4MV code Thusnelda, the new experimental Theora encoder is using this Theora feature that was previously not exploited. fixes issue579
author aurel
date Wed, 03 Sep 2008 00:17:11 +0000
parents 6c7e7fdedfd3
children 800444234375
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
1 /**
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
2 * @file vp56.c
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
3 * VP5 and VP6 compatible video decoder (common features)
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
4 *
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
5 * Copyright (C) 2006 Aurelien Jacobs <aurel@gnuage.org>
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
6 *
3947
c8c591fe26f8 Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents: 3715
diff changeset
7 * This file is part of FFmpeg.
c8c591fe26f8 Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents: 3715
diff changeset
8 *
c8c591fe26f8 Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents: 3715
diff changeset
9 * FFmpeg is free software; you can redistribute it and/or
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
10 * modify it under the terms of the GNU Lesser General Public
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
11 * License as published by the Free Software Foundation; either
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
12 * version 2.1 of the License, or (at your option) any later version.
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
13 *
3947
c8c591fe26f8 Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents: 3715
diff changeset
14 * FFmpeg is distributed in the hope that it will be useful,
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
15 * but WITHOUT ANY WARRANTY; without even the implied warranty of
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
17 * Lesser General Public License for more details.
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
18 *
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
19 * You should have received a copy of the GNU Lesser General Public
3947
c8c591fe26f8 Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents: 3715
diff changeset
20 * License along with FFmpeg; if not, write to the Free Software
5215
2b72f9bc4f06 license header consistency cosmetics
diego
parents: 4596
diff changeset
21 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
22 */
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
23
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
24 #include "avcodec.h"
5714
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
25 #include "bytestream.h"
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
26
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
27 #include "vp56.h"
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
28 #include "vp56data.h"
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
29
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
30
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
31 void vp56_init_dequant(vp56_context_t *s, int quantizer)
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
32 {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
33 s->quantizer = quantizer;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
34 s->dequant_dc = vp56_dc_dequant[quantizer] << 2;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
35 s->dequant_ac = vp56_ac_dequant[quantizer] << 2;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
36 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
37
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
38 static int vp56_get_vectors_predictors(vp56_context_t *s, int row, int col,
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
39 vp56_frame_t ref_frame)
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
40 {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
41 int nb_pred = 0;
3697
596e62da8f29 rename vector to vect to avoid clash with Apple gcc
aurel
parents: 3695
diff changeset
42 vp56_mv_t vect[2] = {{0,0}, {0,0}};
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
43 int pos, offset;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
44 vp56_mv_t mvp;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
45
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
46 for (pos=0; pos<12; pos++) {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
47 mvp.x = col + vp56_candidate_predictor_pos[pos][0];
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
48 mvp.y = row + vp56_candidate_predictor_pos[pos][1];
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
49 if (mvp.x < 0 || mvp.x >= s->mb_width ||
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
50 mvp.y < 0 || mvp.y >= s->mb_height)
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
51 continue;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
52 offset = mvp.x + s->mb_width*mvp.y;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
53
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
54 if (vp56_reference_frame[s->macroblocks[offset].type] != ref_frame)
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
55 continue;
3697
596e62da8f29 rename vector to vect to avoid clash with Apple gcc
aurel
parents: 3695
diff changeset
56 if ((s->macroblocks[offset].mv.x == vect[0].x &&
596e62da8f29 rename vector to vect to avoid clash with Apple gcc
aurel
parents: 3695
diff changeset
57 s->macroblocks[offset].mv.y == vect[0].y) ||
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
58 (s->macroblocks[offset].mv.x == 0 &&
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
59 s->macroblocks[offset].mv.y == 0))
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
60 continue;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
61
3697
596e62da8f29 rename vector to vect to avoid clash with Apple gcc
aurel
parents: 3695
diff changeset
62 vect[nb_pred++] = s->macroblocks[offset].mv;
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
63 if (nb_pred > 1) {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
64 nb_pred = -1;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
65 break;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
66 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
67 s->vector_candidate_pos = pos;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
68 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
69
3697
596e62da8f29 rename vector to vect to avoid clash with Apple gcc
aurel
parents: 3695
diff changeset
70 s->vector_candidate[0] = vect[0];
596e62da8f29 rename vector to vect to avoid clash with Apple gcc
aurel
parents: 3695
diff changeset
71 s->vector_candidate[1] = vect[1];
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
72
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
73 return nb_pred+1;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
74 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
75
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
76 static void vp56_parse_mb_type_models(vp56_context_t *s)
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
77 {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
78 vp56_range_coder_t *c = &s->c;
5711
dae0f80edbb3 move all model related tables into their own struct
aurel
parents: 5709
diff changeset
79 vp56_model_t *model = s->modelp;
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
80 int i, ctx, type;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
81
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
82 for (ctx=0; ctx<3; ctx++) {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
83 if (vp56_rac_get_prob(c, 174)) {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
84 int idx = vp56_rac_gets(c, 4);
5711
dae0f80edbb3 move all model related tables into their own struct
aurel
parents: 5709
diff changeset
85 memcpy(model->mb_types_stats[ctx],
dae0f80edbb3 move all model related tables into their own struct
aurel
parents: 5709
diff changeset
86 vp56_pre_def_mb_type_stats[idx][ctx],
dae0f80edbb3 move all model related tables into their own struct
aurel
parents: 5709
diff changeset
87 sizeof(model->mb_types_stats[ctx]));
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
88 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
89 if (vp56_rac_get_prob(c, 254)) {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
90 for (type=0; type<10; type++) {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
91 for(i=0; i<2; i++) {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
92 if (vp56_rac_get_prob(c, 205)) {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
93 int delta, sign = vp56_rac_get(c);
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
94
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
95 delta = vp56_rac_get_tree(c, vp56_pmbtm_tree,
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
96 vp56_mb_type_model_model);
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
97 if (!delta)
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
98 delta = 4 * vp56_rac_gets(c, 7);
5711
dae0f80edbb3 move all model related tables into their own struct
aurel
parents: 5709
diff changeset
99 model->mb_types_stats[ctx][type][i] += (delta ^ -sign) + sign;
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
100 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
101 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
102 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
103 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
104 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
105
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
106 /* compute MB type probability tables based on previous MB type */
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
107 for (ctx=0; ctx<3; ctx++) {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
108 int p[10];
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
109
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
110 for (type=0; type<10; type++)
5711
dae0f80edbb3 move all model related tables into their own struct
aurel
parents: 5709
diff changeset
111 p[type] = 100 * model->mb_types_stats[ctx][type][1];
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
112
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
113 for (type=0; type<10; type++) {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
114 int p02, p34, p0234, p17, p56, p89, p5689, p156789;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
115
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
116 /* conservative MB type probability */
5711
dae0f80edbb3 move all model related tables into their own struct
aurel
parents: 5709
diff changeset
117 model->mb_type[ctx][type][0] = 255 - (255 * model->mb_types_stats[ctx][type][0]) / (1 + model->mb_types_stats[ctx][type][0] + model->mb_types_stats[ctx][type][1]);
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
118
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
119 p[type] = 0; /* same MB type => weight is null */
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
120
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
121 /* binary tree parsing probabilities */
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
122 p02 = p[0] + p[2];
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
123 p34 = p[3] + p[4];
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
124 p0234 = p02 + p34;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
125 p17 = p[1] + p[7];
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
126 p56 = p[5] + p[6];
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
127 p89 = p[8] + p[9];
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
128 p5689 = p56 + p89;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
129 p156789 = p17 + p5689;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
130
5711
dae0f80edbb3 move all model related tables into their own struct
aurel
parents: 5709
diff changeset
131 model->mb_type[ctx][type][1] = 1 + 255 * p0234/(1+p0234+p156789);
dae0f80edbb3 move all model related tables into their own struct
aurel
parents: 5709
diff changeset
132 model->mb_type[ctx][type][2] = 1 + 255 * p02 / (1+p0234);
dae0f80edbb3 move all model related tables into their own struct
aurel
parents: 5709
diff changeset
133 model->mb_type[ctx][type][3] = 1 + 255 * p17 / (1+p156789);
dae0f80edbb3 move all model related tables into their own struct
aurel
parents: 5709
diff changeset
134 model->mb_type[ctx][type][4] = 1 + 255 * p[0] / (1+p02);
dae0f80edbb3 move all model related tables into their own struct
aurel
parents: 5709
diff changeset
135 model->mb_type[ctx][type][5] = 1 + 255 * p[3] / (1+p34);
dae0f80edbb3 move all model related tables into their own struct
aurel
parents: 5709
diff changeset
136 model->mb_type[ctx][type][6] = 1 + 255 * p[1] / (1+p17);
dae0f80edbb3 move all model related tables into their own struct
aurel
parents: 5709
diff changeset
137 model->mb_type[ctx][type][7] = 1 + 255 * p56 / (1+p5689);
dae0f80edbb3 move all model related tables into their own struct
aurel
parents: 5709
diff changeset
138 model->mb_type[ctx][type][8] = 1 + 255 * p[5] / (1+p56);
dae0f80edbb3 move all model related tables into their own struct
aurel
parents: 5709
diff changeset
139 model->mb_type[ctx][type][9] = 1 + 255 * p[8] / (1+p89);
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
140
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
141 /* restore initial value */
5711
dae0f80edbb3 move all model related tables into their own struct
aurel
parents: 5709
diff changeset
142 p[type] = 100 * model->mb_types_stats[ctx][type][1];
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
143 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
144 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
145 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
146
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
147 static vp56_mb_t vp56_parse_mb_type(vp56_context_t *s,
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
148 vp56_mb_t prev_type, int ctx)
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
149 {
5711
dae0f80edbb3 move all model related tables into their own struct
aurel
parents: 5709
diff changeset
150 uint8_t *mb_type_model = s->modelp->mb_type[ctx][prev_type];
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
151 vp56_range_coder_t *c = &s->c;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
152
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
153 if (vp56_rac_get_prob(c, mb_type_model[0]))
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
154 return prev_type;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
155 else
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
156 return vp56_rac_get_tree(c, vp56_pmbt_tree, mb_type_model);
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
157 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
158
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
159 static void vp56_decode_4mv(vp56_context_t *s, int row, int col)
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
160 {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
161 vp56_mv_t mv = {0,0};
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
162 int type[4];
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
163 int b;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
164
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
165 /* parse each block type */
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
166 for (b=0; b<4; b++) {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
167 type[b] = vp56_rac_gets(&s->c, 2);
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
168 if (type[b])
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
169 type[b]++; /* only returns 0, 2, 3 or 4 (all INTER_PF) */
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
170 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
171
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
172 /* get vectors */
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
173 for (b=0; b<4; b++) {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
174 switch (type[b]) {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
175 case VP56_MB_INTER_NOVEC_PF:
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
176 s->mv[b] = (vp56_mv_t) {0,0};
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
177 break;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
178 case VP56_MB_INTER_DELTA_PF:
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
179 s->parse_vector_adjustment(s, &s->mv[b]);
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
180 break;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
181 case VP56_MB_INTER_V1_PF:
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
182 s->mv[b] = s->vector_candidate[0];
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
183 break;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
184 case VP56_MB_INTER_V2_PF:
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
185 s->mv[b] = s->vector_candidate[1];
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
186 break;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
187 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
188 mv.x += s->mv[b].x;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
189 mv.y += s->mv[b].y;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
190 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
191
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
192 /* this is the one selected for the whole MB for prediction */
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
193 s->macroblocks[row * s->mb_width + col].mv = s->mv[3];
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
194
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
195 /* chroma vectors are average luma vectors */
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
196 if (s->avctx->codec->id == CODEC_ID_VP5) {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
197 s->mv[4].x = s->mv[5].x = RSHIFT(mv.x,2);
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
198 s->mv[4].y = s->mv[5].y = RSHIFT(mv.y,2);
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
199 } else {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
200 s->mv[4] = s->mv[5] = (vp56_mv_t) {mv.x/4, mv.y/4};
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
201 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
202 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
203
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
204 static vp56_mb_t vp56_decode_mv(vp56_context_t *s, int row, int col)
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
205 {
3697
596e62da8f29 rename vector to vect to avoid clash with Apple gcc
aurel
parents: 3695
diff changeset
206 vp56_mv_t *mv, vect = {0,0};
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
207 int ctx, b;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
208
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
209 ctx = vp56_get_vectors_predictors(s, row, col, VP56_FRAME_PREVIOUS);
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
210 s->mb_type = vp56_parse_mb_type(s, s->mb_type, ctx);
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
211 s->macroblocks[row * s->mb_width + col].type = s->mb_type;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
212
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
213 switch (s->mb_type) {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
214 case VP56_MB_INTER_V1_PF:
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
215 mv = &s->vector_candidate[0];
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
216 break;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
217
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
218 case VP56_MB_INTER_V2_PF:
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
219 mv = &s->vector_candidate[1];
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
220 break;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
221
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
222 case VP56_MB_INTER_V1_GF:
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
223 vp56_get_vectors_predictors(s, row, col, VP56_FRAME_GOLDEN);
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
224 mv = &s->vector_candidate[0];
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
225 break;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
226
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
227 case VP56_MB_INTER_V2_GF:
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
228 vp56_get_vectors_predictors(s, row, col, VP56_FRAME_GOLDEN);
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
229 mv = &s->vector_candidate[1];
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
230 break;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
231
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
232 case VP56_MB_INTER_DELTA_PF:
3697
596e62da8f29 rename vector to vect to avoid clash with Apple gcc
aurel
parents: 3695
diff changeset
233 s->parse_vector_adjustment(s, &vect);
596e62da8f29 rename vector to vect to avoid clash with Apple gcc
aurel
parents: 3695
diff changeset
234 mv = &vect;
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
235 break;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
236
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
237 case VP56_MB_INTER_DELTA_GF:
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
238 vp56_get_vectors_predictors(s, row, col, VP56_FRAME_GOLDEN);
3697
596e62da8f29 rename vector to vect to avoid clash with Apple gcc
aurel
parents: 3695
diff changeset
239 s->parse_vector_adjustment(s, &vect);
596e62da8f29 rename vector to vect to avoid clash with Apple gcc
aurel
parents: 3695
diff changeset
240 mv = &vect;
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
241 break;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
242
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
243 case VP56_MB_INTER_4V:
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
244 vp56_decode_4mv(s, row, col);
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
245 return s->mb_type;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
246
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
247 default:
3697
596e62da8f29 rename vector to vect to avoid clash with Apple gcc
aurel
parents: 3695
diff changeset
248 mv = &vect;
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
249 break;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
250 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
251
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
252 s->macroblocks[row*s->mb_width + col].mv = *mv;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
253
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
254 /* same vector for all blocks */
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
255 for (b=0; b<6; b++)
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
256 s->mv[b] = *mv;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
257
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
258 return s->mb_type;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
259 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
260
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
261 static void vp56_add_predictors_dc(vp56_context_t *s, vp56_frame_t ref_frame)
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
262 {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
263 int idx = s->scantable.permutated[0];
5718
bb4293d858da rename one variable to be consistent with the rest of the file
aurel
parents: 5717
diff changeset
264 int b;
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
265
5718
bb4293d858da rename one variable to be consistent with the rest of the file
aurel
parents: 5717
diff changeset
266 for (b=0; b<6; b++) {
bb4293d858da rename one variable to be consistent with the rest of the file
aurel
parents: 5717
diff changeset
267 vp56_ref_dc_t *ab = &s->above_blocks[s->above_block_idx[b]];
bb4293d858da rename one variable to be consistent with the rest of the file
aurel
parents: 5717
diff changeset
268 vp56_ref_dc_t *lb = &s->left_block[vp56_b6to4[b]];
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
269 int count = 0;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
270 int dc = 0;
5719
1643aa6ac147 simplify
aurel
parents: 5718
diff changeset
271 int i;
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
272
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
273 if (ref_frame == lb->ref_frame) {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
274 dc += lb->dc_coeff;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
275 count++;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
276 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
277 if (ref_frame == ab->ref_frame) {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
278 dc += ab->dc_coeff;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
279 count++;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
280 }
5719
1643aa6ac147 simplify
aurel
parents: 5718
diff changeset
281 if (s->avctx->codec->id == CODEC_ID_VP5)
1643aa6ac147 simplify
aurel
parents: 5718
diff changeset
282 for (i=0; i<2; i++)
1643aa6ac147 simplify
aurel
parents: 5718
diff changeset
283 if (count < 2 && ref_frame == ab[-1+2*i].ref_frame) {
1643aa6ac147 simplify
aurel
parents: 5718
diff changeset
284 dc += ab[-1+2*i].dc_coeff;
1643aa6ac147 simplify
aurel
parents: 5718
diff changeset
285 count++;
1643aa6ac147 simplify
aurel
parents: 5718
diff changeset
286 }
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
287 if (count == 0)
5718
bb4293d858da rename one variable to be consistent with the rest of the file
aurel
parents: 5717
diff changeset
288 dc = s->prev_dc[vp56_b2p[b]][ref_frame];
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
289 else if (count == 2)
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
290 dc /= 2;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
291
5718
bb4293d858da rename one variable to be consistent with the rest of the file
aurel
parents: 5717
diff changeset
292 s->block_coeff[b][idx] += dc;
bb4293d858da rename one variable to be consistent with the rest of the file
aurel
parents: 5717
diff changeset
293 s->prev_dc[vp56_b2p[b]][ref_frame] = s->block_coeff[b][idx];
bb4293d858da rename one variable to be consistent with the rest of the file
aurel
parents: 5717
diff changeset
294 ab->dc_coeff = s->block_coeff[b][idx];
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
295 ab->ref_frame = ref_frame;
5718
bb4293d858da rename one variable to be consistent with the rest of the file
aurel
parents: 5717
diff changeset
296 lb->dc_coeff = s->block_coeff[b][idx];
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
297 lb->ref_frame = ref_frame;
5718
bb4293d858da rename one variable to be consistent with the rest of the file
aurel
parents: 5717
diff changeset
298 s->block_coeff[b][idx] *= s->dequant_dc;
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
299 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
300 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
301
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
302 static void vp56_edge_filter(vp56_context_t *s, uint8_t *yuv,
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
303 int pix_inc, int line_inc, int t)
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
304 {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
305 int pix2_inc = 2 * pix_inc;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
306 int i, v;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
307
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
308 for (i=0; i<12; i++) {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
309 v = (yuv[-pix2_inc] + 3*(yuv[0]-yuv[-pix_inc]) - yuv[pix_inc] + 4) >>3;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
310 v = s->adjust(v, t);
4594
a96d905dcbaa Add av_ prefix to clip functions
reimar
parents: 4484
diff changeset
311 yuv[-pix_inc] = av_clip_uint8(yuv[-pix_inc] + v);
a96d905dcbaa Add av_ prefix to clip functions
reimar
parents: 4484
diff changeset
312 yuv[0] = av_clip_uint8(yuv[0] - v);
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
313 yuv += line_inc;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
314 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
315 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
316
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
317 static void vp56_deblock_filter(vp56_context_t *s, uint8_t *yuv,
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
318 int stride, int dx, int dy)
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
319 {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
320 int t = vp56_filter_threshold[s->quantizer];
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
321 if (dx) vp56_edge_filter(s, yuv + 10-dx , 1, stride, t);
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
322 if (dy) vp56_edge_filter(s, yuv + stride*(10-dy), stride, 1, t);
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
323 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
324
5708
8f52599c4c6c some simplifications and uniformisation
aurel
parents: 5215
diff changeset
325 static void vp56_mc(vp56_context_t *s, int b, int plane, uint8_t *src,
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
326 int stride, int x, int y)
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
327 {
4595
340c876320eb Use pointers to avoid copying AVFrame.
aurel
parents: 4594
diff changeset
328 uint8_t *dst=s->framep[VP56_FRAME_CURRENT]->data[plane]+s->block_offset[b];
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
329 uint8_t *src_block;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
330 int src_offset;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
331 int overlap_offset = 0;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
332 int mask = s->vp56_coord_div[b] - 1;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
333 int deblock_filtering = s->deblock_filtering;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
334 int dx;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
335 int dy;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
336
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
337 if (s->avctx->skip_loop_filter >= AVDISCARD_ALL ||
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
338 (s->avctx->skip_loop_filter >= AVDISCARD_NONKEY
4595
340c876320eb Use pointers to avoid copying AVFrame.
aurel
parents: 4594
diff changeset
339 && !s->framep[VP56_FRAME_CURRENT]->key_frame))
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
340 deblock_filtering = 0;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
341
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
342 dx = s->mv[b].x / s->vp56_coord_div[b];
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
343 dy = s->mv[b].y / s->vp56_coord_div[b];
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
344
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
345 if (b >= 4) {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
346 x /= 2;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
347 y /= 2;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
348 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
349 x += dx - 2;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
350 y += dy - 2;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
351
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
352 if (x<0 || x+12>=s->plane_width[plane] ||
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
353 y<0 || y+12>=s->plane_height[plane]) {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
354 ff_emulated_edge_mc(s->edge_emu_buffer,
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
355 src + s->block_offset[b] + (dy-2)*stride + (dx-2),
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
356 stride, 12, 12, x, y,
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
357 s->plane_width[plane],
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
358 s->plane_height[plane]);
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
359 src_block = s->edge_emu_buffer;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
360 src_offset = 2 + 2*stride;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
361 } else if (deblock_filtering) {
3715
cdaee53c5da1 replaces back some C code by dsp.put_pixels_tab[0][0] (revert r6231)
aurel
parents: 3706
diff changeset
362 /* only need a 12x12 block, but there is no such dsp function, */
cdaee53c5da1 replaces back some C code by dsp.put_pixels_tab[0][0] (revert r6231)
aurel
parents: 3706
diff changeset
363 /* so copy a 16x12 block */
cdaee53c5da1 replaces back some C code by dsp.put_pixels_tab[0][0] (revert r6231)
aurel
parents: 3706
diff changeset
364 s->dsp.put_pixels_tab[0][0](s->edge_emu_buffer,
cdaee53c5da1 replaces back some C code by dsp.put_pixels_tab[0][0] (revert r6231)
aurel
parents: 3706
diff changeset
365 src + s->block_offset[b] + (dy-2)*stride + (dx-2),
cdaee53c5da1 replaces back some C code by dsp.put_pixels_tab[0][0] (revert r6231)
aurel
parents: 3706
diff changeset
366 stride, 12);
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
367 src_block = s->edge_emu_buffer;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
368 src_offset = 2 + 2*stride;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
369 } else {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
370 src_block = src;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
371 src_offset = s->block_offset[b] + dy*stride + dx;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
372 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
373
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
374 if (deblock_filtering)
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
375 vp56_deblock_filter(s, src_block, stride, dx&7, dy&7);
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
376
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
377 if (s->mv[b].x & mask)
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
378 overlap_offset += (s->mv[b].x > 0) ? 1 : -1;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
379 if (s->mv[b].y & mask)
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
380 overlap_offset += (s->mv[b].y > 0) ? stride : -stride;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
381
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
382 if (overlap_offset) {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
383 if (s->filter)
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
384 s->filter(s, dst, src_block, src_offset, src_offset+overlap_offset,
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
385 stride, s->mv[b], mask, s->filter_selection, b<4);
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
386 else
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
387 s->dsp.put_no_rnd_pixels_l2[1](dst, src_block+src_offset,
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
388 src_block+src_offset+overlap_offset,
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
389 stride, 8);
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
390 } else {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
391 s->dsp.put_pixels_tab[1][0](dst, src_block+src_offset, stride, 8);
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
392 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
393 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
394
5714
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
395 static void vp56_decode_mb(vp56_context_t *s, int row, int col, int is_alpha)
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
396 {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
397 AVFrame *frame_current, *frame_ref;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
398 vp56_mb_t mb_type;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
399 vp56_frame_t ref_frame;
5717
c5ec68f922d8 consistent spelling: plan => plane
aurel
parents: 5716
diff changeset
400 int b, ab, b_max, plane, off;
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
401
4595
340c876320eb Use pointers to avoid copying AVFrame.
aurel
parents: 4594
diff changeset
402 if (s->framep[VP56_FRAME_CURRENT]->key_frame)
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
403 mb_type = VP56_MB_INTRA;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
404 else
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
405 mb_type = vp56_decode_mv(s, row, col);
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
406 ref_frame = vp56_reference_frame[mb_type];
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
407
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
408 memset(s->block_coeff, 0, sizeof(s->block_coeff));
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
409
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
410 s->parse_coeff(s);
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
411
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
412 vp56_add_predictors_dc(s, ref_frame);
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
413
4595
340c876320eb Use pointers to avoid copying AVFrame.
aurel
parents: 4594
diff changeset
414 frame_current = s->framep[VP56_FRAME_CURRENT];
340c876320eb Use pointers to avoid copying AVFrame.
aurel
parents: 4594
diff changeset
415 frame_ref = s->framep[ref_frame];
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
416
5714
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
417 ab = 6*is_alpha;
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
418 b_max = 6 - 2*is_alpha;
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
419
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
420 switch (mb_type) {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
421 case VP56_MB_INTRA:
5714
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
422 for (b=0; b<b_max; b++) {
5717
c5ec68f922d8 consistent spelling: plan => plane
aurel
parents: 5716
diff changeset
423 plane = vp56_b2p[b+ab];
c5ec68f922d8 consistent spelling: plan => plane
aurel
parents: 5716
diff changeset
424 s->dsp.idct_put(frame_current->data[plane] + s->block_offset[b],
c5ec68f922d8 consistent spelling: plan => plane
aurel
parents: 5716
diff changeset
425 s->stride[plane], s->block_coeff[b]);
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
426 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
427 break;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
428
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
429 case VP56_MB_INTER_NOVEC_PF:
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
430 case VP56_MB_INTER_NOVEC_GF:
5714
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
431 for (b=0; b<b_max; b++) {
5717
c5ec68f922d8 consistent spelling: plan => plane
aurel
parents: 5716
diff changeset
432 plane = vp56_b2p[b+ab];
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
433 off = s->block_offset[b];
5717
c5ec68f922d8 consistent spelling: plan => plane
aurel
parents: 5716
diff changeset
434 s->dsp.put_pixels_tab[1][0](frame_current->data[plane] + off,
c5ec68f922d8 consistent spelling: plan => plane
aurel
parents: 5716
diff changeset
435 frame_ref->data[plane] + off,
c5ec68f922d8 consistent spelling: plan => plane
aurel
parents: 5716
diff changeset
436 s->stride[plane], 8);
c5ec68f922d8 consistent spelling: plan => plane
aurel
parents: 5716
diff changeset
437 s->dsp.idct_add(frame_current->data[plane] + off,
c5ec68f922d8 consistent spelling: plan => plane
aurel
parents: 5716
diff changeset
438 s->stride[plane], s->block_coeff[b]);
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
439 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
440 break;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
441
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
442 case VP56_MB_INTER_DELTA_PF:
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
443 case VP56_MB_INTER_V1_PF:
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
444 case VP56_MB_INTER_V2_PF:
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
445 case VP56_MB_INTER_DELTA_GF:
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
446 case VP56_MB_INTER_4V:
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
447 case VP56_MB_INTER_V1_GF:
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
448 case VP56_MB_INTER_V2_GF:
5714
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
449 for (b=0; b<b_max; b++) {
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
450 int x_off = b==1 || b==3 ? 8 : 0;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
451 int y_off = b==2 || b==3 ? 8 : 0;
5717
c5ec68f922d8 consistent spelling: plan => plane
aurel
parents: 5716
diff changeset
452 plane = vp56_b2p[b+ab];
c5ec68f922d8 consistent spelling: plan => plane
aurel
parents: 5716
diff changeset
453 vp56_mc(s, b, plane, frame_ref->data[plane], s->stride[plane],
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
454 16*col+x_off, 16*row+y_off);
5717
c5ec68f922d8 consistent spelling: plan => plane
aurel
parents: 5716
diff changeset
455 s->dsp.idct_add(frame_current->data[plane] + s->block_offset[b],
c5ec68f922d8 consistent spelling: plan => plane
aurel
parents: 5716
diff changeset
456 s->stride[plane], s->block_coeff[b]);
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
457 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
458 break;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
459 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
460 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
461
5708
8f52599c4c6c some simplifications and uniformisation
aurel
parents: 5215
diff changeset
462 static int vp56_size_changed(AVCodecContext *avctx)
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
463 {
5708
8f52599c4c6c some simplifications and uniformisation
aurel
parents: 5215
diff changeset
464 vp56_context_t *s = avctx->priv_data;
4595
340c876320eb Use pointers to avoid copying AVFrame.
aurel
parents: 4594
diff changeset
465 int stride = s->framep[VP56_FRAME_CURRENT]->linesize[0];
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
466 int i;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
467
5714
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
468 s->plane_width[0] = s->plane_width[3] = avctx->coded_width;
5708
8f52599c4c6c some simplifications and uniformisation
aurel
parents: 5215
diff changeset
469 s->plane_width[1] = s->plane_width[2] = avctx->coded_width/2;
5714
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
470 s->plane_height[0] = s->plane_height[3] = avctx->coded_height;
5708
8f52599c4c6c some simplifications and uniformisation
aurel
parents: 5215
diff changeset
471 s->plane_height[1] = s->plane_height[2] = avctx->coded_height/2;
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
472
5714
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
473 for (i=0; i<4; i++)
4595
340c876320eb Use pointers to avoid copying AVFrame.
aurel
parents: 4594
diff changeset
474 s->stride[i] = s->flip * s->framep[VP56_FRAME_CURRENT]->linesize[i];
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
475
5708
8f52599c4c6c some simplifications and uniformisation
aurel
parents: 5215
diff changeset
476 s->mb_width = (avctx->coded_width +15) / 16;
8f52599c4c6c some simplifications and uniformisation
aurel
parents: 5215
diff changeset
477 s->mb_height = (avctx->coded_height+15) / 16;
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
478
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
479 if (s->mb_width > 1000 || s->mb_height > 1000) {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
480 av_log(avctx, AV_LOG_ERROR, "picture too big\n");
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
481 return -1;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
482 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
483
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
484 s->above_blocks = av_realloc(s->above_blocks,
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
485 (4*s->mb_width+6) * sizeof(*s->above_blocks));
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
486 s->macroblocks = av_realloc(s->macroblocks,
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
487 s->mb_width*s->mb_height*sizeof(*s->macroblocks));
3715
cdaee53c5da1 replaces back some C code by dsp.put_pixels_tab[0][0] (revert r6231)
aurel
parents: 3706
diff changeset
488 av_free(s->edge_emu_buffer_alloc);
cdaee53c5da1 replaces back some C code by dsp.put_pixels_tab[0][0] (revert r6231)
aurel
parents: 3706
diff changeset
489 s->edge_emu_buffer_alloc = av_malloc(16*stride);
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
490 s->edge_emu_buffer = s->edge_emu_buffer_alloc;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
491 if (s->flip < 0)
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
492 s->edge_emu_buffer += 15 * stride;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
493
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
494 return 0;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
495 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
496
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
497 int vp56_decode_frame(AVCodecContext *avctx, void *data, int *data_size,
6297
michael
parents: 5719
diff changeset
498 const uint8_t *buf, int buf_size)
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
499 {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
500 vp56_context_t *s = avctx->priv_data;
4595
340c876320eb Use pointers to avoid copying AVFrame.
aurel
parents: 4594
diff changeset
501 AVFrame *const p = s->framep[VP56_FRAME_CURRENT];
6756
c00f5cad61cc ensure vp56_decode_frame always return unchanged buf_size
aurel
parents: 6517
diff changeset
502 int remaining_buf_size = buf_size;
5714
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
503 int is_alpha, alpha_offset;
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
504
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
505 if (s->has_alpha) {
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
506 alpha_offset = bytestream_get_be24(&buf);
6756
c00f5cad61cc ensure vp56_decode_frame always return unchanged buf_size
aurel
parents: 6517
diff changeset
507 remaining_buf_size -= 3;
5714
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
508 }
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
509
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
510 for (is_alpha=0; is_alpha < 1+s->has_alpha; is_alpha++) {
5715
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
511 int mb_row, mb_col, mb_row_flip, mb_offset = 0;
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
512 int block, y, uv, stride_y, stride_uv;
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
513 int golden_frame = 0;
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
514 int res;
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
515
5715
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
516 s->modelp = &s->models[is_alpha];
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
517
6756
c00f5cad61cc ensure vp56_decode_frame always return unchanged buf_size
aurel
parents: 6517
diff changeset
518 res = s->parse_header(s, buf, remaining_buf_size, &golden_frame);
5715
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
519 if (!res)
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
520 return -1;
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
521
5715
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
522 if (!is_alpha) {
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
523 p->reference = 1;
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
524 if (avctx->get_buffer(avctx, p) < 0) {
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
525 av_log(avctx, AV_LOG_ERROR, "get_buffer() failed\n");
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
526 return -1;
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
527 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
528
5715
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
529 if (res == 2)
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
530 if (vp56_size_changed(avctx)) {
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
531 avctx->release_buffer(avctx, p);
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
532 return -1;
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
533 }
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
534 }
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
535
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
536 if (p->key_frame) {
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
537 p->pict_type = FF_I_TYPE;
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
538 s->default_models_init(s);
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
539 for (block=0; block<s->mb_height*s->mb_width; block++)
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
540 s->macroblocks[block].type = VP56_MB_INTRA;
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
541 } else {
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
542 p->pict_type = FF_P_TYPE;
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
543 vp56_parse_mb_type_models(s);
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
544 s->parse_vector_models(s);
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
545 s->mb_type = VP56_MB_INTER_NOVEC_PF;
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
546 }
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
547
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
548 s->parse_coeff_models(s);
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
549
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
550 memset(s->prev_dc, 0, sizeof(s->prev_dc));
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
551 s->prev_dc[1][VP56_FRAME_CURRENT] = 128;
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
552 s->prev_dc[2][VP56_FRAME_CURRENT] = 128;
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
553
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
554 for (block=0; block < 4*s->mb_width+6; block++) {
6795
6c7e7fdedfd3 Add VP56_FRAME_NONE and use VP56_FRAME_CURRENT.
cehoyos
parents: 6756
diff changeset
555 s->above_blocks[block].ref_frame = VP56_FRAME_NONE;
5715
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
556 s->above_blocks[block].dc_coeff = 0;
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
557 s->above_blocks[block].not_null_dc = 0;
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
558 }
6795
6c7e7fdedfd3 Add VP56_FRAME_NONE and use VP56_FRAME_CURRENT.
cehoyos
parents: 6756
diff changeset
559 s->above_blocks[2*s->mb_width + 2].ref_frame = VP56_FRAME_CURRENT;
6c7e7fdedfd3 Add VP56_FRAME_NONE and use VP56_FRAME_CURRENT.
cehoyos
parents: 6756
diff changeset
560 s->above_blocks[3*s->mb_width + 4].ref_frame = VP56_FRAME_CURRENT;
5715
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
561
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
562 stride_y = p->linesize[0];
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
563 stride_uv = p->linesize[1];
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
564
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
565 if (s->flip < 0)
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
566 mb_offset = 7;
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
567
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
568 /* main macroblocks loop */
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
569 for (mb_row=0; mb_row<s->mb_height; mb_row++) {
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
570 if (s->flip < 0)
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
571 mb_row_flip = s->mb_height - mb_row - 1;
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
572 else
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
573 mb_row_flip = mb_row;
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
574
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
575 for (block=0; block<4; block++) {
6795
6c7e7fdedfd3 Add VP56_FRAME_NONE and use VP56_FRAME_CURRENT.
cehoyos
parents: 6756
diff changeset
576 s->left_block[block].ref_frame = VP56_FRAME_NONE;
5715
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
577 s->left_block[block].dc_coeff = 0;
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
578 s->left_block[block].not_null_dc = 0;
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
579 }
5716
7577e3036290 simplify
aurel
parents: 5715
diff changeset
580 memset(s->coeff_ctx, 0, sizeof(s->coeff_ctx));
5715
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
581 memset(s->coeff_ctx_last, 24, sizeof(s->coeff_ctx_last));
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
582
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
583 s->above_block_idx[0] = 1;
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
584 s->above_block_idx[1] = 2;
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
585 s->above_block_idx[2] = 1;
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
586 s->above_block_idx[3] = 2;
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
587 s->above_block_idx[4] = 2*s->mb_width + 2 + 1;
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
588 s->above_block_idx[5] = 3*s->mb_width + 4 + 1;
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
589
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
590 s->block_offset[s->frbi] = (mb_row_flip*16 + mb_offset) * stride_y;
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
591 s->block_offset[s->srbi] = s->block_offset[s->frbi] + 8*stride_y;
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
592 s->block_offset[1] = s->block_offset[0] + 8;
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
593 s->block_offset[3] = s->block_offset[2] + 8;
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
594 s->block_offset[4] = (mb_row_flip*8 + mb_offset) * stride_uv;
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
595 s->block_offset[5] = s->block_offset[4];
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
596
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
597 for (mb_col=0; mb_col<s->mb_width; mb_col++) {
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
598 vp56_decode_mb(s, mb_row, mb_col, is_alpha);
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
599
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
600 for (y=0; y<4; y++) {
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
601 s->above_block_idx[y] += 2;
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
602 s->block_offset[y] += 16;
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
603 }
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
604
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
605 for (uv=4; uv<6; uv++) {
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
606 s->above_block_idx[uv] += 1;
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
607 s->block_offset[uv] += 8;
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
608 }
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
609 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
610 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
611
5715
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
612 if (p->key_frame || golden_frame) {
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
613 if (s->framep[VP56_FRAME_GOLDEN]->data[0] &&
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
614 s->framep[VP56_FRAME_GOLDEN] != s->framep[VP56_FRAME_GOLDEN2])
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
615 avctx->release_buffer(avctx, s->framep[VP56_FRAME_GOLDEN]);
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
616 s->framep[VP56_FRAME_GOLDEN] = p;
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
617 }
5714
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
618
5715
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
619 if (s->has_alpha) {
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
620 FFSWAP(AVFrame *, s->framep[VP56_FRAME_GOLDEN],
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
621 s->framep[VP56_FRAME_GOLDEN2]);
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
622 buf += alpha_offset;
6756
c00f5cad61cc ensure vp56_decode_frame always return unchanged buf_size
aurel
parents: 6517
diff changeset
623 remaining_buf_size -= alpha_offset;
5715
fbd55dbbf809 cosmetic: indent
aurel
parents: 5714
diff changeset
624 }
5714
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
625 }
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
626
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
627 if (s->framep[VP56_FRAME_PREVIOUS] == s->framep[VP56_FRAME_GOLDEN] ||
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
628 s->framep[VP56_FRAME_PREVIOUS] == s->framep[VP56_FRAME_GOLDEN2]) {
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
629 if (s->framep[VP56_FRAME_UNUSED] != s->framep[VP56_FRAME_GOLDEN] &&
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
630 s->framep[VP56_FRAME_UNUSED] != s->framep[VP56_FRAME_GOLDEN2])
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
631 FFSWAP(AVFrame *, s->framep[VP56_FRAME_PREVIOUS],
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
632 s->framep[VP56_FRAME_UNUSED]);
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
633 else
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
634 FFSWAP(AVFrame *, s->framep[VP56_FRAME_PREVIOUS],
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
635 s->framep[VP56_FRAME_UNUSED2]);
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
636 } else if (s->framep[VP56_FRAME_PREVIOUS]->data[0])
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
637 avctx->release_buffer(avctx, s->framep[VP56_FRAME_PREVIOUS]);
4595
340c876320eb Use pointers to avoid copying AVFrame.
aurel
parents: 4594
diff changeset
638 FFSWAP(AVFrame *, s->framep[VP56_FRAME_CURRENT],
340c876320eb Use pointers to avoid copying AVFrame.
aurel
parents: 4594
diff changeset
639 s->framep[VP56_FRAME_PREVIOUS]);
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
640
4596
4992cbff45c6 cleanup setting of returned data frame
aurel
parents: 4595
diff changeset
641 *(AVFrame*)data = *p;
4992cbff45c6 cleanup setting of returned data frame
aurel
parents: 4595
diff changeset
642 *data_size = sizeof(AVFrame);
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
643
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
644 return buf_size;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
645 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
646
6517
48759bfbd073 Apply 'cold' attribute to init/uninit functions in libavcodec
zuxy
parents: 6297
diff changeset
647 av_cold void vp56_init(AVCodecContext *avctx, int flip, int has_alpha)
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
648 {
5708
8f52599c4c6c some simplifications and uniformisation
aurel
parents: 5215
diff changeset
649 vp56_context_t *s = avctx->priv_data;
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
650 int i;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
651
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
652 s->avctx = avctx;
5714
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
653 avctx->pix_fmt = has_alpha ? PIX_FMT_YUVA420P : PIX_FMT_YUV420P;
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
654
5708
8f52599c4c6c some simplifications and uniformisation
aurel
parents: 5215
diff changeset
655 if (avctx->idct_algo == FF_IDCT_AUTO)
8f52599c4c6c some simplifications and uniformisation
aurel
parents: 5215
diff changeset
656 avctx->idct_algo = FF_IDCT_VP3;
8f52599c4c6c some simplifications and uniformisation
aurel
parents: 5215
diff changeset
657 dsputil_init(&s->dsp, avctx);
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
658 ff_init_scantable(s->dsp.idct_permutation, &s->scantable,ff_zigzag_direct);
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
659
5708
8f52599c4c6c some simplifications and uniformisation
aurel
parents: 5215
diff changeset
660 avcodec_set_dimensions(avctx, 0, 0);
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
661
5714
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
662 for (i=0; i<4; i++)
4595
340c876320eb Use pointers to avoid copying AVFrame.
aurel
parents: 4594
diff changeset
663 s->framep[i] = &s->frames[i];
340c876320eb Use pointers to avoid copying AVFrame.
aurel
parents: 4594
diff changeset
664 s->framep[VP56_FRAME_UNUSED] = s->framep[VP56_FRAME_GOLDEN];
5714
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
665 s->framep[VP56_FRAME_UNUSED2] = s->framep[VP56_FRAME_GOLDEN2];
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
666 s->edge_emu_buffer_alloc = NULL;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
667
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
668 s->above_blocks = NULL;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
669 s->macroblocks = NULL;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
670 s->quantizer = -1;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
671 s->deblock_filtering = 1;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
672
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
673 s->filter = NULL;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
674
5714
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
675 s->has_alpha = has_alpha;
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
676 if (flip) {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
677 s->flip = -1;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
678 s->frbi = 2;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
679 s->srbi = 0;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
680 } else {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
681 s->flip = 1;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
682 s->frbi = 0;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
683 s->srbi = 2;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
684 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
685 }
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
686
6517
48759bfbd073 Apply 'cold' attribute to init/uninit functions in libavcodec
zuxy
parents: 6297
diff changeset
687 av_cold int vp56_free(AVCodecContext *avctx)
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
688 {
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
689 vp56_context_t *s = avctx->priv_data;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
690
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
691 av_free(s->above_blocks);
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
692 av_free(s->macroblocks);
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
693 av_free(s->edge_emu_buffer_alloc);
5708
8f52599c4c6c some simplifications and uniformisation
aurel
parents: 5215
diff changeset
694 if (s->framep[VP56_FRAME_GOLDEN]->data[0])
4595
340c876320eb Use pointers to avoid copying AVFrame.
aurel
parents: 4594
diff changeset
695 avctx->release_buffer(avctx, s->framep[VP56_FRAME_GOLDEN]);
5714
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
696 if (s->framep[VP56_FRAME_GOLDEN2]->data[0])
314be1cfdcb0 add a new vp6a codec (add alpha plan support to vp6)
aurel
parents: 5711
diff changeset
697 avctx->release_buffer(avctx, s->framep[VP56_FRAME_GOLDEN2]);
4595
340c876320eb Use pointers to avoid copying AVFrame.
aurel
parents: 4594
diff changeset
698 if (s->framep[VP56_FRAME_PREVIOUS]->data[0])
340c876320eb Use pointers to avoid copying AVFrame.
aurel
parents: 4594
diff changeset
699 avctx->release_buffer(avctx, s->framep[VP56_FRAME_PREVIOUS]);
3695
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
700 return 0;
6795c9e5f983 VP5 and VP6 video decoder
aurel
parents:
diff changeset
701 }