Open JoergAtGithub opened 7 months ago
The operating systems macOS and Windows provide identifiers for this purpose:
Do you have some sample code of how to do this ?
For macOS you need to get the USBLocationID
property from MIDIDeviceRef
, similar to the code example here:
https://stackoverflow.com/questions/43071011/is-there-a-way-to-tell-if-a-midi-device-is-connected-via-usb-on-ios/50637087#50637087
For Windows you need to get the DEVPKEY_Device_ContainerId
property returned by CM_Get_DevNode_PropertyW
:
https://learn.microsoft.com/en-us/windows-hardware/drivers/install/devpkey-device-containerid#:~:text=The%20DEVPKEY_Device_ContainerId%20device%20property%20is%20used%20by%20the,that%20represents%20an%20instance%20of%20a%20physical%20device
Thanks. Now I have to find how I get these device nodes in MS Windows, as right now the code does not use these APIs AFAIK. For macOS it looks pretty doable.
I'm revisiting this and am wondering: port_information already stores the MIDIObjectRef's UUID so you can get it back in the following way (typing this without access to macOS so likely there are some mistakes but you get the gist):
int32_t usb_id_from_port(const libremidi::port_information& info) {
// Get the MIDI object from the uid
auto uid = std::bit_cast<std::int32_t>((uint32_t)info.port);
MIDIObjectRef object{};
MIDIObjectType type{};
auto ret = MIDIObjectFindByUniqueID(uid, &object, &type);
assert(type == kMIDIObjectType_Source || type == kMIDIObjectType_Destination);
// Get the MIDI entity from the object
MIDIEntityRef entity{};
MIDIEndpointGetEntity(object, &entity);
if(!entity)
throw; // It means it's not a hardware port
// Get the MIDI device from the entity
MIDIDeviceRef device{};
MIDIEntityGetDevice(entity, &device);
if(!device)
throw;
SInt32 res{};
MIDIObjectGetIntegerProperty(device, CFSTR("USBDeviceID"), &res);
return res;
}
For Windows I investigated but I see absolutely no way to get the device ID from the WinMM API. :/
For compound USB devices, that have not only a MIDI interface, but interfaces used with other USB device classes (e.g. a display) as well, it is needed to group them. The operating systems macOS and Windows provide identifiers for this purpose: