66#include " Arduino.h"
77#include " esp32-hal-tinyusb.h"
88
9+ // Initialize static members
10+ char *USBMIDI::midiUserDeviceName = nullptr ;
11+ // Weak definition of getUSBMIDIDefaultDeviceName to provide a default name
12+ __attribute__ ((weak)) const char *getUSBMIDIDefaultDeviceName() {
13+ return ESP32_USB_MIDI_DEFAULT_NAME;
14+ }
15+
916// Default Cable Number (for simplified APIs that do not expose this)
1017#define DEFAULT_CN 0
1118
@@ -18,7 +25,7 @@ extern "C" uint16_t tusb_midi_load_descriptor(uint8_t *dst, uint8_t *itf) {
1825 }
1926 tinyusb_midi_descriptor_loaded = true ;
2027
21- uint8_t str_index = tinyusb_add_string_descriptor (" TinyUSB MIDI " );
28+ uint8_t str_index = tinyusb_add_string_descriptor (USBMIDI::getCurrentDeviceName () );
2229 uint8_t ep_in = tinyusb_get_free_in_endpoint ();
2330 TU_VERIFY (ep_in != 0 );
2431 uint8_t ep_out = tinyusb_get_free_out_endpoint ();
@@ -41,9 +48,68 @@ USBMIDI::USBMIDI() {
4148 }
4249}
4350
51+ // private function for setting a not null/empty MIDI device name limited to 32 characters
52+ void USBMIDI::setDeviceName (const char *name) {
53+ const uint8_t maxNameLength = 32 ; // tinyUSB Descriptor limit
54+ if (name != nullptr && strlen (name) > 0 ) {
55+ if (strlen (name) > maxNameLength) {
56+ log_w (" USBMIDI: Device name too long, truncating to %d characters." , maxNameLength);
57+ }
58+ if (!midiUserDeviceName) {
59+ midiUserDeviceName = new char [maxNameLength + 1 ]; // +1 for null-terminator
60+ }
61+ if (midiUserDeviceName) {
62+ strncpy (midiUserDeviceName, name, maxNameLength);
63+ // Ensure null-termination when overflowing
64+ midiUserDeviceName[maxNameLength] = ' \0 ' ;
65+ } else {
66+ log_e (" USBMIDI: Failed to allocate memory for device name, using default name." );
67+ }
68+ } else {
69+ log_w (" USBMIDI: No device name provided, using default name [%s]." , getUSBMIDIDefaultDeviceName ());
70+ }
71+ }
72+
73+ /* *
74+ * @brief Constructor for setting the current device name
75+ * 1. Name set via constructor (if any)
76+ * 2. Name set via SET_USB_MIDI_DEVICE_NAME() macro (if defined)
77+ * 3. Default name "TinyUSB MIDI"
78+ * If device name is set as "", it will be ignored
79+ */
80+ USBMIDI::USBMIDI (const char *name) {
81+ if (!tinyusb_midi_interface_enabled) {
82+ setDeviceName (name);
83+ tinyusb_midi_interface_enabled = true ;
84+ tinyusb_enable_interface (USB_INTERFACE_MIDI, TUD_MIDI_DESC_LEN, tusb_midi_load_descriptor);
85+ } else {
86+ log_e (" USBMIDI: Multiple instances of USBMIDI not supported!" );
87+ }
88+ }
89+
90+ USBMIDI::~USBMIDI () {
91+ if (midiUserDeviceName) {
92+ delete[] midiUserDeviceName;
93+ midiUserDeviceName = nullptr ;
94+ }
95+ }
96+
4497void USBMIDI::begin () {}
4598void USBMIDI::end () {}
4699
100+ const char *USBMIDI::getCurrentDeviceName (void ) {
101+ if (midiUserDeviceName) {
102+ return midiUserDeviceName;
103+ }
104+ // If no user name set, use the compile-time default name limited to 32 characters
105+ setDeviceName (getUSBMIDIDefaultDeviceName ());
106+ if (midiUserDeviceName && strlen (midiUserDeviceName)) {
107+ return midiUserDeviceName;
108+ } else {
109+ return " TinyUSB MIDI" ;
110+ }
111+ }
112+
47113// uint compatible version of constrain
48114#define uconstrain (amt, low, high ) ((amt) <= (low) ? (low) : ((amt) > (high) ? (high) : (amt)))
49115
0 commit comments