mirror of
https://github.com/FFmpeg/FFmpeg.git
synced 2025-01-08 13:22:53 +02:00
Merge remote-tracking branch 'qatar/master'
* qatar/master: avconv: add presets rtsp: Expose the flag options via private AVOptions for sdp and rtp, too rtsp: Make the rtsp flags avoptions set via a define rtpenc: Set a default video codec avoptions: Fix av_opt_flag_is_set rtp: Fix ff_rtp_get_payload_type doc: Update the documentation on setting options for RTSP rtsp: Remove the separate filter_source variable rtsp: Accept options via private avoptions instead of URL options rtsp: Simplify AVOption definitions rtsp: Merge the AVOption lists lavfi: port libmpcodecs delogo filter lavfi: port boxblur filter from libmpcodecs lavfi: add negate filter lavfi: add LUT (LookUp Table) generic filters AVOptions: don't segfault on NULL parameter in av_set_options_string() avio: Check for invalid buffer length. mpegenc/mpegtsenc: add muxrate private options. lavf: deprecate AVFormatContext.file_size mov: add support for TV metadata atoms tves, tvsn and stik Conflicts: Changelog doc/filters.texi doc/protocols.texi libavfilter/Makefile libavfilter/allfilters.c libavfilter/avfilter.h libavfilter/formats.c libavfilter/internal.h libavfilter/vf_boxblur.c libavfilter/vf_delogo.c libavfilter/vf_lut.c libavformat/mpegtsenc.c libavformat/utils.c libavformat/version.h libavutil/opt.c Merged-by: Michael Niedermayer <michaelni@gmx.at>
This commit is contained in:
commit
fae714a9fb
77
avconv.c
77
avconv.c
@ -347,6 +347,8 @@ typedef struct OptionsContext {
|
||||
int nb_inter_matrices;
|
||||
SpecifierOpt *top_field_first;
|
||||
int nb_top_field_first;
|
||||
SpecifierOpt *presets;
|
||||
int nb_presets;
|
||||
#if CONFIG_AVFILTER
|
||||
SpecifierOpt *filters;
|
||||
int nb_filters;
|
||||
@ -3087,15 +3089,62 @@ static void parse_forced_key_frames(char *kf, OutputStream *ost,
|
||||
}
|
||||
}
|
||||
|
||||
static uint8_t *get_line(AVIOContext *s)
|
||||
{
|
||||
AVIOContext *line;
|
||||
uint8_t *buf;
|
||||
char c;
|
||||
|
||||
if (avio_open_dyn_buf(&line) < 0) {
|
||||
av_log(NULL, AV_LOG_FATAL, "Could not alloc buffer for reading preset.\n");
|
||||
exit_program(1);
|
||||
}
|
||||
|
||||
while ((c = avio_r8(s)) && c != '\n')
|
||||
avio_w8(line, c);
|
||||
avio_w8(line, 0);
|
||||
avio_close_dyn_buf(line, &buf);
|
||||
|
||||
return buf;
|
||||
}
|
||||
|
||||
static int get_preset_file_2(const char *preset_name, const char *codec_name, AVIOContext **s)
|
||||
{
|
||||
int i, ret = 1;
|
||||
char filename[1000];
|
||||
const char *base[3] = { getenv("AVCONV_DATADIR"),
|
||||
getenv("HOME"),
|
||||
AVCONV_DATADIR,
|
||||
};
|
||||
|
||||
for (i = 0; i < FF_ARRAY_ELEMS(base) && ret; i++) {
|
||||
if (!base[i])
|
||||
continue;
|
||||
if (codec_name) {
|
||||
snprintf(filename, sizeof(filename), "%s%s/%s-%s.avpreset", base[i],
|
||||
i != 1 ? "" : "/.avconv", codec_name, preset_name);
|
||||
ret = avio_open(s, filename, AVIO_FLAG_READ);
|
||||
}
|
||||
if (ret) {
|
||||
snprintf(filename, sizeof(filename), "%s%s/%s.avpreset", base[i],
|
||||
i != 1 ? "" : "/.avconv", preset_name);
|
||||
ret = avio_open(s, filename, AVIO_FLAG_READ);
|
||||
}
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
static OutputStream *new_output_stream(OptionsContext *o, AVFormatContext *oc, enum AVMediaType type)
|
||||
{
|
||||
OutputStream *ost;
|
||||
AVStream *st = av_new_stream(oc, oc->nb_streams < o->nb_streamid_map ? o->streamid_map[oc->nb_streams] : 0);
|
||||
int idx = oc->nb_streams - 1;
|
||||
int idx = oc->nb_streams - 1, ret = 0;
|
||||
int64_t max_frames = INT64_MAX;
|
||||
char *bsf = NULL, *next, *codec_tag = NULL;
|
||||
AVBitStreamFilterContext *bsfc, *bsfc_prev = NULL;
|
||||
double qscale = -1;
|
||||
char *buf = NULL, *arg = NULL, *preset = NULL;
|
||||
AVIOContext *s = NULL;
|
||||
|
||||
if (!st) {
|
||||
av_log(NULL, AV_LOG_FATAL, "Could not alloc stream.\n");
|
||||
@ -3117,6 +3166,31 @@ static OutputStream *new_output_stream(OptionsContext *o, AVFormatContext *oc, e
|
||||
avcodec_get_context_defaults3(st->codec, ost->enc);
|
||||
st->codec->codec_type = type; // XXX hack, avcodec_get_context_defaults2() sets type to unknown for stream copy
|
||||
|
||||
MATCH_PER_STREAM_OPT(presets, str, preset, oc, st);
|
||||
if (preset && (!(ret = get_preset_file_2(preset, ost->enc->name, &s)))) {
|
||||
do {
|
||||
buf = get_line(s);
|
||||
if (!buf[0] || buf[0] == '#') {
|
||||
av_free(buf);
|
||||
continue;
|
||||
}
|
||||
if (!(arg = strchr(buf, '='))) {
|
||||
av_log(NULL, AV_LOG_FATAL, "Invalid line found in the preset file.\n");
|
||||
exit_program(1);
|
||||
}
|
||||
*arg++ = 0;
|
||||
av_dict_set(&ost->opts, buf, arg, AV_DICT_DONT_OVERWRITE);
|
||||
av_free(buf);
|
||||
} while (!s->eof_reached);
|
||||
avio_close(s);
|
||||
}
|
||||
if (ret) {
|
||||
av_log(NULL, AV_LOG_FATAL,
|
||||
"Preset %s specified for stream %d:%d, but could not be opened.\n",
|
||||
preset, ost->file_index, ost->index);
|
||||
exit_program(1);
|
||||
}
|
||||
|
||||
MATCH_PER_STREAM_OPT(max_frames, i64, max_frames, oc, st);
|
||||
ost->max_frames = max_frames;
|
||||
|
||||
@ -4027,6 +4101,7 @@ static const OptionDef options[] = {
|
||||
{ "y", OPT_BOOL, {(void*)&file_overwrite}, "overwrite output files" },
|
||||
{ "c", HAS_ARG | OPT_STRING | OPT_SPEC, {.off = OFFSET(codec_names)}, "codec name", "codec" },
|
||||
{ "codec", HAS_ARG | OPT_STRING | OPT_SPEC, {.off = OFFSET(codec_names)}, "codec name", "codec" },
|
||||
{ "pre", HAS_ARG | OPT_STRING | OPT_SPEC, {.off = OFFSET(presets)}, "preset name", "preset" },
|
||||
{ "map", HAS_ARG | OPT_EXPERT | OPT_FUNC2, {(void*)opt_map}, "set input stream mapping", "file.stream[:syncfile.syncstream]" },
|
||||
{ "map_metadata", HAS_ARG | OPT_EXPERT | OPT_FUNC2, {(void*)opt_map_metadata}, "set metadata information of outfile from infile",
|
||||
"outfile[,metadata]:infile[,metadata]" },
|
||||
|
@ -186,6 +186,8 @@ codec-dependent.
|
||||
@var{filter_graph} is a description of the filter graph to apply to
|
||||
the stream. Use @code{-filters} to show all the available filters
|
||||
(including also sources and sinks).
|
||||
@item -pre[:@var{stream_specifier}] @var{preset_name} (@emph{output,per-stream})
|
||||
Specify the preset for matching stream(s).
|
||||
|
||||
@item -stats (@emph{global})
|
||||
Print encoding progress/statistics. On by default.
|
||||
@ -770,6 +772,21 @@ quality).
|
||||
@chapter Examples
|
||||
@c man begin EXAMPLES
|
||||
|
||||
@section Preset files
|
||||
|
||||
A preset file contains a sequence of @var{option=value} pairs, one for
|
||||
each line, specifying a sequence of options which can be specified also on
|
||||
the command line. Lines starting with the hash ('#') character are ignored and
|
||||
are used to provide comments. Empty lines are also ignored. Check the
|
||||
@file{ffpresets} directory in the Libav source tree for examples.
|
||||
|
||||
Preset files are specified with the @code{pre} option, this option takes a
|
||||
preset name as input. Avconv searches for a file named @var{preset_name}.avpreset in
|
||||
the directories @file{$AVCONV_DATADIR} (if set), and @file{$HOME/.avconv}, and in
|
||||
the data directory defined at configuration time (usually @file{$PREFIX/share/avconv})
|
||||
in that order. For example, if the argument is @code{libx264-max}, it will
|
||||
search for the file @file{libx264-max.avpreset}.
|
||||
|
||||
@section Video and Audio grabbing
|
||||
|
||||
If you specify the input format and device then avconv can grab video
|
||||
|
@ -432,7 +432,7 @@ horizontal and vertical chroma subsample values. For example for the
|
||||
pixel format "yuv422p" @var{hsub} is 2 and @var{vsub} is 1.
|
||||
@end table
|
||||
|
||||
The radius must be a non-negative number, and must be not greater than
|
||||
The radius must be a non-negative number, and must not be greater than
|
||||
the value of the expression @code{min(w,h)/2} for the luma and alpha planes,
|
||||
and of @code{min(cw,ch)/2} for the chroma planes.
|
||||
|
||||
|
@ -246,12 +246,15 @@ supporting it (currently Darwin Streaming Server and Mischa Spiegelmock's
|
||||
|
||||
The required syntax for a RTSP url is:
|
||||
@example
|
||||
rtsp://@var{hostname}[:@var{port}]/@var{path}[?@var{options}]
|
||||
rtsp://@var{hostname}[:@var{port}]/@var{path}
|
||||
@end example
|
||||
|
||||
@var{options} is a @code{&}-separated list. The following options
|
||||
The following options (set on the @file{ffmpeg}/@file{ffplay} command
|
||||
line, or set in code via @code{AVOption}s or in @code{avformat_open_input}),
|
||||
are supported:
|
||||
|
||||
Flags for @code{rtsp_transport}:
|
||||
|
||||
@table @option
|
||||
|
||||
@item udp
|
||||
@ -261,21 +264,25 @@ Use UDP as lower transport protocol.
|
||||
Use TCP (interleaving within the RTSP control channel) as lower
|
||||
transport protocol.
|
||||
|
||||
@item multicast
|
||||
@item udp_multicast
|
||||
Use UDP multicast as lower transport protocol.
|
||||
|
||||
@item http
|
||||
Use HTTP tunneling as lower transport protocol, which is useful for
|
||||
passing proxies.
|
||||
|
||||
@item filter_src
|
||||
Accept packets only from negotiated peer address and port.
|
||||
@end table
|
||||
|
||||
Multiple lower transport protocols may be specified, in that case they are
|
||||
tried one at a time (if the setup of one fails, the next one is tried).
|
||||
For the muxer, only the @code{tcp} and @code{udp} options are supported.
|
||||
|
||||
Flags for @code{rtsp_flags}:
|
||||
|
||||
@table @option
|
||||
@item filter_src
|
||||
Accept packets only from negotiated peer address and port.
|
||||
@end table
|
||||
|
||||
When receiving data over UDP, the demuxer tries to reorder received packets
|
||||
(since they may arrive out of order, or packets may get lost totally). In
|
||||
order for this to be enabled, a maximum delay must be specified in the
|
||||
@ -291,13 +298,13 @@ Example command lines:
|
||||
To watch a stream over UDP, with a max reordering delay of 0.5 seconds:
|
||||
|
||||
@example
|
||||
ffplay -max_delay 500000 rtsp://server/video.mp4?udp
|
||||
ffplay -max_delay 500000 -rtsp_transport udp rtsp://server/video.mp4
|
||||
@end example
|
||||
|
||||
To watch a stream tunneled over HTTP:
|
||||
|
||||
@example
|
||||
ffplay rtsp://server/video.mp4?http
|
||||
ffplay -rtsp_transport http rtsp://server/video.mp4
|
||||
@end example
|
||||
|
||||
To send a stream in realtime to a RTSP server, for others to watch:
|
||||
|
77
ffmpeg.c
77
ffmpeg.c
@ -355,6 +355,8 @@ typedef struct OptionsContext {
|
||||
int nb_inter_matrices;
|
||||
SpecifierOpt *top_field_first;
|
||||
int nb_top_field_first;
|
||||
SpecifierOpt *presets;
|
||||
int nb_presets;
|
||||
#if CONFIG_AVFILTER
|
||||
SpecifierOpt *filters;
|
||||
int nb_filters;
|
||||
@ -3202,15 +3204,62 @@ static void parse_forced_key_frames(char *kf, OutputStream *ost)
|
||||
}
|
||||
}
|
||||
|
||||
static uint8_t *get_line(AVIOContext *s)
|
||||
{
|
||||
AVIOContext *line;
|
||||
uint8_t *buf;
|
||||
char c;
|
||||
|
||||
if (avio_open_dyn_buf(&line) < 0) {
|
||||
av_log(NULL, AV_LOG_FATAL, "Could not alloc buffer for reading preset.\n");
|
||||
exit_program(1);
|
||||
}
|
||||
|
||||
while ((c = avio_r8(s)) && c != '\n')
|
||||
avio_w8(line, c);
|
||||
avio_w8(line, 0);
|
||||
avio_close_dyn_buf(line, &buf);
|
||||
|
||||
return buf;
|
||||
}
|
||||
|
||||
static int get_preset_file_2(const char *preset_name, const char *codec_name, AVIOContext **s)
|
||||
{
|
||||
int i, ret = 1;
|
||||
char filename[1000];
|
||||
const char *base[3] = { getenv("AVCONV_DATADIR"),
|
||||
getenv("HOME"),
|
||||
AVCONV_DATADIR,
|
||||
};
|
||||
|
||||
for (i = 0; i < FF_ARRAY_ELEMS(base) && ret; i++) {
|
||||
if (!base[i])
|
||||
continue;
|
||||
if (codec_name) {
|
||||
snprintf(filename, sizeof(filename), "%s%s/%s-%s.avpreset", base[i],
|
||||
i != 1 ? "" : "/.avconv", codec_name, preset_name);
|
||||
ret = avio_open(s, filename, AVIO_FLAG_READ);
|
||||
}
|
||||
if (ret) {
|
||||
snprintf(filename, sizeof(filename), "%s%s/%s.avpreset", base[i],
|
||||
i != 1 ? "" : "/.avconv", preset_name);
|
||||
ret = avio_open(s, filename, AVIO_FLAG_READ);
|
||||
}
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
static OutputStream *new_output_stream(OptionsContext *o, AVFormatContext *oc, enum AVMediaType type)
|
||||
{
|
||||
OutputStream *ost;
|
||||
AVStream *st = av_new_stream(oc, oc->nb_streams < o->nb_streamid_map ? o->streamid_map[oc->nb_streams] : 0);
|
||||
int idx = oc->nb_streams - 1;
|
||||
int idx = oc->nb_streams - 1, ret = 0;
|
||||
int64_t max_frames = INT64_MAX;
|
||||
char *bsf = NULL, *next, *codec_tag = NULL;
|
||||
AVBitStreamFilterContext *bsfc, *bsfc_prev = NULL;
|
||||
double qscale = -1;
|
||||
char *buf = NULL, *arg = NULL, *preset = NULL;
|
||||
AVIOContext *s = NULL;
|
||||
|
||||
if (!st) {
|
||||
av_log(NULL, AV_LOG_FATAL, "Could not alloc stream.\n");
|
||||
@ -3232,6 +3281,31 @@ static OutputStream *new_output_stream(OptionsContext *o, AVFormatContext *oc, e
|
||||
avcodec_get_context_defaults3(st->codec, ost->enc);
|
||||
st->codec->codec_type = type; // XXX hack, avcodec_get_context_defaults2() sets type to unknown for stream copy
|
||||
|
||||
MATCH_PER_STREAM_OPT(presets, str, preset, oc, st);
|
||||
if (preset && (!(ret = get_preset_file_2(preset, ost->enc->name, &s)))) {
|
||||
do {
|
||||
buf = get_line(s);
|
||||
if (!buf[0] || buf[0] == '#') {
|
||||
av_free(buf);
|
||||
continue;
|
||||
}
|
||||
if (!(arg = strchr(buf, '='))) {
|
||||
av_log(NULL, AV_LOG_FATAL, "Invalid line found in the preset file.\n");
|
||||
exit_program(1);
|
||||
}
|
||||
*arg++ = 0;
|
||||
av_dict_set(&ost->opts, buf, arg, AV_DICT_DONT_OVERWRITE);
|
||||
av_free(buf);
|
||||
} while (!s->eof_reached);
|
||||
avio_close(s);
|
||||
}
|
||||
if (ret) {
|
||||
av_log(NULL, AV_LOG_FATAL,
|
||||
"Preset %s specified for stream %d:%d, but could not be opened.\n",
|
||||
preset, ost->file_index, ost->index);
|
||||
exit_program(1);
|
||||
}
|
||||
|
||||
MATCH_PER_STREAM_OPT(max_frames, i64, max_frames, oc, st);
|
||||
ost->max_frames = max_frames;
|
||||
|
||||
@ -4209,6 +4283,7 @@ static const OptionDef options[] = {
|
||||
{ "y", OPT_BOOL, {(void*)&file_overwrite}, "overwrite output files" },
|
||||
{ "c", HAS_ARG | OPT_STRING | OPT_SPEC, {.off = OFFSET(codec_names)}, "codec name", "codec" },
|
||||
{ "codec", HAS_ARG | OPT_STRING | OPT_SPEC, {.off = OFFSET(codec_names)}, "codec name", "codec" },
|
||||
{ "pre", HAS_ARG | OPT_STRING | OPT_SPEC, {.off = OFFSET(presets)}, "preset name", "preset" },
|
||||
{ "map", HAS_ARG | OPT_EXPERT | OPT_FUNC2, {(void*)opt_map}, "set input stream mapping", "file.stream[:syncfile.syncstream]" },
|
||||
{ "map_meta_data", HAS_ARG | OPT_EXPERT | OPT_FUNC2, {(void*)opt_map_meta_data}, "DEPRECATED set meta data information of outfile from infile",
|
||||
"outfile[,metadata]:infile[,metadata]" },
|
||||
|
@ -30,7 +30,7 @@
|
||||
|
||||
#define LIBAVFILTER_VERSION_MAJOR 2
|
||||
#define LIBAVFILTER_VERSION_MINOR 43
|
||||
#define LIBAVFILTER_VERSION_MICRO 6
|
||||
#define LIBAVFILTER_VERSION_MICRO 7
|
||||
|
||||
#define LIBAVFILTER_VERSION_INT AV_VERSION_INT(LIBAVFILTER_VERSION_MAJOR, \
|
||||
LIBAVFILTER_VERSION_MINOR, \
|
||||
|
@ -81,7 +81,7 @@ static av_cold int init(AVFilterContext *ctx, const char *args, void *opaque)
|
||||
|
||||
if (!args) {
|
||||
av_log(ctx, AV_LOG_ERROR,
|
||||
"Filter expects 2 or 4 arguments, none provided\n");
|
||||
"Filter expects 2 or 4 or 6 arguments, none provided\n");
|
||||
return AVERROR(EINVAL);
|
||||
}
|
||||
|
||||
@ -342,4 +342,4 @@ AVFilter avfilter_vf_boxblur = {
|
||||
.outputs = (AVFilterPad[]) {{ .name = "default",
|
||||
.type = AVMEDIA_TYPE_VIDEO, },
|
||||
{ .name = NULL}},
|
||||
};
|
||||
};
|
@ -154,9 +154,9 @@ static const char *delogo_get_name(void *ctx)
|
||||
}
|
||||
|
||||
static const AVClass delogo_class = {
|
||||
"DelogoContext",
|
||||
delogo_get_name,
|
||||
delogo_options
|
||||
.class_name = "DelogoContext",
|
||||
.item_name = delogo_get_name,
|
||||
.option = delogo_options,
|
||||
};
|
||||
|
||||
static int query_formats(AVFilterContext *ctx)
|
||||
@ -285,4 +285,4 @@ AVFilter avfilter_vf_delogo = {
|
||||
.outputs = (AVFilterPad[]) {{ .name = "default",
|
||||
.type = AVMEDIA_TYPE_VIDEO, },
|
||||
{ .name = NULL}},
|
||||
};
|
||||
};
|
@ -350,21 +350,27 @@ static void draw_slice(AVFilterLink *inlink, int y, int h, int slice_dir)
|
||||
{ .name = NULL}}, \
|
||||
}
|
||||
|
||||
#if CONFIG_LUT_FILTER
|
||||
DEFINE_LUT_FILTER(lut, "Compute and apply a lookup table to the RGB/YUV input video.", init);
|
||||
#endif
|
||||
#if CONFIG_LUTYUV_FILTER
|
||||
DEFINE_LUT_FILTER(lutyuv, "Compute and apply a lookup table to the YUV input video.", init);
|
||||
#endif
|
||||
#if CONFIG_LUTRGB_FILTER
|
||||
DEFINE_LUT_FILTER(lutrgb, "Compute and apply a lookup table to the RGB input video.", init);
|
||||
#endif
|
||||
|
||||
#if CONFIG_NEGATE_FILTER
|
||||
|
||||
static int negate_init(AVFilterContext *ctx, const char *args, void *opaque)
|
||||
{
|
||||
LutContext *lut = ctx->priv;
|
||||
char lut_params[1024];
|
||||
char lut_params[64];
|
||||
|
||||
if (args)
|
||||
sscanf(args, "%d", &lut->negate_alpha);
|
||||
|
||||
av_log(ctx, AV_LOG_INFO, "negate_alpha:%d\n", lut->negate_alpha);
|
||||
av_log(ctx, AV_LOG_DEBUG, "negate_alpha:%d\n", lut->negate_alpha);
|
||||
|
||||
snprintf(lut_params, sizeof(lut_params), "c0=negval:c1=negval:c2=negval:a=%s",
|
||||
lut->negate_alpha ? "negval" : "val");
|
||||
@ -374,4 +380,4 @@ static int negate_init(AVFilterContext *ctx, const char *args, void *opaque)
|
||||
|
||||
DEFINE_LUT_FILTER(negate, "Negate input video.", negate_init);
|
||||
|
||||
#endif
|
||||
#endif
|
@ -275,9 +275,6 @@ static int aiff_read_header(AVFormatContext *s,
|
||||
|
||||
got_sound:
|
||||
/* Now positioned, get the sound data start and end */
|
||||
if (st->nb_frames)
|
||||
s->file_size = st->nb_frames * st->codec->block_align;
|
||||
|
||||
av_set_pts_info(st, 64, 1, st->codec->sample_rate);
|
||||
st->start_time = 0;
|
||||
st->duration = st->codec->frame_size ?
|
||||
|
@ -745,10 +745,12 @@ typedef struct AVFormatContext {
|
||||
*/
|
||||
int64_t duration;
|
||||
|
||||
#if FF_API_FILESIZE
|
||||
/**
|
||||
* decoding: total file size, 0 if unknown
|
||||
*/
|
||||
int64_t file_size;
|
||||
attribute_deprecated int64_t file_size;
|
||||
#endif
|
||||
|
||||
/**
|
||||
* Decoding: total stream bitrate in bit/s, 0 if not
|
||||
@ -763,7 +765,12 @@ typedef struct AVFormatContext {
|
||||
/* av_seek_frame() support */
|
||||
int64_t data_offset; /**< offset of the first packet */
|
||||
|
||||
int mux_rate;
|
||||
#if FF_API_MUXRATE
|
||||
/**
|
||||
* use mpeg muxer private options instead
|
||||
*/
|
||||
attribute_deprecated int mux_rate;
|
||||
#endif
|
||||
unsigned int packet_size;
|
||||
int preload;
|
||||
int max_delay;
|
||||
|
@ -778,13 +778,14 @@ int avio_get_str(AVIOContext *s, int maxlen, char *buf, int buflen)
|
||||
{
|
||||
int i;
|
||||
|
||||
if (buflen <= 0)
|
||||
return AVERROR(EINVAL);
|
||||
// reserve 1 byte for terminating 0
|
||||
buflen = FFMIN(buflen - 1, maxlen);
|
||||
for (i = 0; i < buflen; i++)
|
||||
if (!(buf[i] = avio_r8(s)))
|
||||
return i + 1;
|
||||
if (buflen)
|
||||
buf[i] = 0;
|
||||
buf[i] = 0;
|
||||
for (; i < maxlen; i++)
|
||||
if (!avio_r8(s))
|
||||
return i + 1;
|
||||
@ -796,6 +797,8 @@ int avio_get_str(AVIOContext *s, int maxlen, char *buf, int buflen)
|
||||
{\
|
||||
char* q = buf;\
|
||||
int ret = 0;\
|
||||
if (buflen <= 0) \
|
||||
return AVERROR(EINVAL); \
|
||||
while (ret + 1 < maxlen) {\
|
||||
uint8_t tmp;\
|
||||
uint32_t ch;\
|
||||
|
@ -292,8 +292,6 @@ static int read_header(AVFormatContext *s,
|
||||
"block size or frame size are variable.\n");
|
||||
return AVERROR_INVALIDDATA;
|
||||
}
|
||||
s->file_size = avio_size(pb);
|
||||
s->file_size = FFMAX(0, s->file_size);
|
||||
|
||||
av_set_pts_info(st, 64, 1, st->codec->sample_rate);
|
||||
st->start_time = 0;
|
||||
|
@ -99,6 +99,33 @@ static int mov_metadata_track_or_disc_number(MOVContext *c, AVIOContext *pb,
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int mov_metadata_int8(MOVContext *c, AVIOContext *pb,
|
||||
unsigned len, const char *key)
|
||||
{
|
||||
char buf[16];
|
||||
|
||||
/* bypass padding bytes */
|
||||
avio_r8(pb);
|
||||
avio_r8(pb);
|
||||
avio_r8(pb);
|
||||
|
||||
snprintf(buf, sizeof(buf), "%hu", avio_r8(pb));
|
||||
av_dict_set(&c->fc->metadata, key, buf, 0);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int mov_metadata_stik(MOVContext *c, AVIOContext *pb,
|
||||
unsigned len, const char *key)
|
||||
{
|
||||
char buf[16];
|
||||
|
||||
snprintf(buf, sizeof(buf), "%hu", avio_r8(pb));
|
||||
av_dict_set(&c->fc->metadata, key, buf, 0);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static const uint32_t mac_to_unicode[128] = {
|
||||
0x00C4,0x00C5,0x00C7,0x00C9,0x00D1,0x00D6,0x00DC,0x00E1,
|
||||
0x00E0,0x00E2,0x00E4,0x00E3,0x00E5,0x00E7,0x00E9,0x00E8,
|
||||
@ -174,6 +201,12 @@ static int mov_read_udta_string(MOVContext *c, AVIOContext *pb, MOVAtom atom)
|
||||
parse = mov_metadata_track_or_disc_number; break;
|
||||
case MKTAG( 'd','i','s','k'): key = "disc";
|
||||
parse = mov_metadata_track_or_disc_number; break;
|
||||
case MKTAG( 't','v','e','s'): key = "episode_sort";
|
||||
parse = mov_metadata_int8; break;
|
||||
case MKTAG( 't','v','s','n'): key = "season_number";
|
||||
parse = mov_metadata_int8; break;
|
||||
case MKTAG( 's','t','i','k'): key = "media_type";
|
||||
parse = mov_metadata_stik; break;
|
||||
}
|
||||
|
||||
if (c->itunes_metadata && atom.size > 8) {
|
||||
|
@ -20,7 +20,9 @@
|
||||
*/
|
||||
|
||||
#include "libavutil/fifo.h"
|
||||
#include "libavutil/log.h"
|
||||
#include "libavutil/mathematics.h"
|
||||
#include "libavutil/opt.h"
|
||||
#include "libavcodec/put_bits.h"
|
||||
#include "avformat.h"
|
||||
#include "mpeg.h"
|
||||
@ -56,6 +58,7 @@ typedef struct {
|
||||
} StreamInfo;
|
||||
|
||||
typedef struct {
|
||||
const AVClass *class;
|
||||
int packet_size; /* required packet size */
|
||||
int packet_number;
|
||||
int pack_header_freq; /* frequency (in packets^-1) at which we send pack headers */
|
||||
@ -416,9 +419,12 @@ static int mpeg_mux_init(AVFormatContext *ctx)
|
||||
video_bitrate += codec_rate;
|
||||
}
|
||||
|
||||
#if FF_API_MUXRATE
|
||||
if(ctx->mux_rate){
|
||||
s->mux_rate= (ctx->mux_rate + (8 * 50) - 1) / (8 * 50);
|
||||
} else {
|
||||
} else
|
||||
#endif
|
||||
if (!s->mux_rate) {
|
||||
/* we increase slightly the bitrate to take into account the
|
||||
headers. XXX: compute it exactly */
|
||||
bitrate += bitrate*5/100;
|
||||
@ -1227,7 +1233,23 @@ static int mpeg_mux_end(AVFormatContext *ctx)
|
||||
return 0;
|
||||
}
|
||||
|
||||
#define OFFSET(x) offsetof(MpegMuxContext, x)
|
||||
#define E AV_OPT_FLAG_ENCODING_PARAM
|
||||
static const AVOption options[] = {
|
||||
{ "muxrate", NULL, OFFSET(mux_rate), AV_OPT_TYPE_INT, {0}, 0, INT_MAX, E },
|
||||
{ NULL },
|
||||
};
|
||||
|
||||
#define MPEGENC_CLASS(flavor)\
|
||||
static const AVClass flavor ## _class = {\
|
||||
.class_name = #flavor " muxer",\
|
||||
.item_name = av_default_item_name,\
|
||||
.version = LIBAVUTIL_VERSION_INT,\
|
||||
.option = options,\
|
||||
};
|
||||
|
||||
#if CONFIG_MPEG1SYSTEM_MUXER
|
||||
MPEGENC_CLASS(mpeg)
|
||||
AVOutputFormat ff_mpeg1system_muxer = {
|
||||
.name = "mpeg",
|
||||
.long_name = NULL_IF_CONFIG_SMALL("MPEG-1 System format"),
|
||||
@ -1239,9 +1261,11 @@ AVOutputFormat ff_mpeg1system_muxer = {
|
||||
.write_header = mpeg_mux_init,
|
||||
.write_packet = mpeg_mux_write_packet,
|
||||
.write_trailer = mpeg_mux_end,
|
||||
.priv_class = &mpeg_class,
|
||||
};
|
||||
#endif
|
||||
#if CONFIG_MPEG1VCD_MUXER
|
||||
MPEGENC_CLASS(vcd)
|
||||
AVOutputFormat ff_mpeg1vcd_muxer = {
|
||||
.name = "vcd",
|
||||
.long_name = NULL_IF_CONFIG_SMALL("MPEG-1 System format (VCD)"),
|
||||
@ -1252,9 +1276,11 @@ AVOutputFormat ff_mpeg1vcd_muxer = {
|
||||
.write_header = mpeg_mux_init,
|
||||
.write_packet = mpeg_mux_write_packet,
|
||||
.write_trailer = mpeg_mux_end,
|
||||
.priv_class = &vcd_class,
|
||||
};
|
||||
#endif
|
||||
#if CONFIG_MPEG2VOB_MUXER
|
||||
MPEGENC_CLASS(vob)
|
||||
AVOutputFormat ff_mpeg2vob_muxer = {
|
||||
.name = "vob",
|
||||
.long_name = NULL_IF_CONFIG_SMALL("MPEG-2 PS format (VOB)"),
|
||||
@ -1266,11 +1292,13 @@ AVOutputFormat ff_mpeg2vob_muxer = {
|
||||
.write_header = mpeg_mux_init,
|
||||
.write_packet = mpeg_mux_write_packet,
|
||||
.write_trailer = mpeg_mux_end,
|
||||
.priv_class = &vob_class,
|
||||
};
|
||||
#endif
|
||||
|
||||
/* Same as mpeg2vob_mux except that the pack size is 2324 */
|
||||
#if CONFIG_MPEG2SVCD_MUXER
|
||||
MPEGENC_CLASS(svcd)
|
||||
AVOutputFormat ff_mpeg2svcd_muxer = {
|
||||
.name = "svcd",
|
||||
.long_name = NULL_IF_CONFIG_SMALL("MPEG-2 PS format (VOB)"),
|
||||
@ -1282,11 +1310,13 @@ AVOutputFormat ff_mpeg2svcd_muxer = {
|
||||
.write_header = mpeg_mux_init,
|
||||
.write_packet = mpeg_mux_write_packet,
|
||||
.write_trailer = mpeg_mux_end,
|
||||
.priv_class = &svcd_class,
|
||||
};
|
||||
#endif
|
||||
|
||||
/* Same as mpeg2vob_mux except the 'is_dvd' flag is set to produce NAV pkts */
|
||||
#if CONFIG_MPEG2DVD_MUXER
|
||||
MPEGENC_CLASS(dvd)
|
||||
AVOutputFormat ff_mpeg2dvd_muxer = {
|
||||
.name = "dvd",
|
||||
.long_name = NULL_IF_CONFIG_SMALL("MPEG-2 PS format (DVD VOB)"),
|
||||
@ -1298,5 +1328,6 @@ AVOutputFormat ff_mpeg2dvd_muxer = {
|
||||
.write_header = mpeg_mux_init,
|
||||
.write_packet = mpeg_mux_write_packet,
|
||||
.write_trailer = mpeg_mux_end,
|
||||
.priv_class = &dvd_class,
|
||||
};
|
||||
#endif
|
||||
|
@ -92,6 +92,7 @@ static const AVOption options[] = {
|
||||
{"mpegts_m2ts_mode", "Enable m2ts mode.",
|
||||
offsetof(MpegTSWrite, m2ts_mode), AV_OPT_TYPE_INT, {.dbl = -1 },
|
||||
-1,1, AV_OPT_FLAG_ENCODING_PARAM},
|
||||
{ "muxrate", NULL, offsetof(MpegTSWrite, mux_rate), AV_OPT_TYPE_INT, {1}, 0, INT_MAX, AV_OPT_FLAG_ENCODING_PARAM},
|
||||
{ NULL },
|
||||
};
|
||||
|
||||
@ -562,7 +563,10 @@ static int mpegts_write_header(AVFormatContext *s)
|
||||
service->pcr_pid = ts_st->pid;
|
||||
}
|
||||
|
||||
ts->mux_rate = s->mux_rate ? s->mux_rate : 1;
|
||||
#if FF_API_MUXRATE
|
||||
if (s->mux_rate)
|
||||
ts->mux_rate = s->mux_rate;
|
||||
#endif
|
||||
|
||||
if (ts->mux_rate > 1) {
|
||||
service->pcr_packet_period = (ts->mux_rate * PCR_RETRANS_TIME) /
|
||||
|
@ -74,7 +74,9 @@ static const AVClass *format_child_class_next(const AVClass *prev)
|
||||
|
||||
static const AVOption options[]={
|
||||
{"probesize", "set probing size", OFFSET(probesize), AV_OPT_TYPE_INT, {.dbl = 5000000 }, 32, INT_MAX, D},
|
||||
#if FF_API_MUXRATE
|
||||
{"muxrate", "set mux rate", OFFSET(mux_rate), AV_OPT_TYPE_INT, {.dbl = DEFAULT }, 0, INT_MAX, E},
|
||||
#endif
|
||||
{"packetsize", "set packet size", OFFSET(packet_size), AV_OPT_TYPE_INT, {.dbl = DEFAULT }, 0, INT_MAX, E},
|
||||
{"fflags", NULL, OFFSET(flags), AV_OPT_TYPE_FLAGS, {.dbl = DEFAULT }, INT_MIN, INT_MAX, D|E, "fflags"},
|
||||
{"ignidx", "ignore index", 0, AV_OPT_TYPE_CONST, {.dbl = AVFMT_FLAG_IGNIDX }, INT_MIN, INT_MAX, D, "fflags"},
|
||||
|
@ -92,8 +92,7 @@ static int qcp_read_header(AVFormatContext *s, AVFormatParameters *ap)
|
||||
return AVERROR(ENOMEM);
|
||||
|
||||
avio_rb32(pb); // "RIFF"
|
||||
s->file_size = avio_rl32(pb) + 8;
|
||||
avio_skip(pb, 8 + 4 + 1 + 1); // "QLCMfmt " + chunk-size + major-version + minor-version
|
||||
avio_skip(pb, 4 + 8 + 4 + 1 + 1); // filesize + "QLCMfmt " + chunk-size + major-version + minor-version
|
||||
|
||||
st->codec->codec_type = AVMEDIA_TYPE_AUDIO;
|
||||
st->codec->channels = 1;
|
||||
|
@ -98,7 +98,8 @@ int ff_rtp_get_payload_type(AVFormatContext *fmt, AVCodecContext *codec)
|
||||
/* Was the payload type already specified for the RTP muxer? */
|
||||
if (ofmt && ofmt->priv_class) {
|
||||
int64_t payload_type;
|
||||
if (av_opt_get_int(fmt->priv_data, "payload_type", 0, &payload_type) >= 0)
|
||||
if (av_opt_get_int(fmt->priv_data, "payload_type", 0, &payload_type) >= 0 &&
|
||||
payload_type >= 0)
|
||||
return (int)payload_type;
|
||||
}
|
||||
|
||||
|
@ -465,7 +465,7 @@ AVOutputFormat ff_rtp_muxer = {
|
||||
.long_name = NULL_IF_CONFIG_SMALL("RTP output format"),
|
||||
.priv_data_size = sizeof(RTPMuxContext),
|
||||
.audio_codec = CODEC_ID_PCM_MULAW,
|
||||
.video_codec = CODEC_ID_NONE,
|
||||
.video_codec = CODEC_ID_MPEG4,
|
||||
.write_header = rtp_write_header,
|
||||
.write_packet = rtp_write_packet,
|
||||
.write_trailer = rtp_write_trailer,
|
||||
|
@ -45,6 +45,7 @@
|
||||
#include "rtpdec_formats.h"
|
||||
#include "rtpenc_chain.h"
|
||||
#include "url.h"
|
||||
#include "rtpenc.h"
|
||||
|
||||
//#define DEBUG
|
||||
|
||||
@ -56,6 +57,36 @@
|
||||
#define SDP_MAX_SIZE 16384
|
||||
#define RECVBUF_SIZE 10 * RTP_MAX_PACKET_LENGTH
|
||||
|
||||
#define OFFSET(x) offsetof(RTSPState, x)
|
||||
#define DEC AV_OPT_FLAG_DECODING_PARAM
|
||||
#define ENC AV_OPT_FLAG_ENCODING_PARAM
|
||||
|
||||
#define RTSP_FLAG_OPTS(name, longname) \
|
||||
{ name, longname, OFFSET(rtsp_flags), AV_OPT_TYPE_FLAGS, {0}, INT_MIN, INT_MAX, DEC, "rtsp_flags" }, \
|
||||
{ "filter_src", "Only receive packets from the negotiated peer IP", 0, AV_OPT_TYPE_CONST, {RTSP_FLAG_FILTER_SRC}, 0, 0, DEC, "rtsp_flags" }
|
||||
|
||||
const AVOption ff_rtsp_options[] = {
|
||||
{ "initial_pause", "Don't start playing the stream immediately", OFFSET(initial_pause), AV_OPT_TYPE_INT, {0}, 0, 1, DEC },
|
||||
FF_RTP_FLAG_OPTS(RTSPState, rtp_muxer_flags),
|
||||
{ "rtsp_transport", "RTSP transport protocols", OFFSET(lower_transport_mask), AV_OPT_TYPE_FLAGS, {0}, INT_MIN, INT_MAX, DEC|ENC, "rtsp_transport" }, \
|
||||
{ "udp", "UDP", 0, AV_OPT_TYPE_CONST, {1 << RTSP_LOWER_TRANSPORT_UDP}, 0, 0, DEC|ENC, "rtsp_transport" }, \
|
||||
{ "tcp", "TCP", 0, AV_OPT_TYPE_CONST, {1 << RTSP_LOWER_TRANSPORT_TCP}, 0, 0, DEC|ENC, "rtsp_transport" }, \
|
||||
{ "udp_multicast", "UDP multicast", 0, AV_OPT_TYPE_CONST, {1 << RTSP_LOWER_TRANSPORT_UDP_MULTICAST}, 0, 0, DEC, "rtsp_transport" },
|
||||
{ "http", "HTTP tunneling", 0, AV_OPT_TYPE_CONST, {(1 << RTSP_LOWER_TRANSPORT_HTTP)}, 0, 0, DEC, "rtsp_transport" },
|
||||
RTSP_FLAG_OPTS("rtsp_flags", "RTSP flags"),
|
||||
{ NULL },
|
||||
};
|
||||
|
||||
static const AVOption sdp_options[] = {
|
||||
RTSP_FLAG_OPTS("sdp_flags", "SDP flags"),
|
||||
{ NULL },
|
||||
};
|
||||
|
||||
static const AVOption rtp_options[] = {
|
||||
RTSP_FLAG_OPTS("rtp_flags", "RTP flags"),
|
||||
{ NULL },
|
||||
};
|
||||
|
||||
static void get_word_until_chars(char *buf, int buf_size,
|
||||
const char *sep, const char **pp)
|
||||
{
|
||||
@ -1218,7 +1249,7 @@ int ff_rtsp_make_setup_request(AVFormatContext *s, const char *host, int port,
|
||||
case RTSP_LOWER_TRANSPORT_UDP: {
|
||||
char url[1024], options[30] = "";
|
||||
|
||||
if (rt->filter_source)
|
||||
if (rt->rtsp_flags & RTSP_FLAG_FILTER_SRC)
|
||||
av_strlcpy(options, "?connect=1", sizeof(options));
|
||||
/* Use source address if specified */
|
||||
if (reply->transports[0].source[0]) {
|
||||
@ -1308,8 +1339,17 @@ int ff_rtsp_connect(AVFormatContext *s)
|
||||
|
||||
if (!ff_network_init())
|
||||
return AVERROR(EIO);
|
||||
redirect:
|
||||
|
||||
rt->control_transport = RTSP_MODE_PLAIN;
|
||||
if (rt->lower_transport_mask & (1 << RTSP_LOWER_TRANSPORT_HTTP)) {
|
||||
rt->lower_transport_mask = 1 << RTSP_LOWER_TRANSPORT_TCP;
|
||||
rt->control_transport = RTSP_MODE_TUNNEL;
|
||||
}
|
||||
/* Only pass through valid flags from here */
|
||||
rt->lower_transport_mask &= (1 << RTSP_LOWER_TRANSPORT_NB) - 1;
|
||||
|
||||
redirect:
|
||||
lower_transport_mask = rt->lower_transport_mask;
|
||||
/* extract hostname and port */
|
||||
av_url_split(NULL, 0, auth, sizeof(auth),
|
||||
host, sizeof(host), &port, path, sizeof(path), s->filename);
|
||||
@ -1319,6 +1359,7 @@ redirect:
|
||||
if (port < 0)
|
||||
port = RTSP_DEFAULT_PORT;
|
||||
|
||||
#if FF_API_RTSP_URL_OPTIONS
|
||||
/* search for options */
|
||||
option_list = strrchr(path, '?');
|
||||
if (option_list) {
|
||||
@ -1326,6 +1367,7 @@ redirect:
|
||||
* the options back into the same string. */
|
||||
filename = option_list;
|
||||
while (option_list) {
|
||||
int handled = 1;
|
||||
/* move the option pointer */
|
||||
option = ++option_list;
|
||||
option_list = strchr(option_list, '&');
|
||||
@ -1343,7 +1385,7 @@ redirect:
|
||||
lower_transport_mask |= (1<< RTSP_LOWER_TRANSPORT_TCP);
|
||||
rt->control_transport = RTSP_MODE_TUNNEL;
|
||||
} else if (!strcmp(option, "filter_src")) {
|
||||
rt->filter_source = 1;
|
||||
rt->rtsp_flags |= RTSP_FLAG_FILTER_SRC;
|
||||
} else {
|
||||
/* Write options back into the buffer, using memmove instead
|
||||
* of strcpy since the strings may overlap. */
|
||||
@ -1351,10 +1393,16 @@ redirect:
|
||||
memmove(++filename, option, len);
|
||||
filename += len;
|
||||
if (option_list) *filename = '&';
|
||||
handled = 0;
|
||||
}
|
||||
if (handled)
|
||||
av_log(s, AV_LOG_WARNING, "Options passed via URL are "
|
||||
"deprecated, use -rtsp_transport "
|
||||
"and -rtsp_flags instead.\n");
|
||||
}
|
||||
*filename = 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
if (!lower_transport_mask)
|
||||
lower_transport_mask = (1 << RTSP_LOWER_TRANSPORT_NB) - 1;
|
||||
@ -1797,8 +1845,9 @@ static int sdp_read_header(AVFormatContext *s, AVFormatParameters *ap)
|
||||
namebuf, sizeof(namebuf), NULL, 0, NI_NUMERICHOST);
|
||||
ff_url_join(url, sizeof(url), "rtp", NULL,
|
||||
namebuf, rtsp_st->sdp_port,
|
||||
"?localport=%d&ttl=%d", rtsp_st->sdp_port,
|
||||
rtsp_st->sdp_ttl);
|
||||
"?localport=%d&ttl=%d&connect=%d", rtsp_st->sdp_port,
|
||||
rtsp_st->sdp_ttl,
|
||||
rt->rtsp_flags & RTSP_FLAG_FILTER_SRC ? 1 : 0);
|
||||
if (ffurl_open(&rtsp_st->rtp_handle, url, AVIO_FLAG_READ_WRITE) < 0) {
|
||||
err = AVERROR_INVALIDDATA;
|
||||
goto fail;
|
||||
@ -1820,6 +1869,13 @@ static int sdp_read_close(AVFormatContext *s)
|
||||
return 0;
|
||||
}
|
||||
|
||||
static const AVClass sdp_demuxer_class = {
|
||||
.class_name = "SDP demuxer",
|
||||
.item_name = av_default_item_name,
|
||||
.option = sdp_options,
|
||||
.version = LIBAVUTIL_VERSION_INT,
|
||||
};
|
||||
|
||||
AVInputFormat ff_sdp_demuxer = {
|
||||
.name = "sdp",
|
||||
.long_name = NULL_IF_CONFIG_SMALL("SDP"),
|
||||
@ -1828,6 +1884,7 @@ AVInputFormat ff_sdp_demuxer = {
|
||||
.read_header = sdp_read_header,
|
||||
.read_packet = ff_rtsp_fetch_packet,
|
||||
.read_close = sdp_read_close,
|
||||
.priv_class = &sdp_demuxer_class
|
||||
};
|
||||
#endif /* CONFIG_SDP_DEMUXER */
|
||||
|
||||
@ -1924,6 +1981,13 @@ fail:
|
||||
return ret;
|
||||
}
|
||||
|
||||
static const AVClass rtp_demuxer_class = {
|
||||
.class_name = "RTP demuxer",
|
||||
.item_name = av_default_item_name,
|
||||
.option = rtp_options,
|
||||
.version = LIBAVUTIL_VERSION_INT,
|
||||
};
|
||||
|
||||
AVInputFormat ff_rtp_demuxer = {
|
||||
.name = "rtp",
|
||||
.long_name = NULL_IF_CONFIG_SMALL("RTP input format"),
|
||||
@ -1933,6 +1997,7 @@ AVInputFormat ff_rtp_demuxer = {
|
||||
.read_packet = ff_rtsp_fetch_packet,
|
||||
.read_close = sdp_read_close,
|
||||
.flags = AVFMT_NOFILE,
|
||||
.priv_class = &rtp_demuxer_class
|
||||
};
|
||||
#endif /* CONFIG_RTP_DEMUXER */
|
||||
|
||||
|
@ -29,6 +29,7 @@
|
||||
#include "httpauth.h"
|
||||
|
||||
#include "libavutil/log.h"
|
||||
#include "libavutil/opt.h"
|
||||
|
||||
/**
|
||||
* Network layer over which RTP/etc packet data will be transported.
|
||||
@ -37,7 +38,10 @@ enum RTSPLowerTransport {
|
||||
RTSP_LOWER_TRANSPORT_UDP = 0, /**< UDP/unicast */
|
||||
RTSP_LOWER_TRANSPORT_TCP = 1, /**< TCP; interleaved in RTSP */
|
||||
RTSP_LOWER_TRANSPORT_UDP_MULTICAST = 2, /**< UDP/multicast */
|
||||
RTSP_LOWER_TRANSPORT_NB
|
||||
RTSP_LOWER_TRANSPORT_NB,
|
||||
RTSP_LOWER_TRANSPORT_HTTP = 8, /**< HTTP tunneled - not a proper
|
||||
transport mode as such,
|
||||
only for use via AVOptions */
|
||||
};
|
||||
|
||||
/**
|
||||
@ -313,10 +317,6 @@ typedef struct RTSPState {
|
||||
/** Reusable buffer for receiving packets */
|
||||
uint8_t* recvbuf;
|
||||
|
||||
/** Filter incoming UDP packets - receive packets only from the right
|
||||
* source address and port. */
|
||||
int filter_source;
|
||||
|
||||
/**
|
||||
* A mask with all requested transport methods
|
||||
*/
|
||||
@ -349,8 +349,17 @@ typedef struct RTSPState {
|
||||
|
||||
/** Whether the server accepts the x-Dynamic-Rate header */
|
||||
int accept_dynamic_rate;
|
||||
|
||||
/**
|
||||
* Various option flags for the RTSP muxer/demuxer.
|
||||
*/
|
||||
int rtsp_flags;
|
||||
} RTSPState;
|
||||
|
||||
#define RTSP_FLAG_FILTER_SRC 0x1 /**< Filter incoming UDP packets -
|
||||
receive packets only from the right
|
||||
source address and port. */
|
||||
|
||||
/**
|
||||
* Describes a single stream, as identified by a single m= line block in the
|
||||
* SDP content. In the case of RDT, one RTSPStream can represent multiple
|
||||
@ -537,4 +546,6 @@ int ff_rtsp_make_setup_request(AVFormatContext *s, const char *host, int port,
|
||||
*/
|
||||
void ff_rtsp_undo_setup(AVFormatContext *s);
|
||||
|
||||
extern const AVOption ff_rtsp_options[];
|
||||
|
||||
#endif /* AVFORMAT_RTSP_H */
|
||||
|
@ -22,7 +22,6 @@
|
||||
#include "libavutil/avstring.h"
|
||||
#include "libavutil/intreadwrite.h"
|
||||
#include "libavutil/mathematics.h"
|
||||
#include "libavutil/opt.h"
|
||||
#include "avformat.h"
|
||||
|
||||
#include "internal.h"
|
||||
@ -388,15 +387,10 @@ static int rtsp_read_close(AVFormatContext *s)
|
||||
return 0;
|
||||
}
|
||||
|
||||
static const AVOption options[] = {
|
||||
{ "initial_pause", "Don't start playing the stream immediately", offsetof(RTSPState, initial_pause), AV_OPT_TYPE_INT, {.dbl = 0}, 0, 1, AV_OPT_FLAG_DECODING_PARAM },
|
||||
{ NULL },
|
||||
};
|
||||
|
||||
const AVClass rtsp_demuxer_class = {
|
||||
.class_name = "RTSP demuxer",
|
||||
.item_name = av_default_item_name,
|
||||
.option = options,
|
||||
.option = ff_rtsp_options,
|
||||
.version = LIBAVUTIL_VERSION_INT,
|
||||
};
|
||||
|
||||
|
@ -33,20 +33,13 @@
|
||||
#include "libavutil/intreadwrite.h"
|
||||
#include "libavutil/avstring.h"
|
||||
#include "url.h"
|
||||
#include "libavutil/opt.h"
|
||||
#include "rtpenc.h"
|
||||
|
||||
#define SDP_MAX_SIZE 16384
|
||||
|
||||
static const AVOption options[] = {
|
||||
FF_RTP_FLAG_OPTS(RTSPState, rtp_muxer_flags),
|
||||
{ NULL },
|
||||
};
|
||||
|
||||
static const AVClass rtsp_muxer_class = {
|
||||
.class_name = "RTSP muxer",
|
||||
.item_name = av_default_item_name,
|
||||
.option = options,
|
||||
.option = ff_rtsp_options,
|
||||
.version = LIBAVUTIL_VERSION_INT,
|
||||
};
|
||||
|
||||
|
@ -1902,7 +1902,7 @@ static int has_duration(AVFormatContext *ic)
|
||||
static void update_stream_timings(AVFormatContext *ic)
|
||||
{
|
||||
int64_t start_time, start_time1, start_time_text, end_time, end_time1;
|
||||
int64_t duration, duration1;
|
||||
int64_t duration, duration1, filesize;
|
||||
int i;
|
||||
AVStream *st;
|
||||
|
||||
@ -1945,9 +1945,9 @@ static void update_stream_timings(AVFormatContext *ic)
|
||||
if (duration != INT64_MIN && ic->duration == AV_NOPTS_VALUE) {
|
||||
ic->duration = duration;
|
||||
}
|
||||
if (ic->file_size > 0 && ic->duration != AV_NOPTS_VALUE) {
|
||||
if (ic->pb && (filesize = avio_size(ic->pb)) > 0 && ic->duration != AV_NOPTS_VALUE) {
|
||||
/* compute the bitrate */
|
||||
ic->bit_rate = (double)ic->file_size * 8.0 * AV_TIME_BASE /
|
||||
ic->bit_rate = (double)filesize * 8.0 * AV_TIME_BASE /
|
||||
(double)ic->duration;
|
||||
}
|
||||
}
|
||||
@ -1988,9 +1988,8 @@ static void estimate_timings_from_bit_rate(AVFormatContext *ic)
|
||||
|
||||
/* if duration is already set, we believe it */
|
||||
if (ic->duration == AV_NOPTS_VALUE &&
|
||||
ic->bit_rate != 0 &&
|
||||
ic->file_size != 0) {
|
||||
filesize = ic->file_size;
|
||||
ic->bit_rate != 0) {
|
||||
filesize = ic->pb ? avio_size(ic->pb) : 0;
|
||||
if (filesize > 0) {
|
||||
for(i = 0; i < ic->nb_streams; i++) {
|
||||
st = ic->streams[i];
|
||||
@ -2034,7 +2033,7 @@ static void estimate_timings_from_pts(AVFormatContext *ic, int64_t old_offset)
|
||||
|
||||
/* estimate the end time (duration) */
|
||||
/* XXX: may need to support wrapping */
|
||||
filesize = ic->file_size;
|
||||
filesize = ic->pb ? avio_size(ic->pb) : 0;
|
||||
end_time = AV_NOPTS_VALUE;
|
||||
do{
|
||||
offset = filesize - (DURATION_MAX_READ_SIZE<<retry);
|
||||
@ -2098,7 +2097,6 @@ static void estimate_timings(AVFormatContext *ic, int64_t old_offset)
|
||||
if (file_size < 0)
|
||||
file_size = 0;
|
||||
}
|
||||
ic->file_size = file_size;
|
||||
|
||||
if ((!strcmp(ic->iformat->name, "mpeg") ||
|
||||
!strcmp(ic->iformat->name, "mpegts")) &&
|
||||
|
@ -25,7 +25,7 @@
|
||||
|
||||
#define LIBAVFORMAT_VERSION_MAJOR 53
|
||||
#define LIBAVFORMAT_VERSION_MINOR 16
|
||||
#define LIBAVFORMAT_VERSION_MICRO 0
|
||||
#define LIBAVFORMAT_VERSION_MICRO 1
|
||||
|
||||
#define LIBAVFORMAT_VERSION_INT AV_VERSION_INT(LIBAVFORMAT_VERSION_MAJOR, \
|
||||
LIBAVFORMAT_VERSION_MINOR, \
|
||||
@ -89,5 +89,14 @@
|
||||
#ifndef FF_API_TIMESTAMP
|
||||
#define FF_API_TIMESTAMP (LIBAVFORMAT_VERSION_MAJOR < 54)
|
||||
#endif
|
||||
#ifndef FF_API_FILESIZE
|
||||
#define FF_API_FILESIZE (LIBAVFORMAT_VERSION_MAJOR < 54)
|
||||
#endif
|
||||
#ifndef FF_API_MUXRATE
|
||||
#define FF_API_MUXRATE (LIBAVFORMAT_VERSION_MAJOR < 54)
|
||||
#endif
|
||||
#ifndef FF_API_RTSP_URL_OPTIONS
|
||||
#define FF_API_RTSP_URL_OPTIONS (LIBAVFORMAT_VERSION_MAJOR < 54)
|
||||
#endif
|
||||
|
||||
#endif /* AVFORMAT_VERSION_H */
|
||||
|
@ -503,7 +503,8 @@ int av_opt_get_q(void *obj, const char *name, int search_flags, AVRational *out_
|
||||
int av_opt_flag_is_set(void *obj, const char *field_name, const char *flag_name)
|
||||
{
|
||||
const AVOption *field = av_opt_find(obj, field_name, NULL, 0, 0);
|
||||
const AVOption *flag = av_opt_find(obj, flag_name, NULL, 0, 0);
|
||||
const AVOption *flag = av_opt_find(obj, flag_name,
|
||||
field ? field->unit : NULL, 0, 0);
|
||||
int64_t res;
|
||||
|
||||
if (!field || !flag || flag->type != AV_OPT_TYPE_CONST ||
|
||||
@ -700,6 +701,7 @@ int av_set_options_string(void *ctx, const char *opts,
|
||||
|
||||
if (!opts)
|
||||
return 0;
|
||||
|
||||
while (*opts) {
|
||||
if ((ret = parse_key_value_pair(ctx, &opts, key_val_sep, pairs_sep)) < 0)
|
||||
return ret;
|
||||
|
Loading…
Reference in New Issue
Block a user