Working Raspberry Pi Codec Zero with Patchbox and Modep

I’ve built a Raspberry Pi 4 into my eurorack case to run MODEP for end of chain processing / mastering of my live sets. I had a lot of trouble getting the Raspberry Pi Codec Zero hat to work for audio in and out for processing.

Drawing on various threads here and also looking at the code used for the Pistomp project, as well as lots of troubleshooting using Claude I’ve now managed to get it to work reliably. It’s not the fastest boot and I’ve given up trying to optimise it further because it appears that the card just needs time to boot up and get a stable connection - which is big part of what the setup below deals with.

I thought I’d share what I have learned here so that anyone else trying to use this card can learn from it too. It’s a pretty good solution for me for good quality stereo audio i/o for MODEP.

I’ve now got it working reliably and headless in my eurorack case. Sounds great too! I had to add some electronics to get it working how I wanted. The input at eurorack level needs a step down with some resistors to the line level the hat expects. I also found the output very low, not ideal for a live performance system, so I added a line level amplifier to it to step it up.

This is using the latest (as of this post) Bookworm download of Patchbox. I’ve found it needs the kernel update from running rpi-update to have the latest overlays for this HAT.,

The below is taken from my Claude chat I’ve used to get this figured out and working:

The Problem: Your Audio Script Runs Before the Card Is Ready

The Codec Zero uses I²C and I²S to communicate with the Pi, and ALSA (the Linux audio subsystem) needs to fully initialise before your audio script can use it. On Patchbox OS, services start fast — often faster than the HAT is ready. The result is a script that launches, can’t find the audio device, and either crashes silently or plays nothing.

You can verify this is your problem by running:

aplay -l

If you don’t see the Codec Zero listed, ALSA hasn’t finished setting it up yet. Run it again a few seconds later and it’ll appear. That gap is where things are failing.


Step 1: Get the Overlay Right in config.txt

Before anything else, you need the correct device tree overlay loaded. Add these lines to /boot/firmware/config.txt:

dtparam=i2c_arm=on
dtparam=i2s=on
dtoverlay=rpi-codeczero

You also need the overlay file itself. If it’s not already present in /boot/overlays/:

sudo wget https://raw.githubusercontent.com/raspberrypi/firmware/master/boot/overlays/rpi-codeczero.dtbo -O /boot/overlays/rpi-codeczero.dtbo

Without this, the card simply won’t appear to the system at all.


Step 2: Restore the ALSA State — But With a Delay

The Codec Zero needs its mixer controls set correctly at boot, which is done with alsactl restore using a state file from the Pi-Codec repo. The problem is timing — if you run this too early the chip isn’t ready, and it silently fails.

The fix is a systemd drop-in override for the alsa-restore service that adds a 15-second delay and points to your saved state file:

/etc/systemd/system/alsa-restore.service.d/override.conf

[Service]
ExecStartPre=/bin/sleep 15
ExecStart=
ExecStart=/usr/sbin/alsactl -E HOME=/run/alsa -E XDG_RUNTIME_DIR=/run/alsa/runtime restore -f /home/patch/setupfiles/alsastate-hi-volume-output.state

The blank ExecStart= line clears the original command before setting the new one — that’s intentional and required for systemd overrides.

Save your working state (once the card is configured correctly) with:

sudo alsactl store

Or grab a baseline from the Pi-Codec repo:

git clone https://github.com/raspberrypi/Pi-Codec
sudo alsactl restore -f Pi-Codec/Codec_Zero_AUXIN_record_and_HP_playback.state


Step 3: Fix the Service Dependency Chain

MODEP runs several services that depend on each other: JACK needs ALSA ready, mod-host needs JACK, and mod-ui needs mod-host. By default these don’t always wait for each other properly. Use systemd drop-in overrides to enforce the correct order.

/etc/systemd/system/jack.service.d/override.conf:

[Unit]
After=rc-local.service
Requires=rc-local.service

/etc/systemd/system/modep-mod-host.service.d/override.conf:

[Unit]
After=jack.service
Requires=jack.service

/etc/systemd/system/modep-mod-ui.service.d/override.conf:

[Unit]
After=modep-mod-host.service jack.service
Requires=modep-mod-host.service jack.service

After adding any overrides, reload systemd:

sudo systemctl daemon-reload


Step 4: Add a Watchdog for Cold Boot Failures

Even with all the above in place, a cold boot (power on from completely off, rather than a reboot) can still leave the audio stack in a broken state. The symptom is MODEP loading fine but producing no sound and JACK showing very low CPU usage from mod-host.

The fix is a watchdog script that runs after boot, detects this condition by checking mod-host’s CPU usage, and kicks the stack back to life if needed:

/usr/local/bin/audio-watchdog.sh:

#!/bin/bash
# Wait for everything to start up
sleep 10

for i in $(seq 1 10); do
    MOD_CPU=$(ps aux | grep mod-host | grep -v grep | awk '{print $3}')
    echo "mod-host CPU: $MOD_CPU%"

    if (( $(echo "$MOD_CPU < 5.0" | bc -l) )); then
        echo "Audio appears broken, attempting recovery..."
        systemctl stop jack
        sleep 2
        alsactl restore -f /home/patch/setupfiles/alsastate-hi-volume-output.state
        # Play a moment of silence to wake the DAC
        aplay -D hw:Zero -f S16_LE -r 48000 -c 2 /dev/zero &
        APLAY_PID=$!
        sleep 2
        kill $APLAY_PID 2>/dev/null
        sleep 1
        systemctl start jack
        sleep 5
        systemctl restart modep-mod-host.service
        systemctl restart modep-mod-ui.service
        echo "Recovery complete"
        exit 0
    fi
    sleep 2
done

echo "Audio appears healthy"
exit 0

sudo chmod +x /usr/local/bin/audio-watchdog.sh

Then a service to run it at boot, after MODEP has had a chance to start:

/etc/systemd/system/audio-watchdog.service:

[Unit]
Description=Audio watchdog - recover from cold boot audio failure
After=modep-mod-host.service
Wants=modep-mod-host.service

[Service]
Type=oneshot
ExecStart=/usr/local/bin/audio-watchdog.sh
RemainAfterExit=yes

[Install]
WantedBy=multi-user.target

sudo systemctl daemon-reload
sudo systemctl enable audio-watchdog.service

The key trick inside the script is the silent aplay playback — writing /dev/zero to the hardware device for a couple of seconds is enough to wake the DA7212 codec from whatever half-initialised state it’s stuck in after a cold boot, after which JACK can take over cleanly.


Hope this saves someone a few hours. The cold boot issue in particular is a real gotcha — everything looks like it loaded fine in systemctl status, but there’s no audio. The watchdog approach isn’t elegant but it’s reliable.