Как поменять тела методов под Android - PullRequest
0 голосов
/ 09 июня 2019

В чистой Java с помощью агентов внедрения и java существует способ заменить тело метода на время выполнения .

Недоступно java.lang.instrument.Instrumentation недоступно для Android.

Я проверил все другие альтернативы, например, описанную здесь в stackoverflow , которая указывает на устаревшую реализацию javassist-android . Что удивительно работает, но только для новых классов.

Существует также статья под названием Код горячей замены в Android , в которой описывается, как снова загружать классы во время выполнения, а не как заменять существующие методы классов.

Единственной статьей, посвященной этой проблеме, является статья под названием Взлом Android: замена методов системных классов собственным , который пропускает исходный код и ссылается на Dalvik, а не на ART (поэтому он не будет работать) на современном оборудовании).

Итак, есть ли способ сделать это?

...

Итог : причина, по которой я хочу это, состоит в том, чтобы отслеживать специфические вызовы методов в моем приложении, например, когда этот метод вызывается (и выполнять некоторые действия перед ним), и просто когда этот метод завершается (и также выполняет некоторые действия с ним). Эти методы определены во время выполнения, поэтому невозможно знать их заранее, во время компиляции.

1 Ответ

1 голос
/ 09 июня 2019

Одна из новых функций в Android Studio 3.5 - Применить изменения , которая в основном выполняет логику, аналогичную той, которую вы хотите достичь:

".. мы полагаемся на инструментарий времени выполнения, который поддерживается в Android 8.0 (Oreo) и более новые устройства и эмуляторы для переопределения классов на лету. "


Также, в эпизоде ​​108 подкаста АБР Эстебан де ла Канал упомянул:

".. В Android Oreo (8.0) на платформе реализован байт-код инструменты на лету, так что мы можем реально изменить класс dexed работающего приложения .. приложив, в основном, эквивалент JVMTI в Java, поэтому мы можем присоединить агента и сказать: вы можете поменяться местами этот класс с этим. "


Начните с чтения art / openjdkjvmti источников, то есть readme документирует следующее:

плагин openjdkjvmti
Это частичная реализация JVMTI v1.2 Интерфейс для Android Runtime в качестве плагина. Это позволяет использовать агенты, которые могут изменять текущее состояние программы, изменяя файлы dex в памяти и выполнение других операций на глобальном состояние выполнения.


Как только исходники Android Studio 3.5 будут выпущены, посмотрите, как они использовали эти новые API в реализации Apply Changes .

...