summaryrefslogtreecommitdiff
path: root/vp9/encoder/vp9_bitstream.c
diff options
context:
space:
mode:
Diffstat (limited to 'vp9/encoder/vp9_bitstream.c')
-rw-r--r--vp9/encoder/vp9_bitstream.c128
1 files changed, 78 insertions, 50 deletions
diff --git a/vp9/encoder/vp9_bitstream.c b/vp9/encoder/vp9_bitstream.c
index c5f2a70c6..8d6cfe96c 100644
--- a/vp9/encoder/vp9_bitstream.c
+++ b/vp9/encoder/vp9_bitstream.c
@@ -43,11 +43,11 @@ int intra_mode_stats[VP9_KF_BINTRAMODES]
[VP9_KF_BINTRAMODES]
[VP9_KF_BINTRAMODES];
vp9_coeff_stats tree_update_hist_4x4[BLOCK_TYPES_4X4];
-vp9_coeff_stats hybrid_tree_update_hist_4x4[BLOCK_TYPES_4X4];
+vp9_coeff_stats hybrid_tree_update_hist_4x4[BLOCK_TYPES_4X4_HYBRID];
vp9_coeff_stats tree_update_hist_8x8[BLOCK_TYPES_8X8];
-vp9_coeff_stats hybrid_tree_update_hist_8x8[BLOCK_TYPES_8X8];
+vp9_coeff_stats hybrid_tree_update_hist_8x8[BLOCK_TYPES_8X8_HYBRID];
vp9_coeff_stats tree_update_hist_16x16[BLOCK_TYPES_16X16];
-vp9_coeff_stats hybrid_tree_update_hist_16x16[BLOCK_TYPES_16X16];
+vp9_coeff_stats hybrid_tree_update_hist_16x16[BLOCK_TYPES_16X16_HYBRID];
vp9_coeff_stats tree_update_hist_32x32[BLOCK_TYPES_32X32];
extern unsigned int active_section;
@@ -1089,14 +1089,15 @@ static void write_modes_b(VP9_COMP *cpi, MODE_INFO *m, vp9_writer *bc,
}
static void write_modes(VP9_COMP *cpi, vp9_writer* const bc,
- TOKENEXTRA **tok) {
+ TOKENEXTRA **tok, TOKENEXTRA *tok_end) {
VP9_COMMON *const c = &cpi->common;
const int mis = c->mode_info_stride;
- MODE_INFO *m, *m_ptr = c->mi + c->cur_tile_mb_col_start;
+ MODE_INFO *m, *m_ptr = c->mi;
int i, mb_row, mb_col;
- TOKENEXTRA *tok_end = *tok + cpi->tok_count;
- for (mb_row = 0; mb_row < c->mb_rows; mb_row += 4, m_ptr += 4 * mis) {
+ m_ptr += c->cur_tile_mb_col_start + c->cur_tile_mb_row_start * mis;
+ for (mb_row = c->cur_tile_mb_row_start;
+ mb_row < c->cur_tile_mb_row_end; mb_row += 4, m_ptr += 4 * mis) {
m = m_ptr;
for (mb_col = c->cur_tile_mb_col_start;
mb_col < c->cur_tile_mb_col_end; mb_col += 4, m += 4) {
@@ -1186,7 +1187,7 @@ static void build_tree_distribution(vp9_coeff_probs *coef_probs,
for (i = 0; i < block_types; ++i) {
for (j = 0; j < COEF_BANDS; ++j) {
for (k = 0; k < PREV_COEF_CONTEXTS; ++k) {
- if (k >= 3 && ((i == 0 && j == 1) || (i > 0 && j == 0)))
+ if (k >= 3 && j == 0)
continue;
vp9_tree_probs_from_distribution(MAX_ENTROPY_TOKENS,
vp9_coef_encodings, vp9_coef_tree,
@@ -1215,7 +1216,8 @@ static void build_coeff_contexts(VP9_COMP *cpi) {
#ifdef ENTROPY_STATS
cpi, hybrid_context_counters_4x4,
#endif
- cpi->frame_hybrid_branch_ct_4x4, BLOCK_TYPES_4X4);
+ cpi->frame_hybrid_branch_ct_4x4,
+ BLOCK_TYPES_4X4_HYBRID);
build_tree_distribution(cpi->frame_coef_probs_8x8,
cpi->coef_counts_8x8,
#ifdef ENTROPY_STATS
@@ -1227,7 +1229,8 @@ static void build_coeff_contexts(VP9_COMP *cpi) {
#ifdef ENTROPY_STATS
cpi, hybrid_context_counters_8x8,
#endif
- cpi->frame_hybrid_branch_ct_8x8, BLOCK_TYPES_8X8);
+ cpi->frame_hybrid_branch_ct_8x8,
+ BLOCK_TYPES_8X8_HYBRID);
build_tree_distribution(cpi->frame_coef_probs_16x16,
cpi->coef_counts_16x16,
#ifdef ENTROPY_STATS
@@ -1239,7 +1242,8 @@ static void build_coeff_contexts(VP9_COMP *cpi) {
#ifdef ENTROPY_STATS
cpi, hybrid_context_counters_16x16,
#endif
- cpi->frame_hybrid_branch_ct_16x16, BLOCK_TYPES_16X16);
+ cpi->frame_hybrid_branch_ct_16x16,
+ BLOCK_TYPES_16X16_HYBRID);
build_tree_distribution(cpi->frame_coef_probs_32x32,
cpi->coef_counts_32x32,
#ifdef ENTROPY_STATS
@@ -1265,7 +1269,7 @@ static void update_coef_probs_common(vp9_writer* const bc,
/* dry run to see if there is any udpate at all needed */
savings = 0;
for (i = 0; i < block_types; ++i) {
- for (j = !i; j < COEF_BANDS; ++j) {
+ for (j = 0; j < COEF_BANDS; ++j) {
int prev_coef_savings[ENTROPY_NODES] = {0};
for (k = 0; k < PREV_COEF_CONTEXTS; ++k) {
for (t = 0; t < ENTROPY_NODES; ++t) {
@@ -1274,7 +1278,7 @@ static void update_coef_probs_common(vp9_writer* const bc,
const vp9_prob upd = COEF_UPDATE_PROB;
int s = prev_coef_savings[t];
int u = 0;
- if (k >= 3 && ((i == 0 && j == 1) || (i > 0 && j == 0)))
+ if (k >= 3 && j == 0)
continue;
#if defined(SEARCH_NEWP)
s = prob_diff_update_savings_search(
@@ -1309,7 +1313,7 @@ static void update_coef_probs_common(vp9_writer* const bc,
} else {
vp9_write_bit(bc, 1);
for (i = 0; i < block_types; ++i) {
- for (j = !i; j < COEF_BANDS; ++j) {
+ for (j = 0; j < COEF_BANDS; ++j) {
int prev_coef_savings[ENTROPY_NODES] = {0};
for (k = 0; k < PREV_COEF_CONTEXTS; ++k) {
// calc probs and branch cts for this frame only
@@ -1319,7 +1323,7 @@ static void update_coef_probs_common(vp9_writer* const bc,
const vp9_prob upd = COEF_UPDATE_PROB;
int s = prev_coef_savings[t];
int u = 0;
- if (k >= 3 && ((i == 0 && j == 1) || (i > 0 && j == 0)))
+ if (k >= 3 && j == 0)
continue;
#if defined(SEARCH_NEWP)
@@ -1376,7 +1380,7 @@ static void update_coef_probs(VP9_COMP* const cpi, vp9_writer* const bc) {
cpi->frame_hybrid_coef_probs_4x4,
cpi->common.fc.hybrid_coef_probs_4x4,
cpi->frame_hybrid_branch_ct_4x4,
- BLOCK_TYPES_4X4);
+ BLOCK_TYPES_4X4_HYBRID);
/* do not do this if not even allowed */
if (cpi->common.txfm_mode != ONLY_4X4) {
@@ -1398,7 +1402,7 @@ static void update_coef_probs(VP9_COMP* const cpi, vp9_writer* const bc) {
cpi->frame_hybrid_coef_probs_8x8,
cpi->common.fc.hybrid_coef_probs_8x8,
cpi->frame_hybrid_branch_ct_8x8,
- BLOCK_TYPES_8X8);
+ BLOCK_TYPES_8X8_HYBRID);
}
if (cpi->common.txfm_mode > ALLOW_8X8) {
@@ -1419,7 +1423,7 @@ static void update_coef_probs(VP9_COMP* const cpi, vp9_writer* const bc) {
cpi->frame_hybrid_coef_probs_16x16,
cpi->common.fc.hybrid_coef_probs_16x16,
cpi->frame_hybrid_branch_ct_16x16,
- BLOCK_TYPES_16X16);
+ BLOCK_TYPES_16X16_HYBRID);
}
if (cpi->common.txfm_mode > ALLOW_16X16) {
@@ -1668,7 +1672,13 @@ void vp9_pack_bitstream(VP9_COMP *cpi, unsigned char *dest,
vp9_write_literal(&header_bc, pc->sb64_coded, 8);
pc->sb32_coded = get_binary_prob(cpi->sb32_count[0], cpi->sb32_count[1]);
vp9_write_literal(&header_bc, pc->sb32_coded, 8);
-
+#if CONFIG_LOSSLESS
+ vp9_write_bit(&header_bc, cpi->mb.e_mbd.lossless);
+ if (cpi->mb.e_mbd.lossless) {
+ pc->txfm_mode = ONLY_4X4;
+ }
+ else
+#endif
{
if (pc->txfm_mode == TX_MODE_SELECT) {
pc->prob_tx[0] = get_prob(cpi->txfm_count_32x32p[TX_4X4] +
@@ -1779,8 +1789,6 @@ void vp9_pack_bitstream(VP9_COMP *cpi, unsigned char *dest,
// Transmit Dc, Second order and Uv quantizer delta information
put_delta_q(&header_bc, pc->y1dc_delta_q);
- put_delta_q(&header_bc, pc->y2dc_delta_q);
- put_delta_q(&header_bc, pc->y2ac_delta_q);
put_delta_q(&header_bc, pc->uvdc_delta_q);
put_delta_q(&header_bc, pc->uvac_delta_q);
@@ -2040,6 +2048,9 @@ void vp9_pack_bitstream(VP9_COMP *cpi, unsigned char *dest,
break;
}
}
+ vp9_write_bit(&header_bc, pc->log2_tile_rows != 0);
+ if (pc->log2_tile_rows != 0)
+ vp9_write_bit(&header_bc, pc->log2_tile_rows != 1);
}
vp9_stop_encode(&header_bc);
@@ -2069,33 +2080,45 @@ void vp9_pack_bitstream(VP9_COMP *cpi, unsigned char *dest,
}
{
- int tile, total_size = 0;
+ int tile_row, tile_col, total_size = 0;
unsigned char *data_ptr = cx_data + header_bc.pos;
- TOKENEXTRA *tok = cpi->tok;
-
- for (tile = 0; tile < pc->tile_columns; tile++) {
- pc->cur_tile_idx = tile;
- vp9_get_tile_offsets(pc, &pc->cur_tile_mb_col_start,
- &pc->cur_tile_mb_col_end);
-
- if (tile < pc->tile_columns - 1)
- vp9_start_encode(&residual_bc, data_ptr + total_size + 4);
- else
- vp9_start_encode(&residual_bc, data_ptr + total_size);
- write_modes(cpi, &residual_bc, &tok);
- vp9_stop_encode(&residual_bc);
- if (tile < pc->tile_columns - 1) {
- /* size of this tile */
- data_ptr[total_size + 0] = residual_bc.pos;
- data_ptr[total_size + 1] = residual_bc.pos >> 8;
- data_ptr[total_size + 2] = residual_bc.pos >> 16;
- data_ptr[total_size + 3] = residual_bc.pos >> 24;
- total_size += 4;
- }
+ TOKENEXTRA *tok[1 << 6], *tok_end;
+
+ tok[0] = cpi->tok;
+ for (tile_col = 1; tile_col < pc->tile_columns; tile_col++)
+ tok[tile_col] = tok[tile_col - 1] + cpi->tok_count[tile_col - 1];
+
+ for (tile_row = 0; tile_row < pc->tile_rows; tile_row++) {
+ vp9_get_tile_row_offsets(pc, tile_row);
+ tok_end = cpi->tok + cpi->tok_count[0];
+ for (tile_col = 0; tile_col < pc->tile_columns;
+ tile_col++, tok_end += cpi->tok_count[tile_col]) {
+ vp9_get_tile_col_offsets(pc, tile_col);
+
+ if (tile_col < pc->tile_columns - 1 || tile_row < pc->tile_rows - 1)
+ vp9_start_encode(&residual_bc, data_ptr + total_size + 4);
+ else
+ vp9_start_encode(&residual_bc, data_ptr + total_size);
+ write_modes(cpi, &residual_bc, &tok[tile_col], tok_end);
+ vp9_stop_encode(&residual_bc);
+ if (tile_col < pc->tile_columns - 1 || tile_row < pc->tile_rows - 1) {
+ /* size of this tile */
+ data_ptr[total_size + 0] = residual_bc.pos;
+ data_ptr[total_size + 1] = residual_bc.pos >> 8;
+ data_ptr[total_size + 2] = residual_bc.pos >> 16;
+ data_ptr[total_size + 3] = residual_bc.pos >> 24;
+ total_size += 4;
+ }
- total_size += residual_bc.pos;
+ total_size += residual_bc.pos;
+ }
}
+ assert((unsigned int)(tok[0] - cpi->tok) == cpi->tok_count[0]);
+ for (tile_col = 1; tile_col < pc->tile_columns; tile_col++)
+ assert((unsigned int)(tok[tile_col] - tok[tile_col - 1]) ==
+ cpi->tok_count[tile_col]);
+
*size += total_size;
}
}
@@ -2133,17 +2156,22 @@ void print_tree_update_probs() {
print_tree_update_for_type(f, tree_update_hist_4x4, BLOCK_TYPES_4X4,
"vp9_coef_update_probs_4x4[BLOCK_TYPES_4X4]");
- print_tree_update_for_type(f, hybrid_tree_update_hist_4x4, BLOCK_TYPES_4X4,
- "vp9_coef_update_probs_4x4[BLOCK_TYPES_4X4]");
+ print_tree_update_for_type(f, hybrid_tree_update_hist_4x4,
+ BLOCK_TYPES_4X4_HYBRID,
+ "vp9_coef_update_probs_4x4"
+ "[BLOCK_TYPES_4X4_HYBRID]");
print_tree_update_for_type(f, tree_update_hist_8x8, BLOCK_TYPES_8X8,
"vp9_coef_update_probs_8x8[BLOCK_TYPES_8X8]");
- print_tree_update_for_type(f, hybrid_tree_update_hist_8x8, BLOCK_TYPES_8X8,
- "vp9_coef_update_probs_8x8[BLOCK_TYPES_8X8]");
+ print_tree_update_for_type(f, hybrid_tree_update_hist_8x8,
+ BLOCK_TYPES_8X8_HYBRID,
+ "vp9_coef_update_probs_8x8"
+ "[BLOCK_TYPES_8X8_HYBRID]");
print_tree_update_for_type(f, tree_update_hist_16x16, BLOCK_TYPES_16X16,
"vp9_coef_update_probs_16x16[BLOCK_TYPES_16X16]");
print_tree_update_for_type(f, hybrid_tree_update_hist_16x16,
- BLOCK_TYPES_16X16,
- "vp9_coef_update_probs_16x16[BLOCK_TYPES_16X16]");
+ BLOCK_TYPES_16X16_HYBRID,
+ "vp9_coef_update_probs_16x16"
+ "[BLOCK_TYPES_16X16_HYBRID]");
print_tree_update_for_type(f, tree_update_hist_32x32, BLOCK_TYPES_32X32,
"vp9_coef_update_probs_32x32[BLOCK_TYPES_32X32]");