shithub: libvpx

Download patch

ref: 41138e01f5b301952bba3553da20ac6a6cedf8a8
parent: a272530bf0962d4cbf54fdb8abd1051f8fbb5917
author: Marco Paniconi <marpan@google.com>
date: Fri Nov 1 07:03:03 EDT 2013

Fixes to buffer update for temporal layers.

When a frame is dropped due to |buffer_level| < 0 for a given temporal layer,
the buffer level for the upper temporal layers was not updated (in calc_pframe_target_size()).
This change fixes that.

Also, use the layer per-frame-bandwidth for updating the buffer level
of the higher layers when a frame is dropped.

Change-Id: I660c23f3229b47e9d124a950b480314b4307c5a8

--- a/vp8/encoder/onyx_if.c
+++ b/vp8/encoder/onyx_if.c
@@ -3574,7 +3574,8 @@
                 for (i=cpi->current_layer+1; i<cpi->oxcf.number_of_layers; i++)
                 {
                     LAYER_CONTEXT *lc = &cpi->layer_context[i];
-                    lc->bits_off_target += cpi->av_per_frame_bandwidth;
+                    lc->bits_off_target += (int)(lc->target_bandwidth /
+                                                 lc->framerate);
                     if (lc->bits_off_target > lc->maximum_buffer_size)
                         lc->bits_off_target = lc->maximum_buffer_size;
                     lc->buffer_level = lc->bits_off_target;
--- a/vp8/encoder/ratectrl.c
+++ b/vp8/encoder/ratectrl.c
@@ -956,6 +956,21 @@
             if (cpi->bits_off_target > cpi->oxcf.maximum_buffer_size)
               cpi->bits_off_target = (int)cpi->oxcf.maximum_buffer_size;
             cpi->buffer_level = cpi->bits_off_target;
+
+            if (cpi->oxcf.number_of_layers > 1) {
+              unsigned int i;
+
+              // Propagate bits saved by dropping the frame to higher layers.
+              for (i = cpi->current_layer + 1; i < cpi->oxcf.number_of_layers;
+                  i++) {
+                LAYER_CONTEXT *lc = &cpi->layer_context[i];
+                lc->bits_off_target += (int)(lc->target_bandwidth /
+                                             lc->framerate);
+                if (lc->bits_off_target > lc->maximum_buffer_size)
+                  lc->bits_off_target = lc->maximum_buffer_size;
+                lc->buffer_level = lc->bits_off_target;
+              }
+            }
         }
     }