From 868417b995e35c129eb2e76e5764521e4701dc9e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?IOhannes=20m=20zm=C3=B6lnig?= Date: Mon, 7 Jun 2010 14:30:35 +0000 Subject: fixed crasher bugs, workaround issues with locales; minor beautifications this should fix most crasher bugs with plugin~, when no (ladspa) plugin could be loaded; also: when the LANG is set to non-C (e.g. "de"), the text in all boxes would vanish; fixed this by pushing the LANG to C also: use verbose/error where appropriate; use A_SYMBOL rather than A_DEFSYM and then checking whether a symbol has been given TODO: use of locale.h should be made optional svn path=/trunk/externals/plugin~/; revision=13604 --- plugin~.c | 1560 ++++++++++++++++++++++++++++++++----------------------------- 1 file changed, 809 insertions(+), 751 deletions(-) diff --git a/plugin~.c b/plugin~.c index 9777a94..e28c107 100644 --- a/plugin~.c +++ b/plugin~.c @@ -25,288 +25,338 @@ #include "plugin~.h" #include "jutils.h" + #ifndef MIN #define MIN(a,b) ((a)<(b)?(a):(b)) #endif +#define HAVE_LOCALE_H +#ifdef HAVE_LOCALE_H +# include + +static char*s_locale=NULL; +static void plugin_tilde_pushlocale(void) +{ + if(s_locale)verbose(2, "pushing locale '%s'", s_locale); + s_locale=setlocale(LC_NUMERIC, NULL); + setlocale(LC_NUMERIC, "C"); +} + +static void plugin_tilde_poplocale(void) +{ + if(!s_locale)verbose(2, "popping empty locale"); + setlocale(LC_NUMERIC, s_locale); + s_locale=NULL; +} +#else +static void plugin_tilde_pushlocale(void) { + static int again=0; + if(!again) { + verbose(1, "plugins~: couldn't modify locales"); + verbose(1, " if you experience weird characters try running Pd with LANG=C"); + } + again=1; +} +static void plugin_tilde_poplocale (void) {} +#endif + +static int plugin_tilde_have_plugin(Pd_Plugin_Tilde* x); + static t_class* plugin_tilde_class = NULL; void plugin_tilde_setup (void) { - /* Make a new Pd class with 2 string creation parameters */ - plugin_tilde_class = class_new (gensym ("plugin~"), - (t_newmethod)plugin_tilde_new, - (t_method)plugin_tilde_free, - sizeof (Pd_Plugin_Tilde), - 0, - A_DEFSYM, A_DEFSYM, 0); - assert (plugin_tilde_class != NULL); - - /* Let's be explicit in not converting the signals in any way */ - assert (sizeof (float) == sizeof (t_float)); - - assert (sizeof (float) == sizeof (LADSPA_Data)); - - class_addmethod (plugin_tilde_class,(t_method)plugin_tilde_dsp,gensym ("dsp"),0); - class_addmethod (plugin_tilde_class,(t_method)plugin_tilde_control,gensym ("control"),A_DEFSYM, A_DEFFLOAT, 0); - class_addmethod (plugin_tilde_class,(t_method)plugin_tilde_info,gensym ("info"),0); - class_addmethod (plugin_tilde_class,(t_method)plugin_tilde_list,gensym ("listplugins"),0); - class_addmethod (plugin_tilde_class,(t_method)plugin_tilde_plug,gensym ("plug"),A_DEFSYM,0); - class_addmethod (plugin_tilde_class,(t_method)plugin_tilde_active,gensym ("active"),A_DEFFLOAT,0); - class_addmethod (plugin_tilde_class,(t_method)plugin_tilde_reset,gensym ("reset"),0); - class_addmethod (plugin_tilde_class,nullfn,gensym ("signal"),0); + /* Make a new Pd class with 2 string creation parameters */ + plugin_tilde_class = class_new (gensym ("plugin~"), + (t_newmethod)plugin_tilde_new, + (t_method)plugin_tilde_free, + sizeof (Pd_Plugin_Tilde), + 0, + A_DEFSYM, A_DEFSYM, 0); + assert (plugin_tilde_class != NULL); + + /* Let's be explicit in not converting the signals in any way */ + assert (sizeof (float) == sizeof (t_float)); + + assert (sizeof (float) == sizeof (LADSPA_Data)); + + class_addmethod (plugin_tilde_class,(t_method)plugin_tilde_dsp,gensym ("dsp"),0); + class_addmethod (plugin_tilde_class,(t_method)plugin_tilde_control,gensym ("control"),A_SYMBOL, A_FLOAT, 0); + class_addmethod (plugin_tilde_class,(t_method)plugin_tilde_info,gensym ("info"),0); + class_addmethod (plugin_tilde_class,(t_method)plugin_tilde_list,gensym ("listplugins"),0); + class_addmethod (plugin_tilde_class,(t_method)plugin_tilde_plug,gensym ("plug"),A_SYMBOL,0); + class_addmethod (plugin_tilde_class,(t_method)plugin_tilde_active,gensym ("active"),A_FLOAT,0); + class_addmethod (plugin_tilde_class,(t_method)plugin_tilde_reset,gensym ("reset"),0); + class_addmethod (plugin_tilde_class,nullfn,gensym ("signal"),0); } static void* plugin_tilde_new (t_symbol* s_name, t_symbol* s_lib_name) { - Pd_Plugin_Tilde* x = NULL; - unsigned i = 0; + Pd_Plugin_Tilde* x = NULL; + unsigned i = 0; - /* Allocate object struct */ - x = (Pd_Plugin_Tilde*)pd_new (plugin_tilde_class); - assert (x != NULL); + /* Allocate object struct */ + x = (Pd_Plugin_Tilde*)pd_new (plugin_tilde_class); + assert (x != NULL); - /* Initialize object struct */ - x->plugin_library = NULL; - x->plugin_library_filename = NULL; - x->num_audio_inputs = 2; - x->num_audio_outputs = 2; - x->num_control_inputs = 1; - x->num_control_outputs = 1; - x->audio_inlets = NULL; - x->audio_outlets = NULL; - x->control_outlet = NULL; - x->dsp_vec = NULL; - x->dsp_vec_length = 0; - x->dsp_active = 0; - - if (s_name->s_name != NULL) { - if (s_lib_name->s_name == NULL || strlen (s_lib_name->s_name) == 0) - x->plugin_library_filename = plugin_tilde_search_plugin (x, s_name->s_name); - else - x->plugin_library_filename = strdup (s_lib_name->s_name); - if (x->plugin_library_filename != NULL) { - if (plugin_tilde_open_plugin (x, - s_name->s_name, - x->plugin_library_filename, - (unsigned long)sys_getsr ())) - post("plugin~: Unable to open plugin"); - } - } - - /* Create in- and outlet(s) */ + plugin_tilde_pushlocale(); - /* Allocate memory for in- and outlet pointers */ - x->audio_inlets = (t_inlet**)calloc (x->num_audio_inputs, sizeof (t_inlet*)); - x->audio_outlets = (t_outlet**)calloc (x->num_audio_outputs, sizeof (t_outlet*)); + /* Initialize object struct */ + x->plugin_library = NULL; + x->plugin_library_filename = NULL; + x->num_audio_inputs = 2; + x->num_audio_outputs = 2; + x->num_control_inputs = 1; + x->num_control_outputs = 1; + x->audio_inlets = NULL; + x->audio_outlets = NULL; + x->control_outlet = NULL; + x->dsp_vec = NULL; + x->dsp_vec_length = 0; + x->dsp_active = 0; + + if (s_name->s_name != NULL) { + if (s_lib_name->s_name == NULL || strlen (s_lib_name->s_name) == 0) + x->plugin_library_filename = plugin_tilde_search_plugin (x, s_name->s_name); + else + x->plugin_library_filename = strdup (s_lib_name->s_name); - /* The first inlet is always there (needn't be created), and is - used for control messages. Now, create the rest of the - inlets for audio signal input. */ - for (i = 0; i < x->num_audio_inputs; i++) { - x->audio_inlets[i] = inlet_new (&x->x_obj, - &x->x_obj.ob_pd, - gensym ("signal"), - gensym ("signal")); + if (x->plugin_library_filename != NULL) { + if (plugin_tilde_open_plugin (x, + s_name->s_name, + x->plugin_library_filename, + (unsigned long)sys_getsr ())) { + error("plugin~: Unable to open plugin '%s' in '%s'", s_name->s_name, x->plugin_library_filename); + plugin_tilde_ladspa_close_plugin (x); + } } + } + + /* Create in- and outlet(s) */ + + /* Allocate memory for in- and outlet pointers */ + x->audio_inlets = (t_inlet**)calloc (x->num_audio_inputs, sizeof (t_inlet*)); + x->audio_outlets = (t_outlet**)calloc (x->num_audio_outputs, sizeof (t_outlet*)); + + /* The first inlet is always there (needn't be created), and is + used for control messages. Now, create the rest of the + inlets for audio signal input. */ + for (i = 0; i < x->num_audio_inputs; i++) { + x->audio_inlets[i] = inlet_new (&x->x_obj, + &x->x_obj.ob_pd, + gensym ("signal"), + gensym ("signal")); + } - /* We use the first outlet always for LADSPA/VST parameter control - messages */ - x->control_outlet = outlet_new (&x->x_obj, gensym ("control")); - - /* The rest of the outlets are used for audio signal output */ - for (i = 0; i < x->num_audio_outputs; i++) { - x->audio_outlets[i] = outlet_new (&x->x_obj, gensym ("signal")); - } + /* We use the first outlet always for LADSPA/VST parameter control + messages */ + x->control_outlet = outlet_new (&x->x_obj, gensym ("control")); - /* Allocate memory for DSP parameters */ - x->dsp_vec_length = x->num_audio_inputs + x->num_audio_outputs + 2; - x->dsp_vec = (t_int*)calloc (x->dsp_vec_length, sizeof (t_int)); - assert (x->dsp_vec != NULL); + /* The rest of the outlets are used for audio signal output */ + for (i = 0; i < x->num_audio_outputs; i++) { + x->audio_outlets[i] = outlet_new (&x->x_obj, gensym ("signal")); + } - return x; + /* Allocate memory for DSP parameters */ + x->dsp_vec_length = x->num_audio_inputs + x->num_audio_outputs + 2; + x->dsp_vec = (t_int*)calloc (x->dsp_vec_length, sizeof (t_int)); + assert (x->dsp_vec != NULL); + plugin_tilde_poplocale(); + return x; } static void plugin_tilde_free (Pd_Plugin_Tilde* x) { - unsigned i = 0; + unsigned i = 0; + plugin_tilde_pushlocale(); - /* precondition(s) */ - assert (x != NULL); + /* precondition(s) */ + assert (x != NULL); - /* Unload LADSPA/VST plugin */ - plugin_tilde_close_plugin (x); + /* Unload LADSPA/VST plugin */ + plugin_tilde_close_plugin (x); - /* Free DSP parameter memory */ - if (x->dsp_vec != NULL) { - free (x->dsp_vec); - x->dsp_vec = NULL; - x->dsp_vec_length = 0; - } + /* Free DSP parameter memory */ + if (x->dsp_vec != NULL) { + free (x->dsp_vec); + x->dsp_vec = NULL; + x->dsp_vec_length = 0; + } - /* Destroy inlets */ - if (x->audio_inlets != NULL) { - for (i = 0; i < x->num_audio_inputs; i++) { + /* Destroy inlets */ + if (x->audio_inlets != NULL) { + for (i = 0; i < x->num_audio_inputs; i++) { inlet_free (x->audio_inlets[i]); - } - free (x->audio_inlets); - x->audio_inlets = NULL; } + free (x->audio_inlets); + x->audio_inlets = NULL; + } - /* Destroy outlets */ - if (x->control_outlet != NULL) { - outlet_free (x->control_outlet); - x->control_outlet = NULL; - } - if (x->audio_outlets != NULL) { - for (i = 0; i < x->num_audio_outputs; i++) { + /* Destroy outlets */ + if (x->control_outlet != NULL) { + outlet_free (x->control_outlet); + x->control_outlet = NULL; + } + if (x->audio_outlets != NULL) { + for (i = 0; i < x->num_audio_outputs; i++) { outlet_free (x->audio_outlets[i]); - } - free (x->audio_outlets); - x->audio_outlets = NULL; } + free (x->audio_outlets); + x->audio_outlets = NULL; + } - if (x->plugin_library_filename != NULL) { - free ((void*)x->plugin_library_filename); - x->plugin_library_filename = NULL; - } + if (x->plugin_library_filename != NULL) { + free ((void*)x->plugin_library_filename); + x->plugin_library_filename = NULL; + } + plugin_tilde_poplocale(); } static void plugin_tilde_dsp (Pd_Plugin_Tilde* x, t_signal** sp) { - unsigned i = 0; - unsigned long num_samples; + unsigned i = 0; + unsigned long num_samples; - num_samples = sp[0]->s_n; + num_samples = sp[0]->s_n; - /* Pack vector of parameters for DSP routine */ - x->dsp_vec[0] = (t_int)x; - x->dsp_vec[1] = (t_int)num_samples; - /* Inputs are before outputs; ignore the first "null" input */ - for (i = 2; i < x->dsp_vec_length; i++) { - x->dsp_vec[i] = (t_int)(sp[i - 1]->s_vec); - } + /* Pack vector of parameters for DSP routine */ + x->dsp_vec[0] = (t_int)x; + x->dsp_vec[1] = (t_int)num_samples; + /* Inputs are before outputs; ignore the first "null" input */ + for (i = 2; i < x->dsp_vec_length; i++) { + x->dsp_vec[i] = (t_int)(sp[i - 1]->s_vec); + } - /* Connect audio ports with buffers (this is only done when DSP - processing begins) */ - plugin_tilde_connect_audio (x, - (float**)(&x->dsp_vec[2]), - (float**)(&x->dsp_vec[2 + x->num_audio_inputs]), - num_samples); + /* Connect audio ports with buffers (this is only done when DSP + processing begins) */ + plugin_tilde_connect_audio (x, + (float**)(&x->dsp_vec[2]), + (float**)(&x->dsp_vec[2 + x->num_audio_inputs]), + num_samples); - /* add DSP routine to Pd's DSP chain */ - dsp_addv (plugin_tilde_perform, x->dsp_vec_length, x->dsp_vec); + /* add DSP routine to Pd's DSP chain */ + dsp_addv (plugin_tilde_perform, x->dsp_vec_length, x->dsp_vec); } static t_int* plugin_tilde_perform (t_int* w) { - Pd_Plugin_Tilde* x = NULL; - t_float** audio_inputs = NULL; - t_float** audio_outputs = NULL; - int num_samples = 0; + Pd_Plugin_Tilde* x = NULL; + t_float** audio_inputs = NULL; + t_float** audio_outputs = NULL; + int num_samples = 0; - /* precondition(s) */ - assert (w != NULL); + /* precondition(s) */ + assert (w != NULL); - /* Unpack DSP parameter vector */ - x = (Pd_Plugin_Tilde*)(w[1]); - num_samples = (int)(w[2]); - audio_inputs = (t_float**)(&w[3]); - audio_outputs = (t_float**)(&w[3 + x->num_audio_inputs]); - - /* Call the LADSPA/VST plugin */ - plugin_tilde_apply_plugin (x); - - return w + (x->dsp_vec_length + 1); + /* Unpack DSP parameter vector */ + x = (Pd_Plugin_Tilde*)(w[1]); + num_samples = (int)(w[2]); + audio_inputs = (t_float**)(&w[3]); + audio_outputs = (t_float**)(&w[3 + x->num_audio_inputs]); + /* Call the LADSPA/VST plugin */ + plugin_tilde_apply_plugin (x); + return w + (x->dsp_vec_length + 1); } void plugin_tilde_emit_control_output (Pd_Plugin_Tilde* x, - const char* name, - float new_value, - int output_port_index) + const char* name, + float new_value, + int output_port_index) { - /* Construct and outlet a "control" message with three Pd atoms */ - t_atom anything_atoms[3]; - anything_atoms[0].a_type = A_SYMBOL; - anything_atoms[0].a_w.w_symbol = gensym ((char*)name); - anything_atoms[1].a_type = A_FLOAT; - anything_atoms[1].a_w.w_float = new_value; - anything_atoms[2].a_type = A_FLOAT; - anything_atoms[2].a_w.w_float = output_port_index; - outlet_anything (x->control_outlet, gensym ("control"), 3, anything_atoms); + /* Construct and outlet a "control" message with three Pd atoms */ + t_atom anything_atoms[3]; + anything_atoms[0].a_type = A_SYMBOL; + anything_atoms[0].a_w.w_symbol = gensym ((char*)name); + anything_atoms[1].a_type = A_FLOAT; + anything_atoms[1].a_w.w_float = new_value; + anything_atoms[2].a_type = A_FLOAT; + anything_atoms[2].a_w.w_float = output_port_index; + outlet_anything (x->control_outlet, gensym ("control"), 3, anything_atoms); } static void plugin_tilde_control (Pd_Plugin_Tilde* x, - t_symbol* ctrl_name, - t_float ctrl_value) - /* Change the value of a named control port of the plug-in */ + t_symbol* ctrl_name, + t_float ctrl_value) +/* Change the value of a named control port of the plug-in */ { - unsigned parm_num = 0; + unsigned parm_num = 0; + plugin_tilde_pushlocale(); - /* precondition(s) */ - assert (x != NULL); - /* FIXME we assert that the plug-in is already properly opened */ + /* precondition(s) */ + assert (x != NULL); + /* FIXME we assert that the plug-in is already properly opened */ - if (ctrl_name->s_name == NULL || strlen (ctrl_name->s_name) == 0) { - post("plugin~: control messages must have a name and a value"); - return; - } - parm_num = plugin_tilde_get_parm_number (x, ctrl_name->s_name); - if (parm_num) { - plugin_tilde_set_control_input_by_index (x, parm_num - 1, ctrl_value); - } - else { - plugin_tilde_set_control_input_by_name (x, ctrl_name->s_name, ctrl_value); - } -} + if (ctrl_name->s_name == NULL || strlen (ctrl_name->s_name) == 0) { + pd_error(x, "plugin~: control messages must have a name and a value"); + return; + } + + if(!plugin_tilde_have_plugin(x))return; + + parm_num = plugin_tilde_get_parm_number (x, ctrl_name->s_name); + if (parm_num) { + plugin_tilde_set_control_input_by_index (x, parm_num - 1, ctrl_value); + } + else { + plugin_tilde_set_control_input_by_name (x, ctrl_name->s_name, ctrl_value); + } + plugin_tilde_poplocale();} static void plugin_tilde_info (Pd_Plugin_Tilde* x) { - unsigned port_index = 0; - t_atom at[5]; - LADSPA_PortDescriptor port_type; - LADSPA_PortRangeHintDescriptor iHintDescriptor; - at[0].a_type = A_SYMBOL; - at[1].a_type = A_SYMBOL; - at[2].a_type = A_SYMBOL; - at[3].a_type = A_FLOAT; - at[4].a_type = A_FLOAT; - - for (port_index = 0; port_index < x->plugin.ladspa.type->PortCount; port_index++) { - port_type = x->plugin.ladspa.type->PortDescriptors[port_index]; - iHintDescriptor = x->plugin.ladspa.type->PortRangeHints[port_index].HintDescriptor; - - if (LADSPA_IS_PORT_INPUT (port_type)) - at[0].a_w.w_symbol = gensym ("in"); - else if (LADSPA_IS_PORT_OUTPUT (port_type)) - at[0].a_w.w_symbol = gensym ("out"); - if (LADSPA_IS_PORT_CONTROL (port_type)) - at[1].a_w.w_symbol = gensym ("control"); - else if (LADSPA_IS_PORT_AUDIO (port_type)) - at[1].a_w.w_symbol = gensym ("audio"); - at[2].a_w.w_symbol = gensym ((char*)x->plugin.ladspa.type->PortNames[port_index]); - if (LADSPA_IS_HINT_BOUNDED_BELOW(iHintDescriptor)) - at[3].a_w.w_float = x->plugin.ladspa.type->PortRangeHints[port_index].LowerBound; - else - at[3].a_w.w_float = 0; - if (LADSPA_IS_HINT_BOUNDED_ABOVE(iHintDescriptor)) - at[4].a_w.w_float = x->plugin.ladspa.type->PortRangeHints[port_index].UpperBound; - else - at[4].a_w.w_float = 1; - - outlet_anything (x->control_outlet, gensym ("port"), 5, at); - } + unsigned port_index = 0; + t_atom at[5]; + LADSPA_PortDescriptor port_type; + LADSPA_PortRangeHintDescriptor iHintDescriptor; + + if(!plugin_tilde_have_plugin(x))return; + plugin_tilde_pushlocale(); + + at[0].a_type = A_SYMBOL; + at[1].a_type = A_SYMBOL; + at[2].a_type = A_SYMBOL; + at[3].a_type = A_FLOAT; + at[4].a_type = A_FLOAT; + + for (port_index = 0; port_index < x->plugin.ladspa.type->PortCount; port_index++) { + port_type = x->plugin.ladspa.type->PortDescriptors[port_index]; + iHintDescriptor = x->plugin.ladspa.type->PortRangeHints[port_index].HintDescriptor; + + if (LADSPA_IS_PORT_INPUT (port_type)) + at[0].a_w.w_symbol = gensym ("in"); + else if (LADSPA_IS_PORT_OUTPUT (port_type)) + at[0].a_w.w_symbol = gensym ("out"); + if (LADSPA_IS_PORT_CONTROL (port_type)) + at[1].a_w.w_symbol = gensym ("control"); + else if (LADSPA_IS_PORT_AUDIO (port_type)) + at[1].a_w.w_symbol = gensym ("audio"); + at[2].a_w.w_symbol = gensym ((char*)x->plugin.ladspa.type->PortNames[port_index]); + if (LADSPA_IS_HINT_BOUNDED_BELOW(iHintDescriptor)) + at[3].a_w.w_float = x->plugin.ladspa.type->PortRangeHints[port_index].LowerBound; + else + at[3].a_w.w_float = 0; + if (LADSPA_IS_HINT_BOUNDED_ABOVE(iHintDescriptor)) + at[4].a_w.w_float = x->plugin.ladspa.type->PortRangeHints[port_index].UpperBound; + else + at[4].a_w.w_float = 1; + + outlet_anything (x->control_outlet, gensym ("port"), 5, at); + } + plugin_tilde_poplocale(); } static void plugin_tilde_list (Pd_Plugin_Tilde* x) { void* user_data[1]; user_data[0] = x; + plugin_tilde_pushlocale(); LADSPAPluginSearch(plugin_tilde_ladspa_describe,(void*)user_data); + plugin_tilde_poplocale(); + } static void plugin_tilde_ladspa_describe(const char * pcFullFilename, - void * pvPluginHandle, - LADSPA_Descriptor_Function fDescriptorFunction, void* user_data) { + void * pvPluginHandle, + LADSPA_Descriptor_Function fDescriptorFunction, void* user_data) { Pd_Plugin_Tilde* x = (((void**)user_data)[0]); t_atom at[1]; @@ -347,751 +397,759 @@ static void plugin_tilde_plug (Pd_Plugin_Tilde* x, t_symbol* plug_name) { x->plugin_library_filename = NULL; x->plugin_library_filename = plugin_tilde_search_plugin (x, plug_name->s_name); if (x->plugin_library_filename == NULL) - post("plugin~: plugin not found in any library"); + error("plugin~: plugin not found in any library"); if (plugin_tilde_open_plugin (x, plug_name->s_name, x->plugin_library_filename,(unsigned long)sys_getsr ())) - post("plugin~: Unable to open plugin"); + error("plugin~: Unable to open plugin"); } static void plugin_tilde_reset (Pd_Plugin_Tilde* x) { - /* precondition(s) */ - assert (x != NULL); + /* precondition(s) */ + assert (x != NULL); - plugin_tilde_ladspa_reset (x); + plugin_tilde_ladspa_reset (x); } static unsigned plugin_tilde_get_parm_number (Pd_Plugin_Tilde* x, - const char* str) + const char* str) /* find out if str points to a parameter number or not and return the number or zero. The number string has to begin with a '#' character */ { - long num = 0; - char* strend = NULL; + long num = 0; + char* strend = NULL; - assert (x != NULL); - if (str == NULL) { - return 0; - } - if (str[0] != '#') { - return 0; - } - num = strtol (&str[1], &strend, 10); - if (str[1] == 0 || *strend != 0) { - /* invalid string */ - return 0; - } - else if (num >= 1 && num <= (long)x->num_control_inputs) { - /* string ok and within range */ - return (unsigned)num; - } - else { - /* number out of range */ - return 0; - } + assert (x != NULL); + if (str == NULL) { + return 0; + } + if (str[0] != '#') { + return 0; + } + num = strtol (&str[1], &strend, 10); + if (str[1] == 0 || *strend != 0) { + /* invalid string */ + return 0; + } + else if (num >= 1 && num <= (long)x->num_control_inputs) { + /* string ok and within range */ + return (unsigned)num; + } + else { + /* number out of range */ + return 0; + } } static const char* plugin_tilde_search_plugin (Pd_Plugin_Tilde* x, - const char* name) + const char* name) { - - return plugin_tilde_ladspa_search_plugin (x, name); - - + return plugin_tilde_ladspa_search_plugin (x, name); } static int plugin_tilde_open_plugin (Pd_Plugin_Tilde* x, - const char* name, - const char* lib_name, - unsigned long sample_rate) + const char* name, + const char* lib_name, + unsigned long sample_rate) { - int ret = 0; - - - post("plugin~: open_plugin (x, \"%s\", \"%s\", %ld);", - name, lib_name, sample_rate); - + int ret = 0; + verbose(2, "plugin~: open_plugin (x, \"%s\", \"%s\", %ld);", name, lib_name, sample_rate); - ret = plugin_tilde_ladspa_open_plugin (x, name, lib_name, sample_rate); + ret = plugin_tilde_ladspa_open_plugin (x, name, lib_name, sample_rate); - if (ret == 0) { - x->dsp_active = 1; - post("plugin~: plugin active"); - } - - // plugin_tilde_info (x); - - return ret; + if (ret == 0) { + x->dsp_active = 1; + verbose(1, "plugin~: plugin active"); + } + // plugin_tilde_info (x); + return ret; } static void plugin_tilde_close_plugin (Pd_Plugin_Tilde* x) { - post("plugin~: close_plugin (x)"); - - - - plugin_tilde_ladspa_close_plugin (x); - - - - - post("plugin~: destructed plugin successfully"); - + verbose(2, "plugin~: close_plugin (x)"); + plugin_tilde_ladspa_close_plugin (x); + verbose(1, "plugin~: destructed plugin successfully"); } static void plugin_tilde_apply_plugin (Pd_Plugin_Tilde* x) { - if (x->dsp_active == 1) plugin_tilde_ladspa_apply_plugin (x); - } static void plugin_tilde_connect_audio (Pd_Plugin_Tilde* x, - float** audio_inputs, - float** audio_outputs, - unsigned long num_samples) + float** audio_inputs, + float** audio_outputs, + unsigned long num_samples) { - - plugin_tilde_ladspa_connect_audio (x, audio_inputs, audio_outputs, - num_samples); - - + plugin_tilde_ladspa_connect_audio (x, audio_inputs, audio_outputs, + num_samples); } static void plugin_tilde_set_control_input_by_name (Pd_Plugin_Tilde* x, - const char* name, - float value) + const char* name, + float value) { - - plugin_tilde_ladspa_set_control_input_by_name (x, name, value); - - + plugin_tilde_ladspa_set_control_input_by_name (x, name, value); } static void plugin_tilde_set_control_input_by_index (Pd_Plugin_Tilde* x, - unsigned index_, - float value) + unsigned index_, + float value) /* plugin~.c:535: warning: declaration of `index' shadows global declaration */ { - - plugin_tilde_ladspa_set_control_input_by_index (x, index_, value); - - + plugin_tilde_ladspa_set_control_input_by_index (x, index_, value); } const char* plugin_tilde_ladspa_search_plugin (Pd_Plugin_Tilde* x, - const char* name) + const char* name) { - char* lib_name = NULL; - void* user_data[2]; + char* lib_name = NULL; + void* user_data[2]; - user_data[0] = (void*)(&lib_name); - user_data[1] = (void*)name; + user_data[0] = (void*)(&lib_name); + user_data[1] = (void*)name; - lib_name = NULL; - LADSPAPluginSearch (plugin_tilde_ladspa_search_plugin_callback, - (void*)user_data); + lib_name = NULL; + LADSPAPluginSearch (plugin_tilde_ladspa_search_plugin_callback, + (void*)user_data); - /* The callback (allocates and) writes lib_name, if it finds the plugin */ - return lib_name; + /* The callback (allocates and) writes lib_name, if it finds the plugin */ + return lib_name; } static void plugin_tilde_ladspa_search_plugin_callback (const char* full_filename, - void* plugin_handle, - LADSPA_Descriptor_Function descriptor_function, - void* user_data) + void* plugin_handle, + LADSPA_Descriptor_Function descriptor_function, + void* user_data) { - const LADSPA_Descriptor* descriptor = NULL; - unsigned plug_index = 0; + const LADSPA_Descriptor* descriptor = NULL; + unsigned plug_index = 0; - char** out_lib_name = (char**)(((void**)user_data)[0]); - char* name = (char*)(((void**)user_data)[1]); + char** out_lib_name = (char**)(((void**)user_data)[0]); + char* name = (char*)(((void**)user_data)[1]); - /* Stop searching when a first matching plugin is found */ - if (*out_lib_name == NULL) + /* Stop searching when a first matching plugin is found */ + if (*out_lib_name == NULL) { - // post("plugin~: searching library \"%s\"...", full_filename); - - for (plug_index = 0; - (descriptor = descriptor_function (plug_index)) != NULL; - plug_index++) - { - // post("plugin~: label \"%s\"", descriptor->Label); - - if (strcasecmp (name, descriptor->Label) == 0) - { - /* found a matching plugin */ - *out_lib_name = strdup (full_filename); - - post("plugin~: found plugin \"%s\" in library \"%s\"", - name, full_filename); - - /* don't need to look any further */ - break; - } - } + // vedrbose(1, "plugin~: searching library \"%s\"...", full_filename); + + for (plug_index = 0; + (descriptor = descriptor_function (plug_index)) != NULL; + plug_index++) + { + // verbose(1, "plugin~: label \"%s\"", descriptor->Label); + + if (strcasecmp (name, descriptor->Label) == 0) + { + /* found a matching plugin */ + *out_lib_name = strdup (full_filename); + + verbose(1, "plugin~: found plugin \"%s\" in library \"%s\"", + name, full_filename); + + /* don't need to look any further */ + break; + } + } } } int plugin_tilde_ladspa_open_plugin (Pd_Plugin_Tilde* x, - const char* name, - const char* lib_name, - unsigned long sample_rate) + const char* name, + const char* lib_name, + unsigned long sample_rate) { - - /* precondition(s) */ - assert (x != NULL); - assert (lib_name != NULL); - assert (name != NULL); - assert (sample_rate != 0); - - /* Initialize object struct */ - x->plugin.ladspa.type = NULL; - x->plugin.ladspa.instance = NULL; - x->plugin.ladspa.control_input_values = NULL; - x->plugin.ladspa.control_output_values = NULL; - x->plugin.ladspa.control_input_ports = NULL; - x->plugin.ladspa.control_output_ports = NULL; - x->plugin.ladspa.prev_control_output_values = NULL; - x->plugin.ladspa.prev_control_output_values_invalid = 1; - x->plugin.ladspa.outofplace_audio_outputs = NULL; - x->plugin.ladspa.actual_audio_outputs = NULL; - x->plugin.ladspa.num_samples = 0; - x->plugin.ladspa.sample_rate = sample_rate; - - /* Attempt to load the plugin. */ - x->plugin_library = loadLADSPAPluginLibrary (lib_name); - if (x->plugin_library == NULL) + /* precondition(s) */ + assert (x != NULL); + assert (lib_name != NULL); + assert (name != NULL); + assert (sample_rate != 0); + + /* Initialize object struct */ + x->plugin.ladspa.type = NULL; + x->plugin.ladspa.instance = NULL; + x->plugin.ladspa.control_input_values = NULL; + x->plugin.ladspa.control_output_values = NULL; + x->plugin.ladspa.control_input_ports = NULL; + x->plugin.ladspa.control_output_ports = NULL; + x->plugin.ladspa.prev_control_output_values = NULL; + x->plugin.ladspa.prev_control_output_values_invalid = 1; + x->plugin.ladspa.outofplace_audio_outputs = NULL; + x->plugin.ladspa.actual_audio_outputs = NULL; + x->plugin.ladspa.num_samples = 0; + x->plugin.ladspa.sample_rate = sample_rate; + + /* Attempt to load the plugin. */ + x->plugin_library = loadLADSPAPluginLibrary (lib_name); + if (x->plugin_library == NULL) { - /* error */ - post("plugin~: Unable to load LADSPA plugin library \"%s\"", - lib_name); - return 1; + /* error */ + error("plugin~: Unable to load LADSPA plugin library \"%s\"", + lib_name); + return 1; } - x->plugin.ladspa.type = findLADSPAPluginDescriptor (x->plugin_library, - lib_name, - name); - if (x->plugin.ladspa.type == NULL) + x->plugin.ladspa.type = findLADSPAPluginDescriptor (x->plugin_library, + lib_name, + name); + if (x->plugin.ladspa.type == NULL) { - post("plugin~: Unable to find LADSPA plugin \"%s\" within library \"%s\"", - name, lib_name); - return 1; + error("plugin~: Unable to find LADSPA plugin \"%s\" within library \"%s\"", + name, lib_name); + return 1; } - /* Construct the plugin. */ - x->plugin.ladspa.instance - = x->plugin.ladspa.type->instantiate (x->plugin.ladspa.type, - sample_rate); - if (x->plugin.ladspa.instance == NULL) + /* Construct the plugin. */ + x->plugin.ladspa.instance + = x->plugin.ladspa.type->instantiate (x->plugin.ladspa.type, + sample_rate); + if (x->plugin.ladspa.instance == NULL) { - /* error */ - post("plugin~: Unable to instantiate LADSPA plugin \"%s\"", - x->plugin.ladspa.type->Name); - return 1; + /* error */ + error("plugin~: Unable to instantiate LADSPA plugin \"%s\"", + x->plugin.ladspa.type->Name); + return 1; } - post("plugin~: constructed plugin \"%s\" successfully", x->plugin.ladspa.type->Name); + verbose(1, "plugin~: constructed plugin \"%s\" successfully", x->plugin.ladspa.type->Name); - /* Find out the number of inputs and outputs needed. */ - plugin_tilde_ladspa_count_ports (x); + /* Find out the number of inputs and outputs needed. */ + plugin_tilde_ladspa_count_ports (x); - /* Allocate memory for control values */ - if (plugin_tilde_ladspa_alloc_control_memory (x)) { - post("plugin~: out of memory"); - return 1; /* error */ - } + /* Allocate memory for control values */ + if (plugin_tilde_ladspa_alloc_control_memory (x)) { + error("plugin~: out of memory"); + return 1; /* error */ + } - /* Connect control ports with buffers */ - plugin_tilde_ladspa_connect_control_ports (x); + /* Connect control ports with buffers */ + plugin_tilde_ladspa_connect_control_ports (x); - /* Activate the plugin. */ - if (x->plugin.ladspa.type->activate != NULL) + /* Activate the plugin. */ + if (x->plugin.ladspa.type->activate != NULL) { - x->plugin.ladspa.type->activate (x->plugin.ladspa.instance); + x->plugin.ladspa.type->activate (x->plugin.ladspa.instance); } - /* success */ - return 0; + /* success */ + return 0; } void plugin_tilde_ladspa_close_plugin (Pd_Plugin_Tilde* x) { - /* precondition(s) */ - assert (x != NULL); + /* precondition(s) */ + assert (x != NULL); - if (x->plugin.ladspa.instance != NULL) + if (x->plugin.ladspa.instance != NULL) { - /* Deactivate the plugin. */ - if (x->plugin.ladspa.type->deactivate != NULL) - { - x->plugin.ladspa.type->deactivate (x->plugin.ladspa.instance); - } - - /* Destruct the plugin. */ - x->plugin.ladspa.type->cleanup (x->plugin.ladspa.instance); - x->plugin.ladspa.instance = NULL; + /* Deactivate the plugin. */ + if (x->plugin.ladspa.type->deactivate != NULL) + { + x->plugin.ladspa.type->deactivate (x->plugin.ladspa.instance); + } + + /* Destruct the plugin. */ + x->plugin.ladspa.type->cleanup (x->plugin.ladspa.instance); + x->plugin.ladspa.instance = NULL; } - /* Free the control value memory */ - plugin_tilde_ladspa_free_control_memory (x); + /* Free the control value memory */ + plugin_tilde_ladspa_free_control_memory (x); - if (x->plugin_library != NULL) + if (x->plugin_library != NULL) { - unloadLADSPAPluginLibrary (x->plugin_library); - x->plugin_library = NULL; - x->plugin.ladspa.type = NULL; + unloadLADSPAPluginLibrary (x->plugin_library); + x->plugin_library = NULL; + x->plugin.ladspa.type = NULL; } - /* Free the out-of-place memory */ - plugin_tilde_ladspa_free_outofplace_memory (x); + /* Free the out-of-place memory */ + plugin_tilde_ladspa_free_outofplace_memory (x); } void plugin_tilde_ladspa_apply_plugin (Pd_Plugin_Tilde* x) { - unsigned i; + unsigned i; - /* Run the plugin on Pd's buffers */ - x->plugin.ladspa.type->run (x->plugin.ladspa.instance, - x->plugin.ladspa.num_samples); + /* Run the plugin on Pd's buffers */ + x->plugin.ladspa.type->run (x->plugin.ladspa.instance, + x->plugin.ladspa.num_samples); - /* Copy out-of-place buffers to Pd buffers if used */ - if (x->plugin.ladspa.outofplace_audio_outputs != NULL) + /* Copy out-of-place buffers to Pd buffers if used */ + if (x->plugin.ladspa.outofplace_audio_outputs != NULL) { - for (i = 0; i < x->num_audio_outputs; i++) - { - unsigned j; - for (j = 0; j < (unsigned)x->plugin.ladspa.num_samples; j++) - { - x->plugin.ladspa.actual_audio_outputs[i][j] - = x->plugin.ladspa.outofplace_audio_outputs[i][j]; - } - } + for (i = 0; i < x->num_audio_outputs; i++) + { + unsigned j; + for (j = 0; j < (unsigned)x->plugin.ladspa.num_samples; j++) + { + x->plugin.ladspa.actual_audio_outputs[i][j] + = x->plugin.ladspa.outofplace_audio_outputs[i][j]; + } + } } - /* Compare control output values to previous and send control - messages, if necessary */ - for (i = 0; i < x->num_control_outputs; i++) + /* Compare control output values to previous and send control + messages, if necessary */ + for (i = 0; i < x->num_control_outputs; i++) { - /* Check whether the prev values have been initialized; if - not, send a control message for each of the control outputs */ - if ((x->plugin.ladspa.control_output_values[i] - != x->plugin.ladspa.prev_control_output_values[i]) - || x->plugin.ladspa.prev_control_output_values_invalid) - { - /* Emit a control message */ - plugin_tilde_emit_control_output (x, - x->plugin.ladspa.type->PortNames[x->plugin.ladspa.control_output_ports[i]], - x->plugin.ladspa.control_output_values[i], - i); - /* Update the corresponding control monitoring value */ - x->plugin.ladspa.prev_control_output_values[i] = x->plugin.ladspa.control_output_values[i]; - } + /* Check whether the prev values have been initialized; if + not, send a control message for each of the control outputs */ + if ((x->plugin.ladspa.control_output_values[i] + != x->plugin.ladspa.prev_control_output_values[i]) + || x->plugin.ladspa.prev_control_output_values_invalid) + { + /* Emit a control message */ + plugin_tilde_emit_control_output (x, + x->plugin.ladspa.type->PortNames[x->plugin.ladspa.control_output_ports[i]], + x->plugin.ladspa.control_output_values[i], + i); + /* Update the corresponding control monitoring value */ + x->plugin.ladspa.prev_control_output_values[i] = x->plugin.ladspa.control_output_values[i]; + } } - x->plugin.ladspa.prev_control_output_values_invalid = 0; + x->plugin.ladspa.prev_control_output_values_invalid = 0; } void plugin_tilde_ladspa_reset (Pd_Plugin_Tilde* x) { - /* precondition(s) */ - assert (x != NULL); - assert (x->plugin.ladspa.type != NULL); - assert (x->plugin.ladspa.instance != NULL); + /* precondition(s) */ + if(!plugin_tilde_have_plugin(x))return; - if (x->plugin.ladspa.type->activate != NULL - && x->plugin.ladspa.type->deactivate == NULL) + if (x->plugin.ladspa.type->activate != NULL + && x->plugin.ladspa.type->deactivate == NULL) { - post("plugin~: Warning: Plug-in defines activate() method but no deactivate() method"); + post("plugin~: Warning: Plug-in defines activate() method but no deactivate() method"); } - /* reset plug-in by first deactivating and then re-activating it */ - if (x->plugin.ladspa.type->deactivate != NULL) + /* reset plug-in by first deactivating and then re-activating it */ + if (x->plugin.ladspa.type->deactivate != NULL) { - x->plugin.ladspa.type->deactivate (x->plugin.ladspa.instance); + x->plugin.ladspa.type->deactivate (x->plugin.ladspa.instance); } - if (x->plugin.ladspa.type->activate != NULL) + if (x->plugin.ladspa.type->activate != NULL) { - x->plugin.ladspa.type->activate (x->plugin.ladspa.instance); + x->plugin.ladspa.type->activate (x->plugin.ladspa.instance); } } void plugin_tilde_ladspa_connect_audio (Pd_Plugin_Tilde* x, - float** audio_inputs, - float** audio_outputs, - unsigned long num_samples) + float** audio_inputs, + float** audio_outputs, + unsigned long num_samples) { - unsigned port_index = 0; - unsigned input_count = 0; - unsigned output_count = 0; + unsigned port_index = 0; + unsigned input_count = 0; + unsigned output_count = 0; - if (x->plugin_library_filename == NULL) { - post("plugin~: plugin not found"); - return; - } + if(!plugin_tilde_have_plugin(x))return; - /* Allocate out-of-place memory if needed */ - if (plugin_tilde_ladspa_alloc_outofplace_memory (x, num_samples)) { - post("plugin~: out of memory"); - return; - } + /* Allocate out-of-place memory if needed */ + if (plugin_tilde_ladspa_alloc_outofplace_memory (x, num_samples)) { + error("plugin~: out of memory"); + return; + } - if (x->plugin.ladspa.outofplace_audio_outputs != NULL) { - x->plugin.ladspa.actual_audio_outputs = audio_outputs; - audio_outputs = x->plugin.ladspa.outofplace_audio_outputs; - } + if (x->plugin.ladspa.outofplace_audio_outputs != NULL) { + x->plugin.ladspa.actual_audio_outputs = audio_outputs; + audio_outputs = x->plugin.ladspa.outofplace_audio_outputs; + } - input_count = 0; - output_count = 0; - for (port_index = 0; port_index < x->plugin.ladspa.type->PortCount; port_index++) + input_count = 0; + output_count = 0; + for (port_index = 0; port_index < x->plugin.ladspa.type->PortCount; port_index++) { - LADSPA_PortDescriptor port_type; - port_type = x->plugin.ladspa.type->PortDescriptors[port_index]; - if (LADSPA_IS_PORT_AUDIO (port_type)) - { - if (LADSPA_IS_PORT_INPUT (port_type)) - { - x->plugin.ladspa.type->connect_port (x->plugin.ladspa.instance, - port_index, - (LADSPA_Data*)audio_inputs[input_count]); - input_count++; - } - else if (LADSPA_IS_PORT_OUTPUT (port_type)) - { - x->plugin.ladspa.type->connect_port (x->plugin.ladspa.instance, - port_index, - (LADSPA_Data*)audio_outputs[output_count]); - output_count++; - } - } + LADSPA_PortDescriptor port_type; + port_type = x->plugin.ladspa.type->PortDescriptors[port_index]; + if (LADSPA_IS_PORT_AUDIO (port_type)) + { + if (LADSPA_IS_PORT_INPUT (port_type)) + { + x->plugin.ladspa.type->connect_port (x->plugin.ladspa.instance, + port_index, + (LADSPA_Data*)audio_inputs[input_count]); + input_count++; + } + else if (LADSPA_IS_PORT_OUTPUT (port_type)) + { + x->plugin.ladspa.type->connect_port (x->plugin.ladspa.instance, + port_index, + (LADSPA_Data*)audio_outputs[output_count]); + output_count++; + } + } } - x->plugin.ladspa.num_samples = num_samples; + x->plugin.ladspa.num_samples = num_samples; } void plugin_tilde_ladspa_set_control_input_by_name (Pd_Plugin_Tilde* x, - const char* name, - float value) + const char* name, + float value) { - unsigned port_index = 0; - unsigned ctrl_input_index = 0; - int found_port = 0; /* boolean */ + unsigned port_index = 0; + unsigned ctrl_input_index = 0; + int found_port = 0; /* boolean */ - /* precondition(s) */ - assert (x != NULL); + /* precondition(s) */ + assert (x != NULL); + + if (name == NULL || strlen (name) == 0) { + pd_error(x, "plugin~: no control port name specified"); + return; + } + + if(NULL==x->plugin.ladspa.type) { + error("plugin~: unable to determine LADSPA type"); + return; + } - if (name == NULL || strlen (name) == 0) { - post("plugin~: no control port name specified"); - return; - } - /* compare control name to LADSPA control input ports' names - case-insensitively */ - found_port = 0; - ctrl_input_index = 0; - for (port_index = 0; port_index < x->plugin.ladspa.type->PortCount; port_index++) + /* compare control name to LADSPA control input ports' names + case-insensitively */ + found_port = 0; + ctrl_input_index = 0; + for (port_index = 0; port_index < x->plugin.ladspa.type->PortCount; port_index++) { - LADSPA_PortDescriptor port_type; - port_type = x->plugin.ladspa.type->PortDescriptors[port_index]; - if (LADSPA_IS_PORT_CONTROL (port_type) - && LADSPA_IS_PORT_INPUT (port_type)) - { - const char* port_name = NULL; - unsigned cmp_length = 0; - port_name = x->plugin.ladspa.type->PortNames[port_index]; - cmp_length = MIN (strlen (name), strlen (port_name)); - if (cmp_length != 0 - && strncasecmp (name, port_name, cmp_length) == 0) - { - /* found the first port to match */ - found_port = 1; - break; - } - ctrl_input_index++; - } + LADSPA_PortDescriptor port_type; + port_type = x->plugin.ladspa.type->PortDescriptors[port_index]; + if (LADSPA_IS_PORT_CONTROL (port_type) + && LADSPA_IS_PORT_INPUT (port_type)) + { + const char* port_name = NULL; + unsigned cmp_length = 0; + port_name = x->plugin.ladspa.type->PortNames[port_index]; + cmp_length = MIN (strlen (name), strlen (port_name)); + if (cmp_length != 0 + && strncasecmp (name, port_name, cmp_length) == 0) + { + /* found the first port to match */ + found_port = 1; + break; + } + ctrl_input_index++; + } } - if (!found_port) + if (!found_port) { - post("plugin~: plugin doesn't have a control input port named \"%s\"", - name); - return; + error("plugin~: plugin doesn't have a control input port named \"%s\"", + name); + return; } - plugin_tilde_ladspa_set_control_input_by_index (x, - ctrl_input_index, - value); + plugin_tilde_ladspa_set_control_input_by_index (x, + ctrl_input_index, + value); } void plugin_tilde_ladspa_set_control_input_by_index (Pd_Plugin_Tilde* x, - unsigned ctrl_input_index, - float value) + unsigned ctrl_input_index, + float value) { - unsigned port_index = 0; - unsigned ctrl_input_count = 0; - int found_port = 0; /* boolean */ + unsigned port_index = 0; + unsigned ctrl_input_count = 0; + int found_port = 0; /* boolean */ - /* precondition(s) */ - assert (x != NULL); - /* assert (ctrl_input_index >= 0); causes a warning */ - /* assert (ctrl_input_index < x->num_control_inputs); */ - if (ctrl_input_index >= x->num_control_inputs) { - post("plugin~: control port number %d is out of range [1, %d]", - ctrl_input_index + 1, x->num_control_inputs); - return; - } + /* precondition(s) */ + assert (x != NULL); + /* assert (ctrl_input_index >= 0); causes a warning */ + /* assert (ctrl_input_index < x->num_control_inputs); */ + + if(NULL==x->plugin.ladspa.type) { + error("plugin~: unable to determine LADSPA type"); + return; + } + + if (ctrl_input_index >= x->num_control_inputs) { + error("plugin~: control port number %d is out of range [1, %d]", + ctrl_input_index + 1, x->num_control_inputs); + return; + } - /* bound parameter value */ - /* sigh, need to find the N'th ctrl input port by hand */ - found_port = 0; - ctrl_input_count = 0; - for (port_index = 0; port_index < x->plugin.ladspa.type->PortCount; port_index++) + /* bound parameter value */ + /* sigh, need to find the N'th ctrl input port by hand */ + found_port = 0; + ctrl_input_count = 0; + for (port_index = 0; port_index < x->plugin.ladspa.type->PortCount; port_index++) { - LADSPA_PortDescriptor port_type; - port_type = x->plugin.ladspa.type->PortDescriptors[port_index]; - if (LADSPA_IS_PORT_CONTROL (port_type) - && LADSPA_IS_PORT_INPUT (port_type)) - { - if (ctrl_input_index == ctrl_input_count) { - found_port = 1; - break; - } - ctrl_input_count++; - } + LADSPA_PortDescriptor port_type; + port_type = x->plugin.ladspa.type->PortDescriptors[port_index]; + if (LADSPA_IS_PORT_CONTROL (port_type) + && LADSPA_IS_PORT_INPUT (port_type)) + { + if (ctrl_input_index == ctrl_input_count) { + found_port = 1; + break; + } + ctrl_input_count++; + } } - if (!found_port) { - post("plugin~: plugin doesn't have %ud control input ports", + if (!found_port) { + error("plugin~: plugin doesn't have %ud control input ports", ctrl_input_index + 1); - return; - } - - /* out of bounds rules WTF!!!!~ - if (x->plugin.ladspa.type->PortRangeHints != NULL) { - const LADSPA_PortRangeHint* hint - = &x->plugin.ladspa.type->PortRangeHints[port_index]; - if (LADSPA_IS_HINT_BOUNDED_BELOW (hint->HintDescriptor)) { - bounded_from_below = 1; - lower_bound = hint->LowerBound; - if (LADSPA_IS_HINT_SAMPLE_RATE (hint->HintDescriptor)) { - assert (x->plugin.ladspa.sample_rate != 0); - lower_bound *= (float)x->plugin.ladspa.sample_rate; - } - } - if (LADSPA_IS_HINT_BOUNDED_ABOVE (hint->HintDescriptor)) { - bounded_from_above = 1; - upper_bound = hint->UpperBound; - if (LADSPA_IS_HINT_SAMPLE_RATE (hint->HintDescriptor)) { - assert (x->plugin.ladspa.sample_rate != 0); - upper_bound *= (float)x->plugin.ladspa.sample_rate; - } - } - } - bounded = 0; - if (bounded_from_below && value < lower_bound) { - value = lower_bound; - bounded = 1; - } - if (bounded_from_above && value > upper_bound) { - value = upper_bound; - bounded = 1; - } */ - - /* set the appropriate control port value */ - x->plugin.ladspa.control_input_values[ctrl_input_index] = value; + return; + } - // post("plugin~: control change control input port #%ud to value %f", ctrl_input_index + 1, value); + /* out of bounds rules WTF!!!!~ + if (x->plugin.ladspa.type->PortRangeHints != NULL) { + const LADSPA_PortRangeHint* hint + = &x->plugin.ladspa.type->PortRangeHints[port_index]; + if (LADSPA_IS_HINT_BOUNDED_BELOW (hint->HintDescriptor)) { + bounded_from_below = 1; + lower_bound = hint->LowerBound; + if (LADSPA_IS_HINT_SAMPLE_RATE (hint->HintDescriptor)) { + assert (x->plugin.ladspa.sample_rate != 0); + lower_bound *= (float)x->plugin.ladspa.sample_rate; + } + } + if (LADSPA_IS_HINT_BOUNDED_ABOVE (hint->HintDescriptor)) { + bounded_from_above = 1; + upper_bound = hint->UpperBound; + if (LADSPA_IS_HINT_SAMPLE_RATE (hint->HintDescriptor)) { + assert (x->plugin.ladspa.sample_rate != 0); + upper_bound *= (float)x->plugin.ladspa.sample_rate; + } + } + } + bounded = 0; + if (bounded_from_below && value < lower_bound) { + value = lower_bound; + bounded = 1; + } + if (bounded_from_above && value > upper_bound) { + value = upper_bound; + bounded = 1; + } */ + + /* set the appropriate control port value */ + x->plugin.ladspa.control_input_values[ctrl_input_index] = value; + + // verbose(1, "plugin~: control change control input port #%ud to value %f", ctrl_input_index + 1, value); } static void plugin_tilde_ladspa_count_ports (Pd_Plugin_Tilde* x) { - unsigned i = 0; + unsigned i = 0; - x->num_audio_inputs = 0; - x->num_audio_outputs = 0; - x->num_control_inputs = 0; - x->num_control_outputs = 0; + x->num_audio_inputs = 0; + x->num_audio_outputs = 0; + x->num_control_inputs = 0; + x->num_control_outputs = 0; - for (i = 0; i < x->plugin.ladspa.type->PortCount; i++) + for (i = 0; i < x->plugin.ladspa.type->PortCount; i++) { - LADSPA_PortDescriptor port_type; - port_type = x->plugin.ladspa.type->PortDescriptors[i]; - - if (LADSPA_IS_PORT_AUDIO (port_type)) - { - if (LADSPA_IS_PORT_INPUT (port_type)) - { - x->num_audio_inputs++; - } - else if (LADSPA_IS_PORT_OUTPUT (port_type)) - { - x->num_audio_outputs++; - } - } - else if (LADSPA_IS_PORT_CONTROL (port_type)) - { - if (LADSPA_IS_PORT_INPUT (port_type)) - { - x->num_control_inputs++; - } - else if (LADSPA_IS_PORT_OUTPUT (port_type)) - { - x->num_control_outputs++; - } - } + LADSPA_PortDescriptor port_type; + port_type = x->plugin.ladspa.type->PortDescriptors[i]; + + if (LADSPA_IS_PORT_AUDIO (port_type)) + { + if (LADSPA_IS_PORT_INPUT (port_type)) + { + x->num_audio_inputs++; + } + else if (LADSPA_IS_PORT_OUTPUT (port_type)) + { + x->num_audio_outputs++; + } + } + else if (LADSPA_IS_PORT_CONTROL (port_type)) + { + if (LADSPA_IS_PORT_INPUT (port_type)) + { + x->num_control_inputs++; + } + else if (LADSPA_IS_PORT_OUTPUT (port_type)) + { + x->num_control_outputs++; + } + } } - post("plugin~: plugin ports: audio %d/%d ctrl %d/%d", - x->num_audio_inputs, x->num_audio_outputs, - x->num_control_inputs, x->num_control_outputs); + verbose(1, "plugin~: plugin ports: audio %d/%d ctrl %d/%d", + x->num_audio_inputs, x->num_audio_outputs, + x->num_control_inputs, x->num_control_outputs); } static void plugin_tilde_ladspa_connect_control_ports (Pd_Plugin_Tilde* x) { - unsigned port_index = 0; - unsigned input_count = 0; - unsigned output_count = 0; + unsigned port_index = 0; + unsigned input_count = 0; + unsigned output_count = 0; - input_count = 0; - output_count = 0; - for (port_index = 0; port_index < x->plugin.ladspa.type->PortCount; port_index++) + input_count = 0; + output_count = 0; + for (port_index = 0; port_index < x->plugin.ladspa.type->PortCount; port_index++) { - LADSPA_PortDescriptor port_type; - port_type = x->plugin.ladspa.type->PortDescriptors[port_index]; - - if (LADSPA_IS_PORT_CONTROL (port_type)) - { - if (LADSPA_IS_PORT_INPUT (port_type)) - { - x->plugin.ladspa.type->connect_port (x->plugin.ladspa.instance, - port_index, - &x->plugin.ladspa.control_input_values[input_count]); - x->plugin.ladspa.control_input_ports[input_count] = port_index; - input_count++; - } - else if (LADSPA_IS_PORT_OUTPUT (port_type)) - { - x->plugin.ladspa.type->connect_port (x->plugin.ladspa.instance, - port_index, - &x->plugin.ladspa.control_output_values[output_count]); - x->plugin.ladspa.control_output_ports[output_count] = port_index; - - output_count++; - } - } + LADSPA_PortDescriptor port_type; + port_type = x->plugin.ladspa.type->PortDescriptors[port_index]; + + if (LADSPA_IS_PORT_CONTROL (port_type)) + { + if (LADSPA_IS_PORT_INPUT (port_type)) + { + x->plugin.ladspa.type->connect_port (x->plugin.ladspa.instance, + port_index, + &x->plugin.ladspa.control_input_values[input_count]); + x->plugin.ladspa.control_input_ports[input_count] = port_index; + input_count++; + } + else if (LADSPA_IS_PORT_OUTPUT (port_type)) + { + x->plugin.ladspa.type->connect_port (x->plugin.ladspa.instance, + port_index, + &x->plugin.ladspa.control_output_values[output_count]); + x->plugin.ladspa.control_output_ports[output_count] = port_index; + + output_count++; + } + } } } static int plugin_tilde_ladspa_alloc_outofplace_memory (Pd_Plugin_Tilde* x, unsigned long buflen) { - assert (x != NULL); + assert (x != NULL); - plugin_tilde_ladspa_free_outofplace_memory (x); + plugin_tilde_ladspa_free_outofplace_memory (x); - if (LADSPA_IS_INPLACE_BROKEN (x->plugin.ladspa.type->Properties)) + if (LADSPA_IS_INPLACE_BROKEN (x->plugin.ladspa.type->Properties)) { - unsigned i = 0; - - x->plugin.ladspa.outofplace_audio_outputs = (t_float**) - calloc (x->num_audio_outputs, sizeof (t_float*)); - if (x->plugin.ladspa.outofplace_audio_outputs == NULL) { - return 1; /* error */ - } - - for (i = 0; i < x->num_audio_outputs; i++) - { - x->plugin.ladspa.outofplace_audio_outputs[i] = (t_float*) - calloc (buflen, sizeof (t_float)); - if (x->plugin.ladspa.outofplace_audio_outputs[i] == NULL) { - /* FIXME free got buffers? */ - return 1; /* error */ - } - } + unsigned i = 0; + + x->plugin.ladspa.outofplace_audio_outputs = (t_float**) + calloc (x->num_audio_outputs, sizeof (t_float*)); + if (x->plugin.ladspa.outofplace_audio_outputs == NULL) { + return 1; /* error */ + } + + for (i = 0; i < x->num_audio_outputs; i++) + { + x->plugin.ladspa.outofplace_audio_outputs[i] = (t_float*) + calloc (buflen, sizeof (t_float)); + if (x->plugin.ladspa.outofplace_audio_outputs[i] == NULL) { + /* FIXME free got buffers? */ + return 1; /* error */ + } + } } - return 0; /* success */ + return 0; /* success */ } static void plugin_tilde_ladspa_free_outofplace_memory (Pd_Plugin_Tilde* x) { - assert (x != NULL); + assert (x != NULL); - if (x->plugin.ladspa.outofplace_audio_outputs != NULL) + if (x->plugin.ladspa.outofplace_audio_outputs != NULL) { - unsigned i = 0; - for (i = 0; i < x->num_audio_outputs; i++) - { - free (x->plugin.ladspa.outofplace_audio_outputs[i]); - } - free (x->plugin.ladspa.outofplace_audio_outputs); - x->plugin.ladspa.outofplace_audio_outputs = NULL; + unsigned i = 0; + for (i = 0; i < x->num_audio_outputs; i++) + { + free (x->plugin.ladspa.outofplace_audio_outputs[i]); + } + free (x->plugin.ladspa.outofplace_audio_outputs); + x->plugin.ladspa.outofplace_audio_outputs = NULL; } } static int plugin_tilde_ladspa_alloc_control_memory (Pd_Plugin_Tilde* x) { - x->plugin.ladspa.control_input_values = NULL; - x->plugin.ladspa.control_input_ports = NULL; - if (x->num_control_inputs > 0) + x->plugin.ladspa.control_input_values = NULL; + x->plugin.ladspa.control_input_ports = NULL; + if (x->num_control_inputs > 0) { - x->plugin.ladspa.control_input_values = (float*)calloc - (x->num_control_inputs, sizeof (float)); - x->plugin.ladspa.control_input_ports = (int*)calloc - (x->num_control_inputs, sizeof (int)); - if (x->plugin.ladspa.control_input_values == NULL - || x->plugin.ladspa.control_input_ports == NULL) { - return 1; /* error */ - } + x->plugin.ladspa.control_input_values = (float*)calloc + (x->num_control_inputs, sizeof (float)); + x->plugin.ladspa.control_input_ports = (int*)calloc + (x->num_control_inputs, sizeof (int)); + if (x->plugin.ladspa.control_input_values == NULL + || x->plugin.ladspa.control_input_ports == NULL) { + return 1; /* error */ + } } - x->plugin.ladspa.control_output_values = NULL; - x->plugin.ladspa.control_output_ports = NULL; - x->plugin.ladspa.prev_control_output_values = NULL; - if (x->num_control_outputs > 0) + x->plugin.ladspa.control_output_values = NULL; + x->plugin.ladspa.control_output_ports = NULL; + x->plugin.ladspa.prev_control_output_values = NULL; + if (x->num_control_outputs > 0) { - x->plugin.ladspa.control_output_values = (float*)calloc - (x->num_control_outputs, sizeof (float)); - x->plugin.ladspa.control_output_ports = (int*)calloc - (x->num_control_outputs, sizeof (int)); - x->plugin.ladspa.prev_control_output_values = (float*)calloc - (x->num_control_outputs, sizeof (float)); - if (x->plugin.ladspa.control_output_values == NULL - || x->plugin.ladspa.prev_control_output_values == NULL - || x->plugin.ladspa.control_output_ports == NULL) { - return 1; /* error */ - } + x->plugin.ladspa.control_output_values = (float*)calloc + (x->num_control_outputs, sizeof (float)); + x->plugin.ladspa.control_output_ports = (int*)calloc + (x->num_control_outputs, sizeof (int)); + x->plugin.ladspa.prev_control_output_values = (float*)calloc + (x->num_control_outputs, sizeof (float)); + if (x->plugin.ladspa.control_output_values == NULL + || x->plugin.ladspa.prev_control_output_values == NULL + || x->plugin.ladspa.control_output_ports == NULL) { + return 1; /* error */ + } } - /* Indicate initial conditions */ - x->plugin.ladspa.prev_control_output_values_invalid = 1; - return 0; /* success */ + /* Indicate initial conditions */ + x->plugin.ladspa.prev_control_output_values_invalid = 1; + return 0; /* success */ } static void plugin_tilde_ladspa_free_control_memory (Pd_Plugin_Tilde* x) { - if (x->plugin.ladspa.control_input_values != NULL) + if (x->plugin.ladspa.control_input_values != NULL) { - free (x->plugin.ladspa.control_input_values); - x->plugin.ladspa.control_input_values = NULL; + free (x->plugin.ladspa.control_input_values); + x->plugin.ladspa.control_input_values = NULL; } - if (x->plugin.ladspa.control_output_values != NULL) + if (x->plugin.ladspa.control_output_values != NULL) { - free (x->plugin.ladspa.control_output_values); - x->plugin.ladspa.control_output_values = NULL; + free (x->plugin.ladspa.control_output_values); + x->plugin.ladspa.control_output_values = NULL; } - if (x->plugin.ladspa.prev_control_output_values != NULL) + if (x->plugin.ladspa.prev_control_output_values != NULL) { - free (x->plugin.ladspa.prev_control_output_values); - x->plugin.ladspa.prev_control_output_values = NULL; + free (x->plugin.ladspa.prev_control_output_values); + x->plugin.ladspa.prev_control_output_values = NULL; } - if (x->plugin.ladspa.control_input_ports != NULL) + if (x->plugin.ladspa.control_input_ports != NULL) { - free (x->plugin.ladspa.control_input_ports); - x->plugin.ladspa.control_input_ports = NULL; + free (x->plugin.ladspa.control_input_ports); + x->plugin.ladspa.control_input_ports = NULL; } - if (x->plugin.ladspa.control_output_ports != NULL) + if (x->plugin.ladspa.control_output_ports != NULL) { - free (x->plugin.ladspa.control_output_ports); - x->plugin.ladspa.control_output_ports = NULL; + free (x->plugin.ladspa.control_output_ports); + x->plugin.ladspa.control_output_ports = NULL; } } +static int plugin_tilde_have_ladspa_plugin(Pd_Plugin_Tilde* x) { + if(NULL==x->plugin.ladspa.instance) { + error("plugin~: LADSPA instance not found"); + return 0; + } + + if(NULL==x->plugin.ladspa.type) { + error("plugin~: LADSPA type not found"); + return 0; + } + + return 1; +} + +static int plugin_tilde_have_plugin(Pd_Plugin_Tilde* x) { + if(NULL==x)return 0; + + if (NULL==x->plugin_library || x->plugin_library_filename == NULL) { + error("plugin~: plugin not found"); + return 0; + } + + if(NULL==x->plugin.ladspa.type) { + error("plugin~: unable to determine LADSPA type"); + return 0; + } + + return plugin_tilde_have_ladspa_plugin(x); + +} -- cgit v1.2.1