source: 3DVCSoftware/branches/HTM-DEV-2.0-dev1-Fix/source/Lib/TLibCommon/TComDataCU.cpp @ 593

Last change on this file since 593 was 593, checked in by zhang, 12 years ago

fixes of BVSP and VSO related issues, encapsulated by H_3D_FIX

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