[svn] / branches / dev-api-3 / xvidcore / src / motion / motion_est.c Repository:
ViewVC logotype

Diff of /branches/dev-api-3/xvidcore/src/motion/motion_est.c

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 801, Thu Jan 23 13:22:11 2003 UTC revision 819, Sat Feb 8 03:49:47 2003 UTC
# Line 50  Line 50 
50  #define MAX_SAD00_FOR_SKIP      (20)  #define MAX_SAD00_FOR_SKIP      (20)
51  #define MAX_CHROMA_SAD_FOR_SKIP (22)  #define MAX_CHROMA_SAD_FOR_SKIP (22)
52    
53  #define CHECK_CANDIDATE(X,Y,D) { \  #define CHECK_CANDIDATE(X,Y,D) { CheckCandidate((X),(Y), (D), &iDirection, data ); }
 (*CheckCandidate)((const int)(X),(const int)(Y), (D), &iDirection, data ); }  
54    
55  static __inline uint32_t  static __inline uint32_t
56  d_mv_bits(int x, int y, const VECTOR pred, const uint32_t iFcode, const int qpel, const int rrv)  d_mv_bits(int x, int y, const VECTOR pred, const uint32_t iFcode, const int qpel, const int rrv)
57  {  {
58          int xb, yb;          int xb, yb;
59          x += x * qpel; y += y * qpel;          x = qpel ? x<<1 : x;
60            y = qpel ? y<<1 : y;
61          if (rrv) { x = RRV_MV_SCALEDOWN(x); y = RRV_MV_SCALEDOWN(y); }          if (rrv) { x = RRV_MV_SCALEDOWN(x); y = RRV_MV_SCALEDOWN(y); }
62    
63          x -= pred.x;          x -= pred.x;
64          y -= pred.y;          y -= pred.y;
65    
# Line 202  Line 203 
203  {  {
204          switch ( ((x&1)<<1) | (y&1) ) {          switch ( ((x&1)<<1) | (y&1) ) {
205                  case 0 : return data->Ref + x/2 + (y/2)*(data->iEdgedWidth);                  case 0 : return data->Ref + x/2 + (y/2)*(data->iEdgedWidth);
206                    case 3 : return data->RefHV + (x-1)/2 + ((y-1)/2)*(data->iEdgedWidth);
207                  case 1 : return data->RefV + x/2 + ((y-1)/2)*(data->iEdgedWidth);                  case 1 : return data->RefV + x/2 + ((y-1)/2)*(data->iEdgedWidth);
208                  case 2 : return data->RefH + (x-1)/2 + (y/2)*(data->iEdgedWidth);                  default : return data->RefH + (x-1)/2 + (y/2)*(data->iEdgedWidth);      //case 2
                 default : return data->RefHV + (x-1)/2 + ((y-1)/2)*(data->iEdgedWidth);  
209          }          }
210  }  }
211    
# Line 265  Line 266 
266    
267          ref1 = GetReferenceB(halfpel_x, halfpel_y, dir, data);          ref1 = GetReferenceB(halfpel_x, halfpel_y, dir, data);
268          switch( ((x&1)<<1) + (y&1) ) {          switch( ((x&1)<<1) + (y&1) ) {
269          case 0: // pure halfpel position          case 3: // x and y in qpel resolution - the "corners" (top left/right and
270                  return (uint8_t *) ref1;                           // bottom left/right) during qpel refinement
271                    ref2 = GetReferenceB(halfpel_x, y - halfpel_y, dir, data);
272                    ref3 = GetReferenceB(x - halfpel_x, halfpel_y, dir, data);
273                    ref4 = GetReferenceB(x - halfpel_x, y - halfpel_y, dir, data);
274                    interpolate8x8_avg4(Reference, ref1, ref2, ref3, ref4, iEdgedWidth, rounding);
275                    interpolate8x8_avg4(Reference+8, ref1+8, ref2+8, ref3+8, ref4+8, iEdgedWidth, rounding);
276                    interpolate8x8_avg4(Reference+8*iEdgedWidth, ref1+8*iEdgedWidth, ref2+8*iEdgedWidth, ref3+8*iEdgedWidth, ref4+8*iEdgedWidth, iEdgedWidth, rounding);
277                    interpolate8x8_avg4(Reference+8*iEdgedWidth+8, ref1+8*iEdgedWidth+8, ref2+8*iEdgedWidth+8, ref3+8*iEdgedWidth+8, ref4+8*iEdgedWidth+8, iEdgedWidth, rounding);
278                    break;
279    
280          case 1: // x halfpel, y qpel - top or bottom during qpel refinement          case 1: // x halfpel, y qpel - top or bottom during qpel refinement
281                  ref2 = GetReferenceB(halfpel_x, y - halfpel_y, dir, data);                  ref2 = GetReferenceB(halfpel_x, y - halfpel_y, dir, data);
282                  interpolate8x8_avg2(Reference, ref1, ref2, iEdgedWidth, rounding, 8);                  interpolate8x8_avg2(Reference, ref1, ref2, iEdgedWidth, rounding, 8);
# Line 283  Line 293 
293                  interpolate8x8_avg2(Reference+8*iEdgedWidth+8, ref1+8*iEdgedWidth+8, ref2+8*iEdgedWidth+8, iEdgedWidth, rounding, 8);                  interpolate8x8_avg2(Reference+8*iEdgedWidth+8, ref1+8*iEdgedWidth+8, ref2+8*iEdgedWidth+8, iEdgedWidth, rounding, 8);
294                  break;                  break;
295    
296          default: // x and y in qpel resolution - the "corners" (top left/right and          case 0: // pure halfpel position
297                           // bottom left/right) during qpel refinement                  return (uint8_t *) ref1;
                 ref2 = GetReferenceB(halfpel_x, y - halfpel_y, dir, data);  
                 ref3 = GetReferenceB(x - halfpel_x, halfpel_y, dir, data);  
                 ref4 = GetReferenceB(x - halfpel_x, y - halfpel_y, dir, data);  
                 interpolate8x8_avg4(Reference, ref1, ref2, ref3, ref4, iEdgedWidth, rounding);  
                 interpolate8x8_avg4(Reference+8, ref1+8, ref2+8, ref3+8, ref4+8, iEdgedWidth, rounding);  
                 interpolate8x8_avg4(Reference+8*iEdgedWidth, ref1+8*iEdgedWidth, ref2+8*iEdgedWidth, ref3+8*iEdgedWidth, ref4+8*iEdgedWidth, iEdgedWidth, rounding);  
                 interpolate8x8_avg4(Reference+8*iEdgedWidth+8, ref1+8*iEdgedWidth+8, ref2+8*iEdgedWidth+8, ref3+8*iEdgedWidth+8, ref4+8*iEdgedWidth+8, iEdgedWidth, rounding);  
                 break;  
298          }          }
299          return Reference;          return Reference;
300  }  }
# Line 302  Line 304 
304  static void  static void
305  CheckCandidate16(const int x, const int y, const int Direction, int * const dir, const SearchData * const data)  CheckCandidate16(const int x, const int y, const int Direction, int * const dir, const SearchData * const data)
306  {  {
307          int t, xc, yc;          int xc, yc;
308          const uint8_t * Reference;          const uint8_t * Reference;
309          VECTOR * current;          VECTOR * current;
310            int32_t sad; uint32_t t;
311    
312          if ( (x > data->max_dx) | (x < data->min_dx)          if ( (x > data->max_dx) || (x < data->min_dx)
313                  | (y > data->max_dy) | (y < data->min_dy) ) return;                  || (y > data->max_dy) || (y < data->min_dy) ) return;
314    
315          if (data->qpel_precision) { // x and y are in 1/4 precision          if (!data->qpel_precision) {
                 Reference = Interpolate16x16qpel(x, y, 0, data);  
                 xc = x/2; yc = y/2; //for chroma sad  
                 current = data->currentQMV;  
         } else {  
316                  Reference = GetReference(x, y, data);                  Reference = GetReference(x, y, data);
317                  current = data->currentMV;                  current = data->currentMV;
318                  xc = x; yc = y;                  xc = x; yc = y;
319            } else { // x and y are in 1/4 precision
320                    Reference = Interpolate16x16qpel(x, y, 0, data);
321                    xc = x/2; yc = y/2; //for chroma sad
322                    current = data->currentQMV;
323          }          }
         t = d_mv_bits(x, y, data->predMV, data->iFcode, data->qpel^data->qpel_precision, 0);  
324    
325          data->temp[0] = sad16v(data->Cur, Reference, data->iEdgedWidth, data->temp + 1);          sad = sad16v(data->Cur, Reference, data->iEdgedWidth, data->temp + 1);
326            t = d_mv_bits(x, y, data->predMV, data->iFcode, data->qpel^data->qpel_precision, 0);
327    
328          data->temp[0] += (data->lambda16 * t * data->temp[0])>>10;          sad += (data->lambda16 * t * sad)>>10;
329          data->temp[1] += (data->lambda8 * t * (data->temp[1] + NEIGH_8X8_BIAS))>>10;          data->temp[1] += (data->lambda8 * t * (data->temp[1] + NEIGH_8X8_BIAS))>>10;
330    
331          if (data->chroma) data->temp[0] += ChromaSAD((xc >> 1) + roundtab_79[xc & 0x3],          if (data->chroma) sad += ChromaSAD((xc >> 1) + roundtab_79[xc & 0x3],
332                                                                                                          (yc >> 1) + roundtab_79[yc & 0x3], data);                                                                                                          (yc >> 1) + roundtab_79[yc & 0x3], data);
333    
334          if (data->temp[0] < data->iMinSAD[0]) {          if (sad < data->iMinSAD[0]) {
335                  data->iMinSAD[0] = data->temp[0];                  data->iMinSAD[0] = sad;
336                  current[0].x = x; current[0].y = y;                  current[0].x = x; current[0].y = y;
337                  *dir = Direction; }                  *dir = Direction;
338            }
339    
340          if (data->temp[1] < data->iMinSAD[1]) {          if (data->temp[1] < data->iMinSAD[1]) {
341                  data->iMinSAD[1] = data->temp[1]; current[1].x = x; current[1].y= y; }                  data->iMinSAD[1] = data->temp[1]; current[1].x = x; current[1].y= y; }
# Line 345  Line 349 
349  }  }
350    
351  static void  static void
352    CheckCandidate8(const int x, const int y, const int Direction, int * const dir, const SearchData * const data)
353    {
354            int32_t sad; uint32_t t;
355            const uint8_t * Reference;
356    
357            if ( (x > data->max_dx) || (x < data->min_dx)
358                    || (y > data->max_dy) || (y < data->min_dy) ) return;
359    
360            if (!data->qpel_precision) Reference = GetReference(x, y, data);
361            else Reference = Interpolate8x8qpel(x, y, 0, 0, data);
362    
363            sad = sad8(data->Cur, Reference, data->iEdgedWidth);
364            t = d_mv_bits(x, y, data->predMV, data->iFcode, data->qpel^data->qpel_precision, 0);
365    
366            sad += (data->lambda8 * t * (sad+NEIGH_8X8_BIAS))>>10;
367    
368            if (sad < *(data->iMinSAD)) {
369                    *(data->iMinSAD) = sad;
370                    data->currentMV->x = x; data->currentMV->y = y;
371                    *dir = Direction;
372            }
373    }
374    
375    
376    static void
377  CheckCandidate32(const int x, const int y, const int Direction, int * const dir, const SearchData * const data)  CheckCandidate32(const int x, const int y, const int Direction, int * const dir, const SearchData * const data)
378  {  {
379          uint32_t t;          uint32_t t;
380          const uint8_t * Reference;          const uint8_t * Reference;
381    
382          if ( (!(x&1) && x !=0) | (!(y&1) && y !=0) || //non-zero integer value          if ( (!(x&1) && x !=0) || (!(y&1) && y !=0) || //non-zero integer value
383                  (x > data->max_dx) | (x < data->min_dx)                  (x > data->max_dx) || (x < data->min_dx)
384                  | (y > data->max_dy) | (y < data->min_dy) ) return;                  || (y > data->max_dy) || (y < data->min_dy) ) return;
385    
386          Reference = GetReference(x, y, data);          Reference = GetReference(x, y, data);
387          t = d_mv_bits(x, y, data->predMV, data->iFcode, 0, 1);          t = d_mv_bits(x, y, data->predMV, data->iFcode, 0, 1);
# Line 420  Line 449 
449  CheckCandidate32I(const int x, const int y, const int Direction, int * const dir, const SearchData * const data)  CheckCandidate32I(const int x, const int y, const int Direction, int * const dir, const SearchData * const data)
450  {  {
451  // maximum speed - for P/B/I decision  // maximum speed - for P/B/I decision
452            int32_t sad;
453    
454          if ( (x > data->max_dx) | (x < data->min_dx)          if ( (x > data->max_dx) || (x < data->min_dx)
455                  | (y > data->max_dy) | (y < data->min_dy) ) return;                  || (y > data->max_dy) || (y < data->min_dy) ) return;
456    
457          data->temp[0] = sad32v_c(data->Cur, data->Ref + x/2 + (y/2)*(data->iEdgedWidth),          sad = sad32v_c(data->Cur, data->Ref + x/2 + (y/2)*(data->iEdgedWidth),
458                                                          data->iEdgedWidth, data->temp+1);                                                          data->iEdgedWidth, data->temp+1);
459    
460          if (data->temp[0] < *(data->iMinSAD)) {          if (sad < *(data->iMinSAD)) {
461                  *(data->iMinSAD) = data->temp[0];                  *(data->iMinSAD) = sad;
462                  data->currentMV[0].x = x; data->currentMV[0].y = y;                  data->currentMV[0].x = x; data->currentMV[0].y = y;
463                  *dir = Direction; }                  *dir = Direction;
464            }
465          if (data->temp[1] < data->iMinSAD[1]) {          if (data->temp[1] < data->iMinSAD[1]) {
466                  data->iMinSAD[1] = data->temp[1]; data->currentMV[1].x = x; data->currentMV[1].y = y; }                  data->iMinSAD[1] = data->temp[1]; data->currentMV[1].x = x; data->currentMV[1].y = y; }
467          if (data->temp[2] < data->iMinSAD[2]) {          if (data->temp[2] < data->iMinSAD[2]) {
# Line 598  Line 629 
629          }          }
630  }  }
631    
 static void  
 CheckCandidate8(const int x, const int y, const int Direction, int * const dir, const SearchData * const data)  
 {  
         int32_t sad; uint32_t t;  
         const uint8_t * Reference;  
   
         if ( (x > data->max_dx) | (x < data->min_dx)  
                 | (y > data->max_dy) | (y < data->min_dy) ) return;  
   
         if (data->qpel) Reference = Interpolate16x16qpel(x, y, 0, data);  
         else Reference = GetReference(x, y, data);  
   
         sad = sad8(data->Cur, Reference, data->iEdgedWidth);  
         t = d_mv_bits(x, y, data->predMV, data->iFcode, data->qpel^data->qpel_precision, 0);  
   
         sad += (data->lambda8 * t * (sad+NEIGH_8X8_BIAS))>>10;  
   
         if (sad < *(data->iMinSAD)) {  
                 *(data->iMinSAD) = sad;  
                 data->currentMV->x = x; data->currentMV->y = y;  
                 *dir = Direction; }  
 }  
   
632  /* CHECK_CANDIATE FUNCTIONS END */  /* CHECK_CANDIATE FUNCTIONS END */
633    
634  /* MAINSEARCH FUNCTIONS START */  /* MAINSEARCH FUNCTIONS START */
# Line 1103  Line 1111 
1111    
1112          for (i = 1; i < 7; i++) {          for (i = 1; i < 7; i++) {
1113                  if (!(mask = make_mask(pmv, i)) ) continue;                  if (!(mask = make_mask(pmv, i)) ) continue;
1114                  (*CheckCandidate)(pmv[i].x, pmv[i].y, mask, &iDirection, Data);                  CheckCandidate(pmv[i].x, pmv[i].y, mask, &iDirection, Data);
1115                  if (Data->iMinSAD[0] <= threshA) break;                  if (Data->iMinSAD[0] <= threshA) break;
1116          }          }
1117    
# Line 1136  Line 1144 
1144                          if (!(MVequal(startMV, backupMV))) {                          if (!(MVequal(startMV, backupMV))) {
1145                                  bSAD = Data->iMinSAD[0]; Data->iMinSAD[0] = MV_MAX_ERROR;                                  bSAD = Data->iMinSAD[0]; Data->iMinSAD[0] = MV_MAX_ERROR;
1146    
1147                                  (*CheckCandidate)(startMV.x, startMV.y, 255, &iDirection, Data);                                  CheckCandidate(startMV.x, startMV.y, 255, &iDirection, Data);
1148                                  (*MainSearchPtr)(startMV.x, startMV.y, Data, 255);                                  (*MainSearchPtr)(startMV.x, startMV.y, Data, 255);
1149                                  if (bSAD < Data->iMinSAD[0]) {                                  if (bSAD < Data->iMinSAD[0]) {
1150                                          Data->currentMV[0] = backupMV;                                          Data->currentMV[0] = backupMV;
# Line 1149  Line 1157 
1157                          if (!(MVequal(startMV, backupMV))) {                          if (!(MVequal(startMV, backupMV))) {
1158                                  bSAD = Data->iMinSAD[0]; Data->iMinSAD[0] = MV_MAX_ERROR;                                  bSAD = Data->iMinSAD[0]; Data->iMinSAD[0] = MV_MAX_ERROR;
1159    
1160                                  (*CheckCandidate)(startMV.x, startMV.y, 255, &iDirection, Data);                                  CheckCandidate(startMV.x, startMV.y, 255, &iDirection, Data);
1161                                  (*MainSearchPtr)(startMV.x, startMV.y, Data, 255);                                  (*MainSearchPtr)(startMV.x, startMV.y, Data, 255);
1162                                  if (bSAD < Data->iMinSAD[0]) {                                  if (bSAD < Data->iMinSAD[0]) {
1163                                          Data->currentMV[0] = backupMV;                                          Data->currentMV[0] = backupMV;
# Line 1581  Line 1589 
1589    
1590          CheckCandidate = b_mb->mode == MODE_INTER4V ? CheckCandidateDirect : CheckCandidateDirectno4v;          CheckCandidate = b_mb->mode == MODE_INTER4V ? CheckCandidateDirect : CheckCandidateDirectno4v;
1591    
1592          (*CheckCandidate)(0, 0, 255, &k, Data);          CheckCandidate(0, 0, 255, &k, Data);
1593    
1594  // initial (fast) skip decision  // initial (fast) skip decision
1595          if (*Data->iMinSAD < pMB->quant * INITIAL_SKIP_THRESH * (2 + Data->chroma?1:0)) {          if (*Data->iMinSAD < pMB->quant * INITIAL_SKIP_THRESH * (2 + Data->chroma?1:0)) {

Legend:
Removed from v.801  
changed lines
  Added in v.819

No admin address has been configured
ViewVC Help
Powered by ViewVC 1.0.4