[x264-devel] Revise the 2-pass algorithm

Anton Mitrofanov git at videolan.org
Sun Jan 17 22:17:57 CET 2016


x264 | branch: master | Anton Mitrofanov <BugMaster at narod.ru> | Tue Oct 13 12:54:05 2015 +0300| [20821a26ec510979e49fcfd6becc6ad7e2d8b388] | committer: Henrik Gramner

Revise the 2-pass algorithm

> http://git.videolan.org/gitweb.cgi/x264.git/?a=commit;h=20821a26ec510979e49fcfd6becc6ad7e2d8b388
---

 encoder/encoder.c     |    2 +-
 encoder/ratecontrol.c |   75 ++++++++++++++++++++-----------------------------
 2 files changed, 32 insertions(+), 45 deletions(-)

diff --git a/encoder/encoder.c b/encoder/encoder.c
index a0b01fb..2aae3f0 100644
--- a/encoder/encoder.c
+++ b/encoder/encoder.c
@@ -3339,7 +3339,7 @@ int     x264_encoder_encode( x264_t *h,
         if( x264_threadpool_wait_all( h ) < 0 )
             return -1;
 
-    if( h->i_frame == h->i_thread_frames - 1 )
+    if( h->i_frame == 0 )
         h->i_reordered_pts_delay = h->fenc->i_reordered_pts;
     if( h->reconfig )
     {
diff --git a/encoder/ratecontrol.c b/encoder/ratecontrol.c
index ab80460..c60f758 100644
--- a/encoder/ratecontrol.c
+++ b/encoder/ratecontrol.c
@@ -43,10 +43,10 @@ typedef struct
     int mv_bits;
     int tex_bits;
     int misc_bits;
-    uint64_t expected_bits; /*total expected bits up to the current frame (current one excluded)*/
+    double expected_bits; /* total expected bits up to the current frame (current one excluded) */
     double expected_vbv;
     double new_qscale;
-    int new_qp;
+    float new_qp;
     int i_count;
     int p_count;
     int s_count;
@@ -85,7 +85,6 @@ struct x264_ratecontrol_t
 
     /* current frame */
     ratecontrol_entry_t *rce;
-    int qp;                     /* qp for current frame */
     float qpm;                  /* qp for current macroblock: precise float for AQ */
     float qpa_rc;               /* average of macroblocks' qp before aq */
     float qpa_rc_prev;
@@ -1501,12 +1500,11 @@ void x264_ratecontrol_start( x264_t *h, int i_force_qp, int overhead )
 
     rc->qpa_rc = rc->qpa_rc_prev =
     rc->qpa_aq = rc->qpa_aq_prev = 0;
-    rc->qp = x264_clip3( q + 0.5f, 0, QP_MAX );
     h->fdec->f_qp_avg_rc =
     h->fdec->f_qp_avg_aq =
     rc->qpm = q;
     if( rce )
-        rce->new_qp = rc->qp;
+        rce->new_qp = q;
 
     accum_p_qp_update( h, rc->qpm );
 
@@ -2425,10 +2423,12 @@ static float rate_estimate_qscale( x264_t *h )
         else
             q += rcc->pb_offset;
 
-        if( rcc->b_2pass && rcc->b_vbv )
-            rcc->frame_size_planned = qscale2bits( &rce, qp2qscale( q ) );
+        rcc->qp_novbv = q;
+        q = qp2qscale( q );
+        if( rcc->b_2pass )
+            rcc->frame_size_planned = qscale2bits( &rce, q );
         else
-            rcc->frame_size_planned = predict_size( rcc->pred_b_from_p, qp2qscale( q ), h->fref[1][h->i_ref[1]-1]->i_satd );
+            rcc->frame_size_planned = predict_size( rcc->pred_b_from_p, q, h->fref[1][h->i_ref[1]-1]->i_satd );
         /* Limit planned size by MinCR */
         if( rcc->b_vbv )
             rcc->frame_size_planned = X264_MIN( rcc->frame_size_planned, rcc->frame_size_maximum );
@@ -2437,43 +2437,31 @@ static float rate_estimate_qscale( x264_t *h )
         /* For row SATDs */
         if( rcc->b_vbv )
             rcc->last_satd = x264_rc_analyse_slice( h );
-        rcc->qp_novbv = q;
-        return qp2qscale( q );
+        return q;
     }
     else
     {
         double abr_buffer = 2 * rcc->rate_tolerance * rcc->bitrate;
+        double predicted_bits = total_bits;
+        if( h->i_thread_frames > 1 )
+        {
+            int j = h->rc - h->thread[0]->rc;
+            for( int i = 1; i < h->i_thread_frames; i++ )
+            {
+                x264_t *t = h->thread[(j+i) % h->i_thread_frames];
+                double bits = t->rc->frame_size_planned;
+                if( !t->b_thread_active )
+                    continue;
+                bits = X264_MAX(bits, t->rc->frame_size_estimated);
+                predicted_bits += bits;
+            }
+        }
 
         if( rcc->b_2pass )
         {
             double lmin = rcc->lmin[pict_type];
             double lmax = rcc->lmax[pict_type];
-            int64_t diff;
-            int64_t predicted_bits = total_bits;
-
-            if( rcc->b_vbv )
-            {
-                if( h->i_thread_frames > 1 )
-                {
-                    int j = h->rc - h->thread[0]->rc;
-                    for( int i = 1; i < h->i_thread_frames; i++ )
-                    {
-                        x264_t *t = h->thread[ (j+i)%h->i_thread_frames ];
-                        double bits = t->rc->frame_size_planned;
-                        if( !t->b_thread_active )
-                            continue;
-                        bits = X264_MAX(bits, t->rc->frame_size_estimated);
-                        predicted_bits += (int64_t)bits;
-                    }
-                }
-            }
-            else
-            {
-                if( h->i_frame < h->i_thread_frames )
-                    predicted_bits += (int64_t)h->i_frame * rcc->bitrate / rcc->fps;
-                else
-                    predicted_bits += (int64_t)(h->i_thread_frames - 1) * rcc->bitrate / rcc->fps;
-            }
+            double diff;
 
             /* Adjust ABR buffer based on distance to the end of the video. */
             if( rcc->num_entries > h->i_frame )
@@ -2484,11 +2472,10 @@ static float rate_estimate_qscale( x264_t *h )
                 abr_buffer *= 0.5 * X264_MAX( scale_factor, 0.5 );
             }
 
-            diff = predicted_bits - (int64_t)rce.expected_bits;
+            diff = predicted_bits - rce.expected_bits;
             q = rce.new_qscale;
-            q /= x264_clip3f((double)(abr_buffer - diff) / abr_buffer, .5, 2);
-            if( ((h->i_frame + 1 - h->i_thread_frames) >= rcc->fps) &&
-                (rcc->expected_bits_sum > 0))
+            q /= x264_clip3f((abr_buffer - diff) / abr_buffer, .5, 2);
+            if( h->i_frame >= rcc->fps && rcc->expected_bits_sum >= 1 )
             {
                 /* Adjust quant based on the difference between
                  * achieved and expected bitrate so far */
@@ -2563,7 +2550,7 @@ static float rate_estimate_qscale( x264_t *h )
                 if( !rcc->b_vbv_min_rate && rcc->last_satd )
                 {
                     // FIXME is it simpler to keep track of wanted_bits in ratecontrol_end?
-                    int i_frame_done = h->i_frame + 1 - h->i_thread_frames;
+                    int i_frame_done = h->i_frame;
                     double time_done = i_frame_done / rcc->fps;
                     if( h->param.b_vfr_input && i_frame_done > 0 )
                         time_done = ((double)(h->fenc->i_reordered_pts - h->i_reordered_pts_delay)) * h->param.i_timebase_num / h->param.i_timebase_den;
@@ -2571,7 +2558,7 @@ static float rate_estimate_qscale( x264_t *h )
                     if( wanted_bits > 0 )
                     {
                         abr_buffer *= X264_MAX( 1, sqrt( time_done ) );
-                        overflow = x264_clip3f( 1.0 + (total_bits - wanted_bits) / abr_buffer, .5, 2 );
+                        overflow = x264_clip3f( 1.0 + (predicted_bits - wanted_bits) / abr_buffer, .5, 2 );
                         q *= overflow;
                     }
                 }
@@ -2616,8 +2603,8 @@ static float rate_estimate_qscale( x264_t *h )
         if( !(rcc->b_2pass && !rcc->b_vbv) && h->fenc->i_frame == 0 )
             rcc->last_qscale_for[SLICE_TYPE_P] = q * fabs( h->param.rc.f_ip_factor );
 
-        if( rcc->b_2pass && rcc->b_vbv )
-            rcc->frame_size_planned = qscale2bits(&rce, q);
+        if( rcc->b_2pass )
+            rcc->frame_size_planned = qscale2bits( &rce, q );
         else
             rcc->frame_size_planned = predict_size( &rcc->pred[h->sh.i_type], q, rcc->last_satd );
 



More information about the x264-devel mailing list