frida+rpc初版理解
补充区别说明
1. 3.6版本 frida12.8.0版本 3.10 frida16.1.0版本
- scrip.exports..rpc方法名 script.exports_sync.rpc方法名
2.
1. 安装frida
-
目前只知道安装最新版 旧版本的安装失败 # todo暂未解决
pip install frida pip install frida-tools
终端输入
frida --version
测试是否安装成功
2.下载安装手机frida-server包
-
需要安装与pip安装的frida包版本一致
-
需要注意 安卓手机的 cpu版本 x86 x86_64 arm arm_64等等
github下载frida-server对应版本的包如:我测试的是arm64 就下载 安装的frida版本的android-【cpu版本】 frida-server-16.0.14-android-arm64.xz
-
下载完后 解压
-
将解压出来的文件重命名【frida-server】 (ps:名称自己定义 无所谓)
-
执行命令 上传到 手机
adb push frida-server路径 /data/local/tmp/ 举例:adb push /Users/admin/Downloads/frida_android_server_file/frida64 /data/local/tmp/ ps:/data/local/tmp/ 不要修改成其他路径 等待上传成功
-
给frida-serve设置权限(依次执行每一行)
adb shell su cd /data/local/tmp/ chmod 777 frida-server
-
设置frida端口
重新打开一个终端 adb forward tcp:27042 tcp:27042
-
启动frida-server
在之前(步骤5)的adb窗口输入 ./frida-server ps:如果挂起来了运行中 就代表成功了
-
python测试代码
import frida remote_dev = frida.get_remote_device() print(remote_dev) front_app = remote_dev.get_frontmost_application() print(front_app) process = remote_dev.enumerate_processes() print(process) for i in process: print(i)
- ps:运行无报错结果就代表frida启动成功了
3. 安装Jadx-Gui 解析apk文件包
下载地址:
mac: https://www.jianshu.com/p/3cc4e861b3db
window: https://github.com/skylot/jadx 下载已打包好的文件
mac运行jdax-gui:依次找目录:xxxxxxx/jadx/build/jadx/bin/jadx-gui
4. frida拦截包
- 作用:方便查看hook方法的入参 及修改方法
确保手机端已开启frida-server服务
– frida-py.py
– dy_frida_js.js
py代码
import time
import frida # 导入frida模块
import sys # 导入sys模块
def on_message(message, data): # js中执行sen函数后要回调的函数
print(message)
'''
spawn模式,Frida会自动启动并注入进目标app,Hook的时机非常早
'''
# device = frida.get_remote_device()
# pid = device.spawn(['com.jx885.reward']) # 包名
# device.resume(pid)
# time.sleep(1)
# session = device.attach(pid)
'''
attach模式,Frida会附加到当前的目标进程中,既需要app处于启动状态,意味着只能从当前时机往后Hook
'''
session = frida.get_remote_device().attach('驾培创业教练') # AppName app名称 需要已启动状态下才能hook
with open('./dy_frida_js.js') as f:
script = session.create_script(f.read())
script.on('message', on_message) # 加载回调函数,也就是js中执行send函数规定要执行的python函数
script.load() # 加载脚本
sys.stdin.read()
js代码
Java.perform(function () {
// 基础写法
// Java.use('包名.类目').hook的方法名.implementation = function (arg1,arg2...) {
// console.log(arg1,arg2...) # 自己添加自己需要执行的代码
// return this.hook的方法名(arg1,arg2...)
// }
// 重构方法的hook写法
// Java.use('包名.类目').hook的方法名.overload("int (ps:这里是参数类型)").implementation = function (arg1,arg2...) {
// console.log(arg1,arg2...) # 自己添加自己需要执行的代码
// return this.hook的方法名(arg1,arg2...)
// }
Java.use('com.jx885.library.http.CommAction').getSmscode.implementation = function (mi, mstr, mstr2) {
console.log(mi, mstr, mstr2)
return this.getSmscode(mi, mstr, mstr2)
}
Java.use('com.jx885.library.http.network.HttpUtils').getStringMD5toUpperCase.implementation = function (s) {
console.log('sing:',s)
return this.getStringMD5toUpperCase(s)
}
})
-
运行py文件代码 (不报错则正常 报错则异常)
确保手机启动了【驾培创业教练】app
输入手机号
查看py是否有返回
【有返回】 成功
【无返回】 退出app 重新打开 输入手机号 在看py文件是否有返回
5. Friada+rpc拦截包
- 作用:hook加密方法返回的response
- 传入需要加密的参数 通过rpc加密后 返回 且不需要手动操作,只需要app处于启动状态即可
py文件
import time
import frida # 导入frida模块
import sys # 导入sys模块
def on_message(message, data): # js中执行sen函数后要回调的函数
print(message)
'''
spawn模式,Frida会自动启动并注入进目标app,Hook的时机非常早
'''
# device = frida.get_remote_device()
# pid = device.spawn(['com.jx885.reward']) # 包名
# device.resume(pid)
# time.sleep(1)
# session = device.attach(pid)
'''
attach模式,Frida会附加到当前的目标进程中,既需要app处于启动状态,意味着只能从当前时机往后Hook
'''
session = frida.get_remote_device().attach('驾培创业教练') # AppName app名称 需要已启动状态下才能hook
with open('frida-js-rpc.js') as f:
script = session.create_script(f.read())
script.on('message', on_message) # 加载回调函数,也就是js中执行send函数规定要执行的python函数
script.load() # 加载脚本
# TODO rpc加入
"""构造需要加密参数"""
[{"type":"text","key":"userjson","value":"{\"phone\":\"15622728821\",\"sign\":\"5F8BFC91E0855B4107C932B931BD18EC\",\"currTime\":\"20230903121053\",\"type\":\"1\"}"}]
currTime = '20230903121053'
phone = '15622728821'
type = '1'
# 加密传参
s = currTime+type+'wocaonima'+phone
sign = script.exports_sync.getsign(s)
print(sign)
js文件
// Java.perform(function () {
// // 基础写法
// // Java.use('包名.类目').hook的方法名.implementation = function (arg1,arg2...) {
// // console.log(arg1,arg2...) # 自己添加自己需要执行的代码
// // return this.hook的方法名(arg1,arg2...)
// // }
// // 重构方法的hook写法
// // Java.use('包名.类目').hook的方法名.overload("int (ps:这里是参数类型)").implementation = function (arg1,arg2...) {
// // console.log(arg1,arg2...) # 自己添加自己需要执行的代码
// // return this.hook的方法名(arg1,arg2...)
// // }
// Java.use('com.jx885.library.http.CommAction').getSmscode.implementation = function (mi, mstr, mstr2) {
// console.log(mi, mstr, mstr2)
// return this.getSmscode(mi, mstr, mstr2)
// }
// Java.use('com.jx885.library.http.network.HttpUtils').getStringMD5toUpperCase.implementation = function (s) {
// console.log('sing:',s)
// return this.getStringMD5toUpperCase(s)
// }
// })
// 加密的函数 但是不知道怎么加密的 就是用rpc将加密的结果返回出来
// s就是要加密的参数
function sign(s){
// 添加返回值
var result = ''
// hook 传参并return返回值
Java.perform(function () {
result = Java.use('com.jx885.library.http.network.HttpUtils').getStringMD5toUpperCase(s)
})
return result
}
rpc.exports = {
getsign:sign
}
adb 命令
# adb 连接 (手机需开启开发者模式 vmos虚拟机需开启开发者模式连接adb)
adb connect ip:端口
# adb 查看连接设备
adb devices
# adb 安装apk文件推送到手机
adb install apk路径
# adb 本地文件推送到手机
adb pull 本地文件路径 手机路径
# 多台设备是 暂时使用其中一台
adb -s 设备名称/ip:端口 adb命令
# 多台设备 删除无用设备
adb -s xxx kill-server
# 设置端口
adb forward tcp:27042 tcp:27042
# 小米5x 下载路径地址
/storage/emulated/0/Download/
# 查看已安装apk的包名 非adb进入下
frida-ps -Uai