Home | History | Annotate | Download | only in encoder
      1 /*
      2  *  Copyright (c) 2010 The WebM project authors. All Rights Reserved.
      3  *
      4  *  Use of this source code is governed by a BSD-style license
      5  *  that can be found in the LICENSE file in the root of the source
      6  *  tree. An additional intellectual property rights grant can be found
      7  *  in the file PATENTS.  All contributing project authors may
      8  *  be found in the AUTHORS file in the root of the source tree.
      9  */
     10 
     11 
     12 #include "vpx_ports/config.h"
     13 #include "encodemb.h"
     14 #include "encodemv.h"
     15 #include "common.h"
     16 #include "onyx_int.h"
     17 #include "extend.h"
     18 #include "entropymode.h"
     19 #include "quant_common.h"
     20 #include "segmentation.h"
     21 #include "setupintrarecon.h"
     22 #include "encodeintra.h"
     23 #include "reconinter.h"
     24 #include "rdopt.h"
     25 #include "pickinter.h"
     26 #include "findnearmv.h"
     27 #include "reconintra.h"
     28 #include <stdio.h>
     29 #include <limits.h>
     30 #include "subpixel.h"
     31 #include "vpx_ports/vpx_timer.h"
     32 
     33 #if CONFIG_RUNTIME_CPU_DETECT
     34 #define RTCD(x)     &cpi->common.rtcd.x
     35 #define IF_RTCD(x)  (x)
     36 #else
     37 #define RTCD(x)     NULL
     38 #define IF_RTCD(x)  NULL
     39 #endif
     40 extern void vp8_stuff_mb(VP8_COMP *cpi, MACROBLOCKD *x, TOKENEXTRA **t) ;
     41 
     42 extern void vp8cx_initialize_me_consts(VP8_COMP *cpi, int QIndex);
     43 extern void vp8_auto_select_speed(VP8_COMP *cpi);
     44 extern void vp8cx_init_mbrthread_data(VP8_COMP *cpi,
     45                                       MACROBLOCK *x,
     46                                       MB_ROW_COMP *mbr_ei,
     47                                       int mb_row,
     48                                       int count);
     49 void vp8_build_block_offsets(MACROBLOCK *x);
     50 void vp8_setup_block_ptrs(MACROBLOCK *x);
     51 int vp8cx_encode_inter_macroblock(VP8_COMP *cpi, MACROBLOCK *x, TOKENEXTRA **t, int recon_yoffset, int recon_uvoffset);
     52 int vp8cx_encode_intra_macro_block(VP8_COMP *cpi, MACROBLOCK *x, TOKENEXTRA **t);
     53 
     54 #ifdef MODE_STATS
     55 unsigned int inter_y_modes[10] = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0};
     56 unsigned int inter_uv_modes[4] = {0, 0, 0, 0};
     57 unsigned int inter_b_modes[15]  = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0};
     58 unsigned int y_modes[5]   = {0, 0, 0, 0, 0};
     59 unsigned int uv_modes[4]  = {0, 0, 0, 0};
     60 unsigned int b_modes[14]  = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0};
     61 #endif
     62 
     63 static const int qrounding_factors[129] =
     64 {
     65     56, 56, 56, 56, 48, 48, 56, 56,
     66     48, 48, 48, 48, 48, 48, 48, 48,
     67     48, 48, 48, 48, 48, 48, 48, 48,
     68     48, 48, 48, 48, 48, 48, 48, 48,
     69     48, 48, 48, 48, 48, 48, 48, 48,
     70     48, 48, 48, 48, 48, 48, 48, 48,
     71     48, 48, 48, 48, 48, 48, 48, 48,
     72     48, 48, 48, 48, 48, 48, 48, 48,
     73     48, 48, 48, 48, 48, 48, 48, 48,
     74     48, 48, 48, 48, 48, 48, 48, 48,
     75     48, 48, 48, 48, 48, 48, 48, 48,
     76     48, 48, 48, 48, 48, 48, 48, 48,
     77     48, 48, 48, 48, 48, 48, 48, 48,
     78     48, 48, 48, 48, 48, 48, 48, 48,
     79     48, 48, 48, 48, 48, 48, 48, 48,
     80     48, 48, 48, 48, 48, 48, 48, 48,
     81     48,
     82 };
     83 
     84 static const int qzbin_factors[129] =
     85 {
     86     72, 72, 72, 72, 80, 80, 72, 72,
     87     80, 80, 80, 80, 80, 80, 80, 80,
     88     80, 80, 80, 80, 80, 80, 80, 80,
     89     80, 80, 80, 80, 80, 80, 80, 80,
     90     80, 80, 80, 80, 80, 80, 80, 80,
     91     80, 80, 80, 80, 80, 80, 80, 80,
     92     80, 80, 80, 80, 80, 80, 80, 80,
     93     80, 80, 80, 80, 80, 80, 80, 80,
     94     80, 80, 80, 80, 80, 80, 80, 80,
     95     80, 80, 80, 80, 80, 80, 80, 80,
     96     80, 80, 80, 80, 80, 80, 80, 80,
     97     80, 80, 80, 80, 80, 80, 80, 80,
     98     80, 80, 80, 80, 80, 80, 80, 80,
     99     80, 80, 80, 80, 80, 80, 80, 80,
    100     80, 80, 80, 80, 80, 80, 80, 80,
    101     80, 80, 80, 80, 80, 80, 80, 80,
    102     80,
    103 };
    104 
    105 static const int qrounding_factors_y2[129] =
    106 {
    107     56, 56, 56, 56, 48, 48, 56, 56,
    108     48, 48, 48, 48, 48, 48, 48, 48,
    109     48, 48, 48, 48, 48, 48, 48, 48,
    110     48, 48, 48, 48, 48, 48, 48, 48,
    111     48, 48, 48, 48, 48, 48, 48, 48,
    112     48, 48, 48, 48, 48, 48, 48, 48,
    113     48, 48, 48, 48, 48, 48, 48, 48,
    114     48, 48, 48, 48, 48, 48, 48, 48,
    115     48, 48, 48, 48, 48, 48, 48, 48,
    116     48, 48, 48, 48, 48, 48, 48, 48,
    117     48, 48, 48, 48, 48, 48, 48, 48,
    118     48, 48, 48, 48, 48, 48, 48, 48,
    119     48, 48, 48, 48, 48, 48, 48, 48,
    120     48, 48, 48, 48, 48, 48, 48, 48,
    121     48, 48, 48, 48, 48, 48, 48, 48,
    122     48, 48, 48, 48, 48, 48, 48, 48,
    123     48,
    124 };
    125 
    126 static const int qzbin_factors_y2[129] =
    127 {
    128     72, 72, 72, 72, 80, 80, 72, 72,
    129     80, 80, 80, 80, 80, 80, 80, 80,
    130     80, 80, 80, 80, 80, 80, 80, 80,
    131     80, 80, 80, 80, 80, 80, 80, 80,
    132     80, 80, 80, 80, 80, 80, 80, 80,
    133     80, 80, 80, 80, 80, 80, 80, 80,
    134     80, 80, 80, 80, 80, 80, 80, 80,
    135     80, 80, 80, 80, 80, 80, 80, 80,
    136     80, 80, 80, 80, 80, 80, 80, 80,
    137     80, 80, 80, 80, 80, 80, 80, 80,
    138     80, 80, 80, 80, 80, 80, 80, 80,
    139     80, 80, 80, 80, 80, 80, 80, 80,
    140     80, 80, 80, 80, 80, 80, 80, 80,
    141     80, 80, 80, 80, 80, 80, 80, 80,
    142     80, 80, 80, 80, 80, 80, 80, 80,
    143     80, 80, 80, 80, 80, 80, 80, 80,
    144     80,
    145 };
    146 
    147 //#define EXACT_QUANT
    148 #ifdef EXACT_QUANT
    149 static void vp8cx_invert_quant(short *quant, short *shift, short d)
    150 {
    151     unsigned t;
    152     int l;
    153     t = d;
    154     for(l = 0; t > 1; l++)
    155         t>>=1;
    156     t = 1 + (1<<(16+l))/d;
    157     *quant = (short)(t - (1<<16));
    158     *shift = l;
    159 }
    160 
    161 void vp8cx_init_quantizer(VP8_COMP *cpi)
    162 {
    163     int r, c;
    164     int i;
    165     int quant_val;
    166     int Q;
    167 
    168     int zbin_boost[16] = {0, 0, 8, 10, 12, 14, 16, 20, 24, 28, 32, 36, 40, 44, 44, 44};
    169 
    170     for (Q = 0; Q < QINDEX_RANGE; Q++)
    171     {
    172         // dc values
    173         quant_val = vp8_dc_quant(Q, cpi->common.y1dc_delta_q);
    174         vp8cx_invert_quant(cpi->Y1quant[Q][0] + 0,
    175                            cpi->Y1quant_shift[Q][0] + 0, quant_val);
    176         cpi->Y1zbin[Q][0][0] = ((qzbin_factors[Q] * quant_val) + 64) >> 7;
    177         cpi->Y1round[Q][0][0] = (qrounding_factors[Q] * quant_val) >> 7;
    178         cpi->common.Y1dequant[Q][0][0] = quant_val;
    179         cpi->zrun_zbin_boost_y1[Q][0] = (quant_val * zbin_boost[0]) >> 7;
    180 
    181         quant_val = vp8_dc2quant(Q, cpi->common.y2dc_delta_q);
    182         vp8cx_invert_quant(cpi->Y2quant[Q][0] + 0,
    183                            cpi->Y2quant_shift[Q][0] + 0, quant_val);
    184         cpi->Y2zbin[Q][0][0] = ((qzbin_factors_y2[Q] * quant_val) + 64) >> 7;
    185         cpi->Y2round[Q][0][0] = (qrounding_factors_y2[Q] * quant_val) >> 7;
    186         cpi->common.Y2dequant[Q][0][0] = quant_val;
    187         cpi->zrun_zbin_boost_y2[Q][0] = (quant_val * zbin_boost[0]) >> 7;
    188 
    189         quant_val = vp8_dc_uv_quant(Q, cpi->common.uvdc_delta_q);
    190         vp8cx_invert_quant(cpi->UVquant[Q][0] + 0,
    191                            cpi->UVquant_shift[Q][0] + 0, quant_val);
    192         cpi->UVzbin[Q][0][0] = ((qzbin_factors[Q] * quant_val) + 64) >> 7;;
    193         cpi->UVround[Q][0][0] = (qrounding_factors[Q] * quant_val) >> 7;
    194         cpi->common.UVdequant[Q][0][0] = quant_val;
    195         cpi->zrun_zbin_boost_uv[Q][0] = (quant_val * zbin_boost[0]) >> 7;
    196 
    197         // all the ac values = ;
    198         for (i = 1; i < 16; i++)
    199         {
    200             int rc = vp8_default_zig_zag1d[i];
    201             r = (rc >> 2);
    202             c = (rc & 3);
    203 
    204             quant_val = vp8_ac_yquant(Q);
    205             vp8cx_invert_quant(cpi->Y1quant[Q][r] + c,
    206                                cpi->Y1quant_shift[Q][r] + c, quant_val);
    207             cpi->Y1zbin[Q][r][c] = ((qzbin_factors[Q] * quant_val) + 64) >> 7;
    208             cpi->Y1round[Q][r][c] = (qrounding_factors[Q] * quant_val) >> 7;
    209             cpi->common.Y1dequant[Q][r][c] = quant_val;
    210             cpi->zrun_zbin_boost_y1[Q][i] = (quant_val * zbin_boost[i]) >> 7;
    211 
    212             quant_val = vp8_ac2quant(Q, cpi->common.y2ac_delta_q);
    213             vp8cx_invert_quant(cpi->Y2quant[Q][r] + c,
    214                                cpi->Y2quant_shift[Q][r] + c, quant_val);
    215             cpi->Y2zbin[Q][r][c] = ((qzbin_factors_y2[Q] * quant_val) + 64) >> 7;
    216             cpi->Y2round[Q][r][c] = (qrounding_factors_y2[Q] * quant_val) >> 7;
    217             cpi->common.Y2dequant[Q][r][c] = quant_val;
    218             cpi->zrun_zbin_boost_y2[Q][i] = (quant_val * zbin_boost[i]) >> 7;
    219 
    220             quant_val = vp8_ac_uv_quant(Q, cpi->common.uvac_delta_q);
    221             vp8cx_invert_quant(cpi->UVquant[Q][r] + c,
    222                                cpi->UVquant_shift[Q][r] + c, quant_val);
    223             cpi->UVzbin[Q][r][c] = ((qzbin_factors[Q] * quant_val) + 64) >> 7;
    224             cpi->UVround[Q][r][c] = (qrounding_factors[Q] * quant_val) >> 7;
    225             cpi->common.UVdequant[Q][r][c] = quant_val;
    226             cpi->zrun_zbin_boost_uv[Q][i] = (quant_val * zbin_boost[i]) >> 7;
    227         }
    228     }
    229 }
    230 #else
    231 void vp8cx_init_quantizer(VP8_COMP *cpi)
    232 {
    233     int r, c;
    234     int i;
    235     int quant_val;
    236     int Q;
    237 
    238     int zbin_boost[16] = {0, 0, 8, 10, 12, 14, 16, 20, 24, 28, 32, 36, 40, 44, 44, 44};
    239 
    240     for (Q = 0; Q < QINDEX_RANGE; Q++)
    241     {
    242         // dc values
    243         quant_val = vp8_dc_quant(Q, cpi->common.y1dc_delta_q);
    244         cpi->Y1quant[Q][0][0] = (1 << 16) / quant_val;
    245         cpi->Y1zbin[Q][0][0] = ((qzbin_factors[Q] * quant_val) + 64) >> 7;
    246         cpi->Y1round[Q][0][0] = (qrounding_factors[Q] * quant_val) >> 7;
    247         cpi->common.Y1dequant[Q][0][0] = quant_val;
    248         cpi->zrun_zbin_boost_y1[Q][0] = (quant_val * zbin_boost[0]) >> 7;
    249 
    250         quant_val = vp8_dc2quant(Q, cpi->common.y2dc_delta_q);
    251         cpi->Y2quant[Q][0][0] = (1 << 16) / quant_val;
    252         cpi->Y2zbin[Q][0][0] = ((qzbin_factors_y2[Q] * quant_val) + 64) >> 7;
    253         cpi->Y2round[Q][0][0] = (qrounding_factors_y2[Q] * quant_val) >> 7;
    254         cpi->common.Y2dequant[Q][0][0] = quant_val;
    255         cpi->zrun_zbin_boost_y2[Q][0] = (quant_val * zbin_boost[0]) >> 7;
    256 
    257         quant_val = vp8_dc_uv_quant(Q, cpi->common.uvdc_delta_q);
    258         cpi->UVquant[Q][0][0] = (1 << 16) / quant_val;
    259         cpi->UVzbin[Q][0][0] = ((qzbin_factors[Q] * quant_val) + 64) >> 7;;
    260         cpi->UVround[Q][0][0] = (qrounding_factors[Q] * quant_val) >> 7;
    261         cpi->common.UVdequant[Q][0][0] = quant_val;
    262         cpi->zrun_zbin_boost_uv[Q][0] = (quant_val * zbin_boost[0]) >> 7;
    263 
    264         // all the ac values = ;
    265         for (i = 1; i < 16; i++)
    266         {
    267             int rc = vp8_default_zig_zag1d[i];
    268             r = (rc >> 2);
    269             c = (rc & 3);
    270 
    271             quant_val = vp8_ac_yquant(Q);
    272             cpi->Y1quant[Q][r][c] = (1 << 16) / quant_val;
    273             cpi->Y1zbin[Q][r][c] = ((qzbin_factors[Q] * quant_val) + 64) >> 7;
    274             cpi->Y1round[Q][r][c] = (qrounding_factors[Q] * quant_val) >> 7;
    275             cpi->common.Y1dequant[Q][r][c] = quant_val;
    276             cpi->zrun_zbin_boost_y1[Q][i] = (quant_val * zbin_boost[i]) >> 7;
    277 
    278             quant_val = vp8_ac2quant(Q, cpi->common.y2ac_delta_q);
    279             cpi->Y2quant[Q][r][c] = (1 << 16) / quant_val;
    280             cpi->Y2zbin[Q][r][c] = ((qzbin_factors_y2[Q] * quant_val) + 64) >> 7;
    281             cpi->Y2round[Q][r][c] = (qrounding_factors_y2[Q] * quant_val) >> 7;
    282             cpi->common.Y2dequant[Q][r][c] = quant_val;
    283             cpi->zrun_zbin_boost_y2[Q][i] = (quant_val * zbin_boost[i]) >> 7;
    284 
    285             quant_val = vp8_ac_uv_quant(Q, cpi->common.uvac_delta_q);
    286             cpi->UVquant[Q][r][c] = (1 << 16) / quant_val;
    287             cpi->UVzbin[Q][r][c] = ((qzbin_factors[Q] * quant_val) + 64) >> 7;
    288             cpi->UVround[Q][r][c] = (qrounding_factors[Q] * quant_val) >> 7;
    289             cpi->common.UVdequant[Q][r][c] = quant_val;
    290             cpi->zrun_zbin_boost_uv[Q][i] = (quant_val * zbin_boost[i]) >> 7;
    291         }
    292     }
    293 }
    294 #endif
    295 void vp8cx_mb_init_quantizer(VP8_COMP *cpi, MACROBLOCK *x)
    296 {
    297     int i;
    298     int QIndex;
    299     MACROBLOCKD *xd = &x->e_mbd;
    300     int zbin_extra;
    301 
    302     // Select the baseline MB Q index.
    303     if (xd->segmentation_enabled)
    304     {
    305         // Abs Value
    306         if (xd->mb_segement_abs_delta == SEGMENT_ABSDATA)
    307 
    308             QIndex = xd->segment_feature_data[MB_LVL_ALT_Q][xd->mode_info_context->mbmi.segment_id];
    309         // Delta Value
    310         else
    311         {
    312             QIndex = cpi->common.base_qindex + xd->segment_feature_data[MB_LVL_ALT_Q][xd->mode_info_context->mbmi.segment_id];
    313             QIndex = (QIndex >= 0) ? ((QIndex <= MAXQ) ? QIndex : MAXQ) : 0;    // Clamp to valid range
    314         }
    315     }
    316     else
    317         QIndex = cpi->common.base_qindex;
    318 
    319     // Y
    320     zbin_extra = (cpi->common.Y1dequant[QIndex][0][1] * (cpi->zbin_over_quant + cpi->zbin_mode_boost)) >> 7;
    321 
    322     for (i = 0; i < 16; i++)
    323     {
    324         x->block[i].quant = cpi->Y1quant[QIndex];
    325         x->block[i].quant_shift = cpi->Y1quant_shift[QIndex];
    326         x->block[i].zbin = cpi->Y1zbin[QIndex];
    327         x->block[i].round = cpi->Y1round[QIndex];
    328         x->e_mbd.block[i].dequant = cpi->common.Y1dequant[QIndex];
    329         x->block[i].zrun_zbin_boost = cpi->zrun_zbin_boost_y1[QIndex];
    330         x->block[i].zbin_extra = (short)zbin_extra;
    331     }
    332 
    333     // UV
    334     zbin_extra = (cpi->common.UVdequant[QIndex][0][1] * (cpi->zbin_over_quant + cpi->zbin_mode_boost)) >> 7;
    335 
    336     for (i = 16; i < 24; i++)
    337     {
    338         x->block[i].quant = cpi->UVquant[QIndex];
    339         x->block[i].quant_shift = cpi->UVquant_shift[QIndex];
    340         x->block[i].zbin = cpi->UVzbin[QIndex];
    341         x->block[i].round = cpi->UVround[QIndex];
    342         x->e_mbd.block[i].dequant = cpi->common.UVdequant[QIndex];
    343         x->block[i].zrun_zbin_boost = cpi->zrun_zbin_boost_uv[QIndex];
    344         x->block[i].zbin_extra = (short)zbin_extra;
    345     }
    346 
    347     // Y2
    348     zbin_extra = (cpi->common.Y2dequant[QIndex][0][1] * ((cpi->zbin_over_quant / 2) + cpi->zbin_mode_boost)) >> 7;
    349     x->block[24].quant = cpi->Y2quant[QIndex];
    350     x->block[24].quant_shift = cpi->Y2quant_shift[QIndex];
    351     x->block[24].zbin = cpi->Y2zbin[QIndex];
    352     x->block[24].round = cpi->Y2round[QIndex];
    353     x->e_mbd.block[24].dequant = cpi->common.Y2dequant[QIndex];
    354     x->block[24].zrun_zbin_boost = cpi->zrun_zbin_boost_y2[QIndex];
    355     x->block[24].zbin_extra = (short)zbin_extra;
    356 }
    357 
    358 void vp8cx_frame_init_quantizer(VP8_COMP *cpi)
    359 {
    360     // vp8cx_init_quantizer() is first called in vp8_create_compressor(). A check is added here so that vp8cx_init_quantizer() is only called
    361     // when these values are not all zero.
    362     if (cpi->common.y1dc_delta_q | cpi->common.y2dc_delta_q | cpi->common.uvdc_delta_q | cpi->common.y2ac_delta_q | cpi->common.uvac_delta_q)
    363     {
    364         vp8cx_init_quantizer(cpi);
    365     }
    366 
    367     // MB level quantizer setup
    368     vp8cx_mb_init_quantizer(cpi, &cpi->mb);
    369 }
    370 
    371 
    372 
    373 static
    374 void encode_mb_row(VP8_COMP *cpi,
    375                    VP8_COMMON *cm,
    376                    int mb_row,
    377                    MACROBLOCK  *x,
    378                    MACROBLOCKD *xd,
    379                    TOKENEXTRA **tp,
    380                    int *segment_counts,
    381                    int *totalrate)
    382 {
    383     int i;
    384     int recon_yoffset, recon_uvoffset;
    385     int mb_col;
    386     int ref_fb_idx = cm->lst_fb_idx;
    387     int dst_fb_idx = cm->new_fb_idx;
    388     int recon_y_stride = cm->yv12_fb[ref_fb_idx].y_stride;
    389     int recon_uv_stride = cm->yv12_fb[ref_fb_idx].uv_stride;
    390     int seg_map_index = (mb_row * cpi->common.mb_cols);
    391 
    392 
    393     // reset above block coeffs
    394     xd->above_context = cm->above_context;
    395 
    396     xd->up_available = (mb_row != 0);
    397     recon_yoffset = (mb_row * recon_y_stride * 16);
    398     recon_uvoffset = (mb_row * recon_uv_stride * 8);
    399 
    400     cpi->tplist[mb_row].start = *tp;
    401     //printf("Main mb_row = %d\n", mb_row);
    402 
    403     // for each macroblock col in image
    404     for (mb_col = 0; mb_col < cm->mb_cols; mb_col++)
    405     {
    406         // Distance of Mb to the various image edges.
    407         // These specified to 8th pel as they are always compared to values that are in 1/8th pel units
    408         xd->mb_to_left_edge = -((mb_col * 16) << 3);
    409         xd->mb_to_right_edge = ((cm->mb_cols - 1 - mb_col) * 16) << 3;
    410         xd->mb_to_top_edge = -((mb_row * 16) << 3);
    411         xd->mb_to_bottom_edge = ((cm->mb_rows - 1 - mb_row) * 16) << 3;
    412 
    413         // Set up limit values for motion vectors used to prevent them extending outside the UMV borders
    414         x->mv_col_min = -((mb_col * 16) + (VP8BORDERINPIXELS - 16));
    415         x->mv_col_max = ((cm->mb_cols - 1 - mb_col) * 16) + (VP8BORDERINPIXELS - 16);
    416         x->mv_row_min = -((mb_row * 16) + (VP8BORDERINPIXELS - 16));
    417         x->mv_row_max = ((cm->mb_rows - 1 - mb_row) * 16) + (VP8BORDERINPIXELS - 16);
    418 
    419         xd->dst.y_buffer = cm->yv12_fb[dst_fb_idx].y_buffer + recon_yoffset;
    420         xd->dst.u_buffer = cm->yv12_fb[dst_fb_idx].u_buffer + recon_uvoffset;
    421         xd->dst.v_buffer = cm->yv12_fb[dst_fb_idx].v_buffer + recon_uvoffset;
    422         xd->left_available = (mb_col != 0);
    423 
    424         // Is segmentation enabled
    425         // MB level adjutment to quantizer
    426         if (xd->segmentation_enabled)
    427         {
    428             // Code to set segment id in xd->mbmi.segment_id for current MB (with range checking)
    429             if (cpi->segmentation_map[seg_map_index+mb_col] <= 3)
    430                 xd->mode_info_context->mbmi.segment_id = cpi->segmentation_map[seg_map_index+mb_col];
    431             else
    432                 xd->mode_info_context->mbmi.segment_id = 0;
    433 
    434             vp8cx_mb_init_quantizer(cpi, x);
    435         }
    436         else
    437             xd->mode_info_context->mbmi.segment_id = 0;         // Set to Segment 0 by default
    438 
    439         x->active_ptr = cpi->active_map + seg_map_index + mb_col;
    440 
    441         if (cm->frame_type == KEY_FRAME)
    442         {
    443             *totalrate += vp8cx_encode_intra_macro_block(cpi, x, tp);
    444 #ifdef MODE_STATS
    445             y_modes[xd->mbmi.mode] ++;
    446 #endif
    447         }
    448         else
    449         {
    450             *totalrate += vp8cx_encode_inter_macroblock(cpi, x, tp, recon_yoffset, recon_uvoffset);
    451 
    452 #ifdef MODE_STATS
    453             inter_y_modes[xd->mbmi.mode] ++;
    454 
    455             if (xd->mbmi.mode == SPLITMV)
    456             {
    457                 int b;
    458 
    459                 for (b = 0; b < xd->mbmi.partition_count; b++)
    460                 {
    461                     inter_b_modes[x->partition->bmi[b].mode] ++;
    462                 }
    463             }
    464 
    465 #endif
    466 
    467             // Count of last ref frame 0,0 useage
    468             if ((xd->mode_info_context->mbmi.mode == ZEROMV) && (xd->mode_info_context->mbmi.ref_frame == LAST_FRAME))
    469                 cpi->inter_zz_count ++;
    470 
    471             // Special case code for cyclic refresh
    472             // If cyclic update enabled then copy xd->mbmi.segment_id; (which may have been updated based on mode
    473             // during vp8cx_encode_inter_macroblock()) back into the global sgmentation map
    474             if (cpi->cyclic_refresh_mode_enabled && xd->segmentation_enabled)
    475             {
    476                 cpi->segmentation_map[seg_map_index+mb_col] = xd->mode_info_context->mbmi.segment_id;
    477 
    478                 // If the block has been refreshed mark it as clean (the magnitude of the -ve influences how long it will be before we consider another refresh):
    479                 // Else if it was coded (last frame 0,0) and has not already been refreshed then mark it as a candidate for cleanup next time (marked 0)
    480                 // else mark it as dirty (1).
    481                 if (xd->mode_info_context->mbmi.segment_id)
    482                     cpi->cyclic_refresh_map[seg_map_index+mb_col] = -1;
    483                 else if ((xd->mode_info_context->mbmi.mode == ZEROMV) && (xd->mode_info_context->mbmi.ref_frame == LAST_FRAME))
    484                 {
    485                     if (cpi->cyclic_refresh_map[seg_map_index+mb_col] == 1)
    486                         cpi->cyclic_refresh_map[seg_map_index+mb_col] = 0;
    487                 }
    488                 else
    489                     cpi->cyclic_refresh_map[seg_map_index+mb_col] = 1;
    490 
    491             }
    492         }
    493 
    494         cpi->tplist[mb_row].stop = *tp;
    495 
    496         x->gf_active_ptr++;      // Increment pointer into gf useage flags structure for next mb
    497 
    498         for (i = 0; i < 16; i++)
    499             vpx_memcpy(&xd->mode_info_context->bmi[i], &xd->block[i].bmi, sizeof(xd->block[i].bmi));
    500 
    501         // adjust to the next column of macroblocks
    502         x->src.y_buffer += 16;
    503         x->src.u_buffer += 8;
    504         x->src.v_buffer += 8;
    505 
    506         recon_yoffset += 16;
    507         recon_uvoffset += 8;
    508 
    509         // Keep track of segment useage
    510         segment_counts[xd->mode_info_context->mbmi.segment_id] ++;
    511 
    512         // skip to next mb
    513         xd->mode_info_context++;
    514         x->partition_info++;
    515 
    516         xd->above_context++;
    517         cpi->current_mb_col_main = mb_col;
    518     }
    519 
    520     //extend the recon for intra prediction
    521     vp8_extend_mb_row(
    522         &cm->yv12_fb[dst_fb_idx],
    523         xd->dst.y_buffer + 16,
    524         xd->dst.u_buffer + 8,
    525         xd->dst.v_buffer + 8);
    526 
    527     // this is to account for the border
    528     xd->mode_info_context++;
    529     x->partition_info++;
    530 }
    531 
    532 
    533 
    534 
    535 
    536 void vp8_encode_frame(VP8_COMP *cpi)
    537 {
    538     int mb_row;
    539     MACROBLOCK *const x = & cpi->mb;
    540     VP8_COMMON *const cm = & cpi->common;
    541     MACROBLOCKD *const xd = & x->e_mbd;
    542 
    543     int i;
    544     TOKENEXTRA *tp = cpi->tok;
    545     int segment_counts[MAX_MB_SEGMENTS];
    546     int totalrate;
    547 
    548     if (cm->frame_type != KEY_FRAME)
    549     {
    550         if (cm->mcomp_filter_type == SIXTAP)
    551         {
    552             xd->subpixel_predict     = SUBPIX_INVOKE(&cpi->common.rtcd.subpix, sixtap4x4);
    553             xd->subpixel_predict8x4      = SUBPIX_INVOKE(&cpi->common.rtcd.subpix, sixtap8x4);
    554             xd->subpixel_predict8x8      = SUBPIX_INVOKE(&cpi->common.rtcd.subpix, sixtap8x8);
    555             xd->subpixel_predict16x16    = SUBPIX_INVOKE(&cpi->common.rtcd.subpix, sixtap16x16);
    556         }
    557         else
    558         {
    559             xd->subpixel_predict     = SUBPIX_INVOKE(&cpi->common.rtcd.subpix, bilinear4x4);
    560             xd->subpixel_predict8x4      = SUBPIX_INVOKE(&cpi->common.rtcd.subpix, bilinear8x4);
    561             xd->subpixel_predict8x8      = SUBPIX_INVOKE(&cpi->common.rtcd.subpix, bilinear8x8);
    562             xd->subpixel_predict16x16    = SUBPIX_INVOKE(&cpi->common.rtcd.subpix, bilinear16x16);
    563         }
    564     }
    565 
    566     //else  // Key Frame
    567     //{
    568     // For key frames make sure the intra ref frame probability value
    569     // is set to "all intra"
    570     //cpi->prob_intra_coded = 255;
    571     //}
    572 
    573 
    574     x->gf_active_ptr = (signed char *)cpi->gf_active_flags;     // Point to base of GF active flags data structure
    575 
    576     x->vector_range = 32;
    577 
    578     // Count of MBs using the alternate Q if any
    579     cpi->alt_qcount = 0;
    580 
    581     // Reset frame count of inter 0,0 motion vector useage.
    582     cpi->inter_zz_count = 0;
    583 
    584     vpx_memset(segment_counts, 0, sizeof(segment_counts));
    585 
    586     cpi->prediction_error = 0;
    587     cpi->intra_error = 0;
    588     cpi->skip_true_count = 0;
    589     cpi->skip_false_count = 0;
    590 
    591 #if 0
    592     // Experimental code
    593     cpi->frame_distortion = 0;
    594     cpi->last_mb_distortion = 0;
    595 #endif
    596 
    597     totalrate = 0;
    598 
    599     x->partition_info = x->pi;
    600 
    601     xd->mode_info_context = cm->mi;
    602     xd->mode_info_stride = cm->mode_info_stride;
    603 
    604     xd->frame_type = cm->frame_type;
    605 
    606     xd->frames_since_golden = cm->frames_since_golden;
    607     xd->frames_till_alt_ref_frame = cm->frames_till_alt_ref_frame;
    608     vp8_zero(cpi->MVcount);
    609     // vp8_zero( Contexts)
    610     vp8_zero(cpi->coef_counts);
    611 
    612     // reset intra mode contexts
    613     if (cm->frame_type == KEY_FRAME)
    614         vp8_init_mbmode_probs(cm);
    615 
    616 
    617     vp8cx_frame_init_quantizer(cpi);
    618 
    619     if (cpi->compressor_speed == 2)
    620     {
    621         if (cpi->oxcf.cpu_used < 0)
    622             cpi->Speed = -(cpi->oxcf.cpu_used);
    623         else
    624             vp8_auto_select_speed(cpi);
    625     }
    626 
    627     vp8_initialize_rd_consts(cpi, vp8_dc_quant(cm->base_qindex, cm->y1dc_delta_q));
    628     //vp8_initialize_rd_consts( cpi, vp8_dc_quant(cpi->avg_frame_qindex, cm->y1dc_delta_q) );
    629     vp8cx_initialize_me_consts(cpi, cm->base_qindex);
    630     //vp8cx_initialize_me_consts( cpi, cpi->avg_frame_qindex);
    631 
    632     // Copy data over into macro block data sturctures.
    633 
    634     x->src = * cpi->Source;
    635     xd->pre = cm->yv12_fb[cm->lst_fb_idx];
    636     xd->dst = cm->yv12_fb[cm->new_fb_idx];
    637 
    638     // set up frame new frame for intra coded blocks
    639 
    640     vp8_setup_intra_recon(&cm->yv12_fb[cm->new_fb_idx]);
    641 
    642     vp8_build_block_offsets(x);
    643 
    644     vp8_setup_block_dptrs(&x->e_mbd);
    645 
    646     vp8_setup_block_ptrs(x);
    647 
    648     x->rddiv = cpi->RDDIV;
    649     x->rdmult = cpi->RDMULT;
    650 
    651 #if 0
    652     // Experimental rd code
    653     // 2 Pass - Possibly set Rdmult based on last frame distortion + this frame target bits or other metrics
    654     // such as cpi->rate_correction_factor that indicate relative complexity.
    655     /*if ( cpi->pass == 2 && (cpi->last_frame_distortion > 0) && (cpi->target_bits_per_mb > 0) )
    656     {
    657         //x->rdmult = ((cpi->last_frame_distortion * 256)/cpi->common.MBs)/ cpi->target_bits_per_mb;
    658         x->rdmult = (int)(cpi->RDMULT * cpi->rate_correction_factor);
    659     }
    660     else
    661         x->rdmult = cpi->RDMULT; */
    662     //x->rdmult = (int)(cpi->RDMULT * pow( (cpi->rate_correction_factor * 2.0), 0.75 ));
    663 #endif
    664 
    665     xd->mode_info_context->mbmi.mode = DC_PRED;
    666     xd->mode_info_context->mbmi.uv_mode = DC_PRED;
    667 
    668     xd->left_context = &cm->left_context;
    669 
    670     vp8_zero(cpi->count_mb_ref_frame_usage)
    671     vp8_zero(cpi->ymode_count)
    672     vp8_zero(cpi->uv_mode_count)
    673 
    674     x->mvc = cm->fc.mvc;
    675 
    676     vpx_memset(cm->above_context, 0, sizeof(ENTROPY_CONTEXT_PLANES) * cm->mb_cols);
    677 
    678     {
    679         struct vpx_usec_timer  emr_timer;
    680         vpx_usec_timer_start(&emr_timer);
    681 
    682         if (!cpi->b_multi_threaded)
    683         {
    684             // for each macroblock row in image
    685             for (mb_row = 0; mb_row < cm->mb_rows; mb_row++)
    686             {
    687 
    688                 vp8_zero(cm->left_context)
    689 
    690                 encode_mb_row(cpi, cm, mb_row, x, xd, &tp, segment_counts, &totalrate);
    691 
    692                 // adjust to the next row of mbs
    693                 x->src.y_buffer += 16 * x->src.y_stride - 16 * cm->mb_cols;
    694                 x->src.u_buffer += 8 * x->src.uv_stride - 8 * cm->mb_cols;
    695                 x->src.v_buffer += 8 * x->src.uv_stride - 8 * cm->mb_cols;
    696             }
    697 
    698             cpi->tok_count = tp - cpi->tok;
    699 
    700         }
    701         else
    702         {
    703 #if CONFIG_MULTITHREAD
    704             vp8cx_init_mbrthread_data(cpi, x, cpi->mb_row_ei, 1,  cpi->encoding_thread_count);
    705 
    706             for (mb_row = 0; mb_row < cm->mb_rows; mb_row += (cpi->encoding_thread_count + 1))
    707             {
    708                 int i;
    709                 cpi->current_mb_col_main = -1;
    710 
    711                 for (i = 0; i < cpi->encoding_thread_count; i++)
    712                 {
    713                     if ((mb_row + i + 1) >= cm->mb_rows)
    714                         break;
    715 
    716                     cpi->mb_row_ei[i].mb_row = mb_row + i + 1;
    717                     cpi->mb_row_ei[i].tp  = cpi->tok + (mb_row + i + 1) * (cm->mb_cols * 16 * 24);
    718                     cpi->mb_row_ei[i].current_mb_col = -1;
    719                     //SetEvent(cpi->h_event_mbrencoding[i]);
    720                     sem_post(&cpi->h_event_mbrencoding[i]);
    721                 }
    722 
    723                 vp8_zero(cm->left_context)
    724 
    725                 tp = cpi->tok + mb_row * (cm->mb_cols * 16 * 24);
    726 
    727                 encode_mb_row(cpi, cm, mb_row, x, xd, &tp, segment_counts, &totalrate);
    728 
    729                 // adjust to the next row of mbs
    730                 x->src.y_buffer += 16 * x->src.y_stride * (cpi->encoding_thread_count + 1) - 16 * cm->mb_cols;
    731                 x->src.u_buffer +=  8 * x->src.uv_stride * (cpi->encoding_thread_count + 1) - 8 * cm->mb_cols;
    732                 x->src.v_buffer +=  8 * x->src.uv_stride * (cpi->encoding_thread_count + 1) - 8 * cm->mb_cols;
    733 
    734                 xd->mode_info_context += xd->mode_info_stride * cpi->encoding_thread_count;
    735                 x->partition_info  += xd->mode_info_stride * cpi->encoding_thread_count;
    736 
    737                 if (mb_row < cm->mb_rows - 1)
    738                     //WaitForSingleObject(cpi->h_event_main, INFINITE);
    739                     sem_wait(&cpi->h_event_main);
    740             }
    741 
    742             /*
    743             for( ;mb_row<cm->mb_rows; mb_row ++)
    744             {
    745             vp8_zero( cm->left_context)
    746 
    747             tp = cpi->tok + mb_row * (cm->mb_cols * 16 * 24);
    748 
    749             encode_mb_row(cpi, cm, mb_row, x, xd, &tp, segment_counts, &totalrate);
    750             // adjust to the next row of mbs
    751             x->src.y_buffer += 16 * x->src.y_stride - 16 * cm->mb_cols;
    752             x->src.u_buffer +=  8 * x->src.uv_stride - 8 * cm->mb_cols;
    753             x->src.v_buffer +=  8 * x->src.uv_stride - 8 * cm->mb_cols;
    754 
    755             }
    756             */
    757             cpi->tok_count = 0;
    758 
    759             for (mb_row = 0; mb_row < cm->mb_rows; mb_row ++)
    760             {
    761                 cpi->tok_count += cpi->tplist[mb_row].stop - cpi->tplist[mb_row].start;
    762             }
    763 
    764             if (xd->segmentation_enabled)
    765             {
    766 
    767                 int i, j;
    768 
    769                 if (xd->segmentation_enabled)
    770                 {
    771 
    772                     for (i = 0; i < cpi->encoding_thread_count; i++)
    773                     {
    774                         for (j = 0; j < 4; j++)
    775                             segment_counts[j] += cpi->mb_row_ei[i].segment_counts[j];
    776                     }
    777                 }
    778 
    779             }
    780 
    781             for (i = 0; i < cpi->encoding_thread_count; i++)
    782             {
    783                 totalrate += cpi->mb_row_ei[i].totalrate;
    784             }
    785 
    786 #endif
    787 
    788         }
    789 
    790         vpx_usec_timer_mark(&emr_timer);
    791         cpi->time_encode_mb_row += vpx_usec_timer_elapsed(&emr_timer);
    792 
    793     }
    794 
    795 
    796     // Work out the segment probabilites if segmentation is enabled
    797     if (xd->segmentation_enabled)
    798     {
    799         int tot_count;
    800         int i;
    801 
    802         // Set to defaults
    803         vpx_memset(xd->mb_segment_tree_probs, 255 , sizeof(xd->mb_segment_tree_probs));
    804 
    805         tot_count = segment_counts[0] + segment_counts[1] + segment_counts[2] + segment_counts[3];
    806 
    807         if (tot_count)
    808         {
    809             xd->mb_segment_tree_probs[0] = ((segment_counts[0] + segment_counts[1]) * 255) / tot_count;
    810 
    811             tot_count = segment_counts[0] + segment_counts[1];
    812 
    813             if (tot_count > 0)
    814             {
    815                 xd->mb_segment_tree_probs[1] = (segment_counts[0] * 255) / tot_count;
    816             }
    817 
    818             tot_count = segment_counts[2] + segment_counts[3];
    819 
    820             if (tot_count > 0)
    821                 xd->mb_segment_tree_probs[2] = (segment_counts[2] * 255) / tot_count;
    822 
    823             // Zero probabilities not allowed
    824             for (i = 0; i < MB_FEATURE_TREE_PROBS; i ++)
    825             {
    826                 if (xd->mb_segment_tree_probs[i] == 0)
    827                     xd->mb_segment_tree_probs[i] = 1;
    828             }
    829         }
    830     }
    831 
    832     // 256 rate units to the bit
    833     cpi->projected_frame_size = totalrate >> 8;   // projected_frame_size in units of BYTES
    834 
    835     // Make a note of the percentage MBs coded Intra.
    836     if (cm->frame_type == KEY_FRAME)
    837     {
    838         cpi->this_frame_percent_intra = 100;
    839     }
    840     else
    841     {
    842         int tot_modes;
    843 
    844         tot_modes = cpi->count_mb_ref_frame_usage[INTRA_FRAME]
    845                     + cpi->count_mb_ref_frame_usage[LAST_FRAME]
    846                     + cpi->count_mb_ref_frame_usage[GOLDEN_FRAME]
    847                     + cpi->count_mb_ref_frame_usage[ALTREF_FRAME];
    848 
    849         if (tot_modes)
    850             cpi->this_frame_percent_intra = cpi->count_mb_ref_frame_usage[INTRA_FRAME] * 100 / tot_modes;
    851 
    852     }
    853 
    854 #if 0
    855     {
    856         int cnt = 0;
    857         int flag[2] = {0, 0};
    858 
    859         for (cnt = 0; cnt < MVPcount; cnt++)
    860         {
    861             if (cm->fc.pre_mvc[0][cnt] != cm->fc.mvc[0][cnt])
    862             {
    863                 flag[0] = 1;
    864                 vpx_memcpy(cm->fc.pre_mvc[0], cm->fc.mvc[0], MVPcount);
    865                 break;
    866             }
    867         }
    868 
    869         for (cnt = 0; cnt < MVPcount; cnt++)
    870         {
    871             if (cm->fc.pre_mvc[1][cnt] != cm->fc.mvc[1][cnt])
    872             {
    873                 flag[1] = 1;
    874                 vpx_memcpy(cm->fc.pre_mvc[1], cm->fc.mvc[1], MVPcount);
    875                 break;
    876             }
    877         }
    878 
    879         if (flag[0] || flag[1])
    880             vp8_build_component_cost_table(cpi->mb.mvcost, cpi->mb.mvsadcost, (const MV_CONTEXT *) cm->fc.mvc, flag);
    881     }
    882 #endif
    883 
    884     // Adjust the projected reference frame useage probability numbers to reflect
    885     // what we have just seen. This may be usefull when we make multiple itterations
    886     // of the recode loop rather than continuing to use values from the previous frame.
    887     if ((cm->frame_type != KEY_FRAME) && !cm->refresh_alt_ref_frame && !cm->refresh_golden_frame)
    888     {
    889         const int *const rfct = cpi->count_mb_ref_frame_usage;
    890         const int rf_intra = rfct[INTRA_FRAME];
    891         const int rf_inter = rfct[LAST_FRAME] + rfct[GOLDEN_FRAME] + rfct[ALTREF_FRAME];
    892 
    893         if ((rf_intra + rf_inter) > 0)
    894         {
    895             cpi->prob_intra_coded = (rf_intra * 255) / (rf_intra + rf_inter);
    896 
    897             if (cpi->prob_intra_coded < 1)
    898                 cpi->prob_intra_coded = 1;
    899 
    900             if ((cm->frames_since_golden > 0) || cpi->source_alt_ref_active)
    901             {
    902                 cpi->prob_last_coded = rf_inter ? (rfct[LAST_FRAME] * 255) / rf_inter : 128;
    903 
    904                 if (cpi->prob_last_coded < 1)
    905                     cpi->prob_last_coded = 1;
    906 
    907                 cpi->prob_gf_coded = (rfct[GOLDEN_FRAME] + rfct[ALTREF_FRAME])
    908                                      ? (rfct[GOLDEN_FRAME] * 255) / (rfct[GOLDEN_FRAME] + rfct[ALTREF_FRAME]) : 128;
    909 
    910                 if (cpi->prob_gf_coded < 1)
    911                     cpi->prob_gf_coded = 1;
    912             }
    913         }
    914     }
    915 
    916 #if 0
    917     // Keep record of the total distortion this time around for future use
    918     cpi->last_frame_distortion = cpi->frame_distortion;
    919 #endif
    920 
    921 }
    922 void vp8_setup_block_ptrs(MACROBLOCK *x)
    923 {
    924     int r, c;
    925     int i;
    926 
    927     for (r = 0; r < 4; r++)
    928     {
    929         for (c = 0; c < 4; c++)
    930         {
    931             x->block[r*4+c].src_diff = x->src_diff + r * 4 * 16 + c * 4;
    932         }
    933     }
    934 
    935     for (r = 0; r < 2; r++)
    936     {
    937         for (c = 0; c < 2; c++)
    938         {
    939             x->block[16 + r*2+c].src_diff = x->src_diff + 256 + r * 4 * 8 + c * 4;
    940         }
    941     }
    942 
    943 
    944     for (r = 0; r < 2; r++)
    945     {
    946         for (c = 0; c < 2; c++)
    947         {
    948             x->block[20 + r*2+c].src_diff = x->src_diff + 320 + r * 4 * 8 + c * 4;
    949         }
    950     }
    951 
    952     x->block[24].src_diff = x->src_diff + 384;
    953 
    954 
    955     for (i = 0; i < 25; i++)
    956     {
    957         x->block[i].coeff = x->coeff + i * 16;
    958     }
    959 }
    960 
    961 void vp8_build_block_offsets(MACROBLOCK *x)
    962 {
    963     int block = 0;
    964     int br, bc;
    965 
    966     vp8_build_block_doffsets(&x->e_mbd);
    967 
    968     // y blocks
    969     for (br = 0; br < 4; br++)
    970     {
    971         for (bc = 0; bc < 4; bc++)
    972         {
    973             BLOCK *this_block = &x->block[block];
    974             this_block->base_src = &x->src.y_buffer;
    975             this_block->src_stride = x->src.y_stride;
    976             this_block->src = 4 * br * this_block->src_stride + 4 * bc;
    977             ++block;
    978         }
    979     }
    980 
    981     // u blocks
    982     for (br = 0; br < 2; br++)
    983     {
    984         for (bc = 0; bc < 2; bc++)
    985         {
    986             BLOCK *this_block = &x->block[block];
    987             this_block->base_src = &x->src.u_buffer;
    988             this_block->src_stride = x->src.uv_stride;
    989             this_block->src = 4 * br * this_block->src_stride + 4 * bc;
    990             ++block;
    991         }
    992     }
    993 
    994     // v blocks
    995     for (br = 0; br < 2; br++)
    996     {
    997         for (bc = 0; bc < 2; bc++)
    998         {
    999             BLOCK *this_block = &x->block[block];
   1000             this_block->base_src = &x->src.v_buffer;
   1001             this_block->src_stride = x->src.uv_stride;
   1002             this_block->src = 4 * br * this_block->src_stride + 4 * bc;
   1003             ++block;
   1004         }
   1005     }
   1006 }
   1007 
   1008 static void sum_intra_stats(VP8_COMP *cpi, MACROBLOCK *x)
   1009 {
   1010     const MACROBLOCKD *xd = & x->e_mbd;
   1011     const MB_PREDICTION_MODE m = xd->mode_info_context->mbmi.mode;
   1012     const MB_PREDICTION_MODE uvm = xd->mode_info_context->mbmi.uv_mode;
   1013 
   1014 #ifdef MODE_STATS
   1015     const int is_key = cpi->common.frame_type == KEY_FRAME;
   1016 
   1017     ++ (is_key ? uv_modes : inter_uv_modes)[uvm];
   1018 
   1019     if (m == B_PRED)
   1020     {
   1021         unsigned int *const bct = is_key ? b_modes : inter_b_modes;
   1022 
   1023         int b = 0;
   1024 
   1025         do
   1026         {
   1027             ++ bct[xd->block[b].bmi.mode];
   1028         }
   1029         while (++b < 16);
   1030     }
   1031 
   1032 #endif
   1033 
   1034     ++cpi->ymode_count[m];
   1035     ++cpi->uv_mode_count[uvm];
   1036 
   1037 }
   1038 int vp8cx_encode_intra_macro_block(VP8_COMP *cpi, MACROBLOCK *x, TOKENEXTRA **t)
   1039 {
   1040     int Error4x4, Error16x16, error_uv;
   1041     B_PREDICTION_MODE intra_bmodes[16];
   1042     int rate4x4, rate16x16, rateuv;
   1043     int dist4x4, dist16x16, distuv;
   1044     int rate = 0;
   1045     int rate4x4_tokenonly = 0;
   1046     int rate16x16_tokenonly = 0;
   1047     int rateuv_tokenonly = 0;
   1048     int i;
   1049 
   1050     x->e_mbd.mode_info_context->mbmi.ref_frame = INTRA_FRAME;
   1051 
   1052 #if !(CONFIG_REALTIME_ONLY)
   1053 
   1054     if (cpi->sf.RD || cpi->compressor_speed != 2)
   1055     {
   1056         Error4x4 = vp8_rd_pick_intra4x4mby_modes(cpi, x, &rate4x4, &rate4x4_tokenonly, &dist4x4);
   1057 
   1058         //save the b modes for possible later use
   1059         for (i = 0; i < 16; i++)
   1060             intra_bmodes[i] = x->e_mbd.block[i].bmi.mode;
   1061 
   1062         Error16x16 = vp8_rd_pick_intra16x16mby_mode(cpi, x, &rate16x16, &rate16x16_tokenonly, &dist16x16);
   1063 
   1064         error_uv = vp8_rd_pick_intra_mbuv_mode(cpi, x, &rateuv, &rateuv_tokenonly, &distuv);
   1065 
   1066         x->e_mbd.mode_info_context->mbmi.mb_skip_coeff = (cpi->common.mb_no_coeff_skip) ? 1 : 0;
   1067 
   1068         vp8_encode_intra16x16mbuv(IF_RTCD(&cpi->rtcd), x);
   1069         rate += rateuv;
   1070 
   1071         if (Error4x4 < Error16x16)
   1072         {
   1073             rate += rate4x4;
   1074             x->e_mbd.mode_info_context->mbmi.mode = B_PRED;
   1075 
   1076             // get back the intra block modes
   1077             for (i = 0; i < 16; i++)
   1078                 x->e_mbd.block[i].bmi.mode = intra_bmodes[i];
   1079 
   1080             vp8_encode_intra4x4mby(IF_RTCD(&cpi->rtcd), x);
   1081             cpi->prediction_error += Error4x4 ;
   1082 #if 0
   1083             // Experimental RD code
   1084             cpi->frame_distortion += dist4x4;
   1085 #endif
   1086         }
   1087         else
   1088         {
   1089             vp8_encode_intra16x16mby(IF_RTCD(&cpi->rtcd), x);
   1090             rate += rate16x16;
   1091 
   1092 #if 0
   1093             // Experimental RD code
   1094             cpi->prediction_error += Error16x16;
   1095             cpi->frame_distortion += dist16x16;
   1096 #endif
   1097         }
   1098 
   1099         sum_intra_stats(cpi, x);
   1100 
   1101         vp8_tokenize_mb(cpi, &x->e_mbd, t);
   1102     }
   1103     else
   1104 #endif
   1105     {
   1106 
   1107         int rate2, distortion2;
   1108         MB_PREDICTION_MODE mode, best_mode = DC_PRED;
   1109         int this_rd;
   1110         Error16x16 = INT_MAX;
   1111 
   1112         for (mode = DC_PRED; mode <= TM_PRED; mode ++)
   1113         {
   1114             x->e_mbd.mode_info_context->mbmi.mode = mode;
   1115             vp8_build_intra_predictors_mby_ptr(&x->e_mbd);
   1116             distortion2 = VARIANCE_INVOKE(&cpi->rtcd.variance, get16x16prederror)(x->src.y_buffer, x->src.y_stride, x->e_mbd.predictor, 16, 0x7fffffff);
   1117             rate2  = x->mbmode_cost[x->e_mbd.frame_type][mode];
   1118             this_rd = RD_ESTIMATE(x->rdmult, x->rddiv, rate2, distortion2);
   1119 
   1120             if (Error16x16 > this_rd)
   1121             {
   1122                 Error16x16 = this_rd;
   1123                 best_mode = mode;
   1124             }
   1125         }
   1126 
   1127         vp8_pick_intra4x4mby_modes(IF_RTCD(&cpi->rtcd), x, &rate2, &distortion2);
   1128 
   1129         if (distortion2 == INT_MAX)
   1130             Error4x4 = INT_MAX;
   1131         else
   1132             Error4x4 = RD_ESTIMATE(x->rdmult, x->rddiv, rate2, distortion2);
   1133 
   1134         x->e_mbd.mode_info_context->mbmi.mb_skip_coeff = (cpi->common.mb_no_coeff_skip) ? 1 : 0;
   1135 
   1136         if (Error4x4 < Error16x16)
   1137         {
   1138             x->e_mbd.mode_info_context->mbmi.mode = B_PRED;
   1139             vp8_encode_intra4x4mby(IF_RTCD(&cpi->rtcd), x);
   1140             cpi->prediction_error += Error4x4;
   1141         }
   1142         else
   1143         {
   1144             x->e_mbd.mode_info_context->mbmi.mode = best_mode;
   1145             vp8_encode_intra16x16mby(IF_RTCD(&cpi->rtcd), x);
   1146             cpi->prediction_error += Error16x16;
   1147         }
   1148 
   1149         vp8_pick_intra_mbuv_mode(x);
   1150         vp8_encode_intra16x16mbuv(IF_RTCD(&cpi->rtcd), x);
   1151         sum_intra_stats(cpi, x);
   1152         vp8_tokenize_mb(cpi, &x->e_mbd, t);
   1153     }
   1154 
   1155     return rate;
   1156 }
   1157 #ifdef SPEEDSTATS
   1158 extern int cnt_pm;
   1159 #endif
   1160 
   1161 extern void vp8_fix_contexts(MACROBLOCKD *x);
   1162 
   1163 int vp8cx_encode_inter_macroblock
   1164 (
   1165     VP8_COMP *cpi, MACROBLOCK *x, TOKENEXTRA **t,
   1166     int recon_yoffset, int recon_uvoffset
   1167 )
   1168 {
   1169     MACROBLOCKD *const xd = &x->e_mbd;
   1170     int inter_error;
   1171     int intra_error = 0;
   1172     int rate;
   1173     int distortion;
   1174 
   1175     x->skip = 0;
   1176 
   1177     if (xd->segmentation_enabled)
   1178         x->encode_breakout = cpi->segment_encode_breakout[xd->mode_info_context->mbmi.segment_id];
   1179     else
   1180         x->encode_breakout = cpi->oxcf.encode_breakout;
   1181 
   1182 #if !(CONFIG_REALTIME_ONLY)
   1183 
   1184     if (cpi->sf.RD)
   1185     {
   1186         inter_error = vp8_rd_pick_inter_mode(cpi, x, recon_yoffset, recon_uvoffset, &rate, &distortion, &intra_error);
   1187     }
   1188     else
   1189 #endif
   1190         inter_error = vp8_pick_inter_mode(cpi, x, recon_yoffset, recon_uvoffset, &rate, &distortion, &intra_error);
   1191 
   1192 
   1193     cpi->prediction_error += inter_error;
   1194     cpi->intra_error += intra_error;
   1195 
   1196 #if 0
   1197     // Experimental RD code
   1198     cpi->frame_distortion += distortion;
   1199     cpi->last_mb_distortion = distortion;
   1200 #endif
   1201 
   1202     // MB level adjutment to quantizer setup
   1203     if (xd->segmentation_enabled || cpi->zbin_mode_boost_enabled)
   1204     {
   1205         // If cyclic update enabled
   1206         if (cpi->cyclic_refresh_mode_enabled)
   1207         {
   1208             // Clear segment_id back to 0 if not coded (last frame 0,0)
   1209             if ((xd->mode_info_context->mbmi.segment_id == 1) &&
   1210                 ((xd->mode_info_context->mbmi.ref_frame != LAST_FRAME) || (xd->mode_info_context->mbmi.mode != ZEROMV)))
   1211             {
   1212                 xd->mode_info_context->mbmi.segment_id = 0;
   1213             }
   1214         }
   1215 
   1216         // Experimental code. Special case for gf and arf zeromv modes. Increase zbin size to supress noise
   1217         if (cpi->zbin_mode_boost_enabled)
   1218         {
   1219             if ((xd->mode_info_context->mbmi.mode == ZEROMV) && (xd->mode_info_context->mbmi.ref_frame != LAST_FRAME))
   1220                 cpi->zbin_mode_boost = GF_ZEROMV_ZBIN_BOOST;
   1221             else
   1222                 cpi->zbin_mode_boost = 0;
   1223         }
   1224 
   1225         vp8cx_mb_init_quantizer(cpi,  x);
   1226     }
   1227 
   1228     cpi->count_mb_ref_frame_usage[xd->mode_info_context->mbmi.ref_frame] ++;
   1229 
   1230     if (xd->mode_info_context->mbmi.ref_frame == INTRA_FRAME)
   1231     {
   1232         x->e_mbd.mode_info_context->mbmi.mb_skip_coeff = (cpi->common.mb_no_coeff_skip) ? 1 : 0;
   1233 
   1234         vp8_encode_intra16x16mbuv(IF_RTCD(&cpi->rtcd), x);
   1235 
   1236         if (xd->mode_info_context->mbmi.mode == B_PRED)
   1237         {
   1238             vp8_encode_intra4x4mby(IF_RTCD(&cpi->rtcd), x);
   1239         }
   1240         else
   1241         {
   1242             vp8_encode_intra16x16mby(IF_RTCD(&cpi->rtcd), x);
   1243         }
   1244 
   1245         sum_intra_stats(cpi, x);
   1246     }
   1247     else
   1248     {
   1249         MV best_ref_mv;
   1250         MV nearest, nearby;
   1251         int mdcounts[4];
   1252         int ref_fb_idx;
   1253 
   1254         vp8_find_near_mvs(xd, xd->mode_info_context,
   1255                           &nearest, &nearby, &best_ref_mv, mdcounts, xd->mode_info_context->mbmi.ref_frame, cpi->common.ref_frame_sign_bias);
   1256 
   1257         vp8_build_uvmvs(xd, cpi->common.full_pixel);
   1258 
   1259         if (xd->mode_info_context->mbmi.ref_frame == LAST_FRAME)
   1260             ref_fb_idx = cpi->common.lst_fb_idx;
   1261         else if (xd->mode_info_context->mbmi.ref_frame == GOLDEN_FRAME)
   1262             ref_fb_idx = cpi->common.gld_fb_idx;
   1263         else
   1264             ref_fb_idx = cpi->common.alt_fb_idx;
   1265 
   1266         xd->pre.y_buffer = cpi->common.yv12_fb[ref_fb_idx].y_buffer + recon_yoffset;
   1267         xd->pre.u_buffer = cpi->common.yv12_fb[ref_fb_idx].u_buffer + recon_uvoffset;
   1268         xd->pre.v_buffer = cpi->common.yv12_fb[ref_fb_idx].v_buffer + recon_uvoffset;
   1269 
   1270         if (xd->mode_info_context->mbmi.mode == SPLITMV)
   1271         {
   1272             int i;
   1273 
   1274             for (i = 0; i < 16; i++)
   1275             {
   1276                 if (xd->block[i].bmi.mode == NEW4X4)
   1277                 {
   1278                     cpi->MVcount[0][mv_max+((xd->block[i].bmi.mv.as_mv.row - best_ref_mv.row) >> 1)]++;
   1279                     cpi->MVcount[1][mv_max+((xd->block[i].bmi.mv.as_mv.col - best_ref_mv.col) >> 1)]++;
   1280                 }
   1281             }
   1282         }
   1283         else if (xd->mode_info_context->mbmi.mode == NEWMV)
   1284         {
   1285             cpi->MVcount[0][mv_max+((xd->block[0].bmi.mv.as_mv.row - best_ref_mv.row) >> 1)]++;
   1286             cpi->MVcount[1][mv_max+((xd->block[0].bmi.mv.as_mv.col - best_ref_mv.col) >> 1)]++;
   1287         }
   1288 
   1289         if (!x->skip && !x->e_mbd.mode_info_context->mbmi.force_no_skip)
   1290         {
   1291             vp8_encode_inter16x16(IF_RTCD(&cpi->rtcd), x);
   1292 
   1293             // Clear mb_skip_coeff if mb_no_coeff_skip is not set
   1294             if (!cpi->common.mb_no_coeff_skip)
   1295                 xd->mode_info_context->mbmi.mb_skip_coeff = 0;
   1296 
   1297         }
   1298         else
   1299             vp8_stuff_inter16x16(x);
   1300     }
   1301 
   1302     if (!x->skip)
   1303         vp8_tokenize_mb(cpi, xd, t);
   1304     else
   1305     {
   1306         if (cpi->common.mb_no_coeff_skip)
   1307         {
   1308             if (xd->mode_info_context->mbmi.mode != B_PRED && xd->mode_info_context->mbmi.mode != SPLITMV)
   1309                 xd->mode_info_context->mbmi.dc_diff = 0;
   1310             else
   1311                 xd->mode_info_context->mbmi.dc_diff = 1;
   1312 
   1313             xd->mode_info_context->mbmi.mb_skip_coeff = 1;
   1314             cpi->skip_true_count ++;
   1315             vp8_fix_contexts(xd);
   1316         }
   1317         else
   1318         {
   1319             vp8_stuff_mb(cpi, xd, t);
   1320             xd->mode_info_context->mbmi.mb_skip_coeff = 0;
   1321             cpi->skip_false_count ++;
   1322         }
   1323     }
   1324 
   1325     return rate;
   1326 }
   1327