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/types_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/luaproc.h"
37 #include "ardour/plugin.h"
38 #include "ardour/plugin_insert.h"
39 #include "ardour/port.h"
42 #include "ardour/lv2_plugin.h"
45 #ifdef WINDOWS_VST_SUPPORT
46 #include "ardour/windows_vst_plugin.h"
50 #include "ardour/lxvst_plugin.h"
54 #include "ardour/mac_vst_plugin.h"
57 #ifdef AUDIOUNIT_SUPPORT
58 #include "ardour/audio_unit.h"
61 #include "ardour/session.h"
62 #include "ardour/types.h"
67 using namespace ARDOUR;
70 const string PluginInsert::port_automation_node_name = "PortAutomation";
72 PluginInsert::PluginInsert (Session& s, boost::shared_ptr<Plugin> plug)
73 : Processor (s, (plug ? plug->name() : string ("toBeRenamed")))
74 , _sc_playback_latency (0)
75 , _sc_capture_latency (0)
76 , _plugin_signal_latency (0)
77 , _signal_analysis_collected_nframes(0)
78 , _signal_analysis_collect_nframes_max(0)
83 , _maps_from_state (false)
84 , _latency_changed (false)
85 , _bypass_port (UINT32_MAX)
88 /* the first is the master */
92 create_automatable_parameters ();
93 const ChanCount& sc (sidechain_input_pins ());
94 if (sc.n_audio () > 0 || sc.n_midi () > 0) {
95 add_sidechain (sc.n_audio (), sc.n_midi ());
100 PluginInsert::~PluginInsert ()
102 for (CtrlOutMap::const_iterator i = _control_outputs.begin(); i != _control_outputs.end(); ++i) {
103 boost::dynamic_pointer_cast<ReadOnlyControl>(i->second)->drop_references ();
108 PluginInsert::set_strict_io (bool b)
110 bool changed = _strict_io != b;
113 PluginConfigChanged (); /* EMIT SIGNAL */
118 PluginInsert::set_count (uint32_t num)
120 bool require_state = !_plugins.empty();
122 if (require_state && num > 1 && plugin (0)->get_info ()->type == ARDOUR::AudioUnit) {
123 // we don't allow to replicate AUs
127 /* this is a bad idea.... we shouldn't do this while active.
128 * only a route holding their redirect_lock should be calling this
133 } else if (num > _plugins.size()) {
134 uint32_t diff = num - _plugins.size();
136 for (uint32_t n = 0; n < diff; ++n) {
137 boost::shared_ptr<Plugin> p = plugin_factory (_plugins[0]);
141 XMLNode& state = _plugins[0]->get_state ();
142 p->set_state (state, Stateful::loading_state_version);
149 PluginConfigChanged (); /* EMIT SIGNAL */
151 } else if (num < _plugins.size()) {
152 uint32_t diff = _plugins.size() - num;
153 for (uint32_t n= 0; n < diff; ++n) {
156 PluginConfigChanged (); /* EMIT SIGNAL */
164 PluginInsert::set_sinks (const ChanCount& c)
167 /* no signal, change will only be visible after re-config */
171 PluginInsert::set_outputs (const ChanCount& c)
173 bool changed = (_custom_out != c) && _custom_cfg;
176 PluginConfigChanged (); /* EMIT SIGNAL */
181 PluginInsert::set_custom_cfg (bool b)
183 bool changed = _custom_cfg != b;
186 PluginConfigChanged (); /* EMIT SIGNAL */
191 PluginInsert::set_preset_out (const ChanCount& c)
193 bool changed = _preset_out != c;
195 if (changed && !_custom_cfg) {
196 PluginConfigChanged (); /* EMIT SIGNAL */
202 PluginInsert::add_sidechain (uint32_t n_audio, uint32_t n_midi)
204 // caller must hold process lock
208 std::ostringstream n;
209 if (n_audio == 0 && n_midi == 0) {
210 n << "TO BE RESET FROM XML";
211 } else if (owner()) {
212 n << "SC " << owner()->name() << "/" << name() << " " << Session::next_name_id ();
216 SideChain *sc = new SideChain (_session, n.str ());
217 _sidechain = boost::shared_ptr<SideChain> (sc);
218 _sidechain->activate ();
219 for (uint32_t n = 0; n < n_audio; ++n) {
220 _sidechain->input()->add_port ("", owner(), DataType::AUDIO); // add a port, don't connect.
222 for (uint32_t n = 0; n < n_midi; ++n) {
223 _sidechain->input()->add_port ("", owner(), DataType::MIDI); // add a port, don't connect.
225 PluginConfigChanged (); /* EMIT SIGNAL */
230 PluginInsert::del_sidechain ()
236 _sc_playback_latency = 0;
237 _sc_capture_latency = 0;
238 PluginConfigChanged (); /* EMIT SIGNAL */
243 PluginInsert::update_sidechain_name ()
249 std::ostringstream n;
253 n << owner()->name() << "/";
256 n << name() << " " << Session::next_name_id ();
258 _sidechain->set_name (n.str());
262 PluginInsert::control_list_automation_state_changed (Evoral::Parameter which, AutoState s)
264 if (which.type() != PluginAutomation)
267 boost::shared_ptr<AutomationControl> c
268 = boost::dynamic_pointer_cast<AutomationControl>(control (which));
271 _plugins[0]->set_parameter (which.id(), c->list()->eval (_session.transport_sample()));
276 PluginInsert::output_streams() const
278 assert (_configured);
279 return _configured_out;
283 PluginInsert::input_streams() const
285 assert (_configured);
286 return _configured_in;
290 PluginInsert::internal_streams() const
292 assert (_configured);
293 return _configured_internal;
297 PluginInsert::internal_output_streams() const
299 assert (!_plugins.empty());
301 PluginInfoPtr info = _plugins.front()->get_info();
303 if (info->reconfigurable_io()) {
304 ChanCount out = _plugins.front()->output_streams ();
305 // DEBUG_TRACE (DEBUG::Processors, string_compose ("Plugin insert, reconfigur(able) output streams = %1\n", out));
308 ChanCount out = info->n_outputs;
309 // DEBUG_TRACE (DEBUG::Processors, string_compose ("Plugin insert, static output streams = %1 for %2 plugins\n", out, _plugins.size()));
310 out.set_audio (out.n_audio() * _plugins.size());
311 out.set_midi (out.n_midi() * _plugins.size());
317 PluginInsert::internal_input_streams() const
319 assert (!_plugins.empty());
323 PluginInfoPtr info = _plugins.front()->get_info();
325 if (info->reconfigurable_io()) {
326 in = _plugins.front()->input_streams();
331 DEBUG_TRACE (DEBUG::Processors, string_compose ("Plugin insert, input streams = %1, match using %2\n", in, _match.method));
333 if (_match.method == Split) {
335 /* we are splitting 1 processor input to multiple plugin inputs,
336 so we have a maximum of 1 stream of each type.
338 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
339 if (in.get (*t) > 1) {
345 } else if (_match.method == Hide) {
347 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
348 in.set (*t, in.get (*t) - _match.hide.get (*t));
354 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
355 in.set (*t, in.get (*t) * _plugins.size ());
363 PluginInsert::natural_output_streams() const
366 if (is_channelstrip ()) {
367 return ChanCount::min (_configured_out, ChanCount (DataType::AUDIO, 2));
370 return _plugins[0]->get_info()->n_outputs;
374 PluginInsert::natural_input_streams() const
377 if (is_channelstrip ()) {
378 return ChanCount::min (_configured_in, ChanCount (DataType::AUDIO, 2));
381 return _plugins[0]->get_info()->n_inputs;
385 PluginInsert::sidechain_input_pins() const
387 return _cached_sidechain_pins;
391 PluginInsert::has_no_inputs() const
393 return _plugins[0]->get_info()->n_inputs == ChanCount::ZERO;
397 PluginInsert::has_no_audio_inputs() const
399 return _plugins[0]->get_info()->n_inputs.n_audio() == 0;
403 PluginInsert::plugin_latency () const {
404 return _plugins.front()->signal_latency ();
408 PluginInsert::is_instrument() const
410 PluginInfoPtr pip = _plugins[0]->get_info();
411 return (pip->is_instrument ());
415 PluginInsert::has_output_presets (ChanCount in, ChanCount out)
417 if (!_configured && _plugins[0]->get_info ()->reconfigurable_io ()) {
418 // collect possible configurations, prefer given in/out
419 _plugins[0]->can_support_io_configuration (in, out);
422 PluginOutputConfiguration ppc (_plugins[0]->possible_output ());
424 if (ppc.size () == 0) {
427 if (!strict_io () && ppc.size () == 1) {
431 if (strict_io () && ppc.size () == 1) {
432 // "stereo" is currently preferred default for instruments
433 if (ppc.find (2) != ppc.end ()) {
438 if (ppc.size () == 1 && ppc.find (0) != ppc.end () && !_plugins[0]->get_info ()->reconfigurable_io ()) {
439 // some midi-sequencer (e.g. QMidiArp) or other midi-out plugin
440 // pretending to be an "Instrument"
444 if (!is_instrument ()) {
451 PluginInsert::create_automatable_parameters ()
453 assert (!_plugins.empty());
455 boost::shared_ptr<Plugin> plugin = _plugins.front();
456 set<Evoral::Parameter> a = _plugins.front()->automatable ();
458 const uint32_t limit_automatables = Config->get_limit_n_automatables ();
460 for (uint32_t i = 0; i < plugin->parameter_count(); ++i) {
461 if (!plugin->parameter_is_control (i)) {
465 ParameterDescriptor desc;
466 plugin->get_parameter_descriptor(i, desc);
468 if (!plugin->parameter_is_input (i)) {
469 _control_outputs[i] = boost::shared_ptr<ReadOnlyControl> (new ReadOnlyControl (plugin, desc, i));
472 Evoral::Parameter param (PluginAutomation, 0, i);
474 const bool automatable = a.find(param) != a.end();
476 boost::shared_ptr<AutomationList> list(new AutomationList(param, desc));
477 boost::shared_ptr<AutomationControl> c (new PluginControl(this, param, desc, list));
478 if (!automatable || (limit_automatables > 0 && i > limit_automatables)) {
479 c->set_flags (Controllable::Flag ((int)c->flags() | Controllable::NotAutomatable));
482 plugin->set_automation_control (i, c);
486 const Plugin::PropertyDescriptors& pdl (plugin->get_supported_properties ());
487 for (Plugin::PropertyDescriptors::const_iterator p = pdl.begin(); p != pdl.end(); ++p) {
488 Evoral::Parameter param (PluginPropertyAutomation, 0, p->first);
489 const ParameterDescriptor& desc = plugin->get_property_descriptor(param.id());
490 if (desc.datatype != Variant::NOTHING) {
491 boost::shared_ptr<AutomationList> list;
492 if (Variant::type_is_numeric(desc.datatype)) {
493 list = boost::shared_ptr<AutomationList>(new AutomationList(param, desc));
495 boost::shared_ptr<AutomationControl> c (new PluginPropertyControl(this, param, desc, list));
496 if (!Variant::type_is_numeric(desc.datatype)) {
497 c->set_flags (Controllable::Flag ((int)c->flags() | Controllable::NotAutomatable));
503 _bypass_port = plugin->designated_bypass_port ();
505 /* special case VST effSetBypass */
506 if (_bypass_port == UINT32_MAX -1) {
507 // emulate VST Bypass
508 Evoral::Parameter param (PluginAutomation, 0, _bypass_port);
509 ParameterDescriptor desc;
510 desc.label = _("Plugin Enable");
515 boost::shared_ptr<AutomationList> list(new AutomationList(param, desc));
516 boost::shared_ptr<AutomationControl> c (new PluginControl(this, param, desc, list));
520 if (_bypass_port != UINT32_MAX) {
521 boost::shared_ptr<AutomationControl> ac = automation_control (Evoral::Parameter (PluginAutomation, 0, _bypass_port));
522 if (0 == (ac->flags () & Controllable::NotAutomatable)) {
523 ac->alist()->automation_state_changed.connect_same_thread (*this, boost::bind (&PluginInsert::bypassable_changed, this));
524 ac->Changed.connect_same_thread (*this, boost::bind (&PluginInsert::enable_changed, this));
527 plugin->PresetPortSetValue.connect_same_thread (*this, boost::bind (&PluginInsert::preset_load_set_value, this, _1, _2));
530 /** Called when something outside of this host has modified a plugin
531 * parameter. Responsible for propagating the change to two places:
533 * 1) anything listening to the Control itself
534 * 2) any replicated plugins that make up this PluginInsert.
536 * The PluginInsert is connected to the ParameterChangedExternally signal for
537 * the first (primary) plugin, and here broadcasts that change to any others.
539 * XXX We should probably drop this whole replication idea (Paul, October 2015)
540 * since it isn't used by sensible plugin APIs (AU, LV2).
543 PluginInsert::parameter_changed_externally (uint32_t which, float val)
545 boost::shared_ptr<AutomationControl> ac = automation_control (Evoral::Parameter (PluginAutomation, 0, which));
547 /* First propagation: alter the underlying value of the control,
548 * without telling the plugin(s) that own/use it to set it.
555 boost::shared_ptr<PluginControl> pc = boost::dynamic_pointer_cast<PluginControl> (ac);
558 pc->catch_up_with_external_value (val);
561 /* Second propagation: tell all plugins except the first to
562 update the value of this parameter. For sane plugin APIs,
563 there are no other plugins, so this is a no-op in those
567 Plugins::iterator i = _plugins.begin();
569 /* don't set the first plugin, just all the slaves */
571 if (i != _plugins.end()) {
573 for (; i != _plugins.end(); ++i) {
574 (*i)->set_parameter (which, val);
580 PluginInsert::set_block_size (pframes_t nframes)
583 for (Plugins::iterator i = _plugins.begin(); i != _plugins.end(); ++i) {
584 if ((*i)->set_block_size (nframes) != 0) {
592 PluginInsert::automation_run (samplepos_t start, pframes_t nframes)
594 // XXX does not work when rolling backwards
595 if (_loop_location && nframes > 0) {
596 const samplepos_t loop_start = _loop_location->start ();
597 const samplepos_t loop_end = _loop_location->end ();
598 const samplecnt_t looplen = loop_end - loop_start;
600 samplecnt_t remain = nframes;
601 samplepos_t start_pos = start;
604 if (start_pos >= loop_end) {
605 sampleoffset_t start_off = (start_pos - loop_start) % looplen;
606 start_pos = loop_start + start_off;
608 samplecnt_t move = std::min ((samplecnt_t)nframes, loop_end - start_pos);
610 Automatable::automation_run (start_pos, move);
616 Automatable::automation_run (start, nframes);
620 PluginInsert::find_next_event (double now, double end, Evoral::ControlEvent& next_event, bool only_active) const
622 bool rv = Automatable::find_next_event (now, end, next_event, only_active);
624 if (_loop_location && now < end) {
626 end = ceil (next_event.when);
628 const samplepos_t loop_end = _loop_location->end ();
629 assert (now < loop_end); // due to map_loop_range ()
630 if (end > loop_end) {
631 next_event.when = loop_end;
639 PluginInsert::activate ()
641 _timing_stats.reset ();
642 for (Plugins::iterator i = _plugins.begin(); i != _plugins.end(); ++i) {
646 Processor::activate ();
647 /* when setting state e.g ProcessorBox::paste_processor_state ()
648 * the plugin is not yet owned by a route.
649 * but no matter. Route::add_processors() will call activate () again
654 if (_plugin_signal_latency != signal_latency ()) {
655 _plugin_signal_latency = signal_latency ();
661 PluginInsert::deactivate ()
664 if (is_nonbypassable ()) {
668 _timing_stats.reset ();
669 Processor::deactivate ();
671 for (Plugins::iterator i = _plugins.begin(); i != _plugins.end(); ++i) {
674 if (_plugin_signal_latency != signal_latency ()) {
675 _plugin_signal_latency = signal_latency ();
681 PluginInsert::flush ()
683 for (vector<boost::shared_ptr<Plugin> >::iterator i = _plugins.begin(); i != _plugins.end(); ++i) {
689 PluginInsert::enable (bool yn)
691 if (_bypass_port == UINT32_MAX) {
698 if (!_pending_active) {
701 boost::shared_ptr<AutomationControl> ac = automation_control (Evoral::Parameter (PluginAutomation, 0, _bypass_port));
702 const double val = yn ? 1.0 : 0.0;
703 ac->set_value (val, Controllable::NoGroup);
705 #ifdef ALLOW_VST_BYPASS_TO_FAIL // yet unused, see also vst_plugin.cc
706 /* special case VST.. bypass may fail */
707 if (_bypass_port == UINT32_MAX - 1) {
708 /* check if bypass worked */
709 if (ac->get_value () != val) {
710 warning << _("PluginInsert: VST Bypass failed, falling back to host bypass.") << endmsg;
711 // set plugin to enabled (not-byassed)
712 ac->set_value (1.0, Controllable::NoGroup);
713 // ..and use host-provided hard-bypass
728 PluginInsert::enabled () const
730 if (_bypass_port == UINT32_MAX) {
731 return Processor::enabled ();
733 boost::shared_ptr<const AutomationControl> ac = boost::const_pointer_cast<AutomationControl> (automation_control (Evoral::Parameter (PluginAutomation, 0, _bypass_port)));
734 return (ac->get_value () > 0 && _pending_active);
739 PluginInsert::bypassable () const
741 if (_bypass_port == UINT32_MAX) {
744 boost::shared_ptr<const AutomationControl> ac = boost::const_pointer_cast<AutomationControl> (automation_control (Evoral::Parameter (PluginAutomation, 0, _bypass_port)));
746 return !ac->automation_playback ();
751 PluginInsert::enable_changed ()
757 PluginInsert::bypassable_changed ()
759 BypassableChanged ();
763 PluginInsert::write_immediate_event (size_t size, const uint8_t* buf)
766 for (Plugins::iterator i = _plugins.begin(); i != _plugins.end(); ++i) {
767 if (!(*i)->write_immediate_event (size, buf)) {
775 PluginInsert::preset_load_set_value (uint32_t p, float v)
777 boost::shared_ptr<AutomationControl> ac = automation_control (Evoral::Parameter(PluginAutomation, 0, p));
782 if (ac->automation_state() & Play) {
787 ac->set_value (v, Controllable::NoGroup);
792 PluginInsert::inplace_silence_unconnected (BufferSet& bufs, const PinMappings& out_map, samplecnt_t nframes, samplecnt_t offset) const
794 // TODO optimize: store "unconnected" in a fixed set.
795 // it only changes on reconfiguration.
796 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
797 for (uint32_t out = 0; out < bufs.count().get (*t); ++out) {
799 if (*t == DataType::MIDI && out == 0 && has_midi_bypass ()) {
800 mapped = true; // in-place Midi bypass
802 for (uint32_t pc = 0; pc < get_count() && !mapped; ++pc) {
803 PinMappings::const_iterator i = out_map.find (pc);
804 if (i == out_map.end ()) {
807 const ChanMapping& outmap (i->second);
808 for (uint32_t o = 0; o < natural_output_streams().get (*t); ++o) {
810 uint32_t idx = outmap.get (*t, o, &valid);
811 if (valid && idx == out) {
818 bufs.get (*t, out).silence (nframes, offset);
825 PluginInsert::connect_and_run (BufferSet& bufs, samplepos_t start, samplepos_t end, double speed, pframes_t nframes, samplecnt_t offset, bool with_auto)
827 if (_mapping_changed) { // ToDo use a counter, increment until match
828 _no_inplace = check_inplace ();
829 _mapping_changed = false;
831 // TODO: atomically copy maps & _no_inplace
832 PinMappings in_map (_in_map); // TODO Split case below overrides, use const& in_map
833 PinMappings const& out_map (_out_map);
834 ChanMapping const& thru_map (_thru_map);
836 if (_latency_changed) {
837 /* delaylines are configured with the max possible latency (as reported by the plugin)
838 * so this won't allocate memory (unless the plugin lied about its max latency)
839 * It may still 'click' though, since the fixed delaylines are not de-clicked.
840 * Then again plugin-latency changes are not click-free to begin with.
842 * This is also worst case, there is currently no concept of per-stream latency.
844 * e.g. Two identical latent plugins:
845 * 1st plugin: process left (latent), bypass right.
846 * 2nd plugin: bypass left, process right (latent).
847 * -> currently this yields 2 times latency of the plugin,
849 _latency_changed = false;
850 _delaybuffers.set (ChanCount::max(bufs.count(), _configured_out), plugin_latency ());
853 if (_match.method == Split && !_no_inplace) {
854 // TODO: also use this optimization if one source-buffer
855 // feeds _all_ *connected* inputs.
856 // currently this is *first* buffer to all only --
857 // see PluginInsert::check_inplace
858 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
859 if (_configured_internal.get (*t) == 0) {
863 uint32_t first_idx = in_map.p(0).get (*t, 0, &valid);
864 assert (valid && first_idx == 0); // check_inplace ensures this
865 /* copy the first stream's buffer contents to the others */
866 for (uint32_t i = 1; i < natural_input_streams ().get (*t); ++i) {
867 uint32_t idx = in_map.p(0).get (*t, i, &valid);
870 bufs.get (*t, i).read_from (bufs.get (*t, first_idx), nframes, offset, offset);
874 /* the copy operation produces a linear monotonic input map */
875 in_map[0] = ChanMapping (natural_input_streams ());
878 bufs.set_count(ChanCount::max(bufs.count(), _configured_internal));
879 bufs.set_count(ChanCount::max(bufs.count(), _configured_out));
885 for (Controls::const_iterator li = controls().begin(); li != controls().end(); ++li, ++n) {
887 /* boost::dynamic_pointer_cast<> has significant overhead, since we know that
888 * all controls are AutomationControl and their lists - if any - are AutomationList,
889 * we can use static_cast<>. This yields a speedup of 2.8/4.6 over to the
890 * previous code (measuerd with VeeSeeVSTRack 10k parameters, optimized build) */
891 AutomationControl& c = static_cast<AutomationControl&> (*(li->second));
892 boost::shared_ptr<const Evoral::ControlList> clist (c.list());
893 if (clist && (static_cast<AutomationList const&> (*clist)).automation_playback ()) {
895 const float val = c.list()->rt_safe_eval (start, valid);
897 c.set_value_unchecked(val);
903 /* Calculate if, and how many samples we need to collect for analysis */
904 samplecnt_t collect_signal_nframes = (_signal_analysis_collect_nframes_max -
905 _signal_analysis_collected_nframes);
906 if (nframes < collect_signal_nframes) { // we might not get all samples now
907 collect_signal_nframes = nframes;
910 if (collect_signal_nframes > 0) {
912 //std::cerr << "collect input, bufs " << bufs.count().n_audio() << " count, " << bufs.available().n_audio() << " available" << std::endl;
913 //std::cerr << " streams " << internal_input_streams().n_audio() << std::endl;
914 //std::cerr << "filling buffer with " << collect_signal_nframes << " samples at " << _signal_analysis_collected_nframes << std::endl;
916 _signal_analysis_inputs.set_count (ChanCount (DataType::AUDIO, input_streams().n_audio()));
918 for (uint32_t i = 0; i < input_streams().n_audio(); ++i) {
919 _signal_analysis_inputs.get_audio(i).read_from (
921 collect_signal_nframes,
922 _signal_analysis_collected_nframes); // offset is for target buffer
927 if (is_channelstrip ()) {
928 if (_configured_in.n_audio() > 0) {
929 ChanMapping mb_in_map (ChanCount::min (_configured_in, ChanCount (DataType::AUDIO, 2)));
930 ChanMapping mb_out_map (ChanCount::min (_configured_out, ChanCount (DataType::AUDIO, 2)));
932 _plugins.front()->connect_and_run (bufs, start, end, speed, mb_in_map, mb_out_map, nframes, offset);
934 for (uint32_t out = _configured_in.n_audio (); out < bufs.count().get (DataType::AUDIO); ++out) {
935 bufs.get (DataType::AUDIO, out).silence (nframes, offset);
941 // TODO optimize -- build maps once.
943 BufferSet& inplace_bufs = _session.get_noinplace_buffers();
944 ARDOUR::ChanMapping used_outputs;
946 assert (inplace_bufs.count () >= natural_input_streams () + _configured_out);
948 /* build used-output map */
949 for (Plugins::iterator i = _plugins.begin(); i != _plugins.end(); ++i, ++pc) {
950 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
951 for (uint32_t out = 0; out < natural_output_streams().get (*t); ++out) {
953 uint32_t out_idx = out_map.p(pc).get (*t, out, &valid);
955 used_outputs.set (*t, out_idx, 1); // mark as used
960 /* copy thru data to outputs before processing in-place */
961 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
962 for (uint32_t out = 0; out < bufs.count().get (*t); ++out) {
964 uint32_t in_idx = thru_map.get (*t, out, &valid);
965 uint32_t m = out + natural_input_streams ().get (*t);
967 _delaybuffers.delay (*t, out, inplace_bufs.get (*t, m), bufs.get (*t, in_idx), nframes, offset, offset);
968 used_outputs.set (*t, out, 1); // mark as used
970 used_outputs.get (*t, out, &valid);
972 /* the plugin is expected to write here, but may not :(
973 * (e.g. drumgizmo w/o kit loaded)
975 inplace_bufs.get (*t, m).silence (nframes);
982 for (Plugins::iterator i = _plugins.begin(); i != _plugins.end(); ++i, ++pc) {
984 ARDOUR::ChanMapping i_in_map (natural_input_streams());
985 ARDOUR::ChanMapping i_out_map (out_map.p(pc));
986 ARDOUR::ChanCount mapped;
988 /* map inputs sequentially */
989 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
990 for (uint32_t in = 0; in < natural_input_streams().get (*t); ++in) {
992 uint32_t in_idx = in_map.p(pc).get (*t, in, &valid);
993 uint32_t m = mapped.get (*t);
995 inplace_bufs.get (*t, m).read_from (bufs.get (*t, in_idx), nframes, offset, offset);
997 inplace_bufs.get (*t, m).silence (nframes, offset);
999 mapped.set (*t, m + 1);
1003 /* outputs are mapped to inplace_bufs after the inputs */
1004 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
1005 i_out_map.offset_to (*t, natural_input_streams ().get (*t));
1008 if ((*i)->connect_and_run (inplace_bufs, start, end, speed, i_in_map, i_out_map, nframes, offset)) {
1013 /* all instances have completed, now copy data that was written
1014 * and zero unconnected buffers */
1015 ARDOUR::ChanMapping nonzero_out (used_outputs);
1016 if (has_midi_bypass ()) {
1017 nonzero_out.set (DataType::MIDI, 0, 1); // Midi bypass.
1019 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
1020 for (uint32_t out = 0; out < bufs.count().get (*t); ++out) {
1022 used_outputs.get (*t, out, &valid);
1024 nonzero_out.get (*t, out, &valid);
1026 bufs.get (*t, out).silence (nframes, offset);
1029 uint32_t m = out + natural_input_streams ().get (*t);
1030 bufs.get (*t, out).read_from (inplace_bufs.get (*t, m), nframes, offset, offset);
1035 /* in-place processing */
1037 for (Plugins::iterator i = _plugins.begin(); i != _plugins.end(); ++i, ++pc) {
1038 if ((*i)->connect_and_run(bufs, start, end, speed, in_map.p(pc), out_map.p(pc), nframes, offset)) {
1042 // now silence unconnected outputs
1043 inplace_silence_unconnected (bufs, _out_map, nframes, offset);
1046 if (collect_signal_nframes > 0) {
1048 //std::cerr << " output, bufs " << bufs.count().n_audio() << " count, " << bufs.available().n_audio() << " available" << std::endl;
1049 //std::cerr << " streams " << internal_output_streams().n_audio() << std::endl;
1051 _signal_analysis_outputs.set_count (ChanCount (DataType::AUDIO, output_streams().n_audio()));
1053 for (uint32_t i = 0; i < output_streams().n_audio(); ++i) {
1054 _signal_analysis_outputs.get_audio(i).read_from(
1056 collect_signal_nframes,
1057 _signal_analysis_collected_nframes); // offset is for target buffer
1060 _signal_analysis_collected_nframes += collect_signal_nframes;
1061 assert(_signal_analysis_collected_nframes <= _signal_analysis_collect_nframes_max);
1063 if (_signal_analysis_collected_nframes == _signal_analysis_collect_nframes_max) {
1064 _signal_analysis_collect_nframes_max = 0;
1065 _signal_analysis_collected_nframes = 0;
1067 AnalysisDataGathered(&_signal_analysis_inputs,
1068 &_signal_analysis_outputs);
1072 if (_plugin_signal_latency != signal_latency ()) {
1073 _plugin_signal_latency = signal_latency ();
1079 PluginInsert::bypass (BufferSet& bufs, pframes_t nframes)
1081 /* bypass the plugin(s) not the whole processor.
1082 * -> use mappings just like connect_and_run
1084 if (_mapping_changed) {
1085 _no_inplace = check_inplace ();
1086 _mapping_changed = false;
1088 // TODO: atomically copy maps & _no_inplace
1089 ChanMapping const& in_map (no_sc_input_map ());
1090 ChanMapping const& out_map (output_map ());
1092 bufs.set_count(ChanCount::max(bufs.count(), _configured_internal));
1093 bufs.set_count(ChanCount::max(bufs.count(), _configured_out));
1096 ChanMapping thru_map (_thru_map);
1098 BufferSet& inplace_bufs = _session.get_noinplace_buffers();
1100 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
1101 for (uint32_t in = 0; in < _configured_internal.get (*t); ++in) {
1102 inplace_bufs.get (*t, in).read_from (bufs.get (*t, in), nframes, 0, 0);
1105 ARDOUR::ChanMapping used_outputs;
1107 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
1108 for (uint32_t out = 0; out < _configured_out.get (*t); ++out) {
1110 uint32_t in_idx = thru_map.get (*t, out, &valid);
1112 bufs.get (*t, out).read_from (inplace_bufs.get (*t, in_idx), nframes, 0, 0);
1113 used_outputs.set (*t, out, 1); // mark as used
1117 // plugin no-op: assume every plugin has an internal identity map
1118 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
1119 for (uint32_t out = 0; out < _configured_out.get (*t); ++out) {
1121 uint32_t src_idx = out_map.get_src (*t, out, &valid);
1125 uint32_t in_idx = in_map.get (*t, src_idx, &valid);
1129 bufs.get (*t, out).read_from (inplace_bufs.get (*t, in_idx), nframes, 0, 0);
1130 used_outputs.set (*t, out, 1); // mark as used
1133 // now silence all unused outputs
1134 if (has_midi_bypass ()) {
1135 used_outputs.set (DataType::MIDI, 0, 1); // Midi bypass.
1137 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
1138 for (uint32_t out = 0; out < _configured_out.get (*t); ++out) {
1140 used_outputs.get (*t, out, &valid);
1142 bufs.get (*t, out).silence (nframes, 0);
1147 if (_match.method == Split) {
1148 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
1149 if (_configured_internal.get (*t) == 0) {
1152 // copy/feeds _all_ *connected* inputs, copy the first buffer
1154 uint32_t first_idx = in_map.get (*t, 0, &valid);
1155 assert (valid && first_idx == 0); // check_inplace ensures this
1156 for (uint32_t i = 1; i < natural_input_streams ().get (*t); ++i) {
1157 uint32_t idx = in_map.get (*t, i, &valid);
1160 bufs.get (*t, i).read_from (bufs.get (*t, first_idx), nframes, 0, 0);
1166 // apply output map and/or monotonic but not identity i/o mappings
1167 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
1168 for (uint32_t out = 0; out < _configured_out.get (*t); ++out) {
1170 uint32_t src_idx = out_map.get_src (*t, out, &valid);
1172 bufs.get (*t, out).silence (nframes, 0);
1175 uint32_t in_idx = in_map.get (*t, src_idx, &valid);
1177 bufs.get (*t, out).silence (nframes, 0);
1180 if (in_idx != src_idx) {
1181 bufs.get (*t, out).read_from (bufs.get (*t, in_idx), nframes, 0, 0);
1189 PluginInsert::silence (samplecnt_t nframes, samplepos_t start_sample)
1191 automation_run (start_sample, nframes); // evaluate automation only
1194 // XXX delaybuffers need to be offset by nframes
1198 _delaybuffers.flush ();
1200 const ChanMapping in_map (natural_input_streams ());
1201 const ChanMapping out_map (natural_output_streams ());
1202 ChanCount maxbuf = ChanCount::max (natural_input_streams (), natural_output_streams());
1204 if (is_channelstrip ()) {
1205 if (_configured_in.n_audio() > 0) {
1206 _plugins.front()->connect_and_run (_session.get_scratch_buffers (maxbuf, true), start_sample, start_sample + nframes, 1.0, in_map, out_map, nframes, 0);
1210 for (Plugins::iterator i = _plugins.begin(); i != _plugins.end(); ++i) {
1211 (*i)->connect_and_run (_session.get_scratch_buffers (maxbuf, true), start_sample, start_sample + nframes, 1.0, in_map, out_map, nframes, 0);
1216 PluginInsert::run (BufferSet& bufs, samplepos_t start_sample, samplepos_t end_sample, double speed, pframes_t nframes, bool)
1219 // collect sidechain input for complete cycle (!)
1220 // TODO we need delaylines here for latency compensation
1221 _sidechain->run (bufs, start_sample, end_sample, speed, nframes, true);
1224 if (g_atomic_int_compare_and_exchange (&_stat_reset, 1, 0)) {
1225 _timing_stats.reset ();
1228 if (_pending_active) {
1229 _timing_stats.start ();
1230 /* run as normal if we are active or moving from inactive to active */
1232 if (_session.transport_rolling() || _session.bounce_processing()) {
1233 automate_and_run (bufs, start_sample, end_sample, speed, nframes);
1235 Glib::Threads::Mutex::Lock lm (control_lock(), Glib::Threads::TRY_LOCK);
1236 connect_and_run (bufs, start_sample, end_sample, speed, nframes, 0, lm.locked());
1238 _timing_stats.update ();
1241 _timing_stats.reset ();
1242 // XXX should call ::silence() to run plugin(s) for consistent load.
1243 // We'll need to change this anyway when bypass can be automated
1244 bypass (bufs, nframes);
1245 automation_run (start_sample, nframes); // evaluate automation only
1246 _delaybuffers.flush ();
1249 _active = _pending_active;
1251 /* we have no idea whether the plugin generated silence or not, so mark
1252 * all buffers appropriately.
1257 PluginInsert::automate_and_run (BufferSet& bufs, samplepos_t start, samplepos_t end, double speed, pframes_t nframes)
1259 Evoral::ControlEvent next_event (0, 0.0f);
1260 samplecnt_t offset = 0;
1262 Glib::Threads::Mutex::Lock lm (control_lock(), Glib::Threads::TRY_LOCK);
1265 connect_and_run (bufs, start, end, speed, nframes, offset, false);
1269 /* map start back into loop-range, adjust end */
1270 map_loop_range (start, end);
1272 if (!find_next_event (start, end, next_event) || _plugins.front()->requires_fixed_sized_buffers()) {
1274 /* no events have a time within the relevant range */
1276 connect_and_run (bufs, start, end, speed, nframes, offset, true);
1282 samplecnt_t cnt = min (((samplecnt_t) ceil (next_event.when) - start), (samplecnt_t) nframes);
1284 connect_and_run (bufs, start, start + cnt, speed, cnt, offset, true); // XXX (start + cnt) * speed
1290 map_loop_range (start, end);
1292 if (!find_next_event (start, end, next_event)) {
1297 /* cleanup anything that is left to do */
1300 connect_and_run (bufs, start, start + nframes, speed, nframes, offset, true);
1305 PluginInsert::default_parameter_value (const Evoral::Parameter& param)
1307 if (param.type() != PluginAutomation)
1310 if (_plugins.empty()) {
1311 fatal << _("programming error: ") << X_("PluginInsert::default_parameter_value() called with no plugin")
1313 abort(); /*NOTREACHED*/
1316 return _plugins[0]->default_value (param.id());
1321 PluginInsert::can_reset_all_parameters ()
1324 uint32_t params = 0;
1325 for (uint32_t par = 0; par < _plugins[0]->parameter_count(); ++par) {
1327 const uint32_t cid = _plugins[0]->nth_parameter (par, ok);
1329 if (!ok || !_plugins[0]->parameter_is_input(cid)) {
1333 boost::shared_ptr<AutomationControl> ac = automation_control (Evoral::Parameter(PluginAutomation, 0, cid));
1339 if (ac->automation_state() & Play) {
1344 return all && (params > 0);
1348 PluginInsert::reset_parameters_to_default ()
1352 for (uint32_t par = 0; par < _plugins[0]->parameter_count(); ++par) {
1354 const uint32_t cid = _plugins[0]->nth_parameter (par, ok);
1356 if (!ok || !_plugins[0]->parameter_is_input(cid)) {
1360 const float dflt = _plugins[0]->default_value (cid);
1361 const float curr = _plugins[0]->get_parameter (cid);
1367 boost::shared_ptr<AutomationControl> ac = automation_control (Evoral::Parameter(PluginAutomation, 0, cid));
1372 if (ac->automation_state() & Play) {
1377 ac->set_value (dflt, Controllable::NoGroup);
1382 boost::shared_ptr<Plugin>
1383 PluginInsert::plugin_factory (boost::shared_ptr<Plugin> other)
1385 boost::shared_ptr<LadspaPlugin> lp;
1386 boost::shared_ptr<LuaProc> lua;
1388 boost::shared_ptr<LV2Plugin> lv2p;
1390 #ifdef WINDOWS_VST_SUPPORT
1391 boost::shared_ptr<WindowsVSTPlugin> vp;
1393 #ifdef LXVST_SUPPORT
1394 boost::shared_ptr<LXVSTPlugin> lxvp;
1396 #ifdef MACVST_SUPPORT
1397 boost::shared_ptr<MacVSTPlugin> mvp;
1399 #ifdef AUDIOUNIT_SUPPORT
1400 boost::shared_ptr<AUPlugin> ap;
1403 if ((lp = boost::dynamic_pointer_cast<LadspaPlugin> (other)) != 0) {
1404 return boost::shared_ptr<Plugin> (new LadspaPlugin (*lp));
1405 } else if ((lua = boost::dynamic_pointer_cast<LuaProc> (other)) != 0) {
1406 return boost::shared_ptr<Plugin> (new LuaProc (*lua));
1408 } else if ((lv2p = boost::dynamic_pointer_cast<LV2Plugin> (other)) != 0) {
1409 return boost::shared_ptr<Plugin> (new LV2Plugin (*lv2p));
1411 #ifdef WINDOWS_VST_SUPPORT
1412 } else if ((vp = boost::dynamic_pointer_cast<WindowsVSTPlugin> (other)) != 0) {
1413 return boost::shared_ptr<Plugin> (new WindowsVSTPlugin (*vp));
1415 #ifdef LXVST_SUPPORT
1416 } else if ((lxvp = boost::dynamic_pointer_cast<LXVSTPlugin> (other)) != 0) {
1417 return boost::shared_ptr<Plugin> (new LXVSTPlugin (*lxvp));
1419 #ifdef MACVST_SUPPORT
1420 } else if ((mvp = boost::dynamic_pointer_cast<MacVSTPlugin> (other)) != 0) {
1421 return boost::shared_ptr<Plugin> (new MacVSTPlugin (*mvp));
1423 #ifdef AUDIOUNIT_SUPPORT
1424 } else if ((ap = boost::dynamic_pointer_cast<AUPlugin> (other)) != 0) {
1425 return boost::shared_ptr<Plugin> (new AUPlugin (*ap));
1429 fatal << string_compose (_("programming error: %1"),
1430 X_("unknown plugin type in PluginInsert::plugin_factory"))
1432 abort(); /*NOTREACHED*/
1433 return boost::shared_ptr<Plugin> ((Plugin*) 0);
1437 PluginInsert::set_input_map (uint32_t num, ChanMapping m) {
1438 if (num < _in_map.size()) {
1439 bool changed = _in_map[num] != m;
1441 changed |= sanitize_maps ();
1443 PluginMapChanged (); /* EMIT SIGNAL */
1444 _mapping_changed = true;
1445 _session.set_dirty();
1451 PluginInsert::set_output_map (uint32_t num, ChanMapping m) {
1452 if (num < _out_map.size()) {
1453 bool changed = _out_map[num] != m;
1455 changed |= sanitize_maps ();
1457 PluginMapChanged (); /* EMIT SIGNAL */
1458 _mapping_changed = true;
1459 _session.set_dirty();
1465 PluginInsert::set_thru_map (ChanMapping m) {
1466 bool changed = _thru_map != m;
1468 changed |= sanitize_maps ();
1470 PluginMapChanged (); /* EMIT SIGNAL */
1471 _mapping_changed = true;
1472 _session.set_dirty();
1477 PluginInsert::pre_seed (const ChanCount& in, const ChanCount& out,
1478 const ChanMapping& im, const ChanMapping& om, const ChanMapping& tm)
1480 if (_configured) { return false; }
1481 _configured_in = in;
1482 _configured_out = out;
1486 _maps_from_state = in.n_total () > 0 && out.n_total () > 0;
1491 PluginInsert::input_map () const
1495 for (PinMappings::const_iterator i = _in_map.begin (); i != _in_map.end (); ++i, ++pc) {
1496 ChanMapping m (i->second);
1497 const ChanMapping::Mappings& mp ((*i).second.mappings());
1498 for (ChanMapping::Mappings::const_iterator tm = mp.begin(); tm != mp.end(); ++tm) {
1499 for (ChanMapping::TypeMapping::const_iterator i = tm->second.begin(); i != tm->second.end(); ++i) {
1500 rv.set (tm->first, i->first + pc * natural_input_streams().get(tm->first), i->second);
1509 PluginInsert::no_sc_input_map () const
1513 for (PinMappings::const_iterator i = _in_map.begin (); i != _in_map.end (); ++i, ++pc) {
1514 ChanMapping m (i->second);
1515 const ChanMapping::Mappings& mp ((*i).second.mappings());
1516 for (ChanMapping::Mappings::const_iterator tm = mp.begin(); tm != mp.end(); ++tm) {
1517 uint32_t ins = natural_input_streams().get(tm->first) - _cached_sidechain_pins.get(tm->first);
1518 for (ChanMapping::TypeMapping::const_iterator i = tm->second.begin(); i != tm->second.end(); ++i) {
1519 if (i->first < ins) {
1520 rv.set (tm->first, i->first + pc * ins, i->second);
1529 PluginInsert::output_map () const
1533 for (PinMappings::const_iterator i = _out_map.begin (); i != _out_map.end (); ++i, ++pc) {
1534 ChanMapping m (i->second);
1535 const ChanMapping::Mappings& mp ((*i).second.mappings());
1536 for (ChanMapping::Mappings::const_iterator tm = mp.begin(); tm != mp.end(); ++tm) {
1537 for (ChanMapping::TypeMapping::const_iterator i = tm->second.begin(); i != tm->second.end(); ++i) {
1538 rv.set (tm->first, i->first + pc * natural_output_streams().get(tm->first), i->second);
1542 if (has_midi_bypass ()) {
1543 rv.set (DataType::MIDI, 0, 0);
1550 PluginInsert::has_midi_bypass () const
1552 if (_configured_in.n_midi () == 1 && _configured_out.n_midi () == 1
1553 && natural_output_streams ().n_midi () == 0) {
1560 PluginInsert::has_midi_thru () const
1562 if (_configured_in.n_midi () == 1 && _configured_out.n_midi () == 1
1563 && natural_input_streams ().n_midi () == 0 && natural_output_streams ().n_midi () == 0) {
1571 PluginInsert::is_channelstrip () const {
1572 return _plugins.front()->is_channelstrip();
1575 PluginInsert::is_nonbypassable () const {
1576 return _plugins.front()->is_nonbypassable ();
1581 PluginInsert::check_inplace ()
1583 bool inplace_ok = !_plugins.front()->inplace_broken ();
1585 if (_thru_map.n_total () > 0) {
1586 // TODO once midi-bypass is part of the mapping, ignore it
1590 if (_match.method == Split && inplace_ok) {
1591 assert (get_count() == 1);
1592 assert (_in_map.size () == 1);
1593 if (!_out_map[0].is_monotonic ()) {
1596 if (_configured_internal != _configured_in) {
1597 /* no sidechain -- TODO we could allow this with
1598 * some more logic in PluginInsert::connect_and_run().
1600 * PluginInsert::reset_map() already maps it.
1605 for (DataType::iterator t = DataType::begin(); t != DataType::end() && inplace_ok; ++t) {
1606 if (_configured_internal.get (*t) == 0) {
1610 uint32_t first_idx = _in_map[0].get (*t, 0, &valid);
1611 if (!valid || first_idx != 0) {
1612 // so far only allow to copy the *first* stream's buffer to others
1615 for (uint32_t i = 1; i < natural_input_streams ().get (*t); ++i) {
1616 uint32_t idx = _in_map[0].get (*t, i, &valid);
1617 if (valid && idx != first_idx) {
1626 DEBUG_TRACE (DEBUG::ChanMapping, string_compose ("%1: In Place Split Map\n", name()));
1631 for (uint32_t pc = 0; pc < get_count() && inplace_ok ; ++pc) {
1632 if (!_in_map[pc].is_monotonic ()) {
1635 if (!_out_map[pc].is_monotonic ()) {
1641 /* check if every output is fed by the corresponding input
1643 * this prevents in-port 1 -> sink-pin 2 || source-pin 1 -> out port 1, source-pin 2 -> out port 2
1644 * (with in-place, source-pin 1 -> out port 1 overwrites in-port 1)
1646 * but allows in-port 1 -> sink-pin 2 || source-pin 2 -> out port 1
1648 ChanMapping const& in_map (input_map ());
1649 const ChanMapping::Mappings out_m (output_map ().mappings ());
1650 for (ChanMapping::Mappings::const_iterator t = out_m.begin (); t != out_m.end () && inplace_ok; ++t) {
1651 for (ChanMapping::TypeMapping::const_iterator c = (*t).second.begin (); c != (*t).second.end () ; ++c) {
1652 /* src-pin: c->first, out-port: c->second */
1654 uint32_t in_port = in_map.get (t->first, c->first, &valid);
1655 if (valid && in_port != c->second) {
1663 DEBUG_TRACE (DEBUG::ChanMapping, string_compose ("%1: %2\n", name(), inplace_ok ? "In-Place" : "No Inplace Processing"));
1664 return !inplace_ok; // no-inplace
1668 PluginInsert::sanitize_maps ()
1670 bool changed = false;
1671 /* strip dead wood */
1672 PinMappings new_ins;
1673 PinMappings new_outs;
1674 ChanMapping new_thru;
1676 for (uint32_t pc = 0; pc < get_count(); ++pc) {
1678 ChanMapping new_out;
1679 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
1680 for (uint32_t i = 0; i < natural_input_streams().get (*t); ++i) {
1682 uint32_t idx = _in_map[pc].get (*t, i, &valid);
1683 if (valid && idx < _configured_internal.get (*t)) {
1684 new_in.set (*t, i, idx);
1687 for (uint32_t o = 0; o < natural_output_streams().get (*t); ++o) {
1689 uint32_t idx = _out_map[pc].get (*t, o, &valid);
1690 if (valid && idx < _configured_out.get (*t)) {
1691 new_out.set (*t, o, idx);
1695 if (_in_map[pc] != new_in || _out_map[pc] != new_out) {
1698 new_ins[pc] = new_in;
1699 new_outs[pc] = new_out;
1702 /* prevent dup output assignments */
1703 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
1704 for (uint32_t o = 0; o < _configured_out.get (*t); ++o) {
1705 bool mapped = false;
1706 for (uint32_t pc = 0; pc < get_count(); ++pc) {
1708 uint32_t idx = new_outs[pc].get_src (*t, o, &valid);
1709 if (valid && mapped) {
1710 new_outs[pc].unset (*t, idx);
1718 /* remove excess thru */
1719 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
1720 for (uint32_t o = 0; o < _configured_out.get (*t); ++o) {
1722 uint32_t idx = _thru_map.get (*t, o, &valid);
1723 if (valid && idx < _configured_internal.get (*t)) {
1724 new_thru.set (*t, o, idx);
1729 /* prevent out + thru, existing plugin outputs override thru */
1730 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
1731 for (uint32_t o = 0; o < _configured_out.get (*t); ++o) {
1732 bool mapped = false;
1734 for (uint32_t pc = 0; pc < get_count(); ++pc) {
1735 new_outs[pc].get_src (*t, o, &mapped);
1736 if (mapped) { break; }
1738 if (!mapped) { continue; }
1739 uint32_t idx = new_thru.get (*t, o, &valid);
1741 new_thru.unset (*t, idx);
1746 if (has_midi_bypass ()) {
1747 // TODO: include midi-bypass in the thru set,
1748 // remove dedicated handling.
1749 new_thru.unset (DataType::MIDI, 0);
1752 if (_in_map != new_ins || _out_map != new_outs || _thru_map != new_thru) {
1756 _out_map = new_outs;
1757 _thru_map = new_thru;
1763 PluginInsert::reset_map (bool emit)
1765 const PinMappings old_in (_in_map);
1766 const PinMappings old_out (_out_map);
1770 _thru_map = ChanMapping ();
1772 /* build input map */
1773 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
1774 uint32_t sc = 0; // side-chain round-robin (all instances)
1776 for (Plugins::iterator i = _plugins.begin(); i != _plugins.end(); ++i, ++pc) {
1777 const uint32_t nis = natural_input_streams ().get(*t);
1778 const uint32_t stride = nis - sidechain_input_pins().get (*t);
1780 /* SC inputs are last in the plugin-insert.. */
1781 const uint32_t sc_start = _configured_in.get (*t);
1782 const uint32_t sc_len = _configured_internal.get (*t) - sc_start;
1783 /* ...but may not be at the end of the plugin ports.
1784 * in case the side-chain is not the last port, shift connections back.
1785 * and connect to side-chain
1788 uint32_t ic = 0; // split inputs
1789 const uint32_t cend = _configured_in.get (*t);
1791 for (uint32_t in = 0; in < nis; ++in) {
1792 const Plugin::IOPortDescription& iod (_plugins[pc]->describe_io_port (*t, true, in));
1793 if (iod.is_sidechain) {
1794 /* connect sidechain sinks to sidechain inputs in round-robin fashion */
1795 if (sc_len > 0) {// side-chain may be hidden
1796 _in_map[pc].set (*t, in, sc_start + sc);
1797 sc = (sc + 1) % sc_len;
1801 if (_match.method == Split) {
1802 if (cend == 0) { continue; }
1803 if (_strict_io && ic + stride * pc >= cend) {
1806 /* connect *no* sidechain sinks in round-robin fashion */
1807 _in_map[pc].set (*t, in, ic + stride * pc);
1808 if (_strict_io && (ic + 1) == cend) {
1811 ic = (ic + 1) % cend;
1813 uint32_t s = in - shift;
1814 if (stride * pc + s < cend) {
1815 _in_map[pc].set (*t, in, s + stride * pc);
1823 /* build output map */
1825 for (Plugins::iterator i = _plugins.begin(); i != _plugins.end(); ++i, ++pc) {
1826 _out_map[pc] = ChanMapping (ChanCount::min (natural_output_streams(), _configured_out));
1827 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
1828 _out_map[pc].offset_to(*t, pc * natural_output_streams().get(*t));
1833 if (old_in == _in_map && old_out == _out_map) {
1837 PluginMapChanged (); /* EMIT SIGNAL */
1838 _mapping_changed = true;
1839 _session.set_dirty();
1845 PluginInsert::configure_io (ChanCount in, ChanCount out)
1847 Match old_match = _match;
1849 ChanCount old_internal;
1853 old_pins = natural_input_streams();
1854 old_in = _configured_in;
1855 old_out = _configured_out;
1856 old_internal = _configured_internal;
1858 _configured_in = in;
1859 _configured_internal = in;
1860 _configured_out = out;
1863 /* TODO hide midi-bypass, and custom outs. Best /fake/ "out" here.
1864 * (currently _sidechain->configure_io always succeeds
1865 * since Processor::configure_io() succeeds)
1867 if (!_sidechain->configure_io (in, out)) {
1868 DEBUG_TRACE (DEBUG::ChanMapping, "Sidechain configuration failed\n");
1871 _configured_internal += _sidechain->input()->n_ports();
1873 // include (static_cast<Route*>owner())->name() ??
1874 _sidechain->input ()-> set_pretty_name (string_compose (_("SC %1"), name ()));
1877 /* get plugin configuration */
1878 _match = private_can_support_io_configuration (in, out);
1880 if (DEBUG_ENABLED(DEBUG::ChanMapping)) {
1882 DEBUG_STR_APPEND(a, string_compose ("%1: ", name()));
1883 DEBUG_STR_APPEND(a, _match);
1884 DEBUG_TRACE (DEBUG::ChanMapping, DEBUG_STR(a).str());
1888 /* set the matching method and number of plugins that we will use to meet this configuration */
1889 if (set_count (_match.plugins) == false) {
1890 PluginIoReConfigure (); /* EMIT SIGNAL */
1891 _configured = false;
1895 /* configure plugins */
1896 switch (_match.method) {
1899 if (_plugins.front()->configure_io (natural_input_streams(), out) == false) {
1900 PluginIoReConfigure (); /* EMIT SIGNAL */
1901 _configured = false;
1907 ChanCount din (_configured_internal);
1908 ChanCount dout (din); // hint
1910 if (_custom_sinks.n_total () > 0) {
1911 din = _custom_sinks;
1914 } else if (_preset_out.n_audio () > 0) {
1915 dout.set (DataType::AUDIO, _preset_out.n_audio ());
1916 } else if (dout.n_midi () > 0 && dout.n_audio () == 0) {
1917 dout.set (DataType::AUDIO, 2);
1919 if (out.n_audio () == 0) { out.set (DataType::AUDIO, 1); }
1921 DEBUG_TRACE (DEBUG::ChanMapping, string_compose ("%1: Delegate lookup : %2 %3\n", name(), din, dout));
1922 bool const r = _plugins.front()->can_support_io_configuration (din, dout, &useins);
1924 if (useins.n_audio() == 0) {
1927 DEBUG_TRACE (DEBUG::ChanMapping, string_compose ("%1: Delegate configuration: %2 %3\n", name(), useins, dout));
1929 if (_plugins.front()->configure_io (useins, dout) == false) {
1930 PluginIoReConfigure (); /* EMIT SIGNAL */
1931 _configured = false;
1935 _custom_sinks = din;
1940 if (_plugins.front()->configure_io (in, out) == false) {
1941 PluginIoReConfigure (); /* EMIT SIGNAL */
1942 _configured = false;
1948 DEBUG_TRACE (DEBUG::ChanMapping, string_compose ("%1: cfg:%2 state:%3 chn-in:%4 chn-out:%5 inpin:%6 match:%7 cust:%8 size-in:%9 size-out:%10\n",
1950 _configured ? "Y" : "N",
1951 _maps_from_state ? "Y" : "N",
1952 old_in == in ? "==" : "!=",
1953 old_out == out ? "==" : "!=",
1954 old_pins == natural_input_streams () ? "==" : "!=",
1955 old_match.method == _match.method ? "==" : "!=",
1956 old_match.custom_cfg == _match.custom_cfg ? "==" : "!=",
1957 _in_map.size() == get_count () ? "==" : "!=",
1958 _out_map.size() == get_count () ? "==" : "!="
1961 bool mapping_changed = false;
1962 if (old_in == in && old_out == out
1964 && old_pins == natural_input_streams ()
1965 && old_match.method == _match.method
1966 && old_match.custom_cfg == _match.custom_cfg
1967 && _in_map.size() == _out_map.size()
1968 && _in_map.size() == get_count ()
1970 /* If the configuration has not changed, keep the mapping */
1971 mapping_changed = sanitize_maps ();
1972 } else if (_match.custom_cfg && _configured) {
1973 /* don't touch the map in manual mode */
1974 mapping_changed = sanitize_maps ();
1977 if (is_channelstrip ()) {
1978 /* fake channel map - for wire display */
1981 _thru_map = ChanMapping ();
1982 _in_map[0] = ChanMapping (ChanCount::min (_configured_in, ChanCount (DataType::AUDIO, 2)));
1983 _out_map[0] = ChanMapping (ChanCount::min (_configured_out, ChanCount (DataType::AUDIO, 2)));
1984 /* set "thru" map for in-place forward of audio */
1985 for (uint32_t i = 2; i < _configured_in.n_audio(); ++i) {
1986 _thru_map.set (DataType::AUDIO, i, i);
1988 /* and midi (after implicit 1st channel bypass) */
1989 for (uint32_t i = 1; i < _configured_in.n_midi(); ++i) {
1990 _thru_map.set (DataType::MIDI, i, i);
1994 if (_maps_from_state && old_in == in && old_out == out) {
1995 mapping_changed = true;
1998 /* generate a new mapping */
1999 mapping_changed = reset_map (false);
2001 _maps_from_state = false;
2004 if (mapping_changed) {
2005 PluginMapChanged (); /* EMIT SIGNAL */
2008 if (DEBUG_ENABLED(DEBUG::ChanMapping)) {
2011 DEBUG_STR_APPEND(a, "\n--------<<--------\n");
2012 for (Plugins::iterator i = _plugins.begin(); i != _plugins.end(); ++i, ++pc) {
2014 DEBUG_STR_APPEND(a, "----><----\n");
2016 DEBUG_STR_APPEND(a, string_compose ("Channel Map for %1 plugin %2\n", name(), pc));
2017 DEBUG_STR_APPEND(a, " * Inputs:\n");
2018 DEBUG_STR_APPEND(a, _in_map[pc]);
2019 DEBUG_STR_APPEND(a, " * Outputs:\n");
2020 DEBUG_STR_APPEND(a, _out_map[pc]);
2022 DEBUG_STR_APPEND(a, " * Thru:\n");
2023 DEBUG_STR_APPEND(a, _thru_map);
2024 DEBUG_STR_APPEND(a, "-------->>--------\n");
2025 DEBUG_TRACE (DEBUG::ChanMapping, DEBUG_STR(a).str());
2030 _no_inplace = check_inplace ();
2031 _mapping_changed = false;
2033 /* only the "noinplace_buffers" thread buffers need to be this large,
2034 * this can be optimized. other buffers are fine with
2035 * ChanCount::max (natural_input_streams (), natural_output_streams())
2036 * and route.cc's max (configured_in, configured_out)
2038 * no-inplace copies "thru" outputs (to emulate in-place) for
2039 * all outputs (to prevent overwrite) into a temporary space
2040 * which also holds input buffers (in case the plugin does process
2041 * in-place and overwrites those).
2043 * this buffers need to be at least as
2044 * natural_input_streams () + possible outputs.
2046 * sidechain inputs add a constraint on the input:
2047 * configured input + sidechain (=_configured_internal)
2049 * NB. this also satisfies
2050 * max (natural_input_streams(), natural_output_streams())
2051 * which is needed for silence runs
2053 _required_buffers = ChanCount::max (_configured_internal,
2054 natural_input_streams () + ChanCount::max (_configured_out, natural_output_streams () * get_count ()));
2056 if (old_in != in || old_out != out || old_internal != _configured_internal
2057 || old_pins != natural_input_streams ()
2058 || (old_match.method != _match.method && (old_match.method == Split || _match.method == Split))
2060 PluginIoReConfigure (); /* EMIT SIGNAL */
2063 _delaybuffers.configure (_configured_out, _plugins.front ()->max_latency ());
2064 _latency_changed = true;
2066 /* we don't know the analysis window size, so we must work with the
2067 * current buffer size here. each request for data fills in these
2068 * buffers and the analyser makes sure it gets enough data for the
2069 * analysis window. We also only analyze audio, so we can ignore
2072 ChanCount cc_analysis_in (DataType::AUDIO, in.n_audio());
2073 ChanCount cc_analysis_out (DataType::AUDIO, out.n_audio());
2075 session().ensure_buffer_set (_signal_analysis_inputs, cc_analysis_in);
2076 _signal_analysis_inputs.set_count (cc_analysis_in);
2078 session().ensure_buffer_set (_signal_analysis_outputs, cc_analysis_out);
2079 _signal_analysis_outputs.set_count (cc_analysis_out);
2081 // std::cerr << "set counts to i" << in.n_audio() << "/o" << out.n_audio() << std::endl;
2084 return Processor::configure_io (in, out);
2087 /** Decide whether this PluginInsert can support a given IO configuration.
2088 * To do this, we run through a set of possible solutions in rough order of
2091 * @param in Required input channel count.
2092 * @param out Filled in with the output channel count if we return true.
2093 * @return true if the given IO configuration can be supported.
2096 PluginInsert::can_support_io_configuration (const ChanCount& in, ChanCount& out)
2099 _sidechain->can_support_io_configuration (in, out); // never fails, sets "out"
2101 return private_can_support_io_configuration (in, out).method != Impossible;
2105 PluginInsert::private_can_support_io_configuration (ChanCount const& in, ChanCount& out) const
2107 if (!_custom_cfg && _preset_out.n_audio () > 0) {
2108 // preseed hint (for variable i/o)
2109 out.set (DataType::AUDIO, _preset_out.n_audio ());
2112 Match rv = internal_can_support_io_configuration (in, out);
2114 if (!_custom_cfg && _preset_out.n_audio () > 0) {
2115 DEBUG_TRACE (DEBUG::ChanMapping, string_compose ("%1: using output preset: %2\n", name(), _preset_out));
2116 out.set (DataType::AUDIO, _preset_out.n_audio ());
2121 /** A private version of can_support_io_configuration which returns the method
2122 * by which the configuration can be matched, rather than just whether or not
2126 PluginInsert::internal_can_support_io_configuration (ChanCount const & inx, ChanCount& out) const
2128 if (_plugins.empty()) {
2133 if (is_channelstrip ()) {
2135 return Match (ExactMatch, 1);
2139 /* if a user specified a custom cfg, so be it. */
2141 PluginInfoPtr info = _plugins.front()->get_info();
2143 if (info->reconfigurable_io()) {
2144 return Match (Delegate, 1, _strict_io, true);
2146 return Match (ExactMatch, get_count(), _strict_io, true);
2150 /* try automatic configuration */
2151 Match m = PluginInsert::automatic_can_support_io_configuration (inx, out);
2153 PluginInfoPtr info = _plugins.front()->get_info();
2154 ChanCount inputs = info->n_inputs;
2155 ChanCount outputs = info->n_outputs;
2157 /* handle case strict-i/o */
2158 if (_strict_io && m.method != Impossible) {
2161 /* special case MIDI instruments */
2162 if (is_instrument ()) {
2163 // output = midi-bypass + at most master-out channels.
2164 ChanCount max_out (DataType::AUDIO, 2); // TODO use master-out
2165 max_out.set (DataType::MIDI, out.get(DataType::MIDI));
2166 out = ChanCount::min (out, max_out);
2167 DEBUG_TRACE (DEBUG::ChanMapping, string_compose ("%1: special case strict-i/o instrument\n", name()));
2173 if (inx.n_audio () != out.n_audio ()) { // ignore midi bypass
2174 /* replicate processor to match output count (generators and such)
2175 * at least enough to feed every output port. */
2176 uint32_t f = 1; // at least one. e.g. control data filters, no in, no out.
2177 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
2178 uint32_t nout = outputs.get (*t);
2179 if (nout == 0 || inx.get(*t) == 0) { continue; }
2180 f = max (f, (uint32_t) ceil (inx.get(*t) / (float)nout));
2183 DEBUG_TRACE (DEBUG::ChanMapping, string_compose ("%1: special case strict-i/o for generator\n", name()));
2184 return Match (Replicate, f, _strict_io);
2195 if (m.method != Impossible) {
2199 ChanCount ns_inputs = inputs - sidechain_input_pins ();
2201 DEBUG_TRACE (DEBUG::ChanMapping, string_compose ("%1: resolving 'Impossible' match...\n", name()));
2203 if (info->reconfigurable_io()) {
2206 if (out.n_midi () > 0 && out.n_audio () == 0) { out.set (DataType::AUDIO, 2); }
2207 if (out.n_audio () == 0) { out.set (DataType::AUDIO, 1); }
2208 bool const r = _plugins.front()->can_support_io_configuration (inx + sidechain_input_pins (), out, &useins);
2210 // houston, we have a problem.
2211 return Match (Impossible, 0);
2214 if (inx.n_midi () > 0 && out.n_midi () == 0) { out.set (DataType::MIDI, 1); }
2215 return Match (Delegate, 1, _strict_io);
2218 ChanCount midi_bypass;
2219 if (inx.get(DataType::MIDI) == 1 && outputs.get(DataType::MIDI) == 0) {
2220 midi_bypass.set (DataType::MIDI, 1);
2223 // add at least as many plugins so that output count matches input count (w/o sidechain pins)
2225 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
2226 uint32_t nin = ns_inputs.get (*t);
2227 uint32_t nout = outputs.get (*t);
2228 if (nin == 0 || inx.get(*t) == 0) { continue; }
2229 // prefer floor() so the count won't overly increase IFF (nin < nout)
2230 f = max (f, (uint32_t) floor (inx.get(*t) / (float)nout));
2232 if (f > 0 && outputs * f >= _configured_out) {
2233 out = outputs * f + midi_bypass;
2234 return Match (Replicate, f, _strict_io);
2237 // add at least as many plugins needed to connect all inputs (w/o sidechain pins)
2239 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
2240 uint32_t nin = ns_inputs.get (*t);
2241 if (nin == 0 || inx.get(*t) == 0) { continue; }
2242 f = max (f, (uint32_t) ceil (inx.get(*t) / (float)nin));
2245 out = outputs * f + midi_bypass;
2246 return Match (Replicate, f, _strict_io);
2249 // add at least as many plugins needed to connect all inputs
2251 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
2252 uint32_t nin = inputs.get (*t);
2253 if (nin == 0 || inx.get(*t) == 0) { continue; }
2254 f = max (f, (uint32_t) ceil (inx.get(*t) / (float)nin));
2256 out = outputs * f + midi_bypass;
2257 return Match (Replicate, f, _strict_io);
2260 /* this is the original Ardour 3/4 behavior, mainly for backwards compatibility */
2262 PluginInsert::automatic_can_support_io_configuration (ChanCount const & inx, ChanCount& out) const
2264 if (_plugins.empty()) {
2268 PluginInfoPtr info = _plugins.front()->get_info();
2269 ChanCount in; in += inx;
2270 ChanCount midi_bypass;
2272 if (info->reconfigurable_io()) {
2273 /* Plugin has flexible I/O, so delegate to it
2274 * pre-seed outputs, plugin tries closest match
2277 if (out.n_midi () > 0 && out.n_audio () == 0) { out.set (DataType::AUDIO, 2); }
2278 if (out.n_audio () == 0) { out.set (DataType::AUDIO, 1); }
2279 bool const r = _plugins.front()->can_support_io_configuration (in + sidechain_input_pins (), out);
2281 return Match (Impossible, 0);
2284 if (in.n_midi () > 0 && out.n_midi () == 0) { out.set (DataType::MIDI, 1); }
2285 return Match (Delegate, 1);
2288 ChanCount inputs = info->n_inputs;
2289 ChanCount outputs = info->n_outputs;
2290 ChanCount ns_inputs = inputs - sidechain_input_pins ();
2292 if (in.get(DataType::MIDI) == 1 && outputs.get(DataType::MIDI) == 0) {
2293 DEBUG_TRACE (DEBUG::ChanMapping, string_compose ("%1: bypassing midi-data\n", name()));
2294 midi_bypass.set (DataType::MIDI, 1);
2296 if (in.get(DataType::MIDI) == 1 && inputs.get(DataType::MIDI) == 0) {
2297 DEBUG_TRACE (DEBUG::ChanMapping, string_compose ("%1: hiding midi-port from plugin\n", name()));
2298 in.set(DataType::MIDI, 0);
2301 // add internally provided sidechain ports
2302 ChanCount insc = in + sidechain_input_ports ();
2304 bool no_inputs = true;
2305 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
2306 if (inputs.get (*t) != 0) {
2313 /* no inputs so we can take any input configuration since we throw it away */
2314 out = outputs + midi_bypass;
2315 return Match (NoInputs, 1);
2318 /* Plugin inputs match requested inputs + side-chain-ports exactly */
2319 if (inputs == insc) {
2320 out = outputs + midi_bypass;
2321 return Match (ExactMatch, 1);
2324 /* Plugin inputs matches without side-chain-pins */
2325 if (ns_inputs == in) {
2326 out = outputs + midi_bypass;
2327 return Match (ExactMatch, 1);
2330 /* We may be able to run more than one copy of the plugin within this insert
2331 to cope with the insert having more inputs than the plugin.
2332 We allow replication only for plugins with either zero or 1 inputs and outputs
2333 for every valid data type.
2337 bool can_replicate = true;
2338 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
2340 // ignore side-chains
2341 uint32_t nin = ns_inputs.get (*t);
2343 // No inputs of this type
2344 if (nin == 0 && in.get(*t) == 0) {
2348 if (nin != 1 || outputs.get (*t) != 1) {
2349 can_replicate = false;
2353 // Potential factor not set yet
2355 f = in.get(*t) / nin;
2358 // Factor for this type does not match another type, can not replicate
2359 if (f != (in.get(*t) / nin)) {
2360 can_replicate = false;
2365 if (can_replicate && f > 0) {
2366 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
2367 out.set (*t, outputs.get(*t) * f);
2370 return Match (Replicate, f);
2373 /* If the processor has exactly one input of a given type, and
2374 the plugin has more, we can feed the single processor input
2375 to some or all of the plugin inputs. This is rather
2376 special-case-y, but the 1-to-many case is by far the
2377 simplest. How do I split thy 2 processor inputs to 3
2378 plugin inputs? Let me count the ways ...
2381 bool can_split = true;
2382 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
2384 bool const can_split_type = (in.get (*t) == 1 && ns_inputs.get (*t) > 1);
2385 bool const nothing_to_do_for_type = (in.get (*t) == 0 && inputs.get (*t) == 0);
2387 if (!can_split_type && !nothing_to_do_for_type) {
2393 out = outputs + midi_bypass;
2394 return Match (Split, 1);
2397 /* If the plugin has more inputs than we want, we can `hide' some of them
2398 by feeding them silence.
2401 bool could_hide = false;
2402 bool cannot_hide = false;
2403 ChanCount hide_channels;
2405 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
2406 if (inputs.get(*t) > in.get(*t)) {
2407 /* there is potential to hide, since the plugin has more inputs of type t than the insert */
2408 hide_channels.set (*t, inputs.get(*t) - in.get(*t));
2410 } else if (inputs.get(*t) < in.get(*t)) {
2411 /* we definitely cannot hide, since the plugin has fewer inputs of type t than the insert */
2416 if (could_hide && !cannot_hide) {
2417 out = outputs + midi_bypass;
2418 return Match (Hide, 1, false, false, hide_channels);
2421 return Match (Impossible, 0);
2426 PluginInsert::state ()
2428 XMLNode& node = Processor::state ();
2430 node.set_property("type", _plugins[0]->state_node_name());
2431 node.set_property("unique-id", _plugins[0]->unique_id());
2432 node.set_property("count", (uint32_t)_plugins.size());
2434 /* remember actual i/o configuration (for later placeholder
2435 * in case the plugin goes missing) */
2436 node.add_child_nocopy (* _configured_in.state (X_("ConfiguredInput")));
2437 node.add_child_nocopy (* _custom_sinks.state (X_("CustomSinks")));
2438 node.add_child_nocopy (* _configured_out.state (X_("ConfiguredOutput")));
2439 node.add_child_nocopy (* _preset_out.state (X_("PresetOutput")));
2441 /* save custom i/o config */
2442 node.set_property("custom", _custom_cfg);
2443 for (uint32_t pc = 0; pc < get_count(); ++pc) {
2445 snprintf (tmp, sizeof(tmp), "InputMap-%d", pc);
2446 node.add_child_nocopy (* _in_map[pc].state (tmp));
2447 snprintf (tmp, sizeof(tmp), "OutputMap-%d", pc);
2448 node.add_child_nocopy (* _out_map[pc].state (tmp));
2450 node.add_child_nocopy (* _thru_map.state ("ThruMap"));
2453 node.add_child_nocopy (_sidechain->get_state ());
2456 _plugins[0]->set_insert_id(this->id());
2457 node.add_child_nocopy (_plugins[0]->get_state());
2459 for (Controls::iterator c = controls().begin(); c != controls().end(); ++c) {
2460 boost::shared_ptr<AutomationControl> ac = boost::dynamic_pointer_cast<AutomationControl> ((*c).second);
2462 node.add_child_nocopy (ac->get_state());
2470 PluginInsert::set_control_ids (const XMLNode& node, int version)
2472 const XMLNodeList& nlist = node.children();
2473 XMLNodeConstIterator iter;
2474 set<Evoral::Parameter>::const_iterator p;
2476 for (iter = nlist.begin(); iter != nlist.end(); ++iter) {
2477 if ((*iter)->name() == Controllable::xml_node_name) {
2479 uint32_t p = (uint32_t)-1;
2482 if ((*iter)->get_property (X_("symbol"), str)) {
2483 boost::shared_ptr<LV2Plugin> lv2plugin = boost::dynamic_pointer_cast<LV2Plugin> (_plugins[0]);
2485 p = lv2plugin->port_index(str.c_str());
2489 if (p == (uint32_t)-1) {
2490 (*iter)->get_property (X_("parameter"), p);
2493 if (p != (uint32_t)-1) {
2495 /* this may create the new controllable */
2497 boost::shared_ptr<Evoral::Control> c = control (Evoral::Parameter (PluginAutomation, 0, p));
2499 #ifndef NO_PLUGIN_STATE
2503 boost::shared_ptr<AutomationControl> ac = boost::dynamic_pointer_cast<AutomationControl> (c);
2505 ac->set_state (**iter, version);
2514 PluginInsert::set_state(const XMLNode& node, int version)
2516 XMLNodeList nlist = node.children();
2517 XMLNodeIterator niter;
2518 XMLPropertyList plist;
2519 ARDOUR::PluginType type;
2522 if (!node.get_property ("type", str)) {
2523 error << _("XML node describing plugin is missing the `type' field") << endmsg;
2527 if (str == X_("ladspa") || str == X_("Ladspa")) { /* handle old school sessions */
2528 type = ARDOUR::LADSPA;
2529 } else if (str == X_("lv2")) {
2531 } else if (str == X_("windows-vst")) {
2532 type = ARDOUR::Windows_VST;
2533 } else if (str == X_("lxvst")) {
2534 type = ARDOUR::LXVST;
2535 } else if (str == X_("mac-vst")) {
2536 type = ARDOUR::MacVST;
2537 } else if (str == X_("audiounit")) {
2538 type = ARDOUR::AudioUnit;
2539 } else if (str == X_("luaproc")) {
2542 error << string_compose (_("unknown plugin type %1 in plugin insert state"), str) << endmsg;
2546 XMLProperty const * prop = node.property ("unique-id");
2549 #ifdef WINDOWS_VST_SUPPORT
2550 /* older sessions contain VST plugins with only an "id" field. */
2551 if (type == ARDOUR::Windows_VST) {
2552 prop = node.property ("id");
2556 #ifdef LXVST_SUPPORT
2557 /*There shouldn't be any older sessions with linuxVST support.. but anyway..*/
2558 if (type == ARDOUR::LXVST) {
2559 prop = node.property ("id");
2566 error << _("Plugin has no unique ID field") << endmsg;
2571 boost::shared_ptr<Plugin> plugin = find_plugin (_session, prop->value(), type);
2572 bool any_vst = false;
2574 /* treat VST plugins equivalent if they have the same uniqueID
2575 * allow to move sessions windows <> linux */
2576 #ifdef LXVST_SUPPORT
2577 if (plugin == 0 && (type == ARDOUR::Windows_VST || type == ARDOUR::MacVST)) {
2578 type = ARDOUR::LXVST;
2579 plugin = find_plugin (_session, prop->value(), type);
2580 if (plugin) { any_vst = true; }
2584 #ifdef WINDOWS_VST_SUPPORT
2585 if (plugin == 0 && (type == ARDOUR::LXVST || type == ARDOUR::MacVST)) {
2586 type = ARDOUR::Windows_VST;
2587 plugin = find_plugin (_session, prop->value(), type);
2588 if (plugin) { any_vst = true; }
2592 #ifdef MACVST_SUPPORT
2593 if (plugin == 0 && (type == ARDOUR::Windows_VST || type == ARDOUR::LXVST)) {
2594 type = ARDOUR::MacVST;
2595 plugin = find_plugin (_session, prop->value(), type);
2596 if (plugin) { any_vst = true; }
2600 if (plugin == 0 && type == ARDOUR::Lua) {
2601 /* unique ID (sha1 of script) was not found,
2602 * load the plugin from the serialized version in the
2603 * session-file instead.
2605 boost::shared_ptr<LuaProc> lp (new LuaProc (_session.engine(), _session, ""));
2606 XMLNode *ls = node.child (lp->state_node_name().c_str());
2608 lp->set_script_from_state (*ls);
2614 error << string_compose(
2615 _("Found a reference to a plugin (\"%1\") that is unknown.\n"
2616 "Perhaps it was removed or moved since it was last used."),
2622 // The name of the PluginInsert comes from the plugin, nothing else
2623 _name = plugin->get_info()->name;
2627 // Processor::set_state() will set this, but too late
2628 // for it to be available when setting up plugin
2629 // state. We can't call Processor::set_state() until
2630 // the plugins themselves are created and added.
2634 if (_plugins.empty()) {
2635 /* if we are adding the first plugin, we will need to set
2636 up automatable controls.
2638 add_plugin (plugin);
2639 create_automatable_parameters ();
2640 set_control_ids (node, version);
2643 node.get_property ("count", count);
2645 if (_plugins.size() != count) {
2646 for (uint32_t n = 1; n < count; ++n) {
2647 add_plugin (plugin_factory (plugin));
2651 Processor::set_state (node, version);
2653 PBD::ID new_id = this->id();
2654 PBD::ID old_id = this->id();
2656 node.get_property ("id", old_id);
2658 for (niter = nlist.begin(); niter != nlist.end(); ++niter) {
2660 /* find the node with the type-specific node name ("lv2", "ladspa", etc)
2661 and set all plugins to the same state.
2664 if ( ((*niter)->name() == plugin->state_node_name())
2665 || (any_vst && ((*niter)->name() == "lxvst" || (*niter)->name() == "windows-vst" || (*niter)->name() == "mac-vst"))
2668 for (Plugins::iterator i = _plugins.begin(); i != _plugins.end(); ++i) {
2669 /* Plugin state can include external files which are named after the ID.
2671 * If regenerate_xml_or_string_ids() is set, the ID will already have
2672 * been changed, so we need to use the old ID from the XML to load the
2673 * state and then update the ID.
2675 * When copying a plugin-state, route_ui takes care of of updating the ID,
2676 * but we need to call set_insert_id() to clear the cached plugin-state
2677 * and force a change.
2679 if (!regenerate_xml_or_string_ids ()) {
2680 (*i)->set_insert_id (new_id);
2682 (*i)->set_insert_id (old_id);
2685 (*i)->set_state (**niter, version);
2687 if (regenerate_xml_or_string_ids ()) {
2688 (*i)->set_insert_id (new_id);
2692 /* when copying plugin state, notify UI */
2693 for (Controls::const_iterator li = controls().begin(); li != controls().end(); ++li) {
2694 boost::shared_ptr<PBD::Controllable> c = boost::dynamic_pointer_cast<PBD::Controllable> (li->second);
2696 c->Changed (false, Controllable::NoGroup); /* EMIT SIGNAL */
2704 if (version < 3000) {
2706 /* Only 2.X sessions need a call to set_parameter_state() - in 3.X and above
2707 this is all handled by Automatable
2710 for (niter = nlist.begin(); niter != nlist.end(); ++niter) {
2711 if ((*niter)->name() == "Redirect") {
2712 /* XXX do we need to tackle placement? i think not (pd; oct 16 2009) */
2713 Processor::set_state (**niter, version);
2718 set_parameter_state_2X (node, version);
2721 node.get_property (X_("custom"), _custom_cfg);
2723 uint32_t in_maps = 0;
2724 uint32_t out_maps = 0;
2725 XMLNodeList kids = node.children ();
2726 for (XMLNodeIterator i = kids.begin(); i != kids.end(); ++i) {
2727 if ((*i)->name() == X_("ConfiguredInput")) {
2728 _configured_in = ChanCount(**i);
2730 if ((*i)->name() == X_("CustomSinks")) {
2731 _custom_sinks = ChanCount(**i);
2733 if ((*i)->name() == X_("ConfiguredOutput")) {
2734 _custom_out = ChanCount(**i);
2735 _configured_out = ChanCount(**i);
2737 if ((*i)->name() == X_("PresetOutput")) {
2738 _preset_out = ChanCount(**i);
2740 if (strncmp ((*i)->name ().c_str(), X_("InputMap-"), 9) == 0) {
2741 long pc = atol (&((*i)->name().c_str()[9]));
2742 if (pc >= 0 && pc <= (long) get_count()) {
2743 _in_map[pc] = ChanMapping (**i);
2747 if (strncmp ((*i)->name ().c_str(), X_("OutputMap-"), 10) == 0) {
2748 long pc = atol (&((*i)->name().c_str()[10]));
2749 if (pc >= 0 && pc <= (long) get_count()) {
2750 _out_map[pc] = ChanMapping (**i);
2754 if ((*i)->name () == "ThruMap") {
2755 _thru_map = ChanMapping (**i);
2758 // sidechain is a Processor (IO)
2759 if ((*i)->name () == Processor::state_node_name) {
2761 if (regenerate_xml_or_string_ids ()) {
2762 add_sidechain_from_xml (**i, version);
2767 if (!regenerate_xml_or_string_ids ()) {
2768 _sidechain->set_state (**i, version);
2770 update_sidechain_name ();
2775 if (in_maps == out_maps && out_maps >0 && out_maps == get_count()) {
2776 _maps_from_state = true;
2779 for (Plugins::iterator i = _plugins.begin(); i != _plugins.end(); ++i) {
2783 (*i)->deactivate ();
2787 PluginConfigChanged (); /* EMIT SIGNAL */
2792 PluginInsert::update_id (PBD::ID id)
2795 for (Plugins::iterator i = _plugins.begin(); i != _plugins.end(); ++i) {
2796 (*i)->set_insert_id (id);
2801 PluginInsert::set_owner (SessionObject* o)
2803 Processor::set_owner (o);
2804 for (Plugins::iterator i = _plugins.begin(); i != _plugins.end(); ++i) {
2805 (*i)->set_owner (o);
2810 PluginInsert::set_state_dir (const std::string& d)
2812 // state() only saves the state of the first plugin
2813 _plugins[0]->set_state_dir (d);
2817 PluginInsert::set_parameter_state_2X (const XMLNode& node, int version)
2819 XMLNodeList nlist = node.children();
2820 XMLNodeIterator niter;
2822 /* look for port automation node */
2824 for (niter = nlist.begin(); niter != nlist.end(); ++niter) {
2826 if ((*niter)->name() != port_automation_node_name) {
2831 XMLNodeConstIterator iter;
2835 cnodes = (*niter)->children ("port");
2837 for (iter = cnodes.begin(); iter != cnodes.end(); ++iter){
2841 if (!child->get_property("number", port_id)) {
2842 warning << _("PluginInsert: Auto: no ladspa port number") << endmsg;
2846 if (port_id >= _plugins[0]->parameter_count()) {
2847 warning << _("PluginInsert: Auto: port id out of range") << endmsg;
2851 boost::shared_ptr<AutomationControl> c = boost::dynamic_pointer_cast<AutomationControl>(
2852 control(Evoral::Parameter(PluginAutomation, 0, port_id), true));
2854 if (c && c->alist()) {
2855 if (!child->children().empty()) {
2856 c->alist()->set_state (*child->children().front(), version);
2859 error << string_compose (_("PluginInsert: automatable control %1 not found - ignored"), port_id) << endmsg;
2869 boost::shared_ptr<ReadOnlyControl>
2870 PluginInsert::control_output (uint32_t num) const
2872 CtrlOutMap::const_iterator i = _control_outputs.find (num);
2873 if (i == _control_outputs.end ()) {
2874 return boost::shared_ptr<ReadOnlyControl> ();
2881 PluginInsert::describe_parameter (Evoral::Parameter param)
2883 if (param.type() == PluginAutomation) {
2884 return _plugins[0]->describe_parameter (param);
2885 } else if (param.type() == PluginPropertyAutomation) {
2886 boost::shared_ptr<AutomationControl> c(automation_control(param));
2887 if (c && !c->desc().label.empty()) {
2888 return c->desc().label;
2891 return Automatable::describe_parameter(param);
2895 PluginInsert::signal_latency() const
2897 if (!_pending_active) {
2900 if (_user_latency) {
2901 return _user_latency;
2904 return _plugins[0]->signal_latency ();
2908 PluginInsert::type ()
2910 return plugin()->get_info()->type;
2913 PluginInsert::PluginControl::PluginControl (PluginInsert* p,
2914 const Evoral::Parameter& param,
2915 const ParameterDescriptor& desc,
2916 boost::shared_ptr<AutomationList> list)
2917 : AutomationControl (p->session(), param, desc, list, p->describe_parameter(param))
2922 list->set_interpolation(Evoral::ControlList::Discrete);
2927 /** @param val `user' value */
2930 PluginInsert::PluginControl::actually_set_value (double user_val, PBD::Controllable::GroupControlDisposition group_override)
2932 /* FIXME: probably should be taking out some lock here.. */
2934 for (Plugins::iterator i = _plugin->_plugins.begin(); i != _plugin->_plugins.end(); ++i) {
2935 (*i)->set_parameter (_list->parameter().id(), user_val);
2938 boost::shared_ptr<Plugin> iasp = _plugin->_impulseAnalysisPlugin.lock();
2940 iasp->set_parameter (_list->parameter().id(), user_val);
2943 AutomationControl::actually_set_value (user_val, group_override);
2947 PluginInsert::PluginControl::catch_up_with_external_value (double user_val)
2949 AutomationControl::actually_set_value (user_val, Controllable::NoGroup);
2953 PluginInsert::PluginControl::get_state ()
2955 XMLNode& node (AutomationControl::get_state());
2956 node.set_property (X_("parameter"), parameter().id());
2958 boost::shared_ptr<LV2Plugin> lv2plugin = boost::dynamic_pointer_cast<LV2Plugin> (_plugin->_plugins[0]);
2960 node.set_property (X_("symbol"), lv2plugin->port_symbol (parameter().id()));
2967 /** @return `user' val */
2969 PluginInsert::PluginControl::get_value () const
2971 boost::shared_ptr<Plugin> plugin = _plugin->plugin (0);
2977 return plugin->get_parameter (_list->parameter().id());
2980 PluginInsert::PluginPropertyControl::PluginPropertyControl (PluginInsert* p,
2981 const Evoral::Parameter& param,
2982 const ParameterDescriptor& desc,
2983 boost::shared_ptr<AutomationList> list)
2984 : AutomationControl (p->session(), param, desc, list)
2990 PluginInsert::PluginPropertyControl::actually_set_value (double user_val, Controllable::GroupControlDisposition gcd)
2992 /* Old numeric set_value(), coerce to appropriate datatype if possible.
2993 This is lossy, but better than nothing until Ardour's automation system
2994 can handle various datatypes all the way down. */
2995 const Variant value(_desc.datatype, user_val);
2996 if (value.type() == Variant::NOTHING) {
2997 error << "set_value(double) called for non-numeric property" << endmsg;
3001 for (Plugins::iterator i = _plugin->_plugins.begin(); i != _plugin->_plugins.end(); ++i) {
3002 (*i)->set_property(_list->parameter().id(), value);
3007 AutomationControl::actually_set_value (user_val, gcd);
3011 PluginInsert::PluginPropertyControl::get_state ()
3013 XMLNode& node (AutomationControl::get_state());
3014 node.set_property (X_("property"), parameter().id());
3015 node.remove_property (X_("value"));
3021 PluginInsert::PluginPropertyControl::get_value () const
3023 return _value.to_double();
3026 boost::shared_ptr<Plugin>
3027 PluginInsert::get_impulse_analysis_plugin()
3029 boost::shared_ptr<Plugin> ret;
3030 if (_impulseAnalysisPlugin.expired()) {
3031 // LV2 in particular uses various _session params
3032 // during init() -- most notably block_size..
3034 ret = plugin_factory(_plugins[0]);
3035 ChanCount out (internal_output_streams ());
3036 if (ret->get_info ()->reconfigurable_io ()) {
3037 // populate get_info ()->n_inputs and ->n_outputs
3039 ret->can_support_io_configuration (internal_input_streams (), out, &useins);
3040 assert (out == internal_output_streams ());
3042 ret->configure_io (internal_input_streams (), out);
3043 ret->set_owner (_owner);
3044 _impulseAnalysisPlugin = ret;
3046 ret = _impulseAnalysisPlugin.lock();
3053 PluginInsert::collect_signal_for_analysis (samplecnt_t nframes)
3055 // called from outside the audio thread, so this should be safe
3056 // only do audio as analysis is (currently) only for audio plugins
3057 _signal_analysis_inputs.ensure_buffers (DataType::AUDIO, input_streams().n_audio(), nframes);
3058 _signal_analysis_outputs.ensure_buffers (DataType::AUDIO, output_streams().n_audio(), nframes);
3060 _signal_analysis_collected_nframes = 0;
3061 _signal_analysis_collect_nframes_max = nframes;
3064 /** Add a plugin to our list */
3066 PluginInsert::add_plugin (boost::shared_ptr<Plugin> plugin)
3068 plugin->set_insert_id (this->id());
3069 plugin->set_owner (_owner);
3071 if (_plugins.empty()) {
3072 /* first (and probably only) plugin instance - connect to relevant signals */
3074 plugin->ParameterChangedExternally.connect_same_thread (*this, boost::bind (&PluginInsert::parameter_changed_externally, this, _1, _2));
3075 plugin->StartTouch.connect_same_thread (*this, boost::bind (&PluginInsert::start_touch, this, _1));
3076 plugin->EndTouch.connect_same_thread (*this, boost::bind (&PluginInsert::end_touch, this, _1));
3077 _custom_sinks = plugin->get_info()->n_inputs;
3078 // cache sidechain port count
3079 _cached_sidechain_pins.reset ();
3080 const ChanCount& nis (plugin->get_info()->n_inputs);
3081 for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
3082 for (uint32_t in = 0; in < nis.get (*t); ++in) {
3083 const Plugin::IOPortDescription& iod (plugin->describe_io_port (*t, true, in));
3084 if (iod.is_sidechain) {
3085 _cached_sidechain_pins.set (*t, 1 + _cached_sidechain_pins.n(*t));
3090 #if (defined WINDOWS_VST_SUPPORT || defined LXVST_SUPPORT || defined MACVST_SUPPORT)
3091 boost::shared_ptr<VSTPlugin> vst = boost::dynamic_pointer_cast<VSTPlugin> (plugin);
3093 vst->set_insert (this, _plugins.size ());
3097 _plugins.push_back (plugin);
3101 PluginInsert::add_sidechain_from_xml (const XMLNode& node, int version)
3103 if (version < 3000) {
3107 XMLNodeList nlist = node.children();
3109 if (nlist.size() == 0) {
3116 XMLNodeConstIterator it = nlist.front()->children().begin();
3117 for ( ; it != nlist.front()->children().end(); ++ it) {
3118 if ((*it)->name() == "Port") {
3119 DataType type(DataType::NIL);
3120 (*it)->get_property ("type", type);
3121 if (type == DataType::AUDIO) {
3123 } else if (type == DataType::MIDI) {
3129 ChanCount in_cc = ChanCount();
3130 in_cc.set (DataType::AUDIO, audio);
3131 in_cc.set (DataType::MIDI, midi);
3133 add_sidechain (audio, midi);
3137 PluginInsert::load_preset (ARDOUR::Plugin::PresetRecord pr)
3140 for (Plugins::iterator i = _plugins.begin(); i != _plugins.end(); ++i) {
3141 if (! (*i)->load_preset (pr)) {
3149 PluginInsert::realtime_handle_transport_stopped ()
3151 for (Plugins::iterator i = _plugins.begin(); i != _plugins.end(); ++i) {
3152 (*i)->realtime_handle_transport_stopped ();
3157 PluginInsert::realtime_locate ()
3159 for (Plugins::iterator i = _plugins.begin(); i != _plugins.end(); ++i) {
3160 (*i)->realtime_locate ();
3165 PluginInsert::monitoring_changed ()
3167 for (Plugins::iterator i = _plugins.begin(); i != _plugins.end(); ++i) {
3168 (*i)->monitoring_changed ();
3173 PluginInsert::latency_changed ()
3175 // this is called in RT context, LatencyChanged is emitted after run()
3176 _latency_changed = true;
3177 // XXX This also needs a proper API not an owner() hack.
3179 static_cast<Route*>(owner ())->processor_latency_changed (); /* EMIT SIGNAL */
3183 PluginInsert::start_touch (uint32_t param_id)
3185 boost::shared_ptr<AutomationControl> ac = automation_control (Evoral::Parameter (PluginAutomation, 0, param_id));
3187 // ToDo subtract _plugin_signal_latency from audible_sample() when rolling, assert > 0
3188 ac->start_touch (session().audible_sample());
3193 PluginInsert::end_touch (uint32_t param_id)
3195 boost::shared_ptr<AutomationControl> ac = automation_control (Evoral::Parameter (PluginAutomation, 0, param_id));
3197 // ToDo subtract _plugin_signal_latency from audible_sample() when rolling, assert > 0
3198 ac->stop_touch (session().audible_sample());
3203 PluginInsert::get_stats (uint64_t& min, uint64_t& max, double& avg, double& dev) const
3205 /* TODO: consider taking a try/lock: Don't run concurrently with
3206 * TimingStats::update, TimingStats::reset.
3208 return _timing_stats.get_stats (min, max, avg, dev);
3212 PluginInsert::clear_stats ()
3214 g_atomic_int_set (&_stat_reset, 1);
3217 std::ostream& operator<<(std::ostream& o, const ARDOUR::PluginInsert::Match& m)
3220 case PluginInsert::Impossible: o << "Impossible"; break;
3221 case PluginInsert::Delegate: o << "Delegate"; break;
3222 case PluginInsert::NoInputs: o << "NoInputs"; break;
3223 case PluginInsert::ExactMatch: o << "ExactMatch"; break;
3224 case PluginInsert::Replicate: o << "Replicate"; break;
3225 case PluginInsert::Split: o << "Split"; break;
3226 case PluginInsert::Hide: o << "Hide"; break;
3228 o << " cnt: " << m.plugins
3229 << (m.strict_io ? " strict-io" : "")
3230 << (m.custom_cfg ? " custom-cfg" : "");
3231 if (m.method == PluginInsert::Hide) {
3232 o << " hide: " << m.hide;