Commit 55c6bdeb authored by Alex Converse's avatar Alex Converse

Add unpoison_partition_ctx experiment

At the edges of the picture only a subset of partitions are legal. Add
new contexts for these borders so they don't distort the probabilities of
the interior of the image where all partitions are legal.

Only include one context for each block size of each border direction
because so few blocks fall into these contexts to begin with.

objective-1-fast:
   PSNR | PSNR Cb | PSNR Cr | PSNR HVS |    SSIM | MS SSIM | CIEDE 2000
-0.0294 | -0.0911 | -0.2382 |  -0.0481 | -0.0441 | -0.0450 |    -0.0454

derf144: -0.135
lowres: -0.124
midres: -0.076
hdres: -0.078

Change-Id: I909b98eebb7e49273cde90154c8408febe334158
parent 1edf9a30
......@@ -387,6 +387,22 @@ static const aom_prob
{ 58, 32, 12, 128, 128, 128, 128 }, // l split, a not split
{ 10, 7, 6, 128, 128, 128, 128 }, // a/l both split
#endif // CONFIG_EXT_PARTITION
#if CONFIG_UNPOISON_PARTITION_CTX
{ 0, 0, 141, 0, 0, 0, 0 }, // 8x8 -> 4x4
{ 0, 0, 87, 0, 0, 0, 0 }, // 16x16 -> 8x8
{ 0, 0, 59, 0, 0, 0, 0 }, // 32x32 -> 16x16
{ 0, 0, 30, 0, 0, 0, 0 }, // 64x64 -> 32x32
#if CONFIG_EXT_PARTITION
{ 0, 0, 30, 0, 0, 0, 0 }, // 128x128 -> 64x64
#endif // CONFIG_EXT_PARTITION
{ 0, 122, 0, 0, 0, 0, 0 }, // 8x8 -> 4x4
{ 0, 73, 0, 0, 0, 0, 0 }, // 16x16 -> 8x8
{ 0, 58, 0, 0, 0, 0, 0 }, // 32x32 -> 16x16
{ 0, 34, 0, 0, 0, 0, 0 }, // 64x64 -> 32x32
#if CONFIG_EXT_PARTITION
{ 0, 34, 0, 0, 0, 0, 0 }, // 128x128 -> 64x64
#endif // CONFIG_EXT_PARTITION
#endif // CONFIG_UNPOISON_PARTITION_CTX
};
#else
static const aom_prob
......@@ -418,6 +434,22 @@ static const aom_prob
{ 58, 32, 12 }, // l split, a not split
{ 10, 7, 6 }, // a/l both split
#endif // CONFIG_EXT_PARTITION
#if CONFIG_UNPOISON_PARTITION_CTX
{ 0, 0, 141 }, // 8x8 -> 4x4
{ 0, 0, 87 }, // 16x16 -> 8x8
{ 0, 0, 59 }, // 32x32 -> 16x16
{ 0, 0, 30 }, // 64x64 -> 32x32
#if CONFIG_EXT_PARTITION
{ 0, 0, 30 }, // 128x128 -> 64x64
#endif // CONFIG_EXT_PARTITION
{ 0, 122, 0 }, // 8x8 -> 4x4
{ 0, 73, 0 }, // 16x16 -> 8x8
{ 0, 58, 0 }, // 32x32 -> 16x16
{ 0, 34, 0 }, // 64x64 -> 32x32
#if CONFIG_EXT_PARTITION
{ 0, 34, 0 }, // 128x128 -> 64x64
#endif // CONFIG_EXT_PARTITION
#endif // CONFIG_UNPOISON_PARTITION_CTX
};
#endif // CONFIG_EXT_PARTITION_TYPES
......@@ -2039,15 +2071,39 @@ void av1_adapt_intra_frame_probs(AV1_COMMON *cm) {
#if CONFIG_EXT_PARTITION_TYPES
aom_tree_merge_probs(av1_partition_tree, pre_fc->partition_prob[0],
counts->partition[0], fc->partition_prob[0]);
for (i = 1; i < PARTITION_CONTEXTS; i++)
for (i = 1; i < PARTITION_CONTEXTS_PRIMARY; i++)
aom_tree_merge_probs(av1_ext_partition_tree, pre_fc->partition_prob[i],
counts->partition[i], fc->partition_prob[i]);
#else
for (i = 0; i < PARTITION_CONTEXTS; i++) {
for (i = 0; i < PARTITION_CONTEXTS_PRIMARY; i++) {
aom_tree_merge_probs(av1_partition_tree, pre_fc->partition_prob[i],
counts->partition[i], fc->partition_prob[i]);
}
#endif // CONFIG_EXT_PARTITION_TYPES
#if CONFIG_UNPOISON_PARTITION_CTX
for (i = PARTITION_CONTEXTS_PRIMARY;
i < PARTITION_CONTEXTS_PRIMARY + PARTITION_BLOCK_SIZES; ++i) {
unsigned int ct[2] = { counts->partition[i][PARTITION_VERT],
counts->partition[i][PARTITION_SPLIT] };
assert(counts->partition[i][PARTITION_NONE] == 0);
assert(counts->partition[i][PARTITION_HORZ] == 0);
assert(fc->partition_prob[i][PARTITION_NONE] == 0);
assert(fc->partition_prob[i][PARTITION_HORZ] == 0);
fc->partition_prob[i][PARTITION_VERT] =
av1_mode_mv_merge_probs(pre_fc->partition_prob[i][PARTITION_VERT], ct);
}
for (i = PARTITION_CONTEXTS_PRIMARY + PARTITION_BLOCK_SIZES;
i < PARTITION_CONTEXTS_PRIMARY + 2 * PARTITION_BLOCK_SIZES; ++i) {
unsigned int ct[2] = { counts->partition[i][PARTITION_HORZ],
counts->partition[i][PARTITION_SPLIT] };
assert(counts->partition[i][PARTITION_NONE] == 0);
assert(counts->partition[i][PARTITION_VERT] == 0);
assert(fc->partition_prob[i][PARTITION_NONE] == 0);
assert(fc->partition_prob[i][PARTITION_VERT] == 0);
fc->partition_prob[i][PARTITION_HORZ] =
av1_mode_mv_merge_probs(pre_fc->partition_prob[i][PARTITION_HORZ], ct);
}
#endif
#if CONFIG_DELTA_Q
for (i = 0; i < DELTA_Q_CONTEXTS; ++i)
fc->delta_q_prob[i] =
......
......@@ -131,11 +131,14 @@ typedef enum {
typedef char PARTITION_CONTEXT;
#define PARTITION_PLOFFSET 4 // number of probability models per block size
#if CONFIG_EXT_PARTITION
#define PARTITION_CONTEXTS (5 * PARTITION_PLOFFSET)
#define PARTITION_BLOCK_SIZES (4 + CONFIG_EXT_PARTITION)
#define PARTITION_CONTEXTS_PRIMARY (PARTITION_BLOCK_SIZES * PARTITION_PLOFFSET)
#if CONFIG_UNPOISON_PARTITION_CTX
#define PARTITION_CONTEXTS \
(PARTITION_CONTEXTS_PRIMARY + 2 * PARTITION_BLOCK_SIZES)
#else
#define PARTITION_CONTEXTS (4 * PARTITION_PLOFFSET)
#endif // CONFIG_EXT_PARTITION
#define PARTITION_CONTEXTS PARTITION_CONTEXTS_PRIMARY
#endif
// block transform size
typedef enum ATTRIBUTE_PACKED {
......
......@@ -700,7 +700,31 @@ static INLINE void update_ext_partition_context(MACROBLOCKD *xd, int mi_row,
#endif // CONFIG_EXT_PARTITION_TYPES
static INLINE int partition_plane_context(const MACROBLOCKD *xd, int mi_row,
int mi_col, BLOCK_SIZE bsize) {
int mi_col,
#if CONFIG_UNPOISON_PARTITION_CTX
int has_rows, int has_cols,
#endif
BLOCK_SIZE bsize) {
#if CONFIG_UNPOISON_PARTITION_CTX
const PARTITION_CONTEXT *above_ctx = xd->above_seg_context + mi_col;
const PARTITION_CONTEXT *left_ctx =
xd->left_seg_context + (mi_row & MAX_MIB_MASK);
// Minimum partition point is 8x8. Offset the bsl accordingly.
const int bsl = mi_width_log2_lookup[bsize] - mi_width_log2_lookup[BLOCK_8X8];
int above = (*above_ctx >> bsl) & 1, left = (*left_ctx >> bsl) & 1;
assert(b_width_log2_lookup[bsize] == b_height_log2_lookup[bsize]);
assert(bsl >= 0);
if (has_rows && has_cols)
return (left * 2 + above) + bsl * PARTITION_PLOFFSET;
else if (has_rows && !has_cols)
return PARTITION_CONTEXTS_PRIMARY + bsl;
else if (!has_rows && has_cols)
return PARTITION_CONTEXTS_PRIMARY + PARTITION_BLOCK_SIZES + bsl;
else
return -1; // Bogus context, forced SPLIT
#else
const PARTITION_CONTEXT *above_ctx = xd->above_seg_context + mi_col;
const PARTITION_CONTEXT *left_ctx =
xd->left_seg_context + (mi_row & MAX_MIB_MASK);
......@@ -712,6 +736,7 @@ static INLINE int partition_plane_context(const MACROBLOCKD *xd, int mi_row,
assert(bsl >= 0);
return (left * 2 + above) + bsl * PARTITION_PLOFFSET;
#endif
}
static INLINE int max_block_wide(const MACROBLOCKD *xd, const BLOCK_SIZE bsize,
......
......@@ -1822,9 +1822,16 @@ static PARTITION_TYPE read_partition(AV1_COMMON *cm, MACROBLOCKD *xd,
int mi_row, int mi_col, aom_reader *r,
int has_rows, int has_cols,
BLOCK_SIZE bsize) {
#if CONFIG_UNPOISON_PARTITION_CTX
const int ctx =
partition_plane_context(xd, mi_row, mi_col, has_rows, has_cols, bsize);
const aom_prob *const probs = ctx >= 0 ? cm->fc->partition_prob[ctx] : NULL;
FRAME_COUNTS *const counts = ctx >= 0 ? xd->counts : NULL;
#else
const int ctx = partition_plane_context(xd, mi_row, mi_col, bsize);
const aom_prob *const probs = cm->fc->partition_prob[ctx];
FRAME_COUNTS *counts = xd->counts;
FRAME_COUNTS *const counts = xd->counts;
#endif
PARTITION_TYPE p;
if (has_rows && has_cols)
......@@ -4394,15 +4401,21 @@ static int read_compressed_header(AV1Decoder *pbi, const uint8_t *data,
#if CONFIG_EXT_PARTITION_TYPES
for (i = 0; i < PARTITION_TYPES - 1; ++i)
av1_diff_update_prob(&r, &fc->partition_prob[0][i], ACCT_STR);
for (j = 1; j < PARTITION_CONTEXTS; ++j)
for (j = 1; j < PARTITION_CONTEXTS_PRIMARY; ++j)
for (i = 0; i < EXT_PARTITION_TYPES - 1; ++i)
av1_diff_update_prob(&r, &fc->partition_prob[j][i], ACCT_STR);
#else
for (j = 0; j < PARTITION_CONTEXTS; ++j)
for (j = 0; j < PARTITION_CONTEXTS_PRIMARY; ++j)
for (i = 0; i < PARTITION_TYPES - 1; ++i)
av1_diff_update_prob(&r, &fc->partition_prob[j][i], ACCT_STR);
#endif // CONFIG_EXT_PARTITION_TYPES
#endif // EC_ADAPT, DAALA_EC
#if CONFIG_UNPOISON_PARTITION_CTX
for (; j < PARTITION_CONTEXTS_PRIMARY + PARTITION_BLOCK_SIZES; ++j)
av1_diff_update_prob(&r, &fc->partition_prob[j][PARTITION_VERT], ACCT_STR);
for (; j < PARTITION_CONTEXTS_PRIMARY + 2 * PARTITION_BLOCK_SIZES; ++j)
av1_diff_update_prob(&r, &fc->partition_prob[j][PARTITION_HORZ], ACCT_STR);
#endif // CONFIG_UNPOISON_PARTITION_CTX
#endif // CONFIG_EC_ADAPT
#if CONFIG_EXT_INTRA
#if CONFIG_INTRA_INTERP
for (i = 0; i < INTRA_FILTERS + 1; ++i)
......
......@@ -2254,13 +2254,21 @@ static void write_partition(const AV1_COMMON *const cm,
const MACROBLOCKD *const xd, int hbs, int mi_row,
int mi_col, PARTITION_TYPE p, BLOCK_SIZE bsize,
aom_writer *w) {
const int has_rows = (mi_row + hbs) < cm->mi_rows;
const int has_cols = (mi_col + hbs) < cm->mi_cols;
const int is_partition_point = bsize >= BLOCK_8X8;
const int ctx = is_partition_point
? partition_plane_context(xd, mi_row, mi_col, bsize)
? partition_plane_context(xd, mi_row, mi_col,
#if CONFIG_UNPOISON_PARTITION_CTX
has_rows, has_cols,
#endif
bsize)
: 0;
#if CONFIG_UNPOISON_PARTITION_CTX
const aom_prob *const probs = ctx >= 0 ? cm->fc->partition_prob[ctx] : NULL;
#else
const aom_prob *const probs = cm->fc->partition_prob[ctx];
const int has_rows = (mi_row + hbs) < cm->mi_rows;
const int has_cols = (mi_col + hbs) < cm->mi_cols;
#endif
if (!is_partition_point) return;
......@@ -4336,16 +4344,38 @@ static uint32_t write_compressed_header(AV1_COMP *cpi, uint8_t *data) {
#if CONFIG_EXT_PARTITION_TYPES
prob_diff_update(av1_partition_tree, fc->partition_prob[0],
counts->partition[0], PARTITION_TYPES, probwt, header_bc);
for (i = 1; i < PARTITION_CONTEXTS; ++i)
for (i = 1; i < PARTITION_CONTEXTS_PRIMARY; ++i)
prob_diff_update(av1_ext_partition_tree, fc->partition_prob[i],
counts->partition[i], EXT_PARTITION_TYPES, probwt,
header_bc);
#else
for (i = 0; i < PARTITION_CONTEXTS; ++i) {
for (i = 0; i < PARTITION_CONTEXTS_PRIMARY; ++i) {
prob_diff_update(av1_partition_tree, fc->partition_prob[i],
counts->partition[i], PARTITION_TYPES, probwt, header_bc);
}
#endif // CONFIG_EC_ADAPT, CONFIG_DAALA_EC
#endif // CONFIG_EXT_PARTITION_TYPES
#if CONFIG_UNPOISON_PARTITION_CTX
for (; i < PARTITION_CONTEXTS_PRIMARY + PARTITION_BLOCK_SIZES; ++i) {
unsigned int ct[2] = { counts->partition[i][PARTITION_VERT],
counts->partition[i][PARTITION_SPLIT] };
assert(counts->partition[i][PARTITION_NONE] == 0);
assert(counts->partition[i][PARTITION_HORZ] == 0);
assert(fc->partition_prob[i][PARTITION_NONE] == 0);
assert(fc->partition_prob[i][PARTITION_HORZ] == 0);
av1_cond_prob_diff_update(header_bc, &fc->partition_prob[i][PARTITION_VERT],
ct, probwt);
}
for (; i < PARTITION_CONTEXTS_PRIMARY + 2 * PARTITION_BLOCK_SIZES; ++i) {
unsigned int ct[2] = { counts->partition[i][PARTITION_HORZ],
counts->partition[i][PARTITION_SPLIT] };
assert(counts->partition[i][PARTITION_NONE] == 0);
assert(counts->partition[i][PARTITION_VERT] == 0);
assert(fc->partition_prob[i][PARTITION_NONE] == 0);
assert(fc->partition_prob[i][PARTITION_VERT] == 0);
av1_cond_prob_diff_update(header_bc, &fc->partition_prob[i][PARTITION_HORZ],
ct, probwt);
}
#endif
#if CONFIG_EXT_INTRA
#if CONFIG_INTRA_INTERP
......
......@@ -2265,11 +2265,16 @@ static void encode_sb(const AV1_COMP *const cpi, ThreadData *td,
const AV1_COMMON *const cm = &cpi->common;
MACROBLOCK *const x = &td->mb;
MACROBLOCKD *const xd = &x->e_mbd;
const int hbs = mi_size_wide[bsize] / 2;
const int is_partition_root = bsize >= BLOCK_8X8;
const int ctx = is_partition_root
? partition_plane_context(xd, mi_row, mi_col, bsize)
: 0;
const int hbs = mi_size_wide[bsize] / 2;
? partition_plane_context(xd, mi_row, mi_col,
#if CONFIG_UNPOISON_PARTITION_CTX
mi_row + hbs < cm->mi_rows,
mi_col + hbs < cm->mi_cols,
#endif
bsize)
: -1;
const PARTITION_TYPE partition = pc_tree->partitioning;
const BLOCK_SIZE subsize = get_subsize(bsize, partition);
#if CONFIG_EXT_PARTITION_TYPES
......@@ -2285,7 +2290,7 @@ static void encode_sb(const AV1_COMP *const cpi, ThreadData *td,
if (mi_row >= cm->mi_rows || mi_col >= cm->mi_cols) return;
if (!dry_run && is_partition_root) td->counts->partition[ctx][partition]++;
if (!dry_run && ctx >= 0) td->counts->partition[ctx][partition]++;
#if CONFIG_SUPERTX
if (!frame_is_intra_only(cm) && bsize <= MAX_SUPERTX_BLOCK_SIZE &&
......@@ -2562,7 +2567,12 @@ static void rd_use_partition(AV1_COMP *cpi, ThreadData *td,
const int bs = mi_size_wide[bsize];
const int hbs = bs / 2;
int i;
const int pl = partition_plane_context(xd, mi_row, mi_col, bsize);
const int pl = partition_plane_context(xd, mi_row, mi_col,
#if CONFIG_UNPOISON_PARTITION_CTX
mi_row + hbs < cm->mi_rows,
mi_col + hbs < cm->mi_cols,
#endif
bsize);
const PARTITION_TYPE partition = get_partition(cm, mi_row, mi_col, bsize);
const BLOCK_SIZE subsize = get_subsize(bsize, partition);
RD_SEARCH_MACROBLOCK_CONTEXT x_ctx;
......@@ -2638,11 +2648,14 @@ static void rd_use_partition(AV1_COMP *cpi, ThreadData *td,
bsize, ctx_none, INT64_MAX);
if (none_rdc.rate < INT_MAX) {
none_rdc.rate += cpi->partition_cost[pl][PARTITION_NONE];
none_rdc.rate += cpi->partition_cost[pl + CONFIG_UNPOISON_PARTITION_CTX]
[PARTITION_NONE];
none_rdc.rdcost =
RDCOST(x->rdmult, x->rddiv, none_rdc.rate, none_rdc.dist);
#if CONFIG_SUPERTX
none_rate_nocoef += cpi->partition_cost[pl][PARTITION_NONE];
none_rate_nocoef +=
cpi->partition_cost[pl + CONFIG_UNPOISON_PARTITION_CTX]
[PARTITION_NONE];
#endif
}
......@@ -2816,11 +2829,13 @@ static void rd_use_partition(AV1_COMP *cpi, ThreadData *td,
}
if (last_part_rdc.rate < INT_MAX) {
last_part_rdc.rate += cpi->partition_cost[pl][partition];
last_part_rdc.rate +=
cpi->partition_cost[pl + CONFIG_UNPOISON_PARTITION_CTX][partition];
last_part_rdc.rdcost =
RDCOST(x->rdmult, x->rddiv, last_part_rdc.rate, last_part_rdc.dist);
#if CONFIG_SUPERTX
last_part_rate_nocoef += cpi->partition_cost[pl][partition];
last_part_rate_nocoef +=
cpi->partition_cost[pl + CONFIG_UNPOISON_PARTITION_CTX][partition];
#endif
}
......@@ -2895,17 +2910,23 @@ static void rd_use_partition(AV1_COMP *cpi, ThreadData *td,
encode_sb(cpi, td, tile_info, tp, mi_row + y_idx, mi_col + x_idx,
OUTPUT_ENABLED, split_subsize, pc_tree->split[i], NULL);
chosen_rdc.rate += cpi->partition_cost[pl][PARTITION_NONE];
chosen_rdc.rate += cpi->partition_cost[pl + CONFIG_UNPOISON_PARTITION_CTX]
[PARTITION_NONE];
#if CONFIG_SUPERTX
chosen_rate_nocoef += cpi->partition_cost[pl][PARTITION_SPLIT];
chosen_rate_nocoef +=
cpi->partition_cost[pl + CONFIG_UNPOISON_PARTITION_CTX]
[PARTITION_SPLIT];
#endif
}
if (chosen_rdc.rate < INT_MAX) {
chosen_rdc.rate += cpi->partition_cost[pl][PARTITION_SPLIT];
chosen_rdc.rate += cpi->partition_cost[pl + CONFIG_UNPOISON_PARTITION_CTX]
[PARTITION_SPLIT];
chosen_rdc.rdcost =
RDCOST(x->rdmult, x->rddiv, chosen_rdc.rate, chosen_rdc.dist);
#if CONFIG_SUPERTX
chosen_rate_nocoef += cpi->partition_cost[pl][PARTITION_NONE];
chosen_rate_nocoef +=
cpi->partition_cost[pl + CONFIG_UNPOISON_PARTITION_CTX]
[PARTITION_NONE];
#endif
}
}
......@@ -3422,12 +3443,18 @@ static void rd_test_partition3(
#endif // CONFIG_SUPERTX
if (sum_rdc.rdcost < best_rdc->rdcost) {
int pl = partition_plane_context(xd, mi_row, mi_col, bsize);
sum_rdc.rate += cpi->partition_cost[pl][partition];
int pl = partition_plane_context(xd, mi_row, mi_col,
#if CONFIG_UNPOISON_PARTITION_CTX
has_rows, has_cols,
#endif
bsize);
sum_rdc.rate +=
cpi->partition_cost[pl + CONFIG_UNPOISON_PARTITION_CTX][partition];
sum_rdc.rdcost =
RDCOST(x->rdmult, x->rddiv, sum_rdc.rate, sum_rdc.dist);
#if CONFIG_SUPERTX
sum_rate_nocoef += cpi->partition_cost[pl][partition];
sum_rate_nocoef +=
cpi->partition_cost[pl + CONFIG_UNPOISON_PARTITION_CTX][partition];
#endif
if (sum_rdc.rdcost < best_rdc->rdcost) {
#if CONFIG_SUPERTX
......@@ -3462,23 +3489,36 @@ static void rd_pick_partition(const AV1_COMP *const cpi, ThreadData *td,
RD_SEARCH_MACROBLOCK_CONTEXT x_ctx;
const TOKENEXTRA *const tp_orig = *tp;
PICK_MODE_CONTEXT *ctx_none = &pc_tree->none;
#if CONFIG_UNPOISON_PARTITION_CTX
const int hbs = mi_size_wide[bsize] / 2;
const int has_rows = mi_row + hbs < cm->mi_rows;
const int has_cols = mi_col + hbs < cm->mi_cols;
#else
int tmp_partition_cost[PARTITION_TYPES];
#endif
BLOCK_SIZE subsize;
RD_COST this_rdc, sum_rdc, best_rdc;
const int bsize_at_least_8x8 = (bsize >= BLOCK_8X8);
int do_square_split = bsize_at_least_8x8;
#if CONFIG_CB4X4
const int unify_bsize = 1;
const int pl = bsize_at_least_8x8
? partition_plane_context(xd, mi_row, mi_col, bsize)
: 0;
? partition_plane_context(xd, mi_row, mi_col,
#if CONFIG_UNPOISON_PARTITION_CTX
has_rows, has_cols,
#endif
bsize)
: -1;
#else
const int unify_bsize = 0;
const int pl = partition_plane_context(xd, mi_row, mi_col, bsize);
const int pl = partition_plane_context(xd, mi_row, mi_col,
#if CONFIG_UNPOISON_PARTITION_CTX
has_rows, has_cols,
#endif
bsize);
#endif // CONFIG_CB4X4
const int *partition_cost = cpi->partition_cost[pl];
const int *partition_cost =
cpi->partition_cost[pl + CONFIG_UNPOISON_PARTITION_CTX];
#if CONFIG_SUPERTX
int this_rate_nocoef, sum_rate_nocoef = 0, best_rate_nocoef = INT_MAX;
int abort_flag;
......@@ -3518,6 +3558,7 @@ static void rd_pick_partition(const AV1_COMP *const cpi, ThreadData *td,
(void)*tp_orig;
#if !CONFIG_UNPOISON_PARTITION_CTX
if (force_horz_split || force_vert_split) {
tmp_partition_cost[PARTITION_NONE] = INT_MAX;
......@@ -3541,6 +3582,7 @@ static void rd_pick_partition(const AV1_COMP *const cpi, ThreadData *td,
partition_cost = tmp_partition_cost;
}
#endif
#if CONFIG_VAR_TX
#ifndef NDEBUG
......@@ -5975,11 +6017,16 @@ static void predict_sb_complex(const AV1_COMP *const cpi, ThreadData *td,
const AV1_COMMON *const cm = &cpi->common;
MACROBLOCK *const x = &td->mb;
MACROBLOCKD *const xd = &x->e_mbd;
const int hbs = mi_size_wide[bsize] / 2;
const int is_partition_root = bsize >= BLOCK_8X8;
const int ctx = is_partition_root
? partition_plane_context(xd, mi_row, mi_col, bsize)
: 0;
const int hbs = mi_size_wide[bsize] / 2;
? partition_plane_context(xd, mi_row, mi_col,
#if CONFIG_UNPOISON_PARTITION_CTX
mi_row + hbs < cm->mi_rows,
mi_col + hbs < cm->mi_cols,
#endif
bsize)
: -1;
const PARTITION_TYPE partition = pc_tree->partitioning;
const BLOCK_SIZE subsize = get_subsize(bsize, partition);
#if CONFIG_EXT_PARTITION_TYPES
......@@ -6030,7 +6077,7 @@ static void predict_sb_complex(const AV1_COMP *const cpi, ThreadData *td,
}
#endif // CONFIG_AOM_HIGHBITDEPTH
if (!dry_run && is_partition_root && bsize < top_bsize) {
if (!dry_run && ctx >= 0 && bsize < top_bsize) {
// Explicitly cast away const.
FRAME_COUNTS *const frame_counts = (FRAME_COUNTS *)&cm->counts;
frame_counts->partition[ctx][partition]++;
......
......@@ -549,9 +549,11 @@ typedef struct AV1_COMP {
int y_mode_costs[INTRA_MODES][INTRA_MODES][INTRA_MODES];
int switchable_interp_costs[SWITCHABLE_FILTER_CONTEXTS][SWITCHABLE_FILTERS];
#if CONFIG_EXT_PARTITION_TYPES
int partition_cost[PARTITION_CONTEXTS][EXT_PARTITION_TYPES];
int partition_cost[PARTITION_CONTEXTS + CONFIG_UNPOISON_PARTITION_CTX]
[EXT_PARTITION_TYPES];
#else
int partition_cost[PARTITION_CONTEXTS][PARTITION_TYPES];
int partition_cost[PARTITION_CONTEXTS + CONFIG_UNPOISON_PARTITION_CTX]
[PARTITION_TYPES];
#endif
#if CONFIG_PALETTE
int palette_y_size_cost[PALETTE_BLOCK_SIZES][PALETTE_SIZES];
......
......@@ -398,17 +398,41 @@ void av1_initialize_rd_consts(AV1_COMP *cpi) {
if (cpi->sf.partition_search_type != VAR_BASED_PARTITION ||
cm->frame_type == KEY_FRAME) {
#if CONFIG_UNPOISON_PARTITION_CTX
cpi->partition_cost[0][PARTITION_NONE] = INT_MAX;
cpi->partition_cost[0][PARTITION_HORZ] = INT_MAX;
cpi->partition_cost[0][PARTITION_VERT] = INT_MAX;
cpi->partition_cost[0][PARTITION_SPLIT] = 0;
#endif
#if CONFIG_EXT_PARTITION_TYPES
av1_cost_tokens(cpi->partition_cost[0], cm->fc->partition_prob[0],
av1_partition_tree);
for (i = 1; i < PARTITION_CONTEXTS; ++i)
av1_cost_tokens(cpi->partition_cost[i], cm->fc->partition_prob[i],
av1_ext_partition_tree);
av1_cost_tokens(cpi->partition_cost[CONFIG_UNPOISON_PARTITION_CTX],
cm->fc->partition_prob[0], av1_partition_tree);
for (i = 1; i < PARTITION_CONTEXTS_PRIMARY; ++i)
av1_cost_tokens(cpi->partition_cost[CONFIG_UNPOISON_PARTITION_CTX + i],
cm->fc->partition_prob[i], av1_ext_partition_tree);
#else
for (i = 0; i < PARTITION_CONTEXTS; ++i)
av1_cost_tokens(cpi->partition_cost[i], cm->fc->partition_prob[i],
av1_partition_tree);
for (i = 0; i < PARTITION_CONTEXTS_PRIMARY; ++i)
av1_cost_tokens(cpi->partition_cost[CONFIG_UNPOISON_PARTITION_CTX + i],
cm->fc->partition_prob[i], av1_partition_tree);
#endif // CONFIG_EXT_PARTITION_TYPES
#if CONFIG_UNPOISON_PARTITION_CTX
for (; i < PARTITION_CONTEXTS_PRIMARY + PARTITION_BLOCK_SIZES; ++i) {
aom_prob p = cm->fc->partition_prob[i][PARTITION_VERT];
assert(p > 0);
cpi->partition_cost[1 + i][PARTITION_NONE] = INT_MAX;
cpi->partition_cost[1 + i][PARTITION_HORZ] = INT_MAX;
cpi->partition_cost[1 + i][PARTITION_VERT] = av1_cost_bit(p, 0);
cpi->partition_cost[1 + i][PARTITION_SPLIT] = av1_cost_bit(p, 1);
}
for (; i < PARTITION_CONTEXTS_PRIMARY + 2 * PARTITION_BLOCK_SIZES; ++i) {
aom_prob p = cm->fc->partition_prob[i][PARTITION_HORZ];
assert(p > 0);
cpi->partition_cost[1 + i][PARTITION_NONE] = INT_MAX;
cpi->partition_cost[1 + i][PARTITION_HORZ] = av1_cost_bit(p, 0);
cpi->partition_cost[1 + i][PARTITION_VERT] = INT_MAX;
cpi->partition_cost[1 + i][PARTITION_SPLIT] = av1_cost_bit(p, 1);
}
#endif
}
fill_mode_costs(cpi);
......
......@@ -271,6 +271,7 @@ EXPERIMENT_LIST="
loop_restoration
ext_partition
ext_partition_types
unpoison_partition_ctx
ext_tile
motion_var
ncobmc
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment