www.pudn.com > wm2.5.zip > compensation.c


/* 
*********************************************************************** 
* COPYRIGHT AND WARRANTY INFORMATION 
* 
* Copyright 2004, Advanced Audio Video Coding Standard, Part II 
* 
* DISCLAIMER OF WARRANTY 
* 
* These software programs are available to the users without any 
* license fee or royalty on an "as is" basis. The AVS disclaims 
* any and all warranties, whether express, implied, or statutory, 
* including any implied warranties of merchantability or of fitness 
* for a particular purpose. In no event shall the contributors or  
* the AVS be liable for any incidental, punitive, or consequential 
* damages of any kind whatsoever arising from the use of this program. 
* 
* This disclaimer of warranty extends to the user of this program 
* and user's customers, employees, agents, transferees, successors, 
* and assigns. 
* 
* The AVS does not represent or warrant that the program furnished 
* hereunder are free of infringement of any third-party patents. 
* Commercial implementations of AVS, including shareware, may be 
* subject to royalty fees to patent holders. Information regarding 
* the AVS patent policy is available from the AVS Web site at 
* http://www.avs.org.cn 
* 
* THIS IS NOT A GRANT OF PATENT RIGHTS - SEE THE AVS PATENT POLICY. 
************************************************************************ 
*/   
 
#include  
#include  
#include "global.h" 
#include "defines.h" 
#include "block.h" 
#include "intraprediction.h" 
 
void abt_dequant_B8(int qp, int blk);  
void abt_Itransform_B8(int blk);  
					  
/* 
************************************************************************* 
* Function: motion compensation for one macroblock 
* Input:  
* Output: 
* Return:  
* Attention: 
************************************************************************* 
*/ 
int decode_one_macroblock()     
{ // 
 
  int bs_x=8; 
  int bs_y=8; 
  int bx,by; 
  int tmp_block[4][4]; 
  int i=0,j=0,ii=0,jj=0,i1=0,j1=0,j4=0,i4=0; 
  int js0=0,js1=0,js2=0,js3=0,jf=0; 
  int uv; 
  int vec1_x=0,vec1_y=0,vec2_x=0,vec2_y=0; 
  int k; 
  int ioff,joff; 
  int tmp; 
  int b8, b4;   // needed for ABT 
  int ii0,jj0,ii1,jj1,if1,jf1,if0,jf0; 
  int mv_mul,f1,f2,f3,f4; 
  int chroma_offset =0; 
 
#if TRACE 
  int mb_y,mb_x; 
//  int mb_uv; 
#endif 
   
  const byte decode_block_scan[16] = {0,1,4,5,2,3,6,7,8,9,12,13,10,11,14,15}; 
   
  int refframe; // = pgcurrMB->ref_frame; 
  int fw_ref_idx; 
  int*** mv_array; 
  int  b8_s=0,b8_e=4,incr_y=1,off_y=0,even_y=4,add_y=0; 
   
  int mb_nr             = pgImage->current_mb_nr;//GBimg->current_mb_nr; 
  int mb_width          = pgImage->width/16; 
  int mb_available_up; 
  int mb_available_left; 
   
  mb_available_up   = (pgImage->mb_y == 0) ? 0 :  
                      (mb_data[mb_nr].slice_nr == mb_data[mb_nr-mb_width].slice_nr); 
  mb_available_left = (pgImage->mb_x == 0) ? 0 :  
					            (mb_data[mb_nr].slice_nr == mb_data[mb_nr-1].slice_nr); 
   
#ifdef _ISOLATED_REGION_ 
  //added by cbzhu, 2004.12.4 
  if (iREGenable) 
  { 
      if (pgImage->type == P_IMG) 
      { 
          if (mb_available_up != 0) 
          { 
              if (iREGmap[pgImage->mb_y - 1][pgImage->mb_x] != 2) 
              { 
                  mb_available_up = 0; 
              } 
          } 
          if (mb_available_left != 0) 
          { 
              if (iREGmap[pgImage->mb_y][pgImage->mb_x - 1] != 2) 
              { 
                  mb_available_left = 0; 
              } 
          } 
      } 
  } 
#endif // _ISOLATED_REGION_ 
   
  mv_mul=4; 
  f1=8; 
  f2=7; 
   
  f3=f1*f1; 
  f4=f3/2; 
  //if(pgImage->number==1 && pgImage->current_mb_nr ==0) 
   
  //f4=f4; 
  // luma decoding ************************************************** 
  for (b8=0; b8<4; b8++) 
  { 
	  //WJP 040903 
	  if(pgcurrMB->mb_type==4 && pgcurrMB->sub_mb_type[b8]==0 && (!ABT_RDO) && USE_ABT) 
		  pgcurrMB->abt_block_size_flag=1; 
	  //WJP END 
 
	  for (b4 = 0; b4 < 4; b4 ++)  //zhangnan 
	  { 
		  k = b8*4 + b4; 
		  i = (decode_block_scan[k] & 3); 
		  j = ((decode_block_scan[k] >> 2) & 3); 
		   
		  ioff=i*4; 
		  i4=pgImage->block4_x+i; 
		   
		  joff=j*4; 
		  j4=pgImage->block4_y+j; 
		   
		  if (pgcurrMB->mb_type != I4MB) 
		  {//===== FORWARD PREDICTION ===== 
			  refframe = refFrArr[j4][i4]; 
			  fw_ref_idx = refframe; 
			  mv_array = pgImage->mv; 
			   
			  vec1_x = i4*4*mv_mul + mv_array[i4+BLOCK_SIZE][j4][0]; 
			  vec1_y = j4*4*mv_mul + mv_array[i4+BLOCK_SIZE][j4][1]; 
 
	     //fprintf(p_trace,"@INTER_MV (x,y) (%d,%d)\n" , vec1_x,vec1_y); MAZHAN 
			//--- INTER PREDICTION --- 
			//Get the block from reference frame with MVP 
			  get_block(vec1_x, vec1_y, tmp_block,reference_frame[refframe][0]); 
			   
			  for(ii=0;ii<4;ii++) 
				  for(jj=0;jj<4;jj++)  
				  { 
					  pgcurrMB->pred_sample[b8][b4][ii][jj] = tmp_block[ii][jj]; //vld 
				  } 
		  } 
		  else 
		  {			 
			  //--- INTRA PREDICTION --- 
			  tmp = intrapred(b8, b4, ioff, joff, i4, j4); 
			   
			   
			  if ( tmp == SEARCH_SYNC)  /* make 4x4 prediction block mpr from given prediction pgImage->mb_mode */ 
				  return SEARCH_SYNC;       
		  } 
		   
		  Get_residual(b8,b4); 
 
		  if((pgcurrMB->mb_type == I4MB)||(pgcurrMB->abt_block_size_flag==0)) // qhg for abt. 
		  { 
			  Dequant_B4(pgcurrMB->qp, b8, b4);  //zhangnan 
			  Inv_Transform_B4 (b8,b4); 
			  Recon_B4(b8, b4); 
		  } 
	  }  
 
	  if(pgcurrMB->mb_type != I4MB&&pgcurrMB->abt_block_size_flag==1) // qhg for abt. 
	  {		   
		  abt_dequant_B8(pgcurrMB->qp, b8); 
		  abt_Itransform_B8(b8); 
		   
		  for(b4 = 0; b4 < 4; b4 ++) 
		  { 
			  Recon_B4(b8, b4); 
		  } 
	  }  
	  //WJP 040903 
	  if(pgcurrMB->mb_type==4 && pgcurrMB->sub_mb_type[b8]==0 && (!ABT_RDO) && USE_ABT) 
		  pgcurrMB->abt_block_size_flag=0; 
	  //WJP END 
  } 
 
   
  // chroma decoding ******************************************************* 
    if(IS_INTRA(pgcurrMB)) 
    { 
      for (b4=0;b4<4;b4++) 
      { 
        intrapred_chroma_4x4(pgImage->mb_x,pgImage->mb_y,b4,pgcurrMB->c_ipred_mode); 
        bx = (b4 &1)<<2; 
        by = (b4>>1)<<2; 
        for (uv=0; uv<2;uv++) 
        { 
          Get_residual(4+uv,b4); 
          Dequant_B4(pgcurrMB->qp, 4+uv, b4); 
          Inv_Transform_B4 (4+uv,b4); 
          Recon_B4(4+uv, b4); 
        } 
      } 
 
    } 
    else 
    { //--- FORWARD PREDICTION --- 
        for(uv =0;uv<2;uv++) 
        { 
            for (j=4;j<6;j++) 
            { 
                joff = (j-4)*4; 
                j4 = pgImage->pix_c_y + joff; 
                for (i=0;i<2;i++) 
                { 
                    ioff = i*4; 
                    i4 = pgImage->pix_c_x + ioff; 
                    mv_array = pgImage->mv; 
                    for(jj=0;jj<4;jj++) 
                    { 
                        jf=(j4+jj)/2; 
                        for(ii=0;ii<4;ii++) 
                        { 
                            if1=(i4+ii)/2; 
                            refframe = refFrArr[jf][if1]; 
                            fw_ref_idx = refFrArr[jf][if1]; 
                            chroma_offset = 0; 
                            i1=(pgImage->pix_c_x+ii+ioff)*f1+mv_array[if1+4][jf][0]; 
                            j1=(pgImage->pix_c_y+jj+joff)*f1+mv_array[if1+4][jf][1]; 
                            j1 += chroma_offset; 
                            ii0=max (0, min (i1/f1, pgImage->width_cr-1)); 
                            jj0=max (0, min (j1/f1, pgImage->height_cr-1)); 
                            ii1=max (0, min ((i1+f2)/f1, pgImage->width_cr-1)); 
                            jj1=max (0, min ((j1+f2)/f1, pgImage->height_cr-1));				 
                            if1=(i1 & f2); 
                            jf1=(j1 & f2); 
                            if0=f1-if1; 
                            jf0=f1-jf1; 
                            pgcurrMB->pred_sample[4+uv][(j-4)*2+i][ii][jj]= 
                                (if0*jf0*reference_frame[refframe][uv+1][jj0][ii0] 
                                +if1*jf0*reference_frame[refframe][uv+1][jj0][ii1] 
                                +if0*jf1*reference_frame[refframe][uv+1][jj1][ii0] 
                                +if1*jf1*reference_frame[refframe][uv+1][jj1][ii1]+f4)/f3; 
                        } //end for ii 
                    }// end for jj 
                } // end for i 
            }// end for j 
            for(b4=0; b4<4; b4++) 
            { 
                Get_residual(4+uv,b4); 
                Dequant_B4(pgcurrMB->qp, 4+uv, b4); 
            } 
        
            for(b4=0; b4<4; b4++) 
            { 
                Inv_Transform_B4 (4+uv,b4); 
                Recon_B4(4+uv, b4); 
            } 
        }// end for uv 
    } // end for   if(IS_INTRA(pgcurrMB)) 
   
    
#if TRACE 
 
	//Inter Pred Processing: 
    for (b8=0; b8<6; b8++) 
	  for (b4 = 0; b4 < 4; b4 ++)  //zhangnan 
		for(j=0;j<4;j++) 
			 for(i=0;i<4;i++) 
			 { 
				if(b8<4) 
					MB_interpred_Y[((b8>>1)<<3)+((b4>>1)<<2)+j][((b8 &1)<<3)+((b4 &1)<<2)+i] = pgcurrMB->pred_sample[b8][b4][i][j]; 
                else 
				{ 
	  				MB_interpred_UV[0][((b4>>1)<<2)+j][((b4 &1)<<2)+i] = pgcurrMB->pred_sample[4][b4][i][j]; 
					MB_interpred_UV[1][((b4>>1)<<2)+j][((b4 &1)<<2)+i] = pgcurrMB->pred_sample[5][b4][i][j]; 
				} 
			 } 
    
  //MB IQ printout 
  fprintf(p_trace,"@IQ output: \n"); 
  for(mb_y=0;mb_y<16;mb_y++) 
  { 
	  for(mb_x=0;mb_x<16;mb_x++) 
	  { 
		  fprintf(p_trace,"%4d",MB_IQ_Y[mb_y][mb_x]); 
		  if(mb_x%4==3) 
			  fprintf(p_trace,"  "); 
		  if(mb_x==15) 
			  fprintf(p_trace,"\n"); 
	  } 
	  if(mb_y%4==3) 
		  fprintf(p_trace,"\n"); 
  } 
	 
 
		for(mb_y = 0; mb_y < 8;mb_y++) 
		{ 
			for(mb_x=0;mb_x < 8;mb_x++) 
			{ 
				fprintf(p_trace,"%4d",MB_IQ_UV[0][mb_y][mb_x]); 
				if(mb_x%4==3) 
					fprintf(p_trace,"  "); 
			} 
			 
			for(mb_x=0;mb_x < 8;mb_x++) 
			{ 
				fprintf(p_trace,"%4d",MB_IQ_UV[1][mb_y][mb_x]); 
				if(mb_x%4==3) 
					fprintf(p_trace,"  "); 
				if(mb_x==7) 
					fprintf(p_trace,"\n"); 
			} 
 
			if(mb_y%4==3) 
				fprintf(p_trace,"\n"); 
		} 
 
 
 
 
  //MB IDCT printout 
  fprintf(p_trace,"@IDCT output: \n"); 
  for(mb_y=0;mb_y<16;mb_y++) 
  { 
	  for(mb_x=0;mb_x<16;mb_x++) 
	  { 
		  fprintf(p_trace,"%4d",MB_IDCT_Y[mb_y][mb_x]); 
		  if(mb_x%4==3) 
			  fprintf(p_trace,"  "); 
		  if(mb_x==15) 
			  fprintf(p_trace,"\n"); 
	  } 
	  if(mb_y%4==3) 
		  fprintf(p_trace,"\n"); 
  } 
	 
		for(mb_y = 0; mb_y < 8;mb_y++) 
		{ 
			for(mb_x=0;mb_x < 8;mb_x++) 
			{ 
				fprintf(p_trace,"%4d",MB_IDCT_UV[0][mb_y][mb_x]); 
				if(mb_x%4==3) 
					fprintf(p_trace,"  "); 
			} 
			 
			for(mb_x=0;mb_x < 8;mb_x++) 
			{ 
				fprintf(p_trace,"%4d",MB_IDCT_UV[1][mb_y][mb_x]); 
				if(mb_x%4==3) 
					fprintf(p_trace,"  "); 
				if(mb_x==7) 
					fprintf(p_trace,"\n"); 
			} 
 
			if(mb_y%4==3) 
				fprintf(p_trace,"\n"); 
		} 
 
 
 
    
  //IntraPred or InterPred output  
	if(IS_INTRA(pgcurrMB)) 
	{ 
		fprintf(p_trace,"@INTRA Pred output: \n"); 
		for(mb_y=0;mb_y<16;mb_y++) 
		{ 
			for(mb_x=0;mb_x<16;mb_x++) 
			{ 
				fprintf(p_trace,"%4d",MB_intrapred_Y[mb_y][mb_x]); 
				if(mb_x%4==3) 
					fprintf(p_trace,"  "); 
				if(mb_x==15) 
					fprintf(p_trace,"\n"); 
			} 
			if(mb_y%4==3) 
				fprintf(p_trace,"\n"); 
		} 
		 
 
			for(mb_y = 0; mb_y < 8;mb_y++) 
			{ 
				for(mb_x=0;mb_x < 8;mb_x++) 
				{ 
					fprintf(p_trace,"%4d",MB_intrapred_UV[0][mb_y][mb_x]); 
					if(mb_x%4==3) 
						fprintf(p_trace,"  "); 
				} 
				 
				for(mb_x=0;mb_x<8;mb_x++) 
				{ 
					fprintf(p_trace,"%4d",MB_intrapred_UV[1][mb_y][mb_x]); 
					if(mb_x%4==3) 
						fprintf(p_trace,"  "); 
					if(mb_x==7) 
						fprintf(p_trace,"\n"); 
				} 
				if(mb_y%4==3) 
					fprintf(p_trace,"\n"); 
			} 
	 
	} 
	else if(IS_INTER(pgcurrMB)) 
	{ 
	 
		fprintf(p_trace,"@Inter Pred output: \n"); 
		for(mb_y=0;mb_y<16;mb_y++) 
		{ 
			for(mb_x=0;mb_x<16;mb_x++) 
			{ 
				fprintf(p_trace,"%4d",MB_interpred_Y[mb_y][mb_x]); 
				if(mb_x%4==3) 
					fprintf(p_trace,"  "); 
				if(mb_x==15) 
					fprintf(p_trace,"\n"); 
			} 
			if(mb_y%4==3) 
				fprintf(p_trace,"\n"); 
		} 
		 
	 
			for(mb_y = 0; mb_y < 8;mb_y++) 
			{ 
				for(mb_x=0;mb_x < 8;mb_x++) 
				{ 
					fprintf(p_trace,"%4d",MB_interpred_UV[0][mb_y][mb_x]); 
					if(mb_x%4==3) 
						fprintf(p_trace,"  "); 
				} 
				 
				for(mb_x=0;mb_x<8;mb_x++) 
				{ 
					fprintf(p_trace,"%4d",MB_interpred_UV[1][mb_y][mb_x]); 
					if(mb_x%4==3) 
						fprintf(p_trace,"  "); 
					if(mb_x==7) 
						fprintf(p_trace,"\n"); 
				} 
				if(mb_y%4==3) 
					fprintf(p_trace,"\n"); 
			} 
		 
	 
	} 
 
  //Rec MB Luma Printout  
  fprintf(p_trace,"@Rec MB : \n"); 
  for(mb_y=0;mb_y<16;mb_y++) 
  { 
	  for(mb_x=0;mb_x<16;mb_x++) 
	  { 
		  fprintf(p_trace,"%4d",MB_Y[mb_y][mb_x]); 
		  if(mb_x%4==3) 
			  fprintf(p_trace,"  "); 
		  if(mb_x==15) 
			  fprintf(p_trace,"\n"); 
	  } 
	  if(mb_y%4==3) 
		  fprintf(p_trace,"\n"); 
  } 
 
   
  
 
  //Rec MB  chroma Printout  
		for(mb_y = 0; mb_y < 8;mb_y++) 
		{ 
			for(mb_x=0;mb_x < 8;mb_x++) 
			{ 
				fprintf(p_trace,"%4d",MB_UV[0][mb_y][mb_x]); 
				if(mb_x%4==3) 
					fprintf(p_trace,"  "); 
			} 
			 
			for(mb_x=0;mb_x<8;mb_x++) 
			{ 
				fprintf(p_trace,"%4d",MB_UV[1][mb_y][mb_x]); 
				if(mb_x%4==3) 
					fprintf(p_trace,"  "); 
				if(mb_x==7) 
					fprintf(p_trace,"\n"); 
			} 
			if(mb_y%4==3) 
				fprintf(p_trace,"\n"); 
		} 
	 
#endif 
 
  return 0; 
}