MarecekW/scarlett-mixcontrol-1stgen

GitHub: MarecekW/scarlett-mixcontrol-1stgen

Stars: 1 | Forks: 0

App icon

Scarlett MixControl

Community Edition

A native macOS replacement for Focusrite's discontinued MixControl 1.10.6,
for the 1st-generation Scarlett 8i6.
Download latest   macOS 14+   License MIT


Mixer tab — 18×6 matrix mixer with live peak meters

## ✨ Features | | | | --- | ------------------------------------------------------------------------------------------- | | 🎛️ | **Full 18 × 6 matrix mixer** with per-cell gain, mute, solo, pan, stereo link | | 🔀 | **Output routing** — Monitor / Phones / S/PDIF can pick any source (DAW, Analog, Mix M1–M6) | | 🎤 | **USB capture routing** — choose what your DAW sees on each input channel | | 📌 | **Pinned DAW return strip** — DAW 1/2 back into the matrix with one linked fader | | 🔘 | **Hardware switches** — line/inst impedance, hi/lo gain, clock source, sample rate | | 📊 | **Live peak meters** — all 18 inputs + 6 mix buses + 6 DAW playbacks, with held peaks | | 💾 | **Save to hardware** — persist mixer state to device flash, survives power cycle | | 📁 | **Snapshots** — save / load full configurations as `.8i6` JSON files (⌘S / ⌘O) | | 🔌 | **Connection resilience** — auto-reconnect on USB drops, clear status overlay |
Routing tab
Routing — physical outputs + USB capture
Presets tab
Presets — save / load full configurations
Device tab
Device — hardware info, clock, event log

## 📦 Installation ### Download a release _(recommended)_ 1. Grab `Scarlett.MixControl.app.zip` from the [**latest release**](https://github.com/MarecekW/scarlett-mixcontrol-1stgen/releases/latest). 2. Unzip and drag `Scarlett MixControl.app` to `/Applications`. 3. **First launch only** — macOS Gatekeeper will block the app (we use ad-hoc codesigning, not a paid Developer ID). One of these will get past it: - **Right-click** the app → **Open** → confirm the warning dialog. - Or in Terminal: `xattr -dr com.apple.quarantine "/Applications/Scarlett MixControl.app"` ### Build from source Requires the Xcode 15 / Swift 5.9+ toolchain. git clone https://github.com/MarecekW/scarlett-mixcontrol-1stgen.git cd scarlett-mixcontrol-1stgen ./scripts/make-app.sh open "build/Scarlett MixControl.app" For dev iteration without packaging: `swift run scarlett-app`. There's also a `scarlett-cli` companion for low-level protocol poking — try `swift run scarlett-cli --help`.
## 🎯 Compatibility | Device | Status | | ---------------------------- | ---------------------------------------------------- | | **Scarlett 8i6** _(1st gen)_ | ✅   Officially supported — tested on macOS 14+ | | Scarlett 6i6 _(1st gen)_ | 🟡   Detected, support pending | | Scarlett 16i8 _(1st gen)_ | 🟡   Detected, support pending | | Scarlett 18i6 _(1st gen)_ | 🟡   Detected, support pending | | Scarlett 18i8 _(1st gen)_ | 🟡   Detected, support pending | | Scarlett 18i20 _(1st gen)_ | 🟡   Detected, support pending | | Scarlett 2nd / 3rd / 4th gen | ❌   Different protocol — won't work | | Saffire (FireWire) family | ❌   Different transport — won't work |
## 🛠️ How it works
Tech tour (click to expand)
The 1st-gen Scarletts are **USB Audio Class 2.0** devices. macOS's built-in `usbaudiod` claims the audio + MIDI streaming interfaces, but doesn't touch the **audio control interface** (endpoint 0). That's how this app coexists with normal audio playback — every mixer / routing / metering command is a `IOUSBDeviceInterface.DeviceRequest` to endpoint 0, sent through the same USB stack `usbaudiod` is using, without ever issuing `USBDeviceOpen` (which would fail with `kIOReturnExclusiveAccess`). The protocol itself was reverse-engineered by extracting the per-product signal tables (`_USB14Tracker_IpSigTab`, `_USB14Tracker_OpSigTab`, default routing tables, etc.) directly from the original MixControl 1.10.6 binary, then disassembling key dispatch functions (`MacHWDevice::routeChannel`, `setMonMono`, etc.) to confirm `wValue` / `wIndex` semantics. **The three routing dimensions:** | `wIndex` | Purpose | UI surface | | -------- | ------------------------- | ------------------------------------------ | | `0x3200` | Matrix-mixer input source | Source picker on each matrix channel strip | | `0x3300` | Physical output routing | "Output assignments" panel in Routing tab | | `0x3400` | USB capture routing | "USB capture" panel in Routing tab | **Firmware quirks worth knowing:** - Routing GETs always return `00 00` regardless of what was last set — UserDefaults persistence is the only way to remember routes across launches. - Matrix-source assignment silently fails if the source is already wired to another channel — the app does an explicit `.off` disconnect on the previous owner first. - The `setMonitorMono` USB command crashes the firmware when sent from our process, even with byte-perfect parity to MixControl. Probably an undocumented authorization handshake at startup we haven't identified — the Mn button is hidden until we crack it. For full deep-dive, read the commit history — `d175367` (the matrix-mixer breakthrough) and `1294ff7` (feature parity additions) cover most of the protocol reasoning.

## 📜 License Released under the [MIT](LICENSE) license.
Built by @MarecekW · co-authored with Claude