2 * Copyright (c) 2010 The WebM project authors. All Rights Reserved.
4 * Use of this source code is governed by a BSD-style license
5 * that can be found in the LICENSE file in the root of the source
6 * tree. An additional intellectual property rights grant can be found
7 * in the file PATENTS. All contributing project authors may
8 * be found in the AUTHORS file in the root of the source tree.
15 #include "./vp9_rtcd.h"
16 #include "./vpx_config.h"
18 #include "vpx_ports/vpx_timer.h"
20 #include "vp9/common/vp9_common.h"
21 #include "vp9/common/vp9_entropy.h"
22 #include "vp9/common/vp9_entropymode.h"
23 #include "vp9/common/vp9_idct.h"
24 #include "vp9/common/vp9_mvref_common.h"
25 #include "vp9/common/vp9_pred_common.h"
26 #include "vp9/common/vp9_quant_common.h"
27 #include "vp9/common/vp9_reconintra.h"
28 #include "vp9/common/vp9_reconinter.h"
29 #include "vp9/common/vp9_seg_common.h"
30 #include "vp9/common/vp9_systemdependent.h"
31 #include "vp9/common/vp9_tile_common.h"
32 #include "vp9/encoder/vp9_encodeframe.h"
33 #include "vp9/encoder/vp9_encodemb.h"
34 #include "vp9/encoder/vp9_encodemv.h"
35 #include "vp9/encoder/vp9_extend.h"
36 #include "vp9/encoder/vp9_onyx_int.h"
37 #include "vp9/encoder/vp9_pickmode.h"
38 #include "vp9/encoder/vp9_rdopt.h"
39 #include "vp9/encoder/vp9_segmentation.h"
40 #include "vp9/encoder/vp9_tokenize.h"
41 #include "vp9/encoder/vp9_vaq.h"
43 static INLINE uint8_t *get_sb_index(MACROBLOCK *x, BLOCK_SIZE subsize) {
68 static void encode_superblock(VP9_COMP *cpi, TOKENEXTRA **t, int output_enabled,
69 int mi_row, int mi_col, BLOCK_SIZE bsize);
71 static void adjust_act_zbin(VP9_COMP *cpi, MACROBLOCK *x);
73 // activity_avg must be positive, or flat regions could get a zero weight
74 // (infinite lambda), which confounds analysis.
75 // This also avoids the need for divide by zero checks in
76 // vp9_activity_masking().
77 #define ACTIVITY_AVG_MIN (64)
79 // Motion vector component magnitude threshold for defining fast motion.
80 #define FAST_MOTION_MV_THRESH (24)
82 // This is used as a reference when computing the source variance for the
83 // purposes of activity masking.
84 // Eventually this should be replaced by custom no-reference routines,
85 // which will be faster.
86 static const uint8_t VP9_VAR_OFFS[64] = {
87 128, 128, 128, 128, 128, 128, 128, 128,
88 128, 128, 128, 128, 128, 128, 128, 128,
89 128, 128, 128, 128, 128, 128, 128, 128,
90 128, 128, 128, 128, 128, 128, 128, 128,
91 128, 128, 128, 128, 128, 128, 128, 128,
92 128, 128, 128, 128, 128, 128, 128, 128,
93 128, 128, 128, 128, 128, 128, 128, 128,
94 128, 128, 128, 128, 128, 128, 128, 128
97 static unsigned int get_sby_perpixel_variance(VP9_COMP *cpi,
100 unsigned int var, sse;
101 var = cpi->fn_ptr[bs].vf(x->plane[0].src.buf, x->plane[0].src.stride,
102 VP9_VAR_OFFS, 0, &sse);
103 return ROUND_POWER_OF_TWO(var, num_pels_log2_lookup[bs]);
106 static unsigned int get_sby_perpixel_diff_variance(VP9_COMP *cpi,
111 const YV12_BUFFER_CONFIG *yv12 = get_ref_frame_buffer(cpi, LAST_FRAME);
112 int offset = (mi_row * MI_SIZE) * yv12->y_stride + (mi_col * MI_SIZE);
113 unsigned int var, sse;
114 var = cpi->fn_ptr[bs].vf(x->plane[0].src.buf,
115 x->plane[0].src.stride,
116 yv12->y_buffer + offset,
119 return ROUND_POWER_OF_TWO(var, num_pels_log2_lookup[bs]);
122 static BLOCK_SIZE get_rd_var_based_fixed_partition(VP9_COMP *cpi,
125 unsigned int var = get_sby_perpixel_diff_variance(cpi, &cpi->mb,
138 static BLOCK_SIZE get_nonrd_var_based_fixed_partition(VP9_COMP *cpi,
141 unsigned int var = get_sby_perpixel_diff_variance(cpi, &cpi->mb,
152 // Original activity measure from Tim T's code.
153 static unsigned int tt_activity_measure(MACROBLOCK *x) {
155 /* TODO: This could also be done over smaller areas (8x8), but that would
156 * require extensive changes elsewhere, as lambda is assumed to be fixed
157 * over an entire MB in most of the code.
158 * Another option is to compute four 8x8 variances, and pick a single
159 * lambda using a non-linear combination (e.g., the smallest, or second
162 unsigned int act = vp9_variance16x16(x->plane[0].src.buf,
163 x->plane[0].src.stride,
164 VP9_VAR_OFFS, 0, &sse) << 4;
165 // If the region is flat, lower the activity some more.
167 act = MIN(act, 5 << 12);
172 // Stub for alternative experimental activity measures.
173 static unsigned int alt_activity_measure(MACROBLOCK *x, int use_dc_pred) {
174 return vp9_encode_intra(x, use_dc_pred);
177 // Measure the activity of the current macroblock
178 // What we measure here is TBD so abstracted to this function
179 #define ALT_ACT_MEASURE 1
180 static unsigned int mb_activity_measure(MACROBLOCK *x, int mb_row, int mb_col) {
181 unsigned int mb_activity;
183 if (ALT_ACT_MEASURE) {
184 const int use_dc_pred = (mb_col || mb_row) && (!mb_col || !mb_row);
186 // Or use and alternative.
187 mb_activity = alt_activity_measure(x, use_dc_pred);
189 // Original activity measure from Tim T's code.
190 mb_activity = tt_activity_measure(x);
193 return MAX(mb_activity, ACTIVITY_AVG_MIN);
196 // Calculate an "average" mb activity value for the frame
198 static void calc_av_activity(VP9_COMP *cpi, int64_t activity_sum) {
200 // Find median: Simple n^2 algorithm for experimentation
204 unsigned int *sortlist;
207 // Create a list to sort to
208 CHECK_MEM_ERROR(&cpi->common, sortlist, vpx_calloc(sizeof(unsigned int),
211 // Copy map to sort list
212 vpx_memcpy(sortlist, cpi->mb_activity_map,
213 sizeof(unsigned int) * cpi->common.MBs);
215 // Ripple each value down to its correct position
216 for (i = 1; i < cpi->common.MBs; i ++) {
217 for (j = i; j > 0; j --) {
218 if (sortlist[j] < sortlist[j - 1]) {
220 tmp = sortlist[j - 1];
221 sortlist[j - 1] = sortlist[j];
229 // Even number MBs so estimate median as mean of two either side.
230 median = (1 + sortlist[cpi->common.MBs >> 1] +
231 sortlist[(cpi->common.MBs >> 1) + 1]) >> 1;
233 cpi->activity_avg = median;
238 // Simple mean for now
239 cpi->activity_avg = (unsigned int) (activity_sum / cpi->common.MBs);
242 if (cpi->activity_avg < ACTIVITY_AVG_MIN)
243 cpi->activity_avg = ACTIVITY_AVG_MIN;
245 // Experimental code: return fixed value normalized for several clips
247 cpi->activity_avg = 100000;
250 #define USE_ACT_INDEX 0
251 #define OUTPUT_NORM_ACT_STATS 0
254 // Calculate an activity index for each mb
255 static void calc_activity_index(VP9_COMP *cpi, MACROBLOCK *x) {
256 VP9_COMMON *const cm = &cpi->common;
263 #if OUTPUT_NORM_ACT_STATS
264 FILE *f = fopen("norm_act.stt", "a");
265 fprintf(f, "\n%12d\n", cpi->activity_avg);
268 // Reset pointers to start of activity map
269 x->mb_activity_ptr = cpi->mb_activity_map;
271 // Calculate normalized mb activity number.
272 for (mb_row = 0; mb_row < cm->mb_rows; mb_row++) {
273 // for each macroblock col in image
274 for (mb_col = 0; mb_col < cm->mb_cols; mb_col++) {
275 // Read activity from the map
276 act = *(x->mb_activity_ptr);
278 // Calculate a normalized activity number
279 a = act + 4 * cpi->activity_avg;
280 b = 4 * act + cpi->activity_avg;
283 *(x->activity_ptr) = (int)((b + (a >> 1)) / a) - 1;
285 *(x->activity_ptr) = 1 - (int)((a + (b >> 1)) / b);
287 #if OUTPUT_NORM_ACT_STATS
288 fprintf(f, " %6d", *(x->mb_activity_ptr));
290 // Increment activity map pointers
291 x->mb_activity_ptr++;
294 #if OUTPUT_NORM_ACT_STATS
299 #if OUTPUT_NORM_ACT_STATS
303 #endif // USE_ACT_INDEX
305 // Loop through all MBs. Note activity of each, average activity and
306 // calculate a normalized activity for each
307 static void build_activity_map(VP9_COMP *cpi) {
308 MACROBLOCK *const x = &cpi->mb;
309 MACROBLOCKD *xd = &x->e_mbd;
310 VP9_COMMON *const cm = &cpi->common;
313 YV12_BUFFER_CONFIG *new_yv12 = get_frame_new_buffer(cm);
315 int recon_y_stride = new_yv12->y_stride;
319 unsigned int mb_activity;
320 int64_t activity_sum = 0;
322 x->mb_activity_ptr = cpi->mb_activity_map;
324 // for each macroblock row in image
325 for (mb_row = 0; mb_row < cm->mb_rows; mb_row++) {
327 // reset above block coeffs
328 xd->up_available = (mb_row != 0);
329 recon_yoffset = (mb_row * recon_y_stride * 16);
331 // for each macroblock col in image
332 for (mb_col = 0; mb_col < cm->mb_cols; mb_col++) {
334 xd->plane[0].dst.buf = new_yv12->y_buffer + recon_yoffset;
335 xd->left_available = (mb_col != 0);
340 mb_activity = mb_activity_measure(x, mb_row, mb_col);
343 activity_sum += mb_activity;
345 // Store MB level activity details.
346 *x->mb_activity_ptr = mb_activity;
348 // Increment activity map pointer
349 x->mb_activity_ptr++;
351 // adjust to the next column of source macroblocks
352 x->plane[0].src.buf += 16;
355 // adjust to the next row of mbs
356 x->plane[0].src.buf += 16 * x->plane[0].src.stride - 16 * cm->mb_cols;
359 // Calculate an "average" MB activity
360 calc_av_activity(cpi, activity_sum);
363 // Calculate an activity index number of each mb
364 calc_activity_index(cpi, x);
368 // Macroblock activity masking
369 static void activity_masking(VP9_COMP *cpi, MACROBLOCK *x) {
371 x->rdmult += *(x->mb_activity_ptr) * (x->rdmult >> 2);
372 x->errorperbit = x->rdmult * 100 / (110 * x->rddiv);
373 x->errorperbit += (x->errorperbit == 0);
375 const int64_t act = *(x->mb_activity_ptr);
377 // Apply the masking to the RD multiplier.
378 const int64_t a = act + (2 * cpi->activity_avg);
379 const int64_t b = (2 * act) + cpi->activity_avg;
381 x->rdmult = (unsigned int) (((int64_t) x->rdmult * b + (a >> 1)) / a);
382 x->errorperbit = x->rdmult * 100 / (110 * x->rddiv);
383 x->errorperbit += (x->errorperbit == 0);
386 // Activity based Zbin adjustment
387 adjust_act_zbin(cpi, x);
390 // Select a segment for the current SB64
391 static void select_in_frame_q_segment(VP9_COMP *cpi,
392 int mi_row, int mi_col,
393 int output_enabled, int projected_rate) {
394 VP9_COMMON *const cm = &cpi->common;
396 const int mi_offset = mi_row * cm->mi_cols + mi_col;
397 const int bw = num_8x8_blocks_wide_lookup[BLOCK_64X64];
398 const int bh = num_8x8_blocks_high_lookup[BLOCK_64X64];
399 const int xmis = MIN(cm->mi_cols - mi_col, bw);
400 const int ymis = MIN(cm->mi_rows - mi_row, bh);
401 int complexity_metric = 64;
404 unsigned char segment;
406 if (!output_enabled) {
409 // Rate depends on fraction of a SB64 in frame (xmis * ymis / bw * bh).
410 // It is converted to bits * 256 units
411 const int target_rate = (cpi->rc.sb64_target_rate * xmis * ymis * 256) /
414 if (projected_rate < (target_rate / 4)) {
420 if (target_rate > 0) {
422 clamp((int)((projected_rate * 64) / target_rate), 16, 255);
426 // Fill in the entires in the segment map corresponding to this SB64
427 for (y = 0; y < ymis; y++) {
428 for (x = 0; x < xmis; x++) {
429 cpi->segmentation_map[mi_offset + y * cm->mi_cols + x] = segment;
430 cpi->complexity_map[mi_offset + y * cm->mi_cols + x] =
431 (unsigned char)complexity_metric;
436 static void update_state(VP9_COMP *cpi, PICK_MODE_CONTEXT *ctx,
437 BLOCK_SIZE bsize, int output_enabled) {
439 VP9_COMMON *const cm = &cpi->common;
440 MACROBLOCK *const x = &cpi->mb;
441 MACROBLOCKD *const xd = &x->e_mbd;
442 struct macroblock_plane *const p = x->plane;
443 struct macroblockd_plane *const pd = xd->plane;
444 MODE_INFO *mi = &ctx->mic;
445 MB_MODE_INFO *const mbmi = &xd->mi_8x8[0]->mbmi;
446 MODE_INFO *mi_addr = xd->mi_8x8[0];
448 const int mis = cm->mode_info_stride;
449 const int mi_width = num_8x8_blocks_wide_lookup[bsize];
450 const int mi_height = num_8x8_blocks_high_lookup[bsize];
453 assert(mi->mbmi.mode < MB_MODE_COUNT);
454 assert(mi->mbmi.ref_frame[0] < MAX_REF_FRAMES);
455 assert(mi->mbmi.ref_frame[1] < MAX_REF_FRAMES);
456 assert(mi->mbmi.sb_type == bsize);
458 // For in frame adaptive Q copy over the chosen segment id into the
459 // mode innfo context for the chosen mode / partition.
460 if ((cpi->oxcf.aq_mode == COMPLEXITY_AQ) && output_enabled)
461 mi->mbmi.segment_id = xd->mi_8x8[0]->mbmi.segment_id;
465 max_plane = is_inter_block(mbmi) ? MAX_MB_PLANE : 1;
466 for (i = 0; i < max_plane; ++i) {
467 p[i].coeff = ctx->coeff_pbuf[i][1];
468 p[i].qcoeff = ctx->qcoeff_pbuf[i][1];
469 pd[i].dqcoeff = ctx->dqcoeff_pbuf[i][1];
470 p[i].eobs = ctx->eobs_pbuf[i][1];
473 for (i = max_plane; i < MAX_MB_PLANE; ++i) {
474 p[i].coeff = ctx->coeff_pbuf[i][2];
475 p[i].qcoeff = ctx->qcoeff_pbuf[i][2];
476 pd[i].dqcoeff = ctx->dqcoeff_pbuf[i][2];
477 p[i].eobs = ctx->eobs_pbuf[i][2];
480 // Restore the coding context of the MB to that that was in place
481 // when the mode was picked for it
482 for (y = 0; y < mi_height; y++)
483 for (x_idx = 0; x_idx < mi_width; x_idx++)
484 if ((xd->mb_to_right_edge >> (3 + MI_SIZE_LOG2)) + mi_width > x_idx
485 && (xd->mb_to_bottom_edge >> (3 + MI_SIZE_LOG2)) + mi_height > y) {
486 xd->mi_8x8[x_idx + y * mis] = mi_addr;
489 if ((cpi->oxcf.aq_mode == VARIANCE_AQ) ||
490 (cpi->oxcf.aq_mode == COMPLEXITY_AQ)) {
491 vp9_init_plane_quantizers(cpi, x);
494 // FIXME(rbultje) I'm pretty sure this should go to the end of this block
495 // (i.e. after the output_enabled)
496 if (bsize < BLOCK_32X32) {
497 if (bsize < BLOCK_16X16)
498 ctx->tx_rd_diff[ALLOW_16X16] = ctx->tx_rd_diff[ALLOW_8X8];
499 ctx->tx_rd_diff[ALLOW_32X32] = ctx->tx_rd_diff[ALLOW_16X16];
502 if (is_inter_block(mbmi) && mbmi->sb_type < BLOCK_8X8) {
503 mbmi->mv[0].as_int = mi->bmi[3].as_mv[0].as_int;
504 mbmi->mv[1].as_int = mi->bmi[3].as_mv[1].as_int;
508 vpx_memcpy(x->zcoeff_blk[mbmi->tx_size], ctx->zcoeff_blk,
509 sizeof(uint8_t) * ctx->num_4x4_blk);
514 if (!vp9_segfeature_active(&cm->seg, mbmi->segment_id, SEG_LVL_SKIP)) {
515 for (i = 0; i < TX_MODES; i++)
516 cpi->rd_tx_select_diff[i] += ctx->tx_rd_diff[i];
519 #if CONFIG_INTERNAL_STATS
520 if (frame_is_intra_only(cm)) {
521 static const int kf_mode_index[] = {
523 THR_V_PRED /*V_PRED*/,
524 THR_H_PRED /*H_PRED*/,
525 THR_D45_PRED /*D45_PRED*/,
526 THR_D135_PRED /*D135_PRED*/,
527 THR_D117_PRED /*D117_PRED*/,
528 THR_D153_PRED /*D153_PRED*/,
529 THR_D207_PRED /*D207_PRED*/,
530 THR_D63_PRED /*D63_PRED*/,
533 ++cpi->mode_chosen_counts[kf_mode_index[mbmi->mode]];
535 // Note how often each mode chosen as best
536 ++cpi->mode_chosen_counts[ctx->best_mode_index];
539 if (!frame_is_intra_only(cm)) {
540 if (is_inter_block(mbmi)) {
541 if (mbmi->sb_type < BLOCK_8X8 || mbmi->mode == NEWMV) {
543 for (i = 0; i < 1 + has_second_ref(mbmi); ++i)
544 best_mv[i] = mbmi->ref_mvs[mbmi->ref_frame[i]][0].as_mv;
545 vp9_update_mv_count(cm, xd, best_mv);
548 if (cm->interp_filter == SWITCHABLE) {
549 const int ctx = vp9_get_pred_context_switchable_interp(xd);
550 ++cm->counts.switchable_interp[ctx][mbmi->interp_filter];
554 cpi->rd_comp_pred_diff[SINGLE_REFERENCE] += ctx->single_pred_diff;
555 cpi->rd_comp_pred_diff[COMPOUND_REFERENCE] += ctx->comp_pred_diff;
556 cpi->rd_comp_pred_diff[REFERENCE_MODE_SELECT] += ctx->hybrid_pred_diff;
558 for (i = 0; i < SWITCHABLE_FILTER_CONTEXTS; ++i)
559 cpi->rd_filter_diff[i] += ctx->best_filter_diff[i];
563 void vp9_setup_src_planes(MACROBLOCK *x, const YV12_BUFFER_CONFIG *src,
564 int mi_row, int mi_col) {
565 uint8_t *const buffers[4] = {src->y_buffer, src->u_buffer, src->v_buffer,
567 const int strides[4] = {src->y_stride, src->uv_stride, src->uv_stride,
571 // Set current frame pointer.
572 x->e_mbd.cur_buf = src;
574 for (i = 0; i < MAX_MB_PLANE; i++)
575 setup_pred_plane(&x->plane[i].src, buffers[i], strides[i], mi_row, mi_col,
576 NULL, x->e_mbd.plane[i].subsampling_x,
577 x->e_mbd.plane[i].subsampling_y);
580 static void set_offsets(VP9_COMP *cpi, const TileInfo *const tile,
581 int mi_row, int mi_col, BLOCK_SIZE bsize) {
582 MACROBLOCK *const x = &cpi->mb;
583 VP9_COMMON *const cm = &cpi->common;
584 MACROBLOCKD *const xd = &x->e_mbd;
586 const int idx_str = xd->mode_info_stride * mi_row + mi_col;
587 const int mi_width = num_8x8_blocks_wide_lookup[bsize];
588 const int mi_height = num_8x8_blocks_high_lookup[bsize];
589 const int mb_row = mi_row >> 1;
590 const int mb_col = mi_col >> 1;
591 const int idx_map = mb_row * cm->mb_cols + mb_col;
592 const struct segmentation *const seg = &cm->seg;
594 set_skip_context(xd, cpi->above_context, cpi->left_context, mi_row, mi_col);
596 // Activity map pointer
597 x->mb_activity_ptr = &cpi->mb_activity_map[idx_map];
598 x->active_ptr = cpi->active_map + idx_map;
600 xd->mi_8x8 = cm->mi_grid_visible + idx_str;
601 xd->prev_mi_8x8 = cm->prev_mi_grid_visible + idx_str;
603 xd->last_mi = cm->prev_mi ? xd->prev_mi_8x8[0] : NULL;
605 xd->mi_8x8[0] = cm->mi + idx_str;
607 mbmi = &xd->mi_8x8[0]->mbmi;
609 // Set up destination pointers
610 vp9_setup_dst_planes(xd, get_frame_new_buffer(cm), mi_row, mi_col);
612 // Set up limit values for MV components
613 // mv beyond the range do not produce new/different prediction block
614 x->mv_row_min = -(((mi_row + mi_height) * MI_SIZE) + VP9_INTERP_EXTEND);
615 x->mv_col_min = -(((mi_col + mi_width) * MI_SIZE) + VP9_INTERP_EXTEND);
616 x->mv_row_max = (cm->mi_rows - mi_row) * MI_SIZE + VP9_INTERP_EXTEND;
617 x->mv_col_max = (cm->mi_cols - mi_col) * MI_SIZE + VP9_INTERP_EXTEND;
619 // Set up distance of MB to edge of frame in 1/8th pel units
620 assert(!(mi_col & (mi_width - 1)) && !(mi_row & (mi_height - 1)));
621 set_mi_row_col(xd, tile, mi_row, mi_height, mi_col, mi_width,
622 cm->mi_rows, cm->mi_cols);
624 /* set up source buffers */
625 vp9_setup_src_planes(x, cpi->Source, mi_row, mi_col);
628 x->rddiv = cpi->RDDIV;
629 x->rdmult = cpi->RDMULT;
633 if (cpi->oxcf.aq_mode != VARIANCE_AQ) {
634 const uint8_t *const map = seg->update_map ? cpi->segmentation_map
635 : cm->last_frame_seg_map;
636 mbmi->segment_id = vp9_get_segment_id(cm, map, bsize, mi_row, mi_col);
638 vp9_init_plane_quantizers(cpi, x);
640 if (seg->enabled && cpi->seg0_cnt > 0 &&
641 !vp9_segfeature_active(seg, 0, SEG_LVL_REF_FRAME) &&
642 vp9_segfeature_active(seg, 1, SEG_LVL_REF_FRAME)) {
643 cpi->seg0_progress = (cpi->seg0_idx << 16) / cpi->seg0_cnt;
645 const int y = mb_row & ~3;
646 const int x = mb_col & ~3;
647 const int p16 = ((mb_row & 1) << 1) + (mb_col & 1);
648 const int p32 = ((mb_row & 2) << 2) + ((mb_col & 2) << 1);
649 const int tile_progress = tile->mi_col_start * cm->mb_rows >> 1;
650 const int mb_cols = (tile->mi_col_end - tile->mi_col_start) >> 1;
652 cpi->seg0_progress = ((y * mb_cols + x * 4 + p32 + p16 + tile_progress)
656 x->encode_breakout = cpi->segment_encode_breakout[mbmi->segment_id];
658 mbmi->segment_id = 0;
659 x->encode_breakout = cpi->encode_breakout;
663 static void rd_pick_sb_modes(VP9_COMP *cpi, const TileInfo *const tile,
664 int mi_row, int mi_col,
665 int *totalrate, int64_t *totaldist,
666 BLOCK_SIZE bsize, PICK_MODE_CONTEXT *ctx,
668 VP9_COMMON *const cm = &cpi->common;
669 MACROBLOCK *const x = &cpi->mb;
670 MACROBLOCKD *const xd = &x->e_mbd;
671 struct macroblock_plane *const p = x->plane;
672 struct macroblockd_plane *const pd = xd->plane;
674 int orig_rdmult = x->rdmult;
677 vp9_clear_system_state();
678 rdmult_ratio = 1.0; // avoid uninitialized warnings
680 // Use the lower precision, but faster, 32x32 fdct for mode selection.
681 x->use_lp32x32fdct = 1;
683 if (bsize < BLOCK_8X8) {
684 // When ab_index = 0 all sub-blocks are handled, so for ab_index != 0
685 // there is nothing to be done.
686 if (x->ab_index != 0) {
693 set_offsets(cpi, tile, mi_row, mi_col, bsize);
694 xd->mi_8x8[0]->mbmi.sb_type = bsize;
696 for (i = 0; i < MAX_MB_PLANE; ++i) {
697 p[i].coeff = ctx->coeff_pbuf[i][0];
698 p[i].qcoeff = ctx->qcoeff_pbuf[i][0];
699 pd[i].dqcoeff = ctx->dqcoeff_pbuf[i][0];
700 p[i].eobs = ctx->eobs_pbuf[i][0];
705 // Set to zero to make sure we do not use the previous encoded frame stats
706 xd->mi_8x8[0]->mbmi.skip = 0;
708 x->source_variance = get_sby_perpixel_variance(cpi, x, bsize);
710 if (cpi->oxcf.aq_mode == VARIANCE_AQ) {
711 const int energy = bsize <= BLOCK_16X16 ? x->mb_energy
712 : vp9_block_energy(cpi, x, bsize);
714 if (cm->frame_type == KEY_FRAME ||
715 cpi->refresh_alt_ref_frame ||
716 (cpi->refresh_golden_frame && !cpi->rc.is_src_frame_alt_ref)) {
717 xd->mi_8x8[0]->mbmi.segment_id = vp9_vaq_segment_id(energy);
719 const uint8_t *const map = cm->seg.update_map ? cpi->segmentation_map
720 : cm->last_frame_seg_map;
721 xd->mi_8x8[0]->mbmi.segment_id =
722 vp9_get_segment_id(cm, map, bsize, mi_row, mi_col);
725 rdmult_ratio = vp9_vaq_rdmult_ratio(energy);
726 vp9_init_plane_quantizers(cpi, x);
729 if (cpi->oxcf.tuning == VP8_TUNE_SSIM)
730 activity_masking(cpi, x);
732 if (cpi->oxcf.aq_mode == VARIANCE_AQ) {
733 vp9_clear_system_state();
734 x->rdmult = (int)round(x->rdmult * rdmult_ratio);
735 } else if (cpi->oxcf.aq_mode == COMPLEXITY_AQ) {
736 const int mi_offset = mi_row * cm->mi_cols + mi_col;
737 unsigned char complexity = cpi->complexity_map[mi_offset];
738 const int is_edge = (mi_row <= 1) || (mi_row >= (cm->mi_rows - 2)) ||
739 (mi_col <= 1) || (mi_col >= (cm->mi_cols - 2));
741 if (!is_edge && (complexity > 128)) {
742 x->rdmult = x->rdmult + ((x->rdmult * (complexity - 128)) / 256);
746 // Find best coding mode & reconstruct the MB so it is available
747 // as a predictor for MBs that follow in the SB
748 if (frame_is_intra_only(cm)) {
749 vp9_rd_pick_intra_mode_sb(cpi, x, totalrate, totaldist, bsize, ctx,
752 if (bsize >= BLOCK_8X8)
753 vp9_rd_pick_inter_mode_sb(cpi, x, tile, mi_row, mi_col,
754 totalrate, totaldist, bsize, ctx, best_rd);
756 vp9_rd_pick_inter_mode_sub8x8(cpi, x, tile, mi_row, mi_col, totalrate,
757 totaldist, bsize, ctx, best_rd);
760 if (cpi->oxcf.aq_mode == VARIANCE_AQ) {
761 x->rdmult = orig_rdmult;
762 if (*totalrate != INT_MAX) {
763 vp9_clear_system_state();
764 *totalrate = (int)round(*totalrate * rdmult_ratio);
767 else if (cpi->oxcf.aq_mode == COMPLEXITY_AQ) {
768 x->rdmult = orig_rdmult;
772 static void update_stats(VP9_COMP *cpi) {
773 VP9_COMMON *const cm = &cpi->common;
774 const MACROBLOCK *const x = &cpi->mb;
775 const MACROBLOCKD *const xd = &x->e_mbd;
776 const MODE_INFO *const mi = xd->mi_8x8[0];
777 const MB_MODE_INFO *const mbmi = &mi->mbmi;
779 if (!frame_is_intra_only(cm)) {
780 const int seg_ref_active = vp9_segfeature_active(&cm->seg, mbmi->segment_id,
782 if (!seg_ref_active) {
783 FRAME_COUNTS *const counts = &cm->counts;
784 const int inter_block = is_inter_block(mbmi);
786 counts->intra_inter[vp9_get_intra_inter_context(xd)][inter_block]++;
788 // If the segment reference feature is enabled we have only a single
789 // reference frame allowed for the segment so exclude it from
790 // the reference frame counts used to work out probabilities.
792 const MV_REFERENCE_FRAME ref0 = mbmi->ref_frame[0];
794 if (cm->reference_mode == REFERENCE_MODE_SELECT)
795 counts->comp_inter[vp9_get_reference_mode_context(cm, xd)]
796 [has_second_ref(mbmi)]++;
798 if (has_second_ref(mbmi)) {
799 counts->comp_ref[vp9_get_pred_context_comp_ref_p(cm, xd)]
800 [ref0 == GOLDEN_FRAME]++;
802 counts->single_ref[vp9_get_pred_context_single_ref_p1(xd)][0]
803 [ref0 != LAST_FRAME]++;
804 if (ref0 != LAST_FRAME)
805 counts->single_ref[vp9_get_pred_context_single_ref_p2(xd)][1]
806 [ref0 != GOLDEN_FRAME]++;
813 static BLOCK_SIZE *get_sb_partitioning(MACROBLOCK *x, BLOCK_SIZE bsize) {
816 return &x->sb64_partitioning;
818 return &x->sb_partitioning[x->sb_index];
820 return &x->mb_partitioning[x->sb_index][x->mb_index];
822 return &x->b_partitioning[x->sb_index][x->mb_index][x->b_index];
829 static void restore_context(VP9_COMP *cpi, int mi_row, int mi_col,
830 ENTROPY_CONTEXT a[16 * MAX_MB_PLANE],
831 ENTROPY_CONTEXT l[16 * MAX_MB_PLANE],
832 PARTITION_CONTEXT sa[8], PARTITION_CONTEXT sl[8],
834 MACROBLOCK *const x = &cpi->mb;
835 MACROBLOCKD *const xd = &x->e_mbd;
837 const int num_4x4_blocks_wide = num_4x4_blocks_wide_lookup[bsize];
838 const int num_4x4_blocks_high = num_4x4_blocks_high_lookup[bsize];
839 int mi_width = num_8x8_blocks_wide_lookup[bsize];
840 int mi_height = num_8x8_blocks_high_lookup[bsize];
841 for (p = 0; p < MAX_MB_PLANE; p++) {
843 cpi->above_context[p] + ((mi_col * 2) >> xd->plane[p].subsampling_x),
844 a + num_4x4_blocks_wide * p,
845 (sizeof(ENTROPY_CONTEXT) * num_4x4_blocks_wide) >>
846 xd->plane[p].subsampling_x);
849 + ((mi_row & MI_MASK) * 2 >> xd->plane[p].subsampling_y),
850 l + num_4x4_blocks_high * p,
851 (sizeof(ENTROPY_CONTEXT) * num_4x4_blocks_high) >>
852 xd->plane[p].subsampling_y);
854 vpx_memcpy(cpi->above_seg_context + mi_col, sa,
855 sizeof(*cpi->above_seg_context) * mi_width);
856 vpx_memcpy(cpi->left_seg_context + (mi_row & MI_MASK), sl,
857 sizeof(cpi->left_seg_context[0]) * mi_height);
859 static void save_context(VP9_COMP *cpi, int mi_row, int mi_col,
860 ENTROPY_CONTEXT a[16 * MAX_MB_PLANE],
861 ENTROPY_CONTEXT l[16 * MAX_MB_PLANE],
862 PARTITION_CONTEXT sa[8], PARTITION_CONTEXT sl[8],
864 const MACROBLOCK *const x = &cpi->mb;
865 const MACROBLOCKD *const xd = &x->e_mbd;
867 const int num_4x4_blocks_wide = num_4x4_blocks_wide_lookup[bsize];
868 const int num_4x4_blocks_high = num_4x4_blocks_high_lookup[bsize];
869 int mi_width = num_8x8_blocks_wide_lookup[bsize];
870 int mi_height = num_8x8_blocks_high_lookup[bsize];
872 // buffer the above/left context information of the block in search.
873 for (p = 0; p < MAX_MB_PLANE; ++p) {
875 a + num_4x4_blocks_wide * p,
876 cpi->above_context[p] + (mi_col * 2 >> xd->plane[p].subsampling_x),
877 (sizeof(ENTROPY_CONTEXT) * num_4x4_blocks_wide) >>
878 xd->plane[p].subsampling_x);
880 l + num_4x4_blocks_high * p,
882 + ((mi_row & MI_MASK) * 2 >> xd->plane[p].subsampling_y),
883 (sizeof(ENTROPY_CONTEXT) * num_4x4_blocks_high) >>
884 xd->plane[p].subsampling_y);
886 vpx_memcpy(sa, cpi->above_seg_context + mi_col,
887 sizeof(*cpi->above_seg_context) * mi_width);
888 vpx_memcpy(sl, cpi->left_seg_context + (mi_row & MI_MASK),
889 sizeof(cpi->left_seg_context[0]) * mi_height);
892 static void encode_b(VP9_COMP *cpi, const TileInfo *const tile,
893 TOKENEXTRA **tp, int mi_row, int mi_col,
894 int output_enabled, BLOCK_SIZE bsize) {
895 MACROBLOCK *const x = &cpi->mb;
897 if (bsize < BLOCK_8X8) {
898 // When ab_index = 0 all sub-blocks are handled, so for ab_index != 0
899 // there is nothing to be done.
903 set_offsets(cpi, tile, mi_row, mi_col, bsize);
904 update_state(cpi, get_block_context(x, bsize), bsize, output_enabled);
905 encode_superblock(cpi, tp, output_enabled, mi_row, mi_col, bsize);
907 if (output_enabled) {
910 (*tp)->token = EOSB_TOKEN;
915 static void encode_sb(VP9_COMP *cpi, const TileInfo *const tile,
916 TOKENEXTRA **tp, int mi_row, int mi_col,
917 int output_enabled, BLOCK_SIZE bsize) {
918 VP9_COMMON *const cm = &cpi->common;
919 MACROBLOCK *const x = &cpi->mb;
920 const int bsl = b_width_log2(bsize), hbs = (1 << bsl) / 4;
922 PARTITION_TYPE partition;
925 if (mi_row >= cm->mi_rows || mi_col >= cm->mi_cols)
928 if (bsize >= BLOCK_8X8) {
929 ctx = partition_plane_context(cpi->above_seg_context, cpi->left_seg_context,
930 mi_row, mi_col, bsize);
931 subsize = *get_sb_partitioning(x, bsize);
937 partition = partition_lookup[bsl][subsize];
941 if (output_enabled && bsize >= BLOCK_8X8)
942 cm->counts.partition[ctx][PARTITION_NONE]++;
943 encode_b(cpi, tile, tp, mi_row, mi_col, output_enabled, subsize);
947 cm->counts.partition[ctx][PARTITION_VERT]++;
948 *get_sb_index(x, subsize) = 0;
949 encode_b(cpi, tile, tp, mi_row, mi_col, output_enabled, subsize);
950 if (mi_col + hbs < cm->mi_cols) {
951 *get_sb_index(x, subsize) = 1;
952 encode_b(cpi, tile, tp, mi_row, mi_col + hbs, output_enabled, subsize);
957 cm->counts.partition[ctx][PARTITION_HORZ]++;
958 *get_sb_index(x, subsize) = 0;
959 encode_b(cpi, tile, tp, mi_row, mi_col, output_enabled, subsize);
960 if (mi_row + hbs < cm->mi_rows) {
961 *get_sb_index(x, subsize) = 1;
962 encode_b(cpi, tile, tp, mi_row + hbs, mi_col, output_enabled, subsize);
965 case PARTITION_SPLIT:
966 subsize = get_subsize(bsize, PARTITION_SPLIT);
968 cm->counts.partition[ctx][PARTITION_SPLIT]++;
970 *get_sb_index(x, subsize) = 0;
971 encode_sb(cpi, tile, tp, mi_row, mi_col, output_enabled, subsize);
972 *get_sb_index(x, subsize) = 1;
973 encode_sb(cpi, tile, tp, mi_row, mi_col + hbs, output_enabled, subsize);
974 *get_sb_index(x, subsize) = 2;
975 encode_sb(cpi, tile, tp, mi_row + hbs, mi_col, output_enabled, subsize);
976 *get_sb_index(x, subsize) = 3;
977 encode_sb(cpi, tile, tp, mi_row + hbs, mi_col + hbs, output_enabled,
981 assert("Invalid partition type.");
984 if (partition != PARTITION_SPLIT || bsize == BLOCK_8X8)
985 update_partition_context(cpi->above_seg_context, cpi->left_seg_context,
986 mi_row, mi_col, subsize, bsize);
989 // Check to see if the given partition size is allowed for a specified number
990 // of 8x8 block rows and columns remaining in the image.
991 // If not then return the largest allowed partition size
992 static BLOCK_SIZE find_partition_size(BLOCK_SIZE bsize,
993 int rows_left, int cols_left,
995 if (rows_left <= 0 || cols_left <= 0) {
996 return MIN(bsize, BLOCK_8X8);
998 for (; bsize > 0; bsize -= 3) {
999 *bh = num_8x8_blocks_high_lookup[bsize];
1000 *bw = num_8x8_blocks_wide_lookup[bsize];
1001 if ((*bh <= rows_left) && (*bw <= cols_left)) {
1009 // This function attempts to set all mode info entries in a given SB64
1010 // to the same block partition size.
1011 // However, at the bottom and right borders of the image the requested size
1012 // may not be allowed in which case this code attempts to choose the largest
1013 // allowable partition.
1014 static void set_partitioning(VP9_COMP *cpi, const TileInfo *const tile,
1015 MODE_INFO **mi_8x8, int mi_row, int mi_col,
1017 VP9_COMMON *const cm = &cpi->common;
1018 const int mis = cm->mode_info_stride;
1019 int row8x8_remaining = tile->mi_row_end - mi_row;
1020 int col8x8_remaining = tile->mi_col_end - mi_col;
1021 int block_row, block_col;
1022 MODE_INFO *mi_upper_left = cm->mi + mi_row * mis + mi_col;
1023 int bh = num_8x8_blocks_high_lookup[bsize];
1024 int bw = num_8x8_blocks_wide_lookup[bsize];
1026 assert((row8x8_remaining > 0) && (col8x8_remaining > 0));
1028 // Apply the requested partition size to the SB64 if it is all "in image"
1029 if ((col8x8_remaining >= MI_BLOCK_SIZE) &&
1030 (row8x8_remaining >= MI_BLOCK_SIZE)) {
1031 for (block_row = 0; block_row < MI_BLOCK_SIZE; block_row += bh) {
1032 for (block_col = 0; block_col < MI_BLOCK_SIZE; block_col += bw) {
1033 int index = block_row * mis + block_col;
1034 mi_8x8[index] = mi_upper_left + index;
1035 mi_8x8[index]->mbmi.sb_type = bsize;
1039 // Else this is a partial SB64.
1040 for (block_row = 0; block_row < MI_BLOCK_SIZE; block_row += bh) {
1041 for (block_col = 0; block_col < MI_BLOCK_SIZE; block_col += bw) {
1042 int index = block_row * mis + block_col;
1043 // Find a partition size that fits
1044 bsize = find_partition_size(bsize,
1045 (row8x8_remaining - block_row),
1046 (col8x8_remaining - block_col), &bh, &bw);
1047 mi_8x8[index] = mi_upper_left + index;
1048 mi_8x8[index]->mbmi.sb_type = bsize;
1054 static void copy_partitioning(VP9_COMMON *cm, MODE_INFO **mi_8x8,
1055 MODE_INFO **prev_mi_8x8) {
1056 const int mis = cm->mode_info_stride;
1057 int block_row, block_col;
1059 for (block_row = 0; block_row < 8; ++block_row) {
1060 for (block_col = 0; block_col < 8; ++block_col) {
1061 MODE_INFO *const prev_mi = prev_mi_8x8[block_row * mis + block_col];
1062 const BLOCK_SIZE sb_type = prev_mi ? prev_mi->mbmi.sb_type : 0;
1064 const ptrdiff_t offset = prev_mi - cm->prev_mi;
1065 mi_8x8[block_row * mis + block_col] = cm->mi + offset;
1066 mi_8x8[block_row * mis + block_col]->mbmi.sb_type = sb_type;
1072 static int sb_has_motion(const VP9_COMMON *cm, MODE_INFO **prev_mi_8x8) {
1073 const int mis = cm->mode_info_stride;
1074 int block_row, block_col;
1077 for (block_row = 0; block_row < 8; ++block_row) {
1078 for (block_col = 0; block_col < 8; ++block_col) {
1079 const MODE_INFO *prev_mi = prev_mi_8x8[block_row * mis + block_col];
1081 if (abs(prev_mi->mbmi.mv[0].as_mv.row) >= 8 ||
1082 abs(prev_mi->mbmi.mv[0].as_mv.col) >= 8)
1091 static void update_state_rt(VP9_COMP *cpi, const PICK_MODE_CONTEXT *ctx) {
1093 VP9_COMMON *const cm = &cpi->common;
1094 MACROBLOCK *const x = &cpi->mb;
1095 MACROBLOCKD *const xd = &x->e_mbd;
1096 MB_MODE_INFO *const mbmi = &xd->mi_8x8[0]->mbmi;
1098 x->skip = ctx->skip;
1100 #if CONFIG_INTERNAL_STATS
1101 if (frame_is_intra_only(cm)) {
1102 static const int kf_mode_index[] = {
1104 THR_V_PRED /*V_PRED*/,
1105 THR_H_PRED /*H_PRED*/,
1106 THR_D45_PRED /*D45_PRED*/,
1107 THR_D135_PRED /*D135_PRED*/,
1108 THR_D117_PRED /*D117_PRED*/,
1109 THR_D153_PRED /*D153_PRED*/,
1110 THR_D207_PRED /*D207_PRED*/,
1111 THR_D63_PRED /*D63_PRED*/,
1114 ++cpi->mode_chosen_counts[kf_mode_index[mbmi->mode]];
1116 // Note how often each mode chosen as best
1117 ++cpi->mode_chosen_counts[ctx->best_mode_index];
1120 if (!frame_is_intra_only(cm)) {
1121 if (is_inter_block(mbmi)) {
1122 if (mbmi->sb_type < BLOCK_8X8 || mbmi->mode == NEWMV) {
1124 for (i = 0; i < 1 + has_second_ref(mbmi); ++i)
1125 best_mv[i] = mbmi->ref_mvs[mbmi->ref_frame[i]][0].as_mv;
1126 vp9_update_mv_count(cm, xd, best_mv);
1129 if (cm->interp_filter == SWITCHABLE) {
1130 const int pred_ctx = vp9_get_pred_context_switchable_interp(xd);
1131 ++cm->counts.switchable_interp[pred_ctx][mbmi->interp_filter];
1137 static void encode_b_rt(VP9_COMP *cpi, const TileInfo *const tile,
1138 TOKENEXTRA **tp, int mi_row, int mi_col,
1139 int output_enabled, BLOCK_SIZE bsize) {
1140 MACROBLOCK *const x = &cpi->mb;
1142 if (bsize < BLOCK_8X8) {
1143 // When ab_index = 0 all sub-blocks are handled, so for ab_index != 0
1144 // there is nothing to be done.
1145 if (x->ab_index > 0)
1148 set_offsets(cpi, tile, mi_row, mi_col, bsize);
1149 update_state_rt(cpi, get_block_context(x, bsize));
1151 encode_superblock(cpi, tp, output_enabled, mi_row, mi_col, bsize);
1154 (*tp)->token = EOSB_TOKEN;
1158 static void encode_sb_rt(VP9_COMP *cpi, const TileInfo *const tile,
1159 TOKENEXTRA **tp, int mi_row, int mi_col,
1160 int output_enabled, BLOCK_SIZE bsize) {
1161 VP9_COMMON *const cm = &cpi->common;
1162 MACROBLOCK *const x = &cpi->mb;
1163 const int bsl = b_width_log2(bsize), hbs = (1 << bsl) / 4;
1165 PARTITION_TYPE partition;
1168 if (mi_row >= cm->mi_rows || mi_col >= cm->mi_cols)
1171 if (bsize >= BLOCK_8X8) {
1172 MACROBLOCKD *const xd = &cpi->mb.e_mbd;
1173 const int idx_str = xd->mode_info_stride * mi_row + mi_col;
1174 MODE_INFO ** mi_8x8 = cm->mi_grid_visible + idx_str;
1175 ctx = partition_plane_context(cpi->above_seg_context, cpi->left_seg_context,
1176 mi_row, mi_col, bsize);
1177 subsize = mi_8x8[0]->mbmi.sb_type;
1180 subsize = BLOCK_4X4;
1183 partition = partition_lookup[bsl][subsize];
1185 switch (partition) {
1186 case PARTITION_NONE:
1187 if (output_enabled && bsize >= BLOCK_8X8)
1188 cm->counts.partition[ctx][PARTITION_NONE]++;
1189 encode_b_rt(cpi, tile, tp, mi_row, mi_col, output_enabled, subsize);
1191 case PARTITION_VERT:
1193 cm->counts.partition[ctx][PARTITION_VERT]++;
1194 *get_sb_index(x, subsize) = 0;
1195 encode_b_rt(cpi, tile, tp, mi_row, mi_col, output_enabled, subsize);
1196 if (mi_col + hbs < cm->mi_cols) {
1197 *get_sb_index(x, subsize) = 1;
1198 encode_b_rt(cpi, tile, tp, mi_row, mi_col + hbs, output_enabled,
1202 case PARTITION_HORZ:
1204 cm->counts.partition[ctx][PARTITION_HORZ]++;
1205 *get_sb_index(x, subsize) = 0;
1206 encode_b_rt(cpi, tile, tp, mi_row, mi_col, output_enabled, subsize);
1207 if (mi_row + hbs < cm->mi_rows) {
1208 *get_sb_index(x, subsize) = 1;
1209 encode_b_rt(cpi, tile, tp, mi_row + hbs, mi_col, output_enabled,
1213 case PARTITION_SPLIT:
1214 subsize = get_subsize(bsize, PARTITION_SPLIT);
1216 cm->counts.partition[ctx][PARTITION_SPLIT]++;
1218 *get_sb_index(x, subsize) = 0;
1219 encode_sb_rt(cpi, tile, tp, mi_row, mi_col, output_enabled, subsize);
1220 *get_sb_index(x, subsize) = 1;
1221 encode_sb_rt(cpi, tile, tp, mi_row, mi_col + hbs, output_enabled,
1223 *get_sb_index(x, subsize) = 2;
1224 encode_sb_rt(cpi, tile, tp, mi_row + hbs, mi_col, output_enabled,
1226 *get_sb_index(x, subsize) = 3;
1227 encode_sb_rt(cpi, tile, tp, mi_row + hbs, mi_col + hbs, output_enabled,
1231 assert("Invalid partition type.");
1234 if (partition != PARTITION_SPLIT || bsize == BLOCK_8X8)
1235 update_partition_context(cpi->above_seg_context, cpi->left_seg_context,
1236 mi_row, mi_col, subsize, bsize);
1239 static void rd_use_partition(VP9_COMP *cpi,
1240 const TileInfo *const tile,
1242 TOKENEXTRA **tp, int mi_row, int mi_col,
1243 BLOCK_SIZE bsize, int *rate, int64_t *dist,
1245 VP9_COMMON *const cm = &cpi->common;
1246 MACROBLOCK *const x = &cpi->mb;
1247 const int mis = cm->mode_info_stride;
1248 const int bsl = b_width_log2(bsize);
1249 const int num_4x4_blocks_wide = num_4x4_blocks_wide_lookup[bsize];
1250 const int num_4x4_blocks_high = num_4x4_blocks_high_lookup[bsize];
1251 const int ms = num_4x4_blocks_wide / 2;
1252 const int mh = num_4x4_blocks_high / 2;
1253 const int bss = (1 << bsl) / 4;
1255 PARTITION_TYPE partition = PARTITION_NONE;
1257 ENTROPY_CONTEXT l[16 * MAX_MB_PLANE], a[16 * MAX_MB_PLANE];
1258 PARTITION_CONTEXT sl[8], sa[8];
1259 int last_part_rate = INT_MAX;
1260 int64_t last_part_dist = INT64_MAX;
1261 int64_t last_part_rd = INT64_MAX;
1262 int none_rate = INT_MAX;
1263 int64_t none_dist = INT64_MAX;
1264 int64_t none_rd = INT64_MAX;
1265 int chosen_rate = INT_MAX;
1266 int64_t chosen_dist = INT64_MAX;
1267 int64_t chosen_rd = INT64_MAX;
1268 BLOCK_SIZE sub_subsize = BLOCK_4X4;
1269 int splits_below = 0;
1270 BLOCK_SIZE bs_type = mi_8x8[0]->mbmi.sb_type;
1272 if (mi_row >= cm->mi_rows || mi_col >= cm->mi_cols)
1275 partition = partition_lookup[bsl][bs_type];
1276 subsize = get_subsize(bsize, partition);
1278 if (bsize < BLOCK_8X8) {
1279 // When ab_index = 0 all sub-blocks are handled, so for ab_index != 0
1280 // there is nothing to be done.
1281 if (x->ab_index != 0) {
1287 *(get_sb_partitioning(x, bsize)) = subsize;
1289 save_context(cpi, mi_row, mi_col, a, l, sa, sl, bsize);
1291 if (bsize == BLOCK_16X16) {
1292 set_offsets(cpi, tile, mi_row, mi_col, bsize);
1293 x->mb_energy = vp9_block_energy(cpi, x, bsize);
1296 if (cpi->sf.partition_search_type == SEARCH_PARTITION &&
1297 cpi->sf.adjust_partitioning_from_last_frame) {
1298 // Check if any of the sub blocks are further split.
1299 if (partition == PARTITION_SPLIT && subsize > BLOCK_8X8) {
1300 sub_subsize = get_subsize(subsize, PARTITION_SPLIT);
1302 for (i = 0; i < 4; i++) {
1303 int jj = i >> 1, ii = i & 0x01;
1304 MODE_INFO * this_mi = mi_8x8[jj * bss * mis + ii * bss];
1305 if (this_mi && this_mi->mbmi.sb_type >= sub_subsize) {
1311 // If partition is not none try none unless each of the 4 splits are split
1313 if (partition != PARTITION_NONE && !splits_below &&
1314 mi_row + (ms >> 1) < cm->mi_rows &&
1315 mi_col + (ms >> 1) < cm->mi_cols) {
1316 *(get_sb_partitioning(x, bsize)) = bsize;
1317 rd_pick_sb_modes(cpi, tile, mi_row, mi_col, &none_rate, &none_dist, bsize,
1318 get_block_context(x, bsize), INT64_MAX);
1320 pl = partition_plane_context(cpi->above_seg_context,
1321 cpi->left_seg_context,
1322 mi_row, mi_col, bsize);
1324 if (none_rate < INT_MAX) {
1325 none_rate += x->partition_cost[pl][PARTITION_NONE];
1326 none_rd = RDCOST(x->rdmult, x->rddiv, none_rate, none_dist);
1329 restore_context(cpi, mi_row, mi_col, a, l, sa, sl, bsize);
1330 mi_8x8[0]->mbmi.sb_type = bs_type;
1331 *(get_sb_partitioning(x, bsize)) = subsize;
1335 switch (partition) {
1336 case PARTITION_NONE:
1337 rd_pick_sb_modes(cpi, tile, mi_row, mi_col, &last_part_rate,
1338 &last_part_dist, bsize,
1339 get_block_context(x, bsize), INT64_MAX);
1341 case PARTITION_HORZ:
1342 *get_sb_index(x, subsize) = 0;
1343 rd_pick_sb_modes(cpi, tile, mi_row, mi_col, &last_part_rate,
1344 &last_part_dist, subsize,
1345 get_block_context(x, subsize), INT64_MAX);
1346 if (last_part_rate != INT_MAX &&
1347 bsize >= BLOCK_8X8 && mi_row + (mh >> 1) < cm->mi_rows) {
1350 update_state(cpi, get_block_context(x, subsize), subsize, 0);
1351 encode_superblock(cpi, tp, 0, mi_row, mi_col, subsize);
1352 *get_sb_index(x, subsize) = 1;
1353 rd_pick_sb_modes(cpi, tile, mi_row + (ms >> 1), mi_col, &rt, &dt,
1354 subsize, get_block_context(x, subsize), INT64_MAX);
1355 if (rt == INT_MAX || dt == INT64_MAX) {
1356 last_part_rate = INT_MAX;
1357 last_part_dist = INT64_MAX;
1361 last_part_rate += rt;
1362 last_part_dist += dt;
1365 case PARTITION_VERT:
1366 *get_sb_index(x, subsize) = 0;
1367 rd_pick_sb_modes(cpi, tile, mi_row, mi_col, &last_part_rate,
1368 &last_part_dist, subsize,
1369 get_block_context(x, subsize), INT64_MAX);
1370 if (last_part_rate != INT_MAX &&
1371 bsize >= BLOCK_8X8 && mi_col + (ms >> 1) < cm->mi_cols) {
1374 update_state(cpi, get_block_context(x, subsize), subsize, 0);
1375 encode_superblock(cpi, tp, 0, mi_row, mi_col, subsize);
1376 *get_sb_index(x, subsize) = 1;
1377 rd_pick_sb_modes(cpi, tile, mi_row, mi_col + (ms >> 1), &rt, &dt,
1378 subsize, get_block_context(x, subsize), INT64_MAX);
1379 if (rt == INT_MAX || dt == INT64_MAX) {
1380 last_part_rate = INT_MAX;
1381 last_part_dist = INT64_MAX;
1384 last_part_rate += rt;
1385 last_part_dist += dt;
1388 case PARTITION_SPLIT:
1392 for (i = 0; i < 4; i++) {
1393 int x_idx = (i & 1) * (ms >> 1);
1394 int y_idx = (i >> 1) * (ms >> 1);
1395 int jj = i >> 1, ii = i & 0x01;
1399 if ((mi_row + y_idx >= cm->mi_rows) || (mi_col + x_idx >= cm->mi_cols))
1402 *get_sb_index(x, subsize) = i;
1404 rd_use_partition(cpi, tile, mi_8x8 + jj * bss * mis + ii * bss, tp,
1405 mi_row + y_idx, mi_col + x_idx, subsize, &rt, &dt,
1407 if (rt == INT_MAX || dt == INT64_MAX) {
1408 last_part_rate = INT_MAX;
1409 last_part_dist = INT64_MAX;
1412 last_part_rate += rt;
1413 last_part_dist += dt;
1420 pl = partition_plane_context(cpi->above_seg_context, cpi->left_seg_context,
1421 mi_row, mi_col, bsize);
1422 if (last_part_rate < INT_MAX) {
1423 last_part_rate += x->partition_cost[pl][partition];
1424 last_part_rd = RDCOST(x->rdmult, x->rddiv, last_part_rate, last_part_dist);
1427 if (cpi->sf.adjust_partitioning_from_last_frame
1428 && cpi->sf.partition_search_type == SEARCH_PARTITION
1429 && partition != PARTITION_SPLIT && bsize > BLOCK_8X8
1430 && (mi_row + ms < cm->mi_rows || mi_row + (ms >> 1) == cm->mi_rows)
1431 && (mi_col + ms < cm->mi_cols || mi_col + (ms >> 1) == cm->mi_cols)) {
1432 BLOCK_SIZE split_subsize = get_subsize(bsize, PARTITION_SPLIT);
1435 restore_context(cpi, mi_row, mi_col, a, l, sa, sl, bsize);
1438 for (i = 0; i < 4; i++) {
1439 int x_idx = (i & 1) * (num_4x4_blocks_wide >> 2);
1440 int y_idx = (i >> 1) * (num_4x4_blocks_wide >> 2);
1443 ENTROPY_CONTEXT l[16 * MAX_MB_PLANE], a[16 * MAX_MB_PLANE];
1444 PARTITION_CONTEXT sl[8], sa[8];
1446 if ((mi_row + y_idx >= cm->mi_rows) || (mi_col + x_idx >= cm->mi_cols))
1449 *get_sb_index(x, split_subsize) = i;
1450 *get_sb_partitioning(x, bsize) = split_subsize;
1451 *get_sb_partitioning(x, split_subsize) = split_subsize;
1453 save_context(cpi, mi_row, mi_col, a, l, sa, sl, bsize);
1455 rd_pick_sb_modes(cpi, tile, mi_row + y_idx, mi_col + x_idx, &rt, &dt,
1456 split_subsize, get_block_context(x, split_subsize),
1459 restore_context(cpi, mi_row, mi_col, a, l, sa, sl, bsize);
1461 if (rt == INT_MAX || dt == INT64_MAX) {
1462 chosen_rate = INT_MAX;
1463 chosen_dist = INT64_MAX;
1471 encode_sb(cpi, tile, tp, mi_row + y_idx, mi_col + x_idx, 0,
1474 pl = partition_plane_context(cpi->above_seg_context,
1475 cpi->left_seg_context,
1476 mi_row + y_idx, mi_col + x_idx,
1478 chosen_rate += x->partition_cost[pl][PARTITION_NONE];
1480 pl = partition_plane_context(cpi->above_seg_context, cpi->left_seg_context,
1481 mi_row, mi_col, bsize);
1482 if (chosen_rate < INT_MAX) {
1483 chosen_rate += x->partition_cost[pl][PARTITION_SPLIT];
1484 chosen_rd = RDCOST(x->rdmult, x->rddiv, chosen_rate, chosen_dist);
1488 // If last_part is better set the partitioning to that...
1489 if (last_part_rd < chosen_rd) {
1490 mi_8x8[0]->mbmi.sb_type = bsize;
1491 if (bsize >= BLOCK_8X8)
1492 *(get_sb_partitioning(x, bsize)) = subsize;
1493 chosen_rate = last_part_rate;
1494 chosen_dist = last_part_dist;
1495 chosen_rd = last_part_rd;
1497 // If none was better set the partitioning to that...
1498 if (none_rd < chosen_rd) {
1499 if (bsize >= BLOCK_8X8)
1500 *(get_sb_partitioning(x, bsize)) = bsize;
1501 chosen_rate = none_rate;
1502 chosen_dist = none_dist;
1505 restore_context(cpi, mi_row, mi_col, a, l, sa, sl, bsize);
1507 // We must have chosen a partitioning and encoding or we'll fail later on.
1508 // No other opportunities for success.
1509 if ( bsize == BLOCK_64X64)
1510 assert(chosen_rate < INT_MAX && chosen_dist < INT64_MAX);
1513 int output_enabled = (bsize == BLOCK_64X64);
1515 // Check the projected output rate for this SB against it's target
1516 // and and if necessary apply a Q delta using segmentation to get
1517 // closer to the target.
1518 if ((cpi->oxcf.aq_mode == COMPLEXITY_AQ) && cm->seg.update_map) {
1519 select_in_frame_q_segment(cpi, mi_row, mi_col,
1520 output_enabled, chosen_rate);
1523 encode_sb(cpi, tile, tp, mi_row, mi_col, output_enabled, bsize);
1526 *rate = chosen_rate;
1527 *dist = chosen_dist;
1530 static const BLOCK_SIZE min_partition_size[BLOCK_SIZES] = {
1531 BLOCK_4X4, BLOCK_4X4, BLOCK_4X4,
1532 BLOCK_4X4, BLOCK_4X4, BLOCK_4X4,
1533 BLOCK_8X8, BLOCK_8X8, BLOCK_8X8,
1534 BLOCK_16X16, BLOCK_16X16, BLOCK_16X16,
1538 static const BLOCK_SIZE max_partition_size[BLOCK_SIZES] = {
1539 BLOCK_8X8, BLOCK_16X16, BLOCK_16X16,
1540 BLOCK_16X16, BLOCK_32X32, BLOCK_32X32,
1541 BLOCK_32X32, BLOCK_64X64, BLOCK_64X64,
1542 BLOCK_64X64, BLOCK_64X64, BLOCK_64X64,
1546 // Look at all the mode_info entries for blocks that are part of this
1547 // partition and find the min and max values for sb_type.
1548 // At the moment this is designed to work on a 64x64 SB but could be
1549 // adjusted to use a size parameter.
1551 // The min and max are assumed to have been initialized prior to calling this
1552 // function so repeat calls can accumulate a min and max of more than one sb64.
1553 static void get_sb_partition_size_range(VP9_COMP *cpi, MODE_INFO ** mi_8x8,
1554 BLOCK_SIZE * min_block_size,
1555 BLOCK_SIZE * max_block_size ) {
1556 MACROBLOCKD *const xd = &cpi->mb.e_mbd;
1557 int sb_width_in_blocks = MI_BLOCK_SIZE;
1558 int sb_height_in_blocks = MI_BLOCK_SIZE;
1562 // Check the sb_type for each block that belongs to this region.
1563 for (i = 0; i < sb_height_in_blocks; ++i) {
1564 for (j = 0; j < sb_width_in_blocks; ++j) {
1565 MODE_INFO * mi = mi_8x8[index+j];
1566 BLOCK_SIZE sb_type = mi ? mi->mbmi.sb_type : 0;
1567 *min_block_size = MIN(*min_block_size, sb_type);
1568 *max_block_size = MAX(*max_block_size, sb_type);
1570 index += xd->mode_info_stride;
1574 // Next square block size less or equal than current block size.
1575 static const BLOCK_SIZE next_square_size[BLOCK_SIZES] = {
1576 BLOCK_4X4, BLOCK_4X4, BLOCK_4X4,
1577 BLOCK_8X8, BLOCK_8X8, BLOCK_8X8,
1578 BLOCK_16X16, BLOCK_16X16, BLOCK_16X16,
1579 BLOCK_32X32, BLOCK_32X32, BLOCK_32X32,
1583 // Look at neighboring blocks and set a min and max partition size based on
1585 static void rd_auto_partition_range(VP9_COMP *cpi, const TileInfo *const tile,
1587 BLOCK_SIZE *min_block_size,
1588 BLOCK_SIZE *max_block_size) {
1589 VP9_COMMON * const cm = &cpi->common;
1590 MACROBLOCKD *const xd = &cpi->mb.e_mbd;
1591 MODE_INFO ** mi_8x8 = xd->mi_8x8;
1592 MODE_INFO ** prev_mi_8x8 = xd->prev_mi_8x8;
1594 const int left_in_image = xd->left_available && mi_8x8[-1];
1595 const int above_in_image = xd->up_available &&
1596 mi_8x8[-xd->mode_info_stride];
1597 MODE_INFO ** above_sb64_mi_8x8;
1598 MODE_INFO ** left_sb64_mi_8x8;
1600 int row8x8_remaining = tile->mi_row_end - row;
1601 int col8x8_remaining = tile->mi_col_end - col;
1604 // Trap case where we do not have a prediction.
1605 if (!left_in_image && !above_in_image &&
1606 ((cm->frame_type == KEY_FRAME) || !cm->prev_mi)) {
1607 *min_block_size = BLOCK_4X4;
1608 *max_block_size = BLOCK_64X64;
1610 // Default "min to max" and "max to min"
1611 *min_block_size = BLOCK_64X64;
1612 *max_block_size = BLOCK_4X4;
1614 // NOTE: each call to get_sb_partition_size_range() uses the previous
1615 // passed in values for min and max as a starting point.
1617 // Find the min and max partition used in previous frame at this location
1618 if (cm->prev_mi && (cm->frame_type != KEY_FRAME)) {
1619 get_sb_partition_size_range(cpi, prev_mi_8x8,
1620 min_block_size, max_block_size);
1623 // Find the min and max partition sizes used in the left SB64
1624 if (left_in_image) {
1625 left_sb64_mi_8x8 = &mi_8x8[-MI_BLOCK_SIZE];
1626 get_sb_partition_size_range(cpi, left_sb64_mi_8x8,
1627 min_block_size, max_block_size);
1630 // Find the min and max partition sizes used in the above SB64.
1631 if (above_in_image) {
1632 above_sb64_mi_8x8 = &mi_8x8[-xd->mode_info_stride * MI_BLOCK_SIZE];
1633 get_sb_partition_size_range(cpi, above_sb64_mi_8x8,
1634 min_block_size, max_block_size);
1638 // adjust observed min and max
1639 if (cpi->sf.auto_min_max_partition_size == RELAXED_NEIGHBORING_MIN_MAX) {
1640 *min_block_size = min_partition_size[*min_block_size];
1641 *max_block_size = max_partition_size[*max_block_size];
1644 // Check border cases where max and min from neighbours may not be legal.
1645 *max_block_size = find_partition_size(*max_block_size,
1646 row8x8_remaining, col8x8_remaining,
1648 *min_block_size = MIN(*min_block_size, *max_block_size);
1650 // When use_square_partition_only is true, make sure at least one square
1651 // partition is allowed by selecting the next smaller square size as
1653 if (cpi->sf.use_square_partition_only &&
1654 (*max_block_size - *min_block_size) < 2) {
1655 *min_block_size = next_square_size[*min_block_size];
1659 static INLINE void store_pred_mv(MACROBLOCK *x, PICK_MODE_CONTEXT *ctx) {
1660 vpx_memcpy(ctx->pred_mv, x->pred_mv, sizeof(x->pred_mv));
1663 static INLINE void load_pred_mv(MACROBLOCK *x, PICK_MODE_CONTEXT *ctx) {
1664 vpx_memcpy(x->pred_mv, ctx->pred_mv, sizeof(x->pred_mv));
1667 // TODO(jingning,jimbankoski,rbultje): properly skip partition types that are
1668 // unlikely to be selected depending on previous rate-distortion optimization
1669 // results, for encoding speed-up.
1670 static void rd_pick_partition(VP9_COMP *cpi, const TileInfo *const tile,
1671 TOKENEXTRA **tp, int mi_row,
1672 int mi_col, BLOCK_SIZE bsize, int *rate,
1673 int64_t *dist, int do_recon, int64_t best_rd) {
1674 VP9_COMMON *const cm = &cpi->common;
1675 MACROBLOCK *const x = &cpi->mb;
1676 const int ms = num_8x8_blocks_wide_lookup[bsize] / 2;
1677 ENTROPY_CONTEXT l[16 * MAX_MB_PLANE], a[16 * MAX_MB_PLANE];
1678 PARTITION_CONTEXT sl[8], sa[8];
1679 TOKENEXTRA *tp_orig = *tp;
1682 int this_rate, sum_rate = 0, best_rate = INT_MAX;
1683 int64_t this_dist, sum_dist = 0, best_dist = INT64_MAX;
1685 int do_split = bsize >= BLOCK_8X8;
1687 // Override skipping rectangular partition operations for edge blocks
1688 const int force_horz_split = (mi_row + ms >= cm->mi_rows);
1689 const int force_vert_split = (mi_col + ms >= cm->mi_cols);
1690 const int xss = x->e_mbd.plane[1].subsampling_x;
1691 const int yss = x->e_mbd.plane[1].subsampling_y;
1693 int partition_none_allowed = !force_horz_split && !force_vert_split;
1694 int partition_horz_allowed = !force_vert_split && yss <= xss &&
1696 int partition_vert_allowed = !force_horz_split && xss <= yss &&
1700 if (bsize < BLOCK_8X8) {
1701 // When ab_index = 0 all sub-blocks are handled, so for ab_index != 0
1702 // there is nothing to be done.
1703 if (x->ab_index != 0) {
1709 assert(num_8x8_blocks_wide_lookup[bsize] ==
1710 num_8x8_blocks_high_lookup[bsize]);
1712 if (bsize == BLOCK_16X16) {
1713 set_offsets(cpi, tile, mi_row, mi_col, bsize);
1714 x->mb_energy = vp9_block_energy(cpi, x, bsize);
1717 // Determine partition types in search according to the speed features.
1718 // The threshold set here has to be of square block size.
1719 if (cpi->sf.auto_min_max_partition_size) {
1720 partition_none_allowed &= (bsize <= cpi->sf.max_partition_size &&
1721 bsize >= cpi->sf.min_partition_size);
1722 partition_horz_allowed &= ((bsize <= cpi->sf.max_partition_size &&
1723 bsize > cpi->sf.min_partition_size) ||
1725 partition_vert_allowed &= ((bsize <= cpi->sf.max_partition_size &&
1726 bsize > cpi->sf.min_partition_size) ||
1728 do_split &= bsize > cpi->sf.min_partition_size;
1730 if (cpi->sf.use_square_partition_only) {
1731 partition_horz_allowed &= force_horz_split;
1732 partition_vert_allowed &= force_vert_split;
1735 save_context(cpi, mi_row, mi_col, a, l, sa, sl, bsize);
1737 if (cpi->sf.disable_split_var_thresh && partition_none_allowed) {
1738 unsigned int source_variancey;
1739 vp9_setup_src_planes(x, cpi->Source, mi_row, mi_col);
1740 source_variancey = get_sby_perpixel_variance(cpi, x, bsize);
1741 if (source_variancey < cpi->sf.disable_split_var_thresh) {
1743 if (source_variancey < cpi->sf.disable_split_var_thresh / 2)
1749 if (partition_none_allowed) {
1750 rd_pick_sb_modes(cpi, tile, mi_row, mi_col, &this_rate, &this_dist, bsize,
1751 get_block_context(x, bsize), best_rd);
1752 if (this_rate != INT_MAX) {
1753 if (bsize >= BLOCK_8X8) {
1754 pl = partition_plane_context(cpi->above_seg_context,
1755 cpi->left_seg_context,
1756 mi_row, mi_col, bsize);
1757 this_rate += x->partition_cost[pl][PARTITION_NONE];
1759 sum_rd = RDCOST(x->rdmult, x->rddiv, this_rate, this_dist);
1760 if (sum_rd < best_rd) {
1761 int64_t stop_thresh = 4096;
1762 int64_t stop_thresh_rd;
1764 best_rate = this_rate;
1765 best_dist = this_dist;
1767 if (bsize >= BLOCK_8X8)
1768 *(get_sb_partitioning(x, bsize)) = bsize;
1770 // Adjust threshold according to partition size.
1771 stop_thresh >>= 8 - (b_width_log2_lookup[bsize] +
1772 b_height_log2_lookup[bsize]);
1774 stop_thresh_rd = RDCOST(x->rdmult, x->rddiv, 0, stop_thresh);
1775 // If obtained distortion is very small, choose current partition
1776 // and stop splitting.
1777 if (!x->e_mbd.lossless && best_rd < stop_thresh_rd) {
1783 restore_context(cpi, mi_row, mi_col, a, l, sa, sl, bsize);
1786 // store estimated motion vector
1787 if (cpi->sf.adaptive_motion_search)
1788 store_pred_mv(x, get_block_context(x, bsize));
1792 // TODO(jingning): use the motion vectors given by the above search as
1793 // the starting point of motion search in the following partition type check.
1795 subsize = get_subsize(bsize, PARTITION_SPLIT);
1796 for (i = 0; i < 4 && sum_rd < best_rd; ++i) {
1797 const int x_idx = (i & 1) * ms;
1798 const int y_idx = (i >> 1) * ms;
1800 if (mi_row + y_idx >= cm->mi_rows || mi_col + x_idx >= cm->mi_cols)
1803 *get_sb_index(x, subsize) = i;
1804 if (cpi->sf.adaptive_motion_search)
1805 load_pred_mv(x, get_block_context(x, bsize));
1806 if (cpi->sf.adaptive_pred_interp_filter && bsize == BLOCK_8X8 &&
1807 partition_none_allowed)
1808 get_block_context(x, subsize)->pred_interp_filter =
1809 get_block_context(x, bsize)->mic.mbmi.interp_filter;
1810 rd_pick_partition(cpi, tile, tp, mi_row + y_idx, mi_col + x_idx, subsize,
1811 &this_rate, &this_dist, i != 3, best_rd - sum_rd);
1813 if (this_rate == INT_MAX) {
1816 sum_rate += this_rate;
1817 sum_dist += this_dist;
1818 sum_rd = RDCOST(x->rdmult, x->rddiv, sum_rate, sum_dist);
1821 if (sum_rd < best_rd && i == 4) {
1822 pl = partition_plane_context(cpi->above_seg_context,
1823 cpi->left_seg_context,
1824 mi_row, mi_col, bsize);
1825 sum_rate += x->partition_cost[pl][PARTITION_SPLIT];
1826 sum_rd = RDCOST(x->rdmult, x->rddiv, sum_rate, sum_dist);
1827 if (sum_rd < best_rd) {
1828 best_rate = sum_rate;
1829 best_dist = sum_dist;
1831 *(get_sb_partitioning(x, bsize)) = subsize;
1834 // skip rectangular partition test when larger block size
1835 // gives better rd cost
1836 if (cpi->sf.less_rectangular_check)
1837 do_rect &= !partition_none_allowed;
1839 restore_context(cpi, mi_row, mi_col, a, l, sa, sl, bsize);
1843 if (partition_horz_allowed && do_rect) {
1844 subsize = get_subsize(bsize, PARTITION_HORZ);
1845 *get_sb_index(x, subsize) = 0;
1846 if (cpi->sf.adaptive_motion_search)
1847 load_pred_mv(x, get_block_context(x, bsize));
1848 if (cpi->sf.adaptive_pred_interp_filter && bsize == BLOCK_8X8 &&
1849 partition_none_allowed)
1850 get_block_context(x, subsize)->pred_interp_filter =
1851 get_block_context(x, bsize)->mic.mbmi.interp_filter;
1852 rd_pick_sb_modes(cpi, tile, mi_row, mi_col, &sum_rate, &sum_dist, subsize,
1853 get_block_context(x, subsize), best_rd);
1854 sum_rd = RDCOST(x->rdmult, x->rddiv, sum_rate, sum_dist);
1856 if (sum_rd < best_rd && mi_row + ms < cm->mi_rows) {
1857 update_state(cpi, get_block_context(x, subsize), subsize, 0);
1858 encode_superblock(cpi, tp, 0, mi_row, mi_col, subsize);
1860 *get_sb_index(x, subsize) = 1;
1861 if (cpi->sf.adaptive_motion_search)
1862 load_pred_mv(x, get_block_context(x, bsize));
1863 if (cpi->sf.adaptive_pred_interp_filter && bsize == BLOCK_8X8 &&
1864 partition_none_allowed)
1865 get_block_context(x, subsize)->pred_interp_filter =
1866 get_block_context(x, bsize)->mic.mbmi.interp_filter;
1867 rd_pick_sb_modes(cpi, tile, mi_row + ms, mi_col, &this_rate,
1868 &this_dist, subsize, get_block_context(x, subsize),
1870 if (this_rate == INT_MAX) {
1873 sum_rate += this_rate;
1874 sum_dist += this_dist;
1875 sum_rd = RDCOST(x->rdmult, x->rddiv, sum_rate, sum_dist);
1878 if (sum_rd < best_rd) {
1879 pl = partition_plane_context(cpi->above_seg_context,
1880 cpi->left_seg_context,
1881 mi_row, mi_col, bsize);
1882 sum_rate += x->partition_cost[pl][PARTITION_HORZ];
1883 sum_rd = RDCOST(x->rdmult, x->rddiv, sum_rate, sum_dist);
1884 if (sum_rd < best_rd) {
1886 best_rate = sum_rate;
1887 best_dist = sum_dist;
1888 *(get_sb_partitioning(x, bsize)) = subsize;
1891 restore_context(cpi, mi_row, mi_col, a, l, sa, sl, bsize);
1895 if (partition_vert_allowed && do_rect) {
1896 subsize = get_subsize(bsize, PARTITION_VERT);
1898 *get_sb_index(x, subsize) = 0;
1899 if (cpi->sf.adaptive_motion_search)
1900 load_pred_mv(x, get_block_context(x, bsize));
1901 if (cpi->sf.adaptive_pred_interp_filter && bsize == BLOCK_8X8 &&
1902 partition_none_allowed)
1903 get_block_context(x, subsize)->pred_interp_filter =
1904 get_block_context(x, bsize)->mic.mbmi.interp_filter;
1905 rd_pick_sb_modes(cpi, tile, mi_row, mi_col, &sum_rate, &sum_dist, subsize,
1906 get_block_context(x, subsize), best_rd);
1907 sum_rd = RDCOST(x->rdmult, x->rddiv, sum_rate, sum_dist);
1908 if (sum_rd < best_rd && mi_col + ms < cm->mi_cols) {
1909 update_state(cpi, get_block_context(x, subsize), subsize, 0);
1910 encode_superblock(cpi, tp, 0, mi_row, mi_col, subsize);
1912 *get_sb_index(x, subsize) = 1;
1913 if (cpi->sf.adaptive_motion_search)
1914 load_pred_mv(x, get_block_context(x, bsize));
1915 if (cpi->sf.adaptive_pred_interp_filter && bsize == BLOCK_8X8 &&
1916 partition_none_allowed)
1917 get_block_context(x, subsize)->pred_interp_filter =
1918 get_block_context(x, bsize)->mic.mbmi.interp_filter;
1919 rd_pick_sb_modes(cpi, tile, mi_row, mi_col + ms, &this_rate,
1920 &this_dist, subsize, get_block_context(x, subsize),
1922 if (this_rate == INT_MAX) {
1925 sum_rate += this_rate;
1926 sum_dist += this_dist;
1927 sum_rd = RDCOST(x->rdmult, x->rddiv, sum_rate, sum_dist);
1930 if (sum_rd < best_rd) {
1931 pl = partition_plane_context(cpi->above_seg_context,
1932 cpi->left_seg_context,
1933 mi_row, mi_col, bsize);
1934 sum_rate += x->partition_cost[pl][PARTITION_VERT];
1935 sum_rd = RDCOST(x->rdmult, x->rddiv, sum_rate, sum_dist);
1936 if (sum_rd < best_rd) {
1937 best_rate = sum_rate;
1938 best_dist = sum_dist;
1940 *(get_sb_partitioning(x, bsize)) = subsize;
1943 restore_context(cpi, mi_row, mi_col, a, l, sa, sl, bsize);
1946 // TODO(jbb): This code added so that we avoid static analysis
1947 // warning related to the fact that best_rd isn't used after this
1948 // point. This code should be refactored so that the duplicate
1949 // checks occur in some sub function and thus are used...
1954 if (best_rate < INT_MAX && best_dist < INT64_MAX && do_recon) {
1955 int output_enabled = (bsize == BLOCK_64X64);
1957 // Check the projected output rate for this SB against it's target
1958 // and and if necessary apply a Q delta using segmentation to get
1959 // closer to the target.
1960 if ((cpi->oxcf.aq_mode == COMPLEXITY_AQ) && cm->seg.update_map) {
1961 select_in_frame_q_segment(cpi, mi_row, mi_col, output_enabled, best_rate);
1963 encode_sb(cpi, tile, tp, mi_row, mi_col, output_enabled, bsize);
1965 if (bsize == BLOCK_64X64) {
1966 assert(tp_orig < *tp);
1967 assert(best_rate < INT_MAX);
1968 assert(best_dist < INT64_MAX);
1970 assert(tp_orig == *tp);
1974 static void encode_rd_sb_row(VP9_COMP *cpi, const TileInfo *const tile,
1975 int mi_row, TOKENEXTRA **tp) {
1976 VP9_COMMON *const cm = &cpi->common;
1979 // Initialize the left context for the new SB row
1980 vpx_memset(&cpi->left_context, 0, sizeof(cpi->left_context));
1981 vpx_memset(cpi->left_seg_context, 0, sizeof(cpi->left_seg_context));
1983 // Code each SB in the row
1984 for (mi_col = tile->mi_col_start; mi_col < tile->mi_col_end;
1985 mi_col += MI_BLOCK_SIZE) {
1990 MACROBLOCK *x = &cpi->mb;
1992 if (cpi->sf.adaptive_pred_interp_filter) {
1993 for (i = BLOCK_4X4; i < BLOCK_8X8; ++i) {
1994 const int num_4x4_w = num_4x4_blocks_wide_lookup[i];
1995 const int num_4x4_h = num_4x4_blocks_high_lookup[i];
1996 const int num_4x4_blk = MAX(4, num_4x4_w * num_4x4_h);
1997 for (x->sb_index = 0; x->sb_index < 4; ++x->sb_index)
1998 for (x->mb_index = 0; x->mb_index < 4; ++x->mb_index)
1999 for (x->b_index = 0; x->b_index < 16 / num_4x4_blk; ++x->b_index)
2000 get_block_context(x, i)->pred_interp_filter = SWITCHABLE;
2004 vp9_zero(cpi->mb.pred_mv);
2006 if ((cpi->sf.partition_search_type == SEARCH_PARTITION &&
2007 cpi->sf.use_lastframe_partitioning) ||
2008 cpi->sf.partition_search_type == FIXED_PARTITION ||
2009 cpi->sf.partition_search_type == VAR_BASED_FIXED_PARTITION) {
2010 const int idx_str = cm->mode_info_stride * mi_row + mi_col;
2011 MODE_INFO **mi_8x8 = cm->mi_grid_visible + idx_str;
2012 MODE_INFO **prev_mi_8x8 = cm->prev_mi_grid_visible + idx_str;
2013 cpi->mb.source_variance = UINT_MAX;
2014 if (cpi->sf.partition_search_type == FIXED_PARTITION) {
2015 set_offsets(cpi, tile, mi_row, mi_col, BLOCK_64X64);
2016 set_partitioning(cpi, tile, mi_8x8, mi_row, mi_col,
2017 cpi->sf.always_this_block_size);
2018 rd_use_partition(cpi, tile, mi_8x8, tp, mi_row, mi_col, BLOCK_64X64,
2019 &dummy_rate, &dummy_dist, 1);
2020 } else if (cpi->sf.partition_search_type == VAR_BASED_FIXED_PARTITION ||
2021 cpi->sf.partition_search_type == VAR_BASED_PARTITION) {
2022 // TODO(debargha): Implement VAR_BASED_PARTITION as a separate case.
2023 // Currently both VAR_BASED_FIXED_PARTITION/VAR_BASED_PARTITION
2024 // map to the same thing.
2026 set_offsets(cpi, tile, mi_row, mi_col, BLOCK_64X64);
2027 bsize = get_rd_var_based_fixed_partition(cpi, mi_row, mi_col);
2028 set_partitioning(cpi, tile, mi_8x8, mi_row, mi_col, bsize);
2029 rd_use_partition(cpi, tile, mi_8x8, tp, mi_row, mi_col, BLOCK_64X64,
2030 &dummy_rate, &dummy_dist, 1);
2032 if ((cm->current_video_frame
2033 % cpi->sf.last_partitioning_redo_frequency) == 0
2035 || cm->show_frame == 0
2036 || cm->frame_type == KEY_FRAME
2037 || cpi->rc.is_src_frame_alt_ref
2038 || ((cpi->sf.use_lastframe_partitioning ==
2039 LAST_FRAME_PARTITION_LOW_MOTION) &&
2040 sb_has_motion(cm, prev_mi_8x8))) {
2041 // If required set upper and lower partition size limits
2042 if (cpi->sf.auto_min_max_partition_size) {
2043 set_offsets(cpi, tile, mi_row, mi_col, BLOCK_64X64);
2044 rd_auto_partition_range(cpi, tile, mi_row, mi_col,
2045 &cpi->sf.min_partition_size,
2046 &cpi->sf.max_partition_size);
2048 rd_pick_partition(cpi, tile, tp, mi_row, mi_col, BLOCK_64X64,
2049 &dummy_rate, &dummy_dist, 1, INT64_MAX);
2051 copy_partitioning(cm, mi_8x8, prev_mi_8x8);
2052 rd_use_partition(cpi, tile, mi_8x8, tp, mi_row, mi_col, BLOCK_64X64,
2053 &dummy_rate, &dummy_dist, 1);
2057 // If required set upper and lower partition size limits
2058 if (cpi->sf.auto_min_max_partition_size) {
2059 set_offsets(cpi, tile, mi_row, mi_col, BLOCK_64X64);
2060 rd_auto_partition_range(cpi, tile, mi_row, mi_col,
2061 &cpi->sf.min_partition_size,
2062 &cpi->sf.max_partition_size);
2064 rd_pick_partition(cpi, tile, tp, mi_row, mi_col, BLOCK_64X64,
2065 &dummy_rate, &dummy_dist, 1, INT64_MAX);
2070 static void init_encode_frame_mb_context(VP9_COMP *cpi) {
2071 MACROBLOCK *const x = &cpi->mb;
2072 VP9_COMMON *const cm = &cpi->common;
2073 MACROBLOCKD *const xd = &x->e_mbd;
2074 const int aligned_mi_cols = mi_cols_aligned_to_sb(cm->mi_cols);
2076 x->act_zbin_adj = 0;
2079 xd->mode_info_stride = cm->mode_info_stride;
2081 // Copy data over into macro block data structures.
2082 vp9_setup_src_planes(x, cpi->Source, 0, 0);
2084 // TODO(jkoleszar): are these initializations required?
2085 vp9_setup_pre_planes(xd, 0, get_ref_frame_buffer(cpi, LAST_FRAME), 0, 0,
2087 vp9_setup_dst_planes(xd, get_frame_new_buffer(cm), 0, 0);
2089 vp9_setup_block_planes(&x->e_mbd, cm->subsampling_x, cm->subsampling_y);
2091 xd->mi_8x8[0]->mbmi.mode = DC_PRED;
2092 xd->mi_8x8[0]->mbmi.uv_mode = DC_PRED;
2094 vp9_zero(cm->counts.y_mode);
2095 vp9_zero(cm->counts.uv_mode);
2096 vp9_zero(cm->counts.inter_mode);
2097 vp9_zero(cm->counts.partition);
2098 vp9_zero(cm->counts.intra_inter);
2099 vp9_zero(cm->counts.comp_inter);
2100 vp9_zero(cm->counts.single_ref);
2101 vp9_zero(cm->counts.comp_ref);
2102 vp9_zero(cm->counts.tx);
2103 vp9_zero(cm->counts.skip);
2105 // Note: this memset assumes above_context[0], [1] and [2]
2106 // are allocated as part of the same buffer.
2107 vpx_memset(cpi->above_context[0], 0,
2108 sizeof(*cpi->above_context[0]) *
2109 2 * aligned_mi_cols * MAX_MB_PLANE);
2110 vpx_memset(cpi->above_seg_context, 0,
2111 sizeof(*cpi->above_seg_context) * aligned_mi_cols);
2114 static void switch_lossless_mode(VP9_COMP *cpi, int lossless) {
2116 // printf("Switching to lossless\n");
2117 cpi->mb.fwd_txm4x4 = vp9_fwht4x4;
2118 cpi->mb.e_mbd.itxm_add = vp9_iwht4x4_add;
2119 cpi->mb.optimize = 0;
2120 cpi->common.lf.filter_level = 0;
2121 cpi->zbin_mode_boost_enabled = 0;
2122 cpi->common.tx_mode = ONLY_4X4;
2124 // printf("Not lossless\n");
2125 cpi->mb.fwd_txm4x4 = vp9_fdct4x4;
2126 cpi->mb.e_mbd.itxm_add = vp9_idct4x4_add;
2130 static void switch_tx_mode(VP9_COMP *cpi) {
2131 if (cpi->sf.tx_size_search_method == USE_LARGESTALL &&
2132 cpi->common.tx_mode >= ALLOW_32X32)
2133 cpi->common.tx_mode = ALLOW_32X32;
2137 static int check_dual_ref_flags(VP9_COMP *cpi) {
2138 const int ref_flags = cpi->ref_frame_flags;
2140 if (vp9_segfeature_active(&cpi->common.seg, 1, SEG_LVL_REF_FRAME)) {
2143 return (!!(ref_flags & VP9_GOLD_FLAG) + !!(ref_flags & VP9_LAST_FLAG)
2144 + !!(ref_flags & VP9_ALT_FLAG)) >= 2;
2148 static int get_skip_flag(MODE_INFO **mi_8x8, int mis, int ymbs, int xmbs) {
2151 for (y = 0; y < ymbs; y++) {
2152 for (x = 0; x < xmbs; x++) {
2153 if (!mi_8x8[y * mis + x]->mbmi.skip)
2161 static void set_txfm_flag(MODE_INFO **mi_8x8, int mis, int ymbs, int xmbs,
2165 for (y = 0; y < ymbs; y++) {
2166 for (x = 0; x < xmbs; x++)
2167 mi_8x8[y * mis + x]->mbmi.tx_size = tx_size;
2171 static void reset_skip_txfm_size_b(const VP9_COMMON *cm, int mis,
2172 TX_SIZE max_tx_size, int bw, int bh,
2173 int mi_row, int mi_col,
2174 MODE_INFO **mi_8x8) {
2175 if (mi_row >= cm->mi_rows || mi_col >= cm->mi_cols) {
2178 MB_MODE_INFO * const mbmi = &mi_8x8[0]->mbmi;
2179 if (mbmi->tx_size > max_tx_size) {
2180 const int ymbs = MIN(bh, cm->mi_rows - mi_row);
2181 const int xmbs = MIN(bw, cm->mi_cols - mi_col);
2183 assert(vp9_segfeature_active(&cm->seg, mbmi->segment_id, SEG_LVL_SKIP) ||
2184 get_skip_flag(mi_8x8, mis, ymbs, xmbs));
2185 set_txfm_flag(mi_8x8, mis, ymbs, xmbs, max_tx_size);
2190 static void reset_skip_txfm_size_sb(VP9_COMMON *cm, MODE_INFO **mi_8x8,
2191 TX_SIZE max_tx_size, int mi_row, int mi_col,
2193 const int mis = cm->mode_info_stride;
2195 const int bs = num_8x8_blocks_wide_lookup[bsize], hbs = bs / 2;
2197 if (mi_row >= cm->mi_rows || mi_col >= cm->mi_cols)
2200 bw = num_8x8_blocks_wide_lookup[mi_8x8[0]->mbmi.sb_type];
2201 bh = num_8x8_blocks_high_lookup[mi_8x8[0]->mbmi.sb_type];
2203 if (bw == bs && bh == bs) {
2204 reset_skip_txfm_size_b(cm, mis, max_tx_size, bs, bs, mi_row, mi_col,
2206 } else if (bw == bs && bh < bs) {
2207 reset_skip_txfm_size_b(cm, mis, max_tx_size, bs, hbs, mi_row, mi_col,
2209 reset_skip_txfm_size_b(cm, mis, max_tx_size, bs, hbs, mi_row + hbs,
2210 mi_col, mi_8x8 + hbs * mis);
2211 } else if (bw < bs && bh == bs) {
2212 reset_skip_txfm_size_b(cm, mis, max_tx_size, hbs, bs, mi_row, mi_col,
2214 reset_skip_txfm_size_b(cm, mis, max_tx_size, hbs, bs, mi_row,
2215 mi_col + hbs, mi_8x8 + hbs);
2217 const BLOCK_SIZE subsize = subsize_lookup[PARTITION_SPLIT][bsize];
2220 assert(bw < bs && bh < bs);
2222 for (n = 0; n < 4; n++) {
2223 const int mi_dc = hbs * (n & 1);
2224 const int mi_dr = hbs * (n >> 1);
2226 reset_skip_txfm_size_sb(cm, &mi_8x8[mi_dr * mis + mi_dc], max_tx_size,
2227 mi_row + mi_dr, mi_col + mi_dc, subsize);
2232 static void reset_skip_txfm_size(VP9_COMMON *cm, TX_SIZE txfm_max) {
2234 const int mis = cm->mode_info_stride;
2235 MODE_INFO **mi_8x8, **mi_ptr = cm->mi_grid_visible;
2237 for (mi_row = 0; mi_row < cm->mi_rows; mi_row += 8, mi_ptr += 8 * mis) {
2239 for (mi_col = 0; mi_col < cm->mi_cols; mi_col += 8, mi_8x8 += 8) {
2240 reset_skip_txfm_size_sb(cm, mi_8x8, txfm_max, mi_row, mi_col,
2246 static MV_REFERENCE_FRAME get_frame_type(VP9_COMP *cpi) {
2247 if (frame_is_intra_only(&cpi->common))
2249 else if (cpi->rc.is_src_frame_alt_ref && cpi->refresh_golden_frame)
2250 return ALTREF_FRAME;
2251 else if (cpi->refresh_golden_frame || cpi->refresh_alt_ref_frame)
2254 return GOLDEN_FRAME;
2257 static void select_tx_mode(VP9_COMP *cpi) {
2258 if (cpi->oxcf.lossless) {
2259 cpi->common.tx_mode = ONLY_4X4;
2260 } else if (cpi->common.current_video_frame == 0) {
2261 cpi->common.tx_mode = TX_MODE_SELECT;
2263 if (cpi->sf.tx_size_search_method == USE_LARGESTALL) {
2264 cpi->common.tx_mode = ALLOW_32X32;
2265 } else if (cpi->sf.tx_size_search_method == USE_FULL_RD) {
2266 int frame_type = get_frame_type(cpi);
2267 cpi->common.tx_mode =
2268 cpi->rd_tx_select_threshes[frame_type][ALLOW_32X32]
2269 > cpi->rd_tx_select_threshes[frame_type][TX_MODE_SELECT] ?
2270 ALLOW_32X32 : TX_MODE_SELECT;
2272 unsigned int total = 0;
2274 for (i = 0; i < TX_SIZES; ++i)
2275 total += cpi->tx_stepdown_count[i];
2277 double fraction = (double)cpi->tx_stepdown_count[0] / total;
2278 cpi->common.tx_mode = fraction > 0.90 ? ALLOW_32X32 : TX_MODE_SELECT;
2279 // printf("fraction = %f\n", fraction);
2280 } // else keep unchanged
2285 // Start RTC Exploration
2288 ZERO_PLUS_PREDICTED = 1,
2290 NEW_PLUS_NON_INTRA = 3,
2292 INTRA_PLUS_NON_INTRA = 5,
2295 } motion_vector_context;
2297 static void set_mode_info(MB_MODE_INFO *mbmi, BLOCK_SIZE bsize,
2298 MB_PREDICTION_MODE mode) {
2300 mbmi->uv_mode = mode;
2301 mbmi->mv[0].as_int = 0;
2302 mbmi->mv[1].as_int = 0;
2303 mbmi->ref_frame[0] = INTRA_FRAME;
2304 mbmi->ref_frame[1] = NONE;
2305 mbmi->tx_size = max_txsize_lookup[bsize];
2307 mbmi->sb_type = bsize;
2308 mbmi->segment_id = 0;
2311 static INLINE int get_block_row(int b32i, int b16i, int b8i) {
2312 return ((b32i >> 1) << 2) + ((b16i >> 1) << 1) + (b8i >> 1);
2315 static INLINE int get_block_col(int b32i, int b16i, int b8i) {
2316 return ((b32i & 1) << 2) + ((b16i & 1) << 1) + (b8i & 1);
2319 static void nonrd_use_partition(VP9_COMP *cpi, const TileInfo *const tile,
2320 TOKENEXTRA **tp, int mi_row, int mi_col,
2321 BLOCK_SIZE bsize, int *rate, int64_t *dist) {
2322 VP9_COMMON *const cm = &cpi->common;
2323 MACROBLOCK *const x = &cpi->mb;
2324 MACROBLOCKD *const xd = &cpi->mb.e_mbd;
2325 int mis = cm->mode_info_stride;
2328 MB_PREDICTION_MODE mode = DC_PRED;
2329 int rows = MIN(MI_BLOCK_SIZE, tile->mi_row_end - mi_row);
2330 int cols = MIN(MI_BLOCK_SIZE, tile->mi_col_end - mi_col);
2332 int bw = num_8x8_blocks_wide_lookup[bsize];
2333 int bh = num_8x8_blocks_high_lookup[bsize];
2340 // find prediction mode for each 8x8 block
2341 for (br = 0; br < rows; br += bh) {
2342 for (bc = 0; bc < cols; bc += bw) {
2343 int row = mi_row + br;
2344 int col = mi_col + bc;
2346 BLOCK_SIZE bs = find_partition_size(bsize, rows - br, cols - bc,
2349 set_offsets(cpi, tile, row, col, bs);
2351 if (cm->frame_type != KEY_FRAME)
2352 vp9_pick_inter_mode(cpi, x, tile, row, col,
2353 &brate, &bdist, bs);
2355 set_mode_info(&xd->mi_8x8[0]->mbmi, bs, mode);
2360 for (j = 0; j < bh; ++j)
2361 for (i = 0; i < bw; ++i)
2362 xd->mi_8x8[j * mis + i] = xd->mi_8x8[0];
2367 static void encode_nonrd_sb_row(VP9_COMP *cpi, const TileInfo *const tile,
2368 int mi_row, TOKENEXTRA **tp) {
2371 // Initialize the left context for the new SB row
2372 vpx_memset(&cpi->left_context, 0, sizeof(cpi->left_context));
2373 vpx_memset(cpi->left_seg_context, 0, sizeof(cpi->left_seg_context));
2375 // Code each SB in the row
2376 for (mi_col = tile->mi_col_start; mi_col < tile->mi_col_end;
2377 mi_col += MI_BLOCK_SIZE) {
2381 cpi->mb.source_variance = UINT_MAX;
2383 if (cpi->sf.partition_search_type == FIXED_PARTITION) {
2384 nonrd_use_partition(cpi, tile, tp, mi_row, mi_col,
2385 cpi->sf.always_this_block_size,
2386 &dummy_rate, &dummy_dist);
2387 encode_sb_rt(cpi, tile, tp, mi_row, mi_col, 1, BLOCK_64X64);
2388 } else if (cpi->sf.partition_search_type == VAR_BASED_FIXED_PARTITION ||
2389 cpi->sf.partition_search_type == VAR_BASED_PARTITION) {
2390 // TODO(debargha): Implement VAR_BASED_PARTITION as a separate case.
2391 // Currently both VAR_BASED_FIXED_PARTITION/VAR_BASED_PARTITION
2392 // map to the same thing.
2393 BLOCK_SIZE bsize = get_nonrd_var_based_fixed_partition(cpi,
2396 nonrd_use_partition(cpi, tile, tp, mi_row, mi_col,
2397 bsize, &dummy_rate, &dummy_dist);
2398 encode_sb_rt(cpi, tile, tp, mi_row, mi_col, 1, BLOCK_64X64);
2404 // end RTC play code
2406 static void encode_frame_internal(VP9_COMP *cpi) {
2408 MACROBLOCK *const x = &cpi->mb;
2409 VP9_COMMON *const cm = &cpi->common;
2410 MACROBLOCKD *const xd = &x->e_mbd;
2412 // fprintf(stderr, "encode_frame_internal frame %d (%d) type %d\n",
2413 // cpi->common.current_video_frame, cpi->common.show_frame,
2416 vp9_zero(cm->counts.switchable_interp);
2417 vp9_zero(cpi->tx_stepdown_count);
2419 xd->mi_8x8 = cm->mi_grid_visible;
2420 // required for vp9_frame_init_quantizer
2421 xd->mi_8x8[0] = cm->mi;
2423 xd->last_mi = cm->prev_mi;
2425 vp9_zero(cm->counts.mv);
2426 vp9_zero(cpi->coef_counts);
2427 vp9_zero(cm->counts.eob_branch);
2429 // Set frame level transform size use case
2430 select_tx_mode(cpi);
2432 cpi->mb.e_mbd.lossless = cm->base_qindex == 0 && cm->y_dc_delta_q == 0
2433 && cm->uv_dc_delta_q == 0 && cm->uv_ac_delta_q == 0;
2434 switch_lossless_mode(cpi, cpi->mb.e_mbd.lossless);
2436 vp9_frame_init_quantizer(cpi);
2438 vp9_initialize_rd_consts(cpi);
2439 vp9_initialize_me_consts(cpi, cm->base_qindex);
2441 if (cpi->oxcf.tuning == VP8_TUNE_SSIM) {
2442 // Initialize encode frame context.
2443 init_encode_frame_mb_context(cpi);
2445 // Build a frame level activity map
2446 build_activity_map(cpi);
2449 // Re-initialize encode frame context.
2450 init_encode_frame_mb_context(cpi);
2452 vp9_zero(cpi->rd_comp_pred_diff);
2453 vp9_zero(cpi->rd_filter_diff);
2454 vp9_zero(cpi->rd_tx_select_diff);
2455 vp9_zero(cpi->rd_tx_select_threshes);
2459 if (cpi->sf.use_nonrd_pick_mode) {
2460 // Initialize internal buffer pointers for rtc coding, where non-RD
2461 // mode decision is used and hence no buffer pointer swap needed.
2463 struct macroblock_plane *const p = x->plane;
2464 struct macroblockd_plane *const pd = xd->plane;
2465 PICK_MODE_CONTEXT *ctx = &cpi->mb.sb64_context;
2467 for (i = 0; i < MAX_MB_PLANE; ++i) {
2468 p[i].coeff = ctx->coeff_pbuf[i][0];
2469 p[i].qcoeff = ctx->qcoeff_pbuf[i][0];
2470 pd[i].dqcoeff = ctx->dqcoeff_pbuf[i][0];
2471 p[i].eobs = ctx->eobs_pbuf[i][0];
2476 struct vpx_usec_timer emr_timer;
2477 vpx_usec_timer_start(&emr_timer);
2480 // Take tiles into account and give start/end MB
2481 int tile_col, tile_row;
2482 TOKENEXTRA *tp = cpi->tok;
2483 const int tile_cols = 1 << cm->log2_tile_cols;
2484 const int tile_rows = 1 << cm->log2_tile_rows;
2486 for (tile_row = 0; tile_row < tile_rows; tile_row++) {
2487 for (tile_col = 0; tile_col < tile_cols; tile_col++) {
2489 TOKENEXTRA *tp_old = tp;
2491 // For each row of SBs in the frame
2492 vp9_tile_init(&tile, cm, tile_row, tile_col);
2493 for (mi_row = tile.mi_row_start;
2494 mi_row < tile.mi_row_end; mi_row += MI_BLOCK_SIZE) {
2495 if (cpi->sf.use_nonrd_pick_mode && cm->frame_type != KEY_FRAME)
2496 encode_nonrd_sb_row(cpi, &tile, mi_row, &tp);
2498 encode_rd_sb_row(cpi, &tile, mi_row, &tp);
2500 cpi->tok_count[tile_row][tile_col] = (unsigned int)(tp - tp_old);
2501 assert(tp - cpi->tok <= get_token_alloc(cm->mb_rows, cm->mb_cols));
2506 vpx_usec_timer_mark(&emr_timer);
2507 cpi->time_encode_sb_row += vpx_usec_timer_elapsed(&emr_timer);
2510 if (cpi->sf.skip_encode_sb) {
2512 unsigned int intra_count = 0, inter_count = 0;
2513 for (j = 0; j < INTRA_INTER_CONTEXTS; ++j) {
2514 intra_count += cm->counts.intra_inter[j][0];
2515 inter_count += cm->counts.intra_inter[j][1];
2517 cpi->sf.skip_encode_frame = ((intra_count << 2) < inter_count);
2518 cpi->sf.skip_encode_frame &= (cm->frame_type != KEY_FRAME);
2519 cpi->sf.skip_encode_frame &= cm->show_frame;
2521 cpi->sf.skip_encode_frame = 0;
2525 // Keep record of the total distortion this time around for future use
2526 cpi->last_frame_distortion = cpi->frame_distortion;
2530 void vp9_encode_frame(VP9_COMP *cpi) {
2531 VP9_COMMON *const cm = &cpi->common;
2533 // In the longer term the encoder should be generalized to match the
2534 // decoder such that we allow compound where one of the 3 buffers has a
2535 // different sign bias and that buffer is then the fixed ref. However, this
2536 // requires further work in the rd loop. For now the only supported encoder
2537 // side behavior is where the ALT ref buffer has opposite sign bias to
2539 if (!frame_is_intra_only(cm)) {
2540 if ((cm->ref_frame_sign_bias[ALTREF_FRAME] ==
2541 cm->ref_frame_sign_bias[GOLDEN_FRAME]) ||
2542 (cm->ref_frame_sign_bias[ALTREF_FRAME] ==
2543 cm->ref_frame_sign_bias[LAST_FRAME])) {
2544 cm->allow_comp_inter_inter = 0;
2546 cm->allow_comp_inter_inter = 1;
2547 cm->comp_fixed_ref = ALTREF_FRAME;
2548 cm->comp_var_ref[0] = LAST_FRAME;
2549 cm->comp_var_ref[1] = GOLDEN_FRAME;
2553 if (cpi->sf.frame_parameter_update) {
2555 REFERENCE_MODE reference_mode;
2557 * This code does a single RD pass over the whole frame assuming
2558 * either compound, single or hybrid prediction as per whatever has
2559 * worked best for that type of frame in the past.
2560 * It also predicts whether another coding mode would have worked
2561 * better that this coding mode. If that is the case, it remembers
2562 * that for subsequent frames.
2563 * It does the same analysis for transform size selection also.
2565 const MV_REFERENCE_FRAME frame_type = get_frame_type(cpi);
2566 const int64_t *mode_thresh = cpi->rd_prediction_type_threshes[frame_type];
2567 const int64_t *filter_thresh = cpi->rd_filter_threshes[frame_type];
2569 /* prediction (compound, single or hybrid) mode selection */
2570 if (frame_type == 3 || !cm->allow_comp_inter_inter)
2571 reference_mode = SINGLE_REFERENCE;
2572 else if (mode_thresh[COMPOUND_REFERENCE] > mode_thresh[SINGLE_REFERENCE] &&
2573 mode_thresh[COMPOUND_REFERENCE] >
2574 mode_thresh[REFERENCE_MODE_SELECT] &&
2575 check_dual_ref_flags(cpi) &&
2576 cpi->static_mb_pct == 100)
2577 reference_mode = COMPOUND_REFERENCE;
2578 else if (mode_thresh[SINGLE_REFERENCE] > mode_thresh[REFERENCE_MODE_SELECT])
2579 reference_mode = SINGLE_REFERENCE;
2581 reference_mode = REFERENCE_MODE_SELECT;
2583 if (cm->interp_filter == SWITCHABLE) {
2584 if (frame_type != ALTREF_FRAME &&
2585 filter_thresh[EIGHTTAP_SMOOTH] > filter_thresh[EIGHTTAP] &&
2586 filter_thresh[EIGHTTAP_SMOOTH] > filter_thresh[EIGHTTAP_SHARP] &&
2587 filter_thresh[EIGHTTAP_SMOOTH] > filter_thresh[SWITCHABLE - 1]) {
2588 cm->interp_filter = EIGHTTAP_SMOOTH;
2589 } else if (filter_thresh[EIGHTTAP_SHARP] > filter_thresh[EIGHTTAP] &&
2590 filter_thresh[EIGHTTAP_SHARP] > filter_thresh[SWITCHABLE - 1]) {
2591 cm->interp_filter = EIGHTTAP_SHARP;
2592 } else if (filter_thresh[EIGHTTAP] > filter_thresh[SWITCHABLE - 1]) {
2593 cm->interp_filter = EIGHTTAP;
2597 cpi->mb.e_mbd.lossless = cpi->oxcf.lossless;
2599 cm->reference_mode = reference_mode;
2601 encode_frame_internal(cpi);
2603 for (i = 0; i < REFERENCE_MODES; ++i) {
2604 const int diff = (int) (cpi->rd_comp_pred_diff[i] / cm->MBs);
2605 cpi->rd_prediction_type_threshes[frame_type][i] += diff;
2606 cpi->rd_prediction_type_threshes[frame_type][i] >>= 1;
2609 for (i = 0; i < SWITCHABLE_FILTER_CONTEXTS; i++) {
2610 const int64_t diff = cpi->rd_filter_diff[i] / cm->MBs;
2611 cpi->rd_filter_threshes[frame_type][i] =
2612 (cpi->rd_filter_threshes[frame_type][i] + diff) / 2;
2615 for (i = 0; i < TX_MODES; ++i) {
2616 int64_t pd = cpi->rd_tx_select_diff[i];
2618 if (i == TX_MODE_SELECT)
2619 pd -= RDCOST(cpi->mb.rdmult, cpi->mb.rddiv, 2048 * (TX_SIZES - 1), 0);
2620 diff = (int) (pd / cm->MBs);
2621 cpi->rd_tx_select_threshes[frame_type][i] += diff;
2622 cpi->rd_tx_select_threshes[frame_type][i] /= 2;
2625 if (cm->reference_mode == REFERENCE_MODE_SELECT) {
2626 int single_count_zero = 0;
2627 int comp_count_zero = 0;
2629 for (i = 0; i < COMP_INTER_CONTEXTS; i++) {
2630 single_count_zero += cm->counts.comp_inter[i][0];
2631 comp_count_zero += cm->counts.comp_inter[i][1];
2634 if (comp_count_zero == 0) {
2635 cm->reference_mode = SINGLE_REFERENCE;
2636 vp9_zero(cm->counts.comp_inter);
2637 } else if (single_count_zero == 0) {
2638 cm->reference_mode = COMPOUND_REFERENCE;
2639 vp9_zero(cm->counts.comp_inter);
2643 if (cm->tx_mode == TX_MODE_SELECT) {
2645 int count8x8_lp = 0, count8x8_8x8p = 0;
2646 int count16x16_16x16p = 0, count16x16_lp = 0;
2649 for (i = 0; i < TX_SIZE_CONTEXTS; ++i) {
2650 count4x4 += cm->counts.tx.p32x32[i][TX_4X4];
2651 count4x4 += cm->counts.tx.p16x16[i][TX_4X4];
2652 count4x4 += cm->counts.tx.p8x8[i][TX_4X4];
2654 count8x8_lp += cm->counts.tx.p32x32[i][TX_8X8];
2655 count8x8_lp += cm->counts.tx.p16x16[i][TX_8X8];
2656 count8x8_8x8p += cm->counts.tx.p8x8[i][TX_8X8];
2658 count16x16_16x16p += cm->counts.tx.p16x16[i][TX_16X16];
2659 count16x16_lp += cm->counts.tx.p32x32[i][TX_16X16];
2660 count32x32 += cm->counts.tx.p32x32[i][TX_32X32];
2663 if (count4x4 == 0 && count16x16_lp == 0 && count16x16_16x16p == 0 &&
2665 cm->tx_mode = ALLOW_8X8;
2666 reset_skip_txfm_size(cm, TX_8X8);
2667 } else if (count8x8_8x8p == 0 && count16x16_16x16p == 0 &&
2668 count8x8_lp == 0 && count16x16_lp == 0 && count32x32 == 0) {
2669 cm->tx_mode = ONLY_4X4;
2670 reset_skip_txfm_size(cm, TX_4X4);
2671 } else if (count8x8_lp == 0 && count16x16_lp == 0 && count4x4 == 0) {
2672 cm->tx_mode = ALLOW_32X32;
2673 } else if (count32x32 == 0 && count8x8_lp == 0 && count4x4 == 0) {
2674 cm->tx_mode = ALLOW_16X16;
2675 reset_skip_txfm_size(cm, TX_16X16);
2679 cpi->mb.e_mbd.lossless = cpi->oxcf.lossless;
2680 cm->reference_mode = SINGLE_REFERENCE;
2681 // Force the usage of the BILINEAR interp_filter.
2682 cm->interp_filter = BILINEAR;
2683 encode_frame_internal(cpi);
2687 static void sum_intra_stats(FRAME_COUNTS *counts, const MODE_INFO *mi) {
2688 const MB_PREDICTION_MODE y_mode = mi->mbmi.mode;
2689 const MB_PREDICTION_MODE uv_mode = mi->mbmi.uv_mode;
2690 const BLOCK_SIZE bsize = mi->mbmi.sb_type;
2692 ++counts->uv_mode[y_mode][uv_mode];
2694 if (bsize < BLOCK_8X8) {
2696 const int num_4x4_blocks_wide = num_4x4_blocks_wide_lookup[bsize];
2697 const int num_4x4_blocks_high = num_4x4_blocks_high_lookup[bsize];
2698 for (idy = 0; idy < 2; idy += num_4x4_blocks_high)
2699 for (idx = 0; idx < 2; idx += num_4x4_blocks_wide)
2700 ++counts->y_mode[0][mi->bmi[idy * 2 + idx].as_mode];
2702 ++counts->y_mode[size_group_lookup[bsize]][y_mode];
2706 // Experimental stub function to create a per MB zbin adjustment based on
2707 // some previously calculated measure of MB activity.
2708 static void adjust_act_zbin(VP9_COMP *cpi, MACROBLOCK *x) {
2710 x->act_zbin_adj = *(x->mb_activity_ptr);
2714 int64_t act = *(x->mb_activity_ptr);
2716 // Apply the masking to the RD multiplier.
2717 a = act + 4 * cpi->activity_avg;
2718 b = 4 * act + cpi->activity_avg;
2720 if (act > cpi->activity_avg)
2721 x->act_zbin_adj = (int) (((int64_t) b + (a >> 1)) / a) - 1;
2723 x->act_zbin_adj = 1 - (int) (((int64_t) a + (b >> 1)) / b);
2727 static int get_zbin_mode_boost(const MB_MODE_INFO *mbmi, int enabled) {
2729 if (is_inter_block(mbmi)) {
2730 if (mbmi->mode == ZEROMV) {
2731 return mbmi->ref_frame[0] != LAST_FRAME ? GF_ZEROMV_ZBIN_BOOST
2732 : LF_ZEROMV_ZBIN_BOOST;
2734 return mbmi->sb_type < BLOCK_8X8 ? SPLIT_MV_ZBIN_BOOST
2738 return INTRA_ZBIN_BOOST;
2745 static void encode_superblock(VP9_COMP *cpi, TOKENEXTRA **t, int output_enabled,
2746 int mi_row, int mi_col, BLOCK_SIZE bsize) {
2747 VP9_COMMON *const cm = &cpi->common;
2748 MACROBLOCK *const x = &cpi->mb;
2749 MACROBLOCKD *const xd = &x->e_mbd;
2750 MODE_INFO **mi_8x8 = xd->mi_8x8;
2751 MODE_INFO *mi = mi_8x8[0];
2752 MB_MODE_INFO *mbmi = &mi->mbmi;
2753 PICK_MODE_CONTEXT *ctx = get_block_context(x, bsize);
2754 unsigned int segment_id = mbmi->segment_id;
2755 const int mis = cm->mode_info_stride;
2756 const int mi_width = num_8x8_blocks_wide_lookup[bsize];
2757 const int mi_height = num_8x8_blocks_high_lookup[bsize];
2759 x->skip_recode = !x->select_txfm_size && mbmi->sb_type >= BLOCK_8X8 &&
2760 (cpi->oxcf.aq_mode != COMPLEXITY_AQ) &&
2761 !cpi->sf.use_nonrd_pick_mode;
2762 x->skip_optimize = ctx->is_coded;
2764 x->use_lp32x32fdct = cpi->sf.use_lp32x32fdct;
2765 x->skip_encode = (!output_enabled && cpi->sf.skip_encode_frame &&
2766 x->q_index < QIDX_SKIP_THRESH);
2770 if (cm->frame_type == KEY_FRAME) {
2771 if (cpi->oxcf.tuning == VP8_TUNE_SSIM) {
2772 adjust_act_zbin(cpi, x);
2773 vp9_update_zbin_extra(cpi, x);
2776 set_ref_ptrs(cm, xd, mbmi->ref_frame[0], mbmi->ref_frame[1]);
2777 xd->interp_kernel = vp9_get_interp_kernel(mbmi->interp_filter);
2779 if (cpi->oxcf.tuning == VP8_TUNE_SSIM) {
2780 // Adjust the zbin based on this MB rate.
2781 adjust_act_zbin(cpi, x);
2784 // Experimental code. Special case for gf and arf zeromv modes.
2785 // Increase zbin size to suppress noise
2786 cpi->zbin_mode_boost = get_zbin_mode_boost(mbmi,
2787 cpi->zbin_mode_boost_enabled);
2788 vp9_update_zbin_extra(cpi, x);
2791 if (!is_inter_block(mbmi)) {
2794 for (plane = 0; plane < MAX_MB_PLANE; ++plane)
2795 vp9_encode_intra_block_plane(x, MAX(bsize, BLOCK_8X8), plane);
2797 sum_intra_stats(&cm->counts, mi);
2798 vp9_tokenize_sb(cpi, t, !output_enabled, MAX(bsize, BLOCK_8X8));
2801 const int is_compound = has_second_ref(mbmi);
2802 for (ref = 0; ref < 1 + is_compound; ++ref) {
2803 YV12_BUFFER_CONFIG *cfg = get_ref_frame_buffer(cpi,
2804 mbmi->ref_frame[ref]);
2805 vp9_setup_pre_planes(xd, ref, cfg, mi_row, mi_col,
2806 &xd->block_refs[ref]->sf);
2808 vp9_build_inter_predictors_sb(xd, mi_row, mi_col, MAX(bsize, BLOCK_8X8));
2812 vp9_encode_sb(x, MAX(bsize, BLOCK_8X8));
2813 vp9_tokenize_sb(cpi, t, !output_enabled, MAX(bsize, BLOCK_8X8));
2817 cm->counts.skip[vp9_get_skip_context(xd)][1]++;
2818 reset_skip_context(xd, MAX(bsize, BLOCK_8X8));
2822 if (output_enabled) {
2823 if (cm->tx_mode == TX_MODE_SELECT &&
2824 mbmi->sb_type >= BLOCK_8X8 &&
2825 !(is_inter_block(mbmi) &&
2827 vp9_segfeature_active(&cm->seg, segment_id, SEG_LVL_SKIP)))) {
2828 ++get_tx_counts(max_txsize_lookup[bsize], vp9_get_tx_size_context(xd),
2829 &cm->counts.tx)[mbmi->tx_size];
2833 // The new intra coding scheme requires no change of transform size
2834 if (is_inter_block(&mi->mbmi)) {
2835 tx_size = MIN(tx_mode_to_biggest_tx_size[cm->tx_mode],
2836 max_txsize_lookup[bsize]);
2838 tx_size = (bsize >= BLOCK_8X8) ? mbmi->tx_size : TX_4X4;
2841 for (y = 0; y < mi_height; y++)
2842 for (x = 0; x < mi_width; x++)
2843 if (mi_col + x < cm->mi_cols && mi_row + y < cm->mi_rows)
2844 mi_8x8[mis * y + x]->mbmi.tx_size = tx_size;