I'm currently testing a Teensy 4.0 based USB <-> "DIN MIDI" interface. To make sure it passes large amounts of SysEx data correctly I tried a loopback test connecting the DIN MIDI out with the input and then from the computer sending out large amounts of data, making sure I get the same data back in.
Well, it didn't work as expected. Using Bome sendSX on Windows I could observe that SysEx messages longer than about 130 bytes would arrive "shortened". That is, there was data missing in the middle of the transmission. Received data size was usually around 130 to 132 bytes for transmitted SysEx messages of 162 byte length.
So I wrote a Linux app that would send out test patterns and check received data. There I got even less data back (often nothing at all).
Using Teensy as USB->DIN MIDI interface and receiving using some other (off-the-shelf) MIDI interface worked fine. Sending with other MIDI interface and receiving with Teensy also works. So when the Teensy is not being used full-duplex, all is good (which shows that my code doesn't drop/corrupt any data). Full-duplex transmission with other MIDI interfaces I have at hand does work. Interestingly this only effects SysEx data, doing a loopback with note-on/note-off works fine.
Since SysEx first gets "collected" unside the USB MIDI code and then submitted to the callback in chunks of up to 290 bytes (which I then need to send out through slow DIN MIDI) I started to wonder whether the code gets blocked somewhere for too long. And indeed, changing USB_MIDI_SYSEX_MAX in usb_midi.h from 290 to 64 fixes my problem. - Yes I did read the lengthy threads here where people beg for bigger and bigger SysEx buffers so they don't have to re-assemble the data in the callback.
So I guess I have a feature request to make this #define user-adjustable:
I guess my real underlying problem is that trying to put large amounts of data into the HardwareSerial output FIFO will block (i.e. I'm submitting more SysEx than the FIFO can hold) which in turn makes the SysEx callback (and thus usbMIDI.read()) execute for so long that I get a buffer overflow on the serial input in the meantime. Lowering the value of USB_MIDI_SYSEX_MAX simply makes sure the callback function returns faster and my code reads MIDI input from serial before an overflow happens. Assuming that HardwareSerial FIFO is 64 bytes, I should probably set USB_MIDI_SYSEX_MAX to 32.
Well, it didn't work as expected. Using Bome sendSX on Windows I could observe that SysEx messages longer than about 130 bytes would arrive "shortened". That is, there was data missing in the middle of the transmission. Received data size was usually around 130 to 132 bytes for transmitted SysEx messages of 162 byte length.
So I wrote a Linux app that would send out test patterns and check received data. There I got even less data back (often nothing at all).
Using Teensy as USB->DIN MIDI interface and receiving using some other (off-the-shelf) MIDI interface worked fine. Sending with other MIDI interface and receiving with Teensy also works. So when the Teensy is not being used full-duplex, all is good (which shows that my code doesn't drop/corrupt any data). Full-duplex transmission with other MIDI interfaces I have at hand does work. Interestingly this only effects SysEx data, doing a loopback with note-on/note-off works fine.
Since SysEx first gets "collected" unside the USB MIDI code and then submitted to the callback in chunks of up to 290 bytes (which I then need to send out through slow DIN MIDI) I started to wonder whether the code gets blocked somewhere for too long. And indeed, changing USB_MIDI_SYSEX_MAX in usb_midi.h from 290 to 64 fixes my problem. - Yes I did read the lengthy threads here where people beg for bigger and bigger SysEx buffers so they don't have to re-assemble the data in the callback.
So I guess I have a feature request to make this #define user-adjustable:
Code:
#ifndef USB_MIDI_SYSEX_MAX
# define USB_MIDI_SYSEX_MAX 290
#endif
I guess my real underlying problem is that trying to put large amounts of data into the HardwareSerial output FIFO will block (i.e. I'm submitting more SysEx than the FIFO can hold) which in turn makes the SysEx callback (and thus usbMIDI.read()) execute for so long that I get a buffer overflow on the serial input in the meantime. Lowering the value of USB_MIDI_SYSEX_MAX simply makes sure the callback function returns faster and my code reads MIDI input from serial before an overflow happens. Assuming that HardwareSerial FIFO is 64 bytes, I should probably set USB_MIDI_SYSEX_MAX to 32.