Commit db67dcba authored by John Koleszar's avatar John Koleszar

Revert "Reduce overshoot in 1 pass rate control"

This reverts commit 212f6183.

Further testing shows that the overshoot accumulation/damping is too
aggressive on some clips. Allowing the accumulated overshoot to
decay and limiting to damping to golden frames shows some promise.
But some clips show significant overshoot in the buffer window, so
I think this still needs work.

Change-Id: Ic02a9ca34f55229f9cc04786f4fab54cdc1a3ef5
parent 259ea232
......@@ -214,58 +214,33 @@ static int frame_max_bits(VP8_COMP *cpi)
int max_bits;
// For CBR we need to also consider buffer fullness.
// If we are running below the optimal level then we need to gradually tighten up on max_bits.
if (cpi->oxcf.end_usage == USAGE_STREAM_FROM_SERVER)
{
max_bits = 2 * cpi->av_per_frame_bandwidth;
max_bits -= cpi->buffered_av_per_frame_bandwidth;
max_bits *= ((double)cpi->oxcf.two_pass_vbrmax_section / 100.0);
}
// VBR
else
{
// For VBR base this on the bits and frames left plus the two_pass_vbrmax_section rate passed in by the user
max_bits = (int)(((double)cpi->twopass.bits_left / (cpi->twopass.total_stats->count - (double)cpi->common.current_video_frame)) * ((double)cpi->oxcf.two_pass_vbrmax_section / 100.0));
}
// Trap case where we are out of bits
if (max_bits < 0)
max_bits = 0;
double buffer_fullness_ratio = (double)cpi->buffer_level / DOUBLE_DIVIDE_CHECK((double)cpi->oxcf.optimal_buffer_level);
return max_bits;
}
// For CBR base this on the target average bits per frame plus the maximum sedction rate passed in by the user
max_bits = (int)(cpi->av_per_frame_bandwidth * ((double)cpi->oxcf.two_pass_vbrmax_section / 100.0));
// If our buffer is below the optimum level
if (buffer_fullness_ratio < 1.0)
{
// The lower of max_bits / 4 or cpi->av_per_frame_bandwidth / 4.
int min_max_bits = ((cpi->av_per_frame_bandwidth >> 2) < (max_bits >> 2)) ? cpi->av_per_frame_bandwidth >> 2 : max_bits >> 2;
static int gf_group_max_bits(VP8_COMP *cpi)
{
// Max allocation for a golden frame group
int max_bits;
max_bits = (int)(max_bits * buffer_fullness_ratio);
// For CBR we need to also consider buffer fullness.
if (cpi->oxcf.end_usage == USAGE_STREAM_FROM_SERVER)
{
max_bits = cpi->av_per_frame_bandwidth * cpi->baseline_gf_interval;
if (max_bits > cpi->oxcf.optimal_buffer_level)
{
max_bits -= cpi->oxcf.optimal_buffer_level;
max_bits += cpi->buffer_level;
if (max_bits < min_max_bits)
max_bits = min_max_bits; // Lowest value we will set ... which should allow the buffer to refil.
}
else
{
max_bits -= (cpi->buffered_av_per_frame_bandwidth
- cpi->av_per_frame_bandwidth)
* cpi->baseline_gf_interval;
}
max_bits *= ((double)cpi->oxcf.two_pass_vbrmax_section / 100.0);
}
// VBR
else
{
// For VBR base this on the bits and frames left plus the two_pass_vbrmax_section rate passed in by the user
max_bits = (int)(((double)cpi->twopass.bits_left / (cpi->twopass.total_stats->count - (double)cpi->common.current_video_frame)) * ((double)cpi->oxcf.two_pass_vbrmax_section / 100.0));
max_bits *= cpi->baseline_gf_interval;
}
// Trap case where we are out of bits
if (max_bits < 0)
max_bits = 0;
......@@ -1358,7 +1333,7 @@ static void define_gf_group(VP8_COMP *cpi, FIRSTPASS_STATS *this_frame)
double abs_mv_in_out_accumulator = 0.0;
double mod_err_per_mb_accumulator = 0.0;
int max_group_bits;
int max_bits = frame_max_bits(cpi); // Max for a single frame
unsigned int allow_alt_ref =
cpi->oxcf.play_alternate && cpi->oxcf.lag_in_frames;
......@@ -1711,9 +1686,8 @@ static void define_gf_group(VP8_COMP *cpi, FIRSTPASS_STATS *this_frame)
cpi->twopass.gf_group_bits = (cpi->twopass.gf_group_bits < 0) ? 0 : (cpi->twopass.gf_group_bits > cpi->twopass.kf_group_bits) ? cpi->twopass.kf_group_bits : cpi->twopass.gf_group_bits;
// Clip cpi->twopass.gf_group_bits based on user supplied data rate variability limit (cpi->oxcf.two_pass_vbrmax_section)
max_group_bits = gf_group_max_bits(cpi);
if (cpi->twopass.gf_group_bits > max_group_bits)
cpi->twopass.gf_group_bits = max_group_bits;
if (cpi->twopass.gf_group_bits > max_bits * cpi->baseline_gf_interval)
cpi->twopass.gf_group_bits = max_bits * cpi->baseline_gf_interval;
// Reset the file position
reset_fpf_position(cpi, start_pos);
......@@ -1808,6 +1782,13 @@ static void define_gf_group(VP8_COMP *cpi, FIRSTPASS_STATS *this_frame)
}
}
// Apply an additional limit for CBR
if (cpi->oxcf.end_usage == USAGE_STREAM_FROM_SERVER)
{
if (cpi->twopass.gf_bits > (cpi->buffer_level >> 1))
cpi->twopass.gf_bits = cpi->buffer_level >> 1;
}
// Dont allow a negative value for gf_bits
if (gf_bits < 0)
gf_bits = 0;
......
......@@ -1477,7 +1477,6 @@ static void init_config(VP8_PTR ptr, VP8_CONFIG *oxcf)
cpi->rolling_actual_bits = cpi->av_per_frame_bandwidth;
cpi->long_rolling_target_bits = cpi->av_per_frame_bandwidth;
cpi->long_rolling_actual_bits = cpi->av_per_frame_bandwidth;
cpi->buffered_av_per_frame_bandwidth = cpi->av_per_frame_bandwidth;
cpi->total_actual_bits = 0;
cpi->total_target_vs_actual = 0;
......@@ -1573,7 +1572,7 @@ void vp8_change_config(VP8_PTR ptr, VP8_CONFIG *oxcf)
break;
}
if (cpi->pass == 0 && cpi->oxcf.end_usage != USAGE_STREAM_FROM_SERVER)
if (cpi->pass == 0)
cpi->auto_worst_q = 1;
cpi->oxcf.worst_allowed_q = q_trans[oxcf->worst_allowed_q];
......@@ -3454,8 +3453,7 @@ static void encode_frame_to_data_rate
// For CBR if the buffer reaches its maximum level then we can no longer
// save up bits for later frames so we might as well use them up
// on the current frame.
if (cpi->pass == 2
&& (cpi->oxcf.end_usage == USAGE_STREAM_FROM_SERVER) &&
if ((cpi->oxcf.end_usage == USAGE_STREAM_FROM_SERVER) &&
(cpi->buffer_level >= cpi->oxcf.optimal_buffer_level) && cpi->buffered_mode)
{
int Adjustment = cpi->active_worst_quality / 4; // Max adjustment is 1/4
......@@ -3546,9 +3544,6 @@ static void encode_frame_to_data_rate
}
else
{
if(cpi->pass != 2)
Q = cpi->avg_frame_qindex;
cpi->active_best_quality = inter_minq[Q];
// For the constant/constrained quality mode we dont want
......@@ -3850,16 +3845,15 @@ static void encode_frame_to_data_rate
(cpi->active_worst_quality < cpi->worst_quality) &&
(cpi->projected_frame_size > frame_over_shoot_limit))
{
/* step down active_worst_quality such that the corresponding
* active_best_quality will be equal to the current
* active_worst_quality + 1
*/
int i;
int over_size_percent = ((cpi->projected_frame_size - frame_over_shoot_limit) * 100) / frame_over_shoot_limit;
for(i=cpi->active_worst_quality; i<cpi->worst_quality; i++)
if(inter_minq[i] >= cpi->active_worst_quality + 1)
break;
cpi->active_worst_quality = i;
// If so is there any scope for relaxing it
while ((cpi->active_worst_quality < cpi->worst_quality) && (over_size_percent > 0))
{
cpi->active_worst_quality++;
top_index = cpi->active_worst_quality;
over_size_percent = (int)(over_size_percent * 0.96); // Assume 1 qstep = about 4% on frame size.
}
// If we have updated the active max Q do not call vp8_update_rate_correction_factors() this loop.
active_worst_qchanged = TRUE;
......@@ -4247,9 +4241,10 @@ static void encode_frame_to_data_rate
// Update the buffer level variable.
// Non-viewable frames are a special case and are treated as pure overhead.
if ( cm->show_frame )
cpi->bits_off_target += cpi->av_per_frame_bandwidth;
cpi->bits_off_target -= cpi->projected_frame_size;
if ( !cm->show_frame )
cpi->bits_off_target -= cpi->projected_frame_size;
else
cpi->bits_off_target += cpi->av_per_frame_bandwidth - cpi->projected_frame_size;
// Rolling monitors of whether we are over or underspending used to help regulate min and Max Q in two pass.
cpi->rolling_target_bits = ((cpi->rolling_target_bits * 3) + cpi->this_frame_target + 2) / 4;
......@@ -4263,33 +4258,7 @@ static void encode_frame_to_data_rate
// Debug stats
cpi->total_target_vs_actual += (cpi->this_frame_target - cpi->projected_frame_size);
// Update the buffered average bitrate
{
long long numerator;
numerator = cpi->oxcf.maximum_buffer_size
- cpi->buffered_av_per_frame_bandwidth
+ cpi->projected_frame_size;
numerator *= cpi->buffered_av_per_frame_bandwidth;
cpi->buffered_av_per_frame_bandwidth = numerator
/ cpi->oxcf.maximum_buffer_size;
}
{
long long tmp = (long long)cpi->buffered_av_per_frame_bandwidth
* cpi->oxcf.maximum_buffer_size
/ cpi->av_per_frame_bandwidth;
cpi->buffer_level = cpi->oxcf.maximum_buffer_size
- tmp
+ cpi->oxcf.optimal_buffer_level;
}
// Accumulate overshoot error.
cpi->accumulated_overshoot +=
(cpi->projected_frame_size > cpi->av_per_frame_bandwidth)
? cpi->projected_frame_size - cpi->av_per_frame_bandwidth
: 0;
cpi->buffer_level = cpi->bits_off_target;
// Update bits left to the kf and gf groups to account for overshoot or undershoot on these frames
if (cm->frame_type == KEY_FRAME)
......
......@@ -351,10 +351,6 @@ typedef struct VP8_COMP
int per_frame_bandwidth; // Current section per frame bandwidth target
int av_per_frame_bandwidth; // Average frame size target for clip
int min_frame_bandwidth; // Minimum allocation that should be used for any frame
int buffered_av_per_frame_bandwidth; // Average bitrate over the last buffer
int buffered_av_per_frame_bandwidth_rem; // Average bitrate remainder
int accumulated_overshoot; // Accumulated # of bits spent > target
int inter_frame_target;
double output_frame_rate;
long long last_time_stamp_seen;
......
......@@ -605,10 +605,10 @@ static void calc_gf_params(VP8_COMP *cpi)
static void calc_pframe_target_size(VP8_COMP *cpi)
{
int min_frame_target, max_frame_target;
int min_frame_target;
int Adjustment;
min_frame_target = 1;
min_frame_target = 0;
if (cpi->pass == 2)
{
......@@ -616,19 +616,10 @@ static void calc_pframe_target_size(VP8_COMP *cpi)
if (min_frame_target < (cpi->av_per_frame_bandwidth >> 5))
min_frame_target = cpi->av_per_frame_bandwidth >> 5;
max_frame_target = INT_MAX;
}
else
{
if (min_frame_target < cpi->per_frame_bandwidth / 4)
min_frame_target = cpi->per_frame_bandwidth / 4;
else if (min_frame_target < cpi->per_frame_bandwidth / 4)
min_frame_target = cpi->per_frame_bandwidth / 4;
/* Don't allow the target to completely deplete the buffer. */
max_frame_target = cpi->buffer_level + cpi->av_per_frame_bandwidth;
if(max_frame_target < min_frame_target)
max_frame_target = min_frame_target;
}
// Special alt reference frame case
if (cpi->common.refresh_alt_ref_frame)
......@@ -1121,32 +1112,6 @@ static void calc_pframe_target_size(VP8_COMP *cpi)
}
}
if (cpi->pass==0 && cpi->oxcf.end_usage == USAGE_STREAM_FROM_SERVER){
/* determine the accumulated error to apply to this frame. Apply
* more of the error when we've been undershooting, less when
* we've been overshooting
*/
long long adjust;
int bitrate_error;
bitrate_error = cpi->av_per_frame_bandwidth
- cpi->buffered_av_per_frame_bandwidth;
adjust = cpi->accumulated_overshoot;
adjust *= cpi->av_per_frame_bandwidth + bitrate_error;
adjust /= cpi->oxcf.maximum_buffer_size;
if (adjust > (cpi->this_frame_target - min_frame_target))
adjust = (cpi->this_frame_target - min_frame_target);
else if (adjust < 0)
adjust = 0;
cpi->this_frame_target -= adjust;
cpi->accumulated_overshoot -= adjust;
}
if(cpi->this_frame_target > max_frame_target)
cpi->this_frame_target = max_frame_target;
}
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment