]> git.sesse.net Git - ffmpeg/blobdiff - ffmpeg.c
Fix Indel --> Intel typo.
[ffmpeg] / ffmpeg.c
index 888319121e4b0c41108145ce9b51d72e84b56f52..7008ad88456abab8dd864934a3e20bcfbb421fd7 100644 (file)
--- a/ffmpeg.c
+++ b/ffmpeg.c
 #define HAVE_AV_CONFIG_H
 #include <limits.h>
 #include "avformat.h"
+#include "swscale.h"
 #include "framehook.h"
 #include "dsputil.h"
 #include "opt.h"
 
-#ifndef CONFIG_WIN32
+#ifndef __MINGW32__
 #include <unistd.h>
 #include <fcntl.h>
 #include <sys/ioctl.h>
@@ -104,7 +105,6 @@ static int frame_rightBand = 0;
 static int max_frames[4] = {INT_MAX, INT_MAX, INT_MAX, INT_MAX};
 static int frame_rate = 25;
 static int frame_rate_base = 1;
-static int video_bit_rate = 200*1000;
 static int video_bit_rate_tolerance = 4000*1000;
 static float video_qscale = 0;
 static int video_qmin = 2;
@@ -159,9 +159,8 @@ static int me_penalty_compensation= 256;
 static int frame_skip_threshold= 0;
 static int frame_skip_factor= 0;
 static int frame_skip_exp= 0;
-extern int loop_input; /* currently a hack */
+static int loop_input = 0;
 static int loop_output = AVFMT_NOOUTPUTLOOP;
-static int genpts = 0;
 static int qp_hist = 0;
 
 static int gop_size = 12;
@@ -193,6 +192,7 @@ static char *str_title = NULL;
 static char *str_author = NULL;
 static char *str_copyright = NULL;
 static char *str_comment = NULL;
+static char *str_album = NULL;
 static int do_benchmark = 0;
 static int do_hex_dump = 0;
 static int do_pkt_dump = 0;
@@ -246,10 +246,16 @@ static int limit_filesize = 0; //
 static int pgmyuv_compatibility_hack=0;
 static int dts_delta_threshold = 10;
 
+static int sws_flags = SWS_BICUBIC;
+
 const char **opt_names=NULL;
 int opt_name_count=0;
 AVCodecContext *avctx_opts;
+AVFormatContext *avformat_opts;
 
+static AVBitStreamFilterContext *video_bitstream_filters=NULL;
+static AVBitStreamFilterContext *audio_bitstream_filters=NULL;
+static AVBitStreamFilterContext *bitstream_filters[MAX_FILES][MAX_STREAMS];
 
 #define DEFAULT_PASS_LOGFILENAME "ffmpeg2pass"
 
@@ -270,7 +276,8 @@ typedef struct AVOutputStream {
     /* video only */
     int video_resample;
     AVFrame pict_tmp;      /* temporary image for resampling */
-    ImgReSampleContext *img_resample_ctx; /* for image resampling */
+    struct SwsContext *img_resample_ctx; /* for image resampling */
+    int resample_height;
 
     int video_crop;
     int topBand;             /* cropping area sizes */
@@ -314,7 +321,7 @@ typedef struct AVInputFile {
     int nb_streams;       /* nb streams we are aware of */
 } AVInputFile;
 
-#ifndef CONFIG_WIN32
+#ifndef __MINGW32__
 
 /* init terminal so that we can grab keys */
 static struct termios oldtty;
@@ -445,6 +452,25 @@ get_sync_ipts(const AVOutputStream *ost)
     return (double)(ist->pts + input_files_ts_offset[ist->file_index] - start_time)/AV_TIME_BASE;
 }
 
+static void write_frame(AVFormatContext *s, AVPacket *pkt, AVCodecContext *avctx, AVBitStreamFilterContext *bsfc){
+    while(bsfc){
+        AVPacket new_pkt= *pkt;
+        int a= av_bitstream_filter_filter(bsfc, avctx, NULL,
+                                          &new_pkt.data, &new_pkt.size,
+                                          pkt->data, pkt->size,
+                                          pkt->flags & PKT_FLAG_KEY);
+        if(a){
+            av_free_packet(pkt);
+            new_pkt.destruct= av_destruct_packet;
+        }
+        *pkt= new_pkt;
+
+        bsfc= bsfc->next;
+    }
+
+    av_interleaved_write_frame(s, pkt);
+}
+
 #define MAX_AUDIO_PACKET_SIZE (128 * 1024)
 
 static void do_audio_out(AVFormatContext *s,
@@ -548,7 +574,7 @@ static void do_audio_out(AVFormatContext *s,
             if(enc->coded_frame && enc->coded_frame->pts != AV_NOPTS_VALUE)
                 pkt.pts= av_rescale_q(enc->coded_frame->pts, enc->time_base, ost->st->time_base);
             pkt.flags |= PKT_FLAG_KEY;
-            av_interleaved_write_frame(s, &pkt);
+            write_frame(s, &pkt, ost->st->codec, bitstream_filters[ost->file_index][pkt.stream_index]);
 
             ost->sync_opts += enc->frame_size;
         }
@@ -592,7 +618,7 @@ static void do_audio_out(AVFormatContext *s,
         if(enc->coded_frame && enc->coded_frame->pts != AV_NOPTS_VALUE)
             pkt.pts= av_rescale_q(enc->coded_frame->pts, enc->time_base, ost->st->time_base);
         pkt.flags |= PKT_FLAG_KEY;
-        av_interleaved_write_frame(s, &pkt);
+        write_frame(s, &pkt, ost->st->codec, bitstream_filters[ost->file_index][pkt.stream_index]);
     }
 }
 
@@ -691,7 +717,7 @@ static void do_subtitle_out(AVFormatContext *s,
             else
                 pkt.pts += 90 * sub->end_display_time;
         }
-        av_interleaved_write_frame(s, &pkt);
+        write_frame(s, &pkt, ost->st->codec, bitstream_filters[ost->file_index][pkt.stream_index]);
     }
 }
 
@@ -706,12 +732,10 @@ static void do_video_out(AVFormatContext *s,
 {
     int nb_frames, i, ret;
     AVFrame *final_picture, *formatted_picture, *resampling_dst, *padding_src;
-    AVFrame picture_format_temp, picture_crop_temp, picture_pad_temp;
+    AVFrame picture_crop_temp, picture_pad_temp;
     uint8_t *buf = NULL, *buf1 = NULL;
     AVCodecContext *enc, *dec;
-    enum PixelFormat target_pixfmt;
 
-    avcodec_get_frame_defaults(&picture_format_temp);
     avcodec_get_frame_defaults(&picture_crop_temp);
     avcodec_get_frame_defaults(&picture_pad_temp);
 
@@ -748,38 +772,14 @@ static void do_video_out(AVFormatContext *s,
     if (nb_frames <= 0)
         return;
 
-    /* convert pixel format if needed */
-    target_pixfmt = ost->video_resample ? PIX_FMT_YUV420P : enc->pix_fmt;
-    if (dec->pix_fmt != target_pixfmt) {
-        int size;
-
-        /* create temporary picture */
-        size = avpicture_get_size(target_pixfmt, dec->width, dec->height);
-        buf = av_malloc(size);
-        if (!buf)
-            return;
-        formatted_picture = &picture_format_temp;
-        avpicture_fill((AVPicture*)formatted_picture, buf, target_pixfmt, dec->width, dec->height);
-
-        if (img_convert((AVPicture*)formatted_picture, target_pixfmt,
-                        (AVPicture *)in_picture, dec->pix_fmt,
-                        dec->width, dec->height) < 0) {
-
-            if (verbose >= 0)
-                fprintf(stderr, "pixel format conversion not handled\n");
-
-            goto the_end;
-        }
-    } else {
-        formatted_picture = in_picture;
-    }
-
     if (ost->video_crop) {
-        if (img_crop((AVPicture *)&picture_crop_temp, (AVPicture *)formatted_picture, target_pixfmt, ost->topBand, ost->leftBand) < 0) {
+        if (img_crop((AVPicture *)&picture_crop_temp, (AVPicture *)in_picture, dec->pix_fmt, ost->topBand, ost->leftBand) < 0) {
             av_log(NULL, AV_LOG_ERROR, "error cropping picture\n");
             goto the_end;
         }
         formatted_picture = &picture_crop_temp;
+    } else {
+        formatted_picture = in_picture;
     }
 
     final_picture = formatted_picture;
@@ -788,7 +788,7 @@ static void do_video_out(AVFormatContext *s,
     if (ost->video_pad) {
         final_picture = &ost->pict_tmp;
         if (ost->video_resample) {
-            if (img_crop((AVPicture *)&picture_pad_temp, (AVPicture *)final_picture, target_pixfmt, ost->padtop, ost->padleft) < 0) {
+            if (img_crop((AVPicture *)&picture_pad_temp, (AVPicture *)final_picture, enc->pix_fmt, ost->padtop, ost->padleft) < 0) {
                 av_log(NULL, AV_LOG_ERROR, "error padding picture\n");
                 goto the_end;
             }
@@ -796,36 +796,11 @@ static void do_video_out(AVFormatContext *s,
         }
     }
 
-    /* XXX: resampling could be done before raw format conversion in
-       some cases to go faster */
-    /* XXX: only works for YUV420P */
     if (ost->video_resample) {
         padding_src = NULL;
         final_picture = &ost->pict_tmp;
-        img_resample(ost->img_resample_ctx, (AVPicture *)resampling_dst, (AVPicture*)formatted_picture);
-    }
-
-    if (enc->pix_fmt != target_pixfmt) {
-        int size;
-
-        av_free(buf);
-        /* create temporary picture */
-        size = avpicture_get_size(enc->pix_fmt, enc->width, enc->height);
-        buf = av_malloc(size);
-        if (!buf)
-            return;
-        final_picture = &picture_format_temp;
-        avpicture_fill((AVPicture*)final_picture, buf, enc->pix_fmt, enc->width, enc->height);
-
-        if (img_convert((AVPicture*)final_picture, enc->pix_fmt,
-                        (AVPicture*)&ost->pict_tmp, target_pixfmt,
-                        enc->width, enc->height) < 0) {
-
-            if (verbose >= 0)
-                fprintf(stderr, "pixel format conversion not handled\n");
-
-            goto the_end;
-        }
+        sws_scale(ost->img_resample_ctx, formatted_picture->data, formatted_picture->linesize,
+              0, ost->resample_height, resampling_dst->data, resampling_dst->linesize);
     }
 
     if (ost->video_pad) {
@@ -853,7 +828,7 @@ static void do_video_out(AVFormatContext *s,
             if(dec->coded_frame && dec->coded_frame->key_frame)
                 pkt.flags |= PKT_FLAG_KEY;
 
-            av_interleaved_write_frame(s, &pkt);
+            write_frame(s, &pkt, ost->st->codec, bitstream_filters[ost->file_index][pkt.stream_index]);
             enc->coded_frame = old_frame;
         } else {
             AVFrame big_picture;
@@ -896,7 +871,7 @@ static void do_video_out(AVFormatContext *s,
 
                 if(enc->coded_frame && enc->coded_frame->key_frame)
                     pkt.flags |= PKT_FLAG_KEY;
-                av_interleaved_write_frame(s, &pkt);
+                write_frame(s, &pkt, ost->st->codec, bitstream_filters[ost->file_index][pkt.stream_index]);
                 *frame_size = ret;
                 //fprintf(stderr,"\nFrame: %3d %3d size: %5d type: %d",
                 //        enc->frame_number-1, enc->real_pict_num, ret,
@@ -1317,9 +1292,12 @@ static int output_packet(AVInputStream *ist, int ist_index,
                                 opkt.dts= av_rescale_q(dts + input_files_ts_offset[ist->file_index], AV_TIME_BASE_Q,  ost->st->time_base);
                             }
                             opkt.flags= pkt->flags;
+
+                            //FIXME remove the following 2 lines they shall be replaced by the bitstream filters
                             if(av_parser_change(ist->st->parser, ost->st->codec, &opkt.data, &opkt.size, data_buf, data_size, pkt->flags & PKT_FLAG_KEY))
                                 opkt.destruct= av_destruct_packet;
-                            av_interleaved_write_frame(os, &opkt);
+
+                            write_frame(os, &opkt, ost->st->codec, bitstream_filters[ost->file_index][pkt->stream_index]);
                             ost->st->codec->frame_number++;
                             ost->frame_number++;
                             av_free_packet(&opkt);
@@ -1375,10 +1353,8 @@ static int output_packet(AVInputStream *ist, int ist_index,
                                     ret = avcodec_encode_audio(enc, bit_buffer, bit_buffer_size, samples);
                                 }
                                 enc->frame_size = fs_tmp;
-                                if(ret <= 0) {
-                                    ret = avcodec_encode_audio(enc, bit_buffer, bit_buffer_size, NULL);
-                                }
-                            } else {
+                            }
+                            if(ret <= 0) {
                                 ret = avcodec_encode_audio(enc, bit_buffer, bit_buffer_size, NULL);
                             }
                             audio_size += ret;
@@ -1403,7 +1379,7 @@ static int output_packet(AVInputStream *ist, int ist_index,
                         pkt.size= ret;
                         if(enc->coded_frame && enc->coded_frame->pts != AV_NOPTS_VALUE)
                             pkt.pts= av_rescale_q(enc->coded_frame->pts, enc->time_base, ost->st->time_base);
-                        av_interleaved_write_frame(os, &pkt);
+                        write_frame(os, &pkt, ost->st->codec, bitstream_filters[ost->file_index][pkt.stream_index]);
                     }
                 }
             }
@@ -1657,7 +1633,8 @@ static int av_encode(AVFormatContext **output_files,
                                 (frame_padleft + frame_padright)) ||
                         (codec->height != icodec->height -
                                 (frame_topBand  + frame_bottomBand) +
-                                (frame_padtop + frame_padbottom)));
+                                (frame_padtop + frame_padbottom)) ||
+                        (codec->pix_fmt != icodec->pix_fmt));
                 if (ost->video_crop) {
                     ost->topBand = frame_topBand;
                     ost->leftBand = frame_leftBand;
@@ -1676,16 +1653,23 @@ static int av_encode(AVFormatContext **output_files,
                 }
                 if (ost->video_resample) {
                     avcodec_get_frame_defaults(&ost->pict_tmp);
-                    if( avpicture_alloc( (AVPicture*)&ost->pict_tmp, PIX_FMT_YUV420P,
+                    if( avpicture_alloc( (AVPicture*)&ost->pict_tmp, codec->pix_fmt,
                                          codec->width, codec->height ) )
                         goto fail;
 
-                    ost->img_resample_ctx = img_resample_init(
+                    ost->img_resample_ctx = sws_getContext(
+                            icodec->width - (frame_leftBand + frame_rightBand),
+                            icodec->height - (frame_topBand + frame_bottomBand),
+                            icodec->pix_fmt,
                             codec->width - (frame_padleft + frame_padright),
                             codec->height - (frame_padtop + frame_padbottom),
-                            icodec->width - (frame_leftBand + frame_rightBand),
-                            icodec->height - (frame_topBand + frame_bottomBand));
-
+                            codec->pix_fmt,
+                            sws_flags, NULL, NULL, NULL);
+                    if (ost->img_resample_ctx == NULL) {
+                        fprintf(stderr, "Cannot get resampling context\n");
+                        exit(1);
+                    }
+                    ost->resample_height = icodec->height - (frame_topBand + frame_bottomBand);
                 }
                 ost->encoding_needed = 1;
                 ist->decoding_needed = 1;
@@ -1873,7 +1857,7 @@ static int av_encode(AVFormatContext **output_files,
         }
     }
 
-#ifndef CONFIG_WIN32
+#ifndef __MINGW32__
     if ( !using_stdin && verbose >= 0) {
         fprintf(stderr, "Press [q] to stop encoding\n");
         url_set_interrupt_cb(decode_interrupt_cb);
@@ -2063,7 +2047,7 @@ static int av_encode(AVFormatContext **output_files,
                                           initialized but set to zero */
                 av_free(ost->pict_tmp.data[0]);
                 if (ost->video_resample)
-                    img_resample_close(ost->img_resample_ctx);
+                    sws_freeContext(ost->img_resample_ctx);
                 if (ost->audio_resample)
                     audio_resample_close(ost->resample);
                 av_free(ost);
@@ -2131,11 +2115,6 @@ static void opt_format(const char *arg)
     }
 }
 
-static void opt_video_bitrate(const char *arg)
-{
-    video_bit_rate = atoi(arg) * 1000;
-}
-
 static void opt_video_bitrate_tolerance(const char *arg)
 {
     video_bit_rate_tolerance = atoi(arg) * 1000;
@@ -2796,7 +2775,10 @@ static void opt_input_file(const char *filename)
                    !strcmp( filename, "/dev/stdin" );
 
     /* get default parameters from command line */
+    ic = av_alloc_format_context();
+
     memset(ap, 0, sizeof(*ap));
+    ap->prealloced_context = 1;
     ap->sample_rate = audio_sample_rate;
     ap->channels = audio_channels;
     ap->time_base.den = frame_rate;
@@ -2813,6 +2795,12 @@ static void opt_input_file(const char *filename)
     if(pgmyuv_compatibility_hack)
         ap->video_codec_id= CODEC_ID_PGMYUV;
 
+    for(i=0; i<opt_name_count; i++){
+        AVOption *opt;
+        double d= av_get_double(avformat_opts, opt_names[i], &opt);
+        if(d==d && (opt->flags&AV_OPT_FLAG_DECODING_PARAM))
+            av_set_double(ic, opt_names[i], d);
+    }
     /* open the input file with generic libav function */
     err = av_open_input_file(&ic, filename, file_iformat, 0, ap);
     if (err < 0) {
@@ -2820,8 +2808,7 @@ static void opt_input_file(const char *filename)
         exit(1);
     }
 
-    if(genpts)
-        ic->flags|= AVFMT_FLAG_GENPTS;
+    ic->loop_input = loop_input;
 
     /* If not enough info to get the stream parameters, we decode the
        first frames to get it. (used in mpeg case for example) */
@@ -2982,6 +2969,9 @@ static void new_video_stream(AVFormatContext *oc)
         fprintf(stderr, "Could not alloc stream\n");
         exit(1);
     }
+    bitstream_filters[nb_output_files][oc->nb_streams - 1]= video_bitstream_filters;
+    video_bitstream_filters= NULL;
+
 #if defined(HAVE_THREADS)
     if(thread_count>1)
         avcodec_thread_init(st->codec, thread_count);
@@ -3024,7 +3014,6 @@ static void new_video_stream(AVFormatContext *oc)
                  av_set_double(video_enc, opt_names[i], d);
         }
 
-        video_enc->bit_rate = video_bit_rate;
         video_enc->bit_rate_tolerance = video_bit_rate_tolerance;
         video_enc->time_base.den = frame_rate;
         video_enc->time_base.num = frame_rate_base;
@@ -3047,7 +3036,7 @@ static void new_video_stream(AVFormatContext *oc)
 
         video_enc->width = frame_width + frame_padright + frame_padleft;
         video_enc->height = frame_height + frame_padtop + frame_padbottom;
-        video_enc->sample_aspect_ratio = av_d2q(frame_aspect_ratio*frame_height/frame_width, 255);
+        video_enc->sample_aspect_ratio = av_d2q(frame_aspect_ratio*video_enc->height/video_enc->width, 255);
         video_enc->pix_fmt = frame_pix_fmt;
 
         if(codec && codec->pix_fmts){
@@ -3181,6 +3170,10 @@ static void new_audio_stream(AVFormatContext *oc)
         fprintf(stderr, "Could not alloc stream\n");
         exit(1);
     }
+
+    bitstream_filters[nb_output_files][oc->nb_streams - 1]= audio_bitstream_filters;
+    audio_bitstream_filters= NULL;
+
 #if defined(HAVE_THREADS)
     if(thread_count>1)
         avcodec_thread_init(st->codec, thread_count);
@@ -3310,7 +3303,7 @@ static void opt_new_video_stream(void)
 static void opt_output_file(const char *filename)
 {
     AVFormatContext *oc;
-    int use_video, use_audio, input_has_video, input_has_audio;
+    int use_video, use_audio, input_has_video, input_has_audio, i;
     AVFormatParameters params, *ap = &params;
 
     if (!strcmp(filename, "-"))
@@ -3383,13 +3376,15 @@ static void opt_output_file(const char *filename)
             pstrcpy(oc->copyright, sizeof(oc->copyright), str_copyright);
         if (str_comment)
             pstrcpy(oc->comment, sizeof(oc->comment), str_comment);
+        if (str_album)
+            pstrcpy(oc->album, sizeof(oc->album), str_album);
     }
 
     output_files[nb_output_files++] = oc;
 
     /* check filename in case of an image number is expected */
     if (oc->oformat->flags & AVFMT_NEEDNUMBER) {
-        if (filename_number_test(oc->filename) < 0) {
+        if (!av_filename_number_test(oc->filename)) {
             print_error(oc->filename, AVERROR_NUMEXPECTED);
             exit(1);
         }
@@ -3440,6 +3435,13 @@ static void opt_output_file(const char *filename)
     oc->max_delay= (int)(mux_max_delay*AV_TIME_BASE);
     oc->loop_output = loop_output;
 
+    for(i=0; i<opt_name_count; i++){
+        AVOption *opt;
+        double d = av_get_double(avformat_opts, opt_names[i], &opt);
+        if(d==d && (opt->flags&AV_OPT_FLAG_ENCODING_PARAM))
+            av_set_double(oc, opt_names[i], d);
+    }
+
     /* reset some options */
     file_oformat = NULL;
     file_iformat = NULL;
@@ -3555,7 +3557,7 @@ static void opt_pass(const char *pass_str)
     do_pass = pass;
 }
 
-#if defined(CONFIG_WIN32) || defined(CONFIG_OS2)
+#if defined(__MINGW32__) || defined(CONFIG_OS2)
 static int64_t getutime(void)
 {
   return av_gettime();
@@ -3570,7 +3572,9 @@ static int64_t getutime(void)
 }
 #endif
 
+#if defined(CONFIG_FFM_DEMUXER) || defined(CONFIG_FFM_MUXER)
 extern int ffm_nopts;
+#endif
 
 static void show_formats(void)
 {
@@ -3809,7 +3813,7 @@ static void opt_target(const char *arg)
         opt_frame_rate(frame_rates[norm]);
         opt_gop_size(norm ? "18" : "15");
 
-        video_bit_rate = 1150000;
+        opt_default("b", "1150000");
         video_rc_max_rate = 1150000;
         video_rc_min_rate = 1150000;
         video_rc_buffer_size = 40*1024*8;
@@ -3836,7 +3840,7 @@ static void opt_target(const char *arg)
         opt_frame_rate(frame_rates[norm]);
         opt_gop_size(norm ? "18" : "15");
 
-        video_bit_rate = 2040000;
+        opt_default("b", "2040000");
         video_rc_max_rate = 2516000;
         video_rc_min_rate = 0; //1145000;
         video_rc_buffer_size = 224*1024*8;
@@ -3858,7 +3862,7 @@ static void opt_target(const char *arg)
         opt_frame_rate(frame_rates[norm]);
         opt_gop_size(norm ? "18" : "15");
 
-        video_bit_rate = 6000000;
+        opt_default("b", "6000000");
         video_rc_max_rate = 9000000;
         video_rc_min_rate = 0; //1500000;
         video_rc_buffer_size = 224*1024*8;
@@ -3887,6 +3891,41 @@ static void opt_target(const char *arg)
     }
 }
 
+static void opt_video_bsf(const char *arg)
+{
+    AVBitStreamFilterContext *bsfc= av_bitstream_filter_init(arg); //FIXME split name and args for filter at '='
+    AVBitStreamFilterContext **bsfp;
+
+    if(!bsfc){
+        fprintf(stderr, "Unkown bitstream filter %s\n", arg);
+        exit(1);
+    }
+
+    bsfp= &video_bitstream_filters;
+    while(*bsfp)
+        bsfp= &(*bsfp)->next;
+
+    *bsfp= bsfc;
+}
+
+//FIXME avoid audio - video code duplication
+static void opt_audio_bsf(const char *arg)
+{
+    AVBitStreamFilterContext *bsfc= av_bitstream_filter_init(arg); //FIXME split name and args for filter at '='
+    AVBitStreamFilterContext **bsfp;
+
+    if(!bsfc){
+        fprintf(stderr, "Unkown bitstream filter %s\n", arg);
+        exit(1);
+    }
+
+    bsfp= &audio_bitstream_filters;
+    while(*bsfp)
+        bsfp= &(*bsfp)->next;
+
+    *bsfp= bsfc;
+}
+
 static void show_version(void)
 {
     /* TODO: add function interface to avutil and avformat */
@@ -3900,6 +3939,8 @@ static void show_version(void)
 
 static int opt_default(const char *opt, const char *arg){
     AVOption *o= av_set_string(avctx_opts, opt, arg);
+    if(!o)
+        o = av_set_string(avformat_opts, opt, arg);
     if(!o)
         return -1;
 
@@ -3909,9 +3950,11 @@ static int opt_default(const char *opt, const char *arg){
     opt_names= av_realloc(opt_names, sizeof(void*)*(opt_name_count+1));
     opt_names[opt_name_count++]= o->name;
 
+#if defined(CONFIG_FFM_DEMUXER) || defined(CONFIG_FFM_MUXER)
     /* disable generate of real time pts in ffm (need to be supressed anyway) */
     if(avctx_opts->flags & CODEC_FLAG_BITEXACT)
         ffm_nopts = 1;
+#endif
 
     if(avctx_opts->debug)
         av_log_set_level(AV_LOG_DEBUG);
@@ -3939,6 +3982,7 @@ const OptionDef options[] = {
     { "author", HAS_ARG | OPT_STRING, {(void*)&str_author}, "set the author", "string" },
     { "copyright", HAS_ARG | OPT_STRING, {(void*)&str_copyright}, "set the copyright", "string" },
     { "comment", HAS_ARG | OPT_STRING, {(void*)&str_comment}, "set the comment", "string" },
+    { "album", HAS_ARG | OPT_STRING, {(void*)&str_album}, "set the album", "string" },
     { "benchmark", OPT_BOOL | OPT_EXPERT, {(void*)&do_benchmark},
       "add timings for benchmarking" },
     { "dump", OPT_BOOL | OPT_EXPERT, {(void*)&do_pkt_dump},
@@ -3959,7 +4003,6 @@ const OptionDef options[] = {
     { "dts_delta_threshold", HAS_ARG | OPT_INT | OPT_EXPERT, {(void*)&dts_delta_threshold}, "timestamp discontinuity delta threshold", "" },
 
     /* video options */
-    { "b", HAS_ARG | OPT_VIDEO, {(void*)opt_video_bitrate}, "set video bitrate (in kbit/s)", "bitrate" },
     { "vframes", OPT_INT | HAS_ARG | OPT_VIDEO, {(void*)&max_frames[CODEC_TYPE_VIDEO]}, "set the number of video frames to record", "number" },
     { "aframes", OPT_INT | HAS_ARG | OPT_AUDIO, {(void*)&max_frames[CODEC_TYPE_AUDIO]}, "set the number of audio frames to record", "number" },
     { "dframes", OPT_INT | HAS_ARG, {(void*)&max_frames[CODEC_TYPE_DATA]}, "set the number of data frames to record", "number" },
@@ -4036,7 +4079,6 @@ const OptionDef options[] = {
     { "skip_factor", OPT_INT | HAS_ARG | OPT_EXPERT | OPT_VIDEO, {(void*)&frame_skip_factor}, "frame skip factor", "factor" },
     { "skip_exp", OPT_INT | HAS_ARG | OPT_EXPERT | OPT_VIDEO, {(void*)&frame_skip_exp}, "frame skip exponent", "exponent" },
     { "newvideo", OPT_VIDEO, {(void*)opt_new_video_stream}, "add a new video stream to the current output stream" },
-    { "genpts", OPT_BOOL | OPT_EXPERT | OPT_VIDEO, { (void *)&genpts }, "generate pts" },
     { "qphist", OPT_BOOL | OPT_EXPERT | OPT_VIDEO, { (void *)&qp_hist }, "show QP histogram" },
 
     /* audio options */
@@ -4071,6 +4113,10 @@ const OptionDef options[] = {
     { "packetsize", OPT_INT | HAS_ARG | OPT_EXPERT, {(void*)&mux_packet_size}, "set packet size", "size" },
     { "muxdelay", OPT_FLOAT | HAS_ARG | OPT_EXPERT, {(void*)&mux_max_delay}, "set the maximum demux-decode delay", "seconds" },
     { "muxpreload", OPT_FLOAT | HAS_ARG | OPT_EXPERT, {(void*)&mux_preload}, "set the initial demux-decode delay", "seconds" },
+
+    { "absf", HAS_ARG | OPT_AUDIO | OPT_EXPERT, {(void*)opt_audio_bsf}, "", "bitstream filter" },
+    { "vbsf", HAS_ARG | OPT_VIDEO | OPT_EXPERT, {(void*)opt_video_bsf}, "", "bitstream filter" },
+
     { "default", OPT_FUNC2 | HAS_ARG | OPT_AUDIO | OPT_VIDEO | OPT_EXPERT, {(void*)opt_default}, "generic catch all option", "" },
     { NULL, },
 };
@@ -4159,6 +4205,7 @@ static void show_help(void)
                       OPT_EXPERT | OPT_AUDIO | OPT_VIDEO | OPT_GRAB,
                       OPT_EXPERT);
     av_opt_show(avctx_opts, NULL);
+    av_opt_show(avformat_opts, NULL);
 
     exit(1);
 }
@@ -4176,6 +4223,7 @@ int main(int argc, char **argv)
     av_register_all();
 
     avctx_opts= avcodec_alloc_context();
+    avformat_opts = av_alloc_format_context();
 
     if (argc <= 1)
         show_help();
@@ -4230,7 +4278,7 @@ int main(int argc, char **argv)
     powerpc_display_perf_report();
 #endif /* POWERPC_PERFORMANCE_REPORT */
 
-#ifndef CONFIG_WIN32
+#ifndef __MINGW32__
     if (received_sigterm) {
         fprintf(stderr,
             "Received signal %d: terminating.\n",