Skip to content

Fix Push sending a wrong DATA length after a short read - #140

Merged
wherewhere merged 2 commits into
SharpAdb:mainfrom
Alex4SSB:fix/push-short-read
Oct 25, 2026
Merged

wherewhere merged 2 commits into
SharpAdb:mainfrom
Alex4SSB:fix/push-short-read

Conversation

@Alex4SSB

Copy link
Copy Markdown
Contributor

Two fixes in SyncService push, one commit each.

Wrong DATA length after a short read

Push / PushAsync (and the WinRT PushAsync) only rewrote the DATA header's length when a read returned less than a full chunk, assuming that only happens at the end of the stream. When a stream returns a short read and then a full one (pipes, network streams, COM IStreams), the full chunk goes out under the previous short read's length. adbd then aborts the transfer with invalid data message, and the file is not written.

FileStream and MemoryStream sources don't hit this, since their reads are only short at the end. I found it while streaming a pull from one device straight into a push to another through a pipe, and reproduced it on an Android 9 emulator and an Android 12 phone. The length is now set from every read.

Test: PushShortReadTest / PushShortReadAsyncTest push from a stream that returns a 5-byte read followed by full ones; both fail without the fix.

WinRT PushAsync progress

The size of an IRandomAccessStream was assigned to totalBytesRead instead of totalBytesToProcess, so progress started at the full size, ended at twice it, and never reported a total. PushWinRTAsyncTest now checks the final progress, which failed before (1210 sent for a 605-byte file).

🤖 Generated with Claude Code

Alex4SSB and others added 2 commits October 24, 2026 20:57
Push only rewrote the DATA header length when a read returned less than a
full chunk, assuming that happens only at the end of the stream. A stream
that returns a short read followed by a full one (pipes, network or COM
streams) then sent the full chunk under the short read's length, and adbd
aborted the transfer with "invalid data message". The length is now set
from every read, in Push, PushAsync and the WinRT PushAsync.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
The size of a random access stream went into totalBytesRead instead of
totalBytesToProcess, so progress started at the full size, ended at
twice it, and never reported a total.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
@wherewhere

wherewhere commented Oct 25, 2026 •

Copy link
Copy Markdown
Member

Are you sure AI is correctly?

@Alex4SSB

Copy link
Copy Markdown
Contributor Author

Well what happened is that I was implementing a direct streaming from Android to Windows using your library, instead of writing to a temp file and then giving it to Windows (streaming files using drag & drop / clipboard). Claude found this bug when trying the new mechanism with small files, and added tests that supposedly verify the fix. For now I switched to a fork that includes the fix. Naturally, don't take my word for it - feel free to decline the PR, but just to let you know that there might be a bug that needs to be fixed. The WinRT fix is untelated and not really required for my use case.

@wherewhere

Copy link
Copy Markdown
Member

OK, I will merge this.

@wherewhere
wherewhere merged commit bb8648b into SharpAdb:main Oct 25, 2026
5 checks passed
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