0%


title:Java层Hook

Java层Hook

  1. 脚本编写:

    先用Java.use定位到类,定位类使用的所属的package.类名的方式,之后可以通过implementation方法直接覆写静态方法。另外,再次强调,hook的代码的函数的参数,只需要数量上与原型相同,类型可不做要求。

  2. 几个常用的frida框架命令行参数:

    -U:链接USB设备。

    -F:附加最前面的应用。

    -f:主动启动进程。

    -l:加载script脚本文件

    -o:输出日志。

    —no-pauese:启动主线程运行应用。

  3. 基本上new 后面跟随的都是构造方法。

  4. 在js脚本中,使用$init来指代构造方法的名字。

  5. 中间遇到几次什么main thread 什么的,导致注入失败,目前原因不明,过了几天就能注入了,离谱。

  6. 迟来的脚本注入命令:

1
2
3
frida -U -F 进程名 -l xxx.js    //使用-U 是不需要进行端口转发的,-R才需要的.
//然后由于frida在15.2.2之后,默认app在启动时不再暂停,所以--no-pause参数没用了,想让程序暂停,将--no-pause替换为--pause即可
//-F是附加启动,后跟进程名,-f是spawn方式启动,后跟包名

从这开始是关键代码快速定位:

  1. showStacks()显示函数调用栈,主要使用的是Log类的getStackTraceString方法。
1
2
3
4
5
6
function showStacks(){
Java.perform(function(){
console.log(Java.use("android.util.Log").getStackTraceString(Java.use("java.lang.Throwable").$new()));
})
}
//调用的时候最好做个过滤,防止崩溃.
  1. app处理,提交数据通常会将数据放在集合中,HashMap又是这其中最为常用的。
1
2
3
4
5
var hashMap = Java.use("java.util.HashMap");
hashMap.put.implementation=function(a,b){
console.log("HashMap.put",a,b);
return this.put(a,b);
}
  1. Hook Toast
1
2
3
4
5
6
7
8
9
10
11
12
var toast = Java.use("android.widget.Toast");
toast.show.implementation=function(){
showstacks();
console.log("Toast.show");
return this.show();
}

function showstacks(){
Java.perform(function(){
console.log(Java.use("android.util.Log").getStackTraceString(Java.use("java.lang.Throwable").$new()));
})
}
  1. Hook 组件(按钮,输入框那些,此处以登录按钮为例)
1
2
3
4
Java.perform(function(){
var btn_login_id=Java.use("com.dodonew.online.R$id").btn_login.value;
console.log("btn_lgin_id",btn_login_id);
})
  1. Hook用户输入
1
2
3
4
5
6
var textUtils = Java.use("android.text.TextUtils");
textUtils.isEmpty.implementation = function (a) {
showStacks();
console.log("TextUtils.isEmpty: ", a);
return this.isEmpty(a);
}

据说在协议分析中,客户端与服务端进行数据交换时,通常会使用JSON数据作为中间数据进行交互。通常会用到一些JSON类,如JSONObject,Gson等。后者用的相对较多,且可以被混淆。

1
2
3
4
5
6
7
8
9
10
11
12
var jSONObject = Java.use("org.json.JSONObject");
jSONObject.put.overload('java.lang.String', 'java.lang.Object').implementation = function (a, b) {
showStacks();
console.log("JSONObject.put: ", a, b);
return this.put(a, b);
}
jSONObject.getString.implementation = function (a) {
showStacks();
var result = this.getString(a);
console.log("JSONObject.getString: ", a, result);
return result;
}

Hook StringBuilder

Java中,字符串是只读的,对字符串进行修改,拼接等操作都是会创建新的字符串来返回

当有大量的字符串操作时,一般都会用到StringBuilder,Hook其toString方法来定位关键字符串。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
Java.perform(function(){
var stringBuilder = Java.use("java.lang.StringBuilder");
stringBuilder.toString.implementation = function () {
var result = this.toString.apply(this, arguments);
if(result == "username=13866668888"){
showStacks();
console.log("stringBuilder.toString is called!", result);
}
return result;
}
})

function showStacks(){
Java.perform(function(){
console.log(Java.use("android.util.Log").getStackTraceString(Java.use("java.lang.Throwable").$new()));
})
}

MD5 Hook

MAC Hook