Browse code

use new PTS api - corrected AV sync for transcoding - factorized print_report() code

Originally committed as revision 1059 to svn://svn.ffmpeg.org/ffmpeg/trunk

Fabrice Bellard authored on 2002/10/22 02:42:47
Showing 1 changed files
... ...
@@ -18,7 +18,6 @@
18 18
  */
19 19
 #define HAVE_AV_CONFIG_H
20 20
 #include "avformat.h"
21
-#include "tick.h"
22 21
 
23 22
 #ifndef CONFIG_WIN32
24 23
 #include <unistd.h>
... ...
@@ -162,8 +161,12 @@ typedef struct AVOutputStream {
162 162
     int index;               /* stream index in the output file */
163 163
     int source_index;        /* AVInputStream index */
164 164
     AVStream *st;            /* stream in the output file */
165
-    int encoding_needed;   /* true if encoding needed for this stream */
166
-
165
+    int encoding_needed;     /* true if encoding needed for this stream */
166
+    int frame_number;
167
+    /* input pts and corresponding output pts
168
+       for A/V sync */
169
+    double sync_ipts;
170
+    INT64 sync_opts;
167 171
     /* video only */
168 172
     AVPicture pict_tmp;         /* temporary image for resizing */
169 173
     int video_resample;
... ...
@@ -182,12 +185,8 @@ typedef struct AVInputStream {
182 182
     AVStream *st;
183 183
     int discard;             /* true if stream data should be discarded */
184 184
     int decoding_needed;     /* true if the packets must be decoded in 'raw_fifo' */
185
-    Ticker pts_ticker;       /* Ticker for PTS calculation */
186
-    int ticker_inited;       /* to signal if the ticker was initialized */
187
-    INT64 pts;               /* current pts */
188
-    int   pts_increment;     /* expected pts increment for next packet */
189
-    int frame_number;        /* current frame */
190 185
     INT64 sample_index;      /* current sample */
186
+    int frame_decoded;       /* true if a video or audio frame has been decoded */
191 187
 } AVInputStream;
192 188
 
193 189
 typedef struct AVInputFile {
... ...
@@ -330,7 +329,7 @@ static void do_audio_out(AVFormatContext *s,
330 330
                      &ost->fifo.rptr) == 0) {
331 331
             ret = avcodec_encode_audio(enc, audio_out, sizeof(audio_out), 
332 332
                                        (short *)audio_buf);
333
-            s->oformat->write_packet(s, ost->index, audio_out, ret, 0);
333
+            av_write_frame(s, ost->index, audio_out, ret);
334 334
         }
335 335
     } else {
336 336
         /* output a pcm frame */
... ...
@@ -347,7 +346,7 @@ static void do_audio_out(AVFormatContext *s,
347 347
         }
348 348
         ret = avcodec_encode_audio(enc, audio_out, size_out, 
349 349
                                    (short *)buftmp);
350
-        s->oformat->write_packet(s, ost->index, audio_out, ret, 0);
350
+        av_write_frame(s, ost->index, audio_out, ret);
351 351
     }
352 352
 }
353 353
 
... ...
@@ -443,18 +442,20 @@ static void write_picture(AVFormatContext *s, int index, AVPicture *picture,
443 443
     default:
444 444
         return;
445 445
     }
446
-    s->oformat->write_packet(s, index, buf, size, 0);
446
+    av_write_frame(s, index, buf, size);
447 447
     av_free(buf);
448 448
 }
449 449
 
450
+/* we begin to correct av delay at this threshold */
451
+#define AV_DELAY_MAX 0.100
450 452
 
451 453
 static void do_video_out(AVFormatContext *s, 
452 454
                          AVOutputStream *ost, 
453 455
                          AVInputStream *ist,
454 456
                          AVPicture *picture1,
455
-                         int *frame_size)
457
+                         int *frame_size, AVOutputStream *audio_sync)
456 458
 {
457
-    int n1, n2, nb, i, ret, frame_number, dec_frame_rate;
459
+    int nb_frames, i, ret;
458 460
     AVPicture *picture, *picture2, *pict;
459 461
     AVPicture picture_tmp1, picture_tmp2;
460 462
     static UINT8 *video_buffer;
... ...
@@ -466,19 +467,43 @@ static void do_video_out(AVFormatContext *s,
466 466
     enc = &ost->st->codec;
467 467
     dec = &ist->st->codec;
468 468
 
469
-    frame_number = ist->frame_number;
470
-    dec_frame_rate = ist->st->r_frame_rate;
471
-    //    fprintf(stderr, "\n%d", dec_frame_rate);
472
-    /* first drop frame if needed */
473
-    n1 = ((INT64)frame_number * enc->frame_rate) / dec_frame_rate;
474
-    n2 = (((INT64)frame_number + 1) * enc->frame_rate) / dec_frame_rate;
475
-    nb = n2 - n1;
476
-    if (nb <= 0) 
469
+    /* by default, we output a single frame */
470
+    nb_frames = 1;
471
+
472
+    /* NOTE: the A/V sync is always done by considering the audio is
473
+       the master clock. It is suffisant for transcoding or playing,
474
+       but not for the general case */
475
+    if (audio_sync) {
476
+        /* compute the A-V delay and duplicate/remove frames if needed */
477
+        double adelta, vdelta, apts, vpts, av_delay;
478
+        
479
+        if (audio_sync->sync_ipts != AV_NOPTS_VALUE &&
480
+            ost->sync_ipts != AV_NOPTS_VALUE) {
481
+            
482
+            adelta = (double)(ost->st->pts.val - audio_sync->sync_opts) * 
483
+                s->pts_num / s->pts_den;
484
+            apts = audio_sync->sync_ipts + adelta; 
485
+            
486
+            vdelta = (double)(ost->st->pts.val - ost->sync_opts) *
487
+                s->pts_num / s->pts_den;
488
+            vpts = ost->sync_ipts + vdelta;
489
+            
490
+            av_delay = apts - vpts;
491
+            //            printf("delay=%f\n", av_delay);
492
+            if (av_delay < -AV_DELAY_MAX)
493
+                nb_frames = 2;
494
+            else if (av_delay > AV_DELAY_MAX)
495
+                nb_frames = 0;
496
+        }
497
+    }
498
+    /* XXX: also handle frame rate conversion */
499
+    if (nb_frames <= 0) 
477 500
         return;
478 501
 
479 502
     if (!video_buffer)
480
-        video_buffer= av_malloc(VIDEO_BUFFER_SIZE);
481
-    if(!video_buffer) return;
503
+        video_buffer = av_malloc(VIDEO_BUFFER_SIZE);
504
+    if (!video_buffer)
505
+        return;
482 506
 
483 507
     /* deinterlace : must be done before any resize */
484 508
     if (do_deinterlace) {
... ...
@@ -535,10 +560,9 @@ static void do_video_out(AVFormatContext *s,
535 535
     } else {
536 536
         picture = pict;
537 537
     }
538
-    nb=1;
539 538
     /* duplicates frame if needed */
540 539
     /* XXX: pb because no interleaving */
541
-    for(i=0;i<nb;i++) {
540
+    for(i=0;i<nb_frames;i++) {
542 541
         if (enc->codec_id != CODEC_ID_RAWVIDEO) {
543 542
             /* handles sameq here. This is not correct because it may
544 543
                not be a global option */
... ...
@@ -550,7 +574,7 @@ static void do_video_out(AVFormatContext *s,
550 550
                                        video_buffer, VIDEO_BUFFER_SIZE,
551 551
                                        picture);
552 552
             //enc->frame_number = enc->real_pict_num;
553
-            s->oformat->write_packet(s, ost->index, video_buffer, ret, 0);
553
+            av_write_frame(s, ost->index, video_buffer, ret);
554 554
             *frame_size = ret;
555 555
             //fprintf(stderr,"\nFrame: %3d %3d size: %5d type: %d",
556 556
             //        enc->frame_number-1, enc->real_pict_num, ret,
... ...
@@ -564,21 +588,22 @@ static void do_video_out(AVFormatContext *s,
564 564
                 /* raw pictures are written as AVPicture structure to
565 565
                    avoid any copies. We support temorarily the older
566 566
                    method. */
567
-                s->oformat->write_packet(s, ost->index, 
568
-                                         (UINT8 *)picture, sizeof(AVPicture), 0);
567
+                av_write_frame(s, ost->index, 
568
+                               (UINT8 *)picture, sizeof(AVPicture));
569 569
             } else {
570
-                write_picture(s, ost->index, picture, enc->pix_fmt, enc->width, enc->height);
570
+                write_picture(s, ost->index, picture, enc->pix_fmt, 
571
+                              enc->width, enc->height);
571 572
             }
572 573
         }
574
+        ost->frame_number++;
573 575
     }
574
-    the_end:
576
+ the_end:
575 577
     av_free(buf);
576 578
     av_free(buf1);
577 579
 }
578 580
 
579
-static void do_video_stats(AVOutputStream *ost, 
580
-                         AVInputStream *ist,
581
-                         int frame_size)
581
+static void do_video_stats(AVFormatContext *os, AVOutputStream *ost, 
582
+                           int frame_size)
582 583
 {
583 584
     static FILE *fvstats=NULL;
584 585
     static INT64 total_size = 0;
... ...
@@ -607,17 +632,14 @@ static void do_video_stats(AVOutputStream *ost,
607 607
     enc = &ost->st->codec;
608 608
     total_size += frame_size;
609 609
     if (enc->codec_type == CODEC_TYPE_VIDEO) {
610
-        frame_number = ist->frame_number;
610
+        frame_number = ost->frame_number;
611 611
         fprintf(fvstats, "frame= %5d q= %2d ", frame_number, enc->quality);
612 612
         if (do_psnr)
613 613
             fprintf(fvstats, "PSNR= %6.2f ", enc->psnr_y);
614 614
         
615 615
         fprintf(fvstats,"f_size= %6d ", frame_size);
616
-        /* compute min pts value */
617
-        if (!ist->discard && ist->pts < ti) {
618
-            ti = ist->pts;
619
-        }
620
-        ti1 = (double)ti / 1000000.0;
616
+        /* compute pts value */
617
+        ti1 = (double)ost->st->pts.val * os->pts_num / os->pts_den;
621 618
         if (ti1 < 0.01)
622 619
             ti1 = 0.01;
623 620
     
... ...
@@ -627,9 +649,75 @@ static void do_video_stats(AVOutputStream *ost,
627 627
             (double)total_size / 1024, ti1, bitrate, avg_bitrate);
628 628
         fprintf(fvstats,"type= %s\n", enc->key_frame == 1 ? "I" : "P");        
629 629
     }
630
+}
630 631
 
632
+void print_report(AVFormatContext **output_files, 
633
+                  AVOutputStream **ost_table, int nb_ostreams,
634
+                  int is_last_report)
635
+{
636
+    char buf[1024];
637
+    AVOutputStream *ost;
638
+    AVFormatContext *oc, *os;
639
+    INT64 total_size;
640
+    AVCodecContext *enc;
641
+    int frame_number, vid, i;
642
+    double bitrate, ti1, pts;
643
+    static INT64 last_time = -1;
644
+    
645
+    if (!is_last_report) {
646
+        INT64 cur_time;
647
+        /* display the report every 0.5 seconds */
648
+        cur_time = av_gettime();
649
+        if (last_time == -1) {
650
+            last_time = cur_time;
651
+            return;
652
+        } 
653
+        if ((cur_time - last_time) < 500000)
654
+            return;
655
+        last_time = cur_time;
656
+    }
657
+
658
+
659
+    oc = output_files[0];
660
+
661
+    total_size = url_ftell(&oc->pb);
662
+    
663
+    buf[0] = '\0';
664
+    ti1 = 1e10;
665
+    vid = 0;
666
+    for(i=0;i<nb_ostreams;i++) {
667
+        ost = ost_table[i];
668
+        os = output_files[ost->file_index];
669
+        enc = &ost->st->codec;
670
+        if (!vid && enc->codec_type == CODEC_TYPE_VIDEO) {
671
+            frame_number = ost->frame_number;
672
+            sprintf(buf + strlen(buf), "frame=%5d q=%2d ",
673
+                    frame_number, enc->quality);
674
+            if (do_psnr)
675
+                sprintf(buf + strlen(buf), "PSNR=%6.2f ", enc->psnr_y);
676
+            vid = 1;
677
+        }
678
+        /* compute min output value */
679
+        pts = (double)ost->st->pts.val * os->pts_num / os->pts_den;
680
+        if (pts < ti1)
681
+            ti1 = pts;
682
+    }
683
+    if (ti1 < 0.01)
684
+        ti1 = 0.01;
685
+    bitrate = (double)(total_size * 8) / ti1 / 1000.0;
686
+    
687
+    sprintf(buf + strlen(buf), 
688
+            "size=%8.0fkB time=%0.1f bitrate=%6.1fkbits/s",
689
+            (double)total_size / 1024, ti1, bitrate);
631 690
     
691
+    fprintf(stderr, "%s   ", buf);
632 692
     
693
+    if (is_last_report) {
694
+        fprintf(stderr, "\n");
695
+    } else {
696
+        fprintf(stderr, "\r");
697
+        fflush(stderr);
698
+    }
633 699
 }
634 700
 
635 701
 /*
... ...
@@ -641,12 +729,11 @@ static int av_encode(AVFormatContext **output_files,
641 641
                      int nb_input_files,
642 642
                      AVStreamMap *stream_maps, int nb_stream_maps)
643 643
 {
644
-    int ret, i, j, k, n, nb_istreams = 0, nb_ostreams = 0;
644
+    int ret, i, j, k, n, nb_istreams = 0, nb_ostreams = 0, pts_set;
645 645
     AVFormatContext *is, *os;
646 646
     AVCodecContext *codec, *icodec;
647 647
     AVOutputStream *ost, **ost_table = NULL;
648 648
     AVInputStream *ist, **ist_table = NULL;
649
-    INT64 min_pts, start_time;
650 649
     AVInputFile *file_table;
651 650
     AVFormatContext *stream_no_data;
652 651
     int key;
... ...
@@ -942,14 +1029,13 @@ static int av_encode(AVFormatContext **output_files,
942 942
             }
943 943
             //if (ist->st->codec.codec_type == CODEC_TYPE_VIDEO)
944 944
             //    ist->st->codec.flags |= CODEC_FLAG_REPEAT_FIELD;
945
+            ist->frame_decoded = 1;
945 946
         }
946 947
     }
947 948
 
948 949
     /* init pts */
949 950
     for(i=0;i<nb_istreams;i++) {
950 951
         ist = ist_table[i];
951
-        ist->pts = 0;
952
-        ist->frame_number = 0;
953 952
     }
954 953
     
955 954
     /* compute buffer size max (should use a complete heuristic) */
... ...
@@ -976,8 +1062,6 @@ static int av_encode(AVFormatContext **output_files,
976 976
 #endif
977 977
     term_init();
978 978
 
979
-    start_time = av_gettime();
980
-    min_pts = 0;
981 979
     stream_no_data = 0;
982 980
     key = -1;
983 981
 
... ...
@@ -990,7 +1074,8 @@ static int av_encode(AVFormatContext **output_files,
990 990
         int data_size, got_picture;
991 991
         AVPicture picture;
992 992
         short samples[AVCODEC_MAX_AUDIO_FRAME_SIZE / 2];
993
-
993
+        double pts_min;
994
+        
994 995
     redo:
995 996
         /* if 'q' pressed, exits */
996 997
         if (key) {
... ...
@@ -1000,42 +1085,31 @@ static int av_encode(AVFormatContext **output_files,
1000 1000
                 break;
1001 1001
         }
1002 1002
 
1003
-        /* select the input file with the smallest pts */
1003
+        /* select the stream that we must read now by looking at the
1004
+           smallest output pts */
1004 1005
         file_index = -1;
1005
-        min_pts = MAXINT64;
1006
-        for(i=0;i<nb_istreams;i++) {
1007
-            ist = ist_table[i];
1008
-            /* For some reason, the pts_increment code breaks q estimation?!? */
1009
-            if (!ist->discard && !file_table[ist->file_index].eof_reached && 
1010
-                ist->pts /* + ist->pts_increment */ < min_pts && input_files[ist->file_index] != stream_no_data) {
1011
-                min_pts = ist->pts /* + ist->pts_increment */;
1006
+        pts_min = 1e10;
1007
+        for(i=0;i<nb_ostreams;i++) {
1008
+            double pts;
1009
+            ost = ost_table[i];
1010
+            os = output_files[ost->file_index];
1011
+            ist = ist_table[ost->source_index];
1012
+            pts = (double)ost->st->pts.val * os->pts_num / os->pts_den;
1013
+            if (!file_table[ist->file_index].eof_reached && 
1014
+                pts < pts_min) {
1015
+                pts_min = pts;
1012 1016
                 file_index = ist->file_index;
1013 1017
             }
1014 1018
         }
1015 1019
         /* if none, if is finished */
1016 1020
         if (file_index < 0) {
1017
-            if (stream_no_data) {
1018
-#ifndef CONFIG_WIN32 /* no usleep in VisualC ? */
1019
-#ifdef __BEOS__
1020
-                snooze(10 * 1000); /* mmu_man */ /* in microsec */
1021
-#elif defined(__CYGWIN__)
1022
-                usleep(10 * 1000); 
1023
-#else
1024
-                struct timespec ts;
1025
-
1026
-                ts.tv_sec = 0;
1027
-                ts.tv_nsec = 1000 * 1000 * 10;
1028
-                nanosleep(&ts, 0);
1029
-#endif
1030
-#endif
1031
-                stream_no_data = 0;
1032
-                continue;
1033
-            }
1034 1021
             break;
1035
-        }    
1022
+        }
1023
+
1036 1024
         /* finish if recording time exhausted */
1037
-        if (recording_time > 0 && min_pts >= recording_time)
1025
+        if (recording_time > 0 && pts_min >= (recording_time / 1000000.0))
1038 1026
             break;
1027
+
1039 1028
         /* read a packet from it and output it in the fifo */
1040 1029
         is = input_files[file_index];
1041 1030
         if (av_read_packet(is, &pkt) < 0) {
... ...
@@ -1056,9 +1130,6 @@ static int av_encode(AVFormatContext **output_files,
1056 1056
         if (ist->discard)
1057 1057
             goto discard_packet;
1058 1058
 
1059
-        if (pkt.flags & PKT_FLAG_DROPPED_FRAME)
1060
-            ist->frame_number++;
1061
-
1062 1059
         if (do_hex_dump) {
1063 1060
             printf("stream #%d, size=%d:\n", pkt.stream_index, pkt.size);
1064 1061
             av_hex_dump(pkt.data, pkt.size);
... ...
@@ -1068,12 +1139,28 @@ static int av_encode(AVFormatContext **output_files,
1068 1068
 
1069 1069
         len = pkt.size;
1070 1070
         ptr = pkt.data;
1071
+        pts_set = 0;
1071 1072
         while (len > 0) {
1073
+            INT64 ipts;
1074
+
1075
+            ipts = AV_NOPTS_VALUE;
1072 1076
 
1073 1077
             /* decode the packet if needed */
1074 1078
             data_buf = NULL; /* fail safe */
1075 1079
             data_size = 0;
1076 1080
             if (ist->decoding_needed) {
1081
+                /* NOTE1: we only take into account the PTS if a new
1082
+                   frame has begun (MPEG semantics) */
1083
+                /* NOTE2: even if the fraction is not initialized,
1084
+                   av_frac_set can be used to set the integer part */
1085
+                if (ist->frame_decoded && 
1086
+                    pkt.pts != AV_NOPTS_VALUE && 
1087
+                    !pts_set) {
1088
+                    ipts = pkt.pts;
1089
+                    ist->frame_decoded = 0;
1090
+                    pts_set = 1;
1091
+                }
1092
+
1077 1093
                 switch(ist->st->codec.codec_type) {
1078 1094
                 case CODEC_TYPE_AUDIO:
1079 1095
                     /* XXX: could avoid copy if PCM 16 bits with same
... ...
@@ -1130,64 +1217,71 @@ static int av_encode(AVFormatContext **output_files,
1130 1130
                 data_size = len;
1131 1131
                 ret = len;
1132 1132
             }
1133
-            /* init tickers */
1134
-            if (!ist->ticker_inited) {
1135
-                switch (ist->st->codec.codec_type) {
1136
-                case CODEC_TYPE_AUDIO:
1137
-                    ticker_init(&ist->pts_ticker,
1138
-                            (INT64)ist->st->codec.sample_rate,
1139
-                            (INT64)(1000000));
1140
-                    ist->ticker_inited = 1;
1141
-                    break;
1142
-                case CODEC_TYPE_VIDEO:
1143
-                    ticker_init(&ist->pts_ticker,
1144
-                            (INT64)ist->st->r_frame_rate,
1145
-                            ((INT64)1000000 * FRAME_RATE_BASE));
1146
-                    ist->ticker_inited = 1;
1147
-                    break;
1148
-                default:
1149
-                    av_abort();
1150
-                }
1151
-            }
1152
-            /* update pts */
1153
-            switch(ist->st->codec.codec_type) {
1154
-            case CODEC_TYPE_AUDIO:
1155
-                //ist->pts = (INT64)1000000 * ist->sample_index / ist->st->codec.sample_rate;
1156
-                ist->pts = ticker_abs(&ist->pts_ticker, ist->sample_index);
1157
-                ist->sample_index += data_size / (2 * ist->st->codec.channels);
1158
-                ist->pts_increment = (INT64) (data_size / (2 * ist->st->codec.channels)) * 1000000 / ist->st->codec.sample_rate;
1159
-                break;
1160
-            case CODEC_TYPE_VIDEO:
1161
-                ist->frame_number++;
1162
-                //ist->pts = ((INT64)ist->frame_number * 1000000 * FRAME_RATE_BASE) / 
1163
-                //    ist->st->codec.frame_rate;
1164
-                ist->pts = ticker_abs(&ist->pts_ticker, ist->frame_number);
1165
-                ist->pts_increment = ((INT64) 1000000 * FRAME_RATE_BASE) / 
1166
-                    ist->st->codec.frame_rate;
1167
-                break;
1168
-            default:
1169
-                av_abort();
1170
-            }
1171 1133
             ptr += ret;
1172 1134
             len -= ret;
1173 1135
 
1136
+            ist->frame_decoded = 1;
1137
+
1138
+#if 0
1139
+            /* mpeg PTS deordering : if it is a P or I frame, the PTS
1140
+               is the one of the next displayed one */
1141
+            /* XXX: add mpeg4 too ? */
1142
+            if (ist->st->codec.codec_id == CODEC_ID_MPEG1VIDEO) {
1143
+                if (ist->st->codec.pict_type != B_TYPE) {
1144
+                    INT64 tmp;
1145
+                    tmp = ist->last_ip_pts;
1146
+                    ist->last_ip_pts  = ist->frac_pts.val;
1147
+                    ist->frac_pts.val = tmp;
1148
+                }
1149
+            }
1150
+#endif
1174 1151
             /* transcode raw format, encode packets and output them */
1175
-            
1152
+
1176 1153
             for(i=0;i<nb_ostreams;i++) {
1177 1154
                 int frame_size;
1155
+
1178 1156
                 ost = ost_table[i];
1179 1157
                 if (ost->source_index == ist_index) {
1180 1158
                     os = output_files[ost->file_index];
1181 1159
 
1160
+                    if (ipts != AV_NOPTS_VALUE) {
1161
+#if 0
1162
+                        printf("%d: got pts=%f %f\n", 
1163
+                               i, pkt.pts / 90000.0, 
1164
+                               (ipts - ost->st->pts.val) / 90000.0);
1165
+#endif
1166
+                        /* set the input output pts pairs */
1167
+                        ost->sync_ipts = (double)ipts * is->pts_num / 
1168
+                            is->pts_den;
1169
+                        /* XXX: take into account the various fifos,
1170
+                           in particular for audio */
1171
+                        ost->sync_opts = ost->st->pts.val;
1172
+                    }
1173
+
1182 1174
                     if (ost->encoding_needed) {
1183 1175
                         switch(ost->st->codec.codec_type) {
1184 1176
                         case CODEC_TYPE_AUDIO:
1185 1177
                             do_audio_out(os, ost, ist, data_buf, data_size);
1186 1178
                             break;
1187 1179
                         case CODEC_TYPE_VIDEO:
1188
-                            do_video_out(os, ost, ist, &picture, &frame_size);
1189
-                            if (do_vstats)
1190
-                                do_video_stats(ost, ist, frame_size);
1180
+                            /* find an audio stream for synchro */
1181
+                            {
1182
+                                int i;
1183
+                                AVOutputStream *audio_sync, *ost1;
1184
+                                audio_sync = NULL;
1185
+                                for(i=0;i<nb_ostreams;i++) {
1186
+                                    ost1 = ost_table[i];
1187
+                                    if (ost1->file_index == ost->file_index &&
1188
+                                        ost1->st->codec.codec_type == CODEC_TYPE_AUDIO) {
1189
+                                        audio_sync = ost1;
1190
+                                        break;
1191
+                                    }
1192
+                                }
1193
+
1194
+                                do_video_out(os, ost, ist, &picture, &frame_size, audio_sync);
1195
+                                if (do_vstats)
1196
+                                    do_video_stats(os, ost, frame_size);
1197
+                            }
1191 1198
                             break;
1192 1199
                         default:
1193 1200
                             av_abort();
... ...
@@ -1195,113 +1289,23 @@ static int av_encode(AVFormatContext **output_files,
1195 1195
                     } else {
1196 1196
                         /* no reencoding needed : output the packet directly */
1197 1197
                         /* force the input stream PTS */
1198
-                        os->oformat->write_packet(os, ost->index, data_buf, data_size, pkt.pts);
1198
+                        av_write_frame(os, ost->index, data_buf, data_size);
1199 1199
                     }
1200 1200
                 }
1201 1201
             }
1202
+            ipts = AV_NOPTS_VALUE;
1202 1203
         }
1203 1204
     discard_packet:
1204 1205
         av_free_packet(&pkt);
1205 1206
         
1206
-        /* dump report by using the first video and audio streams */
1207
-        {
1208
-            char buf[1024];
1209
-            AVFormatContext *oc;
1210
-            INT64 total_size, ti;
1211
-            AVCodecContext *enc;
1212
-            int frame_number, vid;
1213
-            double bitrate, ti1;
1214
-            static INT64 last_time;
1215
-
1216
-            if ((min_pts - last_time) >= 500000) {
1217
-                last_time = min_pts;
1218
-                
1219
-                oc = output_files[0];
1220
-                
1221
-                total_size = url_ftell(&oc->pb);
1222
-                
1223
-                buf[0] = '\0';
1224
-                ti = MAXINT64;
1225
-                vid = 0;
1226
-                for(i=0;i<nb_ostreams;i++) {
1227
-                    ost = ost_table[i];
1228
-                    enc = &ost->st->codec;
1229
-                    ist = ist_table[ost->source_index];
1230
-                    if (!vid && enc->codec_type == CODEC_TYPE_VIDEO) {
1231
-                        frame_number = ist->frame_number;
1232
-                        sprintf(buf + strlen(buf), "frame=%5d q=%2d ",
1233
-                                frame_number, enc->quality);
1234
-                        if (do_psnr)
1235
-                            sprintf(buf + strlen(buf), "PSNR=%6.2f ", enc->psnr_y);
1236
-                        vid = 1;
1237
-                    }
1238
-                    /* compute min pts value */
1239
-                    if (!ist->discard && ist->pts < ti) {
1240
-                        ti = ist->pts;
1241
-                    }
1242
-                }
1243
-
1244
-                ti1 = (double)ti / 1000000.0;
1245
-                if (ti1 < 0.01)
1246
-                    ti1 = 0.01;
1247
-                bitrate = (double)(total_size * 8) / ti1 / 1000.0;
1248
-
1249
-                sprintf(buf + strlen(buf), 
1250
-                        "size=%8.0fkB time=%0.1f bitrate=%6.1fkbits/s",
1251
-                        (double)total_size / 1024, ti1, bitrate);
1252
-                
1253
-                fprintf(stderr, "%s   \r", buf);
1254
-                fflush(stderr);
1255
-            }
1256
-        }
1207
+        /* dump report by using the output first video and audio streams */
1208
+        print_report(output_files, ost_table, nb_ostreams, 0);
1257 1209
     }
1258 1210
     term_exit();
1259 1211
 
1260 1212
     /* dump report by using the first video and audio streams */
1261
-    {
1262
-        char buf[1024];
1263
-        AVFormatContext *oc;
1264
-        INT64 total_size, ti;
1265
-        AVCodecContext *enc;
1266
-        int frame_number, vid;
1267
-        double bitrate, ti1;
1268
-
1269
-        oc = output_files[0];
1270
-        
1271
-        total_size = url_ftell(&oc->pb);
1272
-        
1273
-        buf[0] = '\0';
1274
-        ti = MAXINT64;
1275
-        vid = 0;
1276
-        for(i=0;i<nb_ostreams;i++) {
1277
-            ost = ost_table[i];
1278
-            enc = &ost->st->codec;
1279
-            ist = ist_table[ost->source_index];
1280
-            if (!vid && enc->codec_type == CODEC_TYPE_VIDEO) {
1281
-                frame_number = ist->frame_number;
1282
-                sprintf(buf + strlen(buf), "frame=%5d q=%2d ",
1283
-                        frame_number, enc->quality);
1284
-                if (do_psnr)
1285
-                    sprintf(buf + strlen(buf), "PSNR=%6.2f ", enc->psnr_y);
1286
-                vid = 1;
1287
-            }
1288
-            /* compute min pts value */
1289
-            if (!ist->discard && ist->pts < ti) {
1290
-                ti = ist->pts;
1291
-            }
1292
-        }
1293
-        
1294
-        ti1 = ti / 1000000.0;
1295
-        if (ti1 < 0.01)
1296
-            ti1 = 0.01;
1297
-        bitrate = (double)(total_size * 8) / ti1 / 1000.0;
1298
-        
1299
-        sprintf(buf + strlen(buf), 
1300
-                "size=%8.0fkB time=%0.1f bitrate=%6.1fkbits/s",
1301
-                (double)total_size / 1024, ti1, bitrate);
1302
-        
1303
-        fprintf(stderr, "%s   \n", buf);
1304
-    }
1213
+    print_report(output_files, ost_table, nb_ostreams, 1);
1214
+
1305 1215
     /* close each encoder */
1306 1216
     for(i=0;i<nb_ostreams;i++) {
1307 1217
         ost = ost_table[i];