Skip to content

Conversation

@roderickvd
Copy link
Member

Fixes two related issues with frame alignment in the queue:

  1. Frame alignment for non-power-of-2 channel counts: The queue used a fixed threshold of 512 samples which could cause channel misalignment when the channel count doesn't evenly divide 512 (e.g., 6 channels: 512 % 6 = 2 sample offset). Replaced with dynamic threshold function that rounds to nearest frame boundary.

  2. Mid-span ending detection: Sources that end before their promised current_span_len() would cause the queue to immediately transition to the next source, potentially mid-frame. Added sample tracking and silence padding to complete frames before transitioning.

Supersedes #684, carrying over the test suite that was added there.

Branched off of #817 which fixes another span boundary problem.

roderickvd and others added 2 commits December 22, 2025 21:49
Fixes incorrect sample_rate() and channels() metadata returned by
SourcesQueueOutput when transitioning between sources with different
formats or from an empty queue. This caused audio distortion at
boundaries where metadata changes occurred.

Changes:
- Clarified Source::current_span_len() contract: returns total span
  size, Some(0) when exhausted
- Fixed SamplesBuffer to return Some(total_size) or Some(0) when
  exhausted (was None)
- Fixed SamplesBuffer::size_hint() to return remaining samples
- Updated SourcesQueueOutput to peek next source metadata when current
  is exhausted
- Added Source::is_exhausted() helper method for cleaner exhaustion
  checks throughout codebase
- Implemented ExactSizeIterator for SamplesBuffer
- Improved SkipDuration precision to avoid rounding errors

This supersedes PR #812 with a cleaner implementation following the
proper current_span_len() contract. Enabled previously ignored
queue::tests::basic test to prevent regressions.

Fixes #811

Co-authored-by: 0----0 <9070490+0----0@users.noreply.github.com>
Fixes two related issues with frame alignment in the queue:

1. Frame alignment for non-power-of-2 channel counts: The queue used a
   fixed threshold of 512 samples which could cause channel misalignment
   when the channel count doesn't evenly divide 512 (e.g., 6 channels:
   512 % 6 = 2 sample offset). Replaced with dynamic threshold function
   that rounds to nearest frame boundary.

2. Mid-span ending detection: Sources that end before their promised
   current_span_len() would cause the queue to immediately transition
   to the next source, potentially mid-frame. Added sample tracking and
   silence padding to complete frames before transitioning.

Changes:
- Replace THRESHOLD constant with threshold(channels) helper function
  that ensures frame-aligned span lengths
- Add sample tracking to detect mid-span source endings
- Inject silence padding to complete incomplete frames
- Add span_ending_mid_frame test to verify padding behavior

Supersedes #684
@yara-blue
Copy link
Member

yara-blue commented Dec 23, 2025

oh this one is fun! Thanks for all the work. I kinda gave up on this :)

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

Labels

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants