Update to latest LV2 atom extension.
git-svn-id: svn://localhost/ardour2/branches/3.0@11548 d708f5d6-7413-0410-9779-e7cbd77b26cf
This commit is contained in:
parent
9dd4d79d6c
commit
8de887f378
@ -112,13 +112,13 @@ public:
|
||||
}
|
||||
|
||||
#ifdef LV2_SUPPORT
|
||||
/** Get a MIDI buffer translated into an LV2 MIDI buffer for use with plugins.
|
||||
* The index here corresponds directly to MIDI buffer numbers (i.e. the index
|
||||
* passed to get_midi), translation back and forth will happen as needed.
|
||||
* If atom_type is 0 the returned buffer will be in the old event API
|
||||
* format. Otherwise, atom_type must be the URID for atom:Sequence.
|
||||
/** Get a MIDI buffer translated into an LV2 MIDI buffer for use with
|
||||
* plugins. The index here corresponds directly to MIDI buffer numbers
|
||||
* (i.e. the index passed to get_midi), translation back and forth will
|
||||
* happen as needed. If old_api is true, the returned buffer will be in
|
||||
* old event format. Otherwise it will be in new atom sequence format.
|
||||
*/
|
||||
LV2_Evbuf* get_lv2_midi(bool input, size_t i, uint32_t atom_type);
|
||||
LV2_Evbuf* get_lv2_midi(bool input, size_t i, bool old_api);
|
||||
|
||||
/** Flush modified LV2 event output buffers back to Ardour buffers */
|
||||
void flush_lv2_midi(bool input, size_t i);
|
||||
|
@ -130,6 +130,13 @@ class LV2Plugin : public ARDOUR::Plugin
|
||||
|
||||
static URIMap _uri_map;
|
||||
|
||||
static uint32_t _midi_event_type_ev;
|
||||
static uint32_t _midi_event_type;
|
||||
static uint32_t _chunk_type;
|
||||
static uint32_t _sequence_type;
|
||||
static uint32_t _event_transfer_type;
|
||||
static uint32_t _state_path_type;
|
||||
|
||||
private:
|
||||
struct Impl;
|
||||
Impl* _impl;
|
||||
@ -193,12 +200,6 @@ class LV2Plugin : public ARDOUR::Plugin
|
||||
bool _was_activated;
|
||||
bool _has_state_interface;
|
||||
|
||||
static uint32_t _midi_event_type_ev;
|
||||
static uint32_t _midi_event_type;
|
||||
static uint32_t _sequence_type;
|
||||
static uint32_t _event_transfer_type;
|
||||
static uint32_t _state_path_type;
|
||||
|
||||
const std::string plugin_dir () const;
|
||||
const std::string scratch_dir () const;
|
||||
const std::string file_dir () const;
|
||||
|
@ -190,8 +190,10 @@ BufferSet::ensure_buffers(DataType type, size_t num_buffers, size_t buffer_capac
|
||||
if (type == DataType::MIDI && _lv2_buffers.size() < _buffers[type].size() * 2 + 1) {
|
||||
while (_lv2_buffers.size() < _buffers[type].size() * 2) {
|
||||
_lv2_buffers.push_back(
|
||||
std::make_pair(false,
|
||||
lv2_evbuf_new(buffer_capacity, LV2_EVBUF_EVENT, 0)));
|
||||
std::make_pair(false, lv2_evbuf_new(buffer_capacity,
|
||||
LV2_EVBUF_EVENT,
|
||||
LV2Plugin::_chunk_type,
|
||||
LV2Plugin::_sequence_type)));
|
||||
}
|
||||
}
|
||||
#endif
|
||||
@ -251,25 +253,23 @@ BufferSet::get(DataType type, size_t i) const
|
||||
#ifdef LV2_SUPPORT
|
||||
|
||||
LV2_Evbuf*
|
||||
BufferSet::get_lv2_midi(bool input, size_t i, uint32_t atom_type)
|
||||
BufferSet::get_lv2_midi(bool input, size_t i, bool old_api)
|
||||
{
|
||||
assert(count().get(DataType::MIDI) > i);
|
||||
|
||||
MidiBuffer& mbuf = get_midi(i);
|
||||
LV2Buffers::value_type b = _lv2_buffers.at(i * 2 + (input ? 0 : 1));
|
||||
LV2_Evbuf* evbuf = b.second;
|
||||
lv2_evbuf_set_type(evbuf,
|
||||
atom_type ? LV2_EVBUF_ATOM : LV2_EVBUF_EVENT,
|
||||
atom_type);
|
||||
lv2_evbuf_set_type(evbuf, old_api ? LV2_EVBUF_EVENT : LV2_EVBUF_ATOM);
|
||||
|
||||
lv2_evbuf_reset(evbuf);
|
||||
lv2_evbuf_reset(evbuf, input);
|
||||
if (input) {
|
||||
DEBUG_TRACE(PBD::DEBUG::LV2,
|
||||
string_compose("%1 bytes of MIDI waiting @ %2\n",
|
||||
mbuf.size(), (void*) mbuf.data()));
|
||||
|
||||
LV2_Evbuf_Iterator i = lv2_evbuf_begin(evbuf);
|
||||
const uint32_t type = LV2Plugin::midi_event_type(atom_type == 0);
|
||||
const uint32_t type = LV2Plugin::midi_event_type(old_api);
|
||||
for (MidiBuffer::iterator e = mbuf.begin(); e != mbuf.end(); ++e) {
|
||||
const Evoral::MIDIEvent<framepos_t> ev(*e, false);
|
||||
#ifndef NDEBUG
|
||||
|
@ -33,6 +33,7 @@
|
||||
#define LV2_ATOM__Beats LV2_ATOM_URI "#Beats"
|
||||
#define LV2_ATOM__Blank LV2_ATOM_URI "#Blank"
|
||||
#define LV2_ATOM__Bool LV2_ATOM_URI "#Bool"
|
||||
#define LV2_ATOM__Chunk LV2_ATOM_URI "#Chunk"
|
||||
#define LV2_ATOM__Double LV2_ATOM_URI "#Double"
|
||||
#define LV2_ATOM__Event LV2_ATOM_URI "#Event"
|
||||
#define LV2_ATOM__Float LV2_ATOM_URI "#Float"
|
||||
@ -55,6 +56,7 @@
|
||||
#define LV2_ATOM__Vector LV2_ATOM_URI "#Vector"
|
||||
#define LV2_ATOM__beatTime LV2_ATOM_URI "#beatTime"
|
||||
#define LV2_ATOM__bufferType LV2_ATOM_URI "#bufferType"
|
||||
#define LV2_ATOM__childType LV2_ATOM_URI "#childType"
|
||||
#define LV2_ATOM__eventTransfer LV2_ATOM_URI "#eventTransfer"
|
||||
#define LV2_ATOM__frameTime LV2_ATOM_URI "#frameTime"
|
||||
#define LV2_ATOM__supports LV2_ATOM_URI "#supports"
|
||||
@ -91,6 +93,12 @@ typedef struct {
|
||||
uint32_t type; /**< Type of this atom (mapped URI). */
|
||||
} LV2_Atom;
|
||||
|
||||
/** A chunk of memory that may be uninitialized or contain an Atom. */
|
||||
typedef struct {
|
||||
LV2_Atom atom; /**< Atom header. */
|
||||
LV2_Atom body; /**< Body atom header. */
|
||||
} LV2_Atom_Chunk;
|
||||
|
||||
/** An atom:Int32 or atom:Bool. May be cast to LV2_Atom. */
|
||||
typedef struct {
|
||||
LV2_Atom atom; /**< Atom header. */
|
||||
@ -229,29 +237,6 @@ typedef struct {
|
||||
LV2_Atom_Literal_Body body; /**< Body. */
|
||||
} LV2_Atom_Sequence;
|
||||
|
||||
/**
|
||||
The contents of an atom:AtomPort buffer.
|
||||
|
||||
This contains a pointer to an Atom, which is the data to be
|
||||
processed/written, as well as additional metadata. This struct may be
|
||||
augmented in the future to add more metadata fields as they become
|
||||
necessary. The initial version of this struct contains data, size, and
|
||||
capacity. Implementations MUST check that any other fields they wish to use
|
||||
are actually present by comparing the size with the offset of that field,
|
||||
e.g.:
|
||||
|
||||
@code
|
||||
if (offsetof(LV2_Atom_Port_Buffer, field) < buf->size) {
|
||||
do_stuff_with(buf->field);
|
||||
}
|
||||
@endcode
|
||||
*/
|
||||
typedef struct {
|
||||
LV2_Atom* data; /** Pointer to data. */
|
||||
uint32_t size; /** Total size of this struct. */
|
||||
uint32_t capacity; /** Available space for data body. */
|
||||
} LV2_Atom_Port_Buffer;
|
||||
|
||||
#ifdef __cplusplus
|
||||
} /* extern "C" */
|
||||
#endif
|
||||
|
@ -131,6 +131,7 @@ lv2_atom_forge_set_buffer(LV2_Atom_Forge* forge, uint8_t* buf, size_t size)
|
||||
forge->offset = 0;
|
||||
forge->sink = NULL;
|
||||
forge->handle = NULL;
|
||||
forge->stack = NULL;
|
||||
}
|
||||
|
||||
/**
|
||||
@ -154,6 +155,7 @@ lv2_atom_forge_set_sink(LV2_Atom_Forge* forge,
|
||||
forge->size = forge->offset = 0;
|
||||
forge->sink = sink;
|
||||
forge->handle = handle;
|
||||
forge->stack = NULL;
|
||||
}
|
||||
|
||||
/**
|
||||
@ -195,7 +197,7 @@ lv2_atom_forge_raw(LV2_Atom_Forge* forge, const void* data, uint32_t size)
|
||||
{
|
||||
uint8_t* out = NULL;
|
||||
if (forge->sink) {
|
||||
out = forge->sink(forge->handle, data, size);
|
||||
out = (uint8_t*)forge->sink(forge->handle, data, size);
|
||||
} else {
|
||||
out = forge->buf + forge->offset;
|
||||
if (forge->offset + size > forge->size) {
|
||||
@ -295,12 +297,12 @@ lv2_atom_forge_string_body(LV2_Atom_Forge* forge,
|
||||
const uint8_t* str,
|
||||
uint32_t len)
|
||||
{
|
||||
uint8_t* out = NULL;
|
||||
void* out = NULL;
|
||||
if ( (out = lv2_atom_forge_raw(forge, str, len))
|
||||
&& (out = lv2_atom_forge_raw(forge, "", 1))) {
|
||||
lv2_atom_forge_pad(forge, len + 1);
|
||||
}
|
||||
return out;
|
||||
return (uint8_t*)out;
|
||||
}
|
||||
|
||||
/** Write an atom compatible with atom:String. Used internally. */
|
||||
@ -424,7 +426,7 @@ static inline LV2_Atom_Tuple*
|
||||
lv2_atom_forge_tuple(LV2_Atom_Forge* forge, LV2_Atom_Forge_Frame* frame)
|
||||
{
|
||||
const LV2_Atom_Tuple a = { { 0, forge->Tuple } };
|
||||
LV2_Atom* atom = lv2_atom_forge_write(forge, &a, sizeof(a));
|
||||
LV2_Atom* atom = (LV2_Atom*)lv2_atom_forge_write(forge, &a, sizeof(a));
|
||||
return (LV2_Atom_Tuple*)lv2_atom_forge_push(forge, frame, atom);
|
||||
}
|
||||
|
||||
|
@ -14,8 +14,6 @@
|
||||
OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
|
||||
*/
|
||||
|
||||
#include <stdint.h>
|
||||
#include <stdbool.h>
|
||||
#include <string.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
@ -27,9 +25,11 @@
|
||||
struct LV2_Evbuf_Impl {
|
||||
LV2_Evbuf_Type type;
|
||||
uint32_t capacity;
|
||||
uint32_t atom_Chunk;
|
||||
uint32_t atom_Sequence;
|
||||
union {
|
||||
LV2_Event_Buffer event;
|
||||
LV2_Atom_Port_Buffer atom;
|
||||
LV2_Event_Buffer event;
|
||||
LV2_Atom_Sequence atom;
|
||||
} buf;
|
||||
};
|
||||
|
||||
@ -40,14 +40,19 @@ lv2_evbuf_pad_size(uint32_t size)
|
||||
}
|
||||
|
||||
LV2_Evbuf*
|
||||
lv2_evbuf_new(uint32_t capacity, LV2_Evbuf_Type type, uint32_t atom_type)
|
||||
lv2_evbuf_new(uint32_t capacity,
|
||||
LV2_Evbuf_Type type,
|
||||
uint32_t atom_Chunk,
|
||||
uint32_t atom_Sequence)
|
||||
{
|
||||
// FIXME: memory must be 64-bit aligned
|
||||
LV2_Evbuf* evbuf = (LV2_Evbuf*)malloc(
|
||||
sizeof(LV2_Evbuf) + sizeof(LV2_Atom_Sequence) + capacity);
|
||||
evbuf->capacity = capacity;
|
||||
lv2_evbuf_set_type(evbuf, type, atom_type);
|
||||
lv2_evbuf_reset(evbuf);
|
||||
evbuf->capacity = capacity;
|
||||
evbuf->atom_Chunk = atom_Chunk;
|
||||
evbuf->atom_Sequence = atom_Sequence;
|
||||
lv2_evbuf_set_type(evbuf, type);
|
||||
lv2_evbuf_reset(evbuf, true);
|
||||
return evbuf;
|
||||
}
|
||||
|
||||
@ -58,7 +63,7 @@ lv2_evbuf_free(LV2_Evbuf* evbuf)
|
||||
}
|
||||
|
||||
void
|
||||
lv2_evbuf_set_type(LV2_Evbuf* evbuf, LV2_Evbuf_Type type, uint32_t atom_type)
|
||||
lv2_evbuf_set_type(LV2_Evbuf* evbuf, LV2_Evbuf_Type type)
|
||||
{
|
||||
evbuf->type = type;
|
||||
switch (type) {
|
||||
@ -67,18 +72,13 @@ lv2_evbuf_set_type(LV2_Evbuf* evbuf, LV2_Evbuf_Type type, uint32_t atom_type)
|
||||
evbuf->buf.event.capacity = evbuf->capacity;
|
||||
break;
|
||||
case LV2_EVBUF_ATOM:
|
||||
evbuf->buf.atom.data = (LV2_Atom*)(evbuf + 1);
|
||||
evbuf->buf.atom.size = sizeof(LV2_Atom_Port_Buffer);
|
||||
evbuf->buf.atom.capacity = evbuf->capacity;
|
||||
evbuf->buf.atom.data->type = atom_type;
|
||||
evbuf->buf.atom.data->size = 0;
|
||||
break;
|
||||
}
|
||||
lv2_evbuf_reset(evbuf);
|
||||
lv2_evbuf_reset(evbuf, true);
|
||||
}
|
||||
|
||||
void
|
||||
lv2_evbuf_reset(LV2_Evbuf* evbuf)
|
||||
lv2_evbuf_reset(LV2_Evbuf* evbuf, bool input)
|
||||
{
|
||||
switch (evbuf->type) {
|
||||
case LV2_EVBUF_EVENT:
|
||||
@ -88,7 +88,13 @@ lv2_evbuf_reset(LV2_Evbuf* evbuf)
|
||||
evbuf->buf.event.size = 0;
|
||||
break;
|
||||
case LV2_EVBUF_ATOM:
|
||||
evbuf->buf.atom.data->size = 0;
|
||||
if (input) {
|
||||
evbuf->buf.atom.atom.size = 0;
|
||||
evbuf->buf.atom.atom.type = evbuf->atom_Sequence;
|
||||
} else {
|
||||
evbuf->buf.atom.atom.size = evbuf->capacity;
|
||||
evbuf->buf.atom.atom.type = evbuf->atom_Chunk;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -99,7 +105,9 @@ lv2_evbuf_get_size(LV2_Evbuf* evbuf)
|
||||
case LV2_EVBUF_EVENT:
|
||||
return evbuf->buf.event.size;
|
||||
case LV2_EVBUF_ATOM:
|
||||
return evbuf->buf.atom.data->size;
|
||||
return evbuf->buf.atom.atom.type == evbuf->atom_Sequence
|
||||
? evbuf->buf.atom.atom.size
|
||||
: 0;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
@ -154,7 +162,7 @@ lv2_evbuf_next(LV2_Evbuf_Iterator iter)
|
||||
break;
|
||||
case LV2_EVBUF_ATOM:
|
||||
size = ((LV2_Atom_Event*)
|
||||
((char*)LV2_ATOM_CONTENTS(LV2_Atom_Sequence, evbuf->buf.atom.data)
|
||||
((char*)LV2_ATOM_CONTENTS(LV2_Atom_Sequence, &evbuf->buf.atom)
|
||||
+ offset))->body.size;
|
||||
offset += lv2_evbuf_pad_size(sizeof(LV2_Atom_Event) + size);
|
||||
break;
|
||||
@ -179,10 +187,10 @@ lv2_evbuf_get(LV2_Evbuf_Iterator iter,
|
||||
return false;
|
||||
}
|
||||
|
||||
LV2_Event_Buffer* ebuf;
|
||||
LV2_Event* ev;
|
||||
LV2_Atom_Port_Buffer* abuf;
|
||||
LV2_Atom_Event* aev;
|
||||
LV2_Event_Buffer* ebuf;
|
||||
LV2_Event* ev;
|
||||
LV2_Atom_Sequence* aseq;
|
||||
LV2_Atom_Event* aev;
|
||||
switch (iter.evbuf->type) {
|
||||
case LV2_EVBUF_EVENT:
|
||||
ebuf = &iter.evbuf->buf.event;
|
||||
@ -194,9 +202,9 @@ lv2_evbuf_get(LV2_Evbuf_Iterator iter,
|
||||
*data = (uint8_t*)ev + sizeof(LV2_Event);
|
||||
break;
|
||||
case LV2_EVBUF_ATOM:
|
||||
abuf = &iter.evbuf->buf.atom;
|
||||
aseq = (LV2_Atom_Sequence*)&iter.evbuf->buf.atom;
|
||||
aev = (LV2_Atom_Event*)(
|
||||
(char*)LV2_ATOM_CONTENTS(LV2_Atom_Sequence, abuf->data)
|
||||
(char*)LV2_ATOM_CONTENTS(LV2_Atom_Sequence, aseq)
|
||||
+ iter.offset);
|
||||
*frames = aev->time.frames;
|
||||
*subframes = 0;
|
||||
@ -217,10 +225,10 @@ lv2_evbuf_write(LV2_Evbuf_Iterator* iter,
|
||||
uint32_t size,
|
||||
const uint8_t* data)
|
||||
{
|
||||
LV2_Event_Buffer* ebuf;
|
||||
LV2_Event* ev;
|
||||
LV2_Atom_Port_Buffer* abuf;
|
||||
LV2_Atom_Event* aev;
|
||||
LV2_Event_Buffer* ebuf;
|
||||
LV2_Event* ev;
|
||||
LV2_Atom_Sequence* aseq;
|
||||
LV2_Atom_Event* aev;
|
||||
switch (iter->evbuf->type) {
|
||||
case LV2_EVBUF_EVENT:
|
||||
ebuf = &iter->evbuf->buf.event;
|
||||
@ -241,22 +249,23 @@ lv2_evbuf_write(LV2_Evbuf_Iterator* iter,
|
||||
iter->offset += size;
|
||||
break;
|
||||
case LV2_EVBUF_ATOM:
|
||||
abuf = &iter->evbuf->buf.atom;
|
||||
if (abuf->capacity - abuf->data->size < sizeof(LV2_Atom_Event) + size) {
|
||||
aseq = (LV2_Atom_Sequence*)&iter->evbuf->buf.atom;
|
||||
if (iter->evbuf->capacity - sizeof(LV2_Atom) - aseq->atom.size
|
||||
< sizeof(LV2_Atom_Event) + size) {
|
||||
return false;
|
||||
}
|
||||
|
||||
aev = (LV2_Atom_Event*)(
|
||||
(char*)LV2_ATOM_CONTENTS(LV2_Atom_Sequence, abuf->data)
|
||||
(char*)LV2_ATOM_CONTENTS(LV2_Atom_Sequence, aseq)
|
||||
+ iter->offset);
|
||||
aev->time.frames = frames;
|
||||
aev->body.type = type;
|
||||
aev->body.size = size;
|
||||
memcpy(LV2_ATOM_BODY(&aev->body), data, size);
|
||||
|
||||
size = lv2_evbuf_pad_size(sizeof(LV2_Atom_Event) + size);
|
||||
abuf->data->size += size;
|
||||
iter->offset += size;
|
||||
size = lv2_evbuf_pad_size(sizeof(LV2_Atom_Event) + size);
|
||||
aseq->atom.size += size;
|
||||
iter->offset += size;
|
||||
break;
|
||||
}
|
||||
|
||||
|
@ -18,10 +18,11 @@
|
||||
#define LV2_EVBUF_H
|
||||
|
||||
#include <stdint.h>
|
||||
#include <stdbool.h>
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#else
|
||||
#include <stdbool.h>
|
||||
#endif
|
||||
|
||||
/**
|
||||
@ -54,11 +55,13 @@ typedef struct {
|
||||
|
||||
/**
|
||||
Allocate a new, empty event buffer.
|
||||
The URID for atom:Sequence must be passed for atom_Sequence if type is
|
||||
LV2_EVBUF_ATOM.
|
||||
URIDs for atom:Chunk and atom:Sequence must be passed for LV2_EVBUF_ATOM.
|
||||
*/
|
||||
LV2_Evbuf*
|
||||
lv2_evbuf_new(uint32_t capacity, LV2_Evbuf_Type type, uint32_t atom_type);
|
||||
lv2_evbuf_new(uint32_t capacity,
|
||||
LV2_Evbuf_Type type,
|
||||
uint32_t atom_Chunk,
|
||||
uint32_t atom_Sequence);
|
||||
|
||||
/**
|
||||
Free an event buffer allocated with lv2_evbuf_new.
|
||||
@ -67,21 +70,21 @@ void
|
||||
lv2_evbuf_free(LV2_Evbuf* evbuf);
|
||||
|
||||
/**
|
||||
Change the type of an existing event buffer. This will clear and reset the
|
||||
buffer, it is not possible to change the type and preserve the buffer
|
||||
contents since the formats differ. The URID for atom:Sequence must be
|
||||
passed for atom_Sequence if type is LV2_EVBUF_ATOM.
|
||||
Reset and change the type of an existing event buffer.
|
||||
URIDs for atom:Chunk and atom:Sequence must be passed for LV2_EVBUF_ATOM.
|
||||
*/
|
||||
void
|
||||
lv2_evbuf_set_type(LV2_Evbuf* evbuf, LV2_Evbuf_Type type, uint32_t atom_type);
|
||||
lv2_evbuf_set_type(LV2_Evbuf* evbuf, LV2_Evbuf_Type type);
|
||||
|
||||
/**
|
||||
Clear and initialize an existing event buffer.
|
||||
The contents of buf are ignored entirely and overwritten, except capacity
|
||||
which is unmodified.
|
||||
If input is false and this is an atom buffer, the buffer will be prepared
|
||||
for writing by the plugin. This MUST be called before every run cycle.
|
||||
*/
|
||||
void
|
||||
lv2_evbuf_reset(LV2_Evbuf* evbuf);
|
||||
lv2_evbuf_reset(LV2_Evbuf* evbuf, bool input);
|
||||
|
||||
/**
|
||||
Return the total padded size of the events stored in the buffer.
|
||||
|
@ -74,6 +74,8 @@ uint32_t LV2Plugin::_midi_event_type_ev = _uri_map.uri_to_id(
|
||||
uint32_t LV2Plugin::_midi_event_type = _uri_map.uri_to_id(
|
||||
NULL,
|
||||
"http://lv2plug.in/ns/ext/midi#MidiEvent");
|
||||
uint32_t LV2Plugin::_chunk_type = _uri_map.uri_to_id(
|
||||
NULL, LV2_ATOM__Chunk);
|
||||
uint32_t LV2Plugin::_sequence_type = _uri_map.uri_to_id(
|
||||
NULL, LV2_ATOM__Sequence);
|
||||
uint32_t LV2Plugin::_event_transfer_type = _uri_map.uri_to_id(
|
||||
@ -88,6 +90,7 @@ public:
|
||||
|
||||
LilvWorld* world;
|
||||
|
||||
LilvNode* atom_Chunk;
|
||||
LilvNode* atom_MessagePort;
|
||||
LilvNode* atom_Sequence;
|
||||
LilvNode* atom_bufferType;
|
||||
@ -231,25 +234,7 @@ LV2Plugin::init(void* c_plugin, framecnt_t rate)
|
||||
for (uint32_t i = 0; i < num_ports; ++i) {
|
||||
const LilvPort* port = lilv_plugin_get_port_by_index(_impl->plugin, i);
|
||||
PortFlags flags = 0;
|
||||
if (lilv_port_is_a(_impl->plugin, port, _world.lv2_ControlPort)) {
|
||||
flags |= PORT_CONTROL;
|
||||
} else if (lilv_port_is_a(_impl->plugin, port, _world.lv2_AudioPort)) {
|
||||
flags |= PORT_AUDIO;
|
||||
} else if (lilv_port_is_a(_impl->plugin, port, _world.ev_EventPort)) {
|
||||
flags |= PORT_EVENT;
|
||||
} else if (lilv_port_is_a(_impl->plugin, port, _world.atom_MessagePort)) {
|
||||
LilvNodes* buffer_types = lilv_port_get_value(
|
||||
_impl->plugin, port, _world.atom_bufferType);
|
||||
if (lilv_nodes_contains(buffer_types, _world.atom_Sequence)) {
|
||||
flags |= PORT_MESSAGE;
|
||||
}
|
||||
lilv_nodes_free(buffer_types);
|
||||
} else {
|
||||
error << string_compose(
|
||||
"LV2: \"%1\" port %2 has no known data type",
|
||||
lilv_node_as_string(_impl->name), i) << endmsg;
|
||||
throw failed_constructor();
|
||||
}
|
||||
|
||||
if (lilv_port_is_a(_impl->plugin, port, _world.lv2_OutputPort)) {
|
||||
flags |= PORT_OUTPUT;
|
||||
} else if (lilv_port_is_a(_impl->plugin, port, _world.lv2_InputPort)) {
|
||||
@ -260,6 +245,27 @@ LV2Plugin::init(void* c_plugin, framecnt_t rate)
|
||||
lilv_node_as_string(_impl->name), i) << endmsg;
|
||||
throw failed_constructor();
|
||||
}
|
||||
|
||||
if (lilv_port_is_a(_impl->plugin, port, _world.lv2_ControlPort)) {
|
||||
flags |= PORT_CONTROL;
|
||||
} else if (lilv_port_is_a(_impl->plugin, port, _world.lv2_AudioPort)) {
|
||||
flags |= PORT_AUDIO;
|
||||
} else if (lilv_port_is_a(_impl->plugin, port, _world.ev_EventPort)) {
|
||||
flags |= PORT_EVENT;
|
||||
} else if (lilv_port_is_a(_impl->plugin, port, _world.atom_MessagePort)) {
|
||||
LilvNodes* buffer_types = lilv_port_get_value(
|
||||
_impl->plugin, port, _world.atom_bufferType);
|
||||
if (lilv_nodes_contains(buffer_types, _world.atom_Sequence)) {
|
||||
flags |= PORT_MESSAGE;
|
||||
}
|
||||
lilv_nodes_free(buffer_types);
|
||||
} else {
|
||||
error << string_compose(
|
||||
"LV2: \"%1\" port %2 has no known data type",
|
||||
lilv_node_as_string(_impl->name), i) << endmsg;
|
||||
throw failed_constructor();
|
||||
}
|
||||
|
||||
_port_flags.push_back(flags);
|
||||
}
|
||||
|
||||
@ -1097,18 +1103,17 @@ LV2Plugin::connect_and_run(BufferSet& bufs,
|
||||
be necessary, but the mapping is illegal in some cases. Ideally
|
||||
that should be fixed, but this is easier...
|
||||
*/
|
||||
const uint32_t atom_type = (flags & PORT_MESSAGE) ? _sequence_type : 0;
|
||||
if (flags & PORT_INPUT) {
|
||||
index = in_map.get(DataType::MIDI, midi_in_index++, &valid);
|
||||
_ev_buffers[port_index] = (valid && bufs.count().n_midi() > index)
|
||||
? bufs.get_lv2_midi(true, index, atom_type)
|
||||
: silent_bufs.get_lv2_midi(true, 0, atom_type);
|
||||
? bufs.get_lv2_midi(true, index, flags & PORT_EVENT)
|
||||
: silent_bufs.get_lv2_midi(true, 0, flags & PORT_EVENT);
|
||||
buf = lv2_evbuf_get_buffer(_ev_buffers[port_index]);
|
||||
} else {
|
||||
index = out_map.get(DataType::MIDI, midi_out_index++, &valid);
|
||||
_ev_buffers[port_index] = (valid && bufs.count().n_midi() > index)
|
||||
? bufs.get_lv2_midi(false, index, atom_type)
|
||||
: scratch_bufs.get_lv2_midi(false, 0, atom_type);
|
||||
? bufs.get_lv2_midi(false, index, flags & PORT_EVENT)
|
||||
: scratch_bufs.get_lv2_midi(false, 0, flags & PORT_EVENT);
|
||||
buf = lv2_evbuf_get_buffer(_ev_buffers[port_index]);
|
||||
}
|
||||
} else {
|
||||
@ -1313,6 +1318,7 @@ LV2World::LV2World()
|
||||
: world(lilv_world_new())
|
||||
{
|
||||
lilv_world_load_all(world);
|
||||
atom_Chunk = lilv_new_uri(world, LV2_ATOM__Chunk);
|
||||
atom_MessagePort = lilv_new_uri(world, LV2_ATOM__MessagePort);
|
||||
atom_Sequence = lilv_new_uri(world, LV2_ATOM__Sequence);
|
||||
atom_bufferType = lilv_new_uri(world, LV2_ATOM__bufferType);
|
||||
@ -1351,6 +1357,7 @@ LV2World::~LV2World()
|
||||
lilv_node_free(atom_bufferType);
|
||||
lilv_node_free(atom_Sequence);
|
||||
lilv_node_free(atom_MessagePort);
|
||||
lilv_node_free(atom_Chunk);
|
||||
}
|
||||
|
||||
LV2PluginInfo::LV2PluginInfo (void* c_plugin)
|
||||
|
Loading…
Reference in New Issue
Block a user