libavcodec/rv34.c
Go to the documentation of this file.
00001 /*
00002  * RV30/40 decoder common data
00003  * Copyright (c) 2007 Mike Melanson, Konstantin Shishkov
00004  *
00005  * This file is part of FFmpeg.
00006  *
00007  * FFmpeg is free software; you can redistribute it and/or
00008  * modify it under the terms of the GNU Lesser General Public
00009  * License as published by the Free Software Foundation; either
00010  * version 2.1 of the License, or (at your option) any later version.
00011  *
00012  * FFmpeg is distributed in the hope that it will be useful,
00013  * but WITHOUT ANY WARRANTY; without even the implied warranty of
00014  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00015  * Lesser General Public License for more details.
00016  *
00017  * You should have received a copy of the GNU Lesser General Public
00018  * License along with FFmpeg; if not, write to the Free Software
00019  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
00020  */
00021 
00027 #include "libavutil/internal.h"
00028 
00029 #include "avcodec.h"
00030 #include "dsputil.h"
00031 #include "mpegvideo.h"
00032 #include "golomb.h"
00033 #include "internal.h"
00034 #include "mathops.h"
00035 #include "rectangle.h"
00036 #include "thread.h"
00037 
00038 #include "rv34vlc.h"
00039 #include "rv34data.h"
00040 #include "rv34.h"
00041 
00042 //#define DEBUG
00043 
00044 static inline void ZERO8x2(void* dst, int stride)
00045 {
00046     fill_rectangle(dst,                 1, 2, stride, 0, 4);
00047     fill_rectangle(((uint8_t*)(dst))+4, 1, 2, stride, 0, 4);
00048 }
00049 
00051 static const int rv34_mb_type_to_lavc[12] = {
00052     MB_TYPE_INTRA,
00053     MB_TYPE_INTRA16x16              | MB_TYPE_SEPARATE_DC,
00054     MB_TYPE_16x16   | MB_TYPE_L0,
00055     MB_TYPE_8x8     | MB_TYPE_L0,
00056     MB_TYPE_16x16   | MB_TYPE_L0,
00057     MB_TYPE_16x16   | MB_TYPE_L1,
00058     MB_TYPE_SKIP,
00059     MB_TYPE_DIRECT2 | MB_TYPE_16x16,
00060     MB_TYPE_16x8    | MB_TYPE_L0,
00061     MB_TYPE_8x16    | MB_TYPE_L0,
00062     MB_TYPE_16x16   | MB_TYPE_L0L1,
00063     MB_TYPE_16x16   | MB_TYPE_L0    | MB_TYPE_SEPARATE_DC
00064 };
00065 
00066 
00067 static RV34VLC intra_vlcs[NUM_INTRA_TABLES], inter_vlcs[NUM_INTER_TABLES];
00068 
00069 static int rv34_decode_mv(RV34DecContext *r, int block_type);
00070 
00076 static const int table_offs[] = {
00077       0,   1818,   3622,   4144,   4698,   5234,   5804,   5868,   5900,   5932,
00078    5996,   6252,   6316,   6348,   6380,   7674,   8944,  10274,  11668,  12250,
00079   14060,  15846,  16372,  16962,  17512,  18148,  18180,  18212,  18244,  18308,
00080   18564,  18628,  18660,  18692,  20036,  21314,  22648,  23968,  24614,  26384,
00081   28190,  28736,  29366,  29938,  30608,  30640,  30672,  30704,  30768,  31024,
00082   31088,  31120,  31184,  32570,  33898,  35236,  36644,  37286,  39020,  40802,
00083   41368,  42052,  42692,  43348,  43380,  43412,  43444,  43476,  43604,  43668,
00084   43700,  43732,  45100,  46430,  47778,  49160,  49802,  51550,  53340,  53972,
00085   54648,  55348,  55994,  56122,  56154,  56186,  56218,  56346,  56410,  56442,
00086   56474,  57878,  59290,  60636,  62036,  62682,  64460,  64524,  64588,  64716,
00087   64844,  66076,  67466,  67978,  68542,  69064,  69648,  70296,  72010,  72074,
00088   72138,  72202,  72330,  73572,  74936,  75454,  76030,  76566,  77176,  77822,
00089   79582,  79646,  79678,  79742,  79870,  81180,  82536,  83064,  83672,  84242,
00090   84934,  85576,  87384,  87448,  87480,  87544,  87672,  88982,  90340,  90902,
00091   91598,  92182,  92846,  93488,  95246,  95278,  95310,  95374,  95502,  96878,
00092   98266,  98848,  99542, 100234, 100884, 101524, 103320, 103352, 103384, 103416,
00093  103480, 104874, 106222, 106910, 107584, 108258, 108902, 109544, 111366, 111398,
00094  111430, 111462, 111494, 112878, 114320, 114988, 115660, 116310, 116950, 117592
00095 };
00096 
00097 static VLC_TYPE table_data[117592][2];
00098 
00107 static void rv34_gen_vlc(const uint8_t *bits, int size, VLC *vlc, const uint8_t *insyms,
00108                          const int num)
00109 {
00110     int i;
00111     int counts[17] = {0}, codes[17];
00112     uint16_t cw[MAX_VLC_SIZE], syms[MAX_VLC_SIZE];
00113     uint8_t bits2[MAX_VLC_SIZE];
00114     int maxbits = 0, realsize = 0;
00115 
00116     for(i = 0; i < size; i++){
00117         if(bits[i]){
00118             bits2[realsize] = bits[i];
00119             syms[realsize] = insyms ? insyms[i] : i;
00120             realsize++;
00121             maxbits = FFMAX(maxbits, bits[i]);
00122             counts[bits[i]]++;
00123         }
00124     }
00125 
00126     codes[0] = 0;
00127     for(i = 0; i < 16; i++)
00128         codes[i+1] = (codes[i] + counts[i]) << 1;
00129     for(i = 0; i < realsize; i++)
00130         cw[i] = codes[bits2[i]]++;
00131 
00132     vlc->table = &table_data[table_offs[num]];
00133     vlc->table_allocated = table_offs[num + 1] - table_offs[num];
00134     init_vlc_sparse(vlc, FFMIN(maxbits, 9), realsize,
00135                     bits2, 1, 1,
00136                     cw,    2, 2,
00137                     syms,  2, 2, INIT_VLC_USE_NEW_STATIC);
00138 }
00139 
00143 static av_cold void rv34_init_tables(void)
00144 {
00145     int i, j, k;
00146 
00147     for(i = 0; i < NUM_INTRA_TABLES; i++){
00148         for(j = 0; j < 2; j++){
00149             rv34_gen_vlc(rv34_table_intra_cbppat   [i][j], CBPPAT_VLC_SIZE,   &intra_vlcs[i].cbppattern[j],     NULL, 19*i + 0 + j);
00150             rv34_gen_vlc(rv34_table_intra_secondpat[i][j], OTHERBLK_VLC_SIZE, &intra_vlcs[i].second_pattern[j], NULL, 19*i + 2 + j);
00151             rv34_gen_vlc(rv34_table_intra_thirdpat [i][j], OTHERBLK_VLC_SIZE, &intra_vlcs[i].third_pattern[j],  NULL, 19*i + 4 + j);
00152             for(k = 0; k < 4; k++){
00153                 rv34_gen_vlc(rv34_table_intra_cbp[i][j+k*2],  CBP_VLC_SIZE,   &intra_vlcs[i].cbp[j][k],         rv34_cbp_code, 19*i + 6 + j*4 + k);
00154             }
00155         }
00156         for(j = 0; j < 4; j++){
00157             rv34_gen_vlc(rv34_table_intra_firstpat[i][j], FIRSTBLK_VLC_SIZE, &intra_vlcs[i].first_pattern[j], NULL, 19*i + 14 + j);
00158         }
00159         rv34_gen_vlc(rv34_intra_coeff[i], COEFF_VLC_SIZE, &intra_vlcs[i].coefficient, NULL, 19*i + 18);
00160     }
00161 
00162     for(i = 0; i < NUM_INTER_TABLES; i++){
00163         rv34_gen_vlc(rv34_inter_cbppat[i], CBPPAT_VLC_SIZE, &inter_vlcs[i].cbppattern[0], NULL, i*12 + 95);
00164         for(j = 0; j < 4; j++){
00165             rv34_gen_vlc(rv34_inter_cbp[i][j], CBP_VLC_SIZE, &inter_vlcs[i].cbp[0][j], rv34_cbp_code, i*12 + 96 + j);
00166         }
00167         for(j = 0; j < 2; j++){
00168             rv34_gen_vlc(rv34_table_inter_firstpat [i][j], FIRSTBLK_VLC_SIZE, &inter_vlcs[i].first_pattern[j],  NULL, i*12 + 100 + j);
00169             rv34_gen_vlc(rv34_table_inter_secondpat[i][j], OTHERBLK_VLC_SIZE, &inter_vlcs[i].second_pattern[j], NULL, i*12 + 102 + j);
00170             rv34_gen_vlc(rv34_table_inter_thirdpat [i][j], OTHERBLK_VLC_SIZE, &inter_vlcs[i].third_pattern[j],  NULL, i*12 + 104 + j);
00171         }
00172         rv34_gen_vlc(rv34_inter_coeff[i], COEFF_VLC_SIZE, &inter_vlcs[i].coefficient, NULL, i*12 + 106);
00173     }
00174 }
00175  // vlc group
00177 
00186 static int rv34_decode_cbp(GetBitContext *gb, RV34VLC *vlc, int table)
00187 {
00188     int pattern, code, cbp=0;
00189     int ones;
00190     static const int cbp_masks[3] = {0x100000, 0x010000, 0x110000};
00191     static const int shifts[4] = { 0, 2, 8, 10 };
00192     const int *curshift = shifts;
00193     int i, t, mask;
00194 
00195     code = get_vlc2(gb, vlc->cbppattern[table].table, 9, 2);
00196     pattern = code & 0xF;
00197     code >>= 4;
00198 
00199     ones = rv34_count_ones[pattern];
00200 
00201     for(mask = 8; mask; mask >>= 1, curshift++){
00202         if(pattern & mask)
00203             cbp |= get_vlc2(gb, vlc->cbp[table][ones].table, vlc->cbp[table][ones].bits, 1) << curshift[0];
00204     }
00205 
00206     for(i = 0; i < 4; i++){
00207         t = (modulo_three_table[code] >> (6 - 2*i)) & 3;
00208         if(t == 1)
00209             cbp |= cbp_masks[get_bits1(gb)] << i;
00210         if(t == 2)
00211             cbp |= cbp_masks[2] << i;
00212     }
00213     return cbp;
00214 }
00215 
00219 static inline void decode_coeff(DCTELEM *dst, int coef, int esc, GetBitContext *gb, VLC* vlc, int q)
00220 {
00221     if(coef){
00222         if(coef == esc){
00223             coef = get_vlc2(gb, vlc->table, 9, 2);
00224             if(coef > 23){
00225                 coef -= 23;
00226                 coef = 22 + ((1 << coef) | get_bits(gb, coef));
00227             }
00228             coef += esc;
00229         }
00230         if(get_bits1(gb))
00231             coef = -coef;
00232         *dst = (coef*q + 8) >> 4;
00233     }
00234 }
00235 
00239 static inline void decode_subblock(DCTELEM *dst, int code, const int is_block2, GetBitContext *gb, VLC *vlc, int q)
00240 {
00241     int flags = modulo_three_table[code];
00242 
00243     decode_coeff(    dst+0*4+0, (flags >> 6)    , 3, gb, vlc, q);
00244     if(is_block2){
00245         decode_coeff(dst+1*4+0, (flags >> 4) & 3, 2, gb, vlc, q);
00246         decode_coeff(dst+0*4+1, (flags >> 2) & 3, 2, gb, vlc, q);
00247     }else{
00248         decode_coeff(dst+0*4+1, (flags >> 4) & 3, 2, gb, vlc, q);
00249         decode_coeff(dst+1*4+0, (flags >> 2) & 3, 2, gb, vlc, q);
00250     }
00251     decode_coeff(    dst+1*4+1, (flags >> 0) & 3, 2, gb, vlc, q);
00252 }
00253 
00257 static inline void decode_subblock1(DCTELEM *dst, int code, GetBitContext *gb, VLC *vlc, int q)
00258 {
00259     int coeff = modulo_three_table[code] >> 6;
00260     decode_coeff(dst, coeff, 3, gb, vlc, q);
00261 }
00262 
00263 static inline void decode_subblock3(DCTELEM *dst, int code, const int is_block2, GetBitContext *gb, VLC *vlc,
00264                                     int q_dc, int q_ac1, int q_ac2)
00265 {
00266     int flags = modulo_three_table[code];
00267 
00268     decode_coeff(    dst+0*4+0, (flags >> 6)    , 3, gb, vlc, q_dc);
00269     if(is_block2){
00270         decode_coeff(dst+1*4+0, (flags >> 4) & 3, 2, gb, vlc, q_ac1);
00271         decode_coeff(dst+0*4+1, (flags >> 2) & 3, 2, gb, vlc, q_ac1);
00272     }else{
00273         decode_coeff(dst+0*4+1, (flags >> 4) & 3, 2, gb, vlc, q_ac1);
00274         decode_coeff(dst+1*4+0, (flags >> 2) & 3, 2, gb, vlc, q_ac1);
00275     }
00276     decode_coeff(    dst+1*4+1, (flags >> 0) & 3, 2, gb, vlc, q_ac2);
00277 }
00278 
00290 static inline int rv34_decode_block(DCTELEM *dst, GetBitContext *gb, RV34VLC *rvlc, int fc, int sc, int q_dc, int q_ac1, int q_ac2)
00291 {
00292     int code, pattern, has_ac = 1;
00293 
00294     code = get_vlc2(gb, rvlc->first_pattern[fc].table, 9, 2);
00295 
00296     pattern = code & 0x7;
00297 
00298     code >>= 3;
00299 
00300     if (modulo_three_table[code] & 0x3F) {
00301         decode_subblock3(dst, code, 0, gb, &rvlc->coefficient, q_dc, q_ac1, q_ac2);
00302     } else {
00303         decode_subblock1(dst, code, gb, &rvlc->coefficient, q_dc);
00304         if (!pattern)
00305             return 0;
00306         has_ac = 0;
00307     }
00308 
00309     if(pattern & 4){
00310         code = get_vlc2(gb, rvlc->second_pattern[sc].table, 9, 2);
00311         decode_subblock(dst + 4*0+2, code, 0, gb, &rvlc->coefficient, q_ac2);
00312     }
00313     if(pattern & 2){ // Looks like coefficients 1 and 2 are swapped for this block
00314         code = get_vlc2(gb, rvlc->second_pattern[sc].table, 9, 2);
00315         decode_subblock(dst + 4*2+0, code, 1, gb, &rvlc->coefficient, q_ac2);
00316     }
00317     if(pattern & 1){
00318         code = get_vlc2(gb, rvlc->third_pattern[sc].table, 9, 2);
00319         decode_subblock(dst + 4*2+2, code, 0, gb, &rvlc->coefficient, q_ac2);
00320     }
00321     return has_ac || pattern;
00322 }
00323 
00333 int ff_rv34_get_start_offset(GetBitContext *gb, int mb_size)
00334 {
00335     int i;
00336     for(i = 0; i < 5; i++)
00337         if(rv34_mb_max_sizes[i] >= mb_size - 1)
00338             break;
00339     return rv34_mb_bits_sizes[i];
00340 }
00341 
00345 static inline RV34VLC* choose_vlc_set(int quant, int mod, int type)
00346 {
00347     if(mod == 2 && quant < 19) quant += 10;
00348     else if(mod && quant < 26) quant += 5;
00349     return type ? &inter_vlcs[rv34_quant_to_vlc_set[1][av_clip(quant, 0, 30)]]
00350                 : &intra_vlcs[rv34_quant_to_vlc_set[0][av_clip(quant, 0, 30)]];
00351 }
00352 
00356 static int rv34_decode_intra_mb_header(RV34DecContext *r, int8_t *intra_types)
00357 {
00358     MpegEncContext *s = &r->s;
00359     GetBitContext *gb = &s->gb;
00360     int mb_pos = s->mb_x + s->mb_y * s->mb_stride;
00361     int t;
00362 
00363     r->is16 = get_bits1(gb);
00364     if(r->is16){
00365         s->current_picture_ptr->f.mb_type[mb_pos] = MB_TYPE_INTRA16x16;
00366         r->block_type = RV34_MB_TYPE_INTRA16x16;
00367         t = get_bits(gb, 2);
00368         fill_rectangle(intra_types, 4, 4, r->intra_types_stride, t, sizeof(intra_types[0]));
00369         r->luma_vlc   = 2;
00370     }else{
00371         if(!r->rv30){
00372             if(!get_bits1(gb))
00373                 av_log(s->avctx, AV_LOG_ERROR, "Need DQUANT\n");
00374         }
00375         s->current_picture_ptr->f.mb_type[mb_pos] = MB_TYPE_INTRA;
00376         r->block_type = RV34_MB_TYPE_INTRA;
00377         if(r->decode_intra_types(r, gb, intra_types) < 0)
00378             return -1;
00379         r->luma_vlc   = 1;
00380     }
00381 
00382     r->chroma_vlc = 0;
00383     r->cur_vlcs   = choose_vlc_set(r->si.quant, r->si.vlc_set, 0);
00384 
00385     return rv34_decode_cbp(gb, r->cur_vlcs, r->is16);
00386 }
00387 
00391 static int rv34_decode_inter_mb_header(RV34DecContext *r, int8_t *intra_types)
00392 {
00393     MpegEncContext *s = &r->s;
00394     GetBitContext *gb = &s->gb;
00395     int mb_pos = s->mb_x + s->mb_y * s->mb_stride;
00396     int i, t;
00397 
00398     r->block_type = r->decode_mb_info(r);
00399     if(r->block_type == -1)
00400         return -1;
00401     s->current_picture_ptr->f.mb_type[mb_pos] = rv34_mb_type_to_lavc[r->block_type];
00402     r->mb_type[mb_pos] = r->block_type;
00403     if(r->block_type == RV34_MB_SKIP){
00404         if(s->pict_type == AV_PICTURE_TYPE_P)
00405             r->mb_type[mb_pos] = RV34_MB_P_16x16;
00406         if(s->pict_type == AV_PICTURE_TYPE_B)
00407             r->mb_type[mb_pos] = RV34_MB_B_DIRECT;
00408     }
00409     r->is16 = !!IS_INTRA16x16(s->current_picture_ptr->f.mb_type[mb_pos]);
00410     rv34_decode_mv(r, r->block_type);
00411     if(r->block_type == RV34_MB_SKIP){
00412         fill_rectangle(intra_types, 4, 4, r->intra_types_stride, 0, sizeof(intra_types[0]));
00413         return 0;
00414     }
00415     r->chroma_vlc = 1;
00416     r->luma_vlc   = 0;
00417 
00418     if(IS_INTRA(s->current_picture_ptr->f.mb_type[mb_pos])){
00419         if(r->is16){
00420             t = get_bits(gb, 2);
00421             fill_rectangle(intra_types, 4, 4, r->intra_types_stride, t, sizeof(intra_types[0]));
00422             r->luma_vlc   = 2;
00423         }else{
00424             if(r->decode_intra_types(r, gb, intra_types) < 0)
00425                 return -1;
00426             r->luma_vlc   = 1;
00427         }
00428         r->chroma_vlc = 0;
00429         r->cur_vlcs = choose_vlc_set(r->si.quant, r->si.vlc_set, 0);
00430     }else{
00431         for(i = 0; i < 16; i++)
00432             intra_types[(i & 3) + (i>>2) * r->intra_types_stride] = 0;
00433         r->cur_vlcs = choose_vlc_set(r->si.quant, r->si.vlc_set, 1);
00434         if(r->mb_type[mb_pos] == RV34_MB_P_MIX16x16){
00435             r->is16 = 1;
00436             r->chroma_vlc = 1;
00437             r->luma_vlc   = 2;
00438             r->cur_vlcs = choose_vlc_set(r->si.quant, r->si.vlc_set, 0);
00439         }
00440     }
00441 
00442     return rv34_decode_cbp(gb, r->cur_vlcs, r->is16);
00443 }
00444  //bitstream functions
00446 
00453 static const uint8_t part_sizes_w[RV34_MB_TYPES] = { 2, 2, 2, 1, 2, 2, 2, 2, 2, 1, 2, 2 };
00454 
00456 static const uint8_t part_sizes_h[RV34_MB_TYPES] = { 2, 2, 2, 1, 2, 2, 2, 2, 1, 2, 2, 2 };
00457 
00459 static const uint8_t avail_indexes[4] = { 6, 7, 10, 11 };
00460 
00468 static void rv34_pred_mv(RV34DecContext *r, int block_type, int subblock_no, int dmv_no)
00469 {
00470     MpegEncContext *s = &r->s;
00471     int mv_pos = s->mb_x * 2 + s->mb_y * 2 * s->b8_stride;
00472     int A[2] = {0}, B[2], C[2];
00473     int i, j;
00474     int mx, my;
00475     int avail_index = avail_indexes[subblock_no];
00476     int c_off = part_sizes_w[block_type];
00477 
00478     mv_pos += (subblock_no & 1) + (subblock_no >> 1)*s->b8_stride;
00479     if(subblock_no == 3)
00480         c_off = -1;
00481 
00482     if(r->avail_cache[avail_index - 1]){
00483         A[0] = s->current_picture_ptr->f.motion_val[0][mv_pos-1][0];
00484         A[1] = s->current_picture_ptr->f.motion_val[0][mv_pos-1][1];
00485     }
00486     if(r->avail_cache[avail_index - 4]){
00487         B[0] = s->current_picture_ptr->f.motion_val[0][mv_pos-s->b8_stride][0];
00488         B[1] = s->current_picture_ptr->f.motion_val[0][mv_pos-s->b8_stride][1];
00489     }else{
00490         B[0] = A[0];
00491         B[1] = A[1];
00492     }
00493     if(!r->avail_cache[avail_index - 4 + c_off]){
00494         if(r->avail_cache[avail_index - 4] && (r->avail_cache[avail_index - 1] || r->rv30)){
00495             C[0] = s->current_picture_ptr->f.motion_val[0][mv_pos-s->b8_stride-1][0];
00496             C[1] = s->current_picture_ptr->f.motion_val[0][mv_pos-s->b8_stride-1][1];
00497         }else{
00498             C[0] = A[0];
00499             C[1] = A[1];
00500         }
00501     }else{
00502         C[0] = s->current_picture_ptr->f.motion_val[0][mv_pos-s->b8_stride+c_off][0];
00503         C[1] = s->current_picture_ptr->f.motion_val[0][mv_pos-s->b8_stride+c_off][1];
00504     }
00505     mx = mid_pred(A[0], B[0], C[0]);
00506     my = mid_pred(A[1], B[1], C[1]);
00507     mx += r->dmv[dmv_no][0];
00508     my += r->dmv[dmv_no][1];
00509     for(j = 0; j < part_sizes_h[block_type]; j++){
00510         for(i = 0; i < part_sizes_w[block_type]; i++){
00511             s->current_picture_ptr->f.motion_val[0][mv_pos + i + j*s->b8_stride][0] = mx;
00512             s->current_picture_ptr->f.motion_val[0][mv_pos + i + j*s->b8_stride][1] = my;
00513         }
00514     }
00515 }
00516 
00517 #define GET_PTS_DIFF(a, b) ((a - b + 8192) & 0x1FFF)
00518 
00522 static int calc_add_mv(RV34DecContext *r, int dir, int val)
00523 {
00524     int mul = dir ? -r->weight2 : r->weight1;
00525 
00526     return (val * mul + 0x2000) >> 14;
00527 }
00528 
00532 static inline void rv34_pred_b_vector(int A[2], int B[2], int C[2],
00533                                       int A_avail, int B_avail, int C_avail,
00534                                       int *mx, int *my)
00535 {
00536     if(A_avail + B_avail + C_avail != 3){
00537         *mx = A[0] + B[0] + C[0];
00538         *my = A[1] + B[1] + C[1];
00539         if(A_avail + B_avail + C_avail == 2){
00540             *mx /= 2;
00541             *my /= 2;
00542         }
00543     }else{
00544         *mx = mid_pred(A[0], B[0], C[0]);
00545         *my = mid_pred(A[1], B[1], C[1]);
00546     }
00547 }
00548 
00552 static void rv34_pred_mv_b(RV34DecContext *r, int block_type, int dir)
00553 {
00554     MpegEncContext *s = &r->s;
00555     int mb_pos = s->mb_x + s->mb_y * s->mb_stride;
00556     int mv_pos = s->mb_x * 2 + s->mb_y * 2 * s->b8_stride;
00557     int A[2], B[2], C[2];
00558     int has_A = 0, has_B = 0, has_C = 0;
00559     int mx, my;
00560     int i, j;
00561     Picture *cur_pic = s->current_picture_ptr;
00562     const int mask = dir ? MB_TYPE_L1 : MB_TYPE_L0;
00563     int type = cur_pic->f.mb_type[mb_pos];
00564 
00565     memset(A, 0, sizeof(A));
00566     memset(B, 0, sizeof(B));
00567     memset(C, 0, sizeof(C));
00568     if((r->avail_cache[6-1] & type) & mask){
00569         A[0] = cur_pic->f.motion_val[dir][mv_pos - 1][0];
00570         A[1] = cur_pic->f.motion_val[dir][mv_pos - 1][1];
00571         has_A = 1;
00572     }
00573     if((r->avail_cache[6-4] & type) & mask){
00574         B[0] = cur_pic->f.motion_val[dir][mv_pos - s->b8_stride][0];
00575         B[1] = cur_pic->f.motion_val[dir][mv_pos - s->b8_stride][1];
00576         has_B = 1;
00577     }
00578     if(r->avail_cache[6-4] && (r->avail_cache[6-2] & type) & mask){
00579         C[0] = cur_pic->f.motion_val[dir][mv_pos - s->b8_stride + 2][0];
00580         C[1] = cur_pic->f.motion_val[dir][mv_pos - s->b8_stride + 2][1];
00581         has_C = 1;
00582     }else if((s->mb_x+1) == s->mb_width && (r->avail_cache[6-5] & type) & mask){
00583         C[0] = cur_pic->f.motion_val[dir][mv_pos - s->b8_stride - 1][0];
00584         C[1] = cur_pic->f.motion_val[dir][mv_pos - s->b8_stride - 1][1];
00585         has_C = 1;
00586     }
00587 
00588     rv34_pred_b_vector(A, B, C, has_A, has_B, has_C, &mx, &my);
00589 
00590     mx += r->dmv[dir][0];
00591     my += r->dmv[dir][1];
00592 
00593     for(j = 0; j < 2; j++){
00594         for(i = 0; i < 2; i++){
00595             cur_pic->f.motion_val[dir][mv_pos + i + j*s->b8_stride][0] = mx;
00596             cur_pic->f.motion_val[dir][mv_pos + i + j*s->b8_stride][1] = my;
00597         }
00598     }
00599     if(block_type == RV34_MB_B_BACKWARD || block_type == RV34_MB_B_FORWARD){
00600         ZERO8x2(cur_pic->f.motion_val[!dir][mv_pos], s->b8_stride);
00601     }
00602 }
00603 
00607 static void rv34_pred_mv_rv3(RV34DecContext *r, int block_type, int dir)
00608 {
00609     MpegEncContext *s = &r->s;
00610     int mv_pos = s->mb_x * 2 + s->mb_y * 2 * s->b8_stride;
00611     int A[2] = {0}, B[2], C[2];
00612     int i, j, k;
00613     int mx, my;
00614     int avail_index = avail_indexes[0];
00615 
00616     if(r->avail_cache[avail_index - 1]){
00617         A[0] = s->current_picture_ptr->f.motion_val[0][mv_pos - 1][0];
00618         A[1] = s->current_picture_ptr->f.motion_val[0][mv_pos - 1][1];
00619     }
00620     if(r->avail_cache[avail_index - 4]){
00621         B[0] = s->current_picture_ptr->f.motion_val[0][mv_pos - s->b8_stride][0];
00622         B[1] = s->current_picture_ptr->f.motion_val[0][mv_pos - s->b8_stride][1];
00623     }else{
00624         B[0] = A[0];
00625         B[1] = A[1];
00626     }
00627     if(!r->avail_cache[avail_index - 4 + 2]){
00628         if(r->avail_cache[avail_index - 4] && (r->avail_cache[avail_index - 1])){
00629             C[0] = s->current_picture_ptr->f.motion_val[0][mv_pos - s->b8_stride - 1][0];
00630             C[1] = s->current_picture_ptr->f.motion_val[0][mv_pos - s->b8_stride - 1][1];
00631         }else{
00632             C[0] = A[0];
00633             C[1] = A[1];
00634         }
00635     }else{
00636         C[0] = s->current_picture_ptr->f.motion_val[0][mv_pos - s->b8_stride + 2][0];
00637         C[1] = s->current_picture_ptr->f.motion_val[0][mv_pos - s->b8_stride + 2][1];
00638     }
00639     mx = mid_pred(A[0], B[0], C[0]);
00640     my = mid_pred(A[1], B[1], C[1]);
00641     mx += r->dmv[0][0];
00642     my += r->dmv[0][1];
00643     for(j = 0; j < 2; j++){
00644         for(i = 0; i < 2; i++){
00645             for(k = 0; k < 2; k++){
00646                 s->current_picture_ptr->f.motion_val[k][mv_pos + i + j*s->b8_stride][0] = mx;
00647                 s->current_picture_ptr->f.motion_val[k][mv_pos + i + j*s->b8_stride][1] = my;
00648             }
00649         }
00650     }
00651 }
00652 
00653 static const int chroma_coeffs[3] = { 0, 3, 5 };
00654 
00670 static inline void rv34_mc(RV34DecContext *r, const int block_type,
00671                           const int xoff, const int yoff, int mv_off,
00672                           const int width, const int height, int dir,
00673                           const int thirdpel, int weighted,
00674                           qpel_mc_func (*qpel_mc)[16],
00675                           h264_chroma_mc_func (*chroma_mc))
00676 {
00677     MpegEncContext *s = &r->s;
00678     uint8_t *Y, *U, *V, *srcY, *srcU, *srcV;
00679     int dxy, mx, my, umx, umy, lx, ly, uvmx, uvmy, src_x, src_y, uvsrc_x, uvsrc_y;
00680     int mv_pos = s->mb_x * 2 + s->mb_y * 2 * s->b8_stride + mv_off;
00681     int is16x16 = 1;
00682 
00683     if(thirdpel){
00684         int chroma_mx, chroma_my;
00685         mx = (s->current_picture_ptr->f.motion_val[dir][mv_pos][0] + (3 << 24)) / 3 - (1 << 24);
00686         my = (s->current_picture_ptr->f.motion_val[dir][mv_pos][1] + (3 << 24)) / 3 - (1 << 24);
00687         lx = (s->current_picture_ptr->f.motion_val[dir][mv_pos][0] + (3 << 24)) % 3;
00688         ly = (s->current_picture_ptr->f.motion_val[dir][mv_pos][1] + (3 << 24)) % 3;
00689         chroma_mx = s->current_picture_ptr->f.motion_val[dir][mv_pos][0] / 2;
00690         chroma_my = s->current_picture_ptr->f.motion_val[dir][mv_pos][1] / 2;
00691         umx = (chroma_mx + (3 << 24)) / 3 - (1 << 24);
00692         umy = (chroma_my + (3 << 24)) / 3 - (1 << 24);
00693         uvmx = chroma_coeffs[(chroma_mx + (3 << 24)) % 3];
00694         uvmy = chroma_coeffs[(chroma_my + (3 << 24)) % 3];
00695     }else{
00696         int cx, cy;
00697         mx = s->current_picture_ptr->f.motion_val[dir][mv_pos][0] >> 2;
00698         my = s->current_picture_ptr->f.motion_val[dir][mv_pos][1] >> 2;
00699         lx = s->current_picture_ptr->f.motion_val[dir][mv_pos][0] & 3;
00700         ly = s->current_picture_ptr->f.motion_val[dir][mv_pos][1] & 3;
00701         cx = s->current_picture_ptr->f.motion_val[dir][mv_pos][0] / 2;
00702         cy = s->current_picture_ptr->f.motion_val[dir][mv_pos][1] / 2;
00703         umx = cx >> 2;
00704         umy = cy >> 2;
00705         uvmx = (cx & 3) << 1;
00706         uvmy = (cy & 3) << 1;
00707         //due to some flaw RV40 uses the same MC compensation routine for H2V2 and H3V3
00708         if(uvmx == 6 && uvmy == 6)
00709             uvmx = uvmy = 4;
00710     }
00711 
00712     if (HAVE_THREADS && (s->avctx->active_thread_type & FF_THREAD_FRAME)) {
00713         /* wait for the referenced mb row to be finished */
00714         int mb_row = s->mb_y + ((yoff + my + 5 + 8 * height) >> 4);
00715         AVFrame *f = dir ? &s->next_picture_ptr->f : &s->last_picture_ptr->f;
00716         ff_thread_await_progress(f, mb_row, 0);
00717     }
00718 
00719     dxy = ly*4 + lx;
00720     srcY = dir ? s->next_picture_ptr->f.data[0] : s->last_picture_ptr->f.data[0];
00721     srcU = dir ? s->next_picture_ptr->f.data[1] : s->last_picture_ptr->f.data[1];
00722     srcV = dir ? s->next_picture_ptr->f.data[2] : s->last_picture_ptr->f.data[2];
00723     src_x = s->mb_x * 16 + xoff + mx;
00724     src_y = s->mb_y * 16 + yoff + my;
00725     uvsrc_x = s->mb_x * 8 + (xoff >> 1) + umx;
00726     uvsrc_y = s->mb_y * 8 + (yoff >> 1) + umy;
00727     srcY += src_y * s->linesize + src_x;
00728     srcU += uvsrc_y * s->uvlinesize + uvsrc_x;
00729     srcV += uvsrc_y * s->uvlinesize + uvsrc_x;
00730     if(s->h_edge_pos - (width << 3) < 6 || s->v_edge_pos - (height << 3) < 6 ||
00731        (unsigned)(src_x - !!lx*2) > s->h_edge_pos - !!lx*2 - (width <<3) - 4 ||
00732        (unsigned)(src_y - !!ly*2) > s->v_edge_pos - !!ly*2 - (height<<3) - 4) {
00733         uint8_t *uvbuf = s->edge_emu_buffer + 22 * s->linesize;
00734 
00735         srcY -= 2 + 2*s->linesize;
00736         s->dsp.emulated_edge_mc(s->edge_emu_buffer, srcY, s->linesize, (width<<3)+6, (height<<3)+6,
00737                             src_x - 2, src_y - 2, s->h_edge_pos, s->v_edge_pos);
00738         srcY = s->edge_emu_buffer + 2 + 2*s->linesize;
00739         s->dsp.emulated_edge_mc(uvbuf     , srcU, s->uvlinesize, (width<<2)+1, (height<<2)+1,
00740                             uvsrc_x, uvsrc_y, s->h_edge_pos >> 1, s->v_edge_pos >> 1);
00741         s->dsp.emulated_edge_mc(uvbuf + 16, srcV, s->uvlinesize, (width<<2)+1, (height<<2)+1,
00742                             uvsrc_x, uvsrc_y, s->h_edge_pos >> 1, s->v_edge_pos >> 1);
00743         srcU = uvbuf;
00744         srcV = uvbuf + 16;
00745     }
00746     if(!weighted){
00747         Y = s->dest[0] + xoff      + yoff     *s->linesize;
00748         U = s->dest[1] + (xoff>>1) + (yoff>>1)*s->uvlinesize;
00749         V = s->dest[2] + (xoff>>1) + (yoff>>1)*s->uvlinesize;
00750     }else{
00751         Y = r->tmp_b_block_y [dir]     +  xoff     +  yoff    *s->linesize;
00752         U = r->tmp_b_block_uv[dir*2]   + (xoff>>1) + (yoff>>1)*s->uvlinesize;
00753         V = r->tmp_b_block_uv[dir*2+1] + (xoff>>1) + (yoff>>1)*s->uvlinesize;
00754     }
00755 
00756     if(block_type == RV34_MB_P_16x8){
00757         qpel_mc[1][dxy](Y, srcY, s->linesize);
00758         Y    += 8;
00759         srcY += 8;
00760     }else if(block_type == RV34_MB_P_8x16){
00761         qpel_mc[1][dxy](Y, srcY, s->linesize);
00762         Y    += 8 * s->linesize;
00763         srcY += 8 * s->linesize;
00764     }
00765     is16x16 = (block_type != RV34_MB_P_8x8) && (block_type != RV34_MB_P_16x8) && (block_type != RV34_MB_P_8x16);
00766     qpel_mc[!is16x16][dxy](Y, srcY, s->linesize);
00767     chroma_mc[2-width]   (U, srcU, s->uvlinesize, height*4, uvmx, uvmy);
00768     chroma_mc[2-width]   (V, srcV, s->uvlinesize, height*4, uvmx, uvmy);
00769 }
00770 
00771 static void rv34_mc_1mv(RV34DecContext *r, const int block_type,
00772                         const int xoff, const int yoff, int mv_off,
00773                         const int width, const int height, int dir)
00774 {
00775     rv34_mc(r, block_type, xoff, yoff, mv_off, width, height, dir, r->rv30, 0,
00776             r->rdsp.put_pixels_tab,
00777             r->rdsp.put_chroma_pixels_tab);
00778 }
00779 
00780 static void rv4_weight(RV34DecContext *r)
00781 {
00782     r->rdsp.rv40_weight_pixels_tab[0](r->s.dest[0],
00783                                       r->tmp_b_block_y[0],
00784                                       r->tmp_b_block_y[1],
00785                                       r->weight1,
00786                                       r->weight2,
00787                                       r->s.linesize);
00788     r->rdsp.rv40_weight_pixels_tab[1](r->s.dest[1],
00789                                       r->tmp_b_block_uv[0],
00790                                       r->tmp_b_block_uv[2],
00791                                       r->weight1,
00792                                       r->weight2,
00793                                       r->s.uvlinesize);
00794     r->rdsp.rv40_weight_pixels_tab[1](r->s.dest[2],
00795                                       r->tmp_b_block_uv[1],
00796                                       r->tmp_b_block_uv[3],
00797                                       r->weight1,
00798                                       r->weight2,
00799                                       r->s.uvlinesize);
00800 }
00801 
00802 static void rv34_mc_2mv(RV34DecContext *r, const int block_type)
00803 {
00804     int weighted = !r->rv30 && block_type != RV34_MB_B_BIDIR && r->weight1 != 8192;
00805 
00806     rv34_mc(r, block_type, 0, 0, 0, 2, 2, 0, r->rv30, weighted,
00807             r->rdsp.put_pixels_tab,
00808             r->rdsp.put_chroma_pixels_tab);
00809     if(!weighted){
00810         rv34_mc(r, block_type, 0, 0, 0, 2, 2, 1, r->rv30, 0,
00811                 r->rdsp.avg_pixels_tab,
00812                 r->rdsp.avg_chroma_pixels_tab);
00813     }else{
00814         rv34_mc(r, block_type, 0, 0, 0, 2, 2, 1, r->rv30, 1,
00815                 r->rdsp.put_pixels_tab,
00816                 r->rdsp.put_chroma_pixels_tab);
00817         rv4_weight(r);
00818     }
00819 }
00820 
00821 static void rv34_mc_2mv_skip(RV34DecContext *r)
00822 {
00823     int i, j;
00824     int weighted = !r->rv30 && r->weight1 != 8192;
00825 
00826     for(j = 0; j < 2; j++)
00827         for(i = 0; i < 2; i++){
00828              rv34_mc(r, RV34_MB_P_8x8, i*8, j*8, i+j*r->s.b8_stride, 1, 1, 0, r->rv30,
00829                      weighted,
00830                      r->rdsp.put_pixels_tab,
00831                      r->rdsp.put_chroma_pixels_tab);
00832              rv34_mc(r, RV34_MB_P_8x8, i*8, j*8, i+j*r->s.b8_stride, 1, 1, 1, r->rv30,
00833                      weighted,
00834                      weighted ? r->rdsp.put_pixels_tab : r->rdsp.avg_pixels_tab,
00835                      weighted ? r->rdsp.put_chroma_pixels_tab : r->rdsp.avg_chroma_pixels_tab);
00836         }
00837     if(weighted)
00838         rv4_weight(r);
00839 }
00840 
00842 static const int num_mvs[RV34_MB_TYPES] = { 0, 0, 1, 4, 1, 1, 0, 0, 2, 2, 2, 1 };
00843 
00848 static int rv34_decode_mv(RV34DecContext *r, int block_type)
00849 {
00850     MpegEncContext *s = &r->s;
00851     GetBitContext *gb = &s->gb;
00852     int i, j, k, l;
00853     int mv_pos = s->mb_x * 2 + s->mb_y * 2 * s->b8_stride;
00854     int next_bt;
00855 
00856     memset(r->dmv, 0, sizeof(r->dmv));
00857     for(i = 0; i < num_mvs[block_type]; i++){
00858         r->dmv[i][0] = svq3_get_se_golomb(gb);
00859         r->dmv[i][1] = svq3_get_se_golomb(gb);
00860     }
00861     switch(block_type){
00862     case RV34_MB_TYPE_INTRA:
00863     case RV34_MB_TYPE_INTRA16x16:
00864         ZERO8x2(s->current_picture_ptr->f.motion_val[0][s->mb_x * 2 + s->mb_y * 2 * s->b8_stride], s->b8_stride);
00865         return 0;
00866     case RV34_MB_SKIP:
00867         if(s->pict_type == AV_PICTURE_TYPE_P){
00868             ZERO8x2(s->current_picture_ptr->f.motion_val[0][s->mb_x * 2 + s->mb_y * 2 * s->b8_stride], s->b8_stride);
00869             rv34_mc_1mv (r, block_type, 0, 0, 0, 2, 2, 0);
00870             break;
00871         }
00872     case RV34_MB_B_DIRECT:
00873         //surprisingly, it uses motion scheme from next reference frame
00874         /* wait for the current mb row to be finished */
00875         if (HAVE_THREADS && (s->avctx->active_thread_type & FF_THREAD_FRAME))
00876             ff_thread_await_progress(&s->next_picture_ptr->f, FFMAX(0, s->mb_y-1), 0);
00877 
00878         next_bt = s->next_picture_ptr->f.mb_type[s->mb_x + s->mb_y * s->mb_stride];
00879         if(IS_INTRA(next_bt) || IS_SKIP(next_bt)){
00880             ZERO8x2(s->current_picture_ptr->f.motion_val[0][s->mb_x * 2 + s->mb_y * 2 * s->b8_stride], s->b8_stride);
00881             ZERO8x2(s->current_picture_ptr->f.motion_val[1][s->mb_x * 2 + s->mb_y * 2 * s->b8_stride], s->b8_stride);
00882         }else
00883             for(j = 0; j < 2; j++)
00884                 for(i = 0; i < 2; i++)
00885                     for(k = 0; k < 2; k++)
00886                         for(l = 0; l < 2; l++)
00887                             s->current_picture_ptr->f.motion_val[l][mv_pos + i + j*s->b8_stride][k] = calc_add_mv(r, l, s->next_picture_ptr->f.motion_val[0][mv_pos + i + j*s->b8_stride][k]);
00888         if(!(IS_16X8(next_bt) || IS_8X16(next_bt) || IS_8X8(next_bt))) //we can use whole macroblock MC
00889             rv34_mc_2mv(r, block_type);
00890         else
00891             rv34_mc_2mv_skip(r);
00892         ZERO8x2(s->current_picture_ptr->f.motion_val[0][s->mb_x * 2 + s->mb_y * 2 * s->b8_stride], s->b8_stride);
00893         break;
00894     case RV34_MB_P_16x16:
00895     case RV34_MB_P_MIX16x16:
00896         rv34_pred_mv(r, block_type, 0, 0);
00897         rv34_mc_1mv (r, block_type, 0, 0, 0, 2, 2, 0);
00898         break;
00899     case RV34_MB_B_FORWARD:
00900     case RV34_MB_B_BACKWARD:
00901         r->dmv[1][0] = r->dmv[0][0];
00902         r->dmv[1][1] = r->dmv[0][1];
00903         if(r->rv30)
00904             rv34_pred_mv_rv3(r, block_type, block_type == RV34_MB_B_BACKWARD);
00905         else
00906             rv34_pred_mv_b  (r, block_type, block_type == RV34_MB_B_BACKWARD);
00907         rv34_mc_1mv     (r, block_type, 0, 0, 0, 2, 2, block_type == RV34_MB_B_BACKWARD);
00908         break;
00909     case RV34_MB_P_16x8:
00910     case RV34_MB_P_8x16:
00911         rv34_pred_mv(r, block_type, 0, 0);
00912         rv34_pred_mv(r, block_type, 1 + (block_type == RV34_MB_P_16x8), 1);
00913         if(block_type == RV34_MB_P_16x8){
00914             rv34_mc_1mv(r, block_type, 0, 0, 0,            2, 1, 0);
00915             rv34_mc_1mv(r, block_type, 0, 8, s->b8_stride, 2, 1, 0);
00916         }
00917         if(block_type == RV34_MB_P_8x16){
00918             rv34_mc_1mv(r, block_type, 0, 0, 0, 1, 2, 0);
00919             rv34_mc_1mv(r, block_type, 8, 0, 1, 1, 2, 0);
00920         }
00921         break;
00922     case RV34_MB_B_BIDIR:
00923         rv34_pred_mv_b  (r, block_type, 0);
00924         rv34_pred_mv_b  (r, block_type, 1);
00925         rv34_mc_2mv     (r, block_type);
00926         break;
00927     case RV34_MB_P_8x8:
00928         for(i=0;i< 4;i++){
00929             rv34_pred_mv(r, block_type, i, i);
00930             rv34_mc_1mv (r, block_type, (i&1)<<3, (i&2)<<2, (i&1)+(i>>1)*s->b8_stride, 1, 1, 0);
00931         }
00932         break;
00933     }
00934 
00935     return 0;
00936 } // mv group
00938 
00944 static const int ittrans[9] = {
00945  DC_PRED, VERT_PRED, HOR_PRED, DIAG_DOWN_RIGHT_PRED, DIAG_DOWN_LEFT_PRED,
00946  VERT_RIGHT_PRED, VERT_LEFT_PRED, HOR_UP_PRED, HOR_DOWN_PRED,
00947 };
00948 
00950 static const int ittrans16[4] = {
00951  DC_PRED8x8, VERT_PRED8x8, HOR_PRED8x8, PLANE_PRED8x8,
00952 };
00953 
00957 static void rv34_pred_4x4_block(RV34DecContext *r, uint8_t *dst, int stride, int itype, int up, int left, int down, int right)
00958 {
00959     uint8_t *prev = dst - stride + 4;
00960     uint32_t topleft;
00961 
00962     if(!up && !left)
00963         itype = DC_128_PRED;
00964     else if(!up){
00965         if(itype == VERT_PRED) itype = HOR_PRED;
00966         if(itype == DC_PRED)   itype = LEFT_DC_PRED;
00967     }else if(!left){
00968         if(itype == HOR_PRED)  itype = VERT_PRED;
00969         if(itype == DC_PRED)   itype = TOP_DC_PRED;
00970         if(itype == DIAG_DOWN_LEFT_PRED) itype = DIAG_DOWN_LEFT_PRED_RV40_NODOWN;
00971     }
00972     if(!down){
00973         if(itype == DIAG_DOWN_LEFT_PRED) itype = DIAG_DOWN_LEFT_PRED_RV40_NODOWN;
00974         if(itype == HOR_UP_PRED) itype = HOR_UP_PRED_RV40_NODOWN;
00975         if(itype == VERT_LEFT_PRED) itype = VERT_LEFT_PRED_RV40_NODOWN;
00976     }
00977     if(!right && up){
00978         topleft = dst[-stride + 3] * 0x01010101u;
00979         prev = (uint8_t*)&topleft;
00980     }
00981     r->h.pred4x4[itype](dst, prev, stride);
00982 }
00983 
00984 static inline int adjust_pred16(int itype, int up, int left)
00985 {
00986     if(!up && !left)
00987         itype = DC_128_PRED8x8;
00988     else if(!up){
00989         if(itype == PLANE_PRED8x8)itype = HOR_PRED8x8;
00990         if(itype == VERT_PRED8x8) itype = HOR_PRED8x8;
00991         if(itype == DC_PRED8x8)   itype = LEFT_DC_PRED8x8;
00992     }else if(!left){
00993         if(itype == PLANE_PRED8x8)itype = VERT_PRED8x8;
00994         if(itype == HOR_PRED8x8)  itype = VERT_PRED8x8;
00995         if(itype == DC_PRED8x8)   itype = TOP_DC_PRED8x8;
00996     }
00997     return itype;
00998 }
00999 
01000 static inline void rv34_process_block(RV34DecContext *r,
01001                                       uint8_t *pdst, int stride,
01002                                       int fc, int sc, int q_dc, int q_ac)
01003 {
01004     MpegEncContext *s = &r->s;
01005     DCTELEM *ptr = s->block[0];
01006     int has_ac = rv34_decode_block(ptr, &s->gb, r->cur_vlcs,
01007                                    fc, sc, q_dc, q_ac, q_ac);
01008     if(has_ac){
01009         r->rdsp.rv34_idct_add(pdst, stride, ptr);
01010     }else{
01011         r->rdsp.rv34_idct_dc_add(pdst, stride, ptr[0]);
01012         ptr[0] = 0;
01013     }
01014 }
01015 
01016 static void rv34_output_i16x16(RV34DecContext *r, int8_t *intra_types, int cbp)
01017 {
01018     LOCAL_ALIGNED_16(DCTELEM, block16, [16]);
01019     MpegEncContext *s    = &r->s;
01020     GetBitContext  *gb   = &s->gb;
01021     int             q_dc = rv34_qscale_tab[ r->luma_dc_quant_i[s->qscale] ],
01022                     q_ac = rv34_qscale_tab[s->qscale];
01023     uint8_t        *dst  = s->dest[0];
01024     DCTELEM        *ptr  = s->block[0];
01025     int       avail[6*8] = {0};
01026     int i, j, itype, has_ac;
01027 
01028     memset(block16, 0, 16 * sizeof(*block16));
01029 
01030     // Set neighbour information.
01031     if(r->avail_cache[1])
01032         avail[0] = 1;
01033     if(r->avail_cache[2])
01034         avail[1] = avail[2] = 1;
01035     if(r->avail_cache[3])
01036         avail[3] = avail[4] = 1;
01037     if(r->avail_cache[4])
01038         avail[5] = 1;
01039     if(r->avail_cache[5])
01040         avail[8] = avail[16] = 1;
01041     if(r->avail_cache[9])
01042         avail[24] = avail[32] = 1;
01043 
01044     has_ac = rv34_decode_block(block16, gb, r->cur_vlcs, 3, 0, q_dc, q_dc, q_ac);
01045     if(has_ac)
01046         r->rdsp.rv34_inv_transform(block16);
01047     else
01048         r->rdsp.rv34_inv_transform_dc(block16);
01049 
01050     itype = ittrans16[intra_types[0]];
01051     itype = adjust_pred16(itype, r->avail_cache[6-4], r->avail_cache[6-1]);
01052     r->h.pred16x16[itype](dst, s->linesize);
01053 
01054     for(j = 0; j < 4; j++){
01055         for(i = 0; i < 4; i++, cbp >>= 1){
01056             int dc = block16[i + j*4];
01057 
01058             if(cbp & 1){
01059                 has_ac = rv34_decode_block(ptr, gb, r->cur_vlcs, r->luma_vlc, 0, q_ac, q_ac, q_ac);
01060             }else
01061                 has_ac = 0;
01062 
01063             if(has_ac){
01064                 ptr[0] = dc;
01065                 r->rdsp.rv34_idct_add(dst+4*i, s->linesize, ptr);
01066             }else
01067                 r->rdsp.rv34_idct_dc_add(dst+4*i, s->linesize, dc);
01068         }
01069 
01070         dst += 4*s->linesize;
01071     }
01072 
01073     itype = ittrans16[intra_types[0]];
01074     if(itype == PLANE_PRED8x8) itype = DC_PRED8x8;
01075     itype = adjust_pred16(itype, r->avail_cache[6-4], r->avail_cache[6-1]);
01076 
01077     q_dc = rv34_qscale_tab[rv34_chroma_quant[1][s->qscale]];
01078     q_ac = rv34_qscale_tab[rv34_chroma_quant[0][s->qscale]];
01079 
01080     for(j = 1; j < 3; j++){
01081         dst = s->dest[j];
01082         r->h.pred8x8[itype](dst, s->uvlinesize);
01083         for(i = 0; i < 4; i++, cbp >>= 1){
01084             uint8_t *pdst;
01085             if(!(cbp & 1)) continue;
01086             pdst   = dst + (i&1)*4 + (i&2)*2*s->uvlinesize;
01087 
01088             rv34_process_block(r, pdst, s->uvlinesize,
01089                                r->chroma_vlc, 1, q_dc, q_ac);
01090         }
01091     }
01092 }
01093 
01094 static void rv34_output_intra(RV34DecContext *r, int8_t *intra_types, int cbp)
01095 {
01096     MpegEncContext *s   = &r->s;
01097     uint8_t        *dst = s->dest[0];
01098     int      avail[6*8] = {0};
01099     int i, j, k;
01100     int idx, q_ac, q_dc;
01101 
01102     // Set neighbour information.
01103     if(r->avail_cache[1])
01104         avail[0] = 1;
01105     if(r->avail_cache[2])
01106         avail[1] = avail[2] = 1;
01107     if(r->avail_cache[3])
01108         avail[3] = avail[4] = 1;
01109     if(r->avail_cache[4])
01110         avail[5] = 1;
01111     if(r->avail_cache[5])
01112         avail[8] = avail[16] = 1;
01113     if(r->avail_cache[9])
01114         avail[24] = avail[32] = 1;
01115 
01116     q_ac = rv34_qscale_tab[s->qscale];
01117     for(j = 0; j < 4; j++){
01118         idx = 9 + j*8;
01119         for(i = 0; i < 4; i++, cbp >>= 1, dst += 4, idx++){
01120             rv34_pred_4x4_block(r, dst, s->linesize, ittrans[intra_types[i]], avail[idx-8], avail[idx-1], avail[idx+7], avail[idx-7]);
01121             avail[idx] = 1;
01122             if(!(cbp & 1)) continue;
01123 
01124             rv34_process_block(r, dst, s->linesize,
01125                                r->luma_vlc, 0, q_ac, q_ac);
01126         }
01127         dst += s->linesize * 4 - 4*4;
01128         intra_types += r->intra_types_stride;
01129     }
01130 
01131     intra_types -= r->intra_types_stride * 4;
01132 
01133     q_dc = rv34_qscale_tab[rv34_chroma_quant[1][s->qscale]];
01134     q_ac = rv34_qscale_tab[rv34_chroma_quant[0][s->qscale]];
01135 
01136     for(k = 0; k < 2; k++){
01137         dst = s->dest[1+k];
01138         fill_rectangle(r->avail_cache + 6, 2, 2, 4, 0, 4);
01139 
01140         for(j = 0; j < 2; j++){
01141             int* acache = r->avail_cache + 6 + j*4;
01142             for(i = 0; i < 2; i++, cbp >>= 1, acache++){
01143                 int itype = ittrans[intra_types[i*2+j*2*r->intra_types_stride]];
01144                 rv34_pred_4x4_block(r, dst+4*i, s->uvlinesize, itype, acache[-4], acache[-1], !i && !j, acache[-3]);
01145                 acache[0] = 1;
01146 
01147                 if(!(cbp&1)) continue;
01148 
01149                 rv34_process_block(r, dst + 4*i, s->uvlinesize,
01150                                    r->chroma_vlc, 1, q_dc, q_ac);
01151             }
01152 
01153             dst += 4*s->uvlinesize;
01154         }
01155     }
01156 }
01157 
01158 static int is_mv_diff_gt_3(int16_t (*motion_val)[2], int step)
01159 {
01160     int d;
01161     d = motion_val[0][0] - motion_val[-step][0];
01162     if(d < -3 || d > 3)
01163         return 1;
01164     d = motion_val[0][1] - motion_val[-step][1];
01165     if(d < -3 || d > 3)
01166         return 1;
01167     return 0;
01168 }
01169 
01170 static int rv34_set_deblock_coef(RV34DecContext *r)
01171 {
01172     MpegEncContext *s = &r->s;
01173     int hmvmask = 0, vmvmask = 0, i, j;
01174     int midx = s->mb_x * 2 + s->mb_y * 2 * s->b8_stride;
01175     int16_t (*motion_val)[2] = &s->current_picture_ptr->f.motion_val[0][midx];
01176     for(j = 0; j < 16; j += 8){
01177         for(i = 0; i < 2; i++){
01178             if(is_mv_diff_gt_3(motion_val + i, 1))
01179                 vmvmask |= 0x11 << (j + i*2);
01180             if((j || s->mb_y) && is_mv_diff_gt_3(motion_val + i, s->b8_stride))
01181                 hmvmask |= 0x03 << (j + i*2);
01182         }
01183         motion_val += s->b8_stride;
01184     }
01185     if(s->first_slice_line)
01186         hmvmask &= ~0x000F;
01187     if(!s->mb_x)
01188         vmvmask &= ~0x1111;
01189     if(r->rv30){ //RV30 marks both subblocks on the edge for filtering
01190         vmvmask |= (vmvmask & 0x4444) >> 1;
01191         hmvmask |= (hmvmask & 0x0F00) >> 4;
01192         if(s->mb_x)
01193             r->deblock_coefs[s->mb_x - 1 + s->mb_y*s->mb_stride] |= (vmvmask & 0x1111) << 3;
01194         if(!s->first_slice_line)
01195             r->deblock_coefs[s->mb_x + (s->mb_y - 1)*s->mb_stride] |= (hmvmask & 0xF) << 12;
01196     }
01197     return hmvmask | vmvmask;
01198 }
01199 
01200 static int rv34_decode_inter_macroblock(RV34DecContext *r, int8_t *intra_types)
01201 {
01202     MpegEncContext *s   = &r->s;
01203     GetBitContext  *gb  = &s->gb;
01204     uint8_t        *dst = s->dest[0];
01205     DCTELEM        *ptr = s->block[0];
01206     int          mb_pos = s->mb_x + s->mb_y * s->mb_stride;
01207     int cbp, cbp2;
01208     int q_dc, q_ac, has_ac;
01209     int i, j;
01210     int dist;
01211 
01212     // Calculate which neighbours are available. Maybe it's worth optimizing too.
01213     memset(r->avail_cache, 0, sizeof(r->avail_cache));
01214     fill_rectangle(r->avail_cache + 6, 2, 2, 4, 1, 4);
01215     dist = (s->mb_x - s->resync_mb_x) + (s->mb_y - s->resync_mb_y) * s->mb_width;
01216     if(s->mb_x && dist)
01217         r->avail_cache[5] =
01218         r->avail_cache[9] = s->current_picture_ptr->f.mb_type[mb_pos - 1];
01219     if(dist >= s->mb_width)
01220         r->avail_cache[2] =
01221         r->avail_cache[3] = s->current_picture_ptr->f.mb_type[mb_pos - s->mb_stride];
01222     if(((s->mb_x+1) < s->mb_width) && dist >= s->mb_width - 1)
01223         r->avail_cache[4] = s->current_picture_ptr->f.mb_type[mb_pos - s->mb_stride + 1];
01224     if(s->mb_x && dist > s->mb_width)
01225         r->avail_cache[1] = s->current_picture_ptr->f.mb_type[mb_pos - s->mb_stride - 1];
01226 
01227     s->qscale = r->si.quant;
01228     cbp = cbp2 = rv34_decode_inter_mb_header(r, intra_types);
01229     r->cbp_luma  [mb_pos] = cbp;
01230     r->cbp_chroma[mb_pos] = cbp >> 16;
01231     r->deblock_coefs[mb_pos] = rv34_set_deblock_coef(r) | r->cbp_luma[mb_pos];
01232     s->current_picture_ptr->f.qscale_table[mb_pos] = s->qscale;
01233 
01234     if(cbp == -1)
01235         return -1;
01236 
01237     if (IS_INTRA(s->current_picture_ptr->f.mb_type[mb_pos])){
01238         if(r->is16) rv34_output_i16x16(r, intra_types, cbp);
01239         else        rv34_output_intra(r, intra_types, cbp);
01240         return 0;
01241     }
01242 
01243     if(r->is16){
01244         // Only for RV34_MB_P_MIX16x16
01245         LOCAL_ALIGNED_16(DCTELEM, block16, [16]);
01246         memset(block16, 0, 16 * sizeof(*block16));
01247         q_dc = rv34_qscale_tab[ r->luma_dc_quant_p[s->qscale] ];
01248         q_ac = rv34_qscale_tab[s->qscale];
01249         if (rv34_decode_block(block16, gb, r->cur_vlcs, 3, 0, q_dc, q_dc, q_ac))
01250             r->rdsp.rv34_inv_transform(block16);
01251         else
01252             r->rdsp.rv34_inv_transform_dc(block16);
01253 
01254         q_ac = rv34_qscale_tab[s->qscale];
01255 
01256         for(j = 0; j < 4; j++){
01257             for(i = 0; i < 4; i++, cbp >>= 1){
01258                 int      dc   = block16[i + j*4];
01259 
01260                 if(cbp & 1){
01261                     has_ac = rv34_decode_block(ptr, gb, r->cur_vlcs, r->luma_vlc, 0, q_ac, q_ac, q_ac);
01262                 }else
01263                     has_ac = 0;
01264 
01265                 if(has_ac){
01266                     ptr[0] = dc;
01267                     r->rdsp.rv34_idct_add(dst+4*i, s->linesize, ptr);
01268                 }else
01269                     r->rdsp.rv34_idct_dc_add(dst+4*i, s->linesize, dc);
01270             }
01271 
01272             dst += 4*s->linesize;
01273         }
01274 
01275         r->cur_vlcs = choose_vlc_set(r->si.quant, r->si.vlc_set, 1);
01276     }else{
01277         q_ac = rv34_qscale_tab[s->qscale];
01278 
01279         for(j = 0; j < 4; j++){
01280             for(i = 0; i < 4; i++, cbp >>= 1){
01281                 if(!(cbp & 1)) continue;
01282 
01283                 rv34_process_block(r, dst + 4*i, s->linesize,
01284                                    r->luma_vlc, 0, q_ac, q_ac);
01285             }
01286             dst += 4*s->linesize;
01287         }
01288     }
01289 
01290     q_dc = rv34_qscale_tab[rv34_chroma_quant[1][s->qscale]];
01291     q_ac = rv34_qscale_tab[rv34_chroma_quant[0][s->qscale]];
01292 
01293     for(j = 1; j < 3; j++){
01294         dst = s->dest[j];
01295         for(i = 0; i < 4; i++, cbp >>= 1){
01296             uint8_t *pdst;
01297             if(!(cbp & 1)) continue;
01298             pdst = dst + (i&1)*4 + (i&2)*2*s->uvlinesize;
01299 
01300             rv34_process_block(r, pdst, s->uvlinesize,
01301                                r->chroma_vlc, 1, q_dc, q_ac);
01302         }
01303     }
01304 
01305     return 0;
01306 }
01307 
01308 static int rv34_decode_intra_macroblock(RV34DecContext *r, int8_t *intra_types)
01309 {
01310     MpegEncContext *s = &r->s;
01311     int cbp, dist;
01312     int mb_pos = s->mb_x + s->mb_y * s->mb_stride;
01313 
01314     // Calculate which neighbours are available. Maybe it's worth optimizing too.
01315     memset(r->avail_cache, 0, sizeof(r->avail_cache));
01316     fill_rectangle(r->avail_cache + 6, 2, 2, 4, 1, 4);
01317     dist = (s->mb_x - s->resync_mb_x) + (s->mb_y - s->resync_mb_y) * s->mb_width;
01318     if(s->mb_x && dist)
01319         r->avail_cache[5] =
01320         r->avail_cache[9] = s->current_picture_ptr->f.mb_type[mb_pos - 1];
01321     if(dist >= s->mb_width)
01322         r->avail_cache[2] =
01323         r->avail_cache[3] = s->current_picture_ptr->f.mb_type[mb_pos - s->mb_stride];
01324     if(((s->mb_x+1) < s->mb_width) && dist >= s->mb_width - 1)
01325         r->avail_cache[4] = s->current_picture_ptr->f.mb_type[mb_pos - s->mb_stride + 1];
01326     if(s->mb_x && dist > s->mb_width)
01327         r->avail_cache[1] = s->current_picture_ptr->f.mb_type[mb_pos - s->mb_stride - 1];
01328 
01329     s->qscale = r->si.quant;
01330     cbp = rv34_decode_intra_mb_header(r, intra_types);
01331     r->cbp_luma  [mb_pos] = cbp;
01332     r->cbp_chroma[mb_pos] = cbp >> 16;
01333     r->deblock_coefs[mb_pos] = 0xFFFF;
01334     s->current_picture_ptr->f.qscale_table[mb_pos] = s->qscale;
01335 
01336     if(cbp == -1)
01337         return -1;
01338 
01339     if(r->is16){
01340         rv34_output_i16x16(r, intra_types, cbp);
01341         return 0;
01342     }
01343 
01344     rv34_output_intra(r, intra_types, cbp);
01345     return 0;
01346 }
01347 
01348 static int check_slice_end(RV34DecContext *r, MpegEncContext *s)
01349 {
01350     int bits;
01351     if(s->mb_y >= s->mb_height)
01352         return 1;
01353     if(!s->mb_num_left)
01354         return 1;
01355     if(r->s.mb_skip_run > 1)
01356         return 0;
01357     bits = get_bits_left(&s->gb);
01358     if(bits < 0 || (bits < 8 && !show_bits(&s->gb, bits)))
01359         return 1;
01360     return 0;
01361 }
01362 
01363 
01364 static void rv34_decoder_free(RV34DecContext *r)
01365 {
01366     av_freep(&r->intra_types_hist);
01367     r->intra_types = NULL;
01368     av_freep(&r->tmp_b_block_base);
01369     av_freep(&r->mb_type);
01370     av_freep(&r->cbp_luma);
01371     av_freep(&r->cbp_chroma);
01372     av_freep(&r->deblock_coefs);
01373 }
01374 
01375 
01376 static int rv34_decoder_alloc(RV34DecContext *r)
01377 {
01378     r->intra_types_stride = r->s.mb_width * 4 + 4;
01379 
01380     r->cbp_chroma       = av_malloc(r->s.mb_stride * r->s.mb_height *
01381                                     sizeof(*r->cbp_chroma));
01382     r->cbp_luma         = av_malloc(r->s.mb_stride * r->s.mb_height *
01383                                     sizeof(*r->cbp_luma));
01384     r->deblock_coefs    = av_malloc(r->s.mb_stride * r->s.mb_height *
01385                                     sizeof(*r->deblock_coefs));
01386     r->intra_types_hist = av_malloc(r->intra_types_stride * 4 * 2 *
01387                                     sizeof(*r->intra_types_hist));
01388     r->mb_type          = av_mallocz(r->s.mb_stride * r->s.mb_height *
01389                                      sizeof(*r->mb_type));
01390 
01391     if (!(r->cbp_chroma       && r->cbp_luma && r->deblock_coefs &&
01392           r->intra_types_hist && r->mb_type)) {
01393         rv34_decoder_free(r);
01394         return AVERROR(ENOMEM);
01395     }
01396 
01397     r->intra_types = r->intra_types_hist + r->intra_types_stride * 4;
01398 
01399     return 0;
01400 }
01401 
01402 
01403 static int rv34_decoder_realloc(RV34DecContext *r)
01404 {
01405     rv34_decoder_free(r);
01406     return rv34_decoder_alloc(r);
01407 }
01408 
01409 
01410 static int rv34_decode_slice(RV34DecContext *r, int end, const uint8_t* buf, int buf_size)
01411 {
01412     MpegEncContext *s = &r->s;
01413     GetBitContext *gb = &s->gb;
01414     int mb_pos;
01415     int res;
01416 
01417     init_get_bits(&r->s.gb, buf, buf_size*8);
01418     res = r->parse_slice_header(r, gb, &r->si);
01419     if(res < 0){
01420         av_log(s->avctx, AV_LOG_ERROR, "Incorrect or unknown slice header\n");
01421         return -1;
01422     }
01423 
01424     if ((s->mb_x == 0 && s->mb_y == 0) || s->current_picture_ptr==NULL) {
01425         if (s->width != r->si.width || s->height != r->si.height) {
01426             int err;
01427 
01428             av_log(s->avctx, AV_LOG_WARNING, "Changing dimensions to %dx%d\n",
01429                    r->si.width, r->si.height);
01430             MPV_common_end(s);
01431             s->width  = r->si.width;
01432             s->height = r->si.height;
01433             avcodec_set_dimensions(s->avctx, s->width, s->height);
01434             if ((err = MPV_common_init(s)) < 0)
01435                 return err;
01436             if ((err = rv34_decoder_realloc(r)) < 0)
01437                 return err;
01438         }
01439         s->pict_type = r->si.type ? r->si.type : AV_PICTURE_TYPE_I;
01440         if(MPV_frame_start(s, s->avctx) < 0)
01441             return -1;
01442         ff_er_frame_start(s);
01443         if (!r->tmp_b_block_base) {
01444             int i;
01445 
01446             r->tmp_b_block_base = av_malloc(s->linesize * 48);
01447             for (i = 0; i < 2; i++)
01448                 r->tmp_b_block_y[i] = r->tmp_b_block_base + i * 16 * s->linesize;
01449             for (i = 0; i < 4; i++)
01450                 r->tmp_b_block_uv[i] = r->tmp_b_block_base + 32 * s->linesize
01451                                        + (i >> 1) * 8 * s->uvlinesize + (i & 1) * 16;
01452         }
01453         r->cur_pts = r->si.pts;
01454         if(s->pict_type != AV_PICTURE_TYPE_B){
01455             r->last_pts = r->next_pts;
01456             r->next_pts = r->cur_pts;
01457         }else{
01458             int refdist = GET_PTS_DIFF(r->next_pts, r->last_pts);
01459             int dist0   = GET_PTS_DIFF(r->cur_pts,  r->last_pts);
01460             int dist1   = GET_PTS_DIFF(r->next_pts, r->cur_pts);
01461 
01462             if(!refdist){
01463                 r->weight1 = r->weight2 = 8192;
01464             }else{
01465                 r->weight1 = (dist0 << 14) / refdist;
01466                 r->weight2 = (dist1 << 14) / refdist;
01467             }
01468         }
01469         s->mb_x = s->mb_y = 0;
01470         ff_thread_finish_setup(s->avctx);
01471     } else {
01472         int slice_type = r->si.type ? r->si.type : AV_PICTURE_TYPE_I;
01473 
01474         if (slice_type != s->pict_type) {
01475             av_log(s->avctx, AV_LOG_ERROR, "Slice type mismatch\n");
01476             return AVERROR_INVALIDDATA;
01477         }
01478         if (s->width != r->si.width || s->height != r->si.height) {
01479             av_log(s->avctx, AV_LOG_ERROR, "Size mismatch\n");
01480             return AVERROR_INVALIDDATA;
01481         }
01482     }
01483 
01484     r->si.end = end;
01485     s->qscale = r->si.quant;
01486     s->mb_num_left = r->si.end - r->si.start;
01487     r->s.mb_skip_run = 0;
01488 
01489     mb_pos = s->mb_x + s->mb_y * s->mb_width;
01490     if(r->si.start != mb_pos){
01491         av_log(s->avctx, AV_LOG_ERROR, "Slice indicates MB offset %d, got %d\n", r->si.start, mb_pos);
01492         s->mb_x = r->si.start % s->mb_width;
01493         s->mb_y = r->si.start / s->mb_width;
01494     }
01495     memset(r->intra_types_hist, -1, r->intra_types_stride * 4 * 2 * sizeof(*r->intra_types_hist));
01496     s->first_slice_line = 1;
01497     s->resync_mb_x = s->mb_x;
01498     s->resync_mb_y = s->mb_y;
01499 
01500     ff_init_block_index(s);
01501     while(!check_slice_end(r, s)) {
01502         ff_update_block_index(s);
01503 
01504         if(r->si.type)
01505             res = rv34_decode_inter_macroblock(r, r->intra_types + s->mb_x * 4 + 4);
01506         else
01507             res = rv34_decode_intra_macroblock(r, r->intra_types + s->mb_x * 4 + 4);
01508         if(res < 0){
01509             ff_er_add_slice(s, s->resync_mb_x, s->resync_mb_y, s->mb_x-1, s->mb_y, ER_MB_ERROR);
01510             return -1;
01511         }
01512         if (++s->mb_x == s->mb_width) {
01513             s->mb_x = 0;
01514             s->mb_y++;
01515             ff_init_block_index(s);
01516 
01517             memmove(r->intra_types_hist, r->intra_types, r->intra_types_stride * 4 * sizeof(*r->intra_types_hist));
01518             memset(r->intra_types, -1, r->intra_types_stride * 4 * sizeof(*r->intra_types_hist));
01519 
01520             if(r->loop_filter && s->mb_y >= 2)
01521                 r->loop_filter(r, s->mb_y - 2);
01522 
01523             if (HAVE_THREADS && (s->avctx->active_thread_type & FF_THREAD_FRAME))
01524                 ff_thread_report_progress(&s->current_picture_ptr->f,
01525                                           s->mb_y - 2, 0);
01526 
01527         }
01528         if(s->mb_x == s->resync_mb_x)
01529             s->first_slice_line=0;
01530         s->mb_num_left--;
01531     }
01532     ff_er_add_slice(s, s->resync_mb_x, s->resync_mb_y, s->mb_x-1, s->mb_y, ER_MB_END);
01533 
01534     return s->mb_y == s->mb_height;
01535 }
01536  // recons group end
01538 
01542 av_cold int ff_rv34_decode_init(AVCodecContext *avctx)
01543 {
01544     RV34DecContext *r = avctx->priv_data;
01545     MpegEncContext *s = &r->s;
01546     int ret;
01547 
01548     MPV_decode_defaults(s);
01549     s->avctx      = avctx;
01550     s->out_format = FMT_H263;
01551     s->codec_id   = avctx->codec_id;
01552 
01553     s->width  = avctx->width;
01554     s->height = avctx->height;
01555 
01556     r->s.avctx = avctx;
01557     avctx->flags |= CODEC_FLAG_EMU_EDGE;
01558     r->s.flags |= CODEC_FLAG_EMU_EDGE;
01559     avctx->pix_fmt = PIX_FMT_YUV420P;
01560     avctx->has_b_frames = 1;
01561     s->low_delay = 0;
01562 
01563     if ((ret = MPV_common_init(s)) < 0)
01564         return ret;
01565 
01566     ff_h264_pred_init(&r->h, CODEC_ID_RV40, 8, 1);
01567 
01568 #if CONFIG_RV30_DECODER
01569     if (avctx->codec_id == CODEC_ID_RV30)
01570         ff_rv30dsp_init(&r->rdsp, &r->s.dsp);
01571 #endif
01572 #if CONFIG_RV40_DECODER
01573     if (avctx->codec_id == CODEC_ID_RV40)
01574         ff_rv40dsp_init(&r->rdsp, &r->s.dsp);
01575 #endif
01576 
01577     if ((ret = rv34_decoder_alloc(r)) < 0)
01578         return ret;
01579 
01580     if(!intra_vlcs[0].cbppattern[0].bits)
01581         rv34_init_tables();
01582 
01583     return 0;
01584 }
01585 
01586 int ff_rv34_decode_init_thread_copy(AVCodecContext *avctx)
01587 {
01588     int err;
01589     RV34DecContext *r = avctx->priv_data;
01590 
01591     r->s.avctx = avctx;
01592 
01593     if (avctx->internal->is_copy) {
01594         r->tmp_b_block_base = NULL;
01595         if ((err = MPV_common_init(&r->s)) < 0)
01596             return err;
01597         if ((err = rv34_decoder_alloc(r)) < 0)
01598             return err;
01599     }
01600     return 0;
01601 }
01602 
01603 int ff_rv34_decode_update_thread_context(AVCodecContext *dst, const AVCodecContext *src)
01604 {
01605     RV34DecContext *r = dst->priv_data, *r1 = src->priv_data;
01606     MpegEncContext * const s = &r->s, * const s1 = &r1->s;
01607     int err;
01608 
01609     if (dst == src || !s1->context_initialized)
01610         return 0;
01611 
01612     if (s->height != s1->height || s->width != s1->width) {
01613         MPV_common_end(s);
01614         s->height = s1->height;
01615         s->width  = s1->width;
01616         if ((err = MPV_common_init(s)) < 0)
01617             return err;
01618         if ((err = rv34_decoder_realloc(r)) < 0)
01619             return err;
01620     }
01621 
01622     if ((err = ff_mpeg_update_thread_context(dst, src)))
01623         return err;
01624 
01625     r->cur_pts  = r1->cur_pts;
01626     r->last_pts = r1->last_pts;
01627     r->next_pts = r1->next_pts;
01628 
01629     memset(&r->si, 0, sizeof(r->si));
01630 
01631     /* necessary since it is it the condition checked for in decode_slice
01632      * to call MPV_frame_start. cmp. comment at the end of decode_frame */
01633     s->current_picture_ptr = NULL;
01634 
01635     return 0;
01636 }
01637 
01638 static int get_slice_offset(AVCodecContext *avctx, const uint8_t *buf, int n)
01639 {
01640     if(avctx->slice_count) return avctx->slice_offset[n];
01641     else                   return AV_RL32(buf + n*8 - 4) == 1 ? AV_RL32(buf + n*8) :  AV_RB32(buf + n*8);
01642 }
01643 
01644 int ff_rv34_decode_frame(AVCodecContext *avctx,
01645                             void *data, int *data_size,
01646                             AVPacket *avpkt)
01647 {
01648     const uint8_t *buf = avpkt->data;
01649     int buf_size = avpkt->size;
01650     RV34DecContext *r = avctx->priv_data;
01651     MpegEncContext *s = &r->s;
01652     AVFrame *pict = data;
01653     SliceInfo si;
01654     int i;
01655     int slice_count;
01656     const uint8_t *slices_hdr = NULL;
01657     int last = 0;
01658 
01659     /* no supplementary picture */
01660     if (buf_size == 0) {
01661         /* special case for last picture */
01662         if (s->low_delay==0 && s->next_picture_ptr) {
01663             *pict = *(AVFrame*)s->next_picture_ptr;
01664             s->next_picture_ptr = NULL;
01665 
01666             *data_size = sizeof(AVFrame);
01667         }
01668         return 0;
01669     }
01670 
01671     if(!avctx->slice_count){
01672         slice_count = (*buf++) + 1;
01673         slices_hdr = buf + 4;
01674         buf += 8 * slice_count;
01675         buf_size -= 1 + 8 * slice_count;
01676     }else
01677         slice_count = avctx->slice_count;
01678 
01679     //parse first slice header to check whether this frame can be decoded
01680     if(get_slice_offset(avctx, slices_hdr, 0) < 0 ||
01681        get_slice_offset(avctx, slices_hdr, 0) > buf_size){
01682         av_log(avctx, AV_LOG_ERROR, "Slice offset is invalid\n");
01683         return -1;
01684     }
01685     init_get_bits(&s->gb, buf+get_slice_offset(avctx, slices_hdr, 0), (buf_size-get_slice_offset(avctx, slices_hdr, 0))*8);
01686     if(r->parse_slice_header(r, &r->s.gb, &si) < 0 || si.start){
01687         av_log(avctx, AV_LOG_ERROR, "First slice header is incorrect\n");
01688         return -1;
01689     }
01690     if ((!s->last_picture_ptr || !s->last_picture_ptr->f.data[0]) && si.type == AV_PICTURE_TYPE_B)
01691         return -1;
01692     if(   (avctx->skip_frame >= AVDISCARD_NONREF && si.type==AV_PICTURE_TYPE_B)
01693        || (avctx->skip_frame >= AVDISCARD_NONKEY && si.type!=AV_PICTURE_TYPE_I)
01694        ||  avctx->skip_frame >= AVDISCARD_ALL)
01695         return avpkt->size;
01696 
01697     for(i = 0; i < slice_count; i++){
01698         int offset = get_slice_offset(avctx, slices_hdr, i);
01699         int size;
01700         if(i+1 == slice_count)
01701             size = buf_size - offset;
01702         else
01703             size = get_slice_offset(avctx, slices_hdr, i+1) - offset;
01704 
01705         if(offset < 0 || offset > buf_size){
01706             av_log(avctx, AV_LOG_ERROR, "Slice offset is invalid\n");
01707             break;
01708         }
01709 
01710         r->si.end = s->mb_width * s->mb_height;
01711         if(i+1 < slice_count){
01712             if (get_slice_offset(avctx, slices_hdr, i+1) < 0 ||
01713                 get_slice_offset(avctx, slices_hdr, i+1) > buf_size) {
01714                 av_log(avctx, AV_LOG_ERROR, "Slice offset is invalid\n");
01715                 break;
01716             }
01717             init_get_bits(&s->gb, buf+get_slice_offset(avctx, slices_hdr, i+1), (buf_size-get_slice_offset(avctx, slices_hdr, i+1))*8);
01718             if(r->parse_slice_header(r, &r->s.gb, &si) < 0){
01719                 if(i+2 < slice_count)
01720                     size = get_slice_offset(avctx, slices_hdr, i+2) - offset;
01721                 else
01722                     size = buf_size - offset;
01723             }else
01724                 r->si.end = si.start;
01725         }
01726         if (size < 0 || size > buf_size - offset) {
01727             av_log(avctx, AV_LOG_ERROR, "Slice size is invalid\n");
01728             break;
01729         }
01730         last = rv34_decode_slice(r, r->si.end, buf + offset, size);
01731         s->mb_num_left = r->s.mb_x + r->s.mb_y*r->s.mb_width - r->si.start;
01732         if(last)
01733             break;
01734     }
01735 
01736     if(last && s->current_picture_ptr){
01737         if(r->loop_filter)
01738             r->loop_filter(r, s->mb_height - 1);
01739         ff_er_frame_end(s);
01740         MPV_frame_end(s);
01741 
01742         if (HAVE_THREADS && (s->avctx->active_thread_type & FF_THREAD_FRAME))
01743             ff_thread_report_progress(&s->current_picture_ptr->f, INT_MAX, 0);
01744 
01745         if (s->pict_type == AV_PICTURE_TYPE_B || s->low_delay) {
01746             *pict = *(AVFrame*)s->current_picture_ptr;
01747         } else if (s->last_picture_ptr != NULL) {
01748             *pict = *(AVFrame*)s->last_picture_ptr;
01749         }
01750 
01751         if(s->last_picture_ptr || s->low_delay){
01752             *data_size = sizeof(AVFrame);
01753             ff_print_debug_info(s, pict);
01754         }
01755         s->current_picture_ptr = NULL; //so we can detect if frame_end wasnt called (find some nicer solution...)
01756     }
01757     return avpkt->size;
01758 }
01759 
01760 av_cold int ff_rv34_decode_end(AVCodecContext *avctx)
01761 {
01762     RV34DecContext *r = avctx->priv_data;
01763 
01764     MPV_common_end(&r->s);
01765     rv34_decoder_free(r);
01766 
01767     return 0;
01768 }