Browse Source

Move VST3 message related code to plugin side

Signed-off-by: falkTX <falktx@falktx.com>
pull/330/head
falkTX 3 years ago
parent
commit
d36ee9f19d
Signed by: falkTX <falktx@falktx.com> GPG Key ID: CDBAA37ABC74FBA0
2 changed files with 400 additions and 397 deletions
  1. +400
    -1
      distrho/src/DistrhoPluginVST3.cpp
  2. +0
    -396
      distrho/src/DistrhoUIVST3.cpp

+ 400
- 1
distrho/src/DistrhoPluginVST3.cpp View File

@@ -38,6 +38,8 @@
#include "travesty/message.h"

#include <atomic>
#include <map>
#include <string>
#include <vector>

/* TODO items:
@@ -269,7 +271,22 @@ static constexpr void (*const snprintf_f32_utf16)(int16_t*, float, size_t) = snp
static constexpr void (*const snprintf_u32_utf16)(int16_t*, uint32_t, size_t) = snprintf_utf16_t<uint32_t, format_u32>;

// --------------------------------------------------------------------------------------------------------------------
// TESTING
// custom attribute list struct, used for sending utf8 strings

struct v3_attribute_list_utf8 {
struct v3_funknown;
V3_API v3_result (*set_string_utf8)(void* self, const char* id, const char* string);
V3_API v3_result (*get_string_utf8)(void* self, const char* id, char* string, uint32_t size);
};

static constexpr const v3_tuid v3_attribute_list_utf8_iid =
V3_ID(d_cconst('D','P','F',' '),
d_cconst('c','l','a','s'),
d_cconst('a','t','t','r'),
d_cconst('u','t','f','8'));

// --------------------------------------------------------------------------------------------------------------------
// create message object (implementation comes later)

v3_message** dpf_message_create(const char* id);

@@ -1593,6 +1610,388 @@ private:
v3_plugin_view** dpf_plugin_view_create(void* instancePointer, double sampleRate);
#endif

// --------------------------------------------------------------------------------------------------------------------

struct dpf_attribute_value {
char type; // one of: i, f, s, b
union {
int64_t integer;
double v_float;
int16_t* string;
struct {
void* ptr;
uint32_t size;
} binary;
};
};

static void dpf_attribute_list_free(std::map<std::string, dpf_attribute_value>& attrs)
{
for (auto& it : attrs)
{
dpf_attribute_value& v(it.second);

switch (v.type)
{
case 's':
case 'b':
std::free(v.binary.ptr);
break;
}
}
}

// --------------------------------------------------------------------------------------------------------------------
// dpf_attribute_list_utf8 (the custom variant)

struct v3_attribute_list_utf8_cpp : v3_funknown {
v3_attribute_list_utf8 attr;
};

struct dpf_attribute_list_utf8 : v3_attribute_list_utf8_cpp {
std::map<std::string, dpf_attribute_value>& attrs;

dpf_attribute_list_utf8(std::map<std::string, dpf_attribute_value>& a)
: attrs(a)
{
static const uint8_t* kSupportedInterfaces[] = {
v3_funknown_iid,
v3_attribute_list_utf8_iid
};

// ------------------------------------------------------------------------------------------------------------
// v3_funknown

query_interface = []V3_API(void* self, const v3_tuid iid, void** iface) -> v3_result
{
d_stdout("dpf_attribute_list_utf8::query_interface => %p %s %p", self, tuid2str(iid), iface);
*iface = NULL;
DISTRHO_SAFE_ASSERT_RETURN(self != nullptr, V3_NO_INTERFACE);

for (const uint8_t* interface_iid : kSupportedInterfaces)
{
if (v3_tuid_match(interface_iid, iid))
{
*iface = self;
return V3_OK;
}
}

return V3_NO_INTERFACE;
};

// there is only a single instance of this, so we don't have to care here
ref = []V3_API(void*) -> uint32_t { return 1; };
unref = []V3_API(void*) -> uint32_t { return 0; };

// ------------------------------------------------------------------------------------------------------------
// v3_attribute_list_utf8

attr.set_string_utf8 = []V3_API(void* self, const char* id, const char* string) -> v3_result
{
dpf_attribute_list_utf8* const attr = *(dpf_attribute_list_utf8**)self;
DISTRHO_SAFE_ASSERT_RETURN(attr != nullptr, V3_NOT_INITIALISED);

const uint32_t size = std::strlen(string) + 1;
int16_t* const copy = (int16_t*)std::malloc(sizeof(int16_t) * size);
DISTRHO_SAFE_ASSERT_RETURN(copy != nullptr, V3_NOMEM);

DISTRHO_NAMESPACE::strncpy_utf16(copy, string, size);

dpf_attribute_value& attrval(attr->attrs[id]);
attrval.type = 's';
attrval.binary.ptr = copy;
attrval.binary.size = sizeof(int16_t) * size;
return V3_OK;
};

attr.get_string_utf8 = []V3_API(void* self, const char* id, char*, uint32_t) -> v3_result
{
dpf_attribute_list_utf8* const attr = *(dpf_attribute_list_utf8**)self;
DISTRHO_SAFE_ASSERT_RETURN(attr != nullptr, V3_NOT_INITIALISED);

if (attr->attrs.find(id) == attr->attrs.end())
return V3_INVALID_ARG;

return V3_NOT_IMPLEMENTED;
};
}
};

// --------------------------------------------------------------------------------------------------------------------
// dpf_attribute_list

struct dpf_attribute_list : v3_attribute_list_cpp {
ScopedPointer<dpf_attribute_list_utf8> attrutf8;
std::map<std::string, dpf_attribute_value> attrs;

dpf_attribute_list()
{
static const uint8_t* kSupportedInterfacesBase[] = {
v3_funknown_iid,
v3_attribute_list_iid
};

// ------------------------------------------------------------------------------------------------------------
// v3_funknown

query_interface = []V3_API(void* self, const v3_tuid iid, void** iface) -> v3_result
{
d_stdout("dpf_attribute_list::query_interface => %p %s %p", self, tuid2str(iid), iface);
*iface = NULL;
DISTRHO_SAFE_ASSERT_RETURN(self != nullptr, V3_NO_INTERFACE);

for (const uint8_t* interface_iid : kSupportedInterfacesBase)
{
if (v3_tuid_match(interface_iid, iid))
{
*iface = self;
return V3_OK;
}
}

dpf_attribute_list* const attr = *(dpf_attribute_list**)self;
DISTRHO_SAFE_ASSERT_RETURN(attr != nullptr, V3_NO_INTERFACE);

if (v3_tuid_match(v3_attribute_list_utf8_iid, iid))
{
if (attr->attrutf8 == nullptr)
attr->attrutf8 = new dpf_attribute_list_utf8(attr->attrs);
*iface = &attr->attrutf8;
return V3_OK;
}

return V3_NO_INTERFACE;
};

// there is only a single instance of this, so we don't have to care here
ref = []V3_API(void*) -> uint32_t { return 1; };
unref = []V3_API(void*) -> uint32_t { return 0; };

// ------------------------------------------------------------------------------------------------------------
// v3_attribute_list

attrlist.set_int = []V3_API(void* self, const char* id, int64_t value) -> v3_result
{
dpf_attribute_list* const attr = *(dpf_attribute_list**)self;
DISTRHO_SAFE_ASSERT_RETURN(attr != nullptr, V3_NOT_INITIALISED);

dpf_attribute_value& attrval(attr->attrs[id]);
attrval.type = 'i';
attrval.integer = value;
return V3_OK;
};

attrlist.get_int = []V3_API(void* self, const char* id, int64_t* value) -> v3_result
{
dpf_attribute_list* const attr = *(dpf_attribute_list**)self;
DISTRHO_SAFE_ASSERT_RETURN(attr != nullptr, V3_NOT_INITIALISED);

if (attr->attrs.find(id) == attr->attrs.end())
return V3_INVALID_ARG;

const dpf_attribute_value& attrval(attr->attrs[id]);
DISTRHO_SAFE_ASSERT_RETURN(attrval.type == 'i', V3_INVALID_ARG);

*value = attrval.integer;
return V3_OK;
};

attrlist.set_float = []V3_API(void* self, const char* id, double value) -> v3_result
{
dpf_attribute_list* const attr = *(dpf_attribute_list**)self;
DISTRHO_SAFE_ASSERT_RETURN(attr != nullptr, V3_NOT_INITIALISED);

dpf_attribute_value& attrval(attr->attrs[id]);
attrval.type = 'f';
attrval.v_float = value;
return V3_OK;
};

attrlist.get_float = []V3_API(void* self, const char* id, double* value) -> v3_result
{
dpf_attribute_list* const attr = *(dpf_attribute_list**)self;
DISTRHO_SAFE_ASSERT_RETURN(attr != nullptr, V3_NOT_INITIALISED);

if (attr->attrs.find(id) == attr->attrs.end())
return V3_INVALID_ARG;

const dpf_attribute_value& attrval(attr->attrs[id]);
DISTRHO_SAFE_ASSERT_RETURN(attrval.type == 'f', V3_INVALID_ARG);

*value = attrval.v_float;
return V3_OK;
};

attrlist.set_string = []V3_API(void* self, const char* id, const int16_t* /*string*/) -> v3_result
{
dpf_attribute_list* const attr = *(dpf_attribute_list**)self;
DISTRHO_SAFE_ASSERT_RETURN(attr != nullptr, V3_NOT_INITIALISED);

dpf_attribute_value& attrval(attr->attrs[id]);
attrval.type = 's';
attrval.binary.ptr = nullptr;
attrval.binary.size = 0;
return V3_NOT_IMPLEMENTED;
};

attrlist.get_string = []V3_API(void* self, const char* id, int16_t* /*string*/, uint32_t /*size*/) -> v3_result
{
dpf_attribute_list* const attr = *(dpf_attribute_list**)self;
DISTRHO_SAFE_ASSERT_RETURN(attr != nullptr, V3_NOT_INITIALISED);

if (attr->attrs.find(id) == attr->attrs.end())
return V3_INVALID_ARG;

const dpf_attribute_value& attrval(attr->attrs[id]);
DISTRHO_SAFE_ASSERT_RETURN(attrval.type == 's', V3_INVALID_ARG);

return V3_NOT_IMPLEMENTED;
};

attrlist.set_binary = []V3_API(void* self, const char* id, const void* data, uint32_t size) -> v3_result
{
dpf_attribute_list* const attr = *(dpf_attribute_list**)self;
DISTRHO_SAFE_ASSERT_RETURN(attr != nullptr, V3_NOT_INITIALISED);

void* const copy = std::malloc(size);
DISTRHO_SAFE_ASSERT_RETURN(copy != nullptr, V3_NOMEM);

std::memcpy(copy, data, size);

dpf_attribute_value& attrval(attr->attrs[id]);
attrval.type = 'b';
attrval.binary.ptr = copy;
attrval.binary.size = size;
return V3_NOT_IMPLEMENTED;
};

attrlist.get_binary = []V3_API(void* self, const char* id, const void** data, uint32_t* size) -> v3_result
{
dpf_attribute_list* const attr = *(dpf_attribute_list**)self;
DISTRHO_SAFE_ASSERT_RETURN(attr != nullptr, V3_NOT_INITIALISED);

if (attr->attrs.find(id) == attr->attrs.end())
return V3_INVALID_ARG;

const dpf_attribute_value& attrval(attr->attrs[id]);
DISTRHO_SAFE_ASSERT_RETURN(attrval.type == 's' || attrval.type == 'b', V3_INVALID_ARG);

*data = attrval.binary.ptr;
*size = attrval.binary.size;
return V3_OK;
};
}
};

// --------------------------------------------------------------------------------------------------------------------
// dpf_message

struct dpf_message : v3_message_cpp {
std::atomic<int> refcounter;
ScopedPointer<dpf_message>* self;
ScopedPointer<dpf_attribute_list> attrlist;
String id;

dpf_message(ScopedPointer<dpf_message>* const s, const char* const id2)
: self(s),
id(id2)
{
static const uint8_t* kSupportedInterfaces[] = {
v3_funknown_iid,
v3_message_iid
};

// ------------------------------------------------------------------------------------------------------------
// v3_funknown

query_interface = []V3_API(void* self, const v3_tuid iid, void** iface) -> v3_result
{
d_stdout("dpf_plugin_view::query_interface => %p %s %p", self, tuid2str(iid), iface);
*iface = NULL;
DISTRHO_SAFE_ASSERT_RETURN(self != nullptr, V3_NO_INTERFACE);

for (const uint8_t* interface_iid : kSupportedInterfaces)
{
if (v3_tuid_match(interface_iid, iid))
{
*iface = self;
return V3_OK;
}
}

return V3_NO_INTERFACE;
};

ref = []V3_API(void* const self) -> uint32_t
{
d_stdout("dpf_message::ref => %p", self);
dpf_message** const messageptr = static_cast<dpf_message**>(self);
DISTRHO_SAFE_ASSERT_RETURN(messageptr != nullptr, 0);
dpf_message* const message = *messageptr;
DISTRHO_SAFE_ASSERT_RETURN(message != nullptr, 0);

return ++message->refcounter;
};

unref = []V3_API(void* const self) -> uint32_t
{
d_stdout("dpf_message::unref => %p", self);
dpf_message** const messageptr = static_cast<dpf_message**>(self);
DISTRHO_SAFE_ASSERT_RETURN(messageptr != nullptr, 0);
dpf_message* const message = *messageptr;
DISTRHO_SAFE_ASSERT_RETURN(message != nullptr, 0);

if (const int refcounter = --message->refcounter)
return refcounter;

if (message->attrlist != nullptr)
dpf_attribute_list_free(message->attrlist->attrs);

*message->self = nullptr;
delete messageptr;
return 0;
};

msg.get_message_id = []V3_API(void* const self) -> const char*
{
d_stdout("dpf_message::get_message_id => %p", self);
dpf_message* const message = *(dpf_message**)self;
DISTRHO_SAFE_ASSERT_RETURN(message != nullptr, nullptr);

return message->id;
};

msg.set_message_id = []V3_API(void* const self, const char* const id) -> void
{
d_stdout("dpf_message::set_message_id => %p %s", self, id);
dpf_message* const message = *(dpf_message**)self;
DISTRHO_SAFE_ASSERT_RETURN(message != nullptr,);

message->id = id;
};

msg.get_attributes = []V3_API(void* const self) -> v3_attribute_list**
{
d_stdout("dpf_message::get_attributes => %p", self);
dpf_message* const message = *(dpf_message**)self;
DISTRHO_SAFE_ASSERT_RETURN(message != nullptr, nullptr);

if (message->attrlist == nullptr)
message->attrlist = new dpf_attribute_list();

return (v3_attribute_list**)&message->attrlist;
};
}
};

v3_message** dpf_message_create(const char* const id)
{
ScopedPointer<dpf_message>* const messageptr = new ScopedPointer<dpf_message>;
*messageptr = new dpf_message(messageptr, id);
return static_cast<v3_message**>(static_cast<void*>(messageptr));
}

// --------------------------------------------------------------------------------------------------------------------
// dpf_dsp_connection_point



+ 0
- 396
distrho/src/DistrhoUIVST3.cpp View File

@@ -44,10 +44,6 @@
#include "travesty/message.h"
#include "travesty/view.h"

#include <atomic>
#include <map>
#include <string>

/* TODO items:
* - disable UI if non-embed UI build
* - sample rate change listener
@@ -71,21 +67,11 @@ static constexpr const setStateFunc setStateCallback = nullptr;

const char* tuid2str(const v3_tuid iid);
void strncpy_utf16(int16_t* dst, const char* src, size_t length);

// --------------------------------------------------------------------------------------------------------------------
// create message object (needed by the UI class, implementation comes later)

v3_message** dpf_message_create(const char* id);

// --------------------------------------------------------------------------------------------------------------------
// custom attribute list struct, used for sending utf8 strings

struct v3_attribute_list_utf8 {
struct v3_funknown;
V3_API v3_result (*set_string_utf8)(void* self, const char* id, const char* string);
V3_API v3_result (*get_string_utf8)(void* self, const char* id, char* string, uint32_t size);
};

static constexpr const v3_tuid v3_attribute_list_utf8_iid =
V3_ID(d_cconst('D','P','F',' '),
d_cconst('c','l','a','s'),
@@ -466,388 +452,6 @@ private:
* VST3 low-level pointer thingies follow, proceed with care.
*/

// --------------------------------------------------------------------------------------------------------------------

struct dpf_attribute_value {
char type; // one of: i, f, s, b
union {
int64_t integer;
double v_float;
int16_t* string;
struct {
void* ptr;
uint32_t size;
} binary;
};
};

static void dpf_attribute_list_free(std::map<std::string, dpf_attribute_value>& attrs)
{
for (auto& it : attrs)
{
dpf_attribute_value& v(it.second);

switch (v.type)
{
case 's':
case 'b':
std::free(v.binary.ptr);
break;
}
}
}

// --------------------------------------------------------------------------------------------------------------------
// dpf_attribute_list_utf8 (the custom variant)

struct v3_attribute_list_utf8_cpp : v3_funknown {
v3_attribute_list_utf8 attr;
};

struct dpf_attribute_list_utf8 : v3_attribute_list_utf8_cpp {
std::map<std::string, dpf_attribute_value>& attrs;

dpf_attribute_list_utf8(std::map<std::string, dpf_attribute_value>& a)
: attrs(a)
{
static const uint8_t* kSupportedInterfaces[] = {
v3_funknown_iid,
v3_attribute_list_utf8_iid
};

// ------------------------------------------------------------------------------------------------------------
// v3_funknown

query_interface = []V3_API(void* self, const v3_tuid iid, void** iface) -> v3_result
{
d_stdout("dpf_attribute_list_utf8::query_interface => %p %s %p", self, tuid2str(iid), iface);
*iface = NULL;
DISTRHO_SAFE_ASSERT_RETURN(self != nullptr, V3_NO_INTERFACE);

for (const uint8_t* interface_iid : kSupportedInterfaces)
{
if (v3_tuid_match(interface_iid, iid))
{
*iface = self;
return V3_OK;
}
}

return V3_NO_INTERFACE;
};

// there is only a single instance of this, so we don't have to care here
ref = []V3_API(void*) -> uint32_t { return 1; };
unref = []V3_API(void*) -> uint32_t { return 0; };

// ------------------------------------------------------------------------------------------------------------
// v3_attribute_list_utf8

attr.set_string_utf8 = []V3_API(void* self, const char* id, const char* string) -> v3_result
{
dpf_attribute_list_utf8* const attr = *(dpf_attribute_list_utf8**)self;
DISTRHO_SAFE_ASSERT_RETURN(attr != nullptr, V3_NOT_INITIALISED);

const uint32_t size = std::strlen(string) + 1;
int16_t* const copy = (int16_t*)std::malloc(sizeof(int16_t) * size);
DISTRHO_SAFE_ASSERT_RETURN(copy != nullptr, V3_NOMEM);

DISTRHO_NAMESPACE::strncpy_utf16(copy, string, size);

dpf_attribute_value& attrval(attr->attrs[id]);
attrval.type = 's';
attrval.binary.ptr = copy;
attrval.binary.size = sizeof(int16_t) * size;
return V3_OK;
};

attr.get_string_utf8 = []V3_API(void* self, const char* id, char*, uint32_t) -> v3_result
{
dpf_attribute_list_utf8* const attr = *(dpf_attribute_list_utf8**)self;
DISTRHO_SAFE_ASSERT_RETURN(attr != nullptr, V3_NOT_INITIALISED);

if (attr->attrs.find(id) == attr->attrs.end())
return V3_INVALID_ARG;

return V3_NOT_IMPLEMENTED;
};
}
};

// --------------------------------------------------------------------------------------------------------------------
// dpf_attribute_list

struct dpf_attribute_list : v3_attribute_list_cpp {
ScopedPointer<dpf_attribute_list_utf8> attrutf8;
std::map<std::string, dpf_attribute_value> attrs;

dpf_attribute_list()
{
static const uint8_t* kSupportedInterfacesBase[] = {
v3_funknown_iid,
v3_attribute_list_iid
};

// ------------------------------------------------------------------------------------------------------------
// v3_funknown

query_interface = []V3_API(void* self, const v3_tuid iid, void** iface) -> v3_result
{
d_stdout("dpf_attribute_list::query_interface => %p %s %p", self, tuid2str(iid), iface);
*iface = NULL;
DISTRHO_SAFE_ASSERT_RETURN(self != nullptr, V3_NO_INTERFACE);

for (const uint8_t* interface_iid : kSupportedInterfacesBase)
{
if (v3_tuid_match(interface_iid, iid))
{
*iface = self;
return V3_OK;
}
}

dpf_attribute_list* const attr = *(dpf_attribute_list**)self;
DISTRHO_SAFE_ASSERT_RETURN(attr != nullptr, V3_NO_INTERFACE);

if (v3_tuid_match(v3_attribute_list_utf8_iid, iid))
{
if (attr->attrutf8 == nullptr)
attr->attrutf8 = new dpf_attribute_list_utf8(attr->attrs);
*iface = &attr->attrutf8;
return V3_OK;
}

return V3_NO_INTERFACE;
};

// there is only a single instance of this, so we don't have to care here
ref = []V3_API(void*) -> uint32_t { return 1; };
unref = []V3_API(void*) -> uint32_t { return 0; };

// ------------------------------------------------------------------------------------------------------------
// v3_attribute_list

attrlist.set_int = []V3_API(void* self, const char* id, int64_t value) -> v3_result
{
dpf_attribute_list* const attr = *(dpf_attribute_list**)self;
DISTRHO_SAFE_ASSERT_RETURN(attr != nullptr, V3_NOT_INITIALISED);

dpf_attribute_value& attrval(attr->attrs[id]);
attrval.type = 'i';
attrval.integer = value;
return V3_OK;
};

attrlist.get_int = []V3_API(void* self, const char* id, int64_t* value) -> v3_result
{
dpf_attribute_list* const attr = *(dpf_attribute_list**)self;
DISTRHO_SAFE_ASSERT_RETURN(attr != nullptr, V3_NOT_INITIALISED);

if (attr->attrs.find(id) == attr->attrs.end())
return V3_INVALID_ARG;

const dpf_attribute_value& attrval(attr->attrs[id]);
DISTRHO_SAFE_ASSERT_RETURN(attrval.type == 'i', V3_INVALID_ARG);

*value = attrval.integer;
return V3_OK;
};

attrlist.set_float = []V3_API(void* self, const char* id, double value) -> v3_result
{
dpf_attribute_list* const attr = *(dpf_attribute_list**)self;
DISTRHO_SAFE_ASSERT_RETURN(attr != nullptr, V3_NOT_INITIALISED);

dpf_attribute_value& attrval(attr->attrs[id]);
attrval.type = 'f';
attrval.v_float = value;
return V3_OK;
};

attrlist.get_float = []V3_API(void* self, const char* id, double* value) -> v3_result
{
dpf_attribute_list* const attr = *(dpf_attribute_list**)self;
DISTRHO_SAFE_ASSERT_RETURN(attr != nullptr, V3_NOT_INITIALISED);

if (attr->attrs.find(id) == attr->attrs.end())
return V3_INVALID_ARG;

const dpf_attribute_value& attrval(attr->attrs[id]);
DISTRHO_SAFE_ASSERT_RETURN(attrval.type == 'f', V3_INVALID_ARG);

*value = attrval.v_float;
return V3_OK;
};

attrlist.set_string = []V3_API(void* self, const char* id, const int16_t* /*string*/) -> v3_result
{
dpf_attribute_list* const attr = *(dpf_attribute_list**)self;
DISTRHO_SAFE_ASSERT_RETURN(attr != nullptr, V3_NOT_INITIALISED);

dpf_attribute_value& attrval(attr->attrs[id]);
attrval.type = 's';
attrval.binary.ptr = nullptr;
attrval.binary.size = 0;
return V3_NOT_IMPLEMENTED;
};

attrlist.get_string = []V3_API(void* self, const char* id, int16_t* /*string*/, uint32_t /*size*/) -> v3_result
{
dpf_attribute_list* const attr = *(dpf_attribute_list**)self;
DISTRHO_SAFE_ASSERT_RETURN(attr != nullptr, V3_NOT_INITIALISED);

if (attr->attrs.find(id) == attr->attrs.end())
return V3_INVALID_ARG;

const dpf_attribute_value& attrval(attr->attrs[id]);
DISTRHO_SAFE_ASSERT_RETURN(attrval.type == 's', V3_INVALID_ARG);

return V3_NOT_IMPLEMENTED;
};

attrlist.set_binary = []V3_API(void* self, const char* id, const void* data, uint32_t size) -> v3_result
{
dpf_attribute_list* const attr = *(dpf_attribute_list**)self;
DISTRHO_SAFE_ASSERT_RETURN(attr != nullptr, V3_NOT_INITIALISED);

void* const copy = std::malloc(size);
DISTRHO_SAFE_ASSERT_RETURN(copy != nullptr, V3_NOMEM);

std::memcpy(copy, data, size);

dpf_attribute_value& attrval(attr->attrs[id]);
attrval.type = 'b';
attrval.binary.ptr = copy;
attrval.binary.size = size;
return V3_NOT_IMPLEMENTED;
};

attrlist.get_binary = []V3_API(void* self, const char* id, const void** data, uint32_t* size) -> v3_result
{
dpf_attribute_list* const attr = *(dpf_attribute_list**)self;
DISTRHO_SAFE_ASSERT_RETURN(attr != nullptr, V3_NOT_INITIALISED);

if (attr->attrs.find(id) == attr->attrs.end())
return V3_INVALID_ARG;

const dpf_attribute_value& attrval(attr->attrs[id]);
DISTRHO_SAFE_ASSERT_RETURN(attrval.type == 's' || attrval.type == 'b', V3_INVALID_ARG);

*data = attrval.binary.ptr;
*size = attrval.binary.size;
return V3_OK;
};
}
};

// --------------------------------------------------------------------------------------------------------------------
// dpf_message

struct dpf_message : v3_message_cpp {
std::atomic<int> refcounter;
ScopedPointer<dpf_message>* self;
ScopedPointer<dpf_attribute_list> attrlist;
String id;

dpf_message(ScopedPointer<dpf_message>* const s, const char* const id2)
: self(s),
id(id2)
{
static const uint8_t* kSupportedInterfaces[] = {
v3_funknown_iid,
v3_message_iid
};

// ------------------------------------------------------------------------------------------------------------
// v3_funknown

query_interface = []V3_API(void* self, const v3_tuid iid, void** iface) -> v3_result
{
d_stdout("dpf_plugin_view::query_interface => %p %s %p", self, tuid2str(iid), iface);
*iface = NULL;
DISTRHO_SAFE_ASSERT_RETURN(self != nullptr, V3_NO_INTERFACE);

for (const uint8_t* interface_iid : kSupportedInterfaces)
{
if (v3_tuid_match(interface_iid, iid))
{
*iface = self;
return V3_OK;
}
}

return V3_NO_INTERFACE;
};

ref = []V3_API(void* const self) -> uint32_t
{
d_stdout("dpf_message::ref => %p", self);
dpf_message** const messageptr = static_cast<dpf_message**>(self);
DISTRHO_SAFE_ASSERT_RETURN(messageptr != nullptr, 0);
dpf_message* const message = *messageptr;
DISTRHO_SAFE_ASSERT_RETURN(message != nullptr, 0);

return ++message->refcounter;
};

unref = []V3_API(void* const self) -> uint32_t
{
d_stdout("dpf_message::unref => %p", self);
dpf_message** const messageptr = static_cast<dpf_message**>(self);
DISTRHO_SAFE_ASSERT_RETURN(messageptr != nullptr, 0);
dpf_message* const message = *messageptr;
DISTRHO_SAFE_ASSERT_RETURN(message != nullptr, 0);

if (const int refcounter = --message->refcounter)
return refcounter;

if (message->attrlist != nullptr)
dpf_attribute_list_free(message->attrlist->attrs);

*message->self = nullptr;
delete messageptr;
return 0;
};

msg.get_message_id = []V3_API(void* const self) -> const char*
{
d_stdout("dpf_message::get_message_id => %p", self);
dpf_message* const message = *(dpf_message**)self;
DISTRHO_SAFE_ASSERT_RETURN(message != nullptr, nullptr);

return message->id;
};

msg.set_message_id = []V3_API(void* const self, const char* const id) -> void
{
d_stdout("dpf_message::set_message_id => %p %s", self, id);
dpf_message* const message = *(dpf_message**)self;
DISTRHO_SAFE_ASSERT_RETURN(message != nullptr,);

message->id = id;
};

msg.get_attributes = []V3_API(void* const self) -> v3_attribute_list**
{
d_stdout("dpf_message::get_attributes => %p", self);
dpf_message* const message = *(dpf_message**)self;
DISTRHO_SAFE_ASSERT_RETURN(message != nullptr, nullptr);

if (message->attrlist == nullptr)
message->attrlist = new dpf_attribute_list();

return (v3_attribute_list**)&message->attrlist;
};
}
};

v3_message** dpf_message_create(const char* const id)
{
ScopedPointer<dpf_message>* const messageptr = new ScopedPointer<dpf_message>;
*messageptr = new dpf_message(messageptr, id);
return static_cast<v3_message**>(static_cast<void*>(messageptr));
}

// --------------------------------------------------------------------------------------------------------------------
// dpf_plugin_view_content_scale



Loading…
Cancel
Save