Skip to content

fix(audio): preserve partial streaming PCM writes - #739

Closed
MrKitty871 wants to merge 1 commit into
Codename-11:mainfrom
MrKitty871:upstream/audio-partial-pcm
Closed

MrKitty871 wants to merge 1 commit into
Codename-11:mainfrom
MrKitty871:upstream/audio-partial-pcm

Conversation

@MrKitty871

Copy link
Copy Markdown

Summary

  • preserve complete PCM payloads when Android AudioTrack.write(..., WRITE_BLOCKING) accepts only a prefix before playback starts
  • start playback after the accepted startup prefix, then continue draining the remainder instead of silently discarding it
  • keep long writes interruptible by allowing stop() to release the active AudioTrack without waiting for the writer lock
  • prevent interrupted writers from restoring nonzero playback amplitude after cancellation
  • add regression coverage for partial writes, zero-progress writes, cancellation, and post-stop amplitude publication

Reproduction

On a Samsung device, the first synthesized TTS delta contained 192,800 bytes of 24-kHz mono PCM while the fast-path AudioTrack buffer held 33,600 bytes (700 ms). The stopped streaming track accepted only that prefix. Relay treated the positive partial return as completion, discarded the remaining 159,200 bytes, and subsequently logged playback underruns. The spoken answer therefore began late and skipped multiple lines.

Verification

  • :app:testSideloadDebugUnitTest --tests 'com.hermesandroid.relay.audio.RealtimePcmBufferPolicyTest'
  • :app:assembleSideloadCandidate
  • git diff --check
  • physical Samsung assistant invocation: complete answer spoken continuously from the beginning
  • independent review: no remaining blockers after cancellation and amplitude-race corrections

@hermes-relay-triage hermes-relay-triage Bot added area:android Kotlin app needs-maintainer-review Automated triage exhausted; needs a human labels Oct 18, 2026
@hermes-relay-triage

Copy link
Copy Markdown

🤖 Hermes-Relay automated PR intake

Thanks for the streaming PCM fix!

Intake sees an Android audio change in RealtimePcmPlayer plus a focused unit test. Summary is present, and Verification lists the focused unit test, :app:assembleSideloadCandidate, git diff --check, and a physical Samsung playback check. Those command results are not stated as pass or fail, so they are not treated as failed. Required checks have not reported yet. No linked issue.

This targets main. Normal fixes target dev. main is for a release PR from dev, or a focused hotfix based on a production tag, so this base needs confirmation.

Still missing from the template: Changes, Screenshots or an explicit "No visual change", Compatibility / risk, Lineage / contributor credit, and Checklist.

A maintainer will review the base branch and the missing intake evidence.

@Codename-11

Copy link
Copy Markdown
Owner

Thanks @MrKitty871 - the 192,800-byte chunk and 33,600-byte buffer reproduction was useful. I compared this with #747, including cancellation and the post-stop amplitude race. The implementation now on dev covers those paths and retries the PCM tail in bounded writes, so I'm closing this as overlapping work. It isn't in an Android release yet, and I haven't repeated your Samsung listening test on that implementation.

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

Labels

area:android Kotlin app needs-maintainer-review Automated triage exhausted; needs a human

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants