diff --git a/patches/src/main/kotlin/app/twitter/patches/DisableOutdatedVersionScreenPatch.kt b/patches/src/main/kotlin/app/twitter/patches/DisableOutdatedVersionScreenPatch.kt index 99b145d..6f8a59d 100644 --- a/patches/src/main/kotlin/app/twitter/patches/DisableOutdatedVersionScreenPatch.kt +++ b/patches/src/main/kotlin/app/twitter/patches/DisableOutdatedVersionScreenPatch.kt @@ -105,6 +105,27 @@ private val serverDrivenCoverRendererFingerprint = Fingerprint( strings = listOf("component") ) +private val serverDrivenCoverLifecycleFingerprint = Fingerprint( + definingClass = "Lcom/x/urt/cover/component/a;", + name = "h", + returnType = "V", + parameters = emptyList(), + strings = listOf("impression") +) + +private val brazeInAppMessageDisplayFingerprint = Fingerprint( + definingClass = "Lcom/braze/ui/inappmessage/BrazeInAppMessageManager;", + name = "displayInAppMessage${'$'}suspendImpl", + returnType = "Ljava/lang/Object;", + parameters = listOf( + "Lcom/braze/ui/inappmessage/BrazeInAppMessageManager;", + "Lcom/braze/models/inappmessage/IInAppMessage;", + "Z", + "Lkotlin/coroutines/Continuation;" + ), + strings = listOf("In-app message is expired. Doing nothing. Expiration: ") +) + private const val APP_UPDATE_ACTIVITY = "com.twitter.clientshutdown.update.AppUpdateActivity" private val disableOutdatedVersionActivityPatch = resourcePatch { @@ -221,8 +242,33 @@ val disableOutdatedVersionScreenPatch = bytecodePatch( invoke-virtual {v0}, Lcom/x/models/timelines/instructions/cover/URTCover${'$'}FullCover;->getData()Lcom/x/models/timelines/instructions/cover/URTFullCover; move-result-object v0 invoke-virtual {v0}, Lcom/x/models/timelines/instructions/cover/URTFullCover;->getPrimaryText()Lcom/x/models/text/RichText; - move-result-object v0 - goto :check_outdated_cover_title + move-result-object v1 + invoke-virtual {v1}, Lcom/x/models/text/RichText;->getText()Ljava/lang/String; + move-result-object v1 + const-string v2, "This app is out of date." + invoke-virtual {v1, v2}, Ljava/lang/String;->contains(Ljava/lang/CharSequence;)Z + move-result v1 + if-nez v1, :block_outdated_server_cover + invoke-virtual {v0}, Lcom/x/models/timelines/instructions/cover/URTFullCover;->getSecondaryText()Lcom/x/models/text/RichText; + move-result-object v1 + if-eqz v1, :check_outdated_full_cover_detail + invoke-virtual {v1}, Lcom/x/models/text/RichText;->getText()Ljava/lang/String; + move-result-object v1 + const-string v2, "This app is out of date." + invoke-virtual {v1, v2}, Ljava/lang/String;->contains(Ljava/lang/CharSequence;)Z + move-result v1 + if-nez v1, :block_outdated_server_cover + :check_outdated_full_cover_detail + invoke-virtual {v0}, Lcom/x/models/timelines/instructions/cover/URTFullCover;->getDetailText()Lcom/x/models/text/RichText; + move-result-object v1 + if-eqz v1, :outdated_server_cover_allowed + invoke-virtual {v1}, Lcom/x/models/text/RichText;->getText()Ljava/lang/String; + move-result-object v1 + const-string v2, "This app is out of date." + invoke-virtual {v1, v2}, Ljava/lang/String;->contains(Ljava/lang/CharSequence;)Z + move-result v1 + if-nez v1, :block_outdated_server_cover + goto :outdated_server_cover_allowed :check_outdated_half_cover instance-of v1, v0, Lcom/x/models/timelines/instructions/cover/URTCover${'$'}HalfCover; if-eqz v1, :outdated_server_cover_allowed @@ -230,18 +276,135 @@ val disableOutdatedVersionScreenPatch = bytecodePatch( invoke-virtual {v0}, Lcom/x/models/timelines/instructions/cover/URTCover${'$'}HalfCover;->getData()Lcom/x/models/timelines/instructions/cover/URTHalfCover; move-result-object v0 invoke-virtual {v0}, Lcom/x/models/timelines/instructions/cover/URTHalfCover;->getPrimaryText()Lcom/x/models/text/RichText; - move-result-object v0 - :check_outdated_cover_title - invoke-virtual {v0}, Lcom/x/models/text/RichText;->getText()Ljava/lang/String; - move-result-object v0 - const-string v1, "This app is out of date." - invoke-virtual {v1, v0}, Ljava/lang/String;->equals(Ljava/lang/Object;)Z - move-result v0 - if-eqz v0, :outdated_server_cover_allowed + move-result-object v1 + invoke-virtual {v1}, Lcom/x/models/text/RichText;->getText()Ljava/lang/String; + move-result-object v1 + const-string v2, "This app is out of date." + invoke-virtual {v1, v2}, Ljava/lang/String;->contains(Ljava/lang/CharSequence;)Z + move-result v1 + if-nez v1, :block_outdated_server_cover + invoke-virtual {v0}, Lcom/x/models/timelines/instructions/cover/URTHalfCover;->getSecondaryText()Lcom/x/models/text/RichText; + move-result-object v1 + if-eqz v1, :outdated_server_cover_allowed + invoke-virtual {v1}, Lcom/x/models/text/RichText;->getText()Ljava/lang/String; + move-result-object v1 + const-string v2, "This app is out of date." + invoke-virtual {v1, v2}, Ljava/lang/String;->contains(Ljava/lang/CharSequence;)Z + move-result v1 + if-eqz v1, :outdated_server_cover_allowed + :block_outdated_server_cover return-void :outdated_server_cover_allowed """ ) + + serverDrivenCoverLifecycleFingerprint.method.addInstructions( + 0, + """ + iget-object v0, p0, Lcom/x/urt/cover/component/a;->a:Lcom/x/urt/cover/component/b; + invoke-virtual {v0}, Lcom/x/urt/cover/component/b;->a()Lcom/x/models/timelines/instructions/cover/URTCover; + move-result-object v1 + instance-of v2, v1, Lcom/x/models/timelines/instructions/cover/URTCover${'$'}FullCover; + if-eqz v2, :check_retained_outdated_half_cover + check-cast v1, Lcom/x/models/timelines/instructions/cover/URTCover${'$'}FullCover; + invoke-virtual {v1}, Lcom/x/models/timelines/instructions/cover/URTCover${'$'}FullCover;->getData()Lcom/x/models/timelines/instructions/cover/URTFullCover; + move-result-object v1 + invoke-virtual {v1}, Lcom/x/models/timelines/instructions/cover/URTFullCover;->getPrimaryText()Lcom/x/models/text/RichText; + move-result-object v2 + invoke-virtual {v2}, Lcom/x/models/text/RichText;->getText()Ljava/lang/String; + move-result-object v2 + const-string v3, "This app is out of date." + invoke-virtual {v2, v3}, Ljava/lang/String;->contains(Ljava/lang/CharSequence;)Z + move-result v2 + if-nez v2, :clear_retained_outdated_cover + invoke-virtual {v1}, Lcom/x/models/timelines/instructions/cover/URTFullCover;->getSecondaryText()Lcom/x/models/text/RichText; + move-result-object v2 + if-eqz v2, :check_retained_outdated_full_cover_detail + invoke-virtual {v2}, Lcom/x/models/text/RichText;->getText()Ljava/lang/String; + move-result-object v2 + const-string v3, "This app is out of date." + invoke-virtual {v2, v3}, Ljava/lang/String;->contains(Ljava/lang/CharSequence;)Z + move-result v2 + if-nez v2, :clear_retained_outdated_cover + :check_retained_outdated_full_cover_detail + invoke-virtual {v1}, Lcom/x/models/timelines/instructions/cover/URTFullCover;->getDetailText()Lcom/x/models/text/RichText; + move-result-object v2 + if-eqz v2, :retained_server_cover_allowed + invoke-virtual {v2}, Lcom/x/models/text/RichText;->getText()Ljava/lang/String; + move-result-object v2 + const-string v3, "This app is out of date." + invoke-virtual {v2, v3}, Ljava/lang/String;->contains(Ljava/lang/CharSequence;)Z + move-result v2 + if-nez v2, :clear_retained_outdated_cover + goto :retained_server_cover_allowed + :check_retained_outdated_half_cover + instance-of v2, v1, Lcom/x/models/timelines/instructions/cover/URTCover${'$'}HalfCover; + if-eqz v2, :retained_server_cover_allowed + check-cast v1, Lcom/x/models/timelines/instructions/cover/URTCover${'$'}HalfCover; + invoke-virtual {v1}, Lcom/x/models/timelines/instructions/cover/URTCover${'$'}HalfCover;->getData()Lcom/x/models/timelines/instructions/cover/URTHalfCover; + move-result-object v1 + invoke-virtual {v1}, Lcom/x/models/timelines/instructions/cover/URTHalfCover;->getPrimaryText()Lcom/x/models/text/RichText; + move-result-object v2 + invoke-virtual {v2}, Lcom/x/models/text/RichText;->getText()Ljava/lang/String; + move-result-object v2 + const-string v3, "This app is out of date." + invoke-virtual {v2, v3}, Ljava/lang/String;->contains(Ljava/lang/CharSequence;)Z + move-result v2 + if-nez v2, :clear_retained_outdated_cover + invoke-virtual {v1}, Lcom/x/models/timelines/instructions/cover/URTHalfCover;->getSecondaryText()Lcom/x/models/text/RichText; + move-result-object v2 + if-eqz v2, :retained_server_cover_allowed + invoke-virtual {v2}, Lcom/x/models/text/RichText;->getText()Ljava/lang/String; + move-result-object v2 + const-string v3, "This app is out of date." + invoke-virtual {v2, v3}, Ljava/lang/String;->contains(Ljava/lang/CharSequence;)Z + move-result v2 + if-eqz v2, :retained_server_cover_allowed + :clear_retained_outdated_cover + iget-object v1, v0, Lcom/x/urt/cover/component/b;->c:Lcom/x/urt/cover/component/e${'$'}a; + iget-object v1, v1, Lcom/x/urt/cover/component/e${'$'}a;->a:Lcom/twitter/tipjar/ui/screen/c; + invoke-virtual {v1}, Lcom/twitter/tipjar/ui/screen/c;->invoke()Ljava/lang/Object; + return-void + :retained_server_cover_allowed + """ + ) + + brazeInAppMessageDisplayFingerprint.method.addInstructions( + 0, + """ + move-object/from16 v0, p1 + instance-of v1, v0, Lcom/braze/models/inappmessage/InAppMessageImmersiveBase; + if-eqz v1, :check_braze_outdated_message_body + move-object v1, v0 + check-cast v1, Lcom/braze/models/inappmessage/InAppMessageImmersiveBase; + invoke-virtual {v1}, Lcom/braze/models/inappmessage/InAppMessageImmersiveBase;->getHeader()Ljava/lang/String; + move-result-object v1 + if-eqz v1, :check_braze_outdated_message_body + const-string v2, "This app is out of date." + invoke-virtual {v1, v2}, Ljava/lang/String;->contains(Ljava/lang/CharSequence;)Z + move-result v1 + if-nez v1, :block_braze_outdated_message + :check_braze_outdated_message_body + instance-of v1, v0, Lcom/braze/models/inappmessage/InAppMessageBase; + if-eqz v1, :braze_in_app_message_allowed + check-cast v0, Lcom/braze/models/inappmessage/InAppMessageBase; + invoke-virtual {v0}, Lcom/braze/models/inappmessage/InAppMessageBase;->getMessage()Ljava/lang/String; + move-result-object v0 + if-eqz v0, :braze_in_app_message_allowed + const-string v1, "This app is out of date." + invoke-virtual {v0, v1}, Ljava/lang/String;->contains(Ljava/lang/CharSequence;)Z + move-result v1 + if-nez v1, :block_braze_outdated_message + const-string v1, "current app version is unsupported" + invoke-virtual {v0, v1}, Ljava/lang/String;->contains(Ljava/lang/CharSequence;)Z + move-result v0 + if-eqz v0, :braze_in_app_message_allowed + :block_braze_outdated_message + sget-object v0, Lkotlin/Unit;->a:Lkotlin/Unit; + return-object v0 + :braze_in_app_message_allowed + """ + ) } }