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

📄 h264avcencodertest.cpp

📁 JVT-Z203_jsvm.rar
💻 CPP
📖 第 1 页 / 共 2 页
字号:
	      ruiBytesInFrame += 4 + cExtBinDataAccessor.size();
        cBinData.reset();       
      }
    }

    ruiBytesInFrame += rcList.front()->size() + 4;
    RNOK( m_pcWriteBitstreamToFile->writePacket( &m_cBinDataStartCode ) );
    RNOK( m_pcWriteBitstreamToFile->writePacket( rcList.front() ) );
    delete[] rcList.front()->data();
    delete   rcList.front();
    rcList.pop_front();
  }

  if( bCoded )
    uiTl0DepRepIdx++;

  return Err::m_nOK;
}


ErrVal
H264AVCEncoderTest::xRelease( ExtBinDataAccessorList& rcList )
{
  while( rcList.size() )
  {
    delete[] rcList.front()->data();
    delete   rcList.front();
    rcList.pop_front();
  }
  return Err::m_nOK;
}


ErrVal
H264AVCEncoderTest::go()
{
  UInt                    uiWrittenBytes          = 0;
  const UInt              uiMaxFrame              = m_pcEncoderCodingParameter->getTotalFrames();
  UInt                    uiNumLayers             = ( m_pcEncoderCodingParameter->getAVCmode() ? 1 : m_pcEncoderCodingParameter->getNumberOfLayers() );
  UInt                    uiFrame;
  UInt                    uiLayer;
  UInt                    auiMbX                  [MAX_LAYERS];
  UInt                    auiMbY                  [MAX_LAYERS];
  UInt                    auiPicSize              [MAX_LAYERS];
  PicBuffer*              apcOriginalPicBuffer    [MAX_LAYERS];
  PicBuffer*              apcReconstructPicBuffer [MAX_LAYERS];
  PicBufferList           acPicBufferOutputList   [MAX_LAYERS];
  PicBufferList           acPicBufferUnusedList   [MAX_LAYERS];
  ExtBinDataAccessorList  cOutExtBinDataAccessorList;
  Bool                    bMoreSets;

  
  //===== initialization =====
  RNOK( m_pcH264AVCEncoder->init( m_pcEncoderCodingParameter ) ); 

  // JVT-W043 {
  bRateControlEnable = (Bool)((m_pcH264AVCEncoder->getCodingParameter()->m_uiRateControlEnable) > 0 ? true : false );
  if ( bRateControlEnable )
  {
    Int   iGOPSize     = m_pcEncoderCodingParameter->getGOPSize();    
    Int   iFullGOPs    = uiMaxFrame / iGOPSize;
    Double dMaximumFrameRate = m_pcEncoderCodingParameter->getMaximumFrameRate();
    iGOPSize =  (Int)floor( 0.5F + iGOPSize / (dMaximumFrameRate / (Float) (m_pcH264AVCEncoder->getCodingParameter()->getLayerParameters(0).m_dOutputFrameRate)) );
    iGOPSize = max( iGOPSize, 1 );
    Int uiLocalMaxFrame =  (Int)floor( 0.5F + uiMaxFrame / (dMaximumFrameRate / (Float) (m_pcH264AVCEncoder->getCodingParameter()->getLayerParameters(0).m_dOutputFrameRate)) );
    if ( uiLocalMaxFrame % iGOPSize == 0 )
      iFullGOPs--;
    Int   iNb          = iFullGOPs * (iGOPSize - 1);

    pcJSVMParams  = new jsvm_parameters;
    pcGenericRC   = new rc_generic( pcJSVMParams );
    pcQuadraticRC = new rc_quadratic( pcGenericRC, pcJSVMParams );    

    // parameter initialization
    pcQuadraticRC->m_iDDquant       = (Int) m_pcH264AVCEncoder->getCodingParameter()->m_uiMaxQpChange;
    pcQuadraticRC->m_iPMaxQpChange  = (Int) m_pcH264AVCEncoder->getCodingParameter()->m_uiMaxQpChange;
    pcJSVMParams->bit_rate          = (Float) (m_pcH264AVCEncoder->getCodingParameter()->m_uiBitRate);
    pcJSVMParams->BasicUnit         = m_pcH264AVCEncoder->getCodingParameter()->m_uiBasicUnit;
    pcJSVMParams->basicunit         = m_pcH264AVCEncoder->getCodingParameter()->m_uiBasicUnit;
    pcJSVMParams->RCMaxQP           = m_pcH264AVCEncoder->getCodingParameter()->m_uiRCMaxQP;
    pcJSVMParams->RCMinQP           = m_pcH264AVCEncoder->getCodingParameter()->m_uiRCMinQP;    
    pcJSVMParams->SetInitialQP      = m_pcH264AVCEncoder->getCodingParameter()->m_uiInitialQp;
    pcJSVMParams->m_uiIntraPeriod   = m_pcEncoderCodingParameter->getIntraPeriod();
    pcJSVMParams->FrameRate         = (Float) (m_pcH264AVCEncoder->getCodingParameter()->getLayerParameters(0).m_dOutputFrameRate);
    pcJSVMParams->height            = m_pcH264AVCEncoder->getCodingParameter()->getLayerParameters(0).m_uiFrameHeight;
    pcJSVMParams->width             = m_pcH264AVCEncoder->getCodingParameter()->getLayerParameters(0).m_uiFrameWidth;
    pcJSVMParams->no_frames         = uiMaxFrame;
    pcJSVMParams->successive_Bframe = iGOPSize - 1;
    pcJSVMParams->m_uiLayerId       = 0;

    if ( m_pcH264AVCEncoder->getCodingParameter()->m_uiAdaptInitialQP )
      pcGenericRC->adaptInitialQP();
  
    switch( iGOPSize )
    {
    case 1:
      pcJSVMParams->HierarchicalLevels = 0;
      break;
    case 2:
      pcJSVMParams->HierarchicalLevels = 1;
      break;
    case 4:
      pcJSVMParams->HierarchicalLevels = 2;
      break;
    case 8:
      pcJSVMParams->HierarchicalLevels = 3;
      break;
    case 16:
      pcJSVMParams->HierarchicalLevels = 4;
      break;
    case 32:
    default:
      fprintf(stderr, "\n RC not stable for large number of hierarchical levels...exiting...\n" );
      assert(0); // some compilers do not compile assert in release/Ox mode
      exit(1);
      break;
    }
    
    // rate control initialization functions
    pcQuadraticRC->init();
    pcQuadraticRC->rc_init_seq();
    pcQuadraticRC->rc_init_GOP(uiMaxFrame - iNb - 1, iNb);
    pcGenericRC->generic_alloc();    
  }
  // JVT-W043 }

  //===== write parameter sets =====
  for( bMoreSets = true; bMoreSets;  )
  {
    UChar   aucParameterSetBuffer[1000];
    BinData cBinData;
    cBinData.reset();
    cBinData.set( aucParameterSetBuffer, 1000 );

    ExtBinDataAccessor cExtBinDataAccessor;
    cBinData.setMemAccessor( cExtBinDataAccessor );

    h264::SequenceParameterSet* pcAVCSPS = NULL;
    RNOK( m_pcH264AVCEncoder->writeParameterSets( &cExtBinDataAccessor, pcAVCSPS, bMoreSets ) );
		if( m_pcH264AVCEncoder->getScalableSeiMessage() )
		{		
      RNOK( m_pcWriteBitstreamToFile->writePacket       ( &m_cBinDataStartCode ) );
      RNOK( m_pcWriteBitstreamToFile->writePacket       ( &cExtBinDataAccessor ) );
      
      uiWrittenBytes += 4 + cExtBinDataAccessor.size();
		}
    cBinData.reset();
    // JVT-V068 {
/* luodan */
    if (pcAVCSPS)
    {
      cBinData.set( aucParameterSetBuffer, 1000 );

      ExtBinDataAccessor cExtBinDataAccessorl;
      cBinData.setMemAccessor( cExtBinDataAccessorl );
      
      RNOK( m_pcH264AVCEncoder->writeAVCCompatibleHRDSEI( &cExtBinDataAccessorl, pcAVCSPS ) );
      
      RNOK( m_pcWriteBitstreamToFile->writePacket       ( &m_cBinDataStartCode ) );
      RNOK( m_pcWriteBitstreamToFile->writePacket       ( &cExtBinDataAccessorl ) );

      uiWrittenBytes += 4 + cExtBinDataAccessorl.size();
      cBinData.reset();
    }
/* luodan */
    // JVT-V068 }
  }
  // JVT-T073 {
  if( m_pcEncoderCodingParameter->getNestingSEIEnable() && m_pcEncoderCodingParameter->getSceneInfoEnable() )
  {
      UChar aucParameterSetBuffer[1000];
      BinData cBinData;
      cBinData.reset();
      cBinData.set( aucParameterSetBuffer, 1000 );
      ExtBinDataAccessor cExtBinDataAccessor;
      cBinData.setMemAccessor( cExtBinDataAccessor );
	  RNOK( m_pcH264AVCEncoder ->writeNestingSEIMessage( &cExtBinDataAccessor ) );
	  RNOK( m_pcWriteBitstreamToFile->writePacket( &m_cBinDataStartCode ) );
	  RNOK( m_pcWriteBitstreamToFile->writePacket( &cExtBinDataAccessor ) );
	  uiWrittenBytes += 4 + cExtBinDataAccessor.size();
	  cBinData.reset();
  }
  // JVT-T073 }

  //===== determine parameters for required frame buffers =====
  for( uiLayer = 0; uiLayer < uiNumLayers; uiLayer++ )
  {
    h264::LayerParameters& rcLayer = m_pcEncoderCodingParameter->getLayerParameters( uiLayer );
    auiMbX        [uiLayer]        = ( rcLayer.getFrameWidth () + 15 ) >> 4;
    auiMbY        [uiLayer]        = ( rcLayer.getFrameHeight() + 15 ) >> 4;
    m_aauiCropping[uiLayer][0]     = 0;
    m_aauiCropping[uiLayer][1]     = ( 16 - ( rcLayer.getFrameWidth () % 16 ) ) % 16;
    m_aauiCropping[uiLayer][2]     = 0;
    m_aauiCropping[uiLayer][3]     = ( 16 - ( rcLayer.getFrameHeight() % 16 ) ) % 16;
    UInt  uiSize            = ((auiMbY[uiLayer]<<4)+2*YUV_Y_MARGIN)*((auiMbX[uiLayer]<<4)+2*YUV_X_MARGIN);
    auiPicSize    [uiLayer] = ((auiMbX[uiLayer]<<4)+2*YUV_X_MARGIN)*((auiMbY[uiLayer]<<4)+2*YUV_Y_MARGIN)*3/2;
    m_auiLumOffset[uiLayer] = ((auiMbX[uiLayer]<<4)+2*YUV_X_MARGIN)* YUV_Y_MARGIN   + YUV_X_MARGIN;  
    m_auiCbOffset [uiLayer] = ((auiMbX[uiLayer]<<3)+  YUV_X_MARGIN)* YUV_Y_MARGIN/2 + YUV_X_MARGIN/2 + uiSize; 
    m_auiCrOffset [uiLayer] = ((auiMbX[uiLayer]<<3)+  YUV_X_MARGIN)* YUV_Y_MARGIN/2 + YUV_X_MARGIN/2 + 5*uiSize/4;
    m_auiHeight   [uiLayer] =   auiMbY[uiLayer]<<4;
    m_auiWidth    [uiLayer] =   auiMbX[uiLayer]<<4;
    m_auiStride   [uiLayer] =  (auiMbX[uiLayer]<<4)+ 2*YUV_X_MARGIN;
  }

  //===== loop over frames =====
  for( uiFrame = 0; uiFrame < uiMaxFrame; uiFrame++ )
  {
    //===== get picture buffers and read original pictures =====
    for( uiLayer = 0; uiLayer < uiNumLayers; uiLayer++ )
    {
      UInt  uiSkip = ( 1 << m_pcEncoderCodingParameter->getLayerParameters( uiLayer ).getTemporalResolution() );

      if( uiFrame % uiSkip == 0 )
      {
        RNOK( xGetNewPicBuffer( apcReconstructPicBuffer [uiLayer], uiLayer, auiPicSize[uiLayer] ) );
        RNOK( xGetNewPicBuffer( apcOriginalPicBuffer    [uiLayer], uiLayer, auiPicSize[uiLayer] ) );

        RNOK( m_apcReadYuv[uiLayer]->readFrame( *apcOriginalPicBuffer[uiLayer] + m_auiLumOffset[uiLayer],
                                                *apcOriginalPicBuffer[uiLayer] + m_auiCbOffset [uiLayer],
                                                *apcOriginalPicBuffer[uiLayer] + m_auiCrOffset [uiLayer],
                                                m_auiHeight [uiLayer],
                                                m_auiWidth  [uiLayer],
                                                m_auiStride [uiLayer] ) );
      }
      else
      {
        apcReconstructPicBuffer [uiLayer] = 0;
        apcOriginalPicBuffer    [uiLayer] = 0;
      }
    }

    //===== call encoder =====
    RNOK( m_pcH264AVCEncoder->process( cOutExtBinDataAccessorList,
                                       apcOriginalPicBuffer,
                                       apcReconstructPicBuffer,
                                       acPicBufferOutputList,
                                       acPicBufferUnusedList ) );

    //===== write and release NAL unit buffers =====
    UInt  uiBytesUsed = 0;
    RNOK( xWrite  ( cOutExtBinDataAccessorList, uiBytesUsed ) );
    uiWrittenBytes   += uiBytesUsed;
    
    //===== write and release reconstructed pictures =====
    for( uiLayer = 0; uiLayer < uiNumLayers; uiLayer++ )
    {
      RNOK( xWrite  ( acPicBufferOutputList[uiLayer], uiLayer ) );
      RNOK( xRelease( acPicBufferUnusedList[uiLayer], uiLayer ) );
    }
  }

  
  //===== finish encoding =====
  UInt  uiNumCodedFrames = 0;
  Double  dHighestLayerOutputRate = 0.0;
  RNOK( m_pcH264AVCEncoder->finish( cOutExtBinDataAccessorList,
                                    acPicBufferOutputList,
                                    acPicBufferUnusedList,
                                    uiNumCodedFrames,
                                    dHighestLayerOutputRate ) );

  //===== write and release NAL unit buffers =====
  RNOK( xWrite  ( cOutExtBinDataAccessorList, uiWrittenBytes ) );

  //===== write and release reconstructed pictures =====
  for( uiLayer = 0; uiLayer < uiNumLayers; uiLayer++ )
  {
    RNOK( xWrite  ( acPicBufferOutputList[uiLayer], uiLayer ) );
    RNOK( xRelease( acPicBufferUnusedList[uiLayer], uiLayer ) );
  }


  //===== set parameters and output summary =====
  m_cEncoderIoParameter.nFrames = uiFrame;
  m_cEncoderIoParameter.nResult = 0;

  if( ! m_pcEncoderCodingParameter->getAVCmode() )
	{
    UChar   aucParameterSetBuffer[10000];
    BinData cBinData;
    cBinData.reset();
    cBinData.set( aucParameterSetBuffer, 10000 );

		ExtBinDataAccessor cExtBinDataAccessor;
		cBinData.setMemAccessor( cExtBinDataAccessor );
		m_pcH264AVCEncoder->SetVeryFirstCall();

  	h264::SequenceParameterSet* pcAVCSPS = NULL;
  	RNOK( m_pcH264AVCEncoder->writeParameterSets( &cExtBinDataAccessor, pcAVCSPS, bMoreSets ) );
    RNOK( m_pcWriteBitstreamToFile->writePacket       ( &m_cBinDataStartCode ) );
		RNOK( m_pcWriteBitstreamToFile->writePacket       ( &cExtBinDataAccessor ) );
		uiWrittenBytes += 4 + cExtBinDataAccessor.size();
		cBinData.reset();
	}

  if( m_pcWriteBitstreamToFile )
  {
    RNOK( m_pcWriteBitstreamToFile->uninit() );  
    RNOK( m_pcWriteBitstreamToFile->destroy() );  
  }

  if( ! m_pcEncoderCodingParameter->getAVCmode() )
  {
    RNOK	( ScalableDealing() );
  }

  // JVT-W043 {
  if ( bRateControlEnable )
  {
    delete pcJSVMParams;
    delete pcGenericRC;
    delete pcQuadraticRC;
  }
  // JVT-W043 }

  return Err::m_nOK;
}

ErrVal
H264AVCEncoderTest::ScalableDealing()
{
  FILE *ftemp = fopen( m_cWriteToBitFileTempName.c_str(), "rb" );
  FILE *f     = fopen( m_cWriteToBitFileName.c_str    (), "wb" );

	UChar pvBuffer[4];

	fseek( ftemp, SEEK_SET, SEEK_END );
	long lFileLength = ftell( ftemp );

	long lpos = 0;
	long loffset = -5;	//start offset from end of file
	Bool bMoreSets = true;
	do
  {
		fseek( ftemp, loffset, SEEK_END);
		fread( pvBuffer, 1, 4, ftemp );
		if( pvBuffer[0] == 0 && pvBuffer[1] == 0 && pvBuffer[2] == 0 && pvBuffer[3] == 1)
		{
			bMoreSets = false;
			lpos = abs( loffset );
		}
		else
		{
			loffset --;
		}
	} while( bMoreSets );

	fseek( ftemp, loffset, SEEK_END );

	UChar *pvChar = new UChar[lFileLength];
	fread( pvChar, 1, lpos, ftemp );
	fseek( ftemp, 0, SEEK_SET );
	fread( pvChar+lpos, 1, lFileLength-lpos, ftemp);
	fclose(ftemp);
	fflush(ftemp);
	fwrite( pvChar, 1, lFileLength, f);	
	delete pvChar;
	fclose(f);
	fflush(f);
	RNOK( remove( m_cWriteToBitFileTempName.c_str() ) ); 

	return Err::m_nOK;
}

⌨️ 快捷键说明

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