MIDI.setHandleSystemExclusive error

Rolfdegen

Well-known member
When i try to receive 348 Byte sysex data via midi with teensy 4.1, the data is missing and error !!!
Receive 348 Byte to usbMIDI works fine :)

Code:
MIDI.setHandleSystemExclusive(myReceiveSysEx);   //Doesn't work because of buffer problems :(
usbMIDI.setHandleSysEx(myReceiveSysEx);   // work very fine :)

//*************************************************************************
// usbMIDI/MIDI receive SystemExclusive Dump
//*************************************************************************
FLASHMEM void myReceiveSysEx(const uint8_t *buffer, uint16_t lenght, boolean flag)
{
    
    static int count = 0;
    static boolean F0status = false;
    static boolean F7status = false;
    
    int SysExBuffer[348];
    
    Serial.print("lenght: ");
    Serial.println(lenght);
    
    for (uint16_t i = 0; i < lenght; i++) {
        
        SysExBuffer[count] = buffer[i];
        count++;
        
        if (buffer[i] == 0xF0) {
            F0status = true;
            Serial.println("F0 status");
        }
        
        if (buffer[i] == 0xF7) {
            F7status = true;
            Serial.println("F7 status");
            Serial.print("receive data lenght: ");
            Serial.println(count);
            count = 0;
        }
    }

receive MIDI SysEX data (missing and error)
SysEx midi.jpg

receive USB SysEx data (very nice)
SysEx usb.jpg
 
Another try with Windows App Bome SendSX, Mios Studio and MIDI-OX.
Each time I receive different data via midi. The only thing that works is reception via usbMIDI :confused:



My scetch Midi SysEx receive with print hex values
Code:
MIDI.setHandleSystemExclusive(myReceiveSysEx1);   //Doesn't work because of buffer problems

//*************************************************************************
// Test MIDI receive SystemExclusive Dump
//*************************************************************************
FLASHMEM void myReceiveSysEx1(const uint8_t *buffer, uint16_t lenght, boolean flag)
{
    Serial.print("SysEx lenght: ");
    Serial.println(lenght);
    for (uint16_t i = 0; i < lenght; i++) {
        uint8_t myByte = buffer[i];
        Serial.print(myByte, HEX); Serial.print(" ");
    }
    Serial.println();
}


Bome SendSX
SysEx 3.jpg

Mios Studio
SysEx 4.jpg

MIDI-OX
SysEx 5.jpg
 
Last edited:
Thanks for the information :)
I set SysExMaxSize in MIDI_Settings.h file to 512 bytes and set the transmission speed in Bome SendSX to 1.29KB/s.
There are no transmission errors.

In MIDI-OX I set send buffer setting to 1 byte and set SysExMaxSize in MIDI_Settings.h file to 512 bytes.
There are no transmission errors.

SysEx 7.jpg

Bome SendSX
SysEx 6.jpg

MIDI-OX
SysEx 8.jpg
 
Hello
I write a simple sketch for Midi SysEx receive data today.


But receiving SysEx data with Teensy is faulty :confused:


Code:
//**********************************************************************
// Simple scetch for receiving SysEx data via Midi
//**********************************************************************


#include <Arduino.h>
#include <MIDI.h>
MIDI_CREATE_DEFAULT_INSTANCE();




//************************************************************************
// setup
//************************************************************************
void setup() {
  Serial.begin(115200);
  MIDI.begin();
}


//*************************************************************************
// Test MIDI receive SystemExclusive Dump
//*************************************************************************
void myMidiRead()
{
  uint8_t myByte = 0;
  uint8_t count = 0;
  
  // SysEx Data lenght
  uint16_t sysLenght = MIDI.getSysExArrayLength();
  Serial.print("Data lenght: ");
  Serial.println(sysLenght);


  // SysEx Data Buffer
  const byte *sysBuffer = MIDI.getSysExArray();


  // print SysEx Data
  for (uint16_t i = 0; i < sysLenght; i++)
  {
    // print hex table
    myByte = sysBuffer[i];
    if(myByte <= 0x0F){
      Serial.print("0");
    }
    Serial.print(myByte, HEX); Serial.print(" ");
     count++;
     if(count == 25) {
      count = 0;
      Serial.println();  
     }
  }
}


//************************************************************************
// Main loop
//************************************************************************
void loop() {
    while (MIDI.read()) {
    myMidiRead();
  }
}


The buffer in MIDI_Settings.h is 128 bytes, reception works not correctly.
I send 348 bytes including SysEx status 0xF0 and 0xF7

SysEx 8.jpg


If the buffer in MIDI_Settings.h is changed from 128 to 512 bytes, reception works correctly.
I send 348 bytes including SysEx status 0xF0 and 0xF7
SysEx 10.jpg

I use Teensy 4.1 with Arduino 1.8.19 and Teensyduino 1.56
 
Not familiar with that method. Am using callback and changed the buffer in MIDI_Settings.h to 256 to receive 140 byte sysex.
 
Yes. It also only seems to work with an increase in the buffer value. I set the value to 512Byte and received 348 bytes. It's the size of a SysEx dump from a sound program in my synthesizer.
 
I have mesured. The maximum transfer rate for receiving SysEx Dump via Midi without errors is 0.41KB/s. This is very slow on a Teensy 4.1.
In my DIY synth with an Teensy 4.1 I will not implement SysEx Dump via Midi. Instead I use for SysEX dump via usbMidi.
It is very faster. The maximum transfer rate of 5.52KB/s.

Greetings from germany. Rolf
 
Last edited:
The maximum transfer rate for receiving SysEx Dump via Midi without errors is 0.41KB/s. This is very slow on a Teensy 4.1.

The standard data rate for MIDI over serial is 31250 bps, which limits the maximum transfer that can be expected. With one start bit + 8 data bits + 1 stop bit per MIDI message byte, you can expect no faster than a maximum raate of 3.125KBps, assuming no other overhead and/or interruptions. Since your Teensy is almost certainly managing a TFT display (showing the progress bar, etc.), as well as potentially doing other things (monitoring for touchscreen inputs, etc.) while the SysEx message is being sent, it should not be much of a surprise that your actual throughput is something somewhat less than the theoretical maximum. When using serial, throughput could also be adversely impacted by the receiving end as well (if using hardware handshakes, etc.).

Sounds like usbMIDI is the way to go for your use case.

Mark J Culross
KD5RXT
 
For the measurement I only used this sketch on a Teensy 4.1. No other functions.

Code:
//**********************************************************************
// Simple scetch for receiving SysEx data via Midi
//**********************************************************************


#include <Arduino.h>
#include <MIDI.h>
MIDI_CREATE_DEFAULT_INSTANCE();




//************************************************************************
// setup
//************************************************************************
void setup() {
  Serial.begin(115200);
  MIDI.begin();
}


//*************************************************************************
// Test MIDI receive SystemExclusive Dump
//*************************************************************************
void myMidiRead()
{
  uint8_t myByte = 0;
  uint8_t count = 0;
  
  // SysEx Data lenght
  uint16_t sysLenght = MIDI.getSysExArrayLength();
  Serial.print("Data lenght: ");
  Serial.println(sysLenght);


  // SysEx Data Buffer
  const byte *sysBuffer = MIDI.getSysExArray();


  // print SysEx Data
  for (uint16_t i = 0; i < sysLenght; i++)
  {
    // print hex table
    myByte = sysBuffer[i];
    if(myByte <= 0x0F){
      Serial.print("0");
    }
    Serial.print(myByte, HEX); Serial.print(" ");
     count++;
     if(count == 25) {
      count = 0;
      Serial.println();  
     }
  }
}


//************************************************************************
// Main loop
//************************************************************************
void loop() {
    while (MIDI.read()) {
    myMidiRead();
  }
}
 
Back
Top