#include <limits.h>
#include "avcodec.h"
+#include "internal.h"
#include "mathops.h"
+#include "motion_est.h"
#include "mpegutils.h"
#include "mpegvideo.h"
#define P_MEDIAN P[4]
#define P_MV1 P[9]
+#define ME_MAP_SHIFT 3
+#define ME_MAP_MV_BITS 11
+
static int sad_hpel_motion_search(MpegEncContext * s,
int *mx_ptr, int *my_ptr, int dmin,
int src_index, int ref_index,
}
static int get_flags(MotionEstContext *c, int direct, int chroma){
- return ((c->avctx->flags&CODEC_FLAG_QPEL) ? FLAG_QPEL : 0)
+ return ((c->avctx->flags&AV_CODEC_FLAG_QPEL) ? FLAG_QPEL : 0)
+ (direct ? FLAG_DIRECT : 0)
+ (chroma ? FLAG_CHROMA : 0);
}
#include "motion_est_template.c"
static int zero_cmp(MpegEncContext *s, uint8_t *a, uint8_t *b,
- int stride, int h)
+ ptrdiff_t stride, int h)
{
return 0;
}
av_log(s->avctx, AV_LOG_ERROR, "ME_MAP size is too small for SAB diamond\n");
return -1;
}
- if (s->me_method != ME_ZERO &&
- s->me_method != ME_EPZS &&
- s->me_method != ME_X1) {
- av_log(s->avctx, AV_LOG_ERROR, "me_method is only allowed to be set to zero and epzs; for hex,umh,full and others see dia_size\n");
- return -1;
+
+#if FF_API_MOTION_EST
+FF_DISABLE_DEPRECATION_WARNINGS
+ if (s->motion_est == FF_ME_EPZS) {
+ if (s->me_method == ME_ZERO)
+ s->motion_est = FF_ME_ZERO;
+ else if (s->me_method == ME_EPZS)
+ s->motion_est = FF_ME_EPZS;
+ else if (s->me_method == ME_X1)
+ s->motion_est = FF_ME_XONE;
+ else {
+ av_log(s->avctx, AV_LOG_ERROR,
+ "me_method is only allowed to be set to zero and epzs; "
+ "for hex,umh,full and others see dia_size\n");
+ return -1;
+ }
}
+FF_ENABLE_DEPRECATION_WARNINGS
+#endif
c->avctx= s->avctx;
av_log(s->avctx, AV_LOG_INFO, "ME_MAP size may be a little small for the selected diamond size\n");
}
- ff_set_cmp(&s->dsp, s->dsp.me_pre_cmp, c->avctx->me_pre_cmp);
- ff_set_cmp(&s->dsp, s->dsp.me_cmp, c->avctx->me_cmp);
- ff_set_cmp(&s->dsp, s->dsp.me_sub_cmp, c->avctx->me_sub_cmp);
- ff_set_cmp(&s->dsp, s->dsp.mb_cmp, c->avctx->mb_cmp);
+ ff_set_cmp(&s->mecc, s->mecc.me_pre_cmp, c->avctx->me_pre_cmp);
+ ff_set_cmp(&s->mecc, s->mecc.me_cmp, c->avctx->me_cmp);
+ ff_set_cmp(&s->mecc, s->mecc.me_sub_cmp, c->avctx->me_sub_cmp);
+ ff_set_cmp(&s->mecc, s->mecc.mb_cmp, c->avctx->mb_cmp);
c->flags = get_flags(c, 0, c->avctx->me_cmp &FF_CMP_CHROMA);
c->sub_flags= get_flags(c, 0, c->avctx->me_sub_cmp&FF_CMP_CHROMA);
c->mb_flags = get_flags(c, 0, c->avctx->mb_cmp &FF_CMP_CHROMA);
/*FIXME s->no_rounding b_type*/
- if(s->flags&CODEC_FLAG_QPEL){
+ if (s->avctx->flags & AV_CODEC_FLAG_QPEL) {
c->sub_motion_search= qpel_motion_search;
c->qpel_avg = s->qdsp.avg_qpel_pixels_tab;
if (s->no_rounding)
/* 8x8 fullpel search would need a 4x4 chroma compare, which we do
* not have yet, and even if we had, the motion estimation code
* does not expect it. */
- if((c->avctx->me_cmp&FF_CMP_CHROMA)/* && !s->dsp.me_cmp[2]*/){
- s->dsp.me_cmp[2]= zero_cmp;
- }
- if((c->avctx->me_sub_cmp&FF_CMP_CHROMA) && !s->dsp.me_sub_cmp[2]){
- s->dsp.me_sub_cmp[2]= zero_cmp;
- }
+ if ((c->avctx->me_cmp & FF_CMP_CHROMA) /* && !s->mecc.me_cmp[2] */)
+ s->mecc.me_cmp[2] = zero_cmp;
+ if ((c->avctx->me_sub_cmp & FF_CMP_CHROMA) && !s->mecc.me_sub_cmp[2])
+ s->mecc.me_sub_cmp[2] = zero_cmp;
c->hpel_put[2][0]= c->hpel_put[2][1]=
c->hpel_put[2][2]= c->hpel_put[2][3]= zero_hpel;
#define CHECK_SAD_HALF_MV(suffix, x, y) \
{\
- d= s->dsp.pix_abs[size][(x?1:0)+(y?2:0)](NULL, pix, ptr+((x)>>1), stride, h);\
+ d = s->mecc.pix_abs[size][(x ? 1 : 0) + (y ? 2 : 0)](NULL, pix, ptr + ((x) >> 1), stride, h); \
d += (mv_penalty[pen_x + x] + mv_penalty[pen_y + y])*penalty_factor;\
COPY3_IF_LT(dminh, d, dx, x, dy, y)\
}
dmin4= c->sub_motion_search(s, &mx4, &my4, dmin4, block, block, size, h);
- if(s->dsp.me_sub_cmp[0] != s->dsp.mb_cmp[0]){
+ if (s->mecc.me_sub_cmp[0] != s->mecc.mb_cmp[0]) {
int dxy;
const int offset= ((block&1) + (block>>1)*stride)*8;
uint8_t *dest_y = c->scratchpad + offset;
if(same)
return INT_MAX;
- if(s->dsp.me_sub_cmp[0] != s->dsp.mb_cmp[0]){
- dmin_sum += s->dsp.mb_cmp[0](s, s->new_picture.f->data[0] + s->mb_x*16 + s->mb_y*16*stride, c->scratchpad, stride, 16);
+ if (s->mecc.me_sub_cmp[0] != s->mecc.mb_cmp[0]) {
+ dmin_sum += s->mecc.mb_cmp[0](s,
+ s->new_picture.f->data[0] +
+ s->mb_x * 16 + s->mb_y * 16 * stride,
+ c->scratchpad, stride, 16);
}
if(c->avctx->mb_cmp&FF_CMP_CHROMA){
s->hdsp.put_pixels_tab [1][dxy](c->scratchpad + 8, s->last_picture.f->data[2] + offset, s->uvlinesize, 8);
}
- dmin_sum += s->dsp.mb_cmp[1](s, s->new_picture.f->data[1] + s->mb_x*8 + s->mb_y*8*s->uvlinesize, c->scratchpad , s->uvlinesize, 8);
- dmin_sum += s->dsp.mb_cmp[1](s, s->new_picture.f->data[2] + s->mb_x*8 + s->mb_y*8*s->uvlinesize, c->scratchpad+8, s->uvlinesize, 8);
+ dmin_sum += s->mecc.mb_cmp[1](s, s->new_picture.f->data[1] + s->mb_x * 8 + s->mb_y * 8 * s->uvlinesize, c->scratchpad, s->uvlinesize, 8);
+ dmin_sum += s->mecc.mb_cmp[1](s, s->new_picture.f->data[2] + s->mb_x * 8 + s->mb_y * 8 * s->uvlinesize, c->scratchpad + 8, s->uvlinesize, 8);
}
c->pred_x= mx;
mv_table[xy][0]= mx_i;
mv_table[xy][1]= my_i;
- if(s->dsp.me_sub_cmp[0] != s->dsp.mb_cmp[0]){
+ if (s->mecc.me_sub_cmp[0] != s->mecc.mb_cmp[0]) {
int dxy;
//FIXME chroma ME
}else{
s->hdsp.put_pixels_tab [size][dxy](c->scratchpad, ref , stride, h);
}
- dmin= s->dsp.mb_cmp[size](s, c->src[block][0], c->scratchpad, stride, h);
+ dmin = s->mecc.mb_cmp[size](s, c->src[block][0], c->scratchpad, stride, h);
dmin+= (mv_penalty[mx_i-c->pred_x] + mv_penalty[my_i-c->pred_y] + 1)*c->mb_penalty_factor;
}else
dmin+= c->mb_penalty_factor; //field_select bits
{
MotionEstContext * const c= &s->me;
uint8_t *pix, *ppix;
- int sum, mx, my, dmin;
+ int sum, mx = 0, my = 0, dmin = 0;
int varc; ///< the variance of the block (sum of squared (p[y][x]-average))
int vard; ///< sum of squared differences with the estimated motion vector
int P[10][2];
pic->mb_var [s->mb_stride * mb_y + mb_x] = (varc+128)>>8;
c->mb_var_sum_temp += (varc+128)>>8;
- switch(s->me_method) {
- case ME_ZERO:
- default:
- mx = 0;
- my = 0;
- dmin = 0;
- break;
- case ME_X1:
- case ME_EPZS:
- {
- const int mot_stride = s->b8_stride;
- const int mot_xy = s->block_index[0];
-
- P_LEFT[0] = s->current_picture.motion_val[0][mot_xy - 1][0];
- P_LEFT[1] = s->current_picture.motion_val[0][mot_xy - 1][1];
-
- if(P_LEFT[0] > (c->xmax<<shift)) P_LEFT[0] = (c->xmax<<shift);
-
- if(!s->first_slice_line) {
- P_TOP[0] = s->current_picture.motion_val[0][mot_xy - mot_stride ][0];
- P_TOP[1] = s->current_picture.motion_val[0][mot_xy - mot_stride ][1];
- P_TOPRIGHT[0] = s->current_picture.motion_val[0][mot_xy - mot_stride + 2][0];
- P_TOPRIGHT[1] = s->current_picture.motion_val[0][mot_xy - mot_stride + 2][1];
- if(P_TOP[1] > (c->ymax<<shift)) P_TOP[1] = (c->ymax<<shift);
- if(P_TOPRIGHT[0] < (c->xmin<<shift)) P_TOPRIGHT[0]= (c->xmin<<shift);
- if(P_TOPRIGHT[1] > (c->ymax<<shift)) P_TOPRIGHT[1]= (c->ymax<<shift);
+ if (s->motion_est != FF_ME_ZERO) {
+ const int mot_stride = s->b8_stride;
+ const int mot_xy = s->block_index[0];
- P_MEDIAN[0]= mid_pred(P_LEFT[0], P_TOP[0], P_TOPRIGHT[0]);
- P_MEDIAN[1]= mid_pred(P_LEFT[1], P_TOP[1], P_TOPRIGHT[1]);
+ P_LEFT[0] = s->current_picture.motion_val[0][mot_xy - 1][0];
+ P_LEFT[1] = s->current_picture.motion_val[0][mot_xy - 1][1];
- if(s->out_format == FMT_H263){
- c->pred_x = P_MEDIAN[0];
- c->pred_y = P_MEDIAN[1];
- }else { /* mpeg1 at least */
- c->pred_x= P_LEFT[0];
- c->pred_y= P_LEFT[1];
- }
- }else{
- c->pred_x= P_LEFT[0];
- c->pred_y= P_LEFT[1];
- }
+ if (P_LEFT[0] > (c->xmax << shift))
+ P_LEFT[0] = c->xmax << shift;
+
+ if (!s->first_slice_line) {
+ P_TOP[0] = s->current_picture.motion_val[0][mot_xy - mot_stride ][0];
+ P_TOP[1] = s->current_picture.motion_val[0][mot_xy - mot_stride ][1];
+ P_TOPRIGHT[0] = s->current_picture.motion_val[0][mot_xy - mot_stride + 2][0];
+ P_TOPRIGHT[1] = s->current_picture.motion_val[0][mot_xy - mot_stride + 2][1];
+ if (P_TOP[1] > (c->ymax << shift))
+ P_TOP[1] = c->ymax << shift;
+ if (P_TOPRIGHT[0] < (c->xmin << shift))
+ P_TOPRIGHT[0] = c->xmin << shift;
+ if (P_TOPRIGHT[1] > (c->ymax << shift))
+ P_TOPRIGHT[1] = c->ymax << shift;
+
+ P_MEDIAN[0] = mid_pred(P_LEFT[0], P_TOP[0], P_TOPRIGHT[0]);
+ P_MEDIAN[1] = mid_pred(P_LEFT[1], P_TOP[1], P_TOPRIGHT[1]);
+ if (s->out_format == FMT_H263) {
+ c->pred_x = P_MEDIAN[0];
+ c->pred_y = P_MEDIAN[1];
+ } else { /* mpeg1 at least */
+ c->pred_x = P_LEFT[0];
+ c->pred_y = P_LEFT[1];
+ }
+ } else {
+ c->pred_x = P_LEFT[0];
+ c->pred_y = P_LEFT[1];
}
dmin = ff_epzs_motion_search(s, &mx, &my, P, 0, 0, s->p_mv_table, (1<<16)>>shift, 0, 16);
-
- break;
}
/* At this point (mx,my) are full-pell and the relative displacement */
ppix = c->ref[0][0] + (my * s->linesize) + mx;
- vard = s->dsp.sse[0](NULL, pix, ppix, s->linesize, 16);
+ vard = s->mecc.sse[0](NULL, pix, ppix, s->linesize, 16);
pic->mc_mb_var[s->mb_stride * mb_y + mb_x] = (vard+128)>>8;
c->mc_mb_var_sum_temp += (vard+128)>>8;
- if(mb_type){
- int p_score= FFMIN(vard, varc-500+(s->lambda2>>FF_LAMBDA_SHIFT)*100);
- int i_score= varc-500+(s->lambda2>>FF_LAMBDA_SHIFT)*20;
- c->scene_change_score+= ff_sqrt(p_score) - ff_sqrt(i_score);
-
- if(mb_type == CANDIDATE_MB_TYPE_INTER){
- c->sub_motion_search(s, &mx, &my, dmin, 0, 0, 0, 16);
- set_p_mv_tables(s, mx, my, 1);
- }else{
- mx <<=shift;
- my <<=shift;
- }
- if(mb_type == CANDIDATE_MB_TYPE_INTER4V){
- h263_mv4_search(s, mx, my, shift);
-
- set_p_mv_tables(s, mx, my, 0);
- }
- if(mb_type == CANDIDATE_MB_TYPE_INTER_I){
- interlaced_search(s, 0, s->p_field_mv_table, s->p_field_select_table, mx, my, 1);
- }
- }else if(c->avctx->mb_decision > FF_MB_DECISION_SIMPLE){
+ if (c->avctx->mb_decision > FF_MB_DECISION_SIMPLE) {
int p_score= FFMIN(vard, varc-500+(s->lambda2>>FF_LAMBDA_SHIFT)*100);
int i_score= varc-500+(s->lambda2>>FF_LAMBDA_SHIFT)*20;
c->scene_change_score+= ff_sqrt(p_score) - ff_sqrt(i_score);
mx <<=shift;
my <<=shift;
}
- if((s->flags&CODEC_FLAG_4MV)
+ if ((s->avctx->flags & AV_CODEC_FLAG_4MV)
&& !c->skip && varc>50<<8 && vard>10<<8){
if(h263_mv4_search(s, mx, my, shift) < INT_MAX)
mb_type|=CANDIDATE_MB_TYPE_INTER4V;
set_p_mv_tables(s, mx, my, 0);
}else
set_p_mv_tables(s, mx, my, 1);
- if((s->flags&CODEC_FLAG_INTERLACED_ME)
+ if ((s->avctx->flags & AV_CODEC_FLAG_INTERLACED_ME)
&& !c->skip){ //FIXME varc/d checks
if(interlaced_search(s, 0, s->p_field_mv_table, s->p_field_select_table, mx, my, 0) < INT_MAX)
mb_type |= CANDIDATE_MB_TYPE_INTER_I;
if(c->avctx->me_sub_cmp != c->avctx->mb_cmp && !c->skip)
dmin= get_mb_score(s, mx, my, 0, 0, 0, 16, 1);
- if((s->flags&CODEC_FLAG_4MV)
+ if ((s->avctx->flags & AV_CODEC_FLAG_4MV)
&& !c->skip && varc>50<<8 && vard>10<<8){
int dmin4= h263_mv4_search(s, mx, my, shift);
if(dmin4 < dmin){
dmin=dmin4;
}
}
- if((s->flags&CODEC_FLAG_INTERLACED_ME)
+ if ((s->avctx->flags & AV_CODEC_FLAG_INTERLACED_ME)
&& !c->skip){ //FIXME varc/d checks
int dmin_i= interlaced_search(s, 0, s->p_field_mv_table, s->p_field_select_table, mx, my, 0);
if(dmin_i < dmin){
*(uint32_t*)(&c->scratchpad[i*s->linesize+12]) = mean;
}
- intra_score= s->dsp.mb_cmp[0](s, c->scratchpad, pix, s->linesize, 16);
+ intra_score= s->mecc.mb_cmp[0](s, c->scratchpad, pix, s->linesize, 16);
}
intra_score += c->mb_penalty_factor*16;
int16_t (*mv_table)[2], int ref_index, int f_code)
{
MotionEstContext * const c= &s->me;
- int mx, my, dmin;
+ int mx = 0, my = 0, dmin = 0;
int P[10][2];
const int shift= 1+s->quarter_sample;
const int mot_stride = s->mb_stride;
get_limits(s, 16*mb_x, 16*mb_y);
- switch(s->me_method) {
- case ME_ZERO:
- default:
- mx = 0;
- my = 0;
- dmin = 0;
- break;
- case ME_X1:
- case ME_EPZS:
+ if (s->motion_est != FF_ME_ZERO) {
P_LEFT[0] = mv_table[mot_xy - 1][0];
P_LEFT[1] = mv_table[mot_xy - 1][1];
}
dmin = ff_epzs_motion_search(s, &mx, &my, P, 0, ref_index, s->p_mv_table, mv_scale, 0, 16);
-
- break;
}
dmin= c->sub_motion_search(s, &mx, &my, dmin, 0, ref_index, 0, 16);
fbmin = (mv_penalty_f[motion_fx-pred_fx] + mv_penalty_f[motion_fy-pred_fy])*c->mb_penalty_factor
+(mv_penalty_b[motion_bx-pred_bx] + mv_penalty_b[motion_by-pred_by])*c->mb_penalty_factor
- + s->dsp.mb_cmp[size](s, src_data[0], dest_y, stride, h); //FIXME new_pic
+ + s->mecc.mb_cmp[size](s, src_data[0], dest_y, stride, h); // FIXME new_pic
if(c->avctx->mb_cmp&FF_CMP_CHROMA){
}
c->skip=0;
bmin = estimate_motion_b(s, mb_x, mb_y, s->b_back_mv_table, 2, s->b_code) +
2 * penalty_factor;
- av_dlog(s, " %d %d ", s->b_forw_mv_table[xy][0], s->b_forw_mv_table[xy][1]);
+ ff_dlog(s, " %d %d ", s->b_forw_mv_table[xy][0], s->b_forw_mv_table[xy][1]);
c->skip=0;
fbmin= bidir_refine(s, mb_x, mb_y) + penalty_factor;
- av_dlog(s, "%d %d %d %d\n", dmin, fmin, bmin, fbmin);
+ ff_dlog(s, "%d %d %d %d\n", dmin, fmin, bmin, fbmin);
- if(s->flags & CODEC_FLAG_INTERLACED_ME){
+ if (s->avctx->flags & AV_CODEC_FLAG_INTERLACED_ME) {
//FIXME mb type penalty
c->skip=0;
c->current_mv_penalty= c->mv_penalty[s->f_code] + MAX_MV;
/* find best f_code for ME which do unlimited searches */
int ff_get_best_fcode(MpegEncContext * s, int16_t (*mv_table)[2], int type)
{
- if(s->me_method>=ME_EPZS){
+ if (s->motion_est != FF_ME_ZERO) {
int score[8];
int i, y, range= s->avctx->me_range ? s->avctx->me_range : (INT_MAX/2);
uint8_t * fcode_tab= s->fcode_tab;
if(c->avctx->me_range && range > c->avctx->me_range) range= c->avctx->me_range;
- if(s->flags&CODEC_FLAG_4MV){
+ if (s->avctx->flags & AV_CODEC_FLAG_4MV) {
const int wrap= s->b8_stride;
/* clip / convert to intra 8x8 type MVs */
int xy= y*s->mb_stride;
for(x=0; x<s->mb_width; x++){
if (s->mb_type[xy] & type){ // RAL: "type" test added...
- if(field_select_table==NULL || field_select_table[xy] == field_select){
+ if (!field_select_table || field_select_table[xy] == field_select) {
if( mv_table[xy][0] >=h_range || mv_table[xy][0] <-h_range
|| mv_table[xy][1] >=v_range || mv_table[xy][1] <-v_range){