Calculate rd cost per transformed block
This commit makes the rate-distortion optimization loop evaluate the rd costs of regular quantization and all zero coeffs, per transformed block. It improves speed 1 compression performance: derf: 0.245% yt: 0.515% For a large partition that consists multiple transformed blocks, this allows more flexibility to selectively force a portion of them coded as all zero coeffs, as well be continued in the next patches. Change-Id: I211518be4179747b57375696f017d1160cc91851
This commit is contained in:
@@ -554,9 +554,13 @@ struct rdcost_block_args {
|
|||||||
TX_SIZE tx_size;
|
TX_SIZE tx_size;
|
||||||
int bw;
|
int bw;
|
||||||
int bh;
|
int bh;
|
||||||
int rate;
|
int rate[256];
|
||||||
int64_t dist;
|
int64_t dist[256];
|
||||||
int64_t sse;
|
int64_t sse[256];
|
||||||
|
int this_rate;
|
||||||
|
int64_t this_dist;
|
||||||
|
int64_t this_sse;
|
||||||
|
int64_t this_rd;
|
||||||
int64_t best_rd;
|
int64_t best_rd;
|
||||||
int skip;
|
int skip;
|
||||||
const int16_t *scan, *nb;
|
const int16_t *scan, *nb;
|
||||||
@@ -573,17 +577,17 @@ static void dist_block(int plane, int block, TX_SIZE tx_size, void *arg) {
|
|||||||
int shift = args->tx_size == TX_32X32 ? 0 : 2;
|
int shift = args->tx_size == TX_32X32 ? 0 : 2;
|
||||||
int16_t *const coeff = BLOCK_OFFSET(p->coeff, block);
|
int16_t *const coeff = BLOCK_OFFSET(p->coeff, block);
|
||||||
int16_t *const dqcoeff = BLOCK_OFFSET(pd->dqcoeff, block);
|
int16_t *const dqcoeff = BLOCK_OFFSET(pd->dqcoeff, block);
|
||||||
args->dist += vp9_block_error(coeff, dqcoeff, 16 << ss_txfrm_size,
|
args->dist[block] = vp9_block_error(coeff, dqcoeff, 16 << ss_txfrm_size,
|
||||||
&this_sse) >> shift;
|
&this_sse) >> shift;
|
||||||
args->sse += this_sse >> shift;
|
args->sse[block] = this_sse >> shift;
|
||||||
|
|
||||||
if (x->skip_encode &&
|
if (x->skip_encode &&
|
||||||
xd->this_mi->mbmi.ref_frame[0] == INTRA_FRAME) {
|
xd->this_mi->mbmi.ref_frame[0] == INTRA_FRAME) {
|
||||||
// TODO(jingning): tune the model to better capture the distortion.
|
// TODO(jingning): tune the model to better capture the distortion.
|
||||||
int64_t p = (pd->dequant[1] * pd->dequant[1] *
|
int64_t p = (pd->dequant[1] * pd->dequant[1] *
|
||||||
(1 << ss_txfrm_size)) >> shift;
|
(1 << ss_txfrm_size)) >> shift;
|
||||||
args->dist += p;
|
args->dist[block] = p;
|
||||||
args->sse += p;
|
args->sse[block] = p;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -594,7 +598,7 @@ static void rate_block(int plane, int block, BLOCK_SIZE plane_bsize,
|
|||||||
int x_idx, y_idx;
|
int x_idx, y_idx;
|
||||||
txfrm_block_to_raster_xy(plane_bsize, args->tx_size, block, &x_idx, &y_idx);
|
txfrm_block_to_raster_xy(plane_bsize, args->tx_size, block, &x_idx, &y_idx);
|
||||||
|
|
||||||
args->rate += cost_coeffs(args->x, plane, block,
|
args->rate[block] = cost_coeffs(args->x, plane, block,
|
||||||
args->t_above + x_idx,
|
args->t_above + x_idx,
|
||||||
args->t_left + y_idx, args->tx_size,
|
args->t_left + y_idx, args->tx_size,
|
||||||
args->scan, args->nb);
|
args->scan, args->nb);
|
||||||
@@ -610,16 +614,6 @@ static void block_yrd_txfm(int plane, int block, BLOCK_SIZE plane_bsize,
|
|||||||
|
|
||||||
if (args->skip)
|
if (args->skip)
|
||||||
return;
|
return;
|
||||||
rd1 = RDCOST(x->rdmult, x->rddiv, args->rate, args->dist);
|
|
||||||
rd2 = RDCOST(x->rdmult, x->rddiv, 0, args->sse);
|
|
||||||
rd = MIN(rd1, rd2);
|
|
||||||
if (rd > args->best_rd) {
|
|
||||||
args->skip = 1;
|
|
||||||
args->rate = INT_MAX;
|
|
||||||
args->dist = INT64_MAX;
|
|
||||||
args->sse = INT64_MAX;
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!is_inter_block(&xd->this_mi->mbmi))
|
if (!is_inter_block(&xd->this_mi->mbmi))
|
||||||
vp9_encode_block_intra(plane, block, plane_bsize, tx_size, &encode_args);
|
vp9_encode_block_intra(plane, block, plane_bsize, tx_size, &encode_args);
|
||||||
@@ -628,6 +622,18 @@ static void block_yrd_txfm(int plane, int block, BLOCK_SIZE plane_bsize,
|
|||||||
|
|
||||||
dist_block(plane, block, tx_size, args);
|
dist_block(plane, block, tx_size, args);
|
||||||
rate_block(plane, block, plane_bsize, tx_size, args);
|
rate_block(plane, block, plane_bsize, tx_size, args);
|
||||||
|
rd1 = RDCOST(x->rdmult, x->rddiv, args->rate[block], args->dist[block]);
|
||||||
|
rd2 = RDCOST(x->rdmult, x->rddiv, 0, args->sse[block]);
|
||||||
|
rd = MIN(rd1, rd2);
|
||||||
|
args->this_rate += args->rate[block];
|
||||||
|
args->this_dist += args->dist[block];
|
||||||
|
args->this_sse += args->sse[block];
|
||||||
|
args->this_rd += rd;
|
||||||
|
|
||||||
|
if (args->this_rd > args->best_rd) {
|
||||||
|
args->skip = 1;
|
||||||
|
return;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static void txfm_rd_in_plane(MACROBLOCK *x,
|
static void txfm_rd_in_plane(MACROBLOCK *x,
|
||||||
@@ -643,7 +649,8 @@ static void txfm_rd_in_plane(MACROBLOCK *x,
|
|||||||
int i;
|
int i;
|
||||||
struct rdcost_block_args args = { x, { 0 }, { 0 }, tx_size,
|
struct rdcost_block_args args = { x, { 0 }, { 0 }, tx_size,
|
||||||
num_4x4_blocks_wide, num_4x4_blocks_high,
|
num_4x4_blocks_wide, num_4x4_blocks_high,
|
||||||
0, 0, 0, ref_best_rd, 0 };
|
{ 0 }, { 0 }, { 0 },
|
||||||
|
0, 0, 0, 0, ref_best_rd, 0 };
|
||||||
if (plane == 0)
|
if (plane == 0)
|
||||||
xd->this_mi->mbmi.tx_size = tx_size;
|
xd->this_mi->mbmi.tx_size = tx_size;
|
||||||
|
|
||||||
@@ -685,10 +692,17 @@ static void txfm_rd_in_plane(MACROBLOCK *x,
|
|||||||
}
|
}
|
||||||
|
|
||||||
foreach_transformed_block_in_plane(xd, bsize, plane, block_yrd_txfm, &args);
|
foreach_transformed_block_in_plane(xd, bsize, plane, block_yrd_txfm, &args);
|
||||||
*distortion = args.dist;
|
if (args.skip) {
|
||||||
*rate = args.rate;
|
*rate = INT_MAX;
|
||||||
*sse = args.sse;
|
*distortion = INT64_MAX;
|
||||||
*skippable = vp9_is_skippable_in_plane(xd, bsize, plane) && (!args.skip);
|
*sse = INT64_MAX;
|
||||||
|
*skippable = 0;
|
||||||
|
} else {
|
||||||
|
*distortion = args.this_dist;
|
||||||
|
*rate = args.this_rate;
|
||||||
|
*sse = args.this_sse;
|
||||||
|
*skippable = vp9_is_skippable_in_plane(xd, bsize, plane);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static void choose_largest_txfm_size(VP9_COMP *cpi, MACROBLOCK *x,
|
static void choose_largest_txfm_size(VP9_COMP *cpi, MACROBLOCK *x,
|
||||||
|
|||||||
Reference in New Issue
Block a user