⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 macroblock.c

📁 JM 11.0 KTA 2.1 Source Code
💻 C
📖 第 1 页 / 共 5 页
字号:
        if(img->cod_counter == 0 && (img->current_mb_nr%2 == 0))
        {
          TRACE_STRING("mb_field_decoding_flag (of coded bottom mb)");
          currSE.len = 1;
          readSyntaxElement_FLC(&currSE, dP->bitstream);
          dP->bitstream->frame_bitoffset--;
          currMB->mb_field = currSE.value1;
        }
        else if(img->cod_counter > 0 && (img->current_mb_nr%2 == 0))
        {
          // check left macroblock pair first
          if (mb_is_available(img->current_mb_nr-2, img->current_mb_nr)&&((img->current_mb_nr%(img->PicWidthInMbs*2))!=0))
          {
            currMB->mb_field = img->mb_data[img->current_mb_nr-2].mb_field;
          }
          else
          {
            // check top macroblock pair
            if (mb_is_available(img->current_mb_nr-2*img->PicWidthInMbs, img->current_mb_nr))
            {
              currMB->mb_field = img->mb_data[img->current_mb_nr-2*img->PicWidthInMbs].mb_field;
            }
            else
              currMB->mb_field = 0;
          }
        }
      }
    }
  }

  dec_picture->mb_field[img->current_mb_nr] = currMB->mb_field;

  img->siblock[img->mb_x][img->mb_y]=0;

  if ((img->type==P_SLICE ))    // inter frame
    interpret_mb_mode_P(img);
  else if (img->type==I_SLICE)                                  // intra frame
    interpret_mb_mode_I(img);
  else if ((img->type==B_SLICE))       // B frame
    interpret_mb_mode_B(img);
  else if ((img->type==SP_SLICE))     // SP frame
    interpret_mb_mode_P(img);
  else if (img->type==SI_SLICE)     // SI frame
    interpret_mb_mode_SI(img);

#ifdef ADAPTIVE_QUANTIZATION
  if( currMB->cbp==0 || currMB->mb_type==IPCM) currMB->mb_iaqms_idx = 0;
#endif  
  if(img->MbaffFrameFlag)
  {
    if(currMB->mb_field)
    {
      img->num_ref_idx_l0_active <<=1;
      img->num_ref_idx_l1_active <<=1;
    }
  }

  //init NoMbPartLessThan8x8Flag
  currMB->NoMbPartLessThan8x8Flag = (IS_DIRECT(currMB) && !(active_sps->direct_8x8_inference_flag))? 0: 1;

  //====== READ 8x8 SUB-PARTITION MODES (modes of 8x8 blocks) and Intra VBST block modes ======
  if (IS_P8x8 (currMB))
  {
    currSE.type    = SE_MBTYPE;
    dP = &(currSlice->partArr[partMap[SE_MBTYPE]]);

    for (i=0; i<4; i++)
    {
      if (active_pps->entropy_coding_mode_flag ==UVLC || dP->bitstream->ei_flag) currSE.mapping = linfo_ue;
      else                                                  currSE.reading = readB8_typeInfo_CABAC;

      TRACE_STRING("sub_mb_type");
      dP->readSyntaxElement (&currSE, img, inp, dP);
      SetB8Mode (img, currMB, currSE.value1, i);

      //set NoMbPartLessThan8x8Flag for P8x8 mode
      currMB->NoMbPartLessThan8x8Flag &= (currMB->b8mode[i]==0 && active_sps->direct_8x8_inference_flag) || 
        (currMB->b8mode[i]==4);
    }
    //--- init macroblock data ---
    init_macroblock       (img);
    readMotionInfoFromNAL (img, inp);
  }


  //============= Transform Size Flag for INTRA MBs =============
  //-------------------------------------------------------------
  //transform size flag for INTRA_4x4 and INTRA_8x8 modes
  if (currMB->mb_type == I4MB && img->Transform8x8Mode)
  {
    currSE.type   =  SE_HEADER;
    dP = &(currSlice->partArr[partMap[SE_HEADER]]);
    currSE.reading = readMB_transform_size_flag_CABAC;
    TRACE_STRING("transform size 8x8 flag");

    // read UVLC transform_size_8x8_flag
    if (active_pps->entropy_coding_mode_flag == UVLC || dP->bitstream->ei_flag)
    {
      currSE.len = 1;
      readSyntaxElement_FLC(&currSE, dP->bitstream);
    } 
    else 
    {
      dP->readSyntaxElement(&currSE,img,inp,dP);
    } 

    currMB->luma_transform_size_8x8_flag = currSE.value1;

    if (currMB->luma_transform_size_8x8_flag)
    {
      currMB->mb_type = I8MB;
      for (i=0;i<4;i++) 
      {
        currMB->b8mode[i]=I8MB;
        currMB->b8pdir[i]=-1;
      }
    }
  }
  else
  {
    currMB->luma_transform_size_8x8_flag = 0;
  }

  if(active_pps->constrained_intra_pred_flag && (img->type==P_SLICE|| img->type==B_SLICE))        // inter frame
  {
    if( !IS_INTRA(currMB) )
    {
      img->intra_block[img->current_mb_nr] = 0;
    }
  }

  //! TO for error concealment
  //! If we have an INTRA Macroblock and we lost the partition
  //! which contains the intra coefficients Copy MB would be better 
  //! than just a gray block.
  //! Seems to be a bit at the wrong place to do this right here, but for this case 
  //! up to now there is no other way.
  dP = &(currSlice->partArr[partMap[SE_CBP_INTRA]]);
  if(IS_INTRA (currMB) && dP->bitstream->ei_flag && img->number)
  {
    currMB->mb_type = 0;
    currMB->ei_flag = 1;
    for (i=0;i<4;i++)
    {
      currMB->b8mode[i]=currMB->b8pdir[i]=0;
    }
  }
  dP = &(currSlice->partArr[partMap[currSE.type]]);
  //! End TO


  //--- init macroblock data ---
  if (!IS_P8x8 (currMB))
    init_macroblock       (img);

  if (IS_DIRECT (currMB) && img->cod_counter >= 0)
  {
    currMB->cbp = 0;
    reset_coeffs();

    if (active_pps->entropy_coding_mode_flag ==CABAC)
      img->cod_counter=-1;

    return DECODE_MB;
  }

  if (IS_COPY (currMB)) //keep last macroblock
  {
    int i, j, k;
    short pmv[2];
    int zeroMotionAbove;
    int zeroMotionLeft;
    PixelPos mb_a, mb_b;
    int      a_mv_y = 0;
    int      a_ref_idx = 0;
    int      b_mv_y = 0;
    int      b_ref_idx = 0;
    int      list_offset = ((img->MbaffFrameFlag)&&(currMB->mb_field))? img->current_mb_nr%2 ? 4 : 2 : 0;

    getLuma4x4Neighbour(img->current_mb_nr,0,0,-1, 0,&mb_a);
    getLuma4x4Neighbour(img->current_mb_nr,0,0, 0,-1,&mb_b);

    if (mb_a.available)
    {
      a_mv_y    = dec_picture->mv[LIST_0][mb_a.pos_y][mb_a.pos_x][1];
      a_ref_idx = dec_picture->ref_idx[LIST_0][mb_a.pos_y][mb_a.pos_x];

      if (currMB->mb_field && !img->mb_data[mb_a.mb_addr].mb_field)
      {
        a_mv_y    /=2;
        a_ref_idx *=2;
      }
      if (!currMB->mb_field && img->mb_data[mb_a.mb_addr].mb_field)
      {
        a_mv_y    *=2;
        a_ref_idx >>=1;
      }
    }

    if (mb_b.available)
    {
      b_mv_y    = dec_picture->mv[LIST_0][mb_b.pos_y][mb_b.pos_x][1];
      b_ref_idx = dec_picture->ref_idx[LIST_0][mb_b.pos_y][mb_b.pos_x];

      if (currMB->mb_field && !img->mb_data[mb_b.mb_addr].mb_field)
      {
        b_mv_y    /=2;
        b_ref_idx *=2;
      }
      if (!currMB->mb_field && img->mb_data[mb_b.mb_addr].mb_field)
      {
        b_mv_y    *=2;
        b_ref_idx >>=1;
      }
    }

    zeroMotionLeft  = !mb_a.available ? 1 : a_ref_idx==0 && dec_picture->mv[LIST_0][mb_a.pos_y][mb_a.pos_x][0]==0 && a_mv_y==0 ? 1 : 0;
    zeroMotionAbove = !mb_b.available ? 1 : b_ref_idx==0 && dec_picture->mv[LIST_0][mb_b.pos_y][mb_b.pos_x][0]==0 && b_mv_y==0 ? 1 : 0;

    currMB->cbp = 0;
    reset_coeffs();

    img_block_y   = img->block_y;

#ifdef MV_COMPETITION

    if (mv_comp.mv_competition > 0)

    {
      short prediction_mode_for_skip;
      short predictor;

      for (prediction_mode_for_skip = 0; prediction_mode_for_skip<mv_comp.nb_mode_for_skip; prediction_mode_for_skip++)
      {
        SetMotionVectorPredictor_Skip(pmv, pmv+1, dec_picture->ref_idx, dec_picture->mv, 0, LIST_0, 0, 0, 16, 16,prediction_mode_for_skip);
        mv_comp.mv_pred_skip[prediction_mode_for_skip][0] = pmv[0];
        mv_comp.mv_pred_skip[prediction_mode_for_skip][1] = pmv[1];
      }

      if ((mv_comp.nb_mode_for_skip> 1) && (read_index_for_skip_mode() == TRUE))
        predictor = readPredictorForSkip(img,inp);
      else 
        predictor = 0;

      for(i=0;i<BLOCK_SIZE;i++)
        for(j=0;j<BLOCK_SIZE;j++)
          for (k=0;k<2;k++)
            dec_picture->mv[LIST_0][img_block_y+j][img->block_x+i][k] = mv_comp.mv_pred_skip[predictor][k];
    }
    else
#endif

    {


      if (zeroMotionAbove || zeroMotionLeft)
      {
        for(i=0;i<BLOCK_SIZE;i++)
          for(j=0;j<BLOCK_SIZE;j++)
            for (k=0;k<2;k++)
              dec_picture->mv[LIST_0][img->block_y+j][img->block_x+i][k] = 0;
      }
      else
      {
        SetMotionVectorPredictor (img, pmv, pmv+1, 0, LIST_0, dec_picture->ref_idx, dec_picture->mv, 0, 0, 16, 16);

        for(i=0;i<BLOCK_SIZE;i++)
          for(j=0;j<BLOCK_SIZE;j++)
            for (k=0;k<2;k++)
            {
              dec_picture->mv[LIST_0][img_block_y+j][img->block_x+i][k] = pmv[k];
            }
      }


    }

    for(i=0;i<BLOCK_SIZE;i++)
      for(j=0;j<BLOCK_SIZE;j++)
      {
        dec_picture->ref_idx[LIST_0][img_block_y+j][img->block_x+i] = 0;
        dec_picture->ref_pic_id[LIST_0][img_block_y+j][img->block_x+i] = 
          dec_picture->ref_pic_num[img->current_slice_nr][LIST_0 + list_offset][(short)dec_picture->ref_idx[LIST_0][img_block_y+j][img->block_x+i]];
      }

      return DECODE_MB;
  }
  if(currMB->mb_type!=IPCM)
  {

    // intra prediction modes for a macroblock 4x4 **********************************************
    read_ipred_modes(img,inp);

    // read inter frame vector data *********************************************************
    if (IS_INTERMV (currMB) && (!IS_P8x8(currMB)))
    {
      readMotionInfoFromNAL (img, inp);
    }
    // read CBP and Coeffs  ***************************************************************
    readCBPandCoeffsFromNAL (img,inp);
  }
  else
  {
    //read pcm_alignment_zero_bit and pcm_byte[i] 

    // here dP is assigned with the same dP as SE_MBTYPE, because IPCM syntax is in the 
    // same category as MBTYPE
    dP = &(currSlice->partArr[partMap[SE_MBTYPE]]);
    readIPCMcoeffsFromNAL(img,inp,dP);
  }

#ifdef ADAPTIVE_FD_SD_CODING
  if (currMB->written_SD_Coding_on_off==0)
  {
    currMB->SD_Coding_on_off=0;
  }
#endif
  return DECODE_MB;
}



/*!
************************************************************************
* \brief
*    Initialize decoding engine after decoding an IPCM macroblock
*    (for IPCM CABAC  28/11/2003)
*
* \author
*    Dong Wang <Dong.Wang@bristol.ac.uk>  
************************************************************************
*/
void init_decoding_engine_IPCM(struct img_par *img)
{
  Slice *currSlice = img->currentSlice;
  Bitstream *currStream;
  int ByteStartPosition;
  int PartitionNumber;
  int i;

  if(currSlice->dp_mode==PAR_DP_1)
    PartitionNumber=1;
  else if(currSlice->dp_mode==PAR_DP_3)
    PartitionNumber=3;
  else
  {
    printf("Partition Mode is not supported\n");
    exit(1);
  }

  for(i=0;i<PartitionNumber;i++)
  {
    currStream = currSlice->partArr[i].bitstream;
    ByteStartPosition = currStream->read_len;


    arideco_start_decoding (&currSlice->partArr[i].de_cabac, currStream->streamBuffer, ByteStartPosition, &currStream->read_len, img->type);
  }
}




/*!
************************************************************************
* \brief
*    Read IPCM pcm_alignment_zero_bit and pcm_byte[i] from stream to img->cof
*    (for IPCM CABAC and IPCM CAVLC)
*
* \author
*    Dong Wang <Dong.Wang@bristol.ac.uk>
************************************************************************
*/

void readIPCMcoeffsFromNAL(struct img_par *img, struct inp_par *inp, struct datapartition *dP)
{
  SyntaxElement currSE;
  int i,j;

  //For CABAC, we don't need to read bits to let stream byte aligned
  //  because we have variable for integer bytes position
  if(active_pps->entropy_coding_mode_flag  == CABAC)
  {
    //read luma and chroma IPCM coefficients
    currSE.len=8;
    TRACE_STRING("pcm_byte luma");

    for(i=0;i<MB_BLOCK_SIZE;i++)
    {
      for(j=0;j<MB_BLOCK_SIZE;j++)
      {
        readIPCMBytes_CABAC(&currSE, dP->bitstream);
        img->cof[i/4][j/4][i%4][j%4]=currSE.value1;
      }
    } 
    if (dec_picture->chroma_format_idc != YUV400)
    {
      TRACE_STRING("pcm_byte chroma");
      for(i=0;i<img->mb_cr_size_y;i++)
      {
        for(j=0;j<img->mb_cr_size_x;j++)
        {
          readIPCMBytes_CABAC(&currSE, dP->bitstream);
          img->cof[i/4][j/4+4][i%4][j%4]=currSE.value1;
        }
      } 
      for(i=0;i<img->mb_cr_size_y;i++)
      {
        for(j=0;j<img->mb_cr_size_x;j++)

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -