2 Copyright (C) 2008-2012 Paul Davis
3 Author: David Robillard
5 This program is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published by
7 the Free Software Foundation; either version 2 of the License, or
8 (at your option) any later version.
10 This program is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 GNU General Public License for more details.
15 You should have received a copy of the GNU General Public License
16 along with this program; if not, write to the Free Software
17 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
29 #include "pbd/gstdio_compat.h"
30 #include <glib/gprintf.h>
33 #include <boost/utility.hpp>
35 #include "pbd/file_utils.h"
36 #include "pbd/stl_delete.h"
37 #include "pbd/compose.h"
38 #include "pbd/error.h"
39 #include "pbd/locale_guard.h"
40 #include "pbd/replace_all.h"
41 #include "pbd/xml++.h"
43 #ifdef PLATFORM_WINDOWS
44 #include <shlobj.h> // CSIDL_*
45 #include "pbd/windows_special_dirs.h"
48 #include "libardour-config.h"
50 #include "ardour/audio_buffer.h"
51 #include "ardour/audioengine.h"
52 #include "ardour/debug.h"
53 #include "ardour/lv2_plugin.h"
54 #include "ardour/midi_patch_manager.h"
55 #include "ardour/session.h"
56 #include "ardour/tempo.h"
57 #include "ardour/types.h"
58 #include "ardour/utils.h"
59 #include "ardour/worker.h"
60 #include "ardour/search_paths.h"
65 #include <lilv/lilv.h>
67 #include "lv2/lv2plug.in/ns/ext/atom/atom.h"
68 #include "lv2/lv2plug.in/ns/ext/atom/forge.h"
69 #include "lv2/lv2plug.in/ns/ext/log/log.h"
70 #include "lv2/lv2plug.in/ns/ext/midi/midi.h"
71 #include "lv2/lv2plug.in/ns/ext/port-props/port-props.h"
72 #include "lv2/lv2plug.in/ns/ext/presets/presets.h"
73 #include "lv2/lv2plug.in/ns/ext/state/state.h"
74 #include "lv2/lv2plug.in/ns/ext/time/time.h"
75 #include "lv2/lv2plug.in/ns/ext/worker/worker.h"
76 #include "lv2/lv2plug.in/ns/ext/resize-port/resize-port.h"
77 #include "lv2/lv2plug.in/ns/extensions/ui/ui.h"
78 #include "lv2/lv2plug.in/ns/extensions/units/units.h"
79 #include "lv2/lv2plug.in/ns/ext/patch/patch.h"
80 #include "lv2/lv2plug.in/ns/ext/port-groups/port-groups.h"
82 #include "lv2/lv2plug.in/ns/ext/buf-size/buf-size.h"
83 #include "lv2/lv2plug.in/ns/ext/options/options.h"
86 #include "lv2_evbuf.h"
89 #include <suil/suil.h>
92 // Compatibility for old LV2
93 #ifndef LV2_ATOM_CONTENTS_CONST
94 #define LV2_ATOM_CONTENTS_CONST(type, atom) \
95 ((const void*)((const uint8_t*)(atom) + sizeof(type)))
97 #ifndef LV2_ATOM_BODY_CONST
98 #define LV2_ATOM_BODY_CONST(atom) LV2_ATOM_CONTENTS_CONST(LV2_Atom, atom)
100 #ifndef LV2_PATCH__property
101 #define LV2_PATCH__property LV2_PATCH_PREFIX "property"
103 #ifndef LV2_PATCH__value
104 #define LV2_PATCH__value LV2_PATCH_PREFIX "value"
106 #ifndef LV2_PATCH__writable
107 #define LV2_PATCH__writable LV2_PATCH_PREFIX "writable"
110 /** The number of MIDI buffers that will fit in a UI/worker comm buffer.
111 This needs to be roughly the number of cycles the UI will get around to
112 actually processing the traffic. Lower values are flakier but save memory.
114 static const size_t NBUFS = 4;
117 using namespace ARDOUR;
120 bool LV2Plugin::force_state_save = false;
122 class LV2World : boost::noncopyable {
127 void load_bundled_plugins(bool verbose=false);
131 LilvNode* atom_AtomPort;
132 LilvNode* atom_Chunk;
133 LilvNode* atom_Sequence;
134 LilvNode* atom_bufferType;
135 LilvNode* atom_eventTransfer;
136 LilvNode* atom_supports;
137 LilvNode* ev_EventPort;
138 LilvNode* ext_logarithmic;
139 LilvNode* ext_notOnGUI;
140 LilvNode* ext_expensive;
141 LilvNode* ext_causesArtifacts;
142 LilvNode* ext_notAutomatic;
143 LilvNode* ext_rangeSteps;
144 LilvNode* groups_group;
145 LilvNode* groups_element;
146 LilvNode* lv2_AudioPort;
147 LilvNode* lv2_ControlPort;
148 LilvNode* lv2_InputPort;
149 LilvNode* lv2_OutputPort;
150 LilvNode* lv2_designation;
151 LilvNode* lv2_enumeration;
152 LilvNode* lv2_freewheeling;
153 LilvNode* lv2_inPlaceBroken;
154 LilvNode* lv2_isSideChain;
156 LilvNode* lv2_integer;
157 LilvNode* lv2_default;
158 LilvNode* lv2_minimum;
159 LilvNode* lv2_maximum;
160 LilvNode* lv2_reportsLatency;
161 LilvNode* lv2_sampleRate;
162 LilvNode* lv2_toggled;
163 LilvNode* midi_MidiEvent;
164 LilvNode* rdfs_comment;
165 LilvNode* rdfs_label;
166 LilvNode* rdfs_range;
167 LilvNode* rsz_minimumSize;
168 LilvNode* time_Position;
170 LilvNode* ui_external;
171 LilvNode* ui_externalkx;
174 LilvNode* units_unit;
175 LilvNode* units_render;
176 LilvNode* units_midiNote;
177 LilvNode* patch_writable;
178 LilvNode* patch_Message;
179 #ifdef HAVE_LV2_1_2_0
180 LilvNode* bufz_powerOf2BlockLength;
181 LilvNode* bufz_fixedBlockLength;
182 LilvNode* bufz_nominalBlockLength;
183 LilvNode* bufz_coarseBlockLength;
186 #ifdef HAVE_LV2_1_10_0
188 LilvNode* atom_float;
189 LilvNode* atom_object; // new in 1.8
190 LilvNode* atom_vector;
193 LilvNode* lv2_noSampleAccurateCtrl;
194 LilvNode* auto_can_write_automatation; // lv2:optionalFeature
195 LilvNode* auto_automation_control; // atom:supports
196 LilvNode* auto_automation_controlled; // lv2:portProperty
197 LilvNode* auto_automation_controller; // lv2:portProperty
198 LilvNode* inline_display_in_gui; // lv2:optionalFeature
202 bool _bundle_checked;
205 static LV2World _world;
207 /* worker extension */
209 /** Called by the plugin to schedule non-RT work. */
210 static LV2_Worker_Status
211 work_schedule(LV2_Worker_Schedule_Handle handle,
215 return (((Worker*)handle)->schedule(size, data)
217 : LV2_WORKER_ERR_UNKNOWN);
220 /** Called by the plugin to respond to non-RT work. */
221 static LV2_Worker_Status
222 work_respond(LV2_Worker_Respond_Handle handle,
226 return (((Worker*)handle)->respond(size, data)
228 : LV2_WORKER_ERR_UNKNOWN);
232 /* inline display extension */
234 queue_draw (LV2_Inline_Display_Handle handle)
236 LV2Plugin* plugin = (LV2Plugin*)handle;
237 plugin->QueueDraw(); /* EMIT SIGNAL */
241 midnam_update (LV2_Midnam_Handle handle)
243 LV2Plugin* plugin = (LV2Plugin*)handle;
244 plugin->UpdateMidnam (); /* EMIT SIGNAL */
251 log_vprintf(LV2_Log_Handle /*handle*/,
257 const int ret = g_vasprintf(&str, fmt, args);
258 /* strip trailing whitespace */
259 while (strlen (str) > 0 && isspace (str[strlen (str) - 1])) {
260 str[strlen (str) - 1] = '\0';
262 if (strlen (str) == 0) {
266 if (type == URIMap::instance().urids.log_Error) {
267 error << str << endmsg;
268 } else if (type == URIMap::instance().urids.log_Warning) {
269 warning << str << endmsg;
270 } else if (type == URIMap::instance().urids.log_Note) {
271 info << str << endmsg;
272 } else if (type == URIMap::instance().urids.log_Trace) {
273 DEBUG_TRACE(DEBUG::LV2, str);
279 log_printf(LV2_Log_Handle handle,
281 const char* fmt, ...)
285 const int ret = log_vprintf(handle, type, fmt, args);
290 struct LV2Plugin::Impl {
291 Impl() : plugin(0), ui(0), ui_type(0), name(0), author(0), instance(0)
293 #ifdef HAVE_LV2_1_2_0
298 #ifdef HAVE_LV2_1_2_0
307 /** Find the LV2 input port with the given designation.
308 * If found, bufptrs[port_index] will be set to bufptr.
310 const LilvPort* designated_input (const char* uri, void** bufptrs[], void** bufptr);
312 const LilvPlugin* plugin;
314 const LilvNode* ui_type;
317 LilvInstance* instance;
318 const LV2_Worker_Interface* work_iface;
319 #ifdef HAVE_LV2_1_2_0
320 const LV2_Options_Interface* opts_iface;
323 LV2_Atom_Forge forge;
324 LV2_Atom_Forge ui_forge;
325 int32_t block_length;
326 #ifdef HAVE_LV2_1_2_0
327 LV2_Options_Option* options;
330 LV2_Inline_Display* queue_draw;
335 LV2Plugin::LV2Plugin (AudioEngine& engine,
337 const void* c_plugin,
339 : Plugin (engine, session)
344 , _state_worker(NULL)
346 , _patch_port_in_index((uint32_t)-1)
347 , _patch_port_out_index((uint32_t)-1)
348 , _uri_map(URIMap::instance())
349 , _no_sample_accurate_ctrl (false)
351 init(c_plugin, rate);
354 LV2Plugin::LV2Plugin (const LV2Plugin& other)
360 , _state_worker(NULL)
361 , _insert_id(other._insert_id)
362 , _patch_port_in_index((uint32_t)-1)
363 , _patch_port_out_index((uint32_t)-1)
364 , _uri_map(URIMap::instance())
365 , _no_sample_accurate_ctrl (false)
367 init(other._impl->plugin, other._sample_rate);
369 for (uint32_t i = 0; i < parameter_count(); ++i) {
370 _control_data[i] = other._shadow_data[i];
371 _shadow_data[i] = other._shadow_data[i];
376 LV2Plugin::init(const void* c_plugin, framecnt_t rate)
378 DEBUG_TRACE(DEBUG::LV2, "init\n");
380 _impl->plugin = (const LilvPlugin*)c_plugin;
382 _impl->ui_type = NULL;
387 _atom_ev_buffers = 0;
389 _bpm_control_port = 0;
390 _freewheel_control_port = 0;
391 _latency_control_port = 0;
392 _next_cycle_start = std::numeric_limits<framepos_t>::max();
393 _next_cycle_speed = 1.0;
394 _seq_size = _engine.raw_buffer_size(DataType::MIDI);
396 _was_activated = false;
397 _has_state_interface = false;
398 _can_write_automation = false;
399 _inline_display_in_gui = false;
401 _current_latency = 0;
402 _impl->block_length = _session.get_block_size();
404 _instance_access_feature.URI = "http://lv2plug.in/ns/ext/instance-access";
405 _data_access_feature.URI = "http://lv2plug.in/ns/ext/data-access";
406 _make_path_feature.URI = LV2_STATE__makePath;
407 _log_feature.URI = LV2_LOG__log;
408 _work_schedule_feature.URI = LV2_WORKER__schedule;
409 _work_schedule_feature.data = NULL;
410 _def_state_feature.URI = LV2_STATE_PREFIX "loadDefaultState"; // Post LV2-1.2.0
411 _def_state_feature.data = NULL;
413 const LilvPlugin* plugin = _impl->plugin;
415 LilvNode* state_iface_uri = lilv_new_uri(_world.world, LV2_STATE__interface);
416 LilvNode* state_uri = lilv_new_uri(_world.world, LV2_STATE_URI);
417 _has_state_interface =
418 // What plugins should have (lv2:extensionData state:Interface)
419 lilv_plugin_has_extension_data(plugin, state_iface_uri)
420 // What some outdated/incorrect ones have
421 || lilv_plugin_has_feature(plugin, state_uri);
422 lilv_node_free(state_uri);
423 lilv_node_free(state_iface_uri);
425 _features = (LV2_Feature**)calloc(13, sizeof(LV2_Feature*));
426 _features[0] = &_instance_access_feature;
427 _features[1] = &_data_access_feature;
428 _features[2] = &_make_path_feature;
429 _features[3] = _uri_map.uri_map_feature();
430 _features[4] = _uri_map.urid_map_feature();
431 _features[5] = _uri_map.urid_unmap_feature();
432 _features[6] = &_log_feature;
434 unsigned n_features = 7;
435 #ifdef HAVE_LV2_1_2_0
436 _features[n_features++] = &_def_state_feature;
439 lv2_atom_forge_init(&_impl->forge, _uri_map.urid_map());
440 lv2_atom_forge_init(&_impl->ui_forge, _uri_map.urid_map());
443 _impl->queue_draw = (LV2_Inline_Display*)
444 malloc (sizeof(LV2_Inline_Display));
445 _impl->queue_draw->handle = this;
446 _impl->queue_draw->queue_draw = queue_draw;
448 _queue_draw_feature.URI = LV2_INLINEDISPLAY__queue_draw;
449 _queue_draw_feature.data = _impl->queue_draw;
450 _features[n_features++] = &_queue_draw_feature;
452 _impl->midnam = (LV2_Midnam*)
453 malloc (sizeof(LV2_Midnam));
454 _impl->midnam->handle = this;
455 _impl->midnam->update = midnam_update;
457 _midnam_feature.URI = LV2_MIDNAM__update;
458 _midnam_feature.data = _impl->midnam;
459 _features[n_features++] = &_midnam_feature;
462 #ifdef HAVE_LV2_1_2_0
463 LV2_URID atom_Int = _uri_map.uri_to_id(LV2_ATOM__Int);
464 static const int32_t _min_block_length = 1; // may happen during split-cycles
465 static const int32_t _max_block_length = 8192; // max possible (with all engines and during export)
466 /* Consider updating max-block-size whenever the buffersize changes.
467 * It requires re-instantiating the plugin (which is a non-realtime operation),
468 * so it should be done lightly and only for plugins that require it.
470 * given that the block-size can change at any time (split-cycles) ardour currently
471 * does not support plugins that require bufz_fixedBlockLength.
473 LV2_Options_Option options[] = {
474 { LV2_OPTIONS_INSTANCE, 0, _uri_map.uri_to_id(LV2_BUF_SIZE__minBlockLength),
475 sizeof(int32_t), atom_Int, &_min_block_length },
476 { LV2_OPTIONS_INSTANCE, 0, _uri_map.uri_to_id(LV2_BUF_SIZE__maxBlockLength),
477 sizeof(int32_t), atom_Int, &_max_block_length },
478 { LV2_OPTIONS_INSTANCE, 0, _uri_map.uri_to_id(LV2_BUF_SIZE__sequenceSize),
479 sizeof(int32_t), atom_Int, &_seq_size },
480 { LV2_OPTIONS_INSTANCE, 0, _uri_map.uri_to_id("http://lv2plug.in/ns/ext/buf-size#nominalBlockLength"),
481 sizeof(int32_t), atom_Int, &_impl->block_length },
482 { LV2_OPTIONS_INSTANCE, 0, 0, 0, 0, NULL }
485 _impl->options = (LV2_Options_Option*) malloc (sizeof (options));
486 memcpy ((void*) _impl->options, (void*) options, sizeof (options));
488 _options_feature.URI = LV2_OPTIONS__options;
489 _options_feature.data = _impl->options;
490 _features[n_features++] = &_options_feature;
493 LV2_State_Make_Path* make_path = (LV2_State_Make_Path*)malloc(
494 sizeof(LV2_State_Make_Path));
495 make_path->handle = this;
496 make_path->path = &lv2_state_make_path;
497 _make_path_feature.data = make_path;
499 LV2_Log_Log* log = (LV2_Log_Log*)malloc(sizeof(LV2_Log_Log));
501 log->printf = &log_printf;
502 log->vprintf = &log_vprintf;
503 _log_feature.data = log;
505 const size_t ring_size = _session.engine().raw_buffer_size(DataType::MIDI) * NBUFS;
506 LilvNode* worker_schedule = lilv_new_uri(_world.world, LV2_WORKER__schedule);
507 if (lilv_plugin_has_feature(plugin, worker_schedule)) {
508 LV2_Worker_Schedule* schedule = (LV2_Worker_Schedule*)malloc(
509 sizeof(LV2_Worker_Schedule));
510 _worker = new Worker(this, ring_size);
511 schedule->handle = _worker;
512 schedule->schedule_work = work_schedule;
513 _work_schedule_feature.data = schedule;
514 _features[n_features++] = &_work_schedule_feature;
516 lilv_node_free(worker_schedule);
518 if (_has_state_interface) {
519 // Create a non-threaded worker for use by state restore
520 _state_worker = new Worker(this, ring_size, false);
523 _impl->instance = lilv_plugin_instantiate(plugin, rate, _features);
524 _impl->name = lilv_plugin_get_name(plugin);
525 _impl->author = lilv_plugin_get_author_name(plugin);
527 if (_impl->instance == 0) {
528 error << _("LV2: Failed to instantiate plugin ") << uri() << endmsg;
529 throw failed_constructor();
532 _instance_access_feature.data = (void*)_impl->instance->lv2_handle;
533 _data_access_extension_data.extension_data = _impl->instance->lv2_descriptor->extension_data;
534 _data_access_feature.data = &_data_access_extension_data;
536 LilvNode* worker_iface_uri = lilv_new_uri(_world.world, LV2_WORKER__interface);
537 if (lilv_plugin_has_extension_data(plugin, worker_iface_uri)) {
538 _impl->work_iface = (const LV2_Worker_Interface*)extension_data(
539 LV2_WORKER__interface);
541 lilv_node_free(worker_iface_uri);
544 #ifdef HAVE_LV2_1_2_0
545 LilvNode* options_iface_uri = lilv_new_uri(_world.world, LV2_OPTIONS__interface);
546 if (lilv_plugin_has_extension_data(plugin, options_iface_uri)) {
547 _impl->opts_iface = (const LV2_Options_Interface*)extension_data(
548 LV2_OPTIONS__interface);
550 lilv_node_free(options_iface_uri);
554 _display_interface = (const LV2_Inline_Display_Interface*)
555 extension_data (LV2_INLINEDISPLAY__interface);
557 _midname_interface = (const LV2_Midnam_Interface*)
558 extension_data (LV2_MIDNAM__interface);
559 if (_midname_interface) {
564 if (lilv_plugin_has_feature(plugin, _world.lv2_inPlaceBroken)) {
565 error << string_compose(
566 _("LV2: \"%1\" cannot be used, since it cannot do inplace processing."),
567 lilv_node_as_string(_impl->name)) << endmsg;
568 lilv_node_free(_impl->name);
569 lilv_node_free(_impl->author);
570 throw failed_constructor();
573 #ifdef HAVE_LV2_1_2_0
574 LilvNodes *required_features = lilv_plugin_get_required_features (plugin);
575 if (lilv_nodes_contains (required_features, _world.bufz_powerOf2BlockLength) ||
576 lilv_nodes_contains (required_features, _world.bufz_fixedBlockLength)
578 error << string_compose(
579 _("LV2: \"%1\" buffer-size requirements cannot be satisfied."),
580 lilv_node_as_string(_impl->name)) << endmsg;
581 lilv_node_free(_impl->name);
582 lilv_node_free(_impl->author);
583 lilv_nodes_free(required_features);
584 throw failed_constructor();
586 lilv_nodes_free(required_features);
589 LilvNodes* optional_features = lilv_plugin_get_optional_features (plugin);
590 #ifdef HAVE_LV2_1_2_0
591 if (lilv_nodes_contains (optional_features, _world.bufz_coarseBlockLength)) {
592 _no_sample_accurate_ctrl = true;
596 if (lilv_nodes_contains (optional_features, _world.lv2_noSampleAccurateCtrl)) {
597 /* deprecated 2016-Sep-18 in favor of bufz_coarseBlockLength */
598 _no_sample_accurate_ctrl = true;
600 if (lilv_nodes_contains (optional_features, _world.auto_can_write_automatation)) {
601 _can_write_automation = true;
603 if (lilv_nodes_contains (optional_features, _world.inline_display_in_gui)) {
604 _inline_display_in_gui = true;
606 lilv_nodes_free(optional_features);
609 #ifdef HAVE_LILV_0_16_0
610 // Load default state
612 /* immediately schedule any work,
613 * so that state restore later will not find a busy
614 * worker. latency_compute_run() flushes any replies
616 _worker->set_synchronous(true);
618 LilvState* state = lilv_state_new_from_world(
619 _world.world, _uri_map.urid_map(), lilv_plugin_get_uri(_impl->plugin));
620 if (state && _has_state_interface) {
621 lilv_state_restore(state, _impl->instance, NULL, NULL, 0, NULL);
623 lilv_state_free(state);
628 const uint32_t num_ports = this->num_ports();
629 for (uint32_t i = 0; i < num_ports; ++i) {
630 const LilvPort* port = lilv_plugin_get_port_by_index(_impl->plugin, i);
632 size_t minimumSize = 0;
634 if (lilv_port_is_a(_impl->plugin, port, _world.lv2_OutputPort)) {
635 flags |= PORT_OUTPUT;
636 } else if (lilv_port_is_a(_impl->plugin, port, _world.lv2_InputPort)) {
639 error << string_compose(
640 "LV2: \"%1\" port %2 is neither input nor output",
641 lilv_node_as_string(_impl->name), i) << endmsg;
642 throw failed_constructor();
645 if (lilv_port_is_a(_impl->plugin, port, _world.lv2_ControlPort)) {
646 flags |= PORT_CONTROL;
647 } else if (lilv_port_is_a(_impl->plugin, port, _world.lv2_AudioPort)) {
649 } else if (lilv_port_is_a(_impl->plugin, port, _world.ev_EventPort)) {
651 flags |= PORT_MIDI; // We assume old event API ports are for MIDI
652 } else if (lilv_port_is_a(_impl->plugin, port, _world.atom_AtomPort)) {
653 LilvNodes* buffer_types = lilv_port_get_value(
654 _impl->plugin, port, _world.atom_bufferType);
655 LilvNodes* atom_supports = lilv_port_get_value(
656 _impl->plugin, port, _world.atom_supports);
658 if (lilv_nodes_contains(buffer_types, _world.atom_Sequence)) {
659 flags |= PORT_SEQUENCE;
660 if (lilv_nodes_contains(atom_supports, _world.midi_MidiEvent)) {
663 if (lilv_nodes_contains(atom_supports, _world.time_Position)) {
664 flags |= PORT_POSITION;
667 if (lilv_nodes_contains(atom_supports, _world.auto_automation_control)) {
668 flags |= PORT_AUTOCTRL;
671 if (lilv_nodes_contains(atom_supports, _world.patch_Message)) {
672 flags |= PORT_PATCHMSG;
673 if (flags & PORT_INPUT) {
674 _patch_port_in_index = i;
676 _patch_port_out_index = i;
680 LilvNodes* min_size_v = lilv_port_get_value(_impl->plugin, port, _world.rsz_minimumSize);
681 LilvNode* min_size = min_size_v ? lilv_nodes_get_first(min_size_v) : NULL;
682 if (min_size && lilv_node_is_int(min_size)) {
683 minimumSize = lilv_node_as_int(min_size);
685 lilv_nodes_free(min_size_v);
686 lilv_nodes_free(buffer_types);
687 lilv_nodes_free(atom_supports);
689 error << string_compose(
690 "LV2: \"%1\" port %2 has no known data type",
691 lilv_node_as_string(_impl->name), i) << endmsg;
692 throw failed_constructor();
695 if ((flags & PORT_INPUT) && (flags & PORT_CONTROL)) {
696 if (lilv_port_has_property(_impl->plugin, port, _world.ext_causesArtifacts)) {
697 flags |= PORT_NOAUTO;
699 if (lilv_port_has_property(_impl->plugin, port, _world.ext_notAutomatic)) {
700 flags |= PORT_NOAUTO;
702 if (lilv_port_has_property(_impl->plugin, port, _world.ext_expensive)) {
703 flags |= PORT_NOAUTO;
707 if (lilv_port_has_property(_impl->plugin, port, _world.auto_automation_controlled)) {
708 if ((flags & PORT_INPUT) && (flags & PORT_CONTROL)) {
709 flags |= PORT_CTRLED;
712 if (lilv_port_has_property(_impl->plugin, port, _world.auto_automation_controller)) {
713 if ((flags & PORT_INPUT) && (flags & PORT_CONTROL)) {
714 flags |= PORT_CTRLER;
719 _port_flags.push_back(flags);
720 _port_minimumSize.push_back(minimumSize);
721 DEBUG_TRACE(DEBUG::LV2, string_compose("port %1 buffer %2 bytes\n", i, minimumSize));
724 _control_data = new float[num_ports];
725 _shadow_data = new float[num_ports];
726 _defaults = new float[num_ports];
727 _ev_buffers = new LV2_Evbuf*[num_ports];
728 memset(_ev_buffers, 0, sizeof(LV2_Evbuf*) * num_ports);
730 const bool latent = lilv_plugin_has_latency(plugin);
731 const uint32_t latency_index = (latent)
732 ? lilv_plugin_get_latency_port_index(plugin)
735 // Build an array of pointers to special parameter buffers
736 void*** params = new void**[num_ports];
737 for (uint32_t i = 0; i < num_ports; ++i) {
740 _impl->designated_input (LV2_TIME__beatsPerMinute, params, (void**)&_bpm_control_port);
741 _impl->designated_input (LV2_CORE__freeWheeling, params, (void**)&_freewheel_control_port);
743 for (uint32_t i = 0; i < num_ports; ++i) {
744 const LilvPort* port = lilv_plugin_get_port_by_index(plugin, i);
745 const LilvNode* sym = lilv_port_get_symbol(plugin, port);
747 // Store index in map so we can look up index by symbol
748 _port_indices.insert(std::make_pair(lilv_node_as_string(sym), i));
750 // Get range and default value if applicable
751 if (parameter_is_control(i)) {
753 lilv_port_get_range(plugin, port, &def, NULL, NULL);
754 _defaults[i] = def ? lilv_node_as_float(def) : 0.0f;
755 if (lilv_port_has_property (plugin, port, _world.lv2_sampleRate)) {
756 _defaults[i] *= _session.frame_rate ();
760 lilv_instance_connect_port(_impl->instance, i, &_control_data[i]);
762 if (latent && i == latency_index) {
764 lilv_port_get_range(_impl->plugin, port, NULL, NULL, &max);
765 _max_latency = max ? lilv_node_as_float(max) : .02 * _sample_rate;
766 _latency_control_port = &_control_data[i];
767 *_latency_control_port = 0;
770 if (parameter_is_input(i)) {
771 _shadow_data[i] = default_value(i);
773 *params[i] = (void*)&_shadow_data[i];
783 LilvUIs* uis = lilv_plugin_get_uis(plugin);
784 if (lilv_uis_size(uis) > 0) {
786 // Look for embeddable UI
787 LILV_FOREACH(uis, u, uis) {
788 const LilvUI* this_ui = lilv_uis_get(uis, u);
789 const LilvNode* this_ui_type = NULL;
790 if (lilv_ui_is_supported(this_ui,
794 // TODO: Multiple UI support
796 _impl->ui_type = this_ui_type;
801 // Look for Gtk native UI
802 LILV_FOREACH(uis, i, uis) {
803 const LilvUI* ui = lilv_uis_get(uis, i);
804 if (lilv_ui_is_a(ui, _world.ui_GtkUI)) {
806 _impl->ui_type = _world.ui_GtkUI;
812 // If Gtk UI is not available, try to find external UI
814 LILV_FOREACH(uis, i, uis) {
815 const LilvUI* ui = lilv_uis_get(uis, i);
816 if (lilv_ui_is_a(ui, _world.ui_externalkx)) {
818 _impl->ui_type = _world.ui_external;
821 if (lilv_ui_is_a(ui, _world.ui_external)) {
823 _impl->ui_type = _world.ui_external;
829 load_supported_properties(_property_descriptors);
830 allocate_atom_event_buffers();
831 latency_compute_run();
835 LV2Plugin::set_block_size (pframes_t nframes)
837 #ifdef HAVE_LV2_1_2_0
838 if (_impl->opts_iface) {
839 LV2_URID atom_Int = _uri_map.uri_to_id(LV2_ATOM__Int);
840 _impl->block_length = nframes;
841 LV2_Options_Option block_size_option = {
842 LV2_OPTIONS_INSTANCE, 0, _uri_map.uri_to_id ("http://lv2plug.in/ns/ext/buf-size#nominalBlockLength"),
843 sizeof(int32_t), atom_Int, (void*)&_impl->block_length
845 _impl->opts_iface->set (_impl->instance->lv2_handle, &block_size_option);
852 LV2Plugin::requires_fixed_sized_buffers () const
854 /* This controls if Ardour will split the plugin's run()
855 * on automation events in order to pass sample-accurate automation
856 * via standard control-ports.
858 * When returning true Ardour will *not* sub-divide the process-cycle.
859 * Automation events that happen between cycle-start and cycle-end will be
860 * ignored (ctrl values are interpolated to cycle-start).
861 * NB. Atom Sequences are still sample accurate.
863 * Note: This does not guarantee a fixed block-size.
864 * e.g The process cycle may be split when looping, also
865 * the period-size may change any time: see set_block_size()
867 if (get_info()->n_inputs.n_midi() > 0) {
868 /* we don't yet implement midi buffer offsets (for split cycles).
869 * Also connect_and_run() also uses _session.transport_frame() directly
870 * (for BBT) which is not offset for plugin cycle split.
874 return _no_sample_accurate_ctrl;
877 LV2Plugin::~LV2Plugin ()
879 DEBUG_TRACE(DEBUG::LV2, string_compose("%1 destroy\n", name()));
886 std::stringstream ss;
889 MIDI::Name::MidiPatchManager::instance().remove_custom_midnam (ss.str());
893 lilv_instance_free(_impl->instance);
894 lilv_state_free(_impl->state);
895 lilv_node_free(_impl->name);
896 lilv_node_free(_impl->author);
897 #ifdef HAVE_LV2_1_2_0
898 free(_impl->options);
901 free(_impl->queue_draw);
906 free(_log_feature.data);
907 free(_make_path_feature.data);
908 free(_work_schedule_feature.data);
913 delete _state_worker;
915 if (_atom_ev_buffers) {
916 LV2_Evbuf** b = _atom_ev_buffers;
921 free(_atom_ev_buffers);
924 delete [] _control_data;
925 delete [] _shadow_data;
927 delete [] _ev_buffers;
932 LV2Plugin::is_external_ui() const
937 return lilv_ui_is_a(_impl->ui, _world.ui_external) || lilv_ui_is_a(_impl->ui, _world.ui_externalkx);
941 LV2Plugin::is_external_kx() const
946 return lilv_ui_is_a(_impl->ui, _world.ui_externalkx);
950 LV2Plugin::ui_is_resizable () const
952 const LilvNode* s = lilv_ui_get_uri(_impl->ui);
953 LilvNode* p = lilv_new_uri(_world.world, LV2_CORE__optionalFeature);
954 LilvNode* fs = lilv_new_uri(_world.world, LV2_UI__fixedSize);
955 LilvNode* nrs = lilv_new_uri(_world.world, LV2_UI__noUserResize);
957 LilvNodes* fs_matches = lilv_world_find_nodes(_world.world, s, p, fs);
958 LilvNodes* nrs_matches = lilv_world_find_nodes(_world.world, s, p, nrs);
960 lilv_nodes_free(nrs_matches);
961 lilv_nodes_free(fs_matches);
966 return !fs_matches && !nrs_matches;
971 LV2Plugin::has_inline_display () {
972 return _display_interface ? true : false;
976 LV2Plugin::inline_display_in_gui () {
977 return _inline_display_in_gui;
980 Plugin::Display_Image_Surface*
981 LV2Plugin::render_inline_display (uint32_t w, uint32_t h) {
982 if (_display_interface) {
983 /* Plugin::Display_Image_Surface is identical to
984 * LV2_Inline_Display_Image_Surface */
985 return (Plugin::Display_Image_Surface*) _display_interface->render ((void*)_impl->instance->lv2_handle, w, h);
991 LV2Plugin::has_midnam () {
992 return _midname_interface ? true : false;
996 LV2Plugin::read_midnam () {
998 if (!_midname_interface) {
1001 char* midnam = _midname_interface->midnam ((void*)_impl->instance->lv2_handle);
1003 std::stringstream ss;
1006 rv = MIDI::Name::MidiPatchManager::instance().update_custom_midnam (ss.str(), midnam);
1010 info << string_compose(_("LV2: update midnam for plugin '%1'"), name ()) << endmsg;
1012 warning << string_compose(_("LV2: Failed to parse midnam of plugin '%1'"), name ()) << endmsg;
1015 _midname_interface->free (midnam);
1020 LV2Plugin::midnam_model () {
1022 if (!_midname_interface) {
1025 char* model = _midname_interface->model ((void*)_impl->instance->lv2_handle);
1029 _midname_interface->free (model);
1035 LV2Plugin::unique_id() const
1037 return lilv_node_as_uri(lilv_plugin_get_uri(_impl->plugin));
1041 LV2Plugin::uri() const
1043 return lilv_node_as_uri(lilv_plugin_get_uri(_impl->plugin));
1047 LV2Plugin::label() const
1049 return lilv_node_as_string(_impl->name);
1053 LV2Plugin::name() const
1055 return lilv_node_as_string(_impl->name);
1059 LV2Plugin::maker() const
1061 return _impl->author ? lilv_node_as_string (_impl->author) : "Unknown";
1065 LV2Plugin::num_ports() const
1067 return lilv_plugin_get_num_ports(_impl->plugin);
1071 LV2Plugin::parameter_count() const
1073 return lilv_plugin_get_num_ports(_impl->plugin);
1077 LV2Plugin::default_value(uint32_t port)
1079 return _defaults[port];
1083 LV2Plugin::port_symbol(uint32_t index) const
1085 const LilvPort* port = lilv_plugin_get_port_by_index(_impl->plugin, index);
1087 error << name() << ": Invalid port index " << index << endmsg;
1090 const LilvNode* sym = lilv_port_get_symbol(_impl->plugin, port);
1091 return lilv_node_as_string(sym);
1095 LV2Plugin::port_index (const char* symbol) const
1097 const map<string, uint32_t>::const_iterator i = _port_indices.find(symbol);
1098 if (i != _port_indices.end()) {
1101 warning << string_compose(_("LV2: Unknown port %1"), symbol) << endmsg;
1102 return (uint32_t)-1;
1107 LV2Plugin::set_parameter(uint32_t which, float val)
1109 DEBUG_TRACE(DEBUG::LV2, string_compose(
1110 "%1 set parameter %2 to %3\n", name(), which, val));
1112 if (which < lilv_plugin_get_num_ports(_impl->plugin)) {
1113 if (get_parameter (which) == val) {
1117 _shadow_data[which] = val;
1119 warning << string_compose(
1120 _("Illegal parameter number used with plugin \"%1\". "
1121 "This is a bug in either %2 or the LV2 plugin <%3>"),
1122 name(), PROGRAM_NAME, unique_id()) << endmsg;
1125 Plugin::set_parameter(which, val);
1129 LV2Plugin::get_parameter(uint32_t which) const
1131 if (parameter_is_input(which)) {
1132 return (float)_shadow_data[which];
1134 return (float)_control_data[which];
1140 LV2Plugin::get_docs() const
1142 LilvNodes* comments = lilv_plugin_get_value(_impl->plugin, _world.rdfs_comment);
1144 const std::string docs(lilv_node_as_string(lilv_nodes_get_first(comments)));
1145 lilv_nodes_free(comments);
1153 LV2Plugin::get_parameter_docs(uint32_t which) const
1155 LilvNodes* comments = lilv_port_get_value(
1157 lilv_plugin_get_port_by_index(_impl->plugin, which),
1158 _world.rdfs_comment);
1161 const std::string docs(lilv_node_as_string(lilv_nodes_get_first(comments)));
1162 lilv_nodes_free(comments);
1170 LV2Plugin::get_layout (uint32_t which, UILayoutHint& h) const
1172 /// TODO lookup port-properties
1173 if (unique_id () != "urn:ardour:a-eq") {
1178 case 0: h.x0 = 0; h.x1 = 1; h.y0 = 2; h.y1 = 3; break; // Frequency L
1179 case 1: h.x0 = 0; h.x1 = 1; h.y0 = 0; h.y1 = 1; break; // Gain L
1180 case 17: h.x0 = 0; h.x1 = 1; h.y0 = 5; h.y1 = 6; break; // enable L
1182 case 2: h.x0 = 1; h.x1 = 3; h.y0 = 2; h.y1 = 3; break; // Frequency 1
1183 case 3: h.x0 = 1; h.x1 = 3; h.y0 = 0; h.y1 = 1; break; // Gain 1
1184 case 4: h.x0 = 1; h.x1 = 3; h.y0 = 1; h.y1 = 2; break; // Bandwidth 1
1185 case 18: h.x0 = 1; h.x1 = 4; h.y0 = 5; h.y1 = 6; break; // enable 1
1187 case 5: h.x0 = 4; h.x1 = 6; h.y0 = 2; h.y1 = 3; break; // Frequency 2
1188 case 6: h.x0 = 4; h.x1 = 6; h.y0 = 0; h.y1 = 1; break; // Gain 2
1189 case 7: h.x0 = 4; h.x1 = 6; h.y0 = 1; h.y1 = 2; break; // Bandwidth 2
1190 case 19: h.x0 = 4; h.x1 = 7; h.y0 = 5; h.y1 = 6; break; // enable 2
1192 case 8: h.x0 = 7; h.x1 = 9; h.y0 = 2; h.y1 = 3; break; // Frequency 3
1193 case 9: h.x0 = 7; h.x1 = 9; h.y0 = 0; h.y1 = 1; break; // Gain 3
1194 case 10: h.x0 = 7; h.x1 = 9; h.y0 = 1; h.y1 = 2; break; // Bandwidth 3
1195 case 20: h.x0 = 7; h.x1 = 10; h.y0 = 5; h.y1 = 6; break; // enable 3
1197 case 11: h.x0 = 10; h.x1 = 12; h.y0 = 2; h.y1 = 3; break; // Frequency 4
1198 case 12: h.x0 = 10; h.x1 = 12; h.y0 = 0; h.y1 = 1; break; // Gain 4
1199 case 13: h.x0 = 10; h.x1 = 12; h.y0 = 1; h.y1 = 2; break; // Bandwidth 4
1200 case 21: h.x0 = 10; h.x1 = 13; h.y0 = 5; h.y1 = 6; break; // enable 4
1202 case 14: h.x0 = 13; h.x1 = 14; h.y0 = 2; h.y1 = 3; break; // Frequency H
1203 case 15: h.x0 = 13; h.x1 = 14; h.y0 = 0; h.y1 = 1; break; // Gain H
1204 case 22: h.x0 = 13; h.x1 = 14; h.y0 = 5; h.y1 = 6; break; // enable H
1206 case 16: h.x0 = 14; h.x1 = 15; h.y0 = 1; h.y1 = 3; break; // Master Gain
1207 case 23: h.x0 = 14; h.x1 = 15; h.y0 = 5; h.y1 = 6; break; // Master Enable
1215 LV2Plugin::nth_parameter(uint32_t n, bool& ok) const
1218 for (uint32_t c = 0, x = 0; x < lilv_plugin_get_num_ports(_impl->plugin); ++x) {
1219 if (parameter_is_control(x)) {
1231 LV2Plugin::extension_data(const char* uri) const
1233 return lilv_instance_get_extension_data(_impl->instance, uri);
1237 LV2Plugin::c_plugin()
1239 return _impl->plugin;
1245 return (const void*)_impl->ui;
1249 LV2Plugin::c_ui_type()
1251 return (const void*)_impl->ui_type;
1254 /** Directory for all plugin state. */
1256 LV2Plugin::plugin_dir() const
1258 if (!_plugin_state_dir.empty ()){
1259 return Glib::build_filename(_plugin_state_dir, _insert_id.to_s());
1261 return Glib::build_filename(_session.plugins_dir(), _insert_id.to_s());
1265 /** Directory for files created by the plugin (except during save). */
1267 LV2Plugin::scratch_dir() const
1269 return Glib::build_filename(plugin_dir(), "scratch");
1272 /** Directory for snapshots of files in the scratch directory. */
1274 LV2Plugin::file_dir() const
1276 return Glib::build_filename(plugin_dir(), "files");
1279 /** Directory to save state snapshot version @c num into. */
1281 LV2Plugin::state_dir(unsigned num) const
1283 return Glib::build_filename(plugin_dir(), string("state") + PBD::to_string (num));
1286 /** Implementation of state:makePath for files created at instantiation time.
1287 * Note this is not used for files created at save time (Lilv deals with that).
1290 LV2Plugin::lv2_state_make_path(LV2_State_Make_Path_Handle handle,
1293 LV2Plugin* me = (LV2Plugin*)handle;
1294 if (me->_insert_id == PBD::ID("0")) {
1295 warning << string_compose(
1296 "File path \"%1\" requested but LV2 %2 has no insert ID",
1297 path, me->name()) << endmsg;
1298 return g_strdup(path);
1301 const std::string abs_path = Glib::build_filename(me->scratch_dir(), path);
1302 const std::string dirname = Glib::path_get_dirname(abs_path);
1303 g_mkdir_with_parents(dirname.c_str(), 0744);
1305 DEBUG_TRACE(DEBUG::LV2, string_compose("new file path %1 => %2\n",
1308 return g_strndup(abs_path.c_str(), abs_path.length());
1312 LV2Plugin::add_state(XMLNode* root) const
1314 assert(_insert_id != PBD::ID("0"));
1319 for (uint32_t i = 0; i < parameter_count(); ++i) {
1320 if (parameter_is_input(i) && parameter_is_control(i)) {
1321 child = new XMLNode("Port");
1322 child->set_property("symbol", port_symbol(i));
1323 child->set_property("value", _shadow_data[i]);
1324 root->add_child_nocopy(*child);
1328 if (!_plugin_state_dir.empty()) {
1329 root->set_property("template-dir", _plugin_state_dir);
1332 if (_has_state_interface) {
1333 // Provisionally increment state version and create directory
1334 const std::string new_dir = state_dir(++_state_version);
1335 // and keep track of it (for templates & archive)
1336 unsigned int saved_state = _state_version;;
1337 g_mkdir_with_parents(new_dir.c_str(), 0744);
1339 LilvState* state = lilv_state_new_from_instance(
1342 _uri_map.urid_map(),
1343 scratch_dir().c_str(),
1345 _session.externals_dir().c_str(),
1348 const_cast<LV2Plugin*>(this),
1352 if (!_plugin_state_dir.empty() || force_state_save
1354 || !lilv_state_equals(state, _impl->state)) {
1355 lilv_state_save(_world.world,
1356 _uri_map.urid_map(),
1357 _uri_map.urid_unmap(),
1363 if (force_state_save) {
1364 // archive or save-as
1365 lilv_state_free(state);
1368 else if (_plugin_state_dir.empty()) {
1369 // normal session save
1370 lilv_state_free(_impl->state);
1371 _impl->state = state;
1373 // template save (dedicated state-dir)
1374 lilv_state_free(state);
1378 // State is identical, decrement version and nuke directory
1379 lilv_state_free(state);
1380 PBD::remove_directory(new_dir);
1382 saved_state = _state_version;
1385 root->set_property("state-dir", string("state") + PBD::to_string (saved_state));
1389 // TODO: Once we can rely on lilv 0.16.0, lilv_world_get can replace this
1391 get_value(LilvWorld* world, const LilvNode* subject, const LilvNode* predicate)
1393 LilvNodes* vs = lilv_world_find_nodes(world, subject, predicate, NULL);
1395 LilvNode* node = lilv_node_duplicate(lilv_nodes_get_first(vs));
1396 lilv_nodes_free(vs);
1403 LV2Plugin::find_presets()
1405 LilvNode* lv2_appliesTo = lilv_new_uri(_world.world, LV2_CORE__appliesTo);
1406 LilvNode* pset_Preset = lilv_new_uri(_world.world, LV2_PRESETS__Preset);
1407 LilvNode* rdfs_label = lilv_new_uri(_world.world, LILV_NS_RDFS "label");
1409 LilvNodes* presets = lilv_plugin_get_related(_impl->plugin, pset_Preset);
1410 LILV_FOREACH(nodes, i, presets) {
1411 const LilvNode* preset = lilv_nodes_get(presets, i);
1412 lilv_world_load_resource(_world.world, preset);
1413 LilvNode* name = get_value(_world.world, preset, rdfs_label);
1414 bool userpreset = true; // TODO
1416 _presets.insert(std::make_pair(lilv_node_as_string(preset),
1417 Plugin::PresetRecord(
1418 lilv_node_as_string(preset),
1419 lilv_node_as_string(name),
1421 lilv_node_free(name);
1423 warning << string_compose(
1424 _("Plugin \"%1\" preset \"%2\" is missing a label\n"),
1425 lilv_node_as_string(lilv_plugin_get_uri(_impl->plugin)),
1426 lilv_node_as_string(preset)) << endmsg;
1429 lilv_nodes_free(presets);
1431 lilv_node_free(rdfs_label);
1432 lilv_node_free(pset_Preset);
1433 lilv_node_free(lv2_appliesTo);
1437 set_port_value(const char* port_symbol,
1443 LV2Plugin* self = (LV2Plugin*)user_data;
1444 if (type != 0 && type != URIMap::instance().urids.atom_Float) {
1445 return; // TODO: Support non-float ports
1448 const uint32_t port_index = self->port_index(port_symbol);
1449 if (port_index != (uint32_t)-1) {
1450 self->set_parameter(port_index, *(const float*)value);
1451 self->PresetPortSetValue (port_index, *(const float*)value); /* EMIT SIGNAL */
1456 LV2Plugin::load_preset(PresetRecord r)
1458 LilvWorld* world = _world.world;
1459 LilvNode* pset = lilv_new_uri(world, r.uri.c_str());
1460 LilvState* state = lilv_state_new_from_world(world, _uri_map.urid_map(), pset);
1462 const LV2_Feature* state_features[2] = { NULL, NULL };
1463 LV2_Worker_Schedule schedule = { _state_worker, work_schedule };
1464 const LV2_Feature state_sched_feature = { LV2_WORKER__schedule, &schedule };
1465 if (_state_worker) {
1466 state_features[0] = &state_sched_feature;
1470 lilv_state_restore(state, _impl->instance, set_port_value, this, 0, state_features);
1471 lilv_state_free(state);
1472 Plugin::load_preset(r);
1475 lilv_node_free(pset);
1480 ARDOUR::lv2plugin_get_port_value(const char* port_symbol,
1485 LV2Plugin *plugin = (LV2Plugin *) user_data;
1487 uint32_t index = plugin->port_index(port_symbol);
1488 if (index != (uint32_t) -1) {
1489 if (plugin->parameter_is_input(index) && plugin->parameter_is_control(index)) {
1491 *size = sizeof(float);
1492 *type = plugin->_uri_map.uri_to_id(LV2_ATOM__Float);
1493 value = &plugin->_shadow_data[index];
1505 LV2Plugin::do_save_preset(string name)
1507 LilvNode* plug_name = lilv_plugin_get_name(_impl->plugin);
1508 const string prefix = legalize_for_uri(lilv_node_as_string(plug_name));
1509 const string base_name = legalize_for_uri(name);
1510 const string file_name = base_name + ".ttl";
1511 #ifdef PLATFORM_WINDOWS
1512 /* http://lv2plug.in/pages/filesystem-hierarchy-standard.html */
1513 std::string appdata = PBD::get_win_special_folder_path (CSIDL_APPDATA);
1514 if (appdata.empty ()) {
1515 // TODO consider a fallback location
1518 const string bundle = Glib::build_filename (
1519 appdata, "LV2", prefix + "_" + base_name + ".lv2");
1521 /* while macOS/OSX user-specific path is
1523 * $HOME/Library/Audio/Plug-Ins/LV2/
1525 * liblilv's LV2 search path on all unices does include ~/.lv2/
1526 * Ardour has been saving lv2 presets to ~/.lv2 for along time,
1527 * so just keep them there.
1529 const string bundle = Glib::build_filename(
1530 Glib::get_home_dir(),
1531 Glib::build_filename(".lv2", prefix + "_" + base_name + ".lv2"));
1534 #ifdef HAVE_LILV_0_21_3
1535 /* delete reference to old preset (if any) */
1536 const PresetRecord* r = preset_by_label(name);
1538 LilvNode* pset = lilv_new_uri (_world.world, r->uri.c_str());
1540 lilv_world_unload_resource (_world.world, pset);
1541 lilv_node_free(pset);
1546 LilvState* state = lilv_state_new_from_instance(
1549 _uri_map.urid_map(),
1550 scratch_dir().c_str(), // file_dir
1551 bundle.c_str(), // copy_dir
1552 bundle.c_str(), // link_dir
1553 bundle.c_str(), // save_dir
1554 lv2plugin_get_port_value, // get_value
1555 (void*)this, // user_data
1556 LV2_STATE_IS_POD|LV2_STATE_IS_PORTABLE, // flags
1557 _features // features
1560 lilv_state_set_label(state, name.c_str());
1562 _world.world, // world
1563 _uri_map.urid_map(), // map
1564 _uri_map.urid_unmap(), // unmap
1566 NULL, // uri (NULL = use file URI)
1567 bundle.c_str(), // dir
1568 file_name.c_str() // filename
1571 lilv_state_free(state);
1573 std::string uri = Glib::filename_to_uri(Glib::build_filename(bundle, file_name));
1574 LilvNode *node_bundle = lilv_new_uri(_world.world, Glib::filename_to_uri(Glib::build_filename(bundle, "/")).c_str());
1575 LilvNode *node_preset = lilv_new_uri(_world.world, uri.c_str());
1576 #ifdef HAVE_LILV_0_21_3
1577 lilv_world_unload_resource(_world.world, node_preset);
1578 lilv_world_unload_bundle(_world.world, node_bundle);
1580 lilv_world_load_bundle(_world.world, node_bundle);
1581 lilv_world_load_resource(_world.world, node_preset);
1582 lilv_node_free(node_bundle);
1583 lilv_node_free(node_preset);
1584 lilv_node_free(plug_name);
1589 LV2Plugin::do_remove_preset(string name)
1591 #ifdef HAVE_LILV_0_21_3
1592 /* Look up preset record by label (FIXME: ick, label as ID) */
1593 const PresetRecord* r = preset_by_label(name);
1598 /* Load a LilvState for the preset. */
1599 LilvWorld* world = _world.world;
1600 LilvNode* pset = lilv_new_uri(world, r->uri.c_str());
1601 LilvState* state = lilv_state_new_from_world(world, _uri_map.urid_map(), pset);
1603 lilv_node_free(pset);
1607 /* Unload preset from world. */
1608 lilv_world_unload_resource(world, pset);
1610 /* Delete it from the file system. This will remove the preset file and the entry
1611 from the manifest. If this results in an empty manifest (i.e. the
1612 preset is the only thing in the bundle), then the bundle is removed. */
1613 lilv_state_delete(world, state);
1615 lilv_state_free(state);
1616 lilv_node_free(pset);
1618 /* Without lilv_state_delete(), we could delete the preset file, but this
1619 would leave a broken bundle/manifest around, so the preset would still
1620 be visible, but broken. Naively deleting a bundle is too dangerous, so
1621 we simply do not support preset deletion with older Lilv */
1625 LV2Plugin::has_editor() const
1627 return _impl->ui != NULL;
1631 LV2Plugin::has_message_output() const
1633 for (uint32_t i = 0; i < num_ports(); ++i) {
1634 if ((_port_flags[i] & PORT_SEQUENCE) &&
1635 (_port_flags[i] & PORT_OUTPUT)) {
1643 LV2Plugin::write_to(RingBuffer<uint8_t>* dest,
1647 const uint8_t* body)
1649 const uint32_t buf_size = sizeof(UIMessage) + size;
1650 vector<uint8_t> buf(buf_size);
1652 UIMessage* msg = (UIMessage*)&buf[0];
1654 msg->protocol = protocol;
1656 memcpy(msg + 1, body, size);
1658 return (dest->write(&buf[0], buf_size) == buf_size);
1662 LV2Plugin::write_from_ui(uint32_t index,
1665 const uint8_t* body)
1668 size_t rbs = _session.engine().raw_buffer_size(DataType::MIDI) * NBUFS;
1669 /* buffer data communication from plugin UI to plugin instance.
1670 * this buffer needs to potentially hold
1671 * (port's minimumSize) * (audio-periods) / (UI-periods)
1674 * e.g 48kSPS / 128fpp -> audio-periods = 375 Hz
1675 * ui-periods = 25 Hz (SuperRapidScreenUpdate)
1676 * default minimumSize = 32K (see LV2Plugin::allocate_atom_event_buffers()
1678 * it is NOT safe to overflow (msg.size will be misinterpreted)
1680 uint32_t bufsiz = 32768;
1681 if (_atom_ev_buffers && _atom_ev_buffers[0]) {
1682 bufsiz = lv2_evbuf_get_capacity(_atom_ev_buffers[0]);
1684 int fact = ceilf(_session.frame_rate () / 3000.f);
1685 rbs = max((size_t) bufsiz * std::max (8, fact), rbs);
1686 _from_ui = new RingBuffer<uint8_t>(rbs);
1689 if (!write_to(_from_ui, index, protocol, size, body)) {
1690 error << "Error writing from UI to plugin" << endmsg;
1697 LV2Plugin::write_to_ui(uint32_t index,
1700 const uint8_t* body)
1702 if (!write_to(_to_ui, index, protocol, size, body)) {
1703 error << "Error writing from plugin to UI" << endmsg;
1710 forge_variant(LV2_Atom_Forge* forge, const Variant& value)
1712 switch (value.type()) {
1713 case Variant::NOTHING:
1715 case Variant::BEATS:
1716 // No atom type for this, just forge a double
1717 lv2_atom_forge_double(forge, value.get_beats().to_double());
1720 lv2_atom_forge_bool(forge, value.get_bool());
1722 case Variant::DOUBLE:
1723 lv2_atom_forge_double(forge, value.get_double());
1725 case Variant::FLOAT:
1726 lv2_atom_forge_float(forge, value.get_float());
1729 lv2_atom_forge_int(forge, value.get_int());
1732 lv2_atom_forge_long(forge, value.get_long());
1735 lv2_atom_forge_path(
1736 forge, value.get_path().c_str(), value.get_path().size());
1738 case Variant::STRING:
1739 lv2_atom_forge_string(
1740 forge, value.get_string().c_str(), value.get_string().size());
1744 forge, value.get_uri().c_str(), value.get_uri().size());
1749 /** Get a variant type from a URI, return false iff no match found. */
1751 uri_to_variant_type(const std::string& uri, Variant::Type& type)
1753 if (uri == LV2_ATOM__Bool) {
1754 type = Variant::BOOL;
1755 } else if (uri == LV2_ATOM__Double) {
1756 type = Variant::DOUBLE;
1757 } else if (uri == LV2_ATOM__Float) {
1758 type = Variant::FLOAT;
1759 } else if (uri == LV2_ATOM__Int) {
1760 type = Variant::INT;
1761 } else if (uri == LV2_ATOM__Long) {
1762 type = Variant::LONG;
1763 } else if (uri == LV2_ATOM__Path) {
1764 type = Variant::PATH;
1765 } else if (uri == LV2_ATOM__String) {
1766 type = Variant::STRING;
1767 } else if (uri == LV2_ATOM__URI) {
1768 type = Variant::URI;
1776 LV2Plugin::set_property(uint32_t key, const Variant& value)
1778 if (_patch_port_in_index == (uint32_t)-1) {
1779 error << "LV2: set_property called with unset patch_port_in_index" << endmsg;
1781 } else if (value.type() == Variant::NOTHING) {
1782 error << "LV2: set_property called with void value" << endmsg;
1786 // Set up forge to write to temporary buffer on the stack
1787 LV2_Atom_Forge* forge = &_impl->ui_forge;
1788 LV2_Atom_Forge_Frame frame;
1789 uint8_t buf[PATH_MAX]; // Ought to be enough for anyone...
1791 lv2_atom_forge_set_buffer(forge, buf, sizeof(buf));
1793 // Serialize patch:Set message to set property
1794 #ifdef HAVE_LV2_1_10_0
1795 lv2_atom_forge_object(forge, &frame, 0, _uri_map.urids.patch_Set);
1796 lv2_atom_forge_key(forge, _uri_map.urids.patch_property);
1797 lv2_atom_forge_urid(forge, key);
1798 lv2_atom_forge_key(forge, _uri_map.urids.patch_value);
1800 lv2_atom_forge_blank(forge, &frame, 0, _uri_map.urids.patch_Set);
1801 lv2_atom_forge_property_head(forge, _uri_map.urids.patch_property, 0);
1802 lv2_atom_forge_urid(forge, key);
1803 lv2_atom_forge_property_head(forge, _uri_map.urids.patch_value, 0);
1806 forge_variant(forge, value);
1808 // Write message to UI=>Plugin ring
1809 const LV2_Atom* const atom = (const LV2_Atom*)buf;
1810 write_from_ui(_patch_port_in_index,
1811 _uri_map.urids.atom_eventTransfer,
1812 lv2_atom_total_size(atom),
1813 (const uint8_t*)atom);
1816 const ParameterDescriptor&
1817 LV2Plugin::get_property_descriptor(uint32_t id) const
1819 PropertyDescriptors::const_iterator p = _property_descriptors.find(id);
1820 if (p != _property_descriptors.end()) {
1823 return Plugin::get_property_descriptor(id);
1827 load_parameter_descriptor_units(LilvWorld* lworld, ParameterDescriptor& desc, const LilvNodes* units)
1829 if (lilv_nodes_contains(units, _world.units_midiNote)) {
1830 desc.unit = ParameterDescriptor::MIDI_NOTE;
1831 } else if (lilv_nodes_contains(units, _world.units_db)) {
1832 desc.unit = ParameterDescriptor::DB;
1833 } else if (lilv_nodes_contains(units, _world.units_hz)) {
1834 desc.unit = ParameterDescriptor::HZ;
1836 if (lilv_nodes_size(units) > 0) {
1837 const LilvNode* unit = lilv_nodes_get_first(units);
1838 LilvNode* render = get_value(lworld, unit, _world.units_render);
1840 desc.print_fmt = lilv_node_as_string(render);
1841 /* override lilv's default "%f" format */
1842 if (desc.integer_step) {
1843 replace_all (desc.print_fmt, "%f", "%.0f");
1844 } else if (desc.upper - desc.lower >= 1000) {
1845 replace_all (desc.print_fmt, "%f", "%.1f");
1846 } else if (desc.upper - desc.lower >= 100) {
1847 replace_all (desc.print_fmt, "%f", "%.2f");
1849 replace_all (desc.print_fmt, "%f", "%.3f");
1851 lilv_node_free(render);
1857 load_parameter_descriptor(LV2World& world,
1858 ParameterDescriptor& desc,
1859 Variant::Type datatype,
1860 const LilvNode* subject)
1862 LilvWorld* lworld = _world.world;
1863 LilvNode* label = get_value(lworld, subject, _world.rdfs_label);
1864 LilvNode* def = get_value(lworld, subject, _world.lv2_default);
1865 LilvNode* minimum = get_value(lworld, subject, _world.lv2_minimum);
1866 LilvNode* maximum = get_value(lworld, subject, _world.lv2_maximum);
1867 LilvNodes* units = lilv_world_find_nodes(lworld, subject, _world.units_unit, NULL);
1869 desc.label = lilv_node_as_string(label);
1872 if (lilv_node_is_float(def)) {
1873 desc.normal = lilv_node_as_float(def);
1874 } else if (lilv_node_is_int(def)) {
1875 desc.normal = lilv_node_as_int(def);
1879 if (lilv_node_is_float(minimum)) {
1880 desc.lower = lilv_node_as_float(minimum);
1881 } else if (lilv_node_is_int(minimum)) {
1882 desc.lower = lilv_node_as_int(minimum);
1886 if (lilv_node_is_float(maximum)) {
1887 desc.upper = lilv_node_as_float(maximum);
1888 } else if (lilv_node_is_int(maximum)) {
1889 desc.upper = lilv_node_as_int(maximum);
1892 load_parameter_descriptor_units(lworld, desc, units);
1893 desc.datatype = datatype;
1894 desc.toggled |= datatype == Variant::BOOL;
1895 desc.integer_step |= datatype == Variant::INT || datatype == Variant::LONG;
1896 desc.update_steps();
1898 lilv_nodes_free(units);
1899 lilv_node_free(label);
1900 lilv_node_free(def);
1901 lilv_node_free(minimum);
1902 lilv_node_free(maximum);
1906 LV2Plugin::load_supported_properties(PropertyDescriptors& descs)
1908 LilvWorld* lworld = _world.world;
1909 const LilvNode* subject = lilv_plugin_get_uri(_impl->plugin);
1910 LilvNodes* properties = lilv_world_find_nodes(
1911 lworld, subject, _world.patch_writable, NULL);
1912 LILV_FOREACH(nodes, p, properties) {
1913 // Get label and range
1914 const LilvNode* prop = lilv_nodes_get(properties, p);
1915 LilvNode* range = get_value(lworld, prop, _world.rdfs_range);
1917 warning << string_compose(_("LV2: property <%1> has no range datatype, ignoring"),
1918 lilv_node_as_uri(prop)) << endmsg;
1922 // Convert range to variant type (TODO: support for multiple range types)
1923 Variant::Type datatype;
1924 if (!uri_to_variant_type(lilv_node_as_uri(range), datatype)) {
1925 error << string_compose(_("LV2: property <%1> has unsupported datatype <%1>"),
1926 lilv_node_as_uri(prop), lilv_node_as_uri(range)) << endmsg;
1930 // Add description to result
1931 ParameterDescriptor desc;
1932 desc.key = _uri_map.uri_to_id(lilv_node_as_uri(prop));
1933 desc.datatype = datatype;
1934 load_parameter_descriptor(_world, desc, datatype, prop);
1935 descs.insert(std::make_pair(desc.key, desc));
1937 lilv_node_free(range);
1939 lilv_nodes_free(properties);
1943 LV2Plugin::announce_property_values()
1945 if (_patch_port_in_index == (uint32_t)-1) {
1949 // Set up forge to write to temporary buffer on the stack
1950 LV2_Atom_Forge* forge = &_impl->ui_forge;
1951 LV2_Atom_Forge_Frame frame;
1952 uint8_t buf[PATH_MAX]; // Ought to be enough for anyone...
1954 lv2_atom_forge_set_buffer(forge, buf, sizeof(buf));
1956 // Serialize patch:Get message with no subject (implicitly plugin instance)
1957 #ifdef HAVE_LV2_1_10_0
1958 lv2_atom_forge_object(forge, &frame, 0, _uri_map.urids.patch_Get);
1960 lv2_atom_forge_blank(forge, &frame, 0, _uri_map.urids.patch_Get);
1963 // Write message to UI=>Plugin ring
1964 const LV2_Atom* const atom = (const LV2_Atom*)buf;
1965 write_from_ui(_patch_port_in_index,
1966 _uri_map.urids.atom_eventTransfer,
1967 lv2_atom_total_size(atom),
1968 (const uint8_t*)atom);
1972 LV2Plugin::enable_ui_emission()
1975 /* see note in LV2Plugin::write_from_ui() */
1976 uint32_t bufsiz = 32768;
1977 if (_atom_ev_buffers && _atom_ev_buffers[0]) {
1978 bufsiz = lv2_evbuf_get_capacity(_atom_ev_buffers[0]);
1980 size_t rbs = _session.engine().raw_buffer_size(DataType::MIDI) * NBUFS;
1981 rbs = max((size_t) bufsiz * 8, rbs);
1982 _to_ui = new RingBuffer<uint8_t>(rbs);
1987 LV2Plugin::emit_to_ui(void* controller, UIMessageSink sink)
1993 uint32_t read_space = _to_ui->read_space();
1994 while (read_space > sizeof(UIMessage)) {
1996 if (_to_ui->read((uint8_t*)&msg, sizeof(msg)) != sizeof(msg)) {
1997 error << "Error reading from Plugin=>UI RingBuffer" << endmsg;
2000 vector<uint8_t> body(msg.size);
2001 if (_to_ui->read(&body[0], msg.size) != msg.size) {
2002 error << "Error reading from Plugin=>UI RingBuffer" << endmsg;
2006 sink(controller, msg.index, msg.size, msg.protocol, &body[0]);
2008 read_space -= sizeof(msg) + msg.size;
2013 LV2Plugin::work(Worker& worker, uint32_t size, const void* data)
2015 Glib::Threads::Mutex::Lock lm(_work_mutex);
2016 return _impl->work_iface->work(
2017 _impl->instance->lv2_handle, work_respond, &worker, size, data);
2021 LV2Plugin::work_response(uint32_t size, const void* data)
2023 return _impl->work_iface->work_response(
2024 _impl->instance->lv2_handle, size, data);
2028 LV2Plugin::set_insert_id(PBD::ID id)
2030 if (_insert_id == "0") {
2032 } else if (_insert_id != id) {
2033 lilv_state_free(_impl->state);
2034 _impl->state = NULL;
2040 LV2Plugin::set_state_dir (const std::string& d)
2042 _plugin_state_dir = d;
2046 LV2Plugin::set_state(const XMLNode& node, int version)
2049 XMLNodeConstIterator iter;
2053 if (node.name() != state_node_name()) {
2054 error << _("Bad node sent to LV2Plugin::set_state") << endmsg;
2058 #ifndef NO_PLUGIN_STATE
2060 if (version < 3000) {
2061 nodes = node.children("port");
2063 nodes = node.children("Port");
2066 for (iter = nodes.begin(); iter != nodes.end(); ++iter) {
2071 if (!child->get_property("symbol", sym)) {
2072 warning << _("LV2: port has no symbol, ignored") << endmsg;
2076 map<string, uint32_t>::iterator i = _port_indices.find(sym);
2080 if (i != _port_indices.end()) {
2081 port_id = i->second;
2083 warning << _("LV2: port has unknown index, ignored") << endmsg;
2088 if (!child->get_property("value", val)) {
2089 warning << _("LV2: port has no value, ignored") << endmsg;
2093 set_parameter(port_id, val);
2096 std::string template_dir;
2097 if (node.get_property("template-dir", template_dir)) {
2098 set_state_dir (template_dir);
2102 std::string state_dir;
2103 if (node.get_property("state-dir", state_dir) != 0) {
2104 if (sscanf(state_dir.c_str(), "state%u", &_state_version) != 1) {
2105 error << string_compose(
2106 "LV2: failed to parse state version from \"%1\"",
2107 state_dir) << endmsg;
2110 std::string state_file = Glib::build_filename(
2112 Glib::build_filename(state_dir, "state.ttl"));
2114 LilvState* state = lilv_state_new_from_file(
2115 _world.world, _uri_map.urid_map(), NULL, state_file.c_str());
2117 lilv_state_restore(state, _impl->instance, NULL, NULL, 0, NULL);
2118 lilv_state_free(_impl->state);
2119 _impl->state = state;
2122 if (!_plugin_state_dir.empty ()) {
2123 // force save with session, next time (increment counter)
2124 lilv_state_free (_impl->state);
2125 _impl->state = NULL;
2129 latency_compute_run();
2132 return Plugin::set_state(node, version);
2136 LV2Plugin::get_parameter_descriptor(uint32_t which, ParameterDescriptor& desc) const
2138 const LilvPort* port = lilv_plugin_get_port_by_index(_impl->plugin, which);
2140 error << string_compose("LV2: get descriptor of non-existent port %1", which)
2145 LilvNodes* portunits;
2146 LilvNode *def, *min, *max;
2147 lilv_port_get_range(_impl->plugin, port, &def, &min, &max);
2148 portunits = lilv_port_get_value(_impl->plugin, port, _world.units_unit);
2150 LilvNode* steps = lilv_port_get(_impl->plugin, port, _world.ext_rangeSteps);
2152 // TODO: Once we can rely on lilv 0.18.0 being present,
2153 // load_parameter_descriptor() can be used for ports as well
2154 desc.integer_step = lilv_port_has_property(_impl->plugin, port, _world.lv2_integer);
2155 desc.toggled = lilv_port_has_property(_impl->plugin, port, _world.lv2_toggled);
2156 desc.logarithmic = lilv_port_has_property(_impl->plugin, port, _world.ext_logarithmic);
2157 desc.sr_dependent = lilv_port_has_property(_impl->plugin, port, _world.lv2_sampleRate);
2158 desc.label = lilv_node_as_string(lilv_port_get_name(_impl->plugin, port));
2159 desc.normal = def ? lilv_node_as_float(def) : 0.0f;
2160 desc.lower = min ? lilv_node_as_float(min) : 0.0f;
2161 desc.upper = max ? lilv_node_as_float(max) : 1.0f;
2162 load_parameter_descriptor_units(_world.world, desc, portunits);
2164 if (desc.sr_dependent) {
2165 desc.lower *= _session.frame_rate ();
2166 desc.upper *= _session.frame_rate ();
2169 desc.enumeration = lilv_port_has_property(_impl->plugin, port, _world.lv2_enumeration);
2170 desc.scale_points = get_scale_points(which);
2173 desc.rangesteps = lilv_node_as_float (steps);
2176 desc.update_steps();
2178 lilv_node_free(def);
2179 lilv_node_free(min);
2180 lilv_node_free(max);
2181 lilv_node_free(steps);
2182 lilv_nodes_free(portunits);
2187 Plugin::IOPortDescription
2188 LV2Plugin::describe_io_port (ARDOUR::DataType dt, bool input, uint32_t id) const
2190 PortFlags match = 0;
2192 case DataType::AUDIO:
2195 case DataType::MIDI:
2196 match = PORT_SEQUENCE | PORT_MIDI; // ignore old PORT_EVENT
2199 return Plugin::IOPortDescription ("?");
2203 match |= PORT_INPUT;
2205 match |= PORT_OUTPUT;
2209 uint32_t idx = UINT32_MAX;
2211 uint32_t const num_ports = parameter_count();
2212 for (uint32_t port_index = 0; port_index < num_ports; ++port_index) {
2213 PortFlags flags = _port_flags[port_index];
2214 if ((flags & match) == match) {
2221 if (idx == UINT32_MAX) {
2222 return Plugin::IOPortDescription ("?");
2225 const LilvPort* pport = lilv_plugin_get_port_by_index (_impl->plugin, idx);
2227 LilvNode* name = lilv_port_get_name(_impl->plugin, pport);
2228 Plugin::IOPortDescription iod (lilv_node_as_string (name));
2229 lilv_node_free(name);
2231 /* get the port's pg:group */
2232 LilvNodes* groups = lilv_port_get_value (_impl->plugin, pport, _world.groups_group);
2233 if (lilv_nodes_size (groups) > 0) {
2234 const LilvNode* group = lilv_nodes_get_first (groups);
2235 LilvNodes* grouplabel = lilv_world_find_nodes (_world.world, group, _world.rdfs_label, NULL);
2237 /* get the name of the port-group */
2238 if (lilv_nodes_size (grouplabel) > 0) {
2239 const LilvNode* grpname = lilv_nodes_get_first (grouplabel);
2240 iod.group_name = lilv_node_as_string (grpname);
2242 lilv_nodes_free (grouplabel);
2244 /* get all port designations.
2245 * we're interested in e.g. lv2:designation pg:right */
2246 LilvNodes* designations = lilv_port_get_value (_impl->plugin, pport, _world.lv2_designation);
2247 if (lilv_nodes_size (designations) > 0) {
2248 /* get all pg:elements of the pg:group */
2249 LilvNodes* group_childs = lilv_world_find_nodes (_world.world, group, _world.groups_element, NULL);
2250 if (lilv_nodes_size (group_childs) > 0) {
2251 /* iterate over all port designations .. */
2252 LILV_FOREACH (nodes, i, designations) {
2253 const LilvNode* designation = lilv_nodes_get (designations, i);
2254 /* match the lv2:designation's element against the port-group's element */
2255 LILV_FOREACH (nodes, j, group_childs) {
2256 const LilvNode* group_element = lilv_nodes_get (group_childs, j);
2257 LilvNodes* elem = lilv_world_find_nodes (_world.world, group_element, _world.lv2_designation, designation);
2258 /* found it. Now look up the index (channel-number) of the pg:Element */
2259 if (lilv_nodes_size (elem) > 0) {
2260 LilvNodes* idx = lilv_world_find_nodes (_world.world, lilv_nodes_get_first (elem), _world.lv2_index, NULL);
2261 if (lilv_node_is_int (lilv_nodes_get_first (idx))) {
2262 iod.group_channel = lilv_node_as_int(lilv_nodes_get_first (idx));
2269 lilv_nodes_free (groups);
2270 lilv_nodes_free (designations);
2273 if (lilv_port_has_property(_impl->plugin, pport, _world.lv2_isSideChain)) {
2274 iod.is_sidechain = true;
2280 LV2Plugin::describe_parameter(Evoral::Parameter which)
2282 if (( which.type() == PluginAutomation) && ( which.id() < parameter_count()) ) {
2284 if (lilv_port_has_property(_impl->plugin,
2285 lilv_plugin_get_port_by_index(_impl->plugin, which.id()), _world.ext_notOnGUI)) {
2286 return X_("hidden");
2289 if (lilv_port_has_property(_impl->plugin,
2290 lilv_plugin_get_port_by_index(_impl->plugin, which.id()), _world.lv2_freewheeling)) {
2291 return X_("hidden");
2294 if (lilv_port_has_property(_impl->plugin,
2295 lilv_plugin_get_port_by_index(_impl->plugin, which.id()), _world.lv2_reportsLatency)) {
2296 return X_("latency");
2299 LilvNode* name = lilv_port_get_name(_impl->plugin,
2300 lilv_plugin_get_port_by_index(_impl->plugin, which.id()));
2301 string ret(lilv_node_as_string(name));
2302 lilv_node_free(name);
2310 LV2Plugin::max_latency () const
2312 return _max_latency;
2316 LV2Plugin::signal_latency() const
2318 if (_latency_control_port) {
2319 return (framecnt_t)floor(*_latency_control_port);
2325 set<Evoral::Parameter>
2326 LV2Plugin::automatable() const
2328 set<Evoral::Parameter> ret;
2330 for (uint32_t i = 0; i < parameter_count(); ++i) {
2331 if (parameter_is_input(i) && parameter_is_control(i) && !(_port_flags[i] & PORT_NOAUTO)) {
2332 ret.insert(ret.end(), Evoral::Parameter(PluginAutomation, 0, i));
2336 for (PropertyDescriptors::const_iterator p = _property_descriptors.begin();
2337 p != _property_descriptors.end();
2339 ret.insert(ret.end(), Evoral::Parameter(PluginPropertyAutomation, 0, p->first));
2345 LV2Plugin::set_automation_control (uint32_t i, boost::shared_ptr<AutomationControl> c)
2347 if ((_port_flags[i] & (PORT_CTRLED | PORT_CTRLER))) {
2348 DEBUG_TRACE(DEBUG::LV2Automate, string_compose ("Ctrl Port %1\n", i));
2349 _ctrl_map [i] = AutomationCtrlPtr (new AutomationCtrl(c));
2353 LV2Plugin::AutomationCtrlPtr
2354 LV2Plugin::get_automation_control (uint32_t i)
2356 if (_ctrl_map.find (i) == _ctrl_map.end()) {
2357 return AutomationCtrlPtr ();
2359 return _ctrl_map[i];
2363 LV2Plugin::activate()
2365 DEBUG_TRACE(DEBUG::LV2, string_compose("%1 activate\n", name()));
2367 if (!_was_activated) {
2368 lilv_instance_activate(_impl->instance);
2369 _was_activated = true;
2374 LV2Plugin::deactivate()
2376 DEBUG_TRACE(DEBUG::LV2, string_compose("%1 deactivate\n", name()));
2378 if (_was_activated) {
2379 lilv_instance_deactivate(_impl->instance);
2380 _was_activated = false;
2385 LV2Plugin::cleanup()
2387 DEBUG_TRACE(DEBUG::LV2, string_compose("%1 cleanup\n", name()));
2390 lilv_instance_free(_impl->instance);
2391 _impl->instance = NULL;
2395 LV2Plugin::allocate_atom_event_buffers()
2397 /* reserve local scratch buffers for ATOM event-queues */
2398 const LilvPlugin* p = _impl->plugin;
2400 /* count non-MIDI atom event-ports
2401 * TODO: nicely ask drobilla to make a lilv_ call for that
2403 int count_atom_out = 0;
2404 int count_atom_in = 0;
2405 int minimumSize = 32768; // TODO use a per-port minimum-size
2406 for (uint32_t i = 0; i < lilv_plugin_get_num_ports(p); ++i) {
2407 const LilvPort* port = lilv_plugin_get_port_by_index(p, i);
2408 if (lilv_port_is_a(p, port, _world.atom_AtomPort)) {
2409 LilvNodes* buffer_types = lilv_port_get_value(
2410 p, port, _world.atom_bufferType);
2411 LilvNodes* atom_supports = lilv_port_get_value(
2412 p, port, _world.atom_supports);
2414 if (lilv_nodes_contains(buffer_types, _world.atom_Sequence)) {
2415 if (lilv_port_is_a(p, port, _world.lv2_InputPort)) {
2418 if (lilv_port_is_a(p, port, _world.lv2_OutputPort)) {
2421 LilvNodes* min_size_v = lilv_port_get_value(_impl->plugin, port, _world.rsz_minimumSize);
2422 LilvNode* min_size = min_size_v ? lilv_nodes_get_first(min_size_v) : NULL;
2423 if (min_size && lilv_node_is_int(min_size)) {
2424 minimumSize = std::max(minimumSize, lilv_node_as_int(min_size));
2426 lilv_nodes_free(min_size_v);
2428 lilv_nodes_free(buffer_types);
2429 lilv_nodes_free(atom_supports);
2433 DEBUG_TRACE(DEBUG::LV2, string_compose("%1 need buffers for %2 atom-in and %3 atom-out event-ports\n",
2434 name(), count_atom_in, count_atom_out));
2436 const int total_atom_buffers = (count_atom_in + count_atom_out);
2437 if (_atom_ev_buffers || total_atom_buffers == 0) {
2441 DEBUG_TRACE(DEBUG::LV2, string_compose("allocate %1 atom_ev_buffers of %2 bytes\n", total_atom_buffers, minimumSize));
2442 _atom_ev_buffers = (LV2_Evbuf**) malloc((total_atom_buffers + 1) * sizeof(LV2_Evbuf*));
2443 for (int i = 0; i < total_atom_buffers; ++i ) {
2444 _atom_ev_buffers[i] = lv2_evbuf_new(minimumSize, LV2_EVBUF_ATOM,
2445 _uri_map.urids.atom_Chunk, _uri_map.urids.atom_Sequence);
2447 _atom_ev_buffers[total_atom_buffers] = 0;
2451 /** Write an ardour position/time/tempo/meter as an LV2 event.
2452 * @return true on success.
2455 write_position(LV2_Atom_Forge* forge,
2457 const TempoMetric& t,
2458 Timecode::BBT_Time& bbt,
2461 framepos_t position,
2464 const URIMap::URIDs& urids = URIMap::instance().urids;
2466 uint8_t pos_buf[256];
2467 lv2_atom_forge_set_buffer(forge, pos_buf, sizeof(pos_buf));
2468 LV2_Atom_Forge_Frame frame;
2469 #ifdef HAVE_LV2_1_10_0
2470 lv2_atom_forge_object(forge, &frame, 0, urids.time_Position);
2471 lv2_atom_forge_key(forge, urids.time_frame);
2472 lv2_atom_forge_long(forge, position);
2473 lv2_atom_forge_key(forge, urids.time_speed);
2474 lv2_atom_forge_float(forge, speed);
2475 lv2_atom_forge_key(forge, urids.time_barBeat);
2476 lv2_atom_forge_float(forge, bbt.beats - 1 +
2477 (bbt.ticks / Timecode::BBT_Time::ticks_per_beat));
2478 lv2_atom_forge_key(forge, urids.time_bar);
2479 lv2_atom_forge_long(forge, bbt.bars - 1);
2480 lv2_atom_forge_key(forge, urids.time_beatUnit);
2481 lv2_atom_forge_int(forge, t.meter().note_divisor());
2482 lv2_atom_forge_key(forge, urids.time_beatsPerBar);
2483 lv2_atom_forge_float(forge, t.meter().divisions_per_bar());
2484 lv2_atom_forge_key(forge, urids.time_beatsPerMinute);
2485 lv2_atom_forge_float(forge, bpm);
2487 lv2_atom_forge_blank(forge, &frame, 1, urids.time_Position);
2488 lv2_atom_forge_property_head(forge, urids.time_frame, 0);
2489 lv2_atom_forge_long(forge, position);
2490 lv2_atom_forge_property_head(forge, urids.time_speed, 0);
2491 lv2_atom_forge_float(forge, speed);
2492 lv2_atom_forge_property_head(forge, urids.time_barBeat, 0);
2493 lv2_atom_forge_float(forge, bbt.beats - 1 +
2494 (bbt.ticks / Timecode::BBT_Time::ticks_per_beat));
2495 lv2_atom_forge_property_head(forge, urids.time_bar, 0);
2496 lv2_atom_forge_long(forge, bbt.bars - 1);
2497 lv2_atom_forge_property_head(forge, urids.time_beatUnit, 0);
2498 lv2_atom_forge_int(forge, t.meter().note_divisor());
2499 lv2_atom_forge_property_head(forge, urids.time_beatsPerBar, 0);
2500 lv2_atom_forge_float(forge, t.meter().divisions_per_bar());
2501 lv2_atom_forge_property_head(forge, urids.time_beatsPerMinute, 0);
2502 lv2_atom_forge_float(forge, bpm);
2505 LV2_Evbuf_Iterator end = lv2_evbuf_end(buf);
2506 const LV2_Atom* const atom = (const LV2_Atom*)pos_buf;
2507 return lv2_evbuf_write(&end, offset, 0, atom->type, atom->size,
2508 (const uint8_t*)(atom + 1));
2512 LV2Plugin::connect_and_run(BufferSet& bufs,
2513 framepos_t start, framepos_t end, double speed,
2514 ChanMapping in_map, ChanMapping out_map,
2515 pframes_t nframes, framecnt_t offset)
2517 DEBUG_TRACE(DEBUG::LV2, string_compose("%1 run %2 offset %3\n", name(), nframes, offset));
2518 Plugin::connect_and_run(bufs, start, end, speed, in_map, out_map, nframes, offset);
2520 cycles_t then = get_cycles();
2522 TempoMap& tmap = _session.tempo_map();
2523 Metrics::const_iterator metric_i = tmap.metrics_end();
2524 TempoMetric tmetric = tmap.metric_at(start, &metric_i);
2526 if (_freewheel_control_port) {
2527 *_freewheel_control_port = _session.engine().freewheeling() ? 1.f : 0.f;
2530 if (_bpm_control_port) {
2531 *_bpm_control_port = tmap.tempo_at_frame (start).note_types_per_minute();
2535 if (_can_write_automation && start != _next_cycle_start) {
2536 // add guard-points after locating
2537 for (AutomationCtrlMap::iterator i = _ctrl_map.begin(); i != _ctrl_map.end(); ++i) {
2538 i->second->guard = true;
2543 ChanCount bufs_count;
2544 bufs_count.set(DataType::AUDIO, 1);
2545 bufs_count.set(DataType::MIDI, 1);
2546 BufferSet& silent_bufs = _session.get_silent_buffers(bufs_count);
2547 BufferSet& scratch_bufs = _session.get_scratch_buffers(bufs_count);
2548 uint32_t const num_ports = parameter_count();
2549 uint32_t const nil_index = std::numeric_limits<uint32_t>::max();
2551 uint32_t audio_in_index = 0;
2552 uint32_t audio_out_index = 0;
2553 uint32_t midi_in_index = 0;
2554 uint32_t midi_out_index = 0;
2555 uint32_t atom_port_index = 0;
2556 for (uint32_t port_index = 0; port_index < num_ports; ++port_index) {
2558 uint32_t index = nil_index;
2559 PortFlags flags = _port_flags[port_index];
2561 if (flags & PORT_AUDIO) {
2562 if (flags & PORT_INPUT) {
2563 index = in_map.get(DataType::AUDIO, audio_in_index++, &valid);
2565 ? bufs.get_audio(index).data(offset)
2566 : silent_bufs.get_audio(0).data(offset);
2568 index = out_map.get(DataType::AUDIO, audio_out_index++, &valid);
2570 ? bufs.get_audio(index).data(offset)
2571 : scratch_bufs.get_audio(0).data(offset);
2573 } else if (flags & (PORT_EVENT|PORT_SEQUENCE)) {
2574 /* FIXME: The checks here for bufs.count().n_midi() > index shouldn't
2575 be necessary, but the mapping is illegal in some cases. Ideally
2576 that should be fixed, but this is easier...
2578 if (flags & PORT_MIDI) {
2579 if (flags & PORT_INPUT) {
2580 index = in_map.get(DataType::MIDI, midi_in_index++, &valid);
2582 index = out_map.get(DataType::MIDI, midi_out_index++, &valid);
2584 if (valid && bufs.count().n_midi() > index) {
2585 /* Note, ensure_lv2_bufsize() is not RT safe!
2586 * However free()/alloc() is only called if a
2587 * plugin requires a rsz:minimumSize buffersize
2588 * and the existing buffer if smaller.
2590 bufs.ensure_lv2_bufsize((flags & PORT_INPUT), index, _port_minimumSize[port_index]);
2591 _ev_buffers[port_index] = bufs.get_lv2_midi(
2592 (flags & PORT_INPUT), index, (flags & PORT_EVENT));
2594 } else if ((flags & PORT_POSITION) && (flags & PORT_INPUT)) {
2595 lv2_evbuf_reset(_atom_ev_buffers[atom_port_index], true);
2596 _ev_buffers[port_index] = _atom_ev_buffers[atom_port_index++];
2600 if (valid && (flags & PORT_INPUT)) {
2601 if ((flags & PORT_POSITION)) {
2602 Timecode::BBT_Time bbt (tmap.bbt_at_frame (start));
2603 double bpm = tmap.tempo_at_frame (start).note_types_per_minute();
2604 double beatpos = (bbt.bars - 1) * tmetric.meter().divisions_per_bar()
2606 + (bbt.ticks / Timecode::BBT_Time::ticks_per_beat);
2607 beatpos *= tmetric.meter().note_divisor() / 4.0;
2608 if (start != _next_cycle_start ||
2609 speed != _next_cycle_speed ||
2610 rint (1000 * beatpos) != rint(1000 * _next_cycle_beat) ||
2611 bpm != _current_bpm) {
2612 // Transport or Tempo has changed, write position at cycle start
2613 write_position(&_impl->forge, _ev_buffers[port_index],
2614 tmetric, bbt, speed, bpm, start, 0);
2618 // Get MIDI iterator range (empty range if no MIDI)
2619 MidiBuffer::iterator m = (index != nil_index)
2620 ? bufs.get_midi(index).begin()
2621 : silent_bufs.get_midi(0).end();
2622 MidiBuffer::iterator m_end = (index != nil_index)
2623 ? bufs.get_midi(index).end()
2626 // Now merge MIDI and any transport events into the buffer
2627 const uint32_t type = _uri_map.urids.midi_MidiEvent;
2628 const framepos_t tend = end;
2630 while (m != m_end || (metric_i != tmap.metrics_end() &&
2631 (*metric_i)->frame() < tend)) {
2632 MetricSection* metric = (metric_i != tmap.metrics_end())
2634 if (m != m_end && (!metric || metric->frame() > (*m).time())) {
2635 const Evoral::Event<framepos_t> ev(*m, false);
2636 if (ev.time() < nframes) {
2637 LV2_Evbuf_Iterator eend = lv2_evbuf_end(_ev_buffers[port_index]);
2638 lv2_evbuf_write(&eend, ev.time(), 0, type, ev.size(), ev.buffer());
2642 tmetric.set_metric(metric);
2643 Timecode::BBT_Time bbt;
2644 bbt = tmap.bbt_at_frame (metric->frame());
2645 double bpm = tmap.tempo_at_frame (start/*XXX*/).note_types_per_minute();
2646 write_position(&_impl->forge, _ev_buffers[port_index],
2647 tmetric, bbt, speed, bpm,
2649 metric->frame() - start);
2653 } else if (!valid) {
2654 // Nothing we understand or care about, connect to scratch
2655 // see note for midi-buffer size above
2656 scratch_bufs.ensure_lv2_bufsize((flags & PORT_INPUT),
2657 0, _port_minimumSize[port_index]);
2658 _ev_buffers[port_index] = scratch_bufs.get_lv2_midi(
2659 (flags & PORT_INPUT), 0, (flags & PORT_EVENT));
2662 buf = lv2_evbuf_get_buffer(_ev_buffers[port_index]);
2664 continue; // Control port, leave buffer alone
2666 lilv_instance_connect_port(_impl->instance, port_index, buf);
2669 // Read messages from UI and push into appropriate buffers
2671 uint32_t read_space = _from_ui->read_space();
2672 while (read_space > sizeof(UIMessage)) {
2674 if (_from_ui->read((uint8_t*)&msg, sizeof(msg)) != sizeof(msg)) {
2675 error << "Error reading from UI=>Plugin RingBuffer" << endmsg;
2678 vector<uint8_t> body(msg.size);
2679 if (_from_ui->read(&body[0], msg.size) != msg.size) {
2680 error << "Error reading from UI=>Plugin RingBuffer" << endmsg;
2683 if (msg.protocol == URIMap::instance().urids.atom_eventTransfer) {
2684 LV2_Evbuf* buf = _ev_buffers[msg.index];
2685 LV2_Evbuf_Iterator i = lv2_evbuf_end(buf);
2686 const LV2_Atom* const atom = (const LV2_Atom*)&body[0];
2687 if (!lv2_evbuf_write(&i, nframes - 1, 0, atom->type, atom->size,
2688 (const uint8_t*)(atom + 1))) {
2689 error << "Failed to write data to LV2 event buffer\n";
2692 error << "Received unknown message type from UI" << endmsg;
2694 read_space -= sizeof(UIMessage) + msg.size;
2701 for (uint32_t port_index = 0; port_index < num_ports; ++port_index) {
2702 PortFlags flags = _port_flags[port_index];
2705 /* TODO ask drobilla about comment
2706 * "Make Ardour event buffers generic so plugins can communicate"
2707 * in libs/ardour/buffer_set.cc:310
2709 * ideally the user could choose which of the following two modes
2710 * to use (e.g. instrument/effect chains MIDI OUT vs MIDI TRHU).
2712 * This implementation follows the discussion on IRC Mar 16 2013 16:47 UTC
2713 * 16:51 < drobilla> rgareus: [..] i.e always replace with MIDI output [of LV2 plugin] if it's there
2714 * 16:52 < drobilla> rgareus: That would probably be good enough [..] to make users not complain
2715 * for quite a while at least ;)
2717 // copy output of LV2 plugin's MIDI port to Ardour MIDI buffers -- MIDI OUT
2718 if ((flags & PORT_OUTPUT) && (flags & (PORT_EVENT|PORT_SEQUENCE|PORT_MIDI))) {
2719 const uint32_t buf_index = out_map.get(
2720 DataType::MIDI, midi_out_index++, &valid);
2722 bufs.forward_lv2_midi(_ev_buffers[port_index], buf_index);
2725 // Flush MIDI (write back to Ardour MIDI buffers) -- MIDI THRU
2726 else if ((flags & PORT_OUTPUT) && (flags & (PORT_EVENT|PORT_SEQUENCE))) {
2727 const uint32_t buf_index = out_map.get(
2728 DataType::MIDI, midi_out_index++, &valid);
2730 bufs.flush_lv2_midi(true, buf_index);
2734 // Write messages to UI
2735 if ((_to_ui || _can_write_automation || _patch_port_out_index != (uint32_t)-1) &&
2736 (flags & PORT_OUTPUT) && (flags & (PORT_EVENT|PORT_SEQUENCE))) {
2737 LV2_Evbuf* buf = _ev_buffers[port_index];
2738 for (LV2_Evbuf_Iterator i = lv2_evbuf_begin(buf);
2739 lv2_evbuf_is_valid(i);
2740 i = lv2_evbuf_next(i)) {
2741 uint32_t frames, subframes, type, size;
2743 lv2_evbuf_get(i, &frames, &subframes, &type, &size, &data);
2746 // Intercept Automation Write Events
2747 if ((flags & PORT_AUTOCTRL)) {
2748 LV2_Atom* atom = (LV2_Atom*)(data - sizeof(LV2_Atom));
2749 if (atom->type == _uri_map.urids.atom_Blank ||
2750 atom->type == _uri_map.urids.atom_Object) {
2751 LV2_Atom_Object* obj = (LV2_Atom_Object*)atom;
2752 if (obj->body.otype == _uri_map.urids.auto_event) {
2753 // only if transport_rolling ??
2754 const LV2_Atom* parameter = NULL;
2755 const LV2_Atom* value = NULL;
2756 lv2_atom_object_get(obj,
2757 _uri_map.urids.auto_parameter, ¶meter,
2758 _uri_map.urids.auto_value, &value,
2760 if (parameter && value) {
2761 const uint32_t p = ((const LV2_Atom_Int*)parameter)->body;
2762 const float v = ((const LV2_Atom_Float*)value)->body;
2763 // -> add automation event..
2764 DEBUG_TRACE(DEBUG::LV2Automate,
2765 string_compose ("Event p: %1 t: %2 v: %3\n", p, frames, v));
2766 AutomationCtrlPtr c = get_automation_control (p);
2768 (c->ac->automation_state() == Touch || c->ac->automation_state() == Write)
2770 framepos_t when = std::max ((framepos_t) 0, start + frames - _current_latency);
2771 assert (start + frames - _current_latency >= 0);
2774 c->ac->list()->add (when, v, true, true);
2776 c->ac->set_double (v, when, true);
2781 else if (obj->body.otype == _uri_map.urids.auto_setup) {
2782 // TODO optional arguments, for now we assume the plugin
2783 // writes automation for its own inputs
2784 // -> put them in "touch" mode (preferably "exclusive plugin touch(TM)"
2785 for (AutomationCtrlMap::iterator i = _ctrl_map.begin(); i != _ctrl_map.end(); ++i) {
2786 if (_port_flags[i->first] & PORT_CTRLED) {
2787 DEBUG_TRACE(DEBUG::LV2Automate,
2788 string_compose ("Setup p: %1\n", i->first));
2789 i->second->ac->set_automation_state (Touch);
2793 else if (obj->body.otype == _uri_map.urids.auto_finalize) {
2794 // set [touched] parameters to "play" ??
2795 // allow plugin to change its mode (from analyze to apply)
2796 const LV2_Atom* parameter = NULL;
2797 const LV2_Atom* value = NULL;
2798 lv2_atom_object_get(obj,
2799 _uri_map.urids.auto_parameter, ¶meter,
2800 _uri_map.urids.auto_value, &value,
2802 if (parameter && value) {
2803 const uint32_t p = ((const LV2_Atom_Int*)parameter)->body;
2804 const float v = ((const LV2_Atom_Float*)value)->body;
2805 AutomationCtrlPtr c = get_automation_control (p);
2806 DEBUG_TRACE(DEBUG::LV2Automate,
2807 string_compose ("Finalize p: %1 v: %2\n", p, v));
2808 if (c && _port_flags[p] & PORT_CTRLER) {
2809 c->ac->set_value(v, Controllable::NoGroup);
2812 DEBUG_TRACE(DEBUG::LV2Automate, "Finalize\n");
2814 for (AutomationCtrlMap::iterator i = _ctrl_map.begin(); i != _ctrl_map.end(); ++i) {
2815 // guard will be false if an event was written
2816 if ((_port_flags[i->first] & PORT_CTRLED) && !i->second->guard) {
2817 DEBUG_TRACE(DEBUG::LV2Automate,
2818 string_compose ("Thin p: %1\n", i->first));
2819 i->second->ac->alist ()->thin (20);
2823 else if (obj->body.otype == _uri_map.urids.auto_start) {
2824 const LV2_Atom* parameter = NULL;
2825 lv2_atom_object_get(obj,
2826 _uri_map.urids.auto_parameter, ¶meter,
2829 const uint32_t p = ((const LV2_Atom_Int*)parameter)->body;
2830 AutomationCtrlPtr c = get_automation_control (p);
2831 DEBUG_TRACE(DEBUG::LV2Automate, string_compose ("Start Touch p: %1\n", p));
2833 c->ac->start_touch (std::max ((framepos_t)0, start - _current_latency));
2838 else if (obj->body.otype == _uri_map.urids.auto_end) {
2839 const LV2_Atom* parameter = NULL;
2840 lv2_atom_object_get(obj,
2841 _uri_map.urids.auto_parameter, ¶meter,
2844 const uint32_t p = ((const LV2_Atom_Int*)parameter)->body;
2845 AutomationCtrlPtr c = get_automation_control (p);
2846 DEBUG_TRACE(DEBUG::LV2Automate, string_compose ("End Touch p: %1\n", p));
2848 c->ac->stop_touch (std::max ((framepos_t)0, start - _current_latency));
2855 // Intercept state dirty message
2856 if (_has_state_interface /* && (flags & PORT_DIRTYMSG)*/) {
2857 LV2_Atom* atom = (LV2_Atom*)(data - sizeof(LV2_Atom));
2858 if (atom->type == _uri_map.urids.atom_Blank ||
2859 atom->type == _uri_map.urids.atom_Object) {
2860 LV2_Atom_Object* obj = (LV2_Atom_Object*)atom;
2861 if (obj->body.otype == _uri_map.urids.state_StateChanged) {
2862 _session.set_dirty ();
2867 // Intercept patch change messages to emit PropertyChanged signal
2868 if ((flags & PORT_PATCHMSG)) {
2869 LV2_Atom* atom = (LV2_Atom*)(data - sizeof(LV2_Atom));
2870 if (atom->type == _uri_map.urids.atom_Blank ||
2871 atom->type == _uri_map.urids.atom_Object) {
2872 LV2_Atom_Object* obj = (LV2_Atom_Object*)atom;
2873 if (obj->body.otype == _uri_map.urids.patch_Set) {
2874 const LV2_Atom* property = NULL;
2875 const LV2_Atom* value = NULL;
2876 lv2_atom_object_get(obj,
2877 _uri_map.urids.patch_property, &property,
2878 _uri_map.urids.patch_value, &value,
2881 if (property && value &&
2882 property->type == _uri_map.urids.atom_URID &&
2883 value->type == _uri_map.urids.atom_Path) {
2884 const uint32_t prop_id = ((const LV2_Atom_URID*)property)->body;
2885 const char* path = (const char*)LV2_ATOM_BODY_CONST(value);
2887 // Emit PropertyChanged signal for UI
2888 // TODO: This should emit the control's Changed signal
2889 PropertyChanged(prop_id, Variant(Variant::PATH, path));
2891 std::cerr << "warning: patch:Set for unknown property" << std::endl;
2897 if (!_to_ui) continue;
2898 write_to_ui(port_index, URIMap::instance().urids.atom_eventTransfer,
2899 size + sizeof(LV2_Atom),
2900 data - sizeof(LV2_Atom));
2905 cycles_t now = get_cycles();
2906 set_cycles((uint32_t)(now - then));
2908 // Update expected transport information for next cycle so we can detect changes
2909 _next_cycle_speed = speed;
2910 _next_cycle_start = end;
2913 /* keep track of lv2:timePosition like plugins can do.
2914 * Note: for no-midi plugins, we only ever send information at cycle-start,
2915 * so it needs to be realative to that.
2917 TempoMetric t = tmap.metric_at(start);
2918 _current_bpm = tmap.tempo_at_frame (start).note_types_per_minute();
2919 Timecode::BBT_Time bbt (tmap.bbt_at_frame (start));
2920 double beatpos = (bbt.bars - 1) * t.meter().divisions_per_bar()
2922 + (bbt.ticks / Timecode::BBT_Time::ticks_per_beat);
2923 beatpos *= tmetric.meter().note_divisor() / 4.0;
2924 _next_cycle_beat = beatpos + nframes * speed * _current_bpm / (60.f * _session.frame_rate());
2927 if (_latency_control_port) {
2928 framecnt_t new_latency = signal_latency ();
2929 _current_latency = new_latency;
2935 LV2Plugin::parameter_is_control(uint32_t param) const
2937 assert(param < _port_flags.size());
2938 return _port_flags[param] & PORT_CONTROL;
2942 LV2Plugin::parameter_is_audio(uint32_t param) const
2944 assert(param < _port_flags.size());
2945 return _port_flags[param] & PORT_AUDIO;
2949 LV2Plugin::parameter_is_event(uint32_t param) const
2951 assert(param < _port_flags.size());
2952 return _port_flags[param] & PORT_EVENT;
2956 LV2Plugin::parameter_is_output(uint32_t param) const
2958 assert(param < _port_flags.size());
2959 return _port_flags[param] & PORT_OUTPUT;
2963 LV2Plugin::parameter_is_input(uint32_t param) const
2965 assert(param < _port_flags.size());
2966 return _port_flags[param] & PORT_INPUT;
2970 LV2Plugin::designated_bypass_port ()
2972 const LilvPort* port = NULL;
2973 LilvNode* designation = lilv_new_uri (_world.world, LV2_CORE_PREFIX "enabled");
2974 port = lilv_plugin_get_port_by_designation (
2975 _impl->plugin, _world.lv2_InputPort, designation);
2976 lilv_node_free(designation);
2978 return lilv_port_get_index (_impl->plugin, port);
2981 /* deprecated on 2016-Sep-18 in favor of lv2:enabled */
2982 designation = lilv_new_uri (_world.world, LV2_PROCESSING_URI__enable);
2983 port = lilv_plugin_get_port_by_designation (
2984 _impl->plugin, _world.lv2_InputPort, designation);
2985 lilv_node_free(designation);
2987 return lilv_port_get_index (_impl->plugin, port);
2994 LV2Plugin::print_parameter(uint32_t param, char* buf, uint32_t len) const
2997 if (param < parameter_count()) {
2998 snprintf(buf, len, "%.3f", get_parameter(param));
3005 boost::shared_ptr<ScalePoints>
3006 LV2Plugin::get_scale_points(uint32_t port_index) const
3008 const LilvPort* port = lilv_plugin_get_port_by_index(_impl->plugin, port_index);
3009 LilvScalePoints* points = lilv_port_get_scale_points(_impl->plugin, port);
3011 boost::shared_ptr<ScalePoints> ret;
3016 ret = boost::shared_ptr<ScalePoints>(new ScalePoints());
3018 LILV_FOREACH(scale_points, i, points) {
3019 const LilvScalePoint* p = lilv_scale_points_get(points, i);
3020 const LilvNode* label = lilv_scale_point_get_label(p);
3021 const LilvNode* value = lilv_scale_point_get_value(p);
3022 if (label && (lilv_node_is_float(value) || lilv_node_is_int(value))) {
3023 ret->insert(make_pair(lilv_node_as_string(label),
3024 lilv_node_as_float(value)));
3028 lilv_scale_points_free(points);
3033 LV2Plugin::run(pframes_t nframes, bool sync_work)
3035 uint32_t const N = parameter_count();
3036 for (uint32_t i = 0; i < N; ++i) {
3037 if (parameter_is_control(i) && parameter_is_input(i)) {
3038 _control_data[i] = _shadow_data[i];
3043 // Execute work synchronously if we're freewheeling (export)
3044 _worker->set_synchronous(sync_work || session().engine().freewheeling());
3047 // Run the plugin for this cycle
3048 lilv_instance_run(_impl->instance, nframes);
3050 // Emit any queued worker responses (calls a plugin callback)
3051 if (_state_worker) {
3052 _state_worker->emit_responses();
3055 _worker->emit_responses();
3058 // Notify the plugin that a work run cycle is complete
3059 if (_impl->work_iface) {
3060 if (_impl->work_iface->end_run) {
3061 _impl->work_iface->end_run(_impl->instance->lv2_handle);
3067 LV2Plugin::latency_compute_run()
3069 if (!_latency_control_port) {
3073 // Run the plugin so that it can set its latency parameter
3075 bool was_activated = _was_activated;
3078 uint32_t port_index = 0;
3079 uint32_t in_index = 0;
3080 uint32_t out_index = 0;
3082 // this is done in the main thread. non realtime.
3083 const framecnt_t bufsize = _engine.samples_per_cycle();
3084 float *buffer = (float*) malloc(_engine.samples_per_cycle() * sizeof(float));
3086 memset(buffer, 0, sizeof(float) * bufsize);
3088 // FIXME: Ensure plugins can handle in-place processing
3092 while (port_index < parameter_count()) {
3093 if (parameter_is_audio(port_index)) {
3094 if (parameter_is_input(port_index)) {
3095 lilv_instance_connect_port(_impl->instance, port_index, buffer);
3097 } else if (parameter_is_output(port_index)) {
3098 lilv_instance_connect_port(_impl->instance, port_index, buffer);
3107 if (was_activated) {
3114 LV2Plugin::Impl::designated_input (const char* uri, void** bufptrs[], void** bufptr)
3116 const LilvPort* port = NULL;
3117 LilvNode* designation = lilv_new_uri(_world.world, uri);
3118 port = lilv_plugin_get_port_by_designation(
3119 plugin, _world.lv2_InputPort, designation);
3120 lilv_node_free(designation);
3122 bufptrs[lilv_port_get_index(plugin, port)] = bufptr;
3127 static bool lv2_filter (const string& str, void* /*arg*/)
3129 /* Not a dotfile, has a prefix before a period, suffix is "lv2" */
3131 return str[0] != '.' && (str.length() > 3 && str.find (".lv2") == (str.length() - 4));
3135 LV2World::LV2World()
3136 : world(lilv_world_new())
3137 , _bundle_checked(false)
3139 atom_AtomPort = lilv_new_uri(world, LV2_ATOM__AtomPort);
3140 atom_Chunk = lilv_new_uri(world, LV2_ATOM__Chunk);
3141 atom_Sequence = lilv_new_uri(world, LV2_ATOM__Sequence);
3142 atom_bufferType = lilv_new_uri(world, LV2_ATOM__bufferType);
3143 atom_supports = lilv_new_uri(world, LV2_ATOM__supports);
3144 atom_eventTransfer = lilv_new_uri(world, LV2_ATOM__eventTransfer);
3145 ev_EventPort = lilv_new_uri(world, LILV_URI_EVENT_PORT);
3146 ext_logarithmic = lilv_new_uri(world, LV2_PORT_PROPS__logarithmic);
3147 ext_notOnGUI = lilv_new_uri(world, LV2_PORT_PROPS__notOnGUI);
3148 ext_expensive = lilv_new_uri(world, LV2_PORT_PROPS__expensive);
3149 ext_causesArtifacts= lilv_new_uri(world, LV2_PORT_PROPS__causesArtifacts);
3150 ext_notAutomatic = lilv_new_uri(world, LV2_PORT_PROPS__notAutomatic);
3151 ext_rangeSteps = lilv_new_uri(world, LV2_PORT_PROPS__rangeSteps);
3152 groups_group = lilv_new_uri(world, LV2_PORT_GROUPS__group);
3153 groups_element = lilv_new_uri(world, LV2_PORT_GROUPS__element);
3154 lv2_AudioPort = lilv_new_uri(world, LILV_URI_AUDIO_PORT);
3155 lv2_ControlPort = lilv_new_uri(world, LILV_URI_CONTROL_PORT);
3156 lv2_InputPort = lilv_new_uri(world, LILV_URI_INPUT_PORT);
3157 lv2_OutputPort = lilv_new_uri(world, LILV_URI_OUTPUT_PORT);
3158 lv2_inPlaceBroken = lilv_new_uri(world, LV2_CORE__inPlaceBroken);
3159 lv2_isSideChain = lilv_new_uri(world, LV2_CORE_PREFIX "isSideChain");
3160 lv2_index = lilv_new_uri(world, LV2_CORE__index);
3161 lv2_integer = lilv_new_uri(world, LV2_CORE__integer);
3162 lv2_default = lilv_new_uri(world, LV2_CORE__default);
3163 lv2_minimum = lilv_new_uri(world, LV2_CORE__minimum);
3164 lv2_maximum = lilv_new_uri(world, LV2_CORE__maximum);
3165 lv2_reportsLatency = lilv_new_uri(world, LV2_CORE__reportsLatency);
3166 lv2_sampleRate = lilv_new_uri(world, LV2_CORE__sampleRate);
3167 lv2_toggled = lilv_new_uri(world, LV2_CORE__toggled);
3168 lv2_designation = lilv_new_uri(world, LV2_CORE__designation);
3169 lv2_enumeration = lilv_new_uri(world, LV2_CORE__enumeration);
3170 lv2_freewheeling = lilv_new_uri(world, LV2_CORE__freeWheeling);
3171 midi_MidiEvent = lilv_new_uri(world, LILV_URI_MIDI_EVENT);
3172 rdfs_comment = lilv_new_uri(world, LILV_NS_RDFS "comment");
3173 rdfs_label = lilv_new_uri(world, LILV_NS_RDFS "label");
3174 rdfs_range = lilv_new_uri(world, LILV_NS_RDFS "range");
3175 rsz_minimumSize = lilv_new_uri(world, LV2_RESIZE_PORT__minimumSize);
3176 time_Position = lilv_new_uri(world, LV2_TIME__Position);
3177 ui_GtkUI = lilv_new_uri(world, LV2_UI__GtkUI);
3178 ui_external = lilv_new_uri(world, "http://lv2plug.in/ns/extensions/ui#external");
3179 ui_externalkx = lilv_new_uri(world, "http://kxstudio.sf.net/ns/lv2ext/external-ui#Widget");
3180 units_unit = lilv_new_uri(world, LV2_UNITS__unit);
3181 units_render = lilv_new_uri(world, LV2_UNITS__render);
3182 units_hz = lilv_new_uri(world, LV2_UNITS__hz);
3183 units_midiNote = lilv_new_uri(world, LV2_UNITS__midiNote);
3184 units_db = lilv_new_uri(world, LV2_UNITS__db);
3185 patch_writable = lilv_new_uri(world, LV2_PATCH__writable);
3186 patch_Message = lilv_new_uri(world, LV2_PATCH__Message);
3188 lv2_noSampleAccurateCtrl = lilv_new_uri(world, "http://ardour.org/lv2/ext#noSampleAccurateControls"); // deprecated 2016-09-18
3189 auto_can_write_automatation = lilv_new_uri(world, LV2_AUTOMATE_URI__can_write);
3190 auto_automation_control = lilv_new_uri(world, LV2_AUTOMATE_URI__control);
3191 auto_automation_controlled = lilv_new_uri(world, LV2_AUTOMATE_URI__controlled);
3192 auto_automation_controller = lilv_new_uri(world, LV2_AUTOMATE_URI__controller);
3193 inline_display_in_gui = lilv_new_uri(world, LV2_INLINEDISPLAY__in_gui);
3195 #ifdef HAVE_LV2_1_2_0
3196 bufz_powerOf2BlockLength = lilv_new_uri(world, LV2_BUF_SIZE__powerOf2BlockLength);
3197 bufz_fixedBlockLength = lilv_new_uri(world, LV2_BUF_SIZE__fixedBlockLength);
3198 bufz_nominalBlockLength = lilv_new_uri(world, "http://lv2plug.in/ns/ext/buf-size#nominalBlockLength");
3199 bufz_coarseBlockLength = lilv_new_uri(world, "http://lv2plug.in/ns/ext/buf-size#coarseBlockLength");
3204 LV2World::~LV2World()
3209 #ifdef HAVE_LV2_1_2_0
3210 lilv_node_free(bufz_coarseBlockLength);
3211 lilv_node_free(bufz_nominalBlockLength);
3212 lilv_node_free(bufz_fixedBlockLength);
3213 lilv_node_free(bufz_powerOf2BlockLength);
3216 lilv_node_free(lv2_noSampleAccurateCtrl);
3217 lilv_node_free(auto_can_write_automatation);
3218 lilv_node_free(auto_automation_control);
3219 lilv_node_free(auto_automation_controlled);
3220 lilv_node_free(auto_automation_controller);
3222 lilv_node_free(patch_Message);
3223 lilv_node_free(patch_writable);
3224 lilv_node_free(units_hz);
3225 lilv_node_free(units_midiNote);
3226 lilv_node_free(units_db);
3227 lilv_node_free(units_unit);
3228 lilv_node_free(units_render);
3229 lilv_node_free(ui_externalkx);
3230 lilv_node_free(ui_external);
3231 lilv_node_free(ui_GtkUI);
3232 lilv_node_free(time_Position);
3233 lilv_node_free(rsz_minimumSize);
3234 lilv_node_free(rdfs_comment);
3235 lilv_node_free(rdfs_label);
3236 lilv_node_free(rdfs_range);
3237 lilv_node_free(midi_MidiEvent);
3238 lilv_node_free(lv2_designation);
3239 lilv_node_free(lv2_enumeration);
3240 lilv_node_free(lv2_freewheeling);
3241 lilv_node_free(lv2_toggled);
3242 lilv_node_free(lv2_sampleRate);
3243 lilv_node_free(lv2_reportsLatency);
3244 lilv_node_free(lv2_index);
3245 lilv_node_free(lv2_integer);
3246 lilv_node_free(lv2_isSideChain);
3247 lilv_node_free(lv2_inPlaceBroken);
3248 lilv_node_free(lv2_OutputPort);
3249 lilv_node_free(lv2_InputPort);
3250 lilv_node_free(lv2_ControlPort);
3251 lilv_node_free(lv2_AudioPort);
3252 lilv_node_free(groups_group);
3253 lilv_node_free(groups_element);
3254 lilv_node_free(ext_rangeSteps);
3255 lilv_node_free(ext_notAutomatic);
3256 lilv_node_free(ext_causesArtifacts);
3257 lilv_node_free(ext_expensive);
3258 lilv_node_free(ext_notOnGUI);
3259 lilv_node_free(ext_logarithmic);
3260 lilv_node_free(ev_EventPort);
3261 lilv_node_free(atom_supports);
3262 lilv_node_free(atom_eventTransfer);
3263 lilv_node_free(atom_bufferType);
3264 lilv_node_free(atom_Sequence);
3265 lilv_node_free(atom_Chunk);
3266 lilv_node_free(atom_AtomPort);
3267 lilv_world_free(world);
3272 LV2World::load_bundled_plugins(bool verbose)
3274 if (!_bundle_checked) {
3276 cout << "Scanning folders for bundled LV2s: " << ARDOUR::lv2_bundled_search_path().to_string() << endl;
3279 vector<string> plugin_objects;
3280 find_paths_matching_filter (plugin_objects, ARDOUR::lv2_bundled_search_path(), lv2_filter, 0, true, true, true);
3281 for ( vector<string>::iterator x = plugin_objects.begin(); x != plugin_objects.end (); ++x) {
3282 #ifdef PLATFORM_WINDOWS
3283 string uri = "file:///" + *x + "/";
3285 string uri = "file://" + *x + "/";
3287 LilvNode *node = lilv_new_uri(world, uri.c_str());
3288 lilv_world_load_bundle(world, node);
3289 lilv_node_free(node);
3292 lilv_world_load_all(world);
3293 _bundle_checked = true;
3297 LV2PluginInfo::LV2PluginInfo (const char* plugin_uri)
3300 _plugin_uri = strdup(plugin_uri);
3303 LV2PluginInfo::~LV2PluginInfo()
3310 LV2PluginInfo::load(Session& session)
3314 const LilvPlugins* plugins = lilv_world_get_all_plugins(_world.world);
3315 LilvNode* uri = lilv_new_uri(_world.world, _plugin_uri);
3316 if (!uri) { throw failed_constructor(); }
3317 const LilvPlugin* lp = lilv_plugins_get_by_uri(plugins, uri);
3318 if (!lp) { throw failed_constructor(); }
3319 plugin.reset(new LV2Plugin(session.engine(), session, lp, session.frame_rate()));
3320 lilv_node_free(uri);
3321 plugin->set_info(PluginInfoPtr(shared_from_this ()));
3323 } catch (failed_constructor& err) {
3324 return PluginPtr((Plugin*)0);
3330 std::vector<Plugin::PresetRecord>
3331 LV2PluginInfo::get_presets (bool /*user_only*/) const
3333 std::vector<Plugin::PresetRecord> p;
3334 #ifndef NO_PLUGIN_STATE
3335 const LilvPlugin* lp = NULL;
3338 const LilvPlugins* plugins = lilv_world_get_all_plugins(_world.world);
3339 LilvNode* uri = lilv_new_uri(_world.world, _plugin_uri);
3340 if (!uri) { throw failed_constructor(); }
3341 lp = lilv_plugins_get_by_uri(plugins, uri);
3342 if (!lp) { throw failed_constructor(); }
3343 lilv_node_free(uri);
3344 } catch (failed_constructor& err) {
3348 // see LV2Plugin::find_presets
3349 LilvNode* lv2_appliesTo = lilv_new_uri(_world.world, LV2_CORE__appliesTo);
3350 LilvNode* pset_Preset = lilv_new_uri(_world.world, LV2_PRESETS__Preset);
3351 LilvNode* rdfs_label = lilv_new_uri(_world.world, LILV_NS_RDFS "label");
3353 LilvNodes* presets = lilv_plugin_get_related(lp, pset_Preset);
3354 LILV_FOREACH(nodes, i, presets) {
3355 const LilvNode* preset = lilv_nodes_get(presets, i);
3356 lilv_world_load_resource(_world.world, preset);
3357 LilvNode* name = get_value(_world.world, preset, rdfs_label);
3358 bool userpreset = true; // TODO
3360 p.push_back (Plugin::PresetRecord (lilv_node_as_string(preset), lilv_node_as_string(name), userpreset));
3361 lilv_node_free(name);
3364 lilv_nodes_free(presets);
3365 lilv_node_free(rdfs_label);
3366 lilv_node_free(pset_Preset);
3367 lilv_node_free(lv2_appliesTo);
3373 LV2PluginInfo::in_category (const std::string &c) const
3375 // TODO use untranslated lilv_plugin_get_class()
3376 // match gtk2_ardour/plugin_selector.cc
3377 return category == c;
3381 LV2PluginInfo::is_instrument () const
3383 if (category == "Instrument") {
3387 /* until we make sure that category remains untranslated in the lv2.ttl spec
3388 * and until most instruments also classify themselves as such, there's a 2nd check:
3390 if (n_inputs.n_midi() > 0 && n_inputs.n_audio() == 0 && n_outputs.n_audio() > 0) {
3398 LV2PluginInfo::discover()
3401 world.load_bundled_plugins();
3402 _world.load_bundled_plugins(true);
3404 PluginInfoList* plugs = new PluginInfoList;
3405 const LilvPlugins* plugins = lilv_world_get_all_plugins(world.world);
3407 LILV_FOREACH(plugins, i, plugins) {
3408 const LilvPlugin* p = lilv_plugins_get(plugins, i);
3409 const LilvNode* pun = lilv_plugin_get_uri(p);
3411 LV2PluginInfoPtr info(new LV2PluginInfo(lilv_node_as_string(pun)));
3413 LilvNode* name = lilv_plugin_get_name(p);
3414 if (!name || !lilv_plugin_get_port_by_index(p, 0)) {
3415 warning << "Ignoring invalid LV2 plugin "
3416 << lilv_node_as_string(lilv_plugin_get_uri(p))
3421 if (lilv_plugin_has_feature(p, world.lv2_inPlaceBroken)) {
3422 warning << string_compose(
3423 _("Ignoring LV2 plugin \"%1\" since it cannot do inplace processing."),
3424 lilv_node_as_string(name)) << endmsg;
3425 lilv_node_free(name);
3429 #ifdef HAVE_LV2_1_2_0
3430 LilvNodes *required_features = lilv_plugin_get_required_features (p);
3431 if (lilv_nodes_contains (required_features, world.bufz_powerOf2BlockLength) ||
3432 lilv_nodes_contains (required_features, world.bufz_fixedBlockLength)
3434 warning << string_compose(
3435 _("Ignoring LV2 plugin \"%1\" because its buffer-size requirements cannot be satisfied."),
3436 lilv_node_as_string(name)) << endmsg;
3437 lilv_nodes_free(required_features);
3438 lilv_node_free(name);
3441 lilv_nodes_free(required_features);
3446 info->name = string(lilv_node_as_string(name));
3447 lilv_node_free(name);
3448 ARDOUR::PluginScanMessage(_("LV2"), info->name, false);
3450 const LilvPluginClass* pclass = lilv_plugin_get_class(p);
3451 const LilvNode* label = lilv_plugin_class_get_label(pclass);
3452 info->category = lilv_node_as_string(label);
3454 LilvNode* author_name = lilv_plugin_get_author_name(p);
3455 info->creator = author_name ? string(lilv_node_as_string(author_name)) : "Unknown";
3456 lilv_node_free(author_name);
3458 info->path = "/NOPATH"; // Meaningless for LV2
3460 /* count atom-event-ports that feature
3461 * atom:supports <http://lv2plug.in/ns/ext/midi#MidiEvent>
3463 * TODO: nicely ask drobilla to make a lilv_ call for that
3465 int count_midi_out = 0;
3466 int count_midi_in = 0;
3467 for (uint32_t i = 0; i < lilv_plugin_get_num_ports(p); ++i) {
3468 const LilvPort* port = lilv_plugin_get_port_by_index(p, i);
3469 if (lilv_port_is_a(p, port, world.atom_AtomPort)) {
3470 LilvNodes* buffer_types = lilv_port_get_value(
3471 p, port, world.atom_bufferType);
3472 LilvNodes* atom_supports = lilv_port_get_value(
3473 p, port, world.atom_supports);
3475 if (lilv_nodes_contains(buffer_types, world.atom_Sequence)
3476 && lilv_nodes_contains(atom_supports, world.midi_MidiEvent)) {
3477 if (lilv_port_is_a(p, port, world.lv2_InputPort)) {
3480 if (lilv_port_is_a(p, port, world.lv2_OutputPort)) {
3484 lilv_nodes_free(buffer_types);
3485 lilv_nodes_free(atom_supports);
3489 info->n_inputs.set_audio(
3490 lilv_plugin_get_num_ports_of_class(
3491 p, world.lv2_InputPort, world.lv2_AudioPort, NULL));
3492 info->n_inputs.set_midi(
3493 lilv_plugin_get_num_ports_of_class(
3494 p, world.lv2_InputPort, world.ev_EventPort, NULL)
3497 info->n_outputs.set_audio(
3498 lilv_plugin_get_num_ports_of_class(
3499 p, world.lv2_OutputPort, world.lv2_AudioPort, NULL));
3500 info->n_outputs.set_midi(
3501 lilv_plugin_get_num_ports_of_class(
3502 p, world.lv2_OutputPort, world.ev_EventPort, NULL)
3505 info->unique_id = lilv_node_as_uri(lilv_plugin_get_uri(p));
3506 info->index = 0; // Meaningless for LV2
3508 plugs->push_back(info);