source: SHVCSoftware/branches/SHM-3.1-dev/source/Lib/TLibEncoder/TEncCu.cpp @ 415

Last change on this file since 415 was 389, checked in by qualcomm, 12 years ago

Signaling representation format in VPS (MACRO: REPN_FORMAT_IN_VPS)

Includes signaling of representation format - including picture resolution, bit depth, chroma format - in the VPS, with the option of updating them in the SPS. The configuration file has "RepFormatIdx%d" added to indicate for each layer which representation format is used. The rep_format() structures are automatically created by the encoder. If the bit depth and the chroma format are also changed across layers, some more configuration support would be needed.

From: Adarsh K. Ramasubramonian <aramasub@…>

  • Property svn:eol-style set to native
File size: 69.9 KB
Line 
1/* The copyright in this software is being made available under the BSD
2 * License, included below. This software may be subject to other third party
3 * and contributor rights, including patent rights, and no such rights are
4 * granted under this license. 
5 *
6 * Copyright (c) 2010-2013, ITU/ISO/IEC
7 * All rights reserved.
8 *
9 * Redistribution and use in source and binary forms, with or without
10 * modification, are permitted provided that the following conditions are met:
11 *
12 *  * Redistributions of source code must retain the above copyright notice,
13 *    this list of conditions and the following disclaimer.
14 *  * Redistributions in binary form must reproduce the above copyright notice,
15 *    this list of conditions and the following disclaimer in the documentation
16 *    and/or other materials provided with the distribution.
17 *  * Neither the name of the ITU/ISO/IEC nor the names of its contributors may
18 *    be used to endorse or promote products derived from this software without
19 *    specific prior written permission.
20 *
21 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
22 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
23 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
24 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS
25 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
26 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
27 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
28 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
29 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
30 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
31 * THE POSSIBILITY OF SUCH DAMAGE.
32 */
33
34/** \file     TEncCu.cpp
35    \brief    Coding Unit (CU) encoder class
36*/
37
38#include <stdio.h>
39#include "TEncTop.h"
40#include "TEncCu.h"
41#include "TEncAnalyze.h"
42
43#include <cmath>
44#include <algorithm>
45using namespace std;
46
47//! \ingroup TLibEncoder
48//! \{
49
50// ====================================================================================================================
51// Constructor / destructor / create / destroy
52// ====================================================================================================================
53
54/**
55 \param    uiTotalDepth  total number of allowable depth
56 \param    uiMaxWidth    largest CU width
57 \param    uiMaxHeight   largest CU height
58 */
59Void TEncCu::create(UChar uhTotalDepth, UInt uiMaxWidth, UInt uiMaxHeight)
60{
61  Int i;
62 
63  m_uhTotalDepth   = uhTotalDepth + 1;
64  m_ppcBestCU      = new TComDataCU*[m_uhTotalDepth-1];
65  m_ppcTempCU      = new TComDataCU*[m_uhTotalDepth-1];
66   
67  m_ppcPredYuvBest = new TComYuv*[m_uhTotalDepth-1];
68  m_ppcResiYuvBest = new TComYuv*[m_uhTotalDepth-1];
69  m_ppcRecoYuvBest = new TComYuv*[m_uhTotalDepth-1];
70  m_ppcPredYuvTemp = new TComYuv*[m_uhTotalDepth-1];
71  m_ppcResiYuvTemp = new TComYuv*[m_uhTotalDepth-1];
72  m_ppcRecoYuvTemp = new TComYuv*[m_uhTotalDepth-1];
73  m_ppcOrigYuv     = new TComYuv*[m_uhTotalDepth-1];
74 
75  UInt uiNumPartitions;
76  for( i=0 ; i<m_uhTotalDepth-1 ; i++)
77  {
78    uiNumPartitions = 1<<( ( m_uhTotalDepth - i - 1 )<<1 );
79    UInt uiWidth  = uiMaxWidth  >> i;
80    UInt uiHeight = uiMaxHeight >> i;
81   
82    m_ppcBestCU[i] = new TComDataCU; m_ppcBestCU[i]->create( uiNumPartitions, uiWidth, uiHeight, false, uiMaxWidth >> (m_uhTotalDepth - 1) );
83    m_ppcTempCU[i] = new TComDataCU; m_ppcTempCU[i]->create( uiNumPartitions, uiWidth, uiHeight, false, uiMaxWidth >> (m_uhTotalDepth - 1) );
84   
85    m_ppcPredYuvBest[i] = new TComYuv; m_ppcPredYuvBest[i]->create(uiWidth, uiHeight);
86    m_ppcResiYuvBest[i] = new TComYuv; m_ppcResiYuvBest[i]->create(uiWidth, uiHeight);
87    m_ppcRecoYuvBest[i] = new TComYuv; m_ppcRecoYuvBest[i]->create(uiWidth, uiHeight);
88   
89    m_ppcPredYuvTemp[i] = new TComYuv; m_ppcPredYuvTemp[i]->create(uiWidth, uiHeight);
90    m_ppcResiYuvTemp[i] = new TComYuv; m_ppcResiYuvTemp[i]->create(uiWidth, uiHeight);
91    m_ppcRecoYuvTemp[i] = new TComYuv; m_ppcRecoYuvTemp[i]->create(uiWidth, uiHeight);
92   
93    m_ppcOrigYuv    [i] = new TComYuv; m_ppcOrigYuv    [i]->create(uiWidth, uiHeight);
94  }
95 
96  m_bEncodeDQP = false;
97#if RATE_CONTROL_LAMBDA_DOMAIN && !M0036_RC_IMPROVEMENT
98  m_LCUPredictionSAD = 0;
99  m_addSADDepth      = 0;
100  m_temporalSAD      = 0;
101#endif
102
103  // initialize partition order.
104  UInt* piTmp = &g_auiZscanToRaster[0];
105  initZscanToRaster( m_uhTotalDepth, 1, 0, piTmp);
106  initRasterToZscan( uiMaxWidth, uiMaxHeight, m_uhTotalDepth );
107 
108  // initialize conversion matrix from partition index to pel
109  initRasterToPelXY( uiMaxWidth, uiMaxHeight, m_uhTotalDepth );
110}
111
112Void TEncCu::destroy()
113{
114  Int i;
115 
116  for( i=0 ; i<m_uhTotalDepth-1 ; i++)
117  {
118    if(m_ppcBestCU[i])
119    {
120      m_ppcBestCU[i]->destroy();      delete m_ppcBestCU[i];      m_ppcBestCU[i] = NULL;
121    }
122    if(m_ppcTempCU[i])
123    {
124      m_ppcTempCU[i]->destroy();      delete m_ppcTempCU[i];      m_ppcTempCU[i] = NULL;
125    }
126    if(m_ppcPredYuvBest[i])
127    {
128      m_ppcPredYuvBest[i]->destroy(); delete m_ppcPredYuvBest[i]; m_ppcPredYuvBest[i] = NULL;
129    }
130    if(m_ppcResiYuvBest[i])
131    {
132      m_ppcResiYuvBest[i]->destroy(); delete m_ppcResiYuvBest[i]; m_ppcResiYuvBest[i] = NULL;
133    }
134    if(m_ppcRecoYuvBest[i])
135    {
136      m_ppcRecoYuvBest[i]->destroy(); delete m_ppcRecoYuvBest[i]; m_ppcRecoYuvBest[i] = NULL;
137    }
138    if(m_ppcPredYuvTemp[i])
139    {
140      m_ppcPredYuvTemp[i]->destroy(); delete m_ppcPredYuvTemp[i]; m_ppcPredYuvTemp[i] = NULL;
141    }
142    if(m_ppcResiYuvTemp[i])
143    {
144      m_ppcResiYuvTemp[i]->destroy(); delete m_ppcResiYuvTemp[i]; m_ppcResiYuvTemp[i] = NULL;
145    }
146    if(m_ppcRecoYuvTemp[i])
147    {
148      m_ppcRecoYuvTemp[i]->destroy(); delete m_ppcRecoYuvTemp[i]; m_ppcRecoYuvTemp[i] = NULL;
149    }
150    if(m_ppcOrigYuv[i])
151    {
152      m_ppcOrigYuv[i]->destroy();     delete m_ppcOrigYuv[i];     m_ppcOrigYuv[i] = NULL;
153    }
154  }
155  if(m_ppcBestCU)
156  {
157    delete [] m_ppcBestCU;
158    m_ppcBestCU = NULL;
159  }
160  if(m_ppcTempCU)
161  {
162    delete [] m_ppcTempCU;
163    m_ppcTempCU = NULL;
164  }
165 
166  if(m_ppcPredYuvBest)
167  {
168    delete [] m_ppcPredYuvBest;
169    m_ppcPredYuvBest = NULL;
170  }
171  if(m_ppcResiYuvBest)
172  {
173    delete [] m_ppcResiYuvBest;
174    m_ppcResiYuvBest = NULL;
175  }
176  if(m_ppcRecoYuvBest)
177  {
178    delete [] m_ppcRecoYuvBest;
179    m_ppcRecoYuvBest = NULL;
180  }
181  if(m_ppcPredYuvTemp)
182  {
183    delete [] m_ppcPredYuvTemp;
184    m_ppcPredYuvTemp = NULL;
185  }
186  if(m_ppcResiYuvTemp)
187  {
188    delete [] m_ppcResiYuvTemp;
189    m_ppcResiYuvTemp = NULL;
190  }
191  if(m_ppcRecoYuvTemp)
192  {
193    delete [] m_ppcRecoYuvTemp;
194    m_ppcRecoYuvTemp = NULL;
195  }
196  if(m_ppcOrigYuv)
197  {
198    delete [] m_ppcOrigYuv;
199    m_ppcOrigYuv = NULL;
200  }
201}
202
203/** \param    pcEncTop      pointer of encoder class
204 */
205Void TEncCu::init( TEncTop* pcEncTop )
206{
207  m_pcEncCfg           = pcEncTop;
208  m_pcPredSearch       = pcEncTop->getPredSearch();
209  m_pcTrQuant          = pcEncTop->getTrQuant();
210  m_pcBitCounter       = pcEncTop->getBitCounter();
211  m_pcRdCost           = pcEncTop->getRdCost();
212 
213#if SVC_EXTENSION
214  m_ppcTEncTop         = pcEncTop->getLayerEnc();
215  for(UInt i=0 ; i< m_uhTotalDepth-1 ; i++)
216  {   
217    m_ppcBestCU[i]->setLayerId(pcEncTop->getLayerId());
218    m_ppcTempCU[i]->setLayerId(pcEncTop->getLayerId());
219  }
220#endif
221 
222  m_pcEntropyCoder     = pcEncTop->getEntropyCoder();
223  m_pcCavlcCoder       = pcEncTop->getCavlcCoder();
224  m_pcSbacCoder       = pcEncTop->getSbacCoder();
225  m_pcBinCABAC         = pcEncTop->getBinCABAC();
226 
227  m_pppcRDSbacCoder   = pcEncTop->getRDSbacCoder();
228  m_pcRDGoOnSbacCoder = pcEncTop->getRDGoOnSbacCoder();
229 
230  m_bUseSBACRD        = pcEncTop->getUseSBACRD();
231  m_pcRateCtrl        = pcEncTop->getRateCtrl();
232}
233
234// ====================================================================================================================
235// Public member functions
236// ====================================================================================================================
237
238/** \param  rpcCU pointer of CU data class
239 */
240Void TEncCu::compressCU( TComDataCU*& rpcCU )
241{
242  // initialize CU data
243  m_ppcBestCU[0]->initCU( rpcCU->getPic(), rpcCU->getAddr() );
244  m_ppcTempCU[0]->initCU( rpcCU->getPic(), rpcCU->getAddr() );
245
246#if RATE_CONTROL_LAMBDA_DOMAIN && !M0036_RC_IMPROVEMENT
247  m_addSADDepth      = 0;
248  m_LCUPredictionSAD = 0;
249  m_temporalSAD      = 0;
250#endif
251
252  // analysis of CU
253  xCompressCU( m_ppcBestCU[0], m_ppcTempCU[0], 0 );
254
255#if ADAPTIVE_QP_SELECTION
256  if( m_pcEncCfg->getUseAdaptQpSelect() )
257  {
258    if(rpcCU->getSlice()->getSliceType()!=I_SLICE) //IIII
259    {
260      xLcuCollectARLStats( rpcCU);
261    }
262  }
263#endif
264}
265/** \param  pcCU  pointer of CU data class
266 */
267Void TEncCu::encodeCU ( TComDataCU* pcCU )
268{
269  if ( pcCU->getSlice()->getPPS()->getUseDQP() )
270  {
271    setdQPFlag(true);
272  }
273
274  // Encode CU data
275  xEncodeCU( pcCU, 0, 0 );
276}
277
278// ====================================================================================================================
279// Protected member functions
280// ====================================================================================================================
281/** Derive small set of test modes for AMP encoder speed-up
282 *\param   rpcBestCU
283 *\param   eParentPartSize
284 *\param   bTestAMP_Hor
285 *\param   bTestAMP_Ver
286 *\param   bTestMergeAMP_Hor
287 *\param   bTestMergeAMP_Ver
288 *\returns Void
289*/
290#if AMP_ENC_SPEEDUP
291#if AMP_MRG
292Void TEncCu::deriveTestModeAMP (TComDataCU *&rpcBestCU, PartSize eParentPartSize, Bool &bTestAMP_Hor, Bool &bTestAMP_Ver, Bool &bTestMergeAMP_Hor, Bool &bTestMergeAMP_Ver)
293#else
294Void TEncCu::deriveTestModeAMP (TComDataCU *&rpcBestCU, PartSize eParentPartSize, Bool &bTestAMP_Hor, Bool &bTestAMP_Ver)
295#endif
296{
297  if ( rpcBestCU->getPartitionSize(0) == SIZE_2NxN )
298  {
299    bTestAMP_Hor = true;
300  }
301  else if ( rpcBestCU->getPartitionSize(0) == SIZE_Nx2N )
302  {
303    bTestAMP_Ver = true;
304  }
305  else if ( rpcBestCU->getPartitionSize(0) == SIZE_2Nx2N && rpcBestCU->getMergeFlag(0) == false && rpcBestCU->isSkipped(0) == false )
306  {
307    bTestAMP_Hor = true;         
308    bTestAMP_Ver = true;         
309  }
310
311#if AMP_MRG
312  //! Utilizing the partition size of parent PU   
313  if ( eParentPartSize >= SIZE_2NxnU && eParentPartSize <= SIZE_nRx2N )
314  { 
315    bTestMergeAMP_Hor = true;
316    bTestMergeAMP_Ver = true;
317  }
318
319  if ( eParentPartSize == SIZE_NONE ) //! if parent is intra
320  {
321    if ( rpcBestCU->getPartitionSize(0) == SIZE_2NxN )
322    {
323      bTestMergeAMP_Hor = true;
324    }
325    else if ( rpcBestCU->getPartitionSize(0) == SIZE_Nx2N )
326    {
327      bTestMergeAMP_Ver = true;
328    }
329  }
330
331  if ( rpcBestCU->getPartitionSize(0) == SIZE_2Nx2N && rpcBestCU->isSkipped(0) == false )
332  {
333    bTestMergeAMP_Hor = true;         
334    bTestMergeAMP_Ver = true;         
335  }
336
337  if ( rpcBestCU->getWidth(0) == 64 )
338  { 
339    bTestAMP_Hor = false;
340    bTestAMP_Ver = false;
341  }   
342#else
343  //! Utilizing the partition size of parent PU       
344  if ( eParentPartSize >= SIZE_2NxnU && eParentPartSize <= SIZE_nRx2N )
345  { 
346    bTestAMP_Hor = true;
347    bTestAMP_Ver = true;
348  }
349
350  if ( eParentPartSize == SIZE_2Nx2N )
351  { 
352    bTestAMP_Hor = false;
353    bTestAMP_Ver = false;
354  }     
355#endif
356}
357#endif
358
359// ====================================================================================================================
360// Protected member functions
361// ====================================================================================================================
362/** Compress a CU block recursively with enabling sub-LCU-level delta QP
363 *\param   rpcBestCU
364 *\param   rpcTempCU
365 *\param   uiDepth
366 *\returns Void
367 *
368 *- for loop of QP value to compress the current CU with all possible QP
369*/
370#if AMP_ENC_SPEEDUP
371Void TEncCu::xCompressCU( TComDataCU*& rpcBestCU, TComDataCU*& rpcTempCU, UInt uiDepth, PartSize eParentPartSize )
372#else
373Void TEncCu::xCompressCU( TComDataCU*& rpcBestCU, TComDataCU*& rpcTempCU, UInt uiDepth )
374#endif
375{
376  TComPic* pcPic = rpcBestCU->getPic();
377
378  // get Original YUV data from picture
379  m_ppcOrigYuv[uiDepth]->copyFromPicYuv( pcPic->getPicYuvOrg(), rpcBestCU->getAddr(), rpcBestCU->getZorderIdxInCU() );
380
381  // variables for fast encoder decision
382  Bool    bEarlySkip  = false;
383  Bool    bTrySplit    = true;
384  Double  fRD_Skip    = MAX_DOUBLE;
385
386  // variable for Early CU determination
387  Bool    bSubBranch = true;
388
389  // variable for Cbf fast mode PU decision
390  Bool    doNotBlockPu = true;
391  Bool earlyDetectionSkipMode = false;
392
393  Bool    bTrySplitDQP  = true;
394
395  static  Double  afCost[ MAX_CU_DEPTH ];
396  static  Int      aiNum [ MAX_CU_DEPTH ];
397
398  if ( rpcBestCU->getAddr() == 0 )
399  {
400    ::memset( afCost, 0, sizeof( afCost ) );
401    ::memset( aiNum,  0, sizeof( aiNum  ) );
402  }
403
404  Bool bBoundary = false;
405  UInt uiLPelX   = rpcBestCU->getCUPelX();
406  UInt uiRPelX   = uiLPelX + rpcBestCU->getWidth(0)  - 1;
407  UInt uiTPelY   = rpcBestCU->getCUPelY();
408  UInt uiBPelY   = uiTPelY + rpcBestCU->getHeight(0) - 1;
409
410  Int iBaseQP = xComputeQP( rpcBestCU, uiDepth );
411  Int iMinQP;
412  Int iMaxQP;
413  Bool isAddLowestQP = false;
414#if REPN_FORMAT_IN_VPS
415  Int lowestQP = -rpcTempCU->getSlice()->getQpBDOffsetY();
416#else
417  Int lowestQP = -rpcTempCU->getSlice()->getSPS()->getQpBDOffsetY();
418#endif
419
420  if( (g_uiMaxCUWidth>>uiDepth) >= rpcTempCU->getSlice()->getPPS()->getMinCuDQPSize() )
421  {
422    Int idQP = m_pcEncCfg->getMaxDeltaQP();
423#if REPN_FORMAT_IN_VPS
424    iMinQP = Clip3( -rpcTempCU->getSlice()->getSPS()->getQpBDOffsetY(), MAX_QP, iBaseQP-idQP );
425    iMaxQP = Clip3( -rpcTempCU->getSlice()->getSPS()->getQpBDOffsetY(), MAX_QP, iBaseQP+idQP );
426#else
427    iMinQP = Clip3( -rpcTempCU->getSlice()->getSPS()->getQpBDOffsetY(), MAX_QP, iBaseQP-idQP );
428    iMaxQP = Clip3( -rpcTempCU->getSlice()->getSPS()->getQpBDOffsetY(), MAX_QP, iBaseQP+idQP );
429#endif
430    if ( (rpcTempCU->getSlice()->getSPS()->getUseLossless()) && (lowestQP < iMinQP) && rpcTempCU->getSlice()->getPPS()->getUseDQP() )
431    {
432      isAddLowestQP = true; 
433      iMinQP = iMinQP - 1;
434    }
435  }
436  else
437  {
438    iMinQP = rpcTempCU->getQP(0);
439    iMaxQP = rpcTempCU->getQP(0);
440  }
441
442#if RATE_CONTROL_LAMBDA_DOMAIN
443  if ( m_pcEncCfg->getUseRateCtrl() )
444  {
445    iMinQP = m_pcRateCtrl->getRCQP();
446    iMaxQP = m_pcRateCtrl->getRCQP();
447  }
448#else
449  if(m_pcEncCfg->getUseRateCtrl())
450  {
451    Int qp = m_pcRateCtrl->getUnitQP();
452    iMinQP  = Clip3( MIN_QP, MAX_QP, qp);
453    iMaxQP  = Clip3( MIN_QP, MAX_QP, qp);
454  }
455#endif
456
457  // If slice start or slice end is within this cu...
458  TComSlice * pcSlice = rpcTempCU->getPic()->getSlice(rpcTempCU->getPic()->getCurrSliceIdx());
459  Bool bSliceStart = pcSlice->getSliceSegmentCurStartCUAddr()>rpcTempCU->getSCUAddr()&&pcSlice->getSliceSegmentCurStartCUAddr()<rpcTempCU->getSCUAddr()+rpcTempCU->getTotalNumPart();
460  Bool bSliceEnd = (pcSlice->getSliceSegmentCurEndCUAddr()>rpcTempCU->getSCUAddr()&&pcSlice->getSliceSegmentCurEndCUAddr()<rpcTempCU->getSCUAddr()+rpcTempCU->getTotalNumPart());
461#if REPN_FORMAT_IN_VPS
462  Bool bInsidePicture = ( uiRPelX < rpcBestCU->getSlice()->getPicWidthInLumaSamples()           ) && ( uiBPelY < rpcBestCU->getSlice()->getPicHeightInLumaSamples()           );
463#else
464  Bool bInsidePicture = ( uiRPelX < rpcBestCU->getSlice()->getSPS()->getPicWidthInLumaSamples() ) && ( uiBPelY < rpcBestCU->getSlice()->getSPS()->getPicHeightInLumaSamples() );
465#endif
466  // We need to split, so don't try these modes.
467  if(!bSliceEnd && !bSliceStart && bInsidePicture )
468  {
469#if (ENCODER_FAST_MODE)
470    Bool testInter = true;
471    if (rpcBestCU->getLayerId() > 0)
472    {
473        if(pcSlice->getSliceType() == P_SLICE && pcSlice->getNumRefIdx(REF_PIC_LIST_0) == pcSlice->getActiveNumILRRefIdx()) 
474            testInter = false; 
475        if(pcSlice->getSliceType() == B_SLICE && pcSlice->getNumRefIdx(REF_PIC_LIST_0) == pcSlice->getActiveNumILRRefIdx() && pcSlice->getNumRefIdx(REF_PIC_LIST_1) == pcSlice->getActiveNumILRRefIdx()) 
476            testInter = false;
477#if M0457_IL_SAMPLE_PRED_ONLY_FLAG
478        if( pcSlice->getInterLayerSamplePredOnlyFlag() ) 
479            testInter = false; 
480#endif
481    }
482#endif
483    for (Int iQP=iMinQP; iQP<=iMaxQP; iQP++)
484    {
485      if (isAddLowestQP && (iQP == iMinQP))
486      {
487        iQP = lowestQP;
488      }
489      // variables for fast encoder decision
490      bEarlySkip  = false;
491      bTrySplit    = true;
492      fRD_Skip    = MAX_DOUBLE;
493
494      rpcTempCU->initEstData( uiDepth, iQP );
495
496      // do inter modes, SKIP and 2Nx2N
497#if (ENCODER_FAST_MODE == 1)
498      if( rpcBestCU->getSlice()->getSliceType() != I_SLICE && testInter )
499#else
500      if( rpcBestCU->getSlice()->getSliceType() != I_SLICE )
501#endif
502      {
503        // 2Nx2N
504        if(m_pcEncCfg->getUseEarlySkipDetection())
505        {
506          xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_2Nx2N );  rpcTempCU->initEstData( uiDepth, iQP );//by Competition for inter_2Nx2N
507        }
508        // SKIP
509        xCheckRDCostMerge2Nx2N( rpcBestCU, rpcTempCU, &earlyDetectionSkipMode );//by Merge for inter_2Nx2N
510        rpcTempCU->initEstData( uiDepth, iQP );
511
512        // fast encoder decision for early skip
513        if ( m_pcEncCfg->getUseFastEnc() )
514        {
515          Int iIdx = g_aucConvertToBit[ rpcBestCU->getWidth(0) ];
516          if ( aiNum [ iIdx ] > 5 && fRD_Skip < EARLY_SKIP_THRES*afCost[ iIdx ]/aiNum[ iIdx ] )
517          {
518            bEarlySkip = true;
519            bTrySplit  = false;
520          }
521        }
522#if (ENCODER_FAST_MODE == 2)
523        if (testInter)
524        {
525#endif
526
527        if(!m_pcEncCfg->getUseEarlySkipDetection())
528        {
529          // 2Nx2N, NxN
530          if ( !bEarlySkip )
531          {
532            xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_2Nx2N );  rpcTempCU->initEstData( uiDepth, iQP );
533            if(m_pcEncCfg->getUseCbfFastMode())
534            {
535              doNotBlockPu = rpcBestCU->getQtRootCbf( 0 ) != 0;
536            }
537          }
538        }
539#if (ENCODER_FAST_MODE == 2)
540    }
541#endif
542
543      }
544
545      if( (g_uiMaxCUWidth>>uiDepth) >= rpcTempCU->getSlice()->getPPS()->getMinCuDQPSize() )
546      {
547        if(iQP == iBaseQP)
548        {
549          bTrySplitDQP = bTrySplit;
550        }
551      }
552      else
553      {
554        bTrySplitDQP = bTrySplit;
555      }
556      if (isAddLowestQP && (iQP == lowestQP))
557      {
558        iQP = iMinQP;
559      }
560    }
561
562#if RATE_CONTROL_LAMBDA_DOMAIN && !M0036_RC_IMPROVEMENT
563    if ( uiDepth <= m_addSADDepth )
564    {
565      m_LCUPredictionSAD += m_temporalSAD;
566      m_addSADDepth = uiDepth;
567    }
568#endif
569
570    if(!earlyDetectionSkipMode)
571    {
572      for (Int iQP=iMinQP; iQP<=iMaxQP; iQP++)
573      {
574        if (isAddLowestQP && (iQP == iMinQP))
575        {
576          iQP = lowestQP;
577        }
578        rpcTempCU->initEstData( uiDepth, iQP );
579
580        // do inter modes, NxN, 2NxN, and Nx2N
581#if (ENCODER_FAST_MODE)
582      if( rpcBestCU->getSlice()->getSliceType() != I_SLICE && testInter )
583#else
584        if( rpcBestCU->getSlice()->getSliceType() != I_SLICE )
585#endif
586        {
587          // 2Nx2N, NxN
588          if ( !bEarlySkip )
589          {
590            if(!( (rpcBestCU->getWidth(0)==8) && (rpcBestCU->getHeight(0)==8) ))
591            {
592              if( uiDepth == g_uiMaxCUDepth - g_uiAddCUDepth && doNotBlockPu)
593              {
594                xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_NxN   );
595                rpcTempCU->initEstData( uiDepth, iQP );
596              }
597            }
598          }
599
600          // 2NxN, Nx2N
601          if(doNotBlockPu)
602          {
603            xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_Nx2N  );
604            rpcTempCU->initEstData( uiDepth, iQP );
605            if(m_pcEncCfg->getUseCbfFastMode() && rpcBestCU->getPartitionSize(0) == SIZE_Nx2N )
606            {
607              doNotBlockPu = rpcBestCU->getQtRootCbf( 0 ) != 0;
608            }
609          }
610          if(doNotBlockPu)
611          {
612            xCheckRDCostInter      ( rpcBestCU, rpcTempCU, SIZE_2NxN  );
613            rpcTempCU->initEstData( uiDepth, iQP );
614            if(m_pcEncCfg->getUseCbfFastMode() && rpcBestCU->getPartitionSize(0) == SIZE_2NxN)
615            {
616              doNotBlockPu = rpcBestCU->getQtRootCbf( 0 ) != 0;
617            }
618          }
619
620#if 1
621          //! Try AMP (SIZE_2NxnU, SIZE_2NxnD, SIZE_nLx2N, SIZE_nRx2N)
622          if( pcPic->getSlice(0)->getSPS()->getAMPAcc(uiDepth) )
623          {
624#if AMP_ENC_SPEEDUP       
625            Bool bTestAMP_Hor = false, bTestAMP_Ver = false;
626
627#if AMP_MRG
628            Bool bTestMergeAMP_Hor = false, bTestMergeAMP_Ver = false;
629
630            deriveTestModeAMP (rpcBestCU, eParentPartSize, bTestAMP_Hor, bTestAMP_Ver, bTestMergeAMP_Hor, bTestMergeAMP_Ver);
631#else
632            deriveTestModeAMP (rpcBestCU, eParentPartSize, bTestAMP_Hor, bTestAMP_Ver);
633#endif
634
635            //! Do horizontal AMP
636            if ( bTestAMP_Hor )
637            {
638              if(doNotBlockPu)
639              {
640                xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_2NxnU );
641                rpcTempCU->initEstData( uiDepth, iQP );
642                if(m_pcEncCfg->getUseCbfFastMode() && rpcBestCU->getPartitionSize(0) == SIZE_2NxnU )
643                {
644                  doNotBlockPu = rpcBestCU->getQtRootCbf( 0 ) != 0;
645                }
646              }
647              if(doNotBlockPu)
648              {
649                xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_2NxnD );
650                rpcTempCU->initEstData( uiDepth, iQP );
651                if(m_pcEncCfg->getUseCbfFastMode() && rpcBestCU->getPartitionSize(0) == SIZE_2NxnD )
652                {
653                  doNotBlockPu = rpcBestCU->getQtRootCbf( 0 ) != 0;
654                }
655              }
656            }
657#if AMP_MRG
658            else if ( bTestMergeAMP_Hor ) 
659            {
660              if(doNotBlockPu)
661              {
662                xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_2NxnU, true );
663                rpcTempCU->initEstData( uiDepth, iQP );
664                if(m_pcEncCfg->getUseCbfFastMode() && rpcBestCU->getPartitionSize(0) == SIZE_2NxnU )
665                {
666                  doNotBlockPu = rpcBestCU->getQtRootCbf( 0 ) != 0;
667                }
668              }
669              if(doNotBlockPu)
670              {
671                xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_2NxnD, true );
672                rpcTempCU->initEstData( uiDepth, iQP );
673                if(m_pcEncCfg->getUseCbfFastMode() && rpcBestCU->getPartitionSize(0) == SIZE_2NxnD )
674                {
675                  doNotBlockPu = rpcBestCU->getQtRootCbf( 0 ) != 0;
676                }
677              }
678            }
679#endif
680
681            //! Do horizontal AMP
682            if ( bTestAMP_Ver )
683            {
684              if(doNotBlockPu)
685              {
686                xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_nLx2N );
687                rpcTempCU->initEstData( uiDepth, iQP );
688                if(m_pcEncCfg->getUseCbfFastMode() && rpcBestCU->getPartitionSize(0) == SIZE_nLx2N )
689                {
690                  doNotBlockPu = rpcBestCU->getQtRootCbf( 0 ) != 0;
691                }
692              }
693              if(doNotBlockPu)
694              {
695                xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_nRx2N );
696                rpcTempCU->initEstData( uiDepth, iQP );
697              }
698            }
699#if AMP_MRG
700            else if ( bTestMergeAMP_Ver )
701            {
702              if(doNotBlockPu)
703              {
704                xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_nLx2N, true );
705                rpcTempCU->initEstData( uiDepth, iQP );
706                if(m_pcEncCfg->getUseCbfFastMode() && rpcBestCU->getPartitionSize(0) == SIZE_nLx2N )
707                {
708                  doNotBlockPu = rpcBestCU->getQtRootCbf( 0 ) != 0;
709                }
710              }
711              if(doNotBlockPu)
712              {
713                xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_nRx2N, true );
714                rpcTempCU->initEstData( uiDepth, iQP );
715              }
716            }
717#endif
718
719#else
720            xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_2NxnU );
721            rpcTempCU->initEstData( uiDepth, iQP );
722            xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_2NxnD );
723            rpcTempCU->initEstData( uiDepth, iQP );
724            xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_nLx2N );
725            rpcTempCU->initEstData( uiDepth, iQP );
726
727            xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_nRx2N );
728            rpcTempCU->initEstData( uiDepth, iQP );
729
730#endif
731          }   
732#endif
733        }
734
735        // do normal intra modes
736        if ( !bEarlySkip )
737        {
738          // speedup for inter frames
739#if (ENCODER_FAST_MODE)
740        if( rpcBestCU->getSlice()->getSliceType() == I_SLICE || 
741          !testInter ||
742          rpcBestCU->getCbf( 0, TEXT_LUMA     ) != 0   ||
743          rpcBestCU->getCbf( 0, TEXT_CHROMA_U ) != 0   ||
744          rpcBestCU->getCbf( 0, TEXT_CHROMA_V ) != 0     ) // avoid very complex intra if it is unlikely
745#else
746          if( rpcBestCU->getSlice()->getSliceType() == I_SLICE || 
747            rpcBestCU->getCbf( 0, TEXT_LUMA     ) != 0   ||
748            rpcBestCU->getCbf( 0, TEXT_CHROMA_U ) != 0   ||
749            rpcBestCU->getCbf( 0, TEXT_CHROMA_V ) != 0     ) // avoid very complex intra if it is unlikely
750#endif
751          {
752            xCheckRDCostIntra( rpcBestCU, rpcTempCU, SIZE_2Nx2N );
753            rpcTempCU->initEstData( uiDepth, iQP );
754            if( uiDepth == g_uiMaxCUDepth - g_uiAddCUDepth )
755            {
756              if( rpcTempCU->getWidth(0) > ( 1 << rpcTempCU->getSlice()->getSPS()->getQuadtreeTULog2MinSize() ) )
757              {
758                xCheckRDCostIntra( rpcBestCU, rpcTempCU, SIZE_NxN   );
759                rpcTempCU->initEstData( uiDepth, iQP );
760              }
761            }
762          }
763        }
764
765        // test PCM
766        if(pcPic->getSlice(0)->getSPS()->getUsePCM()
767          && rpcTempCU->getWidth(0) <= (1<<pcPic->getSlice(0)->getSPS()->getPCMLog2MaxSize())
768          && rpcTempCU->getWidth(0) >= (1<<pcPic->getSlice(0)->getSPS()->getPCMLog2MinSize()) )
769        {
770          UInt uiRawBits = (2 * g_bitDepthY + g_bitDepthC) * rpcBestCU->getWidth(0) * rpcBestCU->getHeight(0) / 2;
771          UInt uiBestBits = rpcBestCU->getTotalBits();
772          if((uiBestBits > uiRawBits) || (rpcBestCU->getTotalCost() > m_pcRdCost->calcRdCost(uiRawBits, 0)))
773          {
774            xCheckIntraPCM (rpcBestCU, rpcTempCU);
775            rpcTempCU->initEstData( uiDepth, iQP );
776          }
777        }
778#if (ENCODER_FAST_MODE)
779      if(pcPic->getLayerId() > 0)
780      {
781        for(Int refLayer = 0; refLayer < pcSlice->getActiveNumILRRefIdx(); refLayer++)
782        { 
783           xCheckRDCostILRUni( rpcBestCU, rpcTempCU, pcSlice->getInterLayerPredLayerIdc(refLayer));
784           rpcTempCU->initEstData( uiDepth, iQP );
785        }
786      }
787#endif
788
789        if (isAddLowestQP && (iQP == lowestQP))
790        {
791          iQP = iMinQP;
792        }
793      }
794    }
795
796    m_pcEntropyCoder->resetBits();
797    m_pcEntropyCoder->encodeSplitFlag( rpcBestCU, 0, uiDepth, true );
798    rpcBestCU->getTotalBits() += m_pcEntropyCoder->getNumberOfWrittenBits(); // split bits
799    if(m_pcEncCfg->getUseSBACRD())
800    {
801      rpcBestCU->getTotalBins() += ((TEncBinCABAC *)((TEncSbac*)m_pcEntropyCoder->m_pcEntropyCoderIf)->getEncBinIf())->getBinsCoded();
802    }
803    rpcBestCU->getTotalCost()  = m_pcRdCost->calcRdCost( rpcBestCU->getTotalBits(), rpcBestCU->getTotalDistortion() );
804
805    // accumulate statistics for early skip
806    if ( m_pcEncCfg->getUseFastEnc() )
807    {
808      if ( rpcBestCU->isSkipped(0) )
809      {
810        Int iIdx = g_aucConvertToBit[ rpcBestCU->getWidth(0) ];
811        afCost[ iIdx ] += rpcBestCU->getTotalCost();
812        aiNum [ iIdx ] ++;
813      }
814    }
815
816    // Early CU determination
817    if( m_pcEncCfg->getUseEarlyCU() && rpcBestCU->isSkipped(0) )
818    {
819      bSubBranch = false;
820    }
821    else
822    {
823      bSubBranch = true;
824    }
825  }
826  else if(!(bSliceEnd && bInsidePicture))
827  {
828    bBoundary = true;
829#if RATE_CONTROL_LAMBDA_DOMAIN && !M0036_RC_IMPROVEMENT
830    m_addSADDepth++;
831#endif
832  }
833
834  // copy orginal YUV samples to PCM buffer
835  if( rpcBestCU->isLosslessCoded(0) && (rpcBestCU->getIPCMFlag(0) == false))
836  {
837    xFillPCMBuffer(rpcBestCU, m_ppcOrigYuv[uiDepth]);
838  }
839  if( (g_uiMaxCUWidth>>uiDepth) == rpcTempCU->getSlice()->getPPS()->getMinCuDQPSize() )
840  {
841    Int idQP = m_pcEncCfg->getMaxDeltaQP();
842#if REPN_FORMAT_IN_VPS
843    iMinQP = Clip3( -rpcTempCU->getSlice()->getQpBDOffsetY(), MAX_QP, iBaseQP-idQP );
844    iMaxQP = Clip3( -rpcTempCU->getSlice()->getQpBDOffsetY(), MAX_QP, iBaseQP+idQP );
845#else
846    iMinQP = Clip3( -rpcTempCU->getSlice()->getSPS()->getQpBDOffsetY(), MAX_QP, iBaseQP-idQP );
847    iMaxQP = Clip3( -rpcTempCU->getSlice()->getSPS()->getQpBDOffsetY(), MAX_QP, iBaseQP+idQP );
848#endif
849    if ( (rpcTempCU->getSlice()->getSPS()->getUseLossless()) && (lowestQP < iMinQP) && rpcTempCU->getSlice()->getPPS()->getUseDQP() )
850    {
851      isAddLowestQP = true;
852      iMinQP = iMinQP - 1;     
853    }
854  }
855  else if( (g_uiMaxCUWidth>>uiDepth) > rpcTempCU->getSlice()->getPPS()->getMinCuDQPSize() )
856  {
857    iMinQP = iBaseQP;
858    iMaxQP = iBaseQP;
859  }
860  else
861  {
862    Int iStartQP;
863    if( pcPic->getCU( rpcTempCU->getAddr() )->getSliceSegmentStartCU(rpcTempCU->getZorderIdxInCU()) == pcSlice->getSliceSegmentCurStartCUAddr())
864    {
865      iStartQP = rpcTempCU->getQP(0);
866    }
867    else
868    {
869      UInt uiCurSliceStartPartIdx = pcSlice->getSliceSegmentCurStartCUAddr() % pcPic->getNumPartInCU() - rpcTempCU->getZorderIdxInCU();
870      iStartQP = rpcTempCU->getQP(uiCurSliceStartPartIdx);
871    }
872    iMinQP = iStartQP;
873    iMaxQP = iStartQP;
874  }
875#if RATE_CONTROL_LAMBDA_DOMAIN
876  if ( m_pcEncCfg->getUseRateCtrl() )
877  {
878    iMinQP = m_pcRateCtrl->getRCQP();
879    iMaxQP = m_pcRateCtrl->getRCQP();
880  }
881#else
882  if(m_pcEncCfg->getUseRateCtrl())
883  {
884    Int qp = m_pcRateCtrl->getUnitQP();
885    iMinQP  = Clip3( MIN_QP, MAX_QP, qp);
886    iMaxQP  = Clip3( MIN_QP, MAX_QP, qp);
887  }
888#endif
889  for (Int iQP=iMinQP; iQP<=iMaxQP; iQP++)
890  {
891    if (isAddLowestQP && (iQP == iMinQP))
892    {
893      iQP = lowestQP;
894    }
895    rpcTempCU->initEstData( uiDepth, iQP );
896
897    // further split
898    if( bSubBranch && bTrySplitDQP && uiDepth < g_uiMaxCUDepth - g_uiAddCUDepth )
899    {
900      UChar       uhNextDepth         = uiDepth+1;
901      TComDataCU* pcSubBestPartCU     = m_ppcBestCU[uhNextDepth];
902      TComDataCU* pcSubTempPartCU     = m_ppcTempCU[uhNextDepth];
903
904      for ( UInt uiPartUnitIdx = 0; uiPartUnitIdx < 4; uiPartUnitIdx++ )
905      {
906        pcSubBestPartCU->initSubCU( rpcTempCU, uiPartUnitIdx, uhNextDepth, iQP );           // clear sub partition datas or init.
907        pcSubTempPartCU->initSubCU( rpcTempCU, uiPartUnitIdx, uhNextDepth, iQP );           // clear sub partition datas or init.
908
909        Bool bInSlice = pcSubBestPartCU->getSCUAddr()+pcSubBestPartCU->getTotalNumPart()>pcSlice->getSliceSegmentCurStartCUAddr()&&pcSubBestPartCU->getSCUAddr()<pcSlice->getSliceSegmentCurEndCUAddr();
910#if REPN_FORMAT_IN_VPS
911        if(bInSlice && ( pcSubBestPartCU->getCUPelX() < pcSlice->getPicWidthInLumaSamples()           ) && ( pcSubBestPartCU->getCUPelY() < pcSlice->getPicHeightInLumaSamples()           ) )
912#else
913        if(bInSlice && ( pcSubBestPartCU->getCUPelX() < pcSlice->getSPS()->getPicWidthInLumaSamples() ) && ( pcSubBestPartCU->getCUPelY() < pcSlice->getSPS()->getPicHeightInLumaSamples() ) )
914#endif
915        {
916          if( m_bUseSBACRD )
917          {
918            if ( 0 == uiPartUnitIdx) //initialize RD with previous depth buffer
919            {
920              m_pppcRDSbacCoder[uhNextDepth][CI_CURR_BEST]->load(m_pppcRDSbacCoder[uiDepth][CI_CURR_BEST]);
921            }
922            else
923            {
924              m_pppcRDSbacCoder[uhNextDepth][CI_CURR_BEST]->load(m_pppcRDSbacCoder[uhNextDepth][CI_NEXT_BEST]);
925            }
926          }
927
928#if AMP_ENC_SPEEDUP
929          if ( rpcBestCU->isIntra(0) )
930          {
931            xCompressCU( pcSubBestPartCU, pcSubTempPartCU, uhNextDepth, SIZE_NONE );
932          }
933          else
934          {
935            xCompressCU( pcSubBestPartCU, pcSubTempPartCU, uhNextDepth, rpcBestCU->getPartitionSize(0) );
936          }
937#else
938          xCompressCU( pcSubBestPartCU, pcSubTempPartCU, uhNextDepth );
939#endif
940
941          rpcTempCU->copyPartFrom( pcSubBestPartCU, uiPartUnitIdx, uhNextDepth );         // Keep best part data to current temporary data.
942          xCopyYuv2Tmp( pcSubBestPartCU->getTotalNumPart()*uiPartUnitIdx, uhNextDepth );
943        }
944        else if (bInSlice)
945        {
946          pcSubBestPartCU->copyToPic( uhNextDepth );
947          rpcTempCU->copyPartFrom( pcSubBestPartCU, uiPartUnitIdx, uhNextDepth );
948        }
949      }
950
951      if( !bBoundary )
952      {
953        m_pcEntropyCoder->resetBits();
954        m_pcEntropyCoder->encodeSplitFlag( rpcTempCU, 0, uiDepth, true );
955
956        rpcTempCU->getTotalBits() += m_pcEntropyCoder->getNumberOfWrittenBits(); // split bits
957        if(m_pcEncCfg->getUseSBACRD())
958        {
959          rpcTempCU->getTotalBins() += ((TEncBinCABAC *)((TEncSbac*)m_pcEntropyCoder->m_pcEntropyCoderIf)->getEncBinIf())->getBinsCoded();
960        }
961      }
962      rpcTempCU->getTotalCost()  = m_pcRdCost->calcRdCost( rpcTempCU->getTotalBits(), rpcTempCU->getTotalDistortion() );
963
964      if( (g_uiMaxCUWidth>>uiDepth) == rpcTempCU->getSlice()->getPPS()->getMinCuDQPSize() && rpcTempCU->getSlice()->getPPS()->getUseDQP())
965      {
966        Bool hasResidual = false;
967        for( UInt uiBlkIdx = 0; uiBlkIdx < rpcTempCU->getTotalNumPart(); uiBlkIdx ++)
968        {
969          if( ( pcPic->getCU( rpcTempCU->getAddr() )->getSliceSegmentStartCU(uiBlkIdx+rpcTempCU->getZorderIdxInCU()) == rpcTempCU->getSlice()->getSliceSegmentCurStartCUAddr() ) && 
970              ( rpcTempCU->getCbf( uiBlkIdx, TEXT_LUMA ) || rpcTempCU->getCbf( uiBlkIdx, TEXT_CHROMA_U ) || rpcTempCU->getCbf( uiBlkIdx, TEXT_CHROMA_V ) ) )
971          {
972            hasResidual = true;
973            break;
974          }
975        }
976
977        UInt uiTargetPartIdx;
978        if ( pcPic->getCU( rpcTempCU->getAddr() )->getSliceSegmentStartCU(rpcTempCU->getZorderIdxInCU()) != pcSlice->getSliceSegmentCurStartCUAddr() )
979        {
980          uiTargetPartIdx = pcSlice->getSliceSegmentCurStartCUAddr() % pcPic->getNumPartInCU() - rpcTempCU->getZorderIdxInCU();
981        }
982        else
983        {
984          uiTargetPartIdx = 0;
985        }
986        if ( hasResidual )
987        {
988#if !RDO_WITHOUT_DQP_BITS
989          m_pcEntropyCoder->resetBits();
990          m_pcEntropyCoder->encodeQP( rpcTempCU, uiTargetPartIdx, false );
991          rpcTempCU->getTotalBits() += m_pcEntropyCoder->getNumberOfWrittenBits(); // dQP bits
992          if(m_pcEncCfg->getUseSBACRD())
993          {
994            rpcTempCU->getTotalBins() += ((TEncBinCABAC *)((TEncSbac*)m_pcEntropyCoder->m_pcEntropyCoderIf)->getEncBinIf())->getBinsCoded();
995          }
996          rpcTempCU->getTotalCost()  = m_pcRdCost->calcRdCost( rpcTempCU->getTotalBits(), rpcTempCU->getTotalDistortion() );
997#endif
998
999          Bool foundNonZeroCbf = false;
1000          rpcTempCU->setQPSubCUs( rpcTempCU->getRefQP( uiTargetPartIdx ), rpcTempCU, 0, uiDepth, foundNonZeroCbf );
1001          assert( foundNonZeroCbf );
1002        }
1003        else
1004        {
1005          rpcTempCU->setQPSubParts( rpcTempCU->getRefQP( uiTargetPartIdx ), 0, uiDepth ); // set QP to default QP
1006        }
1007      }
1008
1009      if( m_bUseSBACRD )
1010      {
1011        m_pppcRDSbacCoder[uhNextDepth][CI_NEXT_BEST]->store(m_pppcRDSbacCoder[uiDepth][CI_TEMP_BEST]);
1012      }
1013      Bool isEndOfSlice        = rpcBestCU->getSlice()->getSliceMode()==FIXED_NUMBER_OF_BYTES
1014                                 && (rpcBestCU->getTotalBits()>rpcBestCU->getSlice()->getSliceArgument()<<3);
1015      Bool isEndOfSliceSegment = rpcBestCU->getSlice()->getSliceSegmentMode()==FIXED_NUMBER_OF_BYTES
1016                                 && (rpcBestCU->getTotalBits()>rpcBestCU->getSlice()->getSliceSegmentArgument()<<3);
1017      if(isEndOfSlice||isEndOfSliceSegment)
1018      {
1019        rpcBestCU->getTotalCost()=rpcTempCU->getTotalCost()+1;
1020      }
1021      xCheckBestMode( rpcBestCU, rpcTempCU, uiDepth);                                  // RD compare current larger prediction
1022    }                                                                                  // with sub partitioned prediction.
1023    if (isAddLowestQP && (iQP == lowestQP))
1024    {
1025      iQP = iMinQP;
1026    }
1027  }
1028
1029  rpcBestCU->copyToPic(uiDepth);                                                     // Copy Best data to Picture for next partition prediction.
1030
1031  xCopyYuv2Pic( rpcBestCU->getPic(), rpcBestCU->getAddr(), rpcBestCU->getZorderIdxInCU(), uiDepth, uiDepth, rpcBestCU, uiLPelX, uiTPelY );   // Copy Yuv data to picture Yuv
1032  if( bBoundary ||(bSliceEnd && bInsidePicture))
1033  {
1034    return;
1035  }
1036
1037  // Assert if Best prediction mode is NONE
1038  // Selected mode's RD-cost must be not MAX_DOUBLE.
1039  assert( rpcBestCU->getPartitionSize ( 0 ) != SIZE_NONE  );
1040  assert( rpcBestCU->getPredictionMode( 0 ) != MODE_NONE  );
1041  assert( rpcBestCU->getTotalCost     (   ) != MAX_DOUBLE );
1042}
1043
1044/** finish encoding a cu and handle end-of-slice conditions
1045 * \param pcCU
1046 * \param uiAbsPartIdx
1047 * \param uiDepth
1048 * \returns Void
1049 */
1050Void TEncCu::finishCU( TComDataCU* pcCU, UInt uiAbsPartIdx, UInt uiDepth )
1051{
1052  TComPic* pcPic = pcCU->getPic();
1053  TComSlice * pcSlice = pcCU->getPic()->getSlice(pcCU->getPic()->getCurrSliceIdx());
1054
1055  //Calculate end address
1056  UInt uiCUAddr = pcCU->getSCUAddr()+uiAbsPartIdx;
1057
1058  UInt uiInternalAddress = pcPic->getPicSym()->getPicSCUAddr(pcSlice->getSliceSegmentCurEndCUAddr()-1) % pcPic->getNumPartInCU();
1059  UInt uiExternalAddress = pcPic->getPicSym()->getPicSCUAddr(pcSlice->getSliceSegmentCurEndCUAddr()-1) / pcPic->getNumPartInCU();
1060  UInt uiPosX = ( uiExternalAddress % pcPic->getFrameWidthInCU() ) * g_uiMaxCUWidth+ g_auiRasterToPelX[ g_auiZscanToRaster[uiInternalAddress] ];
1061  UInt uiPosY = ( uiExternalAddress / pcPic->getFrameWidthInCU() ) * g_uiMaxCUHeight+ g_auiRasterToPelY[ g_auiZscanToRaster[uiInternalAddress] ];
1062#if REPN_FORMAT_IN_VPS
1063  UInt uiWidth =  pcSlice->getPicWidthInLumaSamples();
1064  UInt uiHeight = pcSlice->getPicHeightInLumaSamples();
1065#else
1066  UInt uiWidth = pcSlice->getSPS()->getPicWidthInLumaSamples();
1067  UInt uiHeight = pcSlice->getSPS()->getPicHeightInLumaSamples();
1068#endif
1069  while(uiPosX>=uiWidth||uiPosY>=uiHeight)
1070  {
1071    uiInternalAddress--;
1072    uiPosX = ( uiExternalAddress % pcPic->getFrameWidthInCU() ) * g_uiMaxCUWidth+ g_auiRasterToPelX[ g_auiZscanToRaster[uiInternalAddress] ];
1073    uiPosY = ( uiExternalAddress / pcPic->getFrameWidthInCU() ) * g_uiMaxCUHeight+ g_auiRasterToPelY[ g_auiZscanToRaster[uiInternalAddress] ];
1074  }
1075  uiInternalAddress++;
1076  if(uiInternalAddress==pcCU->getPic()->getNumPartInCU())
1077  {
1078    uiInternalAddress = 0;
1079    uiExternalAddress = pcPic->getPicSym()->getCUOrderMap(pcPic->getPicSym()->getInverseCUOrderMap(uiExternalAddress)+1);
1080  }
1081  UInt uiRealEndAddress = pcPic->getPicSym()->getPicSCUEncOrder(uiExternalAddress*pcPic->getNumPartInCU()+uiInternalAddress);
1082
1083  // Encode slice finish
1084  Bool bTerminateSlice = false;
1085  if (uiCUAddr+(pcCU->getPic()->getNumPartInCU()>>(uiDepth<<1)) == uiRealEndAddress)
1086  {
1087    bTerminateSlice = true;
1088  }
1089  UInt uiGranularityWidth = g_uiMaxCUWidth;
1090  uiPosX = pcCU->getCUPelX() + g_auiRasterToPelX[ g_auiZscanToRaster[uiAbsPartIdx] ];
1091  uiPosY = pcCU->getCUPelY() + g_auiRasterToPelY[ g_auiZscanToRaster[uiAbsPartIdx] ];
1092  Bool granularityBoundary=((uiPosX+pcCU->getWidth(uiAbsPartIdx))%uiGranularityWidth==0||(uiPosX+pcCU->getWidth(uiAbsPartIdx)==uiWidth))
1093    &&((uiPosY+pcCU->getHeight(uiAbsPartIdx))%uiGranularityWidth==0||(uiPosY+pcCU->getHeight(uiAbsPartIdx)==uiHeight));
1094 
1095  if(granularityBoundary)
1096  {
1097    // The 1-terminating bit is added to all streams, so don't add it here when it's 1.
1098    if (!bTerminateSlice)
1099      m_pcEntropyCoder->encodeTerminatingBit( bTerminateSlice ? 1 : 0 );
1100  }
1101 
1102  Int numberOfWrittenBits = 0;
1103  if (m_pcBitCounter)
1104  {
1105    numberOfWrittenBits = m_pcEntropyCoder->getNumberOfWrittenBits();
1106  }
1107 
1108  // Calculate slice end IF this CU puts us over slice bit size.
1109  UInt iGranularitySize = pcCU->getPic()->getNumPartInCU();
1110  Int iGranularityEnd = ((pcCU->getSCUAddr()+uiAbsPartIdx)/iGranularitySize)*iGranularitySize;
1111  if(iGranularityEnd<=pcSlice->getSliceSegmentCurStartCUAddr()) 
1112  {
1113    iGranularityEnd+=max(iGranularitySize,(pcCU->getPic()->getNumPartInCU()>>(uiDepth<<1)));
1114  }
1115  // Set slice end parameter
1116  if(pcSlice->getSliceMode()==FIXED_NUMBER_OF_BYTES&&!pcSlice->getFinalized()&&pcSlice->getSliceBits()+numberOfWrittenBits>pcSlice->getSliceArgument()<<3) 
1117  {
1118    pcSlice->setSliceSegmentCurEndCUAddr(iGranularityEnd);
1119    pcSlice->setSliceCurEndCUAddr(iGranularityEnd);
1120    return;
1121  }
1122  // Set dependent slice end parameter
1123  if(pcSlice->getSliceSegmentMode()==FIXED_NUMBER_OF_BYTES&&!pcSlice->getFinalized()&&pcSlice->getSliceSegmentBits()+numberOfWrittenBits > pcSlice->getSliceSegmentArgument()<<3) 
1124  {
1125    pcSlice->setSliceSegmentCurEndCUAddr(iGranularityEnd);
1126    return;
1127  }
1128  if(granularityBoundary)
1129  {
1130    pcSlice->setSliceBits( (UInt)(pcSlice->getSliceBits() + numberOfWrittenBits) );
1131    pcSlice->setSliceSegmentBits(pcSlice->getSliceSegmentBits()+numberOfWrittenBits);
1132    if (m_pcBitCounter)
1133    {
1134      m_pcEntropyCoder->resetBits();     
1135    }
1136  }
1137}
1138
1139/** Compute QP for each CU
1140 * \param pcCU Target CU
1141 * \param uiDepth CU depth
1142 * \returns quantization parameter
1143 */
1144Int TEncCu::xComputeQP( TComDataCU* pcCU, UInt uiDepth )
1145{
1146  Int iBaseQp = pcCU->getSlice()->getSliceQp();
1147  Int iQpOffset = 0;
1148  if ( m_pcEncCfg->getUseAdaptiveQP() )
1149  {
1150    TEncPic* pcEPic = dynamic_cast<TEncPic*>( pcCU->getPic() );
1151    UInt uiAQDepth = min( uiDepth, pcEPic->getMaxAQDepth()-1 );
1152    TEncPicQPAdaptationLayer* pcAQLayer = pcEPic->getAQLayer( uiAQDepth );
1153    UInt uiAQUPosX = pcCU->getCUPelX() / pcAQLayer->getAQPartWidth();
1154    UInt uiAQUPosY = pcCU->getCUPelY() / pcAQLayer->getAQPartHeight();
1155    UInt uiAQUStride = pcAQLayer->getAQPartStride();
1156    TEncQPAdaptationUnit* acAQU = pcAQLayer->getQPAdaptationUnit();
1157
1158    Double dMaxQScale = pow(2.0, m_pcEncCfg->getQPAdaptationRange()/6.0);
1159    Double dAvgAct = pcAQLayer->getAvgActivity();
1160    Double dCUAct = acAQU[uiAQUPosY * uiAQUStride + uiAQUPosX].getActivity();
1161    Double dNormAct = (dMaxQScale*dCUAct + dAvgAct) / (dCUAct + dMaxQScale*dAvgAct);
1162    Double dQpOffset = log(dNormAct) / log(2.0) * 6.0;
1163    iQpOffset = Int(floor( dQpOffset + 0.49999 ));
1164  }
1165#if REPN_FORMAT_IN_VPS
1166  return Clip3(-pcCU->getSlice()->getQpBDOffsetY(), MAX_QP, iBaseQp+iQpOffset );
1167#else
1168  return Clip3(-pcCU->getSlice()->getSPS()->getQpBDOffsetY(), MAX_QP, iBaseQp+iQpOffset );
1169#endif
1170}
1171
1172/** encode a CU block recursively
1173 * \param pcCU
1174 * \param uiAbsPartIdx
1175 * \param uiDepth
1176 * \returns Void
1177 */
1178Void TEncCu::xEncodeCU( TComDataCU* pcCU, UInt uiAbsPartIdx, UInt uiDepth )
1179{
1180  TComPic* pcPic = pcCU->getPic();
1181 
1182  Bool bBoundary = false;
1183  UInt uiLPelX   = pcCU->getCUPelX() + g_auiRasterToPelX[ g_auiZscanToRaster[uiAbsPartIdx] ];
1184  UInt uiRPelX   = uiLPelX + (g_uiMaxCUWidth>>uiDepth)  - 1;
1185  UInt uiTPelY   = pcCU->getCUPelY() + g_auiRasterToPelY[ g_auiZscanToRaster[uiAbsPartIdx] ];
1186  UInt uiBPelY   = uiTPelY + (g_uiMaxCUHeight>>uiDepth) - 1;
1187 
1188  TComSlice * pcSlice = pcCU->getPic()->getSlice(pcCU->getPic()->getCurrSliceIdx());
1189  // If slice start is within this cu...
1190  Bool bSliceStart = pcSlice->getSliceSegmentCurStartCUAddr() > pcPic->getPicSym()->getInverseCUOrderMap(pcCU->getAddr())*pcCU->getPic()->getNumPartInCU()+uiAbsPartIdx && 
1191    pcSlice->getSliceSegmentCurStartCUAddr() < pcPic->getPicSym()->getInverseCUOrderMap(pcCU->getAddr())*pcCU->getPic()->getNumPartInCU()+uiAbsPartIdx+( pcPic->getNumPartInCU() >> (uiDepth<<1) );
1192  // We need to split, so don't try these modes.
1193#if REPN_FORMAT_IN_VPS
1194  if(!bSliceStart&&( uiRPelX < pcSlice->getPicWidthInLumaSamples()           ) && ( uiBPelY < pcSlice->getPicHeightInLumaSamples()           ) )
1195#else
1196  if(!bSliceStart&&( uiRPelX < pcSlice->getSPS()->getPicWidthInLumaSamples() ) && ( uiBPelY < pcSlice->getSPS()->getPicHeightInLumaSamples() ) )
1197#endif
1198  {
1199    m_pcEntropyCoder->encodeSplitFlag( pcCU, uiAbsPartIdx, uiDepth );
1200  }
1201  else
1202  {
1203    bBoundary = true;
1204  }
1205 
1206  if( ( ( uiDepth < pcCU->getDepth( uiAbsPartIdx ) ) && ( uiDepth < (g_uiMaxCUDepth-g_uiAddCUDepth) ) ) || bBoundary )
1207  {
1208    UInt uiQNumParts = ( pcPic->getNumPartInCU() >> (uiDepth<<1) )>>2;
1209    if( (g_uiMaxCUWidth>>uiDepth) == pcCU->getSlice()->getPPS()->getMinCuDQPSize() && pcCU->getSlice()->getPPS()->getUseDQP())
1210    {
1211      setdQPFlag(true);
1212    }
1213    for ( UInt uiPartUnitIdx = 0; uiPartUnitIdx < 4; uiPartUnitIdx++, uiAbsPartIdx+=uiQNumParts )
1214    {
1215      uiLPelX   = pcCU->getCUPelX() + g_auiRasterToPelX[ g_auiZscanToRaster[uiAbsPartIdx] ];
1216      uiTPelY   = pcCU->getCUPelY() + g_auiRasterToPelY[ g_auiZscanToRaster[uiAbsPartIdx] ];
1217      Bool bInSlice = pcCU->getSCUAddr()+uiAbsPartIdx+uiQNumParts>pcSlice->getSliceSegmentCurStartCUAddr()&&pcCU->getSCUAddr()+uiAbsPartIdx<pcSlice->getSliceSegmentCurEndCUAddr();
1218#if REPN_FORMAT_IN_VPS
1219      if(bInSlice&&( uiLPelX < pcSlice->getPicWidthInLumaSamples()           ) && ( uiTPelY < pcSlice->getPicHeightInLumaSamples()           ) )
1220#else
1221      if(bInSlice&&( uiLPelX < pcSlice->getSPS()->getPicWidthInLumaSamples() ) && ( uiTPelY < pcSlice->getSPS()->getPicHeightInLumaSamples() ) )
1222#endif
1223      {
1224        xEncodeCU( pcCU, uiAbsPartIdx, uiDepth+1 );
1225      }
1226    }
1227    return;
1228  }
1229 
1230  if( (g_uiMaxCUWidth>>uiDepth) >= pcCU->getSlice()->getPPS()->getMinCuDQPSize() && pcCU->getSlice()->getPPS()->getUseDQP())
1231  {
1232    setdQPFlag(true);
1233  }
1234  if (pcCU->getSlice()->getPPS()->getTransquantBypassEnableFlag())
1235  {
1236    m_pcEntropyCoder->encodeCUTransquantBypassFlag( pcCU, uiAbsPartIdx );
1237  }
1238  if( !pcCU->getSlice()->isIntra() )
1239  {
1240    m_pcEntropyCoder->encodeSkipFlag( pcCU, uiAbsPartIdx );
1241  }
1242 
1243  if( pcCU->isSkipped( uiAbsPartIdx ) )
1244  {
1245    m_pcEntropyCoder->encodeMergeIndex( pcCU, uiAbsPartIdx );
1246    finishCU(pcCU,uiAbsPartIdx,uiDepth);
1247    return;
1248  }
1249  m_pcEntropyCoder->encodePredMode( pcCU, uiAbsPartIdx );
1250 
1251  m_pcEntropyCoder->encodePartSize( pcCU, uiAbsPartIdx, uiDepth );
1252 
1253  if (pcCU->isIntra( uiAbsPartIdx ) && pcCU->getPartitionSize( uiAbsPartIdx ) == SIZE_2Nx2N )
1254  {
1255    m_pcEntropyCoder->encodeIPCMInfo( pcCU, uiAbsPartIdx );
1256
1257    if(pcCU->getIPCMFlag(uiAbsPartIdx))
1258    {
1259      // Encode slice finish
1260      finishCU(pcCU,uiAbsPartIdx,uiDepth);
1261      return;
1262    }
1263  }
1264
1265  // prediction Info ( Intra : direction mode, Inter : Mv, reference idx )
1266  m_pcEntropyCoder->encodePredInfo( pcCU, uiAbsPartIdx );
1267 
1268  // Encode Coefficients
1269  Bool bCodeDQP = getdQPFlag();
1270  m_pcEntropyCoder->encodeCoeff( pcCU, uiAbsPartIdx, uiDepth, pcCU->getWidth (uiAbsPartIdx), pcCU->getHeight(uiAbsPartIdx), bCodeDQP );
1271  setdQPFlag( bCodeDQP );
1272
1273  // --- write terminating bit ---
1274  finishCU(pcCU,uiAbsPartIdx,uiDepth);
1275}
1276
1277#if RATE_CONTROL_INTRA
1278Int xCalcHADs8x8_ISlice(Pel *piOrg, Int iStrideOrg) 
1279{
1280  Int k, i, j, jj;
1281  Int diff[64], m1[8][8], m2[8][8], m3[8][8], iSumHad = 0;
1282
1283  for( k = 0; k < 64; k += 8 )
1284  {
1285    diff[k+0] = piOrg[0] ;
1286    diff[k+1] = piOrg[1] ;
1287    diff[k+2] = piOrg[2] ;
1288    diff[k+3] = piOrg[3] ;
1289    diff[k+4] = piOrg[4] ;
1290    diff[k+5] = piOrg[5] ;
1291    diff[k+6] = piOrg[6] ;
1292    diff[k+7] = piOrg[7] ;
1293 
1294    piOrg += iStrideOrg;
1295  }
1296 
1297  //horizontal
1298  for (j=0; j < 8; j++)
1299  {
1300    jj = j << 3;
1301    m2[j][0] = diff[jj  ] + diff[jj+4];
1302    m2[j][1] = diff[jj+1] + diff[jj+5];
1303    m2[j][2] = diff[jj+2] + diff[jj+6];
1304    m2[j][3] = diff[jj+3] + diff[jj+7];
1305    m2[j][4] = diff[jj  ] - diff[jj+4];
1306    m2[j][5] = diff[jj+1] - diff[jj+5];
1307    m2[j][6] = diff[jj+2] - diff[jj+6];
1308    m2[j][7] = diff[jj+3] - diff[jj+7];
1309   
1310    m1[j][0] = m2[j][0] + m2[j][2];
1311    m1[j][1] = m2[j][1] + m2[j][3];
1312    m1[j][2] = m2[j][0] - m2[j][2];
1313    m1[j][3] = m2[j][1] - m2[j][3];
1314    m1[j][4] = m2[j][4] + m2[j][6];
1315    m1[j][5] = m2[j][5] + m2[j][7];
1316    m1[j][6] = m2[j][4] - m2[j][6];
1317    m1[j][7] = m2[j][5] - m2[j][7];
1318   
1319    m2[j][0] = m1[j][0] + m1[j][1];
1320    m2[j][1] = m1[j][0] - m1[j][1];
1321    m2[j][2] = m1[j][2] + m1[j][3];
1322    m2[j][3] = m1[j][2] - m1[j][3];
1323    m2[j][4] = m1[j][4] + m1[j][5];
1324    m2[j][5] = m1[j][4] - m1[j][5];
1325    m2[j][6] = m1[j][6] + m1[j][7];
1326    m2[j][7] = m1[j][6] - m1[j][7];
1327  }
1328 
1329  //vertical
1330  for (i=0; i < 8; i++)
1331  {
1332    m3[0][i] = m2[0][i] + m2[4][i];
1333    m3[1][i] = m2[1][i] + m2[5][i];
1334    m3[2][i] = m2[2][i] + m2[6][i];
1335    m3[3][i] = m2[3][i] + m2[7][i];
1336    m3[4][i] = m2[0][i] - m2[4][i];
1337    m3[5][i] = m2[1][i] - m2[5][i];
1338    m3[6][i] = m2[2][i] - m2[6][i];
1339    m3[7][i] = m2[3][i] - m2[7][i];
1340   
1341    m1[0][i] = m3[0][i] + m3[2][i];
1342    m1[1][i] = m3[1][i] + m3[3][i];
1343    m1[2][i] = m3[0][i] - m3[2][i];
1344    m1[3][i] = m3[1][i] - m3[3][i];
1345    m1[4][i] = m3[4][i] + m3[6][i];
1346    m1[5][i] = m3[5][i] + m3[7][i];
1347    m1[6][i] = m3[4][i] - m3[6][i];
1348    m1[7][i] = m3[5][i] - m3[7][i];
1349   
1350    m2[0][i] = m1[0][i] + m1[1][i];
1351    m2[1][i] = m1[0][i] - m1[1][i];
1352    m2[2][i] = m1[2][i] + m1[3][i];
1353    m2[3][i] = m1[2][i] - m1[3][i];
1354    m2[4][i] = m1[4][i] + m1[5][i];
1355    m2[5][i] = m1[4][i] - m1[5][i];
1356    m2[6][i] = m1[6][i] + m1[7][i];
1357    m2[7][i] = m1[6][i] - m1[7][i];
1358  }
1359 
1360  for (i = 0; i < 8; i++)
1361  {
1362    for (j = 0; j < 8; j++)
1363    {
1364      iSumHad += abs(m2[i][j]);
1365    }
1366  }
1367  iSumHad -= abs(m2[0][0]);
1368  iSumHad =(iSumHad+2)>>2;
1369  return(iSumHad);
1370}
1371
1372Int  TEncCu::updateLCUDataISlice(TComDataCU* pcCU, Int LCUIdx, Int width, Int height)
1373{
1374  Int  xBl, yBl; 
1375  const Int iBlkSize = 8;
1376
1377  Pel* pOrgInit   = pcCU->getPic()->getPicYuvOrg()->getLumaAddr(pcCU->getAddr(), 0);
1378  Int  iStrideOrig = pcCU->getPic()->getPicYuvOrg()->getStride();
1379  Pel  *pOrg;
1380
1381  Int iSumHad = 0;
1382  for ( yBl=0; (yBl+iBlkSize)<=height; yBl+= iBlkSize)
1383  {
1384    for ( xBl=0; (xBl+iBlkSize)<=width; xBl+= iBlkSize)
1385    {
1386      pOrg = pOrgInit + iStrideOrig*yBl + xBl; 
1387      iSumHad += xCalcHADs8x8_ISlice(pOrg, iStrideOrig);
1388    }
1389  }
1390  return(iSumHad);
1391}
1392#endif
1393
1394/** check RD costs for a CU block encoded with merge
1395 * \param rpcBestCU
1396 * \param rpcTempCU
1397 * \returns Void
1398 */
1399Void TEncCu::xCheckRDCostMerge2Nx2N( TComDataCU*& rpcBestCU, TComDataCU*& rpcTempCU, Bool *earlyDetectionSkipMode )
1400{
1401  assert( rpcTempCU->getSlice()->getSliceType() != I_SLICE );
1402  TComMvField  cMvFieldNeighbours[ 2 * MRG_MAX_NUM_CANDS ]; // double length for mv of both lists
1403  UChar uhInterDirNeighbours[MRG_MAX_NUM_CANDS];
1404  Int numValidMergeCand = 0;
1405
1406  for( UInt ui = 0; ui < rpcTempCU->getSlice()->getMaxNumMergeCand(); ++ui )
1407  {
1408    uhInterDirNeighbours[ui] = 0;
1409  }
1410  UChar uhDepth = rpcTempCU->getDepth( 0 );
1411  rpcTempCU->setPartSizeSubParts( SIZE_2Nx2N, 0, uhDepth ); // interprets depth relative to LCU level
1412  rpcTempCU->setCUTransquantBypassSubParts( m_pcEncCfg->getCUTransquantBypassFlagValue(), 0, uhDepth );
1413  rpcTempCU->getInterMergeCandidates( 0, 0, cMvFieldNeighbours,uhInterDirNeighbours, numValidMergeCand );
1414
1415  Int mergeCandBuffer[MRG_MAX_NUM_CANDS];
1416  for( UInt ui = 0; ui < numValidMergeCand; ++ui )
1417  {
1418    mergeCandBuffer[ui] = 0;
1419  }
1420
1421  Bool bestIsSkip = false;
1422
1423  UInt iteration;
1424  if ( rpcTempCU->isLosslessCoded(0))
1425  {
1426    iteration = 1;
1427  }
1428  else 
1429  {
1430    iteration = 2;
1431  }
1432
1433  for( UInt uiNoResidual = 0; uiNoResidual < iteration; ++uiNoResidual )
1434  {
1435    for( UInt uiMergeCand = 0; uiMergeCand < numValidMergeCand; ++uiMergeCand )
1436    {
1437#if REF_IDX_ME_ZEROMV
1438      Bool bZeroMVILR = rpcTempCU->xCheckZeroMVILRMerge(uhInterDirNeighbours[uiMergeCand], cMvFieldNeighbours[0 + 2*uiMergeCand], cMvFieldNeighbours[1 + 2*uiMergeCand]);
1439      if(bZeroMVILR)
1440      {
1441#endif
1442      if(!(uiNoResidual==1 && mergeCandBuffer[uiMergeCand]==1))
1443      {
1444        if( !(bestIsSkip && uiNoResidual == 0) )
1445        {
1446          // set MC parameters
1447          rpcTempCU->setPredModeSubParts( MODE_INTER, 0, uhDepth ); // interprets depth relative to LCU level
1448          rpcTempCU->setCUTransquantBypassSubParts( m_pcEncCfg->getCUTransquantBypassFlagValue(),     0, uhDepth );
1449          rpcTempCU->setPartSizeSubParts( SIZE_2Nx2N, 0, uhDepth ); // interprets depth relative to LCU level
1450          rpcTempCU->setMergeFlagSubParts( true, 0, 0, uhDepth ); // interprets depth relative to LCU level
1451          rpcTempCU->setMergeIndexSubParts( uiMergeCand, 0, 0, uhDepth ); // interprets depth relative to LCU level
1452          rpcTempCU->setInterDirSubParts( uhInterDirNeighbours[uiMergeCand], 0, 0, uhDepth ); // interprets depth relative to LCU level
1453          rpcTempCU->getCUMvField( REF_PIC_LIST_0 )->setAllMvField( cMvFieldNeighbours[0 + 2*uiMergeCand], SIZE_2Nx2N, 0, 0 ); // interprets depth relative to rpcTempCU level
1454          rpcTempCU->getCUMvField( REF_PIC_LIST_1 )->setAllMvField( cMvFieldNeighbours[1 + 2*uiMergeCand], SIZE_2Nx2N, 0, 0 ); // interprets depth relative to rpcTempCU level
1455         
1456          // do MC
1457          m_pcPredSearch->motionCompensation ( rpcTempCU, m_ppcPredYuvTemp[uhDepth] );
1458          // estimate residual and encode everything
1459          m_pcPredSearch->encodeResAndCalcRdInterCU( rpcTempCU,
1460                                                    m_ppcOrigYuv    [uhDepth],
1461                                                    m_ppcPredYuvTemp[uhDepth],
1462                                                    m_ppcResiYuvTemp[uhDepth],
1463                                                    m_ppcResiYuvBest[uhDepth],
1464                                                    m_ppcRecoYuvTemp[uhDepth],
1465                                                    (uiNoResidual? true:false));
1466         
1467         
1468          if ( uiNoResidual == 0 && rpcTempCU->getQtRootCbf(0) == 0 )
1469          {
1470            // If no residual when allowing for one, then set mark to not try case where residual is forced to 0
1471            mergeCandBuffer[uiMergeCand] = 1;
1472          }
1473         
1474          rpcTempCU->setSkipFlagSubParts( rpcTempCU->getQtRootCbf(0) == 0, 0, uhDepth );
1475          Int orgQP = rpcTempCU->getQP( 0 );
1476          xCheckDQP( rpcTempCU );
1477          xCheckBestMode(rpcBestCU, rpcTempCU, uhDepth);
1478          rpcTempCU->initEstData( uhDepth, orgQP );
1479         
1480          if( m_pcEncCfg->getUseFastDecisionForMerge() && !bestIsSkip )
1481          {
1482            bestIsSkip = rpcBestCU->getQtRootCbf(0) == 0;
1483          }
1484        }
1485#if REF_IDX_ME_ZEROMV
1486        }
1487#endif
1488      }
1489  }
1490
1491  if(uiNoResidual == 0 && m_pcEncCfg->getUseEarlySkipDetection())
1492  {
1493    if(rpcBestCU->getQtRootCbf( 0 ) == 0)
1494    {
1495      if( rpcBestCU->getMergeFlag( 0 ))
1496      {
1497        *earlyDetectionSkipMode = true;
1498      }
1499      else
1500      {
1501        Int absoulte_MV=0;
1502        for ( UInt uiRefListIdx = 0; uiRefListIdx < 2; uiRefListIdx++ )
1503        {
1504          if ( rpcBestCU->getSlice()->getNumRefIdx( RefPicList( uiRefListIdx ) ) > 0 )
1505          {
1506            TComCUMvField* pcCUMvField = rpcBestCU->getCUMvField(RefPicList( uiRefListIdx ));
1507            Int iHor = pcCUMvField->getMvd( 0 ).getAbsHor();
1508            Int iVer = pcCUMvField->getMvd( 0 ).getAbsVer();
1509            absoulte_MV+=iHor+iVer;
1510          }
1511        }
1512
1513        if(absoulte_MV == 0)
1514        {
1515          *earlyDetectionSkipMode = true;
1516        }
1517      }
1518    }
1519  }
1520 }
1521}
1522
1523
1524#if AMP_MRG
1525Void TEncCu::xCheckRDCostInter( TComDataCU*& rpcBestCU, TComDataCU*& rpcTempCU, PartSize ePartSize, Bool bUseMRG)
1526#else
1527Void TEncCu::xCheckRDCostInter( TComDataCU*& rpcBestCU, TComDataCU*& rpcTempCU, PartSize ePartSize )
1528#endif
1529{
1530  UChar uhDepth = rpcTempCU->getDepth( 0 );
1531 
1532  rpcTempCU->setDepthSubParts( uhDepth, 0 );
1533 
1534  rpcTempCU->setSkipFlagSubParts( false, 0, uhDepth );
1535
1536  rpcTempCU->setPartSizeSubParts  ( ePartSize,  0, uhDepth );
1537  rpcTempCU->setPredModeSubParts  ( MODE_INTER, 0, uhDepth );
1538  rpcTempCU->setCUTransquantBypassSubParts  ( m_pcEncCfg->getCUTransquantBypassFlagValue(),      0, uhDepth );
1539 
1540#if AMP_MRG
1541  rpcTempCU->setMergeAMP (true);
1542  m_pcPredSearch->predInterSearch ( rpcTempCU, m_ppcOrigYuv[uhDepth], m_ppcPredYuvTemp[uhDepth], m_ppcResiYuvTemp[uhDepth], m_ppcRecoYuvTemp[uhDepth], false, bUseMRG );
1543#else 
1544  m_pcPredSearch->predInterSearch ( rpcTempCU, m_ppcOrigYuv[uhDepth], m_ppcPredYuvTemp[uhDepth], m_ppcResiYuvTemp[uhDepth], m_ppcRecoYuvTemp[uhDepth] );
1545#endif
1546
1547#if AMP_MRG
1548  if ( !rpcTempCU->getMergeAMP() )
1549  {
1550    return;
1551  }
1552#endif
1553
1554#if RATE_CONTROL_LAMBDA_DOMAIN && !M0036_RC_IMPROVEMENT
1555  if ( m_pcEncCfg->getUseRateCtrl() && m_pcEncCfg->getLCULevelRC() && ePartSize == SIZE_2Nx2N && uhDepth <= m_addSADDepth )
1556  {
1557    UInt SAD = m_pcRdCost->getSADPart( g_bitDepthY, m_ppcPredYuvTemp[uhDepth]->getLumaAddr(), m_ppcPredYuvTemp[uhDepth]->getStride(),
1558      m_ppcOrigYuv[uhDepth]->getLumaAddr(), m_ppcOrigYuv[uhDepth]->getStride(),
1559      rpcTempCU->getWidth(0), rpcTempCU->getHeight(0) );
1560    m_temporalSAD = (Int)SAD;
1561  }
1562#endif
1563
1564  m_pcPredSearch->encodeResAndCalcRdInterCU( rpcTempCU, m_ppcOrigYuv[uhDepth], m_ppcPredYuvTemp[uhDepth], m_ppcResiYuvTemp[uhDepth], m_ppcResiYuvBest[uhDepth], m_ppcRecoYuvTemp[uhDepth], false );
1565  rpcTempCU->getTotalCost()  = m_pcRdCost->calcRdCost( rpcTempCU->getTotalBits(), rpcTempCU->getTotalDistortion() );
1566
1567  xCheckDQP( rpcTempCU );
1568  xCheckBestMode(rpcBestCU, rpcTempCU, uhDepth);
1569}
1570
1571Void TEncCu::xCheckRDCostIntra( TComDataCU*& rpcBestCU, TComDataCU*& rpcTempCU, PartSize eSize )
1572{
1573  UInt uiDepth = rpcTempCU->getDepth( 0 );
1574 
1575  rpcTempCU->setSkipFlagSubParts( false, 0, uiDepth );
1576
1577  rpcTempCU->setPartSizeSubParts( eSize, 0, uiDepth );
1578  rpcTempCU->setPredModeSubParts( MODE_INTRA, 0, uiDepth );
1579  rpcTempCU->setCUTransquantBypassSubParts( m_pcEncCfg->getCUTransquantBypassFlagValue(), 0, uiDepth );
1580 
1581  Bool bSeparateLumaChroma = true; // choose estimation mode
1582  UInt uiPreCalcDistC      = 0;
1583  if( !bSeparateLumaChroma )
1584  {
1585    m_pcPredSearch->preestChromaPredMode( rpcTempCU, m_ppcOrigYuv[uiDepth], m_ppcPredYuvTemp[uiDepth] );
1586  }
1587  m_pcPredSearch  ->estIntraPredQT      ( rpcTempCU, m_ppcOrigYuv[uiDepth], m_ppcPredYuvTemp[uiDepth], m_ppcResiYuvTemp[uiDepth], m_ppcRecoYuvTemp[uiDepth], uiPreCalcDistC, bSeparateLumaChroma );
1588
1589  m_ppcRecoYuvTemp[uiDepth]->copyToPicLuma(rpcTempCU->getPic()->getPicYuvRec(), rpcTempCU->getAddr(), rpcTempCU->getZorderIdxInCU() );
1590 
1591  m_pcPredSearch  ->estIntraPredChromaQT( rpcTempCU, m_ppcOrigYuv[uiDepth], m_ppcPredYuvTemp[uiDepth], m_ppcResiYuvTemp[uiDepth], m_ppcRecoYuvTemp[uiDepth], uiPreCalcDistC );
1592 
1593  m_pcEntropyCoder->resetBits();
1594
1595  if ( rpcTempCU->getSlice()->getPPS()->getTransquantBypassEnableFlag())
1596  {
1597    m_pcEntropyCoder->encodeCUTransquantBypassFlag( rpcTempCU, 0,          true );
1598  }
1599  m_pcEntropyCoder->encodeSkipFlag ( rpcTempCU, 0,          true );
1600  m_pcEntropyCoder->encodePredMode( rpcTempCU, 0,          true );
1601  m_pcEntropyCoder->encodePartSize( rpcTempCU, 0, uiDepth, true );
1602  m_pcEntropyCoder->encodePredInfo( rpcTempCU, 0,          true );
1603  m_pcEntropyCoder->encodeIPCMInfo(rpcTempCU, 0, true );
1604
1605  // Encode Coefficients
1606  Bool bCodeDQP = getdQPFlag();
1607  m_pcEntropyCoder->encodeCoeff( rpcTempCU, 0, uiDepth, rpcTempCU->getWidth (0), rpcTempCU->getHeight(0), bCodeDQP );
1608  setdQPFlag( bCodeDQP );
1609 
1610  if( m_bUseSBACRD ) m_pcRDGoOnSbacCoder->store(m_pppcRDSbacCoder[uiDepth][CI_TEMP_BEST]);
1611 
1612  rpcTempCU->getTotalBits() = m_pcEntropyCoder->getNumberOfWrittenBits();
1613  if(m_pcEncCfg->getUseSBACRD())
1614  {
1615    rpcTempCU->getTotalBins() = ((TEncBinCABAC *)((TEncSbac*)m_pcEntropyCoder->m_pcEntropyCoderIf)->getEncBinIf())->getBinsCoded();
1616  }
1617  rpcTempCU->getTotalCost() = m_pcRdCost->calcRdCost( rpcTempCU->getTotalBits(), rpcTempCU->getTotalDistortion() );
1618 
1619  xCheckDQP( rpcTempCU );
1620  xCheckBestMode(rpcBestCU, rpcTempCU, uiDepth);
1621}
1622
1623/** Check R-D costs for a CU with PCM mode.
1624 * \param rpcBestCU pointer to best mode CU data structure
1625 * \param rpcTempCU pointer to testing mode CU data structure
1626 * \returns Void
1627 *
1628 * \note Current PCM implementation encodes sample values in a lossless way. The distortion of PCM mode CUs are zero. PCM mode is selected if the best mode yields bits greater than that of PCM mode.
1629 */
1630Void TEncCu::xCheckIntraPCM( TComDataCU*& rpcBestCU, TComDataCU*& rpcTempCU )
1631{
1632  UInt uiDepth = rpcTempCU->getDepth( 0 );
1633
1634  rpcTempCU->setSkipFlagSubParts( false, 0, uiDepth );
1635
1636  rpcTempCU->setIPCMFlag(0, true);
1637  rpcTempCU->setIPCMFlagSubParts (true, 0, rpcTempCU->getDepth(0));
1638  rpcTempCU->setPartSizeSubParts( SIZE_2Nx2N, 0, uiDepth );
1639  rpcTempCU->setPredModeSubParts( MODE_INTRA, 0, uiDepth );
1640  rpcTempCU->setTrIdxSubParts ( 0, 0, uiDepth );
1641  rpcTempCU->setCUTransquantBypassSubParts( m_pcEncCfg->getCUTransquantBypassFlagValue(), 0, uiDepth );
1642
1643  m_pcPredSearch->IPCMSearch( rpcTempCU, m_ppcOrigYuv[uiDepth], m_ppcPredYuvTemp[uiDepth], m_ppcResiYuvTemp[uiDepth], m_ppcRecoYuvTemp[uiDepth]);
1644
1645  if( m_bUseSBACRD ) m_pcRDGoOnSbacCoder->load(m_pppcRDSbacCoder[uiDepth][CI_CURR_BEST]);
1646
1647  m_pcEntropyCoder->resetBits();
1648
1649  if ( rpcTempCU->getSlice()->getPPS()->getTransquantBypassEnableFlag())
1650  {
1651    m_pcEntropyCoder->encodeCUTransquantBypassFlag( rpcTempCU, 0,          true );
1652  }
1653  m_pcEntropyCoder->encodeSkipFlag ( rpcTempCU, 0,          true );
1654  m_pcEntropyCoder->encodePredMode ( rpcTempCU, 0,          true );
1655  m_pcEntropyCoder->encodePartSize ( rpcTempCU, 0, uiDepth, true );
1656  m_pcEntropyCoder->encodeIPCMInfo ( rpcTempCU, 0, true );
1657
1658  if( m_bUseSBACRD ) m_pcRDGoOnSbacCoder->store(m_pppcRDSbacCoder[uiDepth][CI_TEMP_BEST]);
1659
1660  rpcTempCU->getTotalBits() = m_pcEntropyCoder->getNumberOfWrittenBits();
1661  if(m_pcEncCfg->getUseSBACRD())
1662  {
1663    rpcTempCU->getTotalBins() = ((TEncBinCABAC *)((TEncSbac*)m_pcEntropyCoder->m_pcEntropyCoderIf)->getEncBinIf())->getBinsCoded();
1664  }
1665  rpcTempCU->getTotalCost() = m_pcRdCost->calcRdCost( rpcTempCU->getTotalBits(), rpcTempCU->getTotalDistortion() );
1666
1667  xCheckDQP( rpcTempCU );
1668  xCheckBestMode( rpcBestCU, rpcTempCU, uiDepth );
1669}
1670
1671/** check whether current try is the best with identifying the depth of current try
1672 * \param rpcBestCU
1673 * \param rpcTempCU
1674 * \returns Void
1675 */
1676Void TEncCu::xCheckBestMode( TComDataCU*& rpcBestCU, TComDataCU*& rpcTempCU, UInt uiDepth )
1677{
1678  if( rpcTempCU->getTotalCost() < rpcBestCU->getTotalCost() )
1679  {
1680    TComYuv* pcYuv;
1681    // Change Information data
1682    TComDataCU* pcCU = rpcBestCU;
1683    rpcBestCU = rpcTempCU;
1684    rpcTempCU = pcCU;
1685
1686    // Change Prediction data
1687    pcYuv = m_ppcPredYuvBest[uiDepth];
1688    m_ppcPredYuvBest[uiDepth] = m_ppcPredYuvTemp[uiDepth];
1689    m_ppcPredYuvTemp[uiDepth] = pcYuv;
1690
1691    // Change Reconstruction data
1692    pcYuv = m_ppcRecoYuvBest[uiDepth];
1693    m_ppcRecoYuvBest[uiDepth] = m_ppcRecoYuvTemp[uiDepth];
1694    m_ppcRecoYuvTemp[uiDepth] = pcYuv;
1695
1696    pcYuv = NULL;
1697    pcCU  = NULL;
1698
1699    if( m_bUseSBACRD )  // store temp best CI for next CU coding
1700      m_pppcRDSbacCoder[uiDepth][CI_TEMP_BEST]->store(m_pppcRDSbacCoder[uiDepth][CI_NEXT_BEST]);
1701  }
1702}
1703
1704Void TEncCu::xCheckDQP( TComDataCU* pcCU )
1705{
1706  UInt uiDepth = pcCU->getDepth( 0 );
1707
1708  if( pcCU->getSlice()->getPPS()->getUseDQP() && (g_uiMaxCUWidth>>uiDepth) >= pcCU->getSlice()->getPPS()->getMinCuDQPSize() )
1709  {
1710    if ( pcCU->getCbf( 0, TEXT_LUMA, 0 ) || pcCU->getCbf( 0, TEXT_CHROMA_U, 0 ) || pcCU->getCbf( 0, TEXT_CHROMA_V, 0 ) )
1711    {
1712#if !RDO_WITHOUT_DQP_BITS
1713      m_pcEntropyCoder->resetBits();
1714      m_pcEntropyCoder->encodeQP( pcCU, 0, false );
1715      pcCU->getTotalBits() += m_pcEntropyCoder->getNumberOfWrittenBits(); // dQP bits
1716      if(m_pcEncCfg->getUseSBACRD())
1717      {
1718        pcCU->getTotalBins() += ((TEncBinCABAC *)((TEncSbac*)m_pcEntropyCoder->m_pcEntropyCoderIf)->getEncBinIf())->getBinsCoded();
1719      }
1720      pcCU->getTotalCost() = m_pcRdCost->calcRdCost( pcCU->getTotalBits(), pcCU->getTotalDistortion() );
1721#endif
1722    }
1723    else
1724    {
1725      pcCU->setQPSubParts( pcCU->getRefQP( 0 ), 0, uiDepth ); // set QP to default QP
1726    }
1727  }
1728}
1729
1730Void TEncCu::xCopyAMVPInfo (AMVPInfo* pSrc, AMVPInfo* pDst)
1731{
1732  pDst->iN = pSrc->iN;
1733  for (Int i = 0; i < pSrc->iN; i++)
1734  {
1735    pDst->m_acMvCand[i] = pSrc->m_acMvCand[i];
1736  }
1737}
1738Void TEncCu::xCopyYuv2Pic(TComPic* rpcPic, UInt uiCUAddr, UInt uiAbsPartIdx, UInt uiDepth, UInt uiSrcDepth, TComDataCU* pcCU, UInt uiLPelX, UInt uiTPelY )
1739{
1740  UInt uiRPelX   = uiLPelX + (g_uiMaxCUWidth>>uiDepth)  - 1;
1741  UInt uiBPelY   = uiTPelY + (g_uiMaxCUHeight>>uiDepth) - 1;
1742  TComSlice * pcSlice = pcCU->getPic()->getSlice(pcCU->getPic()->getCurrSliceIdx());
1743  Bool bSliceStart = pcSlice->getSliceSegmentCurStartCUAddr() > rpcPic->getPicSym()->getInverseCUOrderMap(pcCU->getAddr())*pcCU->getPic()->getNumPartInCU()+uiAbsPartIdx && 
1744    pcSlice->getSliceSegmentCurStartCUAddr() < rpcPic->getPicSym()->getInverseCUOrderMap(pcCU->getAddr())*pcCU->getPic()->getNumPartInCU()+uiAbsPartIdx+( pcCU->getPic()->getNumPartInCU() >> (uiDepth<<1) );
1745  Bool bSliceEnd   = pcSlice->getSliceSegmentCurEndCUAddr() > rpcPic->getPicSym()->getInverseCUOrderMap(pcCU->getAddr())*pcCU->getPic()->getNumPartInCU()+uiAbsPartIdx && 
1746    pcSlice->getSliceSegmentCurEndCUAddr() < rpcPic->getPicSym()->getInverseCUOrderMap(pcCU->getAddr())*pcCU->getPic()->getNumPartInCU()+uiAbsPartIdx+( pcCU->getPic()->getNumPartInCU() >> (uiDepth<<1) );
1747#if REPN_FORMAT_IN_VPS
1748  if(!bSliceEnd && !bSliceStart && ( uiRPelX < pcSlice->getPicWidthInLumaSamples()           ) && ( uiBPelY < pcSlice->getPicHeightInLumaSamples()           ) )
1749#else
1750  if(!bSliceEnd && !bSliceStart && ( uiRPelX < pcSlice->getSPS()->getPicWidthInLumaSamples() ) && ( uiBPelY < pcSlice->getSPS()->getPicHeightInLumaSamples() ) )
1751#endif
1752  {
1753    UInt uiAbsPartIdxInRaster = g_auiZscanToRaster[uiAbsPartIdx];
1754    UInt uiSrcBlkWidth = rpcPic->getNumPartInWidth() >> (uiSrcDepth);
1755    UInt uiBlkWidth    = rpcPic->getNumPartInWidth() >> (uiDepth);
1756    UInt uiPartIdxX = ( ( uiAbsPartIdxInRaster % rpcPic->getNumPartInWidth() ) % uiSrcBlkWidth) / uiBlkWidth;
1757    UInt uiPartIdxY = ( ( uiAbsPartIdxInRaster / rpcPic->getNumPartInWidth() ) % uiSrcBlkWidth) / uiBlkWidth;
1758    UInt uiPartIdx = uiPartIdxY * ( uiSrcBlkWidth / uiBlkWidth ) + uiPartIdxX;
1759    m_ppcRecoYuvBest[uiSrcDepth]->copyToPicYuv( rpcPic->getPicYuvRec (), uiCUAddr, uiAbsPartIdx, uiDepth - uiSrcDepth, uiPartIdx);
1760  }
1761  else
1762  {
1763    UInt uiQNumParts = ( pcCU->getPic()->getNumPartInCU() >> (uiDepth<<1) )>>2;
1764
1765    for ( UInt uiPartUnitIdx = 0; uiPartUnitIdx < 4; uiPartUnitIdx++, uiAbsPartIdx+=uiQNumParts )
1766    {
1767      UInt uiSubCULPelX   = uiLPelX + ( g_uiMaxCUWidth >>(uiDepth+1) )*( uiPartUnitIdx &  1 );
1768      UInt uiSubCUTPelY   = uiTPelY + ( g_uiMaxCUHeight>>(uiDepth+1) )*( uiPartUnitIdx >> 1 );
1769
1770      Bool bInSlice = rpcPic->getPicSym()->getInverseCUOrderMap(pcCU->getAddr())*pcCU->getPic()->getNumPartInCU()+uiAbsPartIdx+uiQNumParts > pcSlice->getSliceSegmentCurStartCUAddr() && 
1771        rpcPic->getPicSym()->getInverseCUOrderMap(pcCU->getAddr())*pcCU->getPic()->getNumPartInCU()+uiAbsPartIdx < pcSlice->getSliceSegmentCurEndCUAddr();
1772#if REPN_FORMAT_IN_VPS
1773      if(bInSlice&&( uiSubCULPelX < pcSlice->getPicWidthInLumaSamples()           ) && ( uiSubCUTPelY < pcSlice->getPicHeightInLumaSamples()           ) )
1774#else
1775      if(bInSlice&&( uiSubCULPelX < pcSlice->getSPS()->getPicWidthInLumaSamples() ) && ( uiSubCUTPelY < pcSlice->getSPS()->getPicHeightInLumaSamples() ) )
1776#endif
1777      {
1778        xCopyYuv2Pic( rpcPic, uiCUAddr, uiAbsPartIdx, uiDepth+1, uiSrcDepth, pcCU, uiSubCULPelX, uiSubCUTPelY );   // Copy Yuv data to picture Yuv
1779      }
1780    }
1781  }
1782}
1783
1784Void TEncCu::xCopyYuv2Tmp( UInt uiPartUnitIdx, UInt uiNextDepth )
1785{
1786  UInt uiCurrDepth = uiNextDepth - 1;
1787  m_ppcRecoYuvBest[uiNextDepth]->copyToPartYuv( m_ppcRecoYuvTemp[uiCurrDepth], uiPartUnitIdx );
1788}
1789
1790/** Function for filling the PCM buffer of a CU using its original sample array
1791 * \param pcCU pointer to current CU
1792 * \param pcOrgYuv pointer to original sample array
1793 * \returns Void
1794 */
1795Void TEncCu::xFillPCMBuffer     ( TComDataCU*& pCU, TComYuv* pOrgYuv )
1796{
1797
1798  UInt   width        = pCU->getWidth(0);
1799  UInt   height       = pCU->getHeight(0);
1800
1801  Pel*   pSrcY = pOrgYuv->getLumaAddr(0, width); 
1802  Pel*   pDstY = pCU->getPCMSampleY();
1803  UInt   srcStride = pOrgYuv->getStride();
1804
1805  for(Int y = 0; y < height; y++ )
1806  {
1807    for(Int x = 0; x < width; x++ )
1808    {
1809      pDstY[x] = pSrcY[x];
1810    }
1811    pDstY += width;
1812    pSrcY += srcStride;
1813  }
1814
1815  Pel* pSrcCb       = pOrgYuv->getCbAddr();
1816  Pel* pSrcCr       = pOrgYuv->getCrAddr();;
1817
1818  Pel* pDstCb       = pCU->getPCMSampleCb();
1819  Pel* pDstCr       = pCU->getPCMSampleCr();;
1820
1821  UInt srcStrideC = pOrgYuv->getCStride();
1822  UInt heightC   = height >> 1;
1823  UInt widthC    = width  >> 1;
1824
1825  for(Int y = 0; y < heightC; y++ )
1826  {
1827    for(Int x = 0; x < widthC; x++ )
1828    {
1829      pDstCb[x] = pSrcCb[x];
1830      pDstCr[x] = pSrcCr[x];
1831    }
1832    pDstCb += widthC;
1833    pDstCr += widthC;
1834    pSrcCb += srcStrideC;
1835    pSrcCr += srcStrideC;
1836  }
1837}
1838
1839#if ADAPTIVE_QP_SELECTION
1840/** Collect ARL statistics from one block
1841  */
1842Int TEncCu::xTuCollectARLStats(TCoeff* rpcCoeff, Int* rpcArlCoeff, Int NumCoeffInCU, Double* cSum, UInt* numSamples )
1843{
1844  for( Int n = 0; n < NumCoeffInCU; n++ )
1845  {
1846    Int u = abs( rpcCoeff[ n ] );
1847    Int absc = rpcArlCoeff[ n ];
1848
1849    if( u != 0 )
1850    {
1851      if( u < LEVEL_RANGE )
1852      {
1853        cSum[ u ] += ( Double )absc;
1854        numSamples[ u ]++;
1855      }
1856      else 
1857      {
1858        cSum[ LEVEL_RANGE ] += ( Double )absc - ( Double )( u << ARL_C_PRECISION );
1859        numSamples[ LEVEL_RANGE ]++;
1860      }
1861    }
1862  }
1863
1864  return 0;
1865}
1866
1867/** Collect ARL statistics from one LCU
1868 * \param pcCU
1869 */
1870Void TEncCu::xLcuCollectARLStats(TComDataCU* rpcCU )
1871{
1872  Double cSum[ LEVEL_RANGE + 1 ];     //: the sum of DCT coefficients corresponding to datatype and quantization output
1873  UInt numSamples[ LEVEL_RANGE + 1 ]; //: the number of coefficients corresponding to datatype and quantization output
1874
1875  TCoeff* pCoeffY = rpcCU->getCoeffY();
1876  Int* pArlCoeffY = rpcCU->getArlCoeffY();
1877
1878  UInt uiMinCUWidth = g_uiMaxCUWidth >> g_uiMaxCUDepth;
1879  UInt uiMinNumCoeffInCU = 1 << uiMinCUWidth;
1880
1881  memset( cSum, 0, sizeof( Double )*(LEVEL_RANGE+1) );
1882  memset( numSamples, 0, sizeof( UInt )*(LEVEL_RANGE+1) );
1883
1884  // Collect stats to cSum[][] and numSamples[][]
1885  for(Int i = 0; i < rpcCU->getTotalNumPart(); i ++ )
1886  {
1887    UInt uiTrIdx = rpcCU->getTransformIdx(i);
1888
1889    if(rpcCU->getPredictionMode(i) == MODE_INTER)
1890    if( rpcCU->getCbf( i, TEXT_LUMA, uiTrIdx ) )
1891    {
1892      xTuCollectARLStats(pCoeffY, pArlCoeffY, uiMinNumCoeffInCU, cSum, numSamples);
1893    }//Note that only InterY is processed. QP rounding is based on InterY data only.
1894   
1895    pCoeffY  += uiMinNumCoeffInCU;
1896    pArlCoeffY  += uiMinNumCoeffInCU;
1897  }
1898
1899  for(Int u=1; u<LEVEL_RANGE;u++)
1900  {
1901    m_pcTrQuant->getSliceSumC()[u] += cSum[ u ] ;
1902    m_pcTrQuant->getSliceNSamples()[u] += numSamples[ u ] ;
1903  }
1904  m_pcTrQuant->getSliceSumC()[LEVEL_RANGE] += cSum[ LEVEL_RANGE ] ;
1905  m_pcTrQuant->getSliceNSamples()[LEVEL_RANGE] += numSamples[ LEVEL_RANGE ] ;
1906}
1907#endif
1908
1909#if (ENCODER_FAST_MODE)
1910Void TEncCu::xCheckRDCostILRUni(TComDataCU *&rpcBestCU, TComDataCU *&rpcTempCU, UInt refLayerId)
1911{
1912  UChar uhDepth = rpcTempCU->getDepth( 0 );
1913  rpcTempCU->setDepthSubParts( uhDepth, 0 );
1914#if SKIP_FLAG
1915  rpcTempCU->setSkipFlagSubParts( false, 0, uhDepth );
1916#endif
1917  rpcTempCU->setPartSizeSubParts  ( SIZE_2Nx2N,  0, uhDepth );  //2Nx2N
1918  rpcTempCU->setPredModeSubParts  ( MODE_INTER, 0, uhDepth );
1919  rpcTempCU->setCUTransquantBypassSubParts  ( m_pcEncCfg->getCUTransquantBypassFlagValue(), 0, uhDepth );
1920  Bool exitILR = m_pcPredSearch->predInterSearchILRUni( rpcTempCU, m_ppcOrigYuv[uhDepth], m_ppcPredYuvTemp[uhDepth], m_ppcResiYuvTemp[uhDepth], m_ppcRecoYuvTemp[uhDepth], refLayerId );
1921  if(!exitILR)
1922  {
1923     return;
1924  }
1925  m_pcPredSearch->encodeResAndCalcRdInterCU( rpcTempCU, m_ppcOrigYuv[uhDepth], m_ppcPredYuvTemp[uhDepth], m_ppcResiYuvTemp[uhDepth], m_ppcResiYuvBest[uhDepth], m_ppcRecoYuvTemp[uhDepth], false );
1926  rpcTempCU->getTotalCost()  = m_pcRdCost->calcRdCost( rpcTempCU->getTotalBits(), rpcTempCU->getTotalDistortion() );
1927  xCheckDQP( rpcTempCU );
1928  xCheckBestMode(rpcBestCU, rpcTempCU, uhDepth);
1929  return;
1930}
1931#endif
1932//! \}
Note: See TracBrowser for help on using the repository browser.