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

📄 qualitylevelassigner.cpp

📁 jsvm开发代码包括抽样,编码,抽取,解码等一系列功能,可以做工具或研究用
💻 CPP
📖 第 1 页 / 共 5 页
字号:

          //----- increment output picture number -----
          uiFrame++;
          if( uiLevel == MSYS_UINT_MAX )
            printf( "\rdetermine distortion (layer %d - FGS %d - base layer  ) --> frame %d completed", uiLayer, uiFGSLayer,                                    uiFrame );
          else
            printf( "\rdetermine distortion (layer %d - FGS %d - lev%2d - %s ) --> frame %d completed", uiLayer, uiFGSLayer, uiLevel, bIndependent?"ind":"dep", uiFrame );
        }
      }
    } // if( bToDecode )

    //----- free buffers -----
    RNOK( xRemovePicBuffer( cPicBufferReleaseList ) );
    RNOK( xRemovePicBuffer( cPicBufferUnusedList  ) );

    //----- delete bin data -----
    if( pcBinData )
    {
      RNOK( pcReadBitStream->releasePacket( pcBinData ) );
      pcBinData = 0;
    }
  }
  //----- remove original pic buffer -----
  PicBufferList cPicBufferListOrig; cPicBufferListOrig.push_back( pcPicBufferOrig );
  RNOK( xRemovePicBuffer( cPicBufferListOrig ) );
#if WIN32
  remove( tmp_file_name );
#endif


  //===== uninit =====
  RNOK( m_pcH264AVCPacketAnalyzer ->uninit  () );
  RNOK( m_pcH264AVCDecoder        ->uninit  ( true ) );
  RNOK( pcReadBitStream           ->uninit  () );
  RNOK( pcReadYuv                 ->uninit  () );
  RNOK( pcReadBitStream           ->destroy () );
  RNOK( pcReadYuv                 ->destroy () );
  if( pcWriteYuv )
  {
    RNOK( pcWriteYuv->destroy() );
  }

  //---- re-create decoder (there's something wrong) -----
  RNOK( m_pcH264AVCDecoder->destroy() );
  RNOK( CreaterH264AVCDecoder::create( m_pcH264AVCDecoder ) );

  printf("\n");

  return Err::m_nOK;
}


ErrVal
QualityLevelAssigner::xWriteDataFile( const std::string&  cFileName )
{
  printf( "write data to file \"%s\" ...", cFileName.c_str() );

  FILE* pFile = fopen( cFileName.c_str(), "wt" );
  if( !pFile )
  {
    fprintf( stderr, "\nERROR: Cannot open file \"%s\" for writing!\n\n", cFileName.c_str() );
    return Err::m_nERR;
  }

  for( UInt uiLayer = 0; uiLayer <  m_uiNumLayers;               uiLayer ++ )
  for( UInt uiFGS   = 0; uiFGS   <= m_auiNumFGSLayers[uiLayer];  uiFGS   ++ )
  for( UInt uiFrame = 0; uiFrame <  m_auiNumFrames   [uiLayer];  uiFrame ++ )
  {
    fprintf( pFile,
             "%d  %d  %5d  %6d  %lf\n",
              uiLayer, uiFGS, uiFrame,
              m_aaauiPacketSize [uiLayer][uiFGS][uiFrame],
              m_aaadDeltaDist   [uiLayer][uiFGS][uiFrame] );

  }

  fclose( pFile );

  printf("\n");
  return Err::m_nOK;
}


ErrVal
QualityLevelAssigner::xReadDataFile( const std::string&  cFileName )
{
  printf( "read data from file \"%s\" ...", cFileName.c_str() );

  FILE* pFile = fopen( cFileName.c_str(), "rt" );
  if( !pFile )
  {
    fprintf( stderr, "\nERROR: Cannot open file \"%s\" for reading!\n\n", cFileName.c_str() );
    return Err::m_nERR;
  }

  Bool    bEOS    = false;
  UInt    uiLayer, uiFGS, uiFrame, uiPacketSize, uiNumPackets;
  Double  dDeltaDist;
  for( uiNumPackets = 0; !bEOS; uiNumPackets++ )
  {
    Int iNumRead = fscanf( pFile,
                           " %d %d %d %d %lf",
                           &uiLayer, &uiFGS, &uiFrame, &uiPacketSize, &dDeltaDist );
    if( iNumRead == 5 )
    {
      ROF( uiLayer <  m_uiNumLayers );
      ROF( uiFGS   <= m_auiNumFGSLayers[uiLayer] );
      ROF( uiFrame <  m_auiNumFrames   [uiLayer] );
      m_aaauiPacketSize [uiLayer][uiFGS][uiFrame]  = uiPacketSize;
      m_aaadDeltaDist   [uiLayer][uiFGS][uiFrame]  = dDeltaDist;
    }
    else
    {
      bEOS = true;
      uiNumPackets--;
    }
  }

  //----- check number of elements -----
  UInt uiTargetPackets = 0;
  for( uiLayer = 0; uiLayer < m_uiNumLayers; uiLayer++ )
  {
    uiTargetPackets += ( 1 + m_auiNumFGSLayers[uiLayer] ) * m_auiNumFrames[uiLayer];
  }
  if( uiTargetPackets != uiNumPackets )
  {
    fprintf( stderr, "\nERROR: File \"%s\" contains incomplete data!\n\n", cFileName.c_str() );
    return Err::m_nERR;
  }

  fclose( pFile );

  printf("\n");
  return Err::m_nOK;
}



ErrVal
QualityLevelAssigner::xDetermineQualityIDs()
{
  printf( "determine quality levels ..." );

  //===== determine minimum and maximum quality level id's =====
  UInt  auiMinQualityLevel[MAX_LAYERS];
  UInt  auiMaxQualityLevel[MAX_LAYERS];
  {
    for( Int iLayer = (Int)m_uiNumLayers-1; iLayer >= 0; iLayer-- )
    {
      UInt  uiMinQLLayer          = ( iLayer == (Int)m_uiNumLayers-1 ? 0 : auiMaxQualityLevel[iLayer+1]+1 );
      UInt  uiNumQLInLayer        = ( 63 - uiMinQLLayer ) / ( iLayer + 1 );
      auiMinQualityLevel[iLayer]  = uiMinQLLayer;
      auiMaxQualityLevel[iLayer]  = uiMinQLLayer + uiNumQLInLayer - 1;
    }
  }

  //===== determine optimized quality levels per layer =====
  for( UInt uiLayer = 0; uiLayer < m_uiNumLayers; uiLayer++ )
  {
    //----- create quality estimation object -----
    QualityLevelEstimation  cQualityLevelEstimation;
    RNOK( cQualityLevelEstimation.init( m_uiNumLayers, m_auiNumFGSLayers, m_auiNumFrames ) );

    //----- initialize with packets -----
    {
      for( UInt uiFGSLayer = 1; uiFGSLayer <= m_auiNumFGSLayers[uiLayer]; uiFGSLayer++ )
      for( UInt uiFrame    = 0; uiFrame    <  m_auiNumFrames   [uiLayer]; uiFrame   ++ )
      {
        RNOK( cQualityLevelEstimation.addPacket( uiLayer, uiFGSLayer, uiFrame,
                                                 m_aaauiPacketSize [uiLayer][uiFGSLayer][uiFrame],
                                                 m_aaadDeltaDist   [uiLayer][uiFGSLayer][uiFrame] ) );
      }
    }

    //----- determine quality levels -----
    RNOK( cQualityLevelEstimation.optimizeQualityLevel( uiLayer, uiLayer, auiMinQualityLevel[uiLayer], auiMaxQualityLevel[uiLayer] ) );

    //----- assign quality levels -----
    {
      for( UInt uiFGSLayer = 0; uiFGSLayer <= m_auiNumFGSLayers[uiLayer]; uiFGSLayer++ )
      for( UInt uiFrame    = 0; uiFrame    <  m_auiNumFrames   [uiLayer]; uiFrame   ++ )
      {
        m_aaauiQualityID[uiLayer][uiFGSLayer][uiFrame] = ( uiFGSLayer ? cQualityLevelEstimation.getQualityLevel( uiLayer, uiFGSLayer, uiFrame ) : 63 );
      }
      if( m_bMGS )
      {
        m_aaauiQualityID[uiLayer][1][0] = 62; // first frame must be presents (when any other MGS refinement is present)
      }
    }
  }

  printf("\n");
  return Err::m_nOK;
}

//JVT-S043
ErrVal
QualityLevelAssigner::xDetermineMultiLayerQualityIDs()
{
  printf( "determine ML quality levels ..." );

  //===== determine minimum and maximum quality level id's =====
  UInt  uiMinQualityLevel = 0;
  UInt  uiMaxQualityLevel = 62;

  UInt uiLayer;

 //----- create quality estimation object -----
  QualityLevelEstimation  cQualityLevelEstimation;
  RNOK( cQualityLevelEstimation.init( m_uiNumLayers, m_auiNumFGSLayers, m_auiNumFrames ) );

  //===== determine optimized quality levels per layer =====
  for( uiLayer = 0; uiLayer < m_uiNumLayers; uiLayer++ )
  {
    //----- initialize with packets -----
    {
      for( UInt uiFGSLayer = 1; uiFGSLayer <= m_auiNumFGSLayers[uiLayer]; uiFGSLayer++ )
      for( UInt uiFrame    = 0; uiFrame    <  m_auiNumFrames   [uiLayer]; uiFrame   ++ )
      {
        RNOK( cQualityLevelEstimation.addPacket( uiLayer, uiFGSLayer, uiFrame,
                                                 m_aaauiPacketSize [uiLayer][uiFGSLayer][uiFrame],
                                                 m_aaadDeltaDist   [uiLayer][uiFGSLayer][uiFrame] ) );
      }
    }
  }


  //----- determine quality levels -----
  RNOK( cQualityLevelEstimation.optimizeQualityLevel( m_uiNumLayers-1, 0, uiMinQualityLevel, uiMaxQualityLevel ) );

  for( uiLayer = 0; uiLayer < m_uiNumLayers; uiLayer++ )
  {
    //----- assign quality levels -----
    {
      for( UInt uiFGSLayer = 0; uiFGSLayer <= m_auiNumFGSLayers[uiLayer]; uiFGSLayer++ )
      for( UInt uiFrame    = 0; uiFrame    <  m_auiNumFrames   [uiLayer]; uiFrame   ++ )
      {
        m_aaauiQualityID[uiLayer][uiFGSLayer][uiFrame] = ( uiFGSLayer ? cQualityLevelEstimation.getQualityLevel( uiLayer, uiFGSLayer, uiFrame ) : 63 );
      }
    }
  }

  printf("\n");
  return Err::m_nOK;
}

ErrVal
QualityLevelAssigner::xWriteQualityLayerStreamPID()
{
  printf( "write stream with quality layer (PID) \"%s\" ...", m_pcParameter->getOutputBitStreamName().c_str() );

  BinData*          pcBinData     = 0;
  SEI::SEIMessage*  pcScalableSEI = 0;
  PacketDescription cPacketDescription;
  static Bool    bAVCComaptible = false;  //bug-fix suffix
  UInt              auiFrameNum[MAX_LAYERS] = { MSYS_UINT_MAX, MSYS_UINT_MAX, MSYS_UINT_MAX, MSYS_UINT_MAX, MSYS_UINT_MAX, MSYS_UINT_MAX, MSYS_UINT_MAX, MSYS_UINT_MAX };
  UInt	uiLevel_prefix = 0;//prefix unit
  //===== init =====
  RNOK( m_pcH264AVCPacketAnalyzer->init() );
  ReadBitstreamFile*    pcReadBitStream   = 0;
  WriteBitstreamToFile* pcWriteBitStream  = 0;
  RNOK( ReadBitstreamFile   ::create( pcReadBitStream  ) );
  RNOK( WriteBitstreamToFile::create( pcWriteBitStream ) );
  RNOK( pcReadBitStream ->init( m_pcParameter->getInputBitStreamName  () ) );
  RNOK( pcWriteBitStream->init( m_pcParameter->getOutputBitStreamName () ) );


  //===== loop over packets =====
  while( true )
  {
    //----- read packet -----
    Bool bEOS = false;
    RNOK( pcReadBitStream->extractPacket( pcBinData, bEOS ) );
    if( bEOS )
    {
      //manu.mathew@samsung : memory leak fix
      RNOK( pcReadBitStream ->releasePacket ( pcBinData ) );
      pcBinData = NULL;
      //--
      break;
    }

    //----- get packet description -----
    RNOK( m_pcH264AVCPacketAnalyzer->process( pcBinData, cPacketDescription, pcScalableSEI ) );
//{suffix TL read
    if(cPacketDescription.NalUnitType== NAL_UNIT_CODED_SLICE     ||
      cPacketDescription.NalUnitType== NAL_UNIT_CODED_SLICE_IDR   )
    { 
			cPacketDescription.Level = uiLevel_prefix;//prefix unit
			h264::PacketDescription cPacketDescriptionTemp;
			h264::SEI::SEIMessage*  pcScalableSeiTemp = 0;
			Int iFilePos = 0;
			RNOK( pcReadBitStream->getPosition( iFilePos ) );
			BinData *pcNextBinData;
			Bool bEos;
			RNOK( pcReadBitStream->extractPacket( pcNextBinData, bEos ) );
			m_pcH264AVCPacketAnalyzer->process( pcNextBinData, cPacketDescriptionTemp, pcScalableSeiTemp  ); 
		if( (cPacketDescription.NalUnitType == NAL_UNIT_CODED_SLICE_SCALABLE || cPacketDescription.NalUnitType == NAL_UNIT_CODED_SLICE_IDR_SCALABLE) //prefix unit 
				&& cPacketDescriptionTemp.Layer == 0 && cPacketDescriptionTemp.FGSLayer == 0 ) //AVC suffix 
				cPacketDescription.Level = cPacketDescriptionTemp.Level;
			RNOK( pcReadBitStream->setPosition(iFilePos ) );
    }
//}suffix TL read
    delete pcScalableSEI; pcScalableSEI = 0;

    //----- set packet size -----
    while( pcBinData->data()[ pcBinData->size() - 1 ] == 0x00 )
    {
      RNOK( pcBinData->decreaseEndPos( 1 ) ); // remove trailing zeros
    }

    //----- analyse packets -----
    if( cPacketDescription.FGSLayer )
    {
      // JVT-T083: modify the Position of SimplePriorityId
      // clear previous value
      pcBinData->data()[1] &= 0xC0;
      // write new value of priority ID
      pcBinData->data()[1] |= m_aaauiQualityID[cPacketDescription.Layer][cPacketDescription.FGSLayer][auiFrameNum[cPacketDescription.Layer]];
    }
    else
    {
//bug-fix suffix{{
      if(cPacketDescription.NalUnitType == NAL_UNIT_CODED_SLICE_IDR || cPacketDescription.NalUnitType == NAL_UNIT_CODED_SLICE)
      {
        bAVCComaptible = true;
      }
      if((cPacketDescription.NalUnitType == 20 || cPacketDescription.NalUnitType == 21) && cPacketDescription.Layer == 0 && cPacketDescription.FGSLayer == 0 && bAVCComaptible)
      {
        RNOK( pcWriteBitStream->writePacket   ( &m_cBinDataStartCode ) );
        RNOK( pcWriteBitStream->writePacket   ( pcBinData ) );
        RNOK( pcReadBitStream ->releasePacket ( pcBinData ) );
        continue;
      }
//bug-fix suffix}} 
      if( ! cPacketDescription.ParameterSet && cPacketDescription.NalUnitType != NAL_UNIT_SEI &&
				! cPacketDescription.FGSLayer  && cPacketDescription.NalUnitType != NAL_UNIT_PREFIX)//prefix unit
      {
        auiFrameNum[cPacketDescription.Layer]++;
      }
    }
//prefix unit{{
	  if(cPacketDescription.NalUnitType == 14)
	  {

⌨️ 快捷键说明

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