[cvs] / xvidcore / src / decoder.c Repository:
ViewVC logotype

Diff of /xvidcore/src/decoder.c

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

revision 1.57, Fri May 21 14:40:15 2004 UTC revision 1.75, Tue Nov 22 10:23:01 2005 UTC
# Line 46  Line 46 
46  #include "dct/fdct.h"  #include "dct/fdct.h"
47  #include "utils/mem_transfer.h"  #include "utils/mem_transfer.h"
48  #include "image/interpolate8x8.h"  #include "image/interpolate8x8.h"
 #include "image/reduced.h"  
49  #include "image/font.h"  #include "image/font.h"
50    #include "image/qpel.h"
51    
52  #include "bitstream/mbcoding.h"  #include "bitstream/mbcoding.h"
53  #include "prediction/mbprediction.h"  #include "prediction/mbprediction.h"
# Line 61  Line 61 
61  #include "image/postprocessing.h"  #include "image/postprocessing.h"
62  #include "utils/mem_align.h"  #include "utils/mem_align.h"
63    
64    #define DIV2ROUND(n)  (((n)>>1)|((n)&1))
65    #define DIV2(n)       ((n)>>1)
66    #define DIVUVMOV(n) (((n) >> 1) + roundtab_79[(n) & 0x3]) //
67    
68  static int  static int
69  decoder_resize(DECODER * dec)  decoder_resize(DECODER * dec)
70  {  {
# Line 73  Line 77 
77    
78          image_destroy(&dec->gmc, dec->edged_width, dec->edged_height);          image_destroy(&dec->gmc, dec->edged_width, dec->edged_height);
79    
80          if (dec->last_mbs)    image_null(&dec->cur);
81      image_null(&dec->refn[0]);
82      image_null(&dec->refn[1]);
83      image_null(&dec->tmp);
84      image_null(&dec->qtmp);
85      image_null(&dec->gmc);
86    
87    
88                  xvid_free(dec->last_mbs);                  xvid_free(dec->last_mbs);
         if (dec->mbs)  
89                  xvid_free(dec->mbs);                  xvid_free(dec->mbs);
         if (dec->qscale)  
90                  xvid_free(dec->qscale);                  xvid_free(dec->qscale);
91      dec->last_mbs = NULL;
92      dec->mbs = NULL;
93      dec->qscale = NULL;
94    
95          /* realloc */          /* realloc */
96          dec->mb_width = (dec->width + 15) / 16;          dec->mb_width = (dec->width + 15) / 16;
# Line 87  Line 99 
99          dec->edged_width = 16 * dec->mb_width + 2 * EDGE_SIZE;          dec->edged_width = 16 * dec->mb_width + 2 * EDGE_SIZE;
100          dec->edged_height = 16 * dec->mb_height + 2 * EDGE_SIZE;          dec->edged_height = 16 * dec->mb_height + 2 * EDGE_SIZE;
101    
102          if (image_create(&dec->cur, dec->edged_width, dec->edged_height)) {          if (   image_create(&dec->cur, dec->edged_width, dec->edged_height)
103                  xvid_free(dec);              || image_create(&dec->refn[0], dec->edged_width, dec->edged_height)
104                  return XVID_ERR_MEMORY;              || image_create(&dec->refn[1], dec->edged_width, dec->edged_height)         /* Support B-frame to reference last 2 frame */
105          }              || image_create(&dec->tmp, dec->edged_width, dec->edged_height)
106                || image_create(&dec->qtmp, dec->edged_width, dec->edged_height)
107          if (image_create(&dec->refn[0], dec->edged_width, dec->edged_height)) {        || image_create(&dec->gmc, dec->edged_width, dec->edged_height) )
108                  image_destroy(&dec->cur, dec->edged_width, dec->edged_height);      goto memory_error;
                 xvid_free(dec);  
                 return XVID_ERR_MEMORY;  
         }  
   
         /* Support B-frame to reference last 2 frame */  
         if (image_create(&dec->refn[1], dec->edged_width, dec->edged_height)) {  
                 image_destroy(&dec->cur, dec->edged_width, dec->edged_height);  
                 image_destroy(&dec->refn[0], dec->edged_width, dec->edged_height);  
                 xvid_free(dec);  
                 return XVID_ERR_MEMORY;  
         }  
         if (image_create(&dec->tmp, dec->edged_width, dec->edged_height)) {  
                 image_destroy(&dec->cur, dec->edged_width, dec->edged_height);  
                 image_destroy(&dec->refn[0], dec->edged_width, dec->edged_height);  
                 image_destroy(&dec->refn[1], dec->edged_width, dec->edged_height);  
                 xvid_free(dec);  
                 return XVID_ERR_MEMORY;  
         }  
   
         if (image_create(&dec->qtmp, dec->edged_width, dec->edged_height)) {  
                 image_destroy(&dec->cur, dec->edged_width, dec->edged_height);  
                 image_destroy(&dec->refn[0], dec->edged_width, dec->edged_height);  
                 image_destroy(&dec->refn[1], dec->edged_width, dec->edged_height);  
                 image_destroy(&dec->tmp, dec->edged_width, dec->edged_height);  
                 xvid_free(dec);  
                 return XVID_ERR_MEMORY;  
         }  
   
         if (image_create(&dec->gmc, dec->edged_width, dec->edged_height)) {  
                 image_destroy(&dec->qtmp, dec->edged_width, dec->edged_height);  
                 image_destroy(&dec->cur, dec->edged_width, dec->edged_height);  
                 image_destroy(&dec->refn[0], dec->edged_width, dec->edged_height);  
                 image_destroy(&dec->refn[1], dec->edged_width, dec->edged_height);  
                 image_destroy(&dec->tmp, dec->edged_width, dec->edged_height);  
                 xvid_free(dec);  
                 return XVID_ERR_MEMORY;  
         }  
109    
110          dec->mbs =          dec->mbs =
111                  xvid_malloc(sizeof(MACROBLOCK) * dec->mb_width * dec->mb_height,                  xvid_malloc(sizeof(MACROBLOCK) * dec->mb_width * dec->mb_height,
112                                          CACHE_LINE);                                          CACHE_LINE);
113          if (dec->mbs == NULL) {          if (dec->mbs == NULL)
114                  image_destroy(&dec->cur, dec->edged_width, dec->edged_height);            goto memory_error;
                 image_destroy(&dec->refn[0], dec->edged_width, dec->edged_height);  
                 image_destroy(&dec->refn[1], dec->edged_width, dec->edged_height);  
                 image_destroy(&dec->tmp, dec->edged_width, dec->edged_height);  
                 image_destroy(&dec->qtmp, dec->edged_width, dec->edged_height);  
                 xvid_free(dec);  
                 return XVID_ERR_MEMORY;  
         }  
115          memset(dec->mbs, 0, sizeof(MACROBLOCK) * dec->mb_width * dec->mb_height);          memset(dec->mbs, 0, sizeof(MACROBLOCK) * dec->mb_width * dec->mb_height);
116    
117          /* For skip MB flag */          /* For skip MB flag */
118          dec->last_mbs =          dec->last_mbs =
119                  xvid_malloc(sizeof(MACROBLOCK) * dec->mb_width * dec->mb_height,                  xvid_malloc(sizeof(MACROBLOCK) * dec->mb_width * dec->mb_height,
120                                          CACHE_LINE);                                          CACHE_LINE);
121          if (dec->last_mbs == NULL) {          if (dec->last_mbs == NULL)
122                  xvid_free(dec->mbs);            goto memory_error;
                 image_destroy(&dec->cur, dec->edged_width, dec->edged_height);  
                 image_destroy(&dec->refn[0], dec->edged_width, dec->edged_height);  
                 image_destroy(&dec->refn[1], dec->edged_width, dec->edged_height);  
                 image_destroy(&dec->tmp, dec->edged_width, dec->edged_height);  
                 image_destroy(&dec->qtmp, dec->edged_width, dec->edged_height);  
                 xvid_free(dec);  
                 return XVID_ERR_MEMORY;  
         }  
   
123          memset(dec->last_mbs, 0, sizeof(MACROBLOCK) * dec->mb_width * dec->mb_height);          memset(dec->last_mbs, 0, sizeof(MACROBLOCK) * dec->mb_width * dec->mb_height);
124    
125          /* nothing happens if that fails */          /* nothing happens if that fails */
# Line 171  Line 130 
130                  memset(dec->qscale, 0, sizeof(int) * dec->mb_width * dec->mb_height);                  memset(dec->qscale, 0, sizeof(int) * dec->mb_width * dec->mb_height);
131    
132          return 0;          return 0;
133    
134    memory_error:
135            /* Most structures were deallocated / nullifieded, so it should be safe */
136            /* decoder_destroy(dec) minus the write_timer */
137      xvid_free(dec->mbs);
138      image_destroy(&dec->cur, dec->edged_width, dec->edged_height);
139      image_destroy(&dec->refn[0], dec->edged_width, dec->edged_height);
140      image_destroy(&dec->refn[1], dec->edged_width, dec->edged_height);
141      image_destroy(&dec->tmp, dec->edged_width, dec->edged_height);
142      image_destroy(&dec->qtmp, dec->edged_width, dec->edged_height);
143    
144      xvid_free(dec);
145      return XVID_ERR_MEMORY;
146  }  }
147    
148    
# Line 270  Line 242 
242                                  Bitstream * bs,                                  Bitstream * bs,
243                                  const uint32_t quant,                                  const uint32_t quant,
244                                  const uint32_t intra_dc_threshold,                                  const uint32_t intra_dc_threshold,
245                                  const unsigned int bound,          const unsigned int bound)
                                 const int reduced_resolution)  
246  {  {
247    
248          DECLARE_ALIGNED_MATRIX(block, 6, 64, int16_t, CACHE_LINE);          DECLARE_ALIGNED_MATRIX(block, 6, 64, int16_t, CACHE_LINE);
# Line 284  Line 255 
255          uint32_t iQuant = pMB->quant;          uint32_t iQuant = pMB->quant;
256          uint8_t *pY_Cur, *pU_Cur, *pV_Cur;          uint8_t *pY_Cur, *pU_Cur, *pV_Cur;
257    
         if (reduced_resolution) {  
                 pY_Cur = dec->cur.y + (y_pos << 5) * stride + (x_pos << 5);  
                 pU_Cur = dec->cur.u + (y_pos << 4) * stride2 + (x_pos << 4);  
                 pV_Cur = dec->cur.v + (y_pos << 4) * stride2 + (x_pos << 4);  
         }else{  
258                  pY_Cur = dec->cur.y + (y_pos << 4) * stride + (x_pos << 4);                  pY_Cur = dec->cur.y + (y_pos << 4) * stride + (x_pos << 4);
259                  pU_Cur = dec->cur.u + (y_pos << 3) * stride2 + (x_pos << 3);                  pU_Cur = dec->cur.u + (y_pos << 3) * stride2 + (x_pos << 3);
260                  pV_Cur = dec->cur.v + (y_pos << 3) * stride2 + (x_pos << 3);                  pV_Cur = dec->cur.v + (y_pos << 3) * stride2 + (x_pos << 3);
         }  
261    
262          memset(block, 0, 6 * 64 * sizeof(int16_t));     /* clear */          memset(block, 0, 6 * 64 * sizeof(int16_t));     /* clear */
263    
# Line 303  Line 268 
268    
269                  start_timer();                  start_timer();
270                  predict_acdc(dec->mbs, x_pos, y_pos, dec->mb_width, i, &block[i * 64],                  predict_acdc(dec->mbs, x_pos, y_pos, dec->mb_width, i, &block[i * 64],
271                                           iQuant, iDcScaler, predictors, bound, dec->bs_version);             iQuant, iDcScaler, predictors, bound);
272                  if (!acpred_flag) {                  if (!acpred_flag) {
273                          pMB->acpred_directions[i] = 0;                          pMB->acpred_directions[i] = 0;
274                  }                  }
# Line 339  Line 304 
304                  stop_coding_timer();                  stop_coding_timer();
305    
306                  start_timer();                  start_timer();
307                  add_acdc(pMB, i, &block[i * 64], iDcScaler, predictors);      add_acdc(pMB, i, &block[i * 64], iDcScaler, predictors, dec->bs_version);
308                  stop_prediction_timer();                  stop_prediction_timer();
309    
310                  start_timer();                  start_timer();
# Line 351  Line 316 
316                  stop_iquant_timer();                  stop_iquant_timer();
317    
318                  start_timer();                  start_timer();
319                  idct(&data[i * 64]);      idct((short * const)&data[i * 64]);
320                  stop_idct_timer();                  stop_idct_timer();
321    
322          }          }
# Line 362  Line 327 
327          }          }
328    
329          start_timer();          start_timer();
   
         if (reduced_resolution)  
         {  
                 next_block*=2;  
                 copy_upsampled_8x8_16to8(pY_Cur, &data[0 * 64], stride);  
                 copy_upsampled_8x8_16to8(pY_Cur + 16, &data[1 * 64], stride);  
                 copy_upsampled_8x8_16to8(pY_Cur + next_block, &data[2 * 64], stride);  
                 copy_upsampled_8x8_16to8(pY_Cur + 16 + next_block, &data[3 * 64], stride);  
                 copy_upsampled_8x8_16to8(pU_Cur, &data[4 * 64], stride2);  
                 copy_upsampled_8x8_16to8(pV_Cur, &data[5 * 64], stride2);  
         }else{  
330                  transfer_16to8copy(pY_Cur, &data[0 * 64], stride);                  transfer_16to8copy(pY_Cur, &data[0 * 64], stride);
331                  transfer_16to8copy(pY_Cur + 8, &data[1 * 64], stride);                  transfer_16to8copy(pY_Cur + 8, &data[1 * 64], stride);
332                  transfer_16to8copy(pY_Cur + next_block, &data[2 * 64], stride);                  transfer_16to8copy(pY_Cur + next_block, &data[2 * 64], stride);
333                  transfer_16to8copy(pY_Cur + 8 + next_block, &data[3 * 64], stride);                  transfer_16to8copy(pY_Cur + 8 + next_block, &data[3 * 64], stride);
334                  transfer_16to8copy(pU_Cur, &data[4 * 64], stride2);                  transfer_16to8copy(pU_Cur, &data[4 * 64], stride2);
335                  transfer_16to8copy(pV_Cur, &data[5 * 64], stride2);                  transfer_16to8copy(pV_Cur, &data[5 * 64], stride2);
         }  
336          stop_transfer_timer();          stop_transfer_timer();
337  }  }
338    
# Line 390  Line 343 
343                                  uint8_t * pY_Cur,                                  uint8_t * pY_Cur,
344                                  uint8_t * pU_Cur,                                  uint8_t * pU_Cur,
345                                  uint8_t * pV_Cur,                                  uint8_t * pV_Cur,
                                 const int reduced_resolution,  
346                                  const MACROBLOCK * pMB)                                  const MACROBLOCK * pMB)
347  {  {
348          DECLARE_ALIGNED_MATRIX(block, 1, 64, int16_t, CACHE_LINE);    DECLARE_ALIGNED_MATRIX(data, 1, 64, int16_t, CACHE_LINE);
         DECLARE_ALIGNED_MATRIX(data, 6, 64, int16_t, CACHE_LINE);  
349    
350          int stride = dec->edged_width;          int stride = dec->edged_width;
         int next_block = stride * (reduced_resolution ? 16 : 8);  
         const int stride2 = stride/2;  
351          int i;          int i;
352          const uint32_t iQuant = pMB->quant;          const uint32_t iQuant = pMB->quant;
353          const int direction = dec->alternate_vertical_scan ? 2 : 0;          const int direction = dec->alternate_vertical_scan ? 2 : 0;
354          const quant_interFuncPtr dequant = dec->quant_type == 0 ? dequant_h263_inter : dequant_mpeg_inter;    typedef void (*get_inter_block_function_t)(
355          Bitstream * bs,
356          int16_t * block,
357          int direction,
358          const int quant,
359          const uint16_t *matrix);
360      typedef void (*add_residual_function_t)(
361          uint8_t *predicted_block,
362          const int16_t *residual,
363          int stride);
364    
365      const get_inter_block_function_t get_inter_block = (dec->quant_type == 0)
366        ? (get_inter_block_function_t)get_inter_block_h263
367        : (get_inter_block_function_t)get_inter_block_mpeg;
368    
369      uint8_t *dst[6];
370      int strides[6];
371    
         for (i = 0; i < 6; i++) {  
372    
373                  if (cbp & (1 << (5 - i))) {     /* coded */    if (dec->interlacing && pMB->field_dct) {
374        dst[0] = pY_Cur;
375        dst[1] = pY_Cur + 8;
376        dst[2] = pY_Cur + stride;
377        dst[3] = dst[2] + 8;
378        dst[4] = pU_Cur;
379        dst[5] = pV_Cur;
380        strides[0] = strides[1] = strides[2] = strides[3] = stride*2;
381        strides[4] = stride/2;
382        strides[5] = stride/2;
383      } else {
384        dst[0] = pY_Cur;
385        dst[1] = pY_Cur + 8;
386        dst[2] = pY_Cur + 8*stride;
387        dst[3] = dst[2] + 8;
388        dst[4] = pU_Cur;
389        dst[5] = pV_Cur;
390        strides[0] = strides[1] = strides[2] = strides[3] = stride;
391        strides[4] = stride/2;
392        strides[5] = stride/2;
393      }
394    
395      for (i = 0; i < 6; i++) {
396        /* Process only coded blocks */
397        if (cbp & (1 << (5 - i))) {
398    
399                          memset(block, 0, 64 * sizeof(int16_t)); /* clear */        /* Clear the block */
400          memset(&data[0], 0, 64*sizeof(int16_t));
401    
402          /* Decode coeffs and dequantize on the fly */
403                          start_timer();                          start_timer();
404                          get_inter_block(bs, block, direction);        get_inter_block(bs, &data[0], direction, iQuant, get_inter_matrix(dec->mpeg_quant_matrices));
405                          stop_coding_timer();                          stop_coding_timer();
406    
407          /* iDCT */
408                          start_timer();                          start_timer();
409                          dequant(&data[i * 64], block, iQuant, dec->mpeg_quant_matrices);        idct((short * const)&data[0]);
410                          stop_iquant_timer();        stop_idct_timer();
411    
412          /* Add this residual to the predicted block */
413                          start_timer();                          start_timer();
414                          idct(&data[i * 64]);        transfer_16to8add(dst[i], &data[0], strides[i]);
415                          stop_idct_timer();        stop_transfer_timer();
416                  }                  }
417          }          }
   
         if (dec->interlacing && pMB->field_dct) {  
                 next_block = stride;  
                 stride *= 2;  
418          }          }
419    
420          start_timer();  static void __inline
421          if (reduced_resolution) {  validate_vector(VECTOR * mv, unsigned int x_pos, unsigned int y_pos, const DECODER * dec)
422                  if (cbp & 32)  {
423                          add_upsampled_8x8_16to8(pY_Cur, &data[0 * 64], stride);    /* clip a vector to valid range
424                  if (cbp & 16)       prevents crashes if bitstream is broken
425                          add_upsampled_8x8_16to8(pY_Cur + 16, &data[1 * 64], stride);    */
426                  if (cbp & 8)    int shift = 5 + dec->quarterpel;
427                          add_upsampled_8x8_16to8(pY_Cur + next_block, &data[2 * 64], stride);    int xborder_high = (int)(dec->mb_width - x_pos) << shift;
428                  if (cbp & 4)    int xborder_low = (-(int)x_pos-1) << shift;
429                          add_upsampled_8x8_16to8(pY_Cur + 16 + next_block, &data[3 * 64], stride);    int yborder_high = (int)(dec->mb_height - y_pos) << shift;
430                  if (cbp & 2)    int yborder_low = (-(int)y_pos-1) << shift;
431                          add_upsampled_8x8_16to8(pU_Cur, &data[4 * 64], stride2);  
432                  if (cbp & 1)  #define CHECK_MV(mv) \
433                          add_upsampled_8x8_16to8(pV_Cur, &data[5 * 64], stride2);    do { \
434          } else {    if ((mv).x > xborder_high) { \
435                  if (cbp & 32)      DPRINTF(XVID_DEBUG_MV, "mv.x > max -- %d > %d, MB %d, %d", (mv).x, xborder_high, x_pos, y_pos); \
436                          transfer_16to8add(pY_Cur, &data[0 * 64], stride);      (mv).x = xborder_high; \
437                  if (cbp & 16)    } else if ((mv).x < xborder_low) { \
438                          transfer_16to8add(pY_Cur + 8, &data[1 * 64], stride);      DPRINTF(XVID_DEBUG_MV, "mv.x < min -- %d < %d, MB %d, %d", (mv).x, xborder_low, x_pos, y_pos); \
439                  if (cbp & 8)      (mv).x = xborder_low; \
440                          transfer_16to8add(pY_Cur + next_block, &data[2 * 64], stride);    } \
441                  if (cbp & 4)    if ((mv).y > yborder_high) { \
442                          transfer_16to8add(pY_Cur + 8 + next_block, &data[3 * 64], stride);      DPRINTF(XVID_DEBUG_MV, "mv.y > max -- %d > %d, MB %d, %d", (mv).y, yborder_high, x_pos, y_pos); \
443                  if (cbp & 2)      (mv).y = yborder_high; \
444                          transfer_16to8add(pU_Cur, &data[4 * 64], stride2);    } else if ((mv).y < yborder_low) { \
445                  if (cbp & 1)      DPRINTF(XVID_DEBUG_MV, "mv.y < min -- %d < %d, MB %d, %d", (mv).y, yborder_low, x_pos, y_pos); \
446                          transfer_16to8add(pV_Cur, &data[5 * 64], stride2);      (mv).y = yborder_low; \
447          }    } \
448          stop_transfer_timer();    } while (0)
449  }  
450      CHECK_MV(mv[0]);
451      CHECK_MV(mv[1]);
452      CHECK_MV(mv[2]);
453      CHECK_MV(mv[3]);
454    }
455    
456    /* Up to this version, chroma rounding was wrong with qpel.
457     * So we try to be backward compatible to avoid artifacts */
458    #define BS_VERSION_BUGGY_CHROMA_ROUNDING 1
459    
460  /* decode an inter macroblock */  /* decode an inter macroblock */
461  static void  static void
# Line 469  Line 466 
466                                  const uint32_t cbp,                                  const uint32_t cbp,
467                                  Bitstream * bs,                                  Bitstream * bs,
468                                  const uint32_t rounding,                                  const uint32_t rounding,
                                 const int reduced_resolution,  
469                                  const int ref)                                  const int ref)
470  {  {
471          uint32_t stride = dec->edged_width;          uint32_t stride = dec->edged_width;
# Line 481  Line 477 
477          int uv_dx, uv_dy;          int uv_dx, uv_dy;
478          VECTOR mv[4];   /* local copy of mvs */          VECTOR mv[4];   /* local copy of mvs */
479    
         if (reduced_resolution) {  
                 pY_Cur = dec->cur.y + (y_pos << 5) * stride + (x_pos << 5);  
                 pU_Cur = dec->cur.u + (y_pos << 4) * stride2 + (x_pos << 4);  
                 pV_Cur = dec->cur.v + (y_pos << 4) * stride2 + (x_pos << 4);  
                 for (i = 0; i < 4; i++) {  
                         mv[i].x = RRV_MV_SCALEUP(pMB->mvs[i].x);  
                         mv[i].y = RRV_MV_SCALEUP(pMB->mvs[i].y);  
                 }  
         } else {  
480                  pY_Cur = dec->cur.y + (y_pos << 4) * stride + (x_pos << 4);                  pY_Cur = dec->cur.y + (y_pos << 4) * stride + (x_pos << 4);
481                  pU_Cur = dec->cur.u + (y_pos << 3) * stride2 + (x_pos << 3);                  pU_Cur = dec->cur.u + (y_pos << 3) * stride2 + (x_pos << 3);
482                  pV_Cur = dec->cur.v + (y_pos << 3) * stride2 + (x_pos << 3);                  pV_Cur = dec->cur.v + (y_pos << 3) * stride2 + (x_pos << 3);
483                  for (i = 0; i < 4; i++)                  for (i = 0; i < 4; i++)
484                          mv[i] = pMB->mvs[i];                          mv[i] = pMB->mvs[i];
         }  
485    
486          for (i = 0; i < 4; i++) {    validate_vector(mv, x_pos, y_pos, dec);
                 /* clip to valid range */  
                 int border = (int)(dec->mb_width - x_pos) << (5 + dec->quarterpel);  
                 if (mv[i].x > border) {  
                         DPRINTF(XVID_DEBUG_MV, "mv.x > max -- %d > %d, MB %d, %d", mv[i].x, border, x_pos, y_pos);  
                         mv[i].x = border;  
                 } else {  
                         border = (-(int)x_pos-1) << (5 + dec->quarterpel);  
                         if (mv[i].x < border) {  
                                 DPRINTF(XVID_DEBUG_MV, "mv.x < min -- %d < %d, MB %d, %d", mv[i].x, border, x_pos, y_pos);  
                                 mv[i].x = border;  
                         }  
                 }  
   
                 border = (int)(dec->mb_height - y_pos) << (5 + dec->quarterpel);  
                 if (mv[i].y >  border) {  
                         DPRINTF(XVID_DEBUG_MV, "mv.y > max -- %d > %d, MB %d, %d", mv[i].y, border, x_pos, y_pos);  
                         mv[i].y = border;  
                 } else {  
                         border = (-(int)y_pos-1) << (5 + dec->quarterpel);  
                         if (mv[i].y < border) {  
                                 DPRINTF(XVID_DEBUG_MV, "mv.y < min -- %d < %d, MB %d, %d", mv[i].y, border, x_pos, y_pos);  
                                 mv[i].y = border;  
                         }  
                 }  
         }  
487    
488          start_timer();          start_timer();
489    
# Line 531  Line 492 
492                  uv_dx = mv[0].x;                  uv_dx = mv[0].x;
493                  uv_dy = mv[0].y;                  uv_dy = mv[0].y;
494                  if (dec->quarterpel) {                  if (dec->quarterpel) {
495                            if (dec->bs_version <= BS_VERSION_BUGGY_CHROMA_ROUNDING) {
496                            uv_dx = (uv_dx>>1) | (uv_dx&1);
497                                    uv_dy = (uv_dy>>1) | (uv_dy&1);
498                            }
499                            else {
500                          uv_dx /= 2;                          uv_dx /= 2;
501                          uv_dy /= 2;                          uv_dy /= 2;
502                  }                  }
503        }
504                  uv_dx = (uv_dx >> 1) + roundtab_79[uv_dx & 0x3];                  uv_dx = (uv_dx >> 1) + roundtab_79[uv_dx & 0x3];
505                  uv_dy = (uv_dy >> 1) + roundtab_79[uv_dy & 0x3];                  uv_dy = (uv_dy >> 1) + roundtab_79[uv_dy & 0x3];
506    
507                  if (reduced_resolution)      if (dec->quarterpel)
                         interpolate32x32_switch(dec->cur.y, dec->refn[0].y, 32*x_pos, 32*y_pos,  
                                                                         mv[0].x, mv[0].y, stride, rounding);  
                 else if (dec->quarterpel)  
508                          interpolate16x16_quarterpel(dec->cur.y, dec->refn[ref].y, dec->qtmp.y, dec->qtmp.y + 64,                          interpolate16x16_quarterpel(dec->cur.y, dec->refn[ref].y, dec->qtmp.y, dec->qtmp.y + 64,
509                                                                          dec->qtmp.y + 128, 16*x_pos, 16*y_pos,                                                                          dec->qtmp.y + 128, 16*x_pos, 16*y_pos,
510                                                                                          mv[0].x, mv[0].y, stride, rounding);                                                                                          mv[0].x, mv[0].y, stride, rounding);
# Line 551  Line 515 
515          } else {        /* MODE_INTER4V */          } else {        /* MODE_INTER4V */
516    
517                  if(dec->quarterpel) {                  if(dec->quarterpel) {
518                            if (dec->bs_version <= BS_VERSION_BUGGY_CHROMA_ROUNDING) {
519                                    int z;
520                                    uv_dx = 0; uv_dy = 0;
521                                    for (z = 0; z < 4; z++) {
522                                      uv_dx += ((mv[z].x>>1) | (mv[z].x&1));
523                                      uv_dy += ((mv[z].y>>1) | (mv[z].y&1));
524                                    }
525                            }
526                            else {
527                          uv_dx = (mv[0].x / 2) + (mv[1].x / 2) + (mv[2].x / 2) + (mv[3].x / 2);                          uv_dx = (mv[0].x / 2) + (mv[1].x / 2) + (mv[2].x / 2) + (mv[3].x / 2);
528                          uv_dy = (mv[0].y / 2) + (mv[1].y / 2) + (mv[2].y / 2) + (mv[3].y / 2);                          uv_dy = (mv[0].y / 2) + (mv[1].y / 2) + (mv[2].y / 2) + (mv[3].y / 2);
529          }
530                  } else {                  } else {
531                          uv_dx = mv[0].x + mv[1].x + mv[2].x + mv[3].x;                          uv_dx = mv[0].x + mv[1].x + mv[2].x + mv[3].x;
532                          uv_dy = mv[0].y + mv[1].y + mv[2].y + mv[3].y;                          uv_dy = mv[0].y + mv[1].y + mv[2].y + mv[3].y;
# Line 561  Line 535 
535                  uv_dx = (uv_dx >> 3) + roundtab_76[uv_dx & 0xf];                  uv_dx = (uv_dx >> 3) + roundtab_76[uv_dx & 0xf];
536                  uv_dy = (uv_dy >> 3) + roundtab_76[uv_dy & 0xf];                  uv_dy = (uv_dy >> 3) + roundtab_76[uv_dy & 0xf];
537    
538                  if (reduced_resolution) {      if (dec->quarterpel) {
                         interpolate16x16_switch(dec->cur.y, dec->refn[0].y, 32*x_pos, 32*y_pos,  
                                                                 mv[0].x, mv[0].y, stride, rounding);  
                         interpolate16x16_switch(dec->cur.y, dec->refn[0].y , 32*x_pos + 16, 32*y_pos,  
                                                                 mv[1].x, mv[1].y, stride, rounding);  
                         interpolate16x16_switch(dec->cur.y, dec->refn[0].y , 32*x_pos, 32*y_pos + 16,  
                                                                 mv[2].x, mv[2].y, stride, rounding);  
                         interpolate16x16_switch(dec->cur.y, dec->refn[0].y , 32*x_pos + 16, 32*y_pos + 16,  
                                                                 mv[3].x, mv[3].y, stride, rounding);  
                         interpolate16x16_switch(dec->cur.u, dec->refn[0].u , 16 * x_pos, 16 * y_pos,  
                                                                 uv_dx, uv_dy, stride2, rounding);  
                         interpolate16x16_switch(dec->cur.v, dec->refn[0].v , 16 * x_pos, 16 * y_pos,  
                                                                 uv_dx, uv_dy, stride2, rounding);  
   
                 } else if (dec->quarterpel) {  
539                          interpolate8x8_quarterpel(dec->cur.y, dec->refn[0].y , dec->qtmp.y, dec->qtmp.y + 64,                          interpolate8x8_quarterpel(dec->cur.y, dec->refn[0].y , dec->qtmp.y, dec->qtmp.y + 64,
540                                                                          dec->qtmp.y + 128, 16*x_pos, 16*y_pos,                                                                          dec->qtmp.y + 128, 16*x_pos, 16*y_pos,
541                                                                          mv[0].x, mv[0].y, stride, rounding);                                                                          mv[0].x, mv[0].y, stride, rounding);
# Line 601  Line 561 
561          }          }
562    
563          /* chroma */          /* chroma */
         if (reduced_resolution) {  
                 interpolate16x16_switch(dec->cur.u, dec->refn[0].u, 16 * x_pos, 16 * y_pos,  
                                                                 uv_dx, uv_dy, stride2, rounding);  
                 interpolate16x16_switch(dec->cur.v, dec->refn[0].v, 16 * x_pos, 16 * y_pos,  
                                                                 uv_dx, uv_dy, stride2, rounding);  
         } else {  
564                  interpolate8x8_switch(dec->cur.u, dec->refn[ref].u, 8 * x_pos, 8 * y_pos,                  interpolate8x8_switch(dec->cur.u, dec->refn[ref].u, 8 * x_pos, 8 * y_pos,
565                                                                  uv_dx, uv_dy, stride2, rounding);                                                                  uv_dx, uv_dy, stride2, rounding);
566                  interpolate8x8_switch(dec->cur.v, dec->refn[ref].v, 8 * x_pos, 8 * y_pos,                  interpolate8x8_switch(dec->cur.v, dec->refn[ref].v, 8 * x_pos, 8 * y_pos,
567                                                                  uv_dx, uv_dy, stride2, rounding);                                                                  uv_dx, uv_dy, stride2, rounding);
568    
569      stop_comp_timer();
570    
571      if (cbp)
572        decoder_mb_decode(dec, cbp, bs, pY_Cur, pU_Cur, pV_Cur, pMB);
573    }
574    
575    /* decode an inter macroblock in field mode */
576    static void
577    decoder_mbinter_field(DECODER * dec,
578            const MACROBLOCK * pMB,
579            const uint32_t x_pos,
580            const uint32_t y_pos,
581            const uint32_t cbp,
582            Bitstream * bs,
583            const uint32_t rounding,
584            const int ref)
585    {
586      uint32_t stride = dec->edged_width;
587      uint32_t stride2 = stride / 2;
588    
589      uint8_t *pY_Cur, *pU_Cur, *pV_Cur;
590    
591      int uvtop_dx, uvtop_dy;
592      int uvbot_dx, uvbot_dy;
593      VECTOR mv[4]; /* local copy of mvs */
594    
595      /* Get pointer to memory areas */
596      pY_Cur = dec->cur.y + (y_pos << 4) * stride + (x_pos << 4);
597      pU_Cur = dec->cur.u + (y_pos << 3) * stride2 + (x_pos << 3);
598      pV_Cur = dec->cur.v + (y_pos << 3) * stride2 + (x_pos << 3);
599    
600      mv[0] = pMB->mvs[0];
601      mv[1] = pMB->mvs[1];
602      memset(&mv[2],0,2*sizeof(VECTOR));
603    
604      validate_vector(mv, x_pos, y_pos, dec);
605    
606      start_timer();
607    
608      if(pMB->mode!=MODE_INTER4V)   /* INTER, INTER_Q, NOT_CODED, FORWARD, BACKWARD */
609      {
610        /* Prepare top field vector */
611        uvtop_dx = DIV2ROUND(mv[0].x);
612        uvtop_dy = DIV2ROUND(mv[0].y);
613    
614        /* Prepare bottom field vector */
615        uvbot_dx = DIV2ROUND(mv[1].x);
616        uvbot_dy = DIV2ROUND(mv[1].y);
617    
618        if(dec->quarterpel)
619        {
620          /* NOT supported */
621        }
622        else
623        {
624          /* Interpolate top field left part(we use double stride for every 2nd line) */
625          interpolate8x8_switch(dec->cur.y,dec->refn[ref].y+pMB->field_for_top*stride,
626                                16*x_pos,8*y_pos,mv[0].x, mv[0].y>>1,2*stride, rounding);
627          /* top field right part */
628          interpolate8x8_switch(dec->cur.y,dec->refn[ref].y+pMB->field_for_top*stride,
629                                16*x_pos+8,8*y_pos,mv[0].x, mv[0].y>>1,2*stride, rounding);
630    
631          /* Interpolate bottom field left part(we use double stride for every 2nd line) */
632          interpolate8x8_switch(dec->cur.y+stride,dec->refn[ref].y+pMB->field_for_bot*stride,
633                                16*x_pos,8*y_pos,mv[1].x, mv[1].y>>1,2*stride, rounding);
634          /* Bottom field right part */
635          interpolate8x8_switch(dec->cur.y+stride,dec->refn[ref].y+pMB->field_for_bot*stride,
636                                16*x_pos+8,8*y_pos,mv[1].x, mv[1].y>>1,2*stride, rounding);
637    
638          /* Interpolate field1 U */
639          interpolate8x4_switch(dec->cur.u,dec->refn[ref].u+pMB->field_for_top*stride2,
640                                8*x_pos,4*y_pos,uvtop_dx,DIV2ROUND(uvtop_dy),stride,rounding);
641    
642          /* Interpolate field1 V */
643          interpolate8x4_switch(dec->cur.v,dec->refn[ref].v+pMB->field_for_top*stride2,
644                                8*x_pos,4*y_pos,uvtop_dx,DIV2ROUND(uvtop_dy),stride,rounding);
645    
646          /* Interpolate field2 U */
647          interpolate8x4_switch(dec->cur.u+stride2,dec->refn[ref].u+pMB->field_for_bot*stride2,
648                                8*x_pos,4*y_pos,uvbot_dx,DIV2ROUND(uvbot_dy),stride,rounding);
649    
650          /* Interpolate field2 V */
651          interpolate8x4_switch(dec->cur.v+stride2,dec->refn[ref].v+pMB->field_for_bot*stride2,
652                                8*x_pos,4*y_pos,uvbot_dx,DIV2ROUND(uvbot_dy),stride,rounding);
653        }
654      }
655      else
656      {
657        /* We don't expect 4 motion vectors in interlaced mode */
658          }          }
659    
660          stop_comp_timer();          stop_comp_timer();
661    
662      /* Must add error correction? */
663          if (cbp)          if (cbp)
664                  decoder_mb_decode(dec, cbp, bs, pY_Cur, pU_Cur, pV_Cur,     decoder_mb_decode(dec, cbp, bs, pY_Cur, pU_Cur, pV_Cur, pMB);
                                                         reduced_resolution, pMB);  
665  }  }
666    
667  static void  static void
# Line 664  Line 708 
708          stop_transfer_timer();          stop_transfer_timer();
709    
710          if (cbp)          if (cbp)
711                  decoder_mb_decode(dec, cbp, bs, pY_Cur, pU_Cur, pV_Cur, 0, pMB);      decoder_mb_decode(dec, cbp, bs, pY_Cur, pU_Cur, pV_Cur, pMB);
712    
713  }  }
714    
# Line 672  Line 716 
716  static void  static void
717  decoder_iframe(DECODER * dec,  decoder_iframe(DECODER * dec,
718                                  Bitstream * bs,                                  Bitstream * bs,
                                 int reduced_resolution,  
719                                  int quant,                                  int quant,
720                                  int intra_dc_threshold)                                  int intra_dc_threshold)
721  {  {
722          uint32_t bound;          uint32_t bound;
723          uint32_t x, y;          uint32_t x, y;
724          uint32_t mb_width = dec->mb_width;    const uint32_t mb_width = dec->mb_width;
725          uint32_t mb_height = dec->mb_height;    const uint32_t mb_height = dec->mb_height;
   
         if (reduced_resolution) {  
                 mb_width = (dec->width + 31) / 32;  
                 mb_height = (dec->height + 31) / 32;  
         }  
726    
727          bound = 0;          bound = 0;
728    
# Line 740  Line 778 
778                          }                          }
779    
780                          decoder_mbintra(dec, mb, x, y, acpred_flag, cbp, bs, quant,                          decoder_mbintra(dec, mb, x, y, acpred_flag, cbp, bs, quant,
781                                                          intra_dc_threshold, bound, reduced_resolution);                intra_dc_threshold, bound);
782    
783                  }                  }
784                  if(dec->out_frm)                  if(dec->out_frm)
# Line 793  Line 831 
831          ret_mv->y = mv.y;          ret_mv->y = mv.y;
832  }  }
833    
834    /* We use this when decoder runs interlaced -> different prediction */
835    
836    static void get_motion_vector_interlaced(DECODER * dec,
837            Bitstream * bs,
838            int x,
839            int y,
840            int k,
841            MACROBLOCK *pMB,
842            int fcode,
843            const int bound)
844    {
845      const int scale_fac = 1 << (fcode - 1);
846      const int high = (32 * scale_fac) - 1;
847      const int low = ((-32) * scale_fac);
848      const int range = (64 * scale_fac);
849    
850      /* Get interlaced prediction */
851      const VECTOR pmv=get_pmv2_interlaced(dec->mbs,dec->mb_width,bound,x,y,k);
852      VECTOR mv,mvf1,mvf2;
853    
854      if(!pMB->field_pred)
855      {
856        mv.x = get_mv(bs,fcode);
857        mv.y = get_mv(bs,fcode);
858    
859        mv.x += pmv.x;
860        mv.y += pmv.y;
861    
862        if(mv.x<low) {
863          mv.x += range;
864        } else if (mv.x>high) {
865          mv.x-=range;
866        }
867    
868        if (mv.y < low) {
869          mv.y += range;
870        } else if (mv.y > high) {
871          mv.y -= range;
872        }
873    
874        pMB->mvs[0]=pMB->mvs[1]=pMB->mvs[2]=pMB->mvs[3]=mv;
875      }
876      else
877      {
878        mvf1.x = get_mv(bs, fcode);
879        mvf1.y = get_mv(bs, fcode);
880    
881        mvf1.x += pmv.x;
882        mvf1.y = 2*(mvf1.y+pmv.y/2); /* It's multiple of 2 */
883    
884        if (mvf1.x < low) {
885          mvf1.x += range;
886        } else if (mvf1.x > high) {
887          mvf1.x -= range;
888        }
889    
890        if (mvf1.y < low) {
891          mvf1.y += range;
892        } else if (mvf1.y > high) {
893          mvf1.y -= range;
894        }
895    
896        mvf2.x = get_mv(bs, fcode);
897        mvf2.y = get_mv(bs, fcode);
898    
899        mvf2.x += pmv.x;
900        mvf2.y = 2*(mvf2.y+pmv.y/2); /* It's multiple of 2 */
901    
902        if (mvf2.x < low) {
903          mvf2.x += range;
904        } else if (mvf2.x > high) {
905          mvf2.x -= range;
906        }
907    
908        if (mvf2.y < low) {
909          mvf2.y += range;
910        } else if (mvf2.y > high) {
911          mvf2.y -= range;
912        }
913    
914        pMB->mvs[0]=mvf1;
915        pMB->mvs[1]=mvf2;
916        pMB->mvs[2].x=pMB->mvs[3].x=0;
917        pMB->mvs[2].y=pMB->mvs[3].y=0;
918    
919        /* Calculate average for as it is field predicted */
920        pMB->mvs_avg.x=DIV2ROUND(pMB->mvs[0].x+pMB->mvs[1].x);
921        pMB->mvs_avg.y=DIV2ROUND(pMB->mvs[0].y+pMB->mvs[1].y);
922      }
923    }
924    
925  /* for P_VOP set gmc_warp to NULL */  /* for P_VOP set gmc_warp to NULL */
926  static void  static void
927  decoder_pframe(DECODER * dec,  decoder_pframe(DECODER * dec,
928                                  Bitstream * bs,                                  Bitstream * bs,
929                                  int rounding,                                  int rounding,
                                 int reduced_resolution,  
930                                  int quant,                                  int quant,
931                                  int fcode,                                  int fcode,
932                                  int intra_dc_threshold,                                  int intra_dc_threshold,
# Line 807  Line 935 
935          uint32_t x, y;          uint32_t x, y;
936          uint32_t bound;          uint32_t bound;
937          int cp_mb, st_mb;          int cp_mb, st_mb;
938          uint32_t mb_width = dec->mb_width;    const uint32_t mb_width = dec->mb_width;
939          uint32_t mb_height = dec->mb_height;    const uint32_t mb_height = dec->mb_height;
   
         if (reduced_resolution) {  
                 mb_width = (dec->width + 31) / 32;  
                 mb_height = (dec->height + 31) / 32;  
         }  
940    
941          if (!dec->is_edged[0]) {          if (!dec->is_edged[0]) {
942                  start_timer();                  start_timer();
# Line 891  Line 1014 
1014                                  }                                  }
1015                                  mb->quant = quant;                                  mb->quant = quant;
1016    
1017            mb->field_pred=0;
1018                                  if (dec->interlacing) {                                  if (dec->interlacing) {
1019                                          if (cbp || intra) {                                          if (cbp || intra) {
1020                                                  mb->field_dct = BitstreamGetBit(bs);                                                  mb->field_dct = BitstreamGetBit(bs);
# Line 916  Line 1040 
1040    
1041                                  } else if (mb->mode == MODE_INTER || mb->mode == MODE_INTER_Q) {                                  } else if (mb->mode == MODE_INTER || mb->mode == MODE_INTER_Q) {
1042    
1043                                          if (dec->interlacing && mb->field_pred) {            if(dec->interlacing) {
1044                                                  get_motion_vector(dec, bs, x, y, 0, &mb->mvs[0], fcode, bound);              /* Get motion vectors interlaced, field_pred is handled there */
1045                                                  get_motion_vector(dec, bs, x, y, 0, &mb->mvs[1], fcode, bound);              get_motion_vector_interlaced(dec, bs, x, y, 0, mb, fcode, bound);
1046                                          } else {                                          } else {
1047                                                  get_motion_vector(dec, bs, x, y, 0, &mb->mvs[0], fcode, bound);                                                  get_motion_vector(dec, bs, x, y, 0, &mb->mvs[0], fcode, bound);
1048                                                  mb->mvs[1] = mb->mvs[2] = mb->mvs[3] = mb->mvs[0];                                                  mb->mvs[1] = mb->mvs[2] = mb->mvs[3] = mb->mvs[0];
1049                                          }                                          }
1050                                  } else if (mb->mode == MODE_INTER4V ) {                                  } else if (mb->mode == MODE_INTER4V ) {
1051              /* interlaced missing here */
1052                                          get_motion_vector(dec, bs, x, y, 0, &mb->mvs[0], fcode, bound);                                          get_motion_vector(dec, bs, x, y, 0, &mb->mvs[0], fcode, bound);
1053                                          get_motion_vector(dec, bs, x, y, 1, &mb->mvs[1], fcode, bound);                                          get_motion_vector(dec, bs, x, y, 1, &mb->mvs[1], fcode, bound);
1054                                          get_motion_vector(dec, bs, x, y, 2, &mb->mvs[2], fcode, bound);                                          get_motion_vector(dec, bs, x, y, 2, &mb->mvs[2], fcode, bound);
# Line 932  Line 1057 
1057                                          mb->mvs[0].x = mb->mvs[1].x = mb->mvs[2].x = mb->mvs[3].x = 0;                                          mb->mvs[0].x = mb->mvs[1].x = mb->mvs[2].x = mb->mvs[3].x = 0;
1058                                          mb->mvs[0].y = mb->mvs[1].y = mb->mvs[2].y = mb->mvs[3].y =     0;                                          mb->mvs[0].y = mb->mvs[1].y = mb->mvs[2].y = mb->mvs[3].y =     0;
1059                                          decoder_mbintra(dec, mb, x, y, acpred_flag, cbp, bs, quant,                                          decoder_mbintra(dec, mb, x, y, acpred_flag, cbp, bs, quant,
1060                                                                          intra_dc_threshold, bound, reduced_resolution);                    intra_dc_threshold, bound);
1061                                          continue;                                          continue;
1062                                  }                                  }
1063    
1064                                  decoder_mbinter(dec, mb, x, y, cbp, bs,          /* See how to decode */
1065                                                                  rounding, reduced_resolution, 0);          if(!mb->field_pred)
1066             decoder_mbinter(dec, mb, x, y, cbp, bs, rounding, 0);
1067            else
1068             decoder_mbinter_field(dec, mb, x, y, cbp, bs, rounding, 0);
1069    
1070                          } else if (gmc_warp) {  /* a not coded S(GMC)-VOP macroblock */                          } else if (gmc_warp) {  /* a not coded S(GMC)-VOP macroblock */
1071                                  mb->mode = MODE_NOT_CODED_GMC;                                  mb->mode = MODE_NOT_CODED_GMC;
# Line 955  Line 1083 
1083    
1084                                  mb->mvs[0].x = mb->mvs[1].x = mb->mvs[2].x = mb->mvs[3].x = 0;                                  mb->mvs[0].x = mb->mvs[1].x = mb->mvs[2].x = mb->mvs[3].x = 0;
1085                                  mb->mvs[0].y = mb->mvs[1].y = mb->mvs[2].y = mb->mvs[3].y = 0;                                  mb->mvs[0].y = mb->mvs[1].y = mb->mvs[2].y = mb->mvs[3].y = 0;
1086            mb->field_pred=0; /* (!) */
1087    
1088                                  decoder_mbinter(dec, mb, x, y, 0, bs,                                  decoder_mbinter(dec, mb, x, y, 0, bs,
1089                                                                  rounding, reduced_resolution, 0);                                  rounding, 0);
1090    
1091                                  if(dec->out_frm && cp_mb > 0) {                                  if(dec->out_frm && cp_mb > 0) {
1092                                          output_slice(&dec->cur, dec->edged_width,dec->width,dec->out_frm,st_mb,y,cp_mb);                                          output_slice(&dec->cur, dec->edged_width,dec->width,dec->out_frm,st_mb,y,cp_mb);
# Line 1012  Line 1141 
1141  decoder_bf_interpolate_mbinter(DECODER * dec,  decoder_bf_interpolate_mbinter(DECODER * dec,
1142                                                                  IMAGE forward,                                                                  IMAGE forward,
1143                                                                  IMAGE backward,                                                                  IMAGE backward,
1144                                                                  const MACROBLOCK * pMB,                  MACROBLOCK * pMB,
1145                                                                  const uint32_t x_pos,                                                                  const uint32_t x_pos,
1146                                                                  const uint32_t y_pos,                                                                  const uint32_t y_pos,
1147                                                                  Bitstream * bs,                                                                  Bitstream * bs,
# Line 1029  Line 1158 
1158          pU_Cur = dec->cur.u + (y_pos << 3) * stride2 + (x_pos << 3);          pU_Cur = dec->cur.u + (y_pos << 3) * stride2 + (x_pos << 3);
1159          pV_Cur = dec->cur.v + (y_pos << 3) * stride2 + (x_pos << 3);          pV_Cur = dec->cur.v + (y_pos << 3) * stride2 + (x_pos << 3);
1160    
1161      validate_vector(pMB->mvs, x_pos, y_pos, dec);
1162      validate_vector(pMB->b_mvs, x_pos, y_pos, dec);
1163    
1164          if (!direct) {          if (!direct) {
1165                  uv_dx = pMB->mvs[0].x;                  uv_dx = pMB->mvs[0].x;
1166                  uv_dy = pMB->mvs[0].y;                  uv_dy = pMB->mvs[0].y;
   
1167                  b_uv_dx = pMB->b_mvs[0].x;                  b_uv_dx = pMB->b_mvs[0].x;
1168                  b_uv_dy = pMB->b_mvs[0].y;                  b_uv_dy = pMB->b_mvs[0].y;
1169    
1170                  if (dec->quarterpel) {                  if (dec->quarterpel) {
1171                            if (dec->bs_version <= BS_VERSION_BUGGY_CHROMA_ROUNDING) {
1172                                    uv_dx = (uv_dx>>1) | (uv_dx&1);
1173                                    uv_dy = (uv_dy>>1) | (uv_dy&1);
1174                                    b_uv_dx = (b_uv_dx>>1) | (b_uv_dx&1);
1175                                    b_uv_dy = (b_uv_dy>>1) | (b_uv_dy&1);
1176                            }
1177                            else {
1178                          uv_dx /= 2;                          uv_dx /= 2;
1179                          uv_dy /= 2;                          uv_dy /= 2;
1180                          b_uv_dx /= 2;                          b_uv_dx /= 2;
1181                          b_uv_dy /= 2;                          b_uv_dy /= 2;
1182                  }                  }
1183        }
1184    
1185                  uv_dx = (uv_dx >> 1) + roundtab_79[uv_dx & 0x3];                  uv_dx = (uv_dx >> 1) + roundtab_79[uv_dx & 0x3];
1186                  uv_dy = (uv_dy >> 1) + roundtab_79[uv_dy & 0x3];                  uv_dy = (uv_dy >> 1) + roundtab_79[uv_dy & 0x3];
   
1187                  b_uv_dx = (b_uv_dx >> 1) + roundtab_79[b_uv_dx & 0x3];                  b_uv_dx = (b_uv_dx >> 1) + roundtab_79[b_uv_dx & 0x3];
1188                  b_uv_dy = (b_uv_dy >> 1) + roundtab_79[b_uv_dy & 0x3];                  b_uv_dy = (b_uv_dy >> 1) + roundtab_79[b_uv_dy & 0x3];
1189    
1190          } else {          } else {
                 if(dec->quarterpel) {  
                         uv_dx = (pMB->mvs[0].x / 2) + (pMB->mvs[1].x / 2) + (pMB->mvs[2].x / 2) + (pMB->mvs[3].x / 2);  
                         uv_dy = (pMB->mvs[0].y / 2) + (pMB->mvs[1].y / 2) + (pMB->mvs[2].y / 2) + (pMB->mvs[3].y / 2);  
                         b_uv_dx = (pMB->b_mvs[0].x / 2) + (pMB->b_mvs[1].x / 2) + (pMB->b_mvs[2].x / 2) + (pMB->b_mvs[3].x / 2);  
                         b_uv_dy = (pMB->b_mvs[0].y / 2) + (pMB->b_mvs[1].y / 2) + (pMB->b_mvs[2].y / 2) + (pMB->b_mvs[3].y / 2);  
                 } else {  
1191                          uv_dx = pMB->mvs[0].x + pMB->mvs[1].x + pMB->mvs[2].x + pMB->mvs[3].x;                          uv_dx = pMB->mvs[0].x + pMB->mvs[1].x + pMB->mvs[2].x + pMB->mvs[3].x;
1192                          uv_dy = pMB->mvs[0].y + pMB->mvs[1].y + pMB->mvs[2].y + pMB->mvs[3].y;                          uv_dy = pMB->mvs[0].y + pMB->mvs[1].y + pMB->mvs[2].y + pMB->mvs[3].y;
1193                          b_uv_dx = pMB->b_mvs[0].x + pMB->b_mvs[1].x + pMB->b_mvs[2].x + pMB->b_mvs[3].x;                          b_uv_dx = pMB->b_mvs[0].x + pMB->b_mvs[1].x + pMB->b_mvs[2].x + pMB->b_mvs[3].x;
1194                          b_uv_dy = pMB->b_mvs[0].y + pMB->b_mvs[1].y + pMB->b_mvs[2].y + pMB->b_mvs[3].y;                          b_uv_dy = pMB->b_mvs[0].y + pMB->b_mvs[1].y + pMB->b_mvs[2].y + pMB->b_mvs[3].y;
1195    
1196        if (dec->quarterpel) {
1197          if (dec->bs_version <= BS_VERSION_BUGGY_CHROMA_ROUNDING) {
1198                                    uv_dx = (uv_dx>>1) | (uv_dx&1);
1199                                    uv_dy = (uv_dy>>1) | (uv_dy&1);
1200                                    b_uv_dx = (b_uv_dx>>1) | (b_uv_dx&1);
1201                                    b_uv_dy = (b_uv_dy>>1) | (b_uv_dy&1);
1202                            }
1203                            else {
1204            uv_dx /= 2;
1205            uv_dy /= 2;
1206            b_uv_dx /= 2;
1207            b_uv_dy /= 2;
1208          }
1209                  }                  }
1210    
1211                  uv_dx = (uv_dx >> 3) + roundtab_76[uv_dx & 0xf];                  uv_dx = (uv_dx >> 3) + roundtab_76[uv_dx & 0xf];
# Line 1107  Line 1253 
1253    
1254          if(dec->quarterpel) {          if(dec->quarterpel) {
1255                  if(!direct) {                  if(!direct) {
1256                          interpolate16x16_quarterpel(dec->tmp.y, backward.y, dec->qtmp.y, dec->qtmp.y + 64,        interpolate16x16_add_quarterpel(dec->cur.y, backward.y, dec->qtmp.y, dec->qtmp.y + 64,
1257                                                                                  dec->qtmp.y + 128, 16*x_pos, 16*y_pos,                                                                                  dec->qtmp.y + 128, 16*x_pos, 16*y_pos,
1258                                                                                  pMB->b_mvs[0].x, pMB->b_mvs[0].y, stride, 0);                                                                                  pMB->b_mvs[0].x, pMB->b_mvs[0].y, stride, 0);
1259                  } else {                  } else {
1260                          interpolate8x8_quarterpel(dec->tmp.y, backward.y, dec->qtmp.y, dec->qtmp.y + 64,        interpolate8x8_add_quarterpel(dec->cur.y, backward.y, dec->qtmp.y, dec->qtmp.y + 64,
1261                                                                                  dec->qtmp.y + 128, 16*x_pos, 16*y_pos,                                                                                  dec->qtmp.y + 128, 16*x_pos, 16*y_pos,
1262                                                                                  pMB->b_mvs[0].x, pMB->b_mvs[0].y, stride, 0);                                                                                  pMB->b_mvs[0].x, pMB->b_mvs[0].y, stride, 0);
1263                          interpolate8x8_quarterpel(dec->tmp.y, backward.y, dec->qtmp.y, dec->qtmp.y + 64,        interpolate8x8_add_quarterpel(dec->cur.y, backward.y, dec->qtmp.y, dec->qtmp.y + 64,
1264                                                                                  dec->qtmp.y + 128, 16*x_pos + 8, 16*y_pos,                                                                                  dec->qtmp.y + 128, 16*x_pos + 8, 16*y_pos,
1265                                                                                  pMB->b_mvs[1].x, pMB->b_mvs[1].y, stride, 0);                                                                                  pMB->b_mvs[1].x, pMB->b_mvs[1].y, stride, 0);
1266                          interpolate8x8_quarterpel(dec->tmp.y, backward.y, dec->qtmp.y, dec->qtmp.y + 64,        interpolate8x8_add_quarterpel(dec->cur.y, backward.y, dec->qtmp.y, dec->qtmp.y + 64,
1267                                                                                  dec->qtmp.y + 128, 16*x_pos, 16*y_pos + 8,                                                                                  dec->qtmp.y + 128, 16*x_pos, 16*y_pos + 8,
1268                                                                                  pMB->b_mvs[2].x, pMB->b_mvs[2].y, stride, 0);                                                                                  pMB->b_mvs[2].x, pMB->b_mvs[2].y, stride, 0);
1269                          interpolate8x8_quarterpel(dec->tmp.y, backward.y, dec->qtmp.y, dec->qtmp.y + 64,        interpolate8x8_add_quarterpel(dec->cur.y, backward.y, dec->qtmp.y, dec->qtmp.y + 64,
1270                                                                                  dec->qtmp.y + 128, 16*x_pos + 8, 16*y_pos + 8,                                                                                  dec->qtmp.y + 128, 16*x_pos + 8, 16*y_pos + 8,
1271                                                                                  pMB->b_mvs[3].x, pMB->b_mvs[3].y, stride, 0);                                                                                  pMB->b_mvs[3].x, pMB->b_mvs[3].y, stride, 0);
1272                  }                  }
1273          } else {          } else {
1274                  interpolate8x8_switch(dec->tmp.y, backward.y, 16 * x_pos, 16 * y_pos,      interpolate8x8_add_switch(dec->cur.y, backward.y, 16 * x_pos, 16 * y_pos,
1275                                                          pMB->b_mvs[0].x, pMB->b_mvs[0].y, stride, 0);                                                          pMB->b_mvs[0].x, pMB->b_mvs[0].y, stride, 0);
1276                  interpolate8x8_switch(dec->tmp.y, backward.y, 16 * x_pos + 8,      interpolate8x8_add_switch(dec->cur.y, backward.y, 16 * x_pos + 8,
1277                                                          16 * y_pos, pMB->b_mvs[1].x, pMB->b_mvs[1].y, stride, 0);                                                          16 * y_pos, pMB->b_mvs[1].x, pMB->b_mvs[1].y, stride, 0);
1278                  interpolate8x8_switch(dec->tmp.y, backward.y, 16 * x_pos,      interpolate8x8_add_switch(dec->cur.y, backward.y, 16 * x_pos,
1279                                                          16 * y_pos + 8, pMB->b_mvs[2].x, pMB->b_mvs[2].y, stride, 0);                                                          16 * y_pos + 8, pMB->b_mvs[2].x, pMB->b_mvs[2].y, stride, 0);
1280                  interpolate8x8_switch(dec->tmp.y, backward.y, 16 * x_pos + 8,      interpolate8x8_add_switch(dec->cur.y, backward.y, 16 * x_pos + 8,
1281                                                          16 * y_pos + 8, pMB->b_mvs[3].x, pMB->b_mvs[3].y, stride, 0);                                                          16 * y_pos + 8, pMB->b_mvs[3].x, pMB->b_mvs[3].y, stride, 0);
1282          }          }
1283    
1284          interpolate8x8_switch(dec->tmp.u, backward.u, 8 * x_pos, 8 * y_pos,    interpolate8x8_add_switch(dec->cur.u, backward.u, 8 * x_pos, 8 * y_pos,
1285                                                  b_uv_dx, b_uv_dy, stride2, 0);                                                  b_uv_dx, b_uv_dy, stride2, 0);
1286          interpolate8x8_switch(dec->tmp.v, backward.v, 8 * x_pos, 8 * y_pos,    interpolate8x8_add_switch(dec->cur.v, backward.v, 8 * x_pos, 8 * y_pos,
1287                                                  b_uv_dx, b_uv_dy, stride2, 0);                                                  b_uv_dx, b_uv_dy, stride2, 0);
1288    
         interpolate8x8_avg2(dec->cur.y + (16 * y_pos * stride) + 16 * x_pos,  
                                                 dec->cur.y + (16 * y_pos * stride) + 16 * x_pos,  
                                                 dec->tmp.y + (16 * y_pos * stride) + 16 * x_pos,  
                                                 stride, 1, 8);  
   
         interpolate8x8_avg2(dec->cur.y + (16 * y_pos * stride) + 16 * x_pos + 8,  
                                                 dec->cur.y + (16 * y_pos * stride) + 16 * x_pos + 8,  
                                                 dec->tmp.y + (16 * y_pos * stride) + 16 * x_pos + 8,  
                                                 stride, 1, 8);  
   
         interpolate8x8_avg2(dec->cur.y + ((16 * y_pos + 8) * stride) + 16 * x_pos,  
                                                 dec->cur.y + ((16 * y_pos + 8) * stride) + 16 * x_pos,  
                                                 dec->tmp.y + ((16 * y_pos + 8) * stride) + 16 * x_pos,  
                                                 stride, 1, 8);  
   
         interpolate8x8_avg2(dec->cur.y + ((16 * y_pos + 8) * stride) + 16 * x_pos + 8,  
                                                 dec->cur.y + ((16 * y_pos + 8) * stride) + 16 * x_pos + 8,  
                                                 dec->tmp.y + ((16 * y_pos + 8) * stride) + 16 * x_pos + 8,  
                                                 stride, 1, 8);  
   
         interpolate8x8_avg2(dec->cur.u + (8 * y_pos * stride2) + 8 * x_pos,  
                                                 dec->cur.u + (8 * y_pos * stride2) + 8 * x_pos,  
                                                 dec->tmp.u + (8 * y_pos * stride2) + 8 * x_pos,  
                                                 stride2, 1, 8);  
   
         interpolate8x8_avg2(dec->cur.v + (8 * y_pos * stride2) + 8 * x_pos,  
                                                 dec->cur.v + (8 * y_pos * stride2) + 8 * x_pos,  
                                                 dec->tmp.v + (8 * y_pos * stride2) + 8 * x_pos,  
                                                 stride2, 1, 8);  
   
1289          stop_comp_timer();          stop_comp_timer();
1290    
1291          if (cbp)          if (cbp)
1292                  decoder_mb_decode(dec, cbp, bs, pY_Cur, pU_Cur, pV_Cur, 0, pMB);      decoder_mb_decode(dec, cbp, bs, pY_Cur, pU_Cur, pV_Cur, pMB);
1293  }  }
1294    
1295  /* for decode B-frame dbquant */  /* for decode B-frame dbquant */
# Line 1218  Line 1334 
1334          uint32_t x, y;          uint32_t x, y;
1335          VECTOR mv;          VECTOR mv;
1336          const VECTOR zeromv = {0,0};          const VECTOR zeromv = {0,0};
         const int32_t TRB = dec->time_pp - dec->time_bp, TRD = dec->time_pp;  
1337          int i;          int i;
1338    
1339          if (!dec->is_edged[0]) {          if (!dec->is_edged[0]) {
# Line 1244  Line 1359 
1359                          MACROBLOCK *mb = &dec->mbs[y * dec->mb_width + x];                          MACROBLOCK *mb = &dec->mbs[y * dec->mb_width + x];
1360                          MACROBLOCK *last_mb = &dec->last_mbs[y * dec->mb_width + x];                          MACROBLOCK *last_mb = &dec->last_mbs[y * dec->mb_width + x];
1361                          const int fcode_max = (fcode_forward>fcode_backward) ? fcode_forward : fcode_backward;                          const int fcode_max = (fcode_forward>fcode_backward) ? fcode_forward : fcode_backward;
1362                          uint32_t intra_dc_threshold; /* fake variable */        int intra_dc_threshold; /* fake variable */
1363    
1364                          if (check_resync_marker(bs, fcode_max  - 1)) {                          if (check_resync_marker(bs, fcode_max  - 1)) {
1365                                  int bound = read_video_packet_header(bs, dec, fcode_max - 1, &quant,                                  int bound = read_video_packet_header(bs, dec, fcode_max - 1, &quant,
# Line 1269  Line 1384 
1384                          if (last_mb->mode == MODE_NOT_CODED) {                          if (last_mb->mode == MODE_NOT_CODED) {
1385                                  mb->cbp = 0;                                  mb->cbp = 0;
1386                                  mb->mode = MODE_FORWARD;                                  mb->mode = MODE_FORWARD;
1387                                  decoder_mbinter(dec, mb, x, y, mb->cbp, bs, 0, 0, 1);          decoder_mbinter(dec, mb, x, y, mb->cbp, bs, 0, 1);
1388                                  continue;                                  continue;
1389                          }                          }
1390    
# Line 1322  Line 1437 
1437    
1438                          case MODE_DIRECT_NONE_MV:                          case MODE_DIRECT_NONE_MV:
1439                                  for (i = 0; i < 4; i++) {                                  for (i = 0; i < 4; i++) {
1440                                          mb->mvs[i].x = (int32_t) ((TRB * last_mb->mvs[i].x) / TRD + mv.x);            mb->mvs[i].x = last_mb->mvs[i].x*dec->time_bp/dec->time_pp + mv.x;
1441                                          mb->b_mvs[i].x = (int32_t) ((mv.x == 0)            mb->mvs[i].y = last_mb->mvs[i].y*dec->time_bp/dec->time_pp + mv.y;
1442                                                                          ? ((TRB - TRD) * last_mb->mvs[i].x) / TRD  
1443                                                                          : mb->mvs[i].x - last_mb->mvs[i].x);            mb->b_mvs[i].x = (mv.x)
1444                                          mb->mvs[i].y = (int32_t) ((TRB * last_mb->mvs[i].y) / TRD + mv.y);              ?  mb->mvs[i].x - last_mb->mvs[i].x
1445                                          mb->b_mvs[i].y = (int32_t) ((mv.y == 0)              : last_mb->mvs[i].x*(dec->time_bp - dec->time_pp)/dec->time_pp;
1446                                                                          ? ((TRB - TRD) * last_mb->mvs[i].y) / TRD            mb->b_mvs[i].y = (mv.y)
1447                                                                          : mb->mvs[i].y - last_mb->mvs[i].y);              ? mb->mvs[i].y - last_mb->mvs[i].y
1448                : last_mb->mvs[i].y*(dec->time_bp - dec->time_pp)/dec->time_pp;
1449                                  }                                  }
1450    
1451                                  decoder_bf_interpolate_mbinter(dec, dec->refn[1], dec->refn[0],                                  decoder_bf_interpolate_mbinter(dec, dec->refn[1], dec->refn[0],
# Line 1351  Line 1467 
1467                                  get_b_motion_vector(bs, &mb->mvs[0], fcode_backward, dec->p_bmv, dec, x, y);                                  get_b_motion_vector(bs, &mb->mvs[0], fcode_backward, dec->p_bmv, dec, x, y);
1468                                  dec->p_bmv = mb->mvs[1] = mb->mvs[2] = mb->mvs[3] =     mb->mvs[0];                                  dec->p_bmv = mb->mvs[1] = mb->mvs[2] = mb->mvs[3] =     mb->mvs[0];
1469    
1470                                  decoder_mbinter(dec, mb, x, y, mb->cbp, bs, 0, 0, 0);          decoder_mbinter(dec, mb, x, y, mb->cbp, bs, 0, 0);
1471                                  break;                                  break;
1472    
1473                          case MODE_FORWARD:                          case MODE_FORWARD:
1474                                  get_b_motion_vector(bs, &mb->mvs[0], fcode_forward, dec->p_fmv, dec, x, y);                                  get_b_motion_vector(bs, &mb->mvs[0], fcode_forward, dec->p_fmv, dec, x, y);
1475                                  dec->p_fmv = mb->mvs[1] = mb->mvs[2] = mb->mvs[3] =     mb->mvs[0];                                  dec->p_fmv = mb->mvs[1] = mb->mvs[2] = mb->mvs[3] =     mb->mvs[0];
1476    
1477                                  decoder_mbinter(dec, mb, x, y, mb->cbp, bs, 0, 0, 1);          decoder_mbinter(dec, mb, x, y, mb->cbp, bs, 0, 1);
1478                                  break;                                  break;
1479    
1480                          default:                          default:
# Line 1369  Line 1485 
1485  }  }
1486    
1487  /* perform post processing if necessary, and output the image */  /* perform post processing if necessary, and output the image */
1488  void decoder_output(DECODER * dec, IMAGE * img, MACROBLOCK * mbs,  static void decoder_output(DECODER * dec, IMAGE * img, MACROBLOCK * mbs,
1489                                          xvid_dec_frame_t * frame, xvid_dec_stats_t * stats,                                          xvid_dec_frame_t * frame, xvid_dec_stats_t * stats,
1490                                          int coding_type, int quant)                                          int coding_type, int quant)
1491  {  {
# Line 1400  Line 1516 
1516                  stats->data.vop.qscale_stride = dec->mb_width;                  stats->data.vop.qscale_stride = dec->mb_width;
1517                  stats->data.vop.qscale = dec->qscale;                  stats->data.vop.qscale = dec->qscale;
1518                  if (stats->data.vop.qscale != NULL && mbs != NULL) {                  if (stats->data.vop.qscale != NULL && mbs != NULL) {
1519                          int i;        unsigned int i;
1520                          for (i = 0; i < dec->mb_width*dec->mb_height; i++)                          for (i = 0; i < dec->mb_width*dec->mb_height; i++)
1521                                  stats->data.vop.qscale[i] = mbs[i].quant;                                  stats->data.vop.qscale[i] = mbs[i].quant;
1522                  } else                  } else
# Line 1408  Line 1524 
1524          }          }
1525  }  }
1526    
   
1527  int  int
1528  decoder_decode(DECODER * dec,  decoder_decode(DECODER * dec,
1529                                  xvid_dec_frame_t * frame, xvid_dec_stats_t * stats)                                  xvid_dec_frame_t * frame, xvid_dec_stats_t * stats)
# Line 1416  Line 1531 
1531    
1532          Bitstream bs;          Bitstream bs;
1533          uint32_t rounding;          uint32_t rounding;
         uint32_t reduced_resolution;  
1534          uint32_t quant = 2;          uint32_t quant = 2;
1535          uint32_t fcode_forward;          uint32_t fcode_forward;
1536          uint32_t fcode_backward;          uint32_t fcode_backward;
# Line 1471  Line 1585 
1585    
1586  repeat:  repeat:
1587    
1588          coding_type = BitstreamReadHeaders(&bs, dec, &rounding, &reduced_resolution,    coding_type = BitstreamReadHeaders(&bs, dec, &rounding,
1589                          &quant, &fcode_forward, &fcode_backward, &intra_dc_threshold, &gmc_warp);                          &quant, &fcode_forward, &fcode_backward, &intra_dc_threshold, &gmc_warp);
1590    
1591          DPRINTF(XVID_DEBUG_HEADER, "coding_type=%i,  packed=%i,  time=%lli,  time_pp=%i,  time_bp=%i\n",    DPRINTF(XVID_DEBUG_HEADER, "coding_type=%i,  packed=%i,  time=%"
1592    #if defined(_MSC_VER)
1593        "I64"
1594    #else
1595        "ll"
1596    #endif
1597        "i,  time_pp=%i,  time_bp=%i\n",
1598                                                          coding_type,    dec->packed_mode, dec->time, dec->time_pp, dec->time_bp);                                                          coding_type,    dec->packed_mode, dec->time, dec->time_pp, dec->time_bp);
1599    
1600          if (coding_type == -1) { /* nothing */          if (coding_type == -1) { /* nothing */
# Line 1522  Line 1642 
1642          } else if (coding_type != B_VOP) {          } else if (coding_type != B_VOP) {
1643                  switch(coding_type) {                  switch(coding_type) {
1644                  case I_VOP :                  case I_VOP :
1645                          decoder_iframe(dec, &bs, reduced_resolution, quant, intra_dc_threshold);        decoder_iframe(dec, &bs, quant, intra_dc_threshold);
1646                          break;                          break;
1647                  case P_VOP :                  case P_VOP :
1648                          decoder_pframe(dec, &bs, rounding, reduced_resolution, quant,        decoder_pframe(dec, &bs, rounding, quant,
1649                                                  fcode_forward, intra_dc_threshold, NULL);                                                  fcode_forward, intra_dc_threshold, NULL);
1650                          break;                          break;
1651                  case S_VOP :                  case S_VOP :
1652                          decoder_pframe(dec, &bs, rounding, reduced_resolution, quant,        decoder_pframe(dec, &bs, rounding, quant,
1653                                                  fcode_forward, intra_dc_threshold, &gmc_warp);                                                  fcode_forward, intra_dc_threshold, &gmc_warp);
1654                          break;                          break;
1655                  case N_VOP :                  case N_VOP :
# Line 1540  Line 1660 
1660                          break;                          break;
1661                  }                  }
1662    
                 if (reduced_resolution) {  
                         image_deblock_rrv(&dec->cur, dec->edged_width, dec->mbs,  
                                 (dec->width + 31) / 32, (dec->height + 31) / 32, dec->mb_width,  
                                 16, 0);  
                 }  
   
1663                  /* note: for packed_mode, output is performed when the special-N_VOP is decoded */                  /* note: for packed_mode, output is performed when the special-N_VOP is decoded */
1664                  if (!(dec->low_delay_default && dec->packed_mode)) {                  if (!(dec->low_delay_default && dec->packed_mode)) {
1665                          if (dec->low_delay) {                          if (dec->low_delay) {
# Line 1563  Line 1677 
1677                  image_swap(&dec->cur, &dec->refn[0]);                  image_swap(&dec->cur, &dec->refn[0]);
1678                  dec->is_edged[0] = 0;                  dec->is_edged[0] = 0;
1679                  SWAP(MACROBLOCK *, dec->mbs, dec->last_mbs);                  SWAP(MACROBLOCK *, dec->mbs, dec->last_mbs);
                 dec->last_reduced_resolution = reduced_resolution;  
1680                  dec->last_coding_type = coding_type;                  dec->last_coding_type = coding_type;
1681    
1682                  dec->frames++;                  dec->frames++;
# Line 1573  Line 1686 
1686    
1687                  if (dec->low_delay) {                  if (dec->low_delay) {
1688                          DPRINTF(XVID_DEBUG_ERROR, "warning: bvop found in low_delay==1 stream\n");                          DPRINTF(XVID_DEBUG_ERROR, "warning: bvop found in low_delay==1 stream\n");
1689                          dec->low_delay = 1;        dec->low_delay = 0;
1690                  }                  }
1691    
1692                  if (dec->frames < 2) {                  if (dec->frames < 2) {
# Line 1608  Line 1721 
1721    
1722  done :  done :
1723    
1724          /* low_delay_default mode: if we've gotten here without outputting anything,    /* if we reach here without outputing anything _and_
1725             then output the recently decoded frame, or print an error message  */       the calling application has specified low_delay_default,
1726         we *must* output something.
1727         this always occurs on the first call to decode() call
1728         when bframes are present in the bitstream. it may also
1729         occur if no vops  were seen in the bitstream
1730    
1731         if packed_mode is enabled, then we output the recently
1732         decoded frame (the very first ivop). otherwise we have
1733         nothing to display, and therefore output a black screen.
1734      */
1735          if (dec->low_delay_default && output == 0) {          if (dec->low_delay_default && output == 0) {
1736                  if (dec->packed_mode && seen_something) {                  if (dec->packed_mode && seen_something) {
                         /* output the recently decoded frame */  
1737                          decoder_output(dec, &dec->refn[0], dec->last_mbs, frame, stats, dec->last_coding_type, quant);                          decoder_output(dec, &dec->refn[0], dec->last_mbs, frame, stats, dec->last_coding_type, quant);
1738                  } else {                  } else {
1739                          image_clear(&dec->cur, dec->width, dec->height, dec->edged_width, 0, 128, 128);                          image_clear(&dec->cur, dec->width, dec->height, dec->edged_width, 0, 128, 128);
                         image_printf(&dec->cur, dec->edged_width, dec->height, 16, 16,  
                                 "warning: nothing to output");  
                         image_printf(&dec->cur, dec->edged_width, dec->height, 16, 64,  
                                 "bframe decoder lag");  
   
1740                          decoder_output(dec, &dec->cur, NULL, frame, stats, P_VOP, quant);                          decoder_output(dec, &dec->cur, NULL, frame, stats, P_VOP, quant);
1741                          if (stats) stats->type = XVID_TYPE_NOTHING;                          if (stats) stats->type = XVID_TYPE_NOTHING;
1742                  }                  }

Legend:
Removed from v.1.57  
changed lines
  Added in v.1.75

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