mirror of
https://github.com/alsa-project/alsa-lib.git
synced 2025-11-04 13:30:08 -05:00
pcm_ladspa - setup control outputs all times
It turned out that plugins that had control outputs were not being set up properly if there was no corresponding "output" section. Signed-off-by: Nathan Kurz <nate@verse.com>
This commit is contained in:
parent
9a8a3374a1
commit
d9cfe1e9ff
1 changed files with 170 additions and 121 deletions
|
|
@ -1211,37 +1211,87 @@ static int snd_pcm_ladspa_look_for_plugin(snd_pcm_ladspa_plugin_t * const plugin
|
||||||
return -ENOENT;
|
return -ENOENT;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int snd_pcm_ladspa_parse_ioconfig(snd_pcm_ladspa_plugin_t *lplug,
|
static int snd_pcm_ladspa_add_default_controls(snd_pcm_ladspa_plugin_t *lplug,
|
||||||
|
snd_pcm_ladspa_plugin_io_t *io)
|
||||||
|
{
|
||||||
|
unsigned int count = 0;
|
||||||
|
LADSPA_Data *array;
|
||||||
|
unsigned char *initialized;
|
||||||
|
unsigned long idx;
|
||||||
|
|
||||||
|
for (idx = 0; idx < lplug->desc->PortCount; idx++)
|
||||||
|
if ((lplug->desc->PortDescriptors[idx] & (io->pdesc | LADSPA_PORT_CONTROL)) == (io->pdesc | LADSPA_PORT_CONTROL))
|
||||||
|
count++;
|
||||||
|
array = (LADSPA_Data *)calloc(count, sizeof(LADSPA_Data));
|
||||||
|
if (!array)
|
||||||
|
return -ENOMEM;
|
||||||
|
initialized = (unsigned char *)calloc(count, sizeof(unsigned char));
|
||||||
|
if (!initialized) {
|
||||||
|
free(array);
|
||||||
|
return -ENOMEM;
|
||||||
|
}
|
||||||
|
io->controls_size = count;
|
||||||
|
io->controls_initialized = initialized;
|
||||||
|
io->controls = array;
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int snd_pcm_ladspa_parse_controls(snd_pcm_ladspa_plugin_t *lplug,
|
||||||
snd_pcm_ladspa_plugin_io_t *io,
|
snd_pcm_ladspa_plugin_io_t *io,
|
||||||
snd_config_t *conf)
|
snd_config_t *controls)
|
||||||
{
|
{
|
||||||
snd_config_iterator_t i, next;
|
snd_config_iterator_t i, next;
|
||||||
snd_config_t *bindings = NULL, *controls = NULL;
|
|
||||||
int err;
|
int err;
|
||||||
|
|
||||||
if (conf == NULL)
|
if (snd_config_get_type(controls) != SND_CONFIG_TYPE_COMPOUND) {
|
||||||
return 0;
|
SNDERR("controls definition must be a compound");
|
||||||
if (snd_config_get_type(conf) != SND_CONFIG_TYPE_COMPOUND) {
|
|
||||||
SNDERR("input or output definition must be a compound");
|
|
||||||
return -EINVAL;
|
return -EINVAL;
|
||||||
}
|
}
|
||||||
snd_config_for_each(i, next, conf) {
|
|
||||||
|
snd_config_for_each(i, next, controls) {
|
||||||
snd_config_t *n = snd_config_iterator_entry(i);
|
snd_config_t *n = snd_config_iterator_entry(i);
|
||||||
const char *id;
|
const char *id;
|
||||||
|
long lval;
|
||||||
|
unsigned int port, uval;
|
||||||
|
double dval;
|
||||||
if (snd_config_get_id(n, &id) < 0)
|
if (snd_config_get_id(n, &id) < 0)
|
||||||
continue;
|
continue;
|
||||||
if (strcmp(id, "bindings") == 0) {
|
err = safe_strtol(id, &lval);
|
||||||
bindings = n;
|
if (err >= 0) {
|
||||||
continue;
|
err = snd_pcm_ladspa_find_port(&port, lplug, io->pdesc | LADSPA_PORT_CONTROL, lval);
|
||||||
|
} else {
|
||||||
|
err = snd_pcm_ladspa_find_sport(&port, lplug, io->pdesc | LADSPA_PORT_CONTROL, id);
|
||||||
}
|
}
|
||||||
if (strcmp(id, "controls") == 0) {
|
if (err < 0) {
|
||||||
controls = n;
|
SNDERR("Unable to find an control port (%s)", id);
|
||||||
continue;
|
return err;
|
||||||
}
|
}
|
||||||
|
if (snd_config_get_ireal(n, &dval) < 0) {
|
||||||
|
SNDERR("Control port %s has not an float or integer value", id);
|
||||||
|
return err;
|
||||||
}
|
}
|
||||||
if (bindings) {
|
err = snd_pcm_ladspa_find_port_idx(&uval, lplug, io->pdesc | LADSPA_PORT_CONTROL, port);
|
||||||
|
if (err < 0) {
|
||||||
|
SNDERR("internal error");
|
||||||
|
return err;
|
||||||
|
}
|
||||||
|
io->controls_initialized[uval] = 1;
|
||||||
|
io->controls[uval] = (LADSPA_Data)dval;
|
||||||
|
}
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int snd_pcm_ladspa_parse_bindings(snd_pcm_ladspa_plugin_t *lplug,
|
||||||
|
snd_pcm_ladspa_plugin_io_t *io,
|
||||||
|
snd_config_t *bindings)
|
||||||
|
{
|
||||||
unsigned int count = 0;
|
unsigned int count = 0;
|
||||||
unsigned int *array;
|
unsigned int *array;
|
||||||
|
snd_config_iterator_t i, next;
|
||||||
|
int err;
|
||||||
|
|
||||||
if (snd_config_get_type(bindings) != SND_CONFIG_TYPE_COMPOUND) {
|
if (snd_config_get_type(bindings) != SND_CONFIG_TYPE_COMPOUND) {
|
||||||
SNDERR("bindings definition must be a compound");
|
SNDERR("bindings definition must be a compound");
|
||||||
return -EINVAL;
|
return -EINVAL;
|
||||||
|
|
@ -1303,63 +1353,62 @@ static int snd_pcm_ladspa_parse_ioconfig(snd_pcm_ladspa_plugin_t *lplug,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int snd_pcm_ladspa_parse_ioconfig(snd_pcm_ladspa_plugin_t *lplug,
|
||||||
|
snd_pcm_ladspa_plugin_io_t *io,
|
||||||
|
snd_config_t *conf)
|
||||||
|
{
|
||||||
|
snd_config_iterator_t i, next;
|
||||||
|
snd_config_t *bindings = NULL, *controls = NULL;
|
||||||
|
int err;
|
||||||
|
|
||||||
|
/* always add default controls for both input and output */
|
||||||
|
err = snd_pcm_ladspa_add_default_controls(lplug, io);
|
||||||
|
if (err < 0) {
|
||||||
|
SNDERR("error adding default controls");
|
||||||
|
return err;
|
||||||
}
|
}
|
||||||
if (1) {
|
|
||||||
unsigned int count = 0;
|
if (conf == NULL) {
|
||||||
LADSPA_Data *array;
|
return 0;
|
||||||
unsigned char *initialized;
|
|
||||||
unsigned long idx;
|
|
||||||
for (idx = 0; idx < lplug->desc->PortCount; idx++)
|
|
||||||
if ((lplug->desc->PortDescriptors[idx] & (io->pdesc | LADSPA_PORT_CONTROL)) == (io->pdesc | LADSPA_PORT_CONTROL))
|
|
||||||
count++;
|
|
||||||
array = (LADSPA_Data *)calloc(count, sizeof(LADSPA_Data));
|
|
||||||
if (!array)
|
|
||||||
return -ENOMEM;
|
|
||||||
initialized = (unsigned char *)calloc(count, sizeof(unsigned char));
|
|
||||||
if (!initialized) {
|
|
||||||
free(array);
|
|
||||||
return -ENOMEM;
|
|
||||||
}
|
}
|
||||||
io->controls_size = count;
|
|
||||||
io->controls_initialized = initialized;
|
if (snd_config_get_type(conf) != SND_CONFIG_TYPE_COMPOUND) {
|
||||||
io->controls = array;
|
SNDERR("input or output definition must be a compound");
|
||||||
if (!(io->pdesc & LADSPA_PORT_OUTPUT)) {
|
|
||||||
if (snd_config_get_type(controls) != SND_CONFIG_TYPE_COMPOUND) {
|
|
||||||
SNDERR("controls definition must be a compound");
|
|
||||||
return -EINVAL;
|
return -EINVAL;
|
||||||
}
|
}
|
||||||
snd_config_for_each(i, next, controls) {
|
snd_config_for_each(i, next, conf) {
|
||||||
snd_config_t *n = snd_config_iterator_entry(i);
|
snd_config_t *n = snd_config_iterator_entry(i);
|
||||||
const char *id;
|
const char *id;
|
||||||
long lval;
|
|
||||||
unsigned int port, uval;
|
|
||||||
double dval;
|
|
||||||
if (snd_config_get_id(n, &id) < 0)
|
if (snd_config_get_id(n, &id) < 0)
|
||||||
continue;
|
continue;
|
||||||
err = safe_strtol(id, &lval);
|
if (strcmp(id, "bindings") == 0) {
|
||||||
if (err >= 0) {
|
bindings = n;
|
||||||
err = snd_pcm_ladspa_find_port(&port, lplug, io->pdesc | LADSPA_PORT_CONTROL, lval);
|
continue;
|
||||||
} else {
|
|
||||||
err = snd_pcm_ladspa_find_sport(&port, lplug, io->pdesc | LADSPA_PORT_CONTROL, id);
|
|
||||||
}
|
}
|
||||||
if (err < 0) {
|
if (strcmp(id, "controls") == 0) {
|
||||||
SNDERR("Unable to find an control port (%s)", id);
|
controls = n;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/* ignore values of parameters for output controls */
|
||||||
|
if (controls && !(io->pdesc & LADSPA_PORT_OUTPUT)) {
|
||||||
|
err = snd_pcm_ladspa_parse_controls(lplug, io, controls);
|
||||||
|
if (err < 0)
|
||||||
return err;
|
return err;
|
||||||
}
|
}
|
||||||
if (snd_config_get_ireal(n, &dval) < 0) {
|
|
||||||
SNDERR("Control port %s has not an float or integer value", id);
|
if (bindings) {
|
||||||
|
err = snd_pcm_ladspa_parse_bindings(lplug, io, bindings);
|
||||||
|
if (err < 0)
|
||||||
return err;
|
return err;
|
||||||
}
|
}
|
||||||
err = snd_pcm_ladspa_find_port_idx(&uval, lplug, io->pdesc | LADSPA_PORT_CONTROL, port);
|
|
||||||
if (err < 0) {
|
|
||||||
SNDERR("internal error");
|
|
||||||
return err;
|
|
||||||
}
|
|
||||||
initialized[uval] = 1;
|
|
||||||
array[uval] = (LADSPA_Data)dval;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue