source: 3DVCSoftware/branches/HTM-16.2-dev/source/Lib/TLibEncoder/TEncCu.cpp

Last change on this file was 1412, checked in by tech, 7 years ago
  • Update HM-16.18
  • Cleanups
  • Encoder Extension

-- Representation formats
-- Parameter set sharing
-- GOP configuration

  • Property svn:eol-style set to native
File size: 112.5 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-2017, 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#include "TLibCommon/Debug.h"
43
44#include <cmath>
45#include <algorithm>
46using namespace std;
47
48//! \ingroup TLibEncoder
49//! \{
50
51// ====================================================================================================================
52// Constructor / destructor / create / destroy
53// ====================================================================================================================
54
55/**
56 \param    uhTotalDepth  total number of allowable depth
57 \param    uiMaxWidth    largest CU width
58 \param    uiMaxHeight   largest CU height
59 \param    chromaFormat  chroma format
60 */
61Void TEncCu::create(UChar uhTotalDepth, UInt uiMaxWidth, UInt uiMaxHeight, ChromaFormat chromaFormat)
62{
63  Int i;
64
65  m_uhTotalDepth   = uhTotalDepth + 1;
66  m_ppcBestCU      = new TComDataCU*[m_uhTotalDepth-1];
67  m_ppcTempCU      = new TComDataCU*[m_uhTotalDepth-1];
68
69#if NH_3D
70  m_ppcWeightedTempCU = new TComDataCU*[m_uhTotalDepth-1];
71#endif
72
73  m_ppcPredYuvBest = new TComYuv*[m_uhTotalDepth-1];
74  m_ppcResiYuvBest = new TComYuv*[m_uhTotalDepth-1];
75  m_ppcRecoYuvBest = new TComYuv*[m_uhTotalDepth-1];
76  m_ppcPredYuvTemp = new TComYuv*[m_uhTotalDepth-1];
77  m_ppcResiYuvTemp = new TComYuv*[m_uhTotalDepth-1];
78  m_ppcRecoYuvTemp = new TComYuv*[m_uhTotalDepth-1];
79  m_ppcOrigYuv     = new TComYuv*[m_uhTotalDepth-1];
80#if NH_3D
81  m_ppcOrigYuvDBBP = new TComYuv*[m_uhTotalDepth-1];
82#endif
83
84  UInt uiNumPartitions;
85  for( i=0 ; i<m_uhTotalDepth-1 ; i++)
86  {
87    uiNumPartitions = 1<<( ( m_uhTotalDepth - i - 1 )<<1 );
88    UInt uiWidth  = uiMaxWidth  >> i;
89    UInt uiHeight = uiMaxHeight >> i;
90
91    m_ppcBestCU[i] = new TComDataCU; m_ppcBestCU[i]->create( chromaFormat, uiNumPartitions, uiWidth, uiHeight, false, uiMaxWidth >> (m_uhTotalDepth - 1) );
92    m_ppcTempCU[i] = new TComDataCU; m_ppcTempCU[i]->create( chromaFormat, uiNumPartitions, uiWidth, uiHeight, false, uiMaxWidth >> (m_uhTotalDepth - 1) );
93#if NH_3D
94    m_ppcWeightedTempCU[i] = new TComDataCU; m_ppcWeightedTempCU[i]->create( chromaFormat, uiNumPartitions, uiWidth, uiHeight, false, uiMaxWidth >> (m_uhTotalDepth - 1) );
95#endif 
96
97    m_ppcPredYuvBest[i] = new TComYuv; m_ppcPredYuvBest[i]->create(uiWidth, uiHeight, chromaFormat);
98    m_ppcResiYuvBest[i] = new TComYuv; m_ppcResiYuvBest[i]->create(uiWidth, uiHeight, chromaFormat);
99    m_ppcRecoYuvBest[i] = new TComYuv; m_ppcRecoYuvBest[i]->create(uiWidth, uiHeight, chromaFormat);
100
101    m_ppcPredYuvTemp[i] = new TComYuv; m_ppcPredYuvTemp[i]->create(uiWidth, uiHeight, chromaFormat);
102    m_ppcResiYuvTemp[i] = new TComYuv; m_ppcResiYuvTemp[i]->create(uiWidth, uiHeight, chromaFormat);
103    m_ppcRecoYuvTemp[i] = new TComYuv; m_ppcRecoYuvTemp[i]->create(uiWidth, uiHeight, chromaFormat);
104
105    m_ppcOrigYuv    [i] = new TComYuv; m_ppcOrigYuv    [i]->create(uiWidth, uiHeight, chromaFormat);
106#if NH_3D
107    m_ppcOrigYuvDBBP[i] = new TComYuv; m_ppcOrigYuvDBBP[i]->create(uiWidth, uiHeight, chromaFormat);
108#endif
109
110  }
111
112  m_bEncodeDQP          = false;
113
114#if KWU_RC_MADPRED_E0227
115  m_LCUPredictionSAD = 0;
116  m_addSADDepth      = 0;
117  m_temporalSAD      = 0;
118  m_spatialSAD       = 0;
119#endif
120
121  m_stillToCodeChromaQpOffsetFlag  = false;
122  m_cuChromaQpOffsetIdxPlus1       = 0;
123  m_bFastDeltaQP                   = false;
124
125  // initialize partition order.
126  UInt* piTmp = &g_auiZscanToRaster[0];
127  initZscanToRaster( m_uhTotalDepth, 1, 0, piTmp);
128  initRasterToZscan( uiMaxWidth, uiMaxHeight, m_uhTotalDepth );
129
130  // initialize conversion matrix from partition index to pel
131  initRasterToPelXY( uiMaxWidth, uiMaxHeight, m_uhTotalDepth );
132}
133
134Void TEncCu::destroy()
135{
136  Int i;
137
138  for( i=0 ; i<m_uhTotalDepth-1 ; i++)
139  {
140    if(m_ppcBestCU[i])
141    {
142      m_ppcBestCU[i]->destroy();      delete m_ppcBestCU[i];      m_ppcBestCU[i] = NULL;
143    }
144    if(m_ppcTempCU[i])
145    {
146      m_ppcTempCU[i]->destroy();      delete m_ppcTempCU[i];      m_ppcTempCU[i] = NULL;
147    }
148#if NH_3D
149    if(m_ppcWeightedTempCU[i])
150    {
151      m_ppcWeightedTempCU[i]->destroy(); delete m_ppcWeightedTempCU[i]; m_ppcWeightedTempCU[i] = NULL;
152    }
153#endif
154    if(m_ppcPredYuvBest[i])
155    {
156      m_ppcPredYuvBest[i]->destroy(); delete m_ppcPredYuvBest[i]; m_ppcPredYuvBest[i] = NULL;
157    }
158    if(m_ppcResiYuvBest[i])
159    {
160      m_ppcResiYuvBest[i]->destroy(); delete m_ppcResiYuvBest[i]; m_ppcResiYuvBest[i] = NULL;
161    }
162    if(m_ppcRecoYuvBest[i])
163    {
164      m_ppcRecoYuvBest[i]->destroy(); delete m_ppcRecoYuvBest[i]; m_ppcRecoYuvBest[i] = NULL;
165    }
166    if(m_ppcPredYuvTemp[i])
167    {
168      m_ppcPredYuvTemp[i]->destroy(); delete m_ppcPredYuvTemp[i]; m_ppcPredYuvTemp[i] = NULL;
169    }
170    if(m_ppcResiYuvTemp[i])
171    {
172      m_ppcResiYuvTemp[i]->destroy(); delete m_ppcResiYuvTemp[i]; m_ppcResiYuvTemp[i] = NULL;
173    }
174    if(m_ppcRecoYuvTemp[i])
175    {
176      m_ppcRecoYuvTemp[i]->destroy(); delete m_ppcRecoYuvTemp[i]; m_ppcRecoYuvTemp[i] = NULL;
177    }
178    if(m_ppcOrigYuv[i])
179    {
180      m_ppcOrigYuv[i]->destroy();     delete m_ppcOrigYuv[i];     m_ppcOrigYuv[i] = NULL;
181    }
182#if NH_3D
183    if(m_ppcOrigYuvDBBP[i])
184    {
185      m_ppcOrigYuvDBBP[i]->destroy(); delete m_ppcOrigYuvDBBP[i]; m_ppcOrigYuvDBBP[i] = NULL;
186    }
187#endif
188  }
189  if(m_ppcBestCU)
190  {
191    delete [] m_ppcBestCU;
192    m_ppcBestCU = NULL;
193  }
194  if(m_ppcTempCU)
195  {
196    delete [] m_ppcTempCU;
197    m_ppcTempCU = NULL;
198  }
199
200#if NH_3D
201  if(m_ppcWeightedTempCU)
202  {
203    delete [] m_ppcWeightedTempCU; 
204    m_ppcWeightedTempCU = NULL; 
205  }
206#endif
207  if(m_ppcPredYuvBest)
208  {
209    delete [] m_ppcPredYuvBest;
210    m_ppcPredYuvBest = NULL;
211  }
212  if(m_ppcResiYuvBest)
213  {
214    delete [] m_ppcResiYuvBest;
215    m_ppcResiYuvBest = NULL;
216  }
217  if(m_ppcRecoYuvBest)
218  {
219    delete [] m_ppcRecoYuvBest;
220    m_ppcRecoYuvBest = NULL;
221  }
222  if(m_ppcPredYuvTemp)
223  {
224    delete [] m_ppcPredYuvTemp;
225    m_ppcPredYuvTemp = NULL;
226  }
227  if(m_ppcResiYuvTemp)
228  {
229    delete [] m_ppcResiYuvTemp;
230    m_ppcResiYuvTemp = NULL;
231  }
232  if(m_ppcRecoYuvTemp)
233  {
234    delete [] m_ppcRecoYuvTemp;
235    m_ppcRecoYuvTemp = NULL;
236  }
237  if(m_ppcOrigYuv)
238  {
239    delete [] m_ppcOrigYuv;
240    m_ppcOrigYuv = NULL;
241  }
242#if NH_3D
243  if(m_ppcOrigYuvDBBP)
244  {
245    delete [] m_ppcOrigYuvDBBP;
246    m_ppcOrigYuvDBBP = NULL;
247  }
248#endif
249}
250
251/** \param    pcEncTop      pointer of encoder class
252 */
253Void TEncCu::init( TEncTop* pcEncTop )
254{
255  m_pcEncCfg           = pcEncTop;
256  m_pcPredSearch       = pcEncTop->getPredSearch();
257  m_pcTrQuant          = pcEncTop->getTrQuant();
258  m_pcRdCost           = pcEncTop->getRdCost();
259
260  m_pcEntropyCoder     = pcEncTop->getEntropyCoder();
261  m_pcBinCABAC         = pcEncTop->getBinCABAC();
262
263  m_pppcRDSbacCoder    = pcEncTop->getRDSbacCoder();
264  m_pcRDGoOnSbacCoder  = pcEncTop->getRDGoOnSbacCoder();
265
266  m_pcRateCtrl         = pcEncTop->getRateCtrl();
267  m_lumaQPOffset       = 0;
268  initLumaDeltaQpLUT();
269}
270
271// ====================================================================================================================
272// Public member functions
273// ====================================================================================================================
274
275/**
276 \param  pCtu pointer of CU data class
277 */
278Void TEncCu::compressCtu( TComDataCU* pCtu )
279{
280  // initialize CU data
281  m_ppcBestCU[0]->initCtu( pCtu->getPic(), pCtu->getCtuRsAddr() );
282  m_ppcTempCU[0]->initCtu( pCtu->getPic(), pCtu->getCtuRsAddr() );
283
284#if NH_3D
285  m_ppcWeightedTempCU[0]->initCtu( pCtu->getPic(), pCtu->getCtuRsAddr() );
286#endif
287
288#if KWU_RC_MADPRED_E0227
289  m_LCUPredictionSAD = 0;
290  m_addSADDepth      = 0;
291  m_temporalSAD      = 0;
292  m_spatialSAD       = 0;
293#endif
294
295  // analysis of CU
296  DEBUG_STRING_NEW(sDebug)
297
298  xCompressCU( m_ppcBestCU[0], m_ppcTempCU[0], 0 DEBUG_STRING_PASS_INTO(sDebug) );
299  DEBUG_STRING_OUTPUT(std::cout, sDebug)
300
301#if ADAPTIVE_QP_SELECTION
302  if( m_pcEncCfg->getUseAdaptQpSelect() )
303  {
304    if(pCtu->getSlice()->getSliceType()!=I_SLICE) //IIII
305    {
306      xCtuCollectARLStats( pCtu );
307    }
308  }
309#endif
310}
311/** \param  pCtu  pointer of CU data class
312 */
313Void TEncCu::encodeCtu ( TComDataCU* pCtu )
314{
315  if ( pCtu->getSlice()->getPPS()->getUseDQP() )
316  {
317    setdQPFlag(true);
318  }
319
320  if ( pCtu->getSlice()->getUseChromaQpAdj() )
321  {
322    setCodeChromaQpAdjFlag(true);
323  }
324
325  // Encode CU data
326  xEncodeCU( pCtu, 0, 0 );
327}
328
329// ====================================================================================================================
330// Protected member functions
331// ====================================================================================================================
332
333Void TEncCu::initLumaDeltaQpLUT()
334{
335  const LumaLevelToDeltaQPMapping &mapping=m_pcEncCfg->getLumaLevelToDeltaQPMapping();
336
337  if ( !mapping.isEnabled() )
338  {
339    return;
340  }
341
342  // map the sparse LumaLevelToDeltaQPMapping.mapping to a fully populated linear table.
343
344  Int         lastDeltaQPValue=0;
345  std::size_t nextSparseIndex=0;
346  for(Int index=0; index<LUMA_LEVEL_TO_DQP_LUT_MAXSIZE; index++)
347  {
348    while (nextSparseIndex < mapping.mapping.size() && index>=mapping.mapping[nextSparseIndex].first)
349    {
350      lastDeltaQPValue=mapping.mapping[nextSparseIndex].second;
351      nextSparseIndex++;
352    }
353    m_lumaLevelToDeltaQPLUT[index]=lastDeltaQPValue;
354  }
355}
356
357Int TEncCu::calculateLumaDQP(TComDataCU *pCU, const UInt absPartIdx, const TComYuv * pOrgYuv)
358{
359  const Pel *pY = pOrgYuv->getAddr(COMPONENT_Y, absPartIdx);
360  const Int stride  = pOrgYuv->getStride(COMPONENT_Y);
361  Int width = pCU->getWidth(absPartIdx);
362  Int height = pCU->getHeight(absPartIdx);
363  Double avg = 0;
364
365  // limit the block by picture size
366  const TComSPS* pSPS = pCU->getSlice()->getSPS();
367  if ( pCU->getCUPelX() + width > pSPS->getPicWidthInLumaSamples() )
368  {
369    width = pSPS->getPicWidthInLumaSamples() - pCU->getCUPelX();
370  }
371  if ( pCU->getCUPelY() + height > pSPS->getPicHeightInLumaSamples() )
372  {
373    height = pSPS->getPicHeightInLumaSamples() - pCU->getCUPelY();
374  }
375
376  // Get QP offset derived from Luma level
377  if ( m_pcEncCfg->getLumaLevelToDeltaQPMapping().mode == LUMALVL_TO_DQP_AVG_METHOD )
378  {
379    // Use avg method
380    Int sum = 0;
381    for (Int y = 0; y < height; y++)
382    {
383      for (Int x = 0; x < width; x++)
384      {
385        sum += pY[x];
386      }
387      pY += stride;
388    }
389    avg = (Double)sum/(width*height);
390  }
391  else
392  {
393    // Use maximum luma value
394    Int maxVal = 0;
395    for (Int y = 0; y < height; y++)
396    {
397      for (Int x = 0; x < width; x++)
398      {
399        if (pY[x] > maxVal)
400        {
401          maxVal = pY[x];
402        }
403      }
404      pY += stride;
405    }
406    // use a percentage of the maxVal
407    avg = (Double)maxVal * m_pcEncCfg->getLumaLevelToDeltaQPMapping().maxMethodWeight;
408  }
409
410  Int lumaIdx = Clip3<Int>(0, Int(LUMA_LEVEL_TO_DQP_LUT_MAXSIZE)-1, Int(avg+0.5) );
411  Int QP = m_lumaLevelToDeltaQPLUT[lumaIdx];
412  return QP;
413}
414
415//! Derive small set of test modes for AMP encoder speed-up
416#if AMP_ENC_SPEEDUP
417#if AMP_MRG
418Void TEncCu::deriveTestModeAMP (TComDataCU *pcBestCU, PartSize eParentPartSize, Bool &bTestAMP_Hor, Bool &bTestAMP_Ver, Bool &bTestMergeAMP_Hor, Bool &bTestMergeAMP_Ver)
419#else
420Void TEncCu::deriveTestModeAMP (TComDataCU *pcBestCU, PartSize eParentPartSize, Bool &bTestAMP_Hor, Bool &bTestAMP_Ver)
421#endif
422{
423  if ( pcBestCU->getPartitionSize(0) == SIZE_2NxN )
424  {
425    bTestAMP_Hor = true;
426  }
427  else if ( pcBestCU->getPartitionSize(0) == SIZE_Nx2N )
428  {
429    bTestAMP_Ver = true;
430  }
431  else if ( pcBestCU->getPartitionSize(0) == SIZE_2Nx2N && pcBestCU->getMergeFlag(0) == false && pcBestCU->isSkipped(0) == false )
432  {
433    bTestAMP_Hor = true;
434    bTestAMP_Ver = true;
435  }
436
437#if AMP_MRG
438  //! Utilizing the partition size of parent PU
439  if ( eParentPartSize >= SIZE_2NxnU && eParentPartSize <= SIZE_nRx2N )
440  {
441    bTestMergeAMP_Hor = true;
442    bTestMergeAMP_Ver = true;
443  }
444
445  if ( eParentPartSize == NUMBER_OF_PART_SIZES ) //! if parent is intra
446  {
447    if ( pcBestCU->getPartitionSize(0) == SIZE_2NxN )
448    {
449      bTestMergeAMP_Hor = true;
450    }
451    else if ( pcBestCU->getPartitionSize(0) == SIZE_Nx2N )
452    {
453      bTestMergeAMP_Ver = true;
454    }
455  }
456
457  if ( pcBestCU->getPartitionSize(0) == SIZE_2Nx2N && pcBestCU->isSkipped(0) == false )
458  {
459    bTestMergeAMP_Hor = true;
460    bTestMergeAMP_Ver = true;
461  }
462
463  if ( pcBestCU->getWidth(0) == 64 )
464  {
465    bTestAMP_Hor = false;
466    bTestAMP_Ver = false;
467  }
468#else
469  //! Utilizing the partition size of parent PU
470  if ( eParentPartSize >= SIZE_2NxnU && eParentPartSize <= SIZE_nRx2N )
471  {
472    bTestAMP_Hor = true;
473    bTestAMP_Ver = true;
474  }
475
476  if ( eParentPartSize == SIZE_2Nx2N )
477  {
478    bTestAMP_Hor = false;
479    bTestAMP_Ver = false;
480  }
481#endif
482}
483#endif
484
485
486// ====================================================================================================================
487// Protected member functions
488// ====================================================================================================================
489/** Compress a CU block recursively with enabling sub-CTU-level delta QP
490 *  - for loop of QP value to compress the current CU with all possible QP
491*/
492#if AMP_ENC_SPEEDUP
493Void TEncCu::xCompressCU( TComDataCU*& rpcBestCU, TComDataCU*& rpcTempCU, const UInt uiDepth DEBUG_STRING_FN_DECLARE(sDebug_), PartSize eParentPartSize )
494#else
495Void TEncCu::xCompressCU( TComDataCU*& rpcBestCU, TComDataCU*& rpcTempCU, const UInt uiDepth )
496#endif
497{
498  TComPic* pcPic = rpcBestCU->getPic();
499  DEBUG_STRING_NEW(sDebug)
500  const TComPPS &pps=*(rpcTempCU->getSlice()->getPPS());
501  const TComSPS &sps=*(rpcTempCU->getSlice()->getSPS());
502 
503  // These are only used if getFastDeltaQp() is true
504  const UInt fastDeltaQPCuMaxSize    = Clip3(sps.getMaxCUHeight()>>sps.getLog2DiffMaxMinCodingBlockSize(), sps.getMaxCUHeight(), 32u);
505
506#if NH_3D
507  Bool  bLimQtPredFalg    = pcPic->getSlice(0)->getQtPredFlag(); 
508  TComPic *pcTexture      = rpcBestCU->getSlice()->getTexturePic();
509
510  Bool  depthMapDetect    = (pcTexture != NULL);
511  Bool  bIntraSliceDetect = (rpcBestCU->getSlice()->getSliceType() == I_SLICE);
512
513  Bool rapPic             = (rpcBestCU->getSlice()->getNalUnitType() == NAL_UNIT_CODED_SLICE_IDR_W_RADL || rpcBestCU->getSlice()->getNalUnitType() == NAL_UNIT_CODED_SLICE_IDR_N_LP || rpcBestCU->getSlice()->getNalUnitType() == NAL_UNIT_CODED_SLICE_CRA);
514
515  Bool bTry2NxN           = true;
516  Bool bTryNx2N           = true;
517#endif
518
519  // get Original YUV data from picture
520  m_ppcOrigYuv[uiDepth]->copyFromPicYuv( pcPic->getPicYuvOrg(), rpcBestCU->getCtuRsAddr(), rpcBestCU->getZorderIdxInCtu() );
521
522#if NH_3D
523  Bool    bTrySplit     = true;
524  Bool    bTrySplitDQP  = true;
525#endif
526  // variable for Cbf fast mode PU decision
527  Bool    doNotBlockPu = true;
528  Bool    earlyDetectionSkipMode = false;
529
530#if NH_3D
531  DisInfo DvInfo; 
532  DvInfo.m_acNBDV.setZero();
533  DvInfo.m_aVIdxCan = 0;
534  DvInfo.m_acDoNBDV.setZero();
535#endif
536  const UInt uiLPelX   = rpcBestCU->getCUPelX();
537  const UInt uiRPelX   = uiLPelX + rpcBestCU->getWidth(0)  - 1;
538  const UInt uiTPelY   = rpcBestCU->getCUPelY();
539  const UInt uiBPelY   = uiTPelY + rpcBestCU->getHeight(0) - 1;
540  const UInt uiWidth   = rpcBestCU->getWidth(0);
541
542#if NH_MV_ENC_DEC_TRAC
543#if ENC_DEC_TRACE
544    stopAtPos  ( rpcBestCU->getSlice()->getPOC(), 
545                 rpcBestCU->getSlice()->getLayerId(), 
546                 rpcBestCU->getCUPelX(),
547                 rpcBestCU->getCUPelY(),
548                 rpcBestCU->getWidth(0), 
549                 rpcBestCU->getHeight(0) );
550#endif
551#endif
552
553  Int iBaseQP = xComputeQP( rpcBestCU, uiDepth );
554  Int iMinQP;
555  Int iMaxQP;
556  Bool isAddLowestQP = false;
557
558  const UInt numberValidComponents = rpcBestCU->getPic()->getNumberValidComponents();
559
560  if( uiDepth <= pps.getMaxCuDQPDepth() )
561  {
562    Int idQP = m_pcEncCfg->getMaxDeltaQP();
563    iMinQP = Clip3( -sps.getQpBDOffset(CHANNEL_TYPE_LUMA), MAX_QP, iBaseQP-idQP );
564    iMaxQP = Clip3( -sps.getQpBDOffset(CHANNEL_TYPE_LUMA), MAX_QP, iBaseQP+idQP );
565  }
566  else
567  {
568    iMinQP = rpcTempCU->getQP(0);
569    iMaxQP = rpcTempCU->getQP(0);
570  }
571
572  if ( m_pcEncCfg->getLumaLevelToDeltaQPMapping().isEnabled() )
573  {
574    if ( uiDepth <= pps.getMaxCuDQPDepth() )
575    {
576      // keep using the same m_QP_LUMA_OFFSET in the same CTU
577      m_lumaQPOffset = calculateLumaDQP(rpcTempCU, 0, m_ppcOrigYuv[uiDepth]);
578    }
579    iMinQP = Clip3(-sps.getQpBDOffset(CHANNEL_TYPE_LUMA), MAX_QP, iBaseQP - m_lumaQPOffset);
580    iMaxQP = iMinQP; // force encode choose the modified QO
581  }
582
583  if ( m_pcEncCfg->getUseRateCtrl() )
584  {
585    iMinQP = m_pcRateCtrl->getRCQP();
586    iMaxQP = m_pcRateCtrl->getRCQP();
587  }
588
589  // transquant-bypass (TQB) processing loop variable initialisation ---
590
591  const Int lowestQP = iMinQP; // For TQB, use this QP which is the lowest non TQB QP tested (rather than QP'=0) - that way delta QPs are smaller, and TQB can be tested at all CU levels.
592
593  if ( (pps.getTransquantBypassEnabledFlag()) )
594  {
595    isAddLowestQP = true; // mark that the first iteration is to cost TQB mode.
596    iMinQP = iMinQP - 1;  // increase loop variable range by 1, to allow testing of TQB mode along with other QPs
597    if ( m_pcEncCfg->getCUTransquantBypassFlagForceValue() )
598    {
599      iMaxQP = iMinQP;
600    }
601  }
602
603#if NH_3D
604  Bool bICEnabled = rpcTempCU->getSlice()->getViewIndex() && ( rpcTempCU->getSlice()->getSliceType() == P_SLICE || rpcTempCU->getSlice()->getSliceType() == B_SLICE ) && !rpcTempCU->getSlice()->getIsDepth();
605  bICEnabled = bICEnabled && rpcTempCU->getSlice()->getApplyIC();
606#endif
607
608  TComSlice * pcSlice = rpcTempCU->getPic()->getSlice(rpcTempCU->getPic()->getCurrSliceIdx());
609
610  const Bool bBoundary = !( uiRPelX < sps.getPicWidthInLumaSamples() && uiBPelY < sps.getPicHeightInLumaSamples() );
611#if  NH_3D_FAST_TEXTURE_ENCODING
612    Bool bIVFMerge = false;
613    Int  iIVFMaxD = 0;
614    Bool bFMD = false;
615    Bool bSubBranch = true;
616#endif
617  if ( !bBoundary )
618  {
619    for (Int iQP=iMinQP; iQP<=iMaxQP; iQP++)
620    {
621      const Bool bIsLosslessMode = isAddLowestQP && (iQP == iMinQP);
622
623      if (bIsLosslessMode)
624      {
625        iQP = lowestQP;
626      }
627      if ( m_pcEncCfg->getLumaLevelToDeltaQPMapping().isEnabled() && uiDepth <= pps.getMaxCuDQPDepth() )
628      {
629        getSliceEncoder()->updateLambda(pcSlice, iQP);
630      }
631
632
633
634#if NH_3D
635      bTrySplit    = true;
636#endif
637
638      m_cuChromaQpOffsetIdxPlus1 = 0;
639      if (pcSlice->getUseChromaQpAdj())
640      {
641        /* Pre-estimation of chroma QP based on input block activity may be performed
642         * here, using for example m_ppcOrigYuv[uiDepth] */
643        /* To exercise the current code, the index used for adjustment is based on
644         * block position
645         */
646        Int lgMinCuSize = sps.getLog2MinCodingBlockSize() +
647                          std::max<Int>(0, sps.getLog2DiffMaxMinCodingBlockSize()-Int(pps.getPpsRangeExtension().getDiffCuChromaQpOffsetDepth()));
648        m_cuChromaQpOffsetIdxPlus1 = ((uiLPelX >> lgMinCuSize) + (uiTPelY >> lgMinCuSize)) % (pps.getPpsRangeExtension().getChromaQpOffsetListLen() + 1);
649      }
650
651      rpcTempCU->initEstData( uiDepth, iQP, bIsLosslessMode );
652#if NH_3D
653      //logic for setting bTrySplit using the partition information that is stored of the texture colocated CU
654      if(depthMapDetect && !bIntraSliceDetect && !rapPic && ( m_pcEncCfg->getUseQTL() || bLimQtPredFalg ))
655      {
656        TComDataCU* pcTextureCU = pcTexture->getCtu( rpcBestCU->getCtuRsAddr() ); //Corresponding texture LCU
657        UInt uiCUIdx            = rpcBestCU->getZorderIdxInCtu();
658        assert(pcTextureCU->getDepth(uiCUIdx) >= uiDepth); //Depth cannot be more partitioned than the texture.
659        if (pcTextureCU->getDepth(uiCUIdx) > uiDepth || pcTextureCU->getPartitionSize(uiCUIdx) == SIZE_NxN) //Texture was split.
660        {
661          bTrySplit = true;
662          bTryNx2N  = true;
663          bTry2NxN  = true;
664        }
665        else
666        {
667          bTrySplit = false;
668          bTryNx2N  = false;
669          bTry2NxN  = false;
670          if( pcTextureCU->getDepth(uiCUIdx) == uiDepth && pcTextureCU->getPartitionSize(uiCUIdx) != SIZE_2Nx2N)
671          {
672            if(pcTextureCU->getPartitionSize(uiCUIdx)==SIZE_2NxN || pcTextureCU->getPartitionSize(uiCUIdx)==SIZE_2NxnU|| pcTextureCU->getPartitionSize(uiCUIdx)==SIZE_2NxnD)
673            {
674              bTry2NxN  = true;
675            }
676            else
677            {
678              bTryNx2N  = true;
679            }
680          }
681        }
682      }
683#endif
684
685#if NH_3D
686      if( rpcTempCU->getSlice()->getSliceType() != I_SLICE )
687      {
688        if( rpcTempCU->getSlice()->getIvResPredFlag() || rpcTempCU->getSlice()->getIvMvPredFlag() || rpcTempCU->getSlice()->getViewSynthesisPredFlag() )
689        {
690          PartSize ePartTemp = rpcTempCU->getPartitionSize(0);
691          rpcTempCU->setPartSizeSubParts(SIZE_2Nx2N, 0, uiDepth);
692          if (rpcTempCU->getSlice()->getIsDepth() )
693          {
694            rpcTempCU->getDispforDepth(0, 0, &DvInfo);
695          }
696          else
697          {
698            if( rpcTempCU->getSlice()->getDepthRefinementFlag() )
699            {
700              rpcTempCU->getDisMvpCandNBDV(&DvInfo, true);
701            }
702            else
703            {
704              rpcTempCU->getDisMvpCandNBDV(&DvInfo);
705            }
706          }
707          rpcTempCU->setDvInfoSubParts(DvInfo, 0, uiDepth);
708          rpcBestCU->setDvInfoSubParts(DvInfo, 0, uiDepth);
709          rpcTempCU->setPartSizeSubParts( ePartTemp, 0, uiDepth );
710        }
711      }
712#if  NH_3D_FAST_TEXTURE_ENCODING
713      if(rpcTempCU->getSlice()->getViewIndex() && !rpcTempCU->getSlice()->getIsDepth() && rpcTempCU->getSlice()->getDefaultRefViewIdxAvailableFlag() )
714      {
715        PartSize ePartTemp = rpcTempCU->getPartitionSize(0);
716        rpcTempCU->setPartSizeSubParts( SIZE_2Nx2N, 0, uiDepth ); 
717        rpcTempCU->getIVNStatus( 0, &DvInfo,  bIVFMerge, iIVFMaxD);
718        rpcTempCU->setPartSizeSubParts( ePartTemp, 0, uiDepth );
719      }
720#endif
721#endif
722      // do inter modes, SKIP and 2Nx2N
723      if( rpcBestCU->getSlice()->getSliceType() != I_SLICE )
724      {
725#if NH_3D
726        for( UInt uiICId = 0; uiICId < ( bICEnabled ? 2 : 1 ); uiICId++ )
727        {
728          Bool bICFlag = uiICId ? true : false;
729#endif
730        // 2Nx2N
731        if(m_pcEncCfg->getUseEarlySkipDetection())
732        {
733#if NH_3D
734            rpcTempCU->setICFlagSubParts(bICFlag, 0, 0, uiDepth);
735#endif
736#if  NH_3D_FAST_TEXTURE_ENCODING
737          xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_2Nx2N DEBUG_STRING_PASS_INTO(sDebug), bFMD );  rpcTempCU->initEstData( uiDepth, iQP, bIsLosslessMode  );//by Competition for inter_2Nx2N
738#else
739          xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_2Nx2N DEBUG_STRING_PASS_INTO(sDebug) );
740          rpcTempCU->initEstData( uiDepth, iQP, bIsLosslessMode );//by Competition for inter_2Nx2N
741#endif
742#if NH_3D
743          rpcTempCU->setDvInfoSubParts(DvInfo, 0, uiDepth);
744#endif
745        }
746        // SKIP
747#if NH_3D
748          rpcTempCU->setICFlagSubParts(bICFlag, 0, 0, uiDepth);
749#endif
750        xCheckRDCostMerge2Nx2N( rpcBestCU, rpcTempCU DEBUG_STRING_PASS_INTO(sDebug), &earlyDetectionSkipMode );//by Merge for inter_2Nx2N
751#if  NH_3D_FAST_TEXTURE_ENCODING
752          bFMD = bIVFMerge && rpcBestCU->isSkipped(0);
753#endif
754
755        rpcTempCU->initEstData( uiDepth, iQP, bIsLosslessMode );
756#if NH_3D
757        rpcTempCU->setDvInfoSubParts(DvInfo, 0, uiDepth);
758#endif
759
760        if(!m_pcEncCfg->getUseEarlySkipDetection())
761        {
762          // 2Nx2N, NxN
763#if NH_3D
764            rpcTempCU->setICFlagSubParts(bICFlag, 0, 0, uiDepth);
765#endif
766#if  NH_3D_FAST_TEXTURE_ENCODING
767            xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_2Nx2N DEBUG_STRING_PASS_INTO(sDebug), bFMD );  rpcTempCU->initEstData( uiDepth, iQP, bIsLosslessMode );
768#else
769
770          xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_2Nx2N DEBUG_STRING_PASS_INTO(sDebug) );
771          rpcTempCU->initEstData( uiDepth, iQP, bIsLosslessMode );
772#endif
773#if NH_3D
774          rpcTempCU->setDvInfoSubParts(DvInfo, 0, uiDepth);
775            if( rpcTempCU->getSlice()->getDepthBasedBlkPartFlag() && rpcTempCU->getSlice()->getDefaultRefViewIdxAvailableFlag() )
776            {
777              xCheckRDCostInterDBBP( rpcBestCU, rpcTempCU DEBUG_STRING_PASS_INTO(sDebug), false );
778              rpcTempCU->initEstData( uiDepth, iQP, bIsLosslessMode  );
779              rpcTempCU->setDvInfoSubParts(DvInfo, 0, uiDepth);
780            }
781#endif
782
783          if(m_pcEncCfg->getUseCbfFastMode())
784          {
785            doNotBlockPu = rpcBestCU->getQtRootCbf( 0 ) != 0;
786          }
787        }
788#if NH_3D
789        }
790#endif
791      }
792#if NH_3D
793      if(depthMapDetect && !bIntraSliceDetect && !rapPic && ( m_pcEncCfg->getUseQTL() || bLimQtPredFalg ))
794      {
795        bTrySplitDQP = bTrySplit;
796      }
797#endif
798
799      if (bIsLosslessMode) // Restore loop variable if lossless mode was searched.
800      {
801        iQP = iMinQP;
802      }
803    }
804
805#if KWU_RC_MADPRED_E0227
806    if ( uiDepth <= m_addSADDepth )
807    {
808      m_LCUPredictionSAD += m_temporalSAD;
809      m_addSADDepth = uiDepth;
810    }
811#endif
812#if NH_3D
813    if( rpcBestCU->getSlice()->getIsDepth() && rpcBestCU->getSlice()->isIRAP() )
814    {
815      earlyDetectionSkipMode = false;
816    }
817
818    rpcTempCU->initEstData( uiDepth, iMinQP, isAddLowestQP  );
819    if( rpcBestCU->getSlice()->getDepthIntraSkipFlag() )
820    {
821      xCheckRDCostDIS( rpcBestCU, rpcTempCU, SIZE_2Nx2N DEBUG_STRING_PASS_INTO(sDebug) );
822      rpcTempCU->initEstData( uiDepth, iMinQP, isAddLowestQP  );
823    }
824#endif
825    if(!earlyDetectionSkipMode)
826    {
827      for (Int iQP=iMinQP; iQP<=iMaxQP; iQP++)
828      {
829        const Bool bIsLosslessMode = isAddLowestQP && (iQP == iMinQP); // If lossless, then iQP is irrelevant for subsequent modules.
830
831        if (bIsLosslessMode)
832        {
833          iQP = lowestQP;
834        }
835
836        rpcTempCU->initEstData( uiDepth, iQP, bIsLosslessMode );
837
838        // do inter modes, NxN, 2NxN, and Nx2N
839        if( rpcBestCU->getSlice()->getSliceType() != I_SLICE )
840        {
841          // 2Nx2N, NxN
842
843          if(!( (rpcBestCU->getWidth(0)==8) && (rpcBestCU->getHeight(0)==8) ))
844          {
845            if( uiDepth == sps.getLog2DiffMaxMinCodingBlockSize() && doNotBlockPu
846#if NH_3D
847                && bTrySplit
848#endif
849)
850            {
851#if  NH_3D_FAST_TEXTURE_ENCODING
852              xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_NxN DEBUG_STRING_PASS_INTO(sDebug), bFMD  );
853#else
854
855              xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_NxN DEBUG_STRING_PASS_INTO(sDebug)   );
856#endif
857              rpcTempCU->initEstData( uiDepth, iQP, bIsLosslessMode );
858#if NH_3D
859              rpcTempCU->setDvInfoSubParts(DvInfo, 0, uiDepth);
860#endif
861
862            }
863          }
864
865          if(doNotBlockPu
866#if NH_3D
867            && bTryNx2N
868#endif
869)
870          {
871#if  NH_3D_FAST_TEXTURE_ENCODING
872            xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_Nx2N DEBUG_STRING_PASS_INTO(sDebug), bFMD  );
873#else
874            xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_Nx2N DEBUG_STRING_PASS_INTO(sDebug)  );
875#endif
876            rpcTempCU->initEstData( uiDepth, iQP, bIsLosslessMode );
877#if NH_3D
878            rpcTempCU->setDvInfoSubParts(DvInfo, 0, uiDepth);
879#endif
880
881            if(m_pcEncCfg->getUseCbfFastMode() && rpcBestCU->getPartitionSize(0) == SIZE_Nx2N )
882            {
883              doNotBlockPu = rpcBestCU->getQtRootCbf( 0 ) != 0;
884            }
885          }
886          if(doNotBlockPu
887#if NH_3D
888            && bTry2NxN
889#endif
890)
891          {
892#if  NH_3D_FAST_TEXTURE_ENCODING
893            xCheckRDCostInter      ( rpcBestCU, rpcTempCU, SIZE_2NxN DEBUG_STRING_PASS_INTO(sDebug), bFMD  );
894#else
895
896            xCheckRDCostInter      ( rpcBestCU, rpcTempCU, SIZE_2NxN DEBUG_STRING_PASS_INTO(sDebug)  );
897#endif
898
899            rpcTempCU->initEstData( uiDepth, iQP, bIsLosslessMode );
900#if NH_3D
901            rpcTempCU->setDvInfoSubParts(DvInfo, 0, uiDepth);
902#endif
903
904            if(m_pcEncCfg->getUseCbfFastMode() && rpcBestCU->getPartitionSize(0) == SIZE_2NxN)
905            {
906              doNotBlockPu = rpcBestCU->getQtRootCbf( 0 ) != 0;
907            }
908          }
909
910          //! Try AMP (SIZE_2NxnU, SIZE_2NxnD, SIZE_nLx2N, SIZE_nRx2N)
911          if(sps.getUseAMP() && uiDepth < sps.getLog2DiffMaxMinCodingBlockSize() )
912          {
913#if AMP_ENC_SPEEDUP
914            Bool bTestAMP_Hor = false, bTestAMP_Ver = false;
915
916#if AMP_MRG
917            Bool bTestMergeAMP_Hor = false, bTestMergeAMP_Ver = false;
918
919            deriveTestModeAMP (rpcBestCU, eParentPartSize, bTestAMP_Hor, bTestAMP_Ver, bTestMergeAMP_Hor, bTestMergeAMP_Ver);
920#else
921            deriveTestModeAMP (rpcBestCU, eParentPartSize, bTestAMP_Hor, bTestAMP_Ver);
922#endif
923
924            //! Do horizontal AMP
925            if ( bTestAMP_Hor )
926            {
927              if(doNotBlockPu
928#if NH_3D
929                && bTry2NxN
930#endif
931)
932              {
933#if  NH_3D_FAST_TEXTURE_ENCODING
934                xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_2NxnU DEBUG_STRING_PASS_INTO(sDebug), bFMD );
935#else
936                xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_2NxnU DEBUG_STRING_PASS_INTO(sDebug) );
937#endif
938                rpcTempCU->initEstData( uiDepth, iQP, bIsLosslessMode );
939#if NH_3D
940                rpcTempCU->setDvInfoSubParts(DvInfo, 0, uiDepth);
941#endif
942                if(m_pcEncCfg->getUseCbfFastMode() && rpcBestCU->getPartitionSize(0) == SIZE_2NxnU )
943                {
944                  doNotBlockPu = rpcBestCU->getQtRootCbf( 0 ) != 0;
945                }
946              }
947              if(doNotBlockPu
948#if NH_3D
949                && bTry2NxN
950#endif
951)
952              {
953#if  NH_3D_FAST_TEXTURE_ENCODING
954                xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_2NxnD DEBUG_STRING_PASS_INTO(sDebug), bFMD );
955#else
956                xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_2NxnD DEBUG_STRING_PASS_INTO(sDebug) );
957#endif
958
959                rpcTempCU->initEstData( uiDepth, iQP, bIsLosslessMode );
960#if NH_3D
961                rpcTempCU->setDvInfoSubParts(DvInfo, 0, uiDepth);
962#endif
963
964                if(m_pcEncCfg->getUseCbfFastMode() && rpcBestCU->getPartitionSize(0) == SIZE_2NxnD )
965                {
966                  doNotBlockPu = rpcBestCU->getQtRootCbf( 0 ) != 0;
967                }
968              }
969            }
970#if AMP_MRG
971            else if ( bTestMergeAMP_Hor )
972            {
973              if(doNotBlockPu
974#if NH_3D
975                && bTry2NxN
976#endif
977)
978              {
979#if  NH_3D_FAST_TEXTURE_ENCODING
980                xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_2NxnU DEBUG_STRING_PASS_INTO(sDebug), bFMD, true );
981#else
982
983                xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_2NxnU DEBUG_STRING_PASS_INTO(sDebug), true );
984#endif
985
986                rpcTempCU->initEstData( uiDepth, iQP, bIsLosslessMode );
987#if NH_3D
988                rpcTempCU->setDvInfoSubParts(DvInfo, 0, uiDepth);
989#endif
990                if(m_pcEncCfg->getUseCbfFastMode() && rpcBestCU->getPartitionSize(0) == SIZE_2NxnU )
991                {
992                  doNotBlockPu = rpcBestCU->getQtRootCbf( 0 ) != 0;
993                }
994              }
995              if(doNotBlockPu
996#if NH_3D
997                && bTry2NxN
998#endif
999)
1000              {
1001#if  NH_3D_FAST_TEXTURE_ENCODING
1002                xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_2NxnD DEBUG_STRING_PASS_INTO(sDebug), bFMD, true );
1003#else
1004                xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_2NxnD DEBUG_STRING_PASS_INTO(sDebug), true );
1005#endif
1006                rpcTempCU->initEstData( uiDepth, iQP, bIsLosslessMode );
1007#if NH_3D
1008                rpcTempCU->setDvInfoSubParts(DvInfo, 0, uiDepth);
1009#endif
1010
1011                if(m_pcEncCfg->getUseCbfFastMode() && rpcBestCU->getPartitionSize(0) == SIZE_2NxnD )
1012                {
1013                  doNotBlockPu = rpcBestCU->getQtRootCbf( 0 ) != 0;
1014                }
1015              }
1016            }
1017#endif
1018
1019            //! Do horizontal AMP
1020            if ( bTestAMP_Ver )
1021            {
1022              if(doNotBlockPu
1023#if NH_3D
1024                && bTryNx2N
1025#endif
1026)
1027              {
1028#if  NH_3D_FAST_TEXTURE_ENCODING
1029                xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_nLx2N DEBUG_STRING_PASS_INTO(sDebug), bFMD );
1030#else
1031                xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_nLx2N DEBUG_STRING_PASS_INTO(sDebug) );
1032#endif
1033
1034                rpcTempCU->initEstData( uiDepth, iQP, bIsLosslessMode );
1035#if NH_3D
1036                rpcTempCU->setDvInfoSubParts(DvInfo, 0, uiDepth);
1037#endif
1038                if(m_pcEncCfg->getUseCbfFastMode() && rpcBestCU->getPartitionSize(0) == SIZE_nLx2N )
1039                {
1040                  doNotBlockPu = rpcBestCU->getQtRootCbf( 0 ) != 0;
1041                }
1042              }
1043              if(doNotBlockPu
1044#if NH_3D
1045                && bTryNx2N
1046#endif
1047)
1048              {
1049#if  NH_3D_FAST_TEXTURE_ENCODING
1050                xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_nRx2N DEBUG_STRING_PASS_INTO(sDebug), bFMD );
1051#else
1052                xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_nRx2N DEBUG_STRING_PASS_INTO(sDebug) );
1053#endif
1054                rpcTempCU->initEstData( uiDepth, iQP, bIsLosslessMode );
1055#if NH_3D
1056                rpcTempCU->setDvInfoSubParts(DvInfo, 0, uiDepth);
1057#endif
1058              }
1059            }
1060#if AMP_MRG
1061            else if ( bTestMergeAMP_Ver )
1062            {
1063              if(doNotBlockPu
1064#if NH_3D
1065                && bTryNx2N
1066#endif
1067)
1068              {
1069#if  NH_3D_FAST_TEXTURE_ENCODING
1070                xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_nLx2N DEBUG_STRING_PASS_INTO(sDebug), bFMD, true );
1071#else
1072                xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_nLx2N DEBUG_STRING_PASS_INTO(sDebug), true );
1073#endif
1074                rpcTempCU->initEstData( uiDepth, iQP, bIsLosslessMode );
1075#if NH_3D
1076                rpcTempCU->setDvInfoSubParts(DvInfo, 0, uiDepth);
1077#endif
1078                if(m_pcEncCfg->getUseCbfFastMode() && rpcBestCU->getPartitionSize(0) == SIZE_nLx2N )
1079                {
1080                  doNotBlockPu = rpcBestCU->getQtRootCbf( 0 ) != 0;
1081                }
1082              }
1083              if(doNotBlockPu
1084#if NH_3D
1085                && bTryNx2N
1086#endif
1087)
1088              {
1089#if  NH_3D_FAST_TEXTURE_ENCODING
1090                xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_nRx2N DEBUG_STRING_PASS_INTO(sDebug), bFMD, true );
1091#else
1092
1093                xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_nRx2N DEBUG_STRING_PASS_INTO(sDebug), true );
1094#endif
1095                rpcTempCU->initEstData( uiDepth, iQP, bIsLosslessMode );
1096#if NH_3D
1097                rpcTempCU->setDvInfoSubParts(DvInfo, 0, uiDepth);
1098#endif
1099
1100              }
1101            }
1102#endif
1103
1104#else
1105#if NH_3D
1106            if (bTry2NxN)
1107            {
1108#endif
1109              xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_2NxnU );
1110              rpcTempCU->initEstData( uiDepth, iQP, bIsLosslessMode );
1111#if NH_3D
1112              rpcTempCU->setDvInfoSubParts(DvInfo, 0, uiDepth);
1113#endif
1114              xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_2NxnD );
1115              rpcTempCU->initEstData( uiDepth, iQP, bIsLosslessMode );
1116#if NH_3D
1117              rpcTempCU->setDvInfoSubParts(DvInfo, 0, uiDepth);
1118            }
1119            if (bTryNx2N)
1120            {
1121#endif
1122              xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_nLx2N );
1123              rpcTempCU->initEstData( uiDepth, iQP, bIsLosslessMode );
1124#if NH_3D
1125              rpcTempCU->setDvInfoSubParts(DvInfo, 0, uiDepth);
1126#endif
1127              xCheckRDCostInter( rpcBestCU, rpcTempCU, SIZE_nRx2N );
1128              rpcTempCU->initEstData( uiDepth, iQP, bIsLosslessMode );
1129#if NH_3D
1130              rpcTempCU->setDvInfoSubParts(DvInfo, 0, uiDepth);
1131            }
1132#endif
1133
1134
1135#endif
1136          }
1137        }
1138#if  NH_3D_FAST_TEXTURE_ENCODING
1139        if(!bFMD)
1140        {
1141#endif
1142        // do normal intra modes
1143        // speedup for inter frames
1144
1145
1146#if MCTS_ENC_CHECK
1147        if ( m_pcEncCfg->getTMCTSSEITileConstraint() || (rpcBestCU->getSlice()->getSliceType() == I_SLICE) ||
1148             ((!m_pcEncCfg->getDisableIntraPUsInInterSlices()) && (
1149             (rpcBestCU->getCbf(0, COMPONENT_Y) != 0) ||
1150             ((rpcBestCU->getCbf(0, COMPONENT_Cb) != 0) && (numberValidComponents > COMPONENT_Cb)) ||
1151             ((rpcBestCU->getCbf(0, COMPONENT_Cr) != 0) && (numberValidComponents > COMPONENT_Cr))  // avoid very complex intra if it is unlikely
1152#else
1153        if((rpcBestCU->getSlice()->getSliceType() == I_SLICE)                                        ||
1154            ((!m_pcEncCfg->getDisableIntraPUsInInterSlices()) && (
1155              (rpcBestCU->getCbf( 0, COMPONENT_Y  ) != 0)                                            ||
1156             ((rpcBestCU->getCbf( 0, COMPONENT_Cb ) != 0) && (numberValidComponents > COMPONENT_Cb)) ||
1157             ((rpcBestCU->getCbf( 0, COMPONENT_Cr ) != 0) && (numberValidComponents > COMPONENT_Cr))  // avoid very complex intra if it is unlikely
1158#endif
1159 #if NH_3D
1160            || rpcBestCU->getSlice()->getIsDepth()
1161#endif
1162            )))
1163          {
1164#if NH_3D
1165          Bool bOnlyIVP = false;
1166          Bool bUseIVP = true;
1167          if( (rpcBestCU->getSlice()->getSliceType() != I_SLICE) && 
1168            !( (rpcBestCU->getCbf( 0, COMPONENT_Y  ) != 0)                                            ||
1169            ((rpcBestCU->getCbf( 0, COMPONENT_Cb ) != 0) && (numberValidComponents > COMPONENT_Cb)) ||
1170            ((rpcBestCU->getCbf( 0, COMPONENT_Cr ) != 0) && (numberValidComponents > COMPONENT_Cr))   ) &&
1171            (rpcBestCU->getSlice()->getIsDepth() && !(rpcBestCU->getSlice()->isIRAP())) )
1172          { 
1173            bOnlyIVP = true;
1174            bUseIVP = rpcBestCU->getSlice()->getIntraContourFlag();
1175          }
1176          if( bUseIVP )
1177          {
1178            xCheckRDCostIntra( rpcBestCU, rpcTempCU, SIZE_2Nx2N DEBUG_STRING_PASS_INTO(sDebug), bOnlyIVP );
1179#else
1180            xCheckRDCostIntra( rpcBestCU, rpcTempCU, SIZE_2Nx2N DEBUG_STRING_PASS_INTO(sDebug) );
1181#endif
1182#if KWU_RC_MADPRED_E0227
1183            if ( uiDepth <= m_addSADDepth )
1184            {
1185              m_LCUPredictionSAD += m_spatialSAD;
1186              m_addSADDepth = uiDepth;
1187            }
1188#endif
1189
1190            rpcTempCU->initEstData( uiDepth, iQP, bIsLosslessMode );
1191            if( uiDepth == sps.getLog2DiffMaxMinCodingBlockSize() )
1192            {
1193#if NH_3D   //Try IntraNxN
1194              if(bTrySplit)
1195              {
1196#endif
1197                if( rpcTempCU->getWidth(0) > ( 1 << sps.getQuadtreeTULog2MinSize() ) )
1198                {
1199#if NH_3D
1200                  xCheckRDCostIntra( rpcBestCU, rpcTempCU, SIZE_NxN DEBUG_STRING_PASS_INTO(sDebug), bOnlyIVP );
1201#else
1202                  xCheckRDCostIntra( rpcBestCU, rpcTempCU, SIZE_NxN DEBUG_STRING_PASS_INTO(sDebug)   );
1203#endif       
1204                  rpcTempCU->initEstData( uiDepth, iQP, bIsLosslessMode );
1205                }
1206#if NH_3D
1207              }
1208#endif
1209            }
1210#if NH_3D
1211          }
1212#endif
1213        }
1214
1215        // test PCM
1216        if(sps.getUsePCM()
1217          && rpcTempCU->getWidth(0) <= (1<<sps.getPCMLog2MaxSize())
1218          && rpcTempCU->getWidth(0) >= (1<<sps.getPCMLog2MinSize()) )
1219        {
1220          UInt uiRawBits = getTotalBits(rpcBestCU->getWidth(0), rpcBestCU->getHeight(0), rpcBestCU->getPic()->getChromaFormat(), sps.getBitDepths().recon);
1221          UInt uiBestBits = rpcBestCU->getTotalBits();
1222#if NH_3D_VSO // M7
1223          Double dRDCostTemp = m_pcRdCost->getUseLambdaScaleVSO() ? m_pcRdCost->calcRdCostVSO(uiRawBits, 0) : m_pcRdCost->calcRdCost(uiRawBits, 0);
1224          if((uiBestBits > uiRawBits) || (rpcBestCU->getTotalCost() > dRDCostTemp ))
1225#else
1226          if((uiBestBits > uiRawBits) || (rpcBestCU->getTotalCost() > m_pcRdCost->calcRdCost(uiRawBits, 0)))
1227#endif
1228          {
1229            xCheckIntraPCM (rpcBestCU, rpcTempCU);
1230            rpcTempCU->initEstData( uiDepth, iQP, bIsLosslessMode );
1231          }
1232        }
1233#if  NH_3D_FAST_TEXTURE_ENCODING
1234        }
1235#endif
1236        if (bIsLosslessMode) // Restore loop variable if lossless mode was searched.
1237        {
1238          iQP = iMinQP;
1239        }
1240      }
1241    }
1242
1243    if( rpcBestCU->getTotalCost()!=MAX_DOUBLE )
1244    {
1245      m_pcRDGoOnSbacCoder->load(m_pppcRDSbacCoder[uiDepth][CI_NEXT_BEST]);
1246      m_pcEntropyCoder->resetBits();
1247      m_pcEntropyCoder->encodeSplitFlag( rpcBestCU, 0, uiDepth, true );
1248      rpcBestCU->getTotalBits() += m_pcEntropyCoder->getNumberOfWrittenBits(); // split bits
1249      rpcBestCU->getTotalBins() += ((TEncBinCABAC *)((TEncSbac*)m_pcEntropyCoder->m_pcEntropyCoderIf)->getEncBinIf())->getBinsCoded();
1250#if NH_3D_VSO // M8
1251    if ( m_pcRdCost->getUseLambdaScaleVSO() )   
1252    {
1253      rpcBestCU->getTotalCost()  = m_pcRdCost->calcRdCostVSO( rpcBestCU->getTotalBits(), rpcBestCU->getTotalDistortion() );   
1254    }
1255    else
1256#endif
1257      rpcBestCU->getTotalCost()  = m_pcRdCost->calcRdCost( rpcBestCU->getTotalBits(), rpcBestCU->getTotalDistortion() );
1258      m_pcRDGoOnSbacCoder->store(m_pppcRDSbacCoder[uiDepth][CI_NEXT_BEST]);
1259    }
1260#if  NH_3D_FAST_TEXTURE_ENCODING
1261    if(rpcBestCU->getSlice()->getViewIndex() && !rpcBestCU->getSlice()->getIsDepth() && (uiDepth >=iIVFMaxD) && rpcBestCU->isSkipped(0))
1262    {
1263      bSubBranch = false;
1264    }
1265#endif
1266  }
1267
1268  // copy original YUV samples to PCM buffer
1269  if( rpcBestCU->getTotalCost()!=MAX_DOUBLE && rpcBestCU->isLosslessCoded(0) && (rpcBestCU->getIPCMFlag(0) == false))
1270  {
1271    xFillPCMBuffer(rpcBestCU, m_ppcOrigYuv[uiDepth]);
1272  }
1273
1274  if( uiDepth == pps.getMaxCuDQPDepth() )
1275  {
1276    Int idQP = m_pcEncCfg->getMaxDeltaQP();
1277    iMinQP = Clip3( -sps.getQpBDOffset(CHANNEL_TYPE_LUMA), MAX_QP, iBaseQP-idQP );
1278    iMaxQP = Clip3( -sps.getQpBDOffset(CHANNEL_TYPE_LUMA), MAX_QP, iBaseQP+idQP );
1279  }
1280  else if( uiDepth < pps.getMaxCuDQPDepth() )
1281  {
1282    iMinQP = iBaseQP;
1283    iMaxQP = iBaseQP;
1284  }
1285  else
1286  {
1287    const Int iStartQP = rpcTempCU->getQP(0);
1288    iMinQP = iStartQP;
1289    iMaxQP = iStartQP;
1290  }
1291
1292  if ( m_pcEncCfg->getLumaLevelToDeltaQPMapping().isEnabled() )
1293  {
1294    iMinQP = Clip3(-sps.getQpBDOffset(CHANNEL_TYPE_LUMA), MAX_QP, iBaseQP - m_lumaQPOffset);
1295    iMaxQP = iMinQP;
1296  }
1297
1298  if ( m_pcEncCfg->getUseRateCtrl() )
1299  {
1300    iMinQP = m_pcRateCtrl->getRCQP();
1301    iMaxQP = m_pcRateCtrl->getRCQP();
1302  }
1303
1304  if ( m_pcEncCfg->getCUTransquantBypassFlagForceValue() )
1305  {
1306    iMaxQP = iMinQP; // If all TUs are forced into using transquant bypass, do not loop here.
1307  }
1308#if  NH_3D_FAST_TEXTURE_ENCODING
1309  bSubBranch = bSubBranch && (bBoundary || !( m_pcEncCfg->getUseEarlyCU() && rpcBestCU->getTotalCost()!=MAX_DOUBLE && rpcBestCU->isSkipped(0) ));
1310#else
1311  const Bool bSubBranch = bBoundary || !( m_pcEncCfg->getUseEarlyCU() && rpcBestCU->getTotalCost()!=MAX_DOUBLE && rpcBestCU->isSkipped(0) );
1312#endif
1313#if NH_3D
1314  if( bSubBranch && uiDepth < sps.getLog2DiffMaxMinCodingBlockSize() && (!getFastDeltaQp() || uiWidth > fastDeltaQPCuMaxSize || bBoundary) && bTrySplitDQP )
1315#else
1316  if( bSubBranch && uiDepth < sps.getLog2DiffMaxMinCodingBlockSize() && (!getFastDeltaQp() || uiWidth > fastDeltaQPCuMaxSize || bBoundary))
1317#endif
1318  {
1319    // further split
1320    Double splitTotalCost = 0;
1321
1322    for (Int iQP=iMinQP; iQP<=iMaxQP; iQP++)
1323    {
1324      const Bool bIsLosslessMode = false; // False at this level. Next level down may set it to true.
1325
1326      rpcTempCU->initEstData( uiDepth, iQP, bIsLosslessMode );
1327
1328#if NH_3D_VSO // M9
1329      // reset Model
1330      if( m_pcRdCost->getUseRenModel() )
1331      {
1332        UInt  uiWidthOy     = m_ppcOrigYuv[uiDepth]->getWidth ( COMPONENT_Y );
1333        UInt  uiHeightOy    = m_ppcOrigYuv[uiDepth]->getHeight( COMPONENT_Y );
1334        Pel*  piSrc         = m_ppcOrigYuv[uiDepth]->getAddr  ( COMPONENT_Y, 0 );
1335        UInt  uiSrcStride   = m_ppcOrigYuv[uiDepth]->getStride( COMPONENT_Y  );
1336        m_pcRdCost->setRenModelData( m_ppcBestCU[uiDepth], 0, piSrc, uiSrcStride, uiWidthOy, uiHeightOy );
1337      }
1338#endif
1339      UChar       uhNextDepth         = uiDepth+1;
1340      TComDataCU* pcSubBestPartCU     = m_ppcBestCU[uhNextDepth];
1341      TComDataCU* pcSubTempPartCU     = m_ppcTempCU[uhNextDepth];
1342      DEBUG_STRING_NEW(sTempDebug)
1343
1344#if NH_3D
1345      m_ppcWeightedTempCU[uhNextDepth]->setSlice( m_ppcWeightedTempCU[ uiDepth]->getSlice()); 
1346      m_ppcWeightedTempCU[uhNextDepth]->setPic  ( m_ppcWeightedTempCU[ uiDepth] ); 
1347#endif
1348      for ( UInt uiPartUnitIdx = 0; uiPartUnitIdx < 4; uiPartUnitIdx++ )
1349      {
1350        pcSubBestPartCU->initSubCU( rpcTempCU, uiPartUnitIdx, uhNextDepth, iQP );           // clear sub partition datas or init.
1351        pcSubTempPartCU->initSubCU( rpcTempCU, uiPartUnitIdx, uhNextDepth, iQP );           // clear sub partition datas or init.
1352
1353        if( ( pcSubBestPartCU->getCUPelX() < sps.getPicWidthInLumaSamples() ) && ( pcSubBestPartCU->getCUPelY() < sps.getPicHeightInLumaSamples() ) )
1354        {
1355          if ( 0 == uiPartUnitIdx) //initialize RD with previous depth buffer
1356          {
1357            m_pppcRDSbacCoder[uhNextDepth][CI_CURR_BEST]->load(m_pppcRDSbacCoder[uiDepth][CI_CURR_BEST]);
1358          }
1359          else
1360          {
1361            m_pppcRDSbacCoder[uhNextDepth][CI_CURR_BEST]->load(m_pppcRDSbacCoder[uhNextDepth][CI_NEXT_BEST]);
1362          }
1363
1364#if AMP_ENC_SPEEDUP
1365          DEBUG_STRING_NEW(sChild)
1366          if ( !(rpcBestCU->getTotalCost()!=MAX_DOUBLE && rpcBestCU->isInter(0)) )
1367          {
1368            xCompressCU( pcSubBestPartCU, pcSubTempPartCU, uhNextDepth DEBUG_STRING_PASS_INTO(sChild), NUMBER_OF_PART_SIZES );
1369          }
1370          else
1371          {
1372
1373            xCompressCU( pcSubBestPartCU, pcSubTempPartCU, uhNextDepth DEBUG_STRING_PASS_INTO(sChild), rpcBestCU->getPartitionSize(0) );
1374          }
1375          DEBUG_STRING_APPEND(sTempDebug, sChild)
1376#else
1377          xCompressCU( pcSubBestPartCU, pcSubTempPartCU, uhNextDepth );
1378#endif
1379
1380          rpcTempCU->copyPartFrom( pcSubBestPartCU, uiPartUnitIdx, uhNextDepth );         // Keep best part data to current temporary data.
1381          xCopyYuv2Tmp( pcSubBestPartCU->getTotalNumPart()*uiPartUnitIdx, uhNextDepth );
1382          if ( m_pcEncCfg->getLumaLevelToDeltaQPMapping().isEnabled() && pps.getMaxCuDQPDepth() >= 1 )
1383          {
1384            splitTotalCost += pcSubBestPartCU->getTotalCost();
1385          }
1386        }
1387        else
1388        {
1389          pcSubBestPartCU->copyToPic( uhNextDepth );
1390          rpcTempCU->copyPartFrom( pcSubBestPartCU, uiPartUnitIdx, uhNextDepth );
1391        }
1392      }
1393
1394      m_pcRDGoOnSbacCoder->load(m_pppcRDSbacCoder[uhNextDepth][CI_NEXT_BEST]);
1395      if( !bBoundary )
1396      {
1397        m_pcEntropyCoder->resetBits();
1398        m_pcEntropyCoder->encodeSplitFlag( rpcTempCU, 0, uiDepth, true );
1399        if ( m_pcEncCfg->getLumaLevelToDeltaQPMapping().isEnabled() && pps.getMaxCuDQPDepth() >= 1 )
1400        {
1401          Int splitBits = m_pcEntropyCoder->getNumberOfWrittenBits();
1402          Double splitBitCost = m_pcRdCost->calcRdCost( splitBits, 0 );
1403          splitTotalCost += splitBitCost;
1404        }
1405
1406        rpcTempCU->getTotalBits() += m_pcEntropyCoder->getNumberOfWrittenBits(); // split bits
1407        rpcTempCU->getTotalBins() += ((TEncBinCABAC *)((TEncSbac*)m_pcEntropyCoder->m_pcEntropyCoderIf)->getEncBinIf())->getBinsCoded();
1408      }
1409      if ( m_pcEncCfg->getLumaLevelToDeltaQPMapping().isEnabled() && pps.getMaxCuDQPDepth() >= 1 )
1410      {
1411        rpcTempCU->getTotalCost() = splitTotalCost;
1412      }
1413      else
1414      {
1415#if NH_3D_VSO // M10
1416      if ( m_pcRdCost->getUseLambdaScaleVSO() )
1417      {
1418        rpcTempCU->getTotalCost()  = m_pcRdCost->calcRdCostVSO( rpcTempCU->getTotalBits(), rpcTempCU->getTotalDistortion() );
1419      }
1420      else
1421#endif
1422        rpcTempCU->getTotalCost()  = m_pcRdCost->calcRdCost( rpcTempCU->getTotalBits(), rpcTempCU->getTotalDistortion() );
1423      }
1424
1425      if( uiDepth == pps.getMaxCuDQPDepth() && pps.getUseDQP())
1426      {
1427        Bool hasResidual = false;
1428        for( UInt uiBlkIdx = 0; uiBlkIdx < rpcTempCU->getTotalNumPart(); uiBlkIdx ++)
1429        {
1430          if( (     rpcTempCU->getCbf(uiBlkIdx, COMPONENT_Y)
1431                || (rpcTempCU->getCbf(uiBlkIdx, COMPONENT_Cb) && (numberValidComponents > COMPONENT_Cb))
1432                || (rpcTempCU->getCbf(uiBlkIdx, COMPONENT_Cr) && (numberValidComponents > COMPONENT_Cr)) ) )
1433          {
1434            hasResidual = true;
1435            break;
1436          }
1437        }
1438
1439        if ( hasResidual )
1440        {
1441          m_pcEntropyCoder->resetBits();
1442          m_pcEntropyCoder->encodeQP( rpcTempCU, 0, false );
1443          rpcTempCU->getTotalBits() += m_pcEntropyCoder->getNumberOfWrittenBits(); // dQP bits
1444          rpcTempCU->getTotalBins() += ((TEncBinCABAC *)((TEncSbac*)m_pcEntropyCoder->m_pcEntropyCoderIf)->getEncBinIf())->getBinsCoded();
1445#if NH_3D_VSO // M11
1446          if ( m_pcRdCost->getUseLambdaScaleVSO())         
1447          {
1448            rpcTempCU->getTotalCost()  = m_pcRdCost->calcRdCostVSO( rpcTempCU->getTotalBits(), rpcTempCU->getTotalDistortion() );         
1449          }
1450          else
1451#endif
1452            rpcTempCU->getTotalCost()  = m_pcRdCost->calcRdCost( rpcTempCU->getTotalBits(), rpcTempCU->getTotalDistortion() );
1453
1454          Bool foundNonZeroCbf = false;
1455          rpcTempCU->setQPSubCUs( rpcTempCU->getRefQP( 0 ), 0, uiDepth, foundNonZeroCbf );
1456          assert( foundNonZeroCbf );
1457        }
1458        else
1459        {
1460          rpcTempCU->setQPSubParts( rpcTempCU->getRefQP( 0 ), 0, uiDepth ); // set QP to default QP
1461        }
1462      }
1463
1464      m_pcRDGoOnSbacCoder->store(m_pppcRDSbacCoder[uiDepth][CI_TEMP_BEST]);
1465
1466      // If the configuration being tested exceeds the maximum number of bytes for a slice / slice-segment, then
1467      // a proper RD evaluation cannot be performed. Therefore, termination of the
1468      // slice/slice-segment must be made prior to this CTU.
1469      // This can be achieved by forcing the decision to be that of the rpcTempCU.
1470      // The exception is each slice / slice-segment must have at least one CTU.
1471      if (rpcBestCU->getTotalCost()!=MAX_DOUBLE)
1472      {
1473        const Bool isEndOfSlice        =    pcSlice->getSliceMode()==FIXED_NUMBER_OF_BYTES
1474                                         && ((pcSlice->getSliceBits()+rpcBestCU->getTotalBits())>pcSlice->getSliceArgument()<<3)
1475                                         && rpcBestCU->getCtuRsAddr() != pcPic->getPicSym()->getCtuTsToRsAddrMap(pcSlice->getSliceCurStartCtuTsAddr())
1476                                         && rpcBestCU->getCtuRsAddr() != pcPic->getPicSym()->getCtuTsToRsAddrMap(pcSlice->getSliceSegmentCurStartCtuTsAddr());
1477        const Bool isEndOfSliceSegment =    pcSlice->getSliceSegmentMode()==FIXED_NUMBER_OF_BYTES
1478                                         && ((pcSlice->getSliceSegmentBits()+rpcBestCU->getTotalBits()) > pcSlice->getSliceSegmentArgument()<<3)
1479                                         && rpcBestCU->getCtuRsAddr() != pcPic->getPicSym()->getCtuTsToRsAddrMap(pcSlice->getSliceSegmentCurStartCtuTsAddr());
1480                                             // Do not need to check slice condition for slice-segment since a slice-segment is a subset of a slice.
1481        if(isEndOfSlice||isEndOfSliceSegment)
1482        {
1483          rpcBestCU->getTotalCost()=MAX_DOUBLE;
1484        }
1485      }
1486
1487      xCheckBestMode( rpcBestCU, rpcTempCU, uiDepth DEBUG_STRING_PASS_INTO(sDebug) DEBUG_STRING_PASS_INTO(sTempDebug) DEBUG_STRING_PASS_INTO(false) ); // RD compare current larger prediction
1488                                                                                                                                                       // with sub partitioned prediction.
1489    }
1490  }
1491#if NH_3D_VSO // M12
1492  if( m_pcRdCost->getUseRenModel() )
1493  {
1494    UInt  uiWidthRy     = m_ppcRecoYuvBest[uiDepth]->getWidth   ( COMPONENT_Y );
1495    UInt  uiHeightRy    = m_ppcRecoYuvBest[uiDepth]->getHeight  ( COMPONENT_Y );
1496    Pel*  piSrc       = m_ppcRecoYuvBest[uiDepth]->getAddr    ( COMPONENT_Y,  0 );
1497    UInt  uiSrcStride = m_ppcRecoYuvBest[uiDepth]->getStride  ( COMPONENT_Y );
1498    m_pcRdCost->setRenModelData( rpcBestCU, 0, piSrc, uiSrcStride, uiWidthRy, uiHeightRy );
1499  }
1500#endif
1501
1502  DEBUG_STRING_APPEND(sDebug_, sDebug);
1503
1504  rpcBestCU->copyToPic(uiDepth);                                                     // Copy Best data to Picture for next partition prediction.
1505
1506  xCopyYuv2Pic( rpcBestCU->getPic(), rpcBestCU->getCtuRsAddr(), rpcBestCU->getZorderIdxInCtu(), uiDepth, uiDepth );   // Copy Yuv data to picture Yuv
1507  if (bBoundary)
1508  {
1509    return;
1510  }
1511
1512  // Assert if Best prediction mode is NONE
1513  // Selected mode's RD-cost must be not MAX_DOUBLE.
1514  assert( rpcBestCU->getPartitionSize ( 0 ) != NUMBER_OF_PART_SIZES       );
1515  assert( rpcBestCU->getPredictionMode( 0 ) != NUMBER_OF_PREDICTION_MODES );
1516  assert( rpcBestCU->getTotalCost     (   ) != MAX_DOUBLE                 );
1517}
1518
1519/** finish encoding a cu and handle end-of-slice conditions
1520 * \param pcCU
1521 * \param uiAbsPartIdx
1522 * \param uiDepth
1523 * \returns Void
1524 */
1525Void TEncCu::finishCU( TComDataCU* pcCU, UInt uiAbsPartIdx )
1526{
1527  TComPic* pcPic = pcCU->getPic();
1528  TComSlice * pcSlice = pcCU->getPic()->getSlice(pcCU->getPic()->getCurrSliceIdx());
1529
1530  //Calculate end address
1531  const Int  currentCTUTsAddr = pcPic->getPicSym()->getCtuRsToTsAddrMap(pcCU->getCtuRsAddr());
1532  const Bool isLastSubCUOfCtu = pcCU->isLastSubCUOfCtu(uiAbsPartIdx);
1533  if ( isLastSubCUOfCtu )
1534  {
1535    // The 1-terminating bit is added to all streams, so don't add it here when it's 1.
1536    // i.e. when the slice segment CurEnd CTU address is the current CTU address+1.
1537    if (pcSlice->getSliceSegmentCurEndCtuTsAddr() != currentCTUTsAddr+1)
1538    {
1539      m_pcEntropyCoder->encodeTerminatingBit( 0 );
1540    }
1541  }
1542}
1543
1544/** Compute QP for each CU
1545 * \param pcCU Target CU
1546 * \param uiDepth CU depth
1547 * \returns quantization parameter
1548 */
1549Int TEncCu::xComputeQP( TComDataCU* pcCU, UInt uiDepth )
1550{
1551  Int iBaseQp = pcCU->getSlice()->getSliceQp();
1552  Int iQpOffset = 0;
1553  if ( m_pcEncCfg->getUseAdaptiveQP() )
1554  {
1555    TEncPic* pcEPic = dynamic_cast<TEncPic*>( pcCU->getPic() );
1556    UInt uiAQDepth = min( uiDepth, pcEPic->getMaxAQDepth()-1 );
1557    TEncPicQPAdaptationLayer* pcAQLayer = pcEPic->getAQLayer( uiAQDepth );
1558    UInt uiAQUPosX = pcCU->getCUPelX() / pcAQLayer->getAQPartWidth();
1559    UInt uiAQUPosY = pcCU->getCUPelY() / pcAQLayer->getAQPartHeight();
1560    UInt uiAQUStride = pcAQLayer->getAQPartStride();
1561    TEncQPAdaptationUnit* acAQU = pcAQLayer->getQPAdaptationUnit();
1562
1563    Double dMaxQScale = pow(2.0, m_pcEncCfg->getQPAdaptationRange()/6.0);
1564    Double dAvgAct = pcAQLayer->getAvgActivity();
1565    Double dCUAct = acAQU[uiAQUPosY * uiAQUStride + uiAQUPosX].getActivity();
1566    Double dNormAct = (dMaxQScale*dCUAct + dAvgAct) / (dCUAct + dMaxQScale*dAvgAct);
1567    Double dQpOffset = log(dNormAct) / log(2.0) * 6.0;
1568    iQpOffset = Int(floor( dQpOffset + 0.49999 ));
1569  }
1570
1571  return Clip3(-pcCU->getSlice()->getSPS()->getQpBDOffset(CHANNEL_TYPE_LUMA), MAX_QP, iBaseQp+iQpOffset );
1572}
1573
1574/** encode a CU block recursively
1575 * \param pcCU
1576 * \param uiAbsPartIdx
1577 * \param uiDepth
1578 * \returns Void
1579 */
1580Void TEncCu::xEncodeCU( TComDataCU* pcCU, UInt uiAbsPartIdx, UInt uiDepth )
1581{
1582        TComPic   *const pcPic   = pcCU->getPic();
1583        TComSlice *const pcSlice = pcCU->getSlice();
1584  const TComSPS   &sps =*(pcSlice->getSPS());
1585  const TComPPS   &pps =*(pcSlice->getPPS());
1586
1587  const UInt maxCUWidth  = sps.getMaxCUWidth();
1588  const UInt maxCUHeight = sps.getMaxCUHeight();
1589
1590        Bool bBoundary = false;
1591        UInt uiLPelX   = pcCU->getCUPelX() + g_auiRasterToPelX[ g_auiZscanToRaster[uiAbsPartIdx] ];
1592  const UInt uiRPelX   = uiLPelX + (maxCUWidth>>uiDepth)  - 1;
1593        UInt uiTPelY   = pcCU->getCUPelY() + g_auiRasterToPelY[ g_auiZscanToRaster[uiAbsPartIdx] ];
1594  const UInt uiBPelY   = uiTPelY + (maxCUHeight>>uiDepth) - 1;
1595
1596#if NH_MV_ENC_DEC_TRAC
1597  DTRACE_CU_S("=========== coding_quadtree ===========\n")
1598  DTRACE_CU("x0", uiLPelX)
1599  DTRACE_CU("x1", uiTPelY)
1600  DTRACE_CU("log2CbSize", maxCUWidth>>uiDepth )
1601  DTRACE_CU("cqtDepth"  , uiDepth)
1602#endif
1603
1604  if( ( uiRPelX < sps.getPicWidthInLumaSamples() ) && ( uiBPelY < sps.getPicHeightInLumaSamples() ) )
1605  {
1606    m_pcEntropyCoder->encodeSplitFlag( pcCU, uiAbsPartIdx, uiDepth );
1607  }
1608  else
1609  {
1610    bBoundary = true;
1611  }
1612
1613  if( ( ( uiDepth < pcCU->getDepth( uiAbsPartIdx ) ) && ( uiDepth < sps.getLog2DiffMaxMinCodingBlockSize() ) ) || bBoundary )
1614  {
1615    UInt uiQNumParts = ( pcPic->getNumPartitionsInCtu() >> (uiDepth<<1) )>>2;
1616    if( uiDepth == pps.getMaxCuDQPDepth() && pps.getUseDQP())
1617    {
1618      setdQPFlag(true);
1619    }
1620
1621    if( uiDepth == pps.getPpsRangeExtension().getDiffCuChromaQpOffsetDepth() && pcSlice->getUseChromaQpAdj())
1622    {
1623      setCodeChromaQpAdjFlag(true);
1624    }
1625
1626    for ( UInt uiPartUnitIdx = 0; uiPartUnitIdx < 4; uiPartUnitIdx++, uiAbsPartIdx+=uiQNumParts )
1627    {
1628      uiLPelX   = pcCU->getCUPelX() + g_auiRasterToPelX[ g_auiZscanToRaster[uiAbsPartIdx] ];
1629      uiTPelY   = pcCU->getCUPelY() + g_auiRasterToPelY[ g_auiZscanToRaster[uiAbsPartIdx] ];
1630      if( ( uiLPelX < sps.getPicWidthInLumaSamples() ) && ( uiTPelY < sps.getPicHeightInLumaSamples() ) )
1631      {
1632        xEncodeCU( pcCU, uiAbsPartIdx, uiDepth+1 );
1633      }
1634    }
1635    return;
1636  }
1637
1638#if NH_MV_ENC_DEC_TRAC
1639  DTRACE_CU_S("=========== coding_unit ===========\n")
1640#endif
1641
1642
1643  if( uiDepth <= pps.getMaxCuDQPDepth() && pps.getUseDQP())
1644  {
1645    setdQPFlag(true);
1646  }
1647
1648  if( uiDepth <= pps.getPpsRangeExtension().getDiffCuChromaQpOffsetDepth() && pcSlice->getUseChromaQpAdj())
1649  {
1650    setCodeChromaQpAdjFlag(true);
1651  }
1652
1653  if (pps.getTransquantBypassEnabledFlag())
1654  {
1655    m_pcEntropyCoder->encodeCUTransquantBypassFlag( pcCU, uiAbsPartIdx );
1656  }
1657
1658  if( !pcSlice->isIntra() )
1659  {
1660    m_pcEntropyCoder->encodeSkipFlag( pcCU, uiAbsPartIdx );
1661  }
1662
1663  if( pcCU->isSkipped( uiAbsPartIdx ) )
1664  {
1665#if NH_MV_ENC_DEC_TRAC
1666    DTRACE_PU_S("=========== prediction_unit ===========\n")
1667    DTRACE_PU("x0", uiLPelX)
1668    DTRACE_PU("x1", uiTPelY)
1669#endif
1670
1671    m_pcEntropyCoder->encodeMergeIndex( pcCU, uiAbsPartIdx );
1672#if NH_3D
1673    m_pcEntropyCoder->encodeARPW( pcCU , uiAbsPartIdx );
1674    m_pcEntropyCoder->encodeICFlag  ( pcCU, uiAbsPartIdx );
1675#endif
1676
1677    finishCU(pcCU,uiAbsPartIdx);
1678    return;
1679  }
1680
1681#if NH_3D
1682  m_pcEntropyCoder->encodeDIS( pcCU, uiAbsPartIdx );
1683  if(!pcCU->getDISFlag(uiAbsPartIdx))
1684  {
1685#endif
1686    m_pcEntropyCoder->encodePredMode( pcCU, uiAbsPartIdx );
1687    m_pcEntropyCoder->encodePartSize( pcCU, uiAbsPartIdx, uiDepth );
1688
1689    if (pcCU->isIntra( uiAbsPartIdx ) && pcCU->getPartitionSize( uiAbsPartIdx ) == SIZE_2Nx2N )
1690    {
1691      m_pcEntropyCoder->encodeIPCMInfo( pcCU, uiAbsPartIdx );
1692
1693      if(pcCU->getIPCMFlag(uiAbsPartIdx))
1694      {
1695#if NH_3D
1696        m_pcEntropyCoder->encodeSDCFlag( pcCU, uiAbsPartIdx );
1697#endif 
1698
1699        // Encode slice finish
1700        finishCU(pcCU,uiAbsPartIdx);
1701        return;
1702      }
1703    }
1704
1705    // prediction Info ( Intra : direction mode, Inter : Mv, reference idx )
1706    m_pcEntropyCoder->encodePredInfo( pcCU, uiAbsPartIdx );
1707#if NH_3D
1708    m_pcEntropyCoder->encodeDBBPFlag( pcCU, uiAbsPartIdx );
1709    m_pcEntropyCoder->encodeSDCFlag( pcCU, uiAbsPartIdx );
1710    m_pcEntropyCoder->encodeARPW( pcCU , uiAbsPartIdx );
1711    m_pcEntropyCoder->encodeICFlag  ( pcCU, uiAbsPartIdx );
1712#endif
1713
1714    // Encode Coefficients
1715    Bool bCodeDQP = getdQPFlag();
1716    Bool codeChromaQpAdj = getCodeChromaQpAdjFlag();
1717    m_pcEntropyCoder->encodeCoeff( pcCU, uiAbsPartIdx, uiDepth, bCodeDQP, codeChromaQpAdj );
1718    setCodeChromaQpAdjFlag( codeChromaQpAdj );
1719    setdQPFlag( bCodeDQP );
1720#if NH_3D
1721  }
1722#endif
1723
1724
1725  // --- write terminating bit ---
1726  finishCU(pcCU,uiAbsPartIdx);
1727}
1728
1729Int xCalcHADs8x8_ISlice(Pel *piOrg, Int iStrideOrg)
1730{
1731  Int k, i, j, jj;
1732  Int diff[64], m1[8][8], m2[8][8], m3[8][8], iSumHad = 0;
1733
1734  for( k = 0; k < 64; k += 8 )
1735  {
1736    diff[k+0] = piOrg[0] ;
1737    diff[k+1] = piOrg[1] ;
1738    diff[k+2] = piOrg[2] ;
1739    diff[k+3] = piOrg[3] ;
1740    diff[k+4] = piOrg[4] ;
1741    diff[k+5] = piOrg[5] ;
1742    diff[k+6] = piOrg[6] ;
1743    diff[k+7] = piOrg[7] ;
1744
1745    piOrg += iStrideOrg;
1746  }
1747
1748  //horizontal
1749  for (j=0; j < 8; j++)
1750  {
1751    jj = j << 3;
1752    m2[j][0] = diff[jj  ] + diff[jj+4];
1753    m2[j][1] = diff[jj+1] + diff[jj+5];
1754    m2[j][2] = diff[jj+2] + diff[jj+6];
1755    m2[j][3] = diff[jj+3] + diff[jj+7];
1756    m2[j][4] = diff[jj  ] - diff[jj+4];
1757    m2[j][5] = diff[jj+1] - diff[jj+5];
1758    m2[j][6] = diff[jj+2] - diff[jj+6];
1759    m2[j][7] = diff[jj+3] - diff[jj+7];
1760
1761    m1[j][0] = m2[j][0] + m2[j][2];
1762    m1[j][1] = m2[j][1] + m2[j][3];
1763    m1[j][2] = m2[j][0] - m2[j][2];
1764    m1[j][3] = m2[j][1] - m2[j][3];
1765    m1[j][4] = m2[j][4] + m2[j][6];
1766    m1[j][5] = m2[j][5] + m2[j][7];
1767    m1[j][6] = m2[j][4] - m2[j][6];
1768    m1[j][7] = m2[j][5] - m2[j][7];
1769
1770    m2[j][0] = m1[j][0] + m1[j][1];
1771    m2[j][1] = m1[j][0] - m1[j][1];
1772    m2[j][2] = m1[j][2] + m1[j][3];
1773    m2[j][3] = m1[j][2] - m1[j][3];
1774    m2[j][4] = m1[j][4] + m1[j][5];
1775    m2[j][5] = m1[j][4] - m1[j][5];
1776    m2[j][6] = m1[j][6] + m1[j][7];
1777    m2[j][7] = m1[j][6] - m1[j][7];
1778  }
1779
1780  //vertical
1781  for (i=0; i < 8; i++)
1782  {
1783    m3[0][i] = m2[0][i] + m2[4][i];
1784    m3[1][i] = m2[1][i] + m2[5][i];
1785    m3[2][i] = m2[2][i] + m2[6][i];
1786    m3[3][i] = m2[3][i] + m2[7][i];
1787    m3[4][i] = m2[0][i] - m2[4][i];
1788    m3[5][i] = m2[1][i] - m2[5][i];
1789    m3[6][i] = m2[2][i] - m2[6][i];
1790    m3[7][i] = m2[3][i] - m2[7][i];
1791
1792    m1[0][i] = m3[0][i] + m3[2][i];
1793    m1[1][i] = m3[1][i] + m3[3][i];
1794    m1[2][i] = m3[0][i] - m3[2][i];
1795    m1[3][i] = m3[1][i] - m3[3][i];
1796    m1[4][i] = m3[4][i] + m3[6][i];
1797    m1[5][i] = m3[5][i] + m3[7][i];
1798    m1[6][i] = m3[4][i] - m3[6][i];
1799    m1[7][i] = m3[5][i] - m3[7][i];
1800
1801    m2[0][i] = m1[0][i] + m1[1][i];
1802    m2[1][i] = m1[0][i] - m1[1][i];
1803    m2[2][i] = m1[2][i] + m1[3][i];
1804    m2[3][i] = m1[2][i] - m1[3][i];
1805    m2[4][i] = m1[4][i] + m1[5][i];
1806    m2[5][i] = m1[4][i] - m1[5][i];
1807    m2[6][i] = m1[6][i] + m1[7][i];
1808    m2[7][i] = m1[6][i] - m1[7][i];
1809  }
1810
1811  for (i = 0; i < 8; i++)
1812  {
1813    for (j = 0; j < 8; j++)
1814    {
1815      iSumHad += abs(m2[i][j]);
1816    }
1817  }
1818  iSumHad -= abs(m2[0][0]);
1819  iSumHad =(iSumHad+2)>>2;
1820  return(iSumHad);
1821}
1822
1823Int  TEncCu::updateCtuDataISlice(TComDataCU* pCtu, Int width, Int height)
1824{
1825  Int  xBl, yBl;
1826  const Int iBlkSize = 8;
1827
1828  Pel* pOrgInit   = pCtu->getPic()->getPicYuvOrg()->getAddr(COMPONENT_Y, pCtu->getCtuRsAddr(), 0);
1829  Int  iStrideOrig = pCtu->getPic()->getPicYuvOrg()->getStride(COMPONENT_Y);
1830  Pel  *pOrg;
1831
1832  Int iSumHad = 0;
1833  for ( yBl=0; (yBl+iBlkSize)<=height; yBl+= iBlkSize)
1834  {
1835    for ( xBl=0; (xBl+iBlkSize)<=width; xBl+= iBlkSize)
1836    {
1837      pOrg = pOrgInit + iStrideOrig*yBl + xBl;
1838      iSumHad += xCalcHADs8x8_ISlice(pOrg, iStrideOrig);
1839    }
1840  }
1841  return(iSumHad);
1842}
1843
1844/** check RD costs for a CU block encoded with merge
1845 * \param rpcBestCU
1846 * \param rpcTempCU
1847 * \param earlyDetectionSkipMode
1848 */
1849Void TEncCu::xCheckRDCostMerge2Nx2N( TComDataCU*& rpcBestCU, TComDataCU*& rpcTempCU DEBUG_STRING_FN_DECLARE(sDebug), Bool *earlyDetectionSkipMode )
1850{
1851  assert( rpcTempCU->getSlice()->getSliceType() != I_SLICE );
1852  if(getFastDeltaQp())
1853  {
1854    return;   // never check merge in fast deltaqp mode
1855  }
1856
1857#if NH_MV
1858  D_PRINT_INC_INDENT( g_traceModeCheck, "xCheckRDCostMerge2Nx2N" );
1859#endif
1860
1861#if NH_3D
1862  TComMvField  cMvFieldNeighbours[MRG_MAX_NUM_CANDS_MEM << 1]; // double length for mv of both lists
1863  UChar uhInterDirNeighbours[MRG_MAX_NUM_CANDS_MEM];
1864#else
1865  TComMvField  cMvFieldNeighbours[2 * MRG_MAX_NUM_CANDS]; // double length for mv of both lists
1866  UChar uhInterDirNeighbours[MRG_MAX_NUM_CANDS];
1867#endif
1868  Int numValidMergeCand = 0;
1869  const Bool bTransquantBypassFlag = rpcTempCU->getCUTransquantBypass(0);
1870
1871  for( UInt ui = 0; ui < rpcTempCU->getSlice()->getMaxNumMergeCand(); ++ui )
1872  {
1873    uhInterDirNeighbours[ui] = 0;
1874  }
1875  UChar uhDepth = rpcTempCU->getDepth( 0 );
1876#if NH_3D
1877  Bool bICFlag = rpcTempCU->getICFlag( 0 );
1878#endif
1879#if NH_3D_VSO // M1  //necessary here?
1880  if( m_pcRdCost->getUseRenModel() )
1881  {
1882    UInt  uiWidth     = m_ppcOrigYuv[uhDepth]->getWidth ( COMPONENT_Y );
1883    UInt  uiHeight    = m_ppcOrigYuv[uhDepth]->getHeight( COMPONENT_Y );
1884    Pel*  piSrc       = m_ppcOrigYuv[uhDepth]->getAddr  ( COMPONENT_Y );
1885    UInt  uiSrcStride = m_ppcOrigYuv[uhDepth]->getStride( COMPONENT_Y );
1886    m_pcRdCost->setRenModelData( rpcTempCU, 0, piSrc, uiSrcStride, uiWidth, uiHeight );
1887  }
1888#endif
1889
1890#if NH_3D 
1891  DisInfo cOrigDisInfo = rpcTempCU->getDvInfo(0);
1892#endif
1893
1894  rpcTempCU->setPartSizeSubParts( SIZE_2Nx2N, 0, uhDepth ); // interprets depth relative to CTU level
1895
1896#if NH_3D
1897  Bool bSPIVMPFlag[MRG_MAX_NUM_CANDS_MEM];
1898  memset(bSPIVMPFlag, false, sizeof(Bool)*MRG_MAX_NUM_CANDS_MEM);
1899  TComMvField*  pcMvFieldSP;
1900  UChar* puhInterDirSP;
1901  pcMvFieldSP = new TComMvField[rpcTempCU->getPic()->getPicSym()->getNumPartitionsInCtu()*2]; 
1902  puhInterDirSP = new UChar[rpcTempCU->getPic()->getPicSym()->getNumPartitionsInCtu()]; 
1903  Int mergeCandBuffer[MRG_MAX_NUM_CANDS_MEM];
1904
1905  for( UInt ui = 0; ui < rpcTempCU->getSlice()->getMaxNumMergeCand(); ++ui )
1906#else
1907
1908#if MCTS_ENC_CHECK
1909  UInt numSpatialMergeCandidates = 0;
1910  rpcTempCU->getInterMergeCandidates( 0, 0, cMvFieldNeighbours, uhInterDirNeighbours, numValidMergeCand, numSpatialMergeCandidates );
1911#else
1912  rpcTempCU->getInterMergeCandidates( 0, 0, cMvFieldNeighbours,uhInterDirNeighbours, numValidMergeCand );
1913#endif
1914  Int mergeCandBuffer[MRG_MAX_NUM_CANDS];
1915  for( UInt ui = 0; ui < numValidMergeCand; ++ui )
1916#endif
1917  {
1918    mergeCandBuffer[ui] = 0;
1919  }
1920
1921#if MCTS_ENC_CHECK && !NH_3D
1922  if (m_pcEncCfg->getTMCTSSEITileConstraint() && rpcTempCU->isLastColumnCTUInTile())
1923  {
1924    numValidMergeCand = numSpatialMergeCandidates;
1925  }
1926#endif
1927
1928  Bool bestIsSkip = false;
1929
1930  UInt iteration;
1931  if ( rpcTempCU->isLosslessCoded(0))
1932  {
1933    iteration = 1;
1934  }
1935  else
1936  {
1937    iteration = 2;
1938  }
1939  DEBUG_STRING_NEW(bestStr)
1940
1941#if NH_3D
1942  Int nARPWMax = rpcTempCU->getSlice()->getARPStepNum() - 1;
1943  if( nARPWMax < 0 || bICFlag )
1944  {
1945    nARPWMax = 0;
1946  }
1947  for( Int nARPW=nARPWMax; nARPW >= 0 ; nARPW-- )
1948  {
1949#if DEBUG_STRING
1950    bestStr.clear(); 
1951#endif
1952    memset( mergeCandBuffer, 0, MRG_MAX_NUM_CANDS_MEM*sizeof(Int) );
1953    rpcTempCU->setPartSizeSubParts( SIZE_2Nx2N, 0, uhDepth ); // interprets depth relative to LCU level
1954    rpcTempCU->setARPWSubParts( (UChar)nARPW , 0 , uhDepth );
1955    rpcTempCU->setICFlagSubParts( bICFlag, 0, 0, uhDepth );
1956    rpcTempCU->getDvInfo(0) = cOrigDisInfo;
1957    rpcTempCU->setDvInfoSubParts(cOrigDisInfo, 0, uhDepth );
1958    Int vspFlag[MRG_MAX_NUM_CANDS_MEM];
1959    memset(vspFlag, 0, sizeof(Int)*MRG_MAX_NUM_CANDS_MEM);
1960    rpcTempCU->initAvailableFlags();
1961#if MCTS_ENC_CHECK
1962    UInt numSpatialMergeCandidates = 0;
1963    rpcTempCU->getInterMergeCandidates( 0, 0, cMvFieldNeighbours, uhInterDirNeighbours, numValidMergeCand, numSpatialMergeCandidates  );
1964#else
1965    rpcTempCU->getInterMergeCandidates( 0, 0, cMvFieldNeighbours, uhInterDirNeighbours, numValidMergeCand );
1966#endif
1967    rpcTempCU->xGetInterMergeCandidates( 0, 0, cMvFieldNeighbours,uhInterDirNeighbours, pcMvFieldSP, puhInterDirSP, numValidMergeCand );
1968
1969    rpcTempCU->buildMCL( cMvFieldNeighbours,uhInterDirNeighbours , vspFlag , bSPIVMPFlag, numValidMergeCand );
1970#endif
1971
1972  for( UInt uiNoResidual = 0; uiNoResidual < iteration; ++uiNoResidual )
1973  {
1974#if NH_MV
1975    D_PRINT_INC_INDENT ( g_traceModeCheck, "uiNoResidual: " + n2s( uiNoResidual) );
1976#endif
1977
1978    for( UInt uiMergeCand = 0; uiMergeCand < numValidMergeCand; ++uiMergeCand )
1979    {
1980#if NH_3D
1981      if( rpcTempCU->getSlice()->getApplyIC() && rpcTempCU->getSlice()->getIcSkipParseFlag() )
1982      {
1983        if( bICFlag && uiMergeCand == 0 ) 
1984        {
1985          continue;
1986        }
1987      }
1988#endif
1989#if NH_MV
1990      D_PRINT_INC_INDENT ( g_traceModeCheck, "uiMergeCand: "+  n2s(uiMergeCand) );
1991#endif
1992
1993      if(!(uiNoResidual==1 && mergeCandBuffer[uiMergeCand]==1))
1994      {
1995        if( !(bestIsSkip && uiNoResidual == 0) )
1996        {
1997          DEBUG_STRING_NEW(tmpStr)
1998          // set MC parameters
1999          rpcTempCU->setPredModeSubParts( MODE_INTER, 0, uhDepth ); // interprets depth relative to CTU level
2000#if NH_3D
2001          rpcTempCU->setICFlagSubParts( bICFlag, 0, 0, uhDepth );
2002#endif
2003          rpcTempCU->setCUTransquantBypassSubParts( bTransquantBypassFlag, 0, uhDepth );
2004          rpcTempCU->setChromaQpAdjSubParts( bTransquantBypassFlag ? 0 : m_cuChromaQpOffsetIdxPlus1, 0, uhDepth );
2005          rpcTempCU->setPartSizeSubParts( SIZE_2Nx2N, 0, uhDepth ); // interprets depth relative to CTU level
2006          rpcTempCU->setMergeFlagSubParts( true, 0, 0, uhDepth ); // interprets depth relative to CTU level
2007          rpcTempCU->setMergeIndexSubParts( uiMergeCand, 0, 0, uhDepth ); // interprets depth relative to CTU level
2008#if NH_3D
2009          rpcTempCU->setARPWSubParts( (UChar)nARPW , 0 , uhDepth );
2010          rpcTempCU->setVSPFlagSubParts( vspFlag[uiMergeCand], 0, 0, uhDepth );
2011          rpcTempCU->setSPIVMPFlagSubParts(bSPIVMPFlag[uiMergeCand], 0, 0, uhDepth);
2012          if (bSPIVMPFlag[uiMergeCand])
2013          {
2014            UInt uiSPAddr;
2015            Int iWidth = rpcTempCU->getWidth(0);
2016            Int iHeight = rpcTempCU->getHeight(0);
2017            Int iNumSPInOneLine, iNumSP, iSPWidth, iSPHeight;
2018            rpcTempCU->getSPPara(iWidth, iHeight, iNumSP, iNumSPInOneLine, iSPWidth, iSPHeight);
2019            for (Int iPartitionIdx = 0; iPartitionIdx < iNumSP; iPartitionIdx++)
2020            {
2021              rpcTempCU->getSPAbsPartIdx(0, iSPWidth, iSPHeight, iPartitionIdx, iNumSPInOneLine, uiSPAddr);
2022              rpcTempCU->setInterDirSP(puhInterDirSP[iPartitionIdx], uiSPAddr, iSPWidth, iSPHeight);
2023              rpcTempCU->getCUMvField( REF_PIC_LIST_0 )->setMvFieldSP(rpcTempCU, uiSPAddr, pcMvFieldSP[2*iPartitionIdx], iSPWidth, iSPHeight);
2024              rpcTempCU->getCUMvField( REF_PIC_LIST_1 )->setMvFieldSP(rpcTempCU, uiSPAddr, pcMvFieldSP[2*iPartitionIdx + 1], iSPWidth, iSPHeight);
2025            }
2026          }
2027          else
2028          {
2029            if ( vspFlag[uiMergeCand] )
2030            {
2031              UInt partAddr;
2032              Int vspSize;
2033              Int width, height;
2034              rpcTempCU->getPartIndexAndSize( 0, partAddr, width, height );
2035              if( uhInterDirNeighbours[ uiMergeCand ] & 0x01 )
2036              {
2037                rpcTempCU->setMvFieldPUForVSP( rpcTempCU, partAddr, width, height, REF_PIC_LIST_0, cMvFieldNeighbours[ 2*uiMergeCand + 0 ].getRefIdx(), vspSize );
2038                rpcTempCU->setVSPFlag( partAddr, vspSize );
2039              }
2040              else
2041              {
2042                rpcTempCU->getCUMvField( REF_PIC_LIST_0 )->setAllMvField( cMvFieldNeighbours[0 + 2*uiMergeCand], SIZE_2Nx2N, 0, 0 ); // interprets depth relative to rpcTempCU level
2043              }
2044              if( uhInterDirNeighbours[ uiMergeCand ] & 0x02 )
2045              {
2046                rpcTempCU->setMvFieldPUForVSP( rpcTempCU, partAddr, width, height, REF_PIC_LIST_1 , cMvFieldNeighbours[ 2*uiMergeCand + 1 ].getRefIdx(), vspSize );
2047                rpcTempCU->setVSPFlag( partAddr, vspSize );
2048              }
2049              else
2050              {
2051                rpcTempCU->getCUMvField( REF_PIC_LIST_1 )->setAllMvField( cMvFieldNeighbours[1 + 2*uiMergeCand], SIZE_2Nx2N, 0, 0 ); // interprets depth relative to rpcTempCU level
2052              }
2053              rpcTempCU->setInterDirSubParts( uhInterDirNeighbours[uiMergeCand], 0, 0, uhDepth ); // interprets depth relative to LCU level
2054            }
2055            else
2056            {
2057#endif
2058              rpcTempCU->setInterDirSubParts( uhInterDirNeighbours[uiMergeCand], 0, 0, uhDepth ); // interprets depth relative to CTU level
2059              rpcTempCU->getCUMvField( REF_PIC_LIST_0 )->setAllMvField( cMvFieldNeighbours[0 + 2*uiMergeCand], SIZE_2Nx2N, 0, 0 ); // interprets depth relative to rpcTempCU level
2060              rpcTempCU->getCUMvField( REF_PIC_LIST_1 )->setAllMvField( cMvFieldNeighbours[1 + 2*uiMergeCand], SIZE_2Nx2N, 0, 0 ); // interprets depth relative to rpcTempCU level
2061#if NH_3D
2062            }
2063#endif
2064#if MCTS_ENC_CHECK
2065            if ( m_pcEncCfg->getTMCTSSEITileConstraint () && (!(m_pcPredSearch->checkTMctsMvp(rpcTempCU))))
2066            {
2067              continue;
2068            }
2069#endif
2070#if NH_3D
2071          }
2072#endif
2073          // do MC
2074          m_pcPredSearch->motionCompensation ( rpcTempCU, m_ppcPredYuvTemp[uhDepth] );
2075          // estimate residual and encode everything
2076#if NH_3D_VSO //M2
2077          if( m_pcRdCost->getUseRenModel() )
2078          { //Reset
2079            UInt  uiWidth     = m_ppcOrigYuv[uhDepth]->getWidth    ( COMPONENT_Y );
2080            UInt  uiHeight    = m_ppcOrigYuv[uhDepth]->getHeight   ( COMPONENT_Y );
2081            Pel*  piSrc       = m_ppcOrigYuv[uhDepth]->getAddr     ( COMPONENT_Y );
2082            UInt  uiSrcStride = m_ppcOrigYuv[uhDepth]->getStride   ( COMPONENT_Y );
2083            m_pcRdCost->setRenModelData( rpcTempCU, 0, piSrc, uiSrcStride, uiWidth, uiHeight );
2084          }
2085#endif
2086          m_pcPredSearch->encodeResAndCalcRdInterCU( rpcTempCU,
2087                                                     m_ppcOrigYuv    [uhDepth],
2088                                                     m_ppcPredYuvTemp[uhDepth],
2089                                                     m_ppcResiYuvTemp[uhDepth],
2090                                                     m_ppcResiYuvBest[uhDepth],
2091                                                     m_ppcRecoYuvTemp[uhDepth],
2092                                                     (uiNoResidual != 0) DEBUG_STRING_PASS_INTO(tmpStr) );
2093
2094#if DEBUG_STRING
2095          DebugInterPredResiReco(tmpStr, *(m_ppcPredYuvTemp[uhDepth]), *(m_ppcResiYuvBest[uhDepth]), *(m_ppcRecoYuvTemp[uhDepth]), DebugStringGetPredModeMask(rpcTempCU->getPredictionMode(0)));
2096#endif
2097
2098          if ((uiNoResidual == 0) && (rpcTempCU->getQtRootCbf(0) == 0))
2099          {
2100            // If no residual when allowing for one, then set mark to not try case where residual is forced to 0
2101            mergeCandBuffer[uiMergeCand] = 1;
2102          }
2103#if NH_3D
2104          rpcTempCU->setDISFlagSubParts( false, 0, uhDepth );
2105          if( rpcTempCU->getSkipFlag(0) )
2106          {
2107            rpcTempCU->setTrIdxSubParts(0, 0, uhDepth);
2108          }
2109          TComDataCU *rpcTempCUPre = rpcTempCU;
2110#endif
2111          Int orgQP = rpcTempCU->getQP( 0 );
2112          xCheckDQP( rpcTempCU );
2113          xCheckBestMode(rpcBestCU, rpcTempCU, uhDepth DEBUG_STRING_PASS_INTO(bestStr) DEBUG_STRING_PASS_INTO(tmpStr));
2114#if NH_3D
2115          if( rpcTempCU->getSlice()->getInterSdcFlag() && !uiNoResidual )
2116          {
2117            Double dOffsetCost[3] = {MAX_DOUBLE,MAX_DOUBLE,MAX_DOUBLE};
2118            for( Int uiOffest = 1 ; uiOffest <= 5 ; uiOffest++ )
2119            {
2120              if( uiOffest > 3)
2121              {
2122                if ( dOffsetCost[0] < (0.9*dOffsetCost[1]) && dOffsetCost[0] < (0.9*dOffsetCost[2]) )
2123                {
2124                  continue;
2125                }
2126                if ( dOffsetCost[1] < dOffsetCost[0] && dOffsetCost[0] < dOffsetCost[2] &&  uiOffest == 5)
2127                {
2128                  continue;
2129                }
2130                if ( dOffsetCost[0] < dOffsetCost[1] && dOffsetCost[2] < dOffsetCost[0] &&  uiOffest == 4)
2131                {
2132                  continue;
2133                }
2134              }
2135              if( rpcTempCU != rpcTempCUPre )
2136              {
2137                rpcTempCU->initEstData( uhDepth, orgQP, bTransquantBypassFlag  );
2138                rpcTempCU->copyPartFrom( rpcBestCU, 0, uhDepth );
2139              }
2140              rpcTempCU->setSkipFlagSubParts( false, 0, uhDepth );
2141              rpcTempCU->setDISFlagSubParts( false, 0, uhDepth );
2142              rpcTempCU->setTrIdxSubParts( 0, 0, uhDepth );
2143              rpcTempCU->setCbfSubParts( 1, COMPONENT_Y, 0, uhDepth );
2144#if NH_3D_VSO //M2
2145              if( m_pcRdCost->getUseRenModel() )
2146              { //Reset
2147                UInt  uiWidth     = m_ppcOrigYuv[uhDepth]->getWidth    ( COMPONENT_Y );
2148                UInt  uiHeight    = m_ppcOrigYuv[uhDepth]->getHeight   ( COMPONENT_Y );
2149                Pel*  piSrc       = m_ppcOrigYuv[uhDepth]->getAddr     ( COMPONENT_Y );
2150                UInt  uiSrcStride = m_ppcOrigYuv[uhDepth]->getStride   ( COMPONENT_Y );
2151                m_pcRdCost->setRenModelData( rpcTempCU, 0, piSrc, uiSrcStride, uiWidth, uiHeight );
2152              }
2153#endif
2154              Int iSdcOffset = 0;
2155              if(uiOffest % 2 == 0)
2156              {
2157                iSdcOffset = uiOffest >> 1;
2158              }
2159              else
2160              {
2161                iSdcOffset = -1 * (uiOffest >> 1);
2162              }
2163              m_pcPredSearch->encodeResAndCalcRdInterSDCCU( rpcTempCU, 
2164                m_ppcOrigYuv[uhDepth], 
2165                ( rpcTempCU != rpcTempCUPre ) ? m_ppcPredYuvBest[uhDepth] : m_ppcPredYuvTemp[uhDepth], 
2166                m_ppcResiYuvTemp[uhDepth], 
2167                m_ppcRecoYuvTemp[uhDepth],
2168                iSdcOffset,
2169                uhDepth );
2170              if (uiOffest <= 3 )
2171              {
2172                dOffsetCost [uiOffest -1] = rpcTempCU->getTotalCost();
2173              }
2174
2175              xCheckDQP( rpcTempCU );
2176              xCheckBestMode( rpcBestCU, rpcTempCU, uhDepth DEBUG_STRING_PASS_INTO(bestStr) DEBUG_STRING_PASS_INTO(tmpStr) );
2177            }
2178          }
2179#endif
2180
2181          rpcTempCU->initEstData( uhDepth, orgQP, bTransquantBypassFlag );
2182
2183          if( m_pcEncCfg->getUseFastDecisionForMerge() && !bestIsSkip )
2184          {
2185#if NH_3D
2186            if( rpcTempCU->getSlice()->getInterSdcFlag() )
2187            {
2188              bestIsSkip = !rpcBestCU->getSDCFlag( 0 ) && ( rpcBestCU->getQtRootCbf(0) == 0 );
2189            }
2190            else
2191            {
2192#endif
2193            bestIsSkip = rpcBestCU->getQtRootCbf(0) == 0;
2194#if NH_3D
2195            }
2196#endif
2197          }
2198        }
2199      }
2200#if NH_MV
2201      D_DEC_INDENT( g_traceModeCheck ); 
2202#endif
2203    }
2204
2205    if(uiNoResidual == 0 && m_pcEncCfg->getUseEarlySkipDetection())
2206    {
2207      if(rpcBestCU->getQtRootCbf( 0 ) == 0)
2208      {
2209        if( rpcBestCU->getMergeFlag( 0 ))
2210        {
2211          *earlyDetectionSkipMode = true;
2212        }
2213        else if(m_pcEncCfg->getMotionEstimationSearchMethod() != MESEARCH_SELECTIVE)
2214        {
2215          Int absoulte_MV=0;
2216          for ( UInt uiRefListIdx = 0; uiRefListIdx < 2; uiRefListIdx++ )
2217          {
2218            if ( rpcBestCU->getSlice()->getNumRefIdx( RefPicList( uiRefListIdx ) ) > 0 )
2219            {
2220              TComCUMvField* pcCUMvField = rpcBestCU->getCUMvField(RefPicList( uiRefListIdx ));
2221              Int iHor = pcCUMvField->getMvd( 0 ).getAbsHor();
2222              Int iVer = pcCUMvField->getMvd( 0 ).getAbsVer();
2223              absoulte_MV+=iHor+iVer;
2224            }
2225          }
2226
2227          if(absoulte_MV == 0)
2228          {
2229            *earlyDetectionSkipMode = true;
2230          }
2231        }
2232      }
2233    }
2234#if NH_MV
2235    D_DEC_INDENT( g_traceModeCheck ); 
2236#endif
2237  }
2238  DEBUG_STRING_APPEND(sDebug, bestStr)
2239
2240#if NH_3D
2241 }
2242 delete[] pcMvFieldSP;
2243 delete[] puhInterDirSP;
2244#endif
2245
2246#if NH_MV
2247 D_DEC_INDENT( g_traceModeCheck );
2248#endif
2249}
2250
2251
2252#if AMP_MRG
2253#if  NH_3D_FAST_TEXTURE_ENCODING
2254Void TEncCu::xCheckRDCostInter( TComDataCU*& rpcBestCU, TComDataCU*& rpcTempCU, PartSize ePartSize DEBUG_STRING_FN_DECLARE(sDebug), Bool bFMD, Bool bUseMRG)
2255#else
2256Void TEncCu::xCheckRDCostInter( TComDataCU*& rpcBestCU, TComDataCU*& rpcTempCU, PartSize ePartSize DEBUG_STRING_FN_DECLARE(sDebug), Bool bUseMRG)
2257#endif
2258#else
2259Void TEncCu::xCheckRDCostInter( TComDataCU*& rpcBestCU, TComDataCU*& rpcTempCU, PartSize ePartSize )
2260#endif
2261{
2262  DEBUG_STRING_NEW(sTest)
2263
2264  if(getFastDeltaQp())
2265  {
2266    const TComSPS &sps=*(rpcTempCU->getSlice()->getSPS());
2267    const UInt fastDeltaQPCuMaxSize = Clip3(sps.getMaxCUHeight()>>(sps.getLog2DiffMaxMinCodingBlockSize()), sps.getMaxCUHeight(), 32u);
2268    if(ePartSize != SIZE_2Nx2N || rpcTempCU->getWidth( 0 ) > fastDeltaQPCuMaxSize)
2269    {
2270      return; // only check necessary 2Nx2N Inter in fast deltaqp mode
2271    }
2272  }
2273
2274#if NH_MV
2275  D_PRINT_INC_INDENT(g_traceModeCheck,   "xCheckRDCostInter; ePartSize:" + n2s( ePartSize) );
2276#endif
2277
2278
2279  // prior to this, rpcTempCU will have just been reset using rpcTempCU->initEstData( uiDepth, iQP, bIsLosslessMode );
2280#if NH_3D
2281  const Bool bTransquantBypassFlag = rpcTempCU->getCUTransquantBypass(0);
2282#endif
2283#if  NH_3D_FAST_TEXTURE_ENCODING
2284  if(!(bFMD && (ePartSize == SIZE_2Nx2N)))  //have  motion estimation or merge check
2285  {
2286#endif
2287  UChar uhDepth = rpcTempCU->getDepth( 0 );
2288#if NH_3D
2289    Bool bFirstTime = true;
2290    Int nARPWMax    = rpcTempCU->getSlice()->getARPStepNum() - 1;
2291
2292    if( nARPWMax < 0 || ePartSize != SIZE_2Nx2N || rpcTempCU->getICFlag(0) )
2293    {
2294      nARPWMax = 0;
2295    }
2296
2297    for( Int nARPW = 0; nARPW <= nARPWMax; nARPW++ )
2298    {
2299#if DEBUG_STRING && NH_MV_ENC_DEC_TRAC
2300      sTest.clear(); 
2301#endif
2302
2303      if( !bFirstTime && rpcTempCU->getSlice()->getIvResPredFlag() )
2304      {
2305        rpcTempCU->initEstData( rpcTempCU->getDepth(0), rpcTempCU->getQP(0),bTransquantBypassFlag );     
2306      }
2307#endif
2308#if NH_3D_VSO // M3
2309      if( m_pcRdCost->getUseRenModel() )
2310      {
2311        UInt  uiWidth     = m_ppcOrigYuv[uhDepth]->getWidth ( COMPONENT_Y );
2312        UInt  uiHeight    = m_ppcOrigYuv[uhDepth]->getHeight( COMPONENT_Y );
2313        Pel*  piSrc       = m_ppcOrigYuv[uhDepth]->getAddr  ( COMPONENT_Y );
2314        UInt  uiSrcStride = m_ppcOrigYuv[uhDepth]->getStride( COMPONENT_Y );
2315        m_pcRdCost->setRenModelData( rpcTempCU, 0, piSrc, uiSrcStride, uiWidth, uiHeight );
2316      }
2317#endif
2318#if NH_3D
2319      rpcTempCU->setDISFlagSubParts( false, 0, uhDepth );
2320#endif
2321  rpcTempCU->setPartSizeSubParts  ( ePartSize,  0, uhDepth );
2322  rpcTempCU->setPredModeSubParts  ( MODE_INTER, 0, uhDepth );
2323  rpcTempCU->setChromaQpAdjSubParts( rpcTempCU->getCUTransquantBypass(0) ? 0 : m_cuChromaQpOffsetIdxPlus1, 0, uhDepth );
2324
2325#if MCTS_ENC_CHECK
2326  rpcTempCU->setTMctsMvpIsValid(true);
2327#endif
2328
2329#if NH_3D
2330      rpcTempCU->setARPWSubParts( (UChar)nARPW , 0 , uhDepth );
2331      if( bFirstTime == false && nARPWMax )
2332      {
2333        rpcTempCU->copyPartFrom( m_ppcWeightedTempCU[uhDepth] , 0 , uhDepth );
2334        rpcTempCU->setARPWSubParts( (UChar)nARPW , 0 , uhDepth );
2335
2336        m_pcPredSearch->motionCompensation( rpcTempCU , m_ppcPredYuvTemp[uhDepth] );
2337      }
2338      else
2339      {
2340        bFirstTime = false;
2341#endif
2342#if AMP_MRG
2343  rpcTempCU->setMergeAMP (true);
2344#if  NH_3D_FAST_TEXTURE_ENCODING
2345        m_pcPredSearch->predInterSearch ( rpcTempCU, m_ppcOrigYuv[uhDepth], m_ppcPredYuvTemp[uhDepth], m_ppcResiYuvTemp[uhDepth], m_ppcRecoYuvTemp[uhDepth] DEBUG_STRING_PASS_INTO(sTest), bFMD, false, bUseMRG );
2346#else
2347  m_pcPredSearch->predInterSearch ( rpcTempCU, m_ppcOrigYuv[uhDepth], m_ppcPredYuvTemp[uhDepth], m_ppcResiYuvTemp[uhDepth], m_ppcRecoYuvTemp[uhDepth] DEBUG_STRING_PASS_INTO(sTest), false, bUseMRG );
2348#endif
2349
2350#else
2351  m_pcPredSearch->predInterSearch ( rpcTempCU, m_ppcOrigYuv[uhDepth], m_ppcPredYuvTemp[uhDepth], m_ppcResiYuvTemp[uhDepth], m_ppcRecoYuvTemp[uhDepth] );
2352#endif
2353#if NH_3D
2354        if( nARPWMax )
2355        {
2356          m_ppcWeightedTempCU[uhDepth]->copyPartFrom( rpcTempCU , 0 , uhDepth );
2357        }
2358      }
2359#endif
2360
2361#if AMP_MRG
2362  if ( !rpcTempCU->getMergeAMP() )
2363  {
2364#if NH_3D
2365        if( nARPWMax )
2366        {
2367          continue;
2368        }
2369        else
2370#endif
2371    {
2372#if NH_MV
2373        D_DEC_INDENT( g_traceModeCheck ); 
2374#endif
2375    return;
2376  }
2377  }
2378#endif
2379#if KWU_RC_MADPRED_E0227
2380      if ( m_pcEncCfg->getUseRateCtrl() && m_pcEncCfg->getLCULevelRC() && ePartSize == SIZE_2Nx2N && uhDepth <= m_addSADDepth )
2381      {
2382        UInt SAD = m_pcRdCost->getSADPart( g_bitDepthY, m_ppcPredYuvTemp[uhDepth]->getLumaAddr(), m_ppcPredYuvTemp[uhDepth]->getStride(),
2383          m_ppcOrigYuv[uhDepth]->getLumaAddr(), m_ppcOrigYuv[uhDepth]->getStride(),
2384          rpcTempCU->getWidth(0), rpcTempCU->getHeight(0) );
2385        m_temporalSAD = (Int)SAD;
2386      }
2387#endif
2388
2389#if MCTS_ENC_CHECK
2390  if (m_pcEncCfg->getTMCTSSEITileConstraint() && (!rpcTempCU->getTMctsMvpIsValid()))
2391  {
2392    return;
2393  }
2394#endif
2395
2396
2397  m_pcPredSearch->encodeResAndCalcRdInterCU( rpcTempCU, m_ppcOrigYuv[uhDepth], m_ppcPredYuvTemp[uhDepth], m_ppcResiYuvTemp[uhDepth], m_ppcResiYuvBest[uhDepth], m_ppcRecoYuvTemp[uhDepth], false DEBUG_STRING_PASS_INTO(sTest) );
2398#if NH_3D
2399  if( rpcTempCU->getQtRootCbf(0)==0 )
2400  {
2401    rpcTempCU->setTrIdxSubParts(0, 0, uhDepth);
2402  }
2403#endif
2404#if NH_3D_VSO // M4
2405  if( m_pcRdCost->getUseLambdaScaleVSO() )
2406  {
2407    rpcTempCU->getTotalCost()  = m_pcRdCost->calcRdCostVSO( rpcTempCU->getTotalBits(), rpcTempCU->getTotalDistortion() );
2408  }
2409  else           
2410#endif
2411    rpcTempCU->getTotalCost()  = m_pcRdCost->calcRdCost( rpcTempCU->getTotalBits(), rpcTempCU->getTotalDistortion() );
2412
2413#if DEBUG_STRING
2414  DebugInterPredResiReco(sTest, *(m_ppcPredYuvTemp[uhDepth]), *(m_ppcResiYuvBest[uhDepth]), *(m_ppcRecoYuvTemp[uhDepth]), DebugStringGetPredModeMask(rpcTempCU->getPredictionMode(0)));
2415#endif
2416#if NH_3D
2417      TComDataCU *rpcTempCUPre = rpcTempCU;
2418#endif
2419
2420  xCheckDQP( rpcTempCU );
2421  xCheckBestMode(rpcBestCU, rpcTempCU, uhDepth DEBUG_STRING_PASS_INTO(sDebug) DEBUG_STRING_PASS_INTO(sTest));
2422#if NH_3D
2423      if( rpcTempCU->getSlice()->getInterSdcFlag() && ePartSize == SIZE_2Nx2N)
2424      {
2425        Double dOffsetCost[3] = {MAX_DOUBLE,MAX_DOUBLE,MAX_DOUBLE};
2426        for( Int uiOffest = 1 ; uiOffest <= 5 ; uiOffest++ )
2427        {
2428          if( uiOffest > 3)
2429          {
2430            if ( dOffsetCost[0] < (0.9*dOffsetCost[1]) && dOffsetCost[0] < (0.9*dOffsetCost[2]) )
2431            {
2432              continue;
2433            }
2434            if ( dOffsetCost[1] < dOffsetCost[0] && dOffsetCost[0] < dOffsetCost[2] &&  uiOffest == 5)
2435            {
2436              continue;
2437            }
2438            if ( dOffsetCost[0] < dOffsetCost[1] && dOffsetCost[2] < dOffsetCost[0] &&  uiOffest == 4)
2439            {
2440              continue;
2441            }
2442          }
2443
2444          if( rpcTempCU != rpcTempCUPre )
2445          {
2446            Int orgQP = rpcBestCU->getQP( 0 );
2447            rpcTempCU->initEstData( uhDepth, orgQP ,bTransquantBypassFlag );     
2448            rpcTempCU->copyPartFrom( rpcBestCU, 0, uhDepth );
2449          }
2450          rpcTempCU->setSkipFlagSubParts( false, 0, uhDepth );
2451          rpcTempCU->setDISFlagSubParts( false, 0, uhDepth );
2452          rpcTempCU->setTrIdxSubParts( 0, 0, uhDepth );
2453          rpcTempCU->setCbfSubParts( 1, COMPONENT_Y, 0, uhDepth );
2454#if NH_3D_VSO // M3
2455          if( m_pcRdCost->getUseRenModel() )
2456          {
2457            UInt  uiWidth     = m_ppcOrigYuv[uhDepth]->getWidth ( COMPONENT_Y );
2458            UInt  uiHeight    = m_ppcOrigYuv[uhDepth]->getHeight( COMPONENT_Y  );
2459            Pel*  piSrc       = m_ppcOrigYuv[uhDepth]->getAddr  ( COMPONENT_Y  );
2460            UInt  uiSrcStride = m_ppcOrigYuv[uhDepth]->getStride( COMPONENT_Y  );
2461            m_pcRdCost->setRenModelData( rpcTempCU, 0, piSrc, uiSrcStride, uiWidth, uiHeight );
2462          }
2463#endif
2464
2465          Int iSdcOffset = 0;
2466          if(uiOffest % 2 == 0)
2467          {
2468            iSdcOffset = uiOffest >> 1;
2469          }
2470          else
2471          {
2472            iSdcOffset = -1 * (uiOffest >> 1);
2473          }
2474          m_pcPredSearch->encodeResAndCalcRdInterSDCCU( rpcTempCU, 
2475            m_ppcOrigYuv[uhDepth],
2476            ( rpcTempCU != rpcTempCUPre ) ? m_ppcPredYuvBest[uhDepth] : m_ppcPredYuvTemp[uhDepth],
2477            m_ppcResiYuvTemp[uhDepth],
2478            m_ppcRecoYuvTemp[uhDepth],
2479            iSdcOffset,
2480            uhDepth );
2481          if (uiOffest <= 3 )
2482          {
2483            dOffsetCost [uiOffest -1] = rpcTempCU->getTotalCost();
2484          }
2485
2486          xCheckDQP( rpcTempCU );
2487          xCheckBestMode(rpcBestCU, rpcTempCU, uhDepth DEBUG_STRING_PASS_INTO(sDebug) DEBUG_STRING_PASS_INTO(sTest));
2488        }
2489
2490      }
2491    }
2492#endif
2493#if  NH_3D_FAST_TEXTURE_ENCODING
2494  }
2495#endif
2496#if NH_MV
2497  D_DEC_INDENT( g_traceModeCheck ); 
2498#endif
2499}
2500
2501#if NH_3D
2502Void TEncCu::xInvalidateOriginalSegments( TComYuv* pOrigYuv, TComYuv* pOrigYuvTemp, Bool* pMask, UInt uiValidSegment )
2503{
2504  UInt  uiWidth     = pOrigYuv->getWidth (COMPONENT_Y);
2505  UInt  uiHeight    = pOrigYuv->getHeight(COMPONENT_Y);
2506  Pel*  piSrc       = pOrigYuv->getAddr(COMPONENT_Y);
2507  UInt  uiSrcStride = pOrigYuv->getStride(COMPONENT_Y);
2508  Pel*  piDst       = pOrigYuvTemp->getAddr(COMPONENT_Y);
2509  UInt  uiDstStride = pOrigYuvTemp->getStride(COMPONENT_Y);
2510 
2511  UInt  uiMaskStride= MAX_CU_SIZE;
2512 
2513  AOF( uiWidth == uiHeight );
2514 
2515  // backup pointer
2516  Bool* pMaskStart = pMask;
2517 
2518  for (Int y=0; y<uiHeight; y++)
2519  {
2520    for (Int x=0; x<uiWidth; x++)
2521    {
2522      UChar ucSegment = (UChar)pMask[x];
2523      AOF( ucSegment < 2 );
2524     
2525      piDst[x] = (ucSegment==uiValidSegment)?piSrc[x]:DBBP_INVALID_SHORT;
2526    }
2527   
2528    piSrc  += uiSrcStride;
2529    piDst  += uiDstStride;
2530    pMask  += uiMaskStride;
2531  }
2532 
2533  // now invalidate chroma
2534  Pel*  piSrcU       = pOrigYuv->getAddr(COMPONENT_Cb);
2535  Pel*  piSrcV       = pOrigYuv->getAddr(COMPONENT_Cr);
2536  UInt  uiSrcStrideC = pOrigYuv->getStride(COMPONENT_Cb);
2537  Pel*  piDstU       = pOrigYuvTemp->getAddr(COMPONENT_Cb);
2538  Pel*  piDstV       = pOrigYuvTemp->getAddr(COMPONENT_Cr);
2539  UInt  uiDstStrideC = pOrigYuvTemp->getStride(COMPONENT_Cb);
2540  pMask = pMaskStart;
2541 
2542  for (Int y=0; y<uiHeight/2; y++)
2543  {
2544    for (Int x=0; x<uiWidth/2; x++)
2545    {
2546      UChar ucSegment = (UChar)pMask[x*2];
2547      AOF( ucSegment < 2 );
2548     
2549      piDstU[x] = (ucSegment==uiValidSegment)?piSrcU[x]:DBBP_INVALID_SHORT;
2550      piDstV[x] = (ucSegment==uiValidSegment)?piSrcV[x]:DBBP_INVALID_SHORT;
2551    }
2552   
2553    piSrcU  += uiSrcStrideC;
2554    piSrcV  += uiSrcStrideC;
2555    piDstU  += uiDstStrideC;
2556    piDstV  += uiDstStrideC;
2557    pMask   += 2*uiMaskStride;
2558  }
2559}
2560
2561Void TEncCu::xCheckRDCostInterDBBP( TComDataCU*& rpcBestCU, TComDataCU*& rpcTempCU  DEBUG_STRING_FN_DECLARE(sDebug), Bool bUseMRG )
2562{
2563  DEBUG_STRING_NEW(sTest)
2564  AOF( !rpcTempCU->getSlice()->getIsDepth() );
2565 
2566  UChar uhDepth = rpcTempCU->getDepth( 0 );
2567 
2568#if NH_3D_VSO
2569  if( m_pcRdCost->getUseRenModel() )
2570  {
2571    UInt  uiWidth     = m_ppcOrigYuv[uhDepth]->getWidth ( COMPONENT_Y );
2572    UInt  uiHeight    = m_ppcOrigYuv[uhDepth]->getHeight( COMPONENT_Y );
2573    Pel*  piSrc       = m_ppcOrigYuv[uhDepth]->getAddr  ( COMPONENT_Y );
2574    UInt  uiSrcStride = m_ppcOrigYuv[uhDepth]->getStride( COMPONENT_Y );
2575    m_pcRdCost->setRenModelData( rpcTempCU, 0, piSrc, uiSrcStride, uiWidth, uiHeight );
2576  }
2577#endif
2578 
2579  UInt uiWidth  = rpcTempCU->getWidth(0);
2580  UInt uiHeight = rpcTempCU->getHeight(0);
2581  AOF( uiWidth == uiHeight );
2582 
2583  if(uiWidth <= 8)
2584  {
2585    return;
2586  }
2587 
2588  rpcTempCU->setPartSizeSubParts( SIZE_2Nx2N,  0, uhDepth );
2589 
2590  // fetch virtual depth block
2591  UInt uiDepthStride = 0;
2592  Pel* pDepthPels = rpcTempCU->getVirtualDepthBlock(0, uiWidth, uiHeight, uiDepthStride);
2593  AOF( pDepthPels != NULL );
2594  AOF( uiDepthStride != 0 );
2595 
2596  PartSize eVirtualPartSize = m_pcPredSearch->getPartitionSizeFromDepth(pDepthPels, uiDepthStride, uiWidth, rpcTempCU);
2597
2598  // derive partitioning from depth
2599  Bool pMask[MAX_CU_SIZE*MAX_CU_SIZE];
2600  Bool bValidMask = m_pcPredSearch->getSegmentMaskFromDepth(pDepthPels, uiDepthStride, uiWidth, uiHeight, pMask, rpcTempCU);
2601 
2602  if( !bValidMask )
2603  {
2604    return;
2605  }
2606 
2607  // find optimal motion/disparity vector for each segment
2608  DisInfo originalDvInfo = rpcTempCU->getDvInfo(0);
2609  DbbpTmpData* pDBBPTmpData = rpcTempCU->getDBBPTmpData();
2610  TComYuv* apPredYuv[2] = { m_ppcRecoYuvTemp[uhDepth], m_ppcPredYuvTemp[uhDepth] };
2611 
2612  // find optimal motion vector fields for both segments (as 2Nx2N)
2613  rpcTempCU->setDepthSubParts( uhDepth, 0 );
2614  rpcTempCU->setPartSizeSubParts( SIZE_2Nx2N,  0, uhDepth );
2615  rpcTempCU->setPredModeSubParts( MODE_INTER, 0, uhDepth );
2616  for( UInt uiSegment = 0; uiSegment < 2; uiSegment++ )
2617  {
2618    rpcTempCU->setDBBPFlagSubParts(true, 0, 0, uhDepth);
2619    rpcTempCU->setDvInfoSubParts(originalDvInfo, 0, uhDepth);
2620   
2621    // invalidate all other segments in original YUV
2622    xInvalidateOriginalSegments(m_ppcOrigYuv[uhDepth], m_ppcOrigYuvDBBP[uhDepth], pMask, uiSegment);
2623   
2624    // do motion estimation for this segment
2625    m_pcRdCost->setUseMask(true);
2626    rpcTempCU->getDBBPTmpData()->eVirtualPartSize = eVirtualPartSize;
2627    rpcTempCU->getDBBPTmpData()->uiVirtualPartIndex = uiSegment;
2628    m_pcPredSearch->predInterSearch( rpcTempCU, m_ppcOrigYuvDBBP[uhDepth], apPredYuv[uiSegment], m_ppcResiYuvTemp[uhDepth], m_ppcResiYuvTemp[uhDepth] DEBUG_STRING_PASS_INTO(sTest), false, bUseMRG );
2629    m_pcRdCost->setUseMask(false);
2630   
2631    // extract motion parameters of full block for this segment
2632    pDBBPTmpData->auhInterDir[uiSegment] = rpcTempCU->getInterDir(0);
2633   
2634    pDBBPTmpData->abMergeFlag[uiSegment] = rpcTempCU->getMergeFlag(0);
2635    pDBBPTmpData->auhMergeIndex[uiSegment] = rpcTempCU->getMergeIndex(0);
2636   
2637    AOF( rpcTempCU->getSPIVMPFlag(0) == false );
2638    AOF( rpcTempCU->getVSPFlag(0) == 0 );
2639   
2640    for ( UInt uiRefListIdx = 0; uiRefListIdx < 2; uiRefListIdx++ )
2641    {
2642      RefPicList eRefList = (RefPicList)uiRefListIdx;
2643     
2644      pDBBPTmpData->acMvd[uiSegment][eRefList] = rpcTempCU->getCUMvField(eRefList)->getMvd(0);
2645      pDBBPTmpData->aiMvpNum[uiSegment][eRefList] = rpcTempCU->getMVPNum(eRefList, 0);
2646      pDBBPTmpData->aiMvpIdx[uiSegment][eRefList] = rpcTempCU->getMVPIdx(eRefList, 0);
2647     
2648      rpcTempCU->getMvField(rpcTempCU, 0, eRefList, pDBBPTmpData->acMvField[uiSegment][eRefList]);
2649    }
2650  }
2651 
2652  // store final motion/disparity information in each PU using derived partitioning
2653  rpcTempCU->setDepthSubParts( uhDepth, 0 );
2654  rpcTempCU->setPartSizeSubParts  ( eVirtualPartSize,  0, uhDepth );
2655  rpcTempCU->setPredModeSubParts  ( MODE_INTER, 0, uhDepth );
2656 
2657  UInt uiPUOffset = ( g_auiPUOffset[UInt( eVirtualPartSize )] << ( ( rpcTempCU->getSlice()->getSPS()->getMaxTotalCUDepth() - uhDepth ) << 1 ) ) >> 4;
2658  for( UInt uiSegment = 0; uiSegment < 2; uiSegment++ )
2659  {
2660    UInt uiPartAddr = uiSegment*uiPUOffset;
2661   
2662    rpcTempCU->setDBBPFlagSubParts(true, uiPartAddr, uiSegment, uhDepth);
2663   
2664    // now set stored information from 2Nx2N motion search to each partition
2665    rpcTempCU->setInterDirSubParts(pDBBPTmpData->auhInterDir[uiSegment], uiPartAddr, uiSegment, uhDepth); // interprets depth relative to LCU level
2666   
2667    rpcTempCU->setMergeFlagSubParts(pDBBPTmpData->abMergeFlag[uiSegment], uiPartAddr, uiSegment, uhDepth);
2668    rpcTempCU->setMergeIndexSubParts(pDBBPTmpData->auhMergeIndex[uiSegment], uiPartAddr, uiSegment, uhDepth);
2669       
2670    for ( UInt uiRefListIdx = 0; uiRefListIdx < 2; uiRefListIdx++ )
2671    {
2672      RefPicList eRefList = (RefPicList)uiRefListIdx;
2673     
2674      rpcTempCU->getCUMvField( eRefList )->setAllMvd(pDBBPTmpData->acMvd[uiSegment][eRefList], eVirtualPartSize, uiPartAddr, 0, uiSegment);
2675      rpcTempCU->setMVPNum(eRefList, uiPartAddr, pDBBPTmpData->aiMvpNum[uiSegment][eRefList]);
2676      rpcTempCU->setMVPIdx(eRefList, uiPartAddr, pDBBPTmpData->aiMvpIdx[uiSegment][eRefList]);
2677     
2678      rpcTempCU->getCUMvField( eRefList )->setAllMvField( pDBBPTmpData->acMvField[uiSegment][eRefList], eVirtualPartSize, uiPartAddr, 0, uiSegment ); // interprets depth relative to rpcTempCU level
2679    }
2680  }
2681 
2682  // reconstruct final prediction signal by combining both segments
2683  Int bitDepthY = rpcTempCU->getSlice()->getSPS()->getBitDepth(CHANNEL_TYPE_LUMA);
2684  m_pcPredSearch->combineSegmentsWithMask(apPredYuv, m_ppcPredYuvTemp[uhDepth], pMask, uiWidth, uiHeight, 0, eVirtualPartSize, bitDepthY);
2685  m_pcPredSearch->encodeResAndCalcRdInterCU( rpcTempCU, m_ppcOrigYuv[uhDepth], m_ppcPredYuvTemp[uhDepth], m_ppcResiYuvTemp[uhDepth], m_ppcResiYuvBest[uhDepth], m_ppcRecoYuvTemp[uhDepth], false DEBUG_STRING_PASS_INTO(sTest) );
2686 
2687  xCheckDQP( rpcTempCU );
2688  xCheckBestMode(rpcBestCU, rpcTempCU, uhDepth  DEBUG_STRING_PASS_INTO(sDebug) DEBUG_STRING_PASS_INTO(sTest) );
2689}
2690
2691Void TEncCu::xCheckRDCostDIS( TComDataCU*& rpcBestCU, TComDataCU*& rpcTempCU, PartSize eSize DEBUG_STRING_FN_DECLARE(sDebug) )
2692{
2693  DEBUG_STRING_NEW(sTest)
2694  UInt uiDepth = rpcTempCU->getDepth( 0 );
2695  if( !rpcBestCU->getSlice()->getIsDepth() || (eSize != SIZE_2Nx2N))
2696  {
2697    return;
2698  }
2699
2700#if NH_MV
2701  D_PRINT_INC_INDENT(g_traceModeCheck, "xCheckRDCostDIS" );
2702#endif
2703
2704#if NH_3D_VSO // M5
2705  if( m_pcRdCost->getUseRenModel() )
2706  {
2707    UInt  uiWidth     = m_ppcOrigYuv[uiDepth]->getWidth   ( COMPONENT_Y );
2708    UInt  uiHeight    = m_ppcOrigYuv[uiDepth]->getHeight  ( COMPONENT_Y );
2709    Pel*  piSrc       = m_ppcOrigYuv[uiDepth]->getAddr    ( COMPONENT_Y );
2710    UInt  uiSrcStride = m_ppcOrigYuv[uiDepth]->getStride  ( COMPONENT_Y );
2711    m_pcRdCost->setRenModelData( rpcTempCU, 0, piSrc, uiSrcStride, uiWidth, uiHeight );
2712  }
2713#endif
2714
2715  rpcTempCU->setSkipFlagSubParts( false, 0, uiDepth );
2716  rpcTempCU->setPartSizeSubParts( SIZE_2Nx2N, 0, uiDepth );
2717  rpcTempCU->setPredModeSubParts( MODE_INTRA, 0, uiDepth );
2718  rpcTempCU->setCUTransquantBypassSubParts( rpcTempCU->getCUTransquantBypass(0), 0, uiDepth );
2719
2720  rpcTempCU->setTrIdxSubParts(0, 0, uiDepth);
2721  rpcTempCU->setCbfSubParts(0, COMPONENT_Y, 0, uiDepth);
2722  rpcTempCU->setDISFlagSubParts(true, 0, uiDepth);
2723  rpcTempCU->setIntraDirSubParts(CHANNEL_TYPE_LUMA, DC_IDX, 0, uiDepth);
2724  rpcTempCU->setSDCFlagSubParts( false, 0, uiDepth);
2725
2726  UInt uiPreCalcDistC;
2727  m_pcPredSearch  ->estIntraPredDIS      ( rpcTempCU, m_ppcOrigYuv[uiDepth], m_ppcPredYuvTemp[uiDepth], m_ppcResiYuvTemp[uiDepth], m_ppcRecoYuvTemp[uiDepth], uiPreCalcDistC, false );
2728
2729#if ENC_DEC_TRACE && NH_MV_ENC_DEC_TRAC
2730  Int oldTraceCopyBack = g_traceCopyBack; 
2731  g_traceCopyBack = false; 
2732#endif
2733  m_ppcRecoYuvTemp[uiDepth]->copyToPicComponent(COMPONENT_Y, rpcTempCU->getPic()->getPicYuvRec(), rpcTempCU->getCtuRsAddr(), rpcTempCU->getZorderIdxInCtu() );
2734#if ENC_DEC_TRACE && NH_MV_ENC_DEC_TRAC 
2735  g_traceCopyBack = oldTraceCopyBack; 
2736#endif
2737
2738  m_pcEntropyCoder->resetBits();
2739  if ( rpcTempCU->getSlice()->getPPS()->getTransquantBypassEnabledFlag())
2740  {
2741    m_pcEntropyCoder->encodeCUTransquantBypassFlag( rpcTempCU, 0,          true );
2742  }
2743  m_pcEntropyCoder->encodeSkipFlag ( rpcTempCU, 0,          true );
2744  m_pcEntropyCoder->encodeDIS( rpcTempCU, 0,          true );
2745
2746  m_pcRDGoOnSbacCoder->store(m_pppcRDSbacCoder[uiDepth][CI_TEMP_BEST]);
2747
2748  rpcTempCU->getTotalBits() = m_pcEntropyCoder->getNumberOfWrittenBits();
2749  rpcTempCU->getTotalBins() = ((TEncBinCABAC *)((TEncSbac*)m_pcEntropyCoder->m_pcEntropyCoderIf)->getEncBinIf())->getBinsCoded();
2750
2751#if NH_3D_VSO // M6
2752  if( m_pcRdCost->getUseLambdaScaleVSO())
2753  {
2754    rpcTempCU->getTotalCost() = m_pcRdCost->calcRdCostVSO( rpcTempCU->getTotalBits(), rpcTempCU->getTotalDistortion() ); 
2755  }
2756  else
2757#endif
2758  rpcTempCU->getTotalCost() = m_pcRdCost->calcRdCost( rpcTempCU->getTotalBits(), rpcTempCU->getTotalDistortion() );
2759
2760  xCheckDQP( rpcTempCU );
2761  xCheckBestMode(rpcBestCU, rpcTempCU, uiDepth  DEBUG_STRING_PASS_INTO(sDebug) DEBUG_STRING_PASS_INTO(sTest) );
2762#if NH_MV
2763  D_DEC_INDENT( g_traceModeCheck ); 
2764#endif
2765}
2766#endif
2767Void TEncCu::xCheckRDCostIntra( TComDataCU *&rpcBestCU,
2768                                TComDataCU *&rpcTempCU,
2769                                PartSize     eSize
2770                                DEBUG_STRING_FN_DECLARE(sDebug)
2771#if NH_3D
2772                              , Bool bOnlyIVP
2773#endif
2774                              )
2775{
2776  DEBUG_STRING_NEW(sTest)
2777
2778  if(getFastDeltaQp())
2779  {
2780    const TComSPS &sps=*(rpcTempCU->getSlice()->getSPS());
2781    const UInt fastDeltaQPCuMaxSize = Clip3(sps.getMaxCUHeight()>>(sps.getLog2DiffMaxMinCodingBlockSize()), sps.getMaxCUHeight(), 32u);
2782    if(rpcTempCU->getWidth( 0 ) > fastDeltaQPCuMaxSize)
2783    {
2784      return; // only check necessary 2Nx2N Intra in fast deltaqp mode
2785    }
2786  }
2787
2788#if NH_MV
2789  D_PRINT_INC_INDENT (g_traceModeCheck, "xCheckRDCostIntra; eSize: " + n2s(eSize) );
2790#endif
2791
2792  UInt uiDepth = rpcTempCU->getDepth( 0 );
2793#if NH_3D_VSO // M5
2794  if( m_pcRdCost->getUseRenModel() )
2795  {
2796    UInt  uiWidth     = m_ppcOrigYuv[uiDepth]->getWidth   ( COMPONENT_Y );
2797    UInt  uiHeight    = m_ppcOrigYuv[uiDepth]->getHeight  ( COMPONENT_Y );
2798    Pel*  piSrc       = m_ppcOrigYuv[uiDepth]->getAddr    ( COMPONENT_Y );
2799    UInt  uiSrcStride = m_ppcOrigYuv[uiDepth]->getStride  ( COMPONENT_Y );
2800    m_pcRdCost->setRenModelData( rpcTempCU, 0, piSrc, uiSrcStride, uiWidth, uiHeight );
2801  }
2802#endif
2803
2804  rpcTempCU->setSkipFlagSubParts( false, 0, uiDepth );
2805#if NH_3D
2806  rpcTempCU->setDISFlagSubParts( false, 0, uiDepth );
2807#endif
2808
2809
2810  rpcTempCU->setPartSizeSubParts( eSize, 0, uiDepth );
2811  rpcTempCU->setPredModeSubParts( MODE_INTRA, 0, uiDepth );
2812  rpcTempCU->setChromaQpAdjSubParts( rpcTempCU->getCUTransquantBypass(0) ? 0 : m_cuChromaQpOffsetIdxPlus1, 0, uiDepth );
2813
2814  Pel resiLuma[NUMBER_OF_STORED_RESIDUAL_TYPES][MAX_CU_SIZE * MAX_CU_SIZE];
2815
2816  m_pcPredSearch->estIntraPredLumaQT( rpcTempCU, m_ppcOrigYuv[uiDepth], m_ppcPredYuvTemp[uiDepth], m_ppcResiYuvTemp[uiDepth], m_ppcRecoYuvTemp[uiDepth], resiLuma DEBUG_STRING_PASS_INTO(sTest) 
2817#if NH_3D
2818                                    , bOnlyIVP
2819#endif
2820                                    );
2821
2822  m_ppcRecoYuvTemp[uiDepth]->copyToPicComponent(COMPONENT_Y, rpcTempCU->getPic()->getPicYuvRec(), rpcTempCU->getCtuRsAddr(), rpcTempCU->getZorderIdxInCtu() );
2823
2824  if (rpcBestCU->getPic()->getChromaFormat()!=CHROMA_400)
2825  {
2826    m_pcPredSearch->estIntraPredChromaQT( rpcTempCU, m_ppcOrigYuv[uiDepth], m_ppcPredYuvTemp[uiDepth], m_ppcResiYuvTemp[uiDepth], m_ppcRecoYuvTemp[uiDepth], resiLuma DEBUG_STRING_PASS_INTO(sTest) );
2827  }
2828 
2829#if NH_3D
2830  if( rpcTempCU->getSDCFlag( 0 ) )
2831  {
2832    assert( rpcTempCU->getTransformIdx(0) == 0 );
2833    assert( rpcTempCU->getCbf(0, COMPONENT_Y) == 1 );
2834  }
2835#endif
2836
2837  m_pcEntropyCoder->resetBits();
2838
2839  if ( rpcTempCU->getSlice()->getPPS()->getTransquantBypassEnabledFlag())
2840  {
2841    m_pcEntropyCoder->encodeCUTransquantBypassFlag( rpcTempCU, 0,          true );
2842  }
2843  m_pcEntropyCoder->encodeSkipFlag ( rpcTempCU, 0,          true );
2844#if NH_3D
2845  m_pcEntropyCoder->encodeDIS( rpcTempCU, 0,          true );
2846  if(!rpcTempCU->getDISFlag(0))
2847  {
2848#endif
2849    m_pcEntropyCoder->encodePredMode( rpcTempCU, 0,          true );
2850    m_pcEntropyCoder->encodePartSize( rpcTempCU, 0, uiDepth, true );
2851    m_pcEntropyCoder->encodePredInfo( rpcTempCU, 0 );
2852    m_pcEntropyCoder->encodeIPCMInfo(rpcTempCU, 0, true );
2853#if NH_3D
2854    m_pcEntropyCoder->encodeSDCFlag( rpcTempCU, 0, true );
2855#endif
2856
2857    // Encode Coefficients
2858    Bool bCodeDQP = getdQPFlag();
2859    Bool codeChromaQpAdjFlag = getCodeChromaQpAdjFlag();
2860    m_pcEntropyCoder->encodeCoeff( rpcTempCU, 0, uiDepth, bCodeDQP, codeChromaQpAdjFlag );
2861    setCodeChromaQpAdjFlag( codeChromaQpAdjFlag );
2862    setdQPFlag( bCodeDQP );
2863#if NH_3D
2864  }
2865#endif
2866  m_pcRDGoOnSbacCoder->store(m_pppcRDSbacCoder[uiDepth][CI_TEMP_BEST]);
2867
2868  rpcTempCU->getTotalBits() = m_pcEntropyCoder->getNumberOfWrittenBits();
2869  rpcTempCU->getTotalBins() = ((TEncBinCABAC *)((TEncSbac*)m_pcEntropyCoder->m_pcEntropyCoderIf)->getEncBinIf())->getBinsCoded();
2870#if NH_3D_VSO // M6
2871  if( m_pcRdCost->getUseLambdaScaleVSO()) 
2872  {
2873    rpcTempCU->getTotalCost() = m_pcRdCost->calcRdCostVSO( rpcTempCU->getTotalBits(), rpcTempCU->getTotalDistortion() ); 
2874  }
2875  else
2876#endif
2877    rpcTempCU->getTotalCost() = m_pcRdCost->calcRdCost( rpcTempCU->getTotalBits(), rpcTempCU->getTotalDistortion() );
2878
2879  xCheckDQP( rpcTempCU );
2880
2881  xCheckBestMode(rpcBestCU, rpcTempCU, uiDepth DEBUG_STRING_PASS_INTO(sDebug) DEBUG_STRING_PASS_INTO(sTest));
2882
2883#if NH_MV
2884  D_DEC_INDENT( g_traceModeCheck ); 
2885#endif
2886}
2887
2888
2889/** Check R-D costs for a CU with PCM mode.
2890 * \param rpcBestCU pointer to best mode CU data structure
2891 * \param rpcTempCU pointer to testing mode CU data structure
2892 * \returns Void
2893 *
2894 * \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.
2895 */
2896Void TEncCu::xCheckIntraPCM( TComDataCU*& rpcBestCU, TComDataCU*& rpcTempCU )
2897{
2898  if(getFastDeltaQp())
2899  {
2900    const TComSPS &sps=*(rpcTempCU->getSlice()->getSPS());
2901    const UInt fastDeltaQPCuMaxPCMSize = Clip3((UInt)1<<sps.getPCMLog2MinSize(), (UInt)1<<sps.getPCMLog2MaxSize(), 32u);
2902    if (rpcTempCU->getWidth( 0 ) > fastDeltaQPCuMaxPCMSize)
2903    {
2904      return;   // only check necessary PCM in fast deltaqp mode
2905    }
2906  }
2907 
2908  UInt uiDepth = rpcTempCU->getDepth( 0 );
2909
2910#if NH_3D_VSO // VERY NEW
2911  if( m_pcRdCost->getUseRenModel() )
2912  {
2913    UInt  uiWidth     = m_ppcOrigYuv[uiDepth]->getWidth   ( COMPONENT_Y );
2914    UInt  uiHeight    = m_ppcOrigYuv[uiDepth]->getHeight  ( COMPONENT_Y );
2915    Pel*  piSrc       = m_ppcOrigYuv[uiDepth]->getAddr    ( COMPONENT_Y );
2916    UInt  uiSrcStride = m_ppcOrigYuv[uiDepth]->getStride  ( COMPONENT_Y );
2917    m_pcRdCost->setRenModelData( rpcTempCU, 0, piSrc, uiSrcStride, uiWidth, uiHeight );
2918  }
2919#endif
2920  rpcTempCU->setSkipFlagSubParts( false, 0, uiDepth );
2921#if NH_3D
2922  rpcTempCU->setDISFlagSubParts( false, 0, uiDepth );
2923#endif
2924  rpcTempCU->setIPCMFlag(0, true);
2925  rpcTempCU->setIPCMFlagSubParts (true, 0, rpcTempCU->getDepth(0));
2926  rpcTempCU->setPartSizeSubParts( SIZE_2Nx2N, 0, uiDepth );
2927  rpcTempCU->setPredModeSubParts( MODE_INTRA, 0, uiDepth );
2928  rpcTempCU->setTrIdxSubParts ( 0, 0, uiDepth );
2929  rpcTempCU->setChromaQpAdjSubParts( rpcTempCU->getCUTransquantBypass(0) ? 0 : m_cuChromaQpOffsetIdxPlus1, 0, uiDepth );
2930
2931  m_pcPredSearch->IPCMSearch( rpcTempCU, m_ppcOrigYuv[uiDepth], m_ppcPredYuvTemp[uiDepth], m_ppcResiYuvTemp[uiDepth], m_ppcRecoYuvTemp[uiDepth]);
2932
2933  m_pcRDGoOnSbacCoder->load(m_pppcRDSbacCoder[uiDepth][CI_CURR_BEST]);
2934
2935  m_pcEntropyCoder->resetBits();
2936
2937  if ( rpcTempCU->getSlice()->getPPS()->getTransquantBypassEnabledFlag())
2938  {
2939    m_pcEntropyCoder->encodeCUTransquantBypassFlag( rpcTempCU, 0,          true );
2940  }
2941
2942  m_pcEntropyCoder->encodeSkipFlag ( rpcTempCU, 0,          true );
2943#if NH_3D
2944  m_pcEntropyCoder->encodeDIS( rpcTempCU, 0,          true );
2945#endif
2946  m_pcEntropyCoder->encodePredMode ( rpcTempCU, 0,          true );
2947  m_pcEntropyCoder->encodePartSize ( rpcTempCU, 0, uiDepth, true );
2948  m_pcEntropyCoder->encodeIPCMInfo ( rpcTempCU, 0, true );
2949#if NH_3D
2950  m_pcEntropyCoder->encodeSDCFlag( rpcTempCU, 0, true );
2951#endif
2952  m_pcRDGoOnSbacCoder->store(m_pppcRDSbacCoder[uiDepth][CI_TEMP_BEST]);
2953
2954  rpcTempCU->getTotalBits() = m_pcEntropyCoder->getNumberOfWrittenBits();
2955  rpcTempCU->getTotalBins() = ((TEncBinCABAC *)((TEncSbac*)m_pcEntropyCoder->m_pcEntropyCoderIf)->getEncBinIf())->getBinsCoded();
2956#if NH_3D_VSO // M44
2957  if ( m_pcRdCost->getUseLambdaScaleVSO() )
2958  {
2959    rpcTempCU->getTotalCost() = m_pcRdCost->calcRdCostVSO( rpcTempCU->getTotalBits(), rpcTempCU->getTotalDistortion() );
2960  }
2961  else
2962#endif
2963    rpcTempCU->getTotalCost() = m_pcRdCost->calcRdCost( rpcTempCU->getTotalBits(), rpcTempCU->getTotalDistortion() );
2964
2965  xCheckDQP( rpcTempCU );
2966  DEBUG_STRING_NEW(a)
2967  DEBUG_STRING_NEW(b)
2968  xCheckBestMode(rpcBestCU, rpcTempCU, uiDepth DEBUG_STRING_PASS_INTO(a) DEBUG_STRING_PASS_INTO(b));
2969}
2970
2971/** check whether current try is the best with identifying the depth of current try
2972 * \param rpcBestCU
2973 * \param rpcTempCU
2974 * \param uiDepth
2975 */
2976Void TEncCu::xCheckBestMode( TComDataCU*& rpcBestCU, TComDataCU*& rpcTempCU, UInt uiDepth DEBUG_STRING_FN_DECLARE(sParent) DEBUG_STRING_FN_DECLARE(sTest) DEBUG_STRING_PASS_INTO(Bool bAddSizeInfo) )
2977{
2978  if( rpcTempCU->getTotalCost() < rpcBestCU->getTotalCost() )
2979  {
2980    TComYuv* pcYuv;
2981    // Change Information data
2982    TComDataCU* pcCU = rpcBestCU;
2983    rpcBestCU = rpcTempCU;
2984    rpcTempCU = pcCU;
2985
2986    // Change Prediction data
2987    pcYuv = m_ppcPredYuvBest[uiDepth];
2988    m_ppcPredYuvBest[uiDepth] = m_ppcPredYuvTemp[uiDepth];
2989    m_ppcPredYuvTemp[uiDepth] = pcYuv;
2990
2991    // Change Reconstruction data
2992    pcYuv = m_ppcRecoYuvBest[uiDepth];
2993    m_ppcRecoYuvBest[uiDepth] = m_ppcRecoYuvTemp[uiDepth];
2994    m_ppcRecoYuvTemp[uiDepth] = pcYuv;
2995
2996    pcYuv = NULL;
2997    pcCU  = NULL;
2998
2999    // store temp best CI for next CU coding
3000    m_pppcRDSbacCoder[uiDepth][CI_TEMP_BEST]->store(m_pppcRDSbacCoder[uiDepth][CI_NEXT_BEST]);
3001
3002
3003#if DEBUG_STRING
3004    DEBUG_STRING_SWAP(sParent, sTest)
3005    const PredMode predMode=rpcBestCU->getPredictionMode(0);
3006    if ((DebugOptionList::DebugString_Structure.getInt()&DebugStringGetPredModeMask(predMode)) && bAddSizeInfo)
3007    {
3008      std::stringstream ss(stringstream::out);
3009      ss <<"###: " << (predMode==MODE_INTRA?"Intra   ":"Inter   ") << partSizeToString[rpcBestCU->getPartitionSize(0)] << " CU at " << rpcBestCU->getCUPelX() << ", " << rpcBestCU->getCUPelY() << " width=" << UInt(rpcBestCU->getWidth(0)) << std::endl;
3010      sParent+=ss.str();
3011    }
3012#endif
3013  }
3014}
3015
3016Void TEncCu::xCheckDQP( TComDataCU* pcCU )
3017{
3018  UInt uiDepth = pcCU->getDepth( 0 );
3019
3020  const TComPPS &pps = *(pcCU->getSlice()->getPPS());
3021  if ( pps.getUseDQP() && uiDepth <= pps.getMaxCuDQPDepth() )
3022  {
3023    if ( pcCU->getQtRootCbf( 0) )
3024    {
3025      m_pcEntropyCoder->resetBits();
3026      m_pcEntropyCoder->encodeQP( pcCU, 0, false );
3027      pcCU->getTotalBits() += m_pcEntropyCoder->getNumberOfWrittenBits(); // dQP bits
3028      pcCU->getTotalBins() += ((TEncBinCABAC *)((TEncSbac*)m_pcEntropyCoder->m_pcEntropyCoderIf)->getEncBinIf())->getBinsCoded();
3029#if NH_3D_VSO // M45
3030      if ( m_pcRdCost->getUseLambdaScaleVSO() )     
3031      {
3032        pcCU->getTotalCost() = m_pcRdCost->calcRdCostVSO( pcCU->getTotalBits(), pcCU->getTotalDistortion() );     
3033      }
3034      else
3035#endif
3036        pcCU->getTotalCost() = m_pcRdCost->calcRdCost( pcCU->getTotalBits(), pcCU->getTotalDistortion() );
3037    }
3038    else
3039    {
3040      pcCU->setQPSubParts( pcCU->getRefQP( 0 ), 0, uiDepth ); // set QP to default QP
3041    }
3042  }
3043}
3044
3045Void TEncCu::xCopyAMVPInfo (AMVPInfo* pSrc, AMVPInfo* pDst)
3046{
3047  pDst->iN = pSrc->iN;
3048  for (Int i = 0; i < pSrc->iN; i++)
3049  {
3050    pDst->m_acMvCand[i] = pSrc->m_acMvCand[i];
3051  }
3052}
3053Void TEncCu::xCopyYuv2Pic(TComPic* rpcPic, UInt uiCUAddr, UInt uiAbsPartIdx, UInt uiDepth, UInt uiSrcDepth )
3054{
3055  UInt uiAbsPartIdxInRaster = g_auiZscanToRaster[uiAbsPartIdx];
3056  UInt uiSrcBlkWidth = rpcPic->getNumPartInCtuWidth() >> (uiSrcDepth);
3057  UInt uiBlkWidth    = rpcPic->getNumPartInCtuWidth() >> (uiDepth);
3058  UInt uiPartIdxX = ( ( uiAbsPartIdxInRaster % rpcPic->getNumPartInCtuWidth() ) % uiSrcBlkWidth) / uiBlkWidth;
3059  UInt uiPartIdxY = ( ( uiAbsPartIdxInRaster / rpcPic->getNumPartInCtuWidth() ) % uiSrcBlkWidth) / uiBlkWidth;
3060  UInt uiPartIdx = uiPartIdxY * ( uiSrcBlkWidth / uiBlkWidth ) + uiPartIdxX;
3061  m_ppcRecoYuvBest[uiSrcDepth]->copyToPicYuv( rpcPic->getPicYuvRec (), uiCUAddr, uiAbsPartIdx, uiDepth - uiSrcDepth, uiPartIdx);
3062
3063#if ENC_DEC_TRACE && NH_MV_ENC_DEC_TRAC
3064  Bool oldtraceCopyBack = g_traceCopyBack;
3065  g_traceCopyBack = false; 
3066#endif
3067  m_ppcPredYuvBest[uiSrcDepth]->copyToPicYuv( rpcPic->getPicYuvPred (), uiCUAddr, uiAbsPartIdx, uiDepth - uiSrcDepth, uiPartIdx);
3068
3069#if ENC_DEC_TRACE && NH_MV_ENC_DEC_TRAC
3070  g_traceCopyBack = oldtraceCopyBack; 
3071#endif
3072}
3073
3074Void TEncCu::xCopyYuv2Tmp( UInt uiPartUnitIdx, UInt uiNextDepth )
3075{
3076  UInt uiCurrDepth = uiNextDepth - 1;
3077  m_ppcRecoYuvBest[uiNextDepth]->copyToPartYuv( m_ppcRecoYuvTemp[uiCurrDepth], uiPartUnitIdx );
3078  m_ppcPredYuvBest[uiNextDepth]->copyToPartYuv( m_ppcPredYuvBest[uiCurrDepth], uiPartUnitIdx);
3079}
3080
3081/** Function for filling the PCM buffer of a CU using its original sample array
3082 * \param pCU pointer to current CU
3083 * \param pOrgYuv pointer to original sample array
3084 */
3085Void TEncCu::xFillPCMBuffer     ( TComDataCU* pCU, TComYuv* pOrgYuv )
3086{
3087  const ChromaFormat format = pCU->getPic()->getChromaFormat();
3088  const UInt numberValidComponents = getNumberValidComponents(format);
3089  for (UInt componentIndex = 0; componentIndex < numberValidComponents; componentIndex++)
3090  {
3091    const ComponentID component = ComponentID(componentIndex);
3092
3093    const UInt width  = pCU->getWidth(0)  >> getComponentScaleX(component, format);
3094    const UInt height = pCU->getHeight(0) >> getComponentScaleY(component, format);
3095
3096    Pel *source      = pOrgYuv->getAddr(component, 0, width);
3097    Pel *destination = pCU->getPCMSample(component);
3098
3099    const UInt sourceStride = pOrgYuv->getStride(component);
3100
3101    for (Int line = 0; line < height; line++)
3102    {
3103      for (Int column = 0; column < width; column++)
3104      {
3105        destination[column] = source[column];
3106      }
3107
3108      source      += sourceStride;
3109      destination += width;
3110    }
3111  }
3112}
3113
3114#if ADAPTIVE_QP_SELECTION
3115/** Collect ARL statistics from one block
3116  */
3117Int TEncCu::xTuCollectARLStats(TCoeff* rpcCoeff, TCoeff* rpcArlCoeff, Int NumCoeffInCU, Double* cSum, UInt* numSamples )
3118{
3119  for( Int n = 0; n < NumCoeffInCU; n++ )
3120  {
3121    TCoeff u = abs( rpcCoeff[ n ] );
3122    TCoeff absc = rpcArlCoeff[ n ];
3123
3124    if( u != 0 )
3125    {
3126      if( u < LEVEL_RANGE )
3127      {
3128        cSum[ u ] += ( Double )absc;
3129        numSamples[ u ]++;
3130      }
3131      else
3132      {
3133        cSum[ LEVEL_RANGE ] += ( Double )absc - ( Double )( u << ARL_C_PRECISION );
3134        numSamples[ LEVEL_RANGE ]++;
3135      }
3136    }
3137  }
3138
3139  return 0;
3140}
3141
3142//! Collect ARL statistics from one CTU
3143Void TEncCu::xCtuCollectARLStats(TComDataCU* pCtu )
3144{
3145  Double cSum[ LEVEL_RANGE + 1 ];     //: the sum of DCT coefficients corresponding to data type and quantization output
3146  UInt numSamples[ LEVEL_RANGE + 1 ]; //: the number of coefficients corresponding to data type and quantization output
3147
3148  TCoeff* pCoeffY = pCtu->getCoeff(COMPONENT_Y);
3149  TCoeff* pArlCoeffY = pCtu->getArlCoeff(COMPONENT_Y);
3150  const TComSPS &sps = *(pCtu->getSlice()->getSPS());
3151
3152  const UInt uiMinCUWidth = sps.getMaxCUWidth() >> sps.getMaxTotalCUDepth(); // NOTE: ed - this is not the minimum CU width. It is the square-root of the number of coefficients per part.
3153  const UInt uiMinNumCoeffInCU = 1 << uiMinCUWidth;                          // NOTE: ed - what is this?
3154
3155  memset( cSum, 0, sizeof( Double )*(LEVEL_RANGE+1) );
3156  memset( numSamples, 0, sizeof( UInt )*(LEVEL_RANGE+1) );
3157
3158  // Collect stats to cSum[][] and numSamples[][]
3159  for(Int i = 0; i < pCtu->getTotalNumPart(); i ++ )
3160  {
3161    UInt uiTrIdx = pCtu->getTransformIdx(i);
3162
3163    if(pCtu->isInter(i) && pCtu->getCbf( i, COMPONENT_Y, uiTrIdx ) )
3164    {
3165      xTuCollectARLStats(pCoeffY, pArlCoeffY, uiMinNumCoeffInCU, cSum, numSamples);
3166    }//Note that only InterY is processed. QP rounding is based on InterY data only.
3167
3168    pCoeffY  += uiMinNumCoeffInCU;
3169    pArlCoeffY  += uiMinNumCoeffInCU;
3170  }
3171
3172  for(Int u=1; u<LEVEL_RANGE;u++)
3173  {
3174    m_pcTrQuant->getSliceSumC()[u] += cSum[ u ] ;
3175    m_pcTrQuant->getSliceNSamples()[u] += numSamples[ u ] ;
3176  }
3177  m_pcTrQuant->getSliceSumC()[LEVEL_RANGE] += cSum[ LEVEL_RANGE ] ;
3178  m_pcTrQuant->getSliceNSamples()[LEVEL_RANGE] += numSamples[ LEVEL_RANGE ] ;
3179}
3180#endif
3181
3182//! \}
Note: See TracBrowser for help on using the repository browser.