ref: e570b0406db127ea53047a8e76d22174e5ac0638
parent: bdd60a7be779400e597cae001448a44d21c98f2b
author: Attila Nagy <attilanagy@google.com>
date: Tue Nov 29 08:48:02 EST 2011
Reduce mem copies in encoder loopfilter level picking Do the test filtering in the existing backup frame buffer instead of the original. Copy the original data into extra buffer before doing the filtering. This way there is no need to restore the original unfiltered frame at the end of level picking process. This came up in some discussions with Johann. Thanks! Change-Id: I495f4301d983854673276c34ec0ddf9a9d622122
--- a/vp8/encoder/onyx_if.c
+++ b/vp8/encoder/onyx_if.c
@@ -355,7 +355,7 @@
vp8_de_alloc_frame_buffers(&cpi->common);
- vp8_yv12_de_alloc_frame_buffer(&cpi->last_frame_uf);
+ vp8_yv12_de_alloc_frame_buffer(&cpi->pick_lf_lvl_frame);
vp8_yv12_de_alloc_frame_buffer(&cpi->scaled_source);
#if VP8_TEMPORAL_ALT_REF
vp8_yv12_de_alloc_frame_buffer(&cpi->alt_ref_buffer);
@@ -1365,7 +1365,7 @@
height += 16 - (height & 0xf);
- if (vp8_yv12_alloc_frame_buffer(&cpi->last_frame_uf,
+ if (vp8_yv12_alloc_frame_buffer(&cpi->pick_lf_lvl_frame,
width, height, VP8BORDERINPIXELS))
vpx_internal_error(&cpi->common.error, VPX_CODEC_MEM_ERROR,
"Failed to allocate last frame buffer");
--- a/vp8/encoder/onyx_int.h
+++ b/vp8/encoder/onyx_int.h
@@ -336,7 +336,7 @@
int gold_is_alt; // don't do both alt and gold search ( just do gold).
//int refresh_alt_ref_frame;
- YV12_BUFFER_CONFIG last_frame_uf;
+ YV12_BUFFER_CONFIG pick_lf_lvl_frame;
TOKENEXTRA *tok;
unsigned int tok_count;
--- a/vp8/encoder/picklpf.c
+++ b/vp8/encoder/picklpf.c
@@ -152,9 +152,10 @@
int max_filter_level = get_max_filter_level(cpi, cm->base_qindex);
int filt_val;
int best_filt_val = cm->filter_level;
+ YV12_BUFFER_CONFIG * saved_frame = cm->frame_to_show;
- // Make a copy of the unfiltered / processed recon buffer
- vp8_yv12_copy_partial_frame_ptr(cm->frame_to_show, &cpi->last_frame_uf);
+ /* Replace unfiltered frame buffer with a new one */
+ cm->frame_to_show = &cpi->pick_lf_lvl_frame;
if (cm->frame_type == KEY_FRAME)
cm->sharpness_level = 0;
@@ -177,13 +178,14 @@
best_filt_val = filt_val;
// Get the err using the previous frame's filter value.
+
+ /* Copy the unfiltered / processed recon buffer to the new buffer */
+ vp8_yv12_copy_partial_frame_ptr(saved_frame, cm->frame_to_show);
vp8_loop_filter_partial_frame(cm, &cpi->mb.e_mbd, filt_val);
- best_err = calc_partial_ssl_err(sd, cm->frame_to_show, IF_RTCD(&cpi->rtcd.variance));
+ best_err = calc_partial_ssl_err(sd, cm->frame_to_show,
+ IF_RTCD(&cpi->rtcd.variance));
- // Re-instate the unfiltered frame
- vp8_yv12_copy_partial_frame_ptr(&cpi->last_frame_uf, cm->frame_to_show);
-
filt_val -= (1 + ((filt_val > 10) ? 1 : 0));
// Search lower filter levels
@@ -190,14 +192,13 @@
while (filt_val >= min_filter_level)
{
// Apply the loop filter
+ vp8_yv12_copy_partial_frame_ptr(saved_frame, cm->frame_to_show);
vp8_loop_filter_partial_frame(cm, &cpi->mb.e_mbd, filt_val);
// Get the err for filtered frame
- filt_err = calc_partial_ssl_err(sd, cm->frame_to_show, IF_RTCD(&cpi->rtcd.variance));
+ filt_err = calc_partial_ssl_err(sd, cm->frame_to_show,
+ IF_RTCD(&cpi->rtcd.variance));
- // Re-instate the unfiltered frame
- vp8_yv12_copy_partial_frame_ptr(&cpi->last_frame_uf, cm->frame_to_show);
-
// Update the best case record or exit loop.
if (filt_err < best_err)
{
@@ -222,14 +223,14 @@
while (filt_val < max_filter_level)
{
// Apply the loop filter
+ vp8_yv12_copy_partial_frame_ptr(saved_frame, cm->frame_to_show);
+
vp8_loop_filter_partial_frame(cm, &cpi->mb.e_mbd, filt_val);
// Get the err for filtered frame
- filt_err = calc_partial_ssl_err(sd, cm->frame_to_show, IF_RTCD(&cpi->rtcd.variance));
+ filt_err = calc_partial_ssl_err(sd, cm->frame_to_show,
+ IF_RTCD(&cpi->rtcd.variance));
- // Re-instate the unfiltered frame
- vp8_yv12_copy_partial_frame_ptr(&cpi->last_frame_uf, cm->frame_to_show);
-
// Update the best case record or exit loop.
if (filt_err < best_err)
{
@@ -253,6 +254,9 @@
if (cm->filter_level > max_filter_level)
cm->filter_level = max_filter_level;
+
+ /* restore unfiltered frame pointer */
+ cm->frame_to_show = saved_frame;
}
// Stub function for now Alt LF not used
@@ -283,11 +287,13 @@
int filt_best;
int filt_direction = 0;
- int Bias = 0; // Bias against raising loop filter and in favour of lowering it
+ int Bias = 0; // Bias against raising loop filter and in favor of lowering it
- // Make a copy of the unfiltered / processed recon buffer
- vp8_yv12_copy_y_ptr(cm->frame_to_show, &cpi->last_frame_uf);
+ YV12_BUFFER_CONFIG * saved_frame = cm->frame_to_show;
+ /* Replace unfiltered frame buffer with a new one */
+ cm->frame_to_show = &cpi->pick_lf_lvl_frame;
+
if (cm->frame_type == KEY_FRAME)
cm->sharpness_level = 0;
else
@@ -305,15 +311,17 @@
filter_step = (filt_mid < 16) ? 4 : filt_mid / 4;
// Get baseline error score
+
+ /* Copy the unfiltered / processed recon buffer to the new buffer */
+ vp8_yv12_copy_y_ptr(saved_frame, cm->frame_to_show);
+
vp8cx_set_alt_lf_level(cpi, filt_mid);
vp8_loop_filter_frame_yonly(cm, &cpi->mb.e_mbd, filt_mid);
- best_err = vp8_calc_ss_err(sd, cm->frame_to_show, IF_RTCD(&cpi->rtcd.variance));
+ best_err = vp8_calc_ss_err(sd, cm->frame_to_show,
+ IF_RTCD(&cpi->rtcd.variance));
filt_best = filt_mid;
- // Re-instate the unfiltered frame
- vp8_yv12_copy_y_ptr(&cpi->last_frame_uf, cm->frame_to_show);
-
while (filter_step > 0)
{
Bias = (best_err >> (15 - (filt_mid / 8))) * filter_step; //PGW change 12/12/06 for small images
@@ -328,14 +336,13 @@
if ((filt_direction <= 0) && (filt_low != filt_mid))
{
// Get Low filter error score
+ vp8_yv12_copy_y_ptr(saved_frame, cm->frame_to_show);
vp8cx_set_alt_lf_level(cpi, filt_low);
vp8_loop_filter_frame_yonly(cm, &cpi->mb.e_mbd, filt_low);
- filt_err = vp8_calc_ss_err(sd, cm->frame_to_show, IF_RTCD(&cpi->rtcd.variance));
+ filt_err = vp8_calc_ss_err(sd, cm->frame_to_show,
+ IF_RTCD(&cpi->rtcd.variance));
- // Re-instate the unfiltered frame
- vp8_yv12_copy_y_ptr(&cpi->last_frame_uf, cm->frame_to_show);
-
// If value is close to the best so far then bias towards a lower loop filter value.
if ((filt_err - Bias) < best_err)
{
@@ -350,14 +357,13 @@
// Now look at filt_high
if ((filt_direction >= 0) && (filt_high != filt_mid))
{
+ vp8_yv12_copy_y_ptr(saved_frame, cm->frame_to_show);
vp8cx_set_alt_lf_level(cpi, filt_high);
vp8_loop_filter_frame_yonly(cm, &cpi->mb.e_mbd, filt_high);
- filt_err = vp8_calc_ss_err(sd, cm->frame_to_show, IF_RTCD(&cpi->rtcd.variance));
+ filt_err = vp8_calc_ss_err(sd, cm->frame_to_show,
+ IF_RTCD(&cpi->rtcd.variance));
- // Re-instate the unfiltered frame
- vp8_yv12_copy_y_ptr(&cpi->last_frame_uf, cm->frame_to_show);
-
// Was it better than the previous best?
if (filt_err < (best_err - Bias))
{
@@ -380,4 +386,7 @@
}
cm->filter_level = filt_best;
+
+ /* restore unfiltered frame pointer */
+ cm->frame_to_show = saved_frame;
}