Skip to content

Keep wine session and component installs alive across screen lock#320

Open
maxjivi05 wants to merge 3 commits intoWinNative-Emu:mainfrom
maxjivi05:background-activity-fix
Open

Keep wine session and component installs alive across screen lock#320
maxjivi05 wants to merge 3 commits intoWinNative-Emu:mainfrom
maxjivi05:background-activity-fix

Conversation

@maxjivi05
Copy link
Copy Markdown
Contributor

Add a foreground SessionKeepAliveService (dataSync, stopWithTask=false) that holds the app process alive while a wine session is in the background or while the setup wizard is downloading/installing components. Without it, locking the phone could let the OS reap the process and tear down a paused container, or interrupt an in-flight component install.

XServerDisplayActivity starts the service in onCreate and stops it from exit() and performForcedSessionCleanup, so existing session teardown paths are unchanged. The service's onTaskRemoved runs the same terminateSessionProcessesAndWait + drainDeadChildren cleanup the exit path uses, so user swipe-away still closes the app cleanly with no zombie wine processes.

SetupWizardActivity acquires a keep-alive tag around installImageFs, installAllRecommended, and installAdvancedComponent (released in finally) so screen lock cannot interrupt those operations.

Add a foreground SessionKeepAliveService (dataSync, stopWithTask=false)
that holds the app process alive while a wine session is in the
background or while the setup wizard is downloading/installing
components. Without it, locking the phone could let the OS reap the
process and tear down a paused container, or interrupt an in-flight
component install.

XServerDisplayActivity starts the service in onCreate and stops it from
exit() and performForcedSessionCleanup, so existing session teardown
paths are unchanged. The service's onTaskRemoved runs the same
terminateSessionProcessesAndWait + drainDeadChildren cleanup the exit
path uses, so user swipe-away still closes the app cleanly with no
zombie wine processes.

SetupWizardActivity acquires a keep-alive tag around installImageFs,
installAllRecommended, and installAdvancedComponent (released in
finally) so screen lock cannot interrupt those operations.
Copy link
Copy Markdown

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 36211af52c

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment on lines +1432 to +1435
com.winlator.cmod.runtime.system.SessionKeepAliveService.stopDownload(
applicationContext,
keepAliveTag,
)
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Release keep-alive tag in finally for advanced installs

stopDownload(...) is called only at the end of the coroutine, so any exception thrown before that point (for example during the post-install refresh calls) skips tag release and leaves activeDownloads populated for that URL. In that state, the keep-alive foreground service can remain active longer than intended, and a later install of the same component will not trigger a fresh start command because HashSet.add returns false. Wrap the whole lifecycleScope.launch body in try/finally so the stop call always runs.

Useful? React with 👍 / 👎.

Settings → Components and Settings → Drivers now wrap downloads and
installs with SessionKeepAliveService.startDownload/.stopDownload, so
locking the screen during a Wine/Proton/driver install doesn't tear the
process down. The setup wizard already had this; the runtime entry
points were missed.

While in a game, the wine launcher's process.waitFor() callback or the
Steam exit watch could call exit() while the activity was backgrounded
— after a screen lock the user would unlock to "Closing Container..."
and a torn-down session. Both async exit paths now defer when
activityBackgrounded is true; onResume reconciles by checking
ProcessHelper.listRunningWineProcesses() and only honors the deferred
exit if no wine session processes remain. Spurious triggers (where the
launcher waitFor returned but wine itself is still alive) are dropped
and the session keeps running. Existing exit paths (drawer Exit,
swipe-away cleanup, onDestroy/onStop) are unchanged.
Two changes that together let the user lock the phone for any duration
and come back to a usable container:

1. Stop auto-pausing wine on activity onPause/onResume. Suspending wine
   processes for minutes-to-hours of screen-off time made them prime
   targets for the kernel OOM killer (and the cgroup freezer); the
   process death then surfaced as "Closing Container..." on unlock.
   Wine now keeps running while backgrounded, with the keep-alive
   foreground service holding the app process alive. The drawer
   "Pause all Wine processes" toggle is the only path that suspends
   wine and is still untouched.

2. When the user does manually pause wine, write
   /proc/[pid]/oom_score_adj=-1000 for each suspended process. That
   marks them as OOM_SCORE_ADJ_MIN so the kernel will not reap them on
   memory pressure during a long lock. Resume restores the default
   score before SIGCONT so a running wine session has normal priority.

xServerView.onPause/onResume are still wired up so GL rendering pauses
with the screen, and existing exit/teardown paths are unchanged.
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