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

📄 scan.c

📁 从FFMPEG转换而来的H264解码程序,VC下编译..
💻 C
📖 第 1 页 / 共 5 页
字号:
  ogg_uint32_t   LocalGrpLowSadThresh = ppi->ModifiedGrpLowSadThresh;
  ogg_uint32_t   LocalGrpHighSadThresh = ppi->ModifiedGrpHighSadThresh;
  signed char   *LocalDispFragPtr;
  unsigned char *LocalYuvPtr1;
  unsigned char *LocalYuvPtr2;

  int           InterestingBlocksInRow = 0;

  /* For each row of pixels in the row of blocks */
  for ( j = 0; j < VFRAGPIXELS; j++ ){
    /* Set local block map pointer. */
    LocalDispFragPtr = DispFragPtr;

    /* Set the local pixel data pointers for this row.*/
    LocalYuvPtr1 = YuvPtr1;
    LocalYuvPtr2 = YuvPtr2;

    /* Scan along the row of pixels If the block to which a group of
       pixels belongs is already marked for update then do nothing. */
    for ( i = 0; i < ppi->PlaneHFragments; i ++ ){
      if ( *LocalDispFragPtr <= BLOCK_NOT_CODED ){
	/* Calculate the SAD score for the block row */
        GrpSad = dsp_static_row_sad8(LocalYuvPtr1,LocalYuvPtr2);

	/* Now test the group SAD score */
	if ( GrpSad > LocalGrpLowSadThresh ){
	  /* If SAD very high we must update else we have candidate block */
	  if ( GrpSad > LocalGrpHighSadThresh ){
	    /* Force update */
	    *LocalDispFragPtr = BLOCK_CODED;
	  }else{
	    /* Possible Update required */
	    *LocalDispFragPtr = CANDIDATE_BLOCK;
	  }
	  InterestingBlocksInRow = 1;
	}
      }
      LocalDispFragPtr++;

      LocalYuvPtr1 += 8;
      LocalYuvPtr2 += 8;
    }

    /* Increment the base data pointers to the start of the next line. */
    YuvPtr1 += ppi->PlaneStride;
    YuvPtr2 += ppi->PlaneStride;
  }

  return InterestingBlocksInRow;

}

static int ColSadScan( PP_INSTANCE *ppi,
		       unsigned char * YuvPtr1,
		       unsigned char * YuvPtr2,
		       signed char *  DispFragPtr ){
  ogg_int32_t     i;
  ogg_uint32_t    MaxSad;
  ogg_uint32_t    LocalGrpLowSadThresh = ppi->ModifiedGrpLowSadThresh;
  ogg_uint32_t    LocalGrpHighSadThresh = ppi->ModifiedGrpHighSadThresh;
  signed char   * LocalDispFragPtr;

  unsigned char * LocalYuvPtr1;
  unsigned char * LocalYuvPtr2;

  int     InterestingBlocksInRow = 0;

  /* Set the local pixel data pointers for this row. */
  LocalYuvPtr1 = YuvPtr1;
  LocalYuvPtr2 = YuvPtr2;

  /* Set local block map pointer. */
  LocalDispFragPtr = DispFragPtr;

  /* Scan along the row of blocks */
  for ( i = 0; i < ppi->PlaneHFragments; i ++ ){
    /* Skip if block already marked to be coded. */
    if ( *LocalDispFragPtr <= BLOCK_NOT_CODED ){
      /* Calculate the SAD score for the block column */
      MaxSad = dsp_static_col_sad8x8(LocalYuvPtr1, LocalYuvPtr2, ppi->PlaneStride );

      /* Now test the group SAD score */
      if ( MaxSad > LocalGrpLowSadThresh ){
	/* If SAD very high we must update else we have candidate block */
	if ( MaxSad > LocalGrpHighSadThresh ){
	  /* Force update */
	  *LocalDispFragPtr = BLOCK_CODED;
	}else{
	  /* Possible Update required */
	  *LocalDispFragPtr = CANDIDATE_BLOCK;
	}
	InterestingBlocksInRow = 1;
      }
    }

    /* Increment the block map pointer. */
    LocalDispFragPtr++;

    /* Step data pointers on ready for next block */
    LocalYuvPtr1 += HFRAGPIXELS;
    LocalYuvPtr2 += HFRAGPIXELS;
  }

  return InterestingBlocksInRow;
}

static void SadPass2( PP_INSTANCE *ppi,
		      ogg_int32_t RowNumber,
		      signed char *  DispFragPtr ){
  ogg_int32_t  i;

  /* First row */
  if ( RowNumber == 0 ) {
    /* First block in row. */
    if ( DispFragPtr[0] == CANDIDATE_BLOCK ){
      if ( (DispFragPtr[1] == BLOCK_CODED) ||
	   (DispFragPtr[ppi->PlaneHFragments] == BLOCK_CODED) ||
	   (DispFragPtr[ppi->PlaneHFragments+1] == BLOCK_CODED) ){
	ppi->TmpCodedMap[0] =  BLOCK_CODED_LOW;
      }else{
	ppi->TmpCodedMap[0] = DispFragPtr[0];
      }
    }else{
      ppi->TmpCodedMap[0] = DispFragPtr[0];
    }

    /* All but first and last in row */
    for ( i = 1; (i < ppi->PlaneHFragments-1); i++ ){
      if ( DispFragPtr[i] == CANDIDATE_BLOCK ){
	if ( (DispFragPtr[i-1] == BLOCK_CODED) ||
	     (DispFragPtr[i+1] == BLOCK_CODED) ||
	     (DispFragPtr[i+ppi->PlaneHFragments] == BLOCK_CODED) ||
	     (DispFragPtr[i+ppi->PlaneHFragments-1] == BLOCK_CODED) ||
	     (DispFragPtr[i+ppi->PlaneHFragments+1] == BLOCK_CODED) ){
	  ppi->TmpCodedMap[i] =  BLOCK_CODED_LOW;
	}else{
	  ppi->TmpCodedMap[i] = DispFragPtr[i];
	}
      }else{
	ppi->TmpCodedMap[i] = DispFragPtr[i];
      }
    }

    /* Last block in row. */
    i = ppi->PlaneHFragments-1;
    if ( DispFragPtr[i] == CANDIDATE_BLOCK ){
      if ( (DispFragPtr[i-1] == BLOCK_CODED) ||
	   (DispFragPtr[i+ppi->PlaneHFragments] == BLOCK_CODED) ||
	   (DispFragPtr[i+ppi->PlaneHFragments-1] == BLOCK_CODED) ){
	ppi->TmpCodedMap[i] =  BLOCK_CODED_LOW;
      }else{
	ppi->TmpCodedMap[i] = DispFragPtr[i];
      }
    }else{
      ppi->TmpCodedMap[i] = DispFragPtr[i];
    }
  }else if ( RowNumber < (ppi->PlaneVFragments - 1) ){
    /* General case */
    /* First block in row. */
    if ( DispFragPtr[0] == CANDIDATE_BLOCK ){
      if ( (DispFragPtr[1] == BLOCK_CODED) ||
	   (DispFragPtr[(-ppi->PlaneHFragments)] == BLOCK_CODED) ||
	   (DispFragPtr[(-ppi->PlaneHFragments)+1] == BLOCK_CODED) ||
	   (DispFragPtr[ppi->PlaneHFragments] == BLOCK_CODED) ||
	   (DispFragPtr[ppi->PlaneHFragments+1] == BLOCK_CODED) ){
	ppi->TmpCodedMap[0] =  BLOCK_CODED_LOW;
      }else{
	ppi->TmpCodedMap[0] = DispFragPtr[0];
      }
    }else{
      ppi->TmpCodedMap[0] = DispFragPtr[0];
    }

    /* All but first and last in row */
    for ( i = 1; (i < ppi->PlaneHFragments-1); i++ ){
      if ( DispFragPtr[i] == CANDIDATE_BLOCK ){
	if ( (DispFragPtr[i-1] == BLOCK_CODED) ||
	     (DispFragPtr[i+1] == BLOCK_CODED) ||
	     (DispFragPtr[i-ppi->PlaneHFragments] == BLOCK_CODED) ||
	     (DispFragPtr[i-ppi->PlaneHFragments-1] == BLOCK_CODED) ||
	     (DispFragPtr[i-ppi->PlaneHFragments+1] == BLOCK_CODED) ||
	     (DispFragPtr[i+ppi->PlaneHFragments] == BLOCK_CODED) ||
	     (DispFragPtr[i+ppi->PlaneHFragments-1] == BLOCK_CODED) ||
	     (DispFragPtr[i+ppi->PlaneHFragments+1] == BLOCK_CODED) ){
	  ppi->TmpCodedMap[i] =  BLOCK_CODED_LOW;
	}else{
	  ppi->TmpCodedMap[i] = DispFragPtr[i];
	}
      }else{
	ppi->TmpCodedMap[i] = DispFragPtr[i];
      }
    }

    /* Last block in row. */
    i = ppi->PlaneHFragments-1;
    if ( DispFragPtr[i] == CANDIDATE_BLOCK ){
      if ( (DispFragPtr[i-1] == BLOCK_CODED) ||
	   (DispFragPtr[i-ppi->PlaneHFragments] == BLOCK_CODED) ||
	   (DispFragPtr[i-ppi->PlaneHFragments-1] == BLOCK_CODED) ||
	   (DispFragPtr[i+ppi->PlaneHFragments] == BLOCK_CODED) ||
	   (DispFragPtr[i+ppi->PlaneHFragments-1] == BLOCK_CODED) ){
	ppi->TmpCodedMap[i] =  BLOCK_CODED_LOW;
      }else{
	ppi->TmpCodedMap[i] = DispFragPtr[i];
      }
    }else{
      ppi->TmpCodedMap[i] = DispFragPtr[i];
    }
  }else{
    /* Last row */
    /* First block in row. */
    if ( DispFragPtr[0] == CANDIDATE_BLOCK ){
      if ( (DispFragPtr[1] == BLOCK_CODED) ||
	   (DispFragPtr[(-ppi->PlaneHFragments)] == BLOCK_CODED) ||
	   (DispFragPtr[(-ppi->PlaneHFragments)+1] == BLOCK_CODED)){
	ppi->TmpCodedMap[0] =  BLOCK_CODED_LOW;
      }else{
	ppi->TmpCodedMap[0] = DispFragPtr[0];
      }
    }else{
      ppi->TmpCodedMap[0] = DispFragPtr[0];
    }

    /* All but first and last in row */
    for ( i = 1; (i < ppi->PlaneHFragments-1); i++ ){
      if ( DispFragPtr[i] == CANDIDATE_BLOCK ){
	if ( (DispFragPtr[i-1] == BLOCK_CODED) ||
	     (DispFragPtr[i+1] == BLOCK_CODED) ||
	     (DispFragPtr[i-ppi->PlaneHFragments] == BLOCK_CODED) ||
	     (DispFragPtr[i-ppi->PlaneHFragments-1] == BLOCK_CODED) ||
	     (DispFragPtr[i-ppi->PlaneHFragments+1] == BLOCK_CODED) ){
	  ppi->TmpCodedMap[i] =  BLOCK_CODED_LOW;
	}else{
	  ppi->TmpCodedMap[i] = DispFragPtr[i];
	}
      }else{
	ppi->TmpCodedMap[i] = DispFragPtr[i];
      }
    }

    /* Last block in row. */
    i = ppi->PlaneHFragments-1;
    if ( DispFragPtr[i] == CANDIDATE_BLOCK ){
      if ( (DispFragPtr[i-1] == BLOCK_CODED) ||
	   (DispFragPtr[i-ppi->PlaneHFragments] == BLOCK_CODED) ||
	   (DispFragPtr[i-ppi->PlaneHFragments-1] == BLOCK_CODED) ){
	ppi->TmpCodedMap[i] =  BLOCK_CODED_LOW;
      }else{
	ppi->TmpCodedMap[i] = DispFragPtr[i];
      }
    }else{
      ppi->TmpCodedMap[i] = DispFragPtr[i];
    }
  }

  /* Now copy back the modified Fragment data */
  memcpy( &DispFragPtr[0], &ppi->TmpCodedMap[0], (ppi->PlaneHFragments) );
}

static unsigned char ApplyPakLowPass( PP_INSTANCE *ppi,
				      unsigned char * SrcPtr ){
  unsigned char * SrcPtr1 = SrcPtr - 1;
  unsigned char * SrcPtr0 = SrcPtr1 - ppi->PlaneStride; /* Note the
                                                           use of
                                                           stride not
                                                           width. */
  unsigned char * SrcPtr2 = SrcPtr1 + ppi->PlaneStride;

  return  (unsigned char)( ( (ogg_uint32_t)SrcPtr0[0] +
	      (ogg_uint32_t)SrcPtr0[1] +
	      (ogg_uint32_t)SrcPtr0[2] +
	      (ogg_uint32_t)SrcPtr1[0] +
	      (ogg_uint32_t)SrcPtr1[2] +
	      (ogg_uint32_t)SrcPtr2[0] +
	      (ogg_uint32_t)SrcPtr2[1] +
	      (ogg_uint32_t)SrcPtr2[2]   ) >> 3 );

}

static void RowDiffScan( PP_INSTANCE *ppi,
			 unsigned char * YuvPtr1,
			 unsigned char * YuvPtr2,
			 ogg_int16_t   * YUVDiffsPtr,
			 unsigned char * bits_map_ptr,
			 signed char   * SgcPtr,
			 signed char   * DispFragPtr,
			 unsigned char * FDiffPixels,
			 ogg_int32_t   * RowDiffsPtr,
			 unsigned char * ChLocalsPtr, int EdgeRow ){

  ogg_int32_t    i,j;
  ogg_int32_t    FragChangedPixels;

  ogg_int16_t Diff;     /* Temp local workspace. */

  /* Cannot use kernel if at edge or if PAK disabled */
  if ( (!ppi->PAKEnabled) || EdgeRow ){
    for ( i = 0; i < ppi->PlaneWidth; i += HFRAGPIXELS ){
      /* Reset count of pixels changed for the current fragment. */
      FragChangedPixels = 0;

      /* Test for break out conditions to save time. */
      if (*DispFragPtr == CANDIDATE_BLOCK){

	/* Clear down entries in changed locals array */
        SET8_0(ChLocalsPtr);

	for ( j = 0; j < HFRAGPIXELS; j++ ){
	  /* Take a local copy of the measured difference. */
	  Diff = (int)YuvPtr1[j] - (int)YuvPtr2[j];

	  /* Store the actual difference value */
	  YUVDiffsPtr[j] = Diff;

	  /* Test against the Level thresholds and record the results */
	  SgcPtr[0] += ppi->SgcThreshTable[Diff+255];

	  /* Test against the SRF thresholds */
	  bits_map_ptr[j] = ppi->SrfThreshTable[Diff+255];
	  FragChangedPixels += ppi->SrfThreshTable[Diff+255];
	}
      }else{
	/* If we are breaking out here mark all pixels as changed. */
	if ( *DispFragPtr > BLOCK_NOT_CODED ){
          SET8_1(bits_map_ptr);
          SET8_8(ChLocalsPtr);
	}else{
          SET8_0(ChLocalsPtr);
	}
      }

      *RowDiffsPtr += FragChangedPixels;
      *FDiffPixels += (unsigned char)FragChangedPixels;

      YuvPtr1 += HFRAGPIXELS;
      YuvPtr2 += HFRAGPIXELS;
      bits_map_ptr += HFRAGPIXELS;
      ChLocalsPtr += HFRAGPIXELS;
      YUVDiffsPtr += HFRAGPIXELS;
      SgcPtr ++;
      FDiffPixels ++;

      /* If we have a lot of changed pixels for this fragment on this
	 row then the fragment is almost sure to be picked (e.g. through
	 the line search) so we can mark it as selected and then ignore
	 it. */
      if (FragChangedPixels >= 7){
	*DispFragPtr = BLOCK_CODED_LOW;
      }
      DispFragPtr++;
    }
  }else{

    /*************************************************************/
    /* First fragment of row !! */

    i = 0;
    /* Reset count of pixels changed for the current fragment. */
    FragChangedPixels = 0;

    /* Test for break out conditions to save time. */
    if (*DispFragPtr == CANDIDATE_BLOCK){
      /* Clear down entries in changed locals array */
      SET8_0(ChLocalsPtr);

      for ( j = 0; j < HFRAGPIXELS; j++ ){
	/* Take a local copy of the measured difference. */
	Diff = (int)YuvPtr1[j] - (int)YuvPtr2[j];

	/* Store the actual difference value */
	YUVDiffsPtr[j] = Diff;

	/* Test against the Level thresholds and record the results */
	SgcPtr[0] += ppi->SgcThreshTable[Diff+255];

	if (j>0 && ppi->SrfPakThreshTable[Diff+255] )
	  Diff = (int)ApplyPakLowPass( ppi, &YuvPtr1[j] ) -
	    (int)ApplyPakLowPass( ppi, &YuvPtr2[j] );

	/* Test against the SRF thresholds */
	bits_map_ptr[j] = ppi->SrfThreshTable[Diff+255];
	FragChangedPixels += ppi->SrfThreshTable[Diff+255];
      }
    }else{
      /* If we are breaking out here mark all pixels as changed. */
      if ( *DispFragPtr > BLOCK_NOT_CODED ){
        SET8_1(bits_map_ptr);
        SET8_8(ChLocalsPtr);
      }else{
        SET8_0(ChLocalsPtr);
      }
    }

    *RowDiffsPtr += FragChangedPixels;
    *FDiffPixels += (unsigned char)FragChangedPixels;

    YuvPtr1 += HFRAGPIXELS;
    YuvPtr2 += HFRAGPIXELS;
    bits_map_ptr += HFRAGPIXELS;
    ChLocalsPtr += HFRAGPIXELS;
    YUVDiffsPtr += HFRAGPIXELS;
    SgcPtr ++;

⌨️ 快捷键说明

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