diff options
author | wm4 <wm4@nowhere> | 2013-07-21 19:33:08 +0200 |
---|---|---|
committer | wm4 <wm4@nowhere> | 2013-07-21 23:27:31 +0200 |
commit | 6629a95b928499a46c9686f0800b65aec7fcbb22 (patch) | |
tree | 67e158d3678b54fc521b4fedb19a7dd20b823512 | |
parent | 111a455ec621103b714a199217471af5f3efe35a (diff) | |
download | mpv-6629a95b928499a46c9686f0800b65aec7fcbb22.tar.bz2 mpv-6629a95b928499a46c9686f0800b65aec7fcbb22.tar.xz |
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.
-rw-r--r-- | core/m_config.c | 68 | ||||
-rw-r--r-- | core/m_config.h | 18 | ||||
-rw-r--r-- | core/m_option.c | 130 | ||||
-rw-r--r-- | core/m_option.h | 39 | ||||
-rw-r--r-- | core/mp_common.h | 1 | ||||
-rw-r--r-- | core/options.c | 4 | ||||
-rw-r--r-- | video/filter/vf.c | 89 | ||||
-rw-r--r-- | video/filter/vf.h | 6 | ||||
-rw-r--r-- | video/filter/vf_crop.c | 24 | ||||
-rw-r--r-- | video/filter/vf_delogo.c | 32 | ||||
-rw-r--r-- | video/filter/vf_dlopen.c | 60 | ||||
-rw-r--r-- | video/filter/vf_expand.c | 32 | ||||
-rw-r--r-- | video/filter/vf_format.c | 24 | ||||
-rw-r--r-- | video/filter/vf_gradfun.c | 23 | ||||
-rw-r--r-- | video/filter/vf_lavfi.c | 21 | ||||
-rw-r--r-- | video/filter/vf_noformat.c | 20 | ||||
-rw-r--r-- | video/filter/vf_scale.c | 31 | ||||
-rw-r--r-- | video/filter/vf_stereo3d.c | 26 | ||||
-rw-r--r-- | video/filter/vf_sub.c | 22 | ||||
-rw-r--r-- | video/filter/vf_yadif.c | 21 |
20 files changed, 342 insertions, 349 deletions
diff --git a/core/m_config.c b/core/m_config.c index 336af39447..a447621009 100644 --- a/core/m_config.c +++ b/core/m_config.c @@ -182,6 +182,49 @@ struct m_config *m_config_simple(void *optstruct) return config; } +struct m_config *m_config_from_obj_desc(void *talloc_parent, + struct m_obj_desc *desc) +{ + struct m_config *config = m_config_simple(NULL); + talloc_steal(talloc_parent, config); + if (desc->priv_size) { + config->optstruct = talloc_zero_size(config, desc->priv_size); + if (desc->priv_defaults) + memcpy(config->optstruct, desc->priv_defaults, desc->priv_size); + m_config_register_options(config, desc->options); + } + return config; +} + +int m_config_set_obj_params(struct m_config *conf, char **args) +{ + for (int n = 0; args && args[n * 2 + 0]; n++) { + int r = m_config_set_option(conf, bstr0(args[n * 2 + 0]), + bstr0(args[n * 2 + 1])); + if (r < 0) + return r; + } + return 0; +} + +int m_config_initialize_obj(struct m_config *config, struct m_obj_desc *desc, + void **ppriv, char ***pargs) +{ + if (desc->priv_size) { + int r = m_config_set_obj_params(config, *pargs); + if (r < 0) + return r; + *ppriv = config->optstruct; + *pargs = NULL; + } else if (*pargs && !strcmp((*pargs)[0], "_oldargs_")) { + // Handle things which still use the old subopt parser + *pargs = (char **)((*pargs)[1]); + } else { + *pargs = NULL; + } + return 0; +} + struct m_config *m_config_new(void *optstruct, int includefunc(struct m_config *conf, char *filename)) @@ -414,8 +457,14 @@ static void m_config_add_option(struct m_config *config, // pretend that merge options don't exist (only their children matter) if (!is_merge_opt(co->opt)) { - co->next = config->opts; - config->opts = co; + struct m_config_option **last = &config->opts; + while (*last) + last = &(*last)->next; + *last = co; + if (!co->alias_owner) { // don't make no- etc. options positional + config->num_pos_opts += 1; + co->pos = config->num_pos_opts; + } } add_negation_option(config, parent, arg); @@ -425,10 +474,8 @@ int m_config_register_options(struct m_config *config, const struct m_option *args) { assert(config != NULL); - assert(args != NULL); - - add_options(config, NULL, args); - + if (args) + add_options(config, NULL, args); return 1; } @@ -450,6 +497,15 @@ struct m_config_option *m_config_get_co(const struct m_config *config, return NULL; } +const char *m_config_get_positional_option(const struct m_config *config, int n) +{ + for (struct m_config_option *co = config->opts; co; co = co->next) { + if (co->pos && co->pos - 1 == n) + return co->name; + } + return NULL; +} + static int parse_subopts(struct m_config *config, void *optstruct, char *name, char *prefix, struct bstr param, int flags); diff --git a/core/m_config.h b/core/m_config.h index 98b21c9bf9..28983944df 100644 --- a/core/m_config.h +++ b/core/m_config.h @@ -31,10 +31,13 @@ typedef struct m_profile m_profile_t; struct m_option; struct m_option_type; struct m_sub_options; +struct m_obj_desc; // Config option struct m_config_option { struct m_config_option *next; + // For positional parameters + int pos; // Full name (ie option-subopt). char *name; // Option description. @@ -71,6 +74,7 @@ typedef struct m_config { /** This contains all options and suboptions. */ struct m_config_option *opts; + int num_pos_opts; // When options are set (via m_config_set_option or m_config_set_profile), // back up the old value (unless it's already backed up). Used for restoring // global options when per-file options are set. @@ -92,6 +96,16 @@ m_config_new(void *optstruct, struct m_config *m_config_simple(void *optstruct); +struct m_config *m_config_from_obj_desc(void *talloc_parent, + struct m_obj_desc *desc); + +int m_config_set_obj_params(struct m_config *conf, char **args); + +// Initialize an object (VO/VF/...) in one go, including legacy handling. +// This is pretty specialized, and is just for convenience. +int m_config_initialize_obj(struct m_config *config, struct m_obj_desc *desc, + void **ppriv, char ***pargs); + // Free a config object. void m_config_free(struct m_config *config); @@ -149,6 +163,10 @@ const struct m_option *m_config_get_option(const struct m_config *config, struct m_config_option *m_config_get_co(const struct m_config *config, struct bstr name); +// Return the n-th option by position. n==0 is the first option. If there are +// less than (n + 1) options, return NULL. +const char *m_config_get_positional_option(const struct m_config *config, int n); + // Return a hint to the option parser whether a parameter is/may be required. // The option may still accept empty/non-empty parameters independent from // this, and this function is useful only for handling ambiguous options like diff --git a/core/m_option.c b/core/m_option.c index 9b8256abe4..b6f329c51f 100644 --- a/core/m_option.c +++ b/core/m_option.c @@ -38,6 +38,7 @@ #include "talloc.h" #include "core/mp_common.h" #include "core/m_option.h" +#include "core/m_config.h" #include "core/mp_msg.h" char *m_option_strerror(int code) @@ -1780,20 +1781,16 @@ const m_option_type_t m_option_type_rel_time = { #undef VAL #define VAL(x) (*(m_obj_settings_t **)(x)) -static int find_obj_desc(struct bstr name, const m_obj_list_t *l, - const m_struct_t **ret) +bool m_obj_list_find(struct m_obj_desc *dst, const struct m_obj_list *l, + bstr name) { - int i; - char *n; - - for (i = 0; l->list[i]; i++) { - n = M_ST_MB(char *, l->list[i], l->name_off); - if (!bstrcmp0(name, n)) { - *ret = M_ST_MB(m_struct_t *, l->list[i], l->desc_off); - return 1; - } + for (int i = 0; ; i++) { + if (!l->get_desc(dst, i)) + break; + if (bstr_equals0(name, dst->name)) + return true; } - return 0; + return false; } static void obj_setting_free(m_obj_settings_t *item) @@ -1944,25 +1941,24 @@ static void copy_obj_settings_list(const m_option_t *opt, void *dst, // Consider -vf a=b=c:d=e. This verifies "b"="c" and "d"="e" and that the // option names/values are correct. Try to determine whether an option // without '=' sets a flag, or whether it's a positional argument. -static int get_obj_param(bstr opt_name, bstr obj_name, const m_struct_t *desc, - bstr name, bstr val, int *nold, int oldmax, +static int get_obj_param(bstr opt_name, bstr obj_name, struct m_config *config, + bstr name, bstr val, int *nold, bstr *out_name, bstr *out_val) { - const m_option_t *opt = m_option_list_findb(desc->fields, name); int r; // va.start != NULL => of the form name=val (not positional) // If it's just "name", and the associated option exists and is a flag, // don't accept it as positional argument. - if (val.start || (opt && m_option_required_params(opt) == 0)) { - if (!opt) { - mp_msg(MSGT_CFGPARSER, MSGL_ERR, - "Option %.*s: %.*s doesn't have a %.*s parameter.\n", - BSTR_P(opt_name), BSTR_P(obj_name), BSTR_P(name)); - return M_OPT_UNKNOWN; - } - r = m_option_parse(opt, name, val, NULL); + if (val.start || m_config_option_requires_param(config, name) == 0) { + r = m_config_set_option(config, name, val); if (r < 0) { + if (r == M_OPT_UNKNOWN) { + mp_msg(MSGT_CFGPARSER, MSGL_ERR, + "Option %.*s: %.*s doesn't have a %.*s parameter.\n", + BSTR_P(opt_name), BSTR_P(obj_name), BSTR_P(name)); + return M_OPT_UNKNOWN; + } if (r > M_OPT_EXIT) mp_msg(MSGT_CFGPARSER, MSGL_ERR, "Option %.*s: " "Error while parsing %.*s parameter %.*s (%.*s)\n", @@ -1980,22 +1976,22 @@ static int get_obj_param(bstr opt_name, bstr obj_name, const m_struct_t *desc, (*nold)++; return 0; } - if ((*nold) >= oldmax) { - mp_msg(MSGT_CFGPARSER, MSGL_ERR, "Option %.*s: %.*s has only %d params, so you can't give more than %d unnamed params.\n", - BSTR_P(opt_name), BSTR_P(obj_name), oldmax, oldmax); + const char *opt = m_config_get_positional_option(config, *nold); + if (!opt) { + mp_msg(MSGT_CFGPARSER, MSGL_ERR, "Option %.*s: %.*s has only %d " + "params, so you can't give more than %d unnamed params.\n", + BSTR_P(opt_name), BSTR_P(obj_name), *nold, *nold); return M_OPT_OUT_OF_RANGE; } - opt = &desc->fields[(*nold)]; - r = m_option_parse(opt, bstr0(opt->name), val, NULL); + r = m_config_set_option(config, bstr0(opt), val); if (r < 0) { if (r > M_OPT_EXIT) mp_msg(MSGT_CFGPARSER, MSGL_ERR, "Option %.*s: " "Error while parsing %.*s parameter %s (%.*s)\n", - BSTR_P(opt_name), BSTR_P(obj_name), opt->name, - BSTR_P(val)); + BSTR_P(opt_name), BSTR_P(obj_name), opt, BSTR_P(val)); return r; } - *out_name = bstr0(opt->name); + *out_name = bstr0(opt); *out_val = val; (*nold)++; return 1; @@ -2006,16 +2002,15 @@ static int get_obj_param(bstr opt_name, bstr obj_name, const m_struct_t *desc, // linear array in *_ret. In particular, desc contains what options a the // object takes, and verifies the option values as well. static int get_obj_params(struct bstr opt_name, struct bstr name, - struct bstr *pstr, const m_struct_t *desc, + struct bstr *pstr, struct m_obj_desc *desc, char ***ret) { - int n = 0, nold = 0, nopts; + int nold = 0; char **args = NULL; int num_args = 0; int r = 1; - for (nopts = 0; desc->fields[nopts].name; nopts++) - /* NOP */; + struct m_config *config = m_config_from_obj_desc(NULL, desc); while (pstr->len > 0) { bstr fname, fval; @@ -2024,7 +2019,7 @@ static int get_obj_params(struct bstr opt_name, struct bstr name, goto exit; if (bstr_equals0(fname, "help")) goto print_help; - r = get_obj_param(opt_name, name, desc, fname, fval, &nold, nopts, + r = get_obj_param(opt_name, name, config, fname, fval, &nold, &fname, &fval); if (r < 0) goto exit; @@ -2049,36 +2044,15 @@ static int get_obj_params(struct bstr opt_name, struct bstr name, } } -exit: - return r; + goto exit; print_help: ; - char min[50], max[50]; - if (!desc->fields) { - mp_msg(MSGT_CFGPARSER, MSGL_INFO, - "%.*s doesn't have any options.\n\n", BSTR_P(name)); - return M_OPT_EXIT - 1; - } - mp_msg(MSGT_CFGPARSER, MSGL_INFO, - "\n Name Type Min Max\n\n"); - for (n = 0; desc->fields[n].name; n++) { - const m_option_t *opt = &desc->fields[n]; - if (opt->type->flags & M_OPT_TYPE_HAS_CHILD) - continue; - if (opt->flags & M_OPT_MIN) - sprintf(min, "%-8.0f", opt->min); - else - strcpy(min, "No"); - if (opt->flags & M_OPT_MAX) - sprintf(max, "%-8.0f", opt->max); - else - strcpy(max, "No"); - mp_msg(MSGT_CFGPARSER, MSGL_INFO, - " %-20.20s %-15.15s %-10.10s %-10.10s\n", - opt->name, opt->type->name, min, max); - } - mp_msg(MSGT_CFGPARSER, MSGL_INFO, "\n"); - return M_OPT_EXIT - 1; + m_config_print_option_list(config); + r = M_OPT_EXIT - 1; + +exit: + talloc_free(config); + return r; } // Characters which may appear in a filter name @@ -2086,12 +2060,12 @@ print_help: ; // Parse one item, e.g. -vf a=b:c:d,e=f:g => parse a=b:c:d into "a" and "b:c:d" static int parse_obj_settings(struct bstr opt, struct bstr *pstr, - const m_obj_list_t *list, + const struct m_obj_list *list, m_obj_settings_t **_ret) { int r; char **plist = NULL; - const m_struct_t *desc; + struct m_obj_desc desc; bstr label = {0}; if (bstr_eatstart0(pstr, "@")) { @@ -2109,14 +2083,14 @@ static int parse_obj_settings(struct bstr opt, struct bstr *pstr, if (bstr_eatstart0(pstr, "=")) has_param = true; - if (!find_obj_desc(str, list, &desc)) { + if (!m_obj_list_find(&desc, list, str)) { mp_msg(MSGT_CFGPARSER, MSGL_ERR, "Option %.*s: %.*s doesn't exist.\n", BSTR_P(opt), BSTR_P(str)); return M_OPT_INVALID; } if (has_param) { - if (!desc) { + if (!desc.options) { // Should perhaps be parsed as escape-able string. But this is a // compatibility path, so it's not worth the trouble. int next = bstrcspn(*pstr, ","); @@ -2133,8 +2107,8 @@ static int parse_obj_settings(struct bstr opt, struct bstr *pstr, plist[0] = talloc_strdup(NULL, "_oldargs_"); plist[1] = bstrto0(NULL, param); } - } else if (desc) { - r = get_obj_params(opt, str, pstr, desc, _ret ? &plist : NULL); + } else { + r = get_obj_params(opt, str, pstr, &desc, _ret ? &plist : NULL); if (r < 0) return r; } @@ -2210,6 +2184,7 @@ static int parse_obj_settings_list(const m_option_t *opt, struct bstr name, int op = OP_NONE; bool *mark_del = NULL; int num_items = obj_settings_list_num_items(dst ? VAL(dst) : 0); + struct m_obj_list *ol = opt->priv; assert(opt->priv); @@ -2253,12 +2228,14 @@ static int parse_obj_settings_list(const m_option_t *opt, struct bstr name, } if (!bstrcmp0(param, "help")) { - m_obj_list_t *ol = opt->priv; - mp_msg(MSGT_CFGPARSER, MSGL_INFO, "Available video filters:\n"); - for (int n = 0; ol->list[n]; n++) + mp_msg(MSGT_CFGPARSER, MSGL_INFO, "Available %s:\n", ol->description); + for (int n = 0; ; n++) { + struct m_obj_desc desc; + if (!ol->get_desc(&desc, n)) + break; mp_msg(MSGT_CFGPARSER, MSGL_INFO, " %-15s: %s\n", - M_ST_MB(char *, ol->list[n], ol->name_off), - M_ST_MB(char *, ol->list[n], ol->info_off)); + desc.name, desc.description); + } mp_msg(MSGT_CFGPARSER, MSGL_INFO, "\n"); return M_OPT_EXIT - 1; } @@ -2279,8 +2256,7 @@ static int parse_obj_settings_list(const m_option_t *opt, struct bstr name, if (op == OP_DEL) r = parse_obj_settings_del(name, ¶m, dst, mark_del); if (r == 0) { - r = parse_obj_settings(name, ¶m, opt->priv, - dst ? &res : NULL); + r = parse_obj_settings(name, ¶m, ol, dst ? &res : NULL); } if (r < 0) return r; diff --git a/core/m_option.h b/core/m_option.h index c1aac93a82..5f95232076 100644 --- a/core/m_option.h +++ b/core/m_option.h @@ -93,18 +93,30 @@ struct m_geometry { void m_geometry_apply(int *xpos, int *ypos, int *widw, int *widh, int scrw, int scrh, struct m_geometry *gm); +struct m_obj_desc { + // Name which will be used in the option string + const char *name; + // Will be printed when "help" is passed + const char *description; + // Size of the private struct + int priv_size; + // If not NULL, default values for private struct + const void *priv_defaults; + // Options which refer to members in the private struct + const struct m_option *options; + // For free use by the implementer of m_obj_list.get_desc + const void *p; +}; + // Extra definition needed for \ref m_option_type_obj_settings_list options. -typedef struct { - // Pointer to an array of pointer to some object type description struct. - void **list; - // Offset of the object type name (char*) in the description struct. - void *name_off; - // Offset of the object type info string (char*) in the description struct. - void *info_off; - // Offset of the object type parameter description (\ref m_struct_st) - // in the description struct. - void *desc_off; -} m_obj_list_t; +struct m_obj_list { + bool (*get_desc)(struct m_obj_desc *dst, int index); + const char *description; +}; + +// Find entry by name +bool m_obj_list_find(struct m_obj_desc *dst, const struct m_obj_list *list, + bstr name); // The data type used by \ref m_option_type_obj_settings_list. typedef struct m_obj_settings { @@ -559,7 +571,10 @@ int m_option_required_params(const m_option_t *opt); #define OPT_SETTINGSLIST(optname, varname, flags, objlist) \ OPT_GENERAL(m_obj_settings_t*, optname, varname, flags, \ .type = &m_option_type_obj_settings_list, \ - .priv = objlist) + .priv = (void*)MP_EXPECT_TYPE(const struct m_obj_list*, objlist)) + +#define OPT_IMAGEFORMAT(...) \ + OPT_GENERAL(int, __VA_ARGS__, .type = &m_option_type_imgfmt) #define OPT_AUDIOFORMAT(...) \ OPT_GENERAL(int, __VA_ARGS__, .type = &m_option_type_afmt) diff --git a/core/mp_common.h b/core/mp_common.h index bc6d4f3d32..71e24604ec 100644 --- a/core/mp_common.h +++ b/core/mp_common.h @@ -36,6 +36,7 @@ #define MPMAX(a, b) ((a) > (b) ? (a) : (b)) #define MPMIN(a, b) ((a) > (b) ? (b) : (a)) +#define MP_ARRAY_SIZE(s) (sizeof(s) / sizeof((s)[0])) #define CONTROL_OK 1 #define CONTROL_TRUE 1 diff --git a/core/options.c b/core/options.c index 694a1355a2..854f1bd0cb 100644 --- a/core/options.c +++ b/core/options.c @@ -181,7 +181,7 @@ extern char *dvd_device, *cdrom_device; extern double mf_fps; extern char * mf_type; -extern const m_obj_list_t vf_obj_list; +extern const struct m_obj_list vf_obj_list; static const m_option_t mfopts_conf[]={ {"fps", &mf_fps, CONF_TYPE_DOUBLE, 0, 0, 0, NULL}, @@ -436,7 +436,7 @@ const m_option_t mp_opts[] = { {"af*", &af_cfg.list, CONF_TYPE_STRING_LIST, 0, 0, 0, NULL}, - OPT_SETTINGSLIST("vf*", vf_settings, 0, (void *) &vf_obj_list), + OPT_SETTINGSLIST("vf*", vf_settings, 0, &vf_obj_list), OPT_STRING("ad", audio_decoders, 0), OPT_STRING("vd", video_decoders, 0), diff --git a/video/filter/vf.c b/video/filter/vf.c index c9fd80bceb..5d2b9b8431 100644 --- a/video/filter/vf.c +++ b/video/filter/vf.c @@ -28,7 +28,7 @@ #include "core/mp_msg.h" #include "core/m_option.h" -#include "core/m_struct.h" +#include "core/m_config.h" #include "core/options.h" @@ -115,12 +115,26 @@ static const vf_info_t *const filter_list[] = { NULL }; +static bool get_desc(struct m_obj_desc *dst, int index) +{ + if (index >= MP_ARRAY_SIZE(filter_list) - 1) + return false; + const vf_info_t *vf = filter_list[index]; + *dst = (struct m_obj_desc) { + .name = vf->name, + .description = vf->info, + .priv_size = vf->priv_size, + .priv_defaults = vf->priv_defaults, + .options = vf->options, + .p = vf, + }; + return true; +} + // For the vf option -const m_obj_list_t vf_obj_list = { - (void **)filter_list, - M_ST_OFF(vf_info_t, name), - M_ST_OFF(vf_info_t, info), - M_ST_OFF(vf_info_t, opts) +const struct m_obj_list vf_obj_list = { + .get_desc = get_desc, + .description = "video filters", }; int vf_control(struct vf_instance *vf, int cmd, void *arg) @@ -212,42 +226,34 @@ void vf_print_filter_chain(int msglevel, struct vf_instance *vf) static struct vf_instance *vf_open(struct MPOpts *opts, vf_instance_t *next, const char *name, char **args) { - vf_instance_t *vf; - int i; - for (i = 0;; i++) { - if (!filter_list[i]) { - mp_tmsg(MSGT_VFILTER, MSGL_ERR, - "Couldn't find video filter '%s'.\n", name); - return NULL; // no such filter! - } - if (!strcmp(filter_list[i]->name, name)) - break; + struct m_obj_desc desc; + if (!m_obj_list_find(&desc, &vf_obj_list, bstr0(name))) { + mp_tmsg(MSGT_VFILTER, MSGL_ERR, + "Couldn't find video filter '%s'.\n", name); + return NULL; } - vf = talloc_zero(NULL, struct vf_instance); - vf->opts = opts; - vf->info = filter_list[i]; - vf->next = next; - vf->config = vf_next_config; - vf->control = vf_next_control; - vf->query_format = vf_default_query_format; - vf->filter = vf_default_filter; - vf->out_pool = talloc_steal(vf, mp_image_pool_new(16)); - if (vf->info->opts) { // vf_vo get some special argument - const m_struct_t *st = vf->info->opts; - void *vf_priv = m_struct_alloc(st); - int n; - for (n = 0; args && args[2 * n]; n++) - m_struct_set(st, vf_priv, args[2 * n], bstr0(args[2 * n + 1])); - vf->priv = vf_priv; - args = NULL; - } else // Otherwise we should have the '_oldargs_' - if (args && !strcmp(args[0], "_oldargs_")) - args = (char **)args[1]; - else - args = NULL; + vf_instance_t *vf = talloc_zero(NULL, struct vf_instance); + *vf = (vf_instance_t) { + .info = desc.p, + .opts = opts, + .next = next, + .config = vf_next_config, + .control = vf_next_control, + .query_format = vf_default_query_format, + .filter = vf_default_filter, + .out_pool = talloc_steal(vf, mp_image_pool_new(16)), + }; + struct m_config *config = m_config_from_obj_desc(vf, &desc); + void *priv = NULL; + if (m_config_initialize_obj(config, &desc, &priv, &args) < 0) + goto error; + vf->priv = priv; int retcode = vf->info->vf_open(vf, (char *)args); - if (retcode > 0) - return vf; + if (retcode < 0) + goto error; + return vf; + +error: talloc_free(vf); return NULL; } @@ -551,9 +557,6 @@ void vf_uninit_filter(vf_instance_t *vf) if (vf->uninit) vf->uninit(vf); vf_forget_frames(vf); - const m_struct_t *st = vf->info->opts; - if (st) - m_struct_free(st, vf->priv); talloc_free(vf); } diff --git a/video/filter/vf.h b/video/filter/vf.h index b47f44a7ca..067e857f0d 100644 --- a/video/filter/vf.h +++ b/video/filter/vf.h @@ -36,8 +36,10 @@ typedef struct vf_info { const char *author; const char *comment; int (*vf_open)(struct vf_instance *vf, char *args); - // Ptr to a struct describing the options - const void *opts; + void *damn_you; + int priv_size; + const void *priv_defaults; + const struct m_option *options; } vf_info_t; struct vf_format { diff --git a/video/filter/vf_crop.c b/video/filter/vf_crop.c index 49b4e7e55b..c84dd22b84 100644 --- a/video/filter/vf_crop.c +++ b/video/filter/vf_crop.c @@ -29,7 +29,6 @@ #include "vf.h" #include "core/m_option.h" -#include "core/m_struct.h" static const struct vf_priv_s { int crop_w,crop_h; @@ -95,20 +94,13 @@ static int vf_open(vf_instance_t *vf, char *args){ return 1; } -#define ST_OFF(f) M_ST_OFF(struct vf_priv_s,f) +#define OPT_BASE_STRUCT struct vf_priv_s static const m_option_t vf_opts_fields[] = { - {"w", ST_OFF(crop_w), CONF_TYPE_INT, M_OPT_MIN,0 ,0, NULL}, - {"h", ST_OFF(crop_h), CONF_TYPE_INT, M_OPT_MIN,0 ,0, NULL}, - {"x", ST_OFF(crop_x), CONF_TYPE_INT, M_OPT_MIN,-1 ,0, NULL}, - {"y", ST_OFF(crop_y), CONF_TYPE_INT, M_OPT_MIN,-1 ,0, NULL}, - { NULL, NULL, 0, 0, 0, 0, NULL } -}; - -static const m_struct_t vf_opts = { - "crop", - sizeof(struct vf_priv_s), - &vf_priv_dflt, - vf_opts_fields + OPT_INT("w", crop_w, M_OPT_MIN, .min = 0), + OPT_INT("h", crop_h, M_OPT_MIN, .min = 0), + OPT_INT("x", crop_x, M_OPT_MIN, .min = -1), + OPT_INT("y", crop_y, M_OPT_MIN, .min = -1), + {0} }; const vf_info_t vf_info_crop = { @@ -117,7 +109,9 @@ const vf_info_t vf_info_crop = { "A'rpi", "", vf_open, - &vf_opts + .priv_size = sizeof(struct vf_priv_s), + .priv_defaults = &vf_priv_dflt, + .options = vf_opts_fields, }; //===========================================================================// diff --git a/video/filter/vf_delogo.c b/video/filter/vf_delogo.c index d90d852057..6b716cab14 100644 --- a/video/filter/vf_delogo.c +++ b/video/filter/vf_delogo.c @@ -36,14 +36,13 @@ #include "video/memcpy_pic.h" #include "core/m_option.h" -#include "core/m_struct.h" //===========================================================================// static struct vf_priv_s { unsigned int outfmt; int xoff, yoff, lw, lh, band, show; - const char *file; + char *file; struct timed_rectangle { int ts, x, y, w, h, b; } *timed_rect; @@ -304,23 +303,16 @@ static int vf_open(vf_instance_t *vf, char *args){ return 1; } -#define ST_OFF(f) M_ST_OFF(struct vf_priv_s,f) +#define OPT_BASE_STRUCT struct vf_priv_s static const m_option_t vf_opts_fields[] = { - { "x", ST_OFF(xoff), CONF_TYPE_INT, 0, 0, 0, NULL }, - { "y", ST_OFF(yoff), CONF_TYPE_INT, 0, 0, 0, NULL }, - { "w", ST_OFF(lw), CONF_TYPE_INT, 0, 0, 0, NULL }, - { "h", ST_OFF(lh), CONF_TYPE_INT, 0, 0, 0, NULL }, - { "t", ST_OFF(band), CONF_TYPE_INT, 0, 0, 0, NULL }, - { "band", ST_OFF(band), CONF_TYPE_INT, 0, 0, 0, NULL }, // alias - { "file", ST_OFF(file), CONF_TYPE_STRING, 0, 0, 0, NULL }, - { NULL, NULL, 0, 0, 0, 0, NULL } -}; - -static const m_struct_t vf_opts = { - "delogo", - sizeof(struct vf_priv_s), - &vf_priv_dflt, - vf_opts_fields + OPT_INT("x", xoff, 0), + OPT_INT("y", yoff, 0), + OPT_INT("w", lw, 0), + OPT_INT("h", lh, 0), + OPT_INT("t", band, 0), + OPT_INT("band", band, 0), // alias + OPT_STRING("file", file, 0), + {0} }; const vf_info_t vf_info_delogo = { @@ -329,7 +321,9 @@ const vf_info_t vf_info_delogo = { "Jindrich Makovicka, Alex Beregszaszi", "", vf_open, - &vf_opts + .priv_size = sizeof(struct vf_priv_s), + .priv_defaults = &vf_priv_dflt, + .options = vf_opts_fields, }; //===========================================================================// diff --git a/video/filter/vf_dlopen.c b/video/filter/vf_dlopen.c index 72e747c2a7..f40762beab 100644 --- a/video/filter/vf_dlopen.c +++ b/video/filter/vf_dlopen.c @@ -29,7 +29,6 @@ #include "vf.h" #include "core/m_option.h" -#include "core/m_struct.h" #include "vf_dlopen.h" @@ -46,9 +45,9 @@ #endif static struct vf_priv_s { - const char *cfg_dllname; + char *cfg_dllname; int cfg_argc; - const char *cfg_argv[16]; + char *cfg_argv[16]; void *dll; struct vf_dlopen_context filter; @@ -329,7 +328,9 @@ static int vf_open(vf_instance_t *vf, char *args) if (vf->priv->cfg_argv[i] == NULL) vf->priv->cfg_argv[i] = talloc_strdup (vf->priv, ""); - if (func(&vf->priv->filter, vf->priv->cfg_argc, vf->priv->cfg_argv) < 0) { + if (func(&vf->priv->filter, vf->priv->cfg_argc, + (const char **)vf->priv->cfg_argv) < 0) + { mp_msg(MSGT_VFILTER, MSGL_ERR, "function did not create a filter: %s\n", vf->priv->cfg_dllname); @@ -351,33 +352,26 @@ static int vf_open(vf_instance_t *vf, char *args) return 1; } -#define ST_OFF(f) M_ST_OFF(struct vf_priv_s, f) -static m_option_t vf_opts_fields[] = { - {"dll", ST_OFF(cfg_dllname), CONF_TYPE_STRING, 0, 0, 0, NULL}, - {"a0", ST_OFF(cfg_argv[0]), CONF_TYPE_STRING, 0, 0, 0, NULL}, - {"a1", ST_OF |