diff options
author | Debargha Mukherjee <debargha@google.com> | 2016-01-06 11:24:57 -0800 |
---|---|---|
committer | Debargha Mukherjee <debargha@google.com> | 2016-01-08 11:13:46 -0800 |
commit | f7dfa4ece7b4e2aef190923abe4a3f1d3ca3ece8 (patch) | |
tree | 4f775faea7fd1be5147f090025b413ed62e428ab /vp10/encoder | |
parent | 2bd4f444092bf1902a1caca66e14e8e75189191d (diff) | |
download | libvpx-f7dfa4ece7b4e2aef190923abe4a3f1d3ca3ece8.tar libvpx-f7dfa4ece7b4e2aef190923abe4a3f1d3ca3ece8.tar.gz libvpx-f7dfa4ece7b4e2aef190923abe4a3f1d3ca3ece8.tar.bz2 libvpx-f7dfa4ece7b4e2aef190923abe4a3f1d3ca3ece8.zip |
Modifies inter/intra coding to allow all tx types
The nominal tx_type for a given mode is used as a context
to encode the actual tx_type for intra.
Results:
derflr: -0.241% BDRATE
hevcmr: -0.366% BDRATE
Change-Id: Icfe7b0a58d79bc6497a06e3441779afec6e01e21
Diffstat (limited to 'vp10/encoder')
-rw-r--r-- | vp10/encoder/bitstream.c | 109 | ||||
-rw-r--r-- | vp10/encoder/bitstream.h | 1 | ||||
-rw-r--r-- | vp10/encoder/encodeframe.c | 13 | ||||
-rw-r--r-- | vp10/encoder/encoder.c | 3 | ||||
-rw-r--r-- | vp10/encoder/encoder.h | 4 | ||||
-rw-r--r-- | vp10/encoder/rd.c | 14 | ||||
-rw-r--r-- | vp10/encoder/rdopt.c | 227 | ||||
-rw-r--r-- | vp10/encoder/subexp.c | 9 | ||||
-rw-r--r-- | vp10/encoder/subexp.h | 2 |
9 files changed, 325 insertions, 57 deletions
diff --git a/vp10/encoder/bitstream.c b/vp10/encoder/bitstream.c index d4b8c36db..bc73ad7b5 100644 --- a/vp10/encoder/bitstream.c +++ b/vp10/encoder/bitstream.c @@ -58,6 +58,16 @@ static INLINE void write_uniform(vpx_writer *w, int n, int v) { } } +#if CONFIG_EXT_TX +static struct vp10_token ext_tx_encodings[TX_TYPES]; +#endif // CONFIG_EXT_TX + +void vp10_encode_token_init() { +#if CONFIG_EXT_TX + vp10_tokens_from_tree(ext_tx_encodings, vp10_ext_tx_tree); +#endif // CONFIG_EXT_TX +} + static void write_intra_mode(vpx_writer *w, PREDICTION_MODE mode, const vpx_prob *probs) { vp10_write_token(w, vp10_intra_mode_tree, probs, &intra_mode_encodings[mode]); @@ -90,6 +100,24 @@ static void prob_diff_update(const vpx_tree_index *tree, vp10_cond_prob_diff_update(w, &probs[i], branch_ct[i]); } +static int prob_diff_update_savings(const vpx_tree_index *tree, + vpx_prob probs[/*n - 1*/], + const unsigned int counts[/*n - 1*/], + int n) { + int i; + unsigned int branch_ct[32][2]; + int savings = 0; + + // Assuming max number of probabilities <= 32 + assert(n <= 32); + vp10_tree_probs_from_distribution(tree, branch_ct, counts); + for (i = 0; i < n - 1; ++i) { + savings += vp10_cond_prob_diff_update_savings(&probs[i], + branch_ct[i]); + } + return savings; +} + static void write_selected_tx_size(const VP10_COMMON *cm, const MACROBLOCKD *xd, vpx_writer *w) { TX_SIZE tx_size = xd->mi[0]->mbmi.tx_size; @@ -133,6 +161,51 @@ static void update_switchable_interp_probs(VP10_COMMON *cm, vpx_writer *w, counts->switchable_interp[j], SWITCHABLE_FILTERS, w); } +#if CONFIG_EXT_TX +static void update_ext_tx_probs(VP10_COMMON *cm, vpx_writer *w) { + const int savings_thresh = vp10_cost_one(GROUP_DIFF_UPDATE_PROB) - + vp10_cost_zero(GROUP_DIFF_UPDATE_PROB); + int i, j; + + int savings = 0; + int do_update = 0; + for (i = TX_4X4; i < EXT_TX_SIZES; ++i) { + for (j = 0; j < TX_TYPES; ++j) + savings += prob_diff_update_savings( + vp10_ext_tx_tree, cm->fc->intra_ext_tx_prob[i][j], + cm->counts.intra_ext_tx[i][j], TX_TYPES); + } + do_update = savings > savings_thresh; + vpx_write(w, do_update, GROUP_DIFF_UPDATE_PROB); + if (do_update) { + for (i = TX_4X4; i < EXT_TX_SIZES; ++i) { + for (j = 0; j < TX_TYPES; ++j) + prob_diff_update(vp10_ext_tx_tree, + cm->fc->intra_ext_tx_prob[i][j], + cm->counts.intra_ext_tx[i][j], + TX_TYPES, w); + } + } + savings = 0; + do_update = 0; + for (i = TX_4X4; i < EXT_TX_SIZES; ++i) { + savings += prob_diff_update_savings( + vp10_ext_tx_tree, cm->fc->inter_ext_tx_prob[i], + cm->counts.inter_ext_tx[i], TX_TYPES); + } + do_update = savings > savings_thresh; + vpx_write(w, do_update, GROUP_DIFF_UPDATE_PROB); + if (do_update) { + for (i = TX_4X4; i < EXT_TX_SIZES; ++i) { + prob_diff_update(vp10_ext_tx_tree, + cm->fc->inter_ext_tx_prob[i], + cm->counts.inter_ext_tx[i], + TX_TYPES, w); + } + } +} +#endif // CONFIG_EXT_TX + static void pack_mb_tokens(vpx_writer *w, TOKENEXTRA **tp, const TOKENEXTRA *const stop, vpx_bit_depth_t bit_depth, const TX_SIZE tx) { @@ -370,6 +443,27 @@ static void pack_inter_mode_mvs(VP10_COMP *cpi, const MODE_INFO *mi, } } } +#if CONFIG_EXT_TX + if (mbmi->tx_size < TX_32X32 && + cm->base_qindex > 0 && !mbmi->skip && + !segfeature_active(&cm->seg, mbmi->segment_id, SEG_LVL_SKIP)) { + if (is_inter) { + vp10_write_token( + w, vp10_ext_tx_tree, + cm->fc->inter_ext_tx_prob[mbmi->tx_size], + &ext_tx_encodings[mbmi->tx_type]); + } else { + vp10_write_token( + w, vp10_ext_tx_tree, + cm->fc->intra_ext_tx_prob[mbmi->tx_size] + [intra_mode_to_tx_type_context[mbmi->mode]], + &ext_tx_encodings[mbmi->tx_type]); + } + } else { + if (!mbmi->skip) + assert(mbmi->tx_type == DCT_DCT); + } +#endif // CONFIG_EXT_TX } static void write_mb_modes_kf(const VP10_COMMON *cm, const MACROBLOCKD *xd, @@ -413,6 +507,18 @@ static void write_mb_modes_kf(const VP10_COMMON *cm, const MACROBLOCKD *xd, } write_intra_mode(w, mbmi->uv_mode, cm->fc->uv_mode_prob[mbmi->mode]); + +#if CONFIG_EXT_TX + if (mbmi->tx_size < TX_32X32 && + cm->base_qindex > 0 && !mbmi->skip && + !segfeature_active(&cm->seg, mbmi->segment_id, SEG_LVL_SKIP)) { + vp10_write_token( + w, vp10_ext_tx_tree, + cm->fc->intra_ext_tx_prob[mbmi->tx_size] + [intra_mode_to_tx_type_context[mbmi->mode]], + &ext_tx_encodings[mbmi->tx_type]); + } +#endif // CONFIG_EXT_TX } static void write_modes_b(VP10_COMP *cpi, const TileInfo *const tile, @@ -1381,6 +1487,9 @@ static size_t write_compressed_header(VP10_COMP *cpi, uint8_t *data) { vp10_write_nmv_probs(cm, cm->allow_high_precision_mv, &header_bc, &counts->mv); +#if CONFIG_EXT_TX + update_ext_tx_probs(cm, &header_bc); +#endif // CONFIG_EXT_TX } vpx_stop_encode(&header_bc); diff --git a/vp10/encoder/bitstream.h b/vp10/encoder/bitstream.h index aa0ed2fdf..b1da89f1d 100644 --- a/vp10/encoder/bitstream.h +++ b/vp10/encoder/bitstream.h @@ -18,6 +18,7 @@ extern "C" { #include "vp10/encoder/encoder.h" +void vp10_encode_token_init(); void vp10_pack_bitstream(VP10_COMP *const cpi, uint8_t *dest, size_t *size); static INLINE int vp10_preserve_existing_gf(VP10_COMP *cpi) { diff --git a/vp10/encoder/encodeframe.c b/vp10/encoder/encodeframe.c index 9381b653d..b65d52281 100644 --- a/vp10/encoder/encodeframe.c +++ b/vp10/encoder/encodeframe.c @@ -3024,5 +3024,18 @@ static void encode_superblock(VP10_COMP *cpi, ThreadData *td, } ++td->counts->tx.tx_totals[mbmi->tx_size]; ++td->counts->tx.tx_totals[get_uv_tx_size(mbmi, &xd->plane[1])]; +#if CONFIG_EXT_TX + if (mbmi->tx_size < TX_32X32 && + cm->base_qindex > 0 && !mbmi->skip && + !segfeature_active(&cm->seg, mbmi->segment_id, SEG_LVL_SKIP)) { + if (is_inter_block(mbmi)) { + ++td->counts->inter_ext_tx[mbmi->tx_size][mbmi->tx_type]; + } else { + ++td->counts->intra_ext_tx[mbmi->tx_size] + [intra_mode_to_tx_type_context[mbmi->mode]] + [mbmi->tx_type]; + } + } +#endif // CONFIG_EXT_TX } } diff --git a/vp10/encoder/encoder.c b/vp10/encoder/encoder.c index 175c6d855..9e3bec40e 100644 --- a/vp10/encoder/encoder.c +++ b/vp10/encoder/encoder.c @@ -328,6 +328,7 @@ void vp10_initialize_enc(void) { vp10_rc_init_minq_luts(); vp10_entropy_mv_init(); vp10_temporal_filter_init(); + vp10_encode_token_init(); init_done = 1; } } @@ -2654,7 +2655,7 @@ static void loopfilter_frame(VP10_COMP *cpi, VP10_COMMON *cm) { MACROBLOCKD *xd = &cpi->td.mb.e_mbd; struct loopfilter *lf = &cm->lf; if (is_lossless_requested(&cpi->oxcf)) { - lf->filter_level = 0; + lf->filter_level = 0; } else { struct vpx_usec_timer timer; diff --git a/vp10/encoder/encoder.h b/vp10/encoder/encoder.h index 2a44e4744..0bd3bb95b 100644 --- a/vp10/encoder/encoder.h +++ b/vp10/encoder/encoder.h @@ -467,6 +467,10 @@ typedef struct VP10_COMP { int multi_arf_enabled; int multi_arf_last_grp_enabled; +#if CONFIG_EXT_TX + int intra_tx_type_costs[EXT_TX_SIZES][TX_TYPES][TX_TYPES]; + int inter_tx_type_costs[EXT_TX_SIZES][TX_TYPES]; +#endif // CONFIG_EXT_TX #if CONFIG_VP9_TEMPORAL_DENOISING VP9_DENOISER denoiser; #endif diff --git a/vp10/encoder/rd.c b/vp10/encoder/rd.c index 5623a7202..e24b89501 100644 --- a/vp10/encoder/rd.c +++ b/vp10/encoder/rd.c @@ -83,6 +83,20 @@ static void fill_mode_costs(VP10_COMP *cpi) { for (i = 0; i < SWITCHABLE_FILTER_CONTEXTS; ++i) vp10_cost_tokens(cpi->switchable_interp_costs[i], fc->switchable_interp_prob[i], vp10_switchable_interp_tree); + +#if CONFIG_EXT_TX + for (i = TX_4X4; i < EXT_TX_SIZES; ++i) { + for (j = 0; j < TX_TYPES; ++j) + vp10_cost_tokens(cpi->intra_tx_type_costs[i][j], + fc->intra_ext_tx_prob[i][j], + vp10_ext_tx_tree); + } + for (i = TX_4X4; i < EXT_TX_SIZES; ++i) { + vp10_cost_tokens(cpi->inter_tx_type_costs[i], + fc->inter_ext_tx_prob[i], + vp10_ext_tx_tree); + } +#endif // CONFIG_EXT_TX } static void fill_token_costs(vp10_coeff_cost *c, diff --git a/vp10/encoder/rdopt.c b/vp10/encoder/rdopt.c index bbddc1d29..298ab0abc 100644 --- a/vp10/encoder/rdopt.c +++ b/vp10/encoder/rdopt.c @@ -54,6 +54,10 @@ #define MIN_EARLY_TERM_INDEX 3 #define NEW_MV_DISCOUNT_FACTOR 8 +#if CONFIG_EXT_TX +const double ext_tx_th = 0.99; +#endif // CONFIG_EXT_TX + typedef struct { PREDICTION_MODE mode; MV_REFERENCE_FRAME ref_frame[2]; @@ -598,11 +602,63 @@ static void choose_largest_tx_size(VP10_COMP *cpi, MACROBLOCK *x, MACROBLOCKD *const xd = &x->e_mbd; MB_MODE_INFO *const mbmi = &xd->mi[0]->mbmi; +#if CONFIG_EXT_TX + TX_TYPE tx_type, best_tx_type = DCT_DCT; + int r, s; + int64_t d, psse, this_rd, best_rd = INT64_MAX; + vpx_prob skip_prob = vp10_get_skip_prob(cm, xd); + int s0 = vp10_cost_bit(skip_prob, 0); + int s1 = vp10_cost_bit(skip_prob, 1); + const int is_inter = is_inter_block(mbmi); + + mbmi->tx_size = VPXMIN(max_tx_size, largest_tx_size); + if (mbmi->tx_size < TX_32X32 && + !xd->lossless[mbmi->segment_id]) { + for (tx_type = 0; tx_type < TX_TYPES; ++tx_type) { + mbmi->tx_type = tx_type; + txfm_rd_in_plane(x, &r, &d, &s, + &psse, ref_best_rd, 0, bs, mbmi->tx_size, + cpi->sf.use_fast_coef_costing); + if (r == INT_MAX) + continue; + if (is_inter) + r += cpi->inter_tx_type_costs[mbmi->tx_size][mbmi->tx_type]; + else + r += cpi->intra_tx_type_costs[mbmi->tx_size] + [intra_mode_to_tx_type_context[mbmi->mode]] + [mbmi->tx_type]; + if (s) + this_rd = RDCOST(x->rdmult, x->rddiv, s1, psse); + else + this_rd = RDCOST(x->rdmult, x->rddiv, r + s0, d); + if (is_inter && !xd->lossless[mbmi->segment_id] && !s) + this_rd = VPXMIN(this_rd, RDCOST(x->rdmult, x->rddiv, s1, psse)); + + if (this_rd < ((best_tx_type == DCT_DCT) ? ext_tx_th : 1) * best_rd) { + best_rd = this_rd; + best_tx_type = mbmi->tx_type; + } + } + } + mbmi->tx_type = best_tx_type; + txfm_rd_in_plane(x, rate, distortion, skip, + sse, ref_best_rd, 0, bs, + mbmi->tx_size, cpi->sf.use_fast_coef_costing); + if (mbmi->tx_size < TX_32X32 && !xd->lossless[mbmi->segment_id]) { + if (is_inter) + *rate += cpi->inter_tx_type_costs[mbmi->tx_size][mbmi->tx_type]; + else + *rate += cpi->intra_tx_type_costs[mbmi->tx_size] + [intra_mode_to_tx_type_context[mbmi->mode]] + [mbmi->tx_type]; + } +#else mbmi->tx_size = VPXMIN(max_tx_size, largest_tx_size); txfm_rd_in_plane(x, rate, distortion, skip, sse, ref_best_rd, 0, bs, mbmi->tx_size, cpi->sf.use_fast_coef_costing); +#endif // CONFIG_EXT_TX } static void choose_smallest_tx_size(VP10_COMP *cpi, MACROBLOCK *x, @@ -632,87 +688,137 @@ static void choose_tx_size_from_rd(VP10_COMP *cpi, MACROBLOCK *x, MACROBLOCKD *const xd = &x->e_mbd; MB_MODE_INFO *const mbmi = &xd->mi[0]->mbmi; vpx_prob skip_prob = vp10_get_skip_prob(cm, xd); - int r[TX_SIZES][2], s[TX_SIZES]; - int64_t d[TX_SIZES], sse[TX_SIZES]; - int64_t rd[TX_SIZES][2] = {{INT64_MAX, INT64_MAX}, - {INT64_MAX, INT64_MAX}, - {INT64_MAX, INT64_MAX}, - {INT64_MAX, INT64_MAX}}; + int r, s; + int64_t d, sse; + int64_t rd = INT64_MAX; int n, m; int s0, s1; - int64_t best_rd = INT64_MAX; + int64_t best_rd = INT64_MAX, last_rd = INT64_MAX; TX_SIZE best_tx = max_tx_size; int start_tx, end_tx; + const int tx_select = cm->tx_mode == TX_MODE_SELECT; +#if CONFIG_EXT_TX + TX_TYPE tx_type, best_tx_type = DCT_DCT; +#endif // CONFIG_EXT_TX + const int is_inter = is_inter_block(mbmi); const vpx_prob *tx_probs = get_tx_probs2(max_tx_size, xd, &cm->fc->tx_probs); assert(skip_prob > 0); s0 = vp10_cost_bit(skip_prob, 0); s1 = vp10_cost_bit(skip_prob, 1); - if (cm->tx_mode == TX_MODE_SELECT) { + if (tx_select) { start_tx = max_tx_size; end_tx = 0; } else { - TX_SIZE chosen_tx_size = VPXMIN(max_tx_size, - tx_mode_to_biggest_tx_size[cm->tx_mode]); + const TX_SIZE chosen_tx_size = + VPXMIN(max_tx_size, tx_mode_to_biggest_tx_size[cm->tx_mode]); start_tx = chosen_tx_size; end_tx = chosen_tx_size; } - for (n = start_tx; n >= end_tx; n--) { - int r_tx_size = 0; - for (m = 0; m <= n - (n == (int) max_tx_size); m++) { - if (m == n) - r_tx_size += vp10_cost_zero(tx_probs[m]); - else - r_tx_size += vp10_cost_one(tx_probs[m]); - } - txfm_rd_in_plane(x, &r[n][0], &d[n], &s[n], - &sse[n], ref_best_rd, 0, bs, n, - cpi->sf.use_fast_coef_costing); - r[n][1] = r[n][0]; - if (r[n][0] < INT_MAX) { - r[n][1] += r_tx_size; - } - if (d[n] == INT64_MAX || r[n][0] == INT_MAX) { - rd[n][0] = rd[n][1] = INT64_MAX; - } else if (s[n]) { - if (is_inter_block(mbmi)) { - rd[n][0] = rd[n][1] = RDCOST(x->rdmult, x->rddiv, s1, sse[n]); - r[n][1] -= r_tx_size; + *distortion = INT64_MAX; + *rate = INT_MAX; + *skip = 0; + *psse = INT64_MAX; + +#if CONFIG_EXT_TX + for (tx_type = DCT_DCT; tx_type < TX_TYPES; ++tx_type) { +#endif // CONFIG_EXT_TX + last_rd = INT64_MAX; + for (n = start_tx; n >= end_tx; --n) { + int r_tx_size = 0; + for (m = 0; m <= n - (n == (int) max_tx_size); ++m) { + if (m == n) + r_tx_size += vp10_cost_zero(tx_probs[m]); + else + r_tx_size += vp10_cost_one(tx_probs[m]); + } + +#if CONFIG_EXT_TX + if (n >= TX_32X32 && tx_type != DCT_DCT) { + continue; + } + mbmi->tx_type = tx_type; + txfm_rd_in_plane(x, &r, &d, &s, + &sse, ref_best_rd, 0, bs, n, + cpi->sf.use_fast_coef_costing); + if (n < TX_32X32 && + !xd->lossless[xd->mi[0]->mbmi.segment_id] && + r != INT_MAX) { + if (is_inter) + r += cpi->inter_tx_type_costs[mbmi->tx_size][mbmi->tx_type]; + else + r += cpi->intra_tx_type_costs[mbmi->tx_size] + [intra_mode_to_tx_type_context[mbmi->mode]] + [mbmi->tx_type]; + } +#else // CONFIG_EXT_TX + txfm_rd_in_plane(x, &r, &d, &s, + &sse, ref_best_rd, 0, bs, n, + cpi->sf.use_fast_coef_costing); +#endif // CONFIG_EXT_TX + + if (r == INT_MAX) + continue; + + if (s) { + if (is_inter) { + rd = RDCOST(x->rdmult, x->rddiv, s1, sse); + } else { + rd = RDCOST(x->rdmult, x->rddiv, s1 + r_tx_size * tx_select, sse); + } } else { - rd[n][0] = RDCOST(x->rdmult, x->rddiv, s1, sse[n]); - rd[n][1] = RDCOST(x->rdmult, x->rddiv, s1 + r_tx_size, sse[n]); + rd = RDCOST(x->rdmult, x->rddiv, r + s0 + r_tx_size * tx_select, d); } - } else { - rd[n][0] = RDCOST(x->rdmult, x->rddiv, r[n][0] + s0, d[n]); - rd[n][1] = RDCOST(x->rdmult, x->rddiv, r[n][1] + s0, d[n]); - } - if (is_inter_block(mbmi) && !xd->lossless[mbmi->segment_id] && - !s[n] && sse[n] != INT64_MAX) { - rd[n][0] = VPXMIN(rd[n][0], RDCOST(x->rdmult, x->rddiv, s1, sse[n])); - rd[n][1] = VPXMIN(rd[n][1], RDCOST(x->rdmult, x->rddiv, s1, sse[n])); - } + if (tx_select && !(s && is_inter)) + r += r_tx_size; - // Early termination in transform size search. - if (cpi->sf.tx_size_search_breakout && - (rd[n][1] == INT64_MAX || - (n < (int) max_tx_size && rd[n][1] > rd[n + 1][1]) || - s[n] == 1)) - break; + if (is_inter && !xd->lossless[xd->mi[0]->mbmi.segment_id] && !s) + rd = VPXMIN(rd, RDCOST(x->rdmult, x->rddiv, s1, sse)); - if (rd[n][1] < best_rd) { - best_tx = n; - best_rd = rd[n][1]; + // Early termination in transform size search. + if (cpi->sf.tx_size_search_breakout && + (rd == INT64_MAX || +#if CONFIG_EXT_TX + (s == 1 && tx_type != DCT_DCT && n < start_tx) || +#else + (s == 1 && n < start_tx) || +#endif + (n < (int) max_tx_size && rd > last_rd))) + break; + + last_rd = rd; + if (rd < +#if CONFIG_EXT_TX + (is_inter && best_tx_type == DCT_DCT ? ext_tx_th : 1) * +#endif // CONFIG_EXT_TX + best_rd) { + best_tx = n; + best_rd = rd; + *distortion = d; + *rate = r; + *skip = s; + *psse = sse; +#if CONFIG_EXT_TX + best_tx_type = mbmi->tx_type; +#endif // CONFIG_EXT_TX + } } +#if CONFIG_EXT_TX } - mbmi->tx_size = best_tx; +#endif // CONFIG_EXT_TX - *distortion = d[mbmi->tx_size]; - *rate = r[mbmi->tx_size][cm->tx_mode == TX_MODE_SELECT]; - *skip = s[mbmi->tx_size]; - *psse = sse[mbmi->tx_size]; + mbmi->tx_size = best_tx; +#if CONFIG_EXT_TX + mbmi->tx_type = best_tx_type; + if (mbmi->tx_size >= TX_32X32) + assert(mbmi->tx_type == DCT_DCT); + txfm_rd_in_plane(x, &r, &d, &s, + &sse, ref_best_rd, 0, bs, best_tx, + cpi->sf.use_fast_coef_costing); +#endif // CONFIG_EXT_TX } static void super_block_yrd(VP10_COMP *cpi, MACROBLOCK *x, int *rate, @@ -1065,6 +1171,9 @@ static int64_t rd_pick_intra_sby_mode(VP10_COMP *cpi, MACROBLOCK *x, int this_rate, this_rate_tokenonly, s; int64_t this_distortion, this_rd; TX_SIZE best_tx = TX_4X4; +#if CONFIG_EXT_TX + TX_TYPE best_tx_type = DCT_DCT; +#endif // CONFIG_EXT_TX int *bmode_costs; const MODE_INFO *above_mi = xd->above_mi; const MODE_INFO *left_mi = xd->left_mi; @@ -1091,6 +1200,9 @@ static int64_t rd_pick_intra_sby_mode(VP10_COMP *cpi, MACROBLOCK *x, mode_selected = mode; best_rd = this_rd; best_tx = mic->mbmi.tx_size; +#if CONFIG_EXT_TX + best_tx_type = mic->mbmi.tx_type; +#endif // CONFIG_EXT_TX *rate = this_rate; *rate_tokenonly = this_rate_tokenonly; *distortion = this_distortion; @@ -1100,6 +1212,9 @@ static int64_t rd_pick_intra_sby_mode(VP10_COMP *cpi, MACROBLOCK *x, mic->mbmi.mode = mode_selected; mic->mbmi.tx_size = best_tx; +#if CONFIG_EXT_TX + mic->mbmi.tx_type = best_tx_type; +#endif // CONFIG_EXT_TX return best_rd; } diff --git a/vp10/encoder/subexp.c b/vp10/encoder/subexp.c index 67e820b1f..d4074775b 100644 --- a/vp10/encoder/subexp.c +++ b/vp10/encoder/subexp.c @@ -212,3 +212,12 @@ void vp10_cond_prob_diff_update(vpx_writer *w, vpx_prob *oldp, vpx_write(w, 0, upd); } } + +int vp10_cond_prob_diff_update_savings(vpx_prob *oldp, + const unsigned int ct[2]) { + const vpx_prob upd = DIFF_UPDATE_PROB; + vpx_prob newp = get_binary_prob(ct[0], ct[1]); + const int savings = vp10_prob_diff_update_savings_search(ct, *oldp, &newp, + upd); + return savings; +} diff --git a/vp10/encoder/subexp.h b/vp10/encoder/subexp.h index 04b96c0bd..091334f1f 100644 --- a/vp10/encoder/subexp.h +++ b/vp10/encoder/subexp.h @@ -37,6 +37,8 @@ int vp10_prob_diff_update_savings_search_model(const unsigned int *ct, vpx_prob upd, int stepsize); +int vp10_cond_prob_diff_update_savings(vpx_prob *oldp, + const unsigned int ct[2]); #ifdef __cplusplus } // extern "C" #endif |