2010-01-30 23:24:23 +00:00
|
|
|
/*
|
2015-04-13 07:36:54 +00:00
|
|
|
* This file is part of mpv.
|
2010-01-30 23:24:23 +00:00
|
|
|
*
|
2017-04-21 06:49:25 +00:00
|
|
|
* mpv is free software; you can redistribute it and/or
|
|
|
|
* modify it under the terms of the GNU Lesser General Public
|
|
|
|
* License as published by the Free Software Foundation; either
|
|
|
|
* version 2.1 of the License, or (at your option) any later version.
|
2010-01-30 23:24:23 +00:00
|
|
|
*
|
2015-04-13 07:36:54 +00:00
|
|
|
* mpv is distributed in the hope that it will be useful,
|
2010-01-30 23:24:23 +00:00
|
|
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
|
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
2017-04-21 06:49:25 +00:00
|
|
|
* GNU Lesser General Public License for more details.
|
2010-01-30 23:24:23 +00:00
|
|
|
*
|
2017-04-21 06:49:25 +00:00
|
|
|
* You should have received a copy of the GNU Lesser General Public
|
|
|
|
* License along with mpv. If not, see <http://www.gnu.org/licenses/>.
|
2010-01-30 23:24:23 +00:00
|
|
|
*/
|
|
|
|
|
2008-02-22 09:09:46 +00:00
|
|
|
#ifndef MPLAYER_MPCOMMON_H
|
|
|
|
#define MPLAYER_MPCOMMON_H
|
2008-01-01 21:35:58 +00:00
|
|
|
|
2016-08-28 17:33:04 +00:00
|
|
|
#include <assert.h>
|
2014-04-29 11:14:48 +00:00
|
|
|
#include <stddef.h>
|
mplayer: turn playtree into a list, and change per-file option handling
Summary:
- There is no playtree anymore. It's reduced to a simple list.
- Options are now always global. You can still have per-file options,
but these are optional and require special syntax.
- The slave command pt_step has been removed, and playlist_next
and playlist_prev added. (See etc/input.conf changes.)
This is a user visible incompatible change, and will break slave-mode
applications.
- The pt_clear slave command is renamed to playlist_clear.
- Playtree entries could have multiple files. This is not the case
anymore, and playlist entries have always exactly one entry. Whenever
something adds more than one file (like ASX playlists or dvd:// or
dvdnav:// on the command line), all files are added as separate
playlist entries.
Note that some of the changes are quite deep and violent. Expect
regressions.
The playlist parsing code in particular is of low quality. I didn't try
to improve it, and merely spent to least effort necessary to keep it
somehow working. (Especially ASX playlist handling.)
The playtree code was complicated and bloated. It was also barely used.
Most users don't even know that mplayer manages the playlist as tree,
or how to use it. The most obscure features was probably specifying a
tree on command line (with '{' and '}' to create/close tree nodes). It
filled the player code with complexity and confused users with weird
slave commands like pt_up.
Replace the playtree with a simple flat playlist. Playlist parsers that
actually return trees are changed to append all files to the playlist
pre-order.
It used to be the responsibility of the playtree code to change per-file
config options. Now this is done by the player core, and the playlist
code is free of such details.
Options are not per-file by default anymore. This was a very obscure and
complicated feature that confused even experienced users. Consider the
following command line:
mplayer file1.mkv file2.mkv --no-audio file3.mkv
This will disable the audio for file2.mkv only, because options are
per-file by default. To make the option affect all files, you're
supposed to put it before the first file.
This is bad, because normally you don't need per-file options. They are
very rarely needed, and the only reasonable use cases I can imagine are
use of the encode backend (mplayer encode branch), or for debugging. The
normal use case is made harder, and the feature is perceived as bug.
Even worse, correct usage is hard to explain for users.
Make all options global by default. The position of an option isn't
significant anymore (except for options that compensate each other,
consider --shuffle --no-shuffle).
One other important change is that no options are reset anymore if a
new file is started. If you change settings with slave mode commands,
they will not be changed by playing a new file. (Exceptions include
settings that are too file specific, like audio/subtitle stream
selection.)
There is still some need for per-file options. Debugging and encoding
are use cases that profit from per-file options. Per-file profiles (as
well as per-protocol and per-VO/AO options) need the implementation
related mechanisms to backup and restore options when the playback file
changes.
Simplify the save-slot stuff, which is possible because there is no
hierarchical play tree anymore. Now there's a simple backup field.
Add a way to specify per-file options on command line. Example:
mplayer f1.mkv -o0 --{ -o1 f2.mkv -o2 f3.mkv --} f4.mkv -o3
will have the following options per file set:
f1.mkv, f4.mkv: -o0 -o3
f2.mkv, f3.mkv: -o0 -o3 -o1 -o2
The options --{ and --} start and end per-file options. All files inside
the { } will be affected by the options equally (similar to how global
options and multiple files are handled). When playback of a file starts,
the per-file options are set according to the command line. When
playback ends, the per-file options are restored to the values when
playback started.
2012-07-31 19:33:26 +00:00
|
|
|
#include <stdlib.h>
|
2012-09-01 19:59:13 +00:00
|
|
|
#include <stdbool.h>
|
2013-02-16 21:51:10 +00:00
|
|
|
#include <stdint.h>
|
mplayer: turn playtree into a list, and change per-file option handling
Summary:
- There is no playtree anymore. It's reduced to a simple list.
- Options are now always global. You can still have per-file options,
but these are optional and require special syntax.
- The slave command pt_step has been removed, and playlist_next
and playlist_prev added. (See etc/input.conf changes.)
This is a user visible incompatible change, and will break slave-mode
applications.
- The pt_clear slave command is renamed to playlist_clear.
- Playtree entries could have multiple files. This is not the case
anymore, and playlist entries have always exactly one entry. Whenever
something adds more than one file (like ASX playlists or dvd:// or
dvdnav:// on the command line), all files are added as separate
playlist entries.
Note that some of the changes are quite deep and violent. Expect
regressions.
The playlist parsing code in particular is of low quality. I didn't try
to improve it, and merely spent to least effort necessary to keep it
somehow working. (Especially ASX playlist handling.)
The playtree code was complicated and bloated. It was also barely used.
Most users don't even know that mplayer manages the playlist as tree,
or how to use it. The most obscure features was probably specifying a
tree on command line (with '{' and '}' to create/close tree nodes). It
filled the player code with complexity and confused users with weird
slave commands like pt_up.
Replace the playtree with a simple flat playlist. Playlist parsers that
actually return trees are changed to append all files to the playlist
pre-order.
It used to be the responsibility of the playtree code to change per-file
config options. Now this is done by the player core, and the playlist
code is free of such details.
Options are not per-file by default anymore. This was a very obscure and
complicated feature that confused even experienced users. Consider the
following command line:
mplayer file1.mkv file2.mkv --no-audio file3.mkv
This will disable the audio for file2.mkv only, because options are
per-file by default. To make the option affect all files, you're
supposed to put it before the first file.
This is bad, because normally you don't need per-file options. They are
very rarely needed, and the only reasonable use cases I can imagine are
use of the encode backend (mplayer encode branch), or for debugging. The
normal use case is made harder, and the feature is perceived as bug.
Even worse, correct usage is hard to explain for users.
Make all options global by default. The position of an option isn't
significant anymore (except for options that compensate each other,
consider --shuffle --no-shuffle).
One other important change is that no options are reset anymore if a
new file is started. If you change settings with slave mode commands,
they will not be changed by playing a new file. (Exceptions include
settings that are too file specific, like audio/subtitle stream
selection.)
There is still some need for per-file options. Debugging and encoding
are use cases that profit from per-file options. Per-file profiles (as
well as per-protocol and per-VO/AO options) need the implementation
related mechanisms to backup and restore options when the playback file
changes.
Simplify the save-slot stuff, which is possible because there is no
hierarchical play tree anymore. Now there's a simple backup field.
Add a way to specify per-file options on command line. Example:
mplayer f1.mkv -o0 --{ -o1 f2.mkv -o2 f3.mkv --} f4.mkv -o3
will have the following options per file set:
f1.mkv, f4.mkv: -o0 -o3
f2.mkv, f3.mkv: -o0 -o3 -o1 -o2
The options --{ and --} start and end per-file options. All files inside
the { } will be affected by the options equally (similar to how global
options and multiple files are handled). When playback of a file starts,
the per-file options are set according to the command line. When
playback ends, the per-file options are restored to the values when
playback started.
2012-07-31 19:33:26 +00:00
|
|
|
|
2014-08-29 10:09:04 +00:00
|
|
|
#include "osdep/compiler.h"
|
2016-01-11 18:03:40 +00:00
|
|
|
#include "mpv_talloc.h"
|
2012-11-10 15:19:53 +00:00
|
|
|
|
2014-05-10 08:34:11 +00:00
|
|
|
// double should be able to represent this exactly
|
|
|
|
#define MP_NOPTS_VALUE (-0x1p+63)
|
2011-01-12 13:29:31 +00:00
|
|
|
|
video: decouple internal pixel formats from FourCCs
mplayer's video chain traditionally used FourCCs for pixel formats. For
example, it used IMGFMT_YV12 for 4:2:0 YUV, which was defined to the
string 'YV12' interpreted as unsigned int. Additionally, it used to
encode information into the numeric values of some formats. The RGB
formats had their bit depth and endian encoded into the least
significant byte. Extended planar formats (420P10 etc.) had chroma
shift, endian, and component bit depth encoded. (This has been removed
in recent commits.)
Replace the FourCC mess with a simple enum. Remove all the redundant
formats like YV12/I420/IYUV. Replace some image format names by
something more intuitive, most importantly IMGFMT_YV12 -> IMGFMT_420P.
Add img_fourcc.h, which contains the old IDs for code that actually uses
FourCCs. Change the way demuxers, that output raw video, identify the
video format: they set either MP_FOURCC_RAWVIDEO or MP_FOURCC_IMGFMT to
request the rawvideo decoder, and sh_video->imgfmt specifies the pixel
format. Like the previous hack, this is supposed to avoid the need for
a complete codecs.cfg entry per format, or other lookup tables. (Note
that the RGB raw video FourCCs mostly rely on ffmpeg's mappings for NUT
raw video, but this is still considered better than adding a raw video
decoder - even if trivial, it would be full of annoying lookup tables.)
The TV code has not been tested.
Some corrective changes regarding endian and other image format flags
creep in.
2012-12-23 19:03:30 +00:00
|
|
|
#define MP_CONCAT_(a, b) a ## b
|
|
|
|
#define MP_CONCAT(a, b) MP_CONCAT_(a, b)
|
|
|
|
|
2013-07-15 21:52:47 +00:00
|
|
|
#define MPMAX(a, b) ((a) > (b) ? (a) : (b))
|
|
|
|
#define MPMIN(a, b) ((a) > (b) ? (b) : (a))
|
2013-10-26 13:05:59 +00:00
|
|
|
#define MPCLAMP(a, min, max) (((a) < (min)) ? (min) : (((a) > (max)) ? (max) : (a)))
|
2013-09-25 20:22:02 +00:00
|
|
|
#define MPSWAP(type, a, b) \
|
|
|
|
do { type SWAP_tmp = b; b = a; a = SWAP_tmp; } while (0)
|
options: use m_config for options instead of m_struct
For some reason, both m_config and m_struct are somewhat similar, except
that m_config is much more powerful. m_config is used for VOs and some
other things, so to unify them. We plan to kick out m_struct and use
m_config for everything. (Unfortunately, m_config is also a bit more
bloated, so this commit isn't all that great, but it will allow to
reduce the option parser mess somewhat.)
This commit also switches all video filters to use the option macros.
One reason is that m_struct and m_config, even though they both use
m_option, store the offsets of the option fields differently (sigh...),
meaning the options defined for either are incompatible. It's easier to
switch everything in one go.
This commit will allow using the -vf option parser for other things,
like VOs and AOs.
2013-07-21 17:33:08 +00:00
|
|
|
#define MP_ARRAY_SIZE(s) (sizeof(s) / sizeof((s)[0]))
|
2013-07-15 21:52:47 +00:00
|
|
|
|
2013-09-25 20:44:12 +00:00
|
|
|
// align must be a power of two (align >= 1), x >= 0
|
|
|
|
#define MP_ALIGN_UP(x, align) (((x) + (align) - 1) & ~((align) - 1))
|
|
|
|
#define MP_ALIGN_DOWN(x, align) ((x) & ~((align) - 1))
|
2019-06-07 11:33:47 +00:00
|
|
|
#define MP_IS_ALIGNED(x, align) (!((x) & ((align) - 1)))
|
2019-06-16 16:22:45 +00:00
|
|
|
#define MP_IS_POWER_OF_2(x) ((x) > 0 && !((x) & ((x) - 1)))
|
2013-09-25 20:44:12 +00:00
|
|
|
|
2019-05-31 12:47:18 +00:00
|
|
|
// Return "a", or if that is NOPTS, return "def".
|
|
|
|
#define MP_PTS_OR_DEF(a, def) ((a) == MP_NOPTS_VALUE ? (def) : (a))
|
|
|
|
// If one of the values is NOPTS, always pick the other one.
|
|
|
|
#define MP_PTS_MIN(a, b) MPMIN(MP_PTS_OR_DEF(a, b), MP_PTS_OR_DEF(b, a))
|
|
|
|
#define MP_PTS_MAX(a, b) MPMAX(MP_PTS_OR_DEF(a, b), MP_PTS_OR_DEF(b, a))
|
|
|
|
// Return a+b, unless a is NOPTS. b must not be NOPTS.
|
|
|
|
#define MP_ADD_PTS(a, b) ((a) == MP_NOPTS_VALUE ? (a) : ((a) + (b)))
|
|
|
|
|
core: redo how codecs are mapped, remove codecs.conf
Use codec names instead of FourCCs to identify codecs. Rewrite how
codecs are selected and initialized. Now each decoder exports a list
of decoders (and the codec it supports) via add_decoders(). The order
matters, and the first decoder for a given decoder is preferred over
the other decoders. E.g. all ad_mpg123 decoders are preferred over
ad_lavc, because it comes first in the mpcodecs_ad_drivers array.
Likewise, decoders within ad_lavc that are enumerated first by
libavcodec (using av_codec_next()) are preferred. (This is actually
critical to select h264 software decoding by default instead of vdpau.
libavcodec and ffmpeg/avconv use the same method to select decoders by
default, so we hope this is sane.)
The codec names follow libavcodec's codec names as defined by
AVCodecDescriptor.name (see libavcodec/codec_desc.c). Some decoders
have names different from the canonical codec name. The AVCodecDescriptor
API is relatively new, so we need a compatibility layer for older
libavcodec versions for codec names that are referenced internally,
and which are different from the decoder name. (Add a configure check
for that, because checking versions is getting way too messy.)
demux/codec_tags.c is generated from the former codecs.conf (minus
"special" decoders like vdpau, and excluding the mappings that are the
same as the mappings libavformat's exported RIFF tables). It contains
all the mappings from FourCCs to codec name. This is needed for
demux_mkv, demux_mpg, demux_avi and demux_asf. demux_lavf will set the
codec as determined by libavformat, while the other demuxers have to do
this on their own, using the mp_set_audio/video_codec_from_tag()
functions. Note that the sh_audio/video->format members don't uniquely
identify the codec anymore, and sh->codec takes over this role.
Replace the --ac/--vc/--afm/--vfm with new --vd/--ad options, which
provide cover the functionality of the removed switched.
Note: there's no CODECS_FLAG_FLIP flag anymore. This means some obscure
container/video combinations (e.g. the sample Film_200_zygo_pro.mov)
are played flipped. ffplay/avplay doesn't handle this properly either,
so we don't care and blame ffmeg/libav instead.
2013-02-09 14:15:19 +00:00
|
|
|
#define CONTROL_OK 1
|
|
|
|
#define CONTROL_TRUE 1
|
|
|
|
#define CONTROL_FALSE 0
|
|
|
|
#define CONTROL_UNKNOWN -1
|
|
|
|
#define CONTROL_ERROR -2
|
|
|
|
#define CONTROL_NA -3
|
|
|
|
|
2013-11-23 21:08:42 +00:00
|
|
|
enum stream_type {
|
|
|
|
STREAM_VIDEO,
|
|
|
|
STREAM_AUDIO,
|
|
|
|
STREAM_SUB,
|
|
|
|
STREAM_TYPE_COUNT,
|
|
|
|
};
|
|
|
|
|
2016-09-06 15:58:00 +00:00
|
|
|
extern const char mpv_version[];
|
|
|
|
extern const char mpv_builddate[];
|
2018-01-01 11:16:42 +00:00
|
|
|
extern const char mpv_copyright[];
|
2010-06-28 08:26:14 +00:00
|
|
|
|
2012-09-01 19:59:13 +00:00
|
|
|
char *mp_format_time(double time, bool fractions);
|
2013-03-25 19:32:01 +00:00
|
|
|
char *mp_format_time_fmt(const char *fmt, double time);
|
2012-09-01 19:59:13 +00:00
|
|
|
|
2012-10-25 17:37:36 +00:00
|
|
|
struct mp_rect {
|
|
|
|
int x0, y0;
|
|
|
|
int x1, y1;
|
|
|
|
};
|
|
|
|
|
2014-03-07 11:46:22 +00:00
|
|
|
#define mp_rect_w(r) ((r).x1 - (r).x0)
|
|
|
|
#define mp_rect_h(r) ((r).y1 - (r).y0)
|
|
|
|
|
2012-12-28 14:44:51 +00:00
|
|
|
void mp_rect_union(struct mp_rect *rc, const struct mp_rect *src);
|
|
|
|
bool mp_rect_intersection(struct mp_rect *rc, const struct mp_rect *rc2);
|
2015-04-29 11:51:56 +00:00
|
|
|
bool mp_rect_contains(struct mp_rect *rc, int x, int y);
|
2017-08-07 17:14:18 +00:00
|
|
|
bool mp_rect_equals(struct mp_rect *rc1, struct mp_rect *rc2);
|
2020-05-22 12:17:46 +00:00
|
|
|
int mp_rect_subtract(const struct mp_rect *rc1, const struct mp_rect *rc2,
|
|
|
|
struct mp_rect res_array[4]);
|
2012-12-28 14:44:51 +00:00
|
|
|
|
2019-10-31 12:16:58 +00:00
|
|
|
unsigned int mp_log2(uint32_t v);
|
2019-11-06 20:35:49 +00:00
|
|
|
uint32_t mp_round_next_power_of_2(uint32_t v);
|
2019-10-31 12:16:58 +00:00
|
|
|
|
2014-05-05 21:55:06 +00:00
|
|
|
int mp_snprintf_cat(char *str, size_t size, const char *format, ...)
|
2014-04-29 11:14:48 +00:00
|
|
|
PRINTF_ATTRIBUTE(3, 4);
|
|
|
|
|
2013-02-16 21:51:10 +00:00
|
|
|
struct bstr;
|
2013-12-30 19:28:32 +00:00
|
|
|
|
|
|
|
void mp_append_utf8_bstr(void *talloc_ctx, struct bstr *buf, uint32_t codepoint);
|
|
|
|
|
|
|
|
bool mp_append_escaped_string_noalloc(void *talloc_ctx, struct bstr *dst,
|
|
|
|
struct bstr *src);
|
|
|
|
bool mp_append_escaped_string(void *talloc_ctx, struct bstr *dst,
|
|
|
|
struct bstr *src);
|
2013-02-16 21:51:10 +00:00
|
|
|
|
Do not call strerror()
...because everything is terrible.
strerror() is not documented as having to be thread-safe by POSIX and
C11. (Which is pretty much bullshit, because both mandate threads and
some form of thread-local storage - so there's no excuse why
implementation couldn't implement this in a thread-safe way. Especially
with C11 this is ridiculous, because there is no way to use threads and
convert error numbers to strings at the same time!)
Since we heavily use threads now, we should avoid unsafe functions like
strerror().
strerror_r() is in POSIX, but GNU/glibc deliberately fucks it up and
gives the function different semantics than the POSIX one. It's a bit of
work to convince this piece of shit to expose the POSIX standard
function, and not the messed up GNU one.
strerror_l() is also in POSIX, but only since the 2008 standard, and
thus is not widespread.
The solution is using avlibc (libavutil, by its official name), which
handles the unportable details for us, mostly. We avoid some pain.
2014-11-26 20:21:56 +00:00
|
|
|
char *mp_strerror_buf(char *buf, size_t buf_size, int errnum);
|
|
|
|
#define mp_strerror(e) mp_strerror_buf((char[80]){0}, 80, e)
|
|
|
|
|
2016-01-11 13:35:56 +00:00
|
|
|
char *mp_tag_str_buf(char *buf, size_t buf_size, uint32_t tag);
|
|
|
|
#define mp_tag_str(t) mp_tag_str_buf((char[22]){0}, 22, t)
|
|
|
|
|
2017-07-24 06:07:32 +00:00
|
|
|
// Return a printf(format, ...) formatted string of the given SIZE. SIZE must
|
|
|
|
// be a compile time constant. The result is allocated on the stack and valid
|
|
|
|
// only within the current block scope.
|
|
|
|
#define mp_tprintf(SIZE, format, ...) \
|
|
|
|
mp_tprintf_buf((char[SIZE]){0}, (SIZE), (format), __VA_ARGS__)
|
|
|
|
char *mp_tprintf_buf(char *buf, size_t buf_size, const char *format, ...)
|
|
|
|
PRINTF_ATTRIBUTE(3, 4);
|
|
|
|
|
video: rewrite filtering glue code
Get rid of the old vf.c code. Replace it with a generic filtering
framework, which can potentially handle more than just --vf. At least
reimplementing --af with this code is planned.
This changes some --vf semantics (including runtime behavior and the
"vf" command). The most important ones are listed in interface-changes.
vf_convert.c is renamed to f_swscale.c. It is now an internal filter
that can not be inserted by the user manually.
f_lavfi.c is a refactor of player/lavfi.c. The latter will be removed
once --lavfi-complex is reimplemented on top of f_lavfi.c. (which is
conceptually easy, but a big mess due to the data flow changes).
The existing filters are all changed heavily. The data flow of the new
filter framework is different. Especially EOF handling changes - EOF is
now a "frame" rather than a state, and must be passed through exactly
once.
Another major thing is that all filters must support dynamic format
changes. The filter reconfig() function goes away. (This sounds complex,
but since all filters need to handle EOF draining anyway, they can use
the same code, and it removes the mess with reconfig() having to predict
the output format, which completely breaks with libavfilter anyway.)
In addition, there is no automatic format negotiation or conversion.
libavfilter's primitive and insufficient API simply doesn't allow us to
do this in a reasonable way. Instead, filters can use f_autoconvert as
sub-filter, and tell it which formats they support. This filter will in
turn add actual conversion filters, such as f_swscale, to perform
necessary format changes.
vf_vapoursynth.c uses the same basic principle of operation as before,
but with worryingly different details in data flow. Still appears to
work.
The hardware deint filters (vf_vavpp.c, vf_d3d11vpp.c, vf_vdpaupp.c) are
heavily changed. Fortunately, they all used refqueue.c, which is for
sharing the data flow logic (especially for managing future/past
surfaces and such). It turns out it can be used to factor out most of
the data flow. Some of these filters accepted software input. Instead of
having ad-hoc upload code in each filter, surface upload is now
delegated to f_autoconvert, which can use f_hwupload to perform this.
Exporting VO capabilities is still a big mess (mp_stream_info stuff).
The D3D11 code drops the redundant image formats, and all code uses the
hw_subfmt (sw_format in FFmpeg) instead. Although that too seems to be a
big mess for now.
f_async_queue is unused.
2018-01-16 10:53:44 +00:00
|
|
|
char **mp_dup_str_array(void *tctx, char **s);
|
|
|
|
|
2018-04-22 17:40:36 +00:00
|
|
|
// We generally do not handle allocation failure of small malloc()s. This would
|
|
|
|
// create a large number of rarely tested code paths, which would probably
|
|
|
|
// regress and cause security issues. We prefer to fail fast.
|
|
|
|
// This macro generally behaves like an assert(), except it will make sure to
|
|
|
|
// kill the process even with NDEBUG.
|
|
|
|
#define MP_HANDLE_OOM(x) do { \
|
|
|
|
assert(x); \
|
|
|
|
if (!(x)) \
|
|
|
|
abort(); \
|
|
|
|
} while (0)
|
|
|
|
|
2008-02-22 09:09:46 +00:00
|
|
|
#endif /* MPLAYER_MPCOMMON_H */
|