Commit 7cbe684e authored by Yunqing Wang's avatar Yunqing Wang
Browse files

Improve MV prediction in vp8_pick_inter_mode() for speed>3

Applied same method used in vp8_rd_pick_inter_mode() to improve
the accuracy of MV prediction.

Change-Id: Ia50ae26208b18482695601f32febd99fe89fbc17
parent dcb23e2a
...@@ -11,8 +11,6 @@ ...@@ -11,8 +11,6 @@
#include "findnearmv.h" #include "findnearmv.h"
#define FINDNEAR_SEARCH_SITES 3
/* Predict motion vectors using those from already-decoded nearby blocks. /* Predict motion vectors using those from already-decoded nearby blocks.
Note that we only consider one 4x4 subblock from each candidate 16x16 Note that we only consider one 4x4 subblock from each candidate 16x16
macroblock. */ macroblock. */
......
...@@ -24,7 +24,7 @@ ...@@ -24,7 +24,7 @@
#include "g_common.h" #include "g_common.h"
#include "variance.h" #include "variance.h"
#include "mcomp.h" #include "mcomp.h"
#include "rdopt.h"
#include "vpx_mem/vpx_mem.h" #include "vpx_mem/vpx_mem.h"
#if CONFIG_RUNTIME_CPU_DETECT #if CONFIG_RUNTIME_CPU_DETECT
...@@ -421,7 +421,6 @@ int vp8_pick_intra_mbuv_mode(MACROBLOCK *mb) ...@@ -421,7 +421,6 @@ int vp8_pick_intra_mbuv_mode(MACROBLOCK *mb)
} }
int vp8_pick_inter_mode(VP8_COMP *cpi, MACROBLOCK *x, int recon_yoffset, int recon_uvoffset, int *returnrate, int *returndistortion, int *returnintra) int vp8_pick_inter_mode(VP8_COMP *cpi, MACROBLOCK *x, int recon_yoffset, int recon_uvoffset, int *returnrate, int *returndistortion, int *returnintra)
{ {
BLOCK *b = &x->block[0]; BLOCK *b = &x->block[0];
...@@ -430,7 +429,7 @@ int vp8_pick_inter_mode(VP8_COMP *cpi, MACROBLOCK *x, int recon_yoffset, int rec ...@@ -430,7 +429,7 @@ int vp8_pick_inter_mode(VP8_COMP *cpi, MACROBLOCK *x, int recon_yoffset, int rec
B_MODE_INFO best_bmodes[16]; B_MODE_INFO best_bmodes[16];
MB_MODE_INFO best_mbmode; MB_MODE_INFO best_mbmode;
PARTITION_INFO best_partition; PARTITION_INFO best_partition;
MV best_ref_mv1; MV best_ref_mv;
MV mode_mv[MB_MODE_COUNT]; MV mode_mv[MB_MODE_COUNT];
MB_PREDICTION_MODE this_mode; MB_PREDICTION_MODE this_mode;
int num00; int num00;
...@@ -448,9 +447,14 @@ int vp8_pick_inter_mode(VP8_COMP *cpi, MACROBLOCK *x, int recon_yoffset, int rec ...@@ -448,9 +447,14 @@ int vp8_pick_inter_mode(VP8_COMP *cpi, MACROBLOCK *x, int recon_yoffset, int rec
int best_mode_index = 0; int best_mode_index = 0;
int sse = INT_MAX; int sse = INT_MAX;
MV mvp;
int near_sadidx[8] = {0, 1, 2, 3, 4, 5, 6, 7};
int saddone=0;
int sr=0; //search range got from mv_pred(). It uses step_param levels. (0-7)
MV nearest_mv[4]; MV nearest_mv[4];
MV near_mv[4]; MV near_mv[4];
MV best_ref_mv[4]; MV frame_best_ref_mv[4];
int MDCounts[4][4]; int MDCounts[4][4];
unsigned char *y_buffer[4]; unsigned char *y_buffer[4];
unsigned char *u_buffer[4]; unsigned char *u_buffer[4];
...@@ -470,7 +474,7 @@ int vp8_pick_inter_mode(VP8_COMP *cpi, MACROBLOCK *x, int recon_yoffset, int rec ...@@ -470,7 +474,7 @@ int vp8_pick_inter_mode(VP8_COMP *cpi, MACROBLOCK *x, int recon_yoffset, int rec
YV12_BUFFER_CONFIG *lst_yv12 = &cpi->common.yv12_fb[cpi->common.lst_fb_idx]; YV12_BUFFER_CONFIG *lst_yv12 = &cpi->common.yv12_fb[cpi->common.lst_fb_idx];
vp8_find_near_mvs(&x->e_mbd, x->e_mbd.mode_info_context, &nearest_mv[LAST_FRAME], &near_mv[LAST_FRAME], vp8_find_near_mvs(&x->e_mbd, x->e_mbd.mode_info_context, &nearest_mv[LAST_FRAME], &near_mv[LAST_FRAME],
&best_ref_mv[LAST_FRAME], MDCounts[LAST_FRAME], LAST_FRAME, cpi->common.ref_frame_sign_bias); &frame_best_ref_mv[LAST_FRAME], MDCounts[LAST_FRAME], LAST_FRAME, cpi->common.ref_frame_sign_bias);
y_buffer[LAST_FRAME] = lst_yv12->y_buffer + recon_yoffset; y_buffer[LAST_FRAME] = lst_yv12->y_buffer + recon_yoffset;
u_buffer[LAST_FRAME] = lst_yv12->u_buffer + recon_uvoffset; u_buffer[LAST_FRAME] = lst_yv12->u_buffer + recon_uvoffset;
...@@ -484,7 +488,7 @@ int vp8_pick_inter_mode(VP8_COMP *cpi, MACROBLOCK *x, int recon_yoffset, int rec ...@@ -484,7 +488,7 @@ int vp8_pick_inter_mode(VP8_COMP *cpi, MACROBLOCK *x, int recon_yoffset, int rec
YV12_BUFFER_CONFIG *gld_yv12 = &cpi->common.yv12_fb[cpi->common.gld_fb_idx]; YV12_BUFFER_CONFIG *gld_yv12 = &cpi->common.yv12_fb[cpi->common.gld_fb_idx];
vp8_find_near_mvs(&x->e_mbd, x->e_mbd.mode_info_context, &nearest_mv[GOLDEN_FRAME], &near_mv[GOLDEN_FRAME], vp8_find_near_mvs(&x->e_mbd, x->e_mbd.mode_info_context, &nearest_mv[GOLDEN_FRAME], &near_mv[GOLDEN_FRAME],
&best_ref_mv[GOLDEN_FRAME], MDCounts[GOLDEN_FRAME], GOLDEN_FRAME, cpi->common.ref_frame_sign_bias); &frame_best_ref_mv[GOLDEN_FRAME], MDCounts[GOLDEN_FRAME], GOLDEN_FRAME, cpi->common.ref_frame_sign_bias);
y_buffer[GOLDEN_FRAME] = gld_yv12->y_buffer + recon_yoffset; y_buffer[GOLDEN_FRAME] = gld_yv12->y_buffer + recon_yoffset;
u_buffer[GOLDEN_FRAME] = gld_yv12->u_buffer + recon_uvoffset; u_buffer[GOLDEN_FRAME] = gld_yv12->u_buffer + recon_uvoffset;
...@@ -498,7 +502,7 @@ int vp8_pick_inter_mode(VP8_COMP *cpi, MACROBLOCK *x, int recon_yoffset, int rec ...@@ -498,7 +502,7 @@ int vp8_pick_inter_mode(VP8_COMP *cpi, MACROBLOCK *x, int recon_yoffset, int rec
YV12_BUFFER_CONFIG *alt_yv12 = &cpi->common.yv12_fb[cpi->common.alt_fb_idx]; YV12_BUFFER_CONFIG *alt_yv12 = &cpi->common.yv12_fb[cpi->common.alt_fb_idx];
vp8_find_near_mvs(&x->e_mbd, x->e_mbd.mode_info_context, &nearest_mv[ALTREF_FRAME], &near_mv[ALTREF_FRAME], vp8_find_near_mvs(&x->e_mbd, x->e_mbd.mode_info_context, &nearest_mv[ALTREF_FRAME], &near_mv[ALTREF_FRAME],
&best_ref_mv[ALTREF_FRAME], MDCounts[ALTREF_FRAME], ALTREF_FRAME, cpi->common.ref_frame_sign_bias); &frame_best_ref_mv[ALTREF_FRAME], MDCounts[ALTREF_FRAME], ALTREF_FRAME, cpi->common.ref_frame_sign_bias);
y_buffer[ALTREF_FRAME] = alt_yv12->y_buffer + recon_yoffset; y_buffer[ALTREF_FRAME] = alt_yv12->y_buffer + recon_yoffset;
u_buffer[ALTREF_FRAME] = alt_yv12->u_buffer + recon_uvoffset; u_buffer[ALTREF_FRAME] = alt_yv12->u_buffer + recon_uvoffset;
...@@ -538,10 +542,6 @@ int vp8_pick_inter_mode(VP8_COMP *cpi, MACROBLOCK *x, int recon_yoffset, int rec ...@@ -538,10 +542,6 @@ int vp8_pick_inter_mode(VP8_COMP *cpi, MACROBLOCK *x, int recon_yoffset, int rec
+ vp8_cost_one(cpi->prob_gf_coded); + vp8_cost_one(cpi->prob_gf_coded);
} }
best_rd = INT_MAX;
x->e_mbd.mode_info_context->mbmi.ref_frame = INTRA_FRAME; x->e_mbd.mode_info_context->mbmi.ref_frame = INTRA_FRAME;
// if we encode a new mv this is important // if we encode a new mv this is important
...@@ -604,7 +604,7 @@ int vp8_pick_inter_mode(VP8_COMP *cpi, MACROBLOCK *x, int recon_yoffset, int rec ...@@ -604,7 +604,7 @@ int vp8_pick_inter_mode(VP8_COMP *cpi, MACROBLOCK *x, int recon_yoffset, int rec
x->e_mbd.pre.v_buffer = v_buffer[x->e_mbd.mode_info_context->mbmi.ref_frame]; x->e_mbd.pre.v_buffer = v_buffer[x->e_mbd.mode_info_context->mbmi.ref_frame];
mode_mv[NEARESTMV] = nearest_mv[x->e_mbd.mode_info_context->mbmi.ref_frame]; mode_mv[NEARESTMV] = nearest_mv[x->e_mbd.mode_info_context->mbmi.ref_frame];
mode_mv[NEARMV] = near_mv[x->e_mbd.mode_info_context->mbmi.ref_frame]; mode_mv[NEARMV] = near_mv[x->e_mbd.mode_info_context->mbmi.ref_frame];
best_ref_mv1 = best_ref_mv[x->e_mbd.mode_info_context->mbmi.ref_frame]; best_ref_mv = frame_best_ref_mv[x->e_mbd.mode_info_context->mbmi.ref_frame];
memcpy(mdcounts, MDCounts[x->e_mbd.mode_info_context->mbmi.ref_frame], sizeof(mdcounts)); memcpy(mdcounts, MDCounts[x->e_mbd.mode_info_context->mbmi.ref_frame], sizeof(mdcounts));
} }
...@@ -617,6 +617,28 @@ int vp8_pick_inter_mode(VP8_COMP *cpi, MACROBLOCK *x, int recon_yoffset, int rec ...@@ -617,6 +617,28 @@ int vp8_pick_inter_mode(VP8_COMP *cpi, MACROBLOCK *x, int recon_yoffset, int rec
continue; continue;
} }
if(x->e_mbd.mode_info_context->mbmi.mode == NEWMV)
{
if(!saddone)
{
vp8_cal_sad(cpi,xd,x, recon_yoffset ,&near_sadidx[0] );
saddone = 1;
}
vp8_mv_pred(cpi, &x->e_mbd, x->e_mbd.mode_info_context, &mvp,
x->e_mbd.mode_info_context->mbmi.ref_frame, cpi->common.ref_frame_sign_bias, &sr, &near_sadidx[0]);
/* adjust mvp to make sure it is within MV range */
if(mvp.row > best_ref_mv.row + MAX_FULL_PEL_VAL)
mvp.row = best_ref_mv.row + MAX_FULL_PEL_VAL;
else if(mvp.row < best_ref_mv.row - MAX_FULL_PEL_VAL)
mvp.row = best_ref_mv.row - MAX_FULL_PEL_VAL;
if(mvp.col > best_ref_mv.col + MAX_FULL_PEL_VAL)
mvp.col = best_ref_mv.col + MAX_FULL_PEL_VAL;
else if(mvp.col < best_ref_mv.col - MAX_FULL_PEL_VAL)
mvp.col = best_ref_mv.col - MAX_FULL_PEL_VAL;
}
switch (this_mode) switch (this_mode)
{ {
case B_PRED: case B_PRED:
...@@ -672,61 +694,46 @@ int vp8_pick_inter_mode(VP8_COMP *cpi, MACROBLOCK *x, int recon_yoffset, int rec ...@@ -672,61 +694,46 @@ int vp8_pick_inter_mode(VP8_COMP *cpi, MACROBLOCK *x, int recon_yoffset, int rec
int n = 0; int n = 0;
int sadpb = x->sadperbit16; int sadpb = x->sadperbit16;
// Further step/diamond searches as necessary int col_min = (best_ref_mv.col - MAX_FULL_PEL_VAL) >>3;
if (cpi->Speed < 8) int col_max = (best_ref_mv.col + MAX_FULL_PEL_VAL) >>3;
{ int row_min = (best_ref_mv.row - MAX_FULL_PEL_VAL) >>3;
step_param = cpi->sf.first_step + ((cpi->Speed > 5) ? 1 : 0); int row_max = (best_ref_mv.row + MAX_FULL_PEL_VAL) >>3;
further_steps = (cpi->sf.max_step_search_steps - 1) - step_param;
} int tmp_col_min = x->mv_col_min;
else int tmp_col_max = x->mv_col_max;
{ int tmp_row_min = x->mv_row_min;
step_param = cpi->sf.first_step + 2; int tmp_row_max = x->mv_row_max;
further_steps = 0;
} // Get intersection of UMV window and valid MV window to reduce # of checks in diamond search.
if (x->mv_col_min < col_min )
#if 0 x->mv_col_min = col_min;
if (x->mv_col_max > col_max )
x->mv_col_max = col_max;
if (x->mv_row_min < row_min )
x->mv_row_min = row_min;
if (x->mv_row_max > row_max )
x->mv_row_max = row_max;
// Initial step Search // Further step/diamond searches as necessary
bestsme = vp8_diamond_search_sad(x, b, d, &best_ref_mv1, &d->bmi.mv.as_mv, step_param, x->errorperbit, &num00, &cpi->fn_ptr, cpi->mb.mvsadcost, cpi->mb.mvcost, &best_ref_mv1);
mode_mv[NEWMV].row = d->bmi.mv.as_mv.row;
mode_mv[NEWMV].col = d->bmi.mv.as_mv.col;
// Further step searches
while (n < further_steps)
{ {
n++; int speed_adjust = (cpi->Speed > 5) ? ((cpi->Speed >= 8)? 3 : 2) : 1;
step_param = cpi->sf.first_step + speed_adjust;
if (num00) sr += speed_adjust;
num00--; //adjust search range according to sr from mv prediction
else if(sr > step_param)
{ step_param = sr;
thissme = vp8_diamond_search_sad(x, b, d, &best_ref_mv1, &d->bmi.mv.as_mv, step_param + n, x->errorperbit, &num00, &cpi->fn_ptr, cpi->mb.mvsadcost, x->mvcost, &best_ref_mv1); further_steps = (cpi->Speed >= 8)? 0: (cpi->sf.max_step_search_steps - 1 - step_param);
if (thissme < bestsme)
{
bestsme = thissme;
mode_mv[NEWMV].row = d->bmi.mv.as_mv.row;
mode_mv[NEWMV].col = d->bmi.mv.as_mv.col;
}
else
{
d->bmi.mv.as_mv.row = mode_mv[NEWMV].row;
d->bmi.mv.as_mv.col = mode_mv[NEWMV].col;
}
}
} }
#else
if (cpi->sf.search_method == HEX) if (cpi->sf.search_method == HEX)
{ {
bestsme = vp8_hex_search(x, b, d, &best_ref_mv1, &d->bmi.mv.as_mv, step_param, sadpb/*x->errorperbit*/, &num00, &cpi->fn_ptr[BLOCK_16X16], x->mvsadcost, x->mvcost); bestsme = vp8_hex_search(x, b, d, &best_ref_mv, &d->bmi.mv.as_mv, step_param, sadpb/*x->errorperbit*/, &num00, &cpi->fn_ptr[BLOCK_16X16], x->mvsadcost, x->mvcost);
mode_mv[NEWMV].row = d->bmi.mv.as_mv.row; mode_mv[NEWMV].row = d->bmi.mv.as_mv.row;
mode_mv[NEWMV].col = d->bmi.mv.as_mv.col; mode_mv[NEWMV].col = d->bmi.mv.as_mv.col;
} }
else else
{ {
bestsme = cpi->diamond_search_sad(x, b, d, &best_ref_mv1, &d->bmi.mv.as_mv, step_param, sadpb / 2/*x->errorperbit*/, &num00, &cpi->fn_ptr[BLOCK_16X16], x->mvsadcost, x->mvcost, &best_ref_mv1); //sadpb < 9 bestsme = cpi->diamond_search_sad(x, b, d, &mvp, &d->bmi.mv.as_mv, step_param, sadpb / 2/*x->errorperbit*/, &num00, &cpi->fn_ptr[BLOCK_16X16], x->mvsadcost, x->mvcost, &best_ref_mv); //sadpb < 9
mode_mv[NEWMV].row = d->bmi.mv.as_mv.row; mode_mv[NEWMV].row = d->bmi.mv.as_mv.row;
mode_mv[NEWMV].col = d->bmi.mv.as_mv.col; mode_mv[NEWMV].col = d->bmi.mv.as_mv.col;
...@@ -745,7 +752,7 @@ int vp8_pick_inter_mode(VP8_COMP *cpi, MACROBLOCK *x, int recon_yoffset, int rec ...@@ -745,7 +752,7 @@ int vp8_pick_inter_mode(VP8_COMP *cpi, MACROBLOCK *x, int recon_yoffset, int rec
num00--; num00--;
else else
{ {
thissme = cpi->diamond_search_sad(x, b, d, &best_ref_mv1, &d->bmi.mv.as_mv, step_param + n, sadpb / 4/*x->errorperbit*/, &num00, &cpi->fn_ptr[BLOCK_16X16], x->mvsadcost, x->mvcost, &best_ref_mv1); //sadpb = 9 thissme = cpi->diamond_search_sad(x, b, d, &mvp, &d->bmi.mv.as_mv, step_param + n, sadpb / 4/*x->errorperbit*/, &num00, &cpi->fn_ptr[BLOCK_16X16], x->mvsadcost, x->mvcost, &best_ref_mv); //sadpb = 9
if (thissme < bestsme) if (thissme < bestsme)
{ {
...@@ -762,18 +769,20 @@ int vp8_pick_inter_mode(VP8_COMP *cpi, MACROBLOCK *x, int recon_yoffset, int rec ...@@ -762,18 +769,20 @@ int vp8_pick_inter_mode(VP8_COMP *cpi, MACROBLOCK *x, int recon_yoffset, int rec
} }
} }
#endif x->mv_col_min = tmp_col_min;
} x->mv_col_max = tmp_col_max;
x->mv_row_min = tmp_row_min;
if (bestsme < INT_MAX) x->mv_row_max = tmp_row_max;
cpi->find_fractional_mv_step(x, b, d, &d->bmi.mv.as_mv, &best_ref_mv1, x->errorperbit, &cpi->fn_ptr[BLOCK_16X16], cpi->mb.mvcost);
mode_mv[NEWMV].row = d->bmi.mv.as_mv.row; if (bestsme < INT_MAX)
mode_mv[NEWMV].col = d->bmi.mv.as_mv.col; cpi->find_fractional_mv_step(x, b, d, &d->bmi.mv.as_mv, &best_ref_mv, x->errorperbit, &cpi->fn_ptr[BLOCK_16X16], cpi->mb.mvcost);
// mv cost; mode_mv[NEWMV].row = d->bmi.mv.as_mv.row;
rate2 += vp8_mv_bit_cost(&mode_mv[NEWMV], &best_ref_mv1, cpi->mb.mvcost, 128); mode_mv[NEWMV].col = d->bmi.mv.as_mv.col;
// mv cost;
rate2 += vp8_mv_bit_cost(&mode_mv[NEWMV], &best_ref_mv, cpi->mb.mvcost, 128);
}
case NEARESTMV: case NEARESTMV:
case NEARMV: case NEARMV:
......
...@@ -1657,6 +1657,61 @@ void vp8_mv_pred ...@@ -1657,6 +1657,61 @@ void vp8_mv_pred
vp8_clamp_mv(mvp, xd); vp8_clamp_mv(mvp, xd);
} }
void vp8_cal_sad(VP8_COMP *cpi, MACROBLOCKD *xd, MACROBLOCK *x, int recon_yoffset, int near_sadidx[])
{
int near_sad[8] = {0}; // 0-cf above, 1-cf left, 2-cf aboveleft, 3-lf current, 4-lf above, 5-lf left, 6-lf right, 7-lf below
//calculate sad for current frame 3 nearby MBs.
if( xd->mb_to_top_edge==0 && xd->mb_to_left_edge ==0)
{
near_sad[0] = near_sad[1] = near_sad[2] = INT_MAX;
}else if(xd->mb_to_top_edge==0)
{ //only has left MB for sad calculation.
near_sad[0] = near_sad[2] = INT_MAX;
near_sad[1] = cpi->fn_ptr[BLOCK_16X16].sdf(x->src.y_buffer, x->src.y_stride, xd->dst.y_buffer - 16,xd->dst.y_stride, 0x7fffffff);
}else if(xd->mb_to_left_edge ==0)
{ //only has left MB for sad calculation.
near_sad[1] = near_sad[2] = INT_MAX;
near_sad[0] = cpi->fn_ptr[BLOCK_16X16].sdf(x->src.y_buffer, x->src.y_stride, xd->dst.y_buffer - xd->dst.y_stride *16,xd->dst.y_stride, 0x7fffffff);
}else
{
near_sad[0] = cpi->fn_ptr[BLOCK_16X16].sdf(x->src.y_buffer, x->src.y_stride, xd->dst.y_buffer - xd->dst.y_stride *16,xd->dst.y_stride, 0x7fffffff);
near_sad[1] = cpi->fn_ptr[BLOCK_16X16].sdf(x->src.y_buffer, x->src.y_stride, xd->dst.y_buffer - 16,xd->dst.y_stride, 0x7fffffff);
near_sad[2] = cpi->fn_ptr[BLOCK_16X16].sdf(x->src.y_buffer, x->src.y_stride, xd->dst.y_buffer - xd->dst.y_stride *16 -16,xd->dst.y_stride, 0x7fffffff);
}
if(cpi->common.last_frame_type != KEY_FRAME)
{
//calculate sad for last frame 5 nearby MBs.
unsigned char *pre_y_buffer = cpi->common.yv12_fb[cpi->common.lst_fb_idx].y_buffer + recon_yoffset;
int pre_y_stride = cpi->common.yv12_fb[cpi->common.lst_fb_idx].y_stride;
if(xd->mb_to_top_edge==0) near_sad[4] = INT_MAX;
if(xd->mb_to_left_edge ==0) near_sad[5] = INT_MAX;
if(xd->mb_to_right_edge ==0) near_sad[6] = INT_MAX;
if(xd->mb_to_bottom_edge==0) near_sad[7] = INT_MAX;
if(near_sad[4] != INT_MAX)
near_sad[4] = cpi->fn_ptr[BLOCK_16X16].sdf(x->src.y_buffer, x->src.y_stride, pre_y_buffer - pre_y_stride *16, pre_y_stride, 0x7fffffff);
if(near_sad[5] != INT_MAX)
near_sad[5] = cpi->fn_ptr[BLOCK_16X16].sdf(x->src.y_buffer, x->src.y_stride, pre_y_buffer - 16, pre_y_stride, 0x7fffffff);
near_sad[3] = cpi->fn_ptr[BLOCK_16X16].sdf(x->src.y_buffer, x->src.y_stride, pre_y_buffer, pre_y_stride, 0x7fffffff);
if(near_sad[6] != INT_MAX)
near_sad[6] = cpi->fn_ptr[BLOCK_16X16].sdf(x->src.y_buffer, x->src.y_stride, pre_y_buffer + 16, pre_y_stride, 0x7fffffff);
if(near_sad[7] != INT_MAX)
near_sad[7] = cpi->fn_ptr[BLOCK_16X16].sdf(x->src.y_buffer, x->src.y_stride, pre_y_buffer + pre_y_stride *16, pre_y_stride, 0x7fffffff);
}
if(cpi->common.last_frame_type != KEY_FRAME)
{
quicksortsad(near_sad, near_sadidx, 0, 7);
}else
{
quicksortsad(near_sad, near_sadidx, 0, 2);
}
}
int vp8_rd_pick_inter_mode(VP8_COMP *cpi, MACROBLOCK *x, int recon_yoffset, int recon_uvoffset, int *returnrate, int *returndistortion, int *returnintra) int vp8_rd_pick_inter_mode(VP8_COMP *cpi, MACROBLOCK *x, int recon_yoffset, int recon_uvoffset, int *returnrate, int *returndistortion, int *returnintra)
{ {
BLOCK *b = &x->block[0]; BLOCK *b = &x->block[0];
...@@ -1694,7 +1749,6 @@ int vp8_rd_pick_inter_mode(VP8_COMP *cpi, MACROBLOCK *x, int recon_yoffset, int ...@@ -1694,7 +1749,6 @@ int vp8_rd_pick_inter_mode(VP8_COMP *cpi, MACROBLOCK *x, int recon_yoffset, int
int force_no_skip = 0; int force_no_skip = 0;
MV mvp; MV mvp;
int near_sad[8] = {0}; // 0-cf above, 1-cf left, 2-cf aboveleft, 3-lf current, 4-lf above, 5-lf left, 6-lf right, 7-lf below
int near_sadidx[8] = {0, 1, 2, 3, 4, 5, 6, 7}; int near_sadidx[8] = {0, 1, 2, 3, 4, 5, 6, 7};
int saddone=0; int saddone=0;
int sr=0; //search range got from mv_pred(). It uses step_param levels. (0-7) int sr=0; //search range got from mv_pred(). It uses step_param levels. (0-7)
...@@ -1841,60 +1895,11 @@ int vp8_rd_pick_inter_mode(VP8_COMP *cpi, MACROBLOCK *x, int recon_yoffset, int ...@@ -1841,60 +1895,11 @@ int vp8_rd_pick_inter_mode(VP8_COMP *cpi, MACROBLOCK *x, int recon_yoffset, int
lf_or_gf = frame_lf_or_gf[x->e_mbd.mode_info_context->mbmi.ref_frame]; lf_or_gf = frame_lf_or_gf[x->e_mbd.mode_info_context->mbmi.ref_frame];
} }
if(x->e_mbd.mode_info_context->mbmi.mode == NEWMV) if(x->e_mbd.mode_info_context->mbmi.mode == NEWMV)
{ {
if(!saddone) if(!saddone)
{ {
//calculate sad for current frame 3 nearby MBs. vp8_cal_sad(cpi,xd,x, recon_yoffset ,&near_sadidx[0] );
if( xd->mb_to_top_edge==0 && xd->mb_to_left_edge ==0)
{
near_sad[0] = near_sad[1] = near_sad[2] = INT_MAX;
}else if(xd->mb_to_top_edge==0)
{ //only has left MB for sad calculation.
near_sad[0] = near_sad[2] = INT_MAX;
near_sad[1] = cpi->fn_ptr[BLOCK_16X16].sdf(x->src.y_buffer, x->src.y_stride, xd->dst.y_buffer - 16,xd->dst.y_stride, 0x7fffffff);
}else if(xd->mb_to_left_edge ==0)
{ //only has left MB for sad calculation.
near_sad[1] = near_sad[2] = INT_MAX;
near_sad[0] = cpi->fn_ptr[BLOCK_16X16].sdf(x->src.y_buffer, x->src.y_stride, xd->dst.y_buffer - xd->dst.y_stride *16,xd->dst.y_stride, 0x7fffffff);
}else
{
near_sad[0] = cpi->fn_ptr[BLOCK_16X16].sdf(x->src.y_buffer, x->src.y_stride, xd->dst.y_buffer - xd->dst.y_stride *16,xd->dst.y_stride, 0x7fffffff);
near_sad[1] = cpi->fn_ptr[BLOCK_16X16].sdf(x->src.y_buffer, x->src.y_stride, xd->dst.y_buffer - 16,xd->dst.y_stride, 0x7fffffff);
near_sad[2] = cpi->fn_ptr[BLOCK_16X16].sdf(x->src.y_buffer, x->src.y_stride, xd->dst.y_buffer - xd->dst.y_stride *16 -16,xd->dst.y_stride, 0x7fffffff);
}
if(cpi->common.last_frame_type != KEY_FRAME)
{
//calculate sad for last frame 5 nearby MBs.
unsigned char *pre_y_buffer = cpi->common.yv12_fb[cpi->common.lst_fb_idx].y_buffer + recon_yoffset;
int pre_y_stride = cpi->common.yv12_fb[cpi->common.lst_fb_idx].y_stride;
if(xd->mb_to_top_edge==0) near_sad[4] = INT_MAX;
if(xd->mb_to_left_edge ==0) near_sad[5] = INT_MAX;
if(xd->mb_to_right_edge ==0) near_sad[6] = INT_MAX;
if(xd->mb_to_bottom_edge==0) near_sad[7] = INT_MAX;
if(near_sad[4] != INT_MAX)
near_sad[4] = cpi->fn_ptr[BLOCK_16X16].sdf(x->src.y_buffer, x->src.y_stride, pre_y_buffer - pre_y_stride *16, pre_y_stride, 0x7fffffff);
if(near_sad[5] != INT_MAX)
near_sad[5] = cpi->fn_ptr[BLOCK_16X16].sdf(x->src.y_buffer, x->src.y_stride, pre_y_buffer - 16, pre_y_stride, 0x7fffffff);
near_sad[3] = cpi->fn_ptr[BLOCK_16X16].sdf(x->src.y_buffer, x->src.y_stride, pre_y_buffer, pre_y_stride, 0x7fffffff);
if(near_sad[6] != INT_MAX)
near_sad[6] = cpi->fn_ptr[BLOCK_16X16].sdf(x->src.y_buffer, x->src.y_stride, pre_y_buffer + 16, pre_y_stride, 0x7fffffff);
if(near_sad[7] != INT_MAX)
near_sad[7] = cpi->fn_ptr[BLOCK_16X16].sdf(x->src.y_buffer, x->src.y_stride, pre_y_buffer + pre_y_stride *16, pre_y_stride, 0x7fffffff);
}
if(cpi->common.last_frame_type != KEY_FRAME)
{
quicksortsad(near_sad, near_sadidx, 0, 7);
}else
{
quicksortsad(near_sad, near_sadidx, 0, 2);
}
saddone = 1; saddone = 1;
} }
......
...@@ -17,5 +17,17 @@ int vp8_rd_pick_intra16x16mby_mode(VP8_COMP *cpi, MACROBLOCK *x, int *returnrate ...@@ -17,5 +17,17 @@ int vp8_rd_pick_intra16x16mby_mode(VP8_COMP *cpi, MACROBLOCK *x, int *returnrate
int vp8_rd_pick_intra_mbuv_mode(VP8_COMP *cpi, MACROBLOCK *x, int *rate, int *rate_to, int *distortion); int vp8_rd_pick_intra_mbuv_mode(VP8_COMP *cpi, MACROBLOCK *x, int *rate, int *rate_to, int *distortion);
extern int vp8_rd_pick_inter_mode(VP8_COMP *cpi, MACROBLOCK *x, int recon_yoffset, int recon_uvoffset, int *returnrate, int *returndistortion, int *returnintra); extern int vp8_rd_pick_inter_mode(VP8_COMP *cpi, MACROBLOCK *x, int recon_yoffset, int recon_uvoffset, int *returnrate, int *returndistortion, int *returnintra);
extern void vp8_mv_pred
(
VP8_COMP *cpi,
MACROBLOCKD *xd,
const MODE_INFO *here,
MV *mvp,
int refframe,
int *ref_frame_sign_bias,
int *sr,
int near_sadidx[]
);
void vp8_cal_sad(VP8_COMP *cpi, MACROBLOCKD *xd, MACROBLOCK *x, int recon_yoffset, int near_sadidx[]);
#endif #endif
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment