ncobmc_adapt_weight: allow the usage of new motion mode
The new motion mode "NCOBMC_ADAPT_WEIGHT" cannot be used
in the motion search loop as it requires all mvs from the
neighboring blocks. This patch add a wrapper to skip checking
this mode during mv search.
Change-Id: I3a39954e91101929f26b5479c8c6ae22abdc7bce
diff --git a/av1/common/blockd.h b/av1/common/blockd.h
index 638548f..3471977 100644
--- a/av1/common/blockd.h
+++ b/av1/common/blockd.h
@@ -1371,12 +1371,33 @@
}
#if CONFIG_NCOBMC_ADAPT_WEIGHT && CONFIG_MOTION_VAR
-static INLINE NCOBMC_MODE ncobmc_mode_allowed(BLOCK_SIZE block) {
- if (block < BLOCK_8X8 || block > BLOCK_64X64)
+static INLINE NCOBMC_MODE ncobmc_mode_allowed_bsize(BLOCK_SIZE bsize) {
+ if (bsize < BLOCK_8X8 || bsize > BLOCK_64X64)
return NO_OVERLAP;
else
return (NCOBMC_MODE)(MAX_NCOBMC_MODES - 1);
}
+
+static INLINE MOTION_MODE
+motion_mode_allowed_wrapper(int for_mv_search,
+#if CONFIG_GLOBAL_MOTION && SEPARATE_GLOBAL_MOTION
+ int block, const WarpedMotionParams *gm_params,
+#endif // CONFIG_GLOBAL_MOTION && SEPARATE_GLOBAL_MOTION
+ const MODE_INFO *mi) {
+ const MB_MODE_INFO *mbmi = &mi->mbmi;
+ MOTION_MODE motion_mode_for_mv_search = motion_mode_allowed(
+#if CONFIG_GLOBAL_MOTION && SEPARATE_GLOBAL_MOTION
+ int block, const WarpedMotionParams *gm_params,
+#endif
+ mi);
+ int ncobmc_mode_allowed =
+ ncobmc_mode_allowed_bsize(mbmi->sb_type) && is_inter_mode(mbmi->mode);
+ if (for_mv_search)
+ return motion_mode_for_mv_search;
+ else
+ return ncobmc_mode_allowed ? NCOBMC_ADAPT_WEIGHT
+ : motion_mode_for_mv_search;
+}
#endif
static INLINE void assert_motion_mode_valid(MOTION_MODE mode,
@@ -1385,11 +1406,20 @@
const WarpedMotionParams *gm_params,
#endif // CONFIG_GLOBAL_MOTION && SEPARATE_GLOBAL_MOTION
const MODE_INFO *mi) {
+#if CONFIG_NCOBMC_ADAPT_WEIGHT
+ const MOTION_MODE last_motion_mode_allowed =
+ motion_mode_allowed_wrapper(0,
+#if CONFIG_GLOBAL_MOTION && SEPARATE_GLOBAL_MOTION
+ block, gm_params,
+#endif // CONFIG_GLOBAL_MOTION && SEPARATE_GLOBAL_MOTION
+ mi);
+#else
const MOTION_MODE last_motion_mode_allowed = motion_mode_allowed(
#if CONFIG_GLOBAL_MOTION && SEPARATE_GLOBAL_MOTION
block, gm_params,
#endif // CONFIG_GLOBAL_MOTION && SEPARATE_GLOBAL_MOTION
mi);
+#endif
// Check that the input mode is not illegal
if (last_motion_mode_allowed < mode)
assert(0 && "Illegal motion mode selected");
diff --git a/av1/decoder/decodemv.c b/av1/decoder/decodemv.c
index 0de16c7..f3f8b89 100644
--- a/av1/decoder/decodemv.c
+++ b/av1/decoder/decodemv.c
@@ -315,11 +315,20 @@
static MOTION_MODE read_motion_mode(AV1_COMMON *cm, MACROBLOCKD *xd,
MODE_INFO *mi, aom_reader *r) {
MB_MODE_INFO *mbmi = &mi->mbmi;
+#if CONFIG_NCOBMC_ADAPT_WEIGHT
+ const MOTION_MODE last_motion_mode_allowed =
+ motion_mode_allowed_wrapper(0,
+#if CONFIG_GLOBAL_MOTION && SEPARATE_GLOBAL_MOTION
+ 0, xd->global_motion,
+#endif // CONFIG_GLOBAL_MOTION && SEPARATE_GLOBAL_MOTION
+ mi);
+#else
const MOTION_MODE last_motion_mode_allowed = motion_mode_allowed(
#if CONFIG_GLOBAL_MOTION && SEPARATE_GLOBAL_MOTION
0, xd->global_motion,
#endif // CONFIG_GLOBAL_MOTION && SEPARATE_GLOBAL_MOTION
mi);
+#endif // CONFIG_NCOBMC_ADAPT_WEIGHT
int motion_mode;
FRAME_COUNTS *counts = xd->counts;
@@ -346,11 +355,14 @@
NCOBMC_MODE ncobmc_mode[2], aom_reader *r) {
MB_MODE_INFO *mbmi = &mi->mbmi;
FRAME_COUNTS *counts = xd->counts;
+ MOTION_MODE last_motion_mode_allowed =
+ motion_mode_allowed_wrapper(0,
+#if CONFIG_GLOBAL_MOTION && SEPARATE_GLOBAL_MOTION
+ 0, cm->global_motion,
+#endif // CONFIG_GLOBAL_MOTION && SEPARATE_GLOBAL_MOTION
+ mi);
ADAPT_OVERLAP_BLOCK ao_block = adapt_overlap_block_lookup[mbmi->sb_type];
-
- if (ncobmc_mode_allowed(mbmi->sb_type) == NO_OVERLAP ||
- ao_block == ADAPT_OVERLAP_BLOCK_INVALID)
- return;
+ if (last_motion_mode_allowed < NCOBMC_ADAPT_WEIGHT) return;
ncobmc_mode[0] = aom_read_tree(r, av1_ncobmc_mode_tree,
cm->fc->ncobmc_mode_prob[ao_block], ACCT_STR);
diff --git a/av1/encoder/bitstream.c b/av1/encoder/bitstream.c
index 0e0d609..386c8b3 100644
--- a/av1/encoder/bitstream.c
+++ b/av1/encoder/bitstream.c
@@ -593,12 +593,20 @@
static void write_motion_mode(const AV1_COMMON *cm, const MODE_INFO *mi,
aom_writer *w) {
const MB_MODE_INFO *mbmi = &mi->mbmi;
+#if CONFIG_NCOBMC_ADAPT_WEIGHT
+ MOTION_MODE last_motion_mode_allowed =
+ motion_mode_allowed_wrapper(0,
+#if CONFIG_GLOBAL_MOTION && SEPARATE_GLOBAL_MOTION
+ 0, cm->global_motion,
+#endif // CONFIG_GLOBAL_MOTION && SEPARATE_GLOBAL_MOTION
+ mi);
+#else
MOTION_MODE last_motion_mode_allowed = motion_mode_allowed(
#if CONFIG_GLOBAL_MOTION && SEPARATE_GLOBAL_MOTION
0, cm->global_motion,
#endif // CONFIG_GLOBAL_MOTION && SEPARATE_GLOBAL_MOTION
mi);
-
+#endif // CONFIG_NCOBMC_ADAPT_WEIGHT
if (last_motion_mode_allowed == SIMPLE_TRANSLATION) return;
#if CONFIG_MOTION_VAR && CONFIG_WARPED_MOTION
if (last_motion_mode_allowed == OBMC_CAUSAL) {
@@ -618,10 +626,14 @@
static void write_ncobmc_mode(const AV1_COMMON *cm, const MODE_INFO *mi,
aom_writer *w) {
const MB_MODE_INFO *mbmi = &mi->mbmi;
+ MOTION_MODE last_motion_mode_allowed =
+ motion_mode_allowed_wrapper(0,
+#if CONFIG_GLOBAL_MOTION && SEPARATE_GLOBAL_MOTION
+ 0, cm->global_motion,
+#endif // CONFIG_GLOBAL_MOTION && SEPARATE_GLOBAL_MOTION
+ mi);
ADAPT_OVERLAP_BLOCK ao_block = adapt_overlap_block_lookup[mbmi->sb_type];
- if (ncobmc_mode_allowed(mbmi->sb_type) == NO_OVERLAP ||
- ao_block == ADAPT_OVERLAP_BLOCK_INVALID)
- return;
+ if (last_motion_mode_allowed < NCOBMC_ADAPT_WEIGHT) return;
av1_write_token(w, av1_ncobmc_mode_tree, cm->fc->ncobmc_mode_prob[ao_block],
&ncobmc_mode_encodings[mbmi->ncobmc_mode[0]]);
diff --git a/av1/encoder/encodeframe.c b/av1/encoder/encodeframe.c
index 25fd9dc..511066d 100644
--- a/av1/encoder/encodeframe.c
+++ b/av1/encoder/encodeframe.c
@@ -1705,11 +1705,20 @@
#endif // CONFIG_EXT_INTER
#if CONFIG_MOTION_VAR || CONFIG_WARPED_MOTION
+#if CONFIG_NCOBMC_ADAPT_WEIGHT
+ const MOTION_MODE motion_allowed =
+ motion_mode_allowed_wrapper(0,
+#if CONFIG_GLOBAL_MOTION && SEPARATE_GLOBAL_MOTION
+ 0, xd->global_motion,
+#endif // CONFIG_GLOBAL_MOTION && SEPARATE_GLOBAL_MOTION
+ mi);
+#else
const MOTION_MODE motion_allowed = motion_mode_allowed(
#if CONFIG_GLOBAL_MOTION && SEPARATE_GLOBAL_MOTION
0, xd->global_motion,
#endif // CONFIG_GLOBAL_MOTION && SEPARATE_GLOBAL_MOTION
mi);
+#endif // CONFIG_NCOBMC_ADAPT_WEIGHT
#if CONFIG_SUPERTX
if (!supertx_enabled)
#endif // CONFIG_SUPERTX
@@ -1729,7 +1738,7 @@
#endif // CONFIG_MOTION_VAR && CONFIG_WARPED_MOTION
#if CONFIG_NCOBMC_ADAPT_WEIGHT
- if (ncobmc_mode_allowed(mbmi->sb_type) > NO_OVERLAP) {
+ if (motion_allowed == NCOBMC_ADAPT_WEIGHT) {
ADAPT_OVERLAP_BLOCK ao_block =
adapt_overlap_block_lookup[mbmi->sb_type];
++counts->ncobmc_mode[ao_block][mbmi->ncobmc_mode[0]];
diff --git a/av1/encoder/rdopt.c b/av1/encoder/rdopt.c
index afa3970..02acee9 100644
--- a/av1/encoder/rdopt.c
+++ b/av1/encoder/rdopt.c
@@ -7837,11 +7837,23 @@
#endif // CONFIG_WARPED_MOTION
#if CONFIG_MOTION_VAR || CONFIG_WARPED_MOTION
rate2_nocoeff = rd_stats->rate;
+#if CONFIG_NCOBMC_ADAPT_WEIGHT
+ // We cannot estimate the rd cost for the motion mode NCOBMC_ADAPT_WEIGHT
+ // right now since it requires mvs from all neighboring blocks. We will
+ // check if this mode is beneficial after all the mv's in the current
+ // superblock are selected.
+ last_motion_mode_allowed = motion_mode_allowed_wrapper(1,
+#if CONFIG_GLOBAL_MOTION && SEPARATE_GLOBAL_MOTION
+ 0, xd->global_motion,
+#endif // CONFIG_GLOBAL_MOTION && SEPARATE_GLOBAL_MOTION
+ mi);
+#else
last_motion_mode_allowed = motion_mode_allowed(
#if CONFIG_GLOBAL_MOTION && SEPARATE_GLOBAL_MOTION
0, xd->global_motion,
#endif // CONFIG_GLOBAL_MOTION && SEPARATE_GLOBAL_MOTION
mi);
+#endif // CONFIG_NCOBMC_ADAPT_WEIGHT
base_mbmi = *mbmi;
#endif // CONFIG_MOTION_VAR || CONFIG_WARPED_MOTION