diff options
Diffstat (limited to 'libavcodec/vc1.c')
-rw-r--r-- | libavcodec/vc1.c | 145 |
1 files changed, 105 insertions, 40 deletions
diff --git a/libavcodec/vc1.c b/libavcodec/vc1.c index 23012cdc63..e4b62fe3de 100644 --- a/libavcodec/vc1.c +++ b/libavcodec/vc1.c @@ -4,20 +4,20 @@ * Copyright (c) 2006-2007 Konstantin Shishkov * Partly based on vc9.c (c) 2005 Anonymous, Alex Beregszaszi, Michael Niedermayer * - * This file is part of Libav. + * This file is part of FFmpeg. * - * Libav is free software; you can redistribute it and/or + * FFmpeg is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation; either * version 2.1 of the License, or (at your option) any later version. * - * Libav is distributed in the hope that it will be useful, + * FFmpeg is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public - * License along with Libav; if not, write to the Free Software + * License along with FFmpeg; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA */ @@ -293,7 +293,7 @@ static int decode_sequence_header_adv(VC1Context *v, GetBitContext *gb); */ int ff_vc1_decode_sequence_header(AVCodecContext *avctx, VC1Context *v, GetBitContext *gb) { - av_log(avctx, AV_LOG_DEBUG, "Header: %0X\n", show_bits(gb, 32)); + av_log(avctx, AV_LOG_DEBUG, "Header: %0X\n", show_bits_long(gb, 32)); v->profile = get_bits(gb, 2); if (v->profile == PROFILE_COMPLEX) { av_log(avctx, AV_LOG_WARNING, "WMV3 Complex Profile is not fully supported\n"); @@ -380,8 +380,9 @@ int ff_vc1_decode_sequence_header(AVCodecContext *avctx, VC1Context *v, GetBitCo v->finterpflag = get_bits1(gb); //common if (v->res_sprite) { - v->s.avctx->width = v->s.avctx->coded_width = get_bits(gb, 11); - v->s.avctx->height = v->s.avctx->coded_height = get_bits(gb, 11); + int w = get_bits(gb, 11); + int h = get_bits(gb, 11); + avcodec_set_dimensions(v->s.avctx, w, h); skip_bits(gb, 5); //frame rate v->res_x8 = get_bits1(gb); if (get_bits1(gb)) { // something to do with DC VLC selection @@ -433,10 +434,8 @@ static int decode_sequence_header_adv(VC1Context *v, GetBitContext *gb) v->bitrtq_postproc = get_bits(gb, 5); //common v->postprocflag = get_bits1(gb); //common - v->s.avctx->coded_width = (get_bits(gb, 12) + 1) << 1; - v->s.avctx->coded_height = (get_bits(gb, 12) + 1) << 1; - v->s.avctx->width = v->s.avctx->coded_width; - v->s.avctx->height = v->s.avctx->coded_height; + v->max_coded_width = (get_bits(gb, 12) + 1) << 1; + v->max_coded_height = (get_bits(gb, 12) + 1) << 1; v->broadcast = get_bits1(gb); v->interlace = get_bits1(gb); v->tfcntrflag = get_bits1(gb); @@ -502,9 +501,10 @@ static int decode_sequence_header_adv(VC1Context *v, GetBitContext *gb) } if (get_bits1(gb)) { - v->color_prim = get_bits(gb, 8); - v->transfer_char = get_bits(gb, 8); - v->matrix_coef = get_bits(gb, 8); + v->s.avctx->color_primaries = get_bits(gb, 8); + v->s.avctx->color_trc = get_bits(gb, 8); + v->s.avctx->colorspace = get_bits(gb, 8); + v->s.avctx->color_range = AVCOL_RANGE_MPEG; } } @@ -525,6 +525,7 @@ static int decode_sequence_header_adv(VC1Context *v, GetBitContext *gb) int ff_vc1_decode_entry_point(AVCodecContext *avctx, VC1Context *v, GetBitContext *gb) { int i; + int w,h; av_log(avctx, AV_LOG_DEBUG, "Entry point: %08X\n", show_bits_long(gb, 32)); v->broken_link = get_bits1(gb); @@ -532,6 +533,8 @@ int ff_vc1_decode_entry_point(AVCodecContext *avctx, VC1Context *v, GetBitContex v->panscanflag = get_bits1(gb); v->refdist_flag = get_bits1(gb); v->s.loop_filter = get_bits1(gb); + if (v->s.avctx->skip_loop_filter >= AVDISCARD_ALL) + v->s.loop_filter = 0; v->fastuvmc = get_bits1(gb); v->extended_mv = get_bits1(gb); v->dquant = get_bits(gb, 2); @@ -545,10 +548,14 @@ int ff_vc1_decode_entry_point(AVCodecContext *avctx, VC1Context *v, GetBitContex } } - if (get_bits1(gb)) { - avctx->width = avctx->coded_width = (get_bits(gb, 12) + 1) << 1; - avctx->height = avctx->coded_height = (get_bits(gb, 12) + 1) << 1; + if(get_bits1(gb)){ + w = (get_bits(gb, 12)+1)<<1; + h = (get_bits(gb, 12)+1)<<1; + } else { + w = v->max_coded_width; + h = v->max_coded_height; } + avcodec_set_dimensions(avctx, w, h); if (v->extended_mv) v->extended_dmv = get_bits1(gb); if ((v->range_mapy_flag = get_bits1(gb))) { @@ -571,7 +578,7 @@ int ff_vc1_decode_entry_point(AVCodecContext *avctx, VC1Context *v, GetBitContex } /* fill lookup tables for intensity compensation */ -#define INIT_LUT(lumscale, lumshift, luty, lutuv) do { \ +#define INIT_LUT(lumscale, lumshift, luty, lutuv, chain) do { \ int scale, shift, i; \ if (!lumscale) { \ scale = -64; \ @@ -586,17 +593,45 @@ int ff_vc1_decode_entry_point(AVCodecContext *avctx, VC1Context *v, GetBitContex shift = lumshift << 6; \ } \ for (i = 0; i < 256; i++) { \ - luty[i] = av_clip_uint8((scale * i + shift + 32) >> 6); \ - lutuv[i] = av_clip_uint8((scale * (i - 128) + 128*64 + 32) >> 6); \ + int iy = chain ? luty[i] : i; \ + int iu = chain ? lutuv[i] : i; \ + luty[i] = av_clip_uint8((scale * iy + shift + 32) >> 6); \ + lutuv[i] = av_clip_uint8((scale * (iu - 128) + 128*64 + 32) >> 6);\ } \ } while(0) + +static void rotate_luts(VC1Context *v) +{ +#define ROTATE(DEF, L, N, C, A) do {\ + if (v->s.pict_type == AV_PICTURE_TYPE_BI || v->s.pict_type == AV_PICTURE_TYPE_B) {\ + C = A;\ + } else {\ + DEF;\ + memcpy(&tmp, &L , sizeof(tmp));\ + memcpy(&L , &N , sizeof(tmp));\ + memcpy(&N , &tmp, sizeof(tmp));\ + C = N;\ + }\ + }while(0) + + ROTATE(int tmp , v->last_use_ic, v->next_use_ic, v->curr_use_ic, v->aux_use_ic); + ROTATE(uint8_t tmp[2][256], v->last_luty , v->next_luty , v->curr_luty , v->aux_luty); + ROTATE(uint8_t tmp[2][256], v->last_lutuv, v->next_lutuv, v->curr_lutuv, v->aux_lutuv); + + INIT_LUT(32, 0 , v->curr_luty[0] , v->curr_lutuv[0] , 0); + INIT_LUT(32, 0 , v->curr_luty[1] , v->curr_lutuv[1] , 0); + v->curr_use_ic = 0; +} + int ff_vc1_parse_frame_header(VC1Context *v, GetBitContext* gb) { int pqindex, lowquant, status; if (v->finterpflag) v->interpfrm = get_bits1(gb); + if (!v->s.avctx->codec) + return -1; if (v->s.avctx->codec_id == AV_CODEC_ID_MSS2) v->respic = v->rangered = @@ -677,8 +712,9 @@ int ff_vc1_parse_frame_header(VC1Context *v, GetBitContext* gb) (v->s.pict_type == AV_PICTURE_TYPE_P) ? 'P' : ((v->s.pict_type == AV_PICTURE_TYPE_I) ? 'I' : 'B'), pqindex, v->pq, v->halfpq, v->rangeredfrm); - if (v->s.pict_type == AV_PICTURE_TYPE_I || v->s.pict_type == AV_PICTURE_TYPE_P) - v->use_ic = 0; + if(v->first_pic_header_flag) { + rotate_luts(v); + } switch (v->s.pict_type) { case AV_PICTURE_TYPE_P: @@ -692,9 +728,10 @@ int ff_vc1_parse_frame_header(VC1Context *v, GetBitContext* gb) v->mv_mode2 = ff_vc1_mv_pmode_table2[lowquant][get_unary(gb, 1, 3)]; v->lumscale = get_bits(gb, 6); v->lumshift = get_bits(gb, 6); - v->use_ic = 1; + v->last_use_ic = 1; /* fill lookup tables for intensity compensation */ - INIT_LUT(v->lumscale, v->lumshift, v->luty, v->lutuv); + INIT_LUT(v->lumscale, v->lumshift , v->last_luty[0] , v->last_lutuv[0] , 1); + INIT_LUT(v->lumscale, v->lumshift , v->last_luty[1] , v->last_lutuv[1] , 1); } v->qs_last = v->s.quarter_sample; if (v->mv_mode == MV_PMODE_1MV_HPEL || v->mv_mode == MV_PMODE_1MV_HPEL_BILIN) @@ -812,8 +849,11 @@ int ff_vc1_parse_frame_header_adv(VC1Context *v, GetBitContext* gb) int mbmodetab, imvtab, icbptab, twomvbptab, fourmvbptab; /* useful only for debugging */ int field_mode, fcm; + v->numref=0; v->p_frame_skipped = 0; if (v->second_field) { + if(v->fcm!=2 || v->field_mode!=1) + return -1; v->s.pict_type = (v->fptype & 1) ? AV_PICTURE_TYPE_P : AV_PICTURE_TYPE_I; if (v->fptype & 4) v->s.pict_type = (v->fptype & 1) ? AV_PICTURE_TYPE_BI : AV_PICTURE_TYPE_B; @@ -828,9 +868,6 @@ int ff_vc1_parse_frame_header_adv(VC1Context *v, GetBitContext* gb) if (fcm) { if (fcm == ILACE_FIELD) field_mode = 1; - if (!v->warn_interlaced++) - av_log(v->s.avctx, AV_LOG_ERROR, - "Interlaced frames/fields support is incomplete\n"); } } else { fcm = PROGRESSIVE; @@ -874,6 +911,8 @@ int ff_vc1_parse_frame_header_adv(VC1Context *v, GetBitContext* gb) v->tff = get_bits1(gb); v->rff = get_bits1(gb); } + } else { + v->tff = 1; } if (v->panscanflag) { avpriv_report_missing_feature(v->s.avctx, "Pan-scan"); @@ -885,6 +924,8 @@ int ff_vc1_parse_frame_header_adv(VC1Context *v, GetBitContext* gb) v->rnd = get_bits1(gb); if (v->interlace) v->uvsamp = get_bits1(gb); + if(!ff_vc1_bfraction_vlc.table) + return 0; //parsing only, vlc tables havnt been allocated if (v->field_mode) { if (!v->refdist_flag) v->refdist = 0; @@ -942,12 +983,13 @@ int ff_vc1_parse_frame_header_adv(VC1Context *v, GetBitContext* gb) if (v->postprocflag) v->postproc = get_bits(gb, 2); - if (v->s.pict_type == AV_PICTURE_TYPE_I || v->s.pict_type == AV_PICTURE_TYPE_P) - v->use_ic = 0; - if (v->parse_only) return 0; + if(v->first_pic_header_flag) { + rotate_luts(v); + } + switch (v->s.pict_type) { case AV_PICTURE_TYPE_I: case AV_PICTURE_TYPE_BI: @@ -998,7 +1040,9 @@ int ff_vc1_parse_frame_header_adv(VC1Context *v, GetBitContext* gb) if (v->intcomp) { v->lumscale = get_bits(gb, 6); v->lumshift = get_bits(gb, 6); - INIT_LUT(v->lumscale, v->lumshift, v->luty, v->lutuv); + INIT_LUT(v->lumscale, v->lumshift, v->last_luty[0], v->last_lutuv[0], 1); + INIT_LUT(v->lumscale, v->lumshift, v->last_luty[1], v->last_lutuv[1], 1); + v->last_use_ic = 1; } status = bitplane_decoding(v->s.mbskip_table, &v->skip_is_raw, v); av_log(v->s.avctx, AV_LOG_DEBUG, "SKIPMB plane encoding: " @@ -1041,17 +1085,38 @@ int ff_vc1_parse_frame_header_adv(VC1Context *v, GetBitContext* gb) int mvmode2; mvmode2 = get_unary(gb, 1, 3); v->mv_mode2 = ff_vc1_mv_pmode_table2[lowquant][mvmode2]; - if (v->field_mode) - v->intcompfield = decode210(gb); - v->lumscale = get_bits(gb, 6); - v->lumshift = get_bits(gb, 6); - INIT_LUT(v->lumscale, v->lumshift, v->luty, v->lutuv); - if ((v->field_mode) && !v->intcompfield) { + if (v->field_mode) { + v->intcompfield = decode210(gb)^3; + } else + v->intcompfield = 3; + + v->lumscale2 = v->lumscale = 32; + v->lumshift2 = v->lumshift = 0; + if (v->intcompfield & 1) { + v->lumscale = get_bits(gb, 6); + v->lumshift = get_bits(gb, 6); + } + if ((v->intcompfield & 2) && v->field_mode) { v->lumscale2 = get_bits(gb, 6); v->lumshift2 = get_bits(gb, 6); - INIT_LUT(v->lumscale2, v->lumshift2, v->luty2, v->lutuv2); + } else if(!v->field_mode) { + v->lumscale2 = v->lumscale; + v->lumshift2 = v->lumshift; + } + if (v->field_mode && v->second_field) { + if (v->cur_field_type) { + INIT_LUT(v->lumscale , v->lumshift , v->curr_luty[v->cur_field_type^1], v->curr_lutuv[v->cur_field_type^1], 0); + INIT_LUT(v->lumscale2, v->lumshift2, v->last_luty[v->cur_field_type ], v->last_lutuv[v->cur_field_type ], 1); + } else { + INIT_LUT(v->lumscale2, v->lumshift2, v->curr_luty[v->cur_field_type^1], v->curr_lutuv[v->cur_field_type^1], 0); + INIT_LUT(v->lumscale , v->lumshift , v->last_luty[v->cur_field_type ], v->last_lutuv[v->cur_field_type ], 1); + } + v->next_use_ic = v->curr_use_ic = 1; + } else { + INIT_LUT(v->lumscale , v->lumshift , v->last_luty[0], v->last_lutuv[0], 1); + INIT_LUT(v->lumscale2, v->lumshift2, v->last_luty[1], v->last_lutuv[1], 1); } - v->use_ic = 1; + v->last_use_ic = 1; } v->qs_last = v->s.quarter_sample; if (v->mv_mode == MV_PMODE_1MV_HPEL || v->mv_mode == MV_PMODE_1MV_HPEL_BILIN) @@ -1134,7 +1199,6 @@ int ff_vc1_parse_frame_header_adv(VC1Context *v, GetBitContext* gb) if (v->bfraction == 0) { return -1; } - return -1; // This codepath is still incomplete thus it is disabled } if (v->extended_mv) v->mvrange = get_unary(gb, 0, 3); @@ -1154,6 +1218,7 @@ int ff_vc1_parse_frame_header_adv(VC1Context *v, GetBitContext* gb) if (v->field_mode) { int mvmode; + av_log(v->s.avctx, AV_LOG_DEBUG, "B Fields\n"); if (v->extended_dmv) v->dmvrange = get_unary(gb, 0, 3); mvmode = get_unary(gb, 1, 3); |