Blog Protocol 9 min read

Sysex Preset Dump and Transfer with a Gamepad

Sysex preset dumps from a gamepad — bind transfer to a button, chunk packets safely, and move patches at LAN speed. Full byte-level walkthrough.

By Aidxn Design

Sysex gamepad transfer is the unloved part of MIDI that comes alive when you bind it to a face button. System Exclusive is how synths, drum machines, and effects pedals ship their proprietary data — presets, firmware, LED states, ribbon calibration. A gamepad with a free button to spare is a perfect remote for fetching a DX7 voice, swapping a Virus TI patch, or pushing a calibration blob into a Lyra-8. This post walks the byte layout, the chunking rules, and how to wire transfers to a controller.

TL;DR
  • Sysex framing: 0xF0 (start) … manufacturer ID … payload … 0xF7 (end). Anything between is opaque to MIDI 1.0 routers.
  • Chunk size: 256 bytes per packet is the safe default. Real devices stream the rest with 5 ms inter-chunk delay.
  • Universal device inquiry: F0 7E 7F 06 01 F7. Every sysex-capable device replies with its manufacturer/model.
  • Gamepad workflow: bind Share/Select to "send sysex file"; map d-pad to cycle preset .syx files.
  • Transport matters: USB-C ~1 ms/chunk, BLE MIDI ~15 ms/chunk, RTP-MIDI Ethernet ~0.5 ms/chunk.

What a sysex message actually looks like

Sysex is the only MIDI 1.0 message type with variable length. The spec defines a start byte (0xF0), a manufacturer ID (one byte for the big names, three bytes for everyone else, per the MIDI Association registry), an arbitrary payload, and an end byte (0xF7). Everything inside is the manufacturer's business.

A Yamaha DX7 voice dump for voice slot 5 looks like this:

OffsetHexMeaning
00xF0Sysex start
10x43Manufacturer ID — Yamaha
20x00Substatus + channel (0 = device 1)
30x00Format number — 0 = single voice
4–50x01 0x1BByte count MSB/LSB — 155 bytes
6–160...155 bytes of voice parameters
1610xXXChecksum
1620xF7Sysex end

That fits in a single packet on every transport — USB MIDI, RTP-MIDI, even BLE MIDI if the host doesn't fragment it. Compare that to a Virus TI patch (2,054 bytes) or a Vital preset (~16 kB) and you see why chunking matters.

Chunking rules — what real devices need

The MIDI 1.0 spec leaves chunking to the device implementer. In practice, most synths from 1985 onwards accept sysex in chunks no larger than 256 bytes with a 5 ms gap between chunks. The Yamaha DX7 famously needs a longer gap (~20 ms between voice blocks) because its 6809 CPU can't drain the UART fast enough. Modern devices like the Hydrasynth happily eat 1 kB chunks at line rate.

DeviceSafe chunk (bytes)Inter-chunk gap (ms)Typical preset (kB)
Yamaha DX7155 (one voice)200.15
Roland JV-108025651.2
Access Virus TI25632.0
Korg Microwave XT256100.5
Hydrasynth102413.0
Vital (softsynth)No limit016.0

Universal Controller MIDI ships a chunker that knows about these defaults per device. Pick "Yamaha DX7" from the device profile dropdown and it auto-sets chunk 155 / gap 20. Pick "Generic" and it falls back to 256 / 5. The sysex deep dive covers the device profile catalogue in full.

Binding a transfer to a gamepad button

The bridge exposes three sysex actions you can map to any button:

  • Send sysex file — pick a .syx file from disk, push it to the selected output port on press.
  • Request device dump — emit a device-inquiry or model-specific dump request; the response is written to disk.
  • Cycle preset folder — map d-pad up/down to step through a folder of .syx files. One press = one preset.
# Bridge sysex bindings — DualSense to DX7
[mapping.share_button]
action = "sysex.send_file"
file = "~/Music/dx7/lately-bass.syx"
chunk_bytes = 155
gap_ms = 20

[mapping.dpad_up]
action = "sysex.cycle_folder"
folder = "~/Music/dx7"
step = +1

[mapping.dpad_down]
action = "sysex.cycle_folder"
folder = "~/Music/dx7"
step = -1

[mapping.options_button]
action = "sysex.request_dump"
target = "dx7"
save_to = "~/Music/dx7/dumps/{timestamp}.syx"

The universal device inquiry — your first move

Before you transfer anything, run the universal device inquiry. It is the only sysex message every device understands. The bridge's Tools → Identify device button sends it and shows you the response in plain text — manufacturer, family, model, firmware. Use it to confirm the device is alive and on the right MIDI port.

# Universal Device Inquiry
TX: F0 7E 7F 06 01 F7
                ^^ device ID (7F = broadcast)

# Typical Hydrasynth response
RX: F0 7E 00 06 02 00 20 6B 02 00 00 00 01 0C 00 F7
       ^^ device          ^^ manufacturer (ASM = 00 20 6B)
                                ^^ family code
                                       ^^ firmware bytes

Sysex across transports — measured times

Same preset (Hydrasynth, 3 kB) shipped across four transports from the same bridge to the same device. Timed from first byte sent to last byte ACK'd.

TransportTotal time (ms)Effective throughputNotes
USB-C MIDI direct3.2~960 kB/sReference baseline.
RTP-MIDI, Ethernet4.1~750 kB/sWithin 1 ms of USB.
RTP-MIDI, Wi-Fi 69.8~310 kB/sWi-Fi adds variable jitter.
BLE MIDI 1.03,420~0.9 kB/s20-byte packets × 7.5 ms intervals.

Bluetooth MIDI is over 1,000× slower for sysex. If you plan to swap presets live, do not put sysex on BLE. Stick to USB-C for tracking and RTP-MIDI for distance — see RTP-MIDI vs USB MIDI for the broader transport story.

Gotchas that cost us hours

  1. Stuck-in-receive mode. If a sysex transfer is interrupted mid-stream, some synths sit waiting for the missing 0xF7 forever. Power-cycle them.
  2. Manufacturer ID 0x00 trap. A 0x00 first byte means the next two bytes are the extended manufacturer ID. The bridge handles this; hand-rolled scripts often don't.
  3. Roland's checksum rule. Roland sysex requires a checksum byte before 0xF7. Mess it up and the device silently rejects the dump.
  4. Mac's IAC bus drops sysex on overflow. Macs running multiple sysex pipes through IAC can lose packets if the buffer overruns. Send through a real port if possible.
  5. Browser sysex needs HTTPS + permission. WebMIDI refuses sysex on insecure origins, and the user must explicitly tick the sysex box. See WebMIDI gamepad rig for the prompt flow.
  6. MIDI 2.0 changes the framing. Sysex in MIDI 2.0 uses 7-bit data inside 64-bit UMP packets — the byte stream is gone. The bridge handles the conversion; covered in MPE vs MIDI 2.0.

Why this is worth bothering with

Once you have sysex transfer wired to a button, your gamepad becomes a preset remote — cycle through a folder of DX7 voices during a take, dump the current Virus state to disk on a long press, fire a calibration blob into a Lyra-8 every gig. Hardware synths were designed to be controlled remotely; the gamepad is the cheapest remote you'll ever own.

Grab the bridge from Universal Controller MIDI and bind Share to your favourite preset folder. The sysex deep dive covers bidirectional flows (LED states, haptic ACKs) and MIDI feedback shows how to route the responses back to the gamepad's rumble motors.

Keep reading

More setup walkthroughs