[LV2] LV2 + midnam

Robin Gareus robin at gareus.org
Sat Nov 12 08:17:54 PST 2016

On 11/12/2016 04:54 PM, Bent Bisballe Nyeng wrote:
> On 11/01/16 19:48, Robin Gareus wrote:
>> On 10/29/2016 02:56 AM, Robin Gareus wrote:
>> [..]
>>> The simplest is probably to pass around .midnam files.
>>> Since mappings in plugins can change dynamically a LV2 extension:
>>>  - host asks plugin for the midnam
>>>  - plugin can ask host to re-read it.
>>> The nice part is that most DAWs and sequencers already support midnam.
>> Here's a first draft (working prototype in ardour-git 5.4-249-ge08c803)
>> #define LV2_MIDNAM_URI "http://ardour.org/lv2/midnam"
>> #define LV2_MIDNAM__interface LV2_MIDNAM_PREFIX "interface"
>> #define LV2_MIDNAM__update LV2_MIDNAM_PREFIX "update"
>> typedef void* LV2_Midnam_Handle;
>> /** a LV2 Feature provided by the Host to the plugin */
>> typedef struct {
>>   /** Opaque host data */
>>   LV2_Midnam_Handle handle;
>>   /** Request from run() that the host should re-read the midnam */
>>   void (*update)(LV2_Midnam_Handle handle);
>> } LV2_Midnam;
>> typedef struct {
>>   /** Query midnam document. The plugin
>>    * is expected to return a null-terminated XML
>>    * text which is a valid midnam description
>>    * (or NULL in case of error).
>>    *
>>    * The midnam <Model> must be unique and
>>    * specific for the given plugin-instance.
>>    */
>>   char* (*midnam)(LV2_Handle instance);
>>   /** The unique model id used in the midnam,
>>    * (or NULL).
>>    */
>>   char* (*model)(LV2_Handle instance);
>>   /** free allocated strings. The host
>>    * calls this for every value returned by
>>    * \ref midnam and \ref model.
>>    */
>>   void (*free)(char*);
>> } LV2_Midnam_Interface;
> First a comment to the proposed extension:
> How would a plugin announce to the host that a midnam re-read is needed
> (if a new drumkit is loaded for example)?

see "update()" above

  "Request from run() that the host should re-read the midnam"

setBfree is an example that calls this when the CC mapping changes or a
user creates or renames a patch.

> I think the midnam approach is a bad idea because it is encapsulating an
> existing spec into a new one (LV2) but otoh it will ease the adaptation
> in existing hosts... on the other hand I would really like to see a
> dynamic way of handing over such info to the host without having to
> dynamically write files to disk.
> I therefore propose two new extensions:
> 1) A static midnam file to be used with the plugin, described in the ttl.

Why static? That'd limit synths which can load soundfonts dynamically.

> 2) An atom based approach to hand over the attribute list is a 'pure'
> LV2 way, without having to transfer xml strings, supporting the plugins
> with the need for dynamic note descriptions.

I tried to come up with such a spec and after 2h gave up.

In particular sparse lists are hard. Host asks: give me all CC-Names
Patch-Names and Note-Names (which can be sparsely populated) for all
banks times all channels and/or programs.

As for Atoms: Factor in variable length names and a limited Atom Buffer
size. The list may have to be split across process cycles. Hence an
extension seemed a lot more appropriate.

Also querying them via an extension
  e.g.  char* get_plugin_patch_name (bank, program, /* channel */);
will be a lot of of calls forth and back.

I felt like I was reinventing the wheel. MIDNAM already covers it all
and furthermore there are already existing .midnam files for many sf2
and sfz. Synths that load .sf2 or .sfz would have to parse those and
present them via a new custom API to the host.

I'm neither a midnam fan nor like XML very much, but still other
alternatives seem worse.  In any case  dynamically generating some
midnam for a special-cased plugin does not need fancy XML generators: In
99.9% just sprintf() does the trick.


More information about the Devel mailing list