Commit 7b9f2b3b authored by Fangwen Fu's avatar Fangwen Fu Committed by Yaowu Xu
Browse files

add horizontal tile dependence support

Change-Id: I1050b69045407381d4626b65a0bf6f35957a66f4
parent e4c46918
...@@ -286,7 +286,6 @@ enum aome_enc_control_id { ...@@ -286,7 +286,6 @@ enum aome_enc_control_id {
* By default, the value is 0, i.e. one single row tile for entire image. * By default, the value is 0, i.e. one single row tile for entire image.
*/ */
AV1E_SET_TILE_ROWS, AV1E_SET_TILE_ROWS,
#if CONFIG_LOOPFILTERING_ACROSS_TILES #if CONFIG_LOOPFILTERING_ACROSS_TILES
/*!\brief Codec control function to set loop_filter_across_tiles_enabled. /*!\brief Codec control function to set loop_filter_across_tiles_enabled.
* *
...@@ -482,6 +481,20 @@ enum aome_enc_control_id { ...@@ -482,6 +481,20 @@ enum aome_enc_control_id {
*/ */
AV1E_SET_MTU, AV1E_SET_MTU,
/*!\brief Codec control function to set dependent_horz_tiles.
*
* In encoding and decoding, AV1 allows enabling dependent horizontal tile
* The parameter for this control describes the value of this flag,
* which has a valid range [0, 1]:
* 0 = disable dependent horizontal tile
* 1 = enable dependent horizontal tile,
*
* By default, the value is 0, i.e. disable dependent horizontal tile.
*
* Supported in codecs: AV1
*/
AV1E_SET_TILE_DEPENDENT_ROWS,
/*!\brief Codec control function to set the number of symbols in an ANS data /*!\brief Codec control function to set the number of symbols in an ANS data
* window. * window.
* *
...@@ -606,6 +619,12 @@ AOM_CTRL_USE_TYPE(AV1E_SET_TILE_COLUMNS, int) ...@@ -606,6 +619,12 @@ AOM_CTRL_USE_TYPE(AV1E_SET_TILE_COLUMNS, int)
#define AOM_CTRL_AV1E_SET_TILE_COLUMNS #define AOM_CTRL_AV1E_SET_TILE_COLUMNS
AOM_CTRL_USE_TYPE(AV1E_SET_TILE_ROWS, int) AOM_CTRL_USE_TYPE(AV1E_SET_TILE_ROWS, int)
#define AOM_CTRL_AV1E_SET_TILE_ROWS #define AOM_CTRL_AV1E_SET_TILE_ROWS
#if CONFIG_DEPENDENT_HORZTILES
AOM_CTRL_USE_TYPE(AV1E_SET_TILE_DEPENDENT_ROWS, int)
#define AOM_CTRL_AV1E_SET_TILE_DEPENDENT_ROWS
#endif
#if CONFIG_LOOPFILTERING_ACROSS_TILES #if CONFIG_LOOPFILTERING_ACROSS_TILES
AOM_CTRL_USE_TYPE(AV1E_SET_TILE_LOOPFILTER, int) AOM_CTRL_USE_TYPE(AV1E_SET_TILE_LOOPFILTER, int)
#define AOM_CTRL_AV1E_SET_TILE_LOOPFILTER #define AOM_CTRL_AV1E_SET_TILE_LOOPFILTER
......
...@@ -376,6 +376,10 @@ static const arg_def_t tile_cols = ...@@ -376,6 +376,10 @@ static const arg_def_t tile_cols =
static const arg_def_t tile_rows = static const arg_def_t tile_rows =
ARG_DEF(NULL, "tile-rows", 1, ARG_DEF(NULL, "tile-rows", 1,
"Number of tile rows to use, log2 (set to 0 while threads > 1)"); "Number of tile rows to use, log2 (set to 0 while threads > 1)");
#if CONFIG_DEPENDENT_HORZTILES
static const arg_def_t tile_dependent_rows =
ARG_DEF(NULL, "tile-dependent-rows", 1, "Enable dependent Tile rows");
#endif
#if CONFIG_LOOPFILTERING_ACROSS_TILES #if CONFIG_LOOPFILTERING_ACROSS_TILES
static const arg_def_t tile_loopfilter = ARG_DEF( static const arg_def_t tile_loopfilter = ARG_DEF(
NULL, "tile-loopfilter", 1, "Enable loop filter across tile boundary"); NULL, "tile-loopfilter", 1, "Enable loop filter across tile boundary");
...@@ -476,6 +480,9 @@ static const arg_def_t *av1_args[] = { &cpu_used_av1, ...@@ -476,6 +480,9 @@ static const arg_def_t *av1_args[] = { &cpu_used_av1,
&static_thresh, &static_thresh,
&tile_cols, &tile_cols,
&tile_rows, &tile_rows,
#if CONFIG_DEPENDENT_HORZTILES
&tile_dependent_rows,
#endif
#if CONFIG_LOOPFILTERING_ACROSS_TILES #if CONFIG_LOOPFILTERING_ACROSS_TILES
&tile_loopfilter, &tile_loopfilter,
#endif // CONFIG_LOOPFILTERING_ACROSS_TILES #endif // CONFIG_LOOPFILTERING_ACROSS_TILES
...@@ -521,6 +528,9 @@ static const int av1_arg_ctrl_map[] = { AOME_SET_CPUUSED, ...@@ -521,6 +528,9 @@ static const int av1_arg_ctrl_map[] = { AOME_SET_CPUUSED,
AOME_SET_STATIC_THRESHOLD, AOME_SET_STATIC_THRESHOLD,
AV1E_SET_TILE_COLUMNS, AV1E_SET_TILE_COLUMNS,
AV1E_SET_TILE_ROWS, AV1E_SET_TILE_ROWS,
#if CONFIG_DEPENDENT_HORZTILES
AV1E_SET_TILE_DEPENDENT_ROWS,
#endif
#if CONFIG_LOOPFILTERING_ACROSS_TILES #if CONFIG_LOOPFILTERING_ACROSS_TILES
AV1E_SET_TILE_LOOPFILTER, AV1E_SET_TILE_LOOPFILTER,
#endif // CONFIG_LOOPFILTERING_ACROSS_TILES #endif // CONFIG_LOOPFILTERING_ACROSS_TILES
......
...@@ -34,6 +34,9 @@ struct av1_extracfg { ...@@ -34,6 +34,9 @@ struct av1_extracfg {
unsigned int static_thresh; unsigned int static_thresh;
unsigned int tile_columns; unsigned int tile_columns;
unsigned int tile_rows; unsigned int tile_rows;
#if CONFIG_DEPENDENT_HORZTILES
unsigned int dependent_horz_tiles;
#endif
#if CONFIG_LOOPFILTERING_ACROSS_TILES #if CONFIG_LOOPFILTERING_ACROSS_TILES
unsigned int loop_filter_across_tiles_enabled; unsigned int loop_filter_across_tiles_enabled;
#endif // CONFIG_LOOPFILTERING_ACROSS_TILES #endif // CONFIG_LOOPFILTERING_ACROSS_TILES
...@@ -90,6 +93,9 @@ static struct av1_extracfg default_extra_cfg = { ...@@ -90,6 +93,9 @@ static struct av1_extracfg default_extra_cfg = {
0, // tile_columns 0, // tile_columns
0, // tile_rows 0, // tile_rows
#endif // CONFIG_EXT_TILE #endif // CONFIG_EXT_TILE
#if CONFIG_DEPENDENT_HORZTILES
0, // Depdendent Horizontal tiles
#endif
#if CONFIG_LOOPFILTERING_ACROSS_TILES #if CONFIG_LOOPFILTERING_ACROSS_TILES
1, // loop_filter_across_tiles_enabled 1, // loop_filter_across_tiles_enabled
#endif // CONFIG_LOOPFILTERING_ACROSS_TILES #endif // CONFIG_LOOPFILTERING_ACROSS_TILES
...@@ -268,6 +274,9 @@ static aom_codec_err_t validate_config(aom_codec_alg_priv_t *ctx, ...@@ -268,6 +274,9 @@ static aom_codec_err_t validate_config(aom_codec_alg_priv_t *ctx,
RANGE_CHECK_HI(extra_cfg, tile_columns, 6); RANGE_CHECK_HI(extra_cfg, tile_columns, 6);
RANGE_CHECK_HI(extra_cfg, tile_rows, 2); RANGE_CHECK_HI(extra_cfg, tile_rows, 2);
#endif // CONFIG_EXT_TILE #endif // CONFIG_EXT_TILE
#if CONFIG_DEPENDENT_HORZTILES
RANGE_CHECK_HI(extra_cfg, dependent_horz_tiles, 1);
#endif
#if CONFIG_LOOPFILTERING_ACROSS_TILES #if CONFIG_LOOPFILTERING_ACROSS_TILES
RANGE_CHECK_HI(extra_cfg, loop_filter_across_tiles_enabled, 1); RANGE_CHECK_HI(extra_cfg, loop_filter_across_tiles_enabled, 1);
#endif // CONFIG_LOOPFILTERING_ACROSS_TILES #endif // CONFIG_LOOPFILTERING_ACROSS_TILES
...@@ -512,12 +521,13 @@ static aom_codec_err_t set_encoder_config( ...@@ -512,12 +521,13 @@ static aom_codec_err_t set_encoder_config(
oxcf->tile_columns = extra_cfg->tile_columns; oxcf->tile_columns = extra_cfg->tile_columns;
oxcf->tile_rows = extra_cfg->tile_rows; oxcf->tile_rows = extra_cfg->tile_rows;
#endif // CONFIG_EXT_TILE #endif // CONFIG_EXT_TILE
#if CONFIG_DEPENDENT_HORZTILES
oxcf->dependent_horz_tiles = extra_cfg->dependent_horz_tiles;
#endif
#if CONFIG_LOOPFILTERING_ACROSS_TILES #if CONFIG_LOOPFILTERING_ACROSS_TILES
oxcf->loop_filter_across_tiles_enabled = oxcf->loop_filter_across_tiles_enabled =
extra_cfg->loop_filter_across_tiles_enabled; extra_cfg->loop_filter_across_tiles_enabled;
#endif // CONFIG_LOOPFILTERING_ACROSS_TILES #endif // CONFIG_LOOPFILTERING_ACROSS_TILES
oxcf->error_resilient_mode = cfg->g_error_resilient; oxcf->error_resilient_mode = cfg->g_error_resilient;
oxcf->frame_parallel_decoding_mode = extra_cfg->frame_parallel_decoding_mode; oxcf->frame_parallel_decoding_mode = extra_cfg->frame_parallel_decoding_mode;
...@@ -679,7 +689,14 @@ static aom_codec_err_t ctrl_set_tile_rows(aom_codec_alg_priv_t *ctx, ...@@ -679,7 +689,14 @@ static aom_codec_err_t ctrl_set_tile_rows(aom_codec_alg_priv_t *ctx,
extra_cfg.tile_rows = CAST(AV1E_SET_TILE_ROWS, args); extra_cfg.tile_rows = CAST(AV1E_SET_TILE_ROWS, args);
return update_extra_cfg(ctx, &extra_cfg); return update_extra_cfg(ctx, &extra_cfg);
} }
#if CONFIG_DEPENDENT_HORZTILES
static aom_codec_err_t ctrl_set_tile_dependent_rows(aom_codec_alg_priv_t *ctx,
va_list args) {
struct av1_extracfg extra_cfg = ctx->extra_cfg;
extra_cfg.dependent_horz_tiles = CAST(AV1E_SET_TILE_DEPENDENT_ROWS, args);
return update_extra_cfg(ctx, &extra_cfg);
}
#endif
#if CONFIG_LOOPFILTERING_ACROSS_TILES #if CONFIG_LOOPFILTERING_ACROSS_TILES
static aom_codec_err_t ctrl_set_tile_loopfilter(aom_codec_alg_priv_t *ctx, static aom_codec_err_t ctrl_set_tile_loopfilter(aom_codec_alg_priv_t *ctx,
va_list args) { va_list args) {
...@@ -1390,6 +1407,9 @@ static aom_codec_ctrl_fn_map_t encoder_ctrl_maps[] = { ...@@ -1390,6 +1407,9 @@ static aom_codec_ctrl_fn_map_t encoder_ctrl_maps[] = {
{ AOME_SET_STATIC_THRESHOLD, ctrl_set_static_thresh }, { AOME_SET_STATIC_THRESHOLD, ctrl_set_static_thresh },
{ AV1E_SET_TILE_COLUMNS, ctrl_set_tile_columns }, { AV1E_SET_TILE_COLUMNS, ctrl_set_tile_columns },
{ AV1E_SET_TILE_ROWS, ctrl_set_tile_rows }, { AV1E_SET_TILE_ROWS, ctrl_set_tile_rows },
#if CONFIG_DEPENDENT_HORZTILES
{ AV1E_SET_TILE_DEPENDENT_ROWS, ctrl_set_tile_dependent_rows },
#endif
#if CONFIG_LOOPFILTERING_ACROSS_TILES #if CONFIG_LOOPFILTERING_ACROSS_TILES
{ AV1E_SET_TILE_LOOPFILTER, ctrl_set_tile_loopfilter }, { AV1E_SET_TILE_LOOPFILTER, ctrl_set_tile_loopfilter },
#endif // CONFIG_LOOPFILTERING_ACROSS_TILES #endif // CONFIG_LOOPFILTERING_ACROSS_TILES
......
...@@ -191,7 +191,12 @@ static uint8_t scan_row_mbmi(const AV1_COMMON *cm, const MACROBLOCKD *xd, ...@@ -191,7 +191,12 @@ static uint8_t scan_row_mbmi(const AV1_COMMON *cm, const MACROBLOCKD *xd,
mi_pos.row = row_offset; mi_pos.row = row_offset;
mi_pos.col = i; mi_pos.col = i;
#if CONFIG_DEPENDENT_HORZTILES
if (is_inside(tile, mi_col, mi_row, cm->mi_rows, cm->dependent_horz_tiles,
&mi_pos)) {
#else
if (is_inside(tile, mi_col, mi_row, &mi_pos)) { if (is_inside(tile, mi_col, mi_row, &mi_pos)) {
#endif
const MODE_INFO *const candidate_mi = const MODE_INFO *const candidate_mi =
xd->mi[mi_pos.row * xd->mi_stride + mi_pos.col]; xd->mi[mi_pos.row * xd->mi_stride + mi_pos.col];
const MB_MODE_INFO *const candidate = &candidate_mi->mbmi; const MB_MODE_INFO *const candidate = &candidate_mi->mbmi;
...@@ -238,7 +243,12 @@ static uint8_t scan_col_mbmi(const AV1_COMMON *cm, const MACROBLOCKD *xd, ...@@ -238,7 +243,12 @@ static uint8_t scan_col_mbmi(const AV1_COMMON *cm, const MACROBLOCKD *xd,
mi_pos.row = i; mi_pos.row = i;
mi_pos.col = col_offset; mi_pos.col = col_offset;
#if CONFIG_DEPENDENT_HORZTILES
if (is_inside(tile, mi_col, mi_row, cm->mi_rows, cm->dependent_horz_tiles,
&mi_pos)) {
#else
if (is_inside(tile, mi_col, mi_row, &mi_pos)) { if (is_inside(tile, mi_col, mi_row, &mi_pos)) {
#endif
const MODE_INFO *const candidate_mi = const MODE_INFO *const candidate_mi =
xd->mi[mi_pos.row * xd->mi_stride + mi_pos.col]; xd->mi[mi_pos.row * xd->mi_stride + mi_pos.col];
const MB_MODE_INFO *const candidate = &candidate_mi->mbmi; const MB_MODE_INFO *const candidate = &candidate_mi->mbmi;
...@@ -271,8 +281,14 @@ static uint8_t scan_blk_mbmi(const AV1_COMMON *cm, const MACROBLOCKD *xd, ...@@ -271,8 +281,14 @@ static uint8_t scan_blk_mbmi(const AV1_COMMON *cm, const MACROBLOCKD *xd,
mi_pos.row = row_offset; mi_pos.row = row_offset;
mi_pos.col = col_offset; mi_pos.col = col_offset;
#if CONFIG_DEPENDENT_HORZTILES
if (is_inside(tile, mi_col, mi_row, cm->mi_rows, cm->dependent_horz_tiles,
&mi_pos) &&
*refmv_count < MAX_REF_MV_STACK_SIZE) {
#else
if (is_inside(tile, mi_col, mi_row, &mi_pos) && if (is_inside(tile, mi_col, mi_row, &mi_pos) &&
*refmv_count < MAX_REF_MV_STACK_SIZE) { *refmv_count < MAX_REF_MV_STACK_SIZE) {
#endif
const MODE_INFO *const candidate_mi = const MODE_INFO *const candidate_mi =
xd->mi[mi_pos.row * xd->mi_stride + mi_pos.col]; xd->mi[mi_pos.row * xd->mi_stride + mi_pos.col];
const MB_MODE_INFO *const candidate = &candidate_mi->mbmi; const MB_MODE_INFO *const candidate = &candidate_mi->mbmi;
...@@ -348,7 +364,13 @@ static int add_col_ref_mv(const AV1_COMMON *cm, ...@@ -348,7 +364,13 @@ static int add_col_ref_mv(const AV1_COMMON *cm,
mi_pos.row = blk_row; mi_pos.row = blk_row;
mi_pos.col = blk_col; mi_pos.col = blk_col;
#if CONFIG_DEPENDENT_HORZTILES
if (!is_inside(&xd->tile, mi_col, mi_row, cm->mi_rows,
cm->dependent_horz_tiles, &mi_pos))
return coll_blk_count;
#else
if (!is_inside(&xd->tile, mi_col, mi_row, &mi_pos)) return coll_blk_count; if (!is_inside(&xd->tile, mi_col, mi_row, &mi_pos)) return coll_blk_count;
#endif
for (ref = 0; ref < 2; ++ref) { for (ref = 0; ref < 2; ++ref) {
if (prev_frame_mvs->ref_frame[ref] == ref_frame) { if (prev_frame_mvs->ref_frame[ref] == ref_frame) {
...@@ -607,7 +629,12 @@ static void find_mv_refs_idx(const AV1_COMMON *cm, const MACROBLOCKD *xd, ...@@ -607,7 +629,12 @@ static void find_mv_refs_idx(const AV1_COMMON *cm, const MACROBLOCKD *xd,
// and we also need to keep a mode count. // and we also need to keep a mode count.
for (i = 0; i < 2; ++i) { for (i = 0; i < 2; ++i) {
const POSITION *const mv_ref = &mv_ref_search[i]; const POSITION *const mv_ref = &mv_ref_search[i];
#if CONFIG_DEPENDENT_HORZTILES
if (is_inside(tile, mi_col, mi_row, cm->mi_rows, cm->dependent_horz_tiles,
mv_ref)) {
#else
if (is_inside(tile, mi_col, mi_row, mv_ref)) { if (is_inside(tile, mi_col, mi_row, mv_ref)) {
#endif
const MODE_INFO *const candidate_mi = const MODE_INFO *const candidate_mi =
xd->mi[mv_ref->col + mv_ref->row * xd->mi_stride]; xd->mi[mv_ref->col + mv_ref->row * xd->mi_stride];
const MB_MODE_INFO *const candidate = &candidate_mi->mbmi; const MB_MODE_INFO *const candidate = &candidate_mi->mbmi;
...@@ -629,7 +656,12 @@ static void find_mv_refs_idx(const AV1_COMMON *cm, const MACROBLOCKD *xd, ...@@ -629,7 +656,12 @@ static void find_mv_refs_idx(const AV1_COMMON *cm, const MACROBLOCKD *xd,
// mode counts. // mode counts.
for (; i < MVREF_NEIGHBOURS; ++i) { for (; i < MVREF_NEIGHBOURS; ++i) {
const POSITION *const mv_ref = &mv_ref_search[i]; const POSITION *const mv_ref = &mv_ref_search[i];
#if CONFIG_DEPENDENT_HORZTILES
if (is_inside(tile, mi_col, mi_row, cm->mi_rows, cm->dependent_horz_tiles,
mv_ref)) {
#else
if (is_inside(tile, mi_col, mi_row, mv_ref)) { if (is_inside(tile, mi_col, mi_row, mv_ref)) {
#endif
const MB_MODE_INFO *const candidate = const MB_MODE_INFO *const candidate =
!xd->mi[mv_ref->col + mv_ref->row * xd->mi_stride] !xd->mi[mv_ref->col + mv_ref->row * xd->mi_stride]
? NULL ? NULL
...@@ -683,7 +715,12 @@ static void find_mv_refs_idx(const AV1_COMMON *cm, const MACROBLOCKD *xd, ...@@ -683,7 +715,12 @@ static void find_mv_refs_idx(const AV1_COMMON *cm, const MACROBLOCKD *xd,
if (different_ref_found) { if (different_ref_found) {
for (i = 0; i < MVREF_NEIGHBOURS; ++i) { for (i = 0; i < MVREF_NEIGHBOURS; ++i) {
const POSITION *mv_ref = &mv_ref_search[i]; const POSITION *mv_ref = &mv_ref_search[i];
#if CONFIG_DEPENDENT_HORZTILES
if (is_inside(tile, mi_col, mi_row, cm->mi_rows, cm->dependent_horz_tiles,
mv_ref)) {
#else
if (is_inside(tile, mi_col, mi_row, mv_ref)) { if (is_inside(tile, mi_col, mi_row, mv_ref)) {
#endif
const MB_MODE_INFO *const candidate = const MB_MODE_INFO *const candidate =
!xd->mi[mv_ref->col + mv_ref->row * xd->mi_stride] !xd->mi[mv_ref->col + mv_ref->row * xd->mi_stride]
? NULL ? NULL
...@@ -793,7 +830,12 @@ void av1_update_mv_context(const MACROBLOCKD *xd, MODE_INFO *mi, ...@@ -793,7 +830,12 @@ void av1_update_mv_context(const MACROBLOCKD *xd, MODE_INFO *mi,
// If the size < 8x8, we get the mv from the bmi substructure; // If the size < 8x8, we get the mv from the bmi substructure;
for (i = 0; i < 2; ++i) { for (i = 0; i < 2; ++i) {
const POSITION *const mv_ref = &mv_ref_search[i]; const POSITION *const mv_ref = &mv_ref_search[i];
#if CONFIG_DEPENDENT_HORZTILES
if (is_inside(tile, mi_col, mi_row, cm->mi_rows, cm->dependent_horz_tiles,
mv_ref)) {
#else
if (is_inside(tile, mi_col, mi_row, mv_ref)) { if (is_inside(tile, mi_col, mi_row, mv_ref)) {
#endif
const MODE_INFO *const candidate_mi = const MODE_INFO *const candidate_mi =
xd->mi[mv_ref->col + mv_ref->row * xd->mi_stride]; xd->mi[mv_ref->col + mv_ref->row * xd->mi_stride];
const MB_MODE_INFO *const candidate = &candidate_mi->mbmi; const MB_MODE_INFO *const candidate = &candidate_mi->mbmi;
......
...@@ -345,6 +345,23 @@ static INLINE int_mv scale_mv(const MB_MODE_INFO *mbmi, int ref, ...@@ -345,6 +345,23 @@ static INLINE int_mv scale_mv(const MB_MODE_INFO *mbmi, int ref,
// Checks that the given mi_row, mi_col and search point // Checks that the given mi_row, mi_col and search point
// are inside the borders of the tile. // are inside the borders of the tile.
#if CONFIG_DEPENDENT_HORZTILES
static INLINE int is_inside(const TileInfo *const tile, int mi_col, int mi_row,
int mi_rows, int dependent_horz_tile_flag,
const POSITION *mi_pos) {
if (dependent_horz_tile_flag) {
return !(mi_row + mi_pos->row < 0 ||
mi_col + mi_pos->col < tile->mi_col_start ||
mi_row + mi_pos->row >= mi_rows ||
mi_col + mi_pos->col >= tile->mi_col_end);
} else {
return !(mi_row + mi_pos->row < tile->mi_row_start ||
mi_col + mi_pos->col < tile->mi_col_start ||
mi_row + mi_pos->row >= tile->mi_row_end ||
mi_col + mi_pos->col >= tile->mi_col_end);
}
}
#else
static INLINE int is_inside(const TileInfo *const tile, int mi_col, int mi_row, static INLINE int is_inside(const TileInfo *const tile, int mi_col, int mi_row,
const POSITION *mi_pos) { const POSITION *mi_pos) {
return !(mi_row + mi_pos->row < tile->mi_row_start || return !(mi_row + mi_pos->row < tile->mi_row_start ||
...@@ -352,6 +369,7 @@ static INLINE int is_inside(const TileInfo *const tile, int mi_col, int mi_row, ...@@ -352,6 +369,7 @@ static INLINE int is_inside(const TileInfo *const tile, int mi_col, int mi_row,
mi_row + mi_pos->row >= tile->mi_row_end || mi_row + mi_pos->row >= tile->mi_row_end ||
mi_col + mi_pos->col >= tile->mi_col_end); mi_col + mi_pos->col >= tile->mi_col_end);
} }
#endif
static INLINE void lower_mv_precision(MV *mv, int allow_hp) { static INLINE void lower_mv_precision(MV *mv, int allow_hp) {
if (!allow_hp) { if (!allow_hp) {
......
...@@ -368,6 +368,9 @@ typedef struct AV1Common { ...@@ -368,6 +368,9 @@ typedef struct AV1Common {
int tile_cols, tile_rows; int tile_cols, tile_rows;
int tile_width, tile_height; // In MI units int tile_width, tile_height; // In MI units
#if CONFIG_DEPENDENT_HORZTILES
int dependent_horz_tiles;
#endif
#if CONFIG_LOOPFILTERING_ACROSS_TILES #if CONFIG_LOOPFILTERING_ACROSS_TILES
int loop_filter_across_tiles_enabled; int loop_filter_across_tiles_enabled;
#endif // CONFIG_LOOPFILTERING_ACROSS_TILES #endif // CONFIG_LOOPFILTERING_ACROSS_TILES
...@@ -580,6 +583,54 @@ static INLINE void set_plane_n4(MACROBLOCKD *const xd, int bw, int bh) { ...@@ -580,6 +583,54 @@ static INLINE void set_plane_n4(MACROBLOCKD *const xd, int bw, int bh) {
} }
} }
#if CONFIG_DEPENDENT_HORZTILES
static INLINE void set_mi_row_col(MACROBLOCKD *xd, const TileInfo *const tile,
int mi_row, int bh, int mi_col, int bw,
int mi_rows, int mi_cols,
int dependent_horz_tile_flag) {
xd->mb_to_top_edge = -((mi_row * MI_SIZE) * 8);
xd->mb_to_bottom_edge = ((mi_rows - bh - mi_row) * MI_SIZE) * 8;
xd->mb_to_left_edge = -((mi_col * MI_SIZE) * 8);
xd->mb_to_right_edge = ((mi_cols - bw - mi_col) * MI_SIZE) * 8;
if (dependent_horz_tile_flag) {
xd->up_available = (mi_row > 0);
} else {
// Are edges available for intra prediction?
xd->up_available = (mi_row > tile->mi_row_start);
}
xd->left_available = (mi_col > tile->mi_col_start);
if (xd->up_available) {
xd->above_mi = xd->mi[-xd->mi_stride];
// above_mi may be NULL in encoder's first pass.
xd->above_mbmi = xd->above_mi ? &xd->above_mi->mbmi : NULL;
} else {
xd->above_mi = NULL;
xd->above_mbmi = NULL;
}
if (xd->left_available) {
xd->left_mi = xd->mi[-1];
// left_mi may be NULL in encoder's first pass.
xd->left_mbmi = xd->left_mi ? &xd->left_mi->mbmi : NULL;
} else {
xd->left_mi = NULL;
xd->left_mbmi = NULL;
}
xd->n8_h = bh;
xd->n8_w = bw;
#if CONFIG_REF_MV
xd->is_sec_rect = 0;
if (xd->n8_w < xd->n8_h)
if (mi_col & (xd->n8_h - 1)) xd->is_sec_rect = 1;
if (xd->n8_w > xd->n8_h)
if (mi_row & (xd->n8_w - 1)) xd->is_sec_rect = 1;
#endif
}
#else
static INLINE void set_mi_row_col(MACROBLOCKD *xd, const TileInfo *const tile, static INLINE void set_mi_row_col(MACROBLOCKD *xd, const TileInfo *const tile,
int mi_row, int bh, int mi_col, int bw, int mi_row, int bh, int mi_col, int bw,
int mi_rows, int mi_cols) { int mi_rows, int mi_cols) {
...@@ -620,6 +671,7 @@ static INLINE void set_mi_row_col(MACROBLOCKD *xd, const TileInfo *const tile, ...@@ -620,6 +671,7 @@ static INLINE void set_mi_row_col(MACROBLOCKD *xd, const TileInfo *const tile,
if (mi_row & (xd->n8_w - 1)) xd->is_sec_rect = 1; if (mi_row & (xd->n8_w - 1)) xd->is_sec_rect = 1;
#endif #endif
} }
#endif
static INLINE const aom_prob *get_y_mode_probs(const AV1_COMMON *cm, static INLINE const aom_prob *get_y_mode_probs(const AV1_COMMON *cm,
const MODE_INFO *mi, const MODE_INFO *mi,
......
...@@ -641,9 +641,14 @@ static MB_MODE_INFO *set_offsets(AV1_COMMON *const cm, MACROBLOCKD *const xd, ...@@ -641,9 +641,14 @@ static MB_MODE_INFO *set_offsets(AV1_COMMON *const cm, MACROBLOCKD *const xd,
xd->max_tx_size = max_txsize_lookup[bsize]; xd->max_tx_size = max_txsize_lookup[bsize];
#endif #endif
// Distance of Mb to the various image edges. These are specified to 8th pel // Distance of Mb to the various image edges. These are specified to 8th pel
// as they are always compared to values that are in 1/8th pel units // as they are always compared to values that are in 1/8th pel units
#if CONFIG_DEPENDENT_HORZTILES
set_mi_row_col(xd, tile, mi_row, bh, mi_col, bw, cm->mi_rows, cm->mi_cols,
cm->dependent_horz_tiles);
#else
set_mi_row_col(xd, tile, mi_row, bh, mi_col, bw, cm->mi_rows, cm->mi_cols); set_mi_row_col(xd, tile, mi_row, bh, mi_col, bw, cm->mi_rows, cm->mi_cols);
#endif
av1_setup_dst_planes(xd->plane, get_frame_new_buffer(cm), mi_row, mi_col); av1_setup_dst_planes(xd->plane, get_frame_new_buffer(cm), mi_row, mi_col);
return &xd->mi[0]->mbmi; return &xd->mi[0]->mbmi;
...@@ -664,8 +669,13 @@ static MB_MODE_INFO *set_offsets_extend(AV1_COMMON *const cm, ...@@ -664,8 +669,13 @@ static MB_MODE_INFO *set_offsets_extend(AV1_COMMON *const cm,
const int offset = mi_row_ori * cm->mi_stride + mi_col_ori; const int offset = mi_row_ori * cm->mi_stride + mi_col_ori;
xd->mi = cm->mi_grid_visible + offset; xd->mi = cm->mi_grid_visible + offset;
xd->mi[0] = cm->mi + offset; xd->mi[0] = cm->mi + offset;
#if CONFIG_DEPENDENT_HORZTILES
set_mi_row_col(xd, tile, mi_row_pred, bh, mi_col_pred, bw, cm->mi_rows,
cm->mi_cols, cm->dependent_horz_tiles);
#else
set_mi_row_col(xd, tile, mi_row_pred, bh, mi_col_pred, bw, cm->mi_rows, set_mi_row_col(xd, tile, mi_row_pred, bh, mi_col_pred, bw, cm->mi_rows,
cm->mi_cols); cm->mi_cols);
#endif
xd->up_available = (mi_row_ori > tile->mi_row_start); xd->up_available = (mi_row_ori > tile->mi_row_start);
xd->left_available = (mi_col_ori > tile->mi_col_start); xd->left_available = (mi_col_ori > tile->mi_col_start);
...@@ -688,7 +698,12 @@ static MB_MODE_INFO *set_mb_offsets(AV1_COMMON *const cm, MACROBLOCKD *const xd, ...@@ -688,7 +698,12 @@ static MB_MODE_INFO *set_mb_offsets(AV1_COMMON *const cm, MACROBLOCKD *const xd,
for (y = 0; y < y_mis; ++y) for (y = 0; y < y_mis; ++y)
for (x = !y; x < x_mis; ++x) xd->mi[y * cm->mi_stride + x] = xd->mi[0]; for (x = !y; x < x_mis; ++x) xd->mi[y * cm->mi_stride + x] = xd->mi[0];
#if CONFIG_DEPENDENT_HORZTILES
set_mi_row_col(xd, tile, mi_row, bh, mi_col, bw, cm->mi_rows, cm->mi_cols,
cm->dependent_horz_tiles);
#else
set_mi_row_col(xd, tile, mi_row, bh, mi_col, bw, cm->mi_rows, cm->mi_cols); set_mi_row_col(xd, tile, mi_row, bh, mi_col, bw, cm->mi_rows, cm->mi_cols);
#endif
return &xd->mi[0]->mbmi; return &xd->mi[0]->mbmi;
} }
...@@ -704,7 +719,12 @@ static void set_offsets_topblock(AV1_COMMON *const cm, MACROBLOCKD *const xd, ...@@ -704,7 +719,12 @@ static void set_offsets_topblock(AV1_COMMON *const cm, MACROBLOCKD *const xd,
set_plane_n4(xd, bw, bh); set_plane_n4(xd, bw, bh);
#if CONFIG_DEPENDENT_HORZTILES
set_mi_row_col(xd, tile, mi_row, bh, mi_col, bw, cm->mi_rows, cm->mi_cols,
cm->dependent_horz_tiles);
#else
set_mi_row_col(xd, tile, mi_row, bh, mi_col, bw, cm->mi_rows, cm->mi_cols); set_mi_row_col(xd, tile, mi_row, bh, mi_col, bw, cm->mi_rows, cm->mi_cols);
#endif
av1_setup_dst_planes(xd->plane, get_frame_new_buffer(cm), mi_row, mi_col); av1_setup_dst_planes(xd->plane, get_frame_new_buffer(cm), mi_row, mi_col);
} }
...@@ -2173,8 +2193,14 @@ static void decode_partition(AV1Decoder *const pbi, MACROBLOCKD *const xd, ...@@ -2173,8 +2193,14 @@ static void decode_partition(AV1Decoder *const pbi, MACROBLOCKD *const xd,
xd->mi = cm->mi_grid_visible + offset; xd->mi = cm->mi_grid_visible + offset;
xd->mi[0] = cm->mi + offset; xd->mi[0] = cm->mi + offset;
#if CONFIG_DEPENDENT_HORZTILES
set_mi_row_col(xd, tile, mi_row, mi_size_high[bsize], mi_col,
mi_size_wide[bsize], cm->mi_rows, cm->mi_cols,
cm->dependent_horz_tiles);
#else
set_mi_row_col(xd, tile, mi_row, mi_size_high[bsize], mi_col, set_mi_row_col(xd, tile, mi_row, mi_size_high[bsize], mi_col,
mi_size_wide[bsize], cm->mi_rows, cm->mi_cols); mi_size_wide[bsize], cm->mi_rows, cm->mi_cols);
#endif
set_skip_context(xd, mi_row, mi_col); set_skip_context(xd, mi_row, mi_col);
skip = read_skip(cm, xd, xd->mi[0]->mbmi.segment_id_supertx, r); skip = read_skip(cm, xd, xd->mi[0]->mbmi.segment_id_supertx, r);
if (skip) { if (skip) {
...@@ -2990,6 +3016,13 @@ static void read_tile_info(AV1Decoder *const pbi, ...@@ -2990,6 +3016,13 @@ static void read_tile_info(AV1Decoder *const pbi,
pbi->tile_col_size_bytes = aom_rb_read_literal(rb, 2) + 1; pbi->tile_col_size_bytes = aom_rb_read_literal(rb, 2) + 1;
pbi->tile_size_bytes = aom_rb_read_literal(rb, 2) + 1; pbi->tile_size_bytes = aom_rb_read_literal(rb, 2) + 1;
} }
#if CONFIG_DEPENDENT_HORZTILES
if (cm->tile_rows <= 1)
cm->dependent_horz_tiles = aom_rb_read_bit(rb);
else
cm->dependent_horz_tiles = 0;
#endif
#else #else
int min_log2_tile_cols, max_log2_tile_cols, max_ones; int min_log2_tile_cols, max_log2_tile_cols, max_ones;
av1_get_tile_n_bits(cm->mi_cols, &min_log2_tile_cols, &max_log2_tile_cols);