Skip to content

fix(pulse): use blocking iterate to prevent busy-spin on boot#1919

Closed
markc wants to merge 1 commit into
pop-os:masterfrom
markc:fix/pulse-busy-spin
Closed

fix(pulse): use blocking iterate to prevent busy-spin on boot#1919
markc wants to merge 1 commit into
pop-os:masterfrom
markc:fix/pulse-busy-spin

Conversation

@markc
Copy link
Copy Markdown

@markc markc commented Mar 20, 2026

Summary

  • pa_mainloop_iterate(false) (non-blocking) in the PulseAudio connection loop causes a 100% CPU busy-spin when pipewire-pulse is not yet ready at boot
  • Switches to iterate(true) (blocking) so the loop sleeps until there is an event to process
  • Adds explicit handling for Failed/Terminated context states instead of looping forever

Problem

On systems where PipeWire starts concurrently with COSMIC, pipewire-pulse may not be ready when cosmic-settings-daemon connects. The non-blocking iterate(false) call returns immediately, creating a tight loop that:

  1. Pins one CPU core at 100%
  2. Cascades into cosmic-osd spinning (retrying volume/device notifications)
  3. Causes Firefox and Thunderbird to become unresponsive

Fix

Two changes to subscriptions/pulse/src/lib.rs:

  1. iterate(false)iterate(true) — blocks until there is a PulseAudio event, eliminating the busy-spin
  2. Handle Failed/Terminated states — the previous code only checked for Ready, so a failed connection would loop forever silently. Now it logs an error and exits the thread cleanly.

Testing

Tested on CachyOS (COSMIC desktop from packages) with PipeWire:

  • 0% CPU at T+10s and T+20s after boot (was 100% before the fix)
  • Audio devices available after PipeWire settles (~10s)
  • No regression when PipeWire is already ready at connection time — blocking iterate returns immediately when events are available
  • Firefox and Thunderbird remain responsive throughout boot

When pipewire-pulse is not yet ready at boot, pa_mainloop_iterate(false)
returns immediately, causing a tight 100% CPU loop. This cascades into
cosmic-osd spinning and Firefox/Thunderbird becoming unresponsive.

Switch to iterate(true) (blocking) so the loop sleeps until there is an
event to process. Also handle Failed/Terminated context states explicitly
instead of looping forever.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
@mmstick
Copy link
Copy Markdown
Member

mmstick commented Mar 24, 2026

This crate will be dropped when pop-os/cosmic-settings-daemon#135 is merged.

@mmstick mmstick closed this Mar 24, 2026
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