Car Radio — project map

A custom head unit for a Ford Fusion: a Raspberry Pi drives the factory display (FDIM) and button panel (FCIM) over CAN, and an ADAU1467 DSP over I²C. Generated from the folder contents on 2026-10-26.

ACTIVE current, maintained code EXPERIMENT one-off reverse-engineering tools TEST automated tests CLUTTER stale, duplicate or accidental

TL;DR. The real software is car-radio/fusion/, plus deploy/ to put it on the Pi. Everything under code/ is the earlier CAN-cracking work. The protocol knowledge lives in notes-and-knowledge/, FDIM/ and the ccode/cmd/* probes. Several files are leftovers (see the cleanup section).

Outer folder: projects/car/

car-radio/The git repo. Almost everything lives here.
start_can.shFinds a CANable USB adapter (candleLight or slcan firmware) and brings it up as a SocketCAN canN at 125 kbit/s (Ford MS-CAN). Re-runs itself with sudo/run0. It sits outside the repo, so it isn't version-controlled. ACTIVE
grommet.scad / .stl / .3mfOpenSCAD source, the exported mesh and the slicer project for a small printed grommet (a 6 mm post on an 8 mm flange), probably for routing wires. Unrelated to the code. HARDWARE
.claude/Claude Code local permission settings.

Repo root: car-radio/

README.md, LICENSEA one-line README ("Repo for everything involving… my custom car radio") and the license.
decode.pyThe original Python (python-can) FCIM button decoder, including send_wake_fcim. It's the first working decoder from the initial commit. The Go code later ported it. LEGACY
read-can.txtA cheat sheet: slcand plus candump commands for sniffing the bus. NOTES
write-can.txtPasted shell history (line numbers included) of cansend/cangen experiments. One line is a bad paste where two commands ran together. CLUTTER

fusion/: the main application ACTIVE

This is a Go implementation of the "Fusion Audio UI & Software Specification". It has a pure UI core, and every piece of hardware sits behind an interface. Terminal emulators for the display and the buttons let the whole system run on a laptop. README.md documents how to run it.

cmd/fusiond/The daemon that wires the core to drivers (real CAN/I²C or simulated). console.go is a simulated-hardware REPL with commands like connect Pixel, ring Alice and dsp fail.
cmd/fdim/A terminal emulator of the 2×20 front display. It listens on :7002.
cmd/fcim/A terminal emulator of the button panel. Each keystroke is sent to fusiond as a button pulse on :7001.
core/The UI state machine: pages and menus (pages.go), rendering, text, the clock editor and shared types. script.go runs the .test scenario files.
app/Dependency injection (app.Deps) and the main loop that ties core and drivers together.
fdim/The display driver. can.go/canproto.go drive the real FDIM over CAN, net.go drives the emulator, and there's an in-memory version for tests.
fcim/The button source: the real FCIM over CAN, the emulator over the network, and keymap.go.
can/The low-level SocketCAN wrapper (can_linux.go).
dsp/The DSP interface, a simulator, and the real ADAU1467 driver over I²C (i2c_linux.go).
bt/The Bluetooth module interface. It's simulated only so far.
platform/Clock and persistent settings store.
termui/Shared terminal-drawing helpers for the emulators.
tests/*.testSeven scenario scripts written as key X / expect … steps: boot/standby, volume, menus/source, now playing, clock editor, Bluetooth, phone/health. Each one cites a spec section. TEST
*_test.goGo unit tests in core, app, fdim, fcim, can, dsp, platform and fusiond/console. TEST
run-all.shOpens the three programs in separate terminals or in tmux panes. --build compiles them first.

deploy/: putting it in the car ACTIVE

bootstrap.shOne-time, idempotent setup of the Pi, run from the laptop (deploy/bootstrap.sh main@fusion.local).
99-canable.rulesA udev rule that identifies the CANable adapter.
slcan.serviceA systemd unit that brings up the slcan CAN interface at boot.
fusion.serviceA systemd unit that auto-starts fusiond (latest commit: "Make fusiond auto-boot").

code/: earlier Go prototypes EXPERIMENT

This folder holds the work done before fusion/ existed, and it's the messiest part of the repo. It has three layers, each a newer copy of the previous one. ccode/ and new/ are untracked in git.

main.go, display.go, inputs.go, go.modThe first Go radio prototype (May). It's been superseded: an updated copy lives at ccode/cmd/radio/. STALE
new/An intermediate snapshot: fdimtext, ISO-TP and layout code with tests, plus Ford FDIM text protocol.md, the most complete write-up of how FDIM text is encoded. layout.go and isotp.go are identical to the copies in ccode/. DUPLICATE (keep the .md)
ccode/The newest prototype library: isotp.go (multi-frame CAN transport), layout.go (fitting text into 2×20), clock.go, fcim.go, each with a _test.go. TEST
ccode/cmd/radioAn updated version of the old radio prototype.
ccode/cmd/fcimreadReceive-only sniffer that decodes FCIM button presses.
ccode/cmd/fdimtextPrints the cansend frames for a two-line message without touching the bus. Same purpose as new/main.go.
ccode/cmd/fdimtestCycles test patterns across the whole 2×20 text area.
ccode/cmd/fdimprobeSteps through experiments on the source box, the volume bar and unmapped icons.
ccode/cmd/sweepA fast blind search for the frames that drive the AM/FM/SYNC/AUX source box.
ccode/cmd/backlightIsolates which frame turns on the FCIM backlight. The answer (the 0x3E8 baseline) went into fusion.

FDIM/: raw display experiments EXPERIMENT

send.shReplays a cansend script onto a given CAN interface.
display-text.pyAn early Python generator for display text frames.
display-matthew.txtA captured or hand-written frame sequence that shows a name on the display.
maybe-text.txtA near-copy of the above that's slightly different. It was a guess, as the name says. CLUTTER

notes-and-knowledge/: research REFERENCE

fdim.txtA summary of the FDIM protocol (heartbeat, text) based on p1ne's fdim-controller.
keep-wake.txtNotes on the Ford network-management "ring" that keeps modules awake.
wiring.txtLinks to ACM pinouts and wiring diagrams.
software-design.md, interface-design.mdEarly design docs for the menu and UI that came before the formal spec.

dsp/: ADAU1467 SigmaStudio project

Design 1.dspprojThe SigmaStudio project (the audio signal chain).
Design 1_IC 1/SigmaStudio's compiled export: Program.bin/.dat, the memory images, ParamAddress.dat (register addresses the Go driver needs) and the compiler log. It also contains a second copy of the .dspproj and of bass_remapping.txt.
generate_bass_remapping.pyGenerates a sigmoid lookup curve for remapping bass levels. The output goes to bass_remapping.txt.
Settings/Design 1, Design 3Empty folders. CLUTTER
System Volume Information/, FOUND.000/Windows filesystem debris from when this folder was on a USB stick or SD card. FILE0000.CHK is a chkdsk recovery fragment. These are committed to git by mistake. CLUTTER

Cleanup suggestions