Signed-off-by: Vittorio Giovara <[email protected]>
---
 avconv.c     | 39 ++++++++++++++++++++++++++++-----------
 avconv.h     |  4 ++++
 avconv_opt.c |  9 +++++++++
 3 files changed, 41 insertions(+), 11 deletions(-)

diff --git a/avconv.c b/avconv.c
index 9e69c56..a7f2907 100644
--- a/avconv.c
+++ b/avconv.c
@@ -41,6 +41,7 @@
 #include "libavutil/intreadwrite.h"
 #include "libavutil/dict.h"
 #include "libavutil/mathematics.h"
+#include "libavutil/metadata.h"
 #include "libavutil/pixdesc.h"
 #include "libavutil/avstring.h"
 #include "libavutil/libm.h"
@@ -190,6 +191,7 @@ static void avconv_cleanup(int ret)
         av_freep(&ost->forced_keyframes);
         av_freep(&ost->avfilter);
         av_freep(&ost->logfile_prefix);
+        av_freep(&ost->last_stats);
 
         avcodec_free_context(&ost->enc_ctx);
 
@@ -335,7 +337,14 @@ static void write_frame(AVFormatContext *s, AVPacket *pkt, 
OutputStream *ost)
         }
         ost->frame_number++;
     }
-
+    if (avctx->codec_type == AVMEDIA_TYPE_VIDEO) {
+        uint8_t *s = av_packet_get_side_data(pkt, AV_PKT_DATA_STATISTICS, 
NULL);
+        if (s) {
+            ost->stats_recv = 1;
+            memcpy(ost->last_stats, s, sizeof(AVStats));
+        } else
+            ost->stats_recv = 0;
+    }
     while (bsfc) {
         AVPacket new_pkt = *pkt;
         int a = av_bitstream_filter_filter(bsfc, avctx, NULL,
@@ -620,10 +629,16 @@ static void do_video_stats(OutputStream *ost, int 
frame_size)
     enc = ost->enc_ctx;
     if (enc->codec_type == AVMEDIA_TYPE_VIDEO) {
         frame_number = ost->frame_number;
-        fprintf(vstats_file, "frame= %5d q= %2.1f ", frame_number, 
enc->coded_frame->quality / (float)FF_QP2LAMBDA);
-        if (enc->flags&CODEC_FLAG_PSNR)
-            fprintf(vstats_file, "PSNR= %6.2f ", 
psnr(enc->coded_frame->error[0] / (enc->width * enc->height * 255.0 * 255.0)));
-
+        fprintf(vstats_file, "frame= %5d", frame_number);
+        if (ost->stats_recv) {
+            fprintf(vstats_file, " q= %2.1f ",
+                    ost->last_stats->quality / (float)FF_QP2LAMBDA);
+            if (enc->flags & CODEC_FLAG_PSNR) {
+                double vpsnr = psnr(ost->last_stats->error[0] /
+                                    (enc->width * enc->height * 255.0 * 
255.0));
+                fprintf(vstats_file, "PSNR= %6.2f ", vpsnr);
+            }
+        }
         fprintf(vstats_file,"f_size= %6d ", frame_size);
         /* compute pts value */
         ti1 = ost->sync_opts * av_q2d(enc->time_base);
@@ -634,7 +649,9 @@ static void do_video_stats(OutputStream *ost, int 
frame_size)
         avg_bitrate = (double)(ost->data_size * 8) / ti1 / 1000.0;
         fprintf(vstats_file, "s_size= %8.0fkB time= %0.3f br= %7.1fkbits/s 
avg_br= %7.1fkbits/s ",
                (double)ost->data_size / 1024, ti1, bitrate, avg_bitrate);
-        fprintf(vstats_file, "type= %c\n", 
av_get_picture_type_char(enc->coded_frame->pict_type));
+        if (ost->stats_recv)
+            fprintf(vstats_file, "type= %c\n",
+                    av_get_picture_type_char(ost->last_stats->pict_type));
     }
 }
 
@@ -905,8 +922,8 @@ static void print_report(int is_last_report, int64_t 
timer_start)
         float q = -1;
         ost = output_streams[i];
         enc = ost->enc_ctx;
-        if (!ost->stream_copy && enc->coded_frame)
-            q = enc->coded_frame->quality / (float)FF_QP2LAMBDA;
+        if (!ost->stream_copy && ost->stats_recv)
+            q = ost->last_stats->quality / (float)FF_QP2LAMBDA;
         if (vid && enc->codec_type == AVMEDIA_TYPE_VIDEO) {
             snprintf(buf + strlen(buf), sizeof(buf) - strlen(buf), "q=%2.1f ", 
q);
         }
@@ -926,7 +943,7 @@ static void print_report(int is_last_report, int64_t 
timer_start)
                 for (j = 0; j < 32; j++)
                     snprintf(buf + strlen(buf), sizeof(buf) - strlen(buf), 
"%X", (int)lrintf(log2(qp_histogram[j] + 1)));
             }
-            if (enc->flags&CODEC_FLAG_PSNR) {
+            if ((enc->flags & CODEC_FLAG_PSNR) && ost->stats_recv) {
                 int j;
                 double error, error_sum = 0;
                 double scale, scale_sum = 0;
@@ -934,10 +951,10 @@ static void print_report(int is_last_report, int64_t 
timer_start)
                 snprintf(buf + strlen(buf), sizeof(buf) - strlen(buf), 
"PSNR=");
                 for (j = 0; j < 3; j++) {
                     if (is_last_report) {
-                        error = enc->error[j];
+                        error = ost->last_stats->error[j];
                         scale = enc->width * enc->height * 255.0 * 255.0 * 
frame_number;
                     } else {
-                        error = enc->coded_frame->error[j];
+                        error = ost->last_stats->error[j];
                         scale = enc->width * enc->height * 255.0 * 255.0;
                     }
                     if (j)
diff --git a/avconv.h b/avconv.h
index b932d7e..8aba83d 100644
--- a/avconv.h
+++ b/avconv.h
@@ -358,6 +358,10 @@ typedef struct OutputStream {
     // number of frames/samples sent to the encoder
     uint64_t frames_encoded;
     uint64_t samples_encoded;
+
+    /* last compression statistics received */
+    int stats_recv;
+    AVStats *last_stats;
 } OutputStream;
 
 typedef struct OutputFile {
diff --git a/avconv_opt.c b/avconv_opt.c
index 1625429..74629ea 100644
--- a/avconv_opt.c
+++ b/avconv_opt.c
@@ -36,6 +36,7 @@
 #include "libavutil/intreadwrite.h"
 #include "libavutil/fifo.h"
 #include "libavutil/mathematics.h"
+#include "libavutil/metadata.h"
 #include "libavutil/opt.h"
 #include "libavutil/parseutils.h"
 #include "libavutil/pixdesc.h"
@@ -905,6 +906,14 @@ static OutputStream *new_output_stream(OptionsContext *o, 
AVFormatContext *oc, e
     ost->file_index = nb_output_files - 1;
     ost->index      = idx;
     ost->st         = st;
+    if (type == AVMEDIA_TYPE_VIDEO) {
+        ost->last_stats = av_malloc(sizeof(AVStats));
+        if (!ost->last_stats) {
+            av_log(NULL, AV_LOG_ERROR, "Error allocating the stats buffer.\n");
+            exit_program(1);
+        }
+    }
+
     st->codec->codec_type = type;
     choose_encoder(o, oc, ost);
 
-- 
1.9.5 (Apple Git-50.3)

_______________________________________________
libav-devel mailing list
[email protected]
https://lists.libav.org/mailman/listinfo/libav-devel

Reply via email to