Avoid complete TPL evaluation in shorten gf interval decision

For gop_length_decision_method = 1, complete TPL is performed
when sub-gop size is not determined by performing on fewer layer
frames (i.e, ARF, base + 1 and base + 2 frames).
To simplify the design, this patch removes the second call of TPL
from gop_length_decision_method = 1. This patch also removes
gop_length_decision_method = 0 as it was unused.

     Enc. Instr.            BD-Rate Loss(%)
cpu  Reduction(%) avg.psnr  ovr.psnr   ssim     vmaf   vmaf_neg
 0      0.312       0.0256   0.0240   0.0252   0.0420    0.0393
 1      0.681       0.0267   0.0251   0.0219   0.0259    0.0292
 2      0.376       0.0173   0.0144   0.0183   0.0262    0.0199
 3      0.402       0.0148   0.0140   0.0096   0.0329    0.0134
 4      0.416       0.0280   0.0351   0.0398   0.0504    0.0362

STATS_CHANGED for speed 0 to 4.

Change-Id: I326c238c7693f892ac5b08a5c5c03b346a530cba
diff --git a/av1/encoder/encode_strategy.c b/av1/encoder/encode_strategy.c
index 3cf86a2..d660b39 100644
--- a/av1/encoder/encode_strategy.c
+++ b/av1/encoder/encode_strategy.c
@@ -902,7 +902,7 @@
     if (allow_tpl) {
       if (!cpi->skip_tpl_setup_stats) {
         av1_tpl_preload_rc_estimate(cpi, frame_params);
-        av1_tpl_setup_stats(cpi, 0, frame_params);
+        av1_tpl_setup_stats(cpi, /*approx_gop_eval=*/false, frame_params);
 #if CONFIG_BITRATE_ACCURACY && !CONFIG_THREE_PASS
         assert(cpi->gf_frame_index == 0);
         av1_vbr_rc_update_q_index_list(&cpi->vbr_rc_info, &cpi->ppi->tpl_data,
diff --git a/av1/encoder/pass2_strategy.c b/av1/encoder/pass2_strategy.c
index 42e9186..6ef6164 100644
--- a/av1/encoder/pass2_strategy.c
+++ b/av1/encoder/pass2_strategy.c
@@ -1118,52 +1118,26 @@
       av1_encode_for_extrc(&cpi->ext_ratectrl)) {
     return 0;
   }
-  const RATE_CONTROL *const rc = &cpi->rc;
   PRIMARY_RATE_CONTROL *const p_rc = &cpi->ppi->p_rc;
   int gop_length_decision_method = cpi->sf.tpl_sf.gop_length_decision_method;
-  int shorten_gf_interval;
+  int shorten_gf_interval = 0;
 
   av1_tpl_preload_rc_estimate(cpi, frame_params);
 
-  if (gop_length_decision_method == 2) {
+  if (gop_length_decision_method == 1) {
     // GF group length is decided based on GF boost and tpl stats of ARFs from
     // base layer, (base+1) layer.
     shorten_gf_interval =
         (p_rc->gfu_boost <
          p_rc->num_stats_used_for_gfu_boost * GF_MIN_BOOST * 1.4) &&
-        !av1_tpl_setup_stats(cpi, 3, frame_params);
-  } else {
-    int do_complete_tpl = 1;
-    GF_GROUP *const gf_group = &cpi->ppi->gf_group;
-    int is_temporal_filter_enabled =
-        (rc->frames_since_key > 0 && gf_group->arf_index > -1);
-
-    if (gop_length_decision_method == 1) {
-      // Check if tpl stats of ARFs from base layer, (base+1) layer,
-      // (base+2) layer can decide the GF group length.
-      int gop_length_eval = av1_tpl_setup_stats(cpi, 2, frame_params);
-
-      if (gop_length_eval != 2) {
-        do_complete_tpl = 0;
-        shorten_gf_interval = !gop_length_eval;
-      }
-    }
-
-    if (do_complete_tpl) {
-      // Decide GF group length based on complete tpl stats.
-      shorten_gf_interval = !av1_tpl_setup_stats(cpi, 1, frame_params);
-      // Tpl stats is reused when the ARF is temporally filtered and GF
-      // interval is not shortened.
-      if (is_temporal_filter_enabled && !shorten_gf_interval) {
-        cpi->skip_tpl_setup_stats = 1;
-#if CONFIG_BITRATE_ACCURACY && !CONFIG_THREE_PASS
-        assert(cpi->gf_frame_index == 0);
-        av1_vbr_rc_update_q_index_list(&cpi->vbr_rc_info, &cpi->ppi->tpl_data,
-                                       gf_group,
-                                       cpi->common.seq_params->bit_depth);
-#endif  // CONFIG_BITRATE_ACCURACY
-      }
-    }
+        !av1_tpl_setup_stats(cpi, /*approx_gop_eval=*/true, frame_params);
+  } else if (gop_length_decision_method == 0) {
+    // Check if tpl stats of ARFs from base layer, (base+1) layer,
+    // (base+2) layer can decide the GF group length.
+    int gop_length_eval =
+        av1_tpl_setup_stats(cpi, /*approx_gop_eval=*/true, frame_params);
+    assert(gop_length_eval != -1);
+    shorten_gf_interval = !gop_length_eval;
   }
   return shorten_gf_interval;
 }
@@ -4239,7 +4213,7 @@
       }
       if (max_gop_length > 16 && oxcf->algo_cfg.enable_tpl_model &&
           oxcf->gf_cfg.lag_in_frames >= 32 &&
-          cpi->sf.tpl_sf.gop_length_decision_method != 3) {
+          cpi->sf.tpl_sf.gop_length_decision_method != 2) {
         int this_idx = rc->frames_since_key +
                        p_rc->gf_intervals[p_rc->cur_gf_index] -
                        p_rc->regions_offset - 1;
diff --git a/av1/encoder/speed_features.c b/av1/encoder/speed_features.c
index 736ea8f..03e9693 100644
--- a/av1/encoder/speed_features.c
+++ b/av1/encoder/speed_features.c
@@ -1463,7 +1463,7 @@
     sf->tpl_sf.prune_starting_mv = 3;
     sf->tpl_sf.use_y_only_rate_distortion = 1;
     sf->tpl_sf.subpel_force_stop = FULL_PEL;
-    sf->tpl_sf.gop_length_decision_method = 2;
+    sf->tpl_sf.gop_length_decision_method = 1;
     sf->tpl_sf.use_sad_for_mode_decision = 2;
 
     sf->winner_mode_sf.dc_blk_pred_level = 2;
@@ -1497,7 +1497,7 @@
 
     sf->mv_sf.simple_motion_subpel_force_stop = FULL_PEL;
 
-    sf->tpl_sf.gop_length_decision_method = 3;
+    sf->tpl_sf.gop_length_decision_method = 2;
 
     sf->rd_sf.perform_coeff_opt = is_boosted_arf2_bwd_type ? 6 : 8;
 
@@ -2267,7 +2267,7 @@
 }
 
 static inline void init_tpl_sf(TPL_SPEED_FEATURES *tpl_sf) {
-  tpl_sf->gop_length_decision_method = 1;
+  tpl_sf->gop_length_decision_method = 0;
   tpl_sf->prune_intra_modes = 0;
   tpl_sf->prune_starting_mv = 0;
   tpl_sf->reduce_first_step_size = 0;
diff --git a/av1/encoder/speed_features.h b/av1/encoder/speed_features.h
index 3cf4bc2..49fdd77 100644
--- a/av1/encoder/speed_features.h
+++ b/av1/encoder/speed_features.h
@@ -544,12 +544,11 @@
 /*!\cond */
 typedef struct TPL_SPEED_FEATURES {
   // GOP length adaptive decision.
-  // If set to 0, tpl model decides whether a shorter gf interval is better.
-  // If set to 1, tpl stats of ARFs from base layer, (base+1) layer and
+  // If set to 0, tpl stats of ARFs from base layer, (base+1) layer and
   // (base+2) layer decide whether a shorter gf interval is better.
-  // If set to 2, tpl stats of ARFs from base layer, (base+1) layer and GF boost
+  // If set to 1, tpl stats of ARFs from base layer, (base+1) layer and GF boost
   // decide whether a shorter gf interval is better.
-  // If set to 3, gop length adaptive decision is disabled.
+  // If set to 2, gop length adaptive decision is disabled.
   int gop_length_decision_method;
   // Prune the intra modes search by tpl.
   // If set to 0, we will search all intra modes from DC_PRED to PAETH_PRED.
diff --git a/av1/encoder/tpl_model.c b/av1/encoder/tpl_model.c
index 34cf2bf..a02adc7 100644
--- a/av1/encoder/tpl_model.c
+++ b/av1/encoder/tpl_model.c
@@ -1933,23 +1933,19 @@
   return tpl_data->tpl_frame[gf_frame_index].is_valid;
 }
 
-static inline int eval_gop_length(double *beta, int gop_eval) {
-  switch (gop_eval) {
-    case 1:
+static inline int eval_gop_length(double *beta,
+                                  int gop_length_decision_method) {
+  switch (gop_length_decision_method) {
+    case 0:
       // Allow larger GOP size if the base layer ARF has higher dependency
       // factor than the intermediate ARF and both ARFs have reasonably high
       // dependency factors.
-      return (beta[0] >= beta[1] + 0.7) && beta[0] > 3.0;
-    case 2:
-      if ((beta[0] >= beta[1] + 0.4) && beta[0] > 1.6)
-        return 1;  // Don't shorten the gf interval
-      else if ((beta[0] < beta[1] + 0.1) || beta[0] <= 1.4)
+      if ((beta[0] < beta[1] + 0.1) || beta[0] <= 1.4)
         return 0;  // Shorten the gf interval
       else
-        return 2;  // Cannot decide the gf interval, so redo the
-                   // tpl stats calculation.
-    case 3: return beta[0] > 1.1;
-    default: return 2;
+        return 1;  // Don't shorten the gf interval
+    case 1: return beta[0] > 1.1;
+    default: assert(0 && "Invalid gop length decision method"); return -1;
   }
 }
 
@@ -1974,13 +1970,14 @@
 }
 
 static inline int skip_tpl_for_frame(const GF_GROUP *gf_group, int frame_idx,
-                                     int gop_eval, int approx_gop_eval,
+                                     int gop_length_decision_method,
+                                     int approx_gop_eval,
                                      int reduce_num_frames) {
-  // When gop_eval is set to 2, tpl stats calculation is done for ARFs from base
-  // layer, (base+1) layer and (base+2) layer. When gop_eval is set to 3,
-  // tpl stats calculation is limited to ARFs from base layer and (base+1)
-  // layer.
-  const int num_arf_layers = (gop_eval == 2) ? 3 : 2;
+  // When gop_length_decision_method is set to 0, tpl stats calculation is done
+  // for ARFs from base layer, (base+1) layer and (base+2) layer. When
+  // gop_length_decision_method is set to 1, tpl stats calculation is limited to
+  // ARFs from base layer and (base+1) layer.
+  const int num_arf_layers = (gop_length_decision_method == 0) ? 3 : 2;
   const int gop_length = get_gop_length(gf_group);
 
   if (gf_group->update_type[frame_idx] == INTNL_OVERLAY_UPDATE ||
@@ -2113,7 +2110,7 @@
   extrc_tpl_gop_stats->frame_stats_list = new_frame_stats;
 }
 
-int av1_tpl_setup_stats(AV1_COMP *cpi, int gop_eval,
+int av1_tpl_setup_stats(AV1_COMP *cpi, int approx_gop_eval,
                         const EncodeFrameParams *const frame_params) {
 #if CONFIG_COLLECT_COMPONENT_TIMING
   start_timing(cpi, av1_tpl_setup_stats_time);
@@ -2125,7 +2122,8 @@
   GF_GROUP *gf_group = &cpi->ppi->gf_group;
   EncodeFrameParams this_frame_params = *frame_params;
   TplParams *const tpl_data = &cpi->ppi->tpl_data;
-  int approx_gop_eval = (gop_eval > 1);
+  const int gop_length_decision_method =
+      cpi->sf.tpl_sf.gop_length_decision_method;
 
   if (cpi->superres_mode != AOM_SUPERRES_NONE) {
     assert(cpi->superres_mode != AOM_SUPERRES_AUTO);
@@ -2196,8 +2194,8 @@
   // Backward propagation from tpl_group_frames to 1.
   for (int frame_idx = cpi->gf_frame_index; frame_idx < tpl_gf_group_frames;
        ++frame_idx) {
-    if (skip_tpl_for_frame(gf_group, frame_idx, gop_eval, approx_gop_eval,
-                           reduce_num_frames))
+    if (skip_tpl_for_frame(gf_group, frame_idx, gop_length_decision_method,
+                           approx_gop_eval, reduce_num_frames))
       continue;
 
     init_mc_flow_dispenser(cpi, frame_idx, pframe_qindex);
@@ -2240,8 +2238,8 @@
 
   for (int frame_idx = tpl_gf_group_frames - 1;
        frame_idx >= cpi->gf_frame_index; --frame_idx) {
-    if (skip_tpl_for_frame(gf_group, frame_idx, gop_eval, approx_gop_eval,
-                           reduce_num_frames))
+    if (skip_tpl_for_frame(gf_group, frame_idx, gop_length_decision_method,
+                           approx_gop_eval, reduce_num_frames))
       continue;
 
     mc_flow_synthesizer(tpl_data, frame_idx, cm->mi_params.mi_rows,
@@ -2257,7 +2255,7 @@
 #if CONFIG_COLLECT_COMPONENT_TIMING
   // Record the time if the function returns.
   if (cpi->common.tiles.large_scale || gf_group->max_layer_depth_allowed == 0 ||
-      !gop_eval)
+      !approx_gop_eval)
     end_timing(cpi, av1_tpl_setup_stats_time);
 #endif
 
@@ -2268,7 +2266,7 @@
   }
   if (cpi->common.tiles.large_scale) return 0;
   if (gf_group->max_layer_depth_allowed == 0) return 1;
-  if (!gop_eval) return 0;
+  if (!approx_gop_eval) return 0;
   assert(gf_group->arf_index >= 0);
 
   double beta[2] = { 0.0 };
@@ -2280,7 +2278,7 @@
 #if CONFIG_COLLECT_COMPONENT_TIMING
   end_timing(cpi, av1_tpl_setup_stats_time);
 #endif
-  return eval_gop_length(beta, gop_eval);
+  return eval_gop_length(beta, gop_length_decision_method);
 }
 
 void av1_tpl_rdmult_setup(AV1_COMP *cpi) {
diff --git a/av1/encoder/tpl_model.h b/av1/encoder/tpl_model.h
index 34bcfc6..d8b33eb 100644
--- a/av1/encoder/tpl_model.h
+++ b/av1/encoder/tpl_model.h
@@ -482,13 +482,14 @@
  *
  *\ingroup tpl_modelling
  *
- * \param[in]    cpi           Top - level encoder instance structure
- * \param[in]    gop_eval      Flag if it is in the GOP length decision stage
- * \param[in]    frame_params  Per frame encoding parameters
+ * \param[in]    cpi             Top - level encoder instance structure
+ * \param[in]    approx_gop_eval Flag to indicate TPL is invoked for approximate
+ *                               GOP size evaluation
+ * \param[in]    frame_params    Per frame encoding parameters
  *
  * \return Indicates whether or not we should use a longer GOP length.
  */
-int av1_tpl_setup_stats(struct AV1_COMP *cpi, int gop_eval,
+int av1_tpl_setup_stats(struct AV1_COMP *cpi, int approx_gop_eval,
                         const struct EncodeFrameParams *const frame_params);
 
 /*!\cond */