source: SHVCSoftware/branches/SHM-4.0-dev/source/App/TAppEncoder/TAppEncLayerCfg.cpp @ 461

Last change on this file since 461 was 448, checked in by seregin, 12 years ago

remove SCALED_REF_LAYER_OFFSETS macro

  • Property svn:eol-style set to native
File size: 14.7 KB
Line 
1/** \file     TAppEncLayerCfg.cpp
2\brief    Handle encoder configuration parameters
3*/
4
5#include <stdlib.h>
6#include <cassert>
7#include <cstring>
8#include <string>
9#include "TLibCommon/TComRom.h"
10#include "TAppEncCfg.h"
11#include "TAppEncLayerCfg.h"
12#include "TAppCommon/program_options_lite.h"
13
14#ifdef WIN32
15#define strdup _strdup
16#endif
17
18using namespace std;
19namespace po = df::program_options_lite;
20
21//! \ingroup TAppEncoder
22//! \{
23
24
25// ====================================================================================================================
26// Constructor / destructor / initialization / destroy
27// ====================================================================================================================
28#if SVC_EXTENSION
29TAppEncLayerCfg::TAppEncLayerCfg()
30  :m_cInputFile(string("")),
31  m_cReconFile(string("")),
32  m_conformanceMode( 0 ),
33  m_aidQP(NULL)
34#if REPN_FORMAT_IN_VPS
35, m_repFormatIdx (-1)
36#endif
37{
38  m_confLeft = m_confRight = m_confTop = m_confBottom = 0;
39  m_aiPad[1] = m_aiPad[0] = 0;
40  m_numScaledRefLayerOffsets = 0;
41  ::memset(m_scaledRefLayerLeftOffset,   0, sizeof(m_scaledRefLayerLeftOffset));
42  ::memset(m_scaledRefLayerTopOffset,    0, sizeof(m_scaledRefLayerTopOffset));
43  ::memset(m_scaledRefLayerRightOffset,  0, sizeof(m_scaledRefLayerRightOffset));
44  ::memset(m_scaledRefLayerBottomOffset, 0, sizeof(m_scaledRefLayerBottomOffset));
45}
46
47TAppEncLayerCfg::~TAppEncLayerCfg()
48{
49  if ( m_aidQP )
50  {
51    delete[] m_aidQP;
52  }
53}
54
55Void TAppEncLayerCfg::create()
56{
57}
58
59Void TAppEncLayerCfg::destroy()
60{
61}
62
63
64// ====================================================================================================================
65// Public member functions
66// ====================================================================================================================
67
68/** \param  argc        number of arguments
69\param  argv        array of arguments
70\retval             true when success
71*/
72bool TAppEncLayerCfg::parseCfg( const string& cfgFileName  )
73{
74  string cfg_InputFile;
75  string cfg_ReconFile;
76  string cfg_dQPFile;
77  po::Options opts;
78  opts.addOptions()
79    ("InputFile,i",           cfg_InputFile,  string(""), "original YUV input file name")
80#if AVC_BASE
81    ("InputBLFile,-ibl",      cfg_InputFile,  string(""), "original YUV input file name")
82#endif
83    ("ReconFile,o",           cfg_ReconFile,  string(""), "reconstructed YUV output file name")
84    ("SourceWidth,-wdt",      m_iSourceWidth,  0, "Source picture width")
85    ("SourceHeight,-hgt",     m_iSourceHeight, 0, "Source picture height")
86    ("CroppingMode",          m_conformanceMode,  0, "Cropping mode (0: no cropping, 1:automatic padding, 2: padding, 3:cropping")
87    ("CropLeft",              m_confLeft,      0, "Left cropping/padding for cropping mode 3")
88    ("CropRight",             m_confRight,     0, "Right cropping/padding for cropping mode 3")
89    ("CropTop",               m_confTop,       0, "Top cropping/padding for cropping mode 3")
90    ("CropBottom",            m_confBottom,    0, "Bottom cropping/padding for cropping mode 3")
91    ("HorizontalPadding,-pdx",m_aiPad[0],      0, "horizontal source padding for cropping mode 2")
92    ("VerticalPadding,-pdy",  m_aiPad[1],      0, "vertical source padding for cropping mode 2")
93    ("IntraPeriod,-ip",       m_iIntraPeriod,  -1, "intra period in frames, (-1: only first frame)")
94    ("FrameRate,-fr",         m_iFrameRate,    0, "Frame rate")
95    ("dQPFile,m",             cfg_dQPFile, string(""), "dQP file name")
96    ("QP,q",                  m_fQP,          30.0, "Qp value, if value is float, QP is switched once during encoding")
97    ;
98
99  po::setDefaults(opts);
100  po::parseConfigFile(opts, cfgFileName);
101
102  m_cInputFile = cfg_InputFile;
103  m_cReconFile = cfg_ReconFile;
104  m_pchdQPFile = cfg_dQPFile.empty() ? NULL : strdup(cfg_dQPFile.c_str());
105
106  // reading external dQP description from file
107  if ( m_pchdQPFile )
108  {
109    FILE* fpt=fopen( m_pchdQPFile, "r" );
110    if ( fpt )
111    {
112      Int iValue;
113      Int iPOC = 0;
114      while ( iPOC < m_cAppEncCfg->getNumFrameToBeEncoded() )
115      {
116        if ( fscanf(fpt, "%d", &iValue ) == EOF ) break;
117        m_aidQP[ iPOC ] = iValue;
118        iPOC++;
119      }
120      fclose(fpt);
121    }
122  }
123  return true;
124}
125
126#if AVC_SYNTAX
127Void TAppEncLayerCfg::xPrintParameter( UInt layerId )
128#else
129Void TAppEncLayerCfg::xPrintParameter()
130#endif
131{
132  printf("Input File                    : %s\n", m_cInputFile.c_str()  );
133  printf("Reconstruction File           : %s\n", m_cReconFile.c_str()  );
134#if AVC_SYNTAX
135  if( layerId == 0 )
136  {
137    printf("Base layer syntax file        : %s\n", m_cAppEncCfg->getBLSyntaxFile() );
138  }
139#endif
140  printf("Real     Format               : %dx%d %dHz\n", m_iSourceWidth - m_confLeft - m_confRight, m_iSourceHeight - m_confTop - m_confBottom, m_iFrameRate );
141  printf("Internal Format               : %dx%d %dHz\n", m_iSourceWidth, m_iSourceHeight, m_iFrameRate );
142#if LAYER_CTB
143  printf("CU size / depth               : %d / %d\n", m_uiMaxCUWidth, m_uiMaxCUDepth );
144  printf("RQT trans. size (min / max)   : %d / %d\n", 1 << m_uiQuadtreeTULog2MinSize, 1 << m_uiQuadtreeTULog2MaxSize );
145  printf("Max RQT depth inter           : %d\n", m_uiQuadtreeTUMaxDepthInter);
146  printf("Max RQT depth intra           : %d\n", m_uiQuadtreeTUMaxDepthIntra);
147#endif
148  printf("QP                            : %5.2f\n", m_fQP );
149  printf("Intra period                  : %d\n", m_iIntraPeriod );
150#if RC_SHVC_HARMONIZATION
151  printf("RateControl                   : %d\n", m_RCEnableRateControl );
152  if(m_RCEnableRateControl)
153  {
154    printf("TargetBitrate                 : %d\n", m_RCTargetBitrate );
155    printf("KeepHierarchicalBit           : %d\n", m_RCKeepHierarchicalBit );
156    printf("LCULevelRC                    : %d\n", m_RCLCULevelRC );
157    printf("UseLCUSeparateModel           : %d\n", m_RCUseLCUSeparateModel );
158    printf("InitialQP                     : %d\n", m_RCInitialQP );
159    printf("ForceIntraQP                  : %d\n", m_RCForceIntraQP );
160  }
161#endif
162  printf("WaveFrontSynchro:%d WaveFrontSubstreams:%d", m_cAppEncCfg->getWaveFrontSynchro(), m_iWaveFrontSubstreams);
163#if LAYER_CTB
164  printf("PCM:%d ", (m_cAppEncCfg->getUsePCM() && (1<<m_cAppEncCfg->getPCMLog2MinSize()) <= m_uiMaxCUWidth)? 1 : 0);
165#endif
166}
167
168Bool confirmPara(Bool bflag, const char* message);
169
170Bool TAppEncLayerCfg::xCheckParameter( Bool isField )
171{
172  switch (m_conformanceMode)
173  {
174  case 0:
175    {
176      // no cropping or padding
177      m_confLeft = m_confRight = m_confTop = m_confBottom = 0;
178      m_aiPad[1] = m_aiPad[0] = 0;
179      break;
180    }
181  case 1:
182    {
183      // automatic padding to minimum CU size
184#if LAYER_CTB
185      Int minCuSize = m_uiMaxCUHeight >> (m_uiMaxCUDepth - 1);
186#else
187      Int minCuSize = m_cAppEncCfg->getMaxCUHeight() >> (m_cAppEncCfg->getMaxCUDepth() - 1);
188#endif
189      if (m_iSourceWidth % minCuSize)
190      {
191        m_aiPad[0] = m_confRight  = ((m_iSourceWidth / minCuSize) + 1) * minCuSize - m_iSourceWidth;
192        m_iSourceWidth  += m_confRight;
193      }
194      if (m_iSourceHeight % minCuSize)
195      {
196        m_aiPad[1] = m_confBottom = ((m_iSourceHeight / minCuSize) + 1) * minCuSize - m_iSourceHeight;
197        m_iSourceHeight += m_confBottom;
198        if ( isField )
199        {
200          m_iSourceHeightOrg += m_confBottom << 1;
201          m_aiPad[1] = m_confBottom << 1;
202        }
203      }
204      break;
205    }
206  case 2:
207    {
208      //padding
209      m_iSourceWidth  += m_aiPad[0];
210      m_iSourceHeight += m_aiPad[1];
211      m_confRight  = m_aiPad[0];
212      m_confBottom = m_aiPad[1];
213      break;
214    }
215  case 3:
216    {
217      // conformance
218      if ((m_confLeft == 0) && (m_confRight == 0) && (m_confTop == 0) && (m_confBottom == 0))
219      {
220        fprintf(stderr, "Warning: Cropping enabled, but all cropping parameters set to zero\n");
221      }
222      if ((m_aiPad[1] != 0) || (m_aiPad[0]!=0))
223      {
224        fprintf(stderr, "Warning: Cropping enabled, padding parameters will be ignored\n");
225      }
226      m_aiPad[1] = m_aiPad[0] = 0;
227      break;
228    }
229  }
230
231  // allocate slice-based dQP values
232  Int iFrameToBeEncoded = m_cAppEncCfg->getNumFrameToBeEncoded();
233  Int iGOPSize = m_cAppEncCfg->getGOPSize();
234  if( m_aidQP == NULL )
235    m_aidQP = new Int[iFrameToBeEncoded + iGOPSize + 1 ];
236  ::memset( m_aidQP, 0, sizeof(Int)*( iFrameToBeEncoded + iGOPSize + 1 ) );
237
238  // handling of floating-point QP values
239  // if QP is not integer, sequence is split into two sections having QP and QP+1
240  m_iQP = (Int)( m_fQP );
241  if ( m_iQP < m_fQP )
242  {
243    Int iSwitchPOC = (Int)( iFrameToBeEncoded - (m_fQP - m_iQP)*iFrameToBeEncoded + 0.5 );
244
245
246    iSwitchPOC = (Int)( (Double)iSwitchPOC / iGOPSize + 0.5 )*iGOPSize;
247    for ( Int i=iSwitchPOC; i<iFrameToBeEncoded + iGOPSize + 1; i++ )
248    {
249      m_aidQP[i] = 1;
250    }
251  }
252
253#if LAYER_CTB
254  UInt maxCUWidth = m_uiMaxCUWidth;
255  UInt maxCUHeight = m_uiMaxCUHeight;
256  UInt maxCUDepth = m_uiMaxCUDepth;
257#else
258  UInt maxCUWidth = m_cAppEncCfg->getMaxCUWidth();
259  UInt maxCUHeight = m_cAppEncCfg->getMaxCUHeight();
260  UInt maxCUDepth = m_cAppEncCfg->getMaxCUDepth();
261#endif
262  bool check_failed = false; /* abort if there is a fatal configuration problem */
263#define xConfirmPara(a,b) check_failed |= confirmPara(a,b)
264  // check range of parameters
265  xConfirmPara( m_iFrameRate <= 0,                                                          "Frame rate must be more than 1" );
266  xConfirmPara( (m_iSourceWidth  % (maxCUWidth  >> (maxCUDepth-1)))!=0,             "Resulting coded frame width must be a multiple of the minimum CU size");
267  xConfirmPara( (m_iSourceHeight % (maxCUHeight >> (maxCUDepth-1)))!=0,             "Resulting coded frame height must be a multiple of the minimum CU size");
268  xConfirmPara( (m_iIntraPeriod > 0 && m_iIntraPeriod < iGOPSize) || m_iIntraPeriod == 0, "Intra period must be more than GOP size, or -1 , not 0" );
269  if (m_cAppEncCfg->getDecodingRefreshType() == 2)
270  {
271    xConfirmPara( m_iIntraPeriod > 0 && m_iIntraPeriod <= iGOPSize ,                      "Intra period must be larger than GOP size for periodic IDR pictures");
272  }
273
274  xConfirmPara( m_iQP <  -6 * ((Int)m_cAppEncCfg->getInternalBitDepthY() - 8) || m_iQP > 51,                "QP exceeds supported range (-QpBDOffsety to 51)" );
275
276
277  m_iWaveFrontSubstreams = m_cAppEncCfg->getWaveFrontSynchro() ? (m_iSourceHeight + maxCUHeight - 1) / maxCUHeight : 1;
278  xConfirmPara( m_iWaveFrontSubstreams <= 0, "WaveFrontSubstreams must be positive" );
279  xConfirmPara( m_iWaveFrontSubstreams > 1 && !m_cAppEncCfg->getWaveFrontSynchro(), "Must have WaveFrontSynchro > 0 in order to have WaveFrontSubstreams > 1" );
280
281  //chekc parameters
282  xConfirmPara( m_iSourceWidth  % TComSPS::getWinUnitX(CHROMA_420) != 0, "Picture width must be an integer multiple of the specified chroma subsampling");
283  xConfirmPara( m_iSourceHeight % TComSPS::getWinUnitY(CHROMA_420) != 0, "Picture height must be an integer multiple of the specified chroma subsampling");
284
285  xConfirmPara( m_aiPad[0] % TComSPS::getWinUnitX(CHROMA_420) != 0, "Horizontal padding must be an integer multiple of the specified chroma subsampling");
286  xConfirmPara( m_aiPad[1] % TComSPS::getWinUnitY(CHROMA_420) != 0, "Vertical padding must be an integer multiple of the specified chroma subsampling");
287
288  xConfirmPara( m_confLeft   % TComSPS::getWinUnitX(CHROMA_420) != 0, "Left conformance window offset must be an integer multiple of the specified chroma subsampling");
289  xConfirmPara( m_confRight  % TComSPS::getWinUnitX(CHROMA_420) != 0, "Right conformance window offset must be an integer multiple of the specified chroma subsampling");
290  xConfirmPara( m_confTop    % TComSPS::getWinUnitY(CHROMA_420) != 0, "Top conformance window offset must be an integer multiple of the specified chroma subsampling");
291  xConfirmPara( m_confBottom % TComSPS::getWinUnitY(CHROMA_420) != 0, "Bottom conformance window offset must be an integer multiple of the specified chroma subsampling");
292
293#if LAYER_CTB 
294  xConfirmPara( (m_uiMaxCUWidth  >> m_uiMaxCUDepth) < 4,                                    "Minimum partition width size should be larger than or equal to 8");
295  xConfirmPara( (m_uiMaxCUHeight >> m_uiMaxCUDepth) < 4,                                    "Minimum partition height size should be larger than or equal to 8");
296  xConfirmPara( m_uiMaxCUWidth < 16,                                                        "Maximum partition width size should be larger than or equal to 16");
297  xConfirmPara( m_uiMaxCUHeight < 16,                                                       "Maximum partition height size should be larger than or equal to 16");
298  xConfirmPara( m_uiQuadtreeTULog2MinSize < 2,                                        "QuadtreeTULog2MinSize must be 2 or greater.");
299  xConfirmPara( m_uiQuadtreeTULog2MaxSize > 5,                                        "QuadtreeTULog2MaxSize must be 5 or smaller.");
300  xConfirmPara( (1<<m_uiQuadtreeTULog2MaxSize) > m_uiMaxCUWidth,                                        "QuadtreeTULog2MaxSize must be log2(maxCUSize) or smaller.");
301  xConfirmPara( m_uiQuadtreeTULog2MaxSize < m_uiQuadtreeTULog2MinSize,                "QuadtreeTULog2MaxSize must be greater than or equal to m_uiQuadtreeTULog2MinSize.");
302  xConfirmPara( (1<<m_uiQuadtreeTULog2MinSize)>(m_uiMaxCUWidth >>(m_uiMaxCUDepth-1)), "QuadtreeTULog2MinSize must not be greater than minimum CU size" ); // HS
303  xConfirmPara( (1<<m_uiQuadtreeTULog2MinSize)>(m_uiMaxCUHeight>>(m_uiMaxCUDepth-1)), "QuadtreeTULog2MinSize must not be greater than minimum CU size" ); // HS
304  xConfirmPara( ( 1 << m_uiQuadtreeTULog2MinSize ) > ( m_uiMaxCUWidth  >> m_uiMaxCUDepth ), "Minimum CU width must be greater than minimum transform size." );
305  xConfirmPara( ( 1 << m_uiQuadtreeTULog2MinSize ) > ( m_uiMaxCUHeight >> m_uiMaxCUDepth ), "Minimum CU height must be greater than minimum transform size." );
306  xConfirmPara( m_uiQuadtreeTUMaxDepthInter < 1,                                                         "QuadtreeTUMaxDepthInter must be greater than or equal to 1" );
307  xConfirmPara( m_uiMaxCUWidth < ( 1 << (m_uiQuadtreeTULog2MinSize + m_uiQuadtreeTUMaxDepthInter - 1) ), "QuadtreeTUMaxDepthInter must be less than or equal to the difference between log2(maxCUSize) and QuadtreeTULog2MinSize plus 1" );
308  xConfirmPara( m_uiQuadtreeTUMaxDepthIntra < 1,                                                         "QuadtreeTUMaxDepthIntra must be greater than or equal to 1" );
309  xConfirmPara( m_uiMaxCUWidth < ( 1 << (m_uiQuadtreeTULog2MinSize + m_uiQuadtreeTUMaxDepthIntra - 1) ), "QuadtreeTUMaxDepthInter must be less than or equal to the difference between log2(maxCUSize) and QuadtreeTULog2MinSize plus 1" );
310
311  // max CU width and height should be power of 2
312  UInt ui = m_uiMaxCUWidth;
313  while(ui)
314  {
315    ui >>= 1;
316    if( (ui & 1) == 1)
317      xConfirmPara( ui != 1 , "Width should be 2^n");
318  }
319  ui = m_uiMaxCUHeight;
320  while(ui)
321  {
322    ui >>= 1;
323    if( (ui & 1) == 1)
324      xConfirmPara( ui != 1 , "Height should be 2^n");
325  }
326#endif
327
328#undef xConfirmPara
329  return check_failed;
330}
331
332#endif //SVC_EXTENSION
333
334
335//! \}
Note: See TracBrowser for help on using the repository browser.