2 Copyright (C) 2000 Paul Davis
4 This program is free software; you can redistribute it and/or modify
5 it under the terms of the GNU General Public License as published by
6 the Free Software Foundation; either version 2 of the License, or
7 (at your option) any later version.
9 This program is distributed in the hope that it will be useful,
10 but WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 GNU General Public License for more details.
14 You should have received a copy of the GNU General Public License
15 along with this program; if not, write to the Free Software
16 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
21 #include "libardour-config.h"
26 #include "pbd/failed_constructor.h"
27 #include "pbd/xml++.h"
28 #include "pbd/convert.h"
30 #include "ardour/audio_buffer.h"
31 #include "ardour/automation_list.h"
32 #include "ardour/buffer_set.h"
33 #include "ardour/debug.h"
34 #include "ardour/event_type_map.h"
35 #include "ardour/ladspa_plugin.h"
36 #include "ardour/plugin.h"
37 #include "ardour/plugin_insert.h"
40 #include "ardour/lv2_plugin.h"
43 #ifdef WINDOWS_VST_SUPPORT
44 #include "ardour/windows_vst_plugin.h"
48 #include "ardour/lxvst_plugin.h"
51 #ifdef AUDIOUNIT_SUPPORT
52 #include "ardour/audio_unit.h"
55 #include "ardour/session.h"
56 #include "ardour/types.h"
61 using namespace ARDOUR;
64 const string PluginInsert::port_automation_node_name = "PortAutomation";
66 PluginInsert::PluginInsert (Session& s, boost::shared_ptr<Plugin> plug)
67 : Processor (s, (plug ? plug->name() : string ("toBeRenamed")))
68 , _signal_analysis_collected_nframes(0)
69 , _signal_analysis_collect_nframes_max(0)
71 /* the first is the master */
75 create_automatable_parameters ();
80 PluginInsert::set_count (uint32_t num)
82 bool require_state = !_plugins.empty();
84 /* this is a bad idea.... we shouldn't do this while active.
85 only a route holding their redirect_lock should be calling this
90 } else if (num > _plugins.size()) {
91 uint32_t diff = num - _plugins.size();
93 for (uint32_t n = 0; n < diff; ++n) {
94 boost::shared_ptr<Plugin> p = plugin_factory (_plugins[0]);
101 /* XXX do something */
105 } else if (num < _plugins.size()) {
106 uint32_t diff = _plugins.size() - num;
107 for (uint32_t n= 0; n < diff; ++n) {
115 PluginInsert::~PluginInsert ()
120 PluginInsert::control_list_automation_state_changed (Evoral::Parameter which, AutoState s)
122 if (which.type() != PluginAutomation)
125 boost::shared_ptr<AutomationControl> c
126 = boost::dynamic_pointer_cast<AutomationControl>(control (which));
129 _plugins[0]->set_parameter (which.id(), c->list()->eval (_session.transport_frame()));
134 PluginInsert::output_streams() const
136 assert (!_plugins.empty());
138 PluginInfoPtr info = _plugins.front()->get_info();
140 if (info->reconfigurable_io()) {
141 ChanCount out = _plugins.front()->output_streams ();
142 // DEBUG_TRACE (DEBUG::Processors, string_compose ("Plugin insert, reconfigur(able) output streams = %1\n", out));
145 ChanCount out = info->n_outputs;
146 // DEBUG_TRACE (DEBUG::Processors, string_compose ("Plugin insert, static output streams = %1 for %2 plugins\n", out, _plugins.size()));
147 out.set_audio (out.n_audio() * _plugins.size());
148 out.set_midi (out.n_midi() * _plugins.size() + midi_bypass.n_midi());
154 PluginInsert::input_streams() const
156 assert (!_plugins.empty());
160 PluginInfoPtr info = _plugins.front()->get_info();
162 if (info->reconfigurable_io()) {
163 assert (_plugins.size() == 1);
164 in = _plugins.front()->input_streams();
169 DEBUG_TRACE (DEBUG::Processors, string_compose ("Plugin insert, input streams = %1, match using %2\n", in, _match.method));
171 if (_match.method == Split) {
173 /* we are splitting 1 processor input to multiple plugin inputs,
174 so we have a maximum of 1 stream of each type.
176 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
177 if (in.get (*t) > 1) {
183 } else if (_match.method == Hide) {
185 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
186 in.set (*t, in.get (*t) - _match.hide.get (*t));
192 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
193 in.set (*t, in.get (*t) * _plugins.size ());
201 PluginInsert::natural_output_streams() const
203 return _plugins[0]->get_info()->n_outputs;
207 PluginInsert::natural_input_streams() const
209 return _plugins[0]->get_info()->n_inputs;
213 PluginInsert::has_no_inputs() const
215 return _plugins[0]->get_info()->n_inputs == ChanCount::ZERO;
219 PluginInsert::has_no_audio_inputs() const
221 return _plugins[0]->get_info()->n_inputs.n_audio() == 0;
225 PluginInsert::is_midi_instrument() const
227 /* XXX more finesse is possible here. VST plugins have a
228 a specific "instrument" flag, for example.
230 PluginInfoPtr pi = _plugins[0]->get_info();
232 return pi->n_inputs.n_midi() != 0 &&
233 pi->n_outputs.n_audio() > 0;
237 PluginInsert::create_automatable_parameters ()
239 assert (!_plugins.empty());
241 set<Evoral::Parameter> a = _plugins.front()->automatable ();
243 Plugin::ParameterDescriptor desc;
245 for (set<Evoral::Parameter>::iterator i = a.begin(); i != a.end(); ++i) {
246 if (i->type() == PluginAutomation) {
248 Evoral::Parameter param(*i);
250 _plugins.front()->get_parameter_descriptor(i->id(), desc);
252 /* the Parameter belonging to the actual plugin doesn't have its range set
253 but we want the Controllable related to this Parameter to have those limits.
256 param.set_range (desc.lower, desc.upper, _plugins.front()->default_value(i->id()), desc.toggled);
257 can_automate (param);
258 boost::shared_ptr<AutomationList> list(new AutomationList(param));
259 add_control (boost::shared_ptr<AutomationControl> (new PluginControl(this, param, list)));
265 PluginInsert::parameter_changed (uint32_t which, float val)
267 boost::shared_ptr<AutomationControl> ac = automation_control (Evoral::Parameter (PluginAutomation, 0, which));
272 Plugins::iterator i = _plugins.begin();
274 /* don't set the first plugin, just all the slaves */
276 if (i != _plugins.end()) {
278 for (; i != _plugins.end(); ++i) {
279 (*i)->set_parameter (which, val);
286 PluginInsert::set_block_size (pframes_t nframes)
289 for (Plugins::iterator i = _plugins.begin(); i != _plugins.end(); ++i) {
290 if ((*i)->set_block_size (nframes) != 0) {
298 PluginInsert::activate ()
300 for (Plugins::iterator i = _plugins.begin(); i != _plugins.end(); ++i) {
304 Processor::activate ();
308 PluginInsert::deactivate ()
310 Processor::deactivate ();
312 for (Plugins::iterator i = _plugins.begin(); i != _plugins.end(); ++i) {
318 PluginInsert::flush ()
320 for (vector<boost::shared_ptr<Plugin> >::iterator i = _plugins.begin(); i != _plugins.end(); ++i) {
326 PluginInsert::connect_and_run (BufferSet& bufs, pframes_t nframes, framecnt_t offset, bool with_auto, framepos_t now)
328 // Calculate if, and how many frames we need to collect for analysis
329 framecnt_t collect_signal_nframes = (_signal_analysis_collect_nframes_max -
330 _signal_analysis_collected_nframes);
331 if (nframes < collect_signal_nframes) { // we might not get all frames now
332 collect_signal_nframes = nframes;
335 ChanCount const in_streams = input_streams ();
336 ChanCount const out_streams = output_streams ();
338 ChanMapping in_map (in_streams);
339 ChanMapping out_map (out_streams);
341 if (_match.method == Split) {
342 /* fix the input mapping so that we have maps for each of the plugin's inputs */
343 in_map = ChanMapping (natural_input_streams ());
345 /* copy the first stream's buffer contents to the others */
346 /* XXX: audio only */
347 uint32_t first_idx = in_map.get (DataType::AUDIO, 0, &valid);
349 for (uint32_t i = in_streams.n_audio(); i < natural_input_streams().n_audio(); ++i) {
350 bufs.get_audio(in_map.get (DataType::AUDIO, i, &valid)).read_from(bufs.get_audio(first_idx), nframes, offset, offset);
355 bufs.set_count(ChanCount::max(bufs.count(), in_streams));
356 bufs.set_count(ChanCount::max(bufs.count(), out_streams));
358 /* Note that we've already required that plugins
359 be able to handle in-place processing.
366 for (Controls::iterator li = controls().begin(); li != controls().end(); ++li, ++n) {
368 boost::shared_ptr<AutomationControl> c
369 = boost::dynamic_pointer_cast<AutomationControl>(li->second);
371 if (c->parameter().type() == PluginAutomation && c->automation_playback()) {
374 const float val = c->list()->rt_safe_eval (now, valid);
384 if (collect_signal_nframes > 0) {
386 //std::cerr << "collect input, bufs " << bufs.count().n_audio() << " count, " << bufs.available().n_audio() << " available" << std::endl;
387 //std::cerr << " streams " << input_streams().n_audio() << std::endl;
388 //std::cerr << "filling buffer with " << collect_signal_nframes << " frames at " << _signal_analysis_collected_nframes << std::endl;
390 _signal_analysis_inputs.set_count(input_streams());
392 for (uint32_t i = 0; i < input_streams().n_audio(); ++i) {
393 _signal_analysis_inputs.get_audio(i).read_from(
395 collect_signal_nframes,
396 _signal_analysis_collected_nframes); // offset is for target buffer
401 for (Plugins::iterator i = _plugins.begin(); i != _plugins.end(); ++i) {
402 (*i)->connect_and_run(bufs, in_map, out_map, nframes, offset);
403 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
404 in_map.offset_to(*t, natural_input_streams().get(*t));
405 out_map.offset_to(*t, natural_output_streams().get(*t));
409 if (collect_signal_nframes > 0) {
411 //std::cerr << " output, bufs " << bufs.count().n_audio() << " count, " << bufs.available().n_audio() << " available" << std::endl;
412 //std::cerr << " streams " << output_streams().n_audio() << std::endl;
414 _signal_analysis_outputs.set_count(output_streams());
416 for (uint32_t i = 0; i < output_streams().n_audio(); ++i) {
417 _signal_analysis_outputs.get_audio(i).read_from(
419 collect_signal_nframes,
420 _signal_analysis_collected_nframes); // offset is for target buffer
423 _signal_analysis_collected_nframes += collect_signal_nframes;
424 assert(_signal_analysis_collected_nframes <= _signal_analysis_collect_nframes_max);
426 if (_signal_analysis_collected_nframes == _signal_analysis_collect_nframes_max) {
427 _signal_analysis_collect_nframes_max = 0;
428 _signal_analysis_collected_nframes = 0;
430 AnalysisDataGathered(&_signal_analysis_inputs,
431 &_signal_analysis_outputs);
434 /* leave remaining channel buffers alone */
438 PluginInsert::silence (framecnt_t nframes)
444 ChanMapping in_map(input_streams());
445 ChanMapping out_map(output_streams());
447 if (_match.method == Split) {
448 /* fix the input mapping so that we have maps for each of the plugin's inputs */
449 in_map = ChanMapping (natural_input_streams ());
452 for (Plugins::iterator i = _plugins.begin(); i != _plugins.end(); ++i) {
453 (*i)->connect_and_run (_session.get_scratch_buffers ((*i)->get_info()->n_inputs, true), in_map, out_map, nframes, 0);
458 PluginInsert::run (BufferSet& bufs, framepos_t /*start_frame*/, framepos_t /*end_frame*/, pframes_t nframes, bool)
460 if (_pending_active) {
461 /* run as normal if we are active or moving from inactive to active */
463 if (_session.transport_rolling()) {
464 automation_run (bufs, nframes);
466 connect_and_run (bufs, nframes, 0, false);
470 uint32_t in = input_streams ().n_audio ();
471 uint32_t out = output_streams().n_audio ();
473 if (has_no_audio_inputs() || in == 0) {
475 /* silence all (audio) outputs. Should really declick
476 * at the transitions of "active"
479 for (uint32_t n = 0; n < out; ++n) {
480 bufs.get_audio (n).silence (nframes);
483 } else if (out > in) {
485 /* not active, but something has make up for any channel count increase */
487 // TODO: option round-robin (n % in) or silence additional buffers ??
488 // for now , simply replicate last buffer
489 for (uint32_t n = in; n < out; ++n) {
490 bufs.get_audio(n).read_from(bufs.get_audio(in - 1), nframes);
494 bufs.count().set_audio (out);
497 _active = _pending_active;
499 /* we have no idea whether the plugin generated silence or not, so mark
500 * all buffers appropriately.
506 PluginInsert::set_parameter (Evoral::Parameter param, float val)
508 if (param.type() != PluginAutomation) {
512 /* the others will be set from the event triggered by this */
514 _plugins[0]->set_parameter (param.id(), val);
516 boost::shared_ptr<AutomationControl> ac
517 = boost::dynamic_pointer_cast<AutomationControl>(control(param));
522 warning << "set_parameter called for nonexistant parameter "
523 << EventTypeMap::instance().to_symbol(param) << endmsg;
526 _session.set_dirty();
530 PluginInsert::get_parameter (Evoral::Parameter param)
532 if (param.type() != PluginAutomation) {
535 assert (!_plugins.empty ());
536 return _plugins[0]->get_parameter (param.id());
541 PluginInsert::automation_run (BufferSet& bufs, pframes_t nframes)
543 Evoral::ControlEvent next_event (0, 0.0f);
544 framepos_t now = _session.transport_frame ();
545 framepos_t end = now + nframes;
546 framecnt_t offset = 0;
548 Glib::Threads::Mutex::Lock lm (control_lock(), Glib::Threads::TRY_LOCK);
551 connect_and_run (bufs, nframes, offset, false);
555 if (!find_next_event (now, end, next_event) || requires_fixed_sized_buffers()) {
557 /* no events have a time within the relevant range */
559 connect_and_run (bufs, nframes, offset, true, now);
565 framecnt_t cnt = min (((framecnt_t) ceil (next_event.when) - now), (framecnt_t) nframes);
567 connect_and_run (bufs, cnt, offset, true, now);
573 if (!find_next_event (now, end, next_event)) {
578 /* cleanup anything that is left to do */
581 connect_and_run (bufs, nframes, offset, true, now);
586 PluginInsert::default_parameter_value (const Evoral::Parameter& param)
588 if (param.type() != PluginAutomation)
591 if (_plugins.empty()) {
592 fatal << _("programming error: ") << X_("PluginInsert::default_parameter_value() called with no plugin")
597 return _plugins[0]->default_value (param.id());
600 boost::shared_ptr<Plugin>
601 PluginInsert::plugin_factory (boost::shared_ptr<Plugin> other)
603 boost::shared_ptr<LadspaPlugin> lp;
605 boost::shared_ptr<LV2Plugin> lv2p;
607 #ifdef WINDOWS_VST_SUPPORT
608 boost::shared_ptr<WindowsVSTPlugin> vp;
611 boost::shared_ptr<LXVSTPlugin> lxvp;
613 #ifdef AUDIOUNIT_SUPPORT
614 boost::shared_ptr<AUPlugin> ap;
617 if ((lp = boost::dynamic_pointer_cast<LadspaPlugin> (other)) != 0) {
618 return boost::shared_ptr<Plugin> (new LadspaPlugin (*lp));
620 } else if ((lv2p = boost::dynamic_pointer_cast<LV2Plugin> (other)) != 0) {
621 return boost::shared_ptr<Plugin> (new LV2Plugin (*lv2p));
623 #ifdef WINDOWS_VST_SUPPORT
624 } else if ((vp = boost::dynamic_pointer_cast<WindowsVSTPlugin> (other)) != 0) {
625 return boost::shared_ptr<Plugin> (new WindowsVSTPlugin (*vp));
628 } else if ((lxvp = boost::dynamic_pointer_cast<LXVSTPlugin> (other)) != 0) {
629 return boost::shared_ptr<Plugin> (new LXVSTPlugin (*lxvp));
631 #ifdef AUDIOUNIT_SUPPORT
632 } else if ((ap = boost::dynamic_pointer_cast<AUPlugin> (other)) != 0) {
633 return boost::shared_ptr<Plugin> (new AUPlugin (*ap));
637 fatal << string_compose (_("programming error: %1"),
638 X_("unknown plugin type in PluginInsert::plugin_factory"))
641 return boost::shared_ptr<Plugin> ((Plugin*) 0);
645 PluginInsert::configure_io (ChanCount in, ChanCount out)
647 Match old_match = _match;
648 ChanCount old_in = input_streams ();
649 ChanCount old_out = output_streams ();
651 /* set the matching method and number of plugins that we will use to meet this configuration */
652 _match = private_can_support_io_configuration (in, out);
653 if (set_count (_match.plugins) == false) {
657 if ( (old_match.method != _match.method && (old_match.method == Split || _match.method == Split))
662 PluginIoReConfigure (); /* EMIT SIGNAL */
665 /* configure plugins */
666 switch (_match.method) {
669 if (_plugins.front()->configure_io (_plugins.front()->get_info()->n_inputs, out)) {
675 if (_plugins.front()->configure_io (in, out) == false) {
681 // we don't know the analysis window size, so we must work with the
682 // current buffer size here. each request for data fills in these
683 // buffers and the analyser makes sure it gets enough data for the
685 session().ensure_buffer_set (_signal_analysis_inputs, in);
686 //_signal_analysis_inputs.set_count (in);
688 session().ensure_buffer_set (_signal_analysis_outputs, out);
689 //_signal_analysis_outputs.set_count (out);
691 // std::cerr << "set counts to i" << in.n_audio() << "/o" << out.n_audio() << std::endl;
693 return Processor::configure_io (in, out);
696 /** Decide whether this PluginInsert can support a given IO configuration.
697 * To do this, we run through a set of possible solutions in rough order of
700 * @param in Required input channel count.
701 * @param out Filled in with the output channel count if we return true.
702 * @return true if the given IO configuration can be supported.
705 PluginInsert::can_support_io_configuration (const ChanCount& in, ChanCount& out)
707 return private_can_support_io_configuration (in, out).method != Impossible;
710 /** A private version of can_support_io_configuration which returns the method
711 * by which the configuration can be matched, rather than just whether or not
715 PluginInsert::private_can_support_io_configuration (ChanCount const & inx, ChanCount& out)
717 if (_plugins.empty()) {
721 PluginInfoPtr info = _plugins.front()->get_info();
722 ChanCount in; in += inx;
725 if (info->reconfigurable_io()) {
726 /* Plugin has flexible I/O, so delegate to it */
727 bool const r = _plugins.front()->can_support_io_configuration (in, out);
729 return Match (Impossible, 0);
732 return Match (Delegate, 1);
735 ChanCount inputs = info->n_inputs;
736 ChanCount outputs = info->n_outputs;
738 if (in.get(DataType::MIDI) == 1 && outputs.get(DataType::MIDI) == 0) {
739 DEBUG_TRACE ( DEBUG::Processors, string_compose ("bypassing midi-data around %1\n", name()));
740 midi_bypass.set(DataType::MIDI, 1);
742 if (in.get(DataType::MIDI) == 1 && inputs.get(DataType::MIDI) == 0) {
743 DEBUG_TRACE ( DEBUG::Processors, string_compose ("hiding midi-port from plugin %1\n", name()));
744 in.set(DataType::MIDI, 0);
747 bool no_inputs = true;
748 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
749 if (inputs.get (*t) != 0) {
756 /* no inputs so we can take any input configuration since we throw it away */
757 out = outputs + midi_bypass;
758 return Match (NoInputs, 1);
761 /* Plugin inputs match requested inputs exactly */
763 out = outputs + midi_bypass;
764 return Match (ExactMatch, 1);
767 /* We may be able to run more than one copy of the plugin within this insert
768 to cope with the insert having more inputs than the plugin.
769 We allow replication only for plugins with either zero or 1 inputs and outputs
770 for every valid data type.
774 bool can_replicate = true;
775 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
777 uint32_t nin = inputs.get (*t);
779 // No inputs of this type
780 if (nin == 0 && in.get(*t) == 0) {
784 if (nin != 1 || outputs.get (*t) != 1) {
785 can_replicate = false;
789 // Potential factor not set yet
791 f = in.get(*t) / nin;
794 // Factor for this type does not match another type, can not replicate
795 if (f != (in.get(*t) / nin)) {
796 can_replicate = false;
802 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
803 out.set (*t, outputs.get(*t) * f);
806 return Match (Replicate, f);
809 /* If the processor has exactly one input of a given type, and
810 the plugin has more, we can feed the single processor input
811 to some or all of the plugin inputs. This is rather
812 special-case-y, but the 1-to-many case is by far the
813 simplest. How do I split thy 2 processor inputs to 3
814 plugin inputs? Let me count the ways ...
817 bool can_split = true;
818 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
820 bool const can_split_type = (in.get (*t) == 1 && inputs.get (*t) > 1);
821 bool const nothing_to_do_for_type = (in.get (*t) == 0 && inputs.get (*t) == 0);
823 if (!can_split_type && !nothing_to_do_for_type) {
829 out = outputs + midi_bypass;
830 return Match (Split, 1);
833 /* If the plugin has more inputs than we want, we can `hide' some of them
834 by feeding them silence.
837 bool could_hide = false;
838 bool cannot_hide = false;
839 ChanCount hide_channels;
841 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
842 if (inputs.get(*t) > in.get(*t)) {
843 /* there is potential to hide, since the plugin has more inputs of type t than the insert */
844 hide_channels.set (*t, inputs.get(*t) - in.get(*t));
846 } else if (inputs.get(*t) < in.get(*t)) {
847 /* we definitely cannot hide, since the plugin has fewer inputs of type t than the insert */
852 if (could_hide && !cannot_hide) {
853 out = outputs + midi_bypass;
854 return Match (Hide, 1, hide_channels);
858 return Match (Impossible, 0);
862 PluginInsert::get_state ()
868 PluginInsert::state (bool full)
870 XMLNode& node = Processor::state (full);
872 node.add_property("type", _plugins[0]->state_node_name());
873 node.add_property("unique-id", _plugins[0]->unique_id());
874 node.add_property("count", string_compose("%1", _plugins.size()));
875 node.add_child_nocopy (_plugins[0]->get_state());
877 for (Controls::iterator c = controls().begin(); c != controls().end(); ++c) {
878 boost::shared_ptr<AutomationControl> ac = boost::dynamic_pointer_cast<AutomationControl> ((*c).second);
880 node.add_child_nocopy (ac->get_state());
888 PluginInsert::set_control_ids (const XMLNode& node, int version)
890 const XMLNodeList& nlist = node.children();
891 XMLNodeConstIterator iter;
892 set<Evoral::Parameter>::const_iterator p;
894 for (iter = nlist.begin(); iter != nlist.end(); ++iter) {
895 if ((*iter)->name() == Controllable::xml_node_name) {
896 const XMLProperty* prop;
898 if ((prop = (*iter)->property (X_("parameter"))) != 0) {
899 uint32_t p = atoi (prop->value());
901 /* this may create the new controllable */
903 boost::shared_ptr<Evoral::Control> c = control (Evoral::Parameter (PluginAutomation, 0, p));
905 #ifndef NO_PLUGIN_STATE
909 boost::shared_ptr<AutomationControl> ac = boost::dynamic_pointer_cast<AutomationControl> (c);
911 ac->set_state (**iter, version);
920 PluginInsert::set_state(const XMLNode& node, int version)
922 XMLNodeList nlist = node.children();
923 XMLNodeIterator niter;
924 XMLPropertyList plist;
925 const XMLProperty *prop;
926 ARDOUR::PluginType type;
928 if ((prop = node.property ("type")) == 0) {
929 error << _("XML node describing plugin is missing the `type' field") << endmsg;
933 if (prop->value() == X_("ladspa") || prop->value() == X_("Ladspa")) { /* handle old school sessions */
934 type = ARDOUR::LADSPA;
935 } else if (prop->value() == X_("lv2")) {
937 } else if (prop->value() == X_("windows-vst")) {
938 type = ARDOUR::Windows_VST;
939 } else if (prop->value() == X_("lxvst")) {
940 type = ARDOUR::LXVST;
941 } else if (prop->value() == X_("audiounit")) {
942 type = ARDOUR::AudioUnit;
944 error << string_compose (_("unknown plugin type %1 in plugin insert state"),
950 prop = node.property ("unique-id");
953 #ifdef WINDOWS_VST_SUPPORT
954 /* older sessions contain VST plugins with only an "id" field.
957 if (type == ARDOUR::Windows_VST) {
958 prop = node.property ("id");
963 /*There shouldn't be any older sessions with linuxVST support.. but anyway..*/
965 if (type == ARDOUR::LXVST) {
966 prop = node.property ("id");
972 error << _("Plugin has no unique ID field") << endmsg;
977 boost::shared_ptr<Plugin> plugin = find_plugin (_session, prop->value(), type);
979 /* treat linux and windows VST plugins equivalent if they have the same uniqueID
980 * allow to move sessions windows <> linux */
982 if (plugin == 0 && type == ARDOUR::Windows_VST) {
983 type = ARDOUR::LXVST;
984 plugin = find_plugin (_session, prop->value(), type);
988 #ifdef WINDOWS_VST_SUPPORT
989 if (plugin == 0 && type == ARDOUR::LXVST) {
990 type = ARDOUR::Windows_VST;
991 plugin = find_plugin (_session, prop->value(), type);
996 error << string_compose(
997 _("Found a reference to a plugin (\"%1\") that is unknown.\n"
998 "Perhaps it was removed or moved since it was last used."),
1004 // The name of the PluginInsert comes from the plugin, nothing else
1005 _name = plugin->get_info()->name;
1009 // Processor::set_state() will set this, but too late
1010 // for it to be available when setting up plugin
1011 // state. We can't call Processor::set_state() until
1012 // the plugins themselves are created and added.
1016 if (_plugins.empty()) {
1017 /* if we are adding the first plugin, we will need to set
1018 up automatable controls.
1020 add_plugin (plugin);
1021 create_automatable_parameters ();
1022 set_control_ids (node, version);
1025 if ((prop = node.property ("count")) != 0) {
1026 sscanf (prop->value().c_str(), "%u", &count);
1029 if (_plugins.size() != count) {
1030 for (uint32_t n = 1; n < count; ++n) {
1031 add_plugin (plugin_factory (plugin));
1035 Processor::set_state (node, version);
1037 for (niter = nlist.begin(); niter != nlist.end(); ++niter) {
1039 /* find the node with the type-specific node name ("lv2", "ladspa", etc)
1040 and set all plugins to the same state.
1043 if ((*niter)->name() == plugin->state_node_name()) {
1045 plugin->set_state (**niter, version);
1047 for (Plugins::iterator i = _plugins.begin(); i != _plugins.end(); ++i) {
1048 (*i)->set_state (**niter, version);
1055 if (version < 3000) {
1057 /* Only 2.X sessions need a call to set_parameter_state() - in 3.X and above
1058 this is all handled by Automatable
1061 for (niter = nlist.begin(); niter != nlist.end(); ++niter) {
1062 if ((*niter)->name() == "Redirect") {
1063 /* XXX do we need to tackle placement? i think not (pd; oct 16 2009) */
1064 Processor::set_state (**niter, version);
1069 set_parameter_state_2X (node, version);
1072 for (Plugins::iterator i = _plugins.begin(); i != _plugins.end(); ++i) {
1076 (*i)->deactivate ();
1084 PluginInsert::set_parameter_state_2X (const XMLNode& node, int version)
1086 XMLNodeList nlist = node.children();
1087 XMLNodeIterator niter;
1089 /* look for port automation node */
1091 for (niter = nlist.begin(); niter != nlist.end(); ++niter) {
1093 if ((*niter)->name() != port_automation_node_name) {
1099 XMLNodeConstIterator iter;
1104 cnodes = (*niter)->children ("port");
1106 for (iter = cnodes.begin(); iter != cnodes.end(); ++iter){
1110 if ((cprop = child->property("number")) != 0) {
1111 port = cprop->value().c_str();
1113 warning << _("PluginInsert: Auto: no ladspa port number") << endmsg;
1117 sscanf (port, "%" PRIu32, &port_id);
1119 if (port_id >= _plugins[0]->parameter_count()) {
1120 warning << _("PluginInsert: Auto: port id out of range") << endmsg;
1124 boost::shared_ptr<AutomationControl> c = boost::dynamic_pointer_cast<AutomationControl>(
1125 control(Evoral::Parameter(PluginAutomation, 0, port_id), true));
1128 if (!child->children().empty()) {
1129 c->alist()->set_state (*child->children().front(), version);
1131 /* In some cases 2.X saves lists with min_yval and max_yval
1132 being FLT_MIN and FLT_MAX respectively. This causes problems
1133 in A3 because these min/max values are used to compute
1134 where GUI control points should be drawn. If we see such
1135 values, `correct' them to the min/max of the appropriate
1139 float min_y = c->alist()->get_min_y ();
1140 float max_y = c->alist()->get_max_y ();
1142 Plugin::ParameterDescriptor desc;
1143 _plugins.front()->get_parameter_descriptor (port_id, desc);
1145 if (min_y == FLT_MIN) {
1149 if (max_y == FLT_MAX) {
1153 c->alist()->set_yrange (min_y, max_y);
1156 error << string_compose (_("PluginInsert: automatable control %1 not found - ignored"), port_id) << endmsg;
1168 PluginInsert::describe_parameter (Evoral::Parameter param)
1170 if (param.type() != PluginAutomation) {
1171 return Automatable::describe_parameter(param);
1174 return _plugins[0]->describe_parameter (param);
1178 PluginInsert::signal_latency() const
1180 if (_user_latency) {
1181 return _user_latency;
1184 return _plugins[0]->signal_latency ();
1188 PluginInsert::type ()
1190 return plugin()->get_info()->type;
1193 PluginInsert::PluginControl::PluginControl (PluginInsert* p, const Evoral::Parameter ¶m, boost::shared_ptr<AutomationList> list)
1194 : AutomationControl (p->session(), param, list, p->describe_parameter(param))
1197 Plugin::ParameterDescriptor desc;
1198 boost::shared_ptr<Plugin> plugin = p->plugin (0);
1200 alist()->reset_default (plugin->default_value (param.id()));
1202 plugin->get_parameter_descriptor (param.id(), desc);
1203 _logarithmic = desc.logarithmic;
1204 _sr_dependent = desc.sr_dependent;
1205 _toggled = desc.toggled;
1208 /** @param val `user' value */
1210 PluginInsert::PluginControl::set_value (double user_val)
1212 /* FIXME: probably should be taking out some lock here.. */
1214 for (Plugins::iterator i = _plugin->_plugins.begin(); i != _plugin->_plugins.end(); ++i) {
1215 (*i)->set_parameter (_list->parameter().id(), user_val);
1218 boost::shared_ptr<Plugin> iasp = _plugin->_impulseAnalysisPlugin.lock();
1220 iasp->set_parameter (_list->parameter().id(), user_val);
1223 AutomationControl::set_value (user_val);
1227 PluginInsert::PluginControl::internal_to_interface (double val) const
1230 /* some plugins have a log-scale range "0.."
1231 * ideally we'd map the range down to infinity somehow :)
1233 * one solution could be to use
1234 * val = exp(lower + log(range) * value);
1235 * (log(val) - lower) / range)
1236 * This approach would require access to the actual range (ie
1237 * Plugin::ParameterDescriptor) and also require handling
1238 * of unbound ranges..
1240 * currently an arbitrarly low number is assumed to represnt
1241 * log(0) as hot-fix solution.
1246 val = -8; // ~ -70dB = 20 * log10(exp(-8))
1254 PluginInsert::PluginControl::interface_to_internal (double val) const
1258 /* see note in PluginInsert::PluginControl::internal_to_interface() */
1269 PluginInsert::PluginControl::get_state ()
1273 XMLNode& node (AutomationControl::get_state());
1274 ss << parameter().id();
1275 node.add_property (X_("parameter"), ss.str());
1280 /** @return `user' val */
1282 PluginInsert::PluginControl::get_value () const
1284 /* FIXME: probably should be taking out some lock here.. */
1285 return _plugin->get_parameter (_list->parameter());
1288 boost::shared_ptr<Plugin>
1289 PluginInsert::get_impulse_analysis_plugin()
1291 boost::shared_ptr<Plugin> ret;
1292 if (_impulseAnalysisPlugin.expired()) {
1293 ret = plugin_factory(_plugins[0]);
1294 _impulseAnalysisPlugin = ret;
1296 ret = _impulseAnalysisPlugin.lock();
1303 PluginInsert::collect_signal_for_analysis (framecnt_t nframes)
1305 // called from outside the audio thread, so this should be safe
1306 // only do audio as analysis is (currently) only for audio plugins
1307 _signal_analysis_inputs.ensure_buffers( DataType::AUDIO, input_streams().n_audio(), nframes);
1308 _signal_analysis_outputs.ensure_buffers( DataType::AUDIO, output_streams().n_audio(), nframes);
1310 _signal_analysis_collected_nframes = 0;
1311 _signal_analysis_collect_nframes_max = nframes;
1314 /** Add a plugin to our list */
1316 PluginInsert::add_plugin (boost::shared_ptr<Plugin> plugin)
1318 plugin->set_insert_info (this);
1320 if (_plugins.empty()) {
1321 /* first (and probably only) plugin instance - connect to relevant signals
1324 plugin->ParameterChanged.connect_same_thread (*this, boost::bind (&PluginInsert::parameter_changed, this, _1, _2));
1325 plugin->StartTouch.connect_same_thread (*this, boost::bind (&PluginInsert::start_touch, this, _1));
1326 plugin->EndTouch.connect_same_thread (*this, boost::bind (&PluginInsert::end_touch, this, _1));
1329 _plugins.push_back (plugin);
1333 PluginInsert::realtime_handle_transport_stopped ()
1335 for (Plugins::iterator i = _plugins.begin(); i != _plugins.end(); ++i) {
1336 (*i)->realtime_handle_transport_stopped ();
1341 PluginInsert::realtime_locate ()
1343 for (Plugins::iterator i = _plugins.begin(); i != _plugins.end(); ++i) {
1344 (*i)->realtime_locate ();
1349 PluginInsert::monitoring_changed ()
1351 for (Plugins::iterator i = _plugins.begin(); i != _plugins.end(); ++i) {
1352 (*i)->monitoring_changed ();
1357 PluginInsert::start_touch (uint32_t param_id)
1359 boost::shared_ptr<AutomationControl> ac = automation_control (Evoral::Parameter (PluginAutomation, 0, param_id));
1361 ac->start_touch (session().audible_frame());
1366 PluginInsert::end_touch (uint32_t param_id)
1368 boost::shared_ptr<AutomationControl> ac = automation_control (Evoral::Parameter (PluginAutomation, 0, param_id));
1370 ac->stop_touch (true, session().audible_frame());