mirror of
https://github.com/inotia00/revanced-patches.git
synced 2025-06-13 05:37:40 +02:00
chore: Lint code
This commit is contained in:
@ -30,6 +30,7 @@ object AppClient {
|
|||||||
|
|
||||||
private const val DEVICE_MAKE_IOS = "Apple"
|
private const val DEVICE_MAKE_IOS = "Apple"
|
||||||
private const val OS_NAME_IOS = "iOS"
|
private const val OS_NAME_IOS = "iOS"
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* The device machine id for the iPhone 15 Pro Max (iPhone16,2),
|
* The device machine id for the iPhone 15 Pro Max (iPhone16,2),
|
||||||
* used to get HDR with AV1 hardware decoding.
|
* used to get HDR with AV1 hardware decoding.
|
||||||
@ -240,7 +241,6 @@ object AppClient {
|
|||||||
val userAgent: String,
|
val userAgent: String,
|
||||||
/**
|
/**
|
||||||
* Android SDK version, equivalent to [Build.VERSION.SDK] (System property: ro.build.version.sdk)
|
* Android SDK version, equivalent to [Build.VERSION.SDK] (System property: ro.build.version.sdk)
|
||||||
* Field is null if not applicable.
|
|
||||||
*/
|
*/
|
||||||
val androidSdkVersion: String = Build.VERSION.SDK,
|
val androidSdkVersion: String = Build.VERSION.SDK,
|
||||||
/**
|
/**
|
||||||
|
@ -141,8 +141,9 @@ public class SpoofStreamingDataPatch {
|
|||||||
* 1. Save the requestHeader in a field.
|
* 1. Save the requestHeader in a field.
|
||||||
* 2. Invoke fetchRequest with the videoId used in PlaybackStartDescriptor.
|
* 2. Invoke fetchRequest with the videoId used in PlaybackStartDescriptor.
|
||||||
* <p>
|
* <p>
|
||||||
* @param requestHeaders Save the request Headers used for login to a field.
|
*
|
||||||
* Only used in YouTube Music where login is required.
|
* @param requestHeaders Save the request Headers used for login to a field.
|
||||||
|
* Only used in YouTube Music where login is required.
|
||||||
*/
|
*/
|
||||||
private static void setRequestHeaders(Map<String, String> requestHeaders) {
|
private static void setRequestHeaders(Map<String, String> requestHeaders) {
|
||||||
if (SPOOF_STREAMING_DATA_MUSIC) {
|
if (SPOOF_STREAMING_DATA_MUSIC) {
|
||||||
|
@ -130,17 +130,35 @@ object PlayerRoutes {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@JvmStatic
|
@JvmStatic
|
||||||
fun getPlayerResponseConnectionFromRoute(route: CompiledRoute, clientType: AppClient.ClientType): HttpURLConnection {
|
fun getPlayerResponseConnectionFromRoute(
|
||||||
return getPlayerResponseConnectionFromRoute(route, clientType.userAgent, clientType.id.toString())
|
route: CompiledRoute,
|
||||||
|
clientType: AppClient.ClientType
|
||||||
|
): HttpURLConnection {
|
||||||
|
return getPlayerResponseConnectionFromRoute(
|
||||||
|
route,
|
||||||
|
clientType.userAgent,
|
||||||
|
clientType.id.toString()
|
||||||
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
@JvmStatic
|
@JvmStatic
|
||||||
fun getPlayerResponseConnectionFromRoute(route: CompiledRoute, clientType: WebClient.ClientType): HttpURLConnection {
|
fun getPlayerResponseConnectionFromRoute(
|
||||||
return getPlayerResponseConnectionFromRoute(route, clientType.userAgent, clientType.id.toString())
|
route: CompiledRoute,
|
||||||
|
clientType: WebClient.ClientType
|
||||||
|
): HttpURLConnection {
|
||||||
|
return getPlayerResponseConnectionFromRoute(
|
||||||
|
route,
|
||||||
|
clientType.userAgent,
|
||||||
|
clientType.id.toString()
|
||||||
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
@Throws(IOException::class)
|
@Throws(IOException::class)
|
||||||
fun getPlayerResponseConnectionFromRoute(route: CompiledRoute, userAgent: String, clientVersion: String): HttpURLConnection {
|
fun getPlayerResponseConnectionFromRoute(
|
||||||
|
route: CompiledRoute,
|
||||||
|
userAgent: String,
|
||||||
|
clientVersion: String
|
||||||
|
): HttpURLConnection {
|
||||||
val connection = Requester.getConnectionFromCompiledRoute(YT_API_URL, route)
|
val connection = Requester.getConnectionFromCompiledRoute(YT_API_URL, route)
|
||||||
|
|
||||||
connection.setRequestProperty("Content-Type", "application/json")
|
connection.setRequestProperty("Content-Type", "application/json")
|
||||||
|
@ -9,7 +9,6 @@ import app.revanced.extension.shared.patches.spoof.requests.PlayerRoutes.getPlay
|
|||||||
import app.revanced.extension.shared.settings.BaseSettings
|
import app.revanced.extension.shared.settings.BaseSettings
|
||||||
import app.revanced.extension.shared.utils.Logger
|
import app.revanced.extension.shared.utils.Logger
|
||||||
import app.revanced.extension.shared.utils.Utils
|
import app.revanced.extension.shared.utils.Utils
|
||||||
import org.apache.commons.lang3.ArrayUtils
|
|
||||||
import org.apache.commons.lang3.StringUtils
|
import org.apache.commons.lang3.StringUtils
|
||||||
import java.io.BufferedInputStream
|
import java.io.BufferedInputStream
|
||||||
import java.io.ByteArrayOutputStream
|
import java.io.ByteArrayOutputStream
|
||||||
@ -111,6 +110,7 @@ class StreamingDataRequest private constructor(
|
|||||||
* Any arbitrarily large value, but must be at least twice [.HTTP_TIMEOUT_MILLISECONDS]
|
* Any arbitrarily large value, but must be at least twice [.HTTP_TIMEOUT_MILLISECONDS]
|
||||||
*/
|
*/
|
||||||
private const val MAX_MILLISECONDS_TO_WAIT_FOR_FETCH = 20 * 1000
|
private const val MAX_MILLISECONDS_TO_WAIT_FOR_FETCH = 20 * 1000
|
||||||
|
|
||||||
@GuardedBy("itself")
|
@GuardedBy("itself")
|
||||||
val cache: MutableMap<String, StreamingDataRequest> = Collections.synchronizedMap(
|
val cache: MutableMap<String, StreamingDataRequest> = Collections.synchronizedMap(
|
||||||
object : LinkedHashMap<String, StreamingDataRequest>(100) {
|
object : LinkedHashMap<String, StreamingDataRequest>(100) {
|
||||||
@ -171,11 +171,13 @@ class StreamingDataRequest private constructor(
|
|||||||
Logger.printDebug { "Fetching video streams for: $videoId using client: $clientType" }
|
Logger.printDebug { "Fetching video streams for: $videoId using client: $clientType" }
|
||||||
|
|
||||||
try {
|
try {
|
||||||
val connection = getPlayerResponseConnectionFromRoute(GET_STREAMING_DATA, clientType)
|
val connection =
|
||||||
|
getPlayerResponseConnectionFromRoute(GET_STREAMING_DATA, clientType)
|
||||||
connection.connectTimeout = HTTP_TIMEOUT_MILLISECONDS
|
connection.connectTimeout = HTTP_TIMEOUT_MILLISECONDS
|
||||||
connection.readTimeout = HTTP_TIMEOUT_MILLISECONDS
|
connection.readTimeout = HTTP_TIMEOUT_MILLISECONDS
|
||||||
|
|
||||||
val usePoToken = clientType.requirePoToken && !StringUtils.isAnyEmpty(botGuardPoToken, visitorId)
|
val usePoToken =
|
||||||
|
clientType.requirePoToken && !StringUtils.isAnyEmpty(botGuardPoToken, visitorId)
|
||||||
|
|
||||||
for (key in REQUEST_HEADER_KEYS) {
|
for (key in REQUEST_HEADER_KEYS) {
|
||||||
var value = playerHeaders[key]
|
var value = playerHeaders[key]
|
||||||
@ -248,7 +250,8 @@ class StreamingDataRequest private constructor(
|
|||||||
// Retry with different client if empty response body is received.
|
// Retry with different client if empty response body is received.
|
||||||
for (clientType in CLIENT_ORDER_TO_USE) {
|
for (clientType in CLIENT_ORDER_TO_USE) {
|
||||||
if (clientType.requireAuth &&
|
if (clientType.requireAuth &&
|
||||||
playerHeaders[AUTHORIZATION_HEADER] == null) {
|
playerHeaders[AUTHORIZATION_HEADER] == null
|
||||||
|
) {
|
||||||
Logger.printDebug { "Skipped login-required client (incognito mode or not logged in)\nClient: $clientType\nVideo: $videoId" }
|
Logger.printDebug { "Skipped login-required client (incognito mode or not logged in)\nClient: $clientType\nVideo: $videoId" }
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
@ -270,7 +273,9 @@ class StreamingDataRequest private constructor(
|
|||||||
ByteArrayOutputStream().use { stream ->
|
ByteArrayOutputStream().use { stream ->
|
||||||
val buffer = ByteArray(2048)
|
val buffer = ByteArray(2048)
|
||||||
var bytesRead: Int
|
var bytesRead: Int
|
||||||
while ((inputStream.read(buffer).also { bytesRead = it }) >= 0) {
|
while ((inputStream.read(buffer)
|
||||||
|
.also { bytesRead = it }) >= 0
|
||||||
|
) {
|
||||||
stream.write(buffer, 0, bytesRead)
|
stream.write(buffer, 0, bytesRead)
|
||||||
}
|
}
|
||||||
lastSpoofedClientType = clientType
|
lastSpoofedClientType = clientType
|
||||||
|
@ -121,21 +121,27 @@ public class ReturnYouTubeDislikeApi {
|
|||||||
public static long getFetchCallResponseTimeLast() {
|
public static long getFetchCallResponseTimeLast() {
|
||||||
return fetchCallResponseTimeLast;
|
return fetchCallResponseTimeLast;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static long getFetchCallResponseTimeMin() {
|
public static long getFetchCallResponseTimeMin() {
|
||||||
return fetchCallResponseTimeMin;
|
return fetchCallResponseTimeMin;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static long getFetchCallResponseTimeMax() {
|
public static long getFetchCallResponseTimeMax() {
|
||||||
return fetchCallResponseTimeMax;
|
return fetchCallResponseTimeMax;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static long getFetchCallResponseTimeAverage() {
|
public static long getFetchCallResponseTimeAverage() {
|
||||||
return fetchCallCount == 0 ? 0 : (fetchCallResponseTimeTotal / fetchCallCount);
|
return fetchCallCount == 0 ? 0 : (fetchCallResponseTimeTotal / fetchCallCount);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static int getFetchCallCount() {
|
public static int getFetchCallCount() {
|
||||||
return fetchCallCount;
|
return fetchCallCount;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static int getFetchCallNumberOfFailures() {
|
public static int getFetchCallNumberOfFailures() {
|
||||||
return fetchCallNumberOfFailures;
|
return fetchCallNumberOfFailures;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static int getNumberOfRateLimitRequestsEncountered() {
|
public static int getNumberOfRateLimitRequestsEncountered() {
|
||||||
return numberOfRateLimitRequestsEncountered;
|
return numberOfRateLimitRequestsEncountered;
|
||||||
}
|
}
|
||||||
|
@ -19,7 +19,10 @@ import java.util.concurrent.Future
|
|||||||
import java.util.concurrent.TimeUnit
|
import java.util.concurrent.TimeUnit
|
||||||
import java.util.concurrent.TimeoutException
|
import java.util.concurrent.TimeoutException
|
||||||
|
|
||||||
class MusicRequest private constructor(private val videoId: String, private val checkCategory: Boolean) {
|
class MusicRequest private constructor(
|
||||||
|
private val videoId: String,
|
||||||
|
private val checkCategory: Boolean
|
||||||
|
) {
|
||||||
/**
|
/**
|
||||||
* Time this instance and the fetch future was created.
|
* Time this instance and the fetch future was created.
|
||||||
*/
|
*/
|
||||||
@ -121,7 +124,10 @@ class MusicRequest private constructor(private val videoId: String, private val
|
|||||||
Logger.printDebug { "Fetching playlist request for: $videoId using client: $clientTypeName" }
|
Logger.printDebug { "Fetching playlist request for: $videoId using client: $clientTypeName" }
|
||||||
|
|
||||||
try {
|
try {
|
||||||
val connection = PlayerRoutes.getPlayerResponseConnectionFromRoute(PlayerRoutes.GET_PLAYLIST_PAGE, clientType)
|
val connection = PlayerRoutes.getPlayerResponseConnectionFromRoute(
|
||||||
|
PlayerRoutes.GET_PLAYLIST_PAGE,
|
||||||
|
clientType
|
||||||
|
)
|
||||||
val requestBody =
|
val requestBody =
|
||||||
PlayerRoutes.createApplicationRequestBody(clientType, videoId, "RD$videoId")
|
PlayerRoutes.createApplicationRequestBody(clientType, videoId, "RD$videoId")
|
||||||
|
|
||||||
@ -158,7 +164,10 @@ class MusicRequest private constructor(private val videoId: String, private val
|
|||||||
Logger.printDebug { "Fetching playability request for: $videoId using client: $clientTypeName" }
|
Logger.printDebug { "Fetching playability request for: $videoId using client: $clientTypeName" }
|
||||||
|
|
||||||
try {
|
try {
|
||||||
val connection = PlayerRoutes.getPlayerResponseConnectionFromRoute(PlayerRoutes.GET_CATEGORY, clientType)
|
val connection = PlayerRoutes.getPlayerResponseConnectionFromRoute(
|
||||||
|
PlayerRoutes.GET_CATEGORY,
|
||||||
|
clientType
|
||||||
|
)
|
||||||
val requestBody =
|
val requestBody =
|
||||||
PlayerRoutes.createWebInnertubeBody(clientType, videoId)
|
PlayerRoutes.createWebInnertubeBody(clientType, videoId)
|
||||||
|
|
||||||
|
@ -4,7 +4,6 @@ import android.app.Activity;
|
|||||||
import android.content.Context;
|
import android.content.Context;
|
||||||
import android.os.Bundle;
|
import android.os.Bundle;
|
||||||
import android.util.TypedValue;
|
import android.util.TypedValue;
|
||||||
import android.view.View;
|
|
||||||
import android.view.ViewGroup;
|
import android.view.ViewGroup;
|
||||||
import android.widget.EditText;
|
import android.widget.EditText;
|
||||||
import android.widget.SearchView;
|
import android.widget.SearchView;
|
||||||
|
@ -30,7 +30,9 @@ internal class JsonPatchesFileGenerator : PatchesFileGenerator {
|
|||||||
},
|
},
|
||||||
)
|
)
|
||||||
}.let {
|
}.let {
|
||||||
patchesJson.writeText(GsonBuilder().serializeNulls().setPrettyPrinting().create().toJson(it))
|
patchesJson.writeText(
|
||||||
|
GsonBuilder().serializeNulls().setPrettyPrinting().create().toJson(it)
|
||||||
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -75,7 +75,8 @@ val albumMusicVideoPatch = bytecodePatch(
|
|||||||
|
|
||||||
audioVideoSwitchToggleConstructorFingerprint.methodOrThrow().apply {
|
audioVideoSwitchToggleConstructorFingerprint.methodOrThrow().apply {
|
||||||
val onClickListenerIndex = indexOfAudioVideoSwitchSetOnClickListenerInstruction(this)
|
val onClickListenerIndex = indexOfAudioVideoSwitchSetOnClickListenerInstruction(this)
|
||||||
val viewRegister = getInstruction<FiveRegisterInstruction>(onClickListenerIndex).registerC
|
val viewRegister =
|
||||||
|
getInstruction<FiveRegisterInstruction>(onClickListenerIndex).registerC
|
||||||
|
|
||||||
addInstruction(
|
addInstruction(
|
||||||
onClickListenerIndex + 1,
|
onClickListenerIndex + 1,
|
||||||
@ -83,11 +84,13 @@ val albumMusicVideoPatch = bytecodePatch(
|
|||||||
"$EXTENSION_CLASS_DESCRIPTOR->setAudioVideoSwitchToggleOnLongClickListener(Landroid/view/View;)V"
|
"$EXTENSION_CLASS_DESCRIPTOR->setAudioVideoSwitchToggleOnLongClickListener(Landroid/view/View;)V"
|
||||||
)
|
)
|
||||||
|
|
||||||
val onClickListenerSyntheticIndex = indexOfFirstInstructionReversedOrThrow(onClickListenerIndex) {
|
val onClickListenerSyntheticIndex =
|
||||||
opcode == Opcode.INVOKE_DIRECT &&
|
indexOfFirstInstructionReversedOrThrow(onClickListenerIndex) {
|
||||||
getReference<MethodReference>()?.name == "<init>"
|
opcode == Opcode.INVOKE_DIRECT &&
|
||||||
}
|
getReference<MethodReference>()?.name == "<init>"
|
||||||
val onClickListenerSyntheticClass = (getInstruction<ReferenceInstruction>(onClickListenerSyntheticIndex).reference as MethodReference).definingClass
|
}
|
||||||
|
val onClickListenerSyntheticClass =
|
||||||
|
(getInstruction<ReferenceInstruction>(onClickListenerSyntheticIndex).reference as MethodReference).definingClass
|
||||||
|
|
||||||
findMethodOrThrow(onClickListenerSyntheticClass) {
|
findMethodOrThrow(onClickListenerSyntheticClass) {
|
||||||
name == "onClick"
|
name == "onClick"
|
||||||
|
@ -5,11 +5,8 @@ import app.revanced.util.getReference
|
|||||||
import app.revanced.util.indexOfFirstInstruction
|
import app.revanced.util.indexOfFirstInstruction
|
||||||
import app.revanced.util.or
|
import app.revanced.util.or
|
||||||
import com.android.tools.smali.dexlib2.AccessFlags
|
import com.android.tools.smali.dexlib2.AccessFlags
|
||||||
import com.android.tools.smali.dexlib2.Opcode
|
|
||||||
import com.android.tools.smali.dexlib2.iface.Method
|
import com.android.tools.smali.dexlib2.iface.Method
|
||||||
import com.android.tools.smali.dexlib2.iface.reference.MethodReference
|
import com.android.tools.smali.dexlib2.iface.reference.MethodReference
|
||||||
import com.android.tools.smali.dexlib2.iface.reference.StringReference
|
|
||||||
import com.android.tools.smali.dexlib2.util.MethodUtil
|
|
||||||
|
|
||||||
const val GET_GMS_CORE_VENDOR_GROUP_ID_METHOD_NAME = "getGmsCoreVendorGroupId"
|
const val GET_GMS_CORE_VENDOR_GROUP_ID_METHOD_NAME = "getGmsCoreVendorGroupId"
|
||||||
|
|
||||||
|
@ -1,19 +1,8 @@
|
|||||||
package app.revanced.patches.shared.materialyou
|
package app.revanced.patches.shared.materialyou
|
||||||
|
|
||||||
import app.revanced.patcher.patch.PatchException
|
|
||||||
import app.revanced.patcher.patch.ResourcePatchContext
|
import app.revanced.patcher.patch.ResourcePatchContext
|
||||||
import app.revanced.util.copyXmlNode
|
|
||||||
import app.revanced.util.inputStreamFromBundledResource
|
|
||||||
import org.w3c.dom.Element
|
import org.w3c.dom.Element
|
||||||
import org.w3c.dom.Node
|
|
||||||
import java.io.File
|
|
||||||
import java.nio.file.Files
|
import java.nio.file.Files
|
||||||
import java.nio.file.StandardCopyOption
|
|
||||||
import javax.xml.parsers.DocumentBuilderFactory
|
|
||||||
import javax.xml.transform.OutputKeys
|
|
||||||
import javax.xml.transform.TransformerFactory
|
|
||||||
import javax.xml.transform.dom.DOMSource
|
|
||||||
import javax.xml.transform.stream.StreamResult
|
|
||||||
|
|
||||||
private fun ResourcePatchContext.patchXmlFile(
|
private fun ResourcePatchContext.patchXmlFile(
|
||||||
fromDir: String,
|
fromDir: String,
|
||||||
|
@ -116,15 +116,20 @@ fun baseSpoofStreamingDataPatch(
|
|||||||
// region Replace the streaming data.
|
// region Replace the streaming data.
|
||||||
|
|
||||||
val approxDurationMsReference = formatStreamModelConstructorFingerprint.matchOrThrow().let {
|
val approxDurationMsReference = formatStreamModelConstructorFingerprint.matchOrThrow().let {
|
||||||
with (it.method) {
|
with(it.method) {
|
||||||
getInstruction<ReferenceInstruction>(it.patternMatch!!.startIndex).reference
|
getInstruction<ReferenceInstruction>(it.patternMatch!!.startIndex).reference
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
val streamingDataFormatsReference = with(videoStreamingDataConstructorFingerprint.methodOrThrow(videoStreamingDataToStringFingerprint)) {
|
val streamingDataFormatsReference = with(
|
||||||
|
videoStreamingDataConstructorFingerprint.methodOrThrow(
|
||||||
|
videoStreamingDataToStringFingerprint
|
||||||
|
)
|
||||||
|
) {
|
||||||
val getFormatsFieldIndex = indexOfGetFormatsFieldInstruction(this)
|
val getFormatsFieldIndex = indexOfGetFormatsFieldInstruction(this)
|
||||||
val longMaxValueIndex = indexOfLongMaxValueInstruction(this, getFormatsFieldIndex)
|
val longMaxValueIndex = indexOfLongMaxValueInstruction(this, getFormatsFieldIndex)
|
||||||
val longMaxValueRegister = getInstruction<OneRegisterInstruction>(longMaxValueIndex).registerA
|
val longMaxValueRegister =
|
||||||
|
getInstruction<OneRegisterInstruction>(longMaxValueIndex).registerA
|
||||||
val videoIdIndex =
|
val videoIdIndex =
|
||||||
indexOfFirstInstructionOrThrow(longMaxValueIndex) {
|
indexOfFirstInstructionOrThrow(longMaxValueIndex) {
|
||||||
val reference = getReference<FieldReference>()
|
val reference = getReference<FieldReference>()
|
||||||
|
@ -209,6 +209,10 @@ internal val poTokenToStringFingerprint = legacyFingerprint(
|
|||||||
classDef.fields.find { it.type == "[B" } != null &&
|
classDef.fields.find { it.type == "[B" } != null &&
|
||||||
// In YouTube, this field's type is 'Lcom/google/android/gms/potokens/PoToken;'.
|
// In YouTube, this field's type is 'Lcom/google/android/gms/potokens/PoToken;'.
|
||||||
// In YouTube Music, this class name is obfuscated.
|
// In YouTube Music, this class name is obfuscated.
|
||||||
classDef.fields.find { it.accessFlags == AccessFlags.PRIVATE.value && it.type.startsWith("L") } != null
|
classDef.fields.find {
|
||||||
|
it.accessFlags == AccessFlags.PRIVATE.value && it.type.startsWith(
|
||||||
|
"L"
|
||||||
|
)
|
||||||
|
} != null
|
||||||
},
|
},
|
||||||
)
|
)
|
||||||
|
@ -342,10 +342,11 @@ val toolBarComponentsPatch = bytecodePatch(
|
|||||||
opcode == Opcode.INVOKE_VIRTUAL &&
|
opcode == Opcode.INVOKE_VIRTUAL &&
|
||||||
getReference<MethodReference>()?.toString() == voiceInputControllerActivityMethodCall
|
getReference<MethodReference>()?.toString() == voiceInputControllerActivityMethodCall
|
||||||
}
|
}
|
||||||
val setOnClickListenerIndex = indexOfFirstInstructionOrThrow(voiceInputControllerActivityIndex) {
|
val setOnClickListenerIndex =
|
||||||
opcode == Opcode.INVOKE_VIRTUAL &&
|
indexOfFirstInstructionOrThrow(voiceInputControllerActivityIndex) {
|
||||||
getReference<MethodReference>()?.name == "setOnClickListener"
|
opcode == Opcode.INVOKE_VIRTUAL &&
|
||||||
}
|
getReference<MethodReference>()?.name == "setOnClickListener"
|
||||||
|
}
|
||||||
val viewRegister =
|
val viewRegister =
|
||||||
getInstruction<FiveRegisterInstruction>(setOnClickListenerIndex).registerC
|
getInstruction<FiveRegisterInstruction>(setOnClickListenerIndex).registerC
|
||||||
|
|
||||||
|
@ -249,7 +249,7 @@ val overlayButtonsPatch = resourcePatch(
|
|||||||
)
|
)
|
||||||
|
|
||||||
val isButton = if (is_19_17_or_greater)
|
val isButton = if (is_19_17_or_greater)
|
||||||
// Note: Do not modify fullscreen button and multiview button
|
// Note: Do not modify fullscreen button and multiview button
|
||||||
id.endsWith("_button") && id != "@id/multiview_button"
|
id.endsWith("_button") && id != "@id/multiview_button"
|
||||||
else
|
else
|
||||||
id.endsWith("_button") || id == "@id/youtube_controls_fullscreen_button_stub"
|
id.endsWith("_button") || id == "@id/youtube_controls_fullscreen_button_stub"
|
||||||
|
@ -271,7 +271,9 @@ val seekbarComponentsPatch = bytecodePatch(
|
|||||||
).forEach { method ->
|
).forEach { method ->
|
||||||
method.apply {
|
method.apply {
|
||||||
val literalIndex =
|
val literalIndex =
|
||||||
indexOfFirstLiteralInstructionOrThrow(launchScreenLayoutTypeLotteFeatureFlag)
|
indexOfFirstLiteralInstructionOrThrow(
|
||||||
|
launchScreenLayoutTypeLotteFeatureFlag
|
||||||
|
)
|
||||||
val resultIndex =
|
val resultIndex =
|
||||||
indexOfFirstInstructionOrThrow(literalIndex, Opcode.MOVE_RESULT)
|
indexOfFirstInstructionOrThrow(literalIndex, Opcode.MOVE_RESULT)
|
||||||
val register = getInstruction<OneRegisterInstruction>(resultIndex).registerA
|
val register = getInstruction<OneRegisterInstruction>(resultIndex).registerA
|
||||||
|
@ -17,8 +17,9 @@ internal val mainActivityBaseContextHook = extensionHook(
|
|||||||
attachBaseContextIndex + 1
|
attachBaseContextIndex + 1
|
||||||
},
|
},
|
||||||
contextRegisterResolver = { method ->
|
contextRegisterResolver = { method ->
|
||||||
val overrideInstruction = method.implementation!!.instructions.elementAt(attachBaseContextIndex)
|
val overrideInstruction =
|
||||||
as FiveRegisterInstruction
|
method.implementation!!.instructions.elementAt(attachBaseContextIndex)
|
||||||
|
as FiveRegisterInstruction
|
||||||
"v${overrideInstruction.registerD}"
|
"v${overrideInstruction.registerD}"
|
||||||
},
|
},
|
||||||
) {
|
) {
|
||||||
|
@ -31,18 +31,21 @@ val fullscreenButtonHookPatch = bytecodePatch(
|
|||||||
dependsOn(sharedExtensionPatch)
|
dependsOn(sharedExtensionPatch)
|
||||||
|
|
||||||
execute {
|
execute {
|
||||||
val (referenceClass, fullscreenActionClass) = with (nextGenWatchLayoutFullscreenModeFingerprint.methodOrThrow()) {
|
val (referenceClass, fullscreenActionClass) = with(
|
||||||
|
nextGenWatchLayoutFullscreenModeFingerprint.methodOrThrow()
|
||||||
|
) {
|
||||||
val targetIndex = indexOfFirstInstructionReversedOrThrow {
|
val targetIndex = indexOfFirstInstructionReversedOrThrow {
|
||||||
opcode == Opcode.INVOKE_DIRECT &&
|
opcode == Opcode.INVOKE_DIRECT &&
|
||||||
getReference<MethodReference>()?.parameterTypes?.size == 2
|
getReference<MethodReference>()?.parameterTypes?.size == 2
|
||||||
}
|
}
|
||||||
val targetReference = getInstruction<ReferenceInstruction>(targetIndex).reference as MethodReference
|
val targetReference =
|
||||||
|
getInstruction<ReferenceInstruction>(targetIndex).reference as MethodReference
|
||||||
|
|
||||||
Pair(targetReference.definingClass, targetReference.parameterTypes[1].toString())
|
Pair(targetReference.definingClass, targetReference.parameterTypes[1].toString())
|
||||||
}
|
}
|
||||||
|
|
||||||
val (enterFullscreenReference, exitFullscreenReference, opcodeName) =
|
val (enterFullscreenReference, exitFullscreenReference, opcodeName) =
|
||||||
with (findMethodOrThrow(referenceClass) { parameters == listOf("I") }) {
|
with(findMethodOrThrow(referenceClass) { parameters == listOf("I") }) {
|
||||||
val enterFullscreenIndex = indexOfFirstInstructionOrThrow {
|
val enterFullscreenIndex = indexOfFirstInstructionOrThrow {
|
||||||
val reference = getReference<MethodReference>()
|
val reference = getReference<MethodReference>()
|
||||||
reference?.returnType == "V" &&
|
reference?.returnType == "V" &&
|
||||||
@ -62,7 +65,8 @@ val fullscreenButtonHookPatch = bytecodePatch(
|
|||||||
getInstruction<ReferenceInstruction>(exitFullscreenIndex).reference
|
getInstruction<ReferenceInstruction>(exitFullscreenIndex).reference
|
||||||
val opcode = getInstruction(enterFullscreenIndex).opcode
|
val opcode = getInstruction(enterFullscreenIndex).opcode
|
||||||
|
|
||||||
val enterFullscreenClass = (enterFullscreenReference as MethodReference).definingClass
|
val enterFullscreenClass =
|
||||||
|
(enterFullscreenReference as MethodReference).definingClass
|
||||||
|
|
||||||
enterFullscreenMethod = if (opcode == Opcode.INVOKE_INTERFACE) {
|
enterFullscreenMethod = if (opcode == Opcode.INVOKE_INTERFACE) {
|
||||||
classes.find { classDef -> classDef.interfaces.contains(enterFullscreenClass) }
|
classes.find { classDef -> classDef.interfaces.contains(enterFullscreenClass) }
|
||||||
|
Reference in New Issue
Block a user