Hello,
I'm working with some folks on getting Windows MIDI APIs to correctly recognize/distinguish when two of our same devices are connected. Included in the initial feedback was this:
We are using USB_MIDI16_SERIAL, with one tweak (we only support 12 virtual cables, so MIDI_NUM_CABLES is set to 12). My naive reading of the code in usb_desc.c suggested that I could change the order of the interfaces by simply moving the block of code that defines the MIDI interface, i.e. that begins like this:
#ifdef MIDI_INTERFACE
// Standard MS Interface Descriptor,
9, // bLength
4, // bDescriptorType
MIDI_INTERFACE, // bInterfaceNumber
0, // bAlternateSetting
2, // bNumEndpoints
0x01, // bInterfaceClass (0x01 = Audio)
0x03, // bInterfaceSubClass (0x03 = MIDI)
0x00, // bInterfaceProtocol (unused for MIDI)
0, // iInterface
// MIDI MS Interface Header, USB MIDI 6.1.2.1, page 21, Table 6-2
Above the two defined CDC interfaces, but clearly there are a couple more things to tweak. I found this in usb_desc.h:
#define NUM_INTERFACE 3
#define CDC_IAD_DESCRIPTOR 1
#define CDC_STATUS_INTERFACE 0
#define CDC_DATA_INTERFACE 1 // Serial
...
#define MIDI_INTERFACE 2 // MIDI
Which, again naively, appears to indicate the order, so I modified it thusly:
#define NUM_INTERFACE 3
#define CDC_IAD_DESCRIPTOR 1
#define CDC_STATUS_INTERFACE 1
#define CDC_DATA_INTERFACE 2 // Serial
...
#define MIDI_INTERFACE 0 // MIDI
I'm still not quite done, though, sadly. With just these changes, everyone gets very confused, and the device can't be enumerated on the bus at all - doesn't show up in Device Manager, etc.
Next on my list is to tweak this bit or arithmetic to reflect the new interface order (from usb_desc.c):
#define CDC_IAD_DESCRIPTOR_POS CONFIG_HEADER_DESCRIPTOR_SIZE
#ifdef CDC_IAD_DESCRIPTOR
#define CDC_IAD_DESCRIPTOR_SIZE 8
#else
#define CDC_IAD_DESCRIPTOR_SIZE 0
#endif
#define CDC_DATA_INTERFACE_DESC_POS CDC_IAD_DESCRIPTOR_POS+CDC_IAD_DESCRIPTOR_SIZE
#ifdef CDC_DATA_INTERFACE
#define CDC_DATA_INTERFACE_DESC_SIZE 9+5+5+4+5+7+9+7+7
#else
#define CDC_DATA_INTERFACE_DESC_SIZE 0
#endif
#define CDC2_DATA_INTERFACE_DESC_POS CDC_DATA_INTERFACE_DESC_POS+CDC_DATA_INTERFACE_DESC_SIZE
#ifdef CDC2_DATA_INTERFACE
#define CDC2_DATA_INTERFACE_DESC_SIZE 8 + 9+5+5+4+5+7+9+7+7
#else
#define CDC2_DATA_INTERFACE_DESC_SIZE 0
#endif
#define CDC3_DATA_INTERFACE_DESC_POS CDC2_DATA_INTERFACE_DESC_POS+CDC2_DATA_INTERFACE_DESC_SIZE
#ifdef CDC3_DATA_INTERFACE
#define CDC3_DATA_INTERFACE_DESC_SIZE 8 + 9+5+5+4+5+7+9+7+7
#else
#define CDC3_DATA_INTERFACE_DESC_SIZE 0
#endif
#define MIDI_INTERFACE_DESC_POS CDC3_DATA_INTERFACE_DESC_POS+CDC3_DATA_INTERFACE_DESC_SIZE
#ifdef MIDI_INTERFACE
#if !defined(MIDI_NUM_CABLES) || MIDI_NUM_CABLES < 1 || MIDI_NUM_CABLES > 16
#error "MIDI_NUM_CABLES must be defined between 1 to 16"
#endif
#define MIDI_INTERFACE_DESC_SIZE 9+7+((6+6+9+9)*MIDI_NUM_CABLES)+(9+4+MIDI_NUM_CABLES)*2
#else
#define MIDI_INTERFACE_DESC_SIZE 0
#endif
Has anyone else attempted this? Anything else you can think of that needs modified? Am I barking up the wrong tree, i.e. the order doesn't end up mattering here?
Thanks,
Blake
I'm working with some folks on getting Windows MIDI APIs to correctly recognize/distinguish when two of our same devices are connected. Included in the initial feedback was this:
I’m not sure that order matters here (it often does with USB, though), but every MIDI device I have checked lists either audio streaming or MIDI streaming as its first interface (after any IAD)
We are using USB_MIDI16_SERIAL, with one tweak (we only support 12 virtual cables, so MIDI_NUM_CABLES is set to 12). My naive reading of the code in usb_desc.c suggested that I could change the order of the interfaces by simply moving the block of code that defines the MIDI interface, i.e. that begins like this:
#ifdef MIDI_INTERFACE
// Standard MS Interface Descriptor,
9, // bLength
4, // bDescriptorType
MIDI_INTERFACE, // bInterfaceNumber
0, // bAlternateSetting
2, // bNumEndpoints
0x01, // bInterfaceClass (0x01 = Audio)
0x03, // bInterfaceSubClass (0x03 = MIDI)
0x00, // bInterfaceProtocol (unused for MIDI)
0, // iInterface
// MIDI MS Interface Header, USB MIDI 6.1.2.1, page 21, Table 6-2
Above the two defined CDC interfaces, but clearly there are a couple more things to tweak. I found this in usb_desc.h:
#define NUM_INTERFACE 3
#define CDC_IAD_DESCRIPTOR 1
#define CDC_STATUS_INTERFACE 0
#define CDC_DATA_INTERFACE 1 // Serial
...
#define MIDI_INTERFACE 2 // MIDI
Which, again naively, appears to indicate the order, so I modified it thusly:
#define NUM_INTERFACE 3
#define CDC_IAD_DESCRIPTOR 1
#define CDC_STATUS_INTERFACE 1
#define CDC_DATA_INTERFACE 2 // Serial
...
#define MIDI_INTERFACE 0 // MIDI
I'm still not quite done, though, sadly. With just these changes, everyone gets very confused, and the device can't be enumerated on the bus at all - doesn't show up in Device Manager, etc.
Next on my list is to tweak this bit or arithmetic to reflect the new interface order (from usb_desc.c):
#define CDC_IAD_DESCRIPTOR_POS CONFIG_HEADER_DESCRIPTOR_SIZE
#ifdef CDC_IAD_DESCRIPTOR
#define CDC_IAD_DESCRIPTOR_SIZE 8
#else
#define CDC_IAD_DESCRIPTOR_SIZE 0
#endif
#define CDC_DATA_INTERFACE_DESC_POS CDC_IAD_DESCRIPTOR_POS+CDC_IAD_DESCRIPTOR_SIZE
#ifdef CDC_DATA_INTERFACE
#define CDC_DATA_INTERFACE_DESC_SIZE 9+5+5+4+5+7+9+7+7
#else
#define CDC_DATA_INTERFACE_DESC_SIZE 0
#endif
#define CDC2_DATA_INTERFACE_DESC_POS CDC_DATA_INTERFACE_DESC_POS+CDC_DATA_INTERFACE_DESC_SIZE
#ifdef CDC2_DATA_INTERFACE
#define CDC2_DATA_INTERFACE_DESC_SIZE 8 + 9+5+5+4+5+7+9+7+7
#else
#define CDC2_DATA_INTERFACE_DESC_SIZE 0
#endif
#define CDC3_DATA_INTERFACE_DESC_POS CDC2_DATA_INTERFACE_DESC_POS+CDC2_DATA_INTERFACE_DESC_SIZE
#ifdef CDC3_DATA_INTERFACE
#define CDC3_DATA_INTERFACE_DESC_SIZE 8 + 9+5+5+4+5+7+9+7+7
#else
#define CDC3_DATA_INTERFACE_DESC_SIZE 0
#endif
#define MIDI_INTERFACE_DESC_POS CDC3_DATA_INTERFACE_DESC_POS+CDC3_DATA_INTERFACE_DESC_SIZE
#ifdef MIDI_INTERFACE
#if !defined(MIDI_NUM_CABLES) || MIDI_NUM_CABLES < 1 || MIDI_NUM_CABLES > 16
#error "MIDI_NUM_CABLES must be defined between 1 to 16"
#endif
#define MIDI_INTERFACE_DESC_SIZE 9+7+((6+6+9+9)*MIDI_NUM_CABLES)+(9+4+MIDI_NUM_CABLES)*2
#else
#define MIDI_INTERFACE_DESC_SIZE 0
#endif
Has anyone else attempted this? Anything else you can think of that needs modified? Am I barking up the wrong tree, i.e. the order doesn't end up mattering here?
Thanks,
Blake