Modify reference MV function prototypes

This patch modified the function prototypes in reference MV search,
which prepared for the following change to combine the compound
reference search and 2 single reference search together while the
current block is compound mode. This patch doesn't cause normative
bitstream change.

Change-Id: I0d645983233753861d940b603d13957576ab51fb
diff --git a/av1/common/mvref_common.c b/av1/common/mvref_common.c
index 397da1b..3eb146c 100644
--- a/av1/common/mvref_common.c
+++ b/av1/common/mvref_common.c
@@ -90,8 +90,9 @@
 
 static uint8_t add_ref_mv_candidate(
     const MODE_INFO *const candidate_mi, const MB_MODE_INFO *const candidate,
-    const MV_REFERENCE_FRAME rf[2], uint8_t *refmv_count,
-    uint8_t *ref_match_count, CANDIDATE_MV *ref_mv_stack, const int use_hp,
+    const MV_REFERENCE_FRAME rf[2], uint8_t refmv_counts[MODE_CTX_REF_FRAMES],
+    uint8_t ref_match_counts[MODE_CTX_REF_FRAMES],
+    CANDIDATE_MV ref_mv_stacks[][MAX_REF_MV_STACK_SIZE], const int use_hp,
     int len,
 #if USE_CUR_GM_REFMV
     int_mv *gm_mv_candidates, const WarpedMotionParams *gm_params,
@@ -108,9 +109,13 @@
   int index = 0, ref;
   int newmv_count = 0;
   assert(weight % 2 == 0);
-  (void)ref_match_count;
 
   if (rf[1] == NONE_FRAME) {
+    uint8_t *refmv_count = &refmv_counts[rf[0]];
+    uint8_t *ref_match_count = &ref_match_counts[rf[0]];
+    CANDIDATE_MV *ref_mv_stack = ref_mv_stacks[rf[0]];
+    (void)ref_match_count;
+
     // single reference frame
     for (ref = 0; ref < 2; ++ref) {
       if (candidate->ref_frame[ref] == rf[0]) {
@@ -151,6 +156,12 @@
       }
     }
   } else {
+    MV_REFERENCE_FRAME ref_frame = av1_ref_frame_type(rf);
+    uint8_t *refmv_count = &refmv_counts[ref_frame];
+    uint8_t *ref_match_count = &ref_match_counts[ref_frame];
+    CANDIDATE_MV *ref_mv_stack = ref_mv_stacks[ref_frame];
+    (void)ref_match_count;
+
     // compound reference frame
     if (candidate->ref_frame[0] == rf[0] && candidate->ref_frame[1] == rf[1]) {
       int_mv this_refmv[2];
@@ -203,8 +214,9 @@
 static uint8_t scan_row_mbmi(const AV1_COMMON *cm, const MACROBLOCKD *xd,
                              int mi_row, int mi_col,
                              const MV_REFERENCE_FRAME rf[2], int row_offset,
-                             CANDIDATE_MV *ref_mv_stack, uint8_t *refmv_count,
-                             uint8_t *ref_match_count,
+                             CANDIDATE_MV ref_mv_stack[][MAX_REF_MV_STACK_SIZE],
+                             uint8_t refmv_count[MODE_CTX_REF_FRAMES],
+                             uint8_t ref_match_count[MODE_CTX_REF_FRAMES],
 #if USE_CUR_GM_REFMV
                              int_mv *gm_mv_candidates,
 #endif  // USE_CUR_GM_REFMV
@@ -273,8 +285,9 @@
 static uint8_t scan_col_mbmi(const AV1_COMMON *cm, const MACROBLOCKD *xd,
                              int mi_row, int mi_col,
                              const MV_REFERENCE_FRAME rf[2], int col_offset,
-                             CANDIDATE_MV *ref_mv_stack, uint8_t *refmv_count,
-                             uint8_t *ref_match_count,
+                             CANDIDATE_MV ref_mv_stack[][MAX_REF_MV_STACK_SIZE],
+                             uint8_t refmv_count[MODE_CTX_REF_FRAMES],
+                             uint8_t ref_match_count[MODE_CTX_REF_FRAMES],
 #if USE_CUR_GM_REFMV
                              int_mv *gm_mv_candidates,
 #endif  // USE_CUR_GM_REFMV
@@ -341,12 +354,13 @@
 static uint8_t scan_blk_mbmi(const AV1_COMMON *cm, const MACROBLOCKD *xd,
                              const int mi_row, const int mi_col,
                              const MV_REFERENCE_FRAME rf[2], int row_offset,
-                             int col_offset, CANDIDATE_MV *ref_mv_stack,
-                             uint8_t *ref_match_count,
+                             int col_offset,
+                             CANDIDATE_MV ref_mv_stack[][MAX_REF_MV_STACK_SIZE],
+                             uint8_t ref_match_count[MODE_CTX_REF_FRAMES],
 #if USE_CUR_GM_REFMV
                              int_mv *gm_mv_candidates,
 #endif  // USE_CUR_GM_REFMV
-                             uint8_t *refmv_count) {
+                             uint8_t refmv_count[MODE_CTX_REF_FRAMES]) {
   const TileInfo *const tile = &xd->tile;
   POSITION mi_pos;
   uint8_t newmv_count = 0;
@@ -450,7 +464,8 @@
                           const MACROBLOCKD *xd, int mi_row, int mi_col,
                           MV_REFERENCE_FRAME ref_frame, int blk_row,
                           int blk_col, int_mv *gm_mv_candidates,
-                          uint8_t *refmv_count, CANDIDATE_MV *ref_mv_stack,
+                          uint8_t refmv_count[MODE_CTX_REF_FRAMES],
+                          CANDIDATE_MV ref_mv_stacks[][MAX_REF_MV_STACK_SIZE],
                           int16_t *mode_context) {
   (void)prev_frame_mvs_base;
   POSITION mi_pos;
@@ -478,6 +493,7 @@
     int buf_idx_0 = cm->frame_refs[FWD_RF_OFFSET(rf[0])].idx;
     int frame0_index = cm->buffer_pool->frame_bufs[buf_idx_0].cur_frame_offset;
     int cur_offset_0 = cur_frame_index - frame0_index;
+    CANDIDATE_MV *ref_mv_stack = ref_mv_stacks[rf[0]];
 
     for (int i = 0; i < MFMV_STACK_SIZE; ++i) {
       if (prev_frame_mvs->mfmv0[i].as_int != INVALID_MV) {
@@ -504,18 +520,20 @@
             mode_context[ref_frame] |= (1 << GLOBALMV_OFFSET);
 #endif
 
-        for (idx = 0; idx < *refmv_count; ++idx)
+        for (idx = 0; idx < refmv_count[rf[0]]; ++idx)
           if (this_refmv.as_int == ref_mv_stack[idx].this_mv.as_int) break;
 
-        if (idx < *refmv_count) ref_mv_stack[idx].weight += 2 * weight_unit;
+        if (idx < refmv_count[rf[0]])
+          ref_mv_stack[idx].weight += 2 * weight_unit;
 
-        if (idx == *refmv_count && *refmv_count < MAX_REF_MV_STACK_SIZE) {
+        if (idx == refmv_count[rf[0]] &&
+            refmv_count[rf[0]] < MAX_REF_MV_STACK_SIZE) {
           ref_mv_stack[idx].this_mv.as_int = this_refmv.as_int;
           // TODO(jingning): Hard coded context number. Need to make it better
           // sense.
           ref_mv_stack[idx].pred_diff[0] = 1;
           ref_mv_stack[idx].weight = 2 * weight_unit;
-          ++(*refmv_count);
+          ++(refmv_count[rf[0]]);
         }
 
         ++coll_blk_count;
@@ -532,6 +550,7 @@
     int buf_idx_1 = cm->frame_refs[FWD_RF_OFFSET(rf[1])].idx;
     int frame1_index = cm->buffer_pool->frame_bufs[buf_idx_1].cur_frame_offset;
     int cur_offset_1 = cur_frame_index - frame1_index;
+    CANDIDATE_MV *ref_mv_stack = ref_mv_stacks[ref_frame];
 
     for (int i = 0; i < MFMV_STACK_SIZE; ++i) {
       if (prev_frame_mvs->mfmv0[i].as_int != INVALID_MV) {
@@ -568,14 +587,16 @@
             mode_context[ref_frame] |= (1 << GLOBALMV_OFFSET);
 #endif
 
-        for (idx = 0; idx < *refmv_count; ++idx)
+        for (idx = 0; idx < refmv_count[ref_frame]; ++idx)
           if (this_refmv.as_int == ref_mv_stack[idx].this_mv.as_int &&
               comp_refmv.as_int == ref_mv_stack[idx].comp_mv.as_int)
             break;
 
-        if (idx < *refmv_count) ref_mv_stack[idx].weight += 2 * weight_unit;
+        if (idx < refmv_count[ref_frame])
+          ref_mv_stack[idx].weight += 2 * weight_unit;
 
-        if (idx == *refmv_count && *refmv_count < MAX_REF_MV_STACK_SIZE) {
+        if (idx == refmv_count[ref_frame] &&
+            refmv_count[ref_frame] < MAX_REF_MV_STACK_SIZE) {
           ref_mv_stack[idx].this_mv.as_int = this_refmv.as_int;
           ref_mv_stack[idx].comp_mv.as_int = comp_refmv.as_int;
           // TODO(jingning): Hard coded context number. Need to make it better
@@ -583,7 +604,7 @@
           ref_mv_stack[idx].pred_diff[0] = 1;
           ref_mv_stack[idx].pred_diff[1] = 1;
           ref_mv_stack[idx].weight = 2 * weight_unit;
-          ++(*refmv_count);
+          ++(refmv_count[ref_frame]);
         }
 
         ++coll_blk_count;
@@ -599,8 +620,10 @@
                           const MV_REF *prev_frame_mvs_base,
                           int prev_frame_mvs_stride, const MACROBLOCKD *xd,
                           int mi_row, int mi_col, MV_REFERENCE_FRAME ref_frame,
-                          int blk_row, int blk_col, uint8_t *refmv_count,
-                          CANDIDATE_MV *ref_mv_stack, int16_t *mode_context) {
+                          int blk_row, int blk_col,
+                          uint8_t refmv_count[MODE_CTX_REF_FRAMES],
+                          CANDIDATE_MV ref_mv_stacks[][MAX_REF_MV_STACK_SIZE],
+                          int16_t *mode_context) {
 #if CONFIG_TMV
   const MV_REF *prev_frame_mvs = prev_frame_mvs_base +
                                  (blk_row >> 1) * prev_frame_mvs_stride +
@@ -613,6 +636,7 @@
   int ref, idx;
   int coll_blk_count = 0;
   const int weight_unit = mi_size_wide[BLOCK_8X8];
+  CANDIDATE_MV *ref_mv_stack = ref_mv_stacks[ref_frame];
 
 #if CONFIG_TMV
   mi_pos.row = blk_row;
@@ -642,17 +666,19 @@
           mode_context[ref_frame] |= (1 << GLOBALMV_OFFSET);
       }
 
-      for (idx = 0; idx < *refmv_count; ++idx)
+      for (idx = 0; idx < refmv_count[ref_frame]; ++idx)
         if (this_refmv.as_int == ref_mv_stack[idx].this_mv.as_int) break;
 
-      if (idx < *refmv_count) ref_mv_stack[idx].weight += 2 * weight_unit;
+      if (idx < refmv_count[ref_frame])
+        ref_mv_stack[idx].weight += 2 * weight_unit;
 
-      if (idx == *refmv_count && *refmv_count < MAX_REF_MV_STACK_SIZE) {
+      if (idx == refmv_count[ref_frame] &&
+          refmv_count[ref_frame] < MAX_REF_MV_STACK_SIZE) {
         ref_mv_stack[idx].this_mv.as_int = this_refmv.as_int;
         ref_mv_stack[idx].pred_diff[0] =
             av1_get_pred_diff_ctx(prev_frame_mvs->pred_mv[ref], this_refmv);
         ref_mv_stack[idx].weight = 2 * weight_unit;
-        ++(*refmv_count);
+        ++(refmv_count[ref_frame]);
       }
 
       ++coll_blk_count;
@@ -663,14 +689,15 @@
 }
 #endif  // CONFIG_MFMV
 
-static void setup_ref_mv_list(const AV1_COMMON *cm, const MACROBLOCKD *xd,
-                              MV_REFERENCE_FRAME ref_frame,
-                              uint8_t *refmv_count, CANDIDATE_MV *ref_mv_stack,
-                              int_mv *mv_ref_list,
+static void setup_ref_mv_list(
+    const AV1_COMMON *cm, const MACROBLOCKD *xd, MV_REFERENCE_FRAME ref_frame,
+    uint8_t refmv_count[MODE_CTX_REF_FRAMES],
+    CANDIDATE_MV ref_mv_stack[][MAX_REF_MV_STACK_SIZE],
+    int_mv mv_ref_list[][MAX_MV_REF_CANDIDATES],
 #if USE_CUR_GM_REFMV
-                              int_mv *gm_mv_candidates,
+    int_mv *gm_mv_candidates,
 #endif  // USE_CUR_GM_REFMV
-                              int mi_row, int mi_col, int16_t *mode_context) {
+    int mi_row, int mi_col, int16_t *mode_context, int compound_search) {
 #if CONFIG_TMV
   const int prev_frame_mvs_stride = ROUND_POWER_OF_TWO(cm->mi_cols, 1);
   const int tmi_row = mi_row & 0xfffe;
@@ -703,7 +730,8 @@
 
   av1_set_ref_frame(rf, ref_frame);
   mode_context[ref_frame] = 0;
-  *refmv_count = 0;
+  refmv_count[ref_frame] = 0;
+  (void)compound_search;
 
   // Find valid maximum row/col offset.
   if (xd->up_available) {
@@ -725,13 +753,13 @@
     max_col_offset = find_valid_col_offset(tile, mi_col, max_col_offset);
   }
 
-  uint8_t ref_match_count = 0;
+  uint8_t ref_match_count[MODE_CTX_REF_FRAMES] = { 0 };
   uint8_t newmv_count = 0;
 
   // Scan the first above row mode info. row_offset = -1;
   if (abs(max_row_offset) >= 1)
     newmv_count += scan_row_mbmi(cm, xd, mi_row, mi_col, rf, -1, ref_mv_stack,
-                                 refmv_count, &ref_match_count,
+                                 refmv_count, ref_match_count,
 #if USE_CUR_GM_REFMV
                                  gm_mv_candidates,
 #endif  // USE_CUR_GM_REFMV
@@ -739,7 +767,7 @@
   // Scan the first left column mode info. col_offset = -1;
   if (abs(max_col_offset) >= 1)
     newmv_count += scan_col_mbmi(cm, xd, mi_row, mi_col, rf, -1, ref_mv_stack,
-                                 refmv_count, &ref_match_count,
+                                 refmv_count, ref_match_count,
 #if USE_CUR_GM_REFMV
                                  gm_mv_candidates,
 #endif  // USE_CUR_GM_REFMV
@@ -747,21 +775,25 @@
   // Check top-right boundary
   if (has_tr)
     newmv_count += scan_blk_mbmi(cm, xd, mi_row, mi_col, rf, -1, xd->n8_w,
-                                 ref_mv_stack, &ref_match_count,
+                                 ref_mv_stack, ref_match_count,
 #if USE_CUR_GM_REFMV
                                  gm_mv_candidates,
 #endif  // USE_CUR_GM_REFMV
                                  refmv_count);
 
-  const int nearest_match = ref_match_count;
-  const int nearest_refmv_count = *refmv_count;
+  uint8_t nearest_match[MODE_CTX_REF_FRAMES];
+  uint8_t nearest_refmv_count[MODE_CTX_REF_FRAMES];
 
-  for (int idx = 0; idx < nearest_refmv_count; ++idx)
-    ref_mv_stack[idx].weight += REF_CAT_LEVEL;
+  nearest_match[ref_frame] = ref_match_count[ref_frame];
+  nearest_refmv_count[ref_frame] = refmv_count[ref_frame];
+
+  // TODO(yunqing): for comp_search, do it for all 3 cases.
+  for (int idx = 0; idx < nearest_refmv_count[ref_frame]; ++idx)
+    ref_mv_stack[ref_frame][idx].weight += REF_CAT_LEVEL;
 
 #if CONFIG_MFMV
   if (cm->use_ref_frame_mvs) {
-    int coll_blk_count = 0;
+    int coll_blk_count[MODE_CTX_REF_FRAMES] = { 0 };
     const int voffset = AOMMAX(mi_size_high[BLOCK_8X8], xd->n8_h);
     const int hoffset = AOMMAX(mi_size_wide[BLOCK_8X8], xd->n8_w);
 
@@ -781,11 +813,13 @@
         int is_available = add_tpl_ref_mv(
             cm, prev_frame_mvs_base, xd, mi_row, mi_col, ref_frame, blk_row,
             blk_col, gm_mv_candidates, refmv_count, ref_mv_stack, mode_context);
-        if (blk_row == 0 && blk_col == 0) coll_blk_count = is_available;
+        if (blk_row == 0 && blk_col == 0)
+          coll_blk_count[ref_frame] = is_available;
       }
     }
 
-    if (coll_blk_count == 0) mode_context[ref_frame] |= (1 << GLOBALMV_OFFSET);
+    if (coll_blk_count[ref_frame] == 0)
+      mode_context[ref_frame] |= (1 << GLOBALMV_OFFSET);
 
     for (int i = 0; i < 3 && allow_extension; ++i) {
       const int blk_row = tpl_sample_pos[i][0];
@@ -794,14 +828,14 @@
       if (!check_sb_border(cm, mi_row, mi_col, blk_row, blk_col)) continue;
       // (TODO: yunqing) prev_frame_mvs_base is not used here, tpl_mvs is used.
       // Can be modified the same way.
-      coll_blk_count += add_tpl_ref_mv(
+      coll_blk_count[ref_frame] += add_tpl_ref_mv(
           cm, prev_frame_mvs_base, xd, mi_row, mi_col, ref_frame, blk_row,
           blk_col, gm_mv_candidates, refmv_count, ref_mv_stack, mode_context);
     }
   }
 #else
   if (cm->use_prev_frame_mvs && rf[1] == NONE_FRAME) {
-    int coll_blk_count = 0;
+    int coll_blk_count[MODE_CTX_REF_FRAMES] = { 0 };
     const int mi_step = (xd->n8_w == 1 || xd->n8_h == 1)
                             ? mi_size_wide[BLOCK_8X8]
                             : mi_size_wide[BLOCK_16X16];
@@ -820,14 +854,16 @@
                            refmv_count, ref_mv_stack, mode_context);
 #endif  // CONFIG_TMV
 #if CONFIG_OPT_REF_MV
-        if (blk_row == 0 && blk_col == 0) coll_blk_count = is_available;
+        if (blk_row == 0 && blk_col == 0)
+          coll_blk_count[ref_frame] = is_available;
 #else
-        coll_blk_count += is_available;
+        coll_blk_count[ref_frame] += is_available;
 #endif
       }
     }
 
-    if (coll_blk_count == 0) mode_context[ref_frame] |= (1 << GLOBALMV_OFFSET);
+    if (coll_blk_count[ref_frame] == 0)
+      mode_context[ref_frame] |= (1 << GLOBALMV_OFFSET);
   } else {
     mode_context[ref_frame] |= (1 << GLOBALMV_OFFSET);
   }
@@ -835,7 +871,7 @@
 
   // Scan the second outer area.
   scan_blk_mbmi(cm, xd, mi_row, mi_col, rf, -1, -1, ref_mv_stack,
-                &ref_match_count,
+                ref_match_count,
 #if USE_CUR_GM_REFMV
                 gm_mv_candidates,
 #endif  // USE_CUR_GM_REFMV
@@ -848,7 +884,7 @@
     if (abs(row_offset) <= abs(max_row_offset) &&
         abs(row_offset) > processed_rows)
       scan_row_mbmi(cm, xd, mi_row, mi_col, rf, row_offset, ref_mv_stack,
-                    refmv_count, &ref_match_count,
+                    refmv_count, ref_match_count,
 #if USE_CUR_GM_REFMV
                     gm_mv_candidates,
 #endif  // USE_CUR_GM_REFMV
@@ -857,7 +893,7 @@
     if (abs(col_offset) <= abs(max_col_offset) &&
         abs(col_offset) > processed_cols)
       scan_col_mbmi(cm, xd, mi_row, mi_col, rf, col_offset, ref_mv_stack,
-                    refmv_count, &ref_match_count,
+                    refmv_count, ref_match_count,
 #if USE_CUR_GM_REFMV
                     gm_mv_candidates,
 #endif  // USE_CUR_GM_REFMV
@@ -868,43 +904,43 @@
   if (abs(col_offset) <= abs(max_col_offset) &&
       abs(col_offset) > processed_cols)
     scan_col_mbmi(cm, xd, mi_row, mi_col, rf, col_offset, ref_mv_stack,
-                  refmv_count, &ref_match_count,
+                  refmv_count, ref_match_count,
 #if USE_CUR_GM_REFMV
                   gm_mv_candidates,
 #endif  // USE_CUR_GM_REFMV
                   max_col_offset, &processed_cols);
 
 #if CONFIG_OPT_REF_MV
-  switch (nearest_match)
+  switch (nearest_match[ref_frame])
 #else
-  switch (nearest_refmv_count)
+  switch (nearest_refmv_count[ref_frame])
 #endif
   {
     case 0: mode_context[ref_frame] |= 0;
 #if CONFIG_OPT_REF_MV
-      if (ref_match_count >= 1) mode_context[ref_frame] |= 1;
-      if (ref_match_count == 1)
+      if (ref_match_count[ref_frame] >= 1) mode_context[ref_frame] |= 1;
+      if (ref_match_count[ref_frame] == 1)
         mode_context[ref_frame] |= (1 << REFMV_OFFSET);
-      else if (ref_match_count >= 2)
+      else if (ref_match_count[ref_frame] >= 2)
         mode_context[ref_frame] |= (2 << REFMV_OFFSET);
 #else
-      if (*refmv_count >= 1) mode_context[ref_frame] |= 1;
-      if (*refmv_count == 1)
+      if (refmv_count[ref_frame] >= 1) mode_context[ref_frame] |= 1;
+      if (refmv_count[ref_frame] == 1)
         mode_context[ref_frame] |= (1 << REFMV_OFFSET);
-      else if (*refmv_count >= 2)
+      else if (refmv_count[ref_frame] >= 2)
         mode_context[ref_frame] |= (2 << REFMV_OFFSET);
 #endif
       break;
     case 1: mode_context[ref_frame] |= (newmv_count > 0) ? 2 : 3;
 #if CONFIG_OPT_REF_MV
-      if (ref_match_count == 1)
+      if (ref_match_count[ref_frame] == 1)
         mode_context[ref_frame] |= (3 << REFMV_OFFSET);
-      else if (ref_match_count >= 2)
+      else if (ref_match_count[ref_frame] >= 2)
         mode_context[ref_frame] |= (4 << REFMV_OFFSET);
 #else
-      if (*refmv_count == 1)
+      if (refmv_count[ref_frame] == 1)
         mode_context[ref_frame] |= (3 << REFMV_OFFSET);
-      else if (*refmv_count >= 2)
+      else if (refmv_count[ref_frame] >= 2)
         mode_context[ref_frame] |= (4 << REFMV_OFFSET);
 #endif
       break;
@@ -923,28 +959,30 @@
   }
 
   // Rank the likelihood and assign nearest and near mvs.
-  int len = nearest_refmv_count;
+  int len = nearest_refmv_count[ref_frame];
   while (len > 0) {
     int nr_len = 0;
     for (int idx = 1; idx < len; ++idx) {
-      if (ref_mv_stack[idx - 1].weight < ref_mv_stack[idx].weight) {
-        CANDIDATE_MV tmp_mv = ref_mv_stack[idx - 1];
-        ref_mv_stack[idx - 1] = ref_mv_stack[idx];
-        ref_mv_stack[idx] = tmp_mv;
+      if (ref_mv_stack[ref_frame][idx - 1].weight <
+          ref_mv_stack[ref_frame][idx].weight) {
+        CANDIDATE_MV tmp_mv = ref_mv_stack[ref_frame][idx - 1];
+        ref_mv_stack[ref_frame][idx - 1] = ref_mv_stack[ref_frame][idx];
+        ref_mv_stack[ref_frame][idx] = tmp_mv;
         nr_len = idx;
       }
     }
     len = nr_len;
   }
 
-  len = *refmv_count;
-  while (len > nearest_refmv_count) {
-    int nr_len = nearest_refmv_count;
-    for (int idx = nearest_refmv_count + 1; idx < len; ++idx) {
-      if (ref_mv_stack[idx - 1].weight < ref_mv_stack[idx].weight) {
-        CANDIDATE_MV tmp_mv = ref_mv_stack[idx - 1];
-        ref_mv_stack[idx - 1] = ref_mv_stack[idx];
-        ref_mv_stack[idx] = tmp_mv;
+  len = refmv_count[ref_frame];
+  while (len > nearest_refmv_count[ref_frame]) {
+    int nr_len = nearest_refmv_count[ref_frame];
+    for (int idx = nearest_refmv_count[ref_frame] + 1; idx < len; ++idx) {
+      if (ref_mv_stack[ref_frame][idx - 1].weight <
+          ref_mv_stack[ref_frame][idx].weight) {
+        CANDIDATE_MV tmp_mv = ref_mv_stack[ref_frame][idx - 1];
+        ref_mv_stack[ref_frame][idx - 1] = ref_mv_stack[ref_frame][idx];
+        ref_mv_stack[ref_frame][idx] = tmp_mv;
         nr_len = idx;
       }
     }
@@ -952,17 +990,18 @@
   }
 
   if (rf[1] > NONE_FRAME) {
-    for (int idx = 0; idx < *refmv_count; ++idx) {
-      clamp_mv_ref(&ref_mv_stack[idx].this_mv.as_mv, xd->n8_w << MI_SIZE_LOG2,
-                   xd->n8_h << MI_SIZE_LOG2, xd);
-      clamp_mv_ref(&ref_mv_stack[idx].comp_mv.as_mv, xd->n8_w << MI_SIZE_LOG2,
-                   xd->n8_h << MI_SIZE_LOG2, xd);
+    for (int idx = 0; idx < refmv_count[ref_frame]; ++idx) {
+      clamp_mv_ref(&ref_mv_stack[ref_frame][idx].this_mv.as_mv,
+                   xd->n8_w << MI_SIZE_LOG2, xd->n8_h << MI_SIZE_LOG2, xd);
+      clamp_mv_ref(&ref_mv_stack[ref_frame][idx].comp_mv.as_mv,
+                   xd->n8_w << MI_SIZE_LOG2, xd->n8_h << MI_SIZE_LOG2, xd);
     }
   } else {
-    for (int idx = 0; idx < AOMMIN(MAX_MV_REF_CANDIDATES, *refmv_count);
-         ++idx) {
-      mv_ref_list[idx].as_int = ref_mv_stack[idx].this_mv.as_int;
-      clamp_mv_ref(&mv_ref_list[idx].as_mv, xd->n8_w << MI_SIZE_LOG2,
+    for (int idx = 0;
+         idx < AOMMIN(MAX_MV_REF_CANDIDATES, refmv_count[ref_frame]); ++idx) {
+      mv_ref_list[rf[0]][idx].as_int =
+          ref_mv_stack[ref_frame][idx].this_mv.as_int;
+      clamp_mv_ref(&mv_ref_list[rf[0]][idx].as_mv, xd->n8_w << MI_SIZE_LOG2,
                    xd->n8_h << MI_SIZE_LOG2, xd);
     }
   }
@@ -1170,16 +1209,17 @@
 
 void av1_find_mv_refs(const AV1_COMMON *cm, const MACROBLOCKD *xd,
                       MODE_INFO *mi, MV_REFERENCE_FRAME ref_frame,
-                      uint8_t *ref_mv_count, CANDIDATE_MV *ref_mv_stack,
-                      int16_t *compound_mode_context, int_mv *mv_ref_list,
-                      int mi_row, int mi_col, find_mv_refs_sync sync,
-                      void *const data, int16_t *mode_context) {
+                      uint8_t ref_mv_count[MODE_CTX_REF_FRAMES],
+                      CANDIDATE_MV ref_mv_stack[][MAX_REF_MV_STACK_SIZE],
+                      int16_t *compound_mode_context,
+                      int_mv mv_ref_list[][MAX_MV_REF_CANDIDATES], int mi_row,
+                      int mi_col, find_mv_refs_sync sync, void *const data,
+                      int16_t *mode_context, int compound_search) {
   int_mv zeromv[2];
   BLOCK_SIZE bsize = mi->mbmi.sb_type;
   MV_REFERENCE_FRAME rf[2];
-
+  av1_set_ref_frame(rf, ref_frame);
   if (!CONFIG_INTRABC || ref_frame != INTRA_FRAME) {
-    av1_set_ref_frame(rf, ref_frame);
     zeromv[0].as_int =
         gm_get_motion_vector(&cm->global_motion[rf[0]],
                              cm->allow_high_precision_mv, bsize, mi_col, mi_row
@@ -1208,11 +1248,12 @@
 #if USE_CUR_GM_REFMV
                     zeromv,
 #endif  // USE_CUR_GM_REFMV
-                    mi_row, mi_col, mode_context);
+                    mi_row, mi_col, mode_context, compound_search);
 
   if (ref_frame <= ALTREF_FRAME)
-    find_mv_refs_idx(cm, xd, mi, ref_frame, mv_ref_list, mi_row, mi_col, sync,
-                     data, compound_mode_context, zeromv[0], *ref_mv_count);
+    find_mv_refs_idx(cm, xd, mi, ref_frame, mv_ref_list[rf[0]], mi_row, mi_col,
+                     sync, data, compound_mode_context, zeromv[0],
+                     ref_mv_count[ref_frame]);
 }
 
 void av1_find_best_ref_mvs(int allow_hp, int_mv *mvlist, int_mv *nearest_mv,
diff --git a/av1/common/mvref_common.h b/av1/common/mvref_common.h
index e76f378..7ab8ec0 100644
--- a/av1/common/mvref_common.h
+++ b/av1/common/mvref_common.h
@@ -471,10 +471,12 @@
 typedef void (*find_mv_refs_sync)(void *const data, int mi_row);
 void av1_find_mv_refs(const AV1_COMMON *cm, const MACROBLOCKD *xd,
                       MODE_INFO *mi, MV_REFERENCE_FRAME ref_frame,
-                      uint8_t *ref_mv_count, CANDIDATE_MV *ref_mv_stack,
-                      int16_t *compound_mode_context, int_mv *mv_ref_list,
-                      int mi_row, int mi_col, find_mv_refs_sync sync,
-                      void *const data, int16_t *mode_context);
+                      uint8_t ref_mv_count[MODE_CTX_REF_FRAMES],
+                      CANDIDATE_MV ref_mv_stack[][MAX_REF_MV_STACK_SIZE],
+                      int16_t *compound_mode_context,
+                      int_mv mv_ref_list[][MAX_MV_REF_CANDIDATES], int mi_row,
+                      int mi_col, find_mv_refs_sync sync, void *const data,
+                      int16_t *mode_context, int compound_search);
 
 // check a list of motion vectors by sad score using a number rows of pixels
 // above and a number cols of pixels in the left to select the one with best
diff --git a/av1/decoder/decodemv.c b/av1/decoder/decodemv.c
index c841955..6d635da 100644
--- a/av1/decoder/decodemv.c
+++ b/av1/decoder/decodemv.c
@@ -946,18 +946,18 @@
     mbmi->interp_filters = av1_broadcast_interp_filter(BILINEAR);
 
     int16_t inter_mode_ctx[MODE_CTX_REF_FRAMES];
-    int_mv ref_mvs[MAX_MV_REF_CANDIDATES];
+    int_mv ref_mvs[INTRA_FRAME + 1][MAX_MV_REF_CANDIDATES];
 
-    av1_find_mv_refs(cm, xd, mi, INTRA_FRAME, &xd->ref_mv_count[INTRA_FRAME],
-                     xd->ref_mv_stack[INTRA_FRAME], NULL, ref_mvs, mi_row,
-                     mi_col, NULL, NULL, inter_mode_ctx);
+    av1_find_mv_refs(cm, xd, mi, INTRA_FRAME, xd->ref_mv_count,
+                     xd->ref_mv_stack, NULL, ref_mvs, mi_row, mi_col, NULL,
+                     NULL, inter_mode_ctx, 0);
 
     int_mv nearestmv, nearmv;
 
 #if CONFIG_AMVR
-    av1_find_best_ref_mvs(0, ref_mvs, &nearestmv, &nearmv, 0);
+    av1_find_best_ref_mvs(0, ref_mvs[INTRA_FRAME], &nearestmv, &nearmv, 0);
 #else
-    av1_find_best_ref_mvs(0, ref_mvs, &nearestmv, &nearmv);
+    av1_find_best_ref_mvs(0, ref_mvs[INTRA_FRAME], &nearestmv, &nearmv);
 #endif
     int_mv dv_ref = nearestmv.as_int == 0 ? nearmv : nearestmv;
     if (dv_ref.as_int == 0)
@@ -1728,43 +1728,38 @@
 #if CONFIG_OPT_REF_MV
   if (is_compound) {
     MV_REFERENCE_FRAME ref_frame = av1_ref_frame_type(mbmi->ref_frame);
-    av1_find_mv_refs(cm, xd, mi, ref_frame, &xd->ref_mv_count[ref_frame],
-                     xd->ref_mv_stack[ref_frame], compound_inter_mode_ctx,
-                     ref_mvs[ref_frame], mi_row, mi_col, fpm_sync, (void *)pbi,
-                     inter_mode_ctx);
+    av1_find_mv_refs(cm, xd, mi, ref_frame, xd->ref_mv_count, xd->ref_mv_stack,
+                     compound_inter_mode_ctx, ref_mvs, mi_row, mi_col, fpm_sync,
+                     (void *)pbi, inter_mode_ctx, 0);
     if (xd->ref_mv_count[ref_frame] <= 1) {
       for (int ref = 0; ref < 1 + is_compound; ++ref) {
         MV_REFERENCE_FRAME frame = mbmi->ref_frame[ref];
 
-        av1_find_mv_refs(cm, xd, mi, frame, &xd->ref_mv_count[frame],
-                         xd->ref_mv_stack[frame], compound_inter_mode_ctx,
-                         ref_mvs[frame], mi_row, mi_col, fpm_sync, (void *)pbi,
-                         inter_mode_ctx);
+        av1_find_mv_refs(cm, xd, mi, frame, xd->ref_mv_count, xd->ref_mv_stack,
+                         compound_inter_mode_ctx, ref_mvs, mi_row, mi_col,
+                         fpm_sync, (void *)pbi, inter_mode_ctx, 0);
       }
     }
   } else {
     MV_REFERENCE_FRAME frame = mbmi->ref_frame[0];
-    av1_find_mv_refs(cm, xd, mi, frame, &xd->ref_mv_count[frame],
-                     xd->ref_mv_stack[frame], compound_inter_mode_ctx,
-                     ref_mvs[frame], mi_row, mi_col, fpm_sync, (void *)pbi,
-                     inter_mode_ctx);
+    av1_find_mv_refs(cm, xd, mi, frame, xd->ref_mv_count, xd->ref_mv_stack,
+                     compound_inter_mode_ctx, ref_mvs, mi_row, mi_col, fpm_sync,
+                     (void *)pbi, inter_mode_ctx, 0);
   }
 #else
   for (int ref = 0; ref < 1 + is_compound; ++ref) {
     MV_REFERENCE_FRAME frame = mbmi->ref_frame[ref];
 
-    av1_find_mv_refs(cm, xd, mi, frame, &xd->ref_mv_count[frame],
-                     xd->ref_mv_stack[frame], compound_inter_mode_ctx,
-                     ref_mvs[frame], mi_row, mi_col, fpm_sync, (void *)pbi,
-                     inter_mode_ctx);
+    av1_find_mv_refs(cm, xd, mi, frame, xd->ref_mv_count, xd->ref_mv_stack,
+                     compound_inter_mode_ctx, ref_mvs, mi_row, mi_col, fpm_sync,
+                     (void *)pbi, inter_mode_ctx, 0);
   }
 
   if (is_compound) {
     MV_REFERENCE_FRAME ref_frame = av1_ref_frame_type(mbmi->ref_frame);
-    av1_find_mv_refs(cm, xd, mi, ref_frame, &xd->ref_mv_count[ref_frame],
-                     xd->ref_mv_stack[ref_frame], compound_inter_mode_ctx,
-                     ref_mvs[ref_frame], mi_row, mi_col, fpm_sync, (void *)pbi,
-                     inter_mode_ctx);
+    av1_find_mv_refs(cm, xd, mi, ref_frame, xd->ref_mv_count, xd->ref_mv_stack,
+                     compound_inter_mode_ctx, ref_mvs, mi_row, mi_col, fpm_sync,
+                     (void *)pbi, inter_mode_ctx, 0);
   }
 #endif
 
diff --git a/av1/encoder/rdopt.c b/av1/encoder/rdopt.c
index b1da133..3250ebe 100644
--- a/av1/encoder/rdopt.c
+++ b/av1/encoder/rdopt.c
@@ -6338,10 +6338,10 @@
                        num_planes);
 
   // Gets an initial list of candidate vectors from neighbours and orders them
-  av1_find_mv_refs(cm, xd, mi, ref_frame, &mbmi_ext->ref_mv_count[ref_frame],
-                   mbmi_ext->ref_mv_stack[ref_frame],
-                   mbmi_ext->compound_mode_context, candidates, mi_row, mi_col,
-                   NULL, NULL, mbmi_ext->mode_context);
+  av1_find_mv_refs(cm, xd, mi, ref_frame, mbmi_ext->ref_mv_count,
+                   mbmi_ext->ref_mv_stack, mbmi_ext->compound_mode_context,
+                   mbmi_ext->ref_mvs, mi_row, mi_col, NULL, NULL,
+                   mbmi_ext->mode_context, 0);
 
 // Candidate refinement carried out at encoder and decoder
 #if CONFIG_AMVR
@@ -8785,10 +8785,10 @@
   MB_MODE_INFO_EXT *const mbmi_ext = x->mbmi_ext;
   MV_REFERENCE_FRAME ref_frame = INTRA_FRAME;
   int_mv *const candidates = x->mbmi_ext->ref_mvs[ref_frame];
-  av1_find_mv_refs(cm, xd, mi, ref_frame, &mbmi_ext->ref_mv_count[ref_frame],
-                   mbmi_ext->ref_mv_stack[ref_frame],
-                   mbmi_ext->compound_mode_context, candidates, mi_row, mi_col,
-                   NULL, NULL, mbmi_ext->mode_context);
+  av1_find_mv_refs(cm, xd, mi, ref_frame, mbmi_ext->ref_mv_count,
+                   mbmi_ext->ref_mv_stack, mbmi_ext->compound_mode_context,
+                   mbmi_ext->ref_mvs, mi_row, mi_col, NULL, NULL,
+                   mbmi_ext->mode_context, 0);
 
   int_mv nearestmv, nearmv;
 #if CONFIG_AMVR
@@ -9466,12 +9466,11 @@
   // woud be examined for the RD evaluation.
   for (; ref_frame < MODE_CTX_REF_FRAMES; ++ref_frame) {
     MODE_INFO *const mi = xd->mi[0];
-    int_mv *const candidates = x->mbmi_ext->ref_mvs[ref_frame];
     x->mbmi_ext->mode_context[ref_frame] = 0;
-    av1_find_mv_refs(cm, xd, mi, ref_frame, &mbmi_ext->ref_mv_count[ref_frame],
-                     mbmi_ext->ref_mv_stack[ref_frame],
-                     mbmi_ext->compound_mode_context, candidates, mi_row,
-                     mi_col, NULL, NULL, mbmi_ext->mode_context);
+    av1_find_mv_refs(cm, xd, mi, ref_frame, mbmi_ext->ref_mv_count,
+                     mbmi_ext->ref_mv_stack, mbmi_ext->compound_mode_context,
+                     mbmi_ext->ref_mvs, mi_row, mi_col, NULL, NULL,
+                     mbmi_ext->mode_context, 0);
   }
 
   av1_count_overlappable_neighbors(cm, xd, mi_row, mi_col);