Skip to content

Commit

Permalink
fix: Hook the 'You' library tab
Browse files Browse the repository at this point in the history
  • Loading branch information
LisoUseInAIKyrios committed Mar 21, 2024
1 parent 2094b9d commit 0de51bf
Show file tree
Hide file tree
Showing 4 changed files with 66 additions and 66 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ package app.revanced.patches.youtube.misc.navigation
import app.revanced.patcher.data.BytecodeContext
import app.revanced.patcher.extensions.InstructionExtensions.addInstruction
import app.revanced.patcher.extensions.InstructionExtensions.getInstruction
import app.revanced.patcher.fingerprint.MethodFingerprint
import app.revanced.patcher.patch.BytecodePatch
import app.revanced.patcher.patch.annotation.Patch
import app.revanced.patcher.util.proxy.mutableTypes.MutableMethod
Expand All @@ -14,6 +15,7 @@ import app.revanced.patches.youtube.misc.navigation.fingerprints.PivotBarButtons
import app.revanced.patches.youtube.misc.navigation.fingerprints.PivotBarConstructorFingerprint
import app.revanced.patches.youtube.misc.navigation.fingerprints.PivotBarCreateButtonViewFingerprint
import app.revanced.patches.youtube.misc.navigation.fingerprints.PivotBarEnumFingerprint
import app.revanced.patches.youtube.misc.navigation.fingerprints.YouNavigationTabFingerprint
import app.revanced.patches.youtube.misc.navigation.utils.InjectionUtils.REGISTER_TEMPLATE_REPLACEMENT
import app.revanced.patches.youtube.misc.navigation.utils.InjectionUtils.injectHook
import app.revanced.util.getReference
Expand All @@ -33,8 +35,8 @@ import com.android.tools.smali.dexlib2.iface.reference.MethodReference
object NavigationBarHookPatch : BytecodePatch(
setOf(
PivotBarConstructorFingerprint,
ActionBarSearchResultsFingerprint,
NavigationBarHookCallbackFingerprint
NavigationBarHookCallbackFingerprint,
ActionBarSearchResultsFingerprint
)
) {
internal const val INTEGRATIONS_CLASS_DESCRIPTOR =
Expand All @@ -46,77 +48,62 @@ object NavigationBarHookPatch : BytecodePatch(
private lateinit var navigationTabCreatedCallbackMethod: MutableMethod

override fun execute(context: BytecodeContext) {
PivotBarConstructorFingerprint.resultOrThrow().let {
InitializeButtonsFingerprint.resolve(
context,
it.classDef
)
}

val initializeButtonsResult = InitializeButtonsFingerprint.resultOrThrow()

val fingerprintResults =
arrayOf(PivotBarEnumFingerprint, PivotBarButtonsViewFingerprint)
.onEach {
it.resolve(
context,
initializeButtonsResult.mutableMethod,
initializeButtonsResult.mutableClass,
)
}
.map { it.resultOrThrow().scanResult.patternScanResult!! }

val enumScanResult = fingerprintResults[0]
val buttonViewResult = fingerprintResults[1]

val enumHookInsertIndex = enumScanResult.startIndex + 2
val buttonHookInsertIndex = buttonViewResult.endIndex
InitializeButtonsFingerprint.resolve(
context,
PivotBarConstructorFingerprint.resultOrThrow().classDef
)

/*
* Inject hooks
*/
fun MethodFingerprint.patternScanResult() = resultOrThrow().scanResult.patternScanResult!!

val enumHook = "invoke-static { v$REGISTER_TEMPLATE_REPLACEMENT }, " +
"$INTEGRATIONS_CLASS_DESCRIPTOR->setLastAppNavigationEnum(Ljava/lang/Enum;)V"
val buttonHook = "invoke-static { v$REGISTER_TEMPLATE_REPLACEMENT }, " +
"$INTEGRATIONS_CLASS_DESCRIPTOR->navigationTabLoaded(Landroid/view/View;)V"
// All of these hooks can be found by filtering the method for the calls to PivotBar
// and calls to lookup the Navigation enum.
// But the 'You' tab does not have an enum and that approach makes this patch a bit more complicated.
InitializeButtonsFingerprint.resultOrThrow().apply {

// Inject bottom to top to not mess up the indices
mapOf(
buttonHook to buttonHookInsertIndex,
enumHook to enumHookInsertIndex,
).forEach { (hook, insertIndex) ->
initializeButtonsResult.mutableMethod.injectHook(insertIndex, hook)
}
PivotBarEnumFingerprint.also {
it.resolve(context, mutableMethod, mutableClass)
mutableMethod.injectHook(
it.patternScanResult().startIndex + 2,
"invoke-static { v$REGISTER_TEMPLATE_REPLACEMENT }, " +
"$INTEGRATIONS_CLASS_DESCRIPTOR->setLastAppNavigationEnum(Ljava/lang/Enum;)V"
)
}

PivotBarButtonsViewFingerprint.also {
it.resolve(context, mutableMethod, mutableClass)
mutableMethod.injectHook(
it.patternScanResult().endIndex,
"invoke-static { v$REGISTER_TEMPLATE_REPLACEMENT }, " +
"$INTEGRATIONS_CLASS_DESCRIPTOR->navigationTabLoaded(Landroid/view/View;)V"
)
}

/**
* Unique hook just for the Create tab button.
*/
PivotBarCreateButtonViewFingerprint.resolve(
context,
initializeButtonsResult.mutableMethod,
initializeButtonsResult.mutableClass
)
YouNavigationTabFingerprint.also {
it.resolve(context, mutableMethod, mutableClass)
mutableMethod.injectHook(
it.patternScanResult().startIndex + 3,
"invoke-static/range { v$REGISTER_TEMPLATE_REPLACEMENT .. v$REGISTER_TEMPLATE_REPLACEMENT }, " +
"$INTEGRATIONS_CLASS_DESCRIPTOR->youTabLoaded(Landroid/view/View;)V"
)
}

PivotBarCreateButtonViewFingerprint.resultOrThrow().apply {
val insertIndex = scanResult.patternScanResult!!.endIndex
mutableMethod.injectHook(
insertIndex,
"invoke-static { v$REGISTER_TEMPLATE_REPLACEMENT }, " +
"$INTEGRATIONS_CLASS_DESCRIPTOR->createTabLoaded(Landroid/view/View;)V"
)
PivotBarCreateButtonViewFingerprint.also {
it.resolve(context, mutableMethod, mutableClass)
mutableMethod.injectHook(
it.patternScanResult().endIndex,
"invoke-static { v$REGISTER_TEMPLATE_REPLACEMENT }, " +
"$INTEGRATIONS_CLASS_DESCRIPTOR->createTabLoaded(Landroid/view/View;)V"
)
}
}


/**
* Callback for other patches.
*/
NavigationBarHookCallbackFingerprint.resultOrThrow().apply {
navigationTabCreatedCallbackMethod = mutableMethod
}


/**
* Search bar.
*/
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
package app.revanced.patches.youtube.misc.navigation.fingerprints

import app.revanced.patcher.fingerprint.MethodFingerprint
import com.android.tools.smali.dexlib2.Opcode

/**
* Resolves to the method found in [InitializeButtonsFingerprint].
*/
internal object YouNavigationTabFingerprint : MethodFingerprint(
opcodes = listOf(
Opcode.INVOKE_DIRECT_RANGE,
Opcode.INVOKE_VIRTUAL,
Opcode.MOVE_RESULT_OBJECT, // target reference
Opcode.GOTO_16
)
)
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,6 @@ package app.revanced.patches.youtube.misc.navigation.utils
import app.revanced.patcher.extensions.InstructionExtensions.addInstruction
import app.revanced.patcher.extensions.InstructionExtensions.getInstruction
import app.revanced.patcher.util.proxy.mutableTypes.MutableMethod
import com.android.tools.smali.dexlib2.Opcode.MOVE_RESULT_OBJECT
import com.android.tools.smali.dexlib2.iface.instruction.OneRegisterInstruction

internal object InjectionUtils {
Expand All @@ -13,18 +12,16 @@ internal object InjectionUtils {
* Injects an instruction into insertIndex of the hook.
* @param hook The hook to insert.
* @param insertIndex The index to insert the instruction at.
* [MOVE_RESULT_OBJECT] has to be the previous instruction before [insertIndex].
* a [OneRegisterInstruction] must be present before [insertIndex].
*/
fun MutableMethod.injectHook(insertIndex: Int, hook: String) {
val injectTarget = this

// Register to pass to the hook
val registerIndex = insertIndex - 1 // MOVE_RESULT_OBJECT is always the previous instruction
val register = injectTarget.getInstruction<OneRegisterInstruction>(registerIndex).registerA
val register = getInstruction<OneRegisterInstruction>(registerIndex).registerA

injectTarget.addInstruction(
addInstruction(
insertIndex,
hook.replace("REGISTER_INDEX", register.toString()),
hook.replace("REGISTER_INDEX", register.toString())
)
}
}
2 changes: 1 addition & 1 deletion src/main/resources/addresources/values/strings.xml
Original file line number Diff line number Diff line change
Expand Up @@ -176,7 +176,7 @@
<string name="revanced_hide_keyword_content_subscriptions_title">Hide subscription videos by keywords</string>x
<string name="revanced_hide_keyword_content_subscriptions_summary_on">Videos in the subscriptions tab are filtered by keywords</string>
<string name="revanced_hide_keyword_content_subscriptions_summary_off">Videos in the subscriptions tab are not filtered by keywords</string>
<string name="revanced_hide_keyword_content_search_title">Hide search results by keywords</string>x
<string name="revanced_hide_keyword_content_search_title">Hide search results by keywords</string>
<string name="revanced_hide_keyword_content_search_summary_on">Search results are filtered by keywords</string>
<string name="revanced_hide_keyword_content_search_summary_off">Search results are not filtered by keywords</string>
<string name="revanced_hide_keyword_content_phrases_title">Keywords to hide</string>
Expand Down

0 comments on commit 0de51bf

Please sign in to comment.