Newer
Older
2001
2002
2003
2004
2005
2006
2007
2008
2009
2010
2011
2012
2013
2014
2015
2016
2017
2018
2019
2020
2021
2022
2023
2024
2025
2026
2027
2028
2029
2030
2031
2032
2033
2034
2035
2036
2037
2038
2039
2040
2041
2042
2043
2044
2045
2046
2047
2048
384 * sizeof(m->mbmi.nzcs[0]));
}
}
static void gather_nzcs_sb64(VP9_COMMON *const cm,
MACROBLOCKD *xd) {
int i, j;
MODE_INFO *m = xd->mode_info_context;
int mis = cm->mode_info_stride;
vpx_memset(xd->mode_info_context->mbmi.nzcs, 0,
384 * sizeof(xd->mode_info_context->mbmi.nzcs[0]));
switch (xd->mode_info_context->mbmi.txfm_size) {
case TX_4X4:
for (i = 0; i < 384; ++i) {
xd->mode_info_context->mbmi.nzcs[i] = xd->nzcs[i];
}
break;
case TX_8X8:
for (i = 0; i < 384; i += 4) {
xd->mode_info_context->mbmi.nzcs[i] = xd->nzcs[i];
}
break;
case TX_16X16:
for (i = 0; i < 384; i += 16) {
xd->mode_info_context->mbmi.nzcs[i] = xd->nzcs[i];
}
break;
case TX_32X32:
for (i = 0; i < 384; i += 64) {
xd->mode_info_context->mbmi.nzcs[i] = xd->nzcs[i];
}
break;
default:
break;
}
for (i = 0; i < 4; ++i)
for (j = 0; j < 4; ++j) {
if (i == 0 && j == 0) continue;
vpx_memcpy((m + j + mis * i)->mbmi.nzcs, m->mbmi.nzcs,
384 * sizeof(m->mbmi.nzcs[0]));
}
}
#endif
static void encode_macroblock(VP9_COMP *cpi, TOKENEXTRA **t,
int output_enabled,
int mb_row, int mb_col) {
VP9_COMMON *const cm = &cpi->common;
MACROBLOCK *const x = &cpi->mb;
MODE_INFO *mi = xd->mode_info_context;
MB_MODE_INFO *const mbmi = &mi->mbmi;
const int mis = cm->mode_info_stride;
assert(!xd->mode_info_context->mbmi.sb_type);
enc_debug = (cpi->common.current_video_frame == 1 &&
mb_row == 0 && mb_col == 0 && output_enabled);
if (enc_debug)
printf("Encode MB %d %d output %d\n", mb_row, mb_col, output_enabled);
#endif
if (cm->frame_type == KEY_FRAME) {
if (cpi->oxcf.tuning == VP8_TUNE_SSIM && output_enabled) {
// Adjust the zbin based on this MB rate.
adjust_act_zbin(cpi, x);
vp9_update_zbin_extra(cpi, x);
}
} else {
vp9_setup_interp_filters(xd, mbmi->interp_filter, cm);
if (cpi->oxcf.tuning == VP8_TUNE_SSIM) {
// Adjust the zbin based on this MB rate.
adjust_act_zbin(cpi, x);
}
// Experimental code. Special case for gf and arf zeromv modes.
// Increase zbin size to suppress noise
cpi->zbin_mode_boost = 0;
if (cpi->zbin_mode_boost_enabled) {
if (mbmi->ref_frame != INTRA_FRAME) {
if (mbmi->mode == ZEROMV) {
if (mbmi->ref_frame != LAST_FRAME)
cpi->zbin_mode_boost = GF_ZEROMV_ZBIN_BOOST;
else
cpi->zbin_mode_boost = LF_ZEROMV_ZBIN_BOOST;
cpi->zbin_mode_boost = 0;
else
cpi->zbin_mode_boost = MV_ZBIN_BOOST;
}
vp9_update_zbin_extra(cpi, x);
// SET VARIOUS PREDICTION FLAGS
// Did the chosen reference frame match its predicted value.
ref_pred_flag = ((mbmi->ref_frame == vp9_get_pred_ref(cm, xd)));
vp9_set_pred_flag(xd, PRED_REF, ref_pred_flag);
}
#ifdef ENC_DEBUG
if (enc_debug) {
printf("Mode %d skip %d tx_size %d\n", mbmi->mode, x->skip,
mbmi->txfm_size);
}
#endif
vp9_encode_intra16x16mbuv(cm, x);
vp9_encode_intra8x8mby(x);
vp9_encode_intra8x8mbuv(x);
vp9_encode_intra16x16mbuv(cm, x);
vp9_encode_intra16x16mby(cm, x);
if (output_enabled)
sum_intra_stats(cpi, x);
} else {
int ref_fb_idx;
#ifdef ENC_DEBUG
if (enc_debug)
printf("Mode %d skip %d tx_size %d ref %d ref2 %d mv %d %d interp %d\n",
mbmi->mode, x->skip, mbmi->txfm_size,
mbmi->ref_frame, mbmi->second_ref_frame,
mbmi->mv[0].as_mv.row, mbmi->mv[0].as_mv.col,
mbmi->interp_filter);
assert(cm->frame_type != KEY_FRAME);
ref_fb_idx = cpi->common.ref_frame_map[cpi->lst_fb_idx];
ref_fb_idx = cpi->common.ref_frame_map[cpi->gld_fb_idx];
ref_fb_idx = cpi->common.ref_frame_map[cpi->alt_fb_idx];
setup_pred_block(&xd->pre,
&cpi->common.yv12_fb[ref_fb_idx],
mb_row, mb_col,
&xd->scale_factor[0], &xd->scale_factor_uv[0]);
second_ref_fb_idx = cpi->common.ref_frame_map[cpi->lst_fb_idx];
second_ref_fb_idx = cpi->common.ref_frame_map[cpi->gld_fb_idx];
second_ref_fb_idx = cpi->common.ref_frame_map[cpi->alt_fb_idx];
setup_pred_block(&xd->second_pre,
&cpi->common.yv12_fb[second_ref_fb_idx],
mb_row, mb_col,
&xd->scale_factor[1], &xd->scale_factor_uv[1]);
vp9_encode_inter16x16(cm, x, mb_row, mb_col);
// Clear mb_skip_coeff if mb_no_coeff_skip is not set
if (!cpi->common.mb_no_coeff_skip)
vp9_build_inter16x16_predictors_mb(xd,
xd->dst.y_buffer,
xd->dst.u_buffer,
xd->dst.v_buffer,
xd->dst.y_stride,
xd->dst.uv_stride,
mb_row, mb_col);
#if CONFIG_COMP_INTERINTRA_PRED
if (xd->mode_info_context->mbmi.second_ref_frame == INTRA_FRAME) {
vp9_build_interintra_16x16_predictors_mb(xd,
xd->dst.y_buffer,
xd->dst.u_buffer,
xd->dst.v_buffer,
xd->dst.y_stride,
xd->dst.uv_stride);
}
#endif
int i, j;
printf("\n");
printf("qcoeff\n");
for (i = 0; i < 384; i++) {
printf("%3d ", xd->qcoeff[i]);
if (i % 16 == 15) printf("\n");
}
printf("\n");
2208
2209
2210
2211
2212
2213
2214
2215
2216
2217
2218
2219
2220
2221
2222
2223
2224
2225
2226
2227
2228
2229
2230
2231
2232
2233
2234
2235
2236
2237
2238
printf("predictor\n");
for (i = 0; i < 384; i++) {
printf("%3d ", xd->predictor[i]);
if (i % 16 == 15) printf("\n");
}
printf("\n");
printf("src_diff\n");
for (i = 0; i < 384; i++) {
printf("%3d ", x->src_diff[i]);
if (i % 16 == 15) printf("\n");
}
printf("\n");
printf("diff\n");
for (i = 0; i < 384; i++) {
printf("%3d ", xd->block[0].diff[i]);
if (i % 16 == 15) printf("\n");
}
printf("\n");
printf("final y\n");
for (i = 0; i < 16; i++) {
for (j = 0; j < 16; j++)
printf("%3d ", xd->dst.y_buffer[i * xd->dst.y_stride + j]);
printf("\n");
}
printf("\n");
printf("final u\n");
for (i = 0; i < 8; i++) {
for (j = 0; j < 8; j++)
printf("%3d ", xd->dst.u_buffer[i * xd->dst.uv_stride + j]);
printf("\n");
}
printf("final v\n");
for (i = 0; i < 8; i++) {
for (j = 0; j < 8; j++)
printf("%3d ", xd->dst.v_buffer[i * xd->dst.uv_stride + j]);
printf("\n");
}
#if CONFIG_CODE_NONZEROCOUNT
gather_nzcs_mb16(cm, xd);
#endif
vp9_tokenize_mb(cpi, xd, t, !output_enabled);
// FIXME(rbultje): not tile-aware (mi - 1)
int mb_skip_context = cpi->common.mb_no_coeff_skip ?
(mi - 1)->mbmi.mb_skip_coeff + (mi - mis)->mbmi.mb_skip_coeff : 0;
if (cm->mb_no_coeff_skip) {
if (output_enabled)
cpi->skip_true_count[mb_skip_context]++;
vp9_stuff_mb(cpi, xd, t, !output_enabled);
if (output_enabled)
cpi->skip_false_count[mb_skip_context]++;
if (output_enabled) {
int segment_id = mbmi->segment_id;
if (cpi->common.txfm_mode == TX_MODE_SELECT &&
!((cpi->common.mb_no_coeff_skip && mbmi->mb_skip_coeff) ||
(vp9_segfeature_active(&x->e_mbd, segment_id, SEG_LVL_SKIP)))) {
assert(mbmi->txfm_size <= TX_16X16);
if (mbmi->mode != B_PRED && mbmi->mode != I8X8_PRED &&
mbmi->mode != SPLITMV) {
cpi->txfm_count_16x16p[mbmi->txfm_size]++;
} else if (mbmi->mode == I8X8_PRED ||
(mbmi->mode == SPLITMV &&
mbmi->partitioning != PARTITIONING_4X4)) {
cpi->txfm_count_8x8p[mbmi->txfm_size]++;
} else if (mbmi->mode != B_PRED && mbmi->mode != I8X8_PRED &&
mbmi->mode != SPLITMV && cpi->common.txfm_mode >= ALLOW_16X16) {
mbmi->txfm_size = TX_16X16;
} else if (mbmi->mode != B_PRED &&
!(mbmi->mode == SPLITMV &&
mbmi->partitioning == PARTITIONING_4X4) &&
cpi->common.txfm_mode >= ALLOW_8X8) {
mbmi->txfm_size = TX_8X8;
} else {
mbmi->txfm_size = TX_4X4;
}
}
static void encode_superblock32(VP9_COMP *cpi, TOKENEXTRA **t,
int output_enabled, int mb_row, int mb_col) {
VP9_COMMON *const cm = &cpi->common;
MACROBLOCKD *const xd = &x->e_mbd;
const uint8_t *src = x->src.y_buffer;
uint8_t *dst = xd->dst.y_buffer;
const uint8_t *usrc = x->src.u_buffer;
uint8_t *udst = xd->dst.u_buffer;
const uint8_t *vsrc = x->src.v_buffer;
uint8_t *vdst = xd->dst.v_buffer;
int src_y_stride = x->src.y_stride, dst_y_stride = xd->dst.y_stride;
int src_uv_stride = x->src.uv_stride, dst_uv_stride = xd->dst.uv_stride;
unsigned char ref_pred_flag;
MODE_INFO *mi = x->e_mbd.mode_info_context;
unsigned int segment_id = mi->mbmi.segment_id;
const int mis = cm->mode_info_stride;
#ifdef ENC_DEBUG
enc_debug = (cpi->common.current_video_frame == 1 &&
mb_row == 0 && mb_col == 0 && output_enabled);
if (enc_debug)
printf("Encode SB32 %d %d output %d\n", mb_row, mb_col, output_enabled);
#endif
if (cm->frame_type == KEY_FRAME) {
if (cpi->oxcf.tuning == VP8_TUNE_SSIM) {
adjust_act_zbin(cpi, x);
vp9_update_zbin_extra(cpi, x);
}
} else {
vp9_setup_interp_filters(xd, xd->mode_info_context->mbmi.interp_filter, cm);
if (cpi->oxcf.tuning == VP8_TUNE_SSIM) {
// Adjust the zbin based on this MB rate.
adjust_act_zbin(cpi, x);
}
// Experimental code. Special case for gf and arf zeromv modes.
// Increase zbin size to suppress noise
cpi->zbin_mode_boost = 0;
if (cpi->zbin_mode_boost_enabled) {
if (xd->mode_info_context->mbmi.ref_frame != INTRA_FRAME) {
if (xd->mode_info_context->mbmi.mode == ZEROMV) {
if (xd->mode_info_context->mbmi.ref_frame != LAST_FRAME)
cpi->zbin_mode_boost = GF_ZEROMV_ZBIN_BOOST;
else
cpi->zbin_mode_boost = LF_ZEROMV_ZBIN_BOOST;
} else if (xd->mode_info_context->mbmi.mode == SPLITMV)
cpi->zbin_mode_boost = 0;
else
cpi->zbin_mode_boost = MV_ZBIN_BOOST;
}
}
vp9_update_zbin_extra(cpi, x);
// SET VARIOUS PREDICTION FLAGS
// Did the chosen reference frame match its predicted value.
ref_pred_flag = ((xd->mode_info_context->mbmi.ref_frame ==
vp9_get_pred_ref(cm, xd)));
vp9_set_pred_flag(xd, PRED_REF, ref_pred_flag);
}
if (xd->mode_info_context->mbmi.ref_frame == INTRA_FRAME) {
vp9_build_intra_predictors_sby_s(&x->e_mbd);
vp9_build_intra_predictors_sbuv_s(&x->e_mbd);
if (output_enabled)
sum_intra_stats(cpi, x);
assert(cm->frame_type != KEY_FRAME);
if (xd->mode_info_context->mbmi.ref_frame == LAST_FRAME)
ref_fb_idx = cpi->common.ref_frame_map[cpi->lst_fb_idx];
else if (xd->mode_info_context->mbmi.ref_frame == GOLDEN_FRAME)
ref_fb_idx = cpi->common.ref_frame_map[cpi->gld_fb_idx];
ref_fb_idx = cpi->common.ref_frame_map[cpi->alt_fb_idx];
setup_pred_block(&xd->pre,
&cpi->common.yv12_fb[ref_fb_idx],
mb_row, mb_col,
&xd->scale_factor[0], &xd->scale_factor_uv[0]);
if (xd->mode_info_context->mbmi.second_ref_frame > 0) {
int second_ref_fb_idx;
if (xd->mode_info_context->mbmi.second_ref_frame == LAST_FRAME)
second_ref_fb_idx = cpi->common.ref_frame_map[cpi->lst_fb_idx];
else if (xd->mode_info_context->mbmi.second_ref_frame == GOLDEN_FRAME)
second_ref_fb_idx = cpi->common.ref_frame_map[cpi->gld_fb_idx];
second_ref_fb_idx = cpi->common.ref_frame_map[cpi->alt_fb_idx];
setup_pred_block(&xd->second_pre,
&cpi->common.yv12_fb[second_ref_fb_idx],
mb_row, mb_col,
&xd->scale_factor[1], &xd->scale_factor_uv[1]);
vp9_build_inter32x32_predictors_sb(xd, xd->dst.y_buffer,
xd->dst.y_stride, xd->dst.uv_stride,
mb_row, mb_col);
if (!x->skip) {
vp9_subtract_sby_s_c(x->src_diff, src, src_y_stride,
dst, dst_y_stride);
vp9_subtract_sbuv_s_c(x->src_diff,
usrc, vsrc, src_uv_stride,
udst, vdst, dst_uv_stride);
switch (mi->mbmi.txfm_size) {
case TX_32X32:
vp9_transform_sby_32x32(x);
vp9_transform_sbuv_16x16(x);
vp9_quantize_sby_32x32(x);
vp9_quantize_sbuv_16x16(x);
if (x->optimize) {
vp9_optimize_sby_32x32(cm, x);
vp9_optimize_sbuv_16x16(cm, x);
}
vp9_inverse_transform_sby_32x32(xd);
vp9_inverse_transform_sbuv_16x16(xd);
break;
case TX_16X16:
vp9_transform_sby_16x16(x);
vp9_transform_sbuv_16x16(x);
vp9_quantize_sby_16x16(x);
vp9_quantize_sbuv_16x16(x);
if (x->optimize) {
vp9_optimize_sby_16x16(cm, x);
vp9_optimize_sbuv_16x16(cm, x);
}
vp9_inverse_transform_sby_16x16(xd);
vp9_inverse_transform_sbuv_16x16(xd);
break;
case TX_8X8:
vp9_transform_sby_8x8(x);
vp9_transform_sbuv_8x8(x);
vp9_quantize_sby_8x8(x);
vp9_quantize_sbuv_8x8(x);
if (x->optimize) {
vp9_optimize_sby_8x8(cm, x);
vp9_optimize_sbuv_8x8(cm, x);
}
vp9_inverse_transform_sby_8x8(xd);
vp9_inverse_transform_sbuv_8x8(xd);
break;
case TX_4X4:
vp9_transform_sby_4x4(x);
vp9_transform_sbuv_4x4(x);
vp9_quantize_sby_4x4(x);
vp9_quantize_sbuv_4x4(x);
if (x->optimize) {
vp9_optimize_sby_4x4(cm, x);
vp9_optimize_sbuv_4x4(cm, x);
}
vp9_inverse_transform_sby_4x4(xd);
vp9_inverse_transform_sbuv_4x4(xd);
break;
default: assert(0);
vp9_recon_sby_s_c(xd, dst);
vp9_recon_sbuv_s_c(xd, udst, vdst);
#if CONFIG_CODE_NONZEROCOUNT
gather_nzcs_sb32(cm, xd);
#endif
vp9_tokenize_sb(cpi, xd, t, !output_enabled);
// FIXME(rbultje): not tile-aware (mi - 1)
int mb_skip_context = cm->mb_no_coeff_skip ?
(mi - 1)->mbmi.mb_skip_coeff + (mi - mis)->mbmi.mb_skip_coeff : 0;
mi->mbmi.mb_skip_coeff = 1;
if (cm->mb_no_coeff_skip) {
if (output_enabled)
cpi->skip_true_count[mb_skip_context]++;
vp9_reset_sb_tokens_context(xd);
} else {
vp9_stuff_sb(cpi, xd, t, !output_enabled);
if (output_enabled)
cpi->skip_false_count[mb_skip_context]++;
// copy skip flag on all mb_mode_info contexts in this SB
// if this was a skip at this txfm size
if (mb_col < cm->mb_cols - 1)
mi[1].mbmi.mb_skip_coeff = mi->mbmi.mb_skip_coeff;
if (mb_row < cm->mb_rows - 1) {
mi[mis].mbmi.mb_skip_coeff = mi->mbmi.mb_skip_coeff;
if (mb_col < cm->mb_cols - 1)
mi[mis + 1].mbmi.mb_skip_coeff = mi->mbmi.mb_skip_coeff;
if (output_enabled) {
if (cm->txfm_mode == TX_MODE_SELECT &&
!((cm->mb_no_coeff_skip && mi->mbmi.mb_skip_coeff) ||
(vp9_segfeature_active(xd, segment_id, SEG_LVL_SKIP)))) {
cpi->txfm_count_32x32p[mi->mbmi.txfm_size]++;
} else {
TX_SIZE sz = (cm->txfm_mode == TX_MODE_SELECT) ? TX_32X32 : cm->txfm_mode;
2507
2508
2509
2510
2511
2512
2513
2514
2515
2516
2517
2518
2519
2520
2521
2522
2523
2524
2525
2526
2527
2528
2529
2530
2531
2532
2533
2534
2535
2536
2537
mi->mbmi.txfm_size = sz;
if (mb_col < cm->mb_cols - 1)
mi[1].mbmi.txfm_size = sz;
if (mb_row < cm->mb_rows - 1) {
mi[mis].mbmi.txfm_size = sz;
if (mb_col < cm->mb_cols - 1)
mi[mis + 1].mbmi.txfm_size = sz;
}
}
}
}
static void encode_superblock64(VP9_COMP *cpi, TOKENEXTRA **t,
int output_enabled, int mb_row, int mb_col) {
VP9_COMMON *const cm = &cpi->common;
MACROBLOCK *const x = &cpi->mb;
MACROBLOCKD *const xd = &x->e_mbd;
const uint8_t *src = x->src.y_buffer;
uint8_t *dst = xd->dst.y_buffer;
const uint8_t *usrc = x->src.u_buffer;
uint8_t *udst = xd->dst.u_buffer;
const uint8_t *vsrc = x->src.v_buffer;
uint8_t *vdst = xd->dst.v_buffer;
int src_y_stride = x->src.y_stride, dst_y_stride = xd->dst.y_stride;
int src_uv_stride = x->src.uv_stride, dst_uv_stride = xd->dst.uv_stride;
unsigned char ref_pred_flag;
int n;
MODE_INFO *mi = x->e_mbd.mode_info_context;
unsigned int segment_id = mi->mbmi.segment_id;
const int mis = cm->mode_info_stride;
#ifdef ENC_DEBUG
enc_debug = (cpi->common.current_video_frame == 1 &&
mb_row == 0 && mb_col == 0 && output_enabled);
if (enc_debug)
printf("Encode SB64 %d %d output %d\n", mb_row, mb_col, output_enabled);
#endif
2544
2545
2546
2547
2548
2549
2550
2551
2552
2553
2554
2555
2556
2557
2558
2559
2560
2561
2562
2563
2564
2565
2566
2567
2568
2569
2570
2571
2572
2573
2574
2575
2576
2577
2578
2579
2580
2581
2582
2583
2584
2585
2586
2587
if (cm->frame_type == KEY_FRAME) {
if (cpi->oxcf.tuning == VP8_TUNE_SSIM) {
adjust_act_zbin(cpi, x);
vp9_update_zbin_extra(cpi, x);
}
} else {
vp9_setup_interp_filters(xd, xd->mode_info_context->mbmi.interp_filter, cm);
if (cpi->oxcf.tuning == VP8_TUNE_SSIM) {
// Adjust the zbin based on this MB rate.
adjust_act_zbin(cpi, x);
}
// Experimental code. Special case for gf and arf zeromv modes.
// Increase zbin size to suppress noise
cpi->zbin_mode_boost = 0;
if (cpi->zbin_mode_boost_enabled) {
if (xd->mode_info_context->mbmi.ref_frame != INTRA_FRAME) {
if (xd->mode_info_context->mbmi.mode == ZEROMV) {
if (xd->mode_info_context->mbmi.ref_frame != LAST_FRAME)
cpi->zbin_mode_boost = GF_ZEROMV_ZBIN_BOOST;
else
cpi->zbin_mode_boost = LF_ZEROMV_ZBIN_BOOST;
} else if (xd->mode_info_context->mbmi.mode == SPLITMV) {
cpi->zbin_mode_boost = 0;
} else {
cpi->zbin_mode_boost = MV_ZBIN_BOOST;
}
}
}
vp9_update_zbin_extra(cpi, x);
// Did the chosen reference frame match its predicted value.
ref_pred_flag = ((xd->mode_info_context->mbmi.ref_frame ==
vp9_get_pred_ref(cm, xd)));
vp9_set_pred_flag(xd, PRED_REF, ref_pred_flag);
}
if (xd->mode_info_context->mbmi.ref_frame == INTRA_FRAME) {
vp9_build_intra_predictors_sb64y_s(&x->e_mbd);
vp9_build_intra_predictors_sb64uv_s(&x->e_mbd);
if (output_enabled)
sum_intra_stats(cpi, x);
int ref_fb_idx;
assert(cm->frame_type != KEY_FRAME);
if (xd->mode_info_context->mbmi.ref_frame == LAST_FRAME)
ref_fb_idx = cpi->common.ref_frame_map[cpi->lst_fb_idx];
else if (xd->mode_info_context->mbmi.ref_frame == GOLDEN_FRAME)
ref_fb_idx = cpi->common.ref_frame_map[cpi->gld_fb_idx];
ref_fb_idx = cpi->common.ref_frame_map[cpi->alt_fb_idx];
setup_pred_block(&xd->pre,
&cpi->common.yv12_fb[ref_fb_idx],
mb_row, mb_col,
&xd->scale_factor[0], &xd->scale_factor_uv[0]);
if (xd->mode_info_context->mbmi.second_ref_frame > 0) {
int second_ref_fb_idx;
if (xd->mode_info_context->mbmi.second_ref_frame == LAST_FRAME)
second_ref_fb_idx = cpi->common.ref_frame_map[cpi->lst_fb_idx];
else if (xd->mode_info_context->mbmi.second_ref_frame == GOLDEN_FRAME)
second_ref_fb_idx = cpi->common.ref_frame_map[cpi->gld_fb_idx];
second_ref_fb_idx = cpi->common.ref_frame_map[cpi->alt_fb_idx];
setup_pred_block(&xd->second_pre,
&cpi->common.yv12_fb[second_ref_fb_idx],
mb_row, mb_col,
&xd->scale_factor[1], &xd->scale_factor_uv[1]);
}
vp9_build_inter64x64_predictors_sb(xd, xd->dst.y_buffer,
xd->dst.u_buffer, xd->dst.v_buffer,
xd->dst.y_stride, xd->dst.uv_stride,
mb_row, mb_col);
if (!x->skip) {
vp9_subtract_sb64y_s_c(x->src_diff, src, src_y_stride, dst, dst_y_stride);
vp9_subtract_sb64uv_s_c(x->src_diff, usrc, vsrc, src_uv_stride,
udst, vdst, dst_uv_stride);
switch (xd->mode_info_context->mbmi.txfm_size) {
case TX_32X32:
vp9_transform_sb64y_32x32(x);
vp9_transform_sb64uv_32x32(x);
vp9_quantize_sb64y_32x32(x);
vp9_quantize_sb64uv_32x32(x);
if (x->optimize) {
vp9_optimize_sb64y_32x32(cm, x);
vp9_optimize_sb64uv_32x32(cm, x);
vp9_inverse_transform_sb64y_32x32(xd);
vp9_inverse_transform_sb64uv_32x32(xd);
break;
case TX_16X16:
vp9_transform_sb64y_16x16(x);
vp9_transform_sb64uv_16x16(x);
vp9_quantize_sb64y_16x16(x);
vp9_quantize_sb64uv_16x16(x);
if (x->optimize) {
vp9_optimize_sb64y_16x16(cm, x);
vp9_optimize_sb64uv_16x16(cm, x);
}
vp9_inverse_transform_sb64y_16x16(xd);
vp9_inverse_transform_sb64uv_16x16(xd);
break;
case TX_8X8:
vp9_transform_sb64y_8x8(x);
vp9_transform_sb64uv_8x8(x);
vp9_quantize_sb64y_8x8(x);
vp9_quantize_sb64uv_8x8(x);
if (x->optimize) {
vp9_optimize_sb64y_8x8(cm, x);
vp9_optimize_sb64uv_8x8(cm, x);
}
vp9_inverse_transform_sb64y_8x8(xd);
vp9_inverse_transform_sb64uv_8x8(xd);
break;
case TX_4X4:
vp9_transform_sb64y_4x4(x);
vp9_transform_sb64uv_4x4(x);
vp9_quantize_sb64y_4x4(x);
vp9_quantize_sb64uv_4x4(x);
if (x->optimize) {
vp9_optimize_sb64y_4x4(cm, x);
vp9_optimize_sb64uv_4x4(cm, x);
}
vp9_inverse_transform_sb64y_4x4(xd);
vp9_inverse_transform_sb64uv_4x4(xd);
break;
default: assert(0);
vp9_recon_sb64y_s_c(xd, dst);
vp9_recon_sb64uv_s_c(&x->e_mbd, udst, vdst);
#if CONFIG_CODE_NONZEROCOUNT
gather_nzcs_sb64(cm, &x->e_mbd);
#endif
vp9_tokenize_sb64(cpi, &x->e_mbd, t, !output_enabled);
// FIXME(rbultje): not tile-aware (mi - 1)
int mb_skip_context = cpi->common.mb_no_coeff_skip ?
(mi - 1)->mbmi.mb_skip_coeff + (mi - mis)->mbmi.mb_skip_coeff : 0;
xd->mode_info_context->mbmi.mb_skip_coeff = 1;
if (cm->mb_no_coeff_skip) {
if (output_enabled)
cpi->skip_true_count[mb_skip_context]++;
vp9_reset_sb64_tokens_context(xd);
} else {
vp9_stuff_sb64(cpi, xd, t, !output_enabled);
if (output_enabled)
cpi->skip_false_count[mb_skip_context]++;
// copy skip flag on all mb_mode_info contexts in this SB
// if this was a skip at this txfm size
for (n = 1; n < 16; n++) {
const int x_idx = n & 3, y_idx = n >> 2;
if (mb_col + x_idx < cm->mb_cols && mb_row + y_idx < cm->mb_rows)
mi[x_idx + y_idx * mis].mbmi.mb_skip_coeff = mi->mbmi.mb_skip_coeff;
}
if (output_enabled) {
if (cm->txfm_mode == TX_MODE_SELECT &&
!((cm->mb_no_coeff_skip && mi->mbmi.mb_skip_coeff) ||
(vp9_segfeature_active(xd, segment_id, SEG_LVL_SKIP)))) {
cpi->txfm_count_32x32p[mi->mbmi.txfm_size]++;
} else {
int x, y;
TX_SIZE sz = (cm->txfm_mode == TX_MODE_SELECT) ? TX_32X32 : cm->txfm_mode;
for (y = 0; y < 4; y++) {
for (x = 0; x < 4; x++) {
if (mb_col + x < cm->mb_cols && mb_row + y < cm->mb_rows) {
mi[mis * y + x].mbmi.txfm_size = sz;
}
}
}