使用 Frida 的抽象类方法调用的 Android 钩子



我正在尝试学习弗里达,到目前为止已经进行了一些实验。事情大多有效,因为谢天谢地,我可以找到足够的示例和教程来帮助我完成。 然而,在这个时间点,我手头有一个非常具体的任务。

因此,假设下面是我所指的弗里达钩子:

Java.perform(function () {
var Activity = Java.use("myPack.myClass");
Activity.methodM1.overload('[B', 'java.lang.String').implementation = function (a, str) {
var retval = this.methodM1(a, str);
console.log("[*] return value4: "+retval);
return retval;
};
});

现在根据我到目前为止的理解,对于上面的Java.use,我是说每当创建myPackage.myClass的对象并且如果该对象调用方法methodM1时,请改为获取对我的javascript函数的控制权,并执行其中提到的任何操作。

按预期完成工作。然而,要点(为了讨论而感兴趣(是:如果对象被制造出来,那么就会发生这种情况。

类似地,如果我们也谈论Java.choose((,而不是Java.use,情况将是相同的。所以即使在这种情况下,我们也在说如果对象被创建,那么调用我的回调。

现在,如果我尝试钩接到抽象类的方法会发生什么 假设我正在尝试挂接到该方法

'static getInstance(String(' 之 java.security.KeyPairGenerator(这是一个抽象类(。

这个类是抽象的,它的对象从来没有真正被制作出来。并且该方法是静态的,它直接使用类名本身进行调用。所以在这种情况下,Java.use(( 和 Java.choose((都无法提供帮助(如果我上面的理解是正确的(。

那么在这种情况下,我该如何挂接到getInstance((呢?

这是我已经尝试过的东西:

Java.perform(
function()
{
Java.enumerateLoadedClasses(
{ 
onMatch: function(className)
{
if(className == "java.security.KeyPairGenerator")
{
var item = Java.use(className); 
console.log("the PrivateKey class was just loaded");
item.getInstance.overload('java.lang.String').implementation = function(str)
{
console.log("[*] This got called ");
var ret = item.getInstance(str);
console.log("[*] return value4: "+retval);
return retval;
}
}
},
onComplete:function(){}
});
}
);

但这行不通。同样,我在这里的假设是,每当创建对象并调用getInstance((时,请钩住它。但是在这里,KeyPairGenerator是一个抽象类,它从来没有真正被实例化。我也试过:

className.getInstance((

而不是

item.getInstance((

这也行不通。

从 Frida 10.1.2 开始,早期的检测效果很好,可以在您的情况下用于达到目标。

我在我的设备上尝试了你的代码(Huwaei P8 lite \w Android 6.0(。我使用的是最新的弗里达 (10.1.4(。因此,使用 Java.enumerateLoadedClass(在您的情况下(会使应用程序挂起,几秒钟后,frida 崩溃。

Error: abort was called
at u (frida/node_modules/frida-java/lib/android.js:512)
at p (java.js:2054)
at frida/node_modules/frida-java/index.js:105
at [anon] (repl1.js:28)
at frida/node_modules/frida-java/lib/vm.js:39
at y (frida/node_modules/frida-java/index.js:325)
at frida/node_modules/frida-java/index.js:305
at call (native)
at getPackageInfoNoCheck (Input:1)
[...]

工作解决方案是依靠 Frida 的早期仪器功能:

/*
Working code. 
No need of Java.enumerateLoadedClasses
The following application https://github.com/obaro/SimpleKeystoreApp has been installed  on the target device for testing.
Call the current javascript script like so:
frida -U -f com.sample.foo.simplekeystoreapp -l myscript.js --no-pause
*/
function monitorKPG2()
{
console.log("Starting early instrumentation test...");
Java.perform(function () {
var target = Java.use("java.security.KeyPairGenerator");
console.log("Target = " + target);
target.getInstance.overload("java.lang.String", "java.lang.String").implementation = function(alg, prov) {
console.log("getInstance " + alg);
this.getInstance(alg, prov);
};
}); 
}

console.log("Call me may be");
monitorKPG2();

除了 @D4l3k 的精彩回答之外,以防万一有人像我在 10.0.5 上一样使用旧版本的 Frida(无论出于何种原因(,早期的检测仍然可以使用以下方法实现:Java.performNow(( 而不是Java.perform((

下面是一个使用 Java.performNow(( 的工作示例:

Java.performNow(
function()
{
var item = Java.use("java.security.KeyPairGenerator"); 
console.log("the PrivateKey class was just loaded");
item.getInstance.overload('java.lang.String').implementation = function(str)
{
console.log("[*] This got called " + str);
var ret = this.getInstance(str);
console.log("[*] return value4: "+ret);
return ret;
}
}
);

最新更新