LCOV - code coverage report
Current view: top level - libavcodec - hevc_mvs.c (source / functions) Hit Total Coverage
Test: coverage.info Lines: 402 408 98.5 %
Date: 2017-12-12 11:08:38 Functions: 14 14 100.0 %

          Line data    Source code
       1             : /*
       2             :  * HEVC video decoder
       3             :  *
       4             :  * Copyright (C) 2012 - 2013 Guillaume Martres
       5             :  * Copyright (C) 2013 Anand Meher Kotra
       6             :  *
       7             :  * This file is part of FFmpeg.
       8             :  *
       9             :  * FFmpeg is free software; you can redistribute it and/or
      10             :  * modify it under the terms of the GNU Lesser General Public
      11             :  * License as published by the Free Software Foundation; either
      12             :  * version 2.1 of the License, or (at your option) any later version.
      13             :  *
      14             :  * FFmpeg is distributed in the hope that it will be useful,
      15             :  * but WITHOUT ANY WARRANTY; without even the implied warranty of
      16             :  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
      17             :  * Lesser General Public License for more details.
      18             :  *
      19             :  * You should have received a copy of the GNU Lesser General Public
      20             :  * License along with FFmpeg; if not, write to the Free Software
      21             :  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
      22             :  */
      23             : 
      24             : #include "hevc.h"
      25             : #include "hevcdec.h"
      26             : 
      27             : static const uint8_t l0_l1_cand_idx[12][2] = {
      28             :     { 0, 1, },
      29             :     { 1, 0, },
      30             :     { 0, 2, },
      31             :     { 2, 0, },
      32             :     { 1, 2, },
      33             :     { 2, 1, },
      34             :     { 0, 3, },
      35             :     { 3, 0, },
      36             :     { 1, 3, },
      37             :     { 3, 1, },
      38             :     { 2, 3, },
      39             :     { 3, 2, },
      40             : };
      41             : 
      42    27026979 : void ff_hevc_set_neighbour_available(HEVCContext *s, int x0, int y0,
      43             :                                      int nPbW, int nPbH)
      44             : {
      45    27026979 :     HEVCLocalContext *lc = s->HEVClc;
      46    27026979 :     int x0b = av_mod_uintp2(x0, s->ps.sps->log2_ctb_size);
      47    27026979 :     int y0b = av_mod_uintp2(y0, s->ps.sps->log2_ctb_size);
      48             : 
      49    27026979 :     lc->na.cand_up       = (lc->ctb_up_flag   || y0b);
      50    27026979 :     lc->na.cand_left     = (lc->ctb_left_flag || x0b);
      51    27026979 :     lc->na.cand_up_left  = (!x0b && !y0b) ? lc->ctb_up_left_flag : lc->na.cand_left && lc->na.cand_up;
      52    27026979 :     lc->na.cand_up_right_sap =
      53    27026979 :             ((x0b + nPbW) == (1 << s->ps.sps->log2_ctb_size)) ?
      54    27026979 :                     lc->ctb_up_right_flag && !y0b : lc->na.cand_up;
      55    27026979 :     lc->na.cand_up_right =
      56    27026979 :             lc->na.cand_up_right_sap
      57    27026979 :                      && (x0 + nPbW) < lc->end_of_tiles_x;
      58    27026979 :     lc->na.cand_bottom_left = ((y0 + nPbH) >= lc->end_of_tiles_y) ? 0 : lc->na.cand_left;
      59    27026979 : }
      60             : 
      61             : /*
      62             :  * 6.4.1 Derivation process for z-scan order block availability
      63             :  */
      64     5546265 : static av_always_inline int z_scan_block_avail(HEVCContext *s, int xCurr, int yCurr,
      65             :                               int xN, int yN)
      66             : {
      67             : #define MIN_TB_ADDR_ZS(x, y)                                            \
      68             :     s->ps.pps->min_tb_addr_zs[(y) * (s->ps.sps->tb_mask+2) + (x)]
      69             : 
      70     5546265 :     int xCurr_ctb = xCurr >> s->ps.sps->log2_ctb_size;
      71     5546265 :     int yCurr_ctb = yCurr >> s->ps.sps->log2_ctb_size;
      72     5546265 :     int xN_ctb    = xN    >> s->ps.sps->log2_ctb_size;
      73     5546265 :     int yN_ctb    = yN    >> s->ps.sps->log2_ctb_size;
      74     5546265 :     if( yN_ctb < yCurr_ctb || xN_ctb < xCurr_ctb )
      75     1392445 :         return 1;
      76             :     else {
      77     4153820 :         int Curr = MIN_TB_ADDR_ZS((xCurr >> s->ps.sps->log2_min_tb_size) & s->ps.sps->tb_mask,
      78             :                 (yCurr >> s->ps.sps->log2_min_tb_size) & s->ps.sps->tb_mask);
      79     4153820 :         int N    = MIN_TB_ADDR_ZS((xN >> s->ps.sps->log2_min_tb_size) & s->ps.sps->tb_mask,
      80             :                 (yN >> s->ps.sps->log2_min_tb_size) & s->ps.sps->tb_mask);
      81     4153820 :         return N <= Curr;
      82             :     }
      83             : }
      84             : 
      85             : //check if the two luma locations belong to the same motion estimation region
      86    10973199 : static av_always_inline int is_diff_mer(HEVCContext *s, int xN, int yN, int xP, int yP)
      87             : {
      88    10973199 :     uint8_t plevel = s->ps.pps->log2_parallel_merge_level;
      89             : 
      90    11728273 :     return xN >> plevel == xP >> plevel &&
      91      755074 :            yN >> plevel == yP >> plevel;
      92             : }
      93             : 
      94             : #define MATCH_MV(x) (AV_RN32A(&A.x) == AV_RN32A(&B.x))
      95             : #define MATCH(x) (A.x == B.x)
      96             : 
      97             : // check if the mv's and refidx are the same between A and B
      98     4393759 : static av_always_inline int compare_mv_ref_idx(struct MvField A, struct MvField B)
      99             : {
     100     4393759 :     int a_pf = A.pred_flag;
     101     4393759 :     int b_pf = B.pred_flag;
     102     4393759 :     if (a_pf == b_pf) {
     103     3265411 :         if (a_pf == PF_BI) {
     104     4284025 :             return MATCH(ref_idx[0]) && MATCH_MV(mv[0]) &&
     105     3570074 :                    MATCH(ref_idx[1]) && MATCH_MV(mv[1]);
     106     1492719 :         } else if (a_pf == PF_L0) {
     107     1310939 :             return MATCH(ref_idx[0]) && MATCH_MV(mv[0]);
     108      181780 :         } else if (a_pf == PF_L1) {
     109      181780 :             return MATCH(ref_idx[1]) && MATCH_MV(mv[1]);
     110             :         }
     111             :     }
     112     1128348 :     return 0;
     113             : }
     114             : 
     115     2293792 : static av_always_inline void mv_scale(Mv *dst, Mv *src, int td, int tb)
     116             : {
     117             :     int tx, scale_factor;
     118             : 
     119     2293792 :     td = av_clip_int8(td);
     120     2293792 :     tb = av_clip_int8(tb);
     121     2293792 :     tx = (0x4000 + abs(td / 2)) / td;
     122     2293792 :     scale_factor = av_clip_intp2((tb * tx + 32) >> 6, 12);
     123     4587584 :     dst->x = av_clip_int16((scale_factor * src->x + 127 +
     124     2293792 :                            (scale_factor * src->x < 0)) >> 8);
     125     4587584 :     dst->y = av_clip_int16((scale_factor * src->y + 127 +
     126     2293792 :                            (scale_factor * src->y < 0)) >> 8);
     127     2293792 : }
     128             : 
     129     1784269 : static int check_mvset(Mv *mvLXCol, Mv *mvCol,
     130             :                        int colPic, int poc,
     131             :                        RefPicList *refPicList, int X, int refIdxLx,
     132             :                        RefPicList *refPicList_col, int listCol, int refidxCol)
     133             : {
     134     1784269 :     int cur_lt = refPicList[X].isLongTerm[refIdxLx];
     135     1784269 :     int col_lt = refPicList_col[listCol].isLongTerm[refidxCol];
     136             :     int col_poc_diff, cur_poc_diff;
     137             : 
     138     1784269 :     if (cur_lt != col_lt) {
     139        1036 :         mvLXCol->x = 0;
     140        1036 :         mvLXCol->y = 0;
     141        1036 :         return 0;
     142             :     }
     143             : 
     144     1783233 :     col_poc_diff = colPic - refPicList_col[listCol].list[refidxCol];
     145     1783233 :     cur_poc_diff = poc    - refPicList[X].list[refIdxLx];
     146             : 
     147     1783233 :     if (cur_lt || col_poc_diff == cur_poc_diff || !col_poc_diff) {
     148      331909 :         mvLXCol->x = mvCol->x;
     149      331909 :         mvLXCol->y = mvCol->y;
     150             :     } else {
     151     1451324 :         mv_scale(mvLXCol, mvCol, col_poc_diff, cur_poc_diff);
     152             :     }
     153     1783233 :     return 1;
     154             : }
     155             : 
     156             : #define CHECK_MVSET(l)                                          \
     157             :     check_mvset(mvLXCol, temp_col.mv + l,                       \
     158             :                 colPic, s->poc,                                 \
     159             :                 refPicList, X, refIdxLx,                        \
     160             :                 refPicList_col, L ## l, temp_col.ref_idx[l])
     161             : 
     162             : // derive the motion vectors section 8.5.3.1.8
     163     2227645 : static int derive_temporal_colocated_mvs(HEVCContext *s, MvField temp_col,
     164             :                                          int refIdxLx, Mv *mvLXCol, int X,
     165             :                                          int colPic, RefPicList *refPicList_col)
     166             : {
     167     2227645 :     RefPicList *refPicList = s->ref->refPicList;
     168             : 
     169     2227645 :     if (temp_col.pred_flag == PF_INTRA)
     170      443376 :         return 0;
     171             : 
     172     1784269 :     if (!(temp_col.pred_flag & PF_L0))
     173      210936 :         return CHECK_MVSET(1);
     174     1573333 :     else if (temp_col.pred_flag == PF_L0)
     175      747027 :         return CHECK_MVSET(0);
     176      826306 :     else if (temp_col.pred_flag == PF_BI) {
     177      826306 :         int check_diffpicount = 0;
     178             :         int i, j;
     179     2478918 :         for (j = 0; j < 2; j++) {
     180     4461648 :             for (i = 0; i < refPicList[j].nb_refs; i++) {
     181     3539903 :                 if (refPicList[j].list[i] > s->poc) {
     182      730867 :                     check_diffpicount++;
     183      730867 :                     break;
     184             :                 }
     185             :             }
     186             :         }
     187      826306 :         if (!check_diffpicount) {
     188      237536 :             if (X==0)
     189      133677 :                 return CHECK_MVSET(0);
     190             :             else
     191      103859 :                 return CHECK_MVSET(1);
     192             :         } else {
     193      588770 :             if (s->sh.collocated_list == L1)
     194      327361 :                 return CHECK_MVSET(0);
     195             :             else
     196      261409 :                 return CHECK_MVSET(1);
     197             :         }
     198             :     }
     199             : 
     200           0 :     return 0;
     201             : }
     202             : 
     203             : #define TAB_MVF(x, y)                                                   \
     204             :     tab_mvf[(y) * min_pu_width + x]
     205             : 
     206             : #define TAB_MVF_PU(v)                                                   \
     207             :     TAB_MVF(((x ## v) >> s->ps.sps->log2_min_pu_size),                     \
     208             :             ((y ## v) >> s->ps.sps->log2_min_pu_size))
     209             : 
     210             : #define DERIVE_TEMPORAL_COLOCATED_MVS                                   \
     211             :     derive_temporal_colocated_mvs(s, temp_col,                          \
     212             :                                   refIdxLx, mvLXCol, X, colPic,         \
     213             :                                   ff_hevc_get_ref_list(s, ref, x, y))
     214             : 
     215             : /*
     216             :  * 8.5.3.1.7  temporal luma motion vector prediction
     217             :  */
     218     1998047 : static int temporal_luma_motion_vector(HEVCContext *s, int x0, int y0,
     219             :                                        int nPbW, int nPbH, int refIdxLx,
     220             :                                        Mv *mvLXCol, int X)
     221             : {
     222             :     MvField *tab_mvf;
     223             :     MvField temp_col;
     224             :     int x, y, x_pu, y_pu;
     225     1998047 :     int min_pu_width = s->ps.sps->min_pu_width;
     226     1998047 :     int availableFlagLXCol = 0;
     227             :     int colPic;
     228             : 
     229     1998047 :     HEVCFrame *ref = s->ref->collocated_ref;
     230             : 
     231     1998047 :     if (!ref) {
     232           0 :         memset(mvLXCol, 0, sizeof(*mvLXCol));
     233           0 :         return 0;
     234             :     }
     235             : 
     236     1998047 :     tab_mvf = ref->tab_mvf;
     237     1998047 :     colPic  = ref->poc;
     238             : 
     239             :     //bottom right collocated motion vector
     240     1998047 :     x = x0 + nPbW;
     241     1998047 :     y = y0 + nPbH;
     242             : 
     243     3996094 :     if (tab_mvf &&
     244     3430696 :         (y0 >> s->ps.sps->log2_ctb_size) == (y >> s->ps.sps->log2_ctb_size) &&
     245     2818644 :         y < s->ps.sps->height &&
     246     1385995 :         x < s->ps.sps->width) {
     247     1364051 :         x                 &= ~15;
     248     1364051 :         y                 &= ~15;
     249     1364051 :         if (s->threads_type == FF_THREAD_FRAME)
     250           0 :             ff_thread_await_progress(&ref->tf, y, 0);
     251     1364051 :         x_pu               = x >> s->ps.sps->log2_min_pu_size;
     252     1364051 :         y_pu               = y >> s->ps.sps->log2_min_pu_size;
     253     1364051 :         temp_col           = TAB_MVF(x_pu, y_pu);
     254     1364051 :         availableFlagLXCol = DERIVE_TEMPORAL_COLOCATED_MVS;
     255             :     }
     256             : 
     257             :     // derive center collocated motion vector
     258     1998047 :     if (tab_mvf && !availableFlagLXCol) {
     259      863594 :         x                  = x0 + (nPbW >> 1);
     260      863594 :         y                  = y0 + (nPbH >> 1);
     261      863594 :         x                 &= ~15;
     262      863594 :         y                 &= ~15;
     263      863594 :         if (s->threads_type == FF_THREAD_FRAME)
     264           0 :             ff_thread_await_progress(&ref->tf, y, 0);
     265      863594 :         x_pu               = x >> s->ps.sps->log2_min_pu_size;
     266      863594 :         y_pu               = y >> s->ps.sps->log2_min_pu_size;
     267      863594 :         temp_col           = TAB_MVF(x_pu, y_pu);
     268      863594 :         availableFlagLXCol = DERIVE_TEMPORAL_COLOCATED_MVS;
     269             :     }
     270     1998047 :     return availableFlagLXCol;
     271             : }
     272             : 
     273             : #define AVAILABLE(cand, v)                                      \
     274             :     (cand && !(TAB_MVF_PU(v).pred_flag == PF_INTRA))
     275             : 
     276             : #define PRED_BLOCK_AVAILABLE(v)                                 \
     277             :     z_scan_block_avail(s, x0, y0, x ## v, y ## v)
     278             : 
     279             : #define COMPARE_MV_REFIDX(a, b)                                 \
     280             :     compare_mv_ref_idx(TAB_MVF_PU(a), TAB_MVF_PU(b))
     281             : 
     282             : /*
     283             :  * 8.5.3.1.2  Derivation process for spatial merging candidates
     284             :  */
     285     6106179 : static void derive_spatial_merge_candidates(HEVCContext *s, int x0, int y0,
     286             :                                             int nPbW, int nPbH,
     287             :                                             int log2_cb_size,
     288             :                                             int singleMCLFlag, int part_idx,
     289             :                                             int merge_idx,
     290             :                                             struct MvField mergecandlist[])
     291             : {
     292     6106179 :     HEVCLocalContext *lc   = s->HEVClc;
     293     6106179 :     RefPicList *refPicList = s->ref->refPicList;
     294     6106179 :     MvField *tab_mvf       = s->ref->tab_mvf;
     295             : 
     296     6106179 :     const int min_pu_width = s->ps.sps->min_pu_width;
     297             : 
     298     6106179 :     const int cand_bottom_left = lc->na.cand_bottom_left;
     299     6106179 :     const int cand_left        = lc->na.cand_left;
     300     6106179 :     const int cand_up_left     = lc->na.cand_up_left;
     301     6106179 :     const int cand_up          = lc->na.cand_up;
     302     6106179 :     const int cand_up_right    = lc->na.cand_up_right_sap;
     303             : 
     304     6106179 :     const int xA1    = x0 - 1;
     305     6106179 :     const int yA1    = y0 + nPbH - 1;
     306             : 
     307     6106179 :     const int xB1    = x0 + nPbW - 1;
     308     6106179 :     const int yB1    = y0 - 1;
     309             : 
     310     6106179 :     const int xB0    = x0 + nPbW;
     311     6106179 :     const int yB0    = y0 - 1;
     312             : 
     313     6106179 :     const int xA0    = x0 - 1;
     314     6106179 :     const int yA0    = y0 + nPbH;
     315             : 
     316     6106179 :     const int xB2    = x0 - 1;
     317     6106179 :     const int yB2    = y0 - 1;
     318             : 
     319    12212358 :     const int nb_refs = (s->sh.slice_type == HEVC_SLICE_P) ?
     320     6106179 :                         s->sh.nb_refs[0] : FFMIN(s->sh.nb_refs[0], s->sh.nb_refs[1]);
     321             : 
     322     6106179 :     int zero_idx = 0;
     323             : 
     324     6106179 :     int nb_merge_cand = 0;
     325     6106179 :     int nb_orig_merge_cand = 0;
     326             : 
     327             :     int is_available_a0;
     328             :     int is_available_a1;
     329             :     int is_available_b0;
     330             :     int is_available_b1;
     331             :     int is_available_b2;
     332             : 
     333             : 
     334     6774426 :     if (!singleMCLFlag && part_idx == 1 &&
     335     1072648 :         (lc->cu.part_mode == PART_Nx2N ||
     336      762641 :          lc->cu.part_mode == PART_nLx2N ||
     337     6104981 :          lc->cu.part_mode == PART_nRx2N) ||
     338     5746741 :         is_diff_mer(s, xA1, yA1, x0, y0)) {
     339      497826 :         is_available_a1 = 0;
     340             :     } else {
     341     5608353 :         is_available_a1 = AVAILABLE(cand_left, A1);
     342     5608353 :         if (is_available_a1) {
     343     5238213 :             mergecandlist[nb_merge_cand] = TAB_MVF_PU(A1);
     344     5238213 :             if (merge_idx == 0)
     345     3087539 :                 return;
     346     2150674 :             nb_merge_cand++;
     347             :         }
     348             :     }
     349             : 
     350     3539335 :     if (!singleMCLFlag && part_idx == 1 &&
     351      948733 :         (lc->cu.part_mode == PART_2NxN ||
     352      840383 :          lc->cu.part_mode == PART_2NxnU ||
     353     3305553 :          lc->cu.part_mode == PART_2NxnD) ||
     354     2893208 :         is_diff_mer(s, xB1, yB1, x0, y0)) {
     355      253293 :         is_available_b1 = 0;
     356             :     } else {
     357     2765347 :         is_available_b1 = AVAILABLE(cand_up, B1);
     358     2765347 :         if (is_available_b1 &&
     359     1899593 :             !(is_available_a1 && COMPARE_MV_REFIDX(B1, A1))) {
     360     2209573 :             mergecandlist[nb_merge_cand] = TAB_MVF_PU(B1);
     361     2209573 :             if (merge_idx == nb_merge_cand)
     362     1353282 :                 return;
     363      856291 :             nb_merge_cand++;
     364             :         }
     365             :     }
     366             : 
     367             :     // above right spatial merge candidate
     368     4184867 :     is_available_b0 = AVAILABLE(cand_up_right, B0) &&
     369     2387503 :                       xB0 < s->ps.sps->width &&
     370     3814892 :                       PRED_BLOCK_AVAILABLE(B0) &&
     371      960008 :                       !is_diff_mer(s, xB0, yB0, x0, y0);
     372             : 
     373     1665358 :     if (is_available_b0 &&
     374      853423 :         !(is_available_b1 && COMPARE_MV_REFIDX(B0, B1))) {
     375      538705 :         mergecandlist[nb_merge_cand] = TAB_MVF_PU(B0);
     376      538705 :         if (merge_idx == nb_merge_cand)
     377      306195 :             return;
     378      232510 :         nb_merge_cand++;
     379             :     }
     380             : 
     381             :     // left bottom spatial merge candidate
     382     3184515 :     is_available_a0 = AVAILABLE(cand_bottom_left, A0) &&
     383     1714346 :                       yA0 < s->ps.sps->height &&
     384     2559522 :                       PRED_BLOCK_AVAILABLE(A0) &&
     385      343186 :                       !is_diff_mer(s, xA0, yA0, x0, y0);
     386             : 
     387     1359163 :     if (is_available_a0 &&
     388      311403 :         !(is_available_a1 && COMPARE_MV_REFIDX(A0, A1))) {
     389      145403 :         mergecandlist[nb_merge_cand] = TAB_MVF_PU(A0);
     390      145403 :         if (merge_idx == nb_merge_cand)
     391       80047 :             return;
     392       65356 :         nb_merge_cand++;
     393             :     }
     394             : 
     395             :     // above left spatial merge candidate
     396     2309172 :     is_available_b2 = AVAILABLE(cand_up_left, B2) &&
     397     1030056 :                       !is_diff_mer(s, xB2, yB2, x0, y0);
     398             : 
     399     1279116 :     if (is_available_b2 &&
     400      794239 :         !(is_available_a1 && COMPARE_MV_REFIDX(B2, A1)) &&
     401      535101 :         !(is_available_b1 && COMPARE_MV_REFIDX(B2, B1)) &&
     402             :         nb_merge_cand != 4) {
     403      389720 :         mergecandlist[nb_merge_cand] = TAB_MVF_PU(B2);
     404      389720 :         if (merge_idx == nb_merge_cand)
     405      190977 :             return;
     406      198743 :         nb_merge_cand++;
     407             :     }
     408             : 
     409             :     // temporal motion vector candidate
     410     1937523 :     if (s->sh.slice_temporal_mvp_enabled_flag &&
     411      849384 :         nb_merge_cand < s->sh.max_num_merge_cand) {
     412      849384 :         Mv mv_l0_col = { 0 }, mv_l1_col = { 0 };
     413      849384 :         int available_l0 = temporal_luma_motion_vector(s, x0, y0, nPbW, nPbH,
     414             :                                                        0, &mv_l0_col, 0);
     415     1698768 :         int available_l1 = (s->sh.slice_type == HEVC_SLICE_B) ?
     416             :                            temporal_luma_motion_vector(s, x0, y0, nPbW, nPbH,
     417      849384 :                                                        0, &mv_l1_col, 1) : 0;
     418             : 
     419      849384 :         if (available_l0 || available_l1) {
     420      773786 :             mergecandlist[nb_merge_cand].pred_flag = available_l0 + (available_l1 << 1);
     421      773786 :             AV_ZERO16(mergecandlist[nb_merge_cand].ref_idx);
     422      773786 :             mergecandlist[nb_merge_cand].mv[0]      = mv_l0_col;
     423      773786 :             mergecandlist[nb_merge_cand].mv[1]      = mv_l1_col;
     424             : 
     425      773786 :             if (merge_idx == nb_merge_cand)
     426      484595 :                 return;
     427      289191 :             nb_merge_cand++;
     428             :         }
     429             :     }
     430             : 
     431      603544 :     nb_orig_merge_cand = nb_merge_cand;
     432             : 
     433             :     // combined bi-predictive merge candidates  (applies for B slices)
     434      934781 :     if (s->sh.slice_type == HEVC_SLICE_B && nb_orig_merge_cand > 1 &&
     435      331237 :         nb_orig_merge_cand < s->sh.max_num_merge_cand) {
     436      331237 :         int comb_idx = 0;
     437             : 
     438     1728989 :         for (comb_idx = 0; nb_merge_cand < s->sh.max_num_merge_cand &&
     439     1066515 :                            comb_idx < nb_orig_merge_cand * (nb_orig_merge_cand - 1); comb_idx++) {
     440      650515 :             int l0_cand_idx = l0_l1_cand_idx[comb_idx][0];
     441      650515 :             int l1_cand_idx = l0_l1_cand_idx[comb_idx][1];
     442      650515 :             MvField l0_cand = mergecandlist[l0_cand_idx];
     443      650515 :             MvField l1_cand = mergecandlist[l1_cand_idx];
     444             : 
     445     1083062 :             if ((l0_cand.pred_flag & PF_L0) && (l1_cand.pred_flag & PF_L1) &&
     446      432547 :                 (refPicList[0].list[l0_cand.ref_idx[0]] !=
     447      541069 :                  refPicList[1].list[l1_cand.ref_idx[1]] ||
     448      108522 :                  AV_RN32A(&l0_cand.mv[0]) != AV_RN32A(&l1_cand.mv[1]))) {
     449      418331 :                 mergecandlist[nb_merge_cand].ref_idx[0]   = l0_cand.ref_idx[0];
     450      418331 :                 mergecandlist[nb_merge_cand].ref_idx[1]   = l1_cand.ref_idx[1];
     451      418331 :                 mergecandlist[nb_merge_cand].pred_flag    = PF_BI;
     452      418331 :                 AV_COPY32(&mergecandlist[nb_merge_cand].mv[0], &l0_cand.mv[0]);
     453      418331 :                 AV_COPY32(&mergecandlist[nb_merge_cand].mv[1], &l1_cand.mv[1]);
     454      418331 :                 if (merge_idx == nb_merge_cand)
     455      282876 :                     return;
     456      135455 :                 nb_merge_cand++;
     457             :             }
     458             :         }
     459             :     }
     460             : 
     461             :     // append Zero motion vector candidates
     462      853402 :     while (nb_merge_cand < s->sh.max_num_merge_cand) {
     463      532734 :         mergecandlist[nb_merge_cand].pred_flag    = PF_L0 + ((s->sh.slice_type == HEVC_SLICE_B) << 1);
     464      532734 :         AV_ZERO32(mergecandlist[nb_merge_cand].mv + 0);
     465      532734 :         AV_ZERO32(mergecandlist[nb_merge_cand].mv + 1);
     466      532734 :         mergecandlist[nb_merge_cand].ref_idx[0]   = zero_idx < nb_refs ? zero_idx : 0;
     467      532734 :         mergecandlist[nb_merge_cand].ref_idx[1]   = zero_idx < nb_refs ? zero_idx : 0;
     468             : 
     469      532734 :         if (merge_idx == nb_merge_cand)
     470      320668 :             return;
     471      212066 :         nb_merge_cand++;
     472      212066 :         zero_idx++;
     473             :     }
     474             : }
     475             : 
     476             : /*
     477             :  * 8.5.3.1.1 Derivation process of luma Mvs for merge mode
     478             :  */
     479     6106179 : void ff_hevc_luma_mv_merge_mode(HEVCContext *s, int x0, int y0, int nPbW,
     480             :                                 int nPbH, int log2_cb_size, int part_idx,
     481             :                                 int merge_idx, MvField *mv)
     482             : {
     483     6106179 :     int singleMCLFlag = 0;
     484     6106179 :     int nCS = 1 << log2_cb_size;
     485             :     MvField mergecand_list[MRG_MAX_NUM_CANDS];
     486     6106179 :     int nPbW2 = nPbW;
     487     6106179 :     int nPbH2 = nPbH;
     488     6106179 :     HEVCLocalContext *lc = s->HEVClc;
     489             : 
     490     6106179 :     if (s->ps.pps->log2_parallel_merge_level > 2 && nCS == 8) {
     491      214635 :         singleMCLFlag = 1;
     492      214635 :         x0            = lc->cu.x;
     493      214635 :         y0            = lc->cu.y;
     494      214635 :         nPbW          = nCS;
     495      214635 :         nPbH          = nCS;
     496      214635 :         part_idx      = 0;
     497             :     }
     498             : 
     499     6106179 :     ff_hevc_set_neighbour_available(s, x0, y0, nPbW, nPbH);
     500     6106179 :     derive_spatial_merge_candidates(s, x0, y0, nPbW, nPbH, log2_cb_size,
     501             :                                     singleMCLFlag, part_idx,
     502             :                                     merge_idx, mergecand_list);
     503             : 
     504     9607762 :     if (mergecand_list[merge_idx].pred_flag == PF_BI &&
     505     3501583 :         (nPbW2 + nPbH2) == 12) {
     506      124136 :         mergecand_list[merge_idx].pred_flag = PF_L0;
     507             :     }
     508             : 
     509     6106179 :     *mv = mergecand_list[merge_idx];
     510     6106179 : }
     511             : 
     512      999827 : static av_always_inline void dist_scale(HEVCContext *s, Mv *mv,
     513             :                                         int min_pu_width, int x, int y,
     514             :                                         int elist, int ref_idx_curr, int ref_idx)
     515             : {
     516      999827 :     RefPicList *refPicList = s->ref->refPicList;
     517      999827 :     MvField *tab_mvf       = s->ref->tab_mvf;
     518      999827 :     int ref_pic_elist      = refPicList[elist].list[TAB_MVF(x, y).ref_idx[elist]];
     519      999827 :     int ref_pic_curr       = refPicList[ref_idx_curr].list[ref_idx];
     520             : 
     521      999827 :     if (ref_pic_elist != ref_pic_curr) {
     522      842468 :         int poc_diff = s->poc - ref_pic_elist;
     523      842468 :         if (!poc_diff)
     524           0 :             poc_diff = 1;
     525      842468 :         mv_scale(mv, mv, poc_diff, s->poc - ref_pic_curr);
     526             :     }
     527      999827 : }
     528             : 
     529     9049099 : static int mv_mp_mode_mx(HEVCContext *s, int x, int y, int pred_flag_index,
     530             :                          Mv *mv, int ref_idx_curr, int ref_idx)
     531             : {
     532     9049099 :     MvField *tab_mvf = s->ref->tab_mvf;
     533     9049099 :     int min_pu_width = s->ps.sps->min_pu_width;
     534             : 
     535     9049099 :     RefPicList *refPicList = s->ref->refPicList;
     536             : 
     537    16068173 :     if (((TAB_MVF(x, y).pred_flag) & (1 << pred_flag_index)) &&
     538     7019074 :         refPicList[pred_flag_index].list[TAB_MVF(x, y).ref_idx[pred_flag_index]] == refPicList[ref_idx_curr].list[ref_idx]) {
     539     3694695 :         *mv = TAB_MVF(x, y).mv[pred_flag_index];
     540     3694695 :         return 1;
     541             :     }
     542     5354404 :     return 0;
     543             : }
     544             : 
     545     1269897 : static int mv_mp_mode_mx_lt(HEVCContext *s, int x, int y, int pred_flag_index,
     546             :                             Mv *mv, int ref_idx_curr, int ref_idx)
     547             : {
     548     1269897 :     MvField *tab_mvf = s->ref->tab_mvf;
     549     1269897 :     int min_pu_width = s->ps.sps->min_pu_width;
     550             : 
     551     1269897 :     RefPicList *refPicList = s->ref->refPicList;
     552             : 
     553     1269897 :     if ((TAB_MVF(x, y).pred_flag) & (1 << pred_flag_index)) {
     554     1008303 :         int currIsLongTerm     = refPicList[ref_idx_curr].isLongTerm[ref_idx];
     555             : 
     556     1008303 :         int colIsLongTerm =
     557     1008303 :             refPicList[pred_flag_index].isLongTerm[(TAB_MVF(x, y).ref_idx[pred_flag_index])];
     558             : 
     559     1008303 :         if (colIsLongTerm == currIsLongTerm) {
     560     1003586 :             *mv = TAB_MVF(x, y).mv[pred_flag_index];
     561     1003586 :             if (!currIsLongTerm)
     562      999827 :                 dist_scale(s, mv, min_pu_width, x, y,
     563             :                            pred_flag_index, ref_idx_curr, ref_idx);
     564     1003586 :             return 1;
     565             :         }
     566             :     }
     567      266311 :     return 0;
     568             : }
     569             : 
     570             : #define MP_MX(v, pred, mx)                                      \
     571             :     mv_mp_mode_mx(s,                                            \
     572             :                   (x ## v) >> s->ps.sps->log2_min_pu_size,         \
     573             :                   (y ## v) >> s->ps.sps->log2_min_pu_size,         \
     574             :                   pred, &mx, ref_idx_curr, ref_idx)
     575             : 
     576             : #define MP_MX_LT(v, pred, mx)                                   \
     577             :     mv_mp_mode_mx_lt(s,                                         \
     578             :                      (x ## v) >> s->ps.sps->log2_min_pu_size,      \
     579             :                      (y ## v) >> s->ps.sps->log2_min_pu_size,      \
     580             :                      pred, &mx, ref_idx_curr, ref_idx)
     581             : 
     582     2769288 : void ff_hevc_luma_mv_mvp_mode(HEVCContext *s, int x0, int y0, int nPbW,
     583             :                               int nPbH, int log2_cb_size, int part_idx,
     584             :                               int merge_idx, MvField *mv,
     585             :                               int mvp_lx_flag, int LX)
     586             : {
     587     2769288 :     HEVCLocalContext *lc = s->HEVClc;
     588     2769288 :     MvField *tab_mvf = s->ref->tab_mvf;
     589     2769288 :     int isScaledFlag_L0 = 0;
     590     2769288 :     int availableFlagLXA0 = 1;
     591     2769288 :     int availableFlagLXB0 = 1;
     592     2769288 :     int numMVPCandLX = 0;
     593     2769288 :     int min_pu_width = s->ps.sps->min_pu_width;
     594             : 
     595             :     int xA0, yA0;
     596             :     int is_available_a0;
     597             :     int xA1, yA1;
     598             :     int is_available_a1;
     599             :     int xB0, yB0;
     600             :     int is_available_b0;
     601             :     int xB1, yB1;
     602             :     int is_available_b1;
     603             :     int xB2, yB2;
     604             :     int is_available_b2;
     605             : 
     606     2769288 :     Mv mvpcand_list[2] = { { 0 } };
     607             :     Mv mxA;
     608             :     Mv mxB;
     609             :     int ref_idx_curr;
     610     2769288 :     int ref_idx = 0;
     611             :     int pred_flag_index_l0;
     612             :     int pred_flag_index_l1;
     613             : 
     614     2769288 :     const int cand_bottom_left = lc->na.cand_bottom_left;
     615     2769288 :     const int cand_left        = lc->na.cand_left;
     616     2769288 :     const int cand_up_left     = lc->na.cand_up_left;
     617     2769288 :     const int cand_up          = lc->na.cand_up;
     618     2769288 :     const int cand_up_right    = lc->na.cand_up_right_sap;
     619     2769288 :     ref_idx_curr       = LX;
     620     2769288 :     ref_idx            = mv->ref_idx[LX];
     621     2769288 :     pred_flag_index_l0 = LX;
     622     2769288 :     pred_flag_index_l1 = !LX;
     623             : 
     624             :     // left bottom spatial candidate
     625     2769288 :     xA0 = x0 - 1;
     626     2769288 :     yA0 = y0 + nPbH;
     627             : 
     628     6354383 :     is_available_a0 = AVAILABLE(cand_bottom_left, A0) &&
     629     6065192 :                       yA0 < s->ps.sps->height &&
     630     1647952 :                       PRED_BLOCK_AVAILABLE(A0);
     631             : 
     632             :     //left spatial merge candidate
     633     2769288 :     xA1    = x0 - 1;
     634     2769288 :     yA1    = y0 + nPbH - 1;
     635             : 
     636     2769288 :     is_available_a1 = AVAILABLE(cand_left, A1);
     637     2769288 :     if (is_available_a0 || is_available_a1)
     638     2467868 :         isScaledFlag_L0 = 1;
     639             : 
     640     2769288 :     if (is_available_a0) {
     641      728371 :         if (MP_MX(A0, pred_flag_index_l0, mxA)) {
     642      442478 :             goto b_candidates;
     643             :         }
     644      285893 :         if (MP_MX(A0, pred_flag_index_l1, mxA)) {
     645       47482 :             goto b_candidates;
     646             :         }
     647             :     }
     648             : 
     649     2279328 :     if (is_available_a1) {
     650     1968588 :         if (MP_MX(A1, pred_flag_index_l0, mxA)) {
     651     1107157 :             goto b_candidates;
     652             :         }
     653      861431 :         if (MP_MX(A1, pred_flag_index_l1, mxA)) {
     654      113885 :             goto b_candidates;
     655             :         }
     656             :     }
     657             : 
     658     1058286 :     if (is_available_a0) {
     659      193548 :         if (MP_MX_LT(A0, pred_flag_index_l0, mxA)) {
     660      141520 :             goto b_candidates;
     661             :         }
     662       52028 :         if (MP_MX_LT(A0, pred_flag_index_l1, mxA)) {
     663       51206 :             goto b_candidates;
     664             :         }
     665             :     }
     666             : 
     667      865560 :     if (is_available_a1) {
     668      563922 :         if (MP_MX_LT(A1, pred_flag_index_l0, mxA)) {
     669      384680 :             goto b_candidates;
     670             :         }
     671      179242 :         if (MP_MX_LT(A1, pred_flag_index_l1, mxA)) {
     672      176473 :             goto b_candidates;
     673             :         }
     674             :     }
     675      304407 :     availableFlagLXA0 = 0;
     676             : 
     677     2769288 : b_candidates:
     678             :     // B candidates
     679             :     // above right spatial merge candidate
     680     2769288 :     xB0    = x0 + nPbW;
     681     2769288 :     yB0    = y0 - 1;
     682             : 
     683     6754735 :     is_available_b0 =  AVAILABLE(cand_up_right, B0) &&
     684     6486599 :                        xB0 < s->ps.sps->width &&
     685     1851614 :                        PRED_BLOCK_AVAILABLE(B0);
     686             : 
     687             :     // above spatial merge candidate
     688     2769288 :     xB1    = x0 + nPbW - 1;
     689     2769288 :     yB1    = y0 - 1;
     690     2769288 :     is_available_b1 = AVAILABLE(cand_up, B1);
     691             : 
     692             :     // above left spatial merge candidate
     693     2769288 :     xB2 = x0 - 1;
     694     2769288 :     yB2 = y0 - 1;
     695     2769288 :     is_available_b2 = AVAILABLE(cand_up_left, B2);
     696             : 
     697             :     // above right spatial merge candidate
     698     2769288 :     if (is_available_b0) {
     699     1451891 :         if (MP_MX(B0, pred_flag_index_l0, mxB)) {
     700      900279 :             goto scalef;
     701             :         }
     702      551612 :         if (MP_MX(B0, pred_flag_index_l1, mxB)) {
     703       93879 :             goto scalef;
     704             :         }
     705             :     }
     706             : 
     707             :     // above spatial merge candidate
     708     1775130 :     if (is_available_b1) {
     709     1402055 :         if (MP_MX(B1, pred_flag_index_l0, mxB)) {
     710      707967 :             goto scalef;
     711             :         }
     712      694088 :         if (MP_MX(B1, pred_flag_index_l1, mxB)) {
     713       71087 :             goto scalef;
     714             :         }
     715             :     }
     716             : 
     717             :     // above left spatial merge candidate
     718      996076 :     if (is_available_b2) {
     719      645906 :         if (MP_MX(B2, pred_flag_index_l0, mxB)) {
     720      186642 :             goto scalef;
     721             :         }
     722      459264 :         if (MP_MX(B2, pred_flag_index_l1, mxB)) {
     723       23839 :             goto scalef;
     724             :         }
     725             :     }
     726      785595 :     availableFlagLXB0 = 0;
     727             : 
     728     2769288 : scalef:
     729     2769288 :     if (!isScaledFlag_L0) {
     730      301420 :         if (availableFlagLXB0) {
     731      184590 :             availableFlagLXA0 = 1;
     732      184590 :             mxA = mxB;
     733             :         }
     734      301420 :         availableFlagLXB0 = 0;
     735             : 
     736             :         // XB0 and L1
     737      301420 :         if (is_available_b0) {
     738      138445 :             availableFlagLXB0 = MP_MX_LT(B0, pred_flag_index_l0, mxB);
     739      138445 :             if (!availableFlagLXB0)
     740       16172 :                 availableFlagLXB0 = MP_MX_LT(B0, pred_flag_index_l1, mxB);
     741             :         }
     742             : 
     743      301420 :         if (is_available_b1 && !availableFlagLXB0) {
     744       97982 :             availableFlagLXB0 = MP_MX_LT(B1, pred_flag_index_l0, mxB);
     745       97982 :             if (!availableFlagLXB0)
     746       12532 :                 availableFlagLXB0 = MP_MX_LT(B1, pred_flag_index_l1, mxB);
     747             :         }
     748             : 
     749      301420 :         if (is_available_b2 && !availableFlagLXB0) {
     750       14313 :             availableFlagLXB0 = MP_MX_LT(B2, pred_flag_index_l0, mxB);
     751       14313 :             if (!availableFlagLXB0)
     752        1713 :                 availableFlagLXB0 = MP_MX_LT(B2, pred_flag_index_l1, mxB);
     753             :         }
     754             :     }
     755             : 
     756     2769288 :     if (availableFlagLXA0)
     757     2649471 :         mvpcand_list[numMVPCandLX++] = mxA;
     758             : 
     759     2769288 :     if (availableFlagLXB0 && (!availableFlagLXA0 || mxA.x != mxB.x || mxA.y != mxB.y))
     760     1500545 :         mvpcand_list[numMVPCandLX++] = mxB;
     761             : 
     762             :     //temporal motion vector prediction candidate
     763     2769288 :     if (numMVPCandLX < 2 && s->sh.slice_temporal_mvp_enabled_flag &&
     764             :         mvp_lx_flag == numMVPCandLX) {
     765             :         Mv mv_col;
     766      388925 :         int available_col = temporal_luma_motion_vector(s, x0, y0, nPbW,
     767             :                                                         nPbH, ref_idx,
     768             :                                                         &mv_col, LX);
     769      388925 :         if (available_col)
     770      320819 :             mvpcand_list[numMVPCandLX++] = mv_col;
     771             :     }
     772             : 
     773     2769288 :     mv->mv[LX] = mvpcand_list[mvp_lx_flag];
     774     2769288 : }

Generated by: LCOV version 1.13