Mercurial > libavcodec.hg
annotate vp6.c @ 6323:e6da66f378c7 libavcodec
mpegvideo.h has two function declarations with the 'inline' specifier
but no definition for those functions. The C standard requires a
definition to appear in the same translation unit for any function
declared with 'inline'. Most of the files including mpegvideo.h do not
define those functions. Fix this by removing the 'inline' specifiers
from the header.
patch by Uoti Urpala
author | diego |
---|---|
date | Sun, 03 Feb 2008 17:54:30 +0000 |
parents | 1b91ce6c758c |
children | 7fa807dd7958 |
rev | line source |
---|---|
3695 | 1 /** |
2 * @file vp6.c | |
3 * VP6 compatible video decoder | |
4 * | |
5 * Copyright (C) 2006 Aurelien Jacobs <aurel@gnuage.org> | |
6 * | |
5214 | 7 * The VP6F decoder accepts an optional 1 byte extradata. It is composed of: |
8 * - upper 4bits: difference between encoded width and visible width | |
9 * - lower 4bits: difference between encoded height and visible height | |
10 * | |
3947
c8c591fe26f8
Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents:
3697
diff
changeset
|
11 * This file is part of FFmpeg. |
c8c591fe26f8
Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents:
3697
diff
changeset
|
12 * |
c8c591fe26f8
Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents:
3697
diff
changeset
|
13 * FFmpeg is free software; you can redistribute it and/or |
3695 | 14 * modify it under the terms of the GNU Lesser General Public |
15 * License as published by the Free Software Foundation; either | |
16 * version 2.1 of the License, or (at your option) any later version. | |
17 * | |
3947
c8c591fe26f8
Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents:
3697
diff
changeset
|
18 * FFmpeg is distributed in the hope that it will be useful, |
3695 | 19 * but WITHOUT ANY WARRANTY; without even the implied warranty of |
20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | |
21 * Lesser General Public License for more details. | |
22 * | |
23 * 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:
3697
diff
changeset
|
24 * License along with FFmpeg; if not, write to the Free Software |
5214 | 25 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA |
3695 | 26 */ |
27 | |
28 #include <stdlib.h> | |
29 | |
30 #include "avcodec.h" | |
31 #include "dsputil.h" | |
32 #include "bitstream.h" | |
5821 | 33 #include "huffman.h" |
3695 | 34 #include "mpegvideo.h" |
35 | |
36 #include "vp56.h" | |
37 #include "vp56data.h" | |
38 #include "vp6data.h" | |
39 | |
40 | |
5821 | 41 static void vp6_parse_coeff(vp56_context_t *s); |
42 static void vp6_parse_coeff_huffman(vp56_context_t *s); | |
43 | |
6297 | 44 static int vp6_parse_header(vp56_context_t *s, const uint8_t *buf, int buf_size, |
3695 | 45 int *golden_frame) |
46 { | |
47 vp56_range_coder_t *c = &s->c; | |
4308 | 48 int parse_filter_info = 0; |
4348 | 49 int coeff_offset = 0; |
4308 | 50 int vrt_shift = 0; |
51 int sub_version; | |
3695 | 52 int rows, cols; |
53 int res = 1; | |
4348 | 54 int separated_coeff = buf[0] & 1; |
3695 | 55 |
4595 | 56 s->framep[VP56_FRAME_CURRENT]->key_frame = !(buf[0] & 0x80); |
3695 | 57 vp56_init_dequant(s, (buf[0] >> 1) & 0x3F); |
58 | |
4595 | 59 if (s->framep[VP56_FRAME_CURRENT]->key_frame) { |
4308 | 60 sub_version = buf[1] >> 3; |
61 if (sub_version > 8) | |
62 return 0; | |
4348 | 63 s->filter_header = buf[1] & 0x06; |
3695 | 64 if (buf[1] & 1) { |
65 av_log(s->avctx, AV_LOG_ERROR, "interlacing not supported\n"); | |
66 return 0; | |
67 } | |
4348 | 68 if (separated_coeff || !s->filter_header) { |
4364 | 69 coeff_offset = AV_RB16(buf+2) - 2; |
4348 | 70 buf += 2; |
71 buf_size -= 2; | |
72 } | |
3695 | 73 |
74 rows = buf[2]; /* number of stored macroblock rows */ | |
75 cols = buf[3]; /* number of stored macroblock cols */ | |
76 /* buf[4] is number of displayed macroblock rows */ | |
77 /* buf[5] is number of displayed macroblock cols */ | |
78 | |
79 if (16*cols != s->avctx->coded_width || | |
80 16*rows != s->avctx->coded_height) { | |
81 avcodec_set_dimensions(s->avctx, 16*cols, 16*rows); | |
4062
683d458a251f
use the adjustment value present in FLV to crop VP6 video
aurel
parents:
4001
diff
changeset
|
82 if (s->avctx->extradata_size == 1) { |
683d458a251f
use the adjustment value present in FLV to crop VP6 video
aurel
parents:
4001
diff
changeset
|
83 s->avctx->width -= s->avctx->extradata[0] >> 4; |
683d458a251f
use the adjustment value present in FLV to crop VP6 video
aurel
parents:
4001
diff
changeset
|
84 s->avctx->height -= s->avctx->extradata[0] & 0x0F; |
683d458a251f
use the adjustment value present in FLV to crop VP6 video
aurel
parents:
4001
diff
changeset
|
85 } |
3695 | 86 res = 2; |
87 } | |
88 | |
89 vp56_init_range_decoder(c, buf+6, buf_size-6); | |
90 vp56_rac_gets(c, 2); | |
91 | |
4348 | 92 parse_filter_info = s->filter_header; |
4308 | 93 if (sub_version < 8) |
94 vrt_shift = 5; | |
95 s->sub_version = sub_version; | |
3695 | 96 } else { |
4308 | 97 if (!s->sub_version) |
98 return 0; | |
99 | |
4348 | 100 if (separated_coeff || !s->filter_header) { |
4364 | 101 coeff_offset = AV_RB16(buf+1) - 2; |
4348 | 102 buf += 2; |
103 buf_size -= 2; | |
104 } | |
3695 | 105 vp56_init_range_decoder(c, buf+1, buf_size-1); |
106 | |
107 *golden_frame = vp56_rac_get(c); | |
4348 | 108 if (s->filter_header) { |
4349 | 109 s->deblock_filtering = vp56_rac_get(c); |
110 if (s->deblock_filtering) | |
111 vp56_rac_get(c); | |
112 if (s->sub_version > 7) | |
113 parse_filter_info = vp56_rac_get(c); | |
4348 | 114 } |
3695 | 115 } |
116 | |
117 if (parse_filter_info) { | |
118 if (vp56_rac_get(c)) { | |
119 s->filter_mode = 2; | |
4308 | 120 s->sample_variance_threshold = vp56_rac_gets(c, 5) << vrt_shift; |
3695 | 121 s->max_vector_length = 2 << vp56_rac_gets(c, 3); |
122 } else if (vp56_rac_get(c)) { | |
123 s->filter_mode = 1; | |
124 } else { | |
125 s->filter_mode = 0; | |
126 } | |
4308 | 127 if (s->sub_version > 7) |
128 s->filter_selection = vp56_rac_gets(c, 4); | |
129 else | |
130 s->filter_selection = 16; | |
3695 | 131 } |
132 | |
5821 | 133 s->use_huffman = vp56_rac_get(c); |
4348 | 134 |
5821 | 135 s->parse_coeff = vp6_parse_coeff; |
4348 | 136 if (coeff_offset) { |
5821 | 137 buf += coeff_offset; |
138 buf_size -= coeff_offset; | |
139 if (s->use_huffman) { | |
140 s->parse_coeff = vp6_parse_coeff_huffman; | |
5945 | 141 init_get_bits(&s->gb, buf, buf_size<<3); |
5821 | 142 } else { |
143 vp56_init_range_decoder(&s->cc, buf, buf_size); | |
144 s->ccp = &s->cc; | |
145 } | |
4348 | 146 } else { |
147 s->ccp = &s->c; | |
148 } | |
149 | |
3695 | 150 return res; |
151 } | |
152 | |
153 static void vp6_coeff_order_table_init(vp56_context_t *s) | |
154 { | |
155 int i, pos, idx = 1; | |
156 | |
5711 | 157 s->modelp->coeff_index_to_pos[0] = 0; |
3695 | 158 for (i=0; i<16; i++) |
159 for (pos=1; pos<64; pos++) | |
5711 | 160 if (s->modelp->coeff_reorder[pos] == i) |
161 s->modelp->coeff_index_to_pos[idx++] = pos; | |
3695 | 162 } |
163 | |
164 static void vp6_default_models_init(vp56_context_t *s) | |
165 { | |
5711 | 166 vp56_model_t *model = s->modelp; |
3695 | 167 |
5711 | 168 model->vector_dct[0] = 0xA2; |
169 model->vector_dct[1] = 0xA4; | |
170 model->vector_sig[0] = 0x80; | |
171 model->vector_sig[1] = 0x80; | |
172 | |
173 memcpy(model->mb_types_stats, vp56_def_mb_types_stats, sizeof(model->mb_types_stats)); | |
174 memcpy(model->vector_fdv, vp6_def_fdv_vector_model, sizeof(model->vector_fdv)); | |
175 memcpy(model->vector_pdv, vp6_def_pdv_vector_model, sizeof(model->vector_pdv)); | |
176 memcpy(model->coeff_runv, vp6_def_runv_coeff_model, sizeof(model->coeff_runv)); | |
177 memcpy(model->coeff_reorder, vp6_def_coeff_reorder, sizeof(model->coeff_reorder)); | |
3695 | 178 |
179 vp6_coeff_order_table_init(s); | |
180 } | |
181 | |
182 static void vp6_parse_vector_models(vp56_context_t *s) | |
183 { | |
184 vp56_range_coder_t *c = &s->c; | |
5711 | 185 vp56_model_t *model = s->modelp; |
3695 | 186 int comp, node; |
187 | |
188 for (comp=0; comp<2; comp++) { | |
189 if (vp56_rac_get_prob(c, vp6_sig_dct_pct[comp][0])) | |
5711 | 190 model->vector_dct[comp] = vp56_rac_gets_nn(c, 7); |
3695 | 191 if (vp56_rac_get_prob(c, vp6_sig_dct_pct[comp][1])) |
5711 | 192 model->vector_sig[comp] = vp56_rac_gets_nn(c, 7); |
3695 | 193 } |
194 | |
195 for (comp=0; comp<2; comp++) | |
196 for (node=0; node<7; node++) | |
197 if (vp56_rac_get_prob(c, vp6_pdv_pct[comp][node])) | |
5711 | 198 model->vector_pdv[comp][node] = vp56_rac_gets_nn(c, 7); |
3695 | 199 |
200 for (comp=0; comp<2; comp++) | |
201 for (node=0; node<8; node++) | |
202 if (vp56_rac_get_prob(c, vp6_fdv_pct[comp][node])) | |
5711 | 203 model->vector_fdv[comp][node] = vp56_rac_gets_nn(c, 7); |
3695 | 204 } |
205 | |
5821 | 206 static int vp6_huff_cmp(const void *va, const void *vb) |
207 { | |
208 const Node *a = va, *b = vb; | |
209 return a->count >= b->count; | |
210 } | |
211 | |
212 static void vp6_build_huff_tree(vp56_context_t *s, uint8_t coeff_model[], | |
213 const uint8_t *map, unsigned size, VLC *vlc) | |
214 { | |
215 Node nodes[2*size], *tmp = &nodes[size]; | |
216 int a, b, i; | |
217 | |
218 /* first compute probabilities from model */ | |
219 tmp[0].count = 256; | |
220 for (i=0; i<size-1; i++) { | |
221 a = tmp[i].count * coeff_model[i] >> 8; | |
222 b = tmp[i].count * (255 - coeff_model[i]) >> 8; | |
223 nodes[map[2*i ]].count = a + !a; | |
224 nodes[map[2*i+1]].count = b + !b; | |
225 } | |
226 | |
227 /* then build the huffman tree accodring to probabilities */ | |
228 ff_huff_build_tree(s->avctx, vlc, size, nodes, vp6_huff_cmp, 1); | |
229 } | |
230 | |
3695 | 231 static void vp6_parse_coeff_models(vp56_context_t *s) |
232 { | |
233 vp56_range_coder_t *c = &s->c; | |
5711 | 234 vp56_model_t *model = s->modelp; |
3695 | 235 int def_prob[11]; |
236 int node, cg, ctx, pos; | |
237 int ct; /* code type */ | |
238 int pt; /* plane type (0 for Y, 1 for U or V) */ | |
239 | |
240 memset(def_prob, 0x80, sizeof(def_prob)); | |
241 | |
242 for (pt=0; pt<2; pt++) | |
243 for (node=0; node<11; node++) | |
244 if (vp56_rac_get_prob(c, vp6_dccv_pct[pt][node])) { | |
245 def_prob[node] = vp56_rac_gets_nn(c, 7); | |
5711 | 246 model->coeff_dccv[pt][node] = def_prob[node]; |
4595 | 247 } else if (s->framep[VP56_FRAME_CURRENT]->key_frame) { |
5711 | 248 model->coeff_dccv[pt][node] = def_prob[node]; |
3695 | 249 } |
250 | |
251 if (vp56_rac_get(c)) { | |
252 for (pos=1; pos<64; pos++) | |
253 if (vp56_rac_get_prob(c, vp6_coeff_reorder_pct[pos])) | |
5711 | 254 model->coeff_reorder[pos] = vp56_rac_gets(c, 4); |
3695 | 255 vp6_coeff_order_table_init(s); |
256 } | |
257 | |
258 for (cg=0; cg<2; cg++) | |
259 for (node=0; node<14; node++) | |
260 if (vp56_rac_get_prob(c, vp6_runv_pct[cg][node])) | |
5711 | 261 model->coeff_runv[cg][node] = vp56_rac_gets_nn(c, 7); |
3695 | 262 |
263 for (ct=0; ct<3; ct++) | |
264 for (pt=0; pt<2; pt++) | |
265 for (cg=0; cg<6; cg++) | |
266 for (node=0; node<11; node++) | |
267 if (vp56_rac_get_prob(c, vp6_ract_pct[ct][pt][cg][node])) { | |
268 def_prob[node] = vp56_rac_gets_nn(c, 7); | |
5711 | 269 model->coeff_ract[pt][ct][cg][node] = def_prob[node]; |
4595 | 270 } else if (s->framep[VP56_FRAME_CURRENT]->key_frame) { |
5711 | 271 model->coeff_ract[pt][ct][cg][node] = def_prob[node]; |
3695 | 272 } |
273 | |
5821 | 274 if (s->use_huffman) { |
275 for (pt=0; pt<2; pt++) { | |
276 vp6_build_huff_tree(s, model->coeff_dccv[pt], | |
277 vp6_huff_coeff_map, 12, &s->dccv_vlc[pt]); | |
278 vp6_build_huff_tree(s, model->coeff_runv[pt], | |
279 vp6_huff_run_map, 9, &s->runv_vlc[pt]); | |
280 for (ct=0; ct<3; ct++) | |
281 for (cg = 0; cg < 6; cg++) | |
282 vp6_build_huff_tree(s, model->coeff_ract[pt][ct][cg], | |
283 vp6_huff_coeff_map, 12, | |
284 &s->ract_vlc[pt][ct][cg]); | |
285 } | |
286 memset(s->nb_null, 0, sizeof(s->nb_null)); | |
287 } else { | |
5711 | 288 /* coeff_dcct is a linear combination of coeff_dccv */ |
3695 | 289 for (pt=0; pt<2; pt++) |
290 for (ctx=0; ctx<3; ctx++) | |
291 for (node=0; node<5; node++) | |
5711 | 292 model->coeff_dcct[pt][ctx][node] = av_clip(((model->coeff_dccv[pt][node] * vp6_dccv_lc[ctx][node][0] + 128) >> 8) + vp6_dccv_lc[ctx][node][1], 1, 255); |
5821 | 293 } |
3695 | 294 } |
295 | |
3697 | 296 static void vp6_parse_vector_adjustment(vp56_context_t *s, vp56_mv_t *vect) |
3695 | 297 { |
298 vp56_range_coder_t *c = &s->c; | |
5711 | 299 vp56_model_t *model = s->modelp; |
3695 | 300 int comp; |
301 | |
3697 | 302 *vect = (vp56_mv_t) {0,0}; |
3695 | 303 if (s->vector_candidate_pos < 2) |
3697 | 304 *vect = s->vector_candidate[0]; |
3695 | 305 |
306 for (comp=0; comp<2; comp++) { | |
307 int i, delta = 0; | |
308 | |
5711 | 309 if (vp56_rac_get_prob(c, model->vector_dct[comp])) { |
3695 | 310 static const uint8_t prob_order[] = {0, 1, 2, 7, 6, 5, 4}; |
311 for (i=0; i<sizeof(prob_order); i++) { | |
312 int j = prob_order[i]; | |
5711 | 313 delta |= vp56_rac_get_prob(c, model->vector_fdv[comp][j])<<j; |
3695 | 314 } |
315 if (delta & 0xF0) | |
5711 | 316 delta |= vp56_rac_get_prob(c, model->vector_fdv[comp][3])<<3; |
3695 | 317 else |
318 delta |= 8; | |
319 } else { | |
320 delta = vp56_rac_get_tree(c, vp56_pva_tree, | |
5711 | 321 model->vector_pdv[comp]); |
3695 | 322 } |
323 | |
5711 | 324 if (delta && vp56_rac_get_prob(c, model->vector_sig[comp])) |
3695 | 325 delta = -delta; |
326 | |
327 if (!comp) | |
3697 | 328 vect->x += delta; |
3695 | 329 else |
3697 | 330 vect->y += delta; |
3695 | 331 } |
332 } | |
333 | |
5821 | 334 /** |
335 * Read number of consecutive blocks with null DC or AC. | |
336 * This value is < 74. | |
337 */ | |
338 static unsigned vp6_get_nb_null(vp56_context_t *s) | |
339 { | |
340 unsigned val = get_bits(&s->gb, 2); | |
341 if (val == 2) | |
342 val += get_bits(&s->gb, 2); | |
343 else if (val == 3) { | |
344 val = get_bits1(&s->gb) << 2; | |
345 val = 6+val + get_bits(&s->gb, 2+val); | |
346 } | |
347 return val; | |
348 } | |
349 | |
350 static void vp6_parse_coeff_huffman(vp56_context_t *s) | |
351 { | |
352 vp56_model_t *model = s->modelp; | |
353 uint8_t *permute = s->scantable.permutated; | |
354 VLC *vlc_coeff; | |
355 int coeff, sign, coeff_idx; | |
356 int b, cg, idx; | |
357 int pt = 0; /* plane type (0 for Y, 1 for U or V) */ | |
358 | |
359 for (b=0; b<6; b++) { | |
360 int ct = 0; /* code type */ | |
361 if (b > 3) pt = 1; | |
362 vlc_coeff = &s->dccv_vlc[pt]; | |
363 | |
364 for (coeff_idx=0; coeff_idx<64; ) { | |
365 int run = 1; | |
366 if (coeff_idx<2 && s->nb_null[coeff_idx][pt]) { | |
367 s->nb_null[coeff_idx][pt]--; | |
368 if (coeff_idx) | |
369 break; | |
370 } else { | |
371 coeff = get_vlc2(&s->gb, vlc_coeff->table, 9, 3); | |
372 if (coeff == 0) { | |
373 if (coeff_idx) { | |
374 int pt = (coeff_idx >= 6); | |
375 run += get_vlc2(&s->gb, s->runv_vlc[pt].table, 9, 3); | |
376 if (run >= 9) | |
377 run += get_bits(&s->gb, 6); | |
378 } else | |
379 s->nb_null[0][pt] = vp6_get_nb_null(s); | |
380 ct = 0; | |
381 } else if (coeff == 11) { /* end of block */ | |
382 if (coeff_idx == 1) /* first AC coeff ? */ | |
383 s->nb_null[1][pt] = vp6_get_nb_null(s); | |
384 break; | |
385 } else { | |
386 int coeff2 = vp56_coeff_bias[coeff]; | |
387 if (coeff > 4) | |
388 coeff2 += get_bits(&s->gb, coeff <= 9 ? coeff - 4 : 11); | |
389 ct = 1 + (coeff2 > 1); | |
390 sign = get_bits1(&s->gb); | |
391 coeff2 = (coeff2 ^ -sign) + sign; | |
392 if (coeff_idx) | |
393 coeff2 *= s->dequant_ac; | |
394 idx = model->coeff_index_to_pos[coeff_idx]; | |
395 s->block_coeff[b][permute[idx]] = coeff2; | |
396 } | |
397 } | |
398 coeff_idx+=run; | |
399 cg = FFMIN(vp6_coeff_groups[coeff_idx], 3); | |
400 vlc_coeff = &s->ract_vlc[pt][ct][cg]; | |
401 } | |
402 } | |
403 } | |
404 | |
3695 | 405 static void vp6_parse_coeff(vp56_context_t *s) |
406 { | |
4348 | 407 vp56_range_coder_t *c = s->ccp; |
5711 | 408 vp56_model_t *model = s->modelp; |
3695 | 409 uint8_t *permute = s->scantable.permutated; |
5711 | 410 uint8_t *model1, *model2, *model3; |
3695 | 411 int coeff, sign, coeff_idx; |
412 int b, i, cg, idx, ctx; | |
413 int pt = 0; /* plane type (0 for Y, 1 for U or V) */ | |
414 | |
415 for (b=0; b<6; b++) { | |
416 int ct = 1; /* code type */ | |
417 int run = 1; | |
418 | |
419 if (b > 3) pt = 1; | |
420 | |
421 ctx = s->left_block[vp56_b6to4[b]].not_null_dc | |
422 + s->above_blocks[s->above_block_idx[b]].not_null_dc; | |
5711 | 423 model1 = model->coeff_dccv[pt]; |
424 model2 = model->coeff_dcct[pt][ctx]; | |
3695 | 425 |
426 for (coeff_idx=0; coeff_idx<64; ) { | |
427 if ((coeff_idx>1 && ct==0) || vp56_rac_get_prob(c, model2[0])) { | |
428 /* parse a coeff */ | |
429 if (vp56_rac_get_prob(c, model2[2])) { | |
430 if (vp56_rac_get_prob(c, model2[3])) { | |
5711 | 431 idx = vp56_rac_get_tree(c, vp56_pc_tree, model1); |
5821 | 432 coeff = vp56_coeff_bias[idx+5]; |
3695 | 433 for (i=vp56_coeff_bit_length[idx]; i>=0; i--) |
434 coeff += vp56_rac_get_prob(c, vp56_coeff_parse_table[idx][i]) << i; | |
435 } else { | |
436 if (vp56_rac_get_prob(c, model2[4])) | |
5711 | 437 coeff = 3 + vp56_rac_get_prob(c, model1[5]); |
3695 | 438 else |
439 coeff = 2; | |
440 } | |
441 ct = 2; | |
442 } else { | |
443 ct = 1; | |
444 coeff = 1; | |
445 } | |
446 sign = vp56_rac_get(c); | |
447 coeff = (coeff ^ -sign) + sign; | |
448 if (coeff_idx) | |
449 coeff *= s->dequant_ac; | |
5711 | 450 idx = model->coeff_index_to_pos[coeff_idx]; |
3695 | 451 s->block_coeff[b][permute[idx]] = coeff; |
452 run = 1; | |
453 } else { | |
454 /* parse a run */ | |
455 ct = 0; | |
4925 | 456 if (coeff_idx > 0) { |
3695 | 457 if (!vp56_rac_get_prob(c, model2[1])) |
458 break; | |
459 | |
5711 | 460 model3 = model->coeff_runv[coeff_idx >= 6]; |
3695 | 461 run = vp56_rac_get_tree(c, vp6_pcr_tree, model3); |
462 if (!run) | |
463 for (run=9, i=0; i<6; i++) | |
464 run += vp56_rac_get_prob(c, model3[i+8]) << i; | |
465 } | |
466 } | |
467 | |
468 cg = vp6_coeff_groups[coeff_idx+=run]; | |
5711 | 469 model1 = model2 = model->coeff_ract[pt][ct][cg]; |
3695 | 470 } |
4925 | 471 |
472 s->left_block[vp56_b6to4[b]].not_null_dc = | |
473 s->above_blocks[s->above_block_idx[b]].not_null_dc = !!s->block_coeff[b][0]; | |
3695 | 474 } |
475 } | |
476 | |
477 static int vp6_adjust(int v, int t) | |
478 { | |
479 int V = v, s = v >> 31; | |
480 V ^= s; | |
481 V -= s; | |
482 if (V-t-1 >= (unsigned)(t-1)) | |
483 return v; | |
484 V = 2*t - V; | |
485 V += s; | |
486 V ^= s; | |
487 return V; | |
488 } | |
489 | |
490 static int vp6_block_variance(uint8_t *src, int stride) | |
491 { | |
492 int sum = 0, square_sum = 0; | |
493 int y, x; | |
494 | |
495 for (y=0; y<8; y+=2) { | |
496 for (x=0; x<8; x+=2) { | |
497 sum += src[x]; | |
498 square_sum += src[x]*src[x]; | |
499 } | |
500 src += 2*stride; | |
501 } | |
4306 | 502 return (16*square_sum - sum*sum) >> 8; |
3695 | 503 } |
504 | |
505 static void vp6_filter_hv4(uint8_t *dst, uint8_t *src, int stride, | |
506 int delta, const int16_t *weights) | |
507 { | |
508 int x, y; | |
509 | |
510 for (y=0; y<8; y++) { | |
511 for (x=0; x<8; x++) { | |
4594 | 512 dst[x] = av_clip_uint8(( src[x-delta ] * weights[0] |
3695 | 513 + src[x ] * weights[1] |
514 + src[x+delta ] * weights[2] | |
515 + src[x+2*delta] * weights[3] + 64) >> 7); | |
516 } | |
517 src += stride; | |
518 dst += stride; | |
519 } | |
520 } | |
521 | |
522 static void vp6_filter_diag2(vp56_context_t *s, uint8_t *dst, uint8_t *src, | |
523 int stride, int h_weight, int v_weight) | |
524 { | |
525 uint8_t *tmp = s->edge_emu_buffer+16; | |
4921 | 526 s->dsp.put_h264_chroma_pixels_tab[0](tmp, src, stride, 9, h_weight, 0); |
527 s->dsp.put_h264_chroma_pixels_tab[0](dst, tmp, stride, 8, 0, v_weight); | |
3695 | 528 } |
529 | |
530 static void vp6_filter_diag4(uint8_t *dst, uint8_t *src, int stride, | |
531 const int16_t *h_weights,const int16_t *v_weights) | |
532 { | |
533 int x, y; | |
534 int tmp[8*11]; | |
535 int *t = tmp; | |
536 | |
537 src -= stride; | |
538 | |
539 for (y=0; y<11; y++) { | |
540 for (x=0; x<8; x++) { | |
4594 | 541 t[x] = av_clip_uint8(( src[x-1] * h_weights[0] |
3695 | 542 + src[x ] * h_weights[1] |
543 + src[x+1] * h_weights[2] | |
544 + src[x+2] * h_weights[3] + 64) >> 7); | |
545 } | |
546 src += stride; | |
547 t += 8; | |
548 } | |
549 | |
550 t = tmp + 8; | |
551 for (y=0; y<8; y++) { | |
552 for (x=0; x<8; x++) { | |
4594 | 553 dst[x] = av_clip_uint8(( t[x-8 ] * v_weights[0] |
3695 | 554 + t[x ] * v_weights[1] |
555 + t[x+8 ] * v_weights[2] | |
556 + t[x+16] * v_weights[3] + 64) >> 7); | |
557 } | |
558 dst += stride; | |
559 t += 8; | |
560 } | |
561 } | |
562 | |
563 static void vp6_filter(vp56_context_t *s, uint8_t *dst, uint8_t *src, | |
564 int offset1, int offset2, int stride, | |
565 vp56_mv_t mv, int mask, int select, int luma) | |
566 { | |
567 int filter4 = 0; | |
568 int x8 = mv.x & mask; | |
569 int y8 = mv.y & mask; | |
570 | |
571 if (luma) { | |
572 x8 *= 2; | |
573 y8 *= 2; | |
574 filter4 = s->filter_mode; | |
575 if (filter4 == 2) { | |
576 if (s->max_vector_length && | |
4001 | 577 (FFABS(mv.x) > s->max_vector_length || |
578 FFABS(mv.y) > s->max_vector_length)) { | |
3695 | 579 filter4 = 0; |
4308 | 580 } else if (s->sample_variance_threshold |
581 && (vp6_block_variance(src+offset1, stride) | |
3695 | 582 < s->sample_variance_threshold)) { |
583 filter4 = 0; | |
584 } | |
585 } | |
586 } | |
587 | |
588 if ((y8 && (offset2-offset1)*s->flip<0) || (!y8 && offset1 > offset2)) { | |
589 offset1 = offset2; | |
590 } | |
591 | |
592 if (filter4) { | |
593 if (!y8) { /* left or right combine */ | |
594 vp6_filter_hv4(dst, src+offset1, stride, 1, | |
595 vp6_block_copy_filter[select][x8]); | |
596 } else if (!x8) { /* above or below combine */ | |
597 vp6_filter_hv4(dst, src+offset1, stride, stride, | |
598 vp6_block_copy_filter[select][y8]); | |
4922 | 599 } else { |
600 vp6_filter_diag4(dst, src+offset1 + ((mv.x^mv.y)>>31), stride, | |
3695 | 601 vp6_block_copy_filter[select][x8], |
602 vp6_block_copy_filter[select][y8]); | |
603 } | |
604 } else { | |
4921 | 605 if (!x8 || !y8) { |
606 s->dsp.put_h264_chroma_pixels_tab[0](dst, src+offset1, stride, 8, x8, y8); | |
4922 | 607 } else { |
608 vp6_filter_diag2(s, dst, src+offset1 + ((mv.x^mv.y)>>31), stride, x8, y8); | |
3695 | 609 } |
610 } | |
611 } | |
612 | |
613 static int vp6_decode_init(AVCodecContext *avctx) | |
614 { | |
615 vp56_context_t *s = avctx->priv_data; | |
616 | |
5714
314be1cfdcb0
add a new vp6a codec (add alpha plan support to vp6)
aurel
parents:
5711
diff
changeset
|
617 vp56_init(avctx, avctx->codec->id == CODEC_ID_VP6, |
314be1cfdcb0
add a new vp6a codec (add alpha plan support to vp6)
aurel
parents:
5711
diff
changeset
|
618 avctx->codec->id == CODEC_ID_VP6A); |
3695 | 619 s->vp56_coord_div = vp6_coord_div; |
620 s->parse_vector_adjustment = vp6_parse_vector_adjustment; | |
621 s->adjust = vp6_adjust; | |
622 s->filter = vp6_filter; | |
623 s->default_models_init = vp6_default_models_init; | |
624 s->parse_vector_models = vp6_parse_vector_models; | |
625 s->parse_coeff_models = vp6_parse_coeff_models; | |
626 s->parse_header = vp6_parse_header; | |
627 | |
628 return 0; | |
629 } | |
630 | |
631 AVCodec vp6_decoder = { | |
632 "vp6", | |
633 CODEC_TYPE_VIDEO, | |
634 CODEC_ID_VP6, | |
635 sizeof(vp56_context_t), | |
636 vp6_decode_init, | |
637 NULL, | |
638 vp56_free, | |
639 vp56_decode_frame, | |
4910 | 640 CODEC_CAP_DR1, |
3695 | 641 }; |
642 | |
643 /* flash version, not flipped upside-down */ | |
644 AVCodec vp6f_decoder = { | |
645 "vp6f", | |
646 CODEC_TYPE_VIDEO, | |
647 CODEC_ID_VP6F, | |
648 sizeof(vp56_context_t), | |
649 vp6_decode_init, | |
650 NULL, | |
651 vp56_free, | |
652 vp56_decode_frame, | |
4910 | 653 CODEC_CAP_DR1, |
3695 | 654 }; |
5714
314be1cfdcb0
add a new vp6a codec (add alpha plan support to vp6)
aurel
parents:
5711
diff
changeset
|
655 |
314be1cfdcb0
add a new vp6a codec (add alpha plan support to vp6)
aurel
parents:
5711
diff
changeset
|
656 /* flash version, not flipped upside-down, with alpha channel */ |
314be1cfdcb0
add a new vp6a codec (add alpha plan support to vp6)
aurel
parents:
5711
diff
changeset
|
657 AVCodec vp6a_decoder = { |
314be1cfdcb0
add a new vp6a codec (add alpha plan support to vp6)
aurel
parents:
5711
diff
changeset
|
658 "vp6a", |
314be1cfdcb0
add a new vp6a codec (add alpha plan support to vp6)
aurel
parents:
5711
diff
changeset
|
659 CODEC_TYPE_VIDEO, |
314be1cfdcb0
add a new vp6a codec (add alpha plan support to vp6)
aurel
parents:
5711
diff
changeset
|
660 CODEC_ID_VP6A, |
314be1cfdcb0
add a new vp6a codec (add alpha plan support to vp6)
aurel
parents:
5711
diff
changeset
|
661 sizeof(vp56_context_t), |
314be1cfdcb0
add a new vp6a codec (add alpha plan support to vp6)
aurel
parents:
5711
diff
changeset
|
662 vp6_decode_init, |
314be1cfdcb0
add a new vp6a codec (add alpha plan support to vp6)
aurel
parents:
5711
diff
changeset
|
663 NULL, |
314be1cfdcb0
add a new vp6a codec (add alpha plan support to vp6)
aurel
parents:
5711
diff
changeset
|
664 vp56_free, |
314be1cfdcb0
add a new vp6a codec (add alpha plan support to vp6)
aurel
parents:
5711
diff
changeset
|
665 vp56_decode_frame, |
314be1cfdcb0
add a new vp6a codec (add alpha plan support to vp6)
aurel
parents:
5711
diff
changeset
|
666 CODEC_CAP_DR1, |
314be1cfdcb0
add a new vp6a codec (add alpha plan support to vp6)
aurel
parents:
5711
diff
changeset
|
667 }; |