Skip to content

drm: apple: audio: limit the number of periods to what SIO can serve - #277

Closed
sithglan wants to merge 1 commit into
aurora-silicon:aurora-wipfrom
sithglan:dcp-audio-sio-periods
Closed

sithglan wants to merge 1 commit into
aurora-silicon:aurora-wipfrom
sithglan:dcp-audio-sio-periods

Conversation

@sithglan

@sithglan sithglan commented Oct 11, 2026 •

Copy link
Copy Markdown

SIO has 64 descriptor slots, shared by all its channels, and sio_prep_dma_cyclic() takes one slot per period. The DCP PCM allowed periods_max = UINT_MAX, so PipeWire's default of 256-frame periods in a 32768-frame buffer asked for 128 of them:

  • sio_prep_dma_cyclic() ran out of slots and returned NULL,
  • snd_dmaengine_pcm_trigger() turned that into -ENOMEM,
  • ALSA undid the START with a STOP, a stop_link round trip to DCP,
  • PipeWire retried START about 100 times a second, and there was no sound.

strace on PipeWire's data loop showed ioctl(SNDRV_PCM_IOCTL_START) = -1 ENOMEM about 10 ms apart, and the card's hw_params showed period_size: 256, buffer_size: 32768. speaker-test and aplay worked because they use only a few periods.

Up to three DP audio outputs share one SIO on t600x and t602x (channels 0x64, 0x66, 0x68), so the PCM now allows at most 16 periods per stream: 48 slots for all three.

The limit has been there since the DCP audio driver was added; asahi and fairydust have the same code.

Testing: Mac mini M1 (j274), native boot, aurora-wip 803274a + #276 + #275 + this commit (kernel 7.1.12-g50f475b64fca, with Rust), appledrm.hdmi_audio=1. Two EIZO EV2780: one on the HDMI port (dcp, 238330000.audio-controller) and one on USB-C via DP alt mode (dcpext, 238334000.audio-controller). PipeWire 1.6.9, WirePlumber 0.5.18, default settings.

without this commit with this commit
PipeWire's hw_params on the DP card 256 × 128 periods 256 × 16 (HDMI), 128 × 16 (USB-C)
START -ENOMEM, retried ~100/s succeeds; both streams run at 48 kHz
mpv via PipeWire silent audible

Before this change, limiting PipeWire to 8 periods in a WirePlumber rule (api.alsa.period-num = 8) worked around it. With the kernel change no rule is needed. No runtime PM underflow, "Shim DMA unavailable" or timeout messages in either run.

This is independent of #276 and applies on its own to aurora-wip, but I tested it on top of #276 and #275 (#275 is needed for the USB-C monitor on this Mac mini). It may also explain silent DP audio under PipeWire in other setups: the hardware path works, only the period count is too high.

theoparis pushed a commit to tinted-software/linux that referenced this pull request Oct 13, 2026
On t6020 with the 13.5 firmware, DCP's DPTX port sends AP calls of group
1, commands 3 and 4, around link (re)configuration, audio prepare
included. The AFK v1 notify path dropped the group, so they reached the
group 0 handlers of the same numbers, SET/GET_DRIVE_SETTINGS: DCP
addresses from the payload were stored as drive settings. Behind a USB-C
to HDMI adapter DCP then refused the audio start ("Capabilities
changed") or never confirmed the stream.

Pass the group through a call_v2 op, with the signature of call_v2 on
aurora's J700 test branch (85d81b7, not in aurora-wip), and keep .call
for group 0 only. A group call to a service without call_v2 gets a
warning and no reply: AFK has no handler and does not guess one.

The DPTX port answers group 1 commands 3 and 4 the way macOS 13 does in
42 of 42 traced pairs (TV through the adapter, Dell over Thunderbolt):
an echo of the request with +0x00..0x03 cleared for (1, 3), and
+0x10..0x13 and +0x20 to the end cleared for (1, 4). The lane count sits
at +0x10 in (1, 3) and at +0x00 in (1, 4); macOS keeps it in all 42 and
clears the other slot. The J700 code reads (1, 3) the same way, with
per-lane levels from +0x20, which macOS does not clear there; it refuses
(1, 4), and its group 0 GET (0, 4) has the count at +0x00. Other groups
are echoed with a rate-limited warning.

Testing: MacBook Pro 16" M2 Pro (j416s), DCP firmware 13.5, a TV on a
USB-C to HDMI adapter and a Dell over Thunderbolt, 8 audio starts on
the TV per boot. Cold boots under the m1n1 hypervisor, aurora-wip with
PRs aurora-silicon#275-aurora-silicon#277, the AFK slots series and a bench DT change,
interleaved: with this commit the first start was accepted in 5 of 5
boots, with 0 refusals and 8 of 8 starts played; without it, 3 of 3
boots refused the first start, 2 refusals each, 4 of 8 played. The
Dell had no refusals in any boot, and no group warning was logged.
Natively, on a downstream tree with the same reply rule, the boot
connect and 3 of 8 TV replugs reached DCP (the rest failed earlier, in
the PHY): 0 refusals in 4 connects; before, 10 refusals in 5 connects.
Not tested: other SoCs, other firmware, AFK v2.

Assisted-by: Claude:claude-opus-5-5 checkpatch
Signed-off-by: nekolyanich <me@nekolyanich.com>
@sithglan
sithglan force-pushed the dcp-audio-sio-periods branch from 4259b92 to 4bf34cd Compare October 14, 2026 19:11
SIO has 64 descriptor slots, shared by all its channels, and its
cyclic prep takes one slot per period. The PCM allowed any number of
periods, so PipeWire's default of 256-frame periods in a 32768-frame
buffer asked for 128 of them. sio_prep_dma_cyclic() then ran out of
slots, snd_dmaengine_pcm_trigger() returned -ENOMEM, ALSA undid the
START with a STOP (a stop_link round trip to DCP), and PipeWire
retried about 100 times a second with no sound.

Up to three DP audio outputs share one SIO on t600x and t602x, so
allow at most 16 periods per stream, 48 slots for all three.

Fixes: cb24343 ("gpu: drm: apple: Add DCP audio driver")
Signed-off-by: Thomas Glanzmann <thomas@glanzmann.de>
@sithglan
sithglan force-pushed the dcp-audio-sio-periods branch from 4bf34cd to 7b6a4a7 Compare October 15, 2026 16:59
DjDeveloperr pushed a commit that referenced this pull request Oct 16, 2026
On t6020 with the 13.5 firmware, DCP's DPTX port sends AP calls of group
1, commands 3 and 4, around link (re)configuration, audio prepare
included. The AFK v1 notify path dropped the group, so they reached the
group 0 handlers of the same numbers, SET/GET_DRIVE_SETTINGS: DCP
addresses from the payload were stored as drive settings. Behind a USB-C
to HDMI adapter DCP then refused the audio start ("Capabilities
changed") or never confirmed the stream.

Pass the group through a call_v2 op, with the signature of call_v2 on
aurora's J700 test branch (85d81b7, not in aurora-wip), and keep .call
for group 0 only. A group call to a service without call_v2 gets a
warning and no reply: AFK has no handler and does not guess one.

The DPTX port answers group 1 commands 3 and 4 the way macOS 13 does in
42 of 42 traced pairs (TV through the adapter, Dell over Thunderbolt):
an echo of the request with +0x00..0x03 cleared for (1, 3), and
+0x10..0x13 and +0x20 to the end cleared for (1, 4). The lane count sits
at +0x10 in (1, 3) and at +0x00 in (1, 4); macOS keeps it in all 42 and
clears the other slot. The J700 code reads (1, 3) the same way, with
per-lane levels from +0x20, which macOS does not clear there; it refuses
(1, 4), and its group 0 GET (0, 4) has the count at +0x00. Other groups
are echoed with a rate-limited warning.

Testing: MacBook Pro 16" M2 Pro (j416s), DCP firmware 13.5, a TV on a
USB-C to HDMI adapter and a Dell over Thunderbolt, 8 audio starts on
the TV per boot. Cold boots under the m1n1 hypervisor, aurora-wip with
PRs #275-#277, the AFK slots series and a bench DT change,
interleaved: with this commit the first start was accepted in 5 of 5
boots, with 0 refusals and 8 of 8 starts played; without it, 3 of 3
boots refused the first start, 2 refusals each, 4 of 8 played. The
Dell had no refusals in any boot, and no group warning was logged.
Natively, on a downstream tree with the same reply rule, the boot
connect and 3 of 8 TV replugs reached DCP (the rest failed earlier, in
the PHY): 0 refusals in 4 connects; before, 10 refusals in 5 connects.
Not tested: other SoCs, other firmware, AFK v2.

Assisted-by: Claude:claude-opus-5-5 checkpatch
Signed-off-by: nekolyanich <me@nekolyanich.com>
@RyanTheTide

Copy link
Copy Markdown
Contributor

Closing as superseded: this work was ported by #328 (merged 2026-10-16) and carried into the maintained 7.3 integration/aurora line. Thanks for the original change; nothing here is lost.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants