Skip to content

fix(Twitter): address client shutdown behind update screen - #1763

Open
RodrigoMenaM wants to merge 2 commits into
crimera:devfrom
RodrigoMenaM:codex/fix-block-update-client-shutdown
Open

fix(Twitter): address client shutdown behind update screen#1763
RodrigoMenaM wants to merge 2 commits into
crimera:devfrom
RodrigoMenaM:codex/fix-block-update-client-shutdown

Conversation

@RodrigoMenaM

@RodrigoMenaM RodrigoMenaM commented Aug 21, 2026

Copy link
Copy Markdown
Contributor

Scope

This PR extends the existing Block update screen patch. The fix is the combination of two protections:

  1. The existing full-cover UI hook hides and dismisses the update screen.
  2. This PR makes the underlying client-shutdown state report false while the same setting is enabled.

The state guard must not be shipped as a standalone backport without the full-cover UI hook.

Why both hooks are needed

X persists is_shutdown after its remote minimum-version check. That state is consumed outside the dialog path by launcher-entry handling and the client-shutdown network interceptor. Handling only the visible dialog can therefore leave the shutdown state active.

Conversely, an earlier local compatibility build contained only the state guard. That incomplete backport regressed account-switch navigation: switching profiles could land on a root-level update screen that Back no longer escaped. That build has been withdrawn. The corrected compatibility build combines the existing UI hook with the state guard.

The dev base of this PR already contains the full-cover UI hook; this diff adds the complementary state guard.

Change

  • Identify the shutdown-state class by its stable is_shutdown and shutdown_min_version preference keys.
  • Fingerprint its isShutdown() method directly within that resolved class.
  • When Block update screen is enabled, return false to client-shutdown consumers.
  • When disabled, continue through X's original stored-state path.
  • Keep the visible full-cover fallback tied to the same setting.
  • Place the shared setting lookup in Utils, following maintainer review.

Verification

  • Final revision: :patches:buildAndroid succeeds.
  • The combined implementation was applied to a compatible local X package and both injected hooks were confirmed in the installed DEX.
  • Cold launch stayed on the normal main activity.
  • Profile switching was exercised in both directions without the update screen, update-only activity, or a fatal runtime signal.
  • The reviewer-requested organization/fingerprint refactor does not change the injected runtime branch; its final revision is build-verified.

Addresses #1747 and the continued report in #1717.

return Utils.getBooleanPref(Settings.MISC_BLOCK_UPDATE_SCREEN);
}

public static void blockUpdateScreen(View view) {

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

Move this function to utils

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

System.Collections.Hashtable.Body

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

?

returnType = "V",
strings = listOf("is_shutdown", "shutdown_min_version"),
custom = { _, classDef ->
classDef.type.startsWith("Lcom/twitter/subsystem/clientshutdown/")

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

You can use definingClass

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

System.Collections.Hashtable.Body


execute {
val isShutdownMethod =
ClientShutdownStateFingerprint.classDef.methods.single { method ->

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

Any reason why you have not created fingerprint for it

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

System.Collections.Hashtable.Body

@RodrigoMenaM

Copy link
Copy Markdown
Contributor Author

Correction to my earlier local validation: the first compatibility build I tested was state-only, not the full combined patch. It suppressed the persisted shutdown flag but omitted the existing full-cover UI hook. That incomplete backport regressed account-switch navigation and has been withdrawn.

The working implementation uses both hooks. I rebuilt and installed that combination, confirmed both injections in the installed DEX, and tested cold launch plus profile switching in both directions without the update wall or an update-only activity. I also updated the PR description so nobody backports the state guard alone.

The latest commit addresses all three review notes: the setting helper is in Utils, the class fingerprint uses definingClass, and isShutdown() has its own fingerprint scoped to the preference-key-bearing class. The final revision passes :patches:buildAndroid.


public static boolean redirect(TabLayout$g g) {return Utils.redirect(g);}

public static boolean blockUpdateScreen() {

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

Yo keep this in Pref. I was taking about the blockUpdateScreen(View view) 🤦

@swakwork

Copy link
Copy Markdown
Collaborator

Correction to my earlier local validation: the first compatibility build I tested was state-only, not the full combined patch. It suppressed the persisted shutdown flag but omitted the existing full-cover UI hook. That incomplete backport regressed account-switch navigation and has been withdrawn.

The working implementation uses both hooks. I rebuilt and installed that combination, confirmed both injections in the installed DEX, and tested cold launch plus profile switching in both directions without the update wall or an update-only activity. I also updated the PR description so nobody backports the state guard alone.

The latest commit addresses all three review notes: the setting helper is in Utils, the class fingerprint uses definingClass, and isShutdown() has its own fingerprint scoped to the preference-key-bearing class. The final revision passes :patches:buildAndroid.

Hopefully next time I hear back from a human not an AI

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