ref: c969b2b02b1035130fc09573236dc627ec101106
parent: 16e069b8bb4d523007bf84be7c0a1bdde58539c4
author: Scott LaVarnway <[email protected]>
date: Thu Jul 21 07:47:51 EDT 2016
VP9: get_pred_context_switchable_interp() -- encoder side Change-Id: I7217c90d5cf38c51b76759a2dc4f10070f3a40ac
--- a/vp9/common/vp9_pred_common.c
+++ b/vp9/common/vp9_pred_common.c
@@ -13,29 +13,6 @@
#include "vp9/common/vp9_pred_common.h"
#include "vp9/common/vp9_seg_common.h"
-// Returns a context number for the given MB prediction signal
-int vp9_get_pred_context_switchable_interp(const MACROBLOCKD *xd) {
- // Note:
- // The mode info data structure has a one element border above and to the
- // left of the entries corresponding to real macroblocks.
- // The prediction flags in these dummy entries are initialized to 0.
- const MODE_INFO *const left_mi = xd->left_mi;
- const int left_type = left_mi && is_inter_block(left_mi) ?
- left_mi->interp_filter : SWITCHABLE_FILTERS;
- const MODE_INFO *const above_mi = xd->above_mi;
- const int above_type = above_mi && is_inter_block(above_mi) ?
- above_mi->interp_filter : SWITCHABLE_FILTERS;
-
- if (left_type == above_type)
- return left_type;
- else if (left_type == SWITCHABLE_FILTERS)
- return above_type;
- else if (above_type == SWITCHABLE_FILTERS)
- return left_type;
- else
- return SWITCHABLE_FILTERS;
-}
-
int vp9_get_reference_mode_context(const VP9_COMMON *cm,
const MACROBLOCKD *xd) {
int ctx;
--- a/vp9/common/vp9_pred_common.h
+++ b/vp9/common/vp9_pred_common.h
@@ -66,7 +66,27 @@
return cm->fc->skip_probs[vp9_get_skip_context(xd)];
}
-int vp9_get_pred_context_switchable_interp(const MACROBLOCKD *xd);
+// Returns a context number for the given MB prediction signal
+static INLINE int get_pred_context_switchable_interp(const MACROBLOCKD *xd) {
+ // Note:
+ // The mode info data structure has a one element border above and to the
+ // left of the entries corresponding to real macroblocks.
+ // The prediction flags in these dummy entries are initialized to 0.
+ const MODE_INFO *const left_mi = xd->left_mi;
+ const int left_type = left_mi ? left_mi->interp_filter : SWITCHABLE_FILTERS;
+ const MODE_INFO *const above_mi = xd->above_mi;
+ const int above_type = above_mi ? above_mi->interp_filter
+ : SWITCHABLE_FILTERS;
+
+ if (left_type == above_type)
+ return left_type;
+ else if (left_type == SWITCHABLE_FILTERS)
+ return above_type;
+ else if (above_type == SWITCHABLE_FILTERS)
+ return left_type;
+ else
+ return SWITCHABLE_FILTERS;
+}
// The mode info data structure has a one element border above and to the
// left of the entries corresponding to real macroblocks.
--- a/vp9/decoder/vp9_decodemv.c
+++ b/vp9/decoder/vp9_decodemv.c
@@ -353,36 +353,10 @@
}
}
-// TODO(slavarnway): Move this decoder version of
-// vp9_get_pred_context_switchable_interp() to vp9_pred_common.h and update the
-// encoder.
-//
-// Returns a context number for the given MB prediction signal
-static int dec_get_pred_context_switchable_interp(const MACROBLOCKD *xd) {
- // Note:
- // The mode info data structure has a one element border above and to the
- // left of the entries corresponding to real macroblocks.
- // The prediction flags in these dummy entries are initialized to 0.
- const MODE_INFO *const left_mi = xd->left_mi;
- const int left_type = left_mi ? left_mi->interp_filter : SWITCHABLE_FILTERS;
- const MODE_INFO *const above_mi = xd->above_mi;
- const int above_type = above_mi ? above_mi->interp_filter
- : SWITCHABLE_FILTERS;
-
- if (left_type == above_type)
- return left_type;
- else if (left_type == SWITCHABLE_FILTERS)
- return above_type;
- else if (above_type == SWITCHABLE_FILTERS)
- return left_type;
- else
- return SWITCHABLE_FILTERS;
-}
-
static INLINE INTERP_FILTER read_switchable_interp_filter(
VP9_COMMON *const cm, MACROBLOCKD *const xd,
vpx_reader *r) {
- const int ctx = dec_get_pred_context_switchable_interp(xd);
+ const int ctx = get_pred_context_switchable_interp(xd);
const INTERP_FILTER type =
(INTERP_FILTER)vpx_read_tree(r, vp9_switchable_interp_tree,
cm->fc->switchable_interp_prob[ctx]);
@@ -423,7 +397,7 @@
mi->uv_mode = read_intra_mode_uv(cm, xd, r, mi->mode);
// Initialize interp_filter here so we do not have to check for inter block
- // modes in dec_get_pred_context_switchable_interp()
+ // modes in get_pred_context_switchable_interp()
mi->interp_filter = SWITCHABLE_FILTERS;
mi->ref_frame[0] = INTRA_FRAME;
--- a/vp9/encoder/vp9_bitstream.c
+++ b/vp9/encoder/vp9_bitstream.c
@@ -293,7 +293,7 @@
}
if (cm->interp_filter == SWITCHABLE) {
- const int ctx = vp9_get_pred_context_switchable_interp(xd);
+ const int ctx = get_pred_context_switchable_interp(xd);
vp9_write_token(w, vp9_switchable_interp_tree,
cm->fc->switchable_interp_prob[ctx],
&switchable_interp_encodings[mi->interp_filter]);
--- a/vp9/encoder/vp9_encodeframe.c
+++ b/vp9/encoder/vp9_encodeframe.c
@@ -250,6 +250,7 @@
const int mi_stride = xd->mi_stride;
MODE_INFO *const src_mi = xd->mi[0];
int i, j;
+
for (j = 0; j < block_height; ++j)
for (i = 0; i < block_width; ++i)
xd->mi[j * mi_stride + i] = src_mi;
@@ -1277,7 +1278,7 @@
vp9_update_mv_count(td);
if (cm->interp_filter == SWITCHABLE) {
- const int ctx = vp9_get_pred_context_switchable_interp(xd);
+ const int ctx = get_pred_context_switchable_interp(xd);
++td->counts->switchable_interp[ctx][xdmi->interp_filter];
}
}
@@ -1323,7 +1324,7 @@
MODE_INFO *const mi = xd->mi[0];
INTERP_FILTER filter_ref;
- filter_ref = vp9_get_pred_context_switchable_interp(xd);
+ filter_ref = get_pred_context_switchable_interp(xd);
if (filter_ref == SWITCHABLE_FILTERS)
filter_ref = EIGHTTAP;
@@ -1900,7 +1901,7 @@
if (is_inter_block(mi)) {
vp9_update_mv_count(td);
if (cm->interp_filter == SWITCHABLE) {
- const int pred_ctx = vp9_get_pred_context_switchable_interp(xd);
+ const int pred_ctx = get_pred_context_switchable_interp(xd);
++td->counts->switchable_interp[pred_ctx][mi->interp_filter];
}
@@ -2554,6 +2555,7 @@
RD_COST this_rdc, sum_rdc, best_rdc;
int do_split = bsize >= BLOCK_8X8;
int do_rect = 1;
+ INTERP_FILTER pred_interp_filter;
// Override skipping rectangular partition operations for edge blocks
const int force_horz_split = (mi_row + mi_step >= cm->mi_rows);
@@ -2776,7 +2778,9 @@
// If the interp_filter is marked as SWITCHABLE_FILTERS, it was for an
// intra block and used for context purposes.
if (ctx->mic.interp_filter == SWITCHABLE_FILTERS) {
- ctx->mic.interp_filter = EIGHTTAP;
+ pred_interp_filter = EIGHTTAP;
+ } else {
+ pred_interp_filter = ctx->mic.interp_filter;
}
// PARTITION_SPLIT
@@ -2787,8 +2791,7 @@
if (bsize == BLOCK_8X8) {
i = 4;
if (cpi->sf.adaptive_pred_interp_filter && partition_none_allowed)
- pc_tree->leaf_split[0]->pred_interp_filter =
- ctx->mic.interp_filter;
+ pc_tree->leaf_split[0]->pred_interp_filter = pred_interp_filter;
rd_pick_sb_modes(cpi, tile_data, x, mi_row, mi_col, &sum_rdc, subsize,
pc_tree->leaf_split[0], best_rdc.rdcost);
@@ -2858,8 +2861,7 @@
load_pred_mv(x, ctx);
if (cpi->sf.adaptive_pred_interp_filter && bsize == BLOCK_8X8 &&
partition_none_allowed)
- pc_tree->horizontal[0].pred_interp_filter =
- ctx->mic.interp_filter;
+ pc_tree->horizontal[0].pred_interp_filter = pred_interp_filter;
rd_pick_sb_modes(cpi, tile_data, x, mi_row, mi_col, &sum_rdc, subsize,
&pc_tree->horizontal[0], best_rdc.rdcost);
@@ -2873,8 +2875,7 @@
load_pred_mv(x, ctx);
if (cpi->sf.adaptive_pred_interp_filter && bsize == BLOCK_8X8 &&
partition_none_allowed)
- pc_tree->horizontal[1].pred_interp_filter =
- ctx->mic.interp_filter;
+ pc_tree->horizontal[1].pred_interp_filter = pred_interp_filter;
rd_pick_sb_modes(cpi, tile_data, x, mi_row + mi_step, mi_col,
&this_rdc, subsize, &pc_tree->horizontal[1],
best_rdc.rdcost - sum_rdc.rdcost);
@@ -2911,8 +2912,7 @@
load_pred_mv(x, ctx);
if (cpi->sf.adaptive_pred_interp_filter && bsize == BLOCK_8X8 &&
partition_none_allowed)
- pc_tree->vertical[0].pred_interp_filter =
- ctx->mic.interp_filter;
+ pc_tree->vertical[0].pred_interp_filter = pred_interp_filter;
rd_pick_sb_modes(cpi, tile_data, x, mi_row, mi_col, &sum_rdc, subsize,
&pc_tree->vertical[0], best_rdc.rdcost);
if (sum_rdc.rdcost < best_rdc.rdcost && mi_col + mi_step < cm->mi_cols &&
@@ -2925,8 +2925,7 @@
load_pred_mv(x, ctx);
if (cpi->sf.adaptive_pred_interp_filter && bsize == BLOCK_8X8 &&
partition_none_allowed)
- pc_tree->vertical[1].pred_interp_filter =
- ctx->mic.interp_filter;
+ pc_tree->vertical[1].pred_interp_filter = pred_interp_filter;
rd_pick_sb_modes(cpi, tile_data, x, mi_row, mi_col + mi_step,
&this_rdc, subsize,
&pc_tree->vertical[1], best_rdc.rdcost - sum_rdc.rdcost);
--- a/vp9/encoder/vp9_pickmode.c
+++ b/vp9/encoder/vp9_pickmode.c
@@ -1081,6 +1081,10 @@
vp9_rd_cost_reset(&this_rdc);
mi->ref_frame[0] = INTRA_FRAME;
+ // Initialize interp_filter here so we do not have to check for inter block
+ // modes in get_pred_context_switchable_interp()
+ mi->interp_filter = SWITCHABLE_FILTERS;
+
mi->mv[0].as_int = INVALID_MV;
mi->uv_mode = DC_PRED;
memset(x->skip_txfm, 0, sizeof(x->skip_txfm));
@@ -1514,6 +1518,7 @@
mi->sb_type = bsize;
mi->ref_frame[0] = NONE;
mi->ref_frame[1] = NONE;
+
mi->tx_size = VPXMIN(max_txsize_lookup[bsize],
tx_mode_to_biggest_tx_size[cm->tx_mode]);
--- a/vp9/encoder/vp9_rd.c
+++ b/vp9/encoder/vp9_rd.c
@@ -565,7 +565,7 @@
int vp9_get_switchable_rate(const VP9_COMP *cpi, const MACROBLOCKD *const xd) {
const MODE_INFO *const mi = xd->mi[0];
- const int ctx = vp9_get_pred_context_switchable_interp(xd);
+ const int ctx = get_pred_context_switchable_interp(xd);
return SWITCHABLE_INTERP_RATE_FACTOR *
cpi->switchable_interp_costs[ctx][mi->interp_filter];
}
--- a/vp9/encoder/vp9_rdopt.c
+++ b/vp9/encoder/vp9_rdopt.c
@@ -3573,6 +3573,9 @@
/* required for left and above block mv */
mi->mv[0].as_int = 0;
max_plane = 1;
+ // Initialize interp_filter here so we do not have to check for
+ // inter block modes in get_pred_context_switchable_interp()
+ mi->interp_filter = SWITCHABLE_FILTERS;
} else {
best_pred_sse = x->pred_sse[ref_frame];
}
@@ -4356,6 +4359,9 @@
/* required for left and above block mv */
mi->mv[0].as_int = 0;
max_plane = 1;
+ // Initialize interp_filter here so we do not have to check for
+ // inter block modes in get_pred_context_switchable_interp()
+ mi->interp_filter = SWITCHABLE_FILTERS;
}
rd_cost->rate = rate2;