Run the runtime on a large-stack thread to avoid a main-thread stack overflow on Windows - #246
Open
gimperioso wants to merge 1 commit into
Open
Run the runtime on a large-stack thread to avoid a main-thread stack overflow on Windows#246gimperioso wants to merge 1 commit into
gimperioso wants to merge 1 commit into
Conversation
On Windows the process main thread gets a 1 MiB stack (vs ~8 MiB on Linux). Decoding deeply nested Google Play protobuf responses recurses per nesting level and can overflow it, aborting with "thread 'main' has overflowed its stack" before anything is written to disk. Host the Tokio runtime on a dedicated thread with a 64 MiB stack so downloads succeed regardless of the platform default. Assisted-by: Claude (Anthropic)
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Problem
On Windows,
apkeep 1.0.0aborts while downloading some apps from thegoogle-playsource with:
The process exits with
0xC00000FD(STATUS_STACK_OVERFLOW) and nothing is written tothe output directory. It reproduces on e.g.
org.telegram.messengerandcom.instagram.android. This is the crash reported in #238.Root cause
mainis annotated with#[tokio::main], so the whole program future is driven withblock_onon the process main thread. On Windows the main thread only gets a1 MiB stack by default (Linux typically gives ~8 MiB).
Downloading goes through
gpapi, which decodes the Google Play protobuf responses withprost. Those responses (details/delivery, with their nested item/cluster trees) aredecoded recursively — one stack frame per level of message nesting — and the deeper
responses returned for some apps recurse far enough to overflow the 1 MiB main-thread
stack. The same binary runs fine on Linux because of the larger default stack, which is
why the crash is Windows-specific.
The depth of the response — not the size of the resulting APK — is what matters: some
larger apps download fine while a couple of mid-sized but "busy" listings overflow.
Fix
Host the Tokio runtime on a dedicated thread with a generous (64 MiB) stack, so the
download succeeds regardless of the platform's default main-thread stack size. Since the
work is still driven with
block_on(notspawn), the existing non-Send(Rc) usagein the download path is unaffected.
Verification
Built from the
1.0.0tag, Windows 10 (19045),x86_64-pc-windows-msvc,google-playsource with AAS-token auth.
org.telegram.messengercom.instagram.androidthread 'main' has overflowed its stack, 0 bytes writtenNote: an optimized release build compiled with a current
rustcmay not overflow, sincethe recursion depth sits near the 1 MiB boundary and the outcome depends on
inlining/codegen. That fragility is exactly what this change removes; the crash is
reliably reproducible with a debug build of the same tag, which this fix resolves.
A more fundamental fix would bound the recursion depth when decoding the Play protobuf
responses (in
gpapi/prost), but raising the runtime stack resolves the reported crashwithout touching the parsing path and helps on any platform with a small default
main-thread stack.