/*
 * HEVC video decoder
 *
 * Copyright (C) 2012 - 2013 Guillaume Martres
 * Copyright (C) 2013 Anand Meher Kotra
 *
 * This file is part of FFmpeg.
 *
 * FFmpeg is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * FFmpeg is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with FFmpeg; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
 */

#include "hevc.h"

static const uint8_t l0_l1_cand_idx[12][2] = {
    { 0, 1, },
    { 1, 0, },
    { 0, 2, },
    { 2, 0, },
    { 1, 2, },
    { 2, 1, },
    { 0, 3, },
    { 3, 0, },
    { 1, 3, },
    { 3, 1, },
    { 2, 3, },
    { 3, 2, },
};

void ff_hevc_set_neighbour_available(HEVCContext *s, int x0, int y0,
                                     int nPbW, int nPbH)
{
    HEVCLocalContext *lc = s->HEVClc;
    int x0b = av_mod_uintp2(x0, s->ps.sps->log2_ctb_size);
    int y0b = av_mod_uintp2(y0, s->ps.sps->log2_ctb_size);

    lc->na.cand_up       = (lc->ctb_up_flag   || y0b);
    lc->na.cand_left     = (lc->ctb_left_flag || x0b);
    lc->na.cand_up_left  = (!x0b && !y0b) ? lc->ctb_up_left_flag : lc->na.cand_left && lc->na.cand_up;
    lc->na.cand_up_right_sap =
            ((x0b + nPbW) == (1 << s->ps.sps->log2_ctb_size)) ?
                    lc->ctb_up_right_flag && !y0b : lc->na.cand_up;
    lc->na.cand_up_right =
            lc->na.cand_up_right_sap
                     && (x0 + nPbW) < lc->end_of_tiles_x;
    lc->na.cand_bottom_left = ((y0 + nPbH) >= lc->end_of_tiles_y) ? 0 : lc->na.cand_left;
}

/*
 * 6.4.1 Derivation process for z-scan order block availability
 */
static av_always_inline int z_scan_block_avail(HEVCContext *s, int xCurr, int yCurr,
                              int xN, int yN)
{
#define MIN_TB_ADDR_ZS(x, y)                                            \
    s->ps.pps->min_tb_addr_zs[(y) * (s->ps.sps->tb_mask+2) + (x)]

    int xCurr_ctb = xCurr >> s->ps.sps->log2_ctb_size;
    int yCurr_ctb = yCurr >> s->ps.sps->log2_ctb_size;
    int xN_ctb    = xN    >> s->ps.sps->log2_ctb_size;
    int yN_ctb    = yN    >> s->ps.sps->log2_ctb_size;
    if( yN_ctb < yCurr_ctb || xN_ctb < xCurr_ctb )
        return 1;
    else {
        int Curr = MIN_TB_ADDR_ZS((xCurr >> s->ps.sps->log2_min_tb_size) & s->ps.sps->tb_mask,
                (yCurr >> s->ps.sps->log2_min_tb_size) & s->ps.sps->tb_mask);
        int N    = MIN_TB_ADDR_ZS((xN >> s->ps.sps->log2_min_tb_size) & s->ps.sps->tb_mask,
                (yN >> s->ps.sps->log2_min_tb_size) & s->ps.sps->tb_mask);
        return N <= Curr;
    }
}

//check if the two luma locations belong to the same mostion estimation region
static av_always_inline int is_diff_mer(HEVCContext *s, int xN, int yN, int xP, int yP)
{
    uint8_t plevel = s->ps.pps->log2_parallel_merge_level;

    return xN >> plevel == xP >> plevel &&
           yN >> plevel == yP >> plevel;
}

#define MATCH_MV(x) (AV_RN32A(&A.x) == AV_RN32A(&B.x))
#define MATCH(x) (A.x == B.x)

// check if the mv's and refidx are the same between A and B
static av_always_inline int compare_mv_ref_idx(struct MvField A, struct MvField B)
{
    int a_pf = A.pred_flag;
    int b_pf = B.pred_flag;
    if (a_pf == b_pf) {
        if (a_pf == PF_BI) {
            return MATCH(ref_idx[0]) && MATCH_MV(mv[0]) &&
                   MATCH(ref_idx[1]) && MATCH_MV(mv[1]);
        } else if (a_pf == PF_L0) {
            return MATCH(ref_idx[0]) && MATCH_MV(mv[0]);
        } else if (a_pf == PF_L1) {
            return MATCH(ref_idx[1]) && MATCH_MV(mv[1]);
        }
    }
    return 0;
}

static av_always_inline void mv_scale(Mv *dst, Mv *src, int td, int tb)
{
    int tx, scale_factor;

    td = av_clip_int8(td);
    tb = av_clip_int8(tb);
    tx = (0x4000 + abs(td / 2)) / td;
    scale_factor = av_clip_intp2((tb * tx + 32) >> 6, 12);
    dst->x = av_clip_int16((scale_factor * src->x + 127 +
                           (scale_factor * src->x < 0)) >> 8);
    dst->y = av_clip_int16((scale_factor * src->y + 127 +
                           (scale_factor * src->y < 0)) >> 8);
}

static int check_mvset(Mv *mvLXCol, Mv *mvCol,
                       int colPic, int poc,
                       RefPicList *refPicList, int X, int refIdxLx,
                       RefPicList *refPicList_col, int listCol, int refidxCol)
{
    int cur_lt = refPicList[X].isLongTerm[refIdxLx];
    int col_lt = refPicList_col[listCol].isLongTerm[refidxCol];
    int col_poc_diff, cur_poc_diff;

    if (cur_lt != col_lt) {
        mvLXCol->x = 0;
        mvLXCol->y = 0;
        return 0;
    }

    col_poc_diff = colPic - refPicList_col[listCol].list[refidxCol];
    cur_poc_diff = poc    - refPicList[X].list[refIdxLx];

    if (cur_lt || col_poc_diff == cur_poc_diff || !col_poc_diff) {
        mvLXCol->x = mvCol->x;
        mvLXCol->y = mvCol->y;
    } else {
        mv_scale(mvLXCol, mvCol, col_poc_diff, cur_poc_diff);
    }
    return 1;
}

#define CHECK_MVSET(l)                                          \
    check_mvset(mvLXCol, temp_col.mv + l,                       \
                colPic, s->poc,                                 \
                refPicList, X, refIdxLx,                        \
                refPicList_col, L ## l, temp_col.ref_idx[l])

// derive the motion vectors section 8.5.3.1.8
static int derive_temporal_colocated_mvs(HEVCContext *s, MvField temp_col,
                                         int refIdxLx, Mv *mvLXCol, int X,
                                         int colPic, RefPicList *refPicList_col)
{
    RefPicList *refPicList = s->ref->refPicList;

    if (temp_col.pred_flag == PF_INTRA)
        return 0;

    if (!(temp_col.pred_flag & PF_L0))
        return CHECK_MVSET(1);
    else if (temp_col.pred_flag == PF_L0)
        return CHECK_MVSET(0);
    else if (temp_col.pred_flag == PF_BI) {
        int check_diffpicount = 0;
        int i, j;
        for (j = 0; j < 2; j++) {
            for (i = 0; i < refPicList[j].nb_refs; i++) {
                if (refPicList[j].list[i] > s->poc) {
                    check_diffpicount++;
                    break;
                }
            }
        }
        if (!check_diffpicount) {
            if (X==0)
                return CHECK_MVSET(0);
            else
                return CHECK_MVSET(1);
        } else {
            if (s->sh.collocated_list == L1)
                return CHECK_MVSET(0);
            else
                return CHECK_MVSET(1);
        }
    }

    return 0;
}

#define TAB_MVF(x, y)                                                   \
    tab_mvf[(y) * min_pu_width + x]

#define TAB_MVF_PU(v)                                                   \
    TAB_MVF(((x ## v) >> s->ps.sps->log2_min_pu_size),                     \
            ((y ## v) >> s->ps.sps->log2_min_pu_size))

#define DERIVE_TEMPORAL_COLOCATED_MVS                                   \
    derive_temporal_colocated_mvs(s, temp_col,                          \
                                  refIdxLx, mvLXCol, X, colPic,         \
                                  ff_hevc_get_ref_list(s, ref, x, y))

/*
 * 8.5.3.1.7  temporal luma motion vector prediction
 */
static int temporal_luma_motion_vector(HEVCContext *s, int x0, int y0,
                                       int nPbW, int nPbH, int refIdxLx,
                                       Mv *mvLXCol, int X)
{
    MvField *tab_mvf;
    MvField temp_col;
    int x, y, x_pu, y_pu;
    int min_pu_width = s->ps.sps->min_pu_width;
    int availableFlagLXCol = 0;
    int colPic;

    HEVCFrame *ref = s->ref->collocated_ref;

    if (!ref) {
        memset(mvLXCol, 0, sizeof(*mvLXCol));
        return 0;
    }

    tab_mvf = ref->tab_mvf;
    colPic  = ref->poc;

    //bottom right collocated motion vector
    x = x0 + nPbW;
    y = y0 + nPbH;

    if (tab_mvf &&
        (y0 >> s->ps.sps->log2_ctb_size) == (y >> s->ps.sps->log2_ctb_size) &&
        y < s->ps.sps->height &&
        x < s->ps.sps->width) {
        x                 &= ~15;
        y                 &= ~15;
        if (s->threads_type == FF_THREAD_FRAME)
            ff_thread_await_progress(&ref->tf, y, 0);
        x_pu               = x >> s->ps.sps->log2_min_pu_size;
        y_pu               = y >> s->ps.sps->log2_min_pu_size;
        temp_col           = TAB_MVF(x_pu, y_pu);
        availableFlagLXCol = DERIVE_TEMPORAL_COLOCATED_MVS;
    }

    // derive center collocated motion vector
    if (tab_mvf && !availableFlagLXCol) {
        x                  = x0 + (nPbW >> 1);
        y                  = y0 + (nPbH >> 1);
        x                 &= ~15;
        y                 &= ~15;
        if (s->threads_type == FF_THREAD_FRAME)
            ff_thread_await_progress(&ref->tf, y, 0);
        x_pu               = x >> s->ps.sps->log2_min_pu_size;
        y_pu               = y >> s->ps.sps->log2_min_pu_size;
        temp_col           = TAB_MVF(x_pu, y_pu);
        availableFlagLXCol = DERIVE_TEMPORAL_COLOCATED_MVS;
    }
    return availableFlagLXCol;
}

#define AVAILABLE(cand, v)                                      \
    (cand && !(TAB_MVF_PU(v).pred_flag == PF_INTRA))

#define PRED_BLOCK_AVAILABLE(v)                                 \
    z_scan_block_avail(s, x0, y0, x ## v, y ## v)

#define COMPARE_MV_REFIDX(a, b)                                 \
    compare_mv_ref_idx(TAB_MVF_PU(a), TAB_MVF_PU(b))

/*
 * 8.5.3.1.2  Derivation process for spatial merging candidates
 */
static void derive_spatial_merge_candidates(HEVCContext *s, int x0, int y0,
                                            int nPbW, int nPbH,
                                            int log2_cb_size,
                                            int singleMCLFlag, int part_idx,
                                            int merge_idx,
                                            struct MvField mergecandlist[])
{
    HEVCLocalContext *lc   = s->HEVClc;
    RefPicList *refPicList = s->ref->refPicList;
    MvField *tab_mvf       = s->ref->tab_mvf;

    const int min_pu_width = s->ps.sps->min_pu_width;

    const int cand_bottom_left = lc->na.cand_bottom_left;
    const int cand_left        = lc->na.cand_left;
    const int cand_up_left     = lc->na.cand_up_left;
    const int cand_up          = lc->na.cand_up;
    const int cand_up_right    = lc->na.cand_up_right_sap;

    const int xA1    = x0 - 1;
    const int yA1    = y0 + nPbH - 1;

    const int xB1    = x0 + nPbW - 1;
    const int yB1    = y0 - 1;

    const int xB0    = x0 + nPbW;
    const int yB0    = y0 - 1;

    const int xA0    = x0 - 1;
    const int yA0    = y0 + nPbH;

    const int xB2    = x0 - 1;
    const int yB2    = y0 - 1;

    const int nb_refs = (s->sh.slice_type == P_SLICE) ?
                        s->sh.nb_refs[0] : FFMIN(s->sh.nb_refs[0], s->sh.nb_refs[1]);

    int zero_idx = 0;

    int nb_merge_cand = 0;
    int nb_orig_merge_cand = 0;

    int is_available_a0;
    int is_available_a1;
    int is_available_b0;
    int is_available_b1;
    int is_available_b2;


    if (!singleMCLFlag && part_idx == 1 &&
        (lc->cu.part_mode == PART_Nx2N ||
         lc->cu.part_mode == PART_nLx2N ||
         lc->cu.part_mode == PART_nRx2N) ||
        is_diff_mer(s, xA1, yA1, x0, y0)) {
        is_available_a1 = 0;
    } else {
        is_available_a1 = AVAILABLE(cand_left, A1);
        if (is_available_a1) {
            mergecandlist[nb_merge_cand] = TAB_MVF_PU(A1);
            if (merge_idx == 0)
                return;
            nb_merge_cand++;
        }
    }

    if (!singleMCLFlag && part_idx == 1 &&
        (lc->cu.part_mode == PART_2NxN ||
         lc->cu.part_mode == PART_2NxnU ||
         lc->cu.part_mode == PART_2NxnD) ||
        is_diff_mer(s, xB1, yB1, x0, y0)) {
        is_available_b1 = 0;
    } else {
        is_available_b1 = AVAILABLE(cand_up, B1);
        if (is_available_b1 &&
            !(is_available_a1 && COMPARE_MV_REFIDX(B1, A1))) {
            mergecandlist[nb_merge_cand] = TAB_MVF_PU(B1);
            if (merge_idx == nb_merge_cand)
                return;
            nb_merge_cand++;
        }
    }

    // above right spatial merge candidate
    is_available_b0 = AVAILABLE(cand_up_right, B0) &&
                      xB0 < s->ps.sps->width &&
                      PRED_BLOCK_AVAILABLE(B0) &&
                      !is_diff_mer(s, xB0, yB0, x0, y0);

    if (is_available_b0 &&
        !(is_available_b1 && COMPARE_MV_REFIDX(B0, B1))) {
        mergecandlist[nb_merge_cand] = TAB_MVF_PU(B0);
        if (merge_idx == nb_merge_cand)
            return;
        nb_merge_cand++;
    }

    // left bottom spatial merge candidate
    is_available_a0 = AVAILABLE(cand_bottom_left, A0) &&
                      yA0 < s->ps.sps->height &&
                      PRED_BLOCK_AVAILABLE(A0) &&
                      !is_diff_mer(s, xA0, yA0, x0, y0);

    if (is_available_a0 &&
        !(is_available_a1 && COMPARE_MV_REFIDX(A0, A1))) {
        mergecandlist[nb_merge_cand] = TAB_MVF_PU(A0);
        if (merge_idx == nb_merge_cand)
            return;
        nb_merge_cand++;
    }

    // above left spatial merge candidate
    is_available_b2 = AVAILABLE(cand_up_left, B2) &&
                      !is_diff_mer(s, xB2, yB2, x0, y0);

    if (is_available_b2 &&
        !(is_available_a1 && COMPARE_MV_REFIDX(B2, A1)) &&
        !(is_available_b1 && COMPARE_MV_REFIDX(B2, B1)) &&
        nb_merge_cand != 4) {
        mergecandlist[nb_merge_cand] = TAB_MVF_PU(B2);
        if (merge_idx == nb_merge_cand)
            return;
        nb_merge_cand++;
    }

    // temporal motion vector candidate
    if (s->sh.slice_temporal_mvp_enabled_flag &&
        nb_merge_cand < s->sh.max_num_merge_cand) {
        Mv mv_l0_col = { 0 }, mv_l1_col = { 0 };
        int available_l0 = temporal_luma_motion_vector(s, x0, y0, nPbW, nPbH,
                                                       0, &mv_l0_col, 0);
        int available_l1 = (s->sh.slice_type == B_SLICE) ?
                           temporal_luma_motion_vector(s, x0, y0, nPbW, nPbH,
                                                       0, &mv_l1_col, 1) : 0;

        if (available_l0 || available_l1) {
            mergecandlist[nb_merge_cand].pred_flag = available_l0 + (available_l1 << 1);
            AV_ZERO16(mergecandlist[nb_merge_cand].ref_idx);
            mergecandlist[nb_merge_cand].mv[0]      = mv_l0_col;
            mergecandlist[nb_merge_cand].mv[1]      = mv_l1_col;

            if (merge_idx == nb_merge_cand)
                return;
            nb_merge_cand++;
        }
    }

    nb_orig_merge_cand = nb_merge_cand;

    // combined bi-predictive merge candidates  (applies for B slices)
    if (s->sh.slice_type == B_SLICE && nb_orig_merge_cand > 1 &&
        nb_orig_merge_cand < s->sh.max_num_merge_cand) {
        int comb_idx = 0;

        for (comb_idx = 0; nb_merge_cand < s->sh.max_num_merge_cand &&
                           comb_idx < nb_orig_merge_cand * (nb_orig_merge_cand - 1); comb_idx++) {
            int l0_cand_idx = l0_l1_cand_idx[comb_idx][0];
            int l1_cand_idx = l0_l1_cand_idx[comb_idx][1];
            MvField l0_cand = mergecandlist[l0_cand_idx];
            MvField l1_cand = mergecandlist[l1_cand_idx];

            if ((l0_cand.pred_flag & PF_L0) && (l1_cand.pred_flag & PF_L1) &&
                (refPicList[0].list[l0_cand.ref_idx[0]] !=
                 refPicList[1].list[l1_cand.ref_idx[1]] ||
                 AV_RN32A(&l0_cand.mv[0]) != AV_RN32A(&l1_cand.mv[1]))) {
                mergecandlist[nb_merge_cand].ref_idx[0]   = l0_cand.ref_idx[0];
                mergecandlist[nb_merge_cand].ref_idx[1]   = l1_cand.ref_idx[1];
                mergecandlist[nb_merge_cand].pred_flag    = PF_BI;
                AV_COPY32(&mergecandlist[nb_merge_cand].mv[0], &l0_cand.mv[0]);
                AV_COPY32(&mergecandlist[nb_merge_cand].mv[1], &l1_cand.mv[1]);
                if (merge_idx == nb_merge_cand)
                    return;
                nb_merge_cand++;
            }
        }
    }

    // append Zero motion vector candidates
    while (nb_merge_cand < s->sh.max_num_merge_cand) {
        mergecandlist[nb_merge_cand].pred_flag    = PF_L0 + ((s->sh.slice_type == B_SLICE) << 1);
        AV_ZERO32(mergecandlist[nb_merge_cand].mv + 0);
        AV_ZERO32(mergecandlist[nb_merge_cand].mv + 1);
        mergecandlist[nb_merge_cand].ref_idx[0]   = zero_idx < nb_refs ? zero_idx : 0;
        mergecandlist[nb_merge_cand].ref_idx[1]   = zero_idx < nb_refs ? zero_idx : 0;

        if (merge_idx == nb_merge_cand)
            return;
        nb_merge_cand++;
        zero_idx++;
    }
}

/*
 * 8.5.3.1.1 Derivation process of luma Mvs for merge mode
 */
void ff_hevc_luma_mv_merge_mode(HEVCContext *s, int x0, int y0, int nPbW,
                                int nPbH, int log2_cb_size, int part_idx,
                                int merge_idx, MvField *mv)
{
    int singleMCLFlag = 0;
    int nCS = 1 << log2_cb_size;
    LOCAL_ALIGNED(4, MvField, mergecand_list, [MRG_MAX_NUM_CANDS]);
    int nPbW2 = nPbW;
    int nPbH2 = nPbH;
    HEVCLocalContext *lc = s->HEVClc;

    if (s->ps.pps->log2_parallel_merge_level > 2 && nCS == 8) {
        singleMCLFlag = 1;
        x0            = lc->cu.x;
        y0            = lc->cu.y;
        nPbW          = nCS;
        nPbH          = nCS;
        part_idx      = 0;
    }

    ff_hevc_set_neighbour_available(s, x0, y0, nPbW, nPbH);
    derive_spatial_merge_candidates(s, x0, y0, nPbW, nPbH, log2_cb_size,
                                    singleMCLFlag, part_idx,
                                    merge_idx, mergecand_list);

    if (mergecand_list[merge_idx].pred_flag == PF_BI &&
        (nPbW2 + nPbH2) == 12) {
        mergecand_list[merge_idx].pred_flag = PF_L0;
    }

    *mv = mergecand_list[merge_idx];
}

static av_always_inline void dist_scale(HEVCContext *s, Mv *mv,
                                        int min_pu_width, int x, int y,
                                        int elist, int ref_idx_curr, int ref_idx)
{
    RefPicList *refPicList = s->ref->refPicList;
    MvField *tab_mvf       = s->ref->tab_mvf;
    int ref_pic_elist      = refPicList[elist].list[TAB_MVF(x, y).ref_idx[elist]];
    int ref_pic_curr       = refPicList[ref_idx_curr].list[ref_idx];

    if (ref_pic_elist != ref_pic_curr) {
        int poc_diff = s->poc - ref_pic_elist;
        if (!poc_diff)
            poc_diff = 1;
        mv_scale(mv, mv, poc_diff, s->poc - ref_pic_curr);
    }
}

static int mv_mp_mode_mx(HEVCContext *s, int x, int y, int pred_flag_index,
                         Mv *mv, int ref_idx_curr, int ref_idx)
{
    MvField *tab_mvf = s->ref->tab_mvf;
    int min_pu_width = s->ps.sps->min_pu_width;

    RefPicList *refPicList = s->ref->refPicList;

    if (((TAB_MVF(x, y).pred_flag) & (1 << pred_flag_index)) &&
        refPicList[pred_flag_index].list[TAB_MVF(x, y).ref_idx[pred_flag_index]] == refPicList[ref_idx_curr].list[ref_idx]) {
        *mv = TAB_MVF(x, y).mv[pred_flag_index];
        return 1;
    }
    return 0;
}

static int mv_mp_mode_mx_lt(HEVCContext *s, int x, int y, int pred_flag_index,
                            Mv *mv, int ref_idx_curr, int ref_idx)
{
    MvField *tab_mvf = s->ref->tab_mvf;
    int min_pu_width = s->ps.sps->min_pu_width;

    RefPicList *refPicList = s->ref->refPicList;

    if ((TAB_MVF(x, y).pred_flag) & (1 << pred_flag_index)) {
        int currIsLongTerm     = refPicList[ref_idx_curr].isLongTerm[ref_idx];

        int colIsLongTerm =
            refPicList[pred_flag_index].isLongTerm[(TAB_MVF(x, y).ref_idx[pred_flag_index])];

        if (colIsLongTerm == currIsLongTerm) {
            *mv = TAB_MVF(x, y).mv[pred_flag_index];
            if (!currIsLongTerm)
                dist_scale(s, mv, min_pu_width, x, y,
                           pred_flag_index, ref_idx_curr, ref_idx);
            return 1;
        }
    }
    return 0;
}

#define MP_MX(v, pred, mx)                                      \
    mv_mp_mode_mx(s,                                            \
                  (x ## v) >> s->ps.sps->log2_min_pu_size,         \
                  (y ## v) >> s->ps.sps->log2_min_pu_size,         \
                  pred, &mx, ref_idx_curr, ref_idx)

#define MP_MX_LT(v, pred, mx)                                   \
    mv_mp_mode_mx_lt(s,                                         \
                     (x ## v) >> s->ps.sps->log2_min_pu_size,      \
                     (y ## v) >> s->ps.sps->log2_min_pu_size,      \
                     pred, &mx, ref_idx_curr, ref_idx)

void ff_hevc_luma_mv_mvp_mode(HEVCContext *s, int x0, int y0, int nPbW,
                              int nPbH, int log2_cb_size, int part_idx,
                              int merge_idx, MvField *mv,
                              int mvp_lx_flag, int LX)
{
    HEVCLocalContext *lc = s->HEVClc;
    MvField *tab_mvf = s->ref->tab_mvf;
    int isScaledFlag_L0 = 0;
    int availableFlagLXA0 = 1;
    int availableFlagLXB0 = 1;
    int numMVPCandLX = 0;
    int min_pu_width = s->ps.sps->min_pu_width;

    int xA0, yA0;
    int is_available_a0;
    int xA1, yA1;
    int is_available_a1;
    int xB0, yB0;
    int is_available_b0;
    int xB1, yB1;
    int is_available_b1;
    int xB2, yB2;
    int is_available_b2;

    Mv mvpcand_list[2] = { { 0 } };
    Mv mxA;
    Mv mxB;
    int ref_idx_curr;
    int ref_idx = 0;
    int pred_flag_index_l0;
    int pred_flag_index_l1;

    const int cand_bottom_left = lc->na.cand_bottom_left;
    const int cand_left        = lc->na.cand_left;
    const int cand_up_left     = lc->na.cand_up_left;
    const int cand_up          = lc->na.cand_up;
    const int cand_up_right    = lc->na.cand_up_right_sap;
    ref_idx_curr       = LX;
    ref_idx            = mv->ref_idx[LX];
    pred_flag_index_l0 = LX;
    pred_flag_index_l1 = !LX;

    // left bottom spatial candidate
    xA0 = x0 - 1;
    yA0 = y0 + nPbH;

    is_available_a0 = AVAILABLE(cand_bottom_left, A0) &&
                      yA0 < s->ps.sps->height &&
                      PRED_BLOCK_AVAILABLE(A0);

    //left spatial merge candidate
    xA1    = x0 - 1;
    yA1    = y0 + nPbH - 1;

    is_available_a1 = AVAILABLE(cand_left, A1);
    if (is_available_a0 || is_available_a1)
        isScaledFlag_L0 = 1;

    if (is_available_a0) {
        if (MP_MX(A0, pred_flag_index_l0, mxA)) {
            goto b_candidates;
        }
        if (MP_MX(A0, pred_flag_index_l1, mxA)) {
            goto b_candidates;
        }
    }

    if (is_available_a1) {
        if (MP_MX(A1, pred_flag_index_l0, mxA)) {
            goto b_candidates;
        }
        if (MP_MX(A1, pred_flag_index_l1, mxA)) {
            goto b_candidates;
        }
    }

    if (is_available_a0) {
        if (MP_MX_LT(A0, pred_flag_index_l0, mxA)) {
            goto b_candidates;
        }
        if (MP_MX_LT(A0, pred_flag_index_l1, mxA)) {
            goto b_candidates;
        }
    }

    if (is_available_a1) {
        if (MP_MX_LT(A1, pred_flag_index_l0, mxA)) {
            goto b_candidates;
        }
        if (MP_MX_LT(A1, pred_flag_index_l1, mxA)) {
            goto b_candidates;
        }
    }
    availableFlagLXA0 = 0;

b_candidates:
    // B candidates
    // above right spatial merge candidate
    xB0    = x0 + nPbW;
    yB0    = y0 - 1;

    is_available_b0 =  AVAILABLE(cand_up_right, B0) &&
                       xB0 < s->ps.sps->width &&
                       PRED_BLOCK_AVAILABLE(B0);

    // above spatial merge candidate
    xB1    = x0 + nPbW - 1;
    yB1    = y0 - 1;
    is_available_b1 = AVAILABLE(cand_up, B1);

    // above left spatial merge candidate
    xB2 = x0 - 1;
    yB2 = y0 - 1;
    is_available_b2 = AVAILABLE(cand_up_left, B2);

    // above right spatial merge candidate
    if (is_available_b0) {
        if (MP_MX(B0, pred_flag_index_l0, mxB)) {
            goto scalef;
        }
        if (MP_MX(B0, pred_flag_index_l1, mxB)) {
            goto scalef;
        }
    }

    // above spatial merge candidate
    if (is_available_b1) {
        if (MP_MX(B1, pred_flag_index_l0, mxB)) {
            goto scalef;
        }
        if (MP_MX(B1, pred_flag_index_l1, mxB)) {
            goto scalef;
        }
    }

    // above left spatial merge candidate
    if (is_available_b2) {
        if (MP_MX(B2, pred_flag_index_l0, mxB)) {
            goto scalef;
        }
        if (MP_MX(B2, pred_flag_index_l1, mxB)) {
            goto scalef;
        }
    }
    availableFlagLXB0 = 0;

scalef:
    if (!isScaledFlag_L0) {
        if (availableFlagLXB0) {
            availableFlagLXA0 = 1;
            mxA = mxB;
        }
        availableFlagLXB0 = 0;

        // XB0 and L1
        if (is_available_b0) {
            availableFlagLXB0 = MP_MX_LT(B0, pred_flag_index_l0, mxB);
            if (!availableFlagLXB0)
                availableFlagLXB0 = MP_MX_LT(B0, pred_flag_index_l1, mxB);
        }

        if (is_available_b1 && !availableFlagLXB0) {
            availableFlagLXB0 = MP_MX_LT(B1, pred_flag_index_l0, mxB);
            if (!availableFlagLXB0)
                availableFlagLXB0 = MP_MX_LT(B1, pred_flag_index_l1, mxB);
        }

        if (is_available_b2 && !availableFlagLXB0) {
            availableFlagLXB0 = MP_MX_LT(B2, pred_flag_index_l0, mxB);
            if (!availableFlagLXB0)
                availableFlagLXB0 = MP_MX_LT(B2, pred_flag_index_l1, mxB);
        }
    }

    if (availableFlagLXA0)
        mvpcand_list[numMVPCandLX++] = mxA;

    if (availableFlagLXB0 && (!availableFlagLXA0 || mxA.x != mxB.x || mxA.y != mxB.y))
        mvpcand_list[numMVPCandLX++] = mxB;

    //temporal motion vector prediction candidate
    if (numMVPCandLX < 2 && s->sh.slice_temporal_mvp_enabled_flag &&
        mvp_lx_flag == numMVPCandLX) {
        Mv mv_col;
        int available_col = temporal_luma_motion_vector(s, x0, y0, nPbW,
                                                        nPbH, ref_idx,
                                                        &mv_col, LX);
        if (available_col)
            mvpcand_list[numMVPCandLX++] = mv_col;
    }

    mv->mv[LX] = mvpcand_list[mvp_lx_flag];
}
