source: 3DVCSoftware/branches/HTM-9.3-dev2-MediaTek/source/Lib/TLibCommon/TComDataCU.cpp @ 805

Last change on this file since 805 was 805, checked in by mediatek-htm, 11 years ago

Integration of CABAC simplification for IC flag in JCT3V-G0061. The MACRO is "MTK_IC_FLAG_CABAC_SIMP_G0061".

by Yi-Wen Chen (yiwen.chen@…)

  • Property svn:eol-style set to native
File size: 255.9 KB
Line 
1/* The copyright in this software is being made available under the BSD
2 * License, included below. This software may be subject to other third party
3 * and contributor rights, including patent rights, and no such rights are
4 * granted under this license. 
5 *
6 * Copyright (c) 2010-2013, ITU/ISO/IEC
7 * All rights reserved.
8 *
9 * Redistribution and use in source and binary forms, with or without
10 * modification, are permitted provided that the following conditions are met:
11 *
12 *  * Redistributions of source code must retain the above copyright notice,
13 *    this list of conditions and the following disclaimer.
14 *  * Redistributions in binary form must reproduce the above copyright notice,
15 *    this list of conditions and the following disclaimer in the documentation
16 *    and/or other materials provided with the distribution.
17 *  * Neither the name of the ITU/ISO/IEC nor the names of its contributors may
18 *    be used to endorse or promote products derived from this software without
19 *    specific prior written permission.
20 *
21 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
22 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
23 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
24 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS
25 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
26 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
27 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
28 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
29 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
30 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
31 * THE POSSIBILITY OF SUCH DAMAGE.
32 */
33
34/** \file     TComDataCU.cpp
35    \brief    CU data structure
36    \todo     not all entities are documented
37*/
38
39#include "TComDataCU.h"
40#include "TComPic.h"
41
42//! \ingroup TLibCommon
43//! \{
44
45#if ADAPTIVE_QP_SELECTION
46Int * TComDataCU::m_pcGlbArlCoeffY  = NULL;
47Int * TComDataCU::m_pcGlbArlCoeffCb = NULL;
48Int * TComDataCU::m_pcGlbArlCoeffCr = NULL;
49#endif
50
51// ====================================================================================================================
52// Constructor / destructor / create / destroy
53// ====================================================================================================================
54
55TComDataCU::TComDataCU()
56{
57  m_pcPic              = NULL;
58  m_pcSlice            = NULL;
59  m_puhDepth           = NULL;
60 
61  m_skipFlag           = NULL;
62
63  m_pePartSize         = NULL;
64  m_pePredMode         = NULL;
65  m_CUTransquantBypass = NULL;
66  m_puhWidth           = NULL;
67  m_puhHeight          = NULL;
68  m_phQP               = NULL;
69  m_pbMergeFlag        = NULL;
70  m_puhMergeIndex      = NULL;
71  m_puhLumaIntraDir    = NULL;
72  m_puhChromaIntraDir  = NULL;
73  m_puhInterDir        = NULL;
74  m_puhTrIdx           = NULL;
75  m_puhTransformSkip[0] = NULL;
76  m_puhTransformSkip[1] = NULL;
77  m_puhTransformSkip[2] = NULL;
78  m_puhCbf[0]          = NULL;
79  m_puhCbf[1]          = NULL;
80  m_puhCbf[2]          = NULL;
81  m_pcTrCoeffY         = NULL;
82  m_pcTrCoeffCb        = NULL;
83  m_pcTrCoeffCr        = NULL;
84#if ADAPTIVE_QP_SELECTION 
85  m_ArlCoeffIsAliasedAllocation = false;
86  m_pcArlCoeffY        = NULL;
87  m_pcArlCoeffCb       = NULL;
88  m_pcArlCoeffCr       = NULL;
89#endif
90 
91  m_pbIPCMFlag         = NULL;
92  m_pcIPCMSampleY      = NULL;
93  m_pcIPCMSampleCb     = NULL;
94  m_pcIPCMSampleCr     = NULL;
95
96  m_pcPattern          = NULL;
97 
98  m_pcCUAboveLeft      = NULL;
99  m_pcCUAboveRight     = NULL;
100  m_pcCUAbove          = NULL;
101  m_pcCULeft           = NULL;
102 
103  m_apcCUColocated[0]  = NULL;
104  m_apcCUColocated[1]  = NULL;
105 
106  m_apiMVPIdx[0]       = NULL;
107  m_apiMVPIdx[1]       = NULL;
108  m_apiMVPNum[0]       = NULL;
109  m_apiMVPNum[1]       = NULL;
110
111#if H_3D_DIM
112  for( Int i = 0; i < DIM_NUM_TYPE; i++ )
113  {
114    m_dimDeltaDC[i][0] = NULL; 
115    m_dimDeltaDC[i][1] = NULL;
116  }
117#if H_3D_DIM_DMM
118  for( Int i = 0; i < DMM_NUM_TYPE; i++ )
119  {
120    m_dmmWedgeTabIdx[i] = NULL;
121  }
122#endif
123#if H_3D_DIM_SDC
124  m_pbSDCFlag             = NULL;
125  m_apSegmentDCOffset[0]  = NULL;
126  m_apSegmentDCOffset[1]  = NULL;
127#endif
128#endif
129  m_bDecSubCu          = false;
130  m_sliceStartCU        = 0;
131  m_sliceSegmentStartCU = 0;
132#if H_3D_NBDV
133  m_pDvInfo              = NULL;
134#endif
135#if H_3D_VSP
136  m_piVSPFlag            = NULL;
137#endif
138#if H_3D_SPIVMP
139  m_pbSPIVMPFlag         = NULL;
140#endif
141#if H_3D_ARP
142  m_puhARPW              = NULL;
143#endif
144#if H_3D_IC
145  m_pbICFlag             = NULL;
146#endif
147#if H_3D_INTER_SDC
148  m_pbInterSDCFlag       = NULL;
149  for( Int i = 0; i < 4; i++ )
150  {
151    m_apSegmentInterDCOffset[i] = NULL;
152  }
153  m_pucInterSDCMask       = NULL;
154#endif
155}
156
157TComDataCU::~TComDataCU()
158{
159}
160
161Void TComDataCU::create(UInt uiNumPartition, UInt uiWidth, UInt uiHeight, Bool bDecSubCu, Int unitSize
162#if ADAPTIVE_QP_SELECTION
163                        , Bool bGlobalRMARLBuffer
164#endif                                             
165                        )
166{
167  m_bDecSubCu = bDecSubCu;
168 
169  m_pcPic              = NULL;
170  m_pcSlice            = NULL;
171  m_uiNumPartition     = uiNumPartition;
172  m_unitSize = unitSize;
173 
174  if ( !bDecSubCu )
175  {
176    m_phQP               = (Char*     )xMalloc(Char,     uiNumPartition);
177    m_puhDepth           = (UChar*    )xMalloc(UChar,    uiNumPartition);
178    m_puhWidth           = (UChar*    )xMalloc(UChar,    uiNumPartition);
179    m_puhHeight          = (UChar*    )xMalloc(UChar,    uiNumPartition);
180
181    m_skipFlag           = new Bool[ uiNumPartition ];
182
183    m_pePartSize         = new Char[ uiNumPartition ];
184    memset( m_pePartSize, SIZE_NONE,uiNumPartition * sizeof( *m_pePartSize ) );
185    m_pePredMode         = new Char[ uiNumPartition ];
186    m_CUTransquantBypass = new Bool[ uiNumPartition ];
187    m_pbMergeFlag        = (Bool*  )xMalloc(Bool,   uiNumPartition);
188    m_puhMergeIndex      = (UChar* )xMalloc(UChar,  uiNumPartition);
189#if H_3D_VSP
190    m_piVSPFlag          = (Char*  )xMalloc(Char,   uiNumPartition);
191#endif
192#if H_3D_SPIVMP
193    m_pbSPIVMPFlag       = (Bool*  )xMalloc(Bool,   uiNumPartition);
194#endif
195    m_puhLumaIntraDir    = (UChar* )xMalloc(UChar,  uiNumPartition);
196    m_puhChromaIntraDir  = (UChar* )xMalloc(UChar,  uiNumPartition);
197    m_puhInterDir        = (UChar* )xMalloc(UChar,  uiNumPartition);
198   
199    m_puhTrIdx           = (UChar* )xMalloc(UChar,  uiNumPartition);
200    m_puhTransformSkip[0] = (UChar* )xMalloc(UChar,  uiNumPartition);
201    m_puhTransformSkip[1] = (UChar* )xMalloc(UChar,  uiNumPartition);
202    m_puhTransformSkip[2] = (UChar* )xMalloc(UChar,  uiNumPartition);
203
204    m_puhCbf[0]          = (UChar* )xMalloc(UChar,  uiNumPartition);
205    m_puhCbf[1]          = (UChar* )xMalloc(UChar,  uiNumPartition);
206    m_puhCbf[2]          = (UChar* )xMalloc(UChar,  uiNumPartition);
207   
208    m_apiMVPIdx[0]       = new Char[ uiNumPartition ];
209    m_apiMVPIdx[1]       = new Char[ uiNumPartition ];
210    m_apiMVPNum[0]       = new Char[ uiNumPartition ];
211    m_apiMVPNum[1]       = new Char[ uiNumPartition ];
212    memset( m_apiMVPIdx[0], -1,uiNumPartition * sizeof( Char ) );
213    memset( m_apiMVPIdx[1], -1,uiNumPartition * sizeof( Char ) );
214   
215    m_pcTrCoeffY         = (TCoeff*)xMalloc(TCoeff, uiWidth*uiHeight);
216    m_pcTrCoeffCb        = (TCoeff*)xMalloc(TCoeff, uiWidth*uiHeight/4);
217    m_pcTrCoeffCr        = (TCoeff*)xMalloc(TCoeff, uiWidth*uiHeight/4);
218#if H_3D_NBDV
219    m_pDvInfo            = (DisInfo* )xMalloc(DisInfo,  uiNumPartition);
220#endif
221    memset( m_pcTrCoeffY, 0,uiWidth*uiHeight * sizeof( TCoeff ) );
222    memset( m_pcTrCoeffCb, 0,uiWidth*uiHeight/4 * sizeof( TCoeff ) );
223    memset( m_pcTrCoeffCr, 0,uiWidth*uiHeight/4 * sizeof( TCoeff ) );
224#if ADAPTIVE_QP_SELECTION   
225    if( bGlobalRMARLBuffer )
226    {
227      if( m_pcGlbArlCoeffY == NULL )
228      {
229        m_pcGlbArlCoeffY   = (Int*)xMalloc(Int, uiWidth*uiHeight);
230        m_pcGlbArlCoeffCb  = (Int*)xMalloc(Int, uiWidth*uiHeight/4);
231        m_pcGlbArlCoeffCr  = (Int*)xMalloc(Int, uiWidth*uiHeight/4);
232      }
233      m_pcArlCoeffY        = m_pcGlbArlCoeffY;
234      m_pcArlCoeffCb       = m_pcGlbArlCoeffCb;
235      m_pcArlCoeffCr       = m_pcGlbArlCoeffCr;
236      m_ArlCoeffIsAliasedAllocation = true;
237    }
238    else
239    {
240      m_pcArlCoeffY        = (Int*)xMalloc(Int, uiWidth*uiHeight);
241      m_pcArlCoeffCb       = (Int*)xMalloc(Int, uiWidth*uiHeight/4);
242      m_pcArlCoeffCr       = (Int*)xMalloc(Int, uiWidth*uiHeight/4);
243    }
244#endif
245   
246    m_pbIPCMFlag         = (Bool*  )xMalloc(Bool, uiNumPartition);
247    m_pcIPCMSampleY      = (Pel*   )xMalloc(Pel , uiWidth*uiHeight);
248    m_pcIPCMSampleCb     = (Pel*   )xMalloc(Pel , uiWidth*uiHeight/4);
249    m_pcIPCMSampleCr     = (Pel*   )xMalloc(Pel , uiWidth*uiHeight/4);
250
251    m_acCUMvField[0].create( uiNumPartition );
252    m_acCUMvField[1].create( uiNumPartition );
253   
254#if H_3D_ARP
255    m_puhARPW            = new UChar[ uiNumPartition];
256#endif
257#if H_3D_IC
258    m_pbICFlag           = (Bool* )xMalloc(Bool,   uiNumPartition);
259#endif
260#if H_3D_DIM
261    for( Int i = 0; i < DIM_NUM_TYPE; i++ )
262    {
263      m_dimDeltaDC[i][0] = (Pel* )xMalloc(Pel, uiNumPartition); 
264      m_dimDeltaDC[i][1] = (Pel* )xMalloc(Pel, uiNumPartition);
265    }
266#if H_3D_DIM_DMM
267    for( Int i = 0; i < DMM_NUM_TYPE; i++ )
268    {
269      m_dmmWedgeTabIdx[i]    = (UInt*)xMalloc(UInt, uiNumPartition);
270    }
271#endif
272#if H_3D_DIM_SDC
273    m_pbSDCFlag             = (Bool*)xMalloc(Bool, uiNumPartition);
274    m_apSegmentDCOffset[0]  = (Pel*)xMalloc(Pel, uiNumPartition);
275    m_apSegmentDCOffset[1]  = (Pel*)xMalloc(Pel, uiNumPartition);
276#endif
277#endif
278#if H_3D_INTER_SDC
279    m_pbInterSDCFlag     = (Bool*  )xMalloc(Bool,   uiNumPartition);
280    for( Int i = 0; i < 4; i++ )
281    {
282      m_apSegmentInterDCOffset[i] = (Int*)xMalloc(Int, uiNumPartition);
283    }
284#endif
285  }
286  else
287  {
288    m_acCUMvField[0].setNumPartition(uiNumPartition );
289    m_acCUMvField[1].setNumPartition(uiNumPartition );
290  }
291#if H_3D_INTER_SDC
292  m_pucInterSDCMask     = (UChar*  )xMalloc(UChar,    g_uiMaxCUHeight*g_uiMaxCUWidth);
293#endif
294  m_sliceStartCU        = (UInt*  )xMalloc(UInt, uiNumPartition);
295  m_sliceSegmentStartCU = (UInt*  )xMalloc(UInt, uiNumPartition);
296 
297  // create pattern memory
298  m_pcPattern            = (TComPattern*)xMalloc(TComPattern, 1);
299 
300  // create motion vector fields
301 
302  m_pcCUAboveLeft      = NULL;
303  m_pcCUAboveRight     = NULL;
304  m_pcCUAbove          = NULL;
305  m_pcCULeft           = NULL;
306 
307  m_apcCUColocated[0]  = NULL;
308  m_apcCUColocated[1]  = NULL;
309}
310
311Void TComDataCU::destroy()
312{
313  m_pcPic              = NULL;
314  m_pcSlice            = NULL;
315 
316  if ( m_pcPattern )
317  { 
318    xFree(m_pcPattern);
319    m_pcPattern = NULL;
320  }
321 
322  // encoder-side buffer free
323  if ( !m_bDecSubCu )
324  {
325    if ( m_phQP               ) { xFree(m_phQP);                m_phQP              = NULL; }
326    if ( m_puhDepth           ) { xFree(m_puhDepth);            m_puhDepth          = NULL; }
327    if ( m_puhWidth           ) { xFree(m_puhWidth);            m_puhWidth          = NULL; }
328    if ( m_puhHeight          ) { xFree(m_puhHeight);           m_puhHeight         = NULL; }
329
330    if ( m_skipFlag           ) { delete[] m_skipFlag;          m_skipFlag          = NULL; }
331
332    if ( m_pePartSize         ) { delete[] m_pePartSize;        m_pePartSize        = NULL; }
333    if ( m_pePredMode         ) { delete[] m_pePredMode;        m_pePredMode        = NULL; }
334    if ( m_CUTransquantBypass ) { delete[] m_CUTransquantBypass;m_CUTransquantBypass = NULL; }
335    if ( m_puhCbf[0]          ) { xFree(m_puhCbf[0]);           m_puhCbf[0]         = NULL; }
336    if ( m_puhCbf[1]          ) { xFree(m_puhCbf[1]);           m_puhCbf[1]         = NULL; }
337    if ( m_puhCbf[2]          ) { xFree(m_puhCbf[2]);           m_puhCbf[2]         = NULL; }
338    if ( m_puhInterDir        ) { xFree(m_puhInterDir);         m_puhInterDir       = NULL; }
339    if ( m_pbMergeFlag        ) { xFree(m_pbMergeFlag);         m_pbMergeFlag       = NULL; }
340    if ( m_puhMergeIndex      ) { xFree(m_puhMergeIndex);       m_puhMergeIndex     = NULL; }
341#if H_3D_VSP
342    if ( m_piVSPFlag          ) { xFree(m_piVSPFlag);           m_piVSPFlag         = NULL; }
343#endif
344#if H_3D_SPIVMP
345    if ( m_pbSPIVMPFlag       ) { xFree(m_pbSPIVMPFlag);           m_pbSPIVMPFlag         = NULL; }
346#endif
347    if ( m_puhLumaIntraDir    ) { xFree(m_puhLumaIntraDir);     m_puhLumaIntraDir   = NULL; }
348    if ( m_puhChromaIntraDir  ) { xFree(m_puhChromaIntraDir);   m_puhChromaIntraDir = NULL; }
349    if ( m_puhTrIdx           ) { xFree(m_puhTrIdx);            m_puhTrIdx          = NULL; }
350    if ( m_puhTransformSkip[0]) { xFree(m_puhTransformSkip[0]); m_puhTransformSkip[0] = NULL; }
351    if ( m_puhTransformSkip[1]) { xFree(m_puhTransformSkip[1]); m_puhTransformSkip[1] = NULL; }
352    if ( m_puhTransformSkip[2]) { xFree(m_puhTransformSkip[2]); m_puhTransformSkip[2] = NULL; }
353    if ( m_pcTrCoeffY         ) { xFree(m_pcTrCoeffY);          m_pcTrCoeffY        = NULL; }
354    if ( m_pcTrCoeffCb        ) { xFree(m_pcTrCoeffCb);         m_pcTrCoeffCb       = NULL; }
355    if ( m_pcTrCoeffCr        ) { xFree(m_pcTrCoeffCr);         m_pcTrCoeffCr       = NULL; }
356#if ADAPTIVE_QP_SELECTION
357    if (!m_ArlCoeffIsAliasedAllocation)
358    {
359      xFree(m_pcArlCoeffY); m_pcArlCoeffY = 0;
360      xFree(m_pcArlCoeffCb); m_pcArlCoeffCb = 0;
361      xFree(m_pcArlCoeffCr); m_pcArlCoeffCr = 0;
362    }
363    if ( m_pcGlbArlCoeffY     ) { xFree(m_pcGlbArlCoeffY);      m_pcGlbArlCoeffY    = NULL; }
364    if ( m_pcGlbArlCoeffCb    ) { xFree(m_pcGlbArlCoeffCb);     m_pcGlbArlCoeffCb   = NULL; }
365    if ( m_pcGlbArlCoeffCr    ) { xFree(m_pcGlbArlCoeffCr);     m_pcGlbArlCoeffCr   = NULL; }
366#endif
367    if ( m_pbIPCMFlag         ) { xFree(m_pbIPCMFlag   );       m_pbIPCMFlag        = NULL; }
368    if ( m_pcIPCMSampleY      ) { xFree(m_pcIPCMSampleY);       m_pcIPCMSampleY     = NULL; }
369    if ( m_pcIPCMSampleCb     ) { xFree(m_pcIPCMSampleCb);      m_pcIPCMSampleCb    = NULL; }
370    if ( m_pcIPCMSampleCr     ) { xFree(m_pcIPCMSampleCr);      m_pcIPCMSampleCr    = NULL; }
371    if ( m_apiMVPIdx[0]       ) { delete[] m_apiMVPIdx[0];      m_apiMVPIdx[0]      = NULL; }
372    if ( m_apiMVPIdx[1]       ) { delete[] m_apiMVPIdx[1];      m_apiMVPIdx[1]      = NULL; }
373    if ( m_apiMVPNum[0]       ) { delete[] m_apiMVPNum[0];      m_apiMVPNum[0]      = NULL; }
374    if ( m_apiMVPNum[1]       ) { delete[] m_apiMVPNum[1];      m_apiMVPNum[1]      = NULL; }
375#if H_3D_NBDV
376    if ( m_pDvInfo            ) { xFree(m_pDvInfo);             m_pDvInfo           = NULL; }
377#endif
378
379#if H_3D_ARP
380    if ( m_puhARPW            ) { delete[] m_puhARPW;           m_puhARPW           = NULL; }
381#endif
382#if H_3D_IC
383    if ( m_pbICFlag           ) { xFree(m_pbICFlag);            m_pbICFlag          = NULL; }
384#endif
385    m_acCUMvField[0].destroy();
386    m_acCUMvField[1].destroy();
387
388#if H_3D_DIM
389    for( Int i = 0; i < DIM_NUM_TYPE; i++ )
390    {
391      if ( m_dimDeltaDC[i][0] ) { xFree( m_dimDeltaDC[i][0] ); m_dimDeltaDC[i][0] = NULL; }
392      if ( m_dimDeltaDC[i][1] ) { xFree( m_dimDeltaDC[i][1] ); m_dimDeltaDC[i][1] = NULL; }
393    }
394#if H_3D_DIM_DMM
395    for( Int i = 0; i < DMM_NUM_TYPE; i++ )
396    {
397      if ( m_dmmWedgeTabIdx[i] ) { xFree( m_dmmWedgeTabIdx[i] ); m_dmmWedgeTabIdx[i] = NULL; }
398    }
399#endif
400#if H_3D_DIM_SDC
401    if ( m_pbSDCFlag            ) { xFree(m_pbSDCFlag);             m_pbSDCFlag             = NULL; }
402    if ( m_apSegmentDCOffset[0] ) { xFree(m_apSegmentDCOffset[0]);  m_apSegmentDCOffset[0]  = NULL; }
403    if ( m_apSegmentDCOffset[1] ) { xFree(m_apSegmentDCOffset[1]);  m_apSegmentDCOffset[1]  = NULL; }
404#endif
405#endif   
406#if H_3D_INTER_SDC
407    if ( m_pbInterSDCFlag     ) { xFree(m_pbInterSDCFlag);      m_pbInterSDCFlag    = NULL; }
408    for(Int i = 0; i < 4; i++ )
409    {
410      if ( m_apSegmentInterDCOffset[i] ) { xFree( m_apSegmentInterDCOffset[i] ); m_apSegmentInterDCOffset[i] = NULL; }
411  }
412#endif
413  }
414#if H_3D_INTER_SDC
415  if ( m_pucInterSDCMask     ) { xFree(m_pucInterSDCMask);      m_pucInterSDCMask    = NULL; }
416#endif
417  m_pcCUAboveLeft       = NULL;
418  m_pcCUAboveRight      = NULL;
419  m_pcCUAbove           = NULL;
420  m_pcCULeft            = NULL;
421 
422  m_apcCUColocated[0]   = NULL;
423  m_apcCUColocated[1]   = NULL;
424
425  if( m_sliceStartCU )
426  {
427    xFree(m_sliceStartCU);
428    m_sliceStartCU=NULL;
429  }
430  if(m_sliceSegmentStartCU )
431  {
432    xFree(m_sliceSegmentStartCU);
433    m_sliceSegmentStartCU=NULL;
434  }
435}
436
437const NDBFBlockInfo& NDBFBlockInfo::operator= (const NDBFBlockInfo& src)
438{
439  this->tileID = src.tileID;
440  this->sliceID= src.sliceID;
441  this->startSU= src.startSU;
442  this->endSU  = src.endSU;
443  this->widthSU= src.widthSU;
444  this->heightSU=src.heightSU;
445  this->posX   = src.posX;
446  this->posY   = src.posY;
447  this->width  = src.width;
448  this->height = src.height;
449  ::memcpy(this->isBorderAvailable, src.isBorderAvailable, sizeof(Bool)*((Int)NUM_SGU_BORDER));
450  this->allBordersAvailable = src.allBordersAvailable;
451
452  return *this;
453}
454
455
456// ====================================================================================================================
457// Public member functions
458// ====================================================================================================================
459
460// --------------------------------------------------------------------------------------------------------------------
461// Initialization
462// --------------------------------------------------------------------------------------------------------------------
463
464/**
465 - initialize top-level CU
466 - internal buffers are already created
467 - set values before encoding a CU
468 .
469 \param  pcPic     picture (TComPic) class pointer
470 \param  iCUAddr   CU address
471 */
472Void TComDataCU::initCU( TComPic* pcPic, UInt iCUAddr )
473{
474
475  m_pcPic              = pcPic;
476  m_pcSlice            = pcPic->getSlice(pcPic->getCurrSliceIdx());
477  m_uiCUAddr           = iCUAddr;
478  m_uiCUPelX           = ( iCUAddr % pcPic->getFrameWidthInCU() ) * g_uiMaxCUWidth;
479  m_uiCUPelY           = ( iCUAddr / pcPic->getFrameWidthInCU() ) * g_uiMaxCUHeight;
480  m_uiAbsIdxInLCU      = 0;
481  m_dTotalCost         = MAX_DOUBLE;
482  m_uiTotalDistortion  = 0;
483  m_uiTotalBits        = 0;
484  m_uiTotalBins        = 0;
485  m_uiNumPartition     = pcPic->getNumPartInCU();
486 
487  for(Int i=0; i<pcPic->getNumPartInCU(); i++)
488  {
489    if(pcPic->getPicSym()->getInverseCUOrderMap(iCUAddr)*pcPic->getNumPartInCU()+i>=getSlice()->getSliceCurStartCUAddr())
490    {
491      m_sliceStartCU[i]=getSlice()->getSliceCurStartCUAddr();
492    }
493    else
494    {
495      m_sliceStartCU[i]=pcPic->getCU(getAddr())->m_sliceStartCU[i];
496    }
497  }
498  for(Int i=0; i<pcPic->getNumPartInCU(); i++)
499  {
500    if(pcPic->getPicSym()->getInverseCUOrderMap(iCUAddr)*pcPic->getNumPartInCU()+i>=getSlice()->getSliceSegmentCurStartCUAddr())
501    {
502      m_sliceSegmentStartCU[i]=getSlice()->getSliceSegmentCurStartCUAddr();
503    }
504    else
505    {
506      m_sliceSegmentStartCU[i]=pcPic->getCU(getAddr())->m_sliceSegmentStartCU[i];
507    }
508  }
509
510  Int partStartIdx = getSlice()->getSliceSegmentCurStartCUAddr() - pcPic->getPicSym()->getInverseCUOrderMap(iCUAddr) * pcPic->getNumPartInCU();
511
512  Int numElements = min<Int>( partStartIdx, m_uiNumPartition );
513  for ( Int ui = 0; ui < numElements; ui++ )
514  {
515    TComDataCU * pcFrom = pcPic->getCU(getAddr());
516    m_skipFlag[ui]   = pcFrom->getSkipFlag(ui);
517    m_pePartSize[ui] = pcFrom->getPartitionSize(ui);
518    m_pePredMode[ui] = pcFrom->getPredictionMode(ui);
519    m_CUTransquantBypass[ui] = pcFrom->getCUTransquantBypass(ui);
520    m_puhDepth[ui] = pcFrom->getDepth(ui);
521#if H_3D_ARP
522    m_puhARPW   [ui] = pcFrom->getARPW( ui );
523#endif
524#if H_3D_IC
525    m_pbICFlag[ui]   =  pcFrom->m_pbICFlag[ui];
526#endif
527    m_puhWidth  [ui] = pcFrom->getWidth(ui);
528    m_puhHeight [ui] = pcFrom->getHeight(ui);
529    m_puhTrIdx  [ui] = pcFrom->getTransformIdx(ui);
530    m_puhTransformSkip[0][ui] = pcFrom->getTransformSkip(ui,TEXT_LUMA);
531    m_puhTransformSkip[1][ui] = pcFrom->getTransformSkip(ui,TEXT_CHROMA_U);
532    m_puhTransformSkip[2][ui] = pcFrom->getTransformSkip(ui,TEXT_CHROMA_V);
533    m_apiMVPIdx[0][ui] = pcFrom->m_apiMVPIdx[0][ui];;
534    m_apiMVPIdx[1][ui] = pcFrom->m_apiMVPIdx[1][ui];
535    m_apiMVPNum[0][ui] = pcFrom->m_apiMVPNum[0][ui];
536    m_apiMVPNum[1][ui] = pcFrom->m_apiMVPNum[1][ui];
537    m_phQP[ui]=pcFrom->m_phQP[ui];
538    m_pbMergeFlag[ui]=pcFrom->m_pbMergeFlag[ui];
539    m_puhMergeIndex[ui]=pcFrom->m_puhMergeIndex[ui];
540#if H_3D_VSP
541    m_piVSPFlag[ui] = pcFrom->m_piVSPFlag[ui];
542#endif
543#if H_3D_SPIVMP
544    m_pbSPIVMPFlag[ui] = pcFrom->m_pbSPIVMPFlag[ui];
545#endif
546    m_puhLumaIntraDir[ui]=pcFrom->m_puhLumaIntraDir[ui];
547    m_puhChromaIntraDir[ui]=pcFrom->m_puhChromaIntraDir[ui];
548    m_puhInterDir[ui]=pcFrom->m_puhInterDir[ui];
549    m_puhCbf[0][ui]=pcFrom->m_puhCbf[0][ui];
550    m_puhCbf[1][ui]=pcFrom->m_puhCbf[1][ui];
551    m_puhCbf[2][ui]=pcFrom->m_puhCbf[2][ui];
552    m_pbIPCMFlag[ui] = pcFrom->m_pbIPCMFlag[ui];
553#if H_3D_DIM_SDC
554    m_pbSDCFlag[ui] = pcFrom->m_pbSDCFlag[ui];
555#endif
556#if H_3D_INTER_SDC
557    m_pbInterSDCFlag[ui] = pcFrom->m_pbInterSDCFlag[ui];
558#endif
559  }
560 
561  Int firstElement = max<Int>( partStartIdx, 0 );
562  numElements = m_uiNumPartition - firstElement;
563 
564  if ( numElements > 0 )
565  {
566    memset( m_skipFlag          + firstElement, false,                    numElements * sizeof( *m_skipFlag ) );
567
568    memset( m_pePartSize        + firstElement, SIZE_NONE,                numElements * sizeof( *m_pePartSize ) );
569    memset( m_pePredMode        + firstElement, MODE_NONE,                numElements * sizeof( *m_pePredMode ) );
570    memset( m_CUTransquantBypass+ firstElement, false,                    numElements * sizeof( *m_CUTransquantBypass) );
571    memset( m_puhDepth          + firstElement, 0,                        numElements * sizeof( *m_puhDepth ) );
572    memset( m_puhTrIdx          + firstElement, 0,                        numElements * sizeof( *m_puhTrIdx ) );
573    memset( m_puhTransformSkip[0] + firstElement, 0,                      numElements * sizeof( *m_puhTransformSkip[0]) );
574    memset( m_puhTransformSkip[1] + firstElement, 0,                      numElements * sizeof( *m_puhTransformSkip[1]) );
575    memset( m_puhTransformSkip[2] + firstElement, 0,                      numElements * sizeof( *m_puhTransformSkip[2]) );
576    memset( m_puhWidth          + firstElement, g_uiMaxCUWidth,           numElements * sizeof( *m_puhWidth ) );
577    memset( m_puhHeight         + firstElement, g_uiMaxCUHeight,          numElements * sizeof( *m_puhHeight ) );
578    memset( m_apiMVPIdx[0]      + firstElement, -1,                       numElements * sizeof( *m_apiMVPIdx[0] ) );
579    memset( m_apiMVPIdx[1]      + firstElement, -1,                       numElements * sizeof( *m_apiMVPIdx[1] ) );
580    memset( m_apiMVPNum[0]      + firstElement, -1,                       numElements * sizeof( *m_apiMVPNum[0] ) );
581    memset( m_apiMVPNum[1]      + firstElement, -1,                       numElements * sizeof( *m_apiMVPNum[1] ) );
582    memset( m_phQP              + firstElement, getSlice()->getSliceQp(), numElements * sizeof( *m_phQP ) );
583    memset( m_pbMergeFlag       + firstElement, false,                    numElements * sizeof( *m_pbMergeFlag ) );
584    memset( m_puhMergeIndex     + firstElement, 0,                        numElements * sizeof( *m_puhMergeIndex ) );
585#if H_3D_VSP
586    memset( m_piVSPFlag         + firstElement, 0,                        numElements * sizeof( *m_piVSPFlag ) );
587#endif
588#if H_3D_SPIVMP
589    memset( m_pbSPIVMPFlag      + firstElement, 0,                        numElements * sizeof( *m_pbSPIVMPFlag ) );
590#endif
591    memset( m_puhLumaIntraDir   + firstElement, DC_IDX,                   numElements * sizeof( *m_puhLumaIntraDir ) );
592    memset( m_puhChromaIntraDir + firstElement, 0,                        numElements * sizeof( *m_puhChromaIntraDir ) );
593    memset( m_puhInterDir       + firstElement, 0,                        numElements * sizeof( *m_puhInterDir ) );
594    memset( m_puhCbf[0]         + firstElement, 0,                        numElements * sizeof( *m_puhCbf[0] ) );
595    memset( m_puhCbf[1]         + firstElement, 0,                        numElements * sizeof( *m_puhCbf[1] ) );
596    memset( m_puhCbf[2]         + firstElement, 0,                        numElements * sizeof( *m_puhCbf[2] ) );
597    memset( m_pbIPCMFlag        + firstElement, false,                    numElements * sizeof( *m_pbIPCMFlag ) );
598#if H_3D_ARP
599    memset( m_puhARPW           + firstElement, 0,                        numElements * sizeof( UChar )         );
600#endif
601#if H_3D_IC
602    memset( m_pbICFlag          + firstElement, false,                    numElements * sizeof( *m_pbICFlag )   );
603#endif
604#if H_3D_DIM
605    for( Int i = 0; i < DIM_NUM_TYPE; i++ )
606    {
607      memset( m_dimDeltaDC[i][0] + firstElement, 0,                       numElements * sizeof( *m_dimDeltaDC[i][0] ) );
608      memset( m_dimDeltaDC[i][1] + firstElement, 0,                       numElements * sizeof( *m_dimDeltaDC[i][1] ) );
609    }
610#if H_3D_DIM_DMM
611    for( Int i = 0; i < DMM_NUM_TYPE; i++ )
612    {
613      memset( m_dmmWedgeTabIdx[i] + firstElement, 0,                      numElements * sizeof( *m_dmmWedgeTabIdx[i] ) );
614    }
615#endif
616#if H_3D_DIM_SDC
617    memset( m_pbSDCFlag             + firstElement,     0,                numElements * sizeof( *m_pbSDCFlag            ) );
618    memset( m_apSegmentDCOffset[0]  + firstElement,     0,                numElements * sizeof( *m_apSegmentDCOffset[0] ) );
619    memset( m_apSegmentDCOffset[1]  + firstElement,     0,                numElements * sizeof( *m_apSegmentDCOffset[1] ) );
620#endif
621#endif
622#if H_3D_INTER_SDC
623    memset( m_pbInterSDCFlag   + firstElement,     0,                    numElements * sizeof( *m_pbInterSDCFlag ) );
624    for( Int i = 0; i < 4; i++ )
625    {
626      memset( m_apSegmentInterDCOffset[i] + firstElement,     0,         numElements * sizeof( *m_apSegmentInterDCOffset[i] ) );
627    }
628#endif
629  }
630 
631  UInt uiTmp = g_uiMaxCUWidth*g_uiMaxCUHeight;
632  if ( 0 >= partStartIdx ) 
633  {
634    m_acCUMvField[0].clearMvField();
635    m_acCUMvField[1].clearMvField();
636    memset( m_pcTrCoeffY , 0, sizeof( TCoeff ) * uiTmp );
637#if ADAPTIVE_QP_SELECTION
638    memset( m_pcArlCoeffY , 0, sizeof( Int ) * uiTmp ); 
639#endif
640    memset( m_pcIPCMSampleY , 0, sizeof( Pel ) * uiTmp );
641    uiTmp  >>= 2;
642    memset( m_pcTrCoeffCb, 0, sizeof( TCoeff ) * uiTmp );
643    memset( m_pcTrCoeffCr, 0, sizeof( TCoeff ) * uiTmp );
644#if ADAPTIVE_QP_SELECTION 
645    memset( m_pcArlCoeffCb, 0, sizeof( Int ) * uiTmp );
646    memset( m_pcArlCoeffCr, 0, sizeof( Int ) * uiTmp );
647#endif
648    memset( m_pcIPCMSampleCb , 0, sizeof( Pel ) * uiTmp );
649    memset( m_pcIPCMSampleCr , 0, sizeof( Pel ) * uiTmp );
650  }
651  else 
652  {
653    TComDataCU * pcFrom = pcPic->getCU(getAddr());
654    m_acCUMvField[0].copyFrom(&pcFrom->m_acCUMvField[0],m_uiNumPartition,0);
655    m_acCUMvField[1].copyFrom(&pcFrom->m_acCUMvField[1],m_uiNumPartition,0);
656    for(Int i=0; i<uiTmp; i++)
657    {
658      m_pcTrCoeffY[i]=pcFrom->m_pcTrCoeffY[i];
659#if ADAPTIVE_QP_SELECTION
660      m_pcArlCoeffY[i]=pcFrom->m_pcArlCoeffY[i];
661#endif
662      m_pcIPCMSampleY[i]=pcFrom->m_pcIPCMSampleY[i];
663    }
664    for(Int i=0; i<(uiTmp>>2); i++)
665    {
666      m_pcTrCoeffCb[i]=pcFrom->m_pcTrCoeffCb[i];
667      m_pcTrCoeffCr[i]=pcFrom->m_pcTrCoeffCr[i];
668#if ADAPTIVE_QP_SELECTION
669      m_pcArlCoeffCb[i]=pcFrom->m_pcArlCoeffCb[i];
670      m_pcArlCoeffCr[i]=pcFrom->m_pcArlCoeffCr[i];
671#endif
672      m_pcIPCMSampleCb[i]=pcFrom->m_pcIPCMSampleCb[i];
673      m_pcIPCMSampleCr[i]=pcFrom->m_pcIPCMSampleCr[i];
674    }
675  }
676
677  // Setting neighbor CU
678  m_pcCULeft        = NULL;
679  m_pcCUAbove       = NULL;
680  m_pcCUAboveLeft   = NULL;
681  m_pcCUAboveRight  = NULL;
682
683  m_apcCUColocated[0] = NULL;
684  m_apcCUColocated[1] = NULL;
685
686  UInt uiWidthInCU = pcPic->getFrameWidthInCU();
687  if ( m_uiCUAddr % uiWidthInCU )
688  {
689    m_pcCULeft = pcPic->getCU( m_uiCUAddr - 1 );
690  }
691
692  if ( m_uiCUAddr / uiWidthInCU )
693  {
694    m_pcCUAbove = pcPic->getCU( m_uiCUAddr - uiWidthInCU );
695  }
696
697  if ( m_pcCULeft && m_pcCUAbove )
698  {
699    m_pcCUAboveLeft = pcPic->getCU( m_uiCUAddr - uiWidthInCU - 1 );
700  }
701
702  if ( m_pcCUAbove && ( (m_uiCUAddr%uiWidthInCU) < (uiWidthInCU-1) )  )
703  {
704    m_pcCUAboveRight = pcPic->getCU( m_uiCUAddr - uiWidthInCU + 1 );
705  }
706
707  if ( getSlice()->getNumRefIdx( REF_PIC_LIST_0 ) > 0 )
708  {
709    m_apcCUColocated[0] = getSlice()->getRefPic( REF_PIC_LIST_0, 0)->getCU( m_uiCUAddr );
710  }
711
712  if ( getSlice()->getNumRefIdx( REF_PIC_LIST_1 ) > 0 )
713  {
714    m_apcCUColocated[1] = getSlice()->getRefPic( REF_PIC_LIST_1, 0)->getCU( m_uiCUAddr );
715  }
716}
717
718/** initialize prediction data with enabling sub-LCU-level delta QP
719*\param  uiDepth  depth of the current CU
720*\param  qp     qp for the current CU
721*- set CU width and CU height according to depth
722*- set qp value according to input qp
723*- set last-coded qp value according to input last-coded qp
724*/
725Void TComDataCU::initEstData( UInt uiDepth, Int qp )
726{
727  m_dTotalCost         = MAX_DOUBLE;
728  m_uiTotalDistortion  = 0;
729  m_uiTotalBits        = 0;
730  m_uiTotalBins        = 0;
731
732  UChar uhWidth  = g_uiMaxCUWidth  >> uiDepth;
733  UChar uhHeight = g_uiMaxCUHeight >> uiDepth;
734
735  for (UInt ui = 0; ui < m_uiNumPartition; ui++)
736  {
737    if(getPic()->getPicSym()->getInverseCUOrderMap(getAddr())*m_pcPic->getNumPartInCU()+m_uiAbsIdxInLCU+ui >= getSlice()->getSliceSegmentCurStartCUAddr())
738    {
739      m_apiMVPIdx[0][ui] = -1;
740      m_apiMVPIdx[1][ui] = -1;
741      m_apiMVPNum[0][ui] = -1;
742      m_apiMVPNum[1][ui] = -1;
743      m_puhDepth  [ui] = uiDepth;
744      m_puhWidth  [ui] = uhWidth;
745      m_puhHeight [ui] = uhHeight;
746      m_puhTrIdx  [ui] = 0;
747      m_puhTransformSkip[0][ui] = 0;
748      m_puhTransformSkip[1][ui] = 0;
749      m_puhTransformSkip[2][ui] = 0;
750      m_skipFlag[ui]   = false;
751      m_pePartSize[ui] = SIZE_NONE;
752      m_pePredMode[ui] = MODE_NONE;
753      m_CUTransquantBypass[ui] = false;
754      m_pbIPCMFlag[ui] = 0;
755      m_phQP[ui] = qp;
756      m_pbMergeFlag[ui] = 0;
757      m_puhMergeIndex[ui] = 0;
758#if H_3D_VSP
759      m_piVSPFlag[ui] = 0;
760#endif
761#if H_3D_SPIVMP
762      m_pbSPIVMPFlag[ui] = 0;
763#endif
764      m_puhLumaIntraDir[ui] = DC_IDX;
765      m_puhChromaIntraDir[ui] = 0;
766      m_puhInterDir[ui] = 0;
767      m_puhCbf[0][ui] = 0;
768      m_puhCbf[1][ui] = 0;
769      m_puhCbf[2][ui] = 0;
770#if H_3D_ARP
771      m_puhARPW[ui] = 0;
772#endif
773#if H_3D_IC
774      m_pbICFlag[ui]  = false;
775#endif
776#if H_3D_DIM
777      for( Int i = 0; i < DIM_NUM_TYPE; i++ )
778      {
779        m_dimDeltaDC[i][0] [ui] = 0;
780        m_dimDeltaDC[i][1] [ui] = 0;
781      }
782#if H_3D_DIM_DMM
783      for( Int i = 0; i < DMM_NUM_TYPE; i++ )
784      {
785        m_dmmWedgeTabIdx[i] [ui] = 0;
786      }
787#endif
788#if H_3D_DIM_SDC
789      m_pbSDCFlag           [ui] = false;
790      m_apSegmentDCOffset[0][ui] = 0;
791      m_apSegmentDCOffset[1][ui] = 0;
792#endif
793#endif
794#if H_3D_INTER_SDC
795      m_pbInterSDCFlag[ui] = false;
796      for( Int i = 0; i < 4; i++ )
797      {
798        m_apSegmentInterDCOffset[i][ui] = 0;
799      }
800#endif
801    }
802  }
803
804  if(getPic()->getPicSym()->getInverseCUOrderMap(getAddr())*m_pcPic->getNumPartInCU()+m_uiAbsIdxInLCU >= getSlice()->getSliceSegmentCurStartCUAddr())
805  {
806    m_acCUMvField[0].clearMvField();
807    m_acCUMvField[1].clearMvField();
808    UInt uiTmp = uhWidth*uhHeight;
809   
810    memset( m_pcTrCoeffY,    0, uiTmp * sizeof( *m_pcTrCoeffY    ) );
811#if ADAPTIVE_QP_SELECTION
812    memset( m_pcArlCoeffY ,  0, uiTmp * sizeof( *m_pcArlCoeffY   ) );
813#endif
814    memset( m_pcIPCMSampleY, 0, uiTmp * sizeof( *m_pcIPCMSampleY ) );
815
816    uiTmp>>=2;
817    memset( m_pcTrCoeffCb,    0, uiTmp * sizeof( *m_pcTrCoeffCb    ) );
818    memset( m_pcTrCoeffCr,    0, uiTmp * sizeof( *m_pcTrCoeffCr    ) );
819#if ADAPTIVE_QP_SELECTION 
820    memset( m_pcArlCoeffCb,   0, uiTmp * sizeof( *m_pcArlCoeffCb   ) );
821    memset( m_pcArlCoeffCr,   0, uiTmp * sizeof( *m_pcArlCoeffCr   ) );
822#endif
823    memset( m_pcIPCMSampleCb, 0, uiTmp * sizeof( *m_pcIPCMSampleCb ) );
824    memset( m_pcIPCMSampleCr, 0, uiTmp * sizeof( *m_pcIPCMSampleCr ) );
825  }
826}
827
828
829// initialize Sub partition
830Void TComDataCU::initSubCU( TComDataCU* pcCU, UInt uiPartUnitIdx, UInt uiDepth, Int qp )
831{
832  assert( uiPartUnitIdx<4 );
833
834  UInt uiPartOffset = ( pcCU->getTotalNumPart()>>2 )*uiPartUnitIdx;
835
836  m_pcPic              = pcCU->getPic();
837  m_pcSlice            = m_pcPic->getSlice(m_pcPic->getCurrSliceIdx());
838  m_uiCUAddr           = pcCU->getAddr();
839  m_uiAbsIdxInLCU      = pcCU->getZorderIdxInCU() + uiPartOffset;
840
841  m_uiCUPelX           = pcCU->getCUPelX() + ( g_uiMaxCUWidth>>uiDepth  )*( uiPartUnitIdx &  1 );
842  m_uiCUPelY           = pcCU->getCUPelY() + ( g_uiMaxCUHeight>>uiDepth  )*( uiPartUnitIdx >> 1 );
843
844  m_dTotalCost         = MAX_DOUBLE;
845  m_uiTotalDistortion  = 0;
846  m_uiTotalBits        = 0;
847  m_uiTotalBins        = 0;
848  m_uiNumPartition     = pcCU->getTotalNumPart() >> 2;
849
850  Int iSizeInUchar = sizeof( UChar  ) * m_uiNumPartition;
851  Int iSizeInBool  = sizeof( Bool   ) * m_uiNumPartition;
852
853  Int sizeInChar = sizeof( Char  ) * m_uiNumPartition;
854  memset( m_phQP,              qp,  sizeInChar );
855
856  memset( m_pbMergeFlag,        0, iSizeInBool  );
857  memset( m_puhMergeIndex,      0, iSizeInUchar );
858#if H_3D_VSP
859  memset( m_piVSPFlag,          0, sizeof( Char  ) * m_uiNumPartition );
860#endif
861#if H_3D_SPIVMP
862  memset( m_pbSPIVMPFlag,       0, sizeof( Bool  ) * m_uiNumPartition );
863#endif
864  memset( m_puhLumaIntraDir,    DC_IDX, iSizeInUchar );
865  memset( m_puhChromaIntraDir,  0, iSizeInUchar );
866  memset( m_puhInterDir,        0, iSizeInUchar );
867  memset( m_puhTrIdx,           0, iSizeInUchar );
868  memset( m_puhTransformSkip[0], 0, iSizeInUchar );
869  memset( m_puhTransformSkip[1], 0, iSizeInUchar );
870  memset( m_puhTransformSkip[2], 0, iSizeInUchar );
871  memset( m_puhCbf[0],          0, iSizeInUchar );
872  memset( m_puhCbf[1],          0, iSizeInUchar );
873  memset( m_puhCbf[2],          0, iSizeInUchar );
874  memset( m_puhDepth,     uiDepth, iSizeInUchar );
875#if H_3D_NBDV
876  m_pDvInfo->bDV = false;
877#endif
878#if H_3D_ARP
879  memset( m_puhARPW,            0, iSizeInUchar  );
880#endif
881  UChar uhWidth  = g_uiMaxCUWidth  >> uiDepth;
882  UChar uhHeight = g_uiMaxCUHeight >> uiDepth;
883  memset( m_puhWidth,          uhWidth,  iSizeInUchar );
884  memset( m_puhHeight,         uhHeight, iSizeInUchar );
885  memset( m_pbIPCMFlag,        0, iSizeInBool  );
886#if H_3D_IC
887  memset( m_pbICFlag,          0, iSizeInBool  );
888#endif
889#if H_3D_DIM
890  for( Int i = 0; i < DIM_NUM_TYPE; i++ )
891  {
892    memset( m_dimDeltaDC[i][0], 0, sizeof(Pel ) * m_uiNumPartition );
893    memset( m_dimDeltaDC[i][1], 0, sizeof(Pel ) * m_uiNumPartition );
894  }
895#if H_3D_DIM_DMM
896  for( Int i = 0; i < DMM_NUM_TYPE; i++ )
897  {
898    memset( m_dmmWedgeTabIdx[i], 0, sizeof(UInt) * m_uiNumPartition );
899  }
900#endif
901#if H_3D_DIM_SDC
902  memset( m_pbSDCFlag,            0, sizeof(Bool) * m_uiNumPartition  );
903  memset( m_apSegmentDCOffset[0], 0, sizeof(Pel) * m_uiNumPartition   );
904  memset( m_apSegmentDCOffset[1], 0, sizeof(Pel) * m_uiNumPartition   );
905#endif
906#endif
907#if H_3D_INTER_SDC
908  memset( m_pbInterSDCFlag,           0, sizeof( Bool ) * m_uiNumPartition );
909  for( Int i = 0; i < 4; i++ )
910  {
911    memset( m_apSegmentInterDCOffset[i], 0, sizeof( Int ) * m_uiNumPartition );
912  }
913#endif
914
915  for (UInt ui = 0; ui < m_uiNumPartition; ui++)
916  {
917    m_skipFlag[ui]   = false;
918    m_pePartSize[ui] = SIZE_NONE;
919    m_pePredMode[ui] = MODE_NONE;
920    m_CUTransquantBypass[ui] = false;
921    m_apiMVPIdx[0][ui] = -1;
922    m_apiMVPIdx[1][ui] = -1;
923    m_apiMVPNum[0][ui] = -1;
924    m_apiMVPNum[1][ui] = -1;
925    if(m_pcPic->getPicSym()->getInverseCUOrderMap(getAddr())*m_pcPic->getNumPartInCU()+m_uiAbsIdxInLCU+ui<getSlice()->getSliceSegmentCurStartCUAddr())
926    {
927      m_apiMVPIdx[0][ui] = pcCU->m_apiMVPIdx[0][uiPartOffset+ui];
928      m_apiMVPIdx[1][ui] = pcCU->m_apiMVPIdx[1][uiPartOffset+ui];;
929      m_apiMVPNum[0][ui] = pcCU->m_apiMVPNum[0][uiPartOffset+ui];;
930      m_apiMVPNum[1][ui] = pcCU->m_apiMVPNum[1][uiPartOffset+ui];;
931      m_puhDepth  [ui] = pcCU->getDepth(uiPartOffset+ui);
932      m_puhWidth  [ui] = pcCU->getWidth(uiPartOffset+ui);
933      m_puhHeight  [ui] = pcCU->getHeight(uiPartOffset+ui);
934      m_puhTrIdx  [ui] = pcCU->getTransformIdx(uiPartOffset+ui);
935      m_puhTransformSkip[0][ui] = pcCU->getTransformSkip(uiPartOffset+ui,TEXT_LUMA);
936      m_puhTransformSkip[1][ui] = pcCU->getTransformSkip(uiPartOffset+ui,TEXT_CHROMA_U);
937      m_puhTransformSkip[2][ui] = pcCU->getTransformSkip(uiPartOffset+ui,TEXT_CHROMA_V);
938      m_skipFlag[ui]   = pcCU->getSkipFlag(uiPartOffset+ui);
939      m_pePartSize[ui] = pcCU->getPartitionSize(uiPartOffset+ui);
940      m_pePredMode[ui] = pcCU->getPredictionMode(uiPartOffset+ui);
941      m_CUTransquantBypass[ui] = pcCU->getCUTransquantBypass(uiPartOffset+ui);
942      m_pbIPCMFlag[ui]=pcCU->m_pbIPCMFlag[uiPartOffset+ui];
943      m_phQP[ui] = pcCU->m_phQP[uiPartOffset+ui];
944      m_pbMergeFlag[ui]=pcCU->m_pbMergeFlag[uiPartOffset+ui];
945      m_puhMergeIndex[ui]=pcCU->m_puhMergeIndex[uiPartOffset+ui];
946#if H_3D_VSP
947      m_piVSPFlag[ui]=pcCU->m_piVSPFlag[uiPartOffset+ui];
948      m_pDvInfo[ ui ] = pcCU->m_pDvInfo[uiPartOffset+ui];
949#endif
950#if H_3D_SPIVMP
951      m_pbSPIVMPFlag[ui]=pcCU->m_pbSPIVMPFlag[uiPartOffset+ui];
952#endif
953      m_puhLumaIntraDir[ui]=pcCU->m_puhLumaIntraDir[uiPartOffset+ui];
954      m_puhChromaIntraDir[ui]=pcCU->m_puhChromaIntraDir[uiPartOffset+ui];
955      m_puhInterDir[ui]=pcCU->m_puhInterDir[uiPartOffset+ui];
956      m_puhCbf[0][ui]=pcCU->m_puhCbf[0][uiPartOffset+ui];
957      m_puhCbf[1][ui]=pcCU->m_puhCbf[1][uiPartOffset+ui];
958      m_puhCbf[2][ui]=pcCU->m_puhCbf[2][uiPartOffset+ui];
959
960#if H_3D_ARP
961      m_puhARPW           [ui] = pcCU->getARPW( uiPartOffset+ui );
962#endif
963#if H_3D_IC
964      m_pbICFlag          [ui] = pcCU->m_pbICFlag[uiPartOffset+ui];
965#endif
966#if H_3D_DIM
967      for( Int i = 0; i < DIM_NUM_TYPE; i++ )
968      {
969        m_dimDeltaDC[i][0] [ui] = pcCU->m_dimDeltaDC[i][0] [uiPartOffset+ui];
970        m_dimDeltaDC[i][1] [ui] = pcCU->m_dimDeltaDC[i][1] [uiPartOffset+ui];
971      }
972#if H_3D_DIM_DMM
973      for( Int i = 0; i < DMM_NUM_TYPE; i++ )
974      {
975        m_dmmWedgeTabIdx[i] [ui] = pcCU->m_dmmWedgeTabIdx[i] [uiPartOffset+ui];
976      }
977#endif
978#if H_3D_DIM_SDC
979      m_pbSDCFlag           [ui] = pcCU->m_pbSDCFlag            [ uiPartOffset + ui ];
980      m_apSegmentDCOffset[0][ui] = pcCU->m_apSegmentDCOffset[0] [ uiPartOffset + ui ];
981      m_apSegmentDCOffset[1][ui] = pcCU->m_apSegmentDCOffset[1] [ uiPartOffset + ui ];
982#endif
983#endif
984#if H_3D_INTER_SDC
985      m_pbInterSDCFlag      [ui] = pcCU->m_pbInterSDCFlag    [ uiPartOffset + ui ];
986      for( Int i = 0; i < 4; i++ )
987      {
988        m_apSegmentInterDCOffset[i][ui] = pcCU->m_apSegmentInterDCOffset[i][ uiPartOffset + ui ];
989      }
990#endif
991    }
992  }
993  UInt uiTmp = uhWidth*uhHeight;
994  memset( m_pcTrCoeffY , 0, sizeof(TCoeff)*uiTmp );
995#if ADAPTIVE_QP_SELECTION 
996  memset( m_pcArlCoeffY , 0, sizeof(Int)*uiTmp );
997#endif
998  memset( m_pcIPCMSampleY , 0, sizeof( Pel ) * uiTmp );
999  uiTmp >>= 2;
1000  memset( m_pcTrCoeffCb, 0, sizeof(TCoeff)*uiTmp );
1001  memset( m_pcTrCoeffCr, 0, sizeof(TCoeff)*uiTmp );
1002#if ADAPTIVE_QP_SELECTION
1003  memset( m_pcArlCoeffCb, 0, sizeof(Int)*uiTmp );
1004  memset( m_pcArlCoeffCr, 0, sizeof(Int)*uiTmp );
1005#endif
1006  memset( m_pcIPCMSampleCb , 0, sizeof( Pel ) * uiTmp );
1007  memset( m_pcIPCMSampleCr , 0, sizeof( Pel ) * uiTmp );
1008  m_acCUMvField[0].clearMvField();
1009  m_acCUMvField[1].clearMvField();
1010
1011  if(m_pcPic->getPicSym()->getInverseCUOrderMap(getAddr())*m_pcPic->getNumPartInCU()+m_uiAbsIdxInLCU<getSlice()->getSliceSegmentCurStartCUAddr())
1012  {
1013    // Part of this CU contains data from an older slice. Now copy in that data.
1014    UInt uiMaxCuWidth=pcCU->getSlice()->getSPS()->getMaxCUWidth();
1015    UInt uiMaxCuHeight=pcCU->getSlice()->getSPS()->getMaxCUHeight();
1016    TComDataCU * bigCU = getPic()->getCU(getAddr());
1017    Int minui = uiPartOffset;
1018    minui = -minui;
1019    pcCU->m_acCUMvField[0].copyTo(&m_acCUMvField[0],minui,uiPartOffset,m_uiNumPartition);
1020    pcCU->m_acCUMvField[1].copyTo(&m_acCUMvField[1],minui,uiPartOffset,m_uiNumPartition);
1021    UInt uiCoffOffset = uiMaxCuWidth*uiMaxCuHeight*m_uiAbsIdxInLCU/pcCU->getPic()->getNumPartInCU();
1022    uiTmp = uhWidth*uhHeight;
1023    for(Int i=0; i<uiTmp; i++)
1024    {
1025      m_pcTrCoeffY[i]=bigCU->m_pcTrCoeffY[uiCoffOffset+i];
1026#if ADAPTIVE_QP_SELECTION
1027      m_pcArlCoeffY[i]=bigCU->m_pcArlCoeffY[uiCoffOffset+i];
1028#endif
1029      m_pcIPCMSampleY[i]=bigCU->m_pcIPCMSampleY[uiCoffOffset+i];
1030    }
1031    uiTmp>>=2;
1032    uiCoffOffset>>=2;
1033    for(Int i=0; i<uiTmp; i++)
1034    {
1035      m_pcTrCoeffCr[i]=bigCU->m_pcTrCoeffCr[uiCoffOffset+i];
1036      m_pcTrCoeffCb[i]=bigCU->m_pcTrCoeffCb[uiCoffOffset+i];
1037#if ADAPTIVE_QP_SELECTION
1038      m_pcArlCoeffCr[i]=bigCU->m_pcArlCoeffCr[uiCoffOffset+i];
1039      m_pcArlCoeffCb[i]=bigCU->m_pcArlCoeffCb[uiCoffOffset+i];
1040#endif
1041      m_pcIPCMSampleCb[i]=bigCU->m_pcIPCMSampleCb[uiCoffOffset+i];
1042      m_pcIPCMSampleCr[i]=bigCU->m_pcIPCMSampleCr[uiCoffOffset+i];
1043    }
1044  }
1045
1046  m_pcCULeft        = pcCU->getCULeft();
1047  m_pcCUAbove       = pcCU->getCUAbove();
1048  m_pcCUAboveLeft   = pcCU->getCUAboveLeft();
1049  m_pcCUAboveRight  = pcCU->getCUAboveRight();
1050
1051  m_apcCUColocated[0] = pcCU->getCUColocated(REF_PIC_LIST_0);
1052  m_apcCUColocated[1] = pcCU->getCUColocated(REF_PIC_LIST_1);
1053  memcpy(m_sliceStartCU,pcCU->m_sliceStartCU+uiPartOffset,sizeof(UInt)*m_uiNumPartition);
1054  memcpy(m_sliceSegmentStartCU,pcCU->m_sliceSegmentStartCU+uiPartOffset,sizeof(UInt)*m_uiNumPartition);
1055}
1056
1057Void TComDataCU::setOutsideCUPart( UInt uiAbsPartIdx, UInt uiDepth )
1058{
1059  UInt uiNumPartition = m_uiNumPartition >> (uiDepth << 1);
1060  UInt uiSizeInUchar = sizeof( UChar  ) * uiNumPartition;
1061
1062  UChar uhWidth  = g_uiMaxCUWidth  >> uiDepth;
1063  UChar uhHeight = g_uiMaxCUHeight >> uiDepth;
1064  memset( m_puhDepth    + uiAbsPartIdx,     uiDepth,  uiSizeInUchar );
1065  memset( m_puhWidth    + uiAbsPartIdx,     uhWidth,  uiSizeInUchar );
1066  memset( m_puhHeight   + uiAbsPartIdx,     uhHeight, uiSizeInUchar );
1067}
1068
1069// --------------------------------------------------------------------------------------------------------------------
1070// Copy
1071// --------------------------------------------------------------------------------------------------------------------
1072
1073Void TComDataCU::copySubCU( TComDataCU* pcCU, UInt uiAbsPartIdx, UInt uiDepth )
1074{
1075  UInt uiPart = uiAbsPartIdx;
1076 
1077  m_pcPic              = pcCU->getPic();
1078  m_pcSlice            = pcCU->getSlice();
1079  m_uiCUAddr           = pcCU->getAddr();
1080  m_uiAbsIdxInLCU      = uiAbsPartIdx;
1081 
1082  m_uiCUPelX           = pcCU->getCUPelX() + g_auiRasterToPelX[ g_auiZscanToRaster[uiAbsPartIdx] ];
1083  m_uiCUPelY           = pcCU->getCUPelY() + g_auiRasterToPelY[ g_auiZscanToRaster[uiAbsPartIdx] ];
1084 
1085  m_skipFlag=pcCU->getSkipFlag()          + uiPart;
1086
1087  m_phQP=pcCU->getQP()                    + uiPart;
1088  m_pePartSize = pcCU->getPartitionSize() + uiPart;
1089  m_pePredMode=pcCU->getPredictionMode()  + uiPart;
1090  m_CUTransquantBypass  = pcCU->getCUTransquantBypass()+uiPart;
1091 
1092#if H_3D_NBDV
1093  m_pDvInfo             = pcCU->getDvInfo()           + uiPart;
1094#endif
1095  m_pbMergeFlag         = pcCU->getMergeFlag()        + uiPart;
1096  m_puhMergeIndex       = pcCU->getMergeIndex()       + uiPart;
1097#if H_3D_VSP
1098  m_piVSPFlag           = pcCU->getVSPFlag()          + uiPart;
1099#endif
1100#if H_3D_SPIVMP
1101  m_pbSPIVMPFlag        = pcCU->getSPIVMPFlag()          + uiPart;
1102#endif
1103
1104#if H_3D_ARP
1105  m_puhARPW             = pcCU->getARPW()             + uiPart;
1106#endif
1107#if H_3D_IC
1108  m_pbICFlag            = pcCU->getICFlag()           + uiPart;
1109#endif
1110
1111  m_puhLumaIntraDir     = pcCU->getLumaIntraDir()     + uiPart;
1112  m_puhChromaIntraDir   = pcCU->getChromaIntraDir()   + uiPart;
1113  m_puhInterDir         = pcCU->getInterDir()         + uiPart;
1114  m_puhTrIdx            = pcCU->getTransformIdx()     + uiPart;
1115  m_puhTransformSkip[0] = pcCU->getTransformSkip(TEXT_LUMA)     + uiPart;
1116  m_puhTransformSkip[1] = pcCU->getTransformSkip(TEXT_CHROMA_U) + uiPart;
1117  m_puhTransformSkip[2] = pcCU->getTransformSkip(TEXT_CHROMA_V) + uiPart;
1118
1119  m_puhCbf[0]= pcCU->getCbf(TEXT_LUMA)            + uiPart;
1120  m_puhCbf[1]= pcCU->getCbf(TEXT_CHROMA_U)        + uiPart;
1121  m_puhCbf[2]= pcCU->getCbf(TEXT_CHROMA_V)        + uiPart;
1122#if H_3D_DIM
1123  for( Int i = 0; i < DIM_NUM_TYPE; i++ )
1124  {
1125    m_dimDeltaDC[i][0] = pcCU->getDimDeltaDC( i, 0 ) + uiPart;
1126    m_dimDeltaDC[i][1] = pcCU->getDimDeltaDC( i, 1 ) + uiPart;
1127  }
1128#if H_3D_DIM_DMM
1129  for( Int i = 0; i < DMM_NUM_TYPE; i++ )
1130  {
1131    m_dmmWedgeTabIdx[i] = pcCU->getDmmWedgeTabIdx( i ) + uiPart;
1132  }
1133#endif
1134#if H_3D_DIM_SDC
1135  m_pbSDCFlag               = pcCU->getSDCFlag()              + uiPart;
1136  m_apSegmentDCOffset[0]    = pcCU->getSDCSegmentDCOffset(0)  + uiPart;
1137  m_apSegmentDCOffset[1]    = pcCU->getSDCSegmentDCOffset(1)  + uiPart;
1138#endif
1139#endif 
1140#if H_3D_INTER_SDC
1141  m_pbInterSDCFlag          = pcCU->getInterSDCFlag()       + uiPart;
1142  for( Int i = 0; i < 4; i++ )
1143  {
1144    m_apSegmentInterDCOffset[i] = pcCU->getInterSDCSegmentDCOffset( i ) + uiPart;
1145  }
1146#endif
1147  m_puhDepth=pcCU->getDepth()                     + uiPart;
1148  m_puhWidth=pcCU->getWidth()                     + uiPart;
1149  m_puhHeight=pcCU->getHeight()                   + uiPart;
1150 
1151  m_apiMVPIdx[0]=pcCU->getMVPIdx(REF_PIC_LIST_0)  + uiPart;
1152  m_apiMVPIdx[1]=pcCU->getMVPIdx(REF_PIC_LIST_1)  + uiPart;
1153  m_apiMVPNum[0]=pcCU->getMVPNum(REF_PIC_LIST_0)  + uiPart;
1154  m_apiMVPNum[1]=pcCU->getMVPNum(REF_PIC_LIST_1)  + uiPart;
1155 
1156  m_pbIPCMFlag         = pcCU->getIPCMFlag()        + uiPart;
1157
1158  m_pcCUAboveLeft      = pcCU->getCUAboveLeft();
1159  m_pcCUAboveRight     = pcCU->getCUAboveRight();
1160  m_pcCUAbove          = pcCU->getCUAbove();
1161  m_pcCULeft           = pcCU->getCULeft();
1162 
1163  m_apcCUColocated[0] = pcCU->getCUColocated(REF_PIC_LIST_0);
1164  m_apcCUColocated[1] = pcCU->getCUColocated(REF_PIC_LIST_1);
1165 
1166  UInt uiMaxCuWidth=pcCU->getSlice()->getSPS()->getMaxCUWidth();
1167  UInt uiMaxCuHeight=pcCU->getSlice()->getSPS()->getMaxCUHeight();
1168 
1169  UInt uiCoffOffset = uiMaxCuWidth*uiMaxCuHeight*uiAbsPartIdx/pcCU->getPic()->getNumPartInCU();
1170 
1171  m_pcTrCoeffY = pcCU->getCoeffY() + uiCoffOffset;
1172#if ADAPTIVE_QP_SELECTION
1173  m_pcArlCoeffY= pcCU->getArlCoeffY() + uiCoffOffset; 
1174#endif
1175  m_pcIPCMSampleY = pcCU->getPCMSampleY() + uiCoffOffset;
1176
1177  uiCoffOffset >>=2;
1178  m_pcTrCoeffCb=pcCU->getCoeffCb() + uiCoffOffset;
1179  m_pcTrCoeffCr=pcCU->getCoeffCr() + uiCoffOffset;
1180#if ADAPTIVE_QP_SELECTION 
1181  m_pcArlCoeffCb=pcCU->getArlCoeffCb() + uiCoffOffset;
1182  m_pcArlCoeffCr=pcCU->getArlCoeffCr() + uiCoffOffset;
1183#endif
1184  m_pcIPCMSampleCb = pcCU->getPCMSampleCb() + uiCoffOffset;
1185  m_pcIPCMSampleCr = pcCU->getPCMSampleCr() + uiCoffOffset;
1186
1187  m_acCUMvField[0].linkToWithOffset( pcCU->getCUMvField(REF_PIC_LIST_0), uiPart );
1188  m_acCUMvField[1].linkToWithOffset( pcCU->getCUMvField(REF_PIC_LIST_1), uiPart );
1189  memcpy(m_sliceStartCU,pcCU->m_sliceStartCU+uiPart,sizeof(UInt)*m_uiNumPartition);
1190  memcpy(m_sliceSegmentStartCU,pcCU->m_sliceSegmentStartCU+uiPart,sizeof(UInt)*m_uiNumPartition);
1191}
1192#if H_3D_NBDV
1193Void TComDataCU::copyDVInfoFrom (TComDataCU* pcCU, UInt uiAbsPartIdx)
1194{
1195  m_pDvInfo            = pcCU->getDvInfo()                + uiAbsPartIdx;
1196}
1197#endif
1198// Copy inter prediction info from the biggest CU
1199Void TComDataCU::copyInterPredInfoFrom    ( TComDataCU* pcCU, UInt uiAbsPartIdx, RefPicList eRefPicList
1200#if H_3D_NBDV
1201  , Bool bNBDV
1202#endif
1203  )
1204{
1205  m_pcPic              = pcCU->getPic();
1206  m_pcSlice            = pcCU->getSlice();
1207  m_uiCUAddr           = pcCU->getAddr();
1208  m_uiAbsIdxInLCU      = uiAbsPartIdx;
1209 
1210  Int iRastPartIdx     = g_auiZscanToRaster[uiAbsPartIdx];
1211  m_uiCUPelX           = pcCU->getCUPelX() + m_pcPic->getMinCUWidth ()*( iRastPartIdx % m_pcPic->getNumPartInWidth() );
1212  m_uiCUPelY           = pcCU->getCUPelY() + m_pcPic->getMinCUHeight()*( iRastPartIdx / m_pcPic->getNumPartInWidth() );
1213 
1214  m_pcCUAboveLeft      = pcCU->getCUAboveLeft();
1215  m_pcCUAboveRight     = pcCU->getCUAboveRight();
1216  m_pcCUAbove          = pcCU->getCUAbove();
1217  m_pcCULeft           = pcCU->getCULeft();
1218 
1219  m_apcCUColocated[0]  = pcCU->getCUColocated(REF_PIC_LIST_0);
1220  m_apcCUColocated[1]  = pcCU->getCUColocated(REF_PIC_LIST_1);
1221 
1222  m_skipFlag           = pcCU->getSkipFlag ()             + uiAbsPartIdx;
1223
1224  m_pePartSize         = pcCU->getPartitionSize ()        + uiAbsPartIdx;
1225#if H_3D_NBDV
1226  if(bNBDV == true)
1227  {
1228    m_puhWidth           = pcCU->getWidth ()                + uiAbsPartIdx;
1229    m_puhHeight          = pcCU->getHeight()                + uiAbsPartIdx;
1230    m_puhDepth           = pcCU->getDepth ()                + uiAbsPartIdx;
1231  }
1232  else
1233  {
1234#endif
1235  m_pePredMode         = pcCU->getPredictionMode()        + uiAbsPartIdx;
1236  m_CUTransquantBypass = pcCU->getCUTransquantBypass()    + uiAbsPartIdx;
1237  m_puhInterDir        = pcCU->getInterDir      ()        + uiAbsPartIdx;
1238 
1239  m_puhDepth           = pcCU->getDepth ()                + uiAbsPartIdx;
1240  m_puhWidth           = pcCU->getWidth ()                + uiAbsPartIdx;
1241  m_puhHeight          = pcCU->getHeight()                + uiAbsPartIdx;
1242 
1243  m_pbMergeFlag        = pcCU->getMergeFlag()             + uiAbsPartIdx;
1244  m_puhMergeIndex      = pcCU->getMergeIndex()            + uiAbsPartIdx;
1245#if H_3D_VSP
1246  m_piVSPFlag          = pcCU->getVSPFlag()               + uiAbsPartIdx;
1247  m_pDvInfo            = pcCU->getDvInfo()                + uiAbsPartIdx;
1248#endif
1249#if H_3D_SPIVMP
1250  m_pbSPIVMPFlag       = pcCU->getSPIVMPFlag()               + uiAbsPartIdx;
1251#endif
1252
1253  m_apiMVPIdx[eRefPicList] = pcCU->getMVPIdx(eRefPicList) + uiAbsPartIdx;
1254  m_apiMVPNum[eRefPicList] = pcCU->getMVPNum(eRefPicList) + uiAbsPartIdx;
1255 
1256#if H_3D_ARP
1257  m_puhARPW            = pcCU->getARPW()                  + uiAbsPartIdx;
1258#endif
1259
1260  m_acCUMvField[ eRefPicList ].linkToWithOffset( pcCU->getCUMvField(eRefPicList), uiAbsPartIdx );
1261
1262  memcpy(m_sliceStartCU,pcCU->m_sliceStartCU+uiAbsPartIdx,sizeof(UInt)*m_uiNumPartition);
1263  memcpy(m_sliceSegmentStartCU,pcCU->m_sliceSegmentStartCU+uiAbsPartIdx,sizeof(UInt)*m_uiNumPartition);
1264#if H_3D_NBDV
1265  }
1266#endif
1267#if H_3D_IC
1268  m_pbICFlag           = pcCU->getICFlag()                + uiAbsPartIdx;
1269#endif
1270}
1271
1272// Copy small CU to bigger CU.
1273// One of quarter parts overwritten by predicted sub part.
1274Void TComDataCU::copyPartFrom( TComDataCU* pcCU, UInt uiPartUnitIdx, UInt uiDepth )
1275{
1276  assert( uiPartUnitIdx<4 );
1277 
1278  m_dTotalCost         += pcCU->getTotalCost();
1279  m_uiTotalDistortion  += pcCU->getTotalDistortion();
1280  m_uiTotalBits        += pcCU->getTotalBits();
1281 
1282  UInt uiOffset         = pcCU->getTotalNumPart()*uiPartUnitIdx;
1283 
1284  UInt uiNumPartition = pcCU->getTotalNumPart();
1285  Int iSizeInUchar  = sizeof( UChar ) * uiNumPartition;
1286  Int iSizeInBool   = sizeof( Bool  ) * uiNumPartition;
1287 
1288  Int sizeInChar  = sizeof( Char ) * uiNumPartition;
1289  memcpy( m_skipFlag   + uiOffset, pcCU->getSkipFlag(),       sizeof( *m_skipFlag )   * uiNumPartition );
1290  memcpy( m_phQP       + uiOffset, pcCU->getQP(),             sizeInChar                        );
1291  memcpy( m_pePartSize + uiOffset, pcCU->getPartitionSize(),  sizeof( *m_pePartSize ) * uiNumPartition );
1292  memcpy( m_pePredMode + uiOffset, pcCU->getPredictionMode(), sizeof( *m_pePredMode ) * uiNumPartition );
1293  memcpy( m_CUTransquantBypass + uiOffset, pcCU->getCUTransquantBypass(), sizeof( *m_CUTransquantBypass ) * uiNumPartition );
1294  memcpy( m_pbMergeFlag         + uiOffset, pcCU->getMergeFlag(),         iSizeInBool  );
1295  memcpy( m_puhMergeIndex       + uiOffset, pcCU->getMergeIndex(),        iSizeInUchar );
1296#if H_3D_VSP
1297  memcpy( m_piVSPFlag           + uiOffset, pcCU->getVSPFlag(),           sizeof( Char ) * uiNumPartition );
1298  memcpy( m_pDvInfo             + uiOffset, pcCU->getDvInfo(),            sizeof( *m_pDvInfo ) * uiNumPartition );
1299
1300#endif
1301#if H_3D_SPIVMP
1302  memcpy( m_pbSPIVMPFlag        + uiOffset, pcCU->getSPIVMPFlag(),        sizeof( Bool ) * uiNumPartition );
1303#endif
1304  memcpy( m_puhLumaIntraDir     + uiOffset, pcCU->getLumaIntraDir(),      iSizeInUchar );
1305  memcpy( m_puhChromaIntraDir   + uiOffset, pcCU->getChromaIntraDir(),    iSizeInUchar );
1306  memcpy( m_puhInterDir         + uiOffset, pcCU->getInterDir(),          iSizeInUchar );
1307  memcpy( m_puhTrIdx            + uiOffset, pcCU->getTransformIdx(),      iSizeInUchar );
1308  memcpy( m_puhTransformSkip[0] + uiOffset, pcCU->getTransformSkip(TEXT_LUMA),     iSizeInUchar );
1309  memcpy( m_puhTransformSkip[1] + uiOffset, pcCU->getTransformSkip(TEXT_CHROMA_U), iSizeInUchar );
1310  memcpy( m_puhTransformSkip[2] + uiOffset, pcCU->getTransformSkip(TEXT_CHROMA_V), iSizeInUchar );
1311
1312  memcpy( m_puhCbf[0] + uiOffset, pcCU->getCbf(TEXT_LUMA)    , iSizeInUchar );
1313  memcpy( m_puhCbf[1] + uiOffset, pcCU->getCbf(TEXT_CHROMA_U), iSizeInUchar );
1314  memcpy( m_puhCbf[2] + uiOffset, pcCU->getCbf(TEXT_CHROMA_V), iSizeInUchar );
1315 
1316#if H_3D_DIM
1317  for( Int i = 0; i < DIM_NUM_TYPE; i++ )
1318  {
1319    memcpy( m_dimDeltaDC[i][0] + uiOffset, pcCU->getDimDeltaDC( i, 0 ), sizeof(Pel ) * uiNumPartition );
1320    memcpy( m_dimDeltaDC[i][1] + uiOffset, pcCU->getDimDeltaDC( i, 1 ), sizeof(Pel ) * uiNumPartition );
1321  }
1322#if H_3D_DIM_DMM
1323  for( Int i = 0; i < DMM_NUM_TYPE; i++ )
1324  {
1325    memcpy( m_dmmWedgeTabIdx[i] + uiOffset, pcCU->getDmmWedgeTabIdx( i ), sizeof(UInt) * uiNumPartition );
1326  }
1327#endif
1328#if H_3D_DIM_SDC
1329  memcpy( m_pbSDCFlag             + uiOffset, pcCU->getSDCFlag(),             iSizeInBool  );
1330  memcpy( m_apSegmentDCOffset[0]  + uiOffset, pcCU->getSDCSegmentDCOffset(0), sizeof( Pel ) * uiNumPartition);
1331  memcpy( m_apSegmentDCOffset[1]  + uiOffset, pcCU->getSDCSegmentDCOffset(1), sizeof( Pel ) * uiNumPartition);
1332#endif
1333#endif
1334#if H_3D_INTER_SDC
1335  memcpy( m_pbInterSDCFlag  + uiOffset, pcCU->getInterSDCFlag(),      iSizeInBool  );
1336  for( Int i = 0; i < 4; i++ )
1337  {
1338    memcpy( m_apSegmentInterDCOffset[i] + uiOffset, pcCU->getInterSDCSegmentDCOffset( i ), sizeof( Int ) * uiNumPartition);
1339  }
1340#endif
1341
1342  memcpy( m_puhDepth  + uiOffset, pcCU->getDepth(),  iSizeInUchar );
1343  memcpy( m_puhWidth  + uiOffset, pcCU->getWidth(),  iSizeInUchar );
1344  memcpy( m_puhHeight + uiOffset, pcCU->getHeight(), iSizeInUchar );
1345 
1346  memcpy( m_apiMVPIdx[0] + uiOffset, pcCU->getMVPIdx(REF_PIC_LIST_0), iSizeInUchar );
1347  memcpy( m_apiMVPIdx[1] + uiOffset, pcCU->getMVPIdx(REF_PIC_LIST_1), iSizeInUchar );
1348  memcpy( m_apiMVPNum[0] + uiOffset, pcCU->getMVPNum(REF_PIC_LIST_0), iSizeInUchar );
1349  memcpy( m_apiMVPNum[1] + uiOffset, pcCU->getMVPNum(REF_PIC_LIST_1), iSizeInUchar );
1350 
1351  memcpy( m_pbIPCMFlag + uiOffset, pcCU->getIPCMFlag(), iSizeInBool );
1352
1353  m_pcCUAboveLeft      = pcCU->getCUAboveLeft();
1354  m_pcCUAboveRight     = pcCU->getCUAboveRight();
1355  m_pcCUAbove          = pcCU->getCUAbove();
1356  m_pcCULeft           = pcCU->getCULeft();
1357 
1358  m_apcCUColocated[0] = pcCU->getCUColocated(REF_PIC_LIST_0);
1359  m_apcCUColocated[1] = pcCU->getCUColocated(REF_PIC_LIST_1);
1360 
1361  m_acCUMvField[0].copyFrom( pcCU->getCUMvField( REF_PIC_LIST_0 ), pcCU->getTotalNumPart(), uiOffset );
1362  m_acCUMvField[1].copyFrom( pcCU->getCUMvField( REF_PIC_LIST_1 ), pcCU->getTotalNumPart(), uiOffset );
1363 
1364  UInt uiTmp  = g_uiMaxCUWidth*g_uiMaxCUHeight >> (uiDepth<<1);
1365  UInt uiTmp2 = uiPartUnitIdx*uiTmp;
1366  memcpy( m_pcTrCoeffY  + uiTmp2, pcCU->getCoeffY(),  sizeof(TCoeff)*uiTmp );
1367#if ADAPTIVE_QP_SELECTION
1368  memcpy( m_pcArlCoeffY  + uiTmp2, pcCU->getArlCoeffY(),  sizeof(Int)*uiTmp );
1369#endif
1370  memcpy( m_pcIPCMSampleY + uiTmp2 , pcCU->getPCMSampleY(), sizeof(Pel) * uiTmp );
1371
1372  uiTmp >>= 2; uiTmp2>>= 2;
1373  memcpy( m_pcTrCoeffCb + uiTmp2, pcCU->getCoeffCb(), sizeof(TCoeff)*uiTmp );
1374  memcpy( m_pcTrCoeffCr + uiTmp2, pcCU->getCoeffCr(), sizeof(TCoeff)*uiTmp );
1375#if ADAPTIVE_QP_SELECTION
1376  memcpy( m_pcArlCoeffCb + uiTmp2, pcCU->getArlCoeffCb(), sizeof(Int)*uiTmp );
1377  memcpy( m_pcArlCoeffCr + uiTmp2, pcCU->getArlCoeffCr(), sizeof(Int)*uiTmp );
1378#endif
1379  memcpy( m_pcIPCMSampleCb + uiTmp2 , pcCU->getPCMSampleCb(), sizeof(Pel) * uiTmp );
1380  memcpy( m_pcIPCMSampleCr + uiTmp2 , pcCU->getPCMSampleCr(), sizeof(Pel) * uiTmp );
1381  m_uiTotalBins += pcCU->getTotalBins();
1382  memcpy( m_sliceStartCU        + uiOffset, pcCU->m_sliceStartCU,        sizeof( UInt ) * uiNumPartition  );
1383  memcpy( m_sliceSegmentStartCU + uiOffset, pcCU->m_sliceSegmentStartCU, sizeof( UInt ) * uiNumPartition  );
1384#if H_3D_ARP
1385  memcpy( m_puhARPW             + uiOffset, pcCU->getARPW(),              iSizeInUchar );
1386#endif
1387#if H_3D_IC
1388  memcpy( m_pbICFlag            + uiOffset, pcCU->getICFlag(),            iSizeInBool );
1389#endif
1390}
1391
1392// Copy current predicted part to a CU in picture.
1393// It is used to predict for next part
1394Void TComDataCU::copyToPic( UChar uhDepth )
1395{
1396  TComDataCU*& rpcCU = m_pcPic->getCU( m_uiCUAddr );
1397 
1398  rpcCU->getTotalCost()       = m_dTotalCost;
1399  rpcCU->getTotalDistortion() = m_uiTotalDistortion;
1400  rpcCU->getTotalBits()       = m_uiTotalBits;
1401 
1402  Int iSizeInUchar  = sizeof( UChar ) * m_uiNumPartition;
1403  Int iSizeInBool   = sizeof( Bool  ) * m_uiNumPartition;
1404 
1405  Int sizeInChar  = sizeof( Char ) * m_uiNumPartition;
1406
1407  memcpy( rpcCU->getSkipFlag() + m_uiAbsIdxInLCU, m_skipFlag, sizeof( *m_skipFlag ) * m_uiNumPartition );
1408
1409  memcpy( rpcCU->getQP() + m_uiAbsIdxInLCU, m_phQP, sizeInChar  );
1410#if H_3D_NBDV
1411  memcpy( rpcCU->getDvInfo()         + m_uiAbsIdxInLCU, m_pDvInfo,    sizeof(* m_pDvInfo)     * m_uiNumPartition );
1412#endif
1413
1414  memcpy( rpcCU->getPartitionSize()  + m_uiAbsIdxInLCU, m_pePartSize, sizeof( *m_pePartSize ) * m_uiNumPartition );
1415  memcpy( rpcCU->getPredictionMode() + m_uiAbsIdxInLCU, m_pePredMode, sizeof( *m_pePredMode ) * m_uiNumPartition );
1416  memcpy( rpcCU->getCUTransquantBypass()+ m_uiAbsIdxInLCU, m_CUTransquantBypass, sizeof( *m_CUTransquantBypass ) * m_uiNumPartition );
1417  memcpy( rpcCU->getMergeFlag()         + m_uiAbsIdxInLCU, m_pbMergeFlag,         iSizeInBool  );
1418  memcpy( rpcCU->getMergeIndex()        + m_uiAbsIdxInLCU, m_puhMergeIndex,       iSizeInUchar );
1419#if H_3D_VSP
1420  memcpy( rpcCU->getVSPFlag()           + m_uiAbsIdxInLCU, m_piVSPFlag,           sizeof( Char ) * m_uiNumPartition );
1421  memcpy( rpcCU->getDvInfo()            + m_uiAbsIdxInLCU, m_pDvInfo,             sizeof( *m_pDvInfo ) * m_uiNumPartition );
1422#endif
1423#if H_3D_SPIVMP
1424  memcpy( rpcCU->getSPIVMPFlag()        + m_uiAbsIdxInLCU, m_pbSPIVMPFlag,        sizeof( Bool ) * m_uiNumPartition );
1425#endif
1426  memcpy( rpcCU->getLumaIntraDir()      + m_uiAbsIdxInLCU, m_puhLumaIntraDir,     iSizeInUchar );
1427  memcpy( rpcCU->getChromaIntraDir()    + m_uiAbsIdxInLCU, m_puhChromaIntraDir,   iSizeInUchar );
1428  memcpy( rpcCU->getInterDir()          + m_uiAbsIdxInLCU, m_puhInterDir,         iSizeInUchar );
1429  memcpy( rpcCU->getTransformIdx()      + m_uiAbsIdxInLCU, m_puhTrIdx,            iSizeInUchar );
1430  memcpy( rpcCU->getTransformSkip(TEXT_LUMA)     + m_uiAbsIdxInLCU, m_puhTransformSkip[0], iSizeInUchar );
1431  memcpy( rpcCU->getTransformSkip(TEXT_CHROMA_U) + m_uiAbsIdxInLCU, m_puhTransformSkip[1], iSizeInUchar );
1432  memcpy( rpcCU->getTransformSkip(TEXT_CHROMA_V) + m_uiAbsIdxInLCU, m_puhTransformSkip[2], iSizeInUchar );
1433
1434  memcpy( rpcCU->getCbf(TEXT_LUMA)     + m_uiAbsIdxInLCU, m_puhCbf[0], iSizeInUchar );
1435  memcpy( rpcCU->getCbf(TEXT_CHROMA_U) + m_uiAbsIdxInLCU, m_puhCbf[1], iSizeInUchar );
1436  memcpy( rpcCU->getCbf(TEXT_CHROMA_V) + m_uiAbsIdxInLCU, m_puhCbf[2], iSizeInUchar );
1437 
1438#if H_3D_DIM
1439  for( Int i = 0; i < DIM_NUM_TYPE; i++ )
1440  {
1441    memcpy( rpcCU->getDimDeltaDC( i, 0 ) + m_uiAbsIdxInLCU, m_dimDeltaDC[i][0], sizeof(Pel ) * m_uiNumPartition );
1442    memcpy( rpcCU->getDimDeltaDC( i, 1 ) + m_uiAbsIdxInLCU, m_dimDeltaDC[i][1], sizeof(Pel ) * m_uiNumPartition );
1443  }
1444#if H_3D_DIM_DMM
1445  for( Int i = 0; i < DMM_NUM_TYPE; i++ )
1446  {
1447    memcpy( rpcCU->getDmmWedgeTabIdx( i ) + m_uiAbsIdxInLCU, m_dmmWedgeTabIdx[i], sizeof(UInt) * m_uiNumPartition );
1448  }
1449#endif
1450#if H_3D_DIM_SDC
1451  memcpy( rpcCU->getSDCFlag()             + m_uiAbsIdxInLCU, m_pbSDCFlag,      iSizeInBool  );
1452  memcpy( rpcCU->getSDCSegmentDCOffset(0) + m_uiAbsIdxInLCU, m_apSegmentDCOffset[0], sizeof( Pel ) * m_uiNumPartition);
1453  memcpy( rpcCU->getSDCSegmentDCOffset(1) + m_uiAbsIdxInLCU, m_apSegmentDCOffset[1], sizeof( Pel ) * m_uiNumPartition);
1454#endif
1455#endif
1456#if H_3D_INTER_SDC
1457  memcpy( rpcCU->getInterSDCFlag() + m_uiAbsIdxInLCU, m_pbInterSDCFlag,      iSizeInBool  );
1458  for( Int i = 0;i < 4; i++ )
1459  {
1460    memcpy( rpcCU->getInterSDCSegmentDCOffset( i ) + m_uiAbsIdxInLCU, m_apSegmentInterDCOffset[i], sizeof( Int ) * m_uiNumPartition);
1461  }
1462#endif
1463  memcpy( rpcCU->getDepth()  + m_uiAbsIdxInLCU, m_puhDepth,  iSizeInUchar );
1464  memcpy( rpcCU->getWidth()  + m_uiAbsIdxInLCU, m_puhWidth,  iSizeInUchar );
1465  memcpy( rpcCU->getHeight() + m_uiAbsIdxInLCU, m_puhHeight, iSizeInUchar );
1466 
1467  memcpy( rpcCU->getMVPIdx(REF_PIC_LIST_0) + m_uiAbsIdxInLCU, m_apiMVPIdx[0], iSizeInUchar );
1468  memcpy( rpcCU->getMVPIdx(REF_PIC_LIST_1) + m_uiAbsIdxInLCU, m_apiMVPIdx[1], iSizeInUchar );
1469  memcpy( rpcCU->getMVPNum(REF_PIC_LIST_0) + m_uiAbsIdxInLCU, m_apiMVPNum[0], iSizeInUchar );
1470  memcpy( rpcCU->getMVPNum(REF_PIC_LIST_1) + m_uiAbsIdxInLCU, m_apiMVPNum[1], iSizeInUchar );
1471 
1472  m_acCUMvField[0].copyTo( rpcCU->getCUMvField( REF_PIC_LIST_0 ), m_uiAbsIdxInLCU );
1473  m_acCUMvField[1].copyTo( rpcCU->getCUMvField( REF_PIC_LIST_1 ), m_uiAbsIdxInLCU );
1474 
1475  memcpy( rpcCU->getIPCMFlag() + m_uiAbsIdxInLCU, m_pbIPCMFlag,         iSizeInBool  );
1476
1477  UInt uiTmp  = (g_uiMaxCUWidth*g_uiMaxCUHeight)>>(uhDepth<<1);
1478  UInt uiTmp2 = m_uiAbsIdxInLCU*m_pcPic->getMinCUWidth()*m_pcPic->getMinCUHeight();
1479  memcpy( rpcCU->getCoeffY()  + uiTmp2, m_pcTrCoeffY,  sizeof(TCoeff)*uiTmp  );
1480#if ADAPTIVE_QP_SELECTION 
1481  memcpy( rpcCU->getArlCoeffY()  + uiTmp2, m_pcArlCoeffY,  sizeof(Int)*uiTmp  );
1482#endif
1483  memcpy( rpcCU->getPCMSampleY() + uiTmp2 , m_pcIPCMSampleY, sizeof(Pel)*uiTmp );
1484
1485  uiTmp >>= 2; uiTmp2 >>= 2;
1486  memcpy( rpcCU->getCoeffCb() + uiTmp2, m_pcTrCoeffCb, sizeof(TCoeff)*uiTmp  );
1487  memcpy( rpcCU->getCoeffCr() + uiTmp2, m_pcTrCoeffCr, sizeof(TCoeff)*uiTmp  );
1488#if ADAPTIVE_QP_SELECTION
1489  memcpy( rpcCU->getArlCoeffCb() + uiTmp2, m_pcArlCoeffCb, sizeof(Int)*uiTmp  );
1490  memcpy( rpcCU->getArlCoeffCr() + uiTmp2, m_pcArlCoeffCr, sizeof(Int)*uiTmp  );
1491#endif
1492  memcpy( rpcCU->getPCMSampleCb() + uiTmp2 , m_pcIPCMSampleCb, sizeof( Pel ) * uiTmp );
1493  memcpy( rpcCU->getPCMSampleCr() + uiTmp2 , m_pcIPCMSampleCr, sizeof( Pel ) * uiTmp );
1494  rpcCU->getTotalBins() = m_uiTotalBins;
1495  memcpy( rpcCU->m_sliceStartCU        + m_uiAbsIdxInLCU, m_sliceStartCU,        sizeof( UInt ) * m_uiNumPartition  );
1496  memcpy( rpcCU->m_sliceSegmentStartCU + m_uiAbsIdxInLCU, m_sliceSegmentStartCU, sizeof( UInt ) * m_uiNumPartition  );
1497#if H_3D_ARP
1498  memcpy( rpcCU->getARPW()             + m_uiAbsIdxInLCU, m_puhARPW,             iSizeInUchar );
1499#endif
1500#if H_3D_IC
1501  memcpy( rpcCU->getICFlag()           + m_uiAbsIdxInLCU, m_pbICFlag,            iSizeInBool );
1502#endif
1503}
1504
1505Void TComDataCU::copyToPic( UChar uhDepth, UInt uiPartIdx, UInt uiPartDepth )
1506{
1507  TComDataCU*&  rpcCU       = m_pcPic->getCU( m_uiCUAddr );
1508  UInt          uiQNumPart  = m_uiNumPartition>>(uiPartDepth<<1);
1509 
1510  UInt uiPartStart          = uiPartIdx*uiQNumPart;
1511  UInt uiPartOffset         = m_uiAbsIdxInLCU + uiPartStart;
1512 
1513  rpcCU->getTotalCost()       = m_dTotalCost;
1514  rpcCU->getTotalDistortion() = m_uiTotalDistortion;
1515  rpcCU->getTotalBits()       = m_uiTotalBits;
1516 
1517  Int iSizeInUchar  = sizeof( UChar  ) * uiQNumPart;
1518  Int iSizeInBool   = sizeof( Bool   ) * uiQNumPart;
1519 
1520  Int sizeInChar  = sizeof( Char ) * uiQNumPart;
1521  memcpy( rpcCU->getSkipFlag()       + uiPartOffset, m_skipFlag,   sizeof( *m_skipFlag )   * uiQNumPart );
1522
1523  memcpy( rpcCU->getQP() + uiPartOffset, m_phQP, sizeInChar );
1524  memcpy( rpcCU->getPartitionSize()  + uiPartOffset, m_pePartSize, sizeof( *m_pePartSize ) * uiQNumPart );
1525  memcpy( rpcCU->getPredictionMode() + uiPartOffset, m_pePredMode, sizeof( *m_pePredMode ) * uiQNumPart );
1526  memcpy( rpcCU->getCUTransquantBypass()+ uiPartOffset, m_CUTransquantBypass, sizeof( *m_CUTransquantBypass ) * uiQNumPart );
1527  memcpy( rpcCU->getMergeFlag()         + uiPartOffset, m_pbMergeFlag,         iSizeInBool  );
1528  memcpy( rpcCU->getMergeIndex()        + uiPartOffset, m_puhMergeIndex,       iSizeInUchar );
1529#if H_3D_VSP
1530  memcpy( rpcCU->getVSPFlag()           + uiPartOffset, m_piVSPFlag,           sizeof(Char) * uiQNumPart );
1531#endif
1532#if H_3D_SPIVMP
1533  memcpy( rpcCU->getSPIVMPFlag()        + uiPartOffset, m_pbSPIVMPFlag,        sizeof(Bool) * uiQNumPart );
1534#endif
1535  memcpy( rpcCU->getLumaIntraDir()      + uiPartOffset, m_puhLumaIntraDir,     iSizeInUchar );
1536  memcpy( rpcCU->getChromaIntraDir()    + uiPartOffset, m_puhChromaIntraDir,   iSizeInUchar );
1537  memcpy( rpcCU->getInterDir()          + uiPartOffset, m_puhInterDir,         iSizeInUchar );
1538  memcpy( rpcCU->getTransformIdx()      + uiPartOffset, m_puhTrIdx,            iSizeInUchar );
1539  memcpy( rpcCU->getTransformSkip(TEXT_LUMA)     + uiPartOffset, m_puhTransformSkip[0], iSizeInUchar );
1540  memcpy( rpcCU->getTransformSkip(TEXT_CHROMA_U) + uiPartOffset, m_puhTransformSkip[1], iSizeInUchar );
1541  memcpy( rpcCU->getTransformSkip(TEXT_CHROMA_V) + uiPartOffset, m_puhTransformSkip[2], iSizeInUchar );
1542  memcpy( rpcCU->getCbf(TEXT_LUMA)     + uiPartOffset, m_puhCbf[0], iSizeInUchar );
1543  memcpy( rpcCU->getCbf(TEXT_CHROMA_U) + uiPartOffset, m_puhCbf[1], iSizeInUchar );
1544  memcpy( rpcCU->getCbf(TEXT_CHROMA_V) + uiPartOffset, m_puhCbf[2], iSizeInUchar );
1545 
1546#if H_3D_DIM
1547  for( Int i = 0; i < DMM_NUM_TYPE; i++ )
1548  {
1549    memcpy( rpcCU->getDimDeltaDC( i, 0 ) + uiPartOffset, m_dimDeltaDC[i][0], sizeof(Pel ) * uiQNumPart );
1550    memcpy( rpcCU->getDimDeltaDC( i, 1 ) + uiPartOffset, m_dimDeltaDC[i][1], sizeof(Pel ) * uiQNumPart );
1551  }
1552#if H_3D_DIM_DMM
1553  for( Int i = 0; i < DMM_NUM_TYPE; i++ )
1554  {
1555    memcpy( rpcCU->getDmmWedgeTabIdx( i ) + uiPartOffset, m_dmmWedgeTabIdx[i], sizeof(UInt) * uiQNumPart );
1556  }
1557#endif
1558#if H_3D_DIM_SDC
1559  memcpy( rpcCU->getSDCFlag()             + uiPartOffset, m_pbSDCFlag,      iSizeInBool  );
1560  memcpy( rpcCU->getSDCSegmentDCOffset(0) + uiPartOffset, m_apSegmentDCOffset[0], sizeof( Pel ) * uiQNumPart);
1561  memcpy( rpcCU->getSDCSegmentDCOffset(1) + uiPartOffset, m_apSegmentDCOffset[1], sizeof( Pel ) * uiQNumPart);
1562#endif
1563#endif
1564#if H_3D_INTER_SDC
1565  memcpy( rpcCU->getInterSDCFlag() + uiPartOffset, m_pbInterSDCFlag,      iSizeInBool  );
1566  for( Int i = 0; i < 4; i++ )
1567  {
1568    memcpy( rpcCU->getInterSDCSegmentDCOffset( i ) + uiPartOffset, m_apSegmentInterDCOffset[i], sizeof( Int ) * uiQNumPart);
1569  }
1570#endif
1571  memcpy( rpcCU->getDepth()  + uiPartOffset, m_puhDepth,  iSizeInUchar );
1572  memcpy( rpcCU->getWidth()  + uiPartOffset, m_puhWidth,  iSizeInUchar );
1573  memcpy( rpcCU->getHeight() + uiPartOffset, m_puhHeight, iSizeInUchar );
1574 
1575  memcpy( rpcCU->getMVPIdx(REF_PIC_LIST_0) + uiPartOffset, m_apiMVPIdx[0], iSizeInUchar );
1576  memcpy( rpcCU->getMVPIdx(REF_PIC_LIST_1) + uiPartOffset, m_apiMVPIdx[1], iSizeInUchar );
1577  memcpy( rpcCU->getMVPNum(REF_PIC_LIST_0) + uiPartOffset, m_apiMVPNum[0], iSizeInUchar );
1578  memcpy( rpcCU->getMVPNum(REF_PIC_LIST_1) + uiPartOffset, m_apiMVPNum[1], iSizeInUchar );
1579  m_acCUMvField[0].copyTo( rpcCU->getCUMvField( REF_PIC_LIST_0 ), m_uiAbsIdxInLCU, uiPartStart, uiQNumPart );
1580  m_acCUMvField[1].copyTo( rpcCU->getCUMvField( REF_PIC_LIST_1 ), m_uiAbsIdxInLCU, uiPartStart, uiQNumPart );
1581 
1582  memcpy( rpcCU->getIPCMFlag() + uiPartOffset, m_pbIPCMFlag,         iSizeInBool  );
1583
1584  UInt uiTmp  = (g_uiMaxCUWidth*g_uiMaxCUHeight)>>((uhDepth+uiPartDepth)<<1);
1585  UInt uiTmp2 = uiPartOffset*m_pcPic->getMinCUWidth()*m_pcPic->getMinCUHeight();
1586  memcpy( rpcCU->getCoeffY()  + uiTmp2, m_pcTrCoeffY,  sizeof(TCoeff)*uiTmp  );
1587#if ADAPTIVE_QP_SELECTION
1588  memcpy( rpcCU->getArlCoeffY()  + uiTmp2, m_pcArlCoeffY,  sizeof(Int)*uiTmp  );
1589#endif
1590 
1591  memcpy( rpcCU->getPCMSampleY() + uiTmp2 , m_pcIPCMSampleY, sizeof( Pel ) * uiTmp );
1592
1593  uiTmp >>= 2; uiTmp2 >>= 2;
1594  memcpy( rpcCU->getCoeffCb() + uiTmp2, m_pcTrCoeffCb, sizeof(TCoeff)*uiTmp  );
1595  memcpy( rpcCU->getCoeffCr() + uiTmp2, m_pcTrCoeffCr, sizeof(TCoeff)*uiTmp  );
1596#if ADAPTIVE_QP_SELECTION
1597  memcpy( rpcCU->getArlCoeffCb() + uiTmp2, m_pcArlCoeffCb, sizeof(Int)*uiTmp  );
1598  memcpy( rpcCU->getArlCoeffCr() + uiTmp2, m_pcArlCoeffCr, sizeof(Int)*uiTmp  );
1599#endif
1600
1601  memcpy( rpcCU->getPCMSampleCb() + uiTmp2 , m_pcIPCMSampleCb, sizeof( Pel ) * uiTmp );
1602  memcpy( rpcCU->getPCMSampleCr() + uiTmp2 , m_pcIPCMSampleCr, sizeof( Pel ) * uiTmp );
1603  rpcCU->getTotalBins() = m_uiTotalBins;
1604  memcpy( rpcCU->m_sliceStartCU        + uiPartOffset, m_sliceStartCU,        sizeof( UInt ) * uiQNumPart  );
1605  memcpy( rpcCU->m_sliceSegmentStartCU + uiPartOffset, m_sliceSegmentStartCU, sizeof( UInt ) * uiQNumPart  );
1606#if H_3D_ARP
1607  memcpy( rpcCU->getARPW()             + uiPartOffset, m_puhARPW,             iSizeInUchar );
1608#endif
1609#if H_3D_IC
1610  memcpy( rpcCU->getICFlag()           + uiPartOffset, m_pbICFlag,            iSizeInBool );
1611#endif
1612}
1613
1614// --------------------------------------------------------------------------------------------------------------------
1615// Other public functions
1616// --------------------------------------------------------------------------------------------------------------------
1617
1618TComDataCU* TComDataCU::getPULeft( UInt& uiLPartUnitIdx, 
1619                                   UInt uiCurrPartUnitIdx, 
1620                                   Bool bEnforceSliceRestriction, 
1621                                   Bool bEnforceTileRestriction )
1622{
1623  UInt uiAbsPartIdx       = g_auiZscanToRaster[uiCurrPartUnitIdx];
1624  UInt uiAbsZorderCUIdx   = g_auiZscanToRaster[m_uiAbsIdxInLCU];
1625  UInt uiNumPartInCUWidth = m_pcPic->getNumPartInWidth();
1626 
1627  if ( !RasterAddress::isZeroCol( uiAbsPartIdx, uiNumPartInCUWidth ) )
1628  {
1629    uiLPartUnitIdx = g_auiRasterToZscan[ uiAbsPartIdx - 1 ];
1630    if ( RasterAddress::isEqualCol( uiAbsPartIdx, uiAbsZorderCUIdx, uiNumPartInCUWidth ) )
1631    {
1632      return m_pcPic->getCU( getAddr() );
1633    }
1634    else
1635    {
1636      uiLPartUnitIdx -= m_uiAbsIdxInLCU;
1637      return this;
1638    }
1639  }
1640 
1641  uiLPartUnitIdx = g_auiRasterToZscan[ uiAbsPartIdx + uiNumPartInCUWidth - 1 ];
1642
1643
1644  if ( (bEnforceSliceRestriction && (m_pcCULeft==NULL || m_pcCULeft->getSlice()==NULL || m_pcCULeft->getSCUAddr()+uiLPartUnitIdx < m_pcPic->getCU( getAddr() )->getSliceStartCU(uiCurrPartUnitIdx)))
1645      ||
1646       (bEnforceTileRestriction && ( m_pcCULeft==NULL || m_pcCULeft->getSlice()==NULL || (m_pcPic->getPicSym()->getTileIdxMap( m_pcCULeft->getAddr() ) != m_pcPic->getPicSym()->getTileIdxMap(getAddr()))  )  )
1647      )
1648  {
1649    return NULL;
1650  }
1651  return m_pcCULeft;
1652}
1653
1654TComDataCU* TComDataCU::getPUAbove( UInt& uiAPartUnitIdx,
1655                                    UInt uiCurrPartUnitIdx, 
1656                                    Bool bEnforceSliceRestriction, 
1657                                    Bool planarAtLCUBoundary ,
1658                                    Bool bEnforceTileRestriction )
1659{
1660  UInt uiAbsPartIdx       = g_auiZscanToRaster[uiCurrPartUnitIdx];
1661  UInt uiAbsZorderCUIdx   = g_auiZscanToRaster[m_uiAbsIdxInLCU];
1662  UInt uiNumPartInCUWidth = m_pcPic->getNumPartInWidth();
1663 
1664  if ( !RasterAddress::isZeroRow( uiAbsPartIdx, uiNumPartInCUWidth ) )
1665  {
1666    uiAPartUnitIdx = g_auiRasterToZscan[ uiAbsPartIdx - uiNumPartInCUWidth ];
1667    if ( RasterAddress::isEqualRow( uiAbsPartIdx, uiAbsZorderCUIdx, uiNumPartInCUWidth ) )
1668    {
1669      return m_pcPic->getCU( getAddr() );
1670    }
1671    else
1672    {
1673      uiAPartUnitIdx -= m_uiAbsIdxInLCU;
1674      return this;
1675    }
1676  }
1677
1678  if(planarAtLCUBoundary)
1679  {
1680    return NULL;
1681  }
1682 
1683  uiAPartUnitIdx = g_auiRasterToZscan[ uiAbsPartIdx + m_pcPic->getNumPartInCU() - uiNumPartInCUWidth ];
1684
1685  if ( (bEnforceSliceRestriction && (m_pcCUAbove==NULL || m_pcCUAbove->getSlice()==NULL || m_pcCUAbove->getSCUAddr()+uiAPartUnitIdx < m_pcPic->getCU( getAddr() )->getSliceStartCU(uiCurrPartUnitIdx)))
1686      ||
1687       (bEnforceTileRestriction &&(m_pcCUAbove==NULL || m_pcCUAbove->getSlice()==NULL || (m_pcPic->getPicSym()->getTileIdxMap( m_pcCUAbove->getAddr() ) != m_pcPic->getPicSym()->getTileIdxMap(getAddr()))))
1688      )
1689  {
1690    return NULL;
1691  }
1692  return m_pcCUAbove;
1693}
1694
1695TComDataCU* TComDataCU::getPUAboveLeft( UInt& uiALPartUnitIdx, UInt uiCurrPartUnitIdx, Bool bEnforceSliceRestriction )
1696{
1697  UInt uiAbsPartIdx       = g_auiZscanToRaster[uiCurrPartUnitIdx];
1698  UInt uiAbsZorderCUIdx   = g_auiZscanToRaster[m_uiAbsIdxInLCU];
1699  UInt uiNumPartInCUWidth = m_pcPic->getNumPartInWidth();
1700 
1701  if ( !RasterAddress::isZeroCol( uiAbsPartIdx, uiNumPartInCUWidth ) )
1702  {
1703    if ( !RasterAddress::isZeroRow( uiAbsPartIdx, uiNumPartInCUWidth ) )
1704    {
1705      uiALPartUnitIdx = g_auiRasterToZscan[ uiAbsPartIdx - uiNumPartInCUWidth - 1 ];
1706      if ( RasterAddress::isEqualRowOrCol( uiAbsPartIdx, uiAbsZorderCUIdx, uiNumPartInCUWidth ) )
1707      {
1708        return m_pcPic->getCU( getAddr() );
1709      }
1710      else
1711      {
1712        uiALPartUnitIdx -= m_uiAbsIdxInLCU;
1713        return this;
1714      }
1715    }
1716    uiALPartUnitIdx = g_auiRasterToZscan[ uiAbsPartIdx + getPic()->getNumPartInCU() - uiNumPartInCUWidth - 1 ];
1717    if ( (bEnforceSliceRestriction && (m_pcCUAbove==NULL || m_pcCUAbove->getSlice()==NULL ||
1718       m_pcCUAbove->getSCUAddr()+uiALPartUnitIdx < m_pcPic->getCU( getAddr() )->getSliceStartCU(uiCurrPartUnitIdx)||
1719       (m_pcPic->getPicSym()->getTileIdxMap( m_pcCUAbove->getAddr() ) != m_pcPic->getPicSym()->getTileIdxMap(getAddr()))
1720       ))
1721     )
1722    {
1723      return NULL;
1724    }
1725    return m_pcCUAbove;
1726  }
1727 
1728  if ( !RasterAddress::isZeroRow( uiAbsPartIdx, uiNumPartInCUWidth ) )
1729  {
1730    uiALPartUnitIdx = g_auiRasterToZscan[ uiAbsPartIdx - 1 ];
1731    if ( (bEnforceSliceRestriction && (m_pcCULeft==NULL || m_pcCULeft->getSlice()==NULL || 
1732       m_pcCULeft->getSCUAddr()+uiALPartUnitIdx < m_pcPic->getCU( getAddr() )->getSliceStartCU(uiCurrPartUnitIdx)||
1733       (m_pcPic->getPicSym()->getTileIdxMap( m_pcCULeft->getAddr() ) != m_pcPic->getPicSym()->getTileIdxMap(getAddr()))
1734       ))
1735     )
1736    {
1737      return NULL;
1738    }
1739    return m_pcCULeft;
1740  }
1741 
1742  uiALPartUnitIdx = g_auiRasterToZscan[ m_pcPic->getNumPartInCU() - 1 ];
1743  if ( (bEnforceSliceRestriction && (m_pcCUAboveLeft==NULL || m_pcCUAboveLeft->getSlice()==NULL ||
1744       m_pcCUAboveLeft->getSCUAddr()+uiALPartUnitIdx < m_pcPic->getCU( getAddr() )->getSliceStartCU(uiCurrPartUnitIdx)||
1745       (m_pcPic->getPicSym()->getTileIdxMap( m_pcCUAboveLeft->getAddr() ) != m_pcPic->getPicSym()->getTileIdxMap(getAddr()))
1746       ))
1747     )
1748  {
1749    return NULL;
1750  }
1751  return m_pcCUAboveLeft;
1752}
1753
1754TComDataCU* TComDataCU::getPUAboveRight( UInt& uiARPartUnitIdx, UInt uiCurrPartUnitIdx, Bool bEnforceSliceRestriction )
1755{
1756  UInt uiAbsPartIdxRT     = g_auiZscanToRaster[uiCurrPartUnitIdx];
1757  UInt uiAbsZorderCUIdx   = g_auiZscanToRaster[ m_uiAbsIdxInLCU ] + m_puhWidth[0] / m_pcPic->getMinCUWidth() - 1;
1758  UInt uiNumPartInCUWidth = m_pcPic->getNumPartInWidth();
1759 
1760  if( ( m_pcPic->getCU(m_uiCUAddr)->getCUPelX() + g_auiRasterToPelX[uiAbsPartIdxRT] + m_pcPic->getMinCUWidth() ) >= m_pcSlice->getSPS()->getPicWidthInLumaSamples() )
1761  {
1762    uiARPartUnitIdx = MAX_UINT;
1763    return NULL;
1764  }
1765 
1766  if ( RasterAddress::lessThanCol( uiAbsPartIdxRT, uiNumPartInCUWidth - 1, uiNumPartInCUWidth ) )
1767  {
1768    if ( !RasterAddress::isZeroRow( uiAbsPartIdxRT, uiNumPartInCUWidth ) )
1769    {
1770      if ( uiCurrPartUnitIdx > g_auiRasterToZscan[ uiAbsPartIdxRT - uiNumPartInCUWidth + 1 ] )
1771      {
1772        uiARPartUnitIdx = g_auiRasterToZscan[ uiAbsPartIdxRT - uiNumPartInCUWidth + 1 ];
1773        if ( RasterAddress::isEqualRowOrCol( uiAbsPartIdxRT, uiAbsZorderCUIdx, uiNumPartInCUWidth ) )
1774        {
1775          return m_pcPic->getCU( getAddr() );
1776        }
1777        else
1778        {
1779          uiARPartUnitIdx -= m_uiAbsIdxInLCU;
1780          return this;
1781        }
1782      }
1783      uiARPartUnitIdx = MAX_UINT;
1784      return NULL;
1785    }
1786    uiARPartUnitIdx = g_auiRasterToZscan[ uiAbsPartIdxRT + m_pcPic->getNumPartInCU() - uiNumPartInCUWidth + 1 ];
1787    if ( (bEnforceSliceRestriction && (m_pcCUAbove==NULL || m_pcCUAbove->getSlice()==NULL ||
1788       m_pcCUAbove->getSCUAddr()+uiARPartUnitIdx < m_pcPic->getCU( getAddr() )->getSliceStartCU(uiCurrPartUnitIdx)||
1789       (m_pcPic->getPicSym()->getTileIdxMap( m_pcCUAbove->getAddr() ) != m_pcPic->getPicSym()->getTileIdxMap(getAddr()))
1790       ))
1791     )
1792    {
1793      return NULL;
1794    }
1795    return m_pcCUAbove;
1796  }
1797 
1798  if ( !RasterAddress::isZeroRow( uiAbsPartIdxRT, uiNumPartInCUWidth ) )
1799  {
1800    uiARPartUnitIdx = MAX_UINT;
1801    return NULL;
1802  }
1803 
1804  uiARPartUnitIdx = g_auiRasterToZscan[ m_pcPic->getNumPartInCU() - uiNumPartInCUWidth ];
1805  if ( (bEnforceSliceRestriction && (m_pcCUAboveRight==NULL || m_pcCUAboveRight->getSlice()==NULL ||
1806       m_pcPic->getPicSym()->getInverseCUOrderMap( m_pcCUAboveRight->getAddr()) > m_pcPic->getPicSym()->getInverseCUOrderMap( getAddr()) ||
1807       m_pcCUAboveRight->getSCUAddr()+uiARPartUnitIdx < m_pcPic->getCU( getAddr() )->getSliceStartCU(uiCurrPartUnitIdx)||
1808       (m_pcPic->getPicSym()->getTileIdxMap( m_pcCUAboveRight->getAddr() ) != m_pcPic->getPicSym()->getTileIdxMap(getAddr()))
1809       ))
1810     )
1811  {
1812    return NULL;
1813  }
1814  return m_pcCUAboveRight;
1815}
1816
1817TComDataCU* TComDataCU::getPUBelowLeft( UInt& uiBLPartUnitIdx, UInt uiCurrPartUnitIdx, Bool bEnforceSliceRestriction )
1818{
1819  UInt uiAbsPartIdxLB     = g_auiZscanToRaster[uiCurrPartUnitIdx];
1820  UInt uiAbsZorderCUIdxLB = g_auiZscanToRaster[ m_uiAbsIdxInLCU ] + (m_puhHeight[0] / m_pcPic->getMinCUHeight() - 1)*m_pcPic->getNumPartInWidth();
1821  UInt uiNumPartInCUWidth = m_pcPic->getNumPartInWidth();
1822 
1823  if( ( m_pcPic->getCU(m_uiCUAddr)->getCUPelY() + g_auiRasterToPelY[uiAbsPartIdxLB] + m_pcPic->getMinCUHeight() ) >= m_pcSlice->getSPS()->getPicHeightInLumaSamples() )
1824  {
1825    uiBLPartUnitIdx = MAX_UINT;
1826    return NULL;
1827  }
1828 
1829  if ( RasterAddress::lessThanRow( uiAbsPartIdxLB, m_pcPic->getNumPartInHeight() - 1, uiNumPartInCUWidth ) )
1830  {
1831    if ( !RasterAddress::isZeroCol( uiAbsPartIdxLB, uiNumPartInCUWidth ) )
1832    {
1833      if ( uiCurrPartUnitIdx > g_auiRasterToZscan[ uiAbsPartIdxLB + uiNumPartInCUWidth - 1 ] )
1834      {
1835        uiBLPartUnitIdx = g_auiRasterToZscan[ uiAbsPartIdxLB + uiNumPartInCUWidth - 1 ];
1836        if ( RasterAddress::isEqualRowOrCol( uiAbsPartIdxLB, uiAbsZorderCUIdxLB, uiNumPartInCUWidth ) )
1837        {
1838          return m_pcPic->getCU( getAddr() );
1839        }
1840        else
1841        {
1842          uiBLPartUnitIdx -= m_uiAbsIdxInLCU;
1843          return this;
1844        }
1845      }
1846      uiBLPartUnitIdx = MAX_UINT;
1847      return NULL;
1848    }
1849    uiBLPartUnitIdx = g_auiRasterToZscan[ uiAbsPartIdxLB + uiNumPartInCUWidth*2 - 1 ];
1850    if ( (bEnforceSliceRestriction && (m_pcCULeft==NULL || m_pcCULeft->getSlice()==NULL || 
1851       m_pcCULeft->getSCUAddr()+uiBLPartUnitIdx < m_pcPic->getCU( getAddr() )->getSliceStartCU(uiCurrPartUnitIdx)||
1852       (m_pcPic->getPicSym()->getTileIdxMap( m_pcCULeft->getAddr() ) != m_pcPic->getPicSym()->getTileIdxMap(getAddr()))
1853       ))
1854     )
1855    {
1856      return NULL;
1857    }
1858    return m_pcCULeft;
1859  }
1860 
1861  uiBLPartUnitIdx = MAX_UINT;
1862  return NULL;
1863}
1864
1865TComDataCU* TComDataCU::getPUBelowLeftAdi(UInt& uiBLPartUnitIdx,  UInt uiCurrPartUnitIdx, UInt uiPartUnitOffset, Bool bEnforceSliceRestriction )
1866{
1867  UInt uiAbsPartIdxLB     = g_auiZscanToRaster[uiCurrPartUnitIdx];
1868  UInt uiAbsZorderCUIdxLB = g_auiZscanToRaster[ m_uiAbsIdxInLCU ] + ((m_puhHeight[0] / m_pcPic->getMinCUHeight()) - 1)*m_pcPic->getNumPartInWidth();
1869  UInt uiNumPartInCUWidth = m_pcPic->getNumPartInWidth();
1870 
1871  if( ( m_pcPic->getCU(m_uiCUAddr)->getCUPelY() + g_auiRasterToPelY[uiAbsPartIdxLB] + (m_pcPic->getPicSym()->getMinCUHeight() * uiPartUnitOffset)) >= m_pcSlice->getSPS()->getPicHeightInLumaSamples())
1872  {
1873    uiBLPartUnitIdx = MAX_UINT;
1874    return NULL;
1875  }
1876 
1877  if ( RasterAddress::lessThanRow( uiAbsPartIdxLB, m_pcPic->getNumPartInHeight() - uiPartUnitOffset, uiNumPartInCUWidth ) )
1878  {
1879    if ( !RasterAddress::isZeroCol( uiAbsPartIdxLB, uiNumPartInCUWidth ) )
1880    {
1881      if ( uiCurrPartUnitIdx > g_auiRasterToZscan[ uiAbsPartIdxLB + uiPartUnitOffset * uiNumPartInCUWidth - 1 ] )
1882      {
1883        uiBLPartUnitIdx = g_auiRasterToZscan[ uiAbsPartIdxLB + uiPartUnitOffset * uiNumPartInCUWidth - 1 ];
1884        if ( RasterAddress::isEqualRowOrCol( uiAbsPartIdxLB, uiAbsZorderCUIdxLB, uiNumPartInCUWidth ) )
1885        {
1886          return m_pcPic->getCU( getAddr() );
1887        }
1888        else
1889        {
1890          uiBLPartUnitIdx -= m_uiAbsIdxInLCU;
1891          return this;
1892        }
1893      }
1894      uiBLPartUnitIdx = MAX_UINT;
1895      return NULL;
1896    }
1897    uiBLPartUnitIdx = g_auiRasterToZscan[ uiAbsPartIdxLB + (1+uiPartUnitOffset) * uiNumPartInCUWidth - 1 ];
1898    if ( (bEnforceSliceRestriction && (m_pcCULeft==NULL || m_pcCULeft->getSlice()==NULL || 
1899       m_pcCULeft->getSCUAddr()+uiBLPartUnitIdx < m_pcPic->getCU( getAddr() )->getSliceStartCU(uiCurrPartUnitIdx)||
1900       (m_pcPic->getPicSym()->getTileIdxMap( m_pcCULeft->getAddr() ) != m_pcPic->getPicSym()->getTileIdxMap(getAddr()))
1901       ))
1902     )
1903    {
1904      return NULL;
1905    }
1906    return m_pcCULeft;
1907  }
1908 
1909  uiBLPartUnitIdx = MAX_UINT;
1910  return NULL;
1911}
1912
1913TComDataCU* TComDataCU::getPUAboveRightAdi(UInt&  uiARPartUnitIdx, UInt uiCurrPartUnitIdx, UInt uiPartUnitOffset, Bool bEnforceSliceRestriction )
1914{
1915  UInt uiAbsPartIdxRT     = g_auiZscanToRaster[uiCurrPartUnitIdx];
1916  UInt uiAbsZorderCUIdx   = g_auiZscanToRaster[ m_uiAbsIdxInLCU ] + (m_puhWidth[0] / m_pcPic->getMinCUWidth()) - 1;
1917  UInt uiNumPartInCUWidth = m_pcPic->getNumPartInWidth();
1918 
1919  if( ( m_pcPic->getCU(m_uiCUAddr)->getCUPelX() + g_auiRasterToPelX[uiAbsPartIdxRT] + (m_pcPic->getPicSym()->getMinCUHeight() * uiPartUnitOffset)) >= m_pcSlice->getSPS()->getPicWidthInLumaSamples() )
1920  {
1921    uiARPartUnitIdx = MAX_UINT;
1922    return NULL;
1923  }
1924 
1925  if ( RasterAddress::lessThanCol( uiAbsPartIdxRT, uiNumPartInCUWidth - uiPartUnitOffset, uiNumPartInCUWidth ) )
1926  {
1927    if ( !RasterAddress::isZeroRow( uiAbsPartIdxRT, uiNumPartInCUWidth ) )
1928    {
1929      if ( uiCurrPartUnitIdx > g_auiRasterToZscan[ uiAbsPartIdxRT - uiNumPartInCUWidth + uiPartUnitOffset ] )
1930      {
1931        uiARPartUnitIdx = g_auiRasterToZscan[ uiAbsPartIdxRT - uiNumPartInCUWidth + uiPartUnitOffset ];
1932        if ( RasterAddress::isEqualRowOrCol( uiAbsPartIdxRT, uiAbsZorderCUIdx, uiNumPartInCUWidth ) )
1933        {
1934          return m_pcPic->getCU( getAddr() );
1935        }
1936        else
1937        {
1938          uiARPartUnitIdx -= m_uiAbsIdxInLCU;
1939          return this;
1940        }
1941      }
1942      uiARPartUnitIdx = MAX_UINT;
1943      return NULL;
1944    }
1945    uiARPartUnitIdx = g_auiRasterToZscan[ uiAbsPartIdxRT + m_pcPic->getNumPartInCU() - uiNumPartInCUWidth + uiPartUnitOffset ];
1946    if ( (bEnforceSliceRestriction && (m_pcCUAbove==NULL || m_pcCUAbove->getSlice()==NULL || 
1947       m_pcCUAbove->getSCUAddr()+uiARPartUnitIdx < m_pcPic->getCU( getAddr() )->getSliceStartCU(uiCurrPartUnitIdx)||
1948       (m_pcPic->getPicSym()->getTileIdxMap( m_pcCUAbove->getAddr() ) != m_pcPic->getPicSym()->getTileIdxMap(getAddr()))
1949       ))
1950     )
1951    {
1952      return NULL;
1953    }
1954    return m_pcCUAbove;
1955  }
1956 
1957  if ( !RasterAddress::isZeroRow( uiAbsPartIdxRT, uiNumPartInCUWidth ) )
1958  {
1959    uiARPartUnitIdx = MAX_UINT;
1960    return NULL;
1961  }
1962 
1963  uiARPartUnitIdx = g_auiRasterToZscan[ m_pcPic->getNumPartInCU() - uiNumPartInCUWidth + uiPartUnitOffset-1 ];
1964  if ( (bEnforceSliceRestriction && (m_pcCUAboveRight==NULL || m_pcCUAboveRight->getSlice()==NULL ||
1965       m_pcPic->getPicSym()->getInverseCUOrderMap( m_pcCUAboveRight->getAddr()) > m_pcPic->getPicSym()->getInverseCUOrderMap( getAddr()) ||
1966       m_pcCUAboveRight->getSCUAddr()+uiARPartUnitIdx < m_pcPic->getCU( getAddr() )->getSliceStartCU(uiCurrPartUnitIdx)||
1967       (m_pcPic->getPicSym()->getTileIdxMap( m_pcCUAboveRight->getAddr() ) != m_pcPic->getPicSym()->getTileIdxMap(getAddr()))
1968       ))
1969     )
1970  {
1971    return NULL;
1972  }
1973  return m_pcCUAboveRight;
1974}
1975
1976/** Get left QpMinCu
1977*\param   uiLPartUnitIdx
1978*\param   uiCurrAbsIdxInLCU
1979*\returns TComDataCU*   point of TComDataCU of left QpMinCu
1980*/
1981TComDataCU* TComDataCU::getQpMinCuLeft( UInt& uiLPartUnitIdx, UInt uiCurrAbsIdxInLCU)
1982{
1983  UInt numPartInCUWidth = m_pcPic->getNumPartInWidth();
1984  UInt absZorderQpMinCUIdx = (uiCurrAbsIdxInLCU>>((g_uiMaxCUDepth - getSlice()->getPPS()->getMaxCuDQPDepth())<<1))<<((g_uiMaxCUDepth -getSlice()->getPPS()->getMaxCuDQPDepth())<<1);
1985  UInt absRorderQpMinCUIdx = g_auiZscanToRaster[absZorderQpMinCUIdx];
1986
1987  // check for left LCU boundary
1988  if ( RasterAddress::isZeroCol(absRorderQpMinCUIdx, numPartInCUWidth) )
1989  {
1990    return NULL;
1991  }
1992
1993  // get index of left-CU relative to top-left corner of current quantization group
1994  uiLPartUnitIdx = g_auiRasterToZscan[absRorderQpMinCUIdx - 1];
1995
1996  // return pointer to current LCU
1997  return m_pcPic->getCU( getAddr() );
1998}
1999
2000/** Get Above QpMinCu
2001*\param   aPartUnitIdx
2002*\param   currAbsIdxInLCU
2003*\returns TComDataCU*   point of TComDataCU of above QpMinCu
2004*/
2005TComDataCU* TComDataCU::getQpMinCuAbove( UInt& aPartUnitIdx, UInt currAbsIdxInLCU )
2006{
2007  UInt numPartInCUWidth = m_pcPic->getNumPartInWidth();
2008  UInt absZorderQpMinCUIdx = (currAbsIdxInLCU>>((g_uiMaxCUDepth - getSlice()->getPPS()->getMaxCuDQPDepth())<<1))<<((g_uiMaxCUDepth - getSlice()->getPPS()->getMaxCuDQPDepth())<<1);
2009  UInt absRorderQpMinCUIdx = g_auiZscanToRaster[absZorderQpMinCUIdx];
2010
2011  // check for top LCU boundary
2012  if ( RasterAddress::isZeroRow( absRorderQpMinCUIdx, numPartInCUWidth) )
2013  {
2014    return NULL;
2015  }
2016
2017  // get index of top-CU relative to top-left corner of current quantization group
2018  aPartUnitIdx = g_auiRasterToZscan[absRorderQpMinCUIdx - numPartInCUWidth];
2019
2020  // return pointer to current LCU
2021  return m_pcPic->getCU( getAddr() );
2022}
2023
2024/** Get reference QP from left QpMinCu or latest coded QP
2025*\param   uiCurrAbsIdxInLCU
2026*\returns Char   reference QP value
2027*/
2028Char TComDataCU::getRefQP( UInt uiCurrAbsIdxInLCU )
2029{
2030  UInt        lPartIdx = 0, aPartIdx = 0;
2031  TComDataCU* cULeft  = getQpMinCuLeft ( lPartIdx, m_uiAbsIdxInLCU + uiCurrAbsIdxInLCU );
2032  TComDataCU* cUAbove = getQpMinCuAbove( aPartIdx, m_uiAbsIdxInLCU + uiCurrAbsIdxInLCU );
2033  return (((cULeft? cULeft->getQP( lPartIdx ): getLastCodedQP( uiCurrAbsIdxInLCU )) + (cUAbove? cUAbove->getQP( aPartIdx ): getLastCodedQP( uiCurrAbsIdxInLCU )) + 1) >> 1);
2034}
2035
2036Int TComDataCU::getLastValidPartIdx( Int iAbsPartIdx )
2037{
2038  Int iLastValidPartIdx = iAbsPartIdx-1;
2039  while ( iLastValidPartIdx >= 0
2040       && getPredictionMode( iLastValidPartIdx ) == MODE_NONE )
2041  {
2042    UInt uiDepth = getDepth( iLastValidPartIdx );
2043    iLastValidPartIdx -= m_uiNumPartition>>(uiDepth<<1);
2044  }
2045  return iLastValidPartIdx;
2046}
2047
2048Char TComDataCU::getLastCodedQP( UInt uiAbsPartIdx )
2049{
2050  UInt uiQUPartIdxMask = ~((1<<((g_uiMaxCUDepth - getSlice()->getPPS()->getMaxCuDQPDepth())<<1))-1);
2051  Int iLastValidPartIdx = getLastValidPartIdx( uiAbsPartIdx&uiQUPartIdxMask );
2052  if ( uiAbsPartIdx < m_uiNumPartition
2053    && (getSCUAddr()+iLastValidPartIdx < getSliceStartCU(m_uiAbsIdxInLCU+uiAbsPartIdx)))
2054  {
2055    return getSlice()->getSliceQp();
2056  }
2057  else if ( iLastValidPartIdx >= 0 )
2058  {
2059    return getQP( iLastValidPartIdx );
2060  }
2061  else
2062  {
2063    if ( getZorderIdxInCU() > 0 )
2064    {
2065      return getPic()->getCU( getAddr() )->getLastCodedQP( getZorderIdxInCU() );
2066    }
2067    else if ( getPic()->getPicSym()->getInverseCUOrderMap(getAddr()) > 0
2068      && getPic()->getPicSym()->getTileIdxMap(getAddr()) == getPic()->getPicSym()->getTileIdxMap(getPic()->getPicSym()->getCUOrderMap(getPic()->getPicSym()->getInverseCUOrderMap(getAddr())-1))
2069      && !( getSlice()->getPPS()->getEntropyCodingSyncEnabledFlag() && getAddr() % getPic()->getFrameWidthInCU() == 0 ) )
2070    {
2071      return getPic()->getCU( getPic()->getPicSym()->getCUOrderMap(getPic()->getPicSym()->getInverseCUOrderMap(getAddr())-1) )->getLastCodedQP( getPic()->getNumPartInCU() );
2072    }
2073    else
2074    {
2075      return getSlice()->getSliceQp();
2076    }
2077  }
2078}
2079/** Check whether the CU is coded in lossless coding mode
2080 * \param   uiAbsPartIdx
2081 * \returns true if the CU is coded in lossless coding mode; false if otherwise
2082 */
2083Bool TComDataCU::isLosslessCoded(UInt absPartIdx)
2084{
2085  return (getSlice()->getPPS()->getTransquantBypassEnableFlag() && getCUTransquantBypass (absPartIdx));
2086}
2087
2088/** Get allowed chroma intra modes
2089*\param   uiAbsPartIdx
2090*\param   uiModeList  pointer to chroma intra modes array
2091*\returns
2092*- fill uiModeList with chroma intra modes
2093*/
2094Void TComDataCU::getAllowedChromaDir( UInt uiAbsPartIdx, UInt* uiModeList )
2095{
2096  uiModeList[0] = PLANAR_IDX;
2097  uiModeList[1] = VER_IDX;
2098  uiModeList[2] = HOR_IDX;
2099  uiModeList[3] = DC_IDX;
2100  uiModeList[4] = DM_CHROMA_IDX;
2101
2102  UInt uiLumaMode = getLumaIntraDir( uiAbsPartIdx );
2103
2104  for( Int i = 0; i < NUM_CHROMA_MODE - 1; i++ )
2105  {
2106    if( uiLumaMode == uiModeList[i] )
2107    {
2108      uiModeList[i] = 34; // VER+8 mode
2109      break;
2110    }
2111  }
2112}
2113
2114/** Get most probable intra modes
2115*\param   uiAbsPartIdx
2116*\param   uiIntraDirPred  pointer to the array for MPM storage
2117*\param   piMode          it is set with MPM mode in case both MPM are equal. It is used to restrict RD search at encode side.
2118*\returns Number of MPM
2119*/
2120Int TComDataCU::getIntraDirLumaPredictor( UInt uiAbsPartIdx, Int* uiIntraDirPred, Int* piMode  )
2121{
2122  TComDataCU* pcTempCU;
2123  UInt        uiTempPartIdx;
2124  Int         iLeftIntraDir, iAboveIntraDir;
2125  Int         uiPredNum = 0;
2126 
2127  // Get intra direction of left PU
2128  pcTempCU = getPULeft( uiTempPartIdx, m_uiAbsIdxInLCU + uiAbsPartIdx );
2129 
2130  iLeftIntraDir  = pcTempCU ? ( pcTempCU->isIntra( uiTempPartIdx ) ? pcTempCU->getLumaIntraDir( uiTempPartIdx ) : DC_IDX ) : DC_IDX;
2131#if H_3D_DIM
2132  mapDepthModeToIntraDir( iLeftIntraDir );
2133#endif
2134 
2135  // Get intra direction of above PU
2136  pcTempCU = getPUAbove( uiTempPartIdx, m_uiAbsIdxInLCU + uiAbsPartIdx, true, true );
2137 
2138  iAboveIntraDir = pcTempCU ? ( pcTempCU->isIntra( uiTempPartIdx ) ? pcTempCU->getLumaIntraDir( uiTempPartIdx ) : DC_IDX ) : DC_IDX;
2139#if H_3D_DIM
2140  mapDepthModeToIntraDir( iAboveIntraDir );
2141#endif
2142 
2143  uiPredNum = 3;
2144  if(iLeftIntraDir == iAboveIntraDir)
2145  {
2146    if( piMode )
2147    {
2148      *piMode = 1;
2149    }
2150   
2151    if (iLeftIntraDir > 1) // angular modes
2152    {
2153      uiIntraDirPred[0] = iLeftIntraDir;
2154      uiIntraDirPred[1] = ((iLeftIntraDir + 29) % 32) + 2;
2155      uiIntraDirPred[2] = ((iLeftIntraDir - 1 ) % 32) + 2;
2156    }
2157    else //non-angular
2158    {
2159      uiIntraDirPred[0] = PLANAR_IDX;
2160      uiIntraDirPred[1] = DC_IDX;
2161      uiIntraDirPred[2] = VER_IDX; 
2162    }
2163  }
2164  else
2165  {
2166    if( piMode )
2167    {
2168      *piMode = 2;
2169    }
2170    uiIntraDirPred[0] = iLeftIntraDir;
2171    uiIntraDirPred[1] = iAboveIntraDir;
2172   
2173    if (iLeftIntraDir && iAboveIntraDir ) //both modes are non-planar
2174    {
2175      uiIntraDirPred[2] = PLANAR_IDX;
2176    }
2177    else
2178    {
2179      uiIntraDirPred[2] =  (iLeftIntraDir+iAboveIntraDir)<2? VER_IDX : DC_IDX;
2180    }
2181  }
2182 
2183  return uiPredNum;
2184}
2185
2186UInt TComDataCU::getCtxSplitFlag( UInt uiAbsPartIdx, UInt uiDepth )
2187{
2188  TComDataCU* pcTempCU;
2189  UInt        uiTempPartIdx;
2190  UInt        uiCtx;
2191  // Get left split flag
2192  pcTempCU = getPULeft( uiTempPartIdx, m_uiAbsIdxInLCU + uiAbsPartIdx );
2193  uiCtx  = ( pcTempCU ) ? ( ( pcTempCU->getDepth( uiTempPartIdx ) > uiDepth ) ? 1 : 0 ) : 0;
2194 
2195  // Get above split flag
2196  pcTempCU = getPUAbove( uiTempPartIdx, m_uiAbsIdxInLCU + uiAbsPartIdx );
2197  uiCtx += ( pcTempCU ) ? ( ( pcTempCU->getDepth( uiTempPartIdx ) > uiDepth ) ? 1 : 0 ) : 0;
2198 
2199  return uiCtx;
2200}
2201
2202UInt TComDataCU::getCtxQtCbf( TextType eType, UInt uiTrDepth )
2203{
2204  if( eType )
2205  {
2206    return uiTrDepth;
2207  }
2208  else
2209  {
2210    const UInt uiCtx = ( uiTrDepth == 0 ? 1 : 0 );
2211    return uiCtx;
2212  }
2213}
2214
2215UInt TComDataCU::getQuadtreeTULog2MinSizeInCU( UInt absPartIdx )
2216{
2217  UInt log2CbSize = g_aucConvertToBit[getWidth( absPartIdx )] + 2;
2218  PartSize  partSize  = getPartitionSize( absPartIdx );
2219  UInt quadtreeTUMaxDepth = getPredictionMode( absPartIdx ) == MODE_INTRA ? m_pcSlice->getSPS()->getQuadtreeTUMaxDepthIntra() : m_pcSlice->getSPS()->getQuadtreeTUMaxDepthInter(); 
2220  Int intraSplitFlag = ( getPredictionMode( absPartIdx ) == MODE_INTRA && partSize == SIZE_NxN ) ? 1 : 0;
2221  Int interSplitFlag = ((quadtreeTUMaxDepth == 1) && (getPredictionMode( absPartIdx ) == MODE_INTER) && (partSize != SIZE_2Nx2N) );
2222 
2223  UInt log2MinTUSizeInCU = 0;
2224  if (log2CbSize < (m_pcSlice->getSPS()->getQuadtreeTULog2MinSize() + quadtreeTUMaxDepth - 1 + interSplitFlag + intraSplitFlag) ) 
2225  {
2226    // when fully making use of signaled TUMaxDepth + inter/intraSplitFlag, resulting luma TB size is < QuadtreeTULog2MinSize
2227    log2MinTUSizeInCU = m_pcSlice->getSPS()->getQuadtreeTULog2MinSize();
2228  }
2229  else
2230  {
2231    // when fully making use of signaled TUMaxDepth + inter/intraSplitFlag, resulting luma TB size is still >= QuadtreeTULog2MinSize
2232    log2MinTUSizeInCU = log2CbSize - ( quadtreeTUMaxDepth - 1 + interSplitFlag + intraSplitFlag); // stop when trafoDepth == hierarchy_depth = splitFlag
2233    if ( log2MinTUSizeInCU > m_pcSlice->getSPS()->getQuadtreeTULog2MaxSize())
2234    {
2235      // when fully making use of signaled TUMaxDepth + inter/intraSplitFlag, resulting luma TB size is still > QuadtreeTULog2MaxSize
2236      log2MinTUSizeInCU = m_pcSlice->getSPS()->getQuadtreeTULog2MaxSize();
2237    } 
2238  }
2239  return log2MinTUSizeInCU;
2240}
2241
2242UInt TComDataCU::getCtxSkipFlag( UInt uiAbsPartIdx )
2243{
2244  TComDataCU* pcTempCU;
2245  UInt        uiTempPartIdx;
2246  UInt        uiCtx = 0;
2247 
2248  // Get BCBP of left PU
2249  pcTempCU = getPULeft( uiTempPartIdx, m_uiAbsIdxInLCU + uiAbsPartIdx );
2250  uiCtx    = ( pcTempCU ) ? pcTempCU->isSkipped( uiTempPartIdx ) : 0;
2251 
2252  // Get BCBP of above PU
2253  pcTempCU = getPUAbove( uiTempPartIdx, m_uiAbsIdxInLCU + uiAbsPartIdx );
2254  uiCtx   += ( pcTempCU ) ? pcTempCU->isSkipped( uiTempPartIdx ) : 0;
2255 
2256  return uiCtx;
2257}
2258
2259#if H_3D_ARP
2260UInt TComDataCU::getCTXARPWFlag( UInt uiAbsPartIdx )
2261{
2262  TComDataCU* pcTempCU;
2263  UInt        uiTempPartIdx;
2264  UInt        uiCtx = 0;
2265 
2266  pcTempCU = getPULeft( uiTempPartIdx, m_uiAbsIdxInLCU + uiAbsPartIdx );
2267  uiCtx    = ( pcTempCU ) ? ((pcTempCU->getARPW( uiTempPartIdx )==0)?0:1) : 0;
2268 
2269  pcTempCU = getPUAbove( uiTempPartIdx, m_uiAbsIdxInLCU + uiAbsPartIdx );
2270  uiCtx   += ( pcTempCU ) ? ((pcTempCU->getARPW( uiTempPartIdx )==0)?0:1): 0;
2271 
2272  return uiCtx;
2273}
2274#endif
2275#if !MTK_IC_FLAG_CABAC_SIMP_G0061
2276#if H_3D_IC
2277UInt TComDataCU::getCtxICFlag( UInt uiAbsPartIdx )
2278{
2279  UInt        uiCtx = 0;
2280
2281  TComDataCU* pcTempCU = NULL;
2282  UInt        uiTempPartIdx = 0;
2283
2284  pcTempCU = getPULeft( uiTempPartIdx, m_uiAbsIdxInLCU + uiAbsPartIdx );
2285  uiCtx    = ( pcTempCU ) ? pcTempCU->isIC( uiTempPartIdx ) : 0;
2286
2287  pcTempCU = getPUAbove( uiTempPartIdx, m_uiAbsIdxInLCU + uiAbsPartIdx );
2288  uiCtx    += ( pcTempCU ) ? pcTempCU->isIC( uiTempPartIdx ) : 0;
2289
2290  return uiCtx;
2291}
2292#endif
2293#endif
2294#if H_3D_INTER_SDC
2295Void TComDataCU::setInterSDCFlagSubParts ( Bool bInterSDCFlag, UInt uiAbsPartIdx, UInt uiPartIdx, UInt uiDepth )
2296{
2297  setSubPart( bInterSDCFlag, m_pbInterSDCFlag, uiAbsPartIdx, uiDepth, uiPartIdx );
2298}
2299
2300UInt TComDataCU::getCtxInterSDCFlag( UInt uiAbsPartIdx )
2301{
2302  return 0;
2303}
2304
2305Void TComDataCU::xSetInterSDCCUMask( TComDataCU *pcCU, UChar *pMask )
2306{
2307  UInt  uiWidth      = pcCU->getWidth ( 0 );
2308  UInt  uiHeight     = pcCU->getHeight( 0 );
2309  UInt  uiPartitionSize = pcCU->getPartitionSize( 0 );
2310  UInt  uiXOffset = 0, uiYOffset = 0;
2311
2312  switch( uiPartitionSize )
2313  {
2314  case SIZE_2NxN:
2315    uiXOffset = uiWidth;      uiYOffset = uiHeight >> 1;   break;
2316  case SIZE_2NxnU:
2317    uiXOffset = uiWidth;      uiYOffset = uiHeight >> 2;   break;
2318  case SIZE_2NxnD: 
2319    uiXOffset = uiWidth;      uiYOffset = ( uiHeight >> 1 ) + ( uiHeight >> 2 );   break;
2320  case SIZE_Nx2N:
2321    uiXOffset = uiWidth >> 1; uiYOffset = uiHeight; break;
2322  case SIZE_nLx2N:
2323    uiXOffset = uiWidth >> 2; uiYOffset = uiHeight; break;
2324  case SIZE_nRx2N:
2325    uiXOffset = ( uiWidth >> 1 ) + ( uiWidth >> 2 ); uiYOffset = uiHeight; break;
2326  case SIZE_NxN:
2327    uiXOffset = uiWidth >> 1; uiYOffset = uiHeight >> 1;  break;
2328  default:
2329    assert( uiPartitionSize == SIZE_2Nx2N );
2330    uiXOffset = uiWidth;     uiYOffset = uiHeight;    break;
2331  }
2332
2333  UInt uiPelX, uiPelY;
2334
2335  memset( pMask, 0, uiWidth*uiHeight );
2336
2337  //mask
2338  if( uiPartitionSize == SIZE_2NxN || uiPartitionSize == SIZE_2NxnD || uiPartitionSize == SIZE_2NxnU )
2339  {
2340    for( uiPelY = 0; uiPelY < uiYOffset; uiPelY++ )
2341    {
2342      for( uiPelX = 0; uiPelX < uiWidth; uiPelX++ )
2343      {
2344        pMask[uiPelX + uiPelY*uiWidth] = 0;
2345      }
2346    }
2347
2348    for( ; uiPelY < uiHeight; uiPelY++ )
2349    {
2350      for( uiPelX = 0; uiPelX < uiWidth; uiPelX++ )
2351      {
2352        pMask[uiPelX + uiPelY*uiWidth] = 1;
2353      }
2354    }
2355  }
2356  else if( uiPartitionSize == SIZE_Nx2N || uiPartitionSize == SIZE_nLx2N || uiPartitionSize == SIZE_nRx2N )
2357  {
2358    for( uiPelY = 0; uiPelY < uiHeight; uiPelY++ )
2359    {
2360      for( uiPelX = 0; uiPelX < uiXOffset; uiPelX++ )
2361      {
2362        pMask[uiPelX + uiPelY*uiWidth] = 0;
2363      }
2364
2365      for( ; uiPelX < uiWidth; uiPelX++ )
2366      {
2367        pMask[uiPelX + uiPelY*uiWidth] = 1;
2368      }
2369    }
2370  }
2371  else if( uiPartitionSize == SIZE_NxN )
2372  {
2373    for( uiPelY = 0; uiPelY < uiYOffset; uiPelY++ )
2374    {
2375      for( uiPelX = 0; uiPelX < uiXOffset; uiPelX++ )
2376      {
2377        pMask[uiPelX + uiPelY*uiWidth] = 0;
2378      }
2379
2380      for( ; uiPelX < uiWidth; uiPelX++ )
2381      {
2382        pMask[uiPelX + uiPelY*uiWidth] = 1;
2383      }
2384    }
2385
2386    for( ; uiPelY < uiHeight; uiPelY++ )
2387    {
2388      for( uiPelX = 0; uiPelX < uiXOffset; uiPelX++ )
2389      {
2390        pMask[uiPelX + uiPelY*uiWidth] = 2;
2391      }
2392
2393      for( ; uiPelX < uiWidth; uiPelX++ )
2394      {
2395        pMask[uiPelX + uiPelY*uiWidth] = 3;
2396      }
2397    }
2398  }
2399
2400}
2401#endif
2402
2403UInt TComDataCU::getCtxInterDir( UInt uiAbsPartIdx )
2404{
2405  return getDepth( uiAbsPartIdx );
2406}
2407
2408Void TComDataCU::setCbfSubParts( UInt uiCbfY, UInt uiCbfU, UInt uiCbfV, UInt uiAbsPartIdx, UInt uiDepth )
2409{
2410  UInt uiCurrPartNumb = m_pcPic->getNumPartInCU() >> (uiDepth << 1);
2411  memset( m_puhCbf[0] + uiAbsPartIdx, uiCbfY, sizeof( UChar ) * uiCurrPartNumb );
2412  memset( m_puhCbf[1] + uiAbsPartIdx, uiCbfU, sizeof( UChar ) * uiCurrPartNumb );
2413  memset( m_puhCbf[2] + uiAbsPartIdx, uiCbfV, sizeof( UChar ) * uiCurrPartNumb );
2414}
2415
2416Void TComDataCU::setCbfSubParts( UInt uiCbf, TextType eTType, UInt uiAbsPartIdx, UInt uiDepth )
2417{
2418  UInt uiCurrPartNumb = m_pcPic->getNumPartInCU() >> (uiDepth << 1);
2419  memset( m_puhCbf[g_aucConvertTxtTypeToIdx[eTType]] + uiAbsPartIdx, uiCbf, sizeof( UChar ) * uiCurrPartNumb );
2420}
2421
2422/** Sets a coded block flag for all sub-partitions of a partition
2423 * \param uiCbf The value of the coded block flag to be set
2424 * \param eTType
2425 * \param uiAbsPartIdx
2426 * \param uiPartIdx
2427 * \param uiDepth
2428 * \returns Void
2429 */
2430Void TComDataCU::setCbfSubParts ( UInt uiCbf, TextType eTType, UInt uiAbsPartIdx, UInt uiPartIdx, UInt uiDepth )
2431{
2432  setSubPart<UChar>( uiCbf, m_puhCbf[g_aucConvertTxtTypeToIdx[eTType]], uiAbsPartIdx, uiDepth, uiPartIdx );
2433}
2434
2435Void TComDataCU::setDepthSubParts( UInt uiDepth, UInt uiAbsPartIdx )
2436{
2437  UInt uiCurrPartNumb = m_pcPic->getNumPartInCU() >> (uiDepth << 1);
2438  memset( m_puhDepth + uiAbsPartIdx, uiDepth, sizeof(UChar)*uiCurrPartNumb );
2439}
2440
2441Bool TComDataCU::isFirstAbsZorderIdxInDepth (UInt uiAbsPartIdx, UInt uiDepth)
2442{
2443  UInt uiPartNumb = m_pcPic->getNumPartInCU() >> (uiDepth << 1);
2444  return (((m_uiAbsIdxInLCU + uiAbsPartIdx)% uiPartNumb) == 0);
2445}
2446
2447Void TComDataCU::setPartSizeSubParts( PartSize eMode, UInt uiAbsPartIdx, UInt uiDepth )
2448{
2449  assert( sizeof( *m_pePartSize) == 1 );
2450  memset( m_pePartSize + uiAbsPartIdx, eMode, m_pcPic->getNumPartInCU() >> ( 2 * uiDepth ) );
2451}
2452
2453Void TComDataCU::setCUTransquantBypassSubParts( Bool flag, UInt uiAbsPartIdx, UInt uiDepth )
2454{
2455  memset( m_CUTransquantBypass + uiAbsPartIdx, flag, m_pcPic->getNumPartInCU() >> ( 2 * uiDepth ) );
2456}
2457
2458Void TComDataCU::setSkipFlagSubParts( Bool skip, UInt absPartIdx, UInt depth )
2459{
2460  assert( sizeof( *m_skipFlag) == 1 );
2461  memset( m_skipFlag + absPartIdx, skip, m_pcPic->getNumPartInCU() >> ( 2 * depth ) );
2462}
2463
2464Void TComDataCU::setPredModeSubParts( PredMode eMode, UInt uiAbsPartIdx, UInt uiDepth )
2465{
2466  assert( sizeof( *m_pePredMode) == 1 );
2467  memset( m_pePredMode + uiAbsPartIdx, eMode, m_pcPic->getNumPartInCU() >> ( 2 * uiDepth ) );
2468}
2469
2470Void TComDataCU::setQPSubCUs( Int qp, TComDataCU* pcCU, UInt absPartIdx, UInt depth, Bool &foundNonZeroCbf )
2471{
2472  UInt currPartNumb = m_pcPic->getNumPartInCU() >> (depth << 1);
2473  UInt currPartNumQ = currPartNumb >> 2;
2474
2475  if(!foundNonZeroCbf)
2476  {
2477    if(pcCU->getDepth(absPartIdx) > depth)
2478    {
2479      for ( UInt partUnitIdx = 0; partUnitIdx < 4; partUnitIdx++ )
2480      {
2481        pcCU->setQPSubCUs( qp, pcCU, absPartIdx+partUnitIdx*currPartNumQ, depth+1, foundNonZeroCbf );
2482      }
2483    }
2484    else
2485    {
2486      if(pcCU->getCbf( absPartIdx, TEXT_LUMA ) || pcCU->getCbf( absPartIdx, TEXT_CHROMA_U ) || pcCU->getCbf( absPartIdx, TEXT_CHROMA_V ) )
2487      {
2488        foundNonZeroCbf = true;
2489      }
2490      else
2491      {
2492        setQPSubParts(qp, absPartIdx, depth);
2493      }
2494    }
2495  }
2496}
2497
2498Void TComDataCU::setQPSubParts( Int qp, UInt uiAbsPartIdx, UInt uiDepth )
2499{
2500  UInt uiCurrPartNumb = m_pcPic->getNumPartInCU() >> (uiDepth << 1);
2501  TComSlice * pcSlice = getPic()->getSlice(getPic()->getCurrSliceIdx());
2502
2503  for(UInt uiSCUIdx = uiAbsPartIdx; uiSCUIdx < uiAbsPartIdx+uiCurrPartNumb; uiSCUIdx++)
2504  {
2505    if( m_pcPic->getCU( getAddr() )->getSliceSegmentStartCU(uiSCUIdx+getZorderIdxInCU()) == pcSlice->getSliceSegmentCurStartCUAddr() )
2506    {
2507      m_phQP[uiSCUIdx] = qp;
2508    }
2509  }
2510}
2511
2512Void TComDataCU::setLumaIntraDirSubParts( UInt uiDir, UInt uiAbsPartIdx, UInt uiDepth )
2513{
2514  UInt uiCurrPartNumb = m_pcPic->getNumPartInCU() >> (uiDepth << 1);
2515 
2516  memset( m_puhLumaIntraDir + uiAbsPartIdx, uiDir, sizeof(UChar)*uiCurrPartNumb );
2517}
2518
2519template<typename T>
2520Void TComDataCU::setSubPart( T uiParameter, T* puhBaseLCU, UInt uiCUAddr, UInt uiCUDepth, UInt uiPUIdx )
2521{
2522  assert( sizeof(T) == 1 ); // Using memset() works only for types of size 1
2523 
2524  UInt uiCurrPartNumQ = (m_pcPic->getNumPartInCU() >> (2 * uiCUDepth)) >> 2;
2525  switch ( m_pePartSize[ uiCUAddr ] )
2526  {
2527    case SIZE_2Nx2N:
2528      memset( puhBaseLCU + uiCUAddr, uiParameter, 4 * uiCurrPartNumQ );
2529      break;
2530    case SIZE_2NxN:
2531      memset( puhBaseLCU + uiCUAddr, uiParameter, 2 * uiCurrPartNumQ );
2532      break;
2533    case SIZE_Nx2N:
2534      memset( puhBaseLCU + uiCUAddr, uiParameter, uiCurrPartNumQ );
2535      memset( puhBaseLCU + uiCUAddr + 2 * uiCurrPartNumQ, uiParameter, uiCurrPartNumQ );
2536      break;
2537    case SIZE_NxN:
2538      memset( puhBaseLCU + uiCUAddr, uiParameter, uiCurrPartNumQ ); 
2539      break;
2540    case SIZE_2NxnU:
2541      if ( uiPUIdx == 0 )
2542      {
2543        memset( puhBaseLCU + uiCUAddr, uiParameter, (uiCurrPartNumQ >> 1) );                     
2544        memset( puhBaseLCU + uiCUAddr + uiCurrPartNumQ, uiParameter, (uiCurrPartNumQ >> 1) );                     
2545      }
2546      else if ( uiPUIdx == 1 )
2547      {
2548        memset( puhBaseLCU + uiCUAddr, uiParameter, (uiCurrPartNumQ >> 1) );                     
2549        memset( puhBaseLCU + uiCUAddr + uiCurrPartNumQ, uiParameter, ((uiCurrPartNumQ >> 1) + (uiCurrPartNumQ << 1)) );                     
2550      }
2551      else
2552      {
2553        assert(0);
2554      }
2555      break;
2556    case SIZE_2NxnD:
2557      if ( uiPUIdx == 0 )
2558      {
2559        memset( puhBaseLCU + uiCUAddr, uiParameter, ((uiCurrPartNumQ << 1) + (uiCurrPartNumQ >> 1)) );                     
2560        memset( puhBaseLCU + uiCUAddr + (uiCurrPartNumQ << 1) + uiCurrPartNumQ, uiParameter, (uiCurrPartNumQ >> 1) );                     
2561      }
2562      else if ( uiPUIdx == 1 )
2563      {
2564        memset( puhBaseLCU + uiCUAddr, uiParameter, (uiCurrPartNumQ >> 1) );                     
2565        memset( puhBaseLCU + uiCUAddr + uiCurrPartNumQ, uiParameter, (uiCurrPartNumQ >> 1) );                     
2566      }
2567      else
2568      {
2569        assert(0);
2570      }
2571      break;
2572    case SIZE_nLx2N:
2573      if ( uiPUIdx == 0 )
2574      {
2575        memset( puhBaseLCU + uiCUAddr, uiParameter, (uiCurrPartNumQ >> 2) );
2576        memset( puhBaseLCU + uiCUAddr + (uiCurrPartNumQ >> 1), uiParameter, (uiCurrPartNumQ >> 2) ); 
2577        memset( puhBaseLCU + uiCUAddr + (uiCurrPartNumQ << 1), uiParameter, (uiCurrPartNumQ >> 2) ); 
2578        memset( puhBaseLCU + uiCUAddr + (uiCurrPartNumQ << 1) + (uiCurrPartNumQ >> 1), uiParameter, (uiCurrPartNumQ >> 2) ); 
2579      }
2580      else if ( uiPUIdx == 1 )
2581      {
2582        memset( puhBaseLCU + uiCUAddr, uiParameter, (uiCurrPartNumQ >> 2) );
2583        memset( puhBaseLCU + uiCUAddr + (uiCurrPartNumQ >> 1), uiParameter, (uiCurrPartNumQ + (uiCurrPartNumQ >> 2)) ); 
2584        memset( puhBaseLCU + uiCUAddr + (uiCurrPartNumQ << 1), uiParameter, (uiCurrPartNumQ >> 2) ); 
2585        memset( puhBaseLCU + uiCUAddr + (uiCurrPartNumQ << 1) + (uiCurrPartNumQ >> 1), uiParameter, (uiCurrPartNumQ + (uiCurrPartNumQ >> 2)) ); 
2586      }
2587      else
2588      {
2589        assert(0);
2590      }
2591      break;
2592    case SIZE_nRx2N:
2593      if ( uiPUIdx == 0 )
2594      {     
2595        memset( puhBaseLCU + uiCUAddr, uiParameter, (uiCurrPartNumQ + (uiCurrPartNumQ >> 2)) );                           
2596        memset( puhBaseLCU + uiCUAddr + uiCurrPartNumQ + (uiCurrPartNumQ >> 1), uiParameter, (uiCurrPartNumQ >> 2) );                           
2597        memset( puhBaseLCU + uiCUAddr + (uiCurrPartNumQ << 1), uiParameter, (uiCurrPartNumQ + (uiCurrPartNumQ >> 2)) );                           
2598        memset( puhBaseLCU + uiCUAddr + (uiCurrPartNumQ << 1) + uiCurrPartNumQ + (uiCurrPartNumQ >> 1), uiParameter, (uiCurrPartNumQ >> 2) );                           
2599      }
2600      else if ( uiPUIdx == 1 )
2601      {
2602        memset( puhBaseLCU + uiCUAddr, uiParameter, (uiCurrPartNumQ >> 2) );                           
2603        memset( puhBaseLCU + uiCUAddr + (uiCurrPartNumQ >> 1), uiParameter, (uiCurrPartNumQ >> 2) );                           
2604        memset( puhBaseLCU + uiCUAddr + (uiCurrPartNumQ << 1), uiParameter, (uiCurrPartNumQ >> 2) );                           
2605        memset( puhBaseLCU + uiCUAddr + (uiCurrPartNumQ << 1) + (uiCurrPartNumQ >> 1), uiParameter, (uiCurrPartNumQ >> 2) );                         
2606      }
2607      else
2608      {
2609        assert(0);
2610      }
2611      break;
2612    default:
2613      assert( 0 );
2614  }
2615}
2616
2617#if H_3D_DIM_SDC
2618Void TComDataCU::setSDCFlagSubParts ( Bool bSDCFlag, UInt uiAbsPartIdx, UInt uiDepth )
2619{
2620  assert( sizeof( *m_pbSDCFlag) == 1 );
2621  memset( m_pbSDCFlag + uiAbsPartIdx, bSDCFlag, m_pcPic->getNumPartInCU() >> ( 2 * uiDepth ) );
2622}
2623
2624Bool TComDataCU::getSDCAvailable( UInt uiAbsPartIdx )
2625{
2626  // check general CU information
2627  if( !getSlice()->getIsDepth() || !isIntra(uiAbsPartIdx) || getPartitionSize(uiAbsPartIdx) != SIZE_2Nx2N )
2628    return false;
2629 
2630  // check prediction mode
2631  UInt uiLumaPredMode = getLumaIntraDir( uiAbsPartIdx ); 
2632  if( uiLumaPredMode == PLANAR_IDX || ( getDimType( uiLumaPredMode ) == DMM1_IDX && !isDimDeltaDC( uiLumaPredMode ) ) )
2633    return true;
2634 
2635  // else
2636  return false;
2637}
2638#endif
2639Void TComDataCU::setMergeFlagSubParts ( Bool bMergeFlag, UInt uiAbsPartIdx, UInt uiPartIdx, UInt uiDepth )
2640{
2641  setSubPart( bMergeFlag, m_pbMergeFlag, uiAbsPartIdx, uiDepth, uiPartIdx );
2642}
2643
2644Void TComDataCU::setMergeIndexSubParts ( UInt uiMergeIndex, UInt uiAbsPartIdx, UInt uiPartIdx, UInt uiDepth )
2645{
2646  setSubPart<UChar>( uiMergeIndex, m_puhMergeIndex, uiAbsPartIdx, uiDepth, uiPartIdx );
2647}
2648
2649#if H_3D_SPIVMP
2650Void TComDataCU::setSPIVMPFlagSubParts( Bool bSPIVMPFlag, UInt uiAbsPartIdx, UInt uiPartIdx, UInt uiDepth )
2651{
2652  setSubPart<Bool>( bSPIVMPFlag, m_pbSPIVMPFlag, uiAbsPartIdx, uiDepth, uiPartIdx );
2653}
2654#endif
2655
2656#if H_3D_VSP
2657Void TComDataCU::setVSPFlagSubParts( Char iVSPFlag, UInt uiAbsPartIdx, UInt uiPartIdx, UInt uiDepth )
2658{
2659  setSubPart<Char>( iVSPFlag, m_piVSPFlag, uiAbsPartIdx, uiDepth, uiPartIdx );
2660}
2661#if H_3D_VSP
2662template<typename T>
2663Void TComDataCU::setSubPartT( T uiParameter, T* puhBaseLCU, UInt uiCUAddr, UInt uiCUDepth, UInt uiPUIdx )
2664{
2665  UInt uiCurrPartNumQ = (m_pcPic->getNumPartInCU() >> (2 * uiCUDepth)) >> 2;
2666  switch ( m_pePartSize[ uiCUAddr ] )
2667  {
2668  case SIZE_2Nx2N:
2669    for (UInt ui = 0; ui < 4 * uiCurrPartNumQ; ui++)
2670      puhBaseLCU[uiCUAddr + ui] = uiParameter;
2671
2672    break;
2673  case SIZE_2NxN:
2674    for (UInt ui = 0; ui < 2 * uiCurrPartNumQ; ui++)
2675      puhBaseLCU[uiCUAddr + ui] = uiParameter;
2676    break;
2677  case SIZE_Nx2N:
2678    for (UInt ui = 0; ui < uiCurrPartNumQ; ui++)
2679      puhBaseLCU[uiCUAddr + ui] = uiParameter;
2680    for (UInt ui = 0; ui < uiCurrPartNumQ; ui++)
2681      puhBaseLCU[uiCUAddr + 2 * uiCurrPartNumQ + ui] = uiParameter;
2682    break;
2683  case SIZE_NxN:
2684    for (UInt ui = 0; ui < uiCurrPartNumQ; ui++)
2685      puhBaseLCU[uiCUAddr + ui] = uiParameter;
2686    break;
2687  case SIZE_2NxnU:
2688    if ( uiPUIdx == 0 )
2689    {
2690      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 1); ui++)
2691        puhBaseLCU[uiCUAddr + ui] = uiParameter;
2692      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 1); ui++)
2693        puhBaseLCU[uiCUAddr + uiCurrPartNumQ + ui] = uiParameter;
2694
2695    }
2696    else if ( uiPUIdx == 1 )
2697    {
2698      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 1); ui++)
2699        puhBaseLCU[uiCUAddr + ui] = uiParameter;
2700      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 1) + (uiCurrPartNumQ << 1); ui++)
2701        puhBaseLCU[uiCUAddr + uiCurrPartNumQ + ui] = uiParameter;
2702
2703    }
2704    else
2705    {
2706      assert(0);
2707    }
2708    break;
2709  case SIZE_2NxnD:
2710    if ( uiPUIdx == 0 )
2711    {
2712      for (UInt ui = 0; ui < ((uiCurrPartNumQ << 1) + (uiCurrPartNumQ >> 1)); ui++)
2713        puhBaseLCU[uiCUAddr + ui] = uiParameter;
2714      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 1); ui++)
2715        puhBaseLCU[uiCUAddr + (uiCurrPartNumQ << 1) + uiCurrPartNumQ + ui] = uiParameter;
2716
2717    }
2718    else if ( uiPUIdx == 1 )
2719    {
2720      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 1); ui++)
2721        puhBaseLCU[uiCUAddr + ui] = uiParameter;
2722      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 1); ui++)
2723        puhBaseLCU[uiCUAddr + uiCurrPartNumQ + ui] = uiParameter;
2724
2725    }
2726    else
2727    {
2728      assert(0);
2729    }
2730    break;
2731  case SIZE_nLx2N:
2732    if ( uiPUIdx == 0 )
2733    {
2734      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 2); ui++)
2735        puhBaseLCU[uiCUAddr + ui] = uiParameter;
2736      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 2); ui++)
2737        puhBaseLCU[uiCUAddr + (uiCurrPartNumQ >> 1) + ui] = uiParameter;
2738      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 2); ui++)
2739        puhBaseLCU[uiCUAddr + (uiCurrPartNumQ << 1) + ui] = uiParameter;
2740      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 2); ui++)
2741        puhBaseLCU[uiCUAddr + (uiCurrPartNumQ << 1) + (uiCurrPartNumQ >> 1) + ui] = uiParameter;
2742
2743    }
2744    else if ( uiPUIdx == 1 )
2745    {
2746      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 2); ui++)
2747        puhBaseLCU[uiCUAddr + ui] = uiParameter;
2748      for (UInt ui = 0; ui < (uiCurrPartNumQ + (uiCurrPartNumQ >> 2)); ui++)
2749        puhBaseLCU[uiCUAddr + (uiCurrPartNumQ >> 1) + ui] = uiParameter;
2750      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 2); ui++)
2751        puhBaseLCU[uiCUAddr + (uiCurrPartNumQ << 1) + ui] = uiParameter;
2752      for (UInt ui = 0; ui < (uiCurrPartNumQ + (uiCurrPartNumQ >> 2)); ui++)
2753        puhBaseLCU[uiCUAddr + (uiCurrPartNumQ << 1) + (uiCurrPartNumQ >> 1) + ui] = uiParameter;
2754
2755    }
2756    else
2757    {
2758      assert(0);
2759    }
2760    break;
2761  case SIZE_nRx2N:
2762    if ( uiPUIdx == 0 )
2763    {
2764      for (UInt ui = 0; ui < (uiCurrPartNumQ + (uiCurrPartNumQ >> 2)); ui++)
2765        puhBaseLCU[uiCUAddr + ui] = uiParameter;
2766      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 2); ui++)
2767        puhBaseLCU[uiCUAddr + uiCurrPartNumQ + (uiCurrPartNumQ >> 1) + ui] = uiParameter;
2768      for (UInt ui = 0; ui < (uiCurrPartNumQ + (uiCurrPartNumQ >> 2)); ui++)
2769        puhBaseLCU[uiCUAddr + (uiCurrPartNumQ << 1) + ui] = uiParameter;
2770      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 2); ui++)
2771        puhBaseLCU[uiCUAddr + (uiCurrPartNumQ << 1) + uiCurrPartNumQ + (uiCurrPartNumQ >> 1) + ui] = uiParameter;
2772
2773    }
2774    else if ( uiPUIdx == 1 )
2775    {
2776      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 2); ui++)
2777        puhBaseLCU[uiCUAddr + ui] = uiParameter;
2778      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 2); ui++)
2779        puhBaseLCU[uiCUAddr + (uiCurrPartNumQ >> 1) + ui] = uiParameter;
2780      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 2); ui++)
2781        puhBaseLCU[uiCUAddr + (uiCurrPartNumQ << 1) + ui] = uiParameter;
2782      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 2); ui++)
2783        puhBaseLCU[uiCUAddr + (uiCurrPartNumQ << 1) + (uiCurrPartNumQ >> 1) + ui] = uiParameter;
2784
2785    }
2786    else
2787    {
2788      assert(0);
2789    }
2790    break;
2791  default:
2792    assert( 0 );
2793  }
2794
2795}
2796#endif
2797#endif
2798Void TComDataCU::setChromIntraDirSubParts( UInt uiDir, UInt uiAbsPartIdx, UInt uiDepth )
2799{
2800  UInt uiCurrPartNumb = m_pcPic->getNumPartInCU() >> (uiDepth << 1);
2801 
2802  memset( m_puhChromaIntraDir + uiAbsPartIdx, uiDir, sizeof(UChar)*uiCurrPartNumb );
2803}
2804
2805Void TComDataCU::setInterDirSubParts( UInt uiDir, UInt uiAbsPartIdx, UInt uiPartIdx, UInt uiDepth )
2806{
2807  setSubPart<UChar>( uiDir, m_puhInterDir, uiAbsPartIdx, uiDepth, uiPartIdx );
2808}
2809
2810Void TComDataCU::setMVPIdxSubParts( Int iMVPIdx, RefPicList eRefPicList, UInt uiAbsPartIdx, UInt uiPartIdx, UInt uiDepth )
2811{
2812  setSubPart<Char>( iMVPIdx, m_apiMVPIdx[eRefPicList], uiAbsPartIdx, uiDepth, uiPartIdx );
2813}
2814
2815Void TComDataCU::setMVPNumSubParts( Int iMVPNum, RefPicList eRefPicList, UInt uiAbsPartIdx, UInt uiPartIdx, UInt uiDepth )
2816{
2817  setSubPart<Char>( iMVPNum, m_apiMVPNum[eRefPicList], uiAbsPartIdx, uiDepth, uiPartIdx );
2818}
2819
2820
2821Void TComDataCU::setTrIdxSubParts( UInt uiTrIdx, UInt uiAbsPartIdx, UInt uiDepth )
2822{
2823  UInt uiCurrPartNumb = m_pcPic->getNumPartInCU() >> (uiDepth << 1);
2824 
2825  memset( m_puhTrIdx + uiAbsPartIdx, uiTrIdx, sizeof(UChar)*uiCurrPartNumb );
2826}
2827
2828Void TComDataCU::setTransformSkipSubParts( UInt useTransformSkipY, UInt useTransformSkipU, UInt useTransformSkipV, UInt uiAbsPartIdx, UInt uiDepth )
2829{
2830  UInt uiCurrPartNumb = m_pcPic->getNumPartInCU() >> (uiDepth << 1);
2831
2832  memset( m_puhTransformSkip[0] + uiAbsPartIdx, useTransformSkipY, sizeof( UChar ) * uiCurrPartNumb );
2833  memset( m_puhTransformSkip[1] + uiAbsPartIdx, useTransformSkipU, sizeof( UChar ) * uiCurrPartNumb );
2834  memset( m_puhTransformSkip[2] + uiAbsPartIdx, useTransformSkipV, sizeof( UChar ) * uiCurrPartNumb );
2835}
2836
2837Void TComDataCU::setTransformSkipSubParts( UInt useTransformSkip, TextType eType, UInt uiAbsPartIdx, UInt uiDepth)
2838{
2839  UInt uiCurrPartNumb = m_pcPic->getNumPartInCU() >> (uiDepth << 1);
2840
2841  memset( m_puhTransformSkip[g_aucConvertTxtTypeToIdx[eType]] + uiAbsPartIdx, useTransformSkip, sizeof( UChar ) * uiCurrPartNumb );
2842}
2843
2844Void TComDataCU::setSizeSubParts( UInt uiWidth, UInt uiHeight, UInt uiAbsPartIdx, UInt uiDepth )
2845{
2846  UInt uiCurrPartNumb = m_pcPic->getNumPartInCU() >> (uiDepth << 1);
2847 
2848  memset( m_puhWidth  + uiAbsPartIdx, uiWidth,  sizeof(UChar)*uiCurrPartNumb );
2849  memset( m_puhHeight + uiAbsPartIdx, uiHeight, sizeof(UChar)*uiCurrPartNumb );
2850}
2851
2852UChar TComDataCU::getNumPartInter()
2853{
2854  UChar iNumPart = 0;
2855 
2856  switch ( m_pePartSize[0] )
2857  {
2858    case SIZE_2Nx2N:    iNumPart = 1; break;
2859    case SIZE_2NxN:     iNumPart = 2; break;
2860    case SIZE_Nx2N:     iNumPart = 2; break;
2861    case SIZE_NxN:      iNumPart = 4; break;
2862    case SIZE_2NxnU:    iNumPart = 2; break;
2863    case SIZE_2NxnD:    iNumPart = 2; break;
2864    case SIZE_nLx2N:    iNumPart = 2; break;
2865    case SIZE_nRx2N:    iNumPart = 2; break;
2866    default:            assert (0);   break;
2867  }
2868 
2869  return  iNumPart;
2870}
2871
2872#if H_3D_IC
2873Void TComDataCU::getPartIndexAndSize( UInt uiPartIdx, UInt& ruiPartAddr, Int& riWidth, Int& riHeight, UInt uiAbsPartIdx, Bool bLCU)
2874{
2875  UInt uiNumPartition  = bLCU ? (getWidth(uiAbsPartIdx)*getHeight(uiAbsPartIdx) >> 4) : m_uiNumPartition;
2876  UInt  uiTmpAbsPartIdx  = bLCU ? uiAbsPartIdx : 0;
2877
2878  switch ( m_pePartSize[uiTmpAbsPartIdx] )
2879  {
2880  case SIZE_2NxN:
2881    riWidth = getWidth( uiTmpAbsPartIdx );      riHeight = getHeight( uiTmpAbsPartIdx ) >> 1; ruiPartAddr = ( uiPartIdx == 0 )? 0 : uiNumPartition >> 1;
2882    break;
2883  case SIZE_Nx2N:
2884    riWidth = getWidth( uiTmpAbsPartIdx ) >> 1; riHeight = getHeight( uiTmpAbsPartIdx );      ruiPartAddr = ( uiPartIdx == 0 )? 0 : uiNumPartition >> 2;
2885    break;
2886  case SIZE_NxN:
2887    riWidth = getWidth( uiTmpAbsPartIdx ) >> 1; riHeight = getHeight( uiTmpAbsPartIdx ) >> 1; ruiPartAddr = ( uiNumPartition >> 2 ) * uiPartIdx;
2888    break;
2889  case SIZE_2NxnU:
2890    riWidth     = getWidth( uiTmpAbsPartIdx );
2891    riHeight    = ( uiPartIdx == 0 ) ?  getHeight( uiTmpAbsPartIdx ) >> 2 : ( getHeight( uiTmpAbsPartIdx ) >> 2 ) + ( getHeight( uiTmpAbsPartIdx ) >> 1 );
2892    ruiPartAddr = ( uiPartIdx == 0 ) ? 0 : uiNumPartition >> 3;
2893    break;
2894  case SIZE_2NxnD:
2895    riWidth     = getWidth( uiTmpAbsPartIdx );
2896    riHeight    = ( uiPartIdx == 0 ) ?  ( getHeight( uiTmpAbsPartIdx ) >> 2 ) + ( getHeight( uiTmpAbsPartIdx ) >> 1 ) : getHeight( uiTmpAbsPartIdx ) >> 2;
2897    ruiPartAddr = ( uiPartIdx == 0 ) ? 0 : (uiNumPartition >> 1) + (uiNumPartition >> 3);
2898    break;
2899  case SIZE_nLx2N:
2900    riWidth     = ( uiPartIdx == 0 ) ? getWidth( uiTmpAbsPartIdx ) >> 2 : ( getWidth( uiTmpAbsPartIdx ) >> 2 ) + ( getWidth( uiTmpAbsPartIdx ) >> 1 );
2901    riHeight    = getHeight( uiTmpAbsPartIdx );
2902    ruiPartAddr = ( uiPartIdx == 0 ) ? 0 : uiNumPartition >> 4;
2903    break;
2904  case SIZE_nRx2N:
2905    riWidth     = ( uiPartIdx == 0 ) ? ( getWidth( uiTmpAbsPartIdx ) >> 2 ) + ( getWidth( uiTmpAbsPartIdx ) >> 1 ) : getWidth( uiTmpAbsPartIdx ) >> 2;
2906    riHeight    = getHeight( uiTmpAbsPartIdx );
2907    ruiPartAddr = ( uiPartIdx == 0 ) ? 0 : (uiNumPartition >> 2) + (uiNumPartition >> 4);
2908    break;
2909  default:
2910    assert ( m_pePartSize[uiTmpAbsPartIdx] == SIZE_2Nx2N ); 
2911    riWidth = getWidth( uiTmpAbsPartIdx );      riHeight = getHeight( uiTmpAbsPartIdx );      ruiPartAddr = 0;
2912    break;
2913  }
2914}
2915#else
2916Void TComDataCU::getPartIndexAndSize( UInt uiPartIdx, UInt& ruiPartAddr, Int& riWidth, Int& riHeight )
2917{
2918  switch ( m_pePartSize[0] )
2919  {
2920    case SIZE_2NxN:
2921      riWidth = getWidth(0);      riHeight = getHeight(0) >> 1; ruiPartAddr = ( uiPartIdx == 0 )? 0 : m_uiNumPartition >> 1;
2922      break;
2923    case SIZE_Nx2N:
2924      riWidth = getWidth(0) >> 1; riHeight = getHeight(0);      ruiPartAddr = ( uiPartIdx == 0 )? 0 : m_uiNumPartition >> 2;
2925      break;
2926    case SIZE_NxN:
2927      riWidth = getWidth(0) >> 1; riHeight = getHeight(0) >> 1; ruiPartAddr = ( m_uiNumPartition >> 2 ) * uiPartIdx;
2928      break;
2929    case SIZE_2NxnU:
2930      riWidth     = getWidth(0);
2931      riHeight    = ( uiPartIdx == 0 ) ?  getHeight(0) >> 2 : ( getHeight(0) >> 2 ) + ( getHeight(0) >> 1 );
2932      ruiPartAddr = ( uiPartIdx == 0 ) ? 0 : m_uiNumPartition >> 3;
2933      break;
2934    case SIZE_2NxnD:
2935      riWidth     = getWidth(0);
2936      riHeight    = ( uiPartIdx == 0 ) ?  ( getHeight(0) >> 2 ) + ( getHeight(0) >> 1 ) : getHeight(0) >> 2;
2937      ruiPartAddr = ( uiPartIdx == 0 ) ? 0 : (m_uiNumPartition >> 1) + (m_uiNumPartition >> 3);
2938      break;
2939    case SIZE_nLx2N:
2940      riWidth     = ( uiPartIdx == 0 ) ? getWidth(0) >> 2 : ( getWidth(0) >> 2 ) + ( getWidth(0) >> 1 );
2941      riHeight    = getHeight(0);
2942      ruiPartAddr = ( uiPartIdx == 0 ) ? 0 : m_uiNumPartition >> 4;
2943      break;
2944    case SIZE_nRx2N:
2945      riWidth     = ( uiPartIdx == 0 ) ? ( getWidth(0) >> 2 ) + ( getWidth(0) >> 1 ) : getWidth(0) >> 2;
2946      riHeight    = getHeight(0);
2947      ruiPartAddr = ( uiPartIdx == 0 ) ? 0 : (m_uiNumPartition >> 2) + (m_uiNumPartition >> 4);
2948      break;
2949    default:
2950      assert ( m_pePartSize[0] == SIZE_2Nx2N );
2951      riWidth = getWidth(0);      riHeight = getHeight(0);      ruiPartAddr = 0;
2952      break;
2953  }
2954}
2955#endif
2956
2957
2958Void TComDataCU::getMvField ( TComDataCU* pcCU, UInt uiAbsPartIdx, RefPicList eRefPicList, TComMvField& rcMvField )
2959{
2960  if ( pcCU == NULL )  // OUT OF BOUNDARY
2961  {
2962    TComMv  cZeroMv;
2963    rcMvField.setMvField( cZeroMv, NOT_VALID );
2964    return;
2965  }
2966 
2967  TComCUMvField*  pcCUMvField = pcCU->getCUMvField( eRefPicList );
2968  rcMvField.setMvField( pcCUMvField->getMv( uiAbsPartIdx ), pcCUMvField->getRefIdx( uiAbsPartIdx ) );
2969}
2970
2971Void TComDataCU::deriveLeftRightTopIdxGeneral ( UInt uiAbsPartIdx, UInt uiPartIdx, UInt& ruiPartIdxLT, UInt& ruiPartIdxRT )
2972{
2973  ruiPartIdxLT = m_uiAbsIdxInLCU + uiAbsPartIdx;
2974  UInt uiPUWidth = 0;
2975 
2976  switch ( m_pePartSize[uiAbsPartIdx] )
2977  {
2978    case SIZE_2Nx2N: uiPUWidth = m_puhWidth[uiAbsPartIdx];  break;
2979    case SIZE_2NxN:  uiPUWidth = m_puhWidth[uiAbsPartIdx];   break;
2980    case SIZE_Nx2N:  uiPUWidth = m_puhWidth[uiAbsPartIdx]  >> 1;  break;
2981    case SIZE_NxN:   uiPUWidth = m_puhWidth[uiAbsPartIdx]  >> 1; break;
2982    case SIZE_2NxnU:   uiPUWidth = m_puhWidth[uiAbsPartIdx]; break;
2983    case SIZE_2NxnD:   uiPUWidth = m_puhWidth[uiAbsPartIdx]; break;
2984    case SIZE_nLx2N:   
2985      if ( uiPartIdx == 0 )
2986      {
2987        uiPUWidth = m_puhWidth[uiAbsPartIdx]  >> 2; 
2988      }
2989      else if ( uiPartIdx == 1 )
2990      {
2991        uiPUWidth = (m_puhWidth[uiAbsPartIdx]  >> 1) + (m_puhWidth[uiAbsPartIdx]  >> 2); 
2992      }
2993      else
2994      {
2995        assert(0);
2996      }
2997      break;
2998    case SIZE_nRx2N:   
2999      if ( uiPartIdx == 0 )
3000      {
3001        uiPUWidth = (m_puhWidth[uiAbsPartIdx]  >> 1) + (m_puhWidth[uiAbsPartIdx]  >> 2); 
3002      }
3003      else if ( uiPartIdx == 1 )
3004      {
3005        uiPUWidth = m_puhWidth[uiAbsPartIdx]  >> 2; 
3006      }
3007      else
3008      {
3009        assert(0);
3010      }
3011      break;
3012    default:
3013      assert (0);
3014      break;
3015  }
3016 
3017  ruiPartIdxRT = g_auiRasterToZscan [g_auiZscanToRaster[ ruiPartIdxLT ] + uiPUWidth / m_pcPic->getMinCUWidth() - 1 ];
3018}
3019
3020Void TComDataCU::deriveLeftBottomIdxGeneral( UInt uiAbsPartIdx, UInt uiPartIdx, UInt& ruiPartIdxLB )
3021{
3022  UInt uiPUHeight = 0;
3023  switch ( m_pePartSize[uiAbsPartIdx] )
3024  {
3025    case SIZE_2Nx2N: uiPUHeight = m_puhHeight[uiAbsPartIdx];    break;
3026    case SIZE_2NxN:  uiPUHeight = m_puhHeight[uiAbsPartIdx] >> 1;    break;
3027    case SIZE_Nx2N:  uiPUHeight = m_puhHeight[uiAbsPartIdx];  break;
3028    case SIZE_NxN:   uiPUHeight = m_puhHeight[uiAbsPartIdx] >> 1;    break;
3029    case SIZE_2NxnU: 
3030      if ( uiPartIdx == 0 )
3031      {
3032        uiPUHeight = m_puhHeight[uiAbsPartIdx] >> 2;   
3033      }
3034      else if ( uiPartIdx == 1 )
3035      {
3036        uiPUHeight = (m_puhHeight[uiAbsPartIdx] >> 1) + (m_puhHeight[uiAbsPartIdx] >> 2);   
3037      }
3038      else
3039      {
3040        assert(0);
3041      }
3042      break;
3043    case SIZE_2NxnD: 
3044      if ( uiPartIdx == 0 )
3045      {
3046        uiPUHeight = (m_puhHeight[uiAbsPartIdx] >> 1) + (m_puhHeight[uiAbsPartIdx] >> 2);   
3047      }
3048      else if ( uiPartIdx == 1 )
3049      {
3050        uiPUHeight = m_puhHeight[uiAbsPartIdx] >> 2;   
3051      }
3052      else
3053      {
3054        assert(0);
3055      }
3056      break;
3057    case SIZE_nLx2N: uiPUHeight = m_puhHeight[uiAbsPartIdx];  break;
3058    case SIZE_nRx2N: uiPUHeight = m_puhHeight[uiAbsPartIdx];  break;
3059    default:
3060      assert (0);
3061      break;
3062  }
3063 
3064  ruiPartIdxLB      = g_auiRasterToZscan [g_auiZscanToRaster[ m_uiAbsIdxInLCU + uiAbsPartIdx ] + ((uiPUHeight / m_pcPic->getMinCUHeight()) - 1)*m_pcPic->getNumPartInWidth()];
3065}
3066
3067Void TComDataCU::deriveLeftRightTopIdx ( UInt uiPartIdx, UInt& ruiPartIdxLT, UInt& ruiPartIdxRT )
3068{
3069  ruiPartIdxLT = m_uiAbsIdxInLCU;
3070  ruiPartIdxRT = g_auiRasterToZscan [g_auiZscanToRaster[ ruiPartIdxLT ] + m_puhWidth[0] / m_pcPic->getMinCUWidth() - 1 ];
3071 
3072  switch ( m_pePartSize[0] )
3073  {
3074    case SIZE_2Nx2N:                                                                                                                                break;
3075    case SIZE_2NxN:
3076      ruiPartIdxLT += ( uiPartIdx == 0 )? 0 : m_uiNumPartition >> 1; ruiPartIdxRT += ( uiPartIdx == 0 )? 0 : m_uiNumPartition >> 1;
3077      break;
3078    case SIZE_Nx2N:
3079      ruiPartIdxLT += ( uiPartIdx == 0 )? 0 : m_uiNumPartition >> 2; ruiPartIdxRT -= ( uiPartIdx == 1 )? 0 : m_uiNumPartition >> 2;
3080      break;
3081    case SIZE_NxN:
3082      ruiPartIdxLT += ( m_uiNumPartition >> 2 ) * uiPartIdx;         ruiPartIdxRT +=  ( m_uiNumPartition >> 2 ) * ( uiPartIdx - 1 );
3083      break;
3084    case SIZE_2NxnU:
3085      ruiPartIdxLT += ( uiPartIdx == 0 )? 0 : m_uiNumPartition >> 3;
3086      ruiPartIdxRT += ( uiPartIdx == 0 )? 0 : m_uiNumPartition >> 3;
3087      break;
3088    case SIZE_2NxnD:
3089      ruiPartIdxLT += ( uiPartIdx == 0 )? 0 : ( m_uiNumPartition >> 1 ) + ( m_uiNumPartition >> 3 );
3090      ruiPartIdxRT += ( uiPartIdx == 0 )? 0 : ( m_uiNumPartition >> 1 ) + ( m_uiNumPartition >> 3 );
3091      break;
3092    case SIZE_nLx2N:
3093      ruiPartIdxLT += ( uiPartIdx == 0 )? 0 : m_uiNumPartition >> 4;
3094      ruiPartIdxRT -= ( uiPartIdx == 1 )? 0 : ( m_uiNumPartition >> 2 ) + ( m_uiNumPartition >> 4 );
3095      break;
3096    case SIZE_nRx2N:
3097      ruiPartIdxLT += ( uiPartIdx == 0 )? 0 : ( m_uiNumPartition >> 2 ) + ( m_uiNumPartition >> 4 );
3098      ruiPartIdxRT -= ( uiPartIdx == 1 )? 0 : m_uiNumPartition >> 4;
3099      break;
3100    default:
3101      assert (0);
3102      break;
3103  }
3104 
3105}
3106
3107Void TComDataCU::deriveLeftBottomIdx( UInt  uiPartIdx,      UInt&      ruiPartIdxLB )
3108{
3109  ruiPartIdxLB      = g_auiRasterToZscan [g_auiZscanToRaster[ m_uiAbsIdxInLCU ] + ( ((m_puhHeight[0] / m_pcPic->getMinCUHeight())>>1) - 1)*m_pcPic->getNumPartInWidth()];
3110 
3111  switch ( m_pePartSize[0] )
3112  {
3113    case SIZE_2Nx2N:
3114      ruiPartIdxLB += m_uiNumPartition >> 1;
3115      break;
3116    case SIZE_2NxN:
3117      ruiPartIdxLB += ( uiPartIdx == 0 )? 0 : m_uiNumPartition >> 1;
3118      break;
3119    case SIZE_Nx2N:
3120      ruiPartIdxLB += ( uiPartIdx == 0 )? m_uiNumPartition >> 1 : (m_uiNumPartition >> 2)*3;
3121      break;
3122    case SIZE_NxN:
3123      ruiPartIdxLB += ( m_uiNumPartition >> 2 ) * uiPartIdx;
3124      break;
3125    case SIZE_2NxnU:
3126      ruiPartIdxLB += ( uiPartIdx == 0 ) ? -((Int)m_uiNumPartition >> 3) : m_uiNumPartition >> 1;
3127      break;
3128    case SIZE_2NxnD:
3129      ruiPartIdxLB += ( uiPartIdx == 0 ) ? (m_uiNumPartition >> 2) + (m_uiNumPartition >> 3): m_uiNumPartition >> 1;
3130      break;
3131    case SIZE_nLx2N:
3132      ruiPartIdxLB += ( uiPartIdx == 0 ) ? m_uiNumPartition >> 1 : (m_uiNumPartition >> 1) + (m_uiNumPartition >> 4);
3133      break;
3134    case SIZE_nRx2N:
3135      ruiPartIdxLB += ( uiPartIdx == 0 ) ? m_uiNumPartition >> 1 : (m_uiNumPartition >> 1) + (m_uiNumPartition >> 2) + (m_uiNumPartition >> 4);
3136      break;
3137    default:
3138      assert (0);
3139      break;
3140  }
3141}
3142
3143/** Derives the partition index of neighbouring bottom right block
3144 * \param [in]  eCUMode
3145 * \param [in]  uiPartIdx
3146 * \param [out] ruiPartIdxRB
3147 */
3148Void TComDataCU::deriveRightBottomIdx( UInt  uiPartIdx,      UInt&      ruiPartIdxRB )
3149{
3150  ruiPartIdxRB      = g_auiRasterToZscan [g_auiZscanToRaster[ m_uiAbsIdxInLCU ] + ( ((m_puhHeight[0] / m_pcPic->getMinCUHeight())>>1) - 1)*m_pcPic->getNumPartInWidth() +  m_puhWidth[0] / m_pcPic->getMinCUWidth() - 1];
3151
3152  switch ( m_pePartSize[0] )
3153  {
3154    case SIZE_2Nx2N: 
3155      ruiPartIdxRB += m_uiNumPartition >> 1;   
3156      break;
3157    case SIZE_2NxN: 
3158      ruiPartIdxRB += ( uiPartIdx == 0 )? 0 : m_uiNumPartition >> 1;   
3159      break;
3160    case SIZE_Nx2N: 
3161      ruiPartIdxRB += ( uiPartIdx == 0 )? m_uiNumPartition >> 2 : (m_uiNumPartition >> 1);   
3162      break;
3163    case SIZE_NxN:   
3164      ruiPartIdxRB += ( m_uiNumPartition >> 2 ) * ( uiPartIdx - 1 );   
3165      break;
3166    case SIZE_2NxnU:
3167      ruiPartIdxRB += ( uiPartIdx == 0 ) ? -((Int)m_uiNumPartition >> 3) : m_uiNumPartition >> 1;
3168      break;
3169    case SIZE_2NxnD:
3170      ruiPartIdxRB += ( uiPartIdx == 0 ) ? (m_uiNumPartition >> 2) + (m_uiNumPartition >> 3): m_uiNumPartition >> 1;
3171      break;
3172    case SIZE_nLx2N:
3173      ruiPartIdxRB += ( uiPartIdx == 0 ) ? (m_uiNumPartition >> 3) + (m_uiNumPartition >> 4): m_uiNumPartition >> 1;
3174      break;
3175    case SIZE_nRx2N:
3176      ruiPartIdxRB += ( uiPartIdx == 0 ) ? (m_uiNumPartition >> 2) + (m_uiNumPartition >> 3) + (m_uiNumPartition >> 4) : m_uiNumPartition >> 1;
3177      break;
3178    default:
3179      assert (0);
3180      break;
3181  }
3182}
3183
3184Void TComDataCU::deriveLeftRightTopIdxAdi ( UInt& ruiPartIdxLT, UInt& ruiPartIdxRT, UInt uiPartOffset, UInt uiPartDepth )
3185{
3186  UInt uiNumPartInWidth = (m_puhWidth[0]/m_pcPic->getMinCUWidth())>>uiPartDepth;
3187  ruiPartIdxLT = m_uiAbsIdxInLCU + uiPartOffset;
3188  ruiPartIdxRT = g_auiRasterToZscan[ g_auiZscanToRaster[ ruiPartIdxLT ] + uiNumPartInWidth - 1 ];
3189}
3190
3191Void TComDataCU::deriveLeftBottomIdxAdi( UInt& ruiPartIdxLB, UInt uiPartOffset, UInt uiPartDepth )
3192{
3193  UInt uiAbsIdx;
3194  UInt uiMinCuWidth, uiWidthInMinCus;
3195 
3196  uiMinCuWidth    = getPic()->getMinCUWidth();
3197  uiWidthInMinCus = (getWidth(0)/uiMinCuWidth)>>uiPartDepth;
3198  uiAbsIdx        = getZorderIdxInCU()+uiPartOffset+(m_uiNumPartition>>(uiPartDepth<<1))-1;
3199  uiAbsIdx        = g_auiZscanToRaster[uiAbsIdx]-(uiWidthInMinCus-1);
3200  ruiPartIdxLB    = g_auiRasterToZscan[uiAbsIdx];
3201}
3202
3203Bool TComDataCU::hasEqualMotion( UInt uiAbsPartIdx, TComDataCU* pcCandCU, UInt uiCandAbsPartIdx )
3204{
3205
3206  if ( getInterDir( uiAbsPartIdx ) != pcCandCU->getInterDir( uiCandAbsPartIdx ) )
3207  {
3208    return false;
3209  }
3210
3211  for ( UInt uiRefListIdx = 0; uiRefListIdx < 2; uiRefListIdx++ )
3212  {
3213    if ( getInterDir( uiAbsPartIdx ) & ( 1 << uiRefListIdx ) )
3214    {
3215      if ( getCUMvField( RefPicList( uiRefListIdx ) )->getMv( uiAbsPartIdx )     != pcCandCU->getCUMvField( RefPicList( uiRefListIdx ) )->getMv( uiCandAbsPartIdx ) || 
3216        getCUMvField( RefPicList( uiRefListIdx ) )->getRefIdx( uiAbsPartIdx ) != pcCandCU->getCUMvField( RefPicList( uiRefListIdx ) )->getRefIdx( uiCandAbsPartIdx ) )
3217      {
3218        return false;
3219      }
3220    }
3221  }
3222
3223  return true;
3224}
3225
3226#if H_3D_VSP
3227
3228/** Add a VSP merging candidate
3229 * \Inputs
3230 * \param uiPUIdx: PU index within a CU
3231 * \param ucVspMergePos: Specify the VSP merge candidate position
3232 * \param mrgCandIdx: Target merge candidate index. At encoder, it is set equal to -1, such that the whole merge candidate list will be constructed.
3233 * \param pDinfo: The "disparity information" derived from neighboring blocks. Type 1 MV.
3234 * \param uiCount: The next position to add VSP merge candidate
3235 *
3236 * \Outputs
3237 * \param uiCount: The next position to add merge candidate. Will be updated if VSP is successfully added
3238 * \param abCandIsInter: abCandIsInter[iCount] tells that VSP candidate is an Inter candidate, if VSP is successfully added
3239 * \param pcMvFieldNeighbours:   Return combined motion information, then stored to a global buffer
3240 *                                    1) the "disparity vector". Type 1 MV. To be used to fetch a depth block.
3241 *                                    2) the ref index /list.    Type 2 reference picture pointer, typically for texture
3242 * \param puhInterDirNeighbours: Indicate the VSP prediction direction.
3243 * \param vspFlag: vspFlag[iCount] will be set (equal to 1), if VSP is successfully added. To be used to indicate the actual position of the VSP candidate
3244 *
3245 * \Return
3246 *   true:  if the VSP candidate is added at the target position
3247 *   false: otherwise
3248 */
3249inline Bool TComDataCU::xAddVspCand( Int mrgCandIdx, DisInfo* pDInfo, Int& iCount,
3250  Bool* abCandIsInter, TComMvField* pcMvFieldNeighbours, UChar* puhInterDirNeighbours, Int* vspFlag, Int& iCount3DV, InheritedVSPDisInfo*  inheritedVSPDisInfo  )
3251  {
3252#if MTK_NBDV_IVREF_FIX_G0067
3253  if ( m_pcSlice->getViewIndex() == 0 || !m_pcSlice->getVPS()->getViewSynthesisPredFlag( m_pcSlice->getLayerIdInVps() ) || m_pcSlice->getIsDepth() || pDInfo->m_aVIdxCan == -1)
3254#else
3255  if ( m_pcSlice->getViewIndex() == 0 || !m_pcSlice->getVPS()->getViewSynthesisPredFlag( m_pcSlice->getLayerIdInVps() ) || m_pcSlice->getIsDepth() )
3256#endif
3257  {
3258    return false;
3259  }
3260
3261  Int refViewIdx = pDInfo->m_aVIdxCan;
3262  TComPic* picDepth = getSlice()->getIvPic( true, refViewIdx );
3263 
3264  if( picDepth == NULL ) // No depth reference avail
3265  {
3266    // Is this allowed to happen? When not an assertion should be added here!
3267    return false;
3268  }
3269
3270  rightShiftMergeCandList( pcMvFieldNeighbours, puhInterDirNeighbours, vspFlag, inheritedVSPDisInfo, iCount, (5-iCount), iCount3DV);
3271 
3272  Bool  refViewAvailFlag = false;
3273  UChar predFlag[2]      = {0, 0}; 
3274  Int   refListIdY       = 0;   
3275  Int   viewIdInRefListX = -1;
3276 
3277  for( Int iRefListIdX = 0; iRefListIdX < 2 && !refViewAvailFlag; iRefListIdX++ )
3278  {
3279    RefPicList eRefPicListX = RefPicList( iRefListIdX );
3280    for ( Int i = 0; i < m_pcSlice->getNumRefIdx(eRefPicListX) && !refViewAvailFlag; i++ )
3281    {
3282      Int viewIdxRefInListX = m_pcSlice->getRefPic(eRefPicListX, i)->getViewIndex();
3283      if ( viewIdxRefInListX == refViewIdx )
3284      {
3285        refViewAvailFlag      = true;
3286        predFlag[iRefListIdX] = 1;
3287        viewIdInRefListX      = m_pcSlice->getRefPic(eRefPicListX, i)->getViewId();
3288        refListIdY            = 1 - iRefListIdX;
3289        pcMvFieldNeighbours[(iCount<<1)+iRefListIdX].setMvField( pDInfo->m_acNBDV, i );
3290#if H_3D_NBDV
3291        pcMvFieldNeighbours[(iCount<<1)+iRefListIdX].getMv().setIDVFlag (false);
3292#endif
3293      }
3294    }
3295  }
3296
3297  if (m_pcSlice->isInterB() && refViewAvailFlag)
3298  {
3299    RefPicList eRefPicListY = RefPicList( refListIdY );
3300    refViewAvailFlag = false;
3301    for ( Int i = 0; i < m_pcSlice->getNumRefIdx(eRefPicListY) && !refViewAvailFlag; i++ )
3302    {
3303      Int viewIdxRefInListY = m_pcSlice->getRefPic(eRefPicListY, i)->getViewIndex();
3304      if ( viewIdxRefInListY != refViewIdx && viewIdxRefInListY != m_pcSlice->getViewIndex() )
3305      {
3306        refViewAvailFlag = true;
3307        predFlag[refListIdY] = 1;
3308        TComMv  cMv = pDInfo->m_acNBDV;
3309       
3310        Int viewIdInRefListY = m_pcSlice->getRefPic( eRefPicListY, i)->getViewId();
3311        Int currViewId       = m_pcSlice->getViewId();
3312       
3313        //// Following might be added here when MV-HEVC 5 HLS is included (and derivations above removed):
3314        // Int viewIdInRefListX = m_pcSlice->getVPS()->getViewIdVal( refViewIdx  );
3315       
3316        Int iScale      = xGetDistScaleFactor( currViewId, viewIdInRefListY, currViewId, viewIdInRefListX );
3317       
3318        // Can iScale == 4096 happen?, I guess not since viewIdInRefListY is always unequal to viewIdInRefListX.
3319        if ( iScale != 4096 && m_pcSlice->getVPS()->getIvMvScalingFlag() ) 
3320        {
3321          cMv = cMv.scaleMv( iScale );
3322        }
3323        else
3324        {
3325
3326          cMv = cMv;
3327        }
3328        clipMv( cMv );
3329        pcMvFieldNeighbours[(iCount<<1)+refListIdY].setMvField( cMv, i );
3330#if H_3D_NBDV
3331        pcMvFieldNeighbours[(iCount<<1)+refListIdY].getMv().setIDVFlag (false);
3332#endif
3333      }
3334    }
3335  }
3336
3337  // Set values to be returned
3338  abCandIsInter        [iCount] = true;
3339  puhInterDirNeighbours[iCount] = (predFlag[0] | (predFlag[1] << 1));
3340  vspFlag              [iCount] = 1;
3341
3342  if ( mrgCandIdx == iCount )
3343  {
3344    return true;
3345  }
3346
3347  iCount++;
3348
3349  return false;
3350}
3351
3352#endif
3353
3354#if H_3D_IV_MERGE
3355inline Bool TComDataCU::xAddIvMRGCand( Int mrgCandIdx, Int& iCount, Bool* abCandIsInter, TComMvField* pcMvFieldNeighbours, UChar* puhInterDirNeighbours, Int* ivCandDir, TComMv* ivCandMv, 
3356  Int* ivCandRefIdx, Int iPosIvDC, Int* vspFlag, Int &iCount3DV, InheritedVSPDisInfo*  inheritedVSPDisInfo  )
3357{
3358  for(Int iLoop = 0; iLoop < 2; iLoop ++ ) 
3359  {
3360    // IvDcShift (Derived from spatial Iv neighboring blocks)
3361    if( iLoop == 1 )
3362    {
3363      Int iFirDispCand = -1;
3364      if (xGetPosFirstAvailDmvCand(iCount, pcMvFieldNeighbours, ivCandDir, iPosIvDC, vspFlag, iFirDispCand))
3365      {
3366        TComMv cMv;
3367        cMv = pcMvFieldNeighbours[(iFirDispCand<<1)].getMv();
3368        cMv.setHor(cMv.getHor()+4);
3369        if(m_pcSlice->getVPS()->getViewSynthesisPredFlag(m_pcSlice->getLayerIdInVps()))
3370        {
3371          cMv.setVer(0);
3372        }
3373        clipMv( cMv );
3374
3375        rightShiftMergeCandList( pcMvFieldNeighbours, puhInterDirNeighbours, vspFlag, inheritedVSPDisInfo, iCount, (5-iCount), iCount3DV);
3376
3377        abCandIsInter        [ iCount ] = true;
3378        puhInterDirNeighbours[ iCount ] = puhInterDirNeighbours[iFirDispCand];
3379        pcMvFieldNeighbours  [ iCount << 1      ].setMvField(cMv, pcMvFieldNeighbours[( iFirDispCand << 1)].getRefIdx() );
3380        pcMvFieldNeighbours  [(iCount << 1) + 1 ].setMvField(pcMvFieldNeighbours[(iFirDispCand << 1) + 1].getMv(), pcMvFieldNeighbours[( iFirDispCand << 1) + 1].getRefIdx() );
3381       
3382        if( mrgCandIdx == iCount ) 
3383        {
3384          return true;
3385        }
3386
3387        iCount++;
3388        break;
3389      }
3390    }
3391
3392    /// iLoop = 0 --> IvMCShift
3393    /// iLoop = 1 --> IvDCShift  (Derived from IvDC)
3394    if(ivCandDir[iLoop + 2])
3395    {
3396      TComMvField tmpMV[2];
3397      UChar tmpDir = ivCandDir[iLoop + 2];
3398      if( ( ivCandDir[iLoop + 2] & 1 ) == 1 )
3399      {
3400        tmpMV[0].setMvField( ivCandMv[ (iLoop<<1) + 4 ], ivCandRefIdx[ (iLoop<<1) + 4 ] ); 
3401      }
3402      if( ( ivCandDir[iLoop + 2] & 2 ) == 2 )
3403      {
3404        tmpMV[1].setMvField( ivCandMv[ (iLoop<<1) + 5 ], ivCandRefIdx[ (iLoop<<1) + 5 ] );
3405      }
3406     
3407      // Prune IvMC vs. IvMcShift
3408      Bool bRemove = false;     
3409      if( !iLoop && ivCandDir[0] > 0)
3410      {
3411        if(tmpDir == puhInterDirNeighbours[0] && pcMvFieldNeighbours[0]==tmpMV[0] && pcMvFieldNeighbours[1]==tmpMV[1])
3412        {
3413            bRemove                         = true;
3414        }
3415      }
3416      if(!bRemove)
3417      {
3418        rightShiftMergeCandList( pcMvFieldNeighbours, puhInterDirNeighbours, vspFlag, inheritedVSPDisInfo, iCount, (5-iCount), iCount3DV);
3419
3420        abCandIsInter[ iCount ] = true;
3421        puhInterDirNeighbours[ iCount ] = ivCandDir[iLoop + 2];
3422        if( ( ivCandDir[iLoop + 2] & 1 ) == 1 )
3423        {
3424          pcMvFieldNeighbours[ iCount<<1 ].setMvField( ivCandMv[ (iLoop<<1) + 4 ], ivCandRefIdx[ (iLoop<<1) + 4 ] ); 
3425        }
3426        if( ( ivCandDir[iLoop + 2] & 2 ) == 2 )
3427        {
3428          pcMvFieldNeighbours[ (iCount<<1)+1 ].setMvField( ivCandMv[ (iLoop<<1) + 5 ], ivCandRefIdx[ (iLoop<<1) + 5 ] );
3429        }
3430#if H_3D_NBDV
3431        if(iLoop) // For IvMcShift candidate
3432        {
3433          pcMvFieldNeighbours[iCount<<1    ].getMv().setIDVFlag (false);
3434          pcMvFieldNeighbours[(iCount<<1)+1].getMv().setIDVFlag (false);
3435        }
3436#endif
3437        if( mrgCandIdx == iCount )
3438        {
3439          return true;
3440        }
3441        iCount++;
3442      }
3443      break;
3444    }
3445  }
3446  return false;
3447} 
3448
3449inline Bool TComDataCU::xGetPosFirstAvailDmvCand( Int iCount, TComMvField* pcMvFieldNeighbours, Int* ivCandDir, Int posIvDC, Int* vspFlag, Int& posFirstAvailDmvCand )
3450{
3451  // ivCandDir[0] == true --> IvMC is available and excluded in loop over merge list.
3452  for ( Int currListPos = (ivCandDir[0] ? 1 : 0); currListPos < iCount; currListPos++ )
3453  {
3454    if ( ( currListPos == posIvDC ) || ( vspFlag[ currListPos ] == 1 ) )
3455    {
3456      continue;
3457    }
3458    else if((pcMvFieldNeighbours[currListPos<<1].getRefIdx() != -1 ) && (getSlice()->getViewIndex() != getSlice()->getRefPic(RefPicList(0), pcMvFieldNeighbours[currListPos<<1].getRefIdx())->getViewIndex()))
3459    {
3460      posFirstAvailDmvCand = currListPos;
3461      return true;
3462    }
3463  }
3464 return false; 
3465}
3466                                     
3467#endif
3468
3469#if H_3D
3470Void TComDataCU::rightShiftMergeCandList( TComMvField* pcMvFieldNeighbours, UChar* puhInterDirNeighbours, Int* iVSPIndexTrue, InheritedVSPDisInfo*  inheritedVSPDisInfo, UInt start, UInt num, Int &iCount3DV)
3471{
3472  iCount3DV++;
3473  for (int i=num; i>0; i--)
3474  {
3475    pcMvFieldNeighbours[(start+i)<<1].setMvField(pcMvFieldNeighbours[(start+i-1)<<1].getMv(), pcMvFieldNeighbours[(start+i-1)<<1].getRefIdx());
3476    pcMvFieldNeighbours[((start+i)<<1)+1].setMvField(pcMvFieldNeighbours[((start+i-1)<<1)+1].getMv(), pcMvFieldNeighbours[((start+i-1)<<1)+1].getRefIdx());
3477    puhInterDirNeighbours[start+i] = puhInterDirNeighbours[start+i-1];
3478    iVSPIndexTrue[start+i] = iVSPIndexTrue[start+i-1];
3479    inheritedVSPDisInfo[start+i].m_acDvInfo   = inheritedVSPDisInfo[start+i-1].m_acDvInfo;
3480  }
3481  TComMv  cZeroMv;
3482  pcMvFieldNeighbours[start<<1].setMvField( cZeroMv, NOT_VALID );
3483  pcMvFieldNeighbours[(start<<1)+1].setMvField( cZeroMv, NOT_VALID );
3484  puhInterDirNeighbours[start] = 0;
3485  iVSPIndexTrue[start] = 0;
3486  inheritedVSPDisInfo[start].m_acDvInfo = m_cDefaultDisInfo;
3487
3488  return;
3489}
3490
3491/** Constructs a list of merging candidates
3492 * \param uiAbsPartIdx
3493 * \param uiPUIdx
3494 * \param uiDepth
3495 * \param pcMvFieldNeighbours
3496 * \param puhInterDirNeighbours
3497 * \param numValidMergeCand
3498 */
3499// HM 12.0 based merge candidate list construction
3500
3501Void TComDataCU::getInterMergeCandidates( UInt uiAbsPartIdx, UInt uiPUIdx, TComMvField* pcMvFieldNeighbours, UChar* puhInterDirNeighbours, Int& numValidMergeCand, Int mrgCandIdx )
3502{
3503
3504  UInt uiAbsPartAddr = m_uiAbsIdxInLCU + uiAbsPartIdx;
3505  Bool abCandIsInter[ MRG_MAX_NUM_CANDS_MEM ];
3506  TComMv cZeroMv;
3507  for( UInt ui = 0; ui < getSlice()->getMaxNumMergeCand(); ++ui )
3508  {
3509    abCandIsInter[ui] = false;
3510    pcMvFieldNeighbours[ ( ui << 1 )     ].setMvField(cZeroMv, NOT_VALID);
3511    pcMvFieldNeighbours[ ( ui << 1 ) + 1 ].setMvField(cZeroMv, NOT_VALID);
3512  }
3513  numValidMergeCand = getSlice()->getMaxNumMergeCand();
3514  // compute the location of the current PU
3515  Int xP, yP, nPSW, nPSH;
3516  this->getPartPosition(uiPUIdx, xP, yP, nPSW, nPSH);
3517
3518  Int iCount = 0;
3519
3520  UInt uiPartIdxLT, uiPartIdxRT, uiPartIdxLB;
3521  PartSize cCurPS = getPartitionSize( uiAbsPartIdx );
3522  deriveLeftRightTopIdxGeneral( uiAbsPartIdx, uiPUIdx, uiPartIdxLT, uiPartIdxRT );
3523  deriveLeftBottomIdxGeneral  ( uiAbsPartIdx, uiPUIdx, uiPartIdxLB );
3524
3525  //left
3526  UInt uiLeftPartIdx = 0;
3527  TComDataCU* pcCULeft = 0;
3528  pcCULeft = getPULeft( uiLeftPartIdx, uiPartIdxLB );
3529  Bool isAvailableA1 = pcCULeft &&
3530    pcCULeft->isDiffMER(xP -1, yP+nPSH-1, xP, yP) &&
3531    !( uiPUIdx == 1 && (cCurPS == SIZE_Nx2N || cCurPS == SIZE_nLx2N || cCurPS == SIZE_nRx2N) ) &&
3532    !pcCULeft->isIntra( uiLeftPartIdx ) ;
3533  if ( isAvailableA1 )
3534  {
3535    m_bAvailableFlagA1 = 1;
3536    abCandIsInter[iCount] = true;
3537    // get Inter Dir
3538    puhInterDirNeighbours[iCount] = pcCULeft->getInterDir( uiLeftPartIdx );
3539    // get Mv from Left
3540    pcCULeft->getMvField( pcCULeft, uiLeftPartIdx, REF_PIC_LIST_0, pcMvFieldNeighbours[iCount<<1] );
3541    if ( getSlice()->isInterB() )
3542    {
3543      pcCULeft->getMvField( pcCULeft, uiLeftPartIdx, REF_PIC_LIST_1, pcMvFieldNeighbours[(iCount<<1)+1] );
3544    }
3545
3546    iCount ++;
3547  }
3548 
3549  // early termination
3550  if (iCount == getSlice()->getMaxNumMergeCand()) 
3551  {
3552    return;
3553  }
3554  // above
3555  UInt uiAbovePartIdx = 0;
3556  TComDataCU* pcCUAbove = 0;
3557  pcCUAbove = getPUAbove( uiAbovePartIdx, uiPartIdxRT );
3558  Bool isAvailableB1 = pcCUAbove &&
3559  pcCUAbove->isDiffMER(xP+nPSW-1, yP-1, xP, yP) &&
3560  !( uiPUIdx == 1 && (cCurPS == SIZE_2NxN || cCurPS == SIZE_2NxnU || cCurPS == SIZE_2NxnD) ) &&
3561  !pcCUAbove->isIntra( uiAbovePartIdx );
3562  if ( isAvailableB1 && (!isAvailableA1 || !pcCULeft->hasEqualMotion( uiLeftPartIdx, pcCUAbove, uiAbovePartIdx ) ) )
3563  {
3564    m_bAvailableFlagB1 = 1;
3565    abCandIsInter[iCount] = true;
3566    // get Inter Dir
3567    puhInterDirNeighbours[iCount] = pcCUAbove->getInterDir( uiAbovePartIdx );
3568    // get Mv from Left
3569    pcCUAbove->getMvField( pcCUAbove, uiAbovePartIdx, REF_PIC_LIST_0, pcMvFieldNeighbours[iCount<<1] );
3570    if ( getSlice()->isInterB() )
3571    {
3572      pcCUAbove->getMvField( pcCUAbove, uiAbovePartIdx, REF_PIC_LIST_1, pcMvFieldNeighbours[(iCount<<1)+1] );
3573    }
3574    if ( mrgCandIdx == iCount )
3575    {
3576      return;
3577    }
3578    iCount ++;
3579  }
3580  // early termination
3581  if (iCount == getSlice()->getMaxNumMergeCand()) 
3582  {
3583    return;
3584  }
3585
3586  // above right
3587  UInt uiAboveRightPartIdx = 0;
3588  TComDataCU* pcCUAboveRight = 0;
3589  pcCUAboveRight = getPUAboveRight( uiAboveRightPartIdx, uiPartIdxRT );
3590  Bool isAvailableB0 = pcCUAboveRight &&
3591  pcCUAboveRight->isDiffMER(xP+nPSW, yP-1, xP, yP) &&
3592  !pcCUAboveRight->isIntra( uiAboveRightPartIdx );
3593  if ( isAvailableB0 && ( !isAvailableB1 || !pcCUAbove->hasEqualMotion( uiAbovePartIdx, pcCUAboveRight, uiAboveRightPartIdx ) ) )
3594  {
3595    m_bAvailableFlagB0 = 1;
3596    abCandIsInter[iCount] = true;
3597    // get Inter Dir
3598    puhInterDirNeighbours[iCount] = pcCUAboveRight->getInterDir( uiAboveRightPartIdx );
3599    // get Mv from Left
3600    pcCUAboveRight->getMvField( pcCUAboveRight, uiAboveRightPartIdx, REF_PIC_LIST_0, pcMvFieldNeighbours[iCount<<1] );
3601    if ( getSlice()->isInterB() )
3602    {
3603      pcCUAboveRight->getMvField( pcCUAboveRight, uiAboveRightPartIdx, REF_PIC_LIST_1, pcMvFieldNeighbours[(iCount<<1)+1] );
3604    }
3605    if ( mrgCandIdx == iCount )
3606    {
3607      return;
3608    }
3609    iCount ++;
3610  }
3611  // early termination
3612  if (iCount == getSlice()->getMaxNumMergeCand()) 
3613  {
3614    return;
3615  }
3616
3617  //left bottom
3618  UInt uiLeftBottomPartIdx = 0;
3619  TComDataCU* pcCULeftBottom = 0;
3620  pcCULeftBottom = this->getPUBelowLeft( uiLeftBottomPartIdx, uiPartIdxLB );
3621  Bool isAvailableA0 = pcCULeftBottom &&
3622  pcCULeftBottom->isDiffMER(xP-1, yP+nPSH, xP, yP) &&
3623  !pcCULeftBottom->isIntra( uiLeftBottomPartIdx ) ;
3624  if ( isAvailableA0 && ( !isAvailableA1 || !pcCULeft->hasEqualMotion( uiLeftPartIdx, pcCULeftBottom, uiLeftBottomPartIdx ) ) )
3625  {
3626    m_bAvailableFlagA0 = 1;
3627    abCandIsInter[iCount] = true;
3628    // get Inter Dir
3629    puhInterDirNeighbours[iCount] = pcCULeftBottom->getInterDir( uiLeftBottomPartIdx );
3630    // get Mv from Left
3631    pcCULeftBottom->getMvField( pcCULeftBottom, uiLeftBottomPartIdx, REF_PIC_LIST_0, pcMvFieldNeighbours[iCount<<1] );
3632    if ( getSlice()->isInterB() )
3633    {
3634      pcCULeftBottom->getMvField( pcCULeftBottom, uiLeftBottomPartIdx, REF_PIC_LIST_1, pcMvFieldNeighbours[(iCount<<1)+1] );
3635    }
3636    if ( mrgCandIdx == iCount )
3637    {
3638      return;
3639    }
3640    iCount ++;
3641  }
3642  // early termination
3643  if (iCount == getSlice()->getMaxNumMergeCand()) 
3644  {
3645    return;
3646  }
3647  // above left
3648  if( iCount < 4 )
3649  {
3650    UInt uiAboveLeftPartIdx = 0;
3651    TComDataCU* pcCUAboveLeft = 0;
3652    pcCUAboveLeft = getPUAboveLeft( uiAboveLeftPartIdx, uiAbsPartAddr );
3653    Bool isAvailableB2 = pcCUAboveLeft &&
3654    pcCUAboveLeft->isDiffMER(xP-1, yP-1, xP, yP) &&
3655    !pcCUAboveLeft->isIntra( uiAboveLeftPartIdx );
3656    if ( isAvailableB2 && ( !isAvailableA1 || !pcCULeft->hasEqualMotion( uiLeftPartIdx, pcCUAboveLeft, uiAboveLeftPartIdx ) )
3657        && ( !isAvailableB1 || !pcCUAbove->hasEqualMotion( uiAbovePartIdx, pcCUAboveLeft, uiAboveLeftPartIdx ) ) )
3658    {
3659      m_bAvailableFlagB2 = 1;
3660      abCandIsInter[iCount] = true;
3661      // get Inter Dir
3662      puhInterDirNeighbours[iCount] = pcCUAboveLeft->getInterDir( uiAboveLeftPartIdx );
3663      // get Mv from Left
3664      pcCUAboveLeft->getMvField( pcCUAboveLeft, uiAboveLeftPartIdx, REF_PIC_LIST_0, pcMvFieldNeighbours[iCount<<1] );
3665      if ( getSlice()->isInterB() )
3666      {
3667        pcCUAboveLeft->getMvField( pcCUAboveLeft, uiAboveLeftPartIdx, REF_PIC_LIST_1, pcMvFieldNeighbours[(iCount<<1)+1] );
3668      }
3669      if ( mrgCandIdx == iCount )
3670      {
3671        return;
3672      }
3673      iCount ++;
3674    }
3675  }
3676  // early termination
3677  if (iCount == getSlice()->getMaxNumMergeCand()) 
3678  {
3679    return;
3680  }
3681  if ( getSlice()->getEnableTMVPFlag())
3682  {
3683    //>> MTK colocated-RightBottom
3684    UInt uiPartIdxRB;
3685
3686    deriveRightBottomIdx( uiPUIdx, uiPartIdxRB ); 
3687
3688    UInt uiAbsPartIdxTmp = g_auiZscanToRaster[uiPartIdxRB];
3689    UInt uiNumPartInCUWidth = m_pcPic->getNumPartInWidth();
3690
3691    TComMv cColMv;
3692    Int iRefIdx;
3693    Int uiLCUIdx = -1;
3694
3695    if      ( ( m_pcPic->getCU(m_uiCUAddr)->getCUPelX() + g_auiRasterToPelX[uiAbsPartIdxTmp] + m_pcPic->getMinCUWidth() ) >= m_pcSlice->getSPS()->getPicWidthInLumaSamples() )  // image boundary check
3696    {
3697    }
3698    else if ( ( m_pcPic->getCU(m_uiCUAddr)->getCUPelY() + g_auiRasterToPelY[uiAbsPartIdxTmp] + m_pcPic->getMinCUHeight() ) >= m_pcSlice->getSPS()->getPicHeightInLumaSamples() )
3699    {
3700    }
3701    else
3702    {
3703      if ( ( uiAbsPartIdxTmp % uiNumPartInCUWidth < uiNumPartInCUWidth - 1 ) &&           // is not at the last column of LCU
3704        ( uiAbsPartIdxTmp / uiNumPartInCUWidth < m_pcPic->getNumPartInHeight() - 1 ) ) // is not at the last row    of LCU
3705      {
3706        uiAbsPartAddr = g_auiRasterToZscan[ uiAbsPartIdxTmp + uiNumPartInCUWidth + 1 ];
3707        uiLCUIdx = getAddr();
3708      }
3709      else if ( uiAbsPartIdxTmp % uiNumPartInCUWidth < uiNumPartInCUWidth - 1 )           // is not at the last column of LCU But is last row of LCU
3710      {
3711        uiAbsPartAddr = g_auiRasterToZscan[ (uiAbsPartIdxTmp + uiNumPartInCUWidth + 1) % m_pcPic->getNumPartInCU() ];
3712      }
3713      else if ( uiAbsPartIdxTmp / uiNumPartInCUWidth < m_pcPic->getNumPartInHeight() - 1 ) // is not at the last row of LCU But is last column of LCU
3714      {
3715        uiAbsPartAddr = g_auiRasterToZscan[ uiAbsPartIdxTmp + 1 ];
3716        uiLCUIdx = getAddr() + 1;
3717      }
3718      else //is the right bottom corner of LCU                       
3719      {
3720        uiAbsPartAddr = 0;
3721      }
3722    }
3723
3724    iRefIdx = 0;
3725    Bool bExistMV = false;
3726    UInt uiPartIdxCenter;
3727    UInt uiCurLCUIdx = getAddr();
3728    Int dir = 0;
3729    UInt uiArrayAddr = iCount;
3730    xDeriveCenterIdx( uiPUIdx, uiPartIdxCenter );
3731    bExistMV = uiLCUIdx >= 0 && xGetColMVP( REF_PIC_LIST_0, uiLCUIdx, uiAbsPartAddr, cColMv, iRefIdx );
3732    if( bExistMV == false )
3733    {
3734      bExistMV = xGetColMVP( REF_PIC_LIST_0, uiCurLCUIdx, uiPartIdxCenter, cColMv, iRefIdx );
3735    }
3736    if( bExistMV )
3737    {
3738      dir |= 1;
3739      pcMvFieldNeighbours[ 2 * uiArrayAddr ].setMvField( cColMv, iRefIdx );
3740    }
3741
3742    if ( getSlice()->isInterB() )
3743    {
3744#if H_3D_TMVP
3745      iRefIdx = 0;
3746#endif
3747      bExistMV = uiLCUIdx >= 0 && xGetColMVP( REF_PIC_LIST_1, uiLCUIdx, uiAbsPartAddr, cColMv, iRefIdx);
3748      if( bExistMV == false )
3749      {
3750        bExistMV = xGetColMVP( REF_PIC_LIST_1, uiCurLCUIdx, uiPartIdxCenter, cColMv, iRefIdx );
3751      }
3752      if( bExistMV )
3753      {
3754        dir |= 2;
3755        pcMvFieldNeighbours[ 2 * uiArrayAddr + 1 ].setMvField( cColMv, iRefIdx );
3756      }
3757    }
3758
3759    if (dir != 0)
3760    {
3761      puhInterDirNeighbours[uiArrayAddr] = dir;
3762      abCandIsInter[uiArrayAddr] = true;
3763#if H_3D_NBDV
3764      pcMvFieldNeighbours[iCount<<1    ].getMv().setIDVFlag (false);
3765      pcMvFieldNeighbours[(iCount<<1)+1].getMv().setIDVFlag (false);
3766#endif
3767      if ( mrgCandIdx == iCount )
3768      {
3769        return;
3770      }
3771      iCount++;
3772    }
3773  }
3774  // early termination
3775  if (iCount == getSlice()->getMaxNumMergeCand()) 
3776  {
3777    return;
3778  }
3779  UInt uiArrayAddr = iCount;
3780  UInt uiCutoff = uiArrayAddr;
3781 
3782  if ( getSlice()->isInterB() && iCount<5)  // JCT3V-F0129 by Qualcomm
3783  {
3784    UInt uiPriorityList0[12] = {0 , 1, 0, 2, 1, 2, 0, 3, 1, 3, 2, 3};
3785    UInt uiPriorityList1[12] = {1 , 0, 2, 0, 2, 1, 3, 0, 3, 1, 3, 2};
3786
3787    for (Int idx=0; idx<uiCutoff*(uiCutoff-1) && uiArrayAddr!= getSlice()->getMaxNumMergeCand(); idx++)
3788    {
3789      Int i = uiPriorityList0[idx]; Int j = uiPriorityList1[idx];
3790      if (abCandIsInter[i] && abCandIsInter[j]&& (puhInterDirNeighbours[i]&0x1)&&(puhInterDirNeighbours[j]&0x2))
3791      {
3792        abCandIsInter[uiArrayAddr] = true;
3793        puhInterDirNeighbours[uiArrayAddr] = 3;
3794
3795        // get Mv from cand[i] and cand[j]
3796        pcMvFieldNeighbours[uiArrayAddr << 1].setMvField(pcMvFieldNeighbours[i<<1].getMv(), pcMvFieldNeighbours[i<<1].getRefIdx());
3797        pcMvFieldNeighbours[( uiArrayAddr << 1 ) + 1].setMvField(pcMvFieldNeighbours[(j<<1)+1].getMv(), pcMvFieldNeighbours[(j<<1)+1].getRefIdx());
3798
3799        Int iRefPOCL0 = m_pcSlice->getRefPOC( REF_PIC_LIST_0, pcMvFieldNeighbours[(uiArrayAddr<<1)].getRefIdx() );
3800        Int iRefPOCL1 = m_pcSlice->getRefPOC( REF_PIC_LIST_1, pcMvFieldNeighbours[(uiArrayAddr<<1)+1].getRefIdx() );
3801        if (iRefPOCL0 == iRefPOCL1 && pcMvFieldNeighbours[(uiArrayAddr<<1)].getMv() == pcMvFieldNeighbours[(uiArrayAddr<<1)+1].getMv())
3802        {
3803          abCandIsInter[uiArrayAddr] = false;
3804        }
3805        else
3806        {
3807          uiArrayAddr++;
3808        }
3809      }
3810    }
3811  }
3812  // early termination
3813  if (uiArrayAddr == getSlice()->getMaxNumMergeCand()) 
3814  {
3815    return;
3816  }
3817 
3818  Int iNumRefIdx = (getSlice()->isInterB()) ? min(m_pcSlice->getNumRefIdx(REF_PIC_LIST_0), m_pcSlice->getNumRefIdx(REF_PIC_LIST_1)) : m_pcSlice->getNumRefIdx(REF_PIC_LIST_0);
3819  Int r = 0;
3820  Int refcnt = 0;
3821  while (uiArrayAddr < getSlice()->getMaxNumMergeCand())
3822  {
3823    abCandIsInter[uiArrayAddr] = true;
3824    puhInterDirNeighbours[uiArrayAddr] = 1;
3825    pcMvFieldNeighbours[uiArrayAddr << 1].setMvField( TComMv(0, 0), r);
3826
3827    if ( getSlice()->isInterB() )
3828    {
3829      puhInterDirNeighbours[uiArrayAddr] = 3;
3830      pcMvFieldNeighbours[(uiArrayAddr << 1) + 1].setMvField(TComMv(0, 0), r);
3831    }
3832    uiArrayAddr++;
3833    if ( refcnt == iNumRefIdx - 1 )
3834    {
3835      r = 0;
3836    }
3837    else
3838    {
3839      ++r;
3840      ++refcnt;
3841    }
3842  }
3843 
3844  numValidMergeCand = uiArrayAddr;
3845}
3846
3847
3848
3849/** Constructs a list of merging candidates
3850 * \param uiAbsPartIdx
3851 * \param uiPUIdx
3852 * \param uiDepth
3853 * \param pcMvFieldNeighbours
3854 * \param puhInterDirNeighbours
3855 * \param numValidMergeCand
3856 */
3857#if H_3D
3858Void TComDataCU::xGetInterMergeCandidates( UInt uiAbsPartIdx, UInt uiPUIdx, TComMvField* pcMvFieldNeighbours, UChar* puhInterDirNeighbours
3859#else
3860Void TComDataCU::getInterMergeCandidates( UInt uiAbsPartIdx, UInt uiPUIdx, TComMvField* pcMvFieldNeighbours, UChar* puhInterDirNeighbours
3861#endif
3862#if H_3D_VSP
3863      , Int* vspFlag
3864      , InheritedVSPDisInfo*  inheritedVSPDisInfo
3865#endif
3866#if H_3D_SPIVMP
3867      , Bool* pbSPIVMPFlag, TComMvField* pcMvFieldSP, UChar* puhInterDirSP
3868#endif
3869      , Int& numValidMergeCand, Int mrgCandIdx
3870)
3871{
3872  UInt uiAbsPartAddr = m_uiAbsIdxInLCU + uiAbsPartIdx;
3873#if H_3D_IV_MERGE
3874  ////////////////////////////
3875  //////// INIT LISTS ////////
3876  ////////////////////////////
3877  TComMv cZeroMv;
3878  Bool abCandIsInter[ MRG_MAX_NUM_CANDS_MEM ];
3879#else
3880  Bool abCandIsInter[ MRG_MAX_NUM_CANDS ];
3881#endif
3882#if H_3D
3883  TComMvField tmpMV[2];
3884  UChar tmpDir;
3885
3886  //////////////////////////////////
3887  //////// GET DISPARITIES  ////////
3888  //////////////////////////////////
3889  DisInfo cDisInfo = getDvInfo(uiAbsPartIdx);
3890  for(Int i = 0; i < MRG_MAX_NUM_CANDS_MEM; i++)
3891  {
3892    inheritedVSPDisInfo[i].m_acDvInfo = cDisInfo;   // To prevent run-time error, this code must be executed always for merging process.
3893  }
3894  m_cDefaultDisInfo = cDisInfo;
3895
3896  if (!( getSlice()->getIsDepth() || getSlice()->getViewIndex()>0))  // current slice is not both dependent view or depth
3897  {
3898    return;
3899  }
3900#else
3901  for( UInt ui = 0; ui < getSlice()->getMaxNumMergeCand(); ++ui )
3902  {
3903    abCandIsInter[ui] = false;
3904    pcMvFieldNeighbours[ ( ui << 1 )     ].setRefIdx(NOT_VALID);
3905    pcMvFieldNeighbours[ ( ui << 1 ) + 1 ].setRefIdx(NOT_VALID);
3906  }
3907#endif
3908
3909  numValidMergeCand = getSlice()->getMaxNumMergeCand();
3910#if H_3D
3911  //////////////////////////////////
3912  //////// DERIVE LOCATIONS ////////
3913  //////////////////////////////////
3914#endif
3915  // compute the location of the current PU
3916  Int xP, yP, nPSW, nPSH;
3917  this->getPartPosition(uiPUIdx, xP, yP, nPSW, nPSH);
3918
3919  Int iCount = 0;
3920
3921  UInt uiPartIdxLT, uiPartIdxRT, uiPartIdxLB;
3922#if !H_3D
3923  PartSize cCurPS = getPartitionSize( uiAbsPartIdx );
3924#endif
3925  deriveLeftRightTopIdxGeneral( uiAbsPartIdx, uiPUIdx, uiPartIdxLT, uiPartIdxRT );
3926  deriveLeftBottomIdxGeneral  ( uiAbsPartIdx, uiPUIdx, uiPartIdxLB );
3927#if H_3D
3928  Bool bMPIFlag   = getSlice()->getVPS()->getMPIFlag( getSlice()->getLayerIdInVps() );
3929  Bool bIsDepth = getSlice()->getIsDepth();
3930#endif
3931
3932#if H_3D_IC
3933  Bool bICFlag = getICFlag(uiAbsPartIdx);
3934#endif
3935#if H_3D_ARP
3936  Bool bARPFlag = getARPW(uiAbsPartIdx)>0 ? true : false;
3937#endif
3938
3939#if H_3D
3940  Int  iPosLeftAbove[2] = {-1, -1};
3941
3942  Int iCountHEVC = 0;
3943  Int iCount3DV = 0;
3944  Int numA1B1B0 = 0;
3945  Int numA0B2 = 0;
3946
3947#if H_3D_NBDV
3948  for(Int i = 0; i < MRG_MAX_NUM_CANDS_MEM; i++) 
3949  {
3950    pcMvFieldNeighbours[i<<1    ].getMv().setIDVFlag (false);
3951    pcMvFieldNeighbours[(i<<1)+1].getMv().setIDVFlag (false);
3952  }
3953#endif
3954
3955  //left
3956  UInt uiLeftPartIdx = 0;
3957  TComDataCU* pcCULeft = 0;
3958  pcCULeft = getPULeft( uiLeftPartIdx, uiPartIdxLB ); 
3959  if (getAvailableFlagA1())
3960  {
3961    iPosLeftAbove[0] = numA1B1B0;
3962#if H_3D_VSP
3963    if (pcCULeft->getVSPFlag(uiLeftPartIdx) == 1
3964#if H_3D_IC
3965      && !bICFlag
3966#endif
3967#if H_3D_ARP
3968      && !bARPFlag
3969#endif
3970      )
3971    {
3972      vspFlag[numA1B1B0] = 1;
3973    }
3974#endif
3975    numA1B1B0++;
3976  }
3977
3978  // above
3979  UInt uiAbovePartIdx = 0;
3980  TComDataCU* pcCUAbove = 0;
3981  pcCUAbove = getPUAbove( uiAbovePartIdx, uiPartIdxRT );
3982  if ( getAvailableFlagB1())
3983  {
3984    iPosLeftAbove[1] = numA1B1B0;
3985#if H_3D_VSP
3986    if ( ( ( getAddr() - pcCUAbove->getAddr() ) == 0) && (pcCUAbove->getVSPFlag(uiAbovePartIdx) == 1) 
3987#if H_3D_IC
3988      && !bICFlag
3989#endif
3990#if H_3D_ARP
3991      && !bARPFlag
3992#endif
3993      )
3994    {
3995      vspFlag[numA1B1B0] = 1;
3996    }
3997#endif
3998
3999    numA1B1B0++;
4000  }
4001
4002  // above right
4003  UInt uiAboveRightPartIdx = 0;
4004  TComDataCU* pcCUAboveRight = 0;
4005  pcCUAboveRight = getPUAboveRight( uiAboveRightPartIdx, uiPartIdxRT );
4006  if ( getAvailableFlagB0())
4007  {
4008#if H_3D_VSP
4009    if ( ( ( getAddr() - pcCUAboveRight->getAddr() ) == 0) && (pcCUAboveRight->getVSPFlag(uiAboveRightPartIdx) == 1) 
4010#if H_3D_IC
4011      && !bICFlag
4012#endif
4013#if H_3D_ARP
4014      && !bARPFlag
4015#endif
4016      )
4017    {
4018      vspFlag[numA1B1B0] = 1;
4019    }
4020#endif
4021    numA1B1B0++;
4022  }
4023 
4024  // left bottom
4025  UInt uiLeftBottomPartIdx = 0;
4026  TComDataCU* pcCULeftBottom = getPUBelowLeft( uiLeftBottomPartIdx, uiPartIdxLB );
4027  if ( getAvailableFlagA0())
4028  {
4029#if H_3D_VSP
4030    if (pcCULeftBottom->getVSPFlag(uiLeftBottomPartIdx) == 1
4031#if H_3D_IC
4032      && !bICFlag
4033#endif
4034#if H_3D_ARP
4035      && !bARPFlag
4036#endif
4037      )
4038    {
4039      vspFlag[numA1B1B0] = 1;
4040    }
4041#endif
4042    iCountHEVC++;
4043    numA0B2++;
4044  }
4045 
4046  // above left
4047  UInt uiAboveLeftPartIdx = 0;
4048  TComDataCU* pcCUAboveLeft = 0;
4049  pcCUAboveLeft = getPUAboveLeft( uiAboveLeftPartIdx, uiAbsPartAddr );
4050  if (getAvailableFlagB2())
4051  {
4052#if H_3D_VSP
4053    if ( ( ( getAddr() - pcCUAboveLeft->getAddr() ) == 0) && (pcCUAboveLeft->getVSPFlag(uiAboveLeftPartIdx) == 1) 
4054#if H_3D_IC
4055      && !bICFlag
4056#endif
4057#if H_3D_ARP
4058      && !bARPFlag
4059#endif
4060      )
4061    {
4062      vspFlag[numA1B1B0+iCountHEVC] = 1;
4063    }
4064#endif
4065    iCountHEVC++;
4066    numA0B2++;
4067  }
4068
4069  iCountHEVC = numValidMergeCand;
4070#endif
4071
4072
4073#if H_3D_IV_MERGE
4074
4075  /////////////////////////////////////////////
4076  //////// TEXTURE MERGE CANDIDATE (T) ////////
4077  /////////////////////////////////////////////
4078
4079  if( bMPIFlag)
4080  {
4081    UInt uiPartIdxCenter;
4082    xDeriveCenterIdx( uiPUIdx, uiPartIdxCenter );   
4083    tmpMV[0].setMvField( cZeroMv, NOT_VALID );
4084    tmpMV[1].setMvField( cZeroMv, NOT_VALID );
4085    Int tRef[2]={-1, -1};
4086
4087#if H_3D_FCO
4088    TComPic * pcTexturePic = m_pcSlice->getTexturePic();
4089    TComDataCU *pcTextureCU = 0;
4090    if ( pcTexturePic )
4091      pcTextureCU = pcTexturePic->getCU( getAddr() );
4092#else
4093    TComDataCU *pcTextureCU = m_pcSlice->getTexturePic()->getCU( getAddr() );
4094#endif
4095
4096#if H_3D_FCO
4097    if ( pcTextureCU && pcTexturePic->getReconMark() && !pcTextureCU->isIntra( uiPartIdxCenter ) )
4098#else
4099    if ( pcTextureCU && !pcTextureCU->isIntra( uiPartIdxCenter ) )
4100#endif
4101    {
4102      pcTextureCU->getMvField( pcTextureCU, uiPartIdxCenter, REF_PIC_LIST_0, tmpMV[0] );
4103      tRef[0] = getPic()->isTextRefValid( REF_PIC_LIST_0, tmpMV[0].getRefIdx() );
4104      if( (tmpMV[0].getRefIdx()>=0) && ( tRef[0] >= 0 ) )
4105      {
4106        TComMv cMvPred = tmpMV[0].getMv();
4107        const TComMv cAdd( 1 << ( 2 - 1 ), 1 << ( 2 - 1 ) );
4108        cMvPred+=cAdd;
4109        cMvPred>>=2;
4110        clipMv(cMvPred);
4111        tmpMV[0].setMvField(cMvPred,tRef[0]);
4112      }
4113      if ( getSlice()->isInterB() )
4114      {
4115        pcTextureCU->getMvField( pcTextureCU, uiPartIdxCenter, REF_PIC_LIST_1, tmpMV[1] );
4116        tRef[1] = getPic()->isTextRefValid( REF_PIC_LIST_1, tmpMV[1].getRefIdx() );
4117        if( (tmpMV[1].getRefIdx()>=0) && ( tRef[1] >= 0) )
4118        {
4119          TComMv cMvPred = tmpMV[1].getMv();
4120          const TComMv cAdd( 1 << ( 2 - 1 ), 1 << ( 2 - 1 ) );
4121          cMvPred+=cAdd;
4122          cMvPred>>=2;
4123          clipMv(cMvPred);
4124          tmpMV[1].setMvField(cMvPred,tRef[1]);
4125        }
4126      }
4127
4128      tmpDir = 0;
4129      if( (tmpMV[0].getRefIdx()>=0) && ( tRef[0] >= 0 ) )
4130      {
4131        tmpDir += ((tmpMV[0].getRefIdx()>=0)?1:0);
4132      }
4133      if( (tmpMV[1].getRefIdx()>=0) && ( tRef[1] >= 0) )
4134      {
4135        tmpDir += ((tmpMV[1].getRefIdx()>=0)?2:0);
4136      }
4137
4138      if( tmpDir != 0 )
4139      {
4140        Int iCnloop = 0;
4141        Bool bRemoveSpa = false; //pruning
4142
4143        for(Int i = 0; i < 2; i ++)
4144        {
4145          iCnloop = iPosLeftAbove[i];
4146          if ( iCnloop == -1 ) 
4147          {
4148            continue;
4149          }
4150          if(tmpDir == puhInterDirNeighbours[iCnloop] && tmpMV[0]==pcMvFieldNeighbours[(iCnloop<<1)] && tmpMV[1]==pcMvFieldNeighbours[(iCnloop<<1)+1])
4151          {
4152            bRemoveSpa                      = true;
4153            break;
4154          }     
4155        }
4156
4157        if (!bRemoveSpa)
4158        {
4159          rightShiftMergeCandList( pcMvFieldNeighbours, puhInterDirNeighbours, vspFlag, inheritedVSPDisInfo, iCount, 5-iCount, iCount3DV);
4160        }
4161        else
4162        {
4163          rightShiftMergeCandList( pcMvFieldNeighbours, puhInterDirNeighbours, vspFlag, inheritedVSPDisInfo, iCount, (iCnloop-iCount), iCount3DV);
4164          if (iCnloop<numA1B1B0)
4165          {
4166            numA1B1B0--;
4167          }
4168          iCountHEVC--;
4169
4170          if (iPosLeftAbove[0] != -1)
4171          {
4172            if (iCnloop == iPosLeftAbove[0])
4173            {
4174              iPosLeftAbove[0] = -1;
4175            }
4176            else
4177            {
4178              iPosLeftAbove[0]++;
4179            }
4180          }
4181          if (iPosLeftAbove[1] != -1)
4182          {
4183            if (iCnloop == iPosLeftAbove[1])
4184            {
4185              iPosLeftAbove[1] = -1;
4186            }
4187            else
4188            {
4189              if (iCnloop > iPosLeftAbove[1])
4190              {
4191                iPosLeftAbove[1]++;
4192              }
4193            }
4194          }
4195        }
4196
4197        if( (tmpMV[0].getRefIdx()>=0) && ( tRef[0] >= 0 ) )
4198        {
4199          pcMvFieldNeighbours[iCount<<1].setMvField(tmpMV[0].getMv(), tRef[0]);
4200        }
4201        if ( getSlice()->isInterB())
4202        {
4203          if( (tmpMV[1].getRefIdx()>=0) && ( tRef[1] >= 0) )
4204          {
4205            pcMvFieldNeighbours[(iCount<<1)+1].setMvField(tmpMV[1].getMv(), tRef[1]);
4206          }
4207        }
4208        puhInterDirNeighbours[iCount] = tmpDir;
4209
4210        if ( mrgCandIdx == iCount )
4211        {
4212          return;
4213        }
4214        iCount ++;
4215      }
4216    }
4217  }
4218
4219  /////////////////////////////////////////////////////////////////
4220  //////// DERIVE IvMC, IvMCShift,IvDCShift, IvDC  Candidates /////
4221  /////////////////////////////////////////////////////////////////
4222
4223  Int  posIvDC          = -1;
4224
4225  // { IvMCL0, IvMCL1, IvDCL0, IvDCL1, IvMCL0Shift, IvMCL1Shift, IvDCL0Shift, IvDCL1Shift }; 
4226  // An enumerator would be appropriate here!
4227  TComMv ivCandMv    [8];
4228  Int    ivCandRefIdx[8] = {-1, -1, -1, -1, -1, -1, -1, -1};
4229
4230  // { IvMC, IvDC, IvMCShift, IvDCShift }; 
4231  Int    ivCandDir   [4] = {0, 0, 0, 0};
4232
4233  Bool ivMvPredFlag   = getSlice()->getVPS()->getIvMvPredFlag( getSlice()->getLayerIdInVps() );
4234
4235#if MTK_NBDV_IVREF_FIX_G0067
4236  if ( ivMvPredFlag && cDisInfo.m_aVIdxCan!=-1)
4237#else
4238  if ( ivMvPredFlag )
4239#endif
4240  {
4241    getInterViewMergeCands(uiPUIdx, ivCandRefIdx, ivCandMv, &cDisInfo, ivCandDir , bIsDepth, pcMvFieldSP, puhInterDirSP );
4242  } 
4243
4244  ///////////////////////////////////////////////
4245  //////// INTER VIEW MOTION COMP(IvMC) /////////
4246  ///////////////////////////////////////////////
4247
4248  if( ivCandDir[0] )
4249  {
4250    tmpMV[0].setMvField( cZeroMv, NOT_VALID );
4251    tmpMV[1].setMvField( cZeroMv, NOT_VALID );
4252
4253    if( ( ivCandDir[0] & 1 ) == 1 )
4254    {
4255      tmpMV[0].setMvField( ivCandMv[ 0 ], ivCandRefIdx[ 0 ] );
4256    }
4257    if( ( ivCandDir[0] & 2 ) == 2 )
4258    {
4259      tmpMV[1].setMvField( ivCandMv[ 1 ], ivCandRefIdx[ 1 ] );
4260    }
4261
4262    Bool bRemoveSpa = false; //pruning
4263    Bool bIvMC = false;
4264    Int iCnloop=0;
4265
4266    if (!bIsDepth)
4267    {
4268      for(Int i = 0; i < 2; i ++)
4269      {
4270        iCnloop = iPosLeftAbove[i];
4271        if ( iCnloop == -1 ) 
4272        {
4273          continue;
4274        }
4275        if(ivCandDir[0] == puhInterDirNeighbours[iCnloop] && tmpMV[0]==pcMvFieldNeighbours[(iCnloop<<1)] && tmpMV[1]==pcMvFieldNeighbours[(iCnloop<<1)+1])
4276        {
4277          bRemoveSpa                      = true;
4278          break;
4279        }     
4280      }
4281    }
4282    if (bIsDepth)
4283    {
4284      iCnloop = iCount-1;
4285      for(; iCnloop >= 0; iCnloop --)
4286      {
4287        if(ivCandDir[0] == puhInterDirNeighbours[iCnloop] && pcMvFieldNeighbours[iCnloop<<1]==tmpMV[0] && pcMvFieldNeighbours[(iCnloop<<1)+1]==tmpMV[1])  // F0125 compatible with F0093
4288        {
4289          bRemoveSpa                      = true;
4290          break;
4291        }
4292      }
4293    }
4294
4295    if (!bRemoveSpa)
4296    {
4297      bIvMC = true;
4298      rightShiftMergeCandList( pcMvFieldNeighbours, puhInterDirNeighbours, vspFlag, inheritedVSPDisInfo, iCount, (5-iCount), iCount3DV);
4299
4300      if (iPosLeftAbove[0] != -1)
4301      {
4302        iPosLeftAbove[0]++;
4303      }
4304      if (iPosLeftAbove[1] != -1)
4305      {
4306        iPosLeftAbove[1]++;
4307      }
4308    }
4309    else if (bRemoveSpa && !bIsDepth)
4310    {
4311      bIvMC = true;
4312      rightShiftMergeCandList( pcMvFieldNeighbours, puhInterDirNeighbours, vspFlag, inheritedVSPDisInfo, iCount, (iCnloop-iCount), iCount3DV);
4313
4314      if (iCnloop<numA1B1B0)
4315      {
4316        numA1B1B0--;
4317      }
4318      iCountHEVC--;
4319
4320      if (iPosLeftAbove[0] != -1)
4321      {
4322        if (iCnloop == iPosLeftAbove[0])
4323        {
4324          iPosLeftAbove[0] = -1;
4325        }
4326        else
4327        {
4328          iPosLeftAbove[0]++;
4329        }
4330      }
4331      if (iPosLeftAbove[1] != -1)
4332      {
4333        if (iCnloop == iPosLeftAbove[1])
4334        {
4335          iPosLeftAbove[1] = -1;
4336        }
4337        else
4338        {
4339          if (iCnloop > iPosLeftAbove[1])
4340          {
4341            iPosLeftAbove[1]++;
4342          }
4343        }
4344      }
4345    }
4346
4347    if (bIvMC)
4348    {
4349      pbSPIVMPFlag[iCount] = true;
4350      if( ( ivCandDir[0] & 1 ) == 1 )
4351      {
4352        pcMvFieldNeighbours[iCount<<1].setMvField( ivCandMv[ 0 ], ivCandRefIdx[ 0 ] );
4353      }
4354      if( ( ivCandDir[0] & 2 ) == 2 )
4355      {
4356        pcMvFieldNeighbours[(iCount<<1)+1].setMvField( ivCandMv[ 1 ], ivCandRefIdx[ 1 ] );
4357      }
4358
4359      puhInterDirNeighbours[ iCount ] = ivCandDir[0];
4360
4361      if ( mrgCandIdx == iCount )
4362      {
4363        return;
4364      }
4365      iCount ++;
4366    }
4367  } 
4368
4369  // early termination
4370  if (iCount == getSlice()->getMaxNumMergeCand()) 
4371  {
4372    return;
4373  }
4374#endif
4375
4376#if H_3D
4377  iCount += numA1B1B0;
4378#else
4379  //left
4380  UInt uiLeftPartIdx = 0;
4381  TComDataCU* pcCULeft = 0;
4382  pcCULeft = getPULeft( uiLeftPartIdx, uiPartIdxLB );
4383  Bool isAvailableA1 = pcCULeft &&
4384    pcCULeft->isDiffMER(xP -1, yP+nPSH-1, xP, yP) &&
4385    !( uiPUIdx == 1 && (cCurPS == SIZE_Nx2N || cCurPS == SIZE_nLx2N || cCurPS == SIZE_nRx2N) ) &&
4386    !pcCULeft->isIntra( uiLeftPartIdx ) ;
4387  if ( isAvailableA1 )
4388  {
4389    abCandIsInter[iCount] = true;
4390    // get Inter Dir
4391    puhInterDirNeighbours[iCount] = pcCULeft->getInterDir( uiLeftPartIdx );
4392    // get Mv from Left
4393    pcCULeft->getMvField( pcCULeft, uiLeftPartIdx, REF_PIC_LIST_0, pcMvFieldNeighbours[iCount<<1] );
4394    if ( getSlice()->isInterB() )
4395    {
4396      pcCULeft->getMvField( pcCULeft, uiLeftPartIdx, REF_PIC_LIST_1, pcMvFieldNeighbours[(iCount<<1)+1] );
4397    }
4398
4399    if ( mrgCandIdx == iCount )
4400    {
4401      return;
4402    }
4403    iCount ++;
4404  }
4405
4406  // early termination
4407  if (iCount == getSlice()->getMaxNumMergeCand()) 
4408  {
4409    return;
4410  }
4411
4412  // above
4413  UInt uiAbovePartIdx = 0;
4414  TComDataCU* pcCUAbove = 0;
4415  pcCUAbove = getPUAbove( uiAbovePartIdx, uiPartIdxRT );
4416  Bool isAvailableB1 = pcCUAbove &&
4417    pcCUAbove->isDiffMER(xP+nPSW-1, yP-1, xP, yP) &&
4418    !( uiPUIdx == 1 && (cCurPS == SIZE_2NxN || cCurPS == SIZE_2NxnU || cCurPS == SIZE_2NxnD) ) &&
4419    !pcCUAbove->isIntra( uiAbovePartIdx );
4420  if ( isAvailableB1 && (!isAvailableA1 || !pcCULeft->hasEqualMotion( uiLeftPartIdx, pcCUAbove, uiAbovePartIdx ) ) )
4421  {
4422    abCandIsInter[iCount] = true;
4423    // get Inter Dir
4424    puhInterDirNeighbours[iCount] = pcCUAbove->getInterDir( uiAbovePartIdx );
4425    // get Mv from Left
4426    pcCUAbove->getMvField( pcCUAbove, uiAbovePartIdx, REF_PIC_LIST_0, pcMvFieldNeighbours[iCount<<1] );
4427    if ( getSlice()->isInterB() )
4428    {
4429      pcCUAbove->getMvField( pcCUAbove, uiAbovePartIdx, REF_PIC_LIST_1, pcMvFieldNeighbours[(iCount<<1)+1] );
4430    }
4431
4432    if ( mrgCandIdx == iCount )
4433    {
4434      return;
4435    }
4436    iCount ++;
4437  }
4438  // early termination
4439  if (iCount == getSlice()->getMaxNumMergeCand()) 
4440  {
4441    return;
4442  }
4443
4444  // above right
4445  UInt uiAboveRightPartIdx = 0;
4446  TComDataCU* pcCUAboveRight = 0;
4447  pcCUAboveRight = getPUAboveRight( uiAboveRightPartIdx, uiPartIdxRT );
4448  Bool isAvailableB0 = pcCUAboveRight &&
4449    pcCUAboveRight->isDiffMER(xP+nPSW, yP-1, xP, yP) &&
4450    !pcCUAboveRight->isIntra( uiAboveRightPartIdx );
4451  if ( isAvailableB0 && ( !isAvailableB1 || !pcCUAbove->hasEqualMotion( uiAbovePartIdx, pcCUAboveRight, uiAboveRightPartIdx ) ) )
4452  {
4453    abCandIsInter[iCount] = true;
4454    // get Inter Dir
4455    puhInterDirNeighbours[iCount] = pcCUAboveRight->getInterDir( uiAboveRightPartIdx );
4456    // get Mv from Left
4457    pcCUAboveRight->getMvField( pcCUAboveRight, uiAboveRightPartIdx, REF_PIC_LIST_0, pcMvFieldNeighbours[iCount<<1] );
4458    if ( getSlice()->isInterB() )
4459    {
4460      pcCUAboveRight->getMvField( pcCUAboveRight, uiAboveRightPartIdx, REF_PIC_LIST_1, pcMvFieldNeighbours[(iCount<<1)+1] );
4461    }
4462
4463    if ( mrgCandIdx == iCount )
4464    {
4465      return;
4466    }
4467    iCount ++;
4468  }
4469  // early termination
4470  if (iCount == getSlice()->getMaxNumMergeCand()) 
4471  {
4472    return;
4473  }
4474#endif
4475
4476
4477#if H_3D_IV_MERGE
4478  /////////////////////////////////////////////
4479  //////// INTER VIEW DISP COMP (IvDC) ////////
4480  /////////////////////////////////////////////
4481
4482  if( ivCandDir[1] && iCount < getSlice()->getMaxNumMergeCand())
4483  {
4484    assert(iCount < getSlice()->getMaxNumMergeCand());
4485
4486    tmpMV[0].setMvField( cZeroMv, NOT_VALID );
4487    tmpMV[1].setMvField( cZeroMv, NOT_VALID );
4488    if( ( ivCandDir[1] & 1 ) == 1 )
4489    {
4490      tmpMV[0].setMvField( ivCandMv[ 2 ], ivCandRefIdx[ 2 ] );
4491    }
4492    if( ( ivCandDir[1] & 2 ) == 2 )
4493    {
4494      tmpMV[1].setMvField( ivCandMv[ 3 ], ivCandRefIdx[ 3 ] );
4495    }
4496
4497    Bool bRemoveSpa = false; //pruning to A1, B1
4498    for(Int i = 0; i < 2; i ++)
4499    {
4500      Int iCnloop = iPosLeftAbove[i];
4501      if ( iCnloop == -1 ) 
4502      {
4503        continue;
4504      }
4505      if(puhInterDirNeighbours[iCount] == puhInterDirNeighbours[iCnloop] && pcMvFieldNeighbours[iCnloop<<1]==pcMvFieldNeighbours[(iCount<<1)] && pcMvFieldNeighbours[(iCnloop<<1)+1]==pcMvFieldNeighbours[(iCount<<1)+1])
4506      {
4507        bRemoveSpa                      = true;
4508        break;
4509      }     
4510    }
4511    if(!bRemoveSpa)
4512    {
4513      rightShiftMergeCandList( pcMvFieldNeighbours, puhInterDirNeighbours, vspFlag, inheritedVSPDisInfo, iCount, (5-iCount), iCount3DV);
4514      puhInterDirNeighbours[ iCount ] = ivCandDir[1];
4515      if( ( ivCandDir[1] & 1 ) == 1 )
4516      {
4517        pcMvFieldNeighbours[ iCount<<1    ].setMvField( ivCandMv[ 2 ], ivCandRefIdx[ 2 ] );
4518      }
4519      if( ( ivCandDir[1] & 2 ) == 2 )
4520      {
4521        pcMvFieldNeighbours[(iCount<<1)+1 ].setMvField( ivCandMv[ 3 ], ivCandRefIdx[ 3 ] );
4522      }
4523#if H_3D_NBDV
4524      pcMvFieldNeighbours[iCount<<1    ].getMv().setIDVFlag (false);
4525      pcMvFieldNeighbours[(iCount<<1)+1].getMv().setIDVFlag (false);
4526#endif
4527      posIvDC  = iCount;
4528      if ( mrgCandIdx == iCount )
4529        return;
4530      iCount ++;
4531
4532      // early termination
4533      if (iCount == getSlice()->getMaxNumMergeCand()) 
4534      {
4535        return;
4536      }
4537    }
4538  } 
4539#endif // H_3D_IV_MERGE
4540
4541#if H_3D_VSP
4542  /////////////////////////////////////////////////
4543  //////// VIEW SYNTHESIS PREDICTION (VSP) ////////
4544  /////////////////////////////////////////////////
4545  if (iCount<getSlice()->getMaxNumMergeCand())
4546  {
4547
4548  if (
4549#if H_3D_IC
4550      !bICFlag &&
4551#endif
4552#if H_3D_ARP
4553      !bARPFlag &&
4554#endif
4555      xAddVspCand( mrgCandIdx, &cDisInfo, iCount, abCandIsInter, pcMvFieldNeighbours, puhInterDirNeighbours, vspFlag, iCount3DV, inheritedVSPDisInfo ) )
4556  {
4557    return;
4558  }
4559
4560  // early termination
4561  if (iCount == getSlice()->getMaxNumMergeCand())
4562  {
4563    return;
4564  }
4565#endif
4566#if H_3D
4567  }
4568#endif
4569
4570#if H_3D
4571  iCount += numA0B2;
4572#else
4573  //left bottom
4574  UInt uiLeftBottomPartIdx = 0;
4575  TComDataCU* pcCULeftBottom = 0;
4576  pcCULeftBottom = this->getPUBelowLeft( uiLeftBottomPartIdx, uiPartIdxLB );
4577  Bool isAvailableA0 = pcCULeftBottom &&
4578  pcCULeftBottom->isDiffMER(xP-1, yP+nPSH, xP, yP) &&
4579  !pcCULeftBottom->isIntra( uiLeftBottomPartIdx ) ;
4580  if ( isAvailableA0 && ( !isAvailableA1 || !pcCULeft->hasEqualMotion( uiLeftPartIdx, pcCULeftBottom, uiLeftBottomPartIdx ) ) )
4581  {
4582    abCandIsInter[iCount] = true;
4583    // get Inter Dir
4584    puhInterDirNeighbours[iCount] = pcCULeftBottom->getInterDir( uiLeftBottomPartIdx );
4585    // get Mv from Left
4586    pcCULeftBottom->getMvField( pcCULeftBottom, uiLeftBottomPartIdx, REF_PIC_LIST_0, pcMvFieldNeighbours[iCount<<1] );
4587    if ( getSlice()->isInterB() )
4588    {
4589      pcCULeftBottom->getMvField( pcCULeftBottom, uiLeftBottomPartIdx, REF_PIC_LIST_1, pcMvFieldNeighbours[(iCount<<1)+1] );
4590    }
4591    if ( mrgCandIdx == iCount )
4592    {
4593      return;
4594    }
4595    iCount ++;
4596  }
4597  // early termination
4598  if (iCount == getSlice()->getMaxNumMergeCand()) 
4599  {
4600    return;
4601  }
4602
4603  // above left
4604  if( iCount < 4 )
4605  {
4606    UInt uiAboveLeftPartIdx = 0;
4607    TComDataCU* pcCUAboveLeft = 0;
4608    pcCUAboveLeft = getPUAboveLeft( uiAboveLeftPartIdx, uiAbsPartAddr );
4609    Bool isAvailableB2 = pcCUAboveLeft &&
4610    pcCUAboveLeft->isDiffMER(xP-1, yP-1, xP, yP) &&
4611    !pcCUAboveLeft->isIntra( uiAboveLeftPartIdx );
4612    if ( isAvailableB2 && ( !isAvailableA1 || !pcCULeft->hasEqualMotion( uiLeftPartIdx, pcCUAboveLeft, uiAboveLeftPartIdx ) )
4613        && ( !isAvailableB1 || !pcCUAbove->hasEqualMotion( uiAbovePartIdx, pcCUAboveLeft, uiAboveLeftPartIdx ) ) )
4614    {
4615      abCandIsInter[iCount] = true;
4616      // get Inter Dir
4617      puhInterDirNeighbours[iCount] = pcCUAboveLeft->getInterDir( uiAboveLeftPartIdx );
4618      // get Mv from Left
4619      pcCUAboveLeft->getMvField( pcCUAboveLeft, uiAboveLeftPartIdx, REF_PIC_LIST_0, pcMvFieldNeighbours[iCount<<1] );
4620      if ( getSlice()->isInterB() )
4621      {
4622        pcCUAboveLeft->getMvField( pcCUAboveLeft, uiAboveLeftPartIdx, REF_PIC_LIST_1, pcMvFieldNeighbours[(iCount<<1)+1] );
4623      }
4624      if ( mrgCandIdx == iCount )
4625      {
4626        return;
4627      }
4628      iCount ++;
4629    }
4630  }
4631  // early termination
4632  if (iCount == getSlice()->getMaxNumMergeCand()) 
4633  {
4634    return;
4635  }
4636#endif
4637
4638
4639#if H_3D_IV_MERGE
4640  ////////////////////////////////////////////////////
4641  //////// SHIFTED IV (IvMCShift + IvDCShift) ////////
4642  ////////////////////////////////////////////////////
4643  if(  ivMvPredFlag && iCount < getSlice()->getMaxNumMergeCand() ) 
4644  {
4645    if(xAddIvMRGCand( mrgCandIdx,  iCount, abCandIsInter, pcMvFieldNeighbours, puhInterDirNeighbours, ivCandDir, ivCandMv, ivCandRefIdx, posIvDC, vspFlag, iCount3DV, inheritedVSPDisInfo ) )
4646    {
4647      return;
4648    }
4649    //early termination
4650    if (iCount == getSlice()->getMaxNumMergeCand()) 
4651    {
4652      return;
4653    }
4654  }
4655#endif
4656
4657#if H_3D
4658  if (iCountHEVC + iCount3DV > getSlice()->getMaxNumMergeCand())
4659  {
4660    iCount = getSlice()->getMaxNumMergeCand();
4661  }
4662  else
4663  {
4664    iCount = iCountHEVC + iCount3DV;
4665  }
4666  numValidMergeCand = iCount;
4667#else
4668  if ( getSlice()->getEnableTMVPFlag())
4669  {
4670    //>> MTK colocated-RightBottom
4671    UInt uiPartIdxRB;
4672
4673    deriveRightBottomIdx( uiPUIdx, uiPartIdxRB ); 
4674
4675    UInt uiAbsPartIdxTmp = g_auiZscanToRaster[uiPartIdxRB];
4676    UInt uiNumPartInCUWidth = m_pcPic->getNumPartInWidth();
4677
4678    TComMv cColMv;
4679    Int iRefIdx;
4680    Int uiLCUIdx = -1;
4681
4682    if      ( ( m_pcPic->getCU(m_uiCUAddr)->getCUPelX() + g_auiRasterToPelX[uiAbsPartIdxTmp] + m_pcPic->getMinCUWidth() ) >= m_pcSlice->getSPS()->getPicWidthInLumaSamples() )  // image boundary check
4683    {
4684    }
4685    else if ( ( m_pcPic->getCU(m_uiCUAddr)->getCUPelY() + g_auiRasterToPelY[uiAbsPartIdxTmp] + m_pcPic->getMinCUHeight() ) >= m_pcSlice->getSPS()->getPicHeightInLumaSamples() )
4686    {
4687    }
4688    else
4689    {
4690      if ( ( uiAbsPartIdxTmp % uiNumPartInCUWidth < uiNumPartInCUWidth - 1 ) &&           // is not at the last column of LCU
4691        ( uiAbsPartIdxTmp / uiNumPartInCUWidth < m_pcPic->getNumPartInHeight() - 1 ) ) // is not at the last row    of LCU
4692      {
4693        uiAbsPartAddr = g_auiRasterToZscan[ uiAbsPartIdxTmp + uiNumPartInCUWidth + 1 ];
4694        uiLCUIdx = getAddr();
4695      }
4696      else if ( uiAbsPartIdxTmp % uiNumPartInCUWidth < uiNumPartInCUWidth - 1 )           // is not at the last column of LCU But is last row of LCU
4697      {
4698        uiAbsPartAddr = g_auiRasterToZscan[ (uiAbsPartIdxTmp + uiNumPartInCUWidth + 1) % m_pcPic->getNumPartInCU() ];
4699      }
4700      else if ( uiAbsPartIdxTmp / uiNumPartInCUWidth < m_pcPic->getNumPartInHeight() - 1 ) // is not at the last row of LCU But is last column of LCU
4701      {
4702        uiAbsPartAddr = g_auiRasterToZscan[ uiAbsPartIdxTmp + 1 ];
4703        uiLCUIdx = getAddr() + 1;
4704      }
4705      else //is the right bottom corner of LCU                       
4706      {
4707        uiAbsPartAddr = 0;
4708      }
4709    }
4710   
4711   
4712    iRefIdx = 0;
4713    Bool bExistMV = false;
4714    UInt uiPartIdxCenter;
4715    UInt uiCurLCUIdx = getAddr();
4716    Int dir = 0;
4717    UInt uiArrayAddr = iCount;
4718    xDeriveCenterIdx( uiPUIdx, uiPartIdxCenter );
4719    bExistMV = uiLCUIdx >= 0 && xGetColMVP( REF_PIC_LIST_0, uiLCUIdx, uiAbsPartAddr, cColMv, iRefIdx );
4720    if( bExistMV == false )
4721    {
4722      bExistMV = xGetColMVP( REF_PIC_LIST_0, uiCurLCUIdx, uiPartIdxCenter, cColMv, iRefIdx );
4723    }
4724    if( bExistMV )
4725    {
4726      dir |= 1;
4727      pcMvFieldNeighbours[ 2 * uiArrayAddr ].setMvField( cColMv, iRefIdx );
4728    }
4729
4730    if ( getSlice()->isInterB() )
4731    {
4732      bExistMV = uiLCUIdx >= 0 && xGetColMVP( REF_PIC_LIST_1, uiLCUIdx, uiAbsPartAddr, cColMv, iRefIdx);
4733      if( bExistMV == false )
4734      {
4735        bExistMV = xGetColMVP( REF_PIC_LIST_1, uiCurLCUIdx, uiPartIdxCenter, cColMv, iRefIdx );
4736      }
4737      if( bExistMV )
4738      {
4739        dir |= 2;
4740        pcMvFieldNeighbours[ 2 * uiArrayAddr + 1 ].setMvField( cColMv, iRefIdx );
4741      }
4742    }
4743   
4744    if (dir != 0)
4745    {
4746      puhInterDirNeighbours[uiArrayAddr] = dir;
4747      abCandIsInter[uiArrayAddr] = true;
4748      if ( mrgCandIdx == iCount )
4749      {
4750        return;
4751      }
4752      iCount++;
4753    }
4754  }
4755  // early termination
4756  if (iCount == getSlice()->getMaxNumMergeCand()) 
4757  {
4758    return;
4759  }
4760  UInt uiArrayAddr = iCount;
4761  UInt uiCutoff = uiArrayAddr;
4762   
4763  if ( getSlice()->isInterB())
4764  {
4765    UInt uiPriorityList0[12] = {0 , 1, 0, 2, 1, 2, 0, 3, 1, 3, 2, 3};
4766    UInt uiPriorityList1[12] = {1 , 0, 2, 0, 2, 1, 3, 0, 3, 1, 3, 2};
4767
4768    for (Int idx=0; idx<uiCutoff*(uiCutoff-1) && uiArrayAddr!= getSlice()->getMaxNumMergeCand(); idx++)
4769    {
4770      Int i = uiPriorityList0[idx]; Int j = uiPriorityList1[idx];
4771      if (abCandIsInter[i] && abCandIsInter[j]&& (puhInterDirNeighbours[i]&0x1)&&(puhInterDirNeighbours[j]&0x2))
4772      {
4773        abCandIsInter[uiArrayAddr] = true;
4774        puhInterDirNeighbours[uiArrayAddr] = 3;
4775
4776        // get Mv from cand[i] and cand[j]
4777        pcMvFieldNeighbours[uiArrayAddr << 1].setMvField(pcMvFieldNeighbours[i<<1].getMv(), pcMvFieldNeighbours[i<<1].getRefIdx());
4778        pcMvFieldNeighbours[( uiArrayAddr << 1 ) + 1].setMvField(pcMvFieldNeighbours[(j<<1)+1].getMv(), pcMvFieldNeighbours[(j<<1)+1].getRefIdx());
4779
4780        Int iRefPOCL0 = m_pcSlice->getRefPOC( REF_PIC_LIST_0, pcMvFieldNeighbours[(uiArrayAddr<<1)].getRefIdx() );
4781        Int iRefPOCL1 = m_pcSlice->getRefPOC( REF_PIC_LIST_1, pcMvFieldNeighbours[(uiArrayAddr<<1)+1].getRefIdx() );
4782        if (iRefPOCL0 == iRefPOCL1 && pcMvFieldNeighbours[(uiArrayAddr<<1)].getMv() == pcMvFieldNeighbours[(uiArrayAddr<<1)+1].getMv())
4783        {
4784          abCandIsInter[uiArrayAddr] = false;
4785        }
4786        else
4787        {
4788          uiArrayAddr++;
4789        }
4790      }
4791    }
4792  }
4793  // early termination
4794  if (uiArrayAddr == getSlice()->getMaxNumMergeCand()) 
4795  {
4796    return;
4797  }
4798  Int iNumRefIdx = (getSlice()->isInterB()) ? min(m_pcSlice->getNumRefIdx(REF_PIC_LIST_0), m_pcSlice->getNumRefIdx(REF_PIC_LIST_1)) : m_pcSlice->getNumRefIdx(REF_PIC_LIST_0);
4799  Int r = 0;
4800  Int refcnt = 0;
4801  while (uiArrayAddr < getSlice()->getMaxNumMergeCand())
4802  {
4803    abCandIsInter[uiArrayAddr] = true;
4804    puhInterDirNeighbours[uiArrayAddr] = 1;
4805    pcMvFieldNeighbours[uiArrayAddr << 1].setMvField( TComMv(0, 0), r);
4806
4807    if ( getSlice()->isInterB() )
4808    {
4809      puhInterDirNeighbours[uiArrayAddr] = 3;
4810      pcMvFieldNeighbours[(uiArrayAddr << 1) + 1].setMvField(TComMv(0, 0), r);
4811    }
4812    uiArrayAddr++;
4813    if ( refcnt == iNumRefIdx - 1 )
4814    {
4815      r = 0;
4816    }
4817    else
4818    {
4819      ++r;
4820      ++refcnt;
4821    }
4822  }
4823
4824  numValidMergeCand = uiArrayAddr;
4825#endif
4826}
4827#else
4828
4829/** Constructs a list of merging candidates
4830 * \param uiAbsPartIdx
4831 * \param uiPUIdx
4832 * \param uiDepth
4833 * \param pcMvFieldNeighbours
4834 * \param puhInterDirNeighbours
4835 * \param numValidMergeCand
4836 */
4837Void TComDataCU::getInterMergeCandidates( UInt uiAbsPartIdx, UInt uiPUIdx, TComMvField* pcMvFieldNeighbours, UChar* puhInterDirNeighbours
4838      , Int& numValidMergeCand, Int mrgCandIdx
4839)
4840{
4841  UInt uiAbsPartAddr = m_uiAbsIdxInLCU + uiAbsPartIdx;
4842  Bool abCandIsInter[ MRG_MAX_NUM_CANDS ];
4843  for( UInt ui = 0; ui < getSlice()->getMaxNumMergeCand(); ++ui )
4844  {
4845    abCandIsInter[ui] = false;
4846    pcMvFieldNeighbours[ ( ui << 1 )     ].setRefIdx(NOT_VALID);
4847    pcMvFieldNeighbours[ ( ui << 1 ) + 1 ].setRefIdx(NOT_VALID);
4848  }
4849  numValidMergeCand = getSlice()->getMaxNumMergeCand();
4850  // compute the location of the current PU
4851  Int xP, yP, nPSW, nPSH;
4852  this->getPartPosition(uiPUIdx, xP, yP, nPSW, nPSH);
4853
4854  Int iCount = 0;
4855
4856  UInt uiPartIdxLT, uiPartIdxRT, uiPartIdxLB;
4857  PartSize cCurPS = getPartitionSize( uiAbsPartIdx );
4858  deriveLeftRightTopIdxGeneral( uiAbsPartIdx, uiPUIdx, uiPartIdxLT, uiPartIdxRT );
4859  deriveLeftBottomIdxGeneral  ( uiAbsPartIdx, uiPUIdx, uiPartIdxLB );
4860
4861  //left
4862  UInt uiLeftPartIdx = 0;
4863  TComDataCU* pcCULeft = 0;
4864  pcCULeft = getPULeft( uiLeftPartIdx, uiPartIdxLB );
4865  Bool isAvailableA1 = pcCULeft &&
4866  pcCULeft->isDiffMER(xP -1, yP+nPSH-1, xP, yP) &&
4867  !( uiPUIdx == 1 && (cCurPS == SIZE_Nx2N || cCurPS == SIZE_nLx2N || cCurPS == SIZE_nRx2N) ) &&
4868  !pcCULeft->isIntra( uiLeftPartIdx ) ;
4869  if ( isAvailableA1 )
4870  {
4871    abCandIsInter[iCount] = true;
4872    // get Inter Dir
4873    puhInterDirNeighbours[iCount] = pcCULeft->getInterDir( uiLeftPartIdx );
4874    // get Mv from Left
4875    pcCULeft->getMvField( pcCULeft, uiLeftPartIdx, REF_PIC_LIST_0, pcMvFieldNeighbours[iCount<<1] );
4876    if ( getSlice()->isInterB() )
4877    {
4878      pcCULeft->getMvField( pcCULeft, uiLeftPartIdx, REF_PIC_LIST_1, pcMvFieldNeighbours[(iCount<<1)+1] );
4879    }
4880    if ( mrgCandIdx == iCount )
4881    {
4882      return;
4883    }
4884    iCount ++;
4885  }
4886 
4887  // early termination
4888  if (iCount == getSlice()->getMaxNumMergeCand()) 
4889  {
4890    return;
4891  }
4892
4893  // above
4894  UInt uiAbovePartIdx = 0;
4895  TComDataCU* pcCUAbove = 0;
4896  pcCUAbove = getPUAbove( uiAbovePartIdx, uiPartIdxRT );
4897  Bool isAvailableB1 = pcCUAbove &&
4898  pcCUAbove->isDiffMER(xP+nPSW-1, yP-1, xP, yP) &&
4899  !( uiPUIdx == 1 && (cCurPS == SIZE_2NxN || cCurPS == SIZE_2NxnU || cCurPS == SIZE_2NxnD) ) &&
4900  !pcCUAbove->isIntra( uiAbovePartIdx );
4901  if ( isAvailableB1 && (!isAvailableA1 || !pcCULeft->hasEqualMotion( uiLeftPartIdx, pcCUAbove, uiAbovePartIdx ) ) )
4902  {
4903    abCandIsInter[iCount] = true;
4904    // get Inter Dir
4905    puhInterDirNeighbours[iCount] = pcCUAbove->getInterDir( uiAbovePartIdx );
4906    // get Mv from Left
4907    pcCUAbove->getMvField( pcCUAbove, uiAbovePartIdx, REF_PIC_LIST_0, pcMvFieldNeighbours[iCount<<1] );
4908    if ( getSlice()->isInterB() )
4909    {
4910      pcCUAbove->getMvField( pcCUAbove, uiAbovePartIdx, REF_PIC_LIST_1, pcMvFieldNeighbours[(iCount<<1)+1] );
4911    }
4912
4913    if ( mrgCandIdx == iCount )
4914    {
4915      return;
4916    }
4917    iCount ++;
4918  }
4919  // early termination
4920  if (iCount == getSlice()->getMaxNumMergeCand()) 
4921  {
4922    return;
4923  }
4924
4925
4926  // above right
4927  UInt uiAboveRightPartIdx = 0;
4928  TComDataCU* pcCUAboveRight = 0;
4929  pcCUAboveRight = getPUAboveRight( uiAboveRightPartIdx, uiPartIdxRT );
4930  Bool isAvailableB0 = pcCUAboveRight &&
4931  pcCUAboveRight->isDiffMER(xP+nPSW, yP-1, xP, yP) &&
4932  !pcCUAboveRight->isIntra( uiAboveRightPartIdx );
4933  if ( isAvailableB0 && ( !isAvailableB1 || !pcCUAbove->hasEqualMotion( uiAbovePartIdx, pcCUAboveRight, uiAboveRightPartIdx ) ) )
4934  {
4935    abCandIsInter[iCount] = true;
4936    // get Inter Dir
4937    puhInterDirNeighbours[iCount] = pcCUAboveRight->getInterDir( uiAboveRightPartIdx );
4938    // get Mv from Left
4939    pcCUAboveRight->getMvField( pcCUAboveRight, uiAboveRightPartIdx, REF_PIC_LIST_0, pcMvFieldNeighbours[iCount<<1] );
4940    if ( getSlice()->isInterB() )
4941    {
4942      pcCUAboveRight->getMvField( pcCUAboveRight, uiAboveRightPartIdx, REF_PIC_LIST_1, pcMvFieldNeighbours[(iCount<<1)+1] );
4943    }
4944    if ( mrgCandIdx == iCount )
4945    {
4946      return;
4947    }
4948    iCount ++;
4949  }
4950  // early termination
4951  if (iCount == getSlice()->getMaxNumMergeCand()) 
4952  {
4953    return;
4954  }
4955
4956  //left bottom
4957  UInt uiLeftBottomPartIdx = 0;
4958  TComDataCU* pcCULeftBottom = 0;
4959  pcCULeftBottom = this->getPUBelowLeft( uiLeftBottomPartIdx, uiPartIdxLB );
4960  Bool isAvailableA0 = pcCULeftBottom &&
4961  pcCULeftBottom->isDiffMER(xP-1, yP+nPSH, xP, yP) &&
4962  !pcCULeftBottom->isIntra( uiLeftBottomPartIdx ) ;
4963  if ( isAvailableA0 && ( !isAvailableA1 || !pcCULeft->hasEqualMotion( uiLeftPartIdx, pcCULeftBottom, uiLeftBottomPartIdx ) ) )
4964  {
4965    abCandIsInter[iCount] = true;
4966    // get Inter Dir
4967    puhInterDirNeighbours[iCount] = pcCULeftBottom->getInterDir( uiLeftBottomPartIdx );
4968    // get Mv from Left
4969    pcCULeftBottom->getMvField( pcCULeftBottom, uiLeftBottomPartIdx, REF_PIC_LIST_0, pcMvFieldNeighbours[iCount<<1] );
4970    if ( getSlice()->isInterB() )
4971    {
4972      pcCULeftBottom->getMvField( pcCULeftBottom, uiLeftBottomPartIdx, REF_PIC_LIST_1, pcMvFieldNeighbours[(iCount<<1)+1] );
4973    }
4974
4975    if ( mrgCandIdx == iCount )
4976    {
4977      return;
4978    }
4979    iCount ++;
4980  }
4981  // early termination
4982  if (iCount == getSlice()->getMaxNumMergeCand()) 
4983  {
4984    return;
4985  }
4986
4987  // above left
4988  if( iCount < 4 )
4989  {
4990    UInt uiAboveLeftPartIdx = 0;
4991    TComDataCU* pcCUAboveLeft = 0;
4992    pcCUAboveLeft = getPUAboveLeft( uiAboveLeftPartIdx, uiAbsPartAddr );
4993    Bool isAvailableB2 = pcCUAboveLeft &&
4994    pcCUAboveLeft->isDiffMER(xP-1, yP-1, xP, yP) &&
4995    !pcCUAboveLeft->isIntra( uiAboveLeftPartIdx );
4996    if ( isAvailableB2 && ( !isAvailableA1 || !pcCULeft->hasEqualMotion( uiLeftPartIdx, pcCUAboveLeft, uiAboveLeftPartIdx ) )
4997        && ( !isAvailableB1 || !pcCUAbove->hasEqualMotion( uiAbovePartIdx, pcCUAboveLeft, uiAboveLeftPartIdx ) ) )
4998    {
4999      abCandIsInter[iCount] = true;
5000      // get Inter Dir
5001      puhInterDirNeighbours[iCount] = pcCUAboveLeft->getInterDir( uiAboveLeftPartIdx );
5002      // get Mv from Left
5003      pcCUAboveLeft->getMvField( pcCUAboveLeft, uiAboveLeftPartIdx, REF_PIC_LIST_0, pcMvFieldNeighbours[iCount<<1] );
5004      if ( getSlice()->isInterB() )
5005      {
5006        pcCUAboveLeft->getMvField( pcCUAboveLeft, uiAboveLeftPartIdx, REF_PIC_LIST_1, pcMvFieldNeighbours[(iCount<<1)+1] );
5007      }
5008      if ( mrgCandIdx == iCount )
5009      {
5010        return;
5011      }
5012      iCount ++;
5013    }
5014  }
5015  // early termination
5016  if (iCount == getSlice()->getMaxNumMergeCand()) 
5017  {
5018    return;
5019  }
5020
5021  if ( getSlice()->getEnableTMVPFlag())
5022  {
5023    //>> MTK colocated-RightBottom
5024    UInt uiPartIdxRB;
5025
5026    deriveRightBottomIdx( uiPUIdx, uiPartIdxRB ); 
5027
5028    UInt uiAbsPartIdxTmp = g_auiZscanToRaster[uiPartIdxRB];
5029    UInt uiNumPartInCUWidth = m_pcPic->getNumPartInWidth();
5030
5031    TComMv cColMv;
5032    Int iRefIdx;
5033    Int uiLCUIdx = -1;
5034
5035    if      ( ( m_pcPic->getCU(m_uiCUAddr)->getCUPelX() + g_auiRasterToPelX[uiAbsPartIdxTmp] + m_pcPic->getMinCUWidth() ) >= m_pcSlice->getSPS()->getPicWidthInLumaSamples() )  // image boundary check
5036    {
5037    }
5038    else if ( ( m_pcPic->getCU(m_uiCUAddr)->getCUPelY() + g_auiRasterToPelY[uiAbsPartIdxTmp] + m_pcPic->getMinCUHeight() ) >= m_pcSlice->getSPS()->getPicHeightInLumaSamples() )
5039    {
5040    }
5041    else
5042    {
5043      if ( ( uiAbsPartIdxTmp % uiNumPartInCUWidth < uiNumPartInCUWidth - 1 ) &&           // is not at the last column of LCU
5044        ( uiAbsPartIdxTmp / uiNumPartInCUWidth < m_pcPic->getNumPartInHeight() - 1 ) ) // is not at the last row    of LCU
5045      {
5046        uiAbsPartAddr = g_auiRasterToZscan[ uiAbsPartIdxTmp + uiNumPartInCUWidth + 1 ];
5047        uiLCUIdx = getAddr();
5048      }
5049      else if ( uiAbsPartIdxTmp % uiNumPartInCUWidth < uiNumPartInCUWidth - 1 )           // is not at the last column of LCU But is last row of LCU
5050      {
5051        uiAbsPartAddr = g_auiRasterToZscan[ (uiAbsPartIdxTmp + uiNumPartInCUWidth + 1) % m_pcPic->getNumPartInCU() ];
5052      }
5053      else if ( uiAbsPartIdxTmp / uiNumPartInCUWidth < m_pcPic->getNumPartInHeight() - 1 ) // is not at the last row of LCU But is last column of LCU
5054      {
5055        uiAbsPartAddr = g_auiRasterToZscan[ uiAbsPartIdxTmp + 1 ];
5056        uiLCUIdx = getAddr() + 1;
5057      }
5058      else //is the right bottom corner of LCU                       
5059      {
5060        uiAbsPartAddr = 0;
5061      }
5062    }
5063   
5064   
5065    iRefIdx = 0;
5066    Bool bExistMV = false;
5067    UInt uiPartIdxCenter;
5068    UInt uiCurLCUIdx = getAddr();
5069    Int dir = 0;
5070    UInt uiArrayAddr = iCount;
5071    xDeriveCenterIdx( uiPUIdx, uiPartIdxCenter );
5072    bExistMV = uiLCUIdx >= 0 && xGetColMVP( REF_PIC_LIST_0, uiLCUIdx, uiAbsPartAddr, cColMv, iRefIdx );
5073    if( bExistMV == false )
5074    {
5075      bExistMV = xGetColMVP( REF_PIC_LIST_0, uiCurLCUIdx, uiPartIdxCenter, cColMv, iRefIdx );
5076    }
5077    if( bExistMV )
5078    {
5079      dir |= 1;
5080      pcMvFieldNeighbours[ 2 * uiArrayAddr ].setMvField( cColMv, iRefIdx );
5081    }
5082
5083    if ( getSlice()->isInterB() )
5084    {
5085      bExistMV = uiLCUIdx >= 0 && xGetColMVP( REF_PIC_LIST_1, uiLCUIdx, uiAbsPartAddr, cColMv, iRefIdx);
5086      if( bExistMV == false )
5087      {
5088        bExistMV = xGetColMVP( REF_PIC_LIST_1, uiCurLCUIdx, uiPartIdxCenter, cColMv, iRefIdx );
5089      }
5090      if( bExistMV )
5091      {
5092        dir |= 2;
5093        pcMvFieldNeighbours[ 2 * uiArrayAddr + 1 ].setMvField( cColMv, iRefIdx );
5094      }
5095    }
5096   
5097    if (dir != 0)
5098    {
5099      puhInterDirNeighbours[uiArrayAddr] = dir;
5100      abCandIsInter[uiArrayAddr] = true;
5101      if ( mrgCandIdx == iCount )
5102      {
5103        return;
5104      }
5105      iCount++;
5106    }
5107  }
5108  // early termination
5109  if (iCount == getSlice()->getMaxNumMergeCand()) 
5110  {
5111    return;
5112  }
5113  UInt uiArrayAddr = iCount;
5114  UInt uiCutoff = uiArrayAddr;
5115   
5116  if ( getSlice()->isInterB())
5117  {
5118    UInt uiPriorityList0[12] = {0 , 1, 0, 2, 1, 2, 0, 3, 1, 3, 2, 3};
5119    UInt uiPriorityList1[12] = {1 , 0, 2, 0, 2, 1, 3, 0, 3, 1, 3, 2};
5120
5121    for (Int idx=0; idx<uiCutoff*(uiCutoff-1) && uiArrayAddr!= getSlice()->getMaxNumMergeCand(); idx++)
5122    {
5123      Int i = uiPriorityList0[idx]; Int j = uiPriorityList1[idx];
5124      if (abCandIsInter[i] && abCandIsInter[j]&& (puhInterDirNeighbours[i]&0x1)&&(puhInterDirNeighbours[j]&0x2))
5125      {
5126        abCandIsInter[uiArrayAddr] = true;
5127        puhInterDirNeighbours[uiArrayAddr] = 3;
5128
5129        // get Mv from cand[i] and cand[j]
5130        pcMvFieldNeighbours[uiArrayAddr << 1].setMvField(pcMvFieldNeighbours[i<<1].getMv(), pcMvFieldNeighbours[i<<1].getRefIdx());
5131        pcMvFieldNeighbours[( uiArrayAddr << 1 ) + 1].setMvField(pcMvFieldNeighbours[(j<<1)+1].getMv(), pcMvFieldNeighbours[(j<<1)+1].getRefIdx());
5132
5133        Int iRefPOCL0 = m_pcSlice->getRefPOC( REF_PIC_LIST_0, pcMvFieldNeighbours[(uiArrayAddr<<1)].getRefIdx() );
5134        Int iRefPOCL1 = m_pcSlice->getRefPOC( REF_PIC_LIST_1, pcMvFieldNeighbours[(uiArrayAddr<<1)+1].getRefIdx() );
5135        if (iRefPOCL0 == iRefPOCL1 && pcMvFieldNeighbours[(uiArrayAddr<<1)].getMv() == pcMvFieldNeighbours[(uiArrayAddr<<1)+1].getMv())
5136        {
5137          abCandIsInter[uiArrayAddr] = false;
5138        }
5139        else
5140        {
5141          uiArrayAddr++;
5142        }
5143      }
5144    }
5145  }
5146  // early termination
5147  if (uiArrayAddr == getSlice()->getMaxNumMergeCand()) 
5148  {
5149    return;
5150  }
5151  Int iNumRefIdx = (getSlice()->isInterB()) ? min(m_pcSlice->getNumRefIdx(REF_PIC_LIST_0), m_pcSlice->getNumRefIdx(REF_PIC_LIST_1)) : m_pcSlice->getNumRefIdx(REF_PIC_LIST_0);
5152  Int r = 0;
5153  Int refcnt = 0;
5154  while (uiArrayAddr < getSlice()->getMaxNumMergeCand())
5155  {
5156    abCandIsInter[uiArrayAddr] = true;
5157    puhInterDirNeighbours[uiArrayAddr] = 1;
5158    pcMvFieldNeighbours[uiArrayAddr << 1].setMvField( TComMv(0, 0), r);
5159
5160    if ( getSlice()->isInterB() )
5161    {
5162      puhInterDirNeighbours[uiArrayAddr] = 3;
5163      pcMvFieldNeighbours[(uiArrayAddr << 1) + 1].setMvField(TComMv(0, 0), r);
5164    }
5165    uiArrayAddr++;
5166    if ( refcnt == iNumRefIdx - 1 )
5167    {
5168      r = 0;
5169    }
5170    else
5171    {
5172      ++r;
5173      ++refcnt;
5174    }
5175  }
5176
5177  numValidMergeCand = uiArrayAddr;
5178}
5179#endif
5180
5181
5182#if H_3D_VSP
5183inline Void TComDataCU::xInheritVSPDisInfo(TComDataCU* pcCURef, UInt uiAbsPartIdx, Int iCount, InheritedVSPDisInfo*  inheritedVSPDisInfo)
5184{
5185  inheritedVSPDisInfo[iCount].m_acDvInfo.m_acNBDV   = pcCURef->getDvInfo(uiAbsPartIdx).m_acNBDV;
5186  inheritedVSPDisInfo[iCount].m_acDvInfo.m_aVIdxCan = pcCURef->getDvInfo(uiAbsPartIdx).m_aVIdxCan;
5187}
5188#endif
5189/** Check whether the current PU and a spatial neighboring PU are in a same ME region.
5190 * \param xN, xN   location of the upper-left corner pixel of a neighboring PU
5191 * \param xP, yP   location of the upper-left corner pixel of the current PU
5192 * \returns Bool
5193 */
5194Bool TComDataCU::isDiffMER(Int xN, Int yN, Int xP, Int yP)
5195{
5196
5197  UInt plevel = this->getSlice()->getPPS()->getLog2ParallelMergeLevelMinus2() + 2;
5198  if ((xN>>plevel)!= (xP>>plevel))
5199  {
5200    return true;
5201  }
5202  if ((yN>>plevel)!= (yP>>plevel))
5203  {
5204    return true;
5205  }
5206  return false;
5207}
5208/** calculate the location of upper-left corner pixel and size of the current PU.
5209 * \param partIdx  PU index within a CU
5210 * \param xP, yP   location of the upper-left corner pixel of the current PU
5211 * \param PSW, nPSH    size of the curren PU
5212 * \returns Void
5213 */
5214Void TComDataCU::getPartPosition( UInt partIdx, Int& xP, Int& yP, Int& nPSW, Int& nPSH)
5215{
5216  UInt col = m_uiCUPelX;
5217  UInt row = m_uiCUPelY;
5218
5219  switch ( m_pePartSize[0] )
5220  {
5221  case SIZE_2NxN:
5222    nPSW = getWidth(0);     
5223    nPSH = getHeight(0) >> 1; 
5224    xP   = col;
5225    yP   = (partIdx ==0)? row: row + nPSH;
5226    break;
5227  case SIZE_Nx2N:
5228    nPSW = getWidth(0) >> 1; 
5229    nPSH = getHeight(0);     
5230    xP   = (partIdx ==0)? col: col + nPSW;
5231    yP   = row;
5232    break;
5233  case SIZE_NxN:
5234    nPSW = getWidth(0) >> 1; 
5235    nPSH = getHeight(0) >> 1; 
5236    xP   = col + (partIdx&0x1)*nPSW;
5237    yP   = row + (partIdx>>1)*nPSH;
5238    break;
5239  case SIZE_2NxnU:
5240    nPSW = getWidth(0);
5241    nPSH = ( partIdx == 0 ) ?  getHeight(0) >> 2 : ( getHeight(0) >> 2 ) + ( getHeight(0) >> 1 );
5242    xP   = col;
5243    yP   = (partIdx ==0)? row: row + getHeight(0) - nPSH;
5244
5245    break;
5246  case SIZE_2NxnD:
5247    nPSW = getWidth(0);
5248    nPSH = ( partIdx == 0 ) ?  ( getHeight(0) >> 2 ) + ( getHeight(0) >> 1 ) : getHeight(0) >> 2;
5249    xP   = col;
5250    yP   = (partIdx ==0)? row: row + getHeight(0) - nPSH;
5251    break;
5252  case SIZE_nLx2N:
5253    nPSW = ( partIdx == 0 ) ? getWidth(0) >> 2 : ( getWidth(0) >> 2 ) + ( getWidth(0) >> 1 );
5254    nPSH = getHeight(0);
5255    xP   = (partIdx ==0)? col: col + getWidth(0) - nPSW;
5256    yP   = row;
5257    break;
5258  case SIZE_nRx2N:
5259    nPSW = ( partIdx == 0 ) ? ( getWidth(0) >> 2 ) + ( getWidth(0) >> 1 ) : getWidth(0) >> 2;
5260    nPSH = getHeight(0);
5261    xP   = (partIdx ==0)? col: col + getWidth(0) - nPSW;
5262    yP   = row;
5263    break;
5264  default:
5265    assert ( m_pePartSize[0] == SIZE_2Nx2N );
5266    nPSW = getWidth(0);     
5267    nPSH = getHeight(0);     
5268    xP   = col ;
5269    yP   = row ;
5270
5271    break;
5272  }
5273}
5274
5275/** Constructs a list of candidates for AMVP
5276 * \param uiPartIdx
5277 * \param uiPartAddr
5278 * \param eRefPicList
5279 * \param iRefIdx
5280 * \param pInfo
5281 */
5282Void TComDataCU::fillMvpCand ( UInt uiPartIdx, UInt uiPartAddr, RefPicList eRefPicList, Int iRefIdx, AMVPInfo* pInfo )
5283{
5284  TComMv cMvPred;
5285  Bool bAddedSmvp = false;
5286
5287  pInfo->iN = 0; 
5288  if (iRefIdx < 0)
5289  {
5290    return;
5291  }
5292 
5293  //-- Get Spatial MV
5294  UInt uiPartIdxLT, uiPartIdxRT, uiPartIdxLB;
5295  UInt uiNumPartInCUWidth = m_pcPic->getNumPartInWidth();
5296  Bool bAdded = false;
5297 
5298  deriveLeftRightTopIdx( uiPartIdx, uiPartIdxLT, uiPartIdxRT );
5299  deriveLeftBottomIdx( uiPartIdx, uiPartIdxLB );
5300 
5301  TComDataCU* tmpCU = NULL;
5302  UInt idx;
5303  tmpCU = getPUBelowLeft(idx, uiPartIdxLB);
5304  bAddedSmvp = (tmpCU != NULL) && (tmpCU->getPredictionMode(idx) != MODE_INTRA);
5305
5306  if (!bAddedSmvp)
5307  {
5308    tmpCU = getPULeft(idx, uiPartIdxLB);
5309    bAddedSmvp = (tmpCU != NULL) && (tmpCU->getPredictionMode(idx) != MODE_INTRA);
5310  }
5311
5312  // Left predictor search
5313  bAdded = xAddMVPCand( pInfo, eRefPicList, iRefIdx, uiPartIdxLB, MD_BELOW_LEFT);
5314  if (!bAdded) 
5315  {
5316    bAdded = xAddMVPCand( pInfo, eRefPicList, iRefIdx, uiPartIdxLB, MD_LEFT );
5317  }
5318 
5319  if(!bAdded)
5320  {
5321    bAdded = xAddMVPCandOrder( pInfo, eRefPicList, iRefIdx, uiPartIdxLB, MD_BELOW_LEFT);
5322    if (!bAdded) 
5323    {
5324      xAddMVPCandOrder( pInfo, eRefPicList, iRefIdx, uiPartIdxLB, MD_LEFT );
5325    }
5326  }
5327  // Above predictor search
5328  bAdded = xAddMVPCand( pInfo, eRefPicList, iRefIdx, uiPartIdxRT, MD_ABOVE_RIGHT);
5329
5330  if (!bAdded) 
5331  {
5332    bAdded = xAddMVPCand( pInfo, eRefPicList, iRefIdx, uiPartIdxRT, MD_ABOVE);
5333  }
5334
5335  if(!bAdded)
5336  {
5337    xAddMVPCand( pInfo, eRefPicList, iRefIdx, uiPartIdxLT, MD_ABOVE_LEFT);
5338  }
5339  bAdded = bAddedSmvp;
5340  if (pInfo->iN==2) bAdded = true;
5341
5342  if(!bAdded)
5343  {
5344    bAdded = xAddMVPCandOrder( pInfo, eRefPicList, iRefIdx, uiPartIdxRT, MD_ABOVE_RIGHT);
5345    if (!bAdded) 
5346    {
5347      bAdded = xAddMVPCandOrder( pInfo, eRefPicList, iRefIdx, uiPartIdxRT, MD_ABOVE);
5348    }
5349
5350    if(!bAdded)
5351    {
5352      xAddMVPCandOrder( pInfo, eRefPicList, iRefIdx, uiPartIdxLT, MD_ABOVE_LEFT);
5353    }
5354  }
5355 
5356  if ( pInfo->iN == 2 )
5357  {
5358    if ( pInfo->m_acMvCand[ 0 ] == pInfo->m_acMvCand[ 1 ] )
5359    {
5360      pInfo->iN = 1;
5361    }
5362  }
5363
5364  if ( getSlice()->getEnableTMVPFlag() )
5365  {
5366    // Get Temporal Motion Predictor
5367    Int iRefIdx_Col = iRefIdx;
5368    TComMv cColMv;
5369    UInt uiPartIdxRB;
5370    UInt uiAbsPartIdx; 
5371    UInt uiAbsPartAddr;
5372
5373    deriveRightBottomIdx( uiPartIdx, uiPartIdxRB );
5374    uiAbsPartAddr = m_uiAbsIdxInLCU + uiPartAddr;
5375
5376    //----  co-located RightBottom Temporal Predictor (H) ---//
5377    uiAbsPartIdx = g_auiZscanToRaster[uiPartIdxRB];
5378    Int uiLCUIdx = -1;
5379    if ( ( m_pcPic->getCU(m_uiCUAddr)->getCUPelX() + g_auiRasterToPelX[uiAbsPartIdx] + m_pcPic->getMinCUWidth() ) >= m_pcSlice->getSPS()->getPicWidthInLumaSamples() )  // image boundary check
5380    {
5381    }
5382    else if ( ( m_pcPic->getCU(m_uiCUAddr)->getCUPelY() + g_auiRasterToPelY[uiAbsPartIdx] + m_pcPic->getMinCUHeight() ) >= m_pcSlice->getSPS()->getPicHeightInLumaSamples() )
5383    {
5384    }
5385    else
5386    {
5387      if ( ( uiAbsPartIdx % uiNumPartInCUWidth < uiNumPartInCUWidth - 1 ) &&           // is not at the last column of LCU
5388        ( uiAbsPartIdx / uiNumPartInCUWidth < m_pcPic->getNumPartInHeight() - 1 ) ) // is not at the last row    of LCU
5389      {
5390        uiAbsPartAddr = g_auiRasterToZscan[ uiAbsPartIdx + uiNumPartInCUWidth + 1 ];
5391        uiLCUIdx = getAddr();
5392      }
5393      else if ( uiAbsPartIdx % uiNumPartInCUWidth < uiNumPartInCUWidth - 1 )           // is not at the last column of LCU But is last row of LCU
5394      {
5395        uiAbsPartAddr = g_auiRasterToZscan[ (uiAbsPartIdx + uiNumPartInCUWidth + 1) % m_pcPic->getNumPartInCU() ];
5396      }
5397      else if ( uiAbsPartIdx / uiNumPartInCUWidth < m_pcPic->getNumPartInHeight() - 1 ) // is not at the last row of LCU But is last column of LCU
5398      {
5399        uiAbsPartAddr = g_auiRasterToZscan[ uiAbsPartIdx + 1 ];
5400        uiLCUIdx = getAddr() + 1;
5401      }
5402      else //is the right bottom corner of LCU                       
5403      {
5404        uiAbsPartAddr = 0;
5405      }
5406    }
5407    if ( uiLCUIdx >= 0 && xGetColMVP( eRefPicList, uiLCUIdx, uiAbsPartAddr, cColMv, iRefIdx_Col
5408#if H_3D_TMVP
5409         , 0
5410#endif
5411    ) )
5412    {
5413      pInfo->m_acMvCand[pInfo->iN++] = cColMv;
5414    }
5415    else 
5416    {
5417      UInt uiPartIdxCenter;
5418      UInt uiCurLCUIdx = getAddr();
5419      xDeriveCenterIdx( uiPartIdx, uiPartIdxCenter );
5420      if (xGetColMVP( eRefPicList, uiCurLCUIdx, uiPartIdxCenter,  cColMv, iRefIdx_Col
5421#if H_3D_TMVP
5422         , 0
5423#endif
5424      ))
5425      {
5426        pInfo->m_acMvCand[pInfo->iN++] = cColMv;
5427      }
5428    }
5429    //----  co-located RightBottom Temporal Predictor  ---//
5430  }
5431
5432  if (pInfo->iN > AMVP_MAX_NUM_CANDS)
5433  {
5434    pInfo->iN = AMVP_MAX_NUM_CANDS;
5435  }
5436  while (pInfo->iN < AMVP_MAX_NUM_CANDS)
5437  {
5438      pInfo->m_acMvCand[pInfo->iN].set(0,0);
5439      pInfo->iN++;
5440  }
5441  return ;
5442}
5443
5444Bool TComDataCU::isBipredRestriction(UInt puIdx)
5445{
5446  Int width = 0;
5447  Int height = 0;
5448  UInt partAddr;
5449
5450  getPartIndexAndSize( puIdx, partAddr, width, height );
5451  if ( getWidth(0) == 8 && (width < 8 || height < 8) )
5452  {
5453    return true;
5454  }
5455  return false;
5456}
5457
5458Void TComDataCU::clipMv    (TComMv&  rcMv)
5459{
5460  Int  iMvShift = 2;
5461#if H_3D_IC
5462  if( getSlice()->getIsDepth() )
5463    iMvShift = 0;
5464#endif
5465  Int iOffset = 8;
5466  Int iHorMax = ( m_pcSlice->getSPS()->getPicWidthInLumaSamples() + iOffset - m_uiCUPelX - 1 ) << iMvShift;
5467  Int iHorMin = (       -(Int)g_uiMaxCUWidth - iOffset - (Int)m_uiCUPelX + 1 ) << iMvShift;
5468 
5469  Int iVerMax = ( m_pcSlice->getSPS()->getPicHeightInLumaSamples() + iOffset - m_uiCUPelY - 1 ) << iMvShift;
5470  Int iVerMin = (       -(Int)g_uiMaxCUHeight - iOffset - (Int)m_uiCUPelY + 1 ) << iMvShift;
5471 
5472  rcMv.setHor( min (iHorMax, max (iHorMin, rcMv.getHor())) );
5473  rcMv.setVer( min (iVerMax, max (iVerMin, rcMv.getVer())) );
5474}
5475
5476UInt TComDataCU::getIntraSizeIdx(UInt uiAbsPartIdx)
5477{
5478  UInt uiShift = ( m_pePartSize[uiAbsPartIdx]==SIZE_NxN ? 1 : 0 );
5479 
5480  UChar uiWidth = m_puhWidth[uiAbsPartIdx]>>uiShift;
5481  UInt  uiCnt = 0;
5482  while( uiWidth )
5483  {
5484    uiCnt++;
5485    uiWidth>>=1;
5486  }
5487  uiCnt-=2;
5488  return uiCnt > 6 ? 6 : uiCnt;
5489}
5490
5491Void TComDataCU::clearCbf( UInt uiIdx, TextType eType, UInt uiNumParts )
5492{
5493  ::memset( &m_puhCbf[g_aucConvertTxtTypeToIdx[eType]][uiIdx], 0, sizeof(UChar)*uiNumParts);
5494}
5495
5496/** Set a I_PCM flag for all sub-partitions of a partition.
5497 * \param bIpcmFlag I_PCM flag
5498 * \param uiAbsPartIdx patition index
5499 * \param uiDepth CU depth
5500 * \returns Void
5501 */
5502Void TComDataCU::setIPCMFlagSubParts  (Bool bIpcmFlag, UInt uiAbsPartIdx, UInt uiDepth)
5503{
5504  UInt uiCurrPartNumb = m_pcPic->getNumPartInCU() >> (uiDepth << 1);
5505
5506  memset(m_pbIPCMFlag + uiAbsPartIdx, bIpcmFlag, sizeof(Bool)*uiCurrPartNumb );
5507}
5508
5509/** Test whether the current block is skipped
5510 * \param uiPartIdx Block index
5511 * \returns Flag indicating whether the block is skipped
5512 */
5513Bool TComDataCU::isSkipped( UInt uiPartIdx )
5514{
5515  return ( getSkipFlag( uiPartIdx ) );
5516}
5517
5518#if H_3D_IC
5519Bool TComDataCU::isIC( UInt uiPartIdx )
5520{
5521    if ( m_pcSlice->isIntra () )
5522    {
5523        return false;
5524    }
5525    return ( ( getSkipFlag(uiPartIdx) || getPredictionMode(uiPartIdx) == MODE_INTER) && getICFlag( uiPartIdx ) && isICFlagRequired( uiPartIdx ) );
5526}
5527#endif
5528
5529// ====================================================================================================================
5530// Protected member functions
5531// ====================================================================================================================
5532
5533Bool TComDataCU::xAddMVPCand( AMVPInfo* pInfo, RefPicList eRefPicList, Int iRefIdx, UInt uiPartUnitIdx, MVP_DIR eDir )
5534{
5535  TComDataCU* pcTmpCU = NULL;
5536  UInt uiIdx;
5537  switch( eDir )
5538  {
5539    case MD_LEFT:
5540    {
5541      pcTmpCU = getPULeft(uiIdx, uiPartUnitIdx);
5542      break;
5543    }
5544    case MD_ABOVE:
5545    {
5546      pcTmpCU = getPUAbove(uiIdx, uiPartUnitIdx );
5547      break;
5548    }
5549    case MD_ABOVE_RIGHT:
5550    {
5551      pcTmpCU = getPUAboveRight(uiIdx, uiPartUnitIdx);
5552      break;
5553    }
5554    case MD_BELOW_LEFT:
5555    {
5556      pcTmpCU = getPUBelowLeft(uiIdx, uiPartUnitIdx);
5557      break;
5558    }
5559    case MD_ABOVE_LEFT:
5560    {
5561      pcTmpCU = getPUAboveLeft(uiIdx, uiPartUnitIdx);
5562      break;
5563    }
5564    default:
5565    {
5566      break;
5567    }
5568  }
5569
5570  if ( pcTmpCU == NULL )
5571  {
5572    return false;
5573  }
5574 
5575  if ( pcTmpCU->getCUMvField(eRefPicList)->getRefIdx(uiIdx) >= 0 && m_pcSlice->getRefPic( eRefPicList, iRefIdx)->getPOC() == pcTmpCU->getSlice()->getRefPOC( eRefPicList, pcTmpCU->getCUMvField(eRefPicList)->getRefIdx(uiIdx) ))
5576  {
5577    TComMv cMvPred = pcTmpCU->getCUMvField(eRefPicList)->getMv(uiIdx);
5578   
5579    pInfo->m_acMvCand[ pInfo->iN++] = cMvPred;
5580    return true;
5581  }
5582
5583  RefPicList eRefPicList2nd = REF_PIC_LIST_0;
5584  if(       eRefPicList == REF_PIC_LIST_0 )
5585  {
5586    eRefPicList2nd = REF_PIC_LIST_1;
5587  }
5588  else if ( eRefPicList == REF_PIC_LIST_1)
5589  {
5590    eRefPicList2nd = REF_PIC_LIST_0;
5591  }
5592
5593
5594  Int iCurrRefPOC = m_pcSlice->getRefPic( eRefPicList, iRefIdx)->getPOC();
5595  Int iNeibRefPOC;
5596
5597
5598  if( pcTmpCU->getCUMvField(eRefPicList2nd)->getRefIdx(uiIdx) >= 0 )
5599  {
5600    iNeibRefPOC = pcTmpCU->getSlice()->getRefPOC( eRefPicList2nd, pcTmpCU->getCUMvField(eRefPicList2nd)->getRefIdx(uiIdx) );
5601    if( iNeibRefPOC == iCurrRefPOC ) // Same Reference Frame But Diff List//
5602    {
5603      TComMv cMvPred = pcTmpCU->getCUMvField(eRefPicList2nd)->getMv(uiIdx);
5604      pInfo->m_acMvCand[ pInfo->iN++] = cMvPred;
5605      return true;
5606    }
5607  }
5608  return false;
5609}
5610
5611/**
5612 * \param pInfo
5613 * \param eRefPicList
5614 * \param iRefIdx
5615 * \param uiPartUnitIdx
5616 * \param eDir
5617 * \returns Bool
5618 */
5619Bool TComDataCU::xAddMVPCandOrder( AMVPInfo* pInfo, RefPicList eRefPicList, Int iRefIdx, UInt uiPartUnitIdx, MVP_DIR eDir )
5620{
5621  TComDataCU* pcTmpCU = NULL;
5622  UInt uiIdx;
5623  switch( eDir )
5624  {
5625  case MD_LEFT:
5626    {
5627      pcTmpCU = getPULeft(uiIdx, uiPartUnitIdx);
5628      break;
5629    }
5630  case MD_ABOVE:
5631    {
5632      pcTmpCU = getPUAbove(uiIdx, uiPartUnitIdx);
5633      break;
5634    }
5635  case MD_ABOVE_RIGHT:
5636    {
5637      pcTmpCU = getPUAboveRight(uiIdx, uiPartUnitIdx);
5638      break;
5639    }
5640  case MD_BELOW_LEFT:
5641    {
5642      pcTmpCU = getPUBelowLeft(uiIdx, uiPartUnitIdx);
5643      break;
5644    }
5645  case MD_ABOVE_LEFT:
5646    {
5647      pcTmpCU = getPUAboveLeft(uiIdx, uiPartUnitIdx);
5648      break;
5649    }
5650  default:
5651    {
5652      break;
5653    }
5654  }
5655
5656  if ( pcTmpCU == NULL ) 
5657  {
5658    return false;
5659  }
5660 
5661  RefPicList eRefPicList2nd = REF_PIC_LIST_0;
5662  if(       eRefPicList == REF_PIC_LIST_0 )
5663  {
5664    eRefPicList2nd = REF_PIC_LIST_1;
5665  }
5666  else if ( eRefPicList == REF_PIC_LIST_1)
5667  {
5668    eRefPicList2nd = REF_PIC_LIST_0;
5669  }
5670
5671  Int iCurrPOC = m_pcSlice->getPOC();
5672  Int iCurrRefPOC = m_pcSlice->getRefPic( eRefPicList, iRefIdx)->getPOC();
5673  Int iNeibPOC = iCurrPOC;
5674  Int iNeibRefPOC;
5675
5676  Bool bIsCurrRefLongTerm = m_pcSlice->getRefPic( eRefPicList, iRefIdx)->getIsLongTerm();
5677  Bool bIsNeibRefLongTerm = false;
5678  //---------------  V1 (END) ------------------//
5679  if( pcTmpCU->getCUMvField(eRefPicList)->getRefIdx(uiIdx) >= 0)
5680  {
5681    iNeibRefPOC = pcTmpCU->getSlice()->getRefPOC( eRefPicList, pcTmpCU->getCUMvField(eRefPicList)->getRefIdx(uiIdx) );
5682    TComMv cMvPred = pcTmpCU->getCUMvField(eRefPicList)->getMv(uiIdx);
5683    TComMv rcMv;
5684
5685    bIsNeibRefLongTerm = pcTmpCU->getSlice()->getRefPic( eRefPicList, pcTmpCU->getCUMvField(eRefPicList)->getRefIdx(uiIdx) )->getIsLongTerm();
5686    if ( bIsCurrRefLongTerm == bIsNeibRefLongTerm ) 
5687    {
5688    if ( bIsCurrRefLongTerm || bIsNeibRefLongTerm )
5689    {
5690      rcMv = cMvPred;
5691    }
5692    else
5693    {
5694      Int iScale = xGetDistScaleFactor( iCurrPOC, iCurrRefPOC, iNeibPOC, iNeibRefPOC );
5695      if ( iScale == 4096 )
5696      {
5697        rcMv = cMvPred;
5698      }
5699      else
5700      {
5701        rcMv = cMvPred.scaleMv( iScale );
5702      }
5703    }
5704    pInfo->m_acMvCand[ pInfo->iN++] = rcMv;
5705    return true;
5706    }
5707  }
5708  //---------------------- V2(END) --------------------//
5709  if( pcTmpCU->getCUMvField(eRefPicList2nd)->getRefIdx(uiIdx) >= 0)
5710  {
5711    iNeibRefPOC = pcTmpCU->getSlice()->getRefPOC( eRefPicList2nd, pcTmpCU->getCUMvField(eRefPicList2nd)->getRefIdx(uiIdx) );
5712    TComMv cMvPred = pcTmpCU->getCUMvField(eRefPicList2nd)->getMv(uiIdx);
5713    TComMv rcMv;
5714
5715    bIsNeibRefLongTerm = pcTmpCU->getSlice()->getRefPic( eRefPicList2nd, pcTmpCU->getCUMvField(eRefPicList2nd)->getRefIdx(uiIdx) )->getIsLongTerm();
5716    if ( bIsCurrRefLongTerm == bIsNeibRefLongTerm ) 
5717    {
5718    if ( bIsCurrRefLongTerm || bIsNeibRefLongTerm )
5719    {
5720      rcMv = cMvPred;
5721    }
5722    else
5723    {
5724      Int iScale = xGetDistScaleFactor( iCurrPOC, iCurrRefPOC, iNeibPOC, iNeibRefPOC );
5725      if ( iScale == 4096 )
5726      {
5727        rcMv = cMvPred;
5728      }
5729      else
5730      {
5731        rcMv = cMvPred.scaleMv( iScale );
5732      }
5733    }
5734    pInfo->m_acMvCand[ pInfo->iN++] = rcMv;
5735    return true;
5736    }
5737  }
5738  //---------------------- V3(END) --------------------//
5739  return false;
5740}
5741
5742/**
5743 * \param eRefPicList
5744 * \param uiCUAddr
5745 * \param uiPartUnitIdx
5746 * \param riRefIdx
5747 * \returns Bool
5748 */
5749Bool TComDataCU::xGetColMVP( RefPicList eRefPicList, Int uiCUAddr, Int uiPartUnitIdx, TComMv& rcMv, Int& riRefIdx
5750#if H_3D_TMVP
5751  , Bool bMRG
5752#endif
5753  )
5754{
5755  UInt uiAbsPartAddr = uiPartUnitIdx;
5756
5757  RefPicList  eColRefPicList;
5758  Int iColPOC, iColRefPOC, iCurrPOC, iCurrRefPOC, iScale;
5759  TComMv cColMv;
5760
5761  // use coldir.
5762  TComPic *pColPic = getSlice()->getRefPic( RefPicList(getSlice()->isInterB() ? 1-getSlice()->getColFromL0Flag() : 0), getSlice()->getColRefIdx());
5763  TComDataCU *pColCU = pColPic->getCU( uiCUAddr );
5764  if(pColCU->getPic()==0||pColCU->getPartitionSize(uiPartUnitIdx)==SIZE_NONE)
5765  {
5766    return false;
5767  }
5768  iCurrPOC = m_pcSlice->getPOC();   
5769  iColPOC = pColCU->getSlice()->getPOC(); 
5770
5771  if (pColCU->isIntra(uiAbsPartAddr))
5772  {
5773    return false;
5774  }
5775  eColRefPicList = getSlice()->getCheckLDC() ? eRefPicList : RefPicList(getSlice()->getColFromL0Flag());
5776
5777  Int iColRefIdx = pColCU->getCUMvField(RefPicList(eColRefPicList))->getRefIdx(uiAbsPartAddr);
5778
5779  if (iColRefIdx < 0 )
5780  {
5781    eColRefPicList = RefPicList(1 - eColRefPicList);
5782    iColRefIdx = pColCU->getCUMvField(RefPicList(eColRefPicList))->getRefIdx(uiAbsPartAddr);
5783
5784    if (iColRefIdx < 0 )
5785    {
5786      return false;
5787    }
5788  }
5789
5790  // Scale the vector.
5791  iColRefPOC = pColCU->getSlice()->getRefPOC(eColRefPicList, iColRefIdx);
5792  cColMv = pColCU->getCUMvField(eColRefPicList)->getMv(uiAbsPartAddr);
5793
5794  iCurrRefPOC = m_pcSlice->getRefPic(eRefPicList, riRefIdx)->getPOC();
5795  Bool bIsCurrRefLongTerm = m_pcSlice->getRefPic(eRefPicList, riRefIdx)->getIsLongTerm();
5796  Bool bIsColRefLongTerm = pColCU->getSlice()->getIsUsedAsLongTerm(eColRefPicList, iColRefIdx);
5797
5798  if ( bIsCurrRefLongTerm != bIsColRefLongTerm ) 
5799  {
5800#if H_3D_TMVP
5801    Int iAlterRefIdx  = m_pcSlice->getAlterRefIdx(eRefPicList);
5802    if(bMRG && iAlterRefIdx > 0)
5803    {
5804      riRefIdx = iAlterRefIdx;
5805      bIsCurrRefLongTerm = m_pcSlice->getRefPic(eRefPicList, riRefIdx)->getIsLongTerm();
5806      iCurrRefPOC = m_pcSlice->getRefPic(eRefPicList, riRefIdx)->getPOC();
5807      assert(bIsCurrRefLongTerm == bIsColRefLongTerm);
5808    }
5809    else
5810    {
5811#endif
5812      return false;
5813#if H_3D_TMVP
5814    }
5815#endif
5816  }
5817
5818  if ( bIsCurrRefLongTerm || bIsColRefLongTerm )
5819  {
5820#if H_3D_TMVP
5821    Int iCurrViewId    = m_pcSlice->getViewIndex (); 
5822    Int iCurrRefViewId = m_pcSlice->getRefPic(eRefPicList, riRefIdx)->getViewIndex (); 
5823    Int iColViewId     = pColCU->getSlice()->getViewIndex(); 
5824    Int iColRefViewId  = pColCU->getSlice()->getRefPic( eColRefPicList, pColCU->getCUMvField(eColRefPicList)->getRefIdx(uiAbsPartAddr))->getViewIndex(); 
5825    iScale = xGetDistScaleFactor( iCurrViewId, iCurrRefViewId, iColViewId, iColRefViewId );
5826    if ( iScale != 4096 && m_pcSlice->getVPS()->getIvMvScalingFlag() ) 
5827    {
5828      rcMv = cColMv.scaleMv( iScale );
5829    }
5830    else
5831    {
5832#endif
5833       rcMv = cColMv;
5834#if H_3D_TMVP
5835    }
5836#endif
5837  }
5838  else
5839  {
5840    iScale = xGetDistScaleFactor(iCurrPOC, iCurrRefPOC, iColPOC, iColRefPOC);
5841    if ( iScale == 4096 )
5842    {
5843      rcMv = cColMv;
5844    }
5845    else
5846    {
5847      rcMv = cColMv.scaleMv( iScale );
5848    }
5849  }
5850  return true;
5851}
5852
5853UInt TComDataCU::xGetMvdBits(TComMv cMvd)
5854{
5855  return ( xGetComponentBits(cMvd.getHor()) + xGetComponentBits(cMvd.getVer()) );
5856}
5857
5858UInt TComDataCU::xGetComponentBits(Int iVal)
5859{
5860  UInt uiLength = 1;
5861  UInt uiTemp   = ( iVal <= 0) ? (-iVal<<1)+1: (iVal<<1);
5862 
5863  assert ( uiTemp );
5864 
5865  while ( 1 != uiTemp )
5866  {
5867    uiTemp >>= 1;
5868    uiLength += 2;
5869  }
5870 
5871  return uiLength;
5872}
5873
5874
5875Int TComDataCU::xGetDistScaleFactor(Int iCurrPOC, Int iCurrRefPOC, Int iColPOC, Int iColRefPOC)
5876{
5877  Int iDiffPocD = iColPOC - iColRefPOC;
5878  Int iDiffPocB = iCurrPOC - iCurrRefPOC;
5879 
5880  if( iDiffPocD == iDiffPocB )
5881  {
5882    return 4096;
5883  }
5884  else
5885  {
5886    Int iTDB      = Clip3( -128, 127, iDiffPocB );
5887    Int iTDD      = Clip3( -128, 127, iDiffPocD );
5888    Int iX        = (0x4000 + abs(iTDD/2)) / iTDD;
5889    Int iScale    = Clip3( -4096, 4095, (iTDB * iX + 32) >> 6 );
5890    return iScale;
5891  }
5892}
5893
5894/**
5895 * \param eCUMode
5896 * \param uiPartIdx
5897 * \param ruiPartIdxCenter
5898 * \returns Void
5899 */
5900Void TComDataCU::xDeriveCenterIdx( UInt uiPartIdx, UInt& ruiPartIdxCenter )
5901{
5902  UInt uiPartAddr;
5903  Int  iPartWidth;
5904  Int  iPartHeight;
5905  getPartIndexAndSize( uiPartIdx, uiPartAddr, iPartWidth, iPartHeight);
5906 
5907  ruiPartIdxCenter = m_uiAbsIdxInLCU+uiPartAddr; // partition origin.
5908  ruiPartIdxCenter = g_auiRasterToZscan[ g_auiZscanToRaster[ ruiPartIdxCenter ]
5909                                        + ( iPartHeight/m_pcPic->getMinCUHeight()  )/2*m_pcPic->getNumPartInWidth()
5910                                        + ( iPartWidth/m_pcPic->getMinCUWidth()  )/2];
5911}
5912#if H_3D
5913Void TComDataCU::compressMV(Int scale)
5914#else
5915Void TComDataCU::compressMV()
5916#endif
5917{
5918#if H_3D
5919  Int scaleFactor = (4 / scale ) * AMVP_DECIMATION_FACTOR / m_unitSize;
5920#else
5921  Int scaleFactor = 4 * AMVP_DECIMATION_FACTOR / m_unitSize;
5922#endif
5923  if (scaleFactor > 0)
5924  {
5925    m_acCUMvField[0].compress(m_pePredMode, scaleFactor);
5926    m_acCUMvField[1].compress(m_pePredMode, scaleFactor);   
5927  }
5928}
5929
5930UInt TComDataCU::getCoefScanIdx(UInt uiAbsPartIdx, UInt uiWidth, Bool bIsLuma, Bool bIsIntra)
5931{
5932  UInt uiCTXIdx;
5933  UInt uiScanIdx;
5934  UInt uiDirMode;
5935
5936  if ( !bIsIntra ) 
5937  {
5938    uiScanIdx = SCAN_DIAG;
5939    return uiScanIdx;
5940  }
5941
5942  switch(uiWidth)
5943  {
5944    case  2: uiCTXIdx = 6; break;
5945    case  4: uiCTXIdx = 5; break;
5946    case  8: uiCTXIdx = 4; break;
5947    case 16: uiCTXIdx = 3; break;
5948    case 32: uiCTXIdx = 2; break;
5949    case 64: uiCTXIdx = 1; break;
5950    default: uiCTXIdx = 0; break;
5951  }
5952
5953  if ( bIsLuma )
5954  {
5955    uiDirMode = getLumaIntraDir(uiAbsPartIdx);
5956#if H_3D_DIM
5957    mapDepthModeToIntraDir( uiDirMode );
5958#endif
5959    uiScanIdx = SCAN_DIAG;
5960    if (uiCTXIdx >3 && uiCTXIdx < 6) //if multiple scans supported for transform size
5961    {
5962      uiScanIdx = abs((Int) uiDirMode - VER_IDX) < 5 ? SCAN_HOR : (abs((Int)uiDirMode - HOR_IDX) < 5 ? SCAN_VER : SCAN_DIAG);
5963    }
5964  }
5965  else
5966  {
5967    uiDirMode = getChromaIntraDir(uiAbsPartIdx);
5968    if( uiDirMode == DM_CHROMA_IDX )
5969    {
5970      // get number of partitions in current CU
5971      UInt depth = getDepth(uiAbsPartIdx);
5972      UInt numParts = getPic()->getNumPartInCU() >> (2 * depth);
5973     
5974      // get luma mode from upper-left corner of current CU
5975      uiDirMode = getLumaIntraDir((uiAbsPartIdx/numParts)*numParts);
5976#if H_3D_DIM
5977      mapDepthModeToIntraDir( uiDirMode );
5978#endif
5979    }
5980    uiScanIdx = SCAN_DIAG;
5981    if (uiCTXIdx >4 && uiCTXIdx < 7) //if multiple scans supported for transform size
5982    {
5983      uiScanIdx = abs((Int) uiDirMode - VER_IDX) < 5 ? SCAN_HOR : (abs((Int)uiDirMode - HOR_IDX) < 5 ? SCAN_VER : SCAN_DIAG);
5984    }
5985  }
5986
5987  return uiScanIdx;
5988}
5989
5990UInt TComDataCU::getSCUAddr()
5991{ 
5992  return getPic()->getPicSym()->getInverseCUOrderMap(m_uiCUAddr)*(1<<(m_pcSlice->getSPS()->getMaxCUDepth()<<1))+m_uiAbsIdxInLCU; 
5993}
5994
5995/** Set neighboring blocks availabilities for non-deblocked filtering
5996 * \param numLCUInPicWidth number of LCUs in picture width
5997 * \param numLCUInPicHeight number of LCUs in picture height
5998 * \param numSUInLCUWidth number of SUs in LCU width
5999 * \param numSUInLCUHeight number of SUs in LCU height
6000 * \param picWidth picture width
6001 * \param picHeight picture height
6002 * \param bIndependentSliceBoundaryEnabled true for independent slice boundary enabled
6003 * \param bTopTileBoundary true means that top boundary coincides tile boundary
6004 * \param bDownTileBoundary true means that bottom boundary coincides tile boundary
6005 * \param bLeftTileBoundary true means that left boundary coincides tile boundary
6006 * \param bRightTileBoundary true means that right boundary coincides tile boundary
6007 * \param bIndependentTileBoundaryEnabled true for independent tile boundary enabled
6008 */
6009Void TComDataCU::setNDBFilterBlockBorderAvailability(UInt numLCUInPicWidth, UInt /*numLCUInPicHeight*/, UInt numSUInLCUWidth, UInt numSUInLCUHeight, UInt picWidth, UInt picHeight
6010                                                    ,std::vector<Bool>& LFCrossSliceBoundary
6011                                                    ,Bool bTopTileBoundary, Bool bDownTileBoundary, Bool bLeftTileBoundary, Bool bRightTileBoundary
6012                                                    ,Bool bIndependentTileBoundaryEnabled)
6013{
6014  UInt numSUInLCU = numSUInLCUWidth*numSUInLCUHeight;
6015  Int* pSliceIDMapLCU = m_piSliceSUMap;
6016  Bool onlyOneSliceInPic = ((Int)LFCrossSliceBoundary.size() == 1);
6017  UInt uiLPelX, uiTPelY;
6018  UInt width, height;
6019  Bool bPicRBoundary, bPicBBoundary, bPicTBoundary, bPicLBoundary;
6020  Bool bLCURBoundary= false, bLCUBBoundary= false, bLCUTBoundary= false, bLCULBoundary= false;
6021  Bool* pbAvailBorder;
6022  Bool* pbAvail;
6023  UInt rTLSU, rBRSU, widthSU, heightSU;
6024  UInt zRefSU;
6025  Int* pRefID;
6026  Int* pRefMapLCU;
6027  UInt rTRefSU= 0, rBRefSU= 0, rLRefSU= 0, rRRefSU= 0;
6028  Int* pRRefMapLCU= NULL;
6029  Int* pLRefMapLCU= NULL;
6030  Int* pTRefMapLCU= NULL;
6031  Int* pBRefMapLCU= NULL;
6032  Int  sliceID;
6033  UInt numSGU = (UInt)m_vNDFBlock.size();
6034
6035  for(Int i=0; i< numSGU; i++)
6036  {
6037    NDBFBlockInfo& rSGU = m_vNDFBlock[i];
6038
6039    sliceID = rSGU.sliceID;
6040    uiLPelX = rSGU.posX;
6041    uiTPelY = rSGU.posY;
6042    width   = rSGU.width;
6043    height  = rSGU.height;
6044    rTLSU     = g_auiZscanToRaster[ rSGU.startSU ];
6045    rBRSU     = g_auiZscanToRaster[ rSGU.endSU   ];
6046    widthSU   = rSGU.widthSU;
6047    heightSU  = rSGU.heightSU;
6048
6049    pbAvailBorder = rSGU.isBorderAvailable;
6050
6051    bPicTBoundary= (uiTPelY == 0                       )?(true):(false);
6052    bPicLBoundary= (uiLPelX == 0                       )?(true):(false);
6053    bPicRBoundary= (!(uiLPelX+ width < picWidth )  )?(true):(false);
6054    bPicBBoundary= (!(uiTPelY + height < picHeight))?(true):(false);
6055
6056    bLCULBoundary = (rTLSU % numSUInLCUWidth == 0)?(true):(false);
6057    bLCURBoundary = ( (rTLSU+ widthSU) % numSUInLCUWidth == 0)?(true):(false);
6058    bLCUTBoundary = ( (UInt)(rTLSU / numSUInLCUWidth)== 0)?(true):(false);
6059    bLCUBBoundary = ( (UInt)(rBRSU / numSUInLCUWidth) == (numSUInLCUHeight-1) )?(true):(false);
6060
6061    //       SGU_L
6062    pbAvail = &(pbAvailBorder[SGU_L]);
6063    if(bPicLBoundary)
6064    {
6065      *pbAvail = false;
6066    }
6067    else if (onlyOneSliceInPic)
6068    {
6069      *pbAvail = true;
6070    }
6071    else
6072    {
6073      //      bLCULBoundary = (rTLSU % uiNumSUInLCUWidth == 0)?(true):(false);
6074      if(bLCULBoundary)
6075      {
6076        rLRefSU     = rTLSU + numSUInLCUWidth -1;
6077        zRefSU      = g_auiRasterToZscan[rLRefSU];
6078        pRefMapLCU = pLRefMapLCU= (pSliceIDMapLCU - numSUInLCU);
6079      }
6080      else
6081      {
6082        zRefSU   = g_auiRasterToZscan[rTLSU - 1];
6083        pRefMapLCU  = pSliceIDMapLCU;
6084      }
6085      pRefID = pRefMapLCU + zRefSU;
6086      *pbAvail = (*pRefID == sliceID)?(true):((*pRefID > sliceID)?(LFCrossSliceBoundary[*pRefID]):(LFCrossSliceBoundary[sliceID]));
6087    }
6088
6089    //       SGU_R
6090    pbAvail = &(pbAvailBorder[SGU_R]);
6091    if(bPicRBoundary)
6092    {
6093      *pbAvail = false;
6094    }
6095    else if (onlyOneSliceInPic)
6096    {
6097      *pbAvail = true;
6098    }
6099    else
6100    {
6101      //       bLCURBoundary = ( (rTLSU+ uiWidthSU) % uiNumSUInLCUWidth == 0)?(true):(false);
6102      if(bLCURBoundary)
6103      {
6104        rRRefSU      = rTLSU + widthSU - numSUInLCUWidth;
6105        zRefSU       = g_auiRasterToZscan[rRRefSU];
6106        pRefMapLCU  = pRRefMapLCU= (pSliceIDMapLCU + numSUInLCU);
6107      }
6108      else
6109      {
6110        zRefSU       = g_auiRasterToZscan[rTLSU + widthSU];
6111        pRefMapLCU  = pSliceIDMapLCU;
6112      }
6113      pRefID = pRefMapLCU + zRefSU;
6114      *pbAvail = (*pRefID == sliceID)?(true):((*pRefID > sliceID)?(LFCrossSliceBoundary[*pRefID]):(LFCrossSliceBoundary[sliceID]));
6115    }
6116
6117    //       SGU_T
6118    pbAvail = &(pbAvailBorder[SGU_T]);
6119    if(bPicTBoundary)
6120    {
6121      *pbAvail = false;
6122    }
6123    else if (onlyOneSliceInPic)
6124    {
6125      *pbAvail = true;
6126    }
6127    else
6128    {
6129      //      bLCUTBoundary = ( (UInt)(rTLSU / uiNumSUInLCUWidth)== 0)?(true):(false);
6130      if(bLCUTBoundary)
6131      {
6132        rTRefSU      = numSUInLCU - (numSUInLCUWidth - rTLSU);
6133        zRefSU       = g_auiRasterToZscan[rTRefSU];
6134        pRefMapLCU  = pTRefMapLCU= (pSliceIDMapLCU - (numLCUInPicWidth*numSUInLCU));
6135      }
6136      else
6137      {
6138        zRefSU       = g_auiRasterToZscan[rTLSU - numSUInLCUWidth];
6139        pRefMapLCU  = pSliceIDMapLCU;
6140      }
6141      pRefID = pRefMapLCU + zRefSU;
6142      *pbAvail = (*pRefID == sliceID)?(true):((*pRefID > sliceID)?(LFCrossSliceBoundary[*pRefID]):(LFCrossSliceBoundary[sliceID]));
6143    }
6144
6145    //       SGU_B
6146    pbAvail = &(pbAvailBorder[SGU_B]);
6147    if(bPicBBoundary)
6148    {
6149      *pbAvail = false;
6150    }
6151    else if (onlyOneSliceInPic)
6152    {
6153      *pbAvail = true;
6154    }
6155    else
6156    {
6157      //      bLCUBBoundary = ( (UInt)(rBRSU / uiNumSUInLCUWidth) == (uiNumSUInLCUHeight-1) )?(true):(false);
6158      if(bLCUBBoundary)
6159      {
6160        rBRefSU      = rTLSU % numSUInLCUWidth;
6161        zRefSU       = g_auiRasterToZscan[rBRefSU];
6162        pRefMapLCU  = pBRefMapLCU= (pSliceIDMapLCU + (numLCUInPicWidth*numSUInLCU));
6163      }
6164      else
6165      {
6166        zRefSU       = g_auiRasterToZscan[rTLSU + (heightSU*numSUInLCUWidth)];
6167        pRefMapLCU  = pSliceIDMapLCU;
6168      }
6169      pRefID = pRefMapLCU + zRefSU;
6170      *pbAvail = (*pRefID == sliceID)?(true):((*pRefID > sliceID)?(LFCrossSliceBoundary[*pRefID]):(LFCrossSliceBoundary[sliceID]));
6171    }
6172
6173    //       SGU_TL
6174    pbAvail = &(pbAvailBorder[SGU_TL]);
6175    if(bPicTBoundary || bPicLBoundary)
6176    {
6177      *pbAvail = false;
6178    }
6179    else if (onlyOneSliceInPic)
6180    {
6181      *pbAvail = true;
6182    }
6183    else
6184    {
6185      if(bLCUTBoundary && bLCULBoundary)
6186      {
6187        zRefSU       = numSUInLCU -1;
6188        pRefMapLCU  = pSliceIDMapLCU - ( (numLCUInPicWidth+1)*numSUInLCU);
6189      }
6190      else if(bLCUTBoundary)
6191      {
6192        zRefSU       = g_auiRasterToZscan[ rTRefSU- 1];
6193        pRefMapLCU  = pTRefMapLCU;
6194      }
6195      else if(bLCULBoundary)
6196      {
6197        zRefSU       = g_auiRasterToZscan[ rLRefSU- numSUInLCUWidth ];
6198        pRefMapLCU  = pLRefMapLCU;
6199      }
6200      else //inside LCU
6201      {
6202        zRefSU       = g_auiRasterToZscan[ rTLSU - numSUInLCUWidth -1];
6203        pRefMapLCU  = pSliceIDMapLCU;
6204      }
6205      pRefID = pRefMapLCU + zRefSU;
6206      *pbAvail = (*pRefID == sliceID)?(true):((*pRefID > sliceID)?(LFCrossSliceBoundary[*pRefID]):(LFCrossSliceBoundary[sliceID]));
6207    }
6208
6209    //       SGU_TR
6210    pbAvail = &(pbAvailBorder[SGU_TR]);
6211    if(bPicTBoundary || bPicRBoundary)
6212    {
6213      *pbAvail = false;
6214    }
6215    else if (onlyOneSliceInPic)
6216    {
6217      *pbAvail = true;
6218    }
6219    else
6220    {
6221      if(bLCUTBoundary && bLCURBoundary)
6222      {
6223        zRefSU      = g_auiRasterToZscan[numSUInLCU - numSUInLCUWidth];
6224        pRefMapLCU  = pSliceIDMapLCU - ( (numLCUInPicWidth-1)*numSUInLCU);       
6225      }
6226      else if(bLCUTBoundary)
6227      {
6228        zRefSU       = g_auiRasterToZscan[ rTRefSU+ widthSU];
6229        pRefMapLCU  = pTRefMapLCU;
6230      }
6231      else if(bLCURBoundary)
6232      {
6233        zRefSU       = g_auiRasterToZscan[ rRRefSU- numSUInLCUWidth ];
6234        pRefMapLCU  = pRRefMapLCU;
6235      }
6236      else //inside LCU
6237      {
6238        zRefSU       = g_auiRasterToZscan[ rTLSU - numSUInLCUWidth +widthSU];
6239        pRefMapLCU  = pSliceIDMapLCU;
6240      }
6241      pRefID = pRefMapLCU + zRefSU;
6242      *pbAvail = (*pRefID == sliceID)?(true):((*pRefID > sliceID)?(LFCrossSliceBoundary[*pRefID]):(LFCrossSliceBoundary[sliceID]));
6243    }
6244
6245    //       SGU_BL
6246    pbAvail = &(pbAvailBorder[SGU_BL]);
6247    if(bPicBBoundary || bPicLBoundary)
6248    {
6249      *pbAvail = false;
6250    }
6251    else if (onlyOneSliceInPic)
6252    {
6253      *pbAvail = true;
6254    }
6255    else
6256    {
6257      if(bLCUBBoundary && bLCULBoundary)
6258      {
6259        zRefSU      = g_auiRasterToZscan[numSUInLCUWidth - 1];
6260        pRefMapLCU  = pSliceIDMapLCU + ( (numLCUInPicWidth-1)*numSUInLCU);       
6261      }
6262      else if(bLCUBBoundary)
6263      {
6264        zRefSU       = g_auiRasterToZscan[ rBRefSU - 1];
6265        pRefMapLCU  = pBRefMapLCU;
6266      }
6267      else if(bLCULBoundary)
6268      {
6269        zRefSU       = g_auiRasterToZscan[ rLRefSU+ heightSU*numSUInLCUWidth ];
6270        pRefMapLCU  = pLRefMapLCU;
6271      }
6272      else //inside LCU
6273      {
6274        zRefSU       = g_auiRasterToZscan[ rTLSU + heightSU*numSUInLCUWidth -1];
6275        pRefMapLCU  = pSliceIDMapLCU;
6276      }
6277      pRefID = pRefMapLCU + zRefSU;
6278      *pbAvail = (*pRefID == sliceID)?(true):((*pRefID > sliceID)?(LFCrossSliceBoundary[*pRefID]):(LFCrossSliceBoundary[sliceID]));
6279    }
6280
6281    //       SGU_BR
6282    pbAvail = &(pbAvailBorder[SGU_BR]);
6283    if(bPicBBoundary || bPicRBoundary)
6284    {
6285      *pbAvail = false;
6286    }
6287    else if (onlyOneSliceInPic)
6288    {
6289      *pbAvail = true;
6290    }
6291    else
6292    {
6293      if(bLCUBBoundary && bLCURBoundary)
6294      {
6295        zRefSU = 0;
6296        pRefMapLCU = pSliceIDMapLCU+ ( (numLCUInPicWidth+1)*numSUInLCU);
6297      }
6298      else if(bLCUBBoundary)
6299      {
6300        zRefSU      = g_auiRasterToZscan[ rBRefSU + widthSU];
6301        pRefMapLCU = pBRefMapLCU;
6302      }
6303      else if(bLCURBoundary)
6304      {
6305        zRefSU      = g_auiRasterToZscan[ rRRefSU + (heightSU*numSUInLCUWidth)];
6306        pRefMapLCU = pRRefMapLCU;
6307      }
6308      else //inside LCU
6309      {
6310        zRefSU      = g_auiRasterToZscan[ rTLSU + (heightSU*numSUInLCUWidth)+ widthSU];
6311        pRefMapLCU = pSliceIDMapLCU;
6312      }
6313      pRefID = pRefMapLCU + zRefSU;
6314      *pbAvail = (*pRefID == sliceID)?(true):((*pRefID > sliceID)?(LFCrossSliceBoundary[*pRefID]):(LFCrossSliceBoundary[sliceID]));
6315    }
6316
6317    if(bIndependentTileBoundaryEnabled)
6318    {
6319      //left LCU boundary
6320      if(!bPicLBoundary && bLCULBoundary)
6321      {
6322        if(bLeftTileBoundary)
6323        {
6324          pbAvailBorder[SGU_L] = pbAvailBorder[SGU_TL] = pbAvailBorder[SGU_BL] = false;
6325        }
6326      }
6327      //right LCU boundary
6328      if(!bPicRBoundary && bLCURBoundary)
6329      {
6330        if(bRightTileBoundary)
6331        {
6332          pbAvailBorder[SGU_R] = pbAvailBorder[SGU_TR] = pbAvailBorder[SGU_BR] = false;
6333        }
6334      }
6335      //top LCU boundary
6336      if(!bPicTBoundary && bLCUTBoundary)
6337      {
6338        if(bTopTileBoundary)
6339        {
6340          pbAvailBorder[SGU_T] = pbAvailBorder[SGU_TL] = pbAvailBorder[SGU_TR] = false;
6341        }
6342      }
6343      //down LCU boundary
6344      if(!bPicBBoundary && bLCUBBoundary)
6345      {
6346        if(bDownTileBoundary)
6347        {
6348          pbAvailBorder[SGU_B] = pbAvailBorder[SGU_BL] = pbAvailBorder[SGU_BR] = false;
6349        }
6350      }
6351    }
6352    rSGU.allBordersAvailable = true;
6353    for(Int b=0; b< NUM_SGU_BORDER; b++)
6354    {
6355      if(pbAvailBorder[b] == false)
6356      {
6357        rSGU.allBordersAvailable = false;
6358        break;
6359      }
6360    }
6361  }
6362}
6363
6364#if H_3D
6365Void TComDataCU::getPosInPic( UInt uiAbsPartIndex, Int& riPosX, Int& riPosY )
6366{
6367  riPosX = g_auiRasterToPelX[g_auiZscanToRaster[uiAbsPartIndex]] + getCUPelX();
6368  riPosY = g_auiRasterToPelY[g_auiZscanToRaster[uiAbsPartIndex]] + getCUPelY(); 
6369}
6370#endif
6371#if H_3D_IV_MERGE
6372Bool TComDataCU::getDispNeighBlocks (UInt uiPartIdx, UInt uiPartAddr, DisInfo* pDisp)
6373{
6374  Pel pDepPos[3] = {0, 0, 0};
6375  assert(getPartitionSize( uiPartAddr ) == SIZE_2Nx2N);
6376  Bool bDepAvail = false;
6377  Pel *pDepth  = this->getPic()->getPicYuvRec()->getLumaAddr();
6378  Int iDepStride =  this->getPic()->getPicYuvRec()->getStride();
6379  TComMv cMv; 
6380
6381  Int xP, yP, nPSW, nPSH;
6382  this->getPartPosition(uiPartIdx, xP, yP, nPSW, nPSH);
6383
6384  if(xP != 0 && yP != 0)
6385  {
6386    pDepPos[0] = pDepth[ (yP-1) * iDepStride + (xP-1) ];
6387    bDepAvail = true;
6388  }
6389
6390  if(xP != 0)
6391  {
6392    pDepPos[1] = pDepth[ (yP+nPSH-1) * iDepStride + (xP-1) ];
6393    bDepAvail = true;
6394  }
6395
6396  if(yP != 0)
6397  {
6398    pDepPos[2] = pDepth[ (yP-1) * iDepStride + (xP+nPSW-1) ];
6399    bDepAvail = true;
6400  }
6401
6402  if (bDepAvail)
6403  {
6404    Pel pAvgDepth = (xP != 0 && yP != 0) ? ((5*pDepPos[0] + 5*pDepPos[1] + 6*pDepPos[2] + 8)>>4) : (xP == 0) ? pDepPos[2] : pDepPos[1];
6405    Int iDisp     = getSlice()->getDepthToDisparityB( 0 )[ pAvgDepth ];
6406    cMv.setHor(iDisp);
6407    cMv.setVer(0);
6408    pDisp->m_acNBDV = cMv;
6409    pDisp->m_aVIdxCan = 0;
6410    return true;
6411  }
6412  else
6413  { 
6414    cMv.setZero();
6415    pDisp->m_acNBDV = cMv;
6416    pDisp->m_aVIdxCan = 0;
6417    return false;
6418  }
6419}
6420#endif
6421#if H_3D_NBDV
6422//Notes from QC:
6423//TBD#1: DoNBDV related contributions are just partially integrated under the marco of H_3D_NBDV_REF, remove this comment once DoNBDV and BVSP are done
6424//TBD#2: set of DvMCP values need to be done as part of inter-view motion prediction process. Remove this comment once merge related integration is done
6425//To be checked: Parallel Merge features for NBDV, related to DV_DERIVATION_PARALLEL_B0096 and LGE_IVMP_PARALLEL_MERGE_B0136 are not integrated. The need of these features due to the adoption of CU-based NBDV is not clear. We need confirmation on this, especially by proponents
6426Bool TComDataCU::getDisMvpCandNBDV( DisInfo* pDInfo
6427#if H_3D_NBDV_REF
6428, Bool bDepthRefine
6429#endif
6430)
6431{
6432  //// ******* Init variables ******* /////
6433  // Init disparity struct for results
6434  pDInfo->bDV = false;   
6435#if MTK_NBDV_IVREF_FIX_G0067
6436  pDInfo->m_aVIdxCan = -1;
6437#endif
6438  // Init struct for disparities from MCP neighboring blocks
6439  IDVInfo cIDVInfo;
6440  cIDVInfo.m_bFound = false; 
6441  UInt uiPartIdx = 0;
6442  UInt uiPartAddr = 0;
6443  for (UInt iCurDvMcpCand = 0; iCurDvMcpCand < IDV_CANDS; iCurDvMcpCand++)
6444  {
6445    for (UInt iList = 0; iList < 2; iList++)
6446    {
6447      cIDVInfo.m_acMvCand[iList][iCurDvMcpCand].setZero();
6448      cIDVInfo.m_aVIdxCan[iList][iCurDvMcpCand] = 0; 
6449      cIDVInfo.m_bAvailab[iList][iCurDvMcpCand] = false; 
6450    }
6451  }
6452#if H_3D_NBDV_REF
6453  if( !m_pcSlice->getVPS()->getDepthRefinementFlag( m_pcSlice->getLayerIdInVps() ) )
6454  {
6455    bDepthRefine = false;
6456  }
6457#endif
6458  // Get Positions 
6459  PartSize eCUMode    = getPartitionSize( uiPartAddr );   
6460  assert(eCUMode == SIZE_2Nx2N);
6461  UInt uiPartIdxLT, uiPartIdxRT, uiPartIdxLB; 
6462
6463  deriveLeftRightTopIdxGeneral(uiPartAddr, uiPartIdx, uiPartIdxLT, uiPartIdxRT );
6464  deriveLeftBottomIdxGeneral  (uiPartAddr, uiPartIdx, uiPartIdxLB );
6465
6466  //// ******* Get disparity from temporal neighboring blocks ******* /////
6467  if ( getSlice()->getEnableTMVPFlag() )
6468  {
6469    TComMv cColMv;
6470    Int iTargetViewIdx = 0;
6471    Int iTStartViewIdx = 0;   
6472
6473    ///*** Derive center position ***
6474    UInt uiPartIdxCenter;
6475    Int  uiLCUIdx   = getAddr();
6476    xDeriveCenterIdx(uiPartIdx, uiPartIdxCenter );
6477
6478    ///*** Search temporal candidate pictures for disparity vector ***
6479    const Int iNumCandPics = getPic()->getNumDdvCandPics();
6480    for(Int curCandPic = 0; curCandPic < iNumCandPics; curCandPic++)
6481    {
6482      RefPicList eCurRefPicList   = REF_PIC_LIST_0 ;
6483      Int        curCandPicRefIdx = 0;
6484      if( curCandPic == 0 ) 
6485      { 
6486        eCurRefPicList   = RefPicList(getSlice()->isInterB() ? 1-getSlice()->getColFromL0Flag() : 0);
6487        curCandPicRefIdx = getSlice()->getColRefIdx();
6488      }
6489      else                 
6490      {
6491        eCurRefPicList   = getPic()->getRapRefList();
6492        curCandPicRefIdx = getPic()->getRapRefIdx();
6493      }
6494
6495      Bool bCheck = xGetColDisMV( curCandPic, eCurRefPicList, curCandPicRefIdx, uiLCUIdx,   uiPartIdxCenter,  cColMv, iTargetViewIdx, iTStartViewIdx );
6496
6497      if( bCheck )
6498      {
6499        clipMv(cColMv);
6500        pDInfo->m_acNBDV = cColMv;
6501        pDInfo->m_aVIdxCan  = iTargetViewIdx;
6502
6503#if H_3D_NBDV_REF
6504        TComPic* picDepth = NULL;   
6505#if H_3D_FCO_VSP_DONBDV_E0163
6506        picDepth  = getSlice()->getIvPic(true, getSlice()->getViewIndex() );
6507        if ( picDepth->getPicYuvRec() != NULL  ) 
6508        {
6509          cColMv.setZero();
6510        }
6511        else // Go back with virtual depth
6512        {
6513          picDepth = getSlice()->getIvPic( true, iTargetViewIdx );
6514        }
6515
6516        assert(picDepth != NULL);
6517#else
6518        picDepth = getSlice()->getIvPic( true, iTargetViewIdx );
6519        assert(picDepth != NULL);
6520#endif
6521        if (picDepth && bDepthRefine)
6522          estimateDVFromDM(iTargetViewIdx, uiPartIdx, picDepth, uiPartAddr, &cColMv );
6523
6524        pDInfo->m_acDoNBDV  = cColMv;
6525#endif //H_3D_NBDV_REF
6526        return true;
6527      }
6528    }
6529  } 
6530
6531  UInt uiIdx = 0;
6532  Bool        bCheckMcpDv = false;   
6533  TComDataCU* pcTmpCU     = NULL;
6534
6535  //// ******* Get disparity from left block ******* /////
6536  pcTmpCU = getPULeft(uiIdx, uiPartIdxLB, true, false);
6537  bCheckMcpDv = true; 
6538  if ( xCheckSpatialNBDV( pcTmpCU, uiIdx, pDInfo, bCheckMcpDv, &cIDVInfo, DVFROM_LEFT
6539#if H_3D_NBDV_REF
6540    , bDepthRefine
6541#endif
6542    ) )
6543    return true;
6544
6545  //// ******* Get disparity from above block ******* /////
6546  pcTmpCU = getPUAbove(uiIdx, uiPartIdxRT, true, false, true);
6547  if(pcTmpCU != NULL )
6548  {
6549    bCheckMcpDv = ( ( getAddr() - pcTmpCU->getAddr() ) == 0);
6550    if ( xCheckSpatialNBDV( pcTmpCU, uiIdx, pDInfo, bCheckMcpDv, &cIDVInfo, DVFROM_ABOVE
6551#if H_3D_NBDV_REF
6552      , bDepthRefine
6553#endif
6554      ) )
6555      return true;
6556  }
6557
6558  //// ******* Search MCP blocks ******* /////
6559  if( cIDVInfo.m_bFound ) 
6560  {
6561    for( Int curPos = 0 ; curPos < IDV_CANDS ; curPos++ ) 
6562    {
6563      for(Int iList = 0; iList < (getSlice()->isInterB() ? 2: 1); iList ++)
6564      {
6565        if( cIDVInfo.m_bAvailab[iList][curPos] )
6566        {
6567          TComMv cDispVec = cIDVInfo.m_acMvCand[iList][ curPos ];
6568          clipMv( cDispVec );
6569          pDInfo->m_acNBDV = cDispVec;
6570          pDInfo->m_aVIdxCan = cIDVInfo.m_aVIdxCan[iList][ curPos ];
6571#if H_3D_NBDV_REF
6572#if H_3D_FCO_VSP_DONBDV_E0163
6573          TComPic* picDepth  = NULL;
6574
6575          picDepth  = getSlice()->getIvPic(true, getSlice()->getViewIndex() );
6576          if ( picDepth->getPicYuvRec() != NULL ) 
6577          {
6578            cDispVec.setZero();
6579          }
6580          else // Go back with virtual depth
6581          {
6582            picDepth = getSlice()->getIvPic( true, pDInfo->m_aVIdxCan );
6583          }
6584
6585          assert(picDepth != NULL);
6586#else
6587          TComPic* picDepth = getSlice()->getIvPic( true, pDInfo->m_aVIdxCan );
6588          assert(picDepth!=NULL);
6589#endif
6590
6591          if (picDepth && bDepthRefine)
6592          {
6593            estimateDVFromDM (pDInfo->m_aVIdxCan, uiPartIdx, picDepth, uiPartAddr, &cDispVec);
6594          }
6595          pDInfo->m_acDoNBDV = cDispVec;
6596#endif
6597          return true;
6598        }
6599      }
6600    }
6601  }
6602
6603  TComMv defaultDV(0, 0);
6604  pDInfo->m_acNBDV = defaultDV;
6605
6606  Int valid = 0;
6607  Int viewIndex = 0;
6608  for( UInt uiBId = 0; uiBId < getSlice()->getViewIndex() && valid==0; uiBId++ )
6609  {
6610    UInt        uiBaseId    = uiBId;
6611    TComPic*    pcBasePic   = getSlice()->getIvPic( false, uiBaseId );
6612    for( Int iRefListId = 0; ( iRefListId < (getSlice()->isInterB()? 2:1) ) && !getSlice()->isIntra() && valid==0; iRefListId++ )
6613    {
6614      RefPicList  eRefPicListTest = RefPicList( iRefListId );
6615      Int         iNumRefPics = getSlice()->getNumRefIdx( eRefPicListTest ) ;
6616      for( Int iRefIndex = 0; iRefIndex < iNumRefPics; iRefIndex++ )
6617      { 
6618        if(pcBasePic->getPOC() == getSlice()->getRefPic( eRefPicListTest, iRefIndex )->getPOC() 
6619          && pcBasePic->getViewIndex() == getSlice()->getRefPic( eRefPicListTest, iRefIndex )->getViewIndex())
6620        {
6621          valid=1;
6622          viewIndex = uiBaseId;
6623          break;
6624        }
6625      }
6626    }
6627  }
6628  if(valid)
6629  {
6630    pDInfo->m_aVIdxCan = viewIndex;
6631#if H_3D_NBDV_REF
6632    TComPic* picDepth = NULL;
6633#if H_3D_FCO_VSP_DONBDV_E0163
6634    picDepth  = getSlice()->getIvPic(true, getSlice()->getViewIndex() );
6635    if ( picDepth->getPicYuvRec() != NULL ) 
6636    {
6637      defaultDV.setZero();
6638    }
6639    else // Go back with virtual depth
6640    {
6641      picDepth = getSlice()->getIvPic( true, viewIndex );
6642    }
6643
6644    assert(picDepth != NULL);
6645#else
6646    picDepth = getSlice()->getIvPic( true, viewIndex );
6647    assert(picDepth!=NULL);
6648#endif
6649    if (picDepth && bDepthRefine)
6650    {
6651      estimateDVFromDM(viewIndex, uiPartIdx, picDepth, uiPartAddr, &defaultDV ); // from base view
6652    }
6653    pDInfo->m_acDoNBDV = defaultDV;
6654#endif
6655  }
6656  return false; 
6657}
6658
6659#if H_3D_NBDV_REF
6660Pel TComDataCU::getMcpFromDM(TComPicYuv* pcBaseViewDepthPicYuv, TComMv* mv, Int iBlkX, Int iBlkY, Int iBlkWidth, Int iBlkHeight, Int* aiShiftLUT )
6661{
6662  Int iPictureWidth  = pcBaseViewDepthPicYuv->getWidth();
6663  Int iPictureHeight = pcBaseViewDepthPicYuv->getHeight();
6664 
6665  Int depthStartPosX = Clip3(0,   iPictureWidth - 1,  iBlkX + ((mv->getHor()+2)>>2));
6666  Int depthStartPosY = Clip3(0,   iPictureHeight - 1, iBlkY + ((mv->getVer()+2)>>2));
6667  Int depthEndPosX   = Clip3(0,   iPictureWidth - 1,  iBlkX + iBlkWidth - 1 + ((mv->getHor()+2)>>2));
6668  Int depthEndPosY   = Clip3(0,   iPictureHeight - 1, iBlkY + iBlkHeight - 1 + ((mv->getVer()+2)>>2));
6669
6670  Pel* depthTL  = pcBaseViewDepthPicYuv->getLumaAddr();
6671  Int depStride =  pcBaseViewDepthPicYuv->getStride();
6672
6673  Pel  maxDepthVal = 0;
6674  maxDepthVal = std::max( maxDepthVal, depthTL[ (depthStartPosY) * depStride + depthStartPosX ]);      // Left Top
6675  maxDepthVal = std::max( maxDepthVal, depthTL[ (depthEndPosY)   * depStride + depthStartPosX ]);      // Left Bottom
6676  maxDepthVal = std::max( maxDepthVal, depthTL[ (depthStartPosY) * depStride + depthEndPosX   ]);      // Right Top
6677  maxDepthVal = std::max( maxDepthVal, depthTL[ (depthEndPosY)   * depStride + depthEndPosX   ]);      // Right Bottom
6678
6679  return aiShiftLUT[ maxDepthVal ];
6680}
6681
6682Void TComDataCU::estimateDVFromDM(Int refViewIdx, UInt uiPartIdx, TComPic* picDepth, UInt uiPartAddr, TComMv* cMvPred )
6683{
6684  if (picDepth)
6685  {
6686    UInt uiAbsPartAddrCurrCU = m_uiAbsIdxInLCU + uiPartAddr;
6687    Int iWidth, iHeight;
6688    getPartIndexAndSize( uiPartIdx, uiPartAddr, iWidth, iHeight ); // The modified value of uiPartAddr won't be used any more
6689
6690    TComPicYuv* pcBaseViewDepthPicYuv = picDepth->getPicYuvRec();
6691    Int iBlkX = ( getAddr() % picDepth->getFrameWidthInCU() ) * g_uiMaxCUWidth  + g_auiRasterToPelX[ g_auiZscanToRaster[ uiAbsPartAddrCurrCU ] ];
6692    Int iBlkY = ( getAddr() / picDepth->getFrameWidthInCU() ) * g_uiMaxCUHeight + g_auiRasterToPelY[ g_auiZscanToRaster[ uiAbsPartAddrCurrCU ] ];
6693
6694    Int* aiShiftLUT = getSlice()->getDepthToDisparityB(refViewIdx );
6695
6696    Pel iDisp = getMcpFromDM( pcBaseViewDepthPicYuv, cMvPred, iBlkX, iBlkY, iWidth, iHeight, aiShiftLUT );
6697    cMvPred->setHor( iDisp );
6698    clipMv(*cMvPred);
6699  }
6700}
6701#endif //H_3D_NBDV_REF
6702
6703
6704Bool TComDataCU::xCheckSpatialNBDV( TComDataCU* pcTmpCU, UInt uiIdx, DisInfo* pNbDvInfo, Bool bSearchForMvpDv, IDVInfo* paIDVInfo, UInt uiMvpDvPos
6705#if H_3D_NBDV_REF
6706, Bool bDepthRefine
6707#endif
6708)
6709{
6710  if( pcTmpCU != NULL && !pcTmpCU->isIntra( uiIdx ) )
6711  {
6712    Bool bTmpIsSkipped = pcTmpCU->isSkipped( uiIdx );
6713    for(Int iList = 0; iList < (getSlice()->isInterB() ? 2: 1); iList ++)
6714    {
6715      RefPicList eRefPicList = RefPicList(iList);
6716      Int      refId = pcTmpCU->getCUMvField(eRefPicList)->getRefIdx(uiIdx) ;
6717      TComMv cMvPred = pcTmpCU->getCUMvField(eRefPicList)->getMv(uiIdx);
6718
6719      if( refId >= 0)
6720      {
6721        Int refViewIdx  = pcTmpCU->getSlice()->getRefPic(eRefPicList, refId)->getViewIndex();
6722        if (refViewIdx != m_pcSlice->getViewIndex()) 
6723        {
6724          clipMv(cMvPred);
6725          pNbDvInfo->m_acNBDV = cMvPred;
6726          pNbDvInfo->m_aVIdxCan = refViewIdx;
6727#if H_3D_NBDV_REF
6728          TComPic* picDepth = NULL;
6729          assert(getSlice()->getRefPic(eRefPicList, refId)->getPOC() == getSlice()->getPOC());         
6730#if H_3D_FCO_VSP_DONBDV_E0163
6731          picDepth  = getSlice()->getIvPic(true, getSlice()->getViewIndex() );
6732          if ( picDepth->getPicYuvRec() != NULL ) 
6733          {
6734            cMvPred.setZero();
6735          }
6736          else// Go back with virtual depth
6737          {
6738            picDepth = getSlice()->getIvPic (true, refViewIdx );
6739          }
6740          assert(picDepth != NULL);
6741#else
6742          picDepth   = getSlice()->getIvPic (true, refViewIdx );
6743          assert(picDepth != NULL);
6744#endif
6745          UInt uiPartIdx = 0;   //Notes from MTK: Please confirm that using 0 as partition index and partition address is correct for CU-level DoNBDV
6746          UInt uiPartAddr = 0;  //QC: confirmed
6747
6748          if (picDepth && bDepthRefine)
6749            estimateDVFromDM(refViewIdx, uiPartIdx, picDepth, uiPartAddr, &cMvPred );
6750
6751          pNbDvInfo->m_acDoNBDV = cMvPred;
6752#endif
6753          return true;
6754        }
6755        else if ( bSearchForMvpDv && cMvPred.getIDVFlag() && bTmpIsSkipped )
6756        {
6757          assert( uiMvpDvPos < IDV_CANDS );
6758          paIDVInfo->m_acMvCand[iList][ uiMvpDvPos ] = TComMv( cMvPred.getIDVHor(), cMvPred.getIDVVer() );
6759          //Notes from QC: DvMCP is implemented in a way that doesnot carry the reference view identifier as NBDV. It only works for CTC and needs to be fixed to be aligned with other part of the NBDV design.
6760          paIDVInfo->m_aVIdxCan[iList][ uiMvpDvPos ] = cMvPred.getIDVVId();
6761          paIDVInfo->m_bAvailab[iList][ uiMvpDvPos ] = true;
6762          paIDVInfo->m_bFound                        = true; 
6763        }
6764      }
6765    }
6766  }
6767  return false; 
6768}
6769 
6770Void TComDataCU::xDeriveRightBottomNbIdx(Int &riLCUIdxRBNb, Int &riPartIdxRBNb )
6771{
6772  UInt uiPartIdx = 0;
6773  UInt uiNumPartInCUWidth = m_pcPic->getNumPartInWidth(); 
6774  Int uiLCUIdx = getAddr();
6775
6776  UInt uiPartIdxRB;
6777  deriveRightBottomIdx(uiPartIdx, uiPartIdxRB ); 
6778  UInt uiAbsPartIdxTmp = g_auiZscanToRaster[uiPartIdxRB];
6779
6780  if (( m_pcPic->getCU(m_uiCUAddr)->getCUPelX() + g_auiRasterToPelX[uiAbsPartIdxTmp] + m_pcPic->getMinCUWidth() )>= m_pcSlice->getSPS()->getPicWidthInLumaSamples() )
6781  {
6782    riLCUIdxRBNb  = -1;
6783    riPartIdxRBNb = -1;
6784  }
6785  else if(( m_pcPic->getCU(m_uiCUAddr)->getCUPelY() + g_auiRasterToPelY[uiAbsPartIdxTmp] + m_pcPic->getMinCUHeight() )>= m_pcSlice->getSPS()->getPicHeightInLumaSamples() )
6786  {
6787    riLCUIdxRBNb  = -1;
6788    riPartIdxRBNb = -1;
6789  }
6790  else
6791  {
6792    if ( ( uiAbsPartIdxTmp % uiNumPartInCUWidth < uiNumPartInCUWidth - 1 ) &&           // is not at the last column of LCU
6793      ( uiAbsPartIdxTmp / uiNumPartInCUWidth < m_pcPic->getNumPartInHeight() - 1 ) ) // is not at the last row    of LCU
6794    {
6795      riPartIdxRBNb = g_auiRasterToZscan[ uiAbsPartIdxTmp + uiNumPartInCUWidth + 1 ];
6796      riLCUIdxRBNb  = uiLCUIdx; 
6797    }
6798    else if ( uiAbsPartIdxTmp % uiNumPartInCUWidth < uiNumPartInCUWidth - 1 )           // is not at the last column of LCU But is last row of LCU
6799    {
6800      riPartIdxRBNb = -1;
6801      riLCUIdxRBNb  = -1;
6802    }
6803    else if ( uiAbsPartIdxTmp / uiNumPartInCUWidth < m_pcPic->getNumPartInHeight() - 1 ) // is not at the last row of LCU But is last column of LCU
6804    {
6805      riPartIdxRBNb = g_auiRasterToZscan[ uiAbsPartIdxTmp + 1 ];
6806      riLCUIdxRBNb = uiLCUIdx + 1;
6807    }
6808    else //is the right bottom corner of LCU                       
6809    {
6810      riPartIdxRBNb = -1;
6811      riLCUIdxRBNb  = -1;
6812    }
6813  }
6814}
6815
6816
6817Void TComDataCU::setDvInfoSubParts( DisInfo cDvInfo, UInt uiAbsPartIdx, UInt uiDepth )
6818{
6819  UInt uiCurrPartNumb = m_pcPic->getNumPartInCU() >> (uiDepth << 1);
6820  for (UInt ui = 0; ui < uiCurrPartNumb; ui++ )
6821  {
6822    m_pDvInfo[uiAbsPartIdx + ui] = cDvInfo;
6823  }
6824}
6825#if H_3D_VSP
6826Void TComDataCU::setDvInfoSubParts( DisInfo cDvInfo, UInt uiAbsPartIdx, UInt uiPUIdx, UInt uiDepth )
6827{
6828  setSubPartT<DisInfo>( cDvInfo, m_pDvInfo, uiAbsPartIdx, uiDepth, uiPUIdx );
6829}
6830#endif
6831
6832Bool TComDataCU::xGetColDisMV( Int currCandPic, RefPicList eRefPicList, Int refidx, Int uiCUAddr, Int uiPartUnitIdx, TComMv& rcMv , Int & iTargetViewIdx, Int & iStartViewIdx )
6833{
6834
6835  RefPicList  eColRefPicList = REF_PIC_LIST_0;
6836  Int iColViewIdx, iColRefViewIdx;
6837  TComPic *pColPic = getSlice()->getRefPic( eRefPicList, refidx);
6838  TComDataCU *pColCU = pColPic->getCU( uiCUAddr );
6839  iColViewIdx = pColCU->getSlice()->getViewIndex();
6840  if (pColCU->getPic()==0||pColCU->getPartitionSize(uiPartUnitIdx)==SIZE_NONE||pColCU->isIntra(uiPartUnitIdx))
6841  {
6842    return false;
6843  }
6844  for (Int ilist = 0; ilist < (pColCU->getSlice()->isInterB()? 2:1); ilist++) 
6845  {
6846    if(pColCU->getSlice()->isInterB())
6847    {
6848      eColRefPicList = RefPicList(ilist);
6849    }
6850
6851    Int iColRefIdx = pColCU->getCUMvField(eColRefPicList)->getRefIdx(uiPartUnitIdx);
6852
6853    if (iColRefIdx < 0)
6854    {
6855      continue;
6856    }
6857
6858    iColRefViewIdx = pColCU->getSlice()->getRefPic(eColRefPicList, iColRefIdx)->getViewIndex();
6859
6860    if ( iColViewIdx    == iColRefViewIdx ) // temporal vector
6861    {
6862      continue;
6863    }
6864    else 
6865    {
6866      if(getPic()->isTempIVRefValid(currCandPic, ilist,  iColRefIdx))
6867      {
6868        rcMv = pColCU->getCUMvField(eColRefPicList)->getMv(uiPartUnitIdx);
6869        rcMv.setIDVFlag(0);
6870        iTargetViewIdx  = iColRefViewIdx ;
6871        iStartViewIdx   = iColViewIdx   ;
6872        return true;   
6873      }
6874    }
6875  }
6876
6877  return false;
6878}
6879#endif
6880#if  H_3D_FAST_TEXTURE_ENCODING
6881Void
6882TComDataCU::getIVNStatus       ( UInt uiPartIdx,  DisInfo* pDInfo, Bool& bIVFMerge, Int& iIVFMaxD)
6883{
6884  TComSlice*    pcSlice         = getSlice (); 
6885  Int iViewIndex = pDInfo->m_aVIdxCan;
6886  //--- get base CU/PU and check prediction mode ---
6887  TComPic*    pcBasePic   = pcSlice->getIvPic( false, iViewIndex );
6888  TComPicYuv* pcBaseRec   = pcBasePic->getPicYuvRec   ();
6889
6890  UInt          uiPartAddr;
6891  Int           iWidth;
6892  Int           iHeight;
6893  getPartIndexAndSize( uiPartIdx, uiPartAddr, iWidth, iHeight );
6894
6895  Int  iCurrPosX, iCurrPosY;
6896  pcBaseRec->getTopLeftSamplePos( getAddr(), getZorderIdxInCU() + uiPartAddr, iCurrPosX, iCurrPosY );
6897
6898  iCurrPosX  += ( ( iWidth  - 1 ) >> 1 );
6899  iCurrPosY  += ( ( iHeight - 1 ) >> 1 );
6900
6901  Bool depthRefineFlag = false; 
6902#if H_3D_NBDV_REF
6903  depthRefineFlag = m_pcSlice->getVPS()->getDepthRefinementFlag( m_pcSlice->getLayerIdInVps() ); 
6904#endif // H_3D_NBDV_REF
6905
6906  TComMv      cDv = depthRefineFlag ? pDInfo->m_acDoNBDV : pDInfo->m_acNBDV; 
6907
6908  Int         iBasePosX   = Clip3( 0, pcBaseRec->getWidth () - 1, iCurrPosX + ( (cDv.getHor() + 2 ) >> 2 ) );
6909  Int         iBasePosY   = Clip3( 0, pcBaseRec->getHeight() - 1, iCurrPosY + ( (cDv.getVer() + 2 ) >> 2 )); 
6910  Int         iBaseLPosX   = Clip3( 0, pcBaseRec->getWidth () - 1, iCurrPosX - (iWidth >> 1) + ( (cDv.getHor() + 2 ) >> 2 ) );
6911  Int         iBaseLPosY   = Clip3( 0, pcBaseRec->getHeight() - 1, iCurrPosY + ( (cDv.getVer() + 2 ) >> 2 )); 
6912  Int         iBaseRPosX   = Clip3( 0, pcBaseRec->getWidth () - 1, iCurrPosX + (iWidth >> 1) + 1 + ( (cDv.getHor() + 2 ) >> 2 ) );
6913  Int         iBaseRPosY   = Clip3( 0, pcBaseRec->getHeight() - 1, iCurrPosY + ( (cDv.getVer() + 2 ) >> 2 )); 
6914  Int         iBaseUPosX   = Clip3( 0, pcBaseRec->getWidth () - 1, iCurrPosX + ( (cDv.getHor() + 2 ) >> 2 ) );
6915  Int         iBaseUPosY   = Clip3( 0, pcBaseRec->getHeight() - 1, iCurrPosY - (iHeight >> 1) + ( (cDv.getVer() + 2 ) >> 2 )); 
6916  Int         iBaseDPosX   = Clip3( 0, pcBaseRec->getWidth () - 1, iCurrPosX + ( (cDv.getHor() + 2 ) >> 2 ) );
6917  Int         iBaseDPosY   = Clip3( 0, pcBaseRec->getHeight() - 1, iCurrPosY + (iHeight >> 1) + 1 + ( (cDv.getVer() + 2 ) >> 2 )); 
6918
6919  Int         iBaseCUAddr;
6920  Int         iBaseAbsPartIdx;
6921  Int         iBaseLCUAddr;
6922  Int         iBaseLAbsPartIdx;
6923  Int         iBaseRCUAddr;
6924  Int         iBaseRAbsPartIdx;
6925  Int         iBaseUCUAddr;
6926  Int         iBaseUAbsPartIdx;
6927  Int         iBaseDCUAddr;
6928  Int         iBaseDAbsPartIdx;
6929  pcBaseRec->getCUAddrAndPartIdx( iBasePosX , iBasePosY , iBaseCUAddr, iBaseAbsPartIdx );
6930  pcBaseRec->getCUAddrAndPartIdx( iBaseLPosX , iBaseLPosY , iBaseLCUAddr, iBaseLAbsPartIdx );
6931  pcBaseRec->getCUAddrAndPartIdx( iBaseRPosX , iBaseRPosY , iBaseRCUAddr, iBaseRAbsPartIdx );
6932  pcBaseRec->getCUAddrAndPartIdx( iBaseUPosX , iBaseUPosY , iBaseUCUAddr, iBaseUAbsPartIdx );
6933  pcBaseRec->getCUAddrAndPartIdx( iBaseDPosX , iBaseDPosY , iBaseDCUAddr, iBaseDAbsPartIdx );
6934  TComDataCU* pcBaseCU    = pcBasePic->getCU( iBaseCUAddr );
6935  TComDataCU* pcBaseLCU    = pcBasePic->getCU( iBaseLCUAddr );
6936  TComDataCU* pcBaseRCU    = pcBasePic->getCU( iBaseRCUAddr );
6937  TComDataCU* pcBaseUCU    = pcBasePic->getCU( iBaseUCUAddr );
6938  TComDataCU* pcBaseDCU    = pcBasePic->getCU( iBaseDCUAddr );
6939  bIVFMerge = pcBaseLCU->getMergeFlag( iBaseLAbsPartIdx ) && pcBaseCU->getMergeFlag( iBaseAbsPartIdx ) && pcBaseRCU->getMergeFlag( iBaseRAbsPartIdx ) && pcBaseUCU->getMergeFlag( iBaseUAbsPartIdx ) && pcBaseDCU->getMergeFlag( iBaseDAbsPartIdx );
6940  Int aiDepthL[5]; //depth level
6941  aiDepthL[0] = pcBaseCU->getDepth(iBaseAbsPartIdx);
6942  aiDepthL[1] = pcBaseLCU->getDepth(iBaseLAbsPartIdx);
6943  aiDepthL[2] = pcBaseRCU->getDepth(iBaseRAbsPartIdx);
6944  aiDepthL[3] = pcBaseUCU->getDepth(iBaseUAbsPartIdx);
6945  aiDepthL[4] = pcBaseDCU->getDepth(iBaseDAbsPartIdx);
6946  for (Int i = 0; i < 5; i++)
6947  {
6948    if (iIVFMaxD < aiDepthL[i])
6949      iIVFMaxD = aiDepthL[i];
6950  }
6951}
6952#endif
6953
6954#if H_3D_SPIVMP
6955Void TComDataCU::getSPPara(Int iPUWidth, Int iPUHeight, Int& iNumSP, Int& iNumSPInOneLine, Int& iSPWidth, Int& iSPHeight)
6956{
6957  Int iSubPUSize = 1<<getSlice()->getVPS()->getSubPULog2Size(getSlice()->getLayerId());
6958  iNumSPInOneLine = iPUWidth/iSubPUSize;
6959  iNumSPInOneLine = iNumSPInOneLine < 1 ? 1: iNumSPInOneLine;
6960  Int iNumSPInOneColumn = iPUHeight/iSubPUSize;
6961  iNumSPInOneColumn = iNumSPInOneColumn < 1 ? 1: iNumSPInOneColumn;
6962  iNumSP = iNumSPInOneLine * iNumSPInOneColumn;
6963
6964  iSPWidth = iNumSPInOneLine == 1 ? iPUWidth: iSubPUSize; 
6965  iSPHeight = iNumSPInOneColumn == 1 ? iPUHeight: iSubPUSize; 
6966}
6967
6968Void TComDataCU::getSPAbsPartIdx(UInt uiBaseAbsPartIdx, Int iWidth, Int iHeight, Int iPartIdx, Int iNumPartLine, UInt& ruiPartAddr )
6969{
6970  uiBaseAbsPartIdx += m_uiAbsIdxInLCU;
6971  Int iBasePelX = g_auiRasterToPelX[g_auiZscanToRaster[uiBaseAbsPartIdx]];
6972  Int iBasePelY = g_auiRasterToPelY[g_auiZscanToRaster[uiBaseAbsPartIdx]];
6973  Int iCurrPelX = iBasePelX + iPartIdx%iNumPartLine * iWidth;
6974  Int iCurrPelY = iBasePelY + iPartIdx/iNumPartLine * iHeight;
6975  Int iCurrRaster = iCurrPelY / getPic()->getMinCUHeight() * getPic()->getNumPartInWidth() + iCurrPelX/getPic()->getMinCUWidth();
6976  ruiPartAddr = g_auiRasterToZscan[iCurrRaster];
6977  ruiPartAddr -= m_uiAbsIdxInLCU; 
6978}
6979
6980Void TComDataCU::setInterDirSP( UInt uiDir, UInt uiAbsPartIdx, Int iWidth, Int iHeight )
6981{
6982  uiAbsPartIdx += getZorderIdxInCU();
6983  Int iStartPelX = g_auiRasterToPelX[g_auiZscanToRaster[uiAbsPartIdx]];
6984  Int iStartPelY = g_auiRasterToPelY[g_auiZscanToRaster[uiAbsPartIdx]];
6985  Int iEndPelX = iStartPelX + iWidth;
6986  Int iEndPelY = iStartPelY + iHeight;
6987
6988  Int iCurrRaster, uiPartAddr;
6989
6990  for (Int i=iStartPelY; i<iEndPelY; i+=getPic()->getMinCUHeight())
6991  {
6992    for (Int j=iStartPelX; j < iEndPelX; j += getPic()->getMinCUWidth())
6993    {
6994      iCurrRaster = i / getPic()->getMinCUHeight() * getPic()->getNumPartInWidth() + j/getPic()->getMinCUWidth();
6995      uiPartAddr = g_auiRasterToZscan[iCurrRaster];
6996      uiPartAddr -= getZorderIdxInCU(); 
6997
6998      m_puhInterDir[uiPartAddr] = uiDir;
6999    }
7000  }
7001}
7002#endif
7003
7004#if H_3D_IV_MERGE
7005Bool
7006TComDataCU::getInterViewMergeCands(UInt uiPartIdx, Int* paiPdmRefIdx, TComMv* pacPdmMv, DisInfo* pDInfo, Int* availableMcDc , Bool bIsDepth           
7007#if H_3D_SPIVMP
7008, TComMvField* pcMvFieldSP, UChar* puhInterDirSP
7009#endif
7010)
7011{
7012  TComSlice*    pcSlice = getSlice (); 
7013  Int iViewIndex        = pDInfo->m_aVIdxCan;
7014 
7015  //--- get base CU/PU and check prediction mode ---
7016  TComPic*    pcBasePic   = pcSlice->getIvPic( bIsDepth, iViewIndex );
7017  TComPicYuv* pcBaseRec   = pcBasePic->getPicYuvRec   ();
7018
7019  UInt          uiPartAddr;
7020  Int           iWidth;
7021  Int           iHeight;
7022  getPartIndexAndSize( uiPartIdx, uiPartAddr, iWidth, iHeight );
7023
7024  Int  iCurrPosX, iCurrPosY;
7025  pcBaseRec->getTopLeftSamplePos( getAddr(), getZorderIdxInCU() + uiPartAddr, iCurrPosX, iCurrPosY );
7026
7027#if !H_3D_SPIVMP
7028  iCurrPosX  += ( iWidth  >> 1 );
7029  iCurrPosY  += ( iHeight >> 1 );
7030#endif
7031
7032  Bool depthRefineFlag = false; 
7033#if H_3D_NBDV_REF
7034  depthRefineFlag = m_pcSlice->getVPS()->getDepthRefinementFlag( m_pcSlice->getLayerIdInVps() ); 
7035#endif // H_3D_NBDV_REF
7036
7037  TComMv      cDv = depthRefineFlag ? pDInfo->m_acDoNBDV : pDInfo->m_acNBDV; 
7038 
7039  Bool abPdmAvailable[8] =  {false, false, false, false, false, false, false, false};
7040#if H_3D_NBDV
7041  for( Int i = 0; i < 8; i++)
7042  {
7043    pacPdmMv[i].setIDVFlag   (false);
7044  }
7045#endif
7046
7047#if H_3D_SPIVMP
7048  ////////////////////////////////
7049  //////////sub-PU IvMC///////////
7050  ////////////////////////////////
7051 
7052  Int iNumSPInOneLine, iNumSP, iSPWidth, iSPHeight;
7053  getSPPara(iWidth, iHeight, iNumSP, iNumSPInOneLine, iSPWidth, iSPHeight);
7054
7055  for (Int i=0; i<iNumSP; i++)
7056  {
7057    puhInterDirSP[i] = 0;
7058    pcMvFieldSP[2*i].getMv().set(0, 0);
7059    pcMvFieldSP[2*i+1].getMv().set(0,0);
7060    pcMvFieldSP[2*i].setRefIdx(-1);
7061    pcMvFieldSP[2*i+1].setRefIdx(-1);
7062  }
7063
7064  Int         iBaseCUAddr;
7065  Int         iBaseAbsPartIdx;
7066  TComDataCU* pcBaseCU;
7067  Int iPartition = 0;
7068  Int iInterDirLast = 0;
7069  TComMvField cMvFieldLast[2];
7070
7071  Int iDelX = iSPWidth/2;
7072  Int iDelY = iSPHeight/2;
7073
7074  Int         iBasePosX, iBasePosY;
7075  for (Int i=iCurrPosY; i < iCurrPosY + iHeight; i += iSPHeight)
7076  {
7077    for (Int j = iCurrPosX; j < iCurrPosX + iWidth; j += iSPWidth)
7078    {
7079      iBasePosX   = Clip3( 0, pcBaseRec->getWidth () - 1, j + iDelX + ( (cDv.getHor() + 2 ) >> 2 ));
7080      iBasePosY   = Clip3( 0, pcBaseRec->getHeight() - 1, i + iDelY + ( (cDv.getVer() + 2 ) >> 2 )); 
7081
7082      pcBaseRec->getCUAddrAndPartIdx( iBasePosX , iBasePosY, iBaseCUAddr, iBaseAbsPartIdx );
7083      pcBaseCU    = pcBasePic->getCU( iBaseCUAddr );
7084      if(!( pcBaseCU->getPredictionMode( iBaseAbsPartIdx ) == MODE_INTRA ))
7085      {
7086        for( UInt uiCurrRefListId = 0; uiCurrRefListId < 2; uiCurrRefListId++ )
7087        {
7088          RefPicList  eCurrRefPicList = RefPicList( uiCurrRefListId );
7089          Bool bLoop_stop = false;
7090          for(Int iLoop = 0; iLoop < 2 && !bLoop_stop; ++iLoop)
7091          {
7092            RefPicList eBaseRefPicList = (iLoop ==1)? RefPicList( 1 -  uiCurrRefListId ) : RefPicList( uiCurrRefListId );
7093            TComMvField cBaseMvField;
7094            pcBaseCU->getMvField( pcBaseCU, iBaseAbsPartIdx, eBaseRefPicList, cBaseMvField );
7095            Int         iBaseRefIdx     = cBaseMvField.getRefIdx();
7096            if (iBaseRefIdx >= 0)
7097            {
7098              Int iBaseRefPOC = pcBaseCU->getSlice()->getRefPOC(eBaseRefPicList, iBaseRefIdx);
7099              if (iBaseRefPOC != pcSlice->getPOC())   
7100              {
7101                for (Int iPdmRefIdx = 0; iPdmRefIdx < pcSlice->getNumRefIdx( eCurrRefPicList ); iPdmRefIdx++)
7102                {
7103                  if (iBaseRefPOC == pcSlice->getRefPOC(eCurrRefPicList, iPdmRefIdx))
7104                  {
7105                    abPdmAvailable[ uiCurrRefListId ] = true;
7106                    TComMv cMv(cBaseMvField.getHor(), cBaseMvField.getVer());
7107
7108                    if( !bIsDepth )
7109                    {
7110                      cMv.setIDVFlag   (true);
7111                      cMv.setIDVHor    (cDv.getHor());                 
7112                      cMv.setIDVVer    (cDv.getVer()); 
7113                      cMv.setIDVVId    (iViewIndex); 
7114                    }
7115
7116                    clipMv( cMv );
7117                    bLoop_stop = true;
7118
7119                    pcMvFieldSP[2*iPartition + uiCurrRefListId].setMvField(cMv, iPdmRefIdx);
7120                    break;
7121                  }
7122                }
7123              }
7124            }
7125          }
7126        }
7127      }
7128
7129      puhInterDirSP[iPartition] = (pcMvFieldSP[2*iPartition].getRefIdx()!=-1 ? 1: 0) + (pcMvFieldSP[2*iPartition+1].getRefIdx()!=-1 ? 2: 0);
7130      if (puhInterDirSP[iPartition] == 0)
7131      {
7132        if (iInterDirLast != 0)
7133        {
7134          puhInterDirSP[iPartition] = iInterDirLast;
7135          pcMvFieldSP[2*iPartition] = cMvFieldLast[0];
7136          pcMvFieldSP[2*iPartition + 1] = cMvFieldLast[1];
7137        }
7138      }
7139      else
7140      {
7141        if (iInterDirLast ==0)
7142        {
7143          availableMcDc[0] = puhInterDirSP[iPartition];
7144          paiPdmRefIdx  [ 0 ] = pcMvFieldSP[2*iPartition].getRefIdx();
7145          pacPdmMv      [ 0 ] = pcMvFieldSP[2*iPartition].getMv();
7146          paiPdmRefIdx  [ 1 ] = pcMvFieldSP[2*iPartition+1].getRefIdx();
7147          pacPdmMv      [ 1 ] = pcMvFieldSP[2*iPartition+1].getMv();
7148
7149          if (iPartition != 0)
7150          {
7151            for (Int iPart = iPartition-1; iPart >= 0; iPart--)
7152            {
7153              puhInterDirSP[iPart] = puhInterDirSP[iPartition];
7154              pcMvFieldSP[2*iPart] = pcMvFieldSP[2*iPartition];
7155              pcMvFieldSP[2*iPart + 1] = pcMvFieldSP[2*iPartition + 1];
7156            }
7157          }
7158        }
7159        iInterDirLast = puhInterDirSP[iPartition];
7160        cMvFieldLast[0] = pcMvFieldSP[2*iPartition];
7161        cMvFieldLast[1] = pcMvFieldSP[2*iPartition + 1];
7162      }
7163
7164      iPartition ++;
7165
7166    }
7167  } 
7168
7169  iCurrPosX  += ( iWidth  >> 1 );
7170  iCurrPosY  += ( iHeight >> 1 );
7171#endif
7172
7173  ////////////////////////////////
7174  /////// IvMC + IvMCShift ///////
7175  ////////////////////////////////
7176
7177#if H_3D_SPIVMP
7178  for(Int iLoopCan = 1; iLoopCan < 2; iLoopCan ++) 
7179#else
7180  for(Int iLoopCan = 0; iLoopCan < 2; iLoopCan ++)
7181#endif
7182  {
7183    // iLoopCan == 0 --> IvMC
7184    // iLoopCan == 1 --> IvMCShift
7185
7186#if !H_3D_SPIVMP
7187    Int         iBaseCUAddr;
7188    Int         iBaseAbsPartIdx;
7189#endif
7190
7191    Int offsetW = (iLoopCan == 0) ? 0 : ( ((iWidth /2)*4) + 4 );
7192    Int offsetH = (iLoopCan == 0) ? 0 : ( ((iHeight/2)*4) + 4 );
7193
7194#if H_3D_SPIVMP
7195    iBasePosX   = Clip3( 0, pcBaseRec->getWidth () - 1, iCurrPosX + ( (cDv.getHor() + offsetW + 2 ) >> 2 ) );
7196    iBasePosY   = Clip3( 0, pcBaseRec->getHeight() - 1, iCurrPosY + ( (cDv.getVer() + offsetH + 2 ) >> 2 ) ); 
7197#else
7198    Int         iBasePosX   = Clip3( 0, pcBaseRec->getWidth () - 1, iCurrPosX + ( (cDv.getHor() + offsetW + 2 ) >> 2 ) );
7199    Int         iBasePosY   = Clip3( 0, pcBaseRec->getHeight() - 1, iCurrPosY + ( (cDv.getVer() + offsetH + 2 ) >> 2 ) ); 
7200#endif
7201    pcBaseRec->getCUAddrAndPartIdx( iBasePosX , iBasePosY , iBaseCUAddr, iBaseAbsPartIdx );
7202
7203#if H_3D_SPIVMP
7204    pcBaseCU    = pcBasePic->getCU( iBaseCUAddr );
7205#else
7206    TComDataCU* pcBaseCU    = pcBasePic->getCU( iBaseCUAddr );
7207#endif
7208    if(!( pcBaseCU->getPredictionMode( iBaseAbsPartIdx ) == MODE_INTRA ))
7209    {
7210      // Loop reference picture list of current slice (X in spec).
7211      for( UInt uiCurrRefListId = 0; uiCurrRefListId < 2; uiCurrRefListId++ )       
7212      {
7213        RefPicList  eCurrRefPicList = RefPicList( uiCurrRefListId );
7214
7215        Bool stopLoop = false;
7216        // Loop reference picture list of candidate slice (Y in spec)
7217        for(Int iLoop = 0; iLoop < 2 && !stopLoop; ++iLoop)
7218        {
7219          RefPicList eBaseRefPicList = (iLoop ==1)? RefPicList( 1 -  uiCurrRefListId ) : RefPicList( uiCurrRefListId );
7220          TComMvField cBaseMvField;
7221          pcBaseCU->getMvField( pcBaseCU, iBaseAbsPartIdx, eBaseRefPicList, cBaseMvField );
7222          Int         iBaseRefIdx     = cBaseMvField.getRefIdx();
7223          if (iBaseRefIdx >= 0)
7224          {
7225            Int iBaseRefPOC = pcBaseCU->getSlice()->getRefPOC(eBaseRefPicList, iBaseRefIdx);
7226            if (iBaseRefPOC != pcSlice->getPOC())   
7227            {
7228              for (Int iPdmRefIdx = 0; iPdmRefIdx < pcSlice->getNumRefIdx( eCurrRefPicList ); iPdmRefIdx++)
7229              {
7230                if (iBaseRefPOC == pcSlice->getRefPOC(eCurrRefPicList, iPdmRefIdx))
7231                {
7232                  abPdmAvailable[ (uiCurrRefListId + (iLoopCan<<2)) ] = true;
7233                  TComMv cMv(cBaseMvField.getHor(), cBaseMvField.getVer());
7234#if H_3D_NBDV
7235#if H_3D_IV_MERGE
7236                  if( !bIsDepth )
7237                  {
7238#endif
7239                    cMv.setIDVFlag   (true);
7240                    cMv.setIDVHor    (cDv.getHor());                 
7241                    cMv.setIDVVer    (cDv.getVer()); 
7242                    cMv.setIDVVId    (iViewIndex); 
7243#if H_3D_IV_MERGE
7244                  }
7245#endif
7246#endif
7247                  clipMv( cMv );
7248                  paiPdmRefIdx  [ (uiCurrRefListId + (iLoopCan<<2)) ] = iPdmRefIdx;
7249                  pacPdmMv      [ (uiCurrRefListId + (iLoopCan<<2)) ] = cMv;
7250                  stopLoop = true;
7251                  break;
7252                }
7253              }
7254            }
7255          }
7256        }
7257      }
7258    }
7259  }
7260#if H_3D_SPIVMP
7261  for(Int iLoopCan = 1; iLoopCan < 2; iLoopCan ++)
7262#else
7263  for(Int iLoopCan = 0; iLoopCan < 2; iLoopCan ++)
7264#endif
7265  {
7266    availableMcDc[(iLoopCan << 1)] = ( abPdmAvailable[(iLoopCan<<2)] ? 1 : 0 ) + ( abPdmAvailable[1 + (iLoopCan<<2)] ? 2 : 0);
7267  }
7268 
7269 
7270  ////////////////////////////////
7271  /////// IvDC + IvDCShift ///////
7272  ////////////////////////////////
7273 
7274  for( Int iRefListId = 0; iRefListId < 2 ; iRefListId++ )
7275  {
7276    RefPicList  eRefPicListDMV       = RefPicList( iRefListId );
7277    Int         iNumRefPics       = pcSlice->getNumRefIdx( eRefPicListDMV );
7278    for( Int iPdmRefIdx = 0; iPdmRefIdx < iNumRefPics; iPdmRefIdx++ )
7279    {
7280      if(( pcSlice->getRefPOC( eRefPicListDMV, iPdmRefIdx ) == pcSlice->getPOC()) && (pcSlice->getRefPic( eRefPicListDMV, iPdmRefIdx )->getViewIndex() == pDInfo->m_aVIdxCan))
7281      {
7282        for(Int iLoopCan = 0; iLoopCan < 2; iLoopCan ++)
7283        {
7284          Int ioffsetDV = (iLoopCan == 0) ? 0 : 4;
7285          abPdmAvailable[ iRefListId + 2 + (iLoopCan<<2) ] = true;
7286          paiPdmRefIdx  [ iRefListId + 2 + (iLoopCan<<2) ] = iPdmRefIdx;
7287#if H_3D_NBDV_REF
7288          TComMv cMv = depthRefineFlag ? pDInfo->m_acDoNBDV : pDInfo->m_acNBDV; 
7289#endif
7290          cMv.setHor( cMv.getHor() + ioffsetDV );
7291#if H_3D_IV_MERGE
7292          if( bIsDepth )
7293            cMv.setHor((cMv.getHor()+2)>>2); 
7294#endif
7295          cMv.setVer( 0 );
7296          clipMv( cMv );
7297          pacPdmMv      [iRefListId + 2 + (iLoopCan<<2)] = cMv;
7298        }
7299        break;
7300      }
7301    }
7302  }
7303  for(Int iLoopCan = 0; iLoopCan < 2; iLoopCan ++)
7304  {
7305    availableMcDc[1 + (iLoopCan << 1)] = ( abPdmAvailable[2 + (iLoopCan<<2)] ? 1 : 0 ) + ( abPdmAvailable[3 + (iLoopCan<<2)] ? 2 : 0 );
7306  }
7307  return false;
7308}
7309#endif
7310#if H_3D_ARP
7311Void TComDataCU::setARPWSubParts ( UChar w, UInt uiAbsPartIdx, UInt uiDepth )
7312{
7313  assert( sizeof( *m_puhARPW) == 1 );
7314  memset( m_puhARPW + uiAbsPartIdx, w, m_pcPic->getNumPartInCU() >> ( 2 * uiDepth ) );
7315}
7316#endif
7317
7318#if H_3D_IC
7319Void TComDataCU::setICFlagSubParts( Bool bICFlag, UInt uiAbsPartIdx, UInt uiPartIdx, UInt uiDepth )
7320{
7321  memset( m_pbICFlag + uiAbsPartIdx, bICFlag, (m_pcPic->getNumPartInCU() >> ( 2 * uiDepth ))*sizeof(Bool) );
7322}
7323
7324Bool TComDataCU::isICFlagRequired( UInt uiAbsPartIdx )
7325{
7326  UInt uiPartAddr;
7327  UInt iNumbPart;
7328
7329  if( !( getPartitionSize( uiAbsPartIdx ) == SIZE_2Nx2N ) )
7330  {
7331    return false;
7332  }
7333
7334  if( getSlice()->getIcSkipParseFlag() )
7335  {
7336    if( getMergeFlag( uiAbsPartIdx ) && getMergeIndex( uiAbsPartIdx ) == 0 )
7337    {
7338      return false;
7339    }
7340  }
7341
7342  if( getMergeFlag( uiAbsPartIdx ) )
7343  {
7344    return true;
7345  }
7346
7347
7348  Int iWidth, iHeight;
7349
7350  iNumbPart = ( getPartitionSize( uiAbsPartIdx ) == SIZE_2Nx2N ? 1 : ( getPartitionSize( uiAbsPartIdx ) == SIZE_NxN ? 4 : 2 ) );
7351
7352  for(UInt i = 0; i < iNumbPart; i++)
7353  {
7354    getPartIndexAndSize( i, uiPartAddr, iWidth, iHeight, uiAbsPartIdx, true );
7355    uiPartAddr += uiAbsPartIdx;
7356
7357    for(UInt uiRefIdx = 0; uiRefIdx < 2; uiRefIdx++)
7358    {
7359      RefPicList eRefList = uiRefIdx ? REF_PIC_LIST_1 : REF_PIC_LIST_0;
7360      Int iBestRefIdx = getCUMvField(eRefList)->getRefIdx(uiPartAddr);
7361
7362      if( ( getInterDir( uiPartAddr ) & ( uiRefIdx+1 ) ) && iBestRefIdx >= 0 && getSlice()->getViewIndex() != getSlice()->getRefPic( eRefList, iBestRefIdx )->getViewIndex() )
7363      {
7364        return true;
7365      }
7366    }
7367  }
7368
7369  return false;
7370}
7371#endif
7372#if H_3D_DIM_DMM
7373Void TComDataCU::setDmmWedgeTabIdxSubParts( UInt tabIdx, UInt dmmType, UInt uiAbsPartIdx, UInt uiDepth )
7374{
7375  UInt uiCurrPartNumb = m_pcPic->getNumPartInCU() >> (uiDepth << 1);
7376  for( UInt ui = 0; ui < uiCurrPartNumb; ui++ ) { m_dmmWedgeTabIdx[dmmType][uiAbsPartIdx+ui] = tabIdx; }
7377}
7378#endif
7379
7380
7381//! \}
Note: See TracBrowser for help on using the repository browser.