Add cdf_update_mode experiment

Allow the CDF update to operate in different modes, e.g. update vs no
update.

The update mode is transmitted in the uncompressed frame header of
every keyframe and intra-only frame.

This patch only adds bitstream signaling and API support. The
implementation of the update modes will be in later patches.

Change-Id: Ic9fcd60e8a75f9c01f414253823d78cf9b3113dd
diff --git a/av1/encoder/bitstream.c b/av1/encoder/bitstream.c
index 4152165..a17c810 100644
--- a/av1/encoder/bitstream.c
+++ b/av1/encoder/bitstream.c
@@ -3757,6 +3757,9 @@
 #endif
       aom_wb_write_bit(wb, cm->allow_intrabc);
 #endif  // CONFIG_INTRABC
+#if CONFIG_CDF_UPDATE_MODE
+    aom_wb_write_literal(wb, cm->cdf_update_mode, 2);
+#endif  // CONFIG_CDF_UPDATE_MODE
   } else {
 #if !CONFIG_NO_FRAME_CONTEXT_SIGNALING
     if (!cm->error_resilient_mode) {
@@ -3800,6 +3803,9 @@
 #endif
         aom_wb_write_bit(wb, cm->allow_intrabc);
 #endif  // CONFIG_INTRABC
+#if CONFIG_CDF_UPDATE_MODE
+      aom_wb_write_literal(wb, cm->cdf_update_mode, 2);
+#endif  // CONFIG_CDF_UPDATE_MODE
     } else {
       aom_wb_write_literal(wb, cpi->refresh_frame_mask, REF_FRAMES);
 
@@ -4108,6 +4114,9 @@
 #endif
       aom_wb_write_bit(wb, cm->allow_intrabc);
 #endif  // CONFIG_INTRABC
+#if CONFIG_CDF_UPDATE_MODE
+    aom_wb_write_literal(wb, cm->cdf_update_mode, 2);
+#endif  // CONFIG_CDF_UPDATE_MODE
   } else if (cm->frame_type == INTRA_ONLY_FRAME) {
 #if !CONFIG_NO_FRAME_CONTEXT_SIGNALING
     if (!cm->error_resilient_mode) {
@@ -4137,6 +4146,9 @@
 #endif
         aom_wb_write_bit(wb, cm->allow_intrabc);
 #endif  // CONFIG_INTRABC
+#if CONFIG_CDF_UPDATE_MODE
+      aom_wb_write_literal(wb, cm->cdf_update_mode, 2);
+#endif  // CONFIG_CDF_UPDATE_MODE
     }
   } else if (cm->frame_type == INTER_FRAME) {
     MV_REFERENCE_FRAME ref_frame;
diff --git a/av1/encoder/encodeframe.c b/av1/encoder/encodeframe.c
index b4e2623..80637f2 100644
--- a/av1/encoder/encodeframe.c
+++ b/av1/encoder/encodeframe.c
@@ -356,9 +356,10 @@
       InterpFilter filter =
           av1_extract_interp_filter(mbmi->interp_filters, dir);
       ++counts->switchable_interp[ctx][filter];
-      if (allow_update_cdf)
+      if (allow_update_cdf) {
         update_cdf(xd->tile_ctx->switchable_interp_cdf[ctx], filter,
                    SWITCHABLE_FILTERS);
+      }
     }
   }
 }
@@ -824,10 +825,11 @@
     }
 #endif  // CONFIG_ENTROPY_STATS
     if (allow_update_cdf) {
-      if (use_filter_intra_mode)
+      if (use_filter_intra_mode) {
         update_cdf(fc->filter_intra_mode_cdf,
                    mbmi->filter_intra_mode_info.filter_intra_mode,
                    FILTER_INTRA_MODES);
+      }
       update_cdf(fc->filter_intra_cdfs[mbmi->tx_size], use_filter_intra_mode,
                  2);
     }
@@ -840,10 +842,11 @@
     ++counts->angle_delta[mbmi->mode - V_PRED]
                          [mbmi->angle_delta[PLANE_TYPE_Y] + MAX_ANGLE_DELTA];
 #endif
-    if (allow_update_cdf)
+    if (allow_update_cdf) {
       update_cdf(fc->angle_delta_cdf[mbmi->mode - V_PRED],
                  mbmi->angle_delta[PLANE_TYPE_Y] + MAX_ANGLE_DELTA,
                  2 * MAX_ANGLE_DELTA + 1);
+    }
   }
 #endif  // CONFIG_EXT_INTRA_MOD
 
@@ -858,10 +861,11 @@
     ++counts->angle_delta[mbmi->uv_mode - V_PRED]
                          [mbmi->angle_delta[PLANE_TYPE_UV] + MAX_ANGLE_DELTA];
 #endif
-    if (allow_update_cdf)
+    if (allow_update_cdf) {
       update_cdf(fc->angle_delta_cdf[mbmi->uv_mode - V_PRED],
                  mbmi->angle_delta[PLANE_TYPE_UV] + MAX_ANGLE_DELTA,
                  2 * MAX_ANGLE_DELTA + 1);
+    }
   }
 #endif  // CONFIG_EXT_INTRA_MOD
 #if CONFIG_ENTROPY_STATS
@@ -1005,13 +1009,13 @@
                     frame_is_intra_only(cm), mi_row, mi_col,
                     tile_data->allow_update_cdf);
     if (av1_allow_palette(cm->allow_screen_content_tools, bsize) &&
-        tile_data->allow_update_cdf)
+        allow_update_cdf)
       update_palette_cdf(xd, mi);
   }
 
 #if CONFIG_INTRABC
   if (frame_is_intra_only(cm) && av1_allow_intrabc(cm)) {
-    if (tile_data->allow_update_cdf)
+    if (allow_update_cdf)
       update_cdf(fc->intrabc_cdf, is_intrabc_block(mbmi), 2);
 #if CONFIG_ENTROPY_STATS
     ++td->counts->intrabc[is_intrabc_block(mbmi)];
@@ -1040,9 +1044,10 @@
 
     if (!seg_ref_active) {
       counts->intra_inter[av1_get_intra_inter_context(xd)][inter_block]++;
-      if (allow_update_cdf)
+      if (allow_update_cdf) {
         update_cdf(fc->intra_inter_cdf[av1_get_intra_inter_context(xd)],
                    inter_block, 2);
+      }
       // If the segment reference feature is enabled we have only a single
       // reference frame allowed for the segment so exclude it from
       // the reference frame counts used to work out probabilities.
@@ -1061,9 +1066,10 @@
             counts->comp_inter[av1_get_reference_mode_context(cm, xd)]
                               [has_second_ref(mbmi)]++;
 #endif  // CONFIG_ENTROPY_STATS
-            if (allow_update_cdf)
+            if (allow_update_cdf) {
               update_cdf(av1_get_reference_mode_cdf(cm, xd),
                          has_second_ref(mbmi), 2);
+            }
           }
         }
 
@@ -1220,14 +1226,16 @@
             if (allow_update_cdf)
               update_cdf(fc->interintra_cdf[bsize_group], 1, 2);
             counts->interintra_mode[bsize_group][mbmi->interintra_mode]++;
-            if (allow_update_cdf)
+            if (allow_update_cdf) {
               update_cdf(fc->interintra_mode_cdf[bsize_group],
                          mbmi->interintra_mode, INTERINTRA_MODES);
+            }
             if (is_interintra_wedge_used(bsize)) {
               counts->wedge_interintra[bsize][mbmi->use_wedge_interintra]++;
-              if (allow_update_cdf)
+              if (allow_update_cdf) {
                 update_cdf(fc->wedge_interintra_cdf[bsize],
                            mbmi->use_wedge_interintra, 2);
+              }
             }
           } else {
             counts->interintra[bsize_group][0]++;
@@ -1242,14 +1250,16 @@
         if (mbmi->ref_frame[1] != INTRA_FRAME) {
           if (motion_allowed == WARPED_CAUSAL) {
             counts->motion_mode[bsize][mbmi->motion_mode]++;
-            if (allow_update_cdf)
+            if (allow_update_cdf) {
               update_cdf(fc->motion_mode_cdf[bsize], mbmi->motion_mode,
                          MOTION_MODES);
+            }
           } else if (motion_allowed == OBMC_CAUSAL) {
             counts->obmc[bsize][mbmi->motion_mode == OBMC_CAUSAL]++;
-            if (allow_update_cdf)
+            if (allow_update_cdf) {
               update_cdf(fc->obmc_cdf[bsize], mbmi->motion_mode == OBMC_CAUSAL,
                          2);
+            }
           }
         }
 
@@ -1264,26 +1274,29 @@
           if (masked_compound_used) {
             const int comp_group_idx_ctx = get_comp_group_idx_context(xd);
             ++counts->comp_group_idx[comp_group_idx_ctx][mbmi->comp_group_idx];
-            if (allow_update_cdf)
+            if (allow_update_cdf) {
               update_cdf(fc->comp_group_idx_cdf[comp_group_idx_ctx],
                          mbmi->comp_group_idx, 2);
+            }
           }
 
           if (mbmi->comp_group_idx == 0) {
             const int comp_index_ctx = get_comp_index_context(cm, xd);
             ++counts->compound_index[comp_index_ctx][mbmi->compound_idx];
-            if (allow_update_cdf)
+            if (allow_update_cdf) {
               update_cdf(fc->compound_index_cdf[comp_index_ctx],
                          mbmi->compound_idx, 2);
+            }
           } else {
             assert(masked_compound_used);
             if (is_interinter_compound_used(COMPOUND_WEDGE, bsize)) {
               counts->compound_interinter[bsize]
                                          [mbmi->interinter_compound_type - 1]++;
-              if (allow_update_cdf)
+              if (allow_update_cdf) {
                 update_cdf(fc->compound_type_cdf[bsize],
                            mbmi->interinter_compound_type - 1,
                            COMPOUND_TYPES - 1);
+              }
             }
           }
         }
@@ -1294,9 +1307,10 @@
           if (is_interinter_compound_used(COMPOUND_WEDGE, bsize)) {
             counts
                 ->compound_interinter[bsize][mbmi->interinter_compound_type]++;
-            if (allow_update_cdf)
+            if (allow_update_cdf) {
               update_cdf(fc->compound_type_cdf[bsize],
                          mbmi->interinter_compound_type, COMPOUND_TYPES);
+            }
           }
         }
 #endif  // CONFIG_JNT_COMP
@@ -1323,9 +1337,10 @@
       if (has_second_ref(mbmi)) {
         mode_ctx = mbmi_ext->compound_mode_context[mbmi->ref_frame[0]];
         ++counts->inter_compound_mode[mode_ctx][INTER_COMPOUND_OFFSET(mode)];
-        if (allow_update_cdf)
+        if (allow_update_cdf) {
           update_cdf(fc->inter_compound_mode_cdf[mode_ctx],
                      INTER_COMPOUND_OFFSET(mode), INTER_COMPOUND_MODES);
+        }
       } else {
         mode_ctx =
             av1_mode_context_analyzer(mbmi_ext->mode_context, mbmi->ref_frame);
@@ -3868,7 +3883,6 @@
       pre_tok = cpi->tile_tok[tile_row][tile_col];
       tile_tok = allocated_tokens(
           *tile_info, cm->seq_params.mib_size_log2 + MI_SIZE_LOG2, num_planes);
-
 #if CONFIG_EXT_TILE
       tile_data->allow_update_cdf = !cm->large_scale_tile;
 #else
@@ -4251,6 +4265,9 @@
       cm->allow_screen_content_tools =
           cm->seq_params.force_screen_content_tools;
     }
+#if CONFIG_CDF_UPDATE_MODE
+    cm->cdf_update_mode = cpi->oxcf.cdf_update_mode;
+#endif  // CONFIG_CDF_UPDATE_MODE
   }
 
 #if CONFIG_INTRABC
@@ -4861,10 +4878,11 @@
       const TxSetType tx_set_type = get_ext_tx_set_type(
           tx_size, bsize, is_inter, cm->reduced_tx_set_used);
       if (is_inter) {
-        if (allow_update_cdf)
+        if (allow_update_cdf) {
           update_cdf(fc->inter_ext_tx_cdf[eset][txsize_sqr_map[tx_size]],
                      av1_ext_tx_ind[tx_set_type][tx_type],
                      av1_num_ext_tx_set[tx_set_type]);
+        }
 #if CONFIG_ENTROPY_STATS
         ++counts->inter_ext_tx[eset][txsize_sqr_map[tx_size]][tx_type];
 #endif  // CONFIG_ENTROPY_STATS
@@ -4880,21 +4898,23 @@
         ++counts
               ->intra_ext_tx[eset][txsize_sqr_map[tx_size]][intra_dir][tx_type];
 #endif  // CONFIG_ENTROPY_STATS
-        if (allow_update_cdf)
+        if (allow_update_cdf) {
           update_cdf(
               fc->intra_ext_tx_cdf[eset][txsize_sqr_map[tx_size]][intra_dir],
               av1_ext_tx_ind[tx_set_type][tx_type],
               av1_num_ext_tx_set[tx_set_type]);
+        }
 #else
 #if CONFIG_ENTROPY_STATS
         ++counts->intra_ext_tx[eset][txsize_sqr_map[tx_size]][mbmi->mode]
                               [tx_type];
 #endif  // CONFIG_ENTROPY_STATS
-        if (allow_update_cdf)
+        if (allow_update_cdf) {
           update_cdf(
               fc->intra_ext_tx_cdf[eset][txsize_sqr_map[tx_size]][mbmi->mode],
               av1_ext_tx_ind[tx_set_type][tx_type],
               av1_num_ext_tx_set[tx_set_type]);
+        }
 #endif
       }
     }
diff --git a/av1/encoder/encoder.h b/av1/encoder/encoder.h
index 9c18941..d2c391e 100644
--- a/av1/encoder/encoder.h
+++ b/av1/encoder/encoder.h
@@ -309,6 +309,9 @@
   int film_grain_test_vector;
 #endif
 
+#if CONFIG_CDF_UPDATE_MODE
+  uint8_t cdf_update_mode;
+#endif  // CONFIG_CDF_UPDATE_MODE
 #if CONFIG_EXT_PARTITION
   aom_superblock_size_t superblock_size;
 #endif  // CONFIG_EXT_PARTITION
diff --git a/av1/encoder/encodetxb.c b/av1/encoder/encodetxb.c
index 83d4598..569b3d2 100644
--- a/av1/encoder/encodetxb.c
+++ b/av1/encoder/encodetxb.c
@@ -209,28 +209,32 @@
       break;
     case 3:
       ++counts->eob_multi128[plane][eob_multi_ctx][eob_pt - 1];
-      if (allow_update_cdf)
+      if (allow_update_cdf) {
         update_cdf(ec_ctx->eob_flag_cdf128[plane][eob_multi_ctx], eob_pt - 1,
                    8);
+      }
       break;
     case 4:
       ++counts->eob_multi256[plane][eob_multi_ctx][eob_pt - 1];
-      if (allow_update_cdf)
+      if (allow_update_cdf) {
         update_cdf(ec_ctx->eob_flag_cdf256[plane][eob_multi_ctx], eob_pt - 1,
                    9);
+      }
       break;
     case 5:
       ++counts->eob_multi512[plane][eob_multi_ctx][eob_pt - 1];
-      if (allow_update_cdf)
+      if (allow_update_cdf) {
         update_cdf(ec_ctx->eob_flag_cdf512[plane][eob_multi_ctx], eob_pt - 1,
                    10);
+      }
       break;
     case 6:
     default:
       ++counts->eob_multi1024[plane][eob_multi_ctx][eob_pt - 1];
-      if (allow_update_cdf)
+      if (allow_update_cdf) {
         update_cdf(ec_ctx->eob_flag_cdf1024[plane][eob_multi_ctx], eob_pt - 1,
                    11);
+      }
       break;
   }