Commit 2dbaa4f4 authored by Ronald S. Bultje's avatar Ronald S. Bultje

Change above/left_context to use an 8x8 basis.

Output changes slightly because of a minor bug in (at least) the sb32x16
block2above tx16x16 tables that previously existed in vp9_blockd.c.

Change-Id: I624af28ac200a8322d64454cf05c79e9502968cc
parent 7f8cbda3
...@@ -57,19 +57,20 @@ void vp9_free_frame_buffers(VP9_COMMON *oci) { ...@@ -57,19 +57,20 @@ void vp9_free_frame_buffers(VP9_COMMON *oci) {
vp8_yv12_de_alloc_frame_buffer(&oci->temp_scale_frame); vp8_yv12_de_alloc_frame_buffer(&oci->temp_scale_frame);
vp8_yv12_de_alloc_frame_buffer(&oci->post_proc_buffer); vp8_yv12_de_alloc_frame_buffer(&oci->post_proc_buffer);
vpx_free(oci->above_context);
vpx_free(oci->mip); vpx_free(oci->mip);
vpx_free(oci->prev_mip); vpx_free(oci->prev_mip);
vpx_free(oci->above_seg_context); vpx_free(oci->above_seg_context);
oci->above_context = 0; vpx_free(oci->above_context[0]);
for (i = 0; i < MAX_MB_PLANE; i++)
oci->above_context[i] = 0;
oci->mip = 0; oci->mip = 0;
oci->prev_mip = 0; oci->prev_mip = 0;
oci->above_seg_context = 0; oci->above_seg_context = 0;
} }
int vp9_alloc_frame_buffers(VP9_COMMON *oci, int width, int height) { int vp9_alloc_frame_buffers(VP9_COMMON *oci, int width, int height) {
int i; int i, mb_cols;
// Our internal buffers are always multiples of 16 // Our internal buffers are always multiples of 16
const int aligned_width = multiple16(width); const int aligned_width = multiple16(width);
...@@ -137,13 +138,18 @@ int vp9_alloc_frame_buffers(VP9_COMMON *oci, int width, int height) { ...@@ -137,13 +138,18 @@ int vp9_alloc_frame_buffers(VP9_COMMON *oci, int width, int height) {
oci->prev_mi = oci->prev_mip + oci->mode_info_stride + 1; oci->prev_mi = oci->prev_mip + oci->mode_info_stride + 1;
oci->above_context = // FIXME(jkoleszar): allocate subsampled arrays for U/V once subsampling
vpx_calloc(sizeof(ENTROPY_CONTEXT_PLANES) * mb_cols_aligned_to_sb(oci), 1); // information is exposed at this level
mb_cols = mb_cols_aligned_to_sb(oci);
if (!oci->above_context) { oci->above_context[0] = vpx_calloc(sizeof(ENTROPY_CONTEXT) * 12 * mb_cols, 1);
if (!oci->above_context[0]) {
vp9_free_frame_buffers(oci); vp9_free_frame_buffers(oci);
return 1; return 1;
} }
oci->above_context[1] =
oci->above_context[0] + sizeof(ENTROPY_CONTEXT) * 4 * mb_cols;
oci->above_context[2] =
oci->above_context[1] + sizeof(ENTROPY_CONTEXT) * 4 * mb_cols;
oci->above_seg_context = oci->above_seg_context =
vpx_calloc(sizeof(PARTITION_CONTEXT) * mb_cols_aligned_to_sb(oci), 1); vpx_calloc(sizeof(PARTITION_CONTEXT) * mb_cols_aligned_to_sb(oci), 1);
......
This diff is collapsed.
...@@ -48,11 +48,6 @@ typedef enum { ...@@ -48,11 +48,6 @@ typedef enum {
} PLANE_TYPE; } PLANE_TYPE;
typedef char ENTROPY_CONTEXT; typedef char ENTROPY_CONTEXT;
typedef struct {
ENTROPY_CONTEXT y1[4];
ENTROPY_CONTEXT u[2];
ENTROPY_CONTEXT v[2];
} ENTROPY_CONTEXT_PLANES;
typedef char PARTITION_CONTEXT; typedef char PARTITION_CONTEXT;
...@@ -329,6 +324,8 @@ struct macroblockd_plane { ...@@ -329,6 +324,8 @@ struct macroblockd_plane {
struct buf_2d dst; struct buf_2d dst;
struct buf_2d pre[2]; struct buf_2d pre[2];
int16_t *dequant; int16_t *dequant;
ENTROPY_CONTEXT *above_context;
ENTROPY_CONTEXT *left_context;
}; };
#define BLOCK_OFFSET(x, i, n) ((x) + (i) * (n)) #define BLOCK_OFFSET(x, i, n) ((x) + (i) * (n))
...@@ -354,10 +351,6 @@ typedef struct macroblockd { ...@@ -354,10 +351,6 @@ typedef struct macroblockd {
int left_available; int left_available;
int right_available; int right_available;
/* Y,U,V */
ENTROPY_CONTEXT_PLANES *above_context;
ENTROPY_CONTEXT_PLANES *left_context;
// partition contexts // partition contexts
PARTITION_CONTEXT *above_seg_context; PARTITION_CONTEXT *above_seg_context;
PARTITION_CONTEXT *left_seg_context; PARTITION_CONTEXT *left_seg_context;
...@@ -546,21 +539,6 @@ static TX_TYPE txfm_map(B_PREDICTION_MODE bmode) { ...@@ -546,21 +539,6 @@ static TX_TYPE txfm_map(B_PREDICTION_MODE bmode) {
} }
} }
extern const uint8_t vp9_block2left[TX_SIZE_MAX_MB][24];
extern const uint8_t vp9_block2above[TX_SIZE_MAX_MB][24];
extern const uint8_t vp9_block2left_sb[TX_SIZE_MAX_SB][96];
extern const uint8_t vp9_block2above_sb[TX_SIZE_MAX_SB][96];
extern const uint8_t vp9_block2left_sb64[TX_SIZE_MAX_SB][384];
extern const uint8_t vp9_block2above_sb64[TX_SIZE_MAX_SB][384];
extern const uint8_t vp9_block2left_sb16x32[TX_SIZE_MAX_MB][48];
extern const uint8_t vp9_block2above_sb16x32[TX_SIZE_MAX_MB][48];
extern const uint8_t vp9_block2left_sb32x16[TX_SIZE_MAX_MB][48];
extern const uint8_t vp9_block2above_sb32x16[TX_SIZE_MAX_MB][48];
extern const uint8_t vp9_block2left_sb32x64[TX_SIZE_MAX_SB][192];
extern const uint8_t vp9_block2above_sb32x64[TX_SIZE_MAX_SB][192];
extern const uint8_t vp9_block2left_sb64x32[TX_SIZE_MAX_SB][192];
extern const uint8_t vp9_block2above_sb64x32[TX_SIZE_MAX_SB][192];
#define USE_ADST_FOR_I16X16_8X8 1 #define USE_ADST_FOR_I16X16_8X8 1
#define USE_ADST_FOR_I16X16_4X4 1 #define USE_ADST_FOR_I16X16_4X4 1
#define USE_ADST_FOR_I8X8_4X4 1 #define USE_ADST_FOR_I8X8_4X4 1
......
...@@ -119,10 +119,15 @@ void vp9_adapt_coef_probs(struct VP9Common *); ...@@ -119,10 +119,15 @@ void vp9_adapt_coef_probs(struct VP9Common *);
static INLINE void vp9_reset_sb_tokens_context(MACROBLOCKD* const xd, static INLINE void vp9_reset_sb_tokens_context(MACROBLOCKD* const xd,
BLOCK_SIZE_TYPE bsize) { BLOCK_SIZE_TYPE bsize) {
/* Clear entropy contexts */ /* Clear entropy contexts */
const int bw = 1 << (b_width_log2(bsize) - 2); const int bw = 1 << b_width_log2(bsize);
const int bh = 1 << (b_height_log2(bsize) - 2); const int bh = 1 << b_height_log2(bsize);
vpx_memset(xd->above_context, 0, sizeof(ENTROPY_CONTEXT_PLANES) * bw); int i;
vpx_memset(xd->left_context, 0, sizeof(ENTROPY_CONTEXT_PLANES) * bh); for (i = 0; i < MAX_MB_PLANE; i++) {
vpx_memset(xd->plane[i].above_context, 0,
sizeof(ENTROPY_CONTEXT) * bw >> xd->plane[i].subsampling_x);
vpx_memset(xd->plane[i].left_context, 0,
sizeof(ENTROPY_CONTEXT) * bh >> xd->plane[i].subsampling_y);
}
} }
extern const int vp9_coef_bands8x8[64]; extern const int vp9_coef_bands8x8[64];
......
...@@ -253,8 +253,8 @@ typedef struct VP9Common { ...@@ -253,8 +253,8 @@ typedef struct VP9Common {
int ref_frame_sign_bias[MAX_REF_FRAMES]; /* Two state 0, 1 */ int ref_frame_sign_bias[MAX_REF_FRAMES]; /* Two state 0, 1 */
/* Y,U,V */ /* Y,U,V */
ENTROPY_CONTEXT_PLANES *above_context; /* row of context for each plane */ ENTROPY_CONTEXT *above_context[MAX_MB_PLANE];
ENTROPY_CONTEXT_PLANES left_context[4]; /* (up to) 4 contexts "" */ ENTROPY_CONTEXT left_context[MAX_MB_PLANE][16];
// partition contexts // partition contexts
PARTITION_CONTEXT *above_seg_context; PARTITION_CONTEXT *above_seg_context;
......
...@@ -742,6 +742,7 @@ static void set_offsets(VP9D_COMP *pbi, BLOCK_SIZE_TYPE bsize, ...@@ -742,6 +742,7 @@ static void set_offsets(VP9D_COMP *pbi, BLOCK_SIZE_TYPE bsize,
const int bw = 1 << mi_width_log2(bsize); const int bw = 1 << mi_width_log2(bsize);
VP9_COMMON *const cm = &pbi->common; VP9_COMMON *const cm = &pbi->common;
MACROBLOCKD *const xd = &pbi->mb; MACROBLOCKD *const xd = &pbi->mb;
int i;
const int mi_idx = mi_row * cm->mode_info_stride + mi_col; const int mi_idx = mi_row * cm->mode_info_stride + mi_col;
const YV12_BUFFER_CONFIG *dst_fb = &cm->yv12_fb[cm->new_fb_idx]; const YV12_BUFFER_CONFIG *dst_fb = &cm->yv12_fb[cm->new_fb_idx];
...@@ -754,8 +755,12 @@ static void set_offsets(VP9D_COMP *pbi, BLOCK_SIZE_TYPE bsize, ...@@ -754,8 +755,12 @@ static void set_offsets(VP9D_COMP *pbi, BLOCK_SIZE_TYPE bsize,
xd->mode_info_context->mbmi.sb_type = bsize; xd->mode_info_context->mbmi.sb_type = bsize;
xd->prev_mode_info_context = cm->prev_mi + mi_idx; xd->prev_mode_info_context = cm->prev_mi + mi_idx;
xd->above_context = cm->above_context + (mi_col >> CONFIG_SB8X8); for (i = 0; i < MAX_MB_PLANE; i++) {
xd->left_context = cm->left_context + ((mi_row >> CONFIG_SB8X8) & 3); xd->plane[i].above_context = cm->above_context[i] +
(mi_col * 4 >> (xd->plane[i].subsampling_x + CONFIG_SB8X8));
xd->plane[i].left_context = cm->left_context[i] +
(((mi_row * 4 >> CONFIG_SB8X8) & 15) >> xd->plane[i].subsampling_y);
}
xd->above_seg_context = cm->above_seg_context + (mi_col >> CONFIG_SB8X8); xd->above_seg_context = cm->above_seg_context + (mi_col >> CONFIG_SB8X8);
xd->left_seg_context = cm->left_seg_context + ((mi_row >> CONFIG_SB8X8) & 3); xd->left_seg_context = cm->left_seg_context + ((mi_row >> CONFIG_SB8X8) & 3);
...@@ -1297,7 +1302,7 @@ static void decode_tile(VP9D_COMP *pbi, vp9_reader *r) { ...@@ -1297,7 +1302,7 @@ static void decode_tile(VP9D_COMP *pbi, vp9_reader *r) {
for (mi_row = pc->cur_tile_mi_row_start; for (mi_row = pc->cur_tile_mi_row_start;
mi_row < pc->cur_tile_mi_row_end; mi_row += (4 << CONFIG_SB8X8)) { mi_row < pc->cur_tile_mi_row_end; mi_row += (4 << CONFIG_SB8X8)) {
// For a SB there are 2 left contexts, each pertaining to a MB row within // For a SB there are 2 left contexts, each pertaining to a MB row within
vpx_memset(pc->left_context, 0, sizeof(pc->left_context)); vpx_memset(&pc->left_context, 0, sizeof(pc->left_context));
vpx_memset(pc->left_seg_context, 0, sizeof(pc->left_seg_context)); vpx_memset(pc->left_seg_context, 0, sizeof(pc->left_seg_context));
for (mi_col = pc->cur_tile_mi_col_start; for (mi_col = pc->cur_tile_mi_col_start;
mi_col < pc->cur_tile_mi_col_end; mi_col += (4 << CONFIG_SB8X8)) { mi_col < pc->cur_tile_mi_col_end; mi_col += (4 << CONFIG_SB8X8)) {
...@@ -1328,8 +1333,10 @@ static void decode_tiles(VP9D_COMP *pbi, ...@@ -1328,8 +1333,10 @@ static void decode_tiles(VP9D_COMP *pbi,
pc->tile_columns = 1 << pc->log2_tile_columns; pc->tile_columns = 1 << pc->log2_tile_columns;
pc->tile_rows = 1 << pc->log2_tile_rows; pc->tile_rows = 1 << pc->log2_tile_rows;
vpx_memset(pc->above_context, 0, // Note: this memset assumes above_context[0], [1] and [2]
sizeof(ENTROPY_CONTEXT_PLANES) * mb_cols_aligned_to_sb(pc)); // are allocated as part of the same buffer.
vpx_memset(pc->above_context[0], 0, sizeof(ENTROPY_CONTEXT) * 4 *
MAX_MB_PLANE * mb_cols_aligned_to_sb(pc));
vpx_memset(pc->above_seg_context, 0, sizeof(PARTITION_CONTEXT) * vpx_memset(pc->above_seg_context, 0, sizeof(PARTITION_CONTEXT) *
mb_cols_aligned_to_sb(pc)); mb_cols_aligned_to_sb(pc));
......
...@@ -106,10 +106,8 @@ DECLARE_ALIGNED(16, extern const uint8_t, vp9_norm[256]); ...@@ -106,10 +106,8 @@ DECLARE_ALIGNED(16, extern const uint8_t, vp9_norm[256]);
static int decode_coefs(VP9D_COMP *dx, const MACROBLOCKD *xd, static int decode_coefs(VP9D_COMP *dx, const MACROBLOCKD *xd,
vp9_reader *r, int block_idx, vp9_reader *r, int block_idx,
PLANE_TYPE type, int seg_eob, int16_t *qcoeff_ptr, PLANE_TYPE type, int seg_eob, int16_t *qcoeff_ptr,
TX_SIZE txfm_size, const int16_t *dq) { TX_SIZE txfm_size, const int16_t *dq,
ENTROPY_CONTEXT* const A0 = (ENTROPY_CONTEXT *) xd->above_context; ENTROPY_CONTEXT *A, ENTROPY_CONTEXT *L) {
ENTROPY_CONTEXT* const L0 = (ENTROPY_CONTEXT *) xd->left_context;
int aidx, lidx;
ENTROPY_CONTEXT above_ec, left_ec; ENTROPY_CONTEXT above_ec, left_ec;
FRAME_CONTEXT *const fc = &dx->common.fc; FRAME_CONTEXT *const fc = &dx->common.fc;
int pt, c = 0, pad, default_eob; int pt, c = 0, pad, default_eob;
...@@ -133,37 +131,14 @@ static int decode_coefs(VP9D_COMP *dx, const MACROBLOCKD *xd, ...@@ -133,37 +131,14 @@ static int decode_coefs(VP9D_COMP *dx, const MACROBLOCKD *xd,
vpx_memset(token_cache, UNKNOWN_TOKEN, sizeof(token_cache)); vpx_memset(token_cache, UNKNOWN_TOKEN, sizeof(token_cache));
#endif #endif
if (xd->mode_info_context->mbmi.sb_type == BLOCK_SIZE_SB64X64) {
aidx = vp9_block2above_sb64[txfm_size][block_idx];
lidx = vp9_block2left_sb64[txfm_size][block_idx];
} else if (xd->mode_info_context->mbmi.sb_type == BLOCK_SIZE_SB64X32) {
aidx = vp9_block2above_sb64x32[txfm_size][block_idx];
lidx = vp9_block2left_sb64x32[txfm_size][block_idx];
} else if (xd->mode_info_context->mbmi.sb_type == BLOCK_SIZE_SB32X64) {
aidx = vp9_block2above_sb32x64[txfm_size][block_idx];
lidx = vp9_block2left_sb32x64[txfm_size][block_idx];
} else if (xd->mode_info_context->mbmi.sb_type == BLOCK_SIZE_SB32X32) {
aidx = vp9_block2above_sb[txfm_size][block_idx];
lidx = vp9_block2left_sb[txfm_size][block_idx];
} else if (xd->mode_info_context->mbmi.sb_type == BLOCK_SIZE_SB32X16) {
aidx = vp9_block2above_sb32x16[txfm_size][block_idx];
lidx = vp9_block2left_sb32x16[txfm_size][block_idx];
} else if (xd->mode_info_context->mbmi.sb_type == BLOCK_SIZE_SB16X32) {
aidx = vp9_block2above_sb16x32[txfm_size][block_idx];
lidx = vp9_block2left_sb16x32[txfm_size][block_idx];
} else {
aidx = vp9_block2above[txfm_size][block_idx];
lidx = vp9_block2left[txfm_size][block_idx];
}
switch (txfm_size) { switch (txfm_size) {
default: default:
case TX_4X4: { case TX_4X4: {
tx_type = (type == PLANE_TYPE_Y_WITH_DC) ? tx_type = (type == PLANE_TYPE_Y_WITH_DC) ?
get_tx_type_4x4(xd, block_idx) : DCT_DCT; get_tx_type_4x4(xd, block_idx) : DCT_DCT;
scan = get_scan_4x4(tx_type); scan = get_scan_4x4(tx_type);
above_ec = A0[aidx] != 0; above_ec = A[0] != 0;
left_ec = L0[lidx] != 0; left_ec = L[0] != 0;
coef_probs = fc->coef_probs_4x4; coef_probs = fc->coef_probs_4x4;
coef_counts = fc->coef_counts_4x4; coef_counts = fc->coef_counts_4x4;
default_eob = 16; default_eob = 16;
...@@ -183,8 +158,8 @@ static int decode_coefs(VP9D_COMP *dx, const MACROBLOCKD *xd, ...@@ -183,8 +158,8 @@ static int decode_coefs(VP9D_COMP *dx, const MACROBLOCKD *xd,
scan = get_scan_8x8(tx_type); scan = get_scan_8x8(tx_type);
coef_probs = fc->coef_probs_8x8; coef_probs = fc->coef_probs_8x8;
coef_counts = fc->coef_counts_8x8; coef_counts = fc->coef_counts_8x8;
above_ec = (A0[aidx] + A0[aidx + 1]) != 0; above_ec = (A[0] + A[1]) != 0;
left_ec = (L0[lidx] + L0[lidx + 1]) != 0; left_ec = (L[0] + L[1]) != 0;
default_eob = 64; default_eob = 64;
#if CONFIG_CODE_ZEROGROUP #if CONFIG_CODE_ZEROGROUP
zpc_probs = &(fc->zpc_probs_8x8); zpc_probs = &(fc->zpc_probs_8x8);
...@@ -202,15 +177,8 @@ static int decode_coefs(VP9D_COMP *dx, const MACROBLOCKD *xd, ...@@ -202,15 +177,8 @@ static int decode_coefs(VP9D_COMP *dx, const MACROBLOCKD *xd,
scan = get_scan_16x16(tx_type); scan = get_scan_16x16(tx_type);
coef_probs = fc->coef_probs_16x16; coef_probs = fc->coef_probs_16x16;
coef_counts = fc->coef_counts_16x16; coef_counts = fc->coef_counts_16x16;
if (type == PLANE_TYPE_UV) { above_ec = (A[0] + A[1] + A[2] + A[3]) != 0;
ENTROPY_CONTEXT *A1 = (ENTROPY_CONTEXT *) (xd->above_context + 1); left_ec = (L[0] + L[1] + L[2] + L[3]) != 0;
ENTROPY_CONTEXT *L1 = (ENTROPY_CONTEXT *) (xd->left_context + 1);
above_ec = (A0[aidx] + A0[aidx + 1] + A1[aidx] + A1[aidx + 1]) != 0;
left_ec = (L0[lidx] + L0[lidx + 1] + L1[lidx] + L1[lidx + 1]) != 0;
} else {
above_ec = (A0[aidx] + A0[aidx + 1] + A0[aidx + 2] + A0[aidx + 3]) != 0;
left_ec = (L0[lidx] + L0[lidx + 1] + L0[lidx + 2] + L0[lidx + 3]) != 0;
}
default_eob = 256; default_eob = 256;
#if CONFIG_CODE_ZEROGROUP #if CONFIG_CODE_ZEROGROUP
zpc_probs = &(fc->zpc_probs_16x16); zpc_probs = &(fc->zpc_probs_16x16);
...@@ -222,25 +190,8 @@ static int decode_coefs(VP9D_COMP *dx, const MACROBLOCKD *xd, ...@@ -222,25 +190,8 @@ static int decode_coefs(VP9D_COMP *dx, const MACROBLOCKD *xd,
scan = vp9_default_zig_zag1d_32x32; scan = vp9_default_zig_zag1d_32x32;
coef_probs = fc->coef_probs_32x32; coef_probs = fc->coef_probs_32x32;
coef_counts = fc->coef_counts_32x32; coef_counts = fc->coef_counts_32x32;
if (type == PLANE_TYPE_UV) { above_ec = (A[0] + A[1] + A[2] + A[3] + A[4] + A[5] + A[6] + A[7]) != 0;
ENTROPY_CONTEXT *A1 = (ENTROPY_CONTEXT *) (xd->above_context + 1); left_ec = (L[0] + L[1] + L[2] + L[3] + L[4] + L[5] + L[6] + L[7]) != 0;
ENTROPY_CONTEXT *L1 = (ENTROPY_CONTEXT *) (xd->left_context + 1);
ENTROPY_CONTEXT *A2 = (ENTROPY_CONTEXT *) (xd->above_context + 2);
ENTROPY_CONTEXT *L2 = (ENTROPY_CONTEXT *) (xd->left_context + 2);
ENTROPY_CONTEXT *A3 = (ENTROPY_CONTEXT *) (xd->above_context + 3);
ENTROPY_CONTEXT *L3 = (ENTROPY_CONTEXT *) (xd->left_context + 3);
above_ec = (A0[aidx] + A0[aidx + 1] + A1[aidx] + A1[aidx + 1] +
A2[aidx] + A2[aidx + 1] + A3[aidx] + A3[aidx + 1]) != 0;
left_ec = (L0[lidx] + L0[lidx + 1] + L1[lidx] + L1[lidx + 1] +
L2[lidx] + L2[lidx + 1] + L3[lidx] + L3[lidx + 1]) != 0;
} else {
ENTROPY_CONTEXT *A1 = (ENTROPY_CONTEXT *) (xd->above_context + 1);
ENTROPY_CONTEXT *L1 = (ENTROPY_CONTEXT *) (xd->left_context + 1);
above_ec = (A0[aidx] + A0[aidx + 1] + A0[aidx + 2] + A0[aidx + 3] +
A1[aidx] + A1[aidx + 1] + A1[aidx + 2] + A1[aidx + 3]) != 0;
left_ec = (L0[lidx] + L0[lidx + 1] + L0[lidx + 2] + L0[lidx + 3] +
L1[lidx] + L1[lidx + 1] + L1[lidx + 2] + L1[lidx + 3]) != 0;
}
default_eob = 1024; default_eob = 1024;
#if CONFIG_CODE_ZEROGROUP #if CONFIG_CODE_ZEROGROUP
zpc_probs = &fc->zpc_probs_32x32; zpc_probs = &fc->zpc_probs_32x32;
...@@ -381,33 +332,10 @@ SKIP_START: ...@@ -381,33 +332,10 @@ SKIP_START:
coef_counts[type][ref][get_coef_band(scan, txfm_size, c)] coef_counts[type][ref][get_coef_band(scan, txfm_size, c)]
[pt][DCT_EOB_TOKEN]++; [pt][DCT_EOB_TOKEN]++;
A0[aidx] = L0[lidx] = c > 0; for (pt = 0; pt < (1 << txfm_size); pt++) {
if (txfm_size >= TX_8X8) { A[pt] = L[pt] = c > 0;
A0[aidx + 1] = L0[lidx + 1] = A0[aidx];
if (txfm_size >= TX_16X16) {
if (type == PLANE_TYPE_UV) {
ENTROPY_CONTEXT *A1 = (ENTROPY_CONTEXT *) (xd->above_context + 1);
ENTROPY_CONTEXT *L1 = (ENTROPY_CONTEXT *) (xd->left_context + 1);
A1[aidx] = A1[aidx + 1] = L1[lidx] = L1[lidx + 1] = A0[aidx];
if (txfm_size >= TX_32X32) {
ENTROPY_CONTEXT *A2 = (ENTROPY_CONTEXT *) (xd->above_context + 2);
ENTROPY_CONTEXT *L2 = (ENTROPY_CONTEXT *) (xd->left_context + 2);
ENTROPY_CONTEXT *A3 = (ENTROPY_CONTEXT *) (xd->above_context + 3);
ENTROPY_CONTEXT *L3 = (ENTROPY_CONTEXT *) (xd->left_context + 3);
A2[aidx] = A2[aidx + 1] = A3[aidx] = A3[aidx + 1] = A0[aidx];
L2[lidx] = L2[lidx + 1] = L3[lidx] = L3[lidx + 1] = A0[aidx];
}
} else {
A0[aidx + 2] = A0[aidx + 3] = L0[lidx + 2] = L0[lidx + 3] = A0[aidx];
if (txfm_size >= TX_32X32) {
ENTROPY_CONTEXT *A1 = (ENTROPY_CONTEXT *) (xd->above_context + 1);
ENTROPY_CONTEXT *L1 = (ENTROPY_CONTEXT *) (xd->left_context + 1);
A1[aidx] = A1[aidx + 1] = A1[aidx + 2] = A1[aidx + 3] = A0[aidx];
L1[lidx] = L1[lidx + 1] = L1[lidx + 2] = L1[lidx + 3] = A0[aidx];
}
}
}
} }
return c; return c;
} }
...@@ -436,11 +364,17 @@ static void decode_block(int plane, int block, ...@@ -436,11 +364,17 @@ static void decode_block(int plane, int block,
const TX_SIZE ss_tx_size = ss_txfrm_size / 2; const TX_SIZE ss_tx_size = ss_txfrm_size / 2;
const int seg_eob = get_eob(arg->xd, segment_id, 16 << ss_txfrm_size); const int seg_eob = get_eob(arg->xd, segment_id, 16 << ss_txfrm_size);
int16_t* const qcoeff_base = arg->xd->plane[plane].qcoeff; int16_t* const qcoeff_base = arg->xd->plane[plane].qcoeff;
const int off = block >> ss_txfrm_size;
const int mod = bw - ss_tx_size - arg->xd->plane[plane].subsampling_x;
const int aoff = (off & ((1 << mod) - 1)) << ss_tx_size;
const int loff = (off >> mod) << ss_tx_size;
const int eob = decode_coefs(arg->pbi, arg->xd, arg->r, old_block_idx, const int eob = decode_coefs(arg->pbi, arg->xd, arg->r, old_block_idx,
arg->xd->plane[plane].plane_type, seg_eob, arg->xd->plane[plane].plane_type, seg_eob,
BLOCK_OFFSET(qcoeff_base, block, 16), BLOCK_OFFSET(qcoeff_base, block, 16),
ss_tx_size, arg->xd->plane[plane].dequant); ss_tx_size, arg->xd->plane[plane].dequant,
arg->xd->plane[plane].above_context + aoff,
arg->xd->plane[plane].left_context + loff);
arg->xd->plane[plane].eobs[block] = eob; arg->xd->plane[plane].eobs[block] = eob;
arg->eobtotal[0] += eob; arg->eobtotal[0] += eob;
...@@ -461,9 +395,14 @@ static int decode_coefs_4x4(VP9D_COMP *dx, MACROBLOCKD *xd, ...@@ -461,9 +395,14 @@ static int decode_coefs_4x4(VP9D_COMP *dx, MACROBLOCKD *xd,
vp9_reader *r, vp9_reader *r,
PLANE_TYPE type, int i, int seg_eob) { PLANE_TYPE type, int i, int seg_eob) {
const struct plane_block_idx pb_idx = plane_block_idx(16, i); const struct plane_block_idx pb_idx = plane_block_idx(16, i);
const int mod = 2 - xd->plane[pb_idx.plane].subsampling_x;
const int aoff = pb_idx.block & ((1 << mod) - 1);
const int loff = pb_idx.block >> mod;
ENTROPY_CONTEXT *A = xd->plane[pb_idx.plane].above_context;
ENTROPY_CONTEXT *L = xd->plane[pb_idx.plane].left_context;
const int c = decode_coefs(dx, xd, r, i, type, seg_eob, const int c = decode_coefs(dx, xd, r, i, type, seg_eob,
BLOCK_OFFSET(xd->plane[pb_idx.plane].qcoeff, pb_idx.block, 16), TX_4X4, BLOCK_OFFSET(xd->plane[pb_idx.plane].qcoeff, pb_idx.block, 16), TX_4X4,
xd->plane[pb_idx.plane].dequant); xd->plane[pb_idx.plane].dequant, A + aoff, L + loff);
xd->plane[pb_idx.plane].eobs[pb_idx.block] = c; xd->plane[pb_idx.plane].eobs[pb_idx.block] = c;
return c; return c;
} }
......
...@@ -574,10 +574,15 @@ static void set_offsets(VP9_COMP *cpi, ...@@ -574,10 +574,15 @@ static void set_offsets(VP9_COMP *cpi,
const int mb_row = mi_row >> CONFIG_SB8X8; const int mb_row = mi_row >> CONFIG_SB8X8;
const int mb_col = mi_col >> CONFIG_SB8X8; const int mb_col = mi_col >> CONFIG_SB8X8;
const int idx_map = mb_row * cm->mb_cols + mb_col; const int idx_map = mb_row * cm->mb_cols + mb_col;
int i;
// entropy context structures // entropy context structures
xd->above_context = cm->above_context + mb_col; for (i = 0; i < MAX_MB_PLANE; i++) {
xd->left_context = cm->left_context + (mb_row & 3); xd->plane[i].above_context = cm->above_context[i] +
(mi_col * 4 >> (CONFIG_SB8X8 + xd->plane[i].subsampling_x));
xd->plane[i].left_context = cm->left_context[i] +
(((mi_row * 4 >> CONFIG_SB8X8) & 15) >> xd->plane[i].subsampling_y);
}
// partition contexts // partition contexts
xd->above_seg_context = cm->above_seg_context + mb_col; xd->above_seg_context = cm->above_seg_context + mb_col;
...@@ -983,22 +988,27 @@ static void encode_sb_row(VP9_COMP *cpi, ...@@ -983,22 +988,27 @@ static void encode_sb_row(VP9_COMP *cpi,
int mi_col, pl; int mi_col, pl;
// Initialize the left context for the new SB row // Initialize the left context for the new SB row
vpx_memset(cm->left_context, 0, sizeof(cm->left_context)); vpx_memset(&cm->left_context, 0, sizeof(cm->left_context));
vpx_memset(cm->left_seg_context, 0, sizeof(cm->left_seg_context)); vpx_memset(cm->left_seg_context, 0, sizeof(cm->left_seg_context));
// Code each SB in the row // Code each SB in the row
for (mi_col = cm->cur_tile_mi_col_start; for (mi_col = cm->cur_tile_mi_col_start;
mi_col < cm->cur_tile_mi_col_end; mi_col += (4 << CONFIG_SB8X8)) { mi_col < cm->cur_tile_mi_col_end; mi_col += (4 << CONFIG_SB8X8)) {
int i; int i, p;
BLOCK_SIZE_TYPE sb_partitioning[4]; BLOCK_SIZE_TYPE sb_partitioning[4];
int sb64_rate = 0, sb64_dist = 0; int sb64_rate = 0, sb64_dist = 0;
int sb64_skip = 0; int sb64_skip = 0;
ENTROPY_CONTEXT_PLANES l[4], a[4]; ENTROPY_CONTEXT l[16 * MAX_MB_PLANE], a[16 * MAX_MB_PLANE];
PARTITION_CONTEXT seg_l[4], seg_a[4]; PARTITION_CONTEXT seg_l[4], seg_a[4];
TOKENEXTRA *tp_orig = *tp; TOKENEXTRA *tp_orig = *tp;
memcpy(&a, cm->above_context + (mi_col >> CONFIG_SB8X8), sizeof(a)); for (p = 0; p < MAX_MB_PLANE; p++) {
memcpy(&l, cm->left_context, sizeof(l)); memcpy(a + 16 * p, cm->above_context[p] +
(mi_col * 4 >> (CONFIG_SB8X8 + xd->plane[p].subsampling_x)),
sizeof(ENTROPY_CONTEXT) * 16 >> xd->plane[p].subsampling_x);
memcpy(l + 16 * p, cm->left_context[p],
sizeof(ENTROPY_CONTEXT) * 16 >> xd->plane[p].subsampling_y);
}
memcpy(&seg_a, cm->above_seg_context + (mi_col >> CONFIG_SB8X8), memcpy(&seg_a, cm->above_seg_context + (mi_col >> CONFIG_SB8X8),
sizeof(seg_a)); sizeof(seg_a));
memcpy(&seg_l, cm->left_seg_context, sizeof(seg_l)); memcpy(&seg_l, cm->left_seg_context, sizeof(seg_l));
...@@ -1009,7 +1019,7 @@ static void encode_sb_row(VP9_COMP *cpi, ...@@ -1009,7 +1019,7 @@ static void encode_sb_row(VP9_COMP *cpi,
int splitmodes_used = 0; int splitmodes_used = 0;
int sb32_skip = 0; int sb32_skip = 0;
int j; int j;
ENTROPY_CONTEXT_PLANES l2[2], a2[2]; ENTROPY_CONTEXT l2[8 * MAX_MB_PLANE], a2[8 * MAX_MB_PLANE];
if (mi_row + y_idx >= cm->mi_rows || mi_col + x_idx >= cm->mi_cols) if (mi_row + y_idx >= cm->mi_rows || mi_col + x_idx >= cm->mi_cols)
continue; continue;
...@@ -1017,9 +1027,18 @@ static void encode_sb_row(VP9_COMP *cpi, ...@@ -1017,9 +1027,18 @@ static void encode_sb_row(VP9_COMP *cpi,
xd->sb_index = i; xd->sb_index = i;
/* Function should not modify L & A contexts; save and restore on exit */ /* Function should not modify L & A contexts; save and restore on exit */
vpx_memcpy(l2, cm->left_context + (y_idx >> CONFIG_SB8X8), sizeof(l2)); for (p = 0; p < MAX_MB_PLANE; p++) {
vpx_memcpy(a2, cm->above_context + ((mi_col + x_idx) >> CONFIG_SB8X8), vpx_memcpy(l2 + 8 * p,
sizeof(a2)); cm->left_context[p] +
(y_idx * 4 >> (CONFIG_SB8X8 +
xd->plane[p].subsampling_y)),
sizeof(ENTROPY_CONTEXT) * 8 >> xd->plane[p].subsampling_y);
vpx_memcpy(a2 + 8 * p,
cm->above_context[p] +
((mi_col + x_idx) * 4 >> (CONFIG_SB8X8 +
xd->plane[p].subsampling_x)),
sizeof(ENTROPY_CONTEXT) * 8 >> xd->plane[p].subsampling_x);
}
/* Encode MBs in raster order within the SB */ /* Encode MBs in raster order within the SB */
sb_partitioning[i] = BLOCK_SIZE_MB16X16; sb_partitioning[i] = BLOCK_SIZE_MB16X16;
...@@ -1052,9 +1071,18 @@ static void encode_sb_row(VP9_COMP *cpi, ...@@ -1052,9 +1071,18 @@ static void encode_sb_row(VP9_COMP *cpi,
} }
/* Restore L & A coding context to those in place on entry */ /* Restore L & A coding context to those in place on entry */
vpx_memcpy(cm->left_context + (y_idx >> CONFIG_SB8X8), l2, sizeof(l2)); for (p = 0; p < MAX_MB_PLANE; p++) {
vpx_memcpy(cm->above_context + ((mi_col + x_idx) >> CONFIG_SB8X8), a2, vpx_memcpy(cm->left_context[p] +
sizeof(a2)); (y_idx * 4 >> (CONFIG_SB8X8 +
xd->plane[p].subsampling_y)),
l2 + 8 * p,
sizeof(ENTROPY_CONTEXT) * 8 >> xd->plane[p].subsampling_y);
vpx_memcpy(cm->above_context[p] +
((mi_col + x_idx) * 4 >> (CONFIG_SB8X8 +
xd->plane[p].subsampling_x)),
a2 + 8 * p,
sizeof(ENTROPY_CONTEXT) * 8 >> xd->plane[p].subsampling_x);