mirror of
https://github.com/revanced/revanced-patches.git
synced 2025-04-30 22:54:40 +02:00
chore: Lint code
This commit also changes the API, but these changes are considered fixes.
This commit is contained in:
parent
e8b54bd0ec
commit
9ac558dd2b
@ -314,8 +314,8 @@ public final class app/revanced/patches/music/interaction/permanentrepeat/Perman
|
||||
public synthetic fun execute (Lapp/revanced/patcher/data/Context;)V
|
||||
}
|
||||
|
||||
public final class app/revanced/patches/music/interaction/permanentshuffle/PermanentShuffleTogglePatch : app/revanced/patcher/patch/BytecodePatch {
|
||||
public static final field INSTANCE Lapp/revanced/patches/music/interaction/permanentshuffle/PermanentShuffleTogglePatch;
|
||||
public final class app/revanced/patches/music/interaction/permanentshuffle/PermanentShufflePatch : app/revanced/patcher/patch/BytecodePatch {
|
||||
public static final field INSTANCE Lapp/revanced/patches/music/interaction/permanentshuffle/PermanentShufflePatch;
|
||||
public fun execute (Lapp/revanced/patcher/data/BytecodeContext;)V
|
||||
public synthetic fun execute (Lapp/revanced/patcher/data/Context;)V
|
||||
}
|
||||
@ -894,8 +894,8 @@ public final class app/revanced/patches/strava/upselling/DisableSubscriptionSugg
|
||||
public synthetic fun execute (Lapp/revanced/patcher/data/Context;)V
|
||||
}
|
||||
|
||||
public final class app/revanced/patches/ticktick/misc/themeunlock/UnlockProPatch : app/revanced/patcher/patch/BytecodePatch {
|
||||
public static final field INSTANCE Lapp/revanced/patches/ticktick/misc/themeunlock/UnlockProPatch;
|
||||
public final class app/revanced/patches/ticktick/misc/themeunlock/UnlockThemesPatch : app/revanced/patcher/patch/BytecodePatch {
|
||||
public static final field INSTANCE Lapp/revanced/patches/ticktick/misc/themeunlock/UnlockThemesPatch;
|
||||
public fun execute (Lapp/revanced/patcher/data/BytecodeContext;)V
|
||||
public synthetic fun execute (Lapp/revanced/patcher/data/Context;)V
|
||||
}
|
||||
|
@ -14,7 +14,7 @@ import com.android.tools.smali.dexlib2.iface.instruction.Instruction
|
||||
name = "Spoof Wi-Fi connection",
|
||||
description = "Spoofs an existing Wi-Fi connection.",
|
||||
use = false,
|
||||
requiresIntegrations = true
|
||||
requiresIntegrations = true,
|
||||
)
|
||||
@Suppress("unused")
|
||||
object SpoofWifiPatch : BaseTransformInstructionsPatch<Instruction35cInfo>() {
|
||||
@ -25,12 +25,12 @@ object SpoofWifiPatch : BaseTransformInstructionsPatch<Instruction35cInfo>() {
|
||||
classDef: ClassDef,
|
||||
method: Method,
|
||||
instruction: Instruction,
|
||||
instructionIndex: Int
|
||||
instructionIndex: Int,
|
||||
) = filterMapInstruction35c<MethodCall>(
|
||||
INTEGRATIONS_CLASS_DESCRIPTOR_PREFIX,
|
||||
classDef,
|
||||
instruction,
|
||||
instructionIndex
|
||||
instructionIndex,
|
||||
)
|
||||
|
||||
override fun transform(mutableMethod: MutableMethod, entry: Instruction35cInfo) {
|
||||
@ -38,14 +38,13 @@ object SpoofWifiPatch : BaseTransformInstructionsPatch<Instruction35cInfo>() {
|
||||
methodType.replaceInvokeVirtualWithIntegrations(INTEGRATIONS_CLASS_DESCRIPTOR, mutableMethod, instruction, instructionIndex)
|
||||
}
|
||||
|
||||
|
||||
// Information about method calls we want to replace
|
||||
private enum class MethodCall(
|
||||
override val definedClassName: String,
|
||||
override val methodName: String,
|
||||
override val methodParams: Array<String>,
|
||||
override val returnType: String,
|
||||
): IMethodCall {
|
||||
) : IMethodCall {
|
||||
GetSystemService1(
|
||||
"Landroid/content/Context;",
|
||||
"getSystemService",
|
||||
@ -201,6 +200,6 @@ object SpoofWifiPatch : BaseTransformInstructionsPatch<Instruction35cInfo>() {
|
||||
"unregisterNetworkCallback",
|
||||
arrayOf("Landroid/app/PendingIntent;"),
|
||||
"V",
|
||||
);
|
||||
),
|
||||
}
|
||||
}
|
||||
|
@ -33,48 +33,50 @@ interface IMethodCall {
|
||||
definingClassDescriptor: String,
|
||||
method: MutableMethod,
|
||||
instruction: Instruction35c,
|
||||
instructionIndex: Int
|
||||
instructionIndex: Int,
|
||||
) {
|
||||
val registers = arrayOf(
|
||||
instruction.registerC,
|
||||
instruction.registerD,
|
||||
instruction.registerE,
|
||||
instruction.registerF,
|
||||
instruction.registerG
|
||||
instruction.registerG,
|
||||
)
|
||||
val argsNum = methodParams.size + 1 // + 1 for instance of definedClassName
|
||||
if (argsNum > registers.size) {
|
||||
// should never happen, but just to be sure (also for the future) a safety check
|
||||
throw RuntimeException(
|
||||
"Not enough registers for ${definedClassName}#${methodName}: " +
|
||||
"Required $argsNum registers, but only got ${registers.size}."
|
||||
"Not enough registers for $definedClassName#$methodName: " +
|
||||
"Required $argsNum registers, but only got ${registers.size}.",
|
||||
)
|
||||
}
|
||||
|
||||
val args = registers.take(argsNum).joinToString(separator = ", ") { reg -> "v${reg}" }
|
||||
val args = registers.take(argsNum).joinToString(separator = ", ") { reg -> "v$reg" }
|
||||
val replacementMethodDefinition =
|
||||
"${methodName}(${definedClassName}${methodParams.joinToString(separator = "")})${returnType}"
|
||||
"$methodName(${definedClassName}${methodParams.joinToString(separator = "")})$returnType"
|
||||
|
||||
method.replaceInstruction(
|
||||
instructionIndex,
|
||||
"invoke-static { $args }, ${definingClassDescriptor}->${replacementMethodDefinition}"
|
||||
"invoke-static { $args }, $definingClassDescriptor->$replacementMethodDefinition",
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
inline fun <reified E> fromMethodReference(methodReference: MethodReference)
|
||||
inline fun <reified E> fromMethodReference(
|
||||
methodReference: MethodReference,
|
||||
)
|
||||
where E : Enum<E>, E : IMethodCall = enumValues<E>().firstOrNull { search ->
|
||||
search.definedClassName == methodReference.definingClass
|
||||
&& search.methodName == methodReference.name
|
||||
&& methodReference.parameterTypes.toTypedArray().contentEquals(search.methodParams)
|
||||
&& search.returnType == methodReference.returnType
|
||||
search.definedClassName == methodReference.definingClass &&
|
||||
search.methodName == methodReference.name &&
|
||||
methodReference.parameterTypes.toTypedArray().contentEquals(search.methodParams) &&
|
||||
search.returnType == methodReference.returnType
|
||||
}
|
||||
|
||||
inline fun <reified E> filterMapInstruction35c(
|
||||
integrationsClassDescriptorPrefix: String,
|
||||
classDef: ClassDef,
|
||||
instruction: Instruction,
|
||||
instructionIndex: Int
|
||||
instructionIndex: Int,
|
||||
): Instruction35cInfo? where E : Enum<E>, E : IMethodCall {
|
||||
if (classDef.type.startsWith(integrationsClassDescriptorPrefix)) {
|
||||
// avoid infinite recursion
|
||||
|
@ -15,20 +15,21 @@ import com.android.tools.smali.dexlib2.iface.instruction.Instruction
|
||||
description = "Removes the restriction of capturing audio from apps that normally wouldn't allow it.",
|
||||
dependencies = [RemoveCaptureRestrictionResourcePatch::class],
|
||||
use = false,
|
||||
requiresIntegrations = true
|
||||
requiresIntegrations = true,
|
||||
)
|
||||
@Suppress("unused")
|
||||
object RemoveCaptureRestrictionPatch : BaseTransformInstructionsPatch<Instruction35cInfo>() {
|
||||
private const val INTEGRATIONS_CLASS_DESCRIPTOR_PREFIX =
|
||||
"Lapp/revanced/integrations/all/screencapture/removerestriction/RemoveScreencaptureRestrictionPatch"
|
||||
private const val INTEGRATIONS_CLASS_DESCRIPTOR = "$INTEGRATIONS_CLASS_DESCRIPTOR_PREFIX;"
|
||||
|
||||
// Information about method calls we want to replace
|
||||
enum class MethodCall(
|
||||
override val definedClassName: String,
|
||||
override val methodName: String,
|
||||
override val methodParams: Array<String>,
|
||||
override val returnType: String
|
||||
): IMethodCall {
|
||||
override val returnType: String,
|
||||
) : IMethodCall {
|
||||
SetAllowedCapturePolicySingle(
|
||||
"Landroid/media/AudioAttributes\$Builder;",
|
||||
"setAllowedCapturePolicy",
|
||||
@ -40,19 +41,19 @@ object RemoveCaptureRestrictionPatch : BaseTransformInstructionsPatch<Instructio
|
||||
"setAllowedCapturePolicy",
|
||||
arrayOf("I"),
|
||||
"V",
|
||||
);
|
||||
),
|
||||
}
|
||||
|
||||
override fun filterMap(
|
||||
classDef: ClassDef,
|
||||
method: Method,
|
||||
instruction: Instruction,
|
||||
instructionIndex: Int
|
||||
instructionIndex: Int,
|
||||
) = filterMapInstruction35c<MethodCall>(
|
||||
INTEGRATIONS_CLASS_DESCRIPTOR_PREFIX,
|
||||
classDef,
|
||||
instruction,
|
||||
instructionIndex
|
||||
instructionIndex,
|
||||
)
|
||||
|
||||
override fun transform(mutableMethod: MutableMethod, entry: Instruction35cInfo) {
|
||||
|
@ -24,7 +24,7 @@ import com.android.tools.smali.dexlib2.iface.reference.FieldReference
|
||||
@Suppress("unused")
|
||||
object RemoveScreenshotRestrictionPatch : BaseTransformInstructionsPatch<Instruction35cInfo>() {
|
||||
private const val INTEGRATIONS_CLASS_DESCRIPTOR_PREFIX =
|
||||
"Lapp/revanced/integrations/all/screenshot/removerestriction/RemoveScreenshotRestrictionPatch"
|
||||
"Lapp/revanced/integrations/all/screenshot/removerestriction/RemoveScreenshotRestrictionPatch"
|
||||
private const val INTEGRATIONS_CLASS_DESCRIPTOR = "$INTEGRATIONS_CLASS_DESCRIPTOR_PREFIX;"
|
||||
|
||||
override fun execute(context: BytecodeContext) {
|
||||
@ -36,12 +36,12 @@ object RemoveScreenshotRestrictionPatch : BaseTransformInstructionsPatch<Instruc
|
||||
classDef: ClassDef,
|
||||
method: Method,
|
||||
instruction: Instruction,
|
||||
instructionIndex: Int
|
||||
instructionIndex: Int,
|
||||
) = filterMapInstruction35c<MethodCall>(
|
||||
INTEGRATIONS_CLASS_DESCRIPTOR_PREFIX,
|
||||
classDef,
|
||||
instruction,
|
||||
instructionIndex
|
||||
instructionIndex,
|
||||
)
|
||||
|
||||
override fun transform(mutableMethod: MutableMethod, entry: Instruction35cInfo) {
|
||||
@ -54,8 +54,8 @@ object RemoveScreenshotRestrictionPatch : BaseTransformInstructionsPatch<Instruc
|
||||
override val definedClassName: String,
|
||||
override val methodName: String,
|
||||
override val methodParams: Array<String>,
|
||||
override val returnType: String
|
||||
): IMethodCall {
|
||||
override val returnType: String,
|
||||
) : IMethodCall {
|
||||
AddFlags(
|
||||
"Landroid/view/Window;",
|
||||
"addFlags",
|
||||
@ -67,7 +67,7 @@ object RemoveScreenshotRestrictionPatch : BaseTransformInstructionsPatch<Instruc
|
||||
"setFlags",
|
||||
arrayOf("I", "I"),
|
||||
"V",
|
||||
);
|
||||
),
|
||||
}
|
||||
}
|
||||
|
||||
@ -76,7 +76,7 @@ private class ModifyLayoutParamsFlags : BaseTransformInstructionsPatch<Pair<Inst
|
||||
classDef: ClassDef,
|
||||
method: Method,
|
||||
instruction: Instruction,
|
||||
instructionIndex: Int
|
||||
instructionIndex: Int,
|
||||
): Pair<Instruction22c, Int>? {
|
||||
if (instruction.opcode != Opcode.IPUT) {
|
||||
return null
|
||||
@ -85,9 +85,10 @@ private class ModifyLayoutParamsFlags : BaseTransformInstructionsPatch<Pair<Inst
|
||||
val instruction22c = instruction as Instruction22c
|
||||
val fieldReference = instruction22c.reference as FieldReference
|
||||
|
||||
if (fieldReference.definingClass != "Landroid/view/WindowManager\$LayoutParams;"
|
||||
|| fieldReference.name != "flags"
|
||||
|| fieldReference.type != "I") {
|
||||
if (fieldReference.definingClass != "Landroid/view/WindowManager\$LayoutParams;" ||
|
||||
fieldReference.name != "flags" ||
|
||||
fieldReference.type != "I"
|
||||
) {
|
||||
return null
|
||||
}
|
||||
|
||||
@ -100,7 +101,7 @@ private class ModifyLayoutParamsFlags : BaseTransformInstructionsPatch<Pair<Inst
|
||||
|
||||
mutableMethod.addInstructions(
|
||||
index,
|
||||
"and-int/lit16 v$register, v$register, -0x2001"
|
||||
"and-int/lit16 v$register, v$register, -0x2001",
|
||||
)
|
||||
}
|
||||
}
|
||||
|
@ -16,7 +16,6 @@ import com.android.tools.smali.dexlib2.immutable.reference.ImmutableMethodRefere
|
||||
import com.android.tools.smali.dexlib2.util.MethodUtil
|
||||
import java.util.*
|
||||
|
||||
|
||||
@Patch(
|
||||
name = "Spoof SIM country",
|
||||
description = "Spoofs country information returned by the SIM card provider.",
|
||||
@ -46,14 +45,14 @@ object SpoofSimCountryPatch : BaseTransformInstructionsPatch<Pair<Int, String>>(
|
||||
title,
|
||||
"ISO-3166-1 alpha-2 country code equivalent for the SIM provider's country code.",
|
||||
false,
|
||||
validator = { it: String? -> it == null || it.uppercase() in countries.values }
|
||||
validator = { it: String? -> it == null || it.uppercase() in countries.values },
|
||||
)
|
||||
|
||||
override fun filterMap(
|
||||
classDef: ClassDef,
|
||||
method: Method,
|
||||
instruction: Instruction,
|
||||
instructionIndex: Int
|
||||
instructionIndex: Int,
|
||||
): Pair<Int, String>? {
|
||||
if (instruction !is ReferenceInstruction) return null
|
||||
|
||||
@ -73,12 +72,12 @@ object SpoofSimCountryPatch : BaseTransformInstructionsPatch<Pair<Int, String>>(
|
||||
|
||||
override fun transform(
|
||||
mutableMethod: MutableMethod,
|
||||
entry: Pair<Int, String>
|
||||
entry: Pair<Int, String>,
|
||||
) = transformMethodCall(entry, mutableMethod)
|
||||
|
||||
private fun transformMethodCall(
|
||||
entry: Pair<Int, String>,
|
||||
mutableMethod: MutableMethod
|
||||
mutableMethod: MutableMethod,
|
||||
) {
|
||||
val (instructionIndex, methodCallValue) = entry
|
||||
|
||||
@ -86,28 +85,28 @@ object SpoofSimCountryPatch : BaseTransformInstructionsPatch<Pair<Int, String>>(
|
||||
|
||||
mutableMethod.replaceInstruction(
|
||||
instructionIndex + 1,
|
||||
"const-string v$register, \"$methodCallValue\""
|
||||
"const-string v$register, \"$methodCallValue\"",
|
||||
)
|
||||
}
|
||||
|
||||
private enum class MethodCall(
|
||||
val reference: MethodReference
|
||||
val reference: MethodReference,
|
||||
) {
|
||||
NetworkCountryIso(
|
||||
ImmutableMethodReference(
|
||||
"Landroid/telephony/TelephonyManager;",
|
||||
"getNetworkCountryIso",
|
||||
emptyList(),
|
||||
"Ljava/lang/String;"
|
||||
)
|
||||
"Landroid/telephony/TelephonyManager;",
|
||||
"getNetworkCountryIso",
|
||||
emptyList(),
|
||||
"Ljava/lang/String;",
|
||||
),
|
||||
),
|
||||
SimCountryIso(
|
||||
ImmutableMethodReference(
|
||||
"Landroid/telephony/TelephonyManager;",
|
||||
"getSimCountryIso",
|
||||
emptyList(),
|
||||
"Ljava/lang/String;"
|
||||
)
|
||||
)
|
||||
"Landroid/telephony/TelephonyManager;",
|
||||
"getSimCountryIso",
|
||||
emptyList(),
|
||||
"Ljava/lang/String;",
|
||||
),
|
||||
),
|
||||
}
|
||||
}
|
||||
|
@ -1,6 +1,5 @@
|
||||
package app.revanced.patches.backdrops.misc.pro
|
||||
|
||||
import app.revanced.util.exception
|
||||
import app.revanced.patcher.data.BytecodeContext
|
||||
import app.revanced.patcher.extensions.InstructionExtensions.addInstruction
|
||||
import app.revanced.patcher.extensions.InstructionExtensions.getInstruction
|
||||
@ -8,15 +7,16 @@ import app.revanced.patcher.patch.BytecodePatch
|
||||
import app.revanced.patcher.patch.annotation.CompatiblePackage
|
||||
import app.revanced.patcher.patch.annotation.Patch
|
||||
import app.revanced.patches.backdrops.misc.pro.fingerprints.ProUnlockFingerprint
|
||||
import app.revanced.util.exception
|
||||
import com.android.tools.smali.dexlib2.iface.instruction.OneRegisterInstruction
|
||||
|
||||
@Patch(
|
||||
name = "Pro unlock",
|
||||
compatiblePackages = [CompatiblePackage("com.backdrops.wallpapers", ["4.52"])]
|
||||
compatiblePackages = [CompatiblePackage("com.backdrops.wallpapers", ["4.52"])],
|
||||
)
|
||||
@Suppress("unused")
|
||||
object ProUnlockPatch : BytecodePatch(
|
||||
setOf(ProUnlockFingerprint)
|
||||
setOf(ProUnlockFingerprint),
|
||||
) {
|
||||
override fun execute(context: BytecodeContext) {
|
||||
ProUnlockFingerprint.result?.let { result ->
|
||||
@ -28,10 +28,9 @@ object ProUnlockPatch : BytecodePatch(
|
||||
result.scanResult.patternScanResult!!.endIndex,
|
||||
"""
|
||||
const/4 v$register, 0x1
|
||||
"""
|
||||
""",
|
||||
)
|
||||
}
|
||||
|
||||
} ?: throw ProUnlockFingerprint.exception
|
||||
}
|
||||
}
|
@ -9,10 +9,10 @@ internal object ProUnlockFingerprint : MethodFingerprint(
|
||||
Opcode.MOVE_RESULT_OBJECT,
|
||||
Opcode.INVOKE_INTERFACE,
|
||||
Opcode.MOVE_RESULT,
|
||||
Opcode.IF_EQZ
|
||||
Opcode.IF_EQZ,
|
||||
),
|
||||
customFingerprint = { methodDef, _ ->
|
||||
methodDef.definingClass == "Lcom/backdrops/wallpapers/data/local/DatabaseHandlerIAB;"
|
||||
&& methodDef.name == "lambda\$existPurchase\$0"
|
||||
}
|
||||
methodDef.definingClass == "Lcom/backdrops/wallpapers/data/local/DatabaseHandlerIAB;" &&
|
||||
methodDef.name == "lambda\$existPurchase\$0"
|
||||
},
|
||||
)
|
@ -1,20 +1,20 @@
|
||||
package app.revanced.patches.candylinkvpn
|
||||
|
||||
import app.revanced.util.exception
|
||||
import app.revanced.patcher.data.BytecodeContext
|
||||
import app.revanced.patcher.extensions.InstructionExtensions.addInstructions
|
||||
import app.revanced.patcher.patch.BytecodePatch
|
||||
import app.revanced.patcher.patch.annotation.CompatiblePackage
|
||||
import app.revanced.patcher.patch.annotation.Patch
|
||||
import app.revanced.patches.candylinkvpn.fingerprints.IsPremiumPurchasedFingerprint
|
||||
import app.revanced.util.exception
|
||||
|
||||
@Patch(
|
||||
name = "Unlock pro",
|
||||
compatiblePackages = [CompatiblePackage("com.candylink.openvpn")]
|
||||
compatiblePackages = [CompatiblePackage("com.candylink.openvpn")],
|
||||
)
|
||||
@Suppress("unused")
|
||||
object UnlockProPatch : BytecodePatch(
|
||||
setOf(IsPremiumPurchasedFingerprint)
|
||||
setOf(IsPremiumPurchasedFingerprint),
|
||||
) {
|
||||
override fun execute(context: BytecodeContext) {
|
||||
IsPremiumPurchasedFingerprint.result?.mutableMethod?.addInstructions(
|
||||
@ -22,7 +22,7 @@ object UnlockProPatch : BytecodePatch(
|
||||
"""
|
||||
const/4 v0, 0x1
|
||||
return v0
|
||||
"""
|
||||
""",
|
||||
) ?: throw IsPremiumPurchasedFingerprint.exception
|
||||
}
|
||||
}
|
@ -5,6 +5,6 @@ import app.revanced.patcher.fingerprint.MethodFingerprint
|
||||
internal object IsPremiumPurchasedFingerprint : MethodFingerprint(
|
||||
customFingerprint = { methodDef, _ ->
|
||||
methodDef.definingClass.endsWith("PreferenceProvider;") &&
|
||||
methodDef.name == "isPremiumPurchased"
|
||||
}
|
||||
methodDef.name == "isPremiumPurchased"
|
||||
},
|
||||
)
|
@ -1,21 +1,21 @@
|
||||
package app.revanced.patches.cieid.restrictions.root
|
||||
|
||||
import app.revanced.util.exception
|
||||
import app.revanced.patcher.data.BytecodeContext
|
||||
import app.revanced.patcher.extensions.InstructionExtensions.addInstruction
|
||||
import app.revanced.patcher.patch.BytecodePatch
|
||||
import app.revanced.patcher.patch.annotation.CompatiblePackage
|
||||
import app.revanced.patcher.patch.annotation.Patch
|
||||
import app.revanced.patches.cieid.restrictions.root.fingerprints.CheckRootFingerprint
|
||||
import app.revanced.util.exception
|
||||
|
||||
@Patch(
|
||||
name = "Bypass root checks",
|
||||
description = "Removes the restriction to use the app with root permissions or on a custom ROM.",
|
||||
compatiblePackages = [CompatiblePackage("it.ipzs.cieid")]
|
||||
compatiblePackages = [CompatiblePackage("it.ipzs.cieid")],
|
||||
)
|
||||
@Suppress("unused")
|
||||
object BypassRootChecksPatch : BytecodePatch(
|
||||
setOf(CheckRootFingerprint)
|
||||
setOf(CheckRootFingerprint),
|
||||
) {
|
||||
override fun execute(context: BytecodeContext) {
|
||||
CheckRootFingerprint.result?.mutableMethod?.addInstruction(1, "return-void")
|
||||
|
@ -5,5 +5,5 @@ import app.revanced.patcher.fingerprint.MethodFingerprint
|
||||
internal object CheckRootFingerprint : MethodFingerprint(
|
||||
customFingerprint = { methodDef, _ ->
|
||||
methodDef.definingClass == "Lit/ipzs/cieid/BaseActivity;" && methodDef.name == "onResume"
|
||||
}
|
||||
},
|
||||
)
|
@ -1,6 +1,5 @@
|
||||
package app.revanced.patches.facebook.ads.story
|
||||
|
||||
import app.revanced.util.exception
|
||||
import app.revanced.patcher.data.BytecodeContext
|
||||
import app.revanced.patcher.extensions.InstructionExtensions.replaceInstruction
|
||||
import app.revanced.patcher.patch.BytecodePatch
|
||||
@ -8,15 +7,16 @@ import app.revanced.patcher.patch.annotation.CompatiblePackage
|
||||
import app.revanced.patcher.patch.annotation.Patch
|
||||
import app.revanced.patches.facebook.ads.story.fingerprints.AdsInsertionFingerprint
|
||||
import app.revanced.patches.facebook.ads.story.fingerprints.FetchMoreAdsFingerprint
|
||||
import app.revanced.util.exception
|
||||
|
||||
@Patch(
|
||||
name = "Hide story ads",
|
||||
description = "Hides the ads in the Facebook app stories.",
|
||||
compatiblePackages = [CompatiblePackage("com.facebook.katana")]
|
||||
compatiblePackages = [CompatiblePackage("com.facebook.katana")],
|
||||
)
|
||||
@Suppress("unused")
|
||||
object HideStoryAdsPatch : BytecodePatch(
|
||||
setOf(FetchMoreAdsFingerprint, AdsInsertionFingerprint)
|
||||
setOf(FetchMoreAdsFingerprint, AdsInsertionFingerprint),
|
||||
) {
|
||||
override fun execute(context: BytecodeContext) =
|
||||
setOf(FetchMoreAdsFingerprint, AdsInsertionFingerprint).forEach { fingerprint ->
|
||||
|
@ -11,5 +11,5 @@ internal abstract class FieldMethodFingerprint(fieldValue: String) : MethodFinge
|
||||
if (field.name != "__redex_internal_original_name") return@any false
|
||||
(field.initialValue as? StringEncodedValue)?.value == fieldValue
|
||||
}
|
||||
}
|
||||
},
|
||||
)
|
||||
|
@ -1,6 +1,5 @@
|
||||
package app.revanced.patches.finanzonline.detection.bootloader
|
||||
|
||||
import app.revanced.util.exception
|
||||
import app.revanced.patcher.data.BytecodeContext
|
||||
import app.revanced.patcher.extensions.InstructionExtensions.addInstructions
|
||||
import app.revanced.patcher.patch.BytecodePatch
|
||||
@ -8,16 +7,16 @@ import app.revanced.patcher.patch.annotation.CompatiblePackage
|
||||
import app.revanced.patcher.patch.annotation.Patch
|
||||
import app.revanced.patches.finanzonline.detection.bootloader.fingerprints.BootStateFingerprint
|
||||
import app.revanced.patches.finanzonline.detection.bootloader.fingerprints.CreateKeyFingerprint
|
||||
|
||||
import app.revanced.util.exception
|
||||
|
||||
@Patch(
|
||||
name = "Remove bootloader detection",
|
||||
description = "Removes the check for an unlocked bootloader.",
|
||||
compatiblePackages = [CompatiblePackage("at.gv.bmf.bmf2go")]
|
||||
compatiblePackages = [CompatiblePackage("at.gv.bmf.bmf2go")],
|
||||
)
|
||||
@Suppress("unused")
|
||||
object BootloaderDetectionPatch : BytecodePatch(
|
||||
setOf(CreateKeyFingerprint, BootStateFingerprint)
|
||||
setOf(CreateKeyFingerprint, BootStateFingerprint),
|
||||
) {
|
||||
override fun execute(context: BytecodeContext) {
|
||||
arrayOf(CreateKeyFingerprint, BootStateFingerprint).forEach { fingerprint ->
|
||||
@ -26,7 +25,7 @@ object BootloaderDetectionPatch : BytecodePatch(
|
||||
"""
|
||||
const/4 v0, 0x1
|
||||
return v0
|
||||
"""
|
||||
""",
|
||||
) ?: throw fingerprint.exception
|
||||
}
|
||||
}
|
||||
|
@ -25,6 +25,6 @@ internal object BootStateFingerprint : MethodFingerprint(
|
||||
Opcode.IF_NE,
|
||||
Opcode.GOTO,
|
||||
Opcode.MOVE,
|
||||
Opcode.RETURN
|
||||
)
|
||||
Opcode.RETURN,
|
||||
),
|
||||
)
|
||||
|
@ -7,5 +7,5 @@ import com.android.tools.smali.dexlib2.AccessFlags
|
||||
internal object CreateKeyFingerprint : MethodFingerprint(
|
||||
"Z",
|
||||
accessFlags = AccessFlags.PUBLIC.value,
|
||||
strings = listOf("attestation", "SHA-256", "random", "EC", "AndroidKeyStore")
|
||||
strings = listOf("attestation", "SHA-256", "random", "EC", "AndroidKeyStore"),
|
||||
)
|
||||
|
@ -1,21 +1,21 @@
|
||||
package app.revanced.patches.finanzonline.detection.root
|
||||
|
||||
import app.revanced.util.exception
|
||||
import app.revanced.patcher.data.BytecodeContext
|
||||
import app.revanced.patcher.extensions.InstructionExtensions.addInstructions
|
||||
import app.revanced.patcher.patch.BytecodePatch
|
||||
import app.revanced.patcher.patch.annotation.CompatiblePackage
|
||||
import app.revanced.patcher.patch.annotation.Patch
|
||||
import app.revanced.patches.finanzonline.detection.root.fingerprints.RootDetectionFingerprint
|
||||
import app.revanced.util.exception
|
||||
|
||||
@Patch(
|
||||
name = "Remove root detection",
|
||||
description = "Removes the check for root permissions.",
|
||||
compatiblePackages = [CompatiblePackage("at.gv.bmf.bmf2go")]
|
||||
compatiblePackages = [CompatiblePackage("at.gv.bmf.bmf2go")],
|
||||
)
|
||||
@Suppress("unused")
|
||||
object RootDetectionPatch : BytecodePatch(
|
||||
setOf(RootDetectionFingerprint)
|
||||
setOf(RootDetectionFingerprint),
|
||||
) {
|
||||
override fun execute(context: BytecodeContext) {
|
||||
RootDetectionFingerprint.result?.mutableMethod?.addInstructions(
|
||||
@ -23,7 +23,7 @@ object RootDetectionPatch : BytecodePatch(
|
||||
"""
|
||||
sget-object v0, Ljava/lang/Boolean;->FALSE:Ljava/lang/Boolean;
|
||||
return-object v0
|
||||
"""
|
||||
""",
|
||||
) ?: throw RootDetectionFingerprint.exception
|
||||
}
|
||||
}
|
||||
|
@ -17,6 +17,6 @@ internal object RootDetectionFingerprint : MethodFingerprint(
|
||||
Opcode.MOVE_RESULT,
|
||||
Opcode.INVOKE_STATIC,
|
||||
Opcode.MOVE_RESULT_OBJECT,
|
||||
Opcode.RETURN_OBJECT
|
||||
)
|
||||
Opcode.RETURN_OBJECT,
|
||||
),
|
||||
)
|
||||
|
@ -1,6 +1,5 @@
|
||||
package app.revanced.patches.googlerecorder.restrictions
|
||||
|
||||
import app.revanced.util.exception
|
||||
import app.revanced.patcher.data.BytecodeContext
|
||||
import app.revanced.patcher.extensions.InstructionExtensions.addInstruction
|
||||
import app.revanced.patcher.extensions.InstructionExtensions.getInstruction
|
||||
@ -9,16 +8,17 @@ import app.revanced.patcher.patch.BytecodePatch
|
||||
import app.revanced.patcher.patch.annotation.CompatiblePackage
|
||||
import app.revanced.patcher.patch.annotation.Patch
|
||||
import app.revanced.patches.googlerecorder.restrictions.fingerprints.OnApplicationCreateFingerprint
|
||||
import app.revanced.util.exception
|
||||
import com.android.tools.smali.dexlib2.iface.instruction.OneRegisterInstruction
|
||||
|
||||
@Patch(
|
||||
name = "Remove device restrictions",
|
||||
description = "Removes restrictions from using the app on any device. Requires mounting patched app over original.",
|
||||
compatiblePackages = [CompatiblePackage("com.google.android.apps.recorder")]
|
||||
compatiblePackages = [CompatiblePackage("com.google.android.apps.recorder")],
|
||||
)
|
||||
@Suppress("unused")
|
||||
object RemoveDeviceRestrictions : BytecodePatch(
|
||||
setOf(OnApplicationCreateFingerprint)
|
||||
setOf(OnApplicationCreateFingerprint),
|
||||
) {
|
||||
override fun execute(context: BytecodeContext) {
|
||||
OnApplicationCreateFingerprint.result?.let {
|
||||
|
@ -8,5 +8,5 @@ internal object OnApplicationCreateFingerprint : MethodFingerprint(
|
||||
if (methodDef.name != "onCreate") return@custom false
|
||||
|
||||
classDef.type.endsWith("RecorderApplication;")
|
||||
}
|
||||
},
|
||||
)
|
||||
|
@ -1,26 +1,26 @@
|
||||
package app.revanced.patches.hexeditor.ad
|
||||
|
||||
import app.revanced.util.exception
|
||||
import app.revanced.patcher.data.BytecodeContext
|
||||
import app.revanced.patcher.extensions.InstructionExtensions.replaceInstructions
|
||||
import app.revanced.patcher.patch.BytecodePatch
|
||||
import app.revanced.patcher.patch.annotation.CompatiblePackage
|
||||
import app.revanced.patcher.patch.annotation.Patch
|
||||
import app.revanced.patches.hexeditor.ad.fingerprints.PrimaryAdsFingerprint
|
||||
import app.revanced.util.exception
|
||||
|
||||
@Patch(
|
||||
name = "Disable ads",
|
||||
compatiblePackages = [CompatiblePackage("com.myprog.hexedit")]
|
||||
compatiblePackages = [CompatiblePackage("com.myprog.hexedit")],
|
||||
)
|
||||
@Suppress("unused")
|
||||
object DisableAdsPatch : BytecodePatch(
|
||||
setOf(PrimaryAdsFingerprint)
|
||||
setOf(PrimaryAdsFingerprint),
|
||||
) {
|
||||
override fun execute(context: BytecodeContext) = PrimaryAdsFingerprint.result?.mutableMethod?.replaceInstructions(
|
||||
0,
|
||||
"""
|
||||
const/4 v0, 0x1
|
||||
return v0
|
||||
"""
|
||||
""",
|
||||
) ?: throw PrimaryAdsFingerprint.exception
|
||||
}
|
||||
|
@ -5,5 +5,5 @@ import app.revanced.patcher.fingerprint.MethodFingerprint
|
||||
internal object PrimaryAdsFingerprint : MethodFingerprint(
|
||||
customFingerprint = { methodDef, _ ->
|
||||
methodDef.definingClass.endsWith("PreferencesHelper;") && methodDef.name == "isAdsDisabled"
|
||||
}
|
||||
},
|
||||
)
|
@ -9,11 +9,11 @@ import app.revanced.patches.iconpackstudio.misc.pro.fingerprints.CheckProFingerp
|
||||
|
||||
@Patch(
|
||||
name = "Unlock pro",
|
||||
compatiblePackages = [CompatiblePackage("ginlemon.iconpackstudio", ["2.2 build 016"])]
|
||||
compatiblePackages = [CompatiblePackage("ginlemon.iconpackstudio", ["2.2 build 016"])],
|
||||
)
|
||||
@Suppress("unused")
|
||||
object UnlockProPatch : BytecodePatch(
|
||||
setOf(CheckProFingerprint)
|
||||
setOf(CheckProFingerprint),
|
||||
) {
|
||||
override fun execute(context: BytecodeContext) {
|
||||
val method = CheckProFingerprint.result!!.mutableMethod
|
||||
@ -22,7 +22,7 @@ object UnlockProPatch : BytecodePatch(
|
||||
"""
|
||||
const/4 v0, 0x1
|
||||
return v0
|
||||
"""
|
||||
""",
|
||||
)
|
||||
}
|
||||
}
|
||||
|
@ -4,5 +4,5 @@ import app.revanced.patcher.fingerprint.MethodFingerprint
|
||||
|
||||
internal object CheckProFingerprint : MethodFingerprint(
|
||||
"Z",
|
||||
customFingerprint = { methodDef, _ -> methodDef.definingClass.endsWith("IPSPurchaseRepository;")}
|
||||
customFingerprint = { methodDef, _ -> methodDef.definingClass.endsWith("IPSPurchaseRepository;") },
|
||||
)
|
||||
|
@ -12,15 +12,15 @@ import app.revanced.util.returnEarly
|
||||
@Patch(
|
||||
name = "Remove root detection",
|
||||
description = "Removes the check for root permissions and unlocked bootloader.",
|
||||
compatiblePackages = [CompatiblePackage("at.gv.oe.app")]
|
||||
compatiblePackages = [CompatiblePackage("at.gv.oe.app")],
|
||||
)
|
||||
@Suppress("unused")
|
||||
object RootDetectionPatch : BytecodePatch(
|
||||
setOf(AttestationSupportedCheckFingerprint, BootloaderCheckFingerprint, RootCheckFingerprint)
|
||||
setOf(AttestationSupportedCheckFingerprint, BootloaderCheckFingerprint, RootCheckFingerprint),
|
||||
) {
|
||||
override fun execute(context: BytecodeContext) = listOf(
|
||||
AttestationSupportedCheckFingerprint,
|
||||
BootloaderCheckFingerprint,
|
||||
RootCheckFingerprint
|
||||
RootCheckFingerprint,
|
||||
).returnEarly(true)
|
||||
}
|
||||
|
@ -8,6 +8,6 @@ internal object AttestationSupportedCheckFingerprint : MethodFingerprint(
|
||||
accessFlags = AccessFlags.PUBLIC.value,
|
||||
customFingerprint = { methodDef, _ ->
|
||||
methodDef.name == "attestationSupportCheck" &&
|
||||
methodDef.definingClass.endsWith("/DeviceIntegrityCheck;")
|
||||
}
|
||||
methodDef.definingClass.endsWith("/DeviceIntegrityCheck;")
|
||||
},
|
||||
)
|
||||
|
@ -8,6 +8,6 @@ internal object BootloaderCheckFingerprint : MethodFingerprint(
|
||||
accessFlags = AccessFlags.PUBLIC.value,
|
||||
customFingerprint = { methodDef, _ ->
|
||||
methodDef.name == "bootloaderCheck" &&
|
||||
methodDef.definingClass.endsWith("/DeviceIntegrityCheck;")
|
||||
}
|
||||
methodDef.definingClass.endsWith("/DeviceIntegrityCheck;")
|
||||
},
|
||||
)
|
||||
|
@ -8,6 +8,6 @@ internal object RootCheckFingerprint : MethodFingerprint(
|
||||
accessFlags = AccessFlags.PUBLIC.value,
|
||||
customFingerprint = { methodDef, _ ->
|
||||
methodDef.name == "rootCheck" &&
|
||||
methodDef.definingClass.endsWith("/DeviceIntegrityCheck;")
|
||||
}
|
||||
methodDef.definingClass.endsWith("/DeviceIntegrityCheck;")
|
||||
},
|
||||
)
|
||||
|
@ -10,24 +10,24 @@ import app.revanced.patches.idaustria.detection.signature.fingerprints.SpoofSign
|
||||
@Patch(
|
||||
name = "Spoof signature",
|
||||
description = "Spoofs the signature of the app.",
|
||||
compatiblePackages = [CompatiblePackage("at.gv.oe.app")]
|
||||
compatiblePackages = [CompatiblePackage("at.gv.oe.app")],
|
||||
)
|
||||
@Suppress("unused")
|
||||
object SpoofSignaturePatch : BytecodePatch(
|
||||
setOf(SpoofSignatureFingerprint)
|
||||
setOf(SpoofSignatureFingerprint),
|
||||
) {
|
||||
private const val EXPECTED_SIGNATURE =
|
||||
"OpenSSLRSAPublicKey{modulus=ac3e6fd6050aa7e0d6010ae58190404cd89a56935b44f6fee" +
|
||||
"067c149768320026e10b24799a1339e414605e448e3f264444a327b9ae292be2b62ad567dd1800dbed4a88f718a33dc6db6b" +
|
||||
"f5178aa41aa0efff8a3409f5ca95dbfccd92c7b4298966df806ea7a0204a00f0e745f6d9f13bdf24f3df715d7b62c1600906" +
|
||||
"15de1c8a956b9286764985a3b3c060963c435fb9481a5543aaf0671fc2dba6c5c2b17d1ef1d85137f14dc9bbdf3490288087" +
|
||||
"324cd48341cce64fabf6a9b55d1a7bf23b2fcdff451fd85bf0c7feb0a5e884d7c5c078e413149566a12a686e6efa70ae5161" +
|
||||
"a0201307692834cda336c55157fef125e67c01c1359886f94742105596b42a790404bbcda5dad6a65f115aaff5e45ef3c28b" +
|
||||
"2316ff6cef07aa49a45aa58c07bf258051b13ef449ccb37a3679afd5cfb9132f70bb9d931a937897544f90c3bcc80ed012e9" +
|
||||
"f6ba020b8cdc23f8c29ac092b88f0e370ff9434e4f0f359e614ae0868dc526fa41e4b7596533e8d10279b66e923ecd9f0b20" +
|
||||
"0def55be2c1f6f9c72c92fb45d7e0a9ac571cb38f0a9a37bb33ea06f223fde8c7a92e8c47769e386f9799776e8f110c21df2" +
|
||||
"77ef1be61b2c01ebdabddcbf53cc4b6fd9a3c445606ee77b3758162c80ad8f8137b3c6864e92db904807dcb2be9d7717dd21" +
|
||||
"bf42c121d620ddfb7914f7a95c713d9e1c1b7bdb4a03d618e40cf7e9e235c0b5687e03b7ab3,publicExponent=10001}"
|
||||
"067c149768320026e10b24799a1339e414605e448e3f264444a327b9ae292be2b62ad567dd1800dbed4a88f718a33dc6db6b" +
|
||||
"f5178aa41aa0efff8a3409f5ca95dbfccd92c7b4298966df806ea7a0204a00f0e745f6d9f13bdf24f3df715d7b62c1600906" +
|
||||
"15de1c8a956b9286764985a3b3c060963c435fb9481a5543aaf0671fc2dba6c5c2b17d1ef1d85137f14dc9bbdf3490288087" +
|
||||
"324cd48341cce64fabf6a9b55d1a7bf23b2fcdff451fd85bf0c7feb0a5e884d7c5c078e413149566a12a686e6efa70ae5161" +
|
||||
"a0201307692834cda336c55157fef125e67c01c1359886f94742105596b42a790404bbcda5dad6a65f115aaff5e45ef3c28b" +
|
||||
"2316ff6cef07aa49a45aa58c07bf258051b13ef449ccb37a3679afd5cfb9132f70bb9d931a937897544f90c3bcc80ed012e9" +
|
||||
"f6ba020b8cdc23f8c29ac092b88f0e370ff9434e4f0f359e614ae0868dc526fa41e4b7596533e8d10279b66e923ecd9f0b20" +
|
||||
"0def55be2c1f6f9c72c92fb45d7e0a9ac571cb38f0a9a37bb33ea06f223fde8c7a92e8c47769e386f9799776e8f110c21df2" +
|
||||
"77ef1be61b2c01ebdabddcbf53cc4b6fd9a3c445606ee77b3758162c80ad8f8137b3c6864e92db904807dcb2be9d7717dd21" +
|
||||
"bf42c121d620ddfb7914f7a95c713d9e1c1b7bdb4a03d618e40cf7e9e235c0b5687e03b7ab3,publicExponent=10001}"
|
||||
|
||||
override fun execute(context: BytecodeContext) {
|
||||
SpoofSignatureFingerprint.result!!.mutableMethod.addInstructions(
|
||||
@ -35,7 +35,7 @@ object SpoofSignaturePatch : BytecodePatch(
|
||||
"""
|
||||
const-string v0, "$EXPECTED_SIGNATURE"
|
||||
return-object v0
|
||||
"""
|
||||
""",
|
||||
)
|
||||
}
|
||||
}
|
||||
|
@ -9,5 +9,5 @@ internal object SpoofSignatureFingerprint : MethodFingerprint(
|
||||
accessFlags = AccessFlags.PRIVATE.value,
|
||||
customFingerprint = { methodDef, _ ->
|
||||
methodDef.definingClass.endsWith("/SL2Step1Task;") && methodDef.name == "getPubKey"
|
||||
}
|
||||
},
|
||||
)
|
||||
|
@ -1,20 +1,20 @@
|
||||
package app.revanced.patches.inshorts.ad
|
||||
|
||||
import app.revanced.util.exception
|
||||
import app.revanced.patcher.data.BytecodeContext
|
||||
import app.revanced.patcher.extensions.InstructionExtensions.addInstruction
|
||||
import app.revanced.patcher.patch.BytecodePatch
|
||||
import app.revanced.patcher.patch.annotation.CompatiblePackage
|
||||
import app.revanced.patcher.patch.annotation.Patch
|
||||
import app.revanced.patches.inshorts.ad.fingerprints.InshortsAdsFingerprint
|
||||
import app.revanced.util.exception
|
||||
|
||||
@Patch(
|
||||
name = "Hide ads",
|
||||
compatiblePackages = [CompatiblePackage("com.nis.app")]
|
||||
compatiblePackages = [CompatiblePackage("com.nis.app")],
|
||||
)
|
||||
@Suppress("unused")
|
||||
object HideAdsPatch : BytecodePatch(
|
||||
setOf(InshortsAdsFingerprint)
|
||||
setOf(InshortsAdsFingerprint),
|
||||
) {
|
||||
override fun execute(context: BytecodeContext) {
|
||||
InshortsAdsFingerprint.result?.let { result ->
|
||||
@ -23,7 +23,7 @@ object HideAdsPatch : BytecodePatch(
|
||||
0,
|
||||
"""
|
||||
return-void
|
||||
"""
|
||||
""",
|
||||
)
|
||||
}
|
||||
} ?: throw InshortsAdsFingerprint.exception
|
@ -4,5 +4,5 @@ import app.revanced.patcher.fingerprint.MethodFingerprint
|
||||
|
||||
internal object InshortsAdsFingerprint : MethodFingerprint(
|
||||
"V",
|
||||
strings = listOf("GoogleAdLoader","exception in requestAd"),
|
||||
strings = listOf("GoogleAdLoader", "exception in requestAd"),
|
||||
)
|
@ -1,6 +1,5 @@
|
||||
package app.revanced.patches.instagram.patches.ads.timeline
|
||||
|
||||
import app.revanced.util.exception
|
||||
import app.revanced.patcher.data.BytecodeContext
|
||||
import app.revanced.patcher.extensions.InstructionExtensions.addInstructionsWithLabels
|
||||
import app.revanced.patcher.extensions.InstructionExtensions.getInstruction
|
||||
@ -15,21 +14,23 @@ import app.revanced.patches.instagram.patches.ads.timeline.fingerprints.ads.Gene
|
||||
import app.revanced.patches.instagram.patches.ads.timeline.fingerprints.ads.MediaAdFingerprint
|
||||
import app.revanced.patches.instagram.patches.ads.timeline.fingerprints.ads.PaidPartnershipAdFingerprint
|
||||
import app.revanced.patches.instagram.patches.ads.timeline.fingerprints.ads.ShoppingAdFingerprint
|
||||
import app.revanced.util.exception
|
||||
import com.android.tools.smali.dexlib2.iface.instruction.FiveRegisterInstruction
|
||||
import com.android.tools.smali.dexlib2.iface.instruction.OneRegisterInstruction
|
||||
|
||||
@Patch(
|
||||
name = "Hide timeline ads",
|
||||
description = "Removes ads from the timeline.",
|
||||
compatiblePackages = [CompatiblePackage("com.instagram.android", ["275.0.0.27.98"])]
|
||||
compatiblePackages = [CompatiblePackage("com.instagram.android", ["275.0.0.27.98"])],
|
||||
)
|
||||
@Suppress("unused")
|
||||
object HideTimelineAdsPatch : BytecodePatch(
|
||||
setOf(
|
||||
ShowAdFingerprint,
|
||||
MediaFingerprint,
|
||||
PaidPartnershipAdFingerprint // Unlike the other ads this one is resolved from all classes.
|
||||
)
|
||||
// Unlike the other ads this one is resolved from all classes.
|
||||
PaidPartnershipAdFingerprint,
|
||||
),
|
||||
) {
|
||||
override fun execute(context: BytecodeContext) {
|
||||
// region Resolve required methods to check for ads.
|
||||
@ -80,8 +81,9 @@ object HideTimelineAdsPatch : BytecodePatch(
|
||||
checkForAdInstructions,
|
||||
ExternalLabel(
|
||||
returnFalseLabel,
|
||||
mutableMethod.getInstruction(mutableMethod.implementation!!.instructions.size - 2 /* return false = ad */)
|
||||
)
|
||||
// return false = ad
|
||||
mutableMethod.getInstruction(mutableMethod.implementation!!.instructions.size - 2),
|
||||
),
|
||||
)
|
||||
|
||||
// endregion
|
||||
@ -92,7 +94,7 @@ object HideTimelineAdsPatch : BytecodePatch(
|
||||
addInstructionsWithLabels(
|
||||
jumpIndex + 1,
|
||||
"if-nez v$freeRegister, :start_check",
|
||||
ExternalLabel("start_check", getInstruction(insertIndex))
|
||||
ExternalLabel("start_check", getInstruction(insertIndex)),
|
||||
)
|
||||
}.removeInstruction(jumpIndex)
|
||||
|
||||
|
@ -3,5 +3,5 @@ package app.revanced.patches.instagram.patches.ads.timeline.fingerprints
|
||||
import app.revanced.patcher.fingerprint.MethodFingerprint
|
||||
|
||||
internal object MediaFingerprint : MethodFingerprint(
|
||||
strings = listOf("force_overlay", "Media#updateFields", "live_reels_metadata")
|
||||
strings = listOf("force_overlay", "Media#updateFields", "live_reels_metadata"),
|
||||
)
|
||||
|
@ -12,7 +12,7 @@ internal object GenericMediaAdFingerprint : MediaAdFingerprint(
|
||||
Opcode.IF_EQZ,
|
||||
Opcode.CONST_4,
|
||||
Opcode.RETURN,
|
||||
)
|
||||
),
|
||||
) {
|
||||
override fun toString() = result!!.method.toString()
|
||||
}
|
@ -12,13 +12,13 @@ internal abstract class MediaAdFingerprint(
|
||||
accessFlags: Int? = AccessFlags.PUBLIC or AccessFlags.FINAL,
|
||||
parameters: Iterable<String>? = listOf(),
|
||||
opcodes: Iterable<Opcode>?,
|
||||
customFingerprint: ((methodDef: Method, classDef: ClassDef) -> Boolean)? = null
|
||||
customFingerprint: ((methodDef: Method, classDef: ClassDef) -> Boolean)? = null,
|
||||
) : MethodFingerprint(
|
||||
returnType,
|
||||
accessFlags,
|
||||
parameters,
|
||||
opcodes,
|
||||
customFingerprint = customFingerprint
|
||||
customFingerprint = customFingerprint,
|
||||
) {
|
||||
abstract override fun toString(): String
|
||||
}
|
@ -12,11 +12,11 @@ internal object PaidPartnershipAdFingerprint : MediaAdFingerprint(
|
||||
Opcode.INVOKE_VIRTUAL,
|
||||
Opcode.MOVE_RESULT,
|
||||
Opcode.IPUT_BOOLEAN,
|
||||
Opcode.IPUT_BOOLEAN
|
||||
Opcode.IPUT_BOOLEAN,
|
||||
),
|
||||
customFingerprint = { methodDef, _ ->
|
||||
methodDef.definingClass.endsWith("ClipsEditMetadataController;")
|
||||
}
|
||||
},
|
||||
) {
|
||||
override fun toString() = result!!.let {
|
||||
val adCheckIndex = it.scanResult.patternScanResult!!.startIndex
|
||||
|
@ -15,7 +15,7 @@ internal object ShoppingAdFingerprint : MediaAdFingerprint(
|
||||
Opcode.MOVE_RESULT,
|
||||
Opcode.XOR_INT_LIT8,
|
||||
Opcode.IF_EQZ,
|
||||
)
|
||||
),
|
||||
) {
|
||||
override fun toString() = result!!.method.toString()
|
||||
}
|
@ -7,14 +7,13 @@ import app.revanced.patcher.patch.annotation.CompatiblePackage
|
||||
import app.revanced.patcher.patch.annotation.Patch
|
||||
import app.revanced.patches.irplus.ad.fingerprints.IrplusAdsFingerprint
|
||||
|
||||
|
||||
@Patch(
|
||||
name = "Remove ads",
|
||||
compatiblePackages = [CompatiblePackage("net.binarymode.android.irplus")]
|
||||
compatiblePackages = [CompatiblePackage("net.binarymode.android.irplus")],
|
||||
)
|
||||
@Suppress("unused")
|
||||
object RemoveAdsPatch : BytecodePatch(
|
||||
setOf(IrplusAdsFingerprint)
|
||||
setOf(IrplusAdsFingerprint),
|
||||
) {
|
||||
override fun execute(context: BytecodeContext) {
|
||||
val method = IrplusAdsFingerprint.result!!.mutableMethod
|
||||
|
@ -8,5 +8,5 @@ internal object IrplusAdsFingerprint : MethodFingerprint(
|
||||
"V",
|
||||
AccessFlags.PUBLIC or AccessFlags.CONSTRUCTOR,
|
||||
listOf("L", "Z"),
|
||||
strings = listOf("TAGGED")
|
||||
strings = listOf("TAGGED"),
|
||||
)
|
@ -1,20 +1,20 @@
|
||||
package app.revanced.patches.lightroom.misc.login
|
||||
|
||||
import app.revanced.util.exception
|
||||
import app.revanced.patcher.data.BytecodeContext
|
||||
import app.revanced.patcher.extensions.InstructionExtensions.replaceInstruction
|
||||
import app.revanced.patcher.patch.BytecodePatch
|
||||
import app.revanced.patcher.patch.annotation.CompatiblePackage
|
||||
import app.revanced.patcher.patch.annotation.Patch
|
||||
import app.revanced.patches.lightroom.misc.login.fingerprints.IsLoggedInFingerprint
|
||||
import app.revanced.util.exception
|
||||
|
||||
@Patch(
|
||||
name = "Disable mandatory login",
|
||||
compatiblePackages = [CompatiblePackage("com.adobe.lrmobile")]
|
||||
compatiblePackages = [CompatiblePackage("com.adobe.lrmobile")],
|
||||
)
|
||||
@Suppress("unused")
|
||||
object DisableMandatoryLoginPatch : BytecodePatch(
|
||||
setOf(IsLoggedInFingerprint)
|
||||
setOf(IsLoggedInFingerprint),
|
||||
) {
|
||||
override fun execute(context: BytecodeContext) {
|
||||
IsLoggedInFingerprint.result?.mutableMethod?.apply {
|
||||
|
@ -14,6 +14,6 @@ internal object IsLoggedInFingerprint : MethodFingerprint(
|
||||
Opcode.SGET_OBJECT,
|
||||
Opcode.IF_NE,
|
||||
Opcode.CONST_4,
|
||||
Opcode.GOTO
|
||||
)
|
||||
Opcode.GOTO,
|
||||
),
|
||||
)
|
||||
|
@ -1,23 +1,23 @@
|
||||
package app.revanced.patches.lightroom.misc.premium
|
||||
|
||||
import app.revanced.util.exception
|
||||
import app.revanced.patcher.data.BytecodeContext
|
||||
import app.revanced.patcher.extensions.InstructionExtensions.replaceInstruction
|
||||
import app.revanced.patcher.patch.BytecodePatch
|
||||
import app.revanced.patcher.patch.annotation.CompatiblePackage
|
||||
import app.revanced.patcher.patch.annotation.Patch
|
||||
import app.revanced.patches.lightroom.misc.premium.fingerprints.HasPurchasedFingerprint
|
||||
import app.revanced.util.exception
|
||||
|
||||
@Patch(
|
||||
name = "Unlock premium",
|
||||
compatiblePackages = [CompatiblePackage("com.adobe.lrmobile")]
|
||||
compatiblePackages = [CompatiblePackage("com.adobe.lrmobile")],
|
||||
)
|
||||
@Suppress("unused")
|
||||
object UnlockPremiumPatch : BytecodePatch(
|
||||
setOf(HasPurchasedFingerprint)
|
||||
){
|
||||
setOf(HasPurchasedFingerprint),
|
||||
) {
|
||||
override fun execute(context: BytecodeContext) {
|
||||
// Set hasPremium = true.
|
||||
// Set hasPremium = true.
|
||||
HasPurchasedFingerprint.result?.mutableMethod?.replaceInstruction(2, "const/4 v2, 0x1")
|
||||
?: throw HasPurchasedFingerprint.exception
|
||||
}
|
||||
|
@ -14,5 +14,5 @@ internal object HasPurchasedFingerprint : MethodFingerprint(
|
||||
Opcode.CONST_4,
|
||||
Opcode.CONST_4,
|
||||
Opcode.CONST_4,
|
||||
)
|
||||
),
|
||||
)
|
||||
|
@ -1,15 +1,15 @@
|
||||
package app.revanced.patches.memegenerator.detection.license
|
||||
|
||||
import app.revanced.util.exception
|
||||
import app.revanced.patcher.data.BytecodeContext
|
||||
import app.revanced.patcher.extensions.InstructionExtensions.replaceInstructions
|
||||
import app.revanced.patcher.patch.BytecodePatch
|
||||
import app.revanced.patcher.patch.annotation.Patch
|
||||
import app.revanced.patches.memegenerator.detection.license.fingerprints.LicenseValidationFingerprint
|
||||
import app.revanced.util.exception
|
||||
|
||||
@Patch(description = "Disables Firebase license validation.")
|
||||
object LicenseValidationPatch : BytecodePatch(
|
||||
setOf(LicenseValidationFingerprint)
|
||||
setOf(LicenseValidationFingerprint),
|
||||
) {
|
||||
override fun execute(context: BytecodeContext) {
|
||||
LicenseValidationFingerprint.result?.apply {
|
||||
@ -18,7 +18,7 @@ object LicenseValidationPatch : BytecodePatch(
|
||||
"""
|
||||
const/4 p0, 0x1
|
||||
return p0
|
||||
"""
|
||||
""",
|
||||
)
|
||||
} ?: throw LicenseValidationFingerprint.exception
|
||||
}
|
||||
|
@ -19,6 +19,6 @@ internal object LicenseValidationFingerprint : MethodFingerprint(
|
||||
Opcode.CONST_4,
|
||||
Opcode.RETURN,
|
||||
Opcode.CONST_4,
|
||||
Opcode.RETURN
|
||||
)
|
||||
Opcode.RETURN,
|
||||
),
|
||||
)
|
||||
|
@ -1,15 +1,15 @@
|
||||
package app.revanced.patches.memegenerator.detection.signature
|
||||
|
||||
import app.revanced.util.exception
|
||||
import app.revanced.patcher.data.BytecodeContext
|
||||
import app.revanced.patcher.extensions.InstructionExtensions.replaceInstructions
|
||||
import app.revanced.patcher.patch.BytecodePatch
|
||||
import app.revanced.patcher.patch.annotation.Patch
|
||||
import app.revanced.patches.memegenerator.detection.signature.fingerprints.VerifySignatureFingerprint
|
||||
import app.revanced.util.exception
|
||||
|
||||
@Patch(description = "Disables detection of incorrect signature.")
|
||||
object SignatureVerificationPatch : BytecodePatch(
|
||||
setOf(VerifySignatureFingerprint)
|
||||
setOf(VerifySignatureFingerprint),
|
||||
) {
|
||||
override fun execute(context: BytecodeContext) {
|
||||
VerifySignatureFingerprint.result?.apply {
|
||||
@ -18,7 +18,7 @@ object SignatureVerificationPatch : BytecodePatch(
|
||||
"""
|
||||
const/4 p0, 0x1
|
||||
return p0
|
||||
"""
|
||||
""",
|
||||
)
|
||||
} ?: throw VerifySignatureFingerprint.exception
|
||||
}
|
||||
|
@ -1,8 +1,8 @@
|
||||
package app.revanced.patches.memegenerator.detection.signature.fingerprints
|
||||
|
||||
import app.revanced.patcher.extensions.or
|
||||
import app.revanced.patcher.fingerprint.annotation.FuzzyPatternScanMethod
|
||||
import app.revanced.patcher.fingerprint.MethodFingerprint
|
||||
import app.revanced.patcher.fingerprint.annotation.FuzzyPatternScanMethod
|
||||
import com.android.tools.smali.dexlib2.AccessFlags
|
||||
import com.android.tools.smali.dexlib2.Opcode
|
||||
|
||||
@ -30,6 +30,6 @@ internal object VerifySignatureFingerprint : MethodFingerprint(
|
||||
Opcode.IF_EQZ,
|
||||
Opcode.CONST_4,
|
||||
Opcode.RETURN,
|
||||
Opcode.ADD_INT_LIT8
|
||||
Opcode.ADD_INT_LIT8,
|
||||
),
|
||||
)
|
@ -1,6 +1,5 @@
|
||||
package app.revanced.patches.memegenerator.misc.pro
|
||||
|
||||
import app.revanced.util.exception
|
||||
import app.revanced.patcher.data.BytecodeContext
|
||||
import app.revanced.patcher.extensions.InstructionExtensions.replaceInstructions
|
||||
import app.revanced.patcher.patch.BytecodePatch
|
||||
@ -9,35 +8,38 @@ import app.revanced.patcher.patch.annotation.Patch
|
||||
import app.revanced.patches.memegenerator.detection.license.LicenseValidationPatch
|
||||
import app.revanced.patches.memegenerator.detection.signature.SignatureVerificationPatch
|
||||
import app.revanced.patches.memegenerator.misc.pro.fingerprints.IsFreeVersionFingerprint
|
||||
import app.revanced.util.exception
|
||||
|
||||
@Patch(
|
||||
name = "Unlock pro",
|
||||
dependencies = [
|
||||
SignatureVerificationPatch::class,
|
||||
LicenseValidationPatch::class
|
||||
LicenseValidationPatch::class,
|
||||
],
|
||||
compatiblePackages = [
|
||||
CompatiblePackage(
|
||||
"com.zombodroid.MemeGenerator", [
|
||||
"com.zombodroid.MemeGenerator",
|
||||
[
|
||||
"4.6364",
|
||||
"4.6370",
|
||||
"4.6375",
|
||||
"4.6377"
|
||||
]
|
||||
)
|
||||
]
|
||||
"4.6377",
|
||||
],
|
||||
),
|
||||
],
|
||||
)
|
||||
@Suppress("unused")
|
||||
object UnlockProVersionPatch : BytecodePatch(
|
||||
setOf(IsFreeVersionFingerprint)
|
||||
setOf(IsFreeVersionFingerprint),
|
||||
) {
|
||||
override fun execute(context: BytecodeContext) {
|
||||
IsFreeVersionFingerprint.result?.apply {
|
||||
mutableMethod.replaceInstructions(0,
|
||||
mutableMethod.replaceInstructions(
|
||||
0,
|
||||
"""
|
||||
sget-object p0, Ljava/lang/Boolean;->FALSE:Ljava/lang/Boolean;
|
||||
return-object p0
|
||||
"""
|
||||
""",
|
||||
)
|
||||
} ?: throw IsFreeVersionFingerprint.exception
|
||||
}
|
||||
|
@ -17,6 +17,6 @@ internal object IsFreeVersionFingerprint : MethodFingerprint(
|
||||
Opcode.CONST_STRING,
|
||||
Opcode.INVOKE_VIRTUAL,
|
||||
Opcode.MOVE_RESULT,
|
||||
Opcode.IF_EQZ
|
||||
)
|
||||
Opcode.IF_EQZ,
|
||||
),
|
||||
)
|
||||
|
@ -8,11 +8,10 @@ internal object LoadInboxAdsFingerprint : MethodFingerprint(
|
||||
returnType = "V",
|
||||
strings = listOf(
|
||||
"ads_load_begin",
|
||||
"inbox_ads_fetch_start"
|
||||
"inbox_ads_fetch_start",
|
||||
),
|
||||
accessFlags = AccessFlags.PUBLIC or AccessFlags.STATIC,
|
||||
customFingerprint = { methodDef, _ ->
|
||||
methodDef.definingClass == "Lcom/facebook/messaging/business/inboxads/plugins/inboxads/itemsupplier/InboxAdsItemSupplierImplementation;"
|
||||
}
|
||||
},
|
||||
)
|
||||
|
||||
|
@ -1,21 +1,21 @@
|
||||
package app.revanced.patches.messenger.ads.inbox.patch
|
||||
|
||||
import app.revanced.util.exception
|
||||
import app.revanced.patcher.data.BytecodeContext
|
||||
import app.revanced.patcher.extensions.InstructionExtensions.replaceInstruction
|
||||
import app.revanced.patcher.patch.BytecodePatch
|
||||
import app.revanced.patcher.patch.annotation.CompatiblePackage
|
||||
import app.revanced.patcher.patch.annotation.Patch
|
||||
import app.revanced.patches.messenger.ads.inbox.fingerprints.LoadInboxAdsFingerprint
|
||||
import app.revanced.util.exception
|
||||
|
||||
@Patch(
|
||||
name = "Hide inbox ads",
|
||||
description = "Hides ads in inbox.",
|
||||
compatiblePackages = [CompatiblePackage("com.facebook.orca")]
|
||||
compatiblePackages = [CompatiblePackage("com.facebook.orca")],
|
||||
)
|
||||
@Suppress("unused")
|
||||
object HideInboxAdsPatch : BytecodePatch(
|
||||
setOf(LoadInboxAdsFingerprint)
|
||||
setOf(LoadInboxAdsFingerprint),
|
||||
) {
|
||||
override fun execute(context: BytecodeContext) {
|
||||
LoadInboxAdsFingerprint.result?.mutableMethod?.apply {
|
||||
@ -23,4 +23,3 @@ object HideInboxAdsPatch : BytecodePatch(
|
||||
} ?: throw LoadInboxAdsFingerprint.exception
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -8,8 +8,8 @@ internal object SendTypingIndicatorFingerprint : MethodFingerprint(
|
||||
parameters = listOf(),
|
||||
customFingerprint = { methodDef, classDef ->
|
||||
methodDef.name == "run" && classDef.fields.any {
|
||||
it.name == "__redex_internal_original_name"
|
||||
&& (it.initialValue as? DexBackedStringEncodedValue)?.value == "ConversationTypingContext\$sendActiveStateRunnable\$1"
|
||||
it.name == "__redex_internal_original_name" &&
|
||||
(it.initialValue as? DexBackedStringEncodedValue)?.value == "ConversationTypingContext\$sendActiveStateRunnable\$1"
|
||||
}
|
||||
}
|
||||
},
|
||||
)
|
||||
|
@ -13,6 +13,6 @@ internal object SwitchMessangeInputEmojiButtonFingerprint : MethodFingerprint(
|
||||
Opcode.CONST_STRING,
|
||||
Opcode.GOTO,
|
||||
Opcode.CONST_STRING,
|
||||
Opcode.GOTO
|
||||
)
|
||||
Opcode.GOTO,
|
||||
),
|
||||
)
|
@ -1,6 +1,5 @@
|
||||
package app.revanced.patches.messenger.inputfield.patch
|
||||
|
||||
import app.revanced.util.exception
|
||||
import app.revanced.patcher.data.BytecodeContext
|
||||
import app.revanced.patcher.extensions.InstructionExtensions.getInstruction
|
||||
import app.revanced.patcher.extensions.InstructionExtensions.replaceInstruction
|
||||
@ -8,16 +7,17 @@ import app.revanced.patcher.patch.BytecodePatch
|
||||
import app.revanced.patcher.patch.annotation.CompatiblePackage
|
||||
import app.revanced.patcher.patch.annotation.Patch
|
||||
import app.revanced.patches.messenger.inputfield.fingerprints.SwitchMessangeInputEmojiButtonFingerprint
|
||||
import app.revanced.util.exception
|
||||
import com.android.tools.smali.dexlib2.iface.instruction.OneRegisterInstruction
|
||||
|
||||
@Patch(
|
||||
name = "Disable switching emoji to sticker",
|
||||
description = "Disables switching from emoji to sticker search mode in message input field.",
|
||||
compatiblePackages = [CompatiblePackage("com.facebook.orca")]
|
||||
compatiblePackages = [CompatiblePackage("com.facebook.orca")],
|
||||
)
|
||||
@Suppress("unused")
|
||||
object DisableSwitchingEmojiToStickerPatch : BytecodePatch(
|
||||
setOf(SwitchMessangeInputEmojiButtonFingerprint)
|
||||
setOf(SwitchMessangeInputEmojiButtonFingerprint),
|
||||
) {
|
||||
override fun execute(context: BytecodeContext) {
|
||||
SwitchMessangeInputEmojiButtonFingerprint.result?.let {
|
||||
@ -28,7 +28,7 @@ object DisableSwitchingEmojiToStickerPatch : BytecodePatch(
|
||||
|
||||
replaceInstruction(
|
||||
setStringIndex,
|
||||
"const-string v$targetRegister, \"expression\""
|
||||
"const-string v$targetRegister, \"expression\"",
|
||||
)
|
||||
}
|
||||
} ?: throw SwitchMessangeInputEmojiButtonFingerprint.exception
|
||||
|
@ -1,22 +1,22 @@
|
||||
package app.revanced.patches.messenger.inputfield.patch
|
||||
|
||||
import app.revanced.util.exception
|
||||
import app.revanced.patcher.data.BytecodeContext
|
||||
import app.revanced.patcher.extensions.InstructionExtensions.replaceInstruction
|
||||
import app.revanced.patcher.patch.BytecodePatch
|
||||
import app.revanced.patcher.patch.annotation.CompatiblePackage
|
||||
import app.revanced.patcher.patch.annotation.Patch
|
||||
import app.revanced.patches.messenger.inputfield.fingerprints.SendTypingIndicatorFingerprint
|
||||
import app.revanced.util.exception
|
||||
|
||||
@Patch(
|
||||
name = "Disable typing indicator",
|
||||
description = "Disables the indicator while typing a message.",
|
||||
compatiblePackages = [CompatiblePackage("com.facebook.orca")]
|
||||
compatiblePackages = [CompatiblePackage("com.facebook.orca")],
|
||||
)
|
||||
@Suppress("unused")
|
||||
object DisableTypingIndicatorPatch : BytecodePatch(
|
||||
setOf(SendTypingIndicatorFingerprint)
|
||||
){
|
||||
setOf(SendTypingIndicatorFingerprint),
|
||||
) {
|
||||
override fun execute(context: BytecodeContext) {
|
||||
SendTypingIndicatorFingerprint.result?.mutableMethod?.replaceInstruction(0, "return-void")
|
||||
?: throw SendTypingIndicatorFingerprint.exception
|
||||
|
@ -9,19 +9,19 @@ import app.revanced.patches.moneymanager.fingerprints.UnlockProFingerprint
|
||||
|
||||
@Patch(
|
||||
name = "Unlock pro",
|
||||
compatiblePackages = [CompatiblePackage("com.ithebk.expensemanager")]
|
||||
compatiblePackages = [CompatiblePackage("com.ithebk.expensemanager")],
|
||||
)
|
||||
@Suppress("unused")
|
||||
object UnlockProPatch : BytecodePatch(
|
||||
setOf(UnlockProFingerprint)
|
||||
){
|
||||
setOf(UnlockProFingerprint),
|
||||
) {
|
||||
override fun execute(context: BytecodeContext) {
|
||||
UnlockProFingerprint.result!!.mutableMethod.addInstructions(
|
||||
UnlockProFingerprint.result!!.mutableMethod.addInstructions(
|
||||
0,
|
||||
"""
|
||||
const/4 v0, 0x1
|
||||
return v0
|
||||
"""
|
||||
""",
|
||||
)
|
||||
}
|
||||
}
|
@ -11,9 +11,9 @@ internal object UnlockProFingerprint : MethodFingerprint(
|
||||
parameters = listOf("L"),
|
||||
opcodes = listOf(
|
||||
Opcode.IGET_BOOLEAN,
|
||||
Opcode.RETURN
|
||||
Opcode.RETURN,
|
||||
),
|
||||
customFingerprint = { methodDef, _ ->
|
||||
methodDef.definingClass.endsWith("MainActivity;")
|
||||
}
|
||||
},
|
||||
)
|
@ -11,11 +11,11 @@ import app.revanced.patches.music.ad.video.fingerprints.ShowMusicVideoAdsFingerp
|
||||
@Patch(
|
||||
name = "Music video ads",
|
||||
description = "Removes ads in the music player.",
|
||||
compatiblePackages = [CompatiblePackage("com.google.android.apps.youtube.music")]
|
||||
compatiblePackages = [CompatiblePackage("com.google.android.apps.youtube.music")],
|
||||
)
|
||||
@Suppress("unused")
|
||||
object MusicVideoAdsPatch : BytecodePatch(
|
||||
setOf(ShowMusicVideoAdsConstructorFingerprint)
|
||||
setOf(ShowMusicVideoAdsConstructorFingerprint),
|
||||
) {
|
||||
override fun execute(context: BytecodeContext) {
|
||||
ShowMusicVideoAdsFingerprint.resolve(context, ShowMusicVideoAdsConstructorFingerprint.result!!.classDef)
|
||||
@ -26,7 +26,7 @@ object MusicVideoAdsPatch : BytecodePatch(
|
||||
result.scanResult.patternScanResult!!.startIndex,
|
||||
"""
|
||||
const/4 p1, 0x0
|
||||
"""
|
||||
""",
|
||||
)
|
||||
}
|
||||
}
|
||||
|
@ -1,13 +1,16 @@
|
||||
package app.revanced.patches.music.ad.video.fingerprints
|
||||
import app.revanced.patcher.extensions.or
|
||||
import app.revanced.patcher.fingerprint.annotation.FuzzyPatternScanMethod
|
||||
import app.revanced.patcher.fingerprint.MethodFingerprint
|
||||
import app.revanced.patcher.fingerprint.annotation.FuzzyPatternScanMethod
|
||||
import com.android.tools.smali.dexlib2.AccessFlags
|
||||
import com.android.tools.smali.dexlib2.Opcode
|
||||
|
||||
@FuzzyPatternScanMethod(2) // FIXME: Test this threshold and find the best value.
|
||||
internal object ShowMusicVideoAdsConstructorFingerprint : MethodFingerprint(
|
||||
"V", AccessFlags.PUBLIC or AccessFlags.CONSTRUCTOR, listOf("L", "L", "L"), listOf(
|
||||
"V",
|
||||
AccessFlags.PUBLIC or AccessFlags.CONSTRUCTOR,
|
||||
listOf("L", "L", "L"),
|
||||
listOf(
|
||||
Opcode.INVOKE_DIRECT,
|
||||
Opcode.NEW_INSTANCE,
|
||||
Opcode.INVOKE_DIRECT,
|
||||
@ -22,6 +25,6 @@ internal object ShowMusicVideoAdsConstructorFingerprint : MethodFingerprint(
|
||||
Opcode.IPUT_OBJECT,
|
||||
Opcode.CONST_4,
|
||||
Opcode.IPUT_BOOLEAN,
|
||||
Opcode.RETURN_VOID
|
||||
)
|
||||
Opcode.RETURN_VOID,
|
||||
),
|
||||
)
|
||||
|
@ -6,9 +6,12 @@ import com.android.tools.smali.dexlib2.AccessFlags
|
||||
import com.android.tools.smali.dexlib2.Opcode
|
||||
|
||||
internal object ShowMusicVideoAdsFingerprint : MethodFingerprint(
|
||||
"V", AccessFlags.PUBLIC or AccessFlags.FINAL, listOf("Z"), listOf(
|
||||
"V",
|
||||
AccessFlags.PUBLIC or AccessFlags.FINAL,
|
||||
listOf("Z"),
|
||||
listOf(
|
||||
Opcode.IPUT_BOOLEAN,
|
||||
Opcode.INVOKE_VIRTUAL,
|
||||
Opcode.RETURN_VOID
|
||||
)
|
||||
Opcode.RETURN_VOID,
|
||||
),
|
||||
)
|
||||
|
@ -12,11 +12,11 @@ import com.android.tools.smali.dexlib2.Opcode
|
||||
@Patch(
|
||||
name = "Codecs unlock",
|
||||
description = "Adds more audio codec options. The new audio codecs usually result in better audio quality.",
|
||||
compatiblePackages = [CompatiblePackage("com.google.android.apps.youtube.music")]
|
||||
compatiblePackages = [CompatiblePackage("com.google.android.apps.youtube.music")],
|
||||
)
|
||||
@Suppress("unused")
|
||||
object CodecsUnlockPatch : BytecodePatch(
|
||||
setOf(CodecsLockFingerprint, AllCodecsReferenceFingerprint)
|
||||
setOf(CodecsLockFingerprint, AllCodecsReferenceFingerprint),
|
||||
) {
|
||||
override fun execute(context: BytecodeContext) {
|
||||
val codecsLockResult = CodecsLockFingerprint.result!!
|
||||
@ -25,13 +25,13 @@ object CodecsUnlockPatch : BytecodePatch(
|
||||
|
||||
val scanResultStartIndex = codecsLockResult.scanResult.patternScanResult!!.startIndex
|
||||
val instructionIndex = scanResultStartIndex +
|
||||
if (implementation.instructions[scanResultStartIndex - 1].opcode == Opcode.CHECK_CAST) {
|
||||
// for 5.16.xx and lower
|
||||
-3
|
||||
} else {
|
||||
// since 5.17.xx
|
||||
-2
|
||||
}
|
||||
if (implementation.instructions[scanResultStartIndex - 1].opcode == Opcode.CHECK_CAST) {
|
||||
// for 5.16.xx and lower
|
||||
-3
|
||||
} else {
|
||||
// since 5.17.xx
|
||||
-2
|
||||
}
|
||||
|
||||
val allCodecsResult = AllCodecsReferenceFingerprint.result!!
|
||||
val allCodecsMethod =
|
||||
@ -41,7 +41,7 @@ object CodecsUnlockPatch : BytecodePatch(
|
||||
|
||||
implementation.replaceInstruction(
|
||||
instructionIndex,
|
||||
"invoke-static {}, ${allCodecsMethod.definingClass}->${allCodecsMethod.name}()Ljava/util/Set;".toInstruction()
|
||||
"invoke-static {}, ${allCodecsMethod.definingClass}->${allCodecsMethod.name}()Ljava/util/Set;".toInstruction(),
|
||||
)
|
||||
}
|
||||
}
|
||||
|
@ -1,15 +1,17 @@
|
||||
package app.revanced.patches.music.audio.codecs.fingerprints
|
||||
|
||||
import app.revanced.patcher.extensions.or
|
||||
import app.revanced.patcher.fingerprint.annotation.FuzzyPatternScanMethod
|
||||
import app.revanced.patcher.fingerprint.MethodFingerprint
|
||||
import app.revanced.patcher.fingerprint.annotation.FuzzyPatternScanMethod
|
||||
import com.android.tools.smali.dexlib2.AccessFlags
|
||||
import com.android.tools.smali.dexlib2.Opcode
|
||||
|
||||
|
||||
@FuzzyPatternScanMethod(2) // FIXME: Test this threshold and find the best value.
|
||||
internal object AllCodecsReferenceFingerprint : MethodFingerprint(
|
||||
"J", AccessFlags.PUBLIC or AccessFlags.FINAL, listOf("L"), listOf(
|
||||
"J",
|
||||
AccessFlags.PUBLIC or AccessFlags.FINAL,
|
||||
listOf("L"),
|
||||
listOf(
|
||||
Opcode.INVOKE_STATIC,
|
||||
Opcode.MOVE_RESULT_OBJECT,
|
||||
Opcode.INVOKE_STATIC,
|
||||
@ -47,6 +49,7 @@ internal object AllCodecsReferenceFingerprint : MethodFingerprint(
|
||||
Opcode.MOVE_EXCEPTION,
|
||||
Opcode.INVOKE_SUPER,
|
||||
Opcode.MOVE_RESULT_WIDE,
|
||||
Opcode.RETURN_WIDE
|
||||
), listOf("itag")
|
||||
Opcode.RETURN_WIDE,
|
||||
),
|
||||
listOf("itag"),
|
||||
)
|
@ -1,15 +1,16 @@
|
||||
package app.revanced.patches.music.audio.codecs.fingerprints
|
||||
|
||||
import app.revanced.patcher.extensions.or
|
||||
import app.revanced.patcher.fingerprint.annotation.FuzzyPatternScanMethod
|
||||
import app.revanced.patcher.fingerprint.MethodFingerprint
|
||||
import app.revanced.patcher.fingerprint.annotation.FuzzyPatternScanMethod
|
||||
import com.android.tools.smali.dexlib2.AccessFlags
|
||||
import com.android.tools.smali.dexlib2.Opcode
|
||||
|
||||
|
||||
@FuzzyPatternScanMethod(2) // FIXME: Test this threshold and find the best value.
|
||||
internal object CodecsLockFingerprint : MethodFingerprint(
|
||||
"L", AccessFlags.PUBLIC or AccessFlags.STATIC, opcodes = listOf(
|
||||
"L",
|
||||
AccessFlags.PUBLIC or AccessFlags.STATIC,
|
||||
opcodes = listOf(
|
||||
Opcode.INVOKE_DIRECT,
|
||||
Opcode.INVOKE_VIRTUAL,
|
||||
Opcode.MOVE_RESULT,
|
||||
@ -23,7 +24,7 @@ internal object CodecsLockFingerprint : MethodFingerprint(
|
||||
Opcode.MOVE_RESULT_OBJECT,
|
||||
Opcode.INVOKE_INTERFACE,
|
||||
Opcode.INVOKE_VIRTUAL,
|
||||
Opcode.RETURN_OBJECT
|
||||
Opcode.RETURN_OBJECT,
|
||||
),
|
||||
strings = listOf("eac3_supported")
|
||||
strings = listOf("eac3_supported"),
|
||||
)
|
||||
|
@ -1,30 +1,30 @@
|
||||
package app.revanced.patches.music.audio.exclusiveaudio
|
||||
|
||||
import app.revanced.util.exception
|
||||
import app.revanced.patcher.data.BytecodeContext
|
||||
import app.revanced.patcher.extensions.InstructionExtensions.addInstructions
|
||||
import app.revanced.patcher.patch.BytecodePatch
|
||||
import app.revanced.patcher.patch.annotation.CompatiblePackage
|
||||
import app.revanced.patcher.patch.annotation.Patch
|
||||
import app.revanced.patches.music.audio.exclusiveaudio.fingerprints.AllowExclusiveAudioPlaybackFingerprint
|
||||
import app.revanced.util.exception
|
||||
|
||||
@Patch(
|
||||
name = "Exclusive audio playback",
|
||||
description = "Enables the option to play audio without video.",
|
||||
compatiblePackages = [CompatiblePackage("com.google.android.apps.youtube.music")]
|
||||
compatiblePackages = [CompatiblePackage("com.google.android.apps.youtube.music")],
|
||||
)
|
||||
@Suppress("unused")
|
||||
object ExclusiveAudioPatch : BytecodePatch(
|
||||
setOf(AllowExclusiveAudioPlaybackFingerprint)
|
||||
setOf(AllowExclusiveAudioPlaybackFingerprint),
|
||||
) {
|
||||
override fun execute(context: BytecodeContext) {
|
||||
AllowExclusiveAudioPlaybackFingerprint.result?.mutableMethod?.apply {
|
||||
addInstructions(
|
||||
0,
|
||||
"""
|
||||
"""
|
||||
const/4 v0, 0x1
|
||||
return v0
|
||||
"""
|
||||
""",
|
||||
)
|
||||
} ?: throw AllowExclusiveAudioPlaybackFingerprint.exception
|
||||
}
|
||||
|
@ -5,7 +5,7 @@ import app.revanced.patcher.fingerprint.MethodFingerprint
|
||||
import com.android.tools.smali.dexlib2.AccessFlags
|
||||
import com.android.tools.smali.dexlib2.Opcode
|
||||
|
||||
internal object AllowExclusiveAudioPlaybackFingerprint: MethodFingerprint(
|
||||
internal object AllowExclusiveAudioPlaybackFingerprint : MethodFingerprint(
|
||||
"Z",
|
||||
AccessFlags.PUBLIC or AccessFlags.FINAL,
|
||||
listOf(),
|
||||
@ -20,6 +20,6 @@ internal object AllowExclusiveAudioPlaybackFingerprint: MethodFingerprint(
|
||||
Opcode.GOTO,
|
||||
Opcode.INVOKE_VIRTUAL,
|
||||
Opcode.MOVE_RESULT,
|
||||
Opcode.RETURN
|
||||
)
|
||||
Opcode.RETURN,
|
||||
),
|
||||
)
|
@ -1,6 +1,5 @@
|
||||
package app.revanced.patches.music.interaction.permanentrepeat
|
||||
|
||||
import app.revanced.util.exception
|
||||
import app.revanced.patcher.data.BytecodeContext
|
||||
import app.revanced.patcher.extensions.InstructionExtensions.addInstructionsWithLabels
|
||||
import app.revanced.patcher.extensions.InstructionExtensions.getInstruction
|
||||
@ -9,16 +8,17 @@ import app.revanced.patcher.patch.annotation.CompatiblePackage
|
||||
import app.revanced.patcher.patch.annotation.Patch
|
||||
import app.revanced.patcher.util.smali.ExternalLabel
|
||||
import app.revanced.patches.music.interaction.permanentrepeat.fingerprints.RepeatTrackFingerprint
|
||||
import app.revanced.util.exception
|
||||
|
||||
@Patch(
|
||||
name = "Permanent repeat",
|
||||
description = "Permanently remember your repeating preference even if the playlist ends or another track is played.",
|
||||
compatiblePackages = [CompatiblePackage("com.google.android.apps.youtube.music")],
|
||||
use = false
|
||||
use = false,
|
||||
)
|
||||
@Suppress("unused")
|
||||
object PermanentRepeatPatch : BytecodePatch(
|
||||
setOf(RepeatTrackFingerprint)
|
||||
setOf(RepeatTrackFingerprint),
|
||||
) {
|
||||
override fun execute(context: BytecodeContext) {
|
||||
RepeatTrackFingerprint.result?.let {
|
||||
@ -29,7 +29,7 @@ object PermanentRepeatPatch : BytecodePatch(
|
||||
addInstructionsWithLabels(
|
||||
startIndex,
|
||||
"goto :repeat",
|
||||
ExternalLabel("repeat", getInstruction(repeatIndex))
|
||||
ExternalLabel("repeat", getInstruction(repeatIndex)),
|
||||
)
|
||||
}
|
||||
} ?: throw RepeatTrackFingerprint.exception
|
||||
|
@ -17,6 +17,6 @@ internal object RepeatTrackFingerprint : MethodFingerprint(
|
||||
Opcode.SGET_OBJECT,
|
||||
Opcode.INVOKE_VIRTUAL,
|
||||
Opcode.MOVE_RESULT,
|
||||
Opcode.IF_NEZ
|
||||
)
|
||||
Opcode.IF_NEZ,
|
||||
),
|
||||
)
|
||||
|
@ -1,23 +1,22 @@
|
||||
package app.revanced.patches.music.interaction.permanentshuffle
|
||||
|
||||
import app.revanced.util.exception
|
||||
import app.revanced.patcher.data.BytecodeContext
|
||||
import app.revanced.patcher.extensions.InstructionExtensions.addInstruction
|
||||
import app.revanced.patcher.patch.BytecodePatch
|
||||
import app.revanced.patcher.patch.annotation.CompatiblePackage
|
||||
import app.revanced.patcher.patch.annotation.Patch
|
||||
import app.revanced.patches.music.interaction.permanentshuffle.fingerprints.DisableShuffleFingerprint
|
||||
|
||||
import app.revanced.util.exception
|
||||
|
||||
@Patch(
|
||||
name = "Permanent shuffle",
|
||||
description = "Permanently remember your shuffle preference " +
|
||||
"even if the playlist ends or another track is played.",
|
||||
"even if the playlist ends or another track is played.",
|
||||
compatiblePackages = [CompatiblePackage("com.google.android.apps.youtube.music")],
|
||||
use = false
|
||||
use = false,
|
||||
)
|
||||
@Suppress("unused")
|
||||
object PermanentShuffleTogglePatch : BytecodePatch(setOf(DisableShuffleFingerprint)) {
|
||||
object PermanentShufflePatch : BytecodePatch(setOf(DisableShuffleFingerprint)) {
|
||||
override fun execute(context: BytecodeContext) {
|
||||
DisableShuffleFingerprint.result?.mutableMethod?.addInstruction(0, "return-void")
|
||||
?: throw DisableShuffleFingerprint.exception
|
||||
|
@ -15,6 +15,6 @@ internal object DisableShuffleFingerprint : MethodFingerprint(
|
||||
Opcode.SGET_OBJECT,
|
||||
Opcode.IPUT_OBJECT,
|
||||
Opcode.IGET_OBJECT,
|
||||
Opcode.INVOKE_VIRTUAL
|
||||
)
|
||||
Opcode.INVOKE_VIRTUAL,
|
||||
),
|
||||
)
|
||||
|
@ -12,11 +12,11 @@ import com.android.tools.smali.dexlib2.builder.instruction.BuilderInstruction11x
|
||||
name = "Compact header",
|
||||
description = "Hides the music category bar at the top of the homepage.",
|
||||
compatiblePackages = [CompatiblePackage("com.google.android.apps.youtube.music")],
|
||||
use = false
|
||||
use = false,
|
||||
)
|
||||
@Suppress("unused")
|
||||
object CompactHeaderPatch : BytecodePatch(
|
||||
setOf(CompactHeaderConstructorFingerprint)
|
||||
setOf(CompactHeaderConstructorFingerprint),
|
||||
) {
|
||||
override fun execute(context: BytecodeContext) {
|
||||
val result = CompactHeaderConstructorFingerprint.result!!
|
||||
@ -25,10 +25,11 @@ object CompactHeaderPatch : BytecodePatch(
|
||||
val insertIndex = result.scanResult.patternScanResult!!.endIndex
|
||||
val register = (method.implementation!!.instructions[insertIndex - 1] as BuilderInstruction11x).registerA
|
||||
method.addInstructions(
|
||||
insertIndex, """
|
||||
const/16 v2, 0x8
|
||||
invoke-virtual {v${register}, v2}, Landroid/view/View;->setVisibility(I)V
|
||||
insertIndex,
|
||||
"""
|
||||
const/16 v2, 0x8
|
||||
invoke-virtual {v$register, v2}, Landroid/view/View;->setVisibility(I)V
|
||||
""",
|
||||
)
|
||||
}
|
||||
}
|
||||
|
@ -6,7 +6,10 @@ import com.android.tools.smali.dexlib2.AccessFlags
|
||||
import com.android.tools.smali.dexlib2.Opcode
|
||||
|
||||
internal object CompactHeaderConstructorFingerprint : MethodFingerprint(
|
||||
"V", AccessFlags.PUBLIC or AccessFlags.CONSTRUCTOR, listOf("L", "L", "L", "L", "L"), listOf(
|
||||
"V",
|
||||
AccessFlags.PUBLIC or AccessFlags.CONSTRUCTOR,
|
||||
listOf("L", "L", "L", "L", "L"),
|
||||
listOf(
|
||||
Opcode.INVOKE_DIRECT,
|
||||
Opcode.IPUT_OBJECT,
|
||||
Opcode.IPUT_OBJECT,
|
||||
@ -18,6 +21,6 @@ internal object CompactHeaderConstructorFingerprint : MethodFingerprint(
|
||||
Opcode.CONST_4,
|
||||
Opcode.INVOKE_STATIC,
|
||||
Opcode.MOVE_RESULT_OBJECT,
|
||||
Opcode.CHECK_CAST
|
||||
)
|
||||
Opcode.CHECK_CAST,
|
||||
),
|
||||
)
|
||||
|
@ -1,18 +1,17 @@
|
||||
package app.revanced.patches.music.layout.minimizedplayback
|
||||
|
||||
import app.revanced.util.exception
|
||||
import app.revanced.patcher.data.BytecodeContext
|
||||
import app.revanced.patcher.extensions.InstructionExtensions.addInstruction
|
||||
import app.revanced.patcher.patch.BytecodePatch
|
||||
import app.revanced.patcher.patch.annotation.CompatiblePackage
|
||||
import app.revanced.patcher.patch.annotation.Patch
|
||||
import app.revanced.patches.music.layout.minimizedplayback.fingerprints.MinimizedPlaybackManagerFingerprint
|
||||
|
||||
import app.revanced.util.exception
|
||||
|
||||
@Patch(
|
||||
name = "Minimized playback music",
|
||||
description = "Enables minimized playback on Kids music.",
|
||||
compatiblePackages = [CompatiblePackage("com.google.android.apps.youtube.music")]
|
||||
compatiblePackages = [CompatiblePackage("com.google.android.apps.youtube.music")],
|
||||
)
|
||||
@Suppress("unused")
|
||||
object MinimizedPlaybackPatch : BytecodePatch(setOf(MinimizedPlaybackManagerFingerprint)) {
|
||||
@ -21,6 +20,6 @@ object MinimizedPlaybackPatch : BytecodePatch(setOf(MinimizedPlaybackManagerFing
|
||||
0,
|
||||
"""
|
||||
return-void
|
||||
"""
|
||||
""",
|
||||
) ?: throw MinimizedPlaybackManagerFingerprint.exception
|
||||
}
|
||||
|
@ -22,5 +22,5 @@ internal object MinimizedPlaybackManagerFingerprint : MethodFingerprint(
|
||||
Opcode.CONST_4,
|
||||
Opcode.IF_NE,
|
||||
Opcode.IPUT_BOOLEAN,
|
||||
)
|
||||
),
|
||||
)
|
||||
|
@ -12,7 +12,7 @@ import app.revanced.patches.music.layout.premium.fingerprints.HideGetPremiumPare
|
||||
@Patch(
|
||||
name = "Hide get premium",
|
||||
description = "Removes all \"Get Premium\" evidences from the avatar menu.",
|
||||
compatiblePackages = [CompatiblePackage("com.google.android.apps.youtube.music")]
|
||||
compatiblePackages = [CompatiblePackage("com.google.android.apps.youtube.music")],
|
||||
)
|
||||
@Suppress("unused")
|
||||
object HideGetPremiumPatch : BytecodePatch(setOf(HideGetPremiumParentFingerprint)) {
|
||||
@ -27,7 +27,7 @@ object HideGetPremiumPatch : BytecodePatch(setOf(HideGetPremiumParentFingerprint
|
||||
startIndex,
|
||||
"""
|
||||
const/4 v1, 0x0
|
||||
"""
|
||||
""",
|
||||
)
|
||||
|
||||
val result = HideGetPremiumFingerprint.result!!
|
||||
@ -36,7 +36,7 @@ object HideGetPremiumPatch : BytecodePatch(setOf(HideGetPremiumParentFingerprint
|
||||
startIndex,
|
||||
"""
|
||||
const/16 v0, 0x8
|
||||
"""
|
||||
""",
|
||||
)
|
||||
}
|
||||
}
|
||||
|
@ -6,11 +6,14 @@ import com.android.tools.smali.dexlib2.AccessFlags
|
||||
import com.android.tools.smali.dexlib2.Opcode
|
||||
|
||||
internal object HideGetPremiumFingerprint : MethodFingerprint(
|
||||
"V", AccessFlags.PUBLIC or AccessFlags.FINAL, listOf(), listOf(
|
||||
"V",
|
||||
AccessFlags.PUBLIC or AccessFlags.FINAL,
|
||||
listOf(),
|
||||
listOf(
|
||||
Opcode.IF_NEZ,
|
||||
Opcode.CONST_16,
|
||||
Opcode.GOTO,
|
||||
Opcode.NOP,
|
||||
Opcode.INVOKE_VIRTUAL
|
||||
)
|
||||
Opcode.INVOKE_VIRTUAL,
|
||||
),
|
||||
)
|
||||
|
@ -6,14 +6,17 @@ import com.android.tools.smali.dexlib2.AccessFlags
|
||||
import com.android.tools.smali.dexlib2.Opcode
|
||||
|
||||
internal object HideGetPremiumParentFingerprint : MethodFingerprint(
|
||||
"V", AccessFlags.PUBLIC or AccessFlags.FINAL, listOf(), listOf(
|
||||
"V",
|
||||
AccessFlags.PUBLIC or AccessFlags.FINAL,
|
||||
listOf(),
|
||||
listOf(
|
||||
Opcode.IGET_BOOLEAN,
|
||||
Opcode.CONST_4,
|
||||
Opcode.IF_EQZ,
|
||||
Opcode.IGET_OBJECT,
|
||||
Opcode.INVOKE_VIRTUAL,
|
||||
Opcode.MOVE_RESULT_OBJECT,
|
||||
Opcode.INVOKE_STATIC
|
||||
Opcode.INVOKE_STATIC,
|
||||
),
|
||||
listOf("FEmusic_history"),
|
||||
)
|
||||
|
@ -12,15 +12,14 @@ import com.android.tools.smali.dexlib2.builder.instruction.BuilderInstruction22t
|
||||
import com.android.tools.smali.dexlib2.iface.instruction.formats.Instruction22c
|
||||
import com.android.tools.smali.dexlib2.iface.instruction.formats.Instruction35c
|
||||
|
||||
|
||||
@Patch(
|
||||
name = "Remove upgrade button",
|
||||
description = "Removes the upgrade tab from the pivot bar.",
|
||||
compatiblePackages = [CompatiblePackage("com.google.android.apps.youtube.music")]
|
||||
compatiblePackages = [CompatiblePackage("com.google.android.apps.youtube.music")],
|
||||
)
|
||||
@Suppress("unused")
|
||||
object RemoveUpgradeButtonPatch : BytecodePatch(
|
||||
setOf(PivotBarConstructorFingerprint)
|
||||
setOf(PivotBarConstructorFingerprint),
|
||||
) {
|
||||
override fun execute(context: BytecodeContext) {
|
||||
val result = PivotBarConstructorFingerprint.result!!
|
||||
@ -39,19 +38,20 @@ object RemoveUpgradeButtonPatch : BytecodePatch(
|
||||
iput-object v0, v$register, $pivotBarElementFieldRef
|
||||
""".toInstructions().toMutableList()
|
||||
|
||||
|
||||
val endIndex = result.scanResult.patternScanResult!!.endIndex
|
||||
|
||||
// replace the instruction to retain the label at given index
|
||||
implementation.replaceInstruction(
|
||||
endIndex - 1, instructionList[0] // invoke-interface
|
||||
endIndex - 1,
|
||||
instructionList[0], // invoke-interface
|
||||
)
|
||||
// do not forget to remove this instruction since we added it already
|
||||
instructionList.removeFirst()
|
||||
|
||||
val exitInstruction = instructionList.last() // iput-object
|
||||
implementation.addInstruction(
|
||||
endIndex, exitInstruction
|
||||
endIndex,
|
||||
exitInstruction,
|
||||
)
|
||||
// do not forget to remove this instruction since we added it already
|
||||
instructionList.removeLast()
|
||||
@ -60,12 +60,16 @@ object RemoveUpgradeButtonPatch : BytecodePatch(
|
||||
instructionList.add(
|
||||
2, // if-le
|
||||
BuilderInstruction22t(
|
||||
Opcode.IF_LE, 1, 2, implementation.newLabelForIndex(endIndex)
|
||||
)
|
||||
Opcode.IF_LE,
|
||||
1,
|
||||
2,
|
||||
implementation.newLabelForIndex(endIndex),
|
||||
),
|
||||
)
|
||||
|
||||
implementation.addInstructions(
|
||||
endIndex, instructionList
|
||||
endIndex,
|
||||
instructionList,
|
||||
)
|
||||
}
|
||||
}
|
||||
|
@ -1,12 +1,11 @@
|
||||
package app.revanced.patches.music.layout.upgradebutton.fingerprints
|
||||
|
||||
import app.revanced.patcher.extensions.or
|
||||
import app.revanced.patcher.fingerprint.annotation.FuzzyPatternScanMethod
|
||||
import app.revanced.patcher.fingerprint.MethodFingerprint
|
||||
import app.revanced.patcher.fingerprint.annotation.FuzzyPatternScanMethod
|
||||
import com.android.tools.smali.dexlib2.AccessFlags
|
||||
import com.android.tools.smali.dexlib2.Opcode
|
||||
|
||||
|
||||
@FuzzyPatternScanMethod(2) // FIXME: Test this threshold and find the best value.
|
||||
internal object PivotBarConstructorFingerprint : MethodFingerprint(
|
||||
"V",
|
||||
@ -57,6 +56,6 @@ internal object PivotBarConstructorFingerprint : MethodFingerprint(
|
||||
Opcode.GOTO,
|
||||
Opcode.NOP,
|
||||
Opcode.IPUT_OBJECT,
|
||||
Opcode.RETURN_VOID
|
||||
)
|
||||
Opcode.RETURN_VOID,
|
||||
),
|
||||
)
|
@ -1,28 +1,28 @@
|
||||
package app.revanced.patches.music.misc.androidauto
|
||||
|
||||
import app.revanced.util.exception
|
||||
import app.revanced.patcher.data.BytecodeContext
|
||||
import app.revanced.patcher.extensions.InstructionExtensions.addInstructions
|
||||
import app.revanced.patcher.patch.BytecodePatch
|
||||
import app.revanced.patcher.patch.annotation.CompatiblePackage
|
||||
import app.revanced.patcher.patch.annotation.Patch
|
||||
import app.revanced.patches.music.misc.androidauto.fingerprints.CheckCertificateFingerprint
|
||||
|
||||
import app.revanced.util.exception
|
||||
|
||||
@Patch(
|
||||
name = "Bypass certificate checks",
|
||||
description = "Bypasses certificate checks which prevent YouTube Music from working on Android Auto.",
|
||||
compatiblePackages = [CompatiblePackage("com.google.android.apps.youtube.music")]
|
||||
compatiblePackages = [CompatiblePackage("com.google.android.apps.youtube.music")],
|
||||
)
|
||||
@Suppress("unused")
|
||||
object BypassCertificateChecksPatch : BytecodePatch(setOf(CheckCertificateFingerprint)) {
|
||||
override fun execute(context: BytecodeContext) {
|
||||
CheckCertificateFingerprint.result?.apply {
|
||||
mutableMethod.addInstructions(
|
||||
0, """
|
||||
0,
|
||||
"""
|
||||
const/4 v0, 0x1
|
||||
return v0
|
||||
"""
|
||||
""",
|
||||
)
|
||||
} ?: throw CheckCertificateFingerprint.exception
|
||||
}
|
||||
|
@ -8,5 +8,5 @@ internal object CheckCertificateFingerprint : MethodFingerprint(
|
||||
accessFlags = AccessFlags.PUBLIC or AccessFlags.FINAL,
|
||||
returnType = "Z",
|
||||
parameters = listOf("Ljava/lang/String;"),
|
||||
strings = listOf("X509", "Failed to get certificate.")
|
||||
strings = listOf("X509", "Failed to get certificate."),
|
||||
)
|
@ -4,10 +4,10 @@ import app.revanced.patches.music.misc.gms.Constants.MUSIC_PACKAGE_NAME
|
||||
import app.revanced.patches.music.misc.gms.Constants.REVANCED_MUSIC_PACKAGE_NAME
|
||||
import app.revanced.patches.music.misc.gms.GmsCoreSupportResourcePatch.gmsCoreVendorOption
|
||||
import app.revanced.patches.music.misc.gms.fingerprints.*
|
||||
import app.revanced.patches.music.misc.integrations.fingerprints.ApplicationInitFingerprint
|
||||
import app.revanced.patches.music.misc.integrations.IntegrationsPatch
|
||||
import app.revanced.patches.shared.misc.gms.BaseGmsCoreSupportPatch
|
||||
import app.revanced.patches.music.misc.integrations.fingerprints.ApplicationInitFingerprint
|
||||
import app.revanced.patches.shared.fingerprints.CastContextFetchFingerprint
|
||||
import app.revanced.patches.shared.misc.gms.BaseGmsCoreSupportPatch
|
||||
|
||||
@Suppress("unused")
|
||||
object GmsCoreSupportPatch : BaseGmsCoreSupportPatch(
|
||||
@ -32,7 +32,7 @@ object GmsCoreSupportPatch : BaseGmsCoreSupportPatch(
|
||||
CastDynamiteModuleV2Fingerprint,
|
||||
CastContextFetchFingerprint,
|
||||
PrimeMethodFingerprint,
|
||||
)
|
||||
),
|
||||
) {
|
||||
override val gmsCoreVendor by gmsCoreVendorOption
|
||||
}
|
||||
|
@ -7,5 +7,5 @@ import app.revanced.patches.shared.misc.gms.BaseGmsCoreSupportResourcePatch
|
||||
object GmsCoreSupportResourcePatch : BaseGmsCoreSupportResourcePatch(
|
||||
fromPackageName = MUSIC_PACKAGE_NAME,
|
||||
toPackageName = REVANCED_MUSIC_PACKAGE_NAME,
|
||||
spoofedPackageSignature = "afb0fed5eeaebdd86f56a97742f4b6b33ef59875"
|
||||
spoofedPackageSignature = "afb0fed5eeaebdd86f56a97742f4b6b33ef59875",
|
||||
)
|
||||
|
@ -1,8 +1,7 @@
|
||||
package app.revanced.patches.music.misc.gms.fingerprints
|
||||
|
||||
|
||||
import app.revanced.patcher.fingerprint.MethodFingerprint
|
||||
|
||||
internal object CastDynamiteModuleFingerprint : MethodFingerprint(
|
||||
strings = listOf("com.google.android.gms.cast.framework.internal.CastDynamiteModuleImpl")
|
||||
strings = listOf("com.google.android.gms.cast.framework.internal.CastDynamiteModuleImpl"),
|
||||
)
|
@ -1,8 +1,7 @@
|
||||
package app.revanced.patches.music.misc.gms.fingerprints
|
||||
|
||||
|
||||
import app.revanced.patcher.fingerprint.MethodFingerprint
|
||||
|
||||
internal object CastDynamiteModuleV2Fingerprint : MethodFingerprint(
|
||||
strings = listOf("Failed to load module via V2: ")
|
||||
strings = listOf("Failed to load module via V2: "),
|
||||
)
|
@ -13,6 +13,6 @@ internal object GooglePlayUtilityFingerprint : MethodFingerprint(
|
||||
"MetadataValueReader",
|
||||
"GooglePlayServicesUtil",
|
||||
"com.android.vending",
|
||||
"android.hardware.type.embedded"
|
||||
)
|
||||
"android.hardware.type.embedded",
|
||||
),
|
||||
)
|
@ -1,8 +1,7 @@
|
||||
package app.revanced.patches.music.misc.gms.fingerprints
|
||||
|
||||
|
||||
import app.revanced.patcher.fingerprint.MethodFingerprint
|
||||
|
||||
internal object PrimeMethodFingerprint : MethodFingerprint(
|
||||
strings = listOf("com.google.android.GoogleCamera", "com.android.vending")
|
||||
strings = listOf("com.google.android.GoogleCamera", "com.android.vending"),
|
||||
)
|
@ -12,7 +12,7 @@ internal object ApplicationInitFingerprint : IntegrationsFingerprint(
|
||||
Opcode.INVOKE_STATIC,
|
||||
Opcode.NEW_INSTANCE,
|
||||
Opcode.INVOKE_DIRECT,
|
||||
Opcode.INVOKE_VIRTUAL
|
||||
Opcode.INVOKE_VIRTUAL,
|
||||
),
|
||||
strings = listOf("activity"),
|
||||
customFingerprint = { methodDef, _ -> methodDef.name == "onCreate" },
|
||||
|
@ -1,26 +1,26 @@
|
||||
package app.revanced.patches.music.premium.backgroundplay
|
||||
|
||||
import app.revanced.util.exception
|
||||
import app.revanced.patcher.data.BytecodeContext
|
||||
import app.revanced.patcher.extensions.InstructionExtensions.addInstructions
|
||||
import app.revanced.patcher.patch.BytecodePatch
|
||||
import app.revanced.patcher.patch.annotation.CompatiblePackage
|
||||
import app.revanced.patcher.patch.annotation.Patch
|
||||
import app.revanced.patches.music.premium.backgroundplay.fingerprints.BackgroundPlaybackDisableFingerprint
|
||||
|
||||
import app.revanced.util.exception
|
||||
|
||||
@Patch(
|
||||
name = "Background play",
|
||||
description = "Enables playing music in the background.",
|
||||
compatiblePackages = [CompatiblePackage("com.google.android.apps.youtube.music")]
|
||||
compatiblePackages = [CompatiblePackage("com.google.android.apps.youtube.music")],
|
||||
)
|
||||
@Suppress("unused")
|
||||
object BackgroundPlayPatch : BytecodePatch(setOf(BackgroundPlaybackDisableFingerprint)) {
|
||||
override fun execute(context: BytecodeContext) =
|
||||
BackgroundPlaybackDisableFingerprint.result?.mutableMethod?.addInstructions(
|
||||
0, """
|
||||
0,
|
||||
"""
|
||||
const/4 v0, 0x1
|
||||
return v0
|
||||
"""
|
||||
""",
|
||||
) ?: throw BackgroundPlaybackDisableFingerprint.exception
|
||||
}
|
@ -1,15 +1,17 @@
|
||||
package app.revanced.patches.music.premium.backgroundplay.fingerprints
|
||||
|
||||
import app.revanced.patcher.extensions.or
|
||||
import app.revanced.patcher.fingerprint.annotation.FuzzyPatternScanMethod
|
||||
import app.revanced.patcher.fingerprint.MethodFingerprint
|
||||
import app.revanced.patcher.fingerprint.annotation.FuzzyPatternScanMethod
|
||||
import com.android.tools.smali.dexlib2.AccessFlags
|
||||
import com.android.tools.smali.dexlib2.Opcode
|
||||
|
||||
|
||||
@FuzzyPatternScanMethod(2) // FIXME: Test this threshold and find the best value.
|
||||
internal object BackgroundPlaybackDisableFingerprint : MethodFingerprint(
|
||||
"Z", AccessFlags.PUBLIC or AccessFlags.STATIC, listOf("L"), listOf(
|
||||
"Z",
|
||||
AccessFlags.PUBLIC or AccessFlags.STATIC,
|
||||
listOf("L"),
|
||||
listOf(
|
||||
Opcode.CONST_4,
|
||||
Opcode.IF_EQZ,
|
||||
Opcode.IGET,
|
||||
@ -38,6 +40,6 @@ internal object BackgroundPlaybackDisableFingerprint : MethodFingerprint(
|
||||
Opcode.CONST_4,
|
||||
Opcode.RETURN,
|
||||
Opcode.RETURN,
|
||||
Opcode.RETURN
|
||||
)
|
||||
Opcode.RETURN,
|
||||
),
|
||||
)
|
@ -1,16 +1,16 @@
|
||||
package app.revanced.patches.myexpenses.misc.pro
|
||||
|
||||
import app.revanced.util.exception
|
||||
import app.revanced.patcher.data.BytecodeContext
|
||||
import app.revanced.patcher.extensions.InstructionExtensions.addInstructions
|
||||
import app.revanced.patcher.patch.BytecodePatch
|
||||
import app.revanced.patcher.patch.annotation.CompatiblePackage
|
||||
import app.revanced.patcher.patch.annotation.Patch
|
||||
import app.revanced.patches.myexpenses.misc.pro.fingerprints.IsEnabledFingerprint
|
||||
import app.revanced.util.exception
|
||||
|
||||
@Patch(
|
||||
name = "Unlock pro",
|
||||
compatiblePackages = [CompatiblePackage("org.totschnig.myexpenses", ["3.4.9"])]
|
||||
compatiblePackages = [CompatiblePackage("org.totschnig.myexpenses", ["3.4.9"])],
|
||||
)
|
||||
@Suppress("unused")
|
||||
object UnlockProPatch : BytecodePatch(setOf(IsEnabledFingerprint)) {
|
||||
@ -19,7 +19,6 @@ object UnlockProPatch : BytecodePatch(setOf(IsEnabledFingerprint)) {
|
||||
"""
|
||||
const/4 v0, 0x1
|
||||
return v0
|
||||
"""
|
||||
""",
|
||||
) ?: throw IsEnabledFingerprint.exception
|
||||
|
||||
}
|
||||
|
@ -4,5 +4,5 @@ import app.revanced.patcher.fingerprint.MethodFingerprint
|
||||
|
||||
internal object IsEnabledFingerprint : MethodFingerprint(
|
||||
"Z",
|
||||
strings = listOf("feature", "feature.licenceStatus")
|
||||
strings = listOf("feature", "feature.licenceStatus"),
|
||||
)
|
||||
|
@ -12,11 +12,11 @@ import app.revanced.util.exception
|
||||
@Patch(
|
||||
name = "Hide ads",
|
||||
description = "Hides most of the ads across the app.",
|
||||
compatiblePackages = [CompatiblePackage("com.myfitnesspal.android")]
|
||||
compatiblePackages = [CompatiblePackage("com.myfitnesspal.android")],
|
||||
)
|
||||
@Suppress("unused")
|
||||
object HideAdsPatch : BytecodePatch(
|
||||
setOf(IsPremiumUseCaseImplFingerprint, MainActivityNavigateToNativePremiumUpsellFingerprint)
|
||||
setOf(IsPremiumUseCaseImplFingerprint, MainActivityNavigateToNativePremiumUpsellFingerprint),
|
||||
) {
|
||||
override fun execute(context: BytecodeContext) {
|
||||
// Overwrite the premium status specifically for ads.
|
||||
@ -25,14 +25,14 @@ object HideAdsPatch : BytecodePatch(
|
||||
"""
|
||||
sget-object v0, Ljava/lang/Boolean;->TRUE:Ljava/lang/Boolean;
|
||||
return-object v0
|
||||
"""
|
||||
""",
|
||||
) ?: throw IsPremiumUseCaseImplFingerprint.exception
|
||||
|
||||
// Prevent the premium upsell dialog from showing when the main activity is launched.
|
||||
// In other places that are premium-only the dialog will still show.
|
||||
MainActivityNavigateToNativePremiumUpsellFingerprint.result?.mutableMethod?.replaceInstructions(
|
||||
0,
|
||||
"return-void"
|
||||
"return-void",
|
||||
) ?: throw MainActivityNavigateToNativePremiumUpsellFingerprint.exception
|
||||
}
|
||||
}
|
||||
|
@ -7,5 +7,5 @@ object IsPremiumUseCaseImplFingerprint : MethodFingerprint(
|
||||
accessFlags = AccessFlags.PUBLIC.value,
|
||||
customFingerprint = { methodDef, classDef ->
|
||||
classDef.type.endsWith("IsPremiumUseCaseImpl;") && methodDef.name == "doWork"
|
||||
}
|
||||
},
|
||||
)
|
||||
|
@ -9,5 +9,5 @@ object MainActivityNavigateToNativePremiumUpsellFingerprint : MethodFingerprint(
|
||||
accessFlags = AccessFlags.PRIVATE or AccessFlags.FINAL,
|
||||
customFingerprint = { methodDef, classDef ->
|
||||
classDef.type.endsWith("MainActivity;") && methodDef.name == "navigateToNativePremiumUpsell"
|
||||
}
|
||||
},
|
||||
)
|
||||
|
@ -1,25 +1,25 @@
|
||||
package app.revanced.patches.nfctoolsse.misc.pro
|
||||
|
||||
import app.revanced.util.exception
|
||||
import app.revanced.patcher.data.BytecodeContext
|
||||
import app.revanced.patcher.extensions.InstructionExtensions.addInstructions
|
||||
import app.revanced.patcher.patch.BytecodePatch
|
||||
import app.revanced.patcher.patch.annotation.CompatiblePackage
|
||||
import app.revanced.patcher.patch.annotation.Patch
|
||||
import app.revanced.patches.nfctoolsse.misc.pro.fingerprints.IsLicenseRegisteredFingerprint
|
||||
|
||||
import app.revanced.util.exception
|
||||
|
||||
@Patch(
|
||||
name = "Unlock pro",
|
||||
compatiblePackages = [CompatiblePackage("com.wakdev.apps.nfctools.se")]
|
||||
compatiblePackages = [CompatiblePackage("com.wakdev.apps.nfctools.se")],
|
||||
)
|
||||
@Suppress("unused")
|
||||
object UnlockProPatch : BytecodePatch(setOf(IsLicenseRegisteredFingerprint)) {
|
||||
override fun execute(context: BytecodeContext) = IsLicenseRegisteredFingerprint.result?.mutableMethod
|
||||
?.addInstructions(
|
||||
0, """
|
||||
0,
|
||||
"""
|
||||
const/4 v0, 0x1
|
||||
return v0
|
||||
"""
|
||||
""",
|
||||
) ?: throw IsLicenseRegisteredFingerprint.exception
|
||||
}
|
||||
|
@ -6,5 +6,5 @@ import com.android.tools.smali.dexlib2.AccessFlags
|
||||
internal object IsLicenseRegisteredFingerprint : MethodFingerprint(
|
||||
returnType = "Z",
|
||||
accessFlags = AccessFlags.PUBLIC.value,
|
||||
strings = listOf("kLicenseCheck")
|
||||
strings = listOf("kLicenseCheck"),
|
||||
)
|
@ -1,24 +1,24 @@
|
||||
package app.revanced.patches.nyx.misc.pro
|
||||
|
||||
import app.revanced.util.exception
|
||||
import app.revanced.patcher.data.BytecodeContext
|
||||
import app.revanced.patcher.extensions.InstructionExtensions.addInstructions
|
||||
import app.revanced.patcher.patch.BytecodePatch
|
||||
import app.revanced.patcher.patch.annotation.CompatiblePackage
|
||||
import app.revanced.patcher.patch.annotation.Patch
|
||||
import app.revanced.patches.nyx.misc.pro.fingerprints.CheckProFingerprint
|
||||
import app.revanced.util.exception
|
||||
|
||||
@Patch(
|
||||
name = "Unlock pro",
|
||||
compatiblePackages = [CompatiblePackage("com.awedea.nyx", ["2.2.7"])]
|
||||
compatiblePackages = [CompatiblePackage("com.awedea.nyx", ["2.2.7"])],
|
||||
)
|
||||
@Suppress("unused")
|
||||
object UnlockProPatch : BytecodePatch(setOf(CheckProFingerprint)) {
|
||||
override fun execute(context: BytecodeContext) = CheckProFingerprint.result?.mutableMethod?.addInstructions(
|
||||
0,
|
||||
"""
|
||||
0,
|
||||
"""
|
||||
const/4 v0, 0x1
|
||||
return v0
|
||||
"""
|
||||
""",
|
||||
) ?: throw CheckProFingerprint.exception
|
||||
}
|
@ -5,5 +5,5 @@ import app.revanced.patcher.fingerprint.MethodFingerprint
|
||||
internal object CheckProFingerprint : MethodFingerprint(
|
||||
customFingerprint = { methodDef, _ ->
|
||||
methodDef.definingClass.endsWith("BillingManager;") && methodDef.name == "isProVersion"
|
||||
}
|
||||
},
|
||||
)
|
||||
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
x
Reference in New Issue
Block a user