猿人学2022安卓逆向对抗比赛第三题分析
1.charles 抓包工具2.pixelxl 真机3.jadx4.本机安装 python 和 frida第三题依旧是计算 1~100也的数值之和通过抓包可以 获取到 post 提交的路径post form 表单数据有两个参数直接 搜索 /app3可以获取到 唯一匹配值然后 依旧是 双击进入,找到 url路由定义的类右键 查找 用例可以看到有三个前两个是一样的,直接第一个双击进入可以看到一个 cr
第一步 准备工具
1.charles 抓包工具
2.pixelxl 真机
3.jadx
4.本机安装 python 和 frida
抓包分析数据
第三题依旧是计算 1~100也的数值之和

通过抓包可以 获取到 post 提交的路径
https://appmatch.yuanrenxue.com/app3
post form 表单数据 有两个参数

m 为 加密的数据
page 为 页数
jadx 分析
直接 搜索 /app3 可以获取到 唯一匹配值

然后 依旧是 双击进入,找到 url 路由定义的类

右键 查找 用例 可以看到有三个
前两个是一样的,直接第一个双击进入

可以看到一个 crypto 加密方法 直接 Ctrl + 鼠标左键进入

发现 也是一个 so 层的加密函数 ,那么 和 第二题一样,直接 frida hook 一下这个 函数 ,查看一下 函数 传入的值是啥
注意一点,这里有两个参数 ,一个是String 一个是long
所以在 hook的时候,记住 加入 overload
代码如下
function main(){
console.log("hooking.......")
Java.perform(function(){
var crypto = Java.use("com.yuanrenxue.match2022.fragment.challenge.ChallengeThreeFragment");
crypto.crypto.overload('java.lang.String', 'long').implementation = function(arg1,arg2){
console.log("args1=>",arg1);
console.log("args2=>",arg2);
var result = this.crypto(arg1,arg2);
console.log(result);
return result;
}
});
}
setImmediate(main);

可以看到的是
arg1 => 0051657273703000
args2=> 1657273703000
可以猜一下
arg1 应该是 005 的page 页数 + 13位的时间戳
arg2 就是13为的时间戳
可以重新在滑动一下手机,跳转到第六页试试看

欸,好像没毛病!
那么就简单了,我们主动调用试试看
主动调用
代码如下
function invokesign(str,long){
var result = null;
Java.perform(function(){
Java.choose("com.yuanrenxue.match2022.fragment.challenge.ChallengeThreeFragment",{
onMatch:function(ins){
console.log('ins=>',ins);
result = ins.crypto(str,long);
console.log("result=>",result);
},onComplete(){}
})
});
return result;
}
效果如下

欸,好像没啥问题,那么就直接 rpc 一波试试看
frida rpc 调用
代码如下
function main(){
console.log("hooking.......")
Java.perform(function(){
var crypto = Java.use("com.yuanrenxue.match2022.fragment.challenge.ChallengeThreeFragment");
crypto.crypto.overload('java.lang.String', 'long').implementation = function(arg1,arg2){
console.log("args1=>",arg1);
console.log("args2=>",arg2);
var result = this.crypto(arg1,arg2);
console.log(result);
return result;
}
});
}
setImmediate(main);
//invokesign("0041657273677000",1657273677000)
function invokecrypto(str,long){
var result = null;
Java.perform(function(){
Java.choose("com.yuanrenxue.match2022.fragment.challenge.ChallengeThreeFragment",{
onMatch:function(ins){
console.log('ins=>',ins);
result = ins.crypto(str,long);
console.log("result=>",result);
},onComplete(){}
})
});
return result;
}
rpc.exports = {
invokecrypto:invokecrypto,
}
python 代码如下
import time
import frida
import requests
from requests.packages import urllib3
urllib3.disable_warnings()
def my_message_handler(message, payload):
print("message=>",message)
print("payloa=>d",payload)
# connect wifiadb
device = frida.get_device_manager().add_remote_device("192.168.0.102:8888")
print('设备=>',device)
session = device.attach("com.yuanrenxue.match2022")
print('session=>',session)
# load script
with open("app3.js") as f:
script = session.create_script(f.read())
script.on("message", my_message_handler)
script.load()
# script.exports.invokecrypto("0041657273677000",1657273677000)
def get_url():
num = 0
for i in range(1,101):
url = 'https://appmatch.yuanrenxue.com/app3'
headers = {
'accept-language': 'zh-CN,zh;q=0.8',
'user-agent': 'Mozilla/5.0 (Linux; U; Android 8.1.0; zh-cn; Pixel XL Build/OPM1.171019.011) AppleWebKit/534.30 (KHTML, like Gecko) Version/4.0 Mobile Safari/534.30',
'content-type': 'application/x-www-form-urlencoded',
'accept-encoding': 'gzip',
'cache-control': 'no-cache'
}
data = {
'page':str(i),
}
ts = int(time.time())*1000
if i <10:
data['m'] = script.exports.invokecrypto(str('00'+str(i)+str(ts)),ts)
elif 10 <=i and i <100:
data['m'] = script.exports.invokecrypto(str('0'+str(i)+str(ts)),ts)
elif i >= 100:
data['m'] = script.exports.invokinvokecryptoesign(str(str(i)+str(ts)),ts)
print('data->',data)
response = requests.post(url,headers=headers,data=data,verify=False)
print(response.text)
value_data = response.json()
for value in value_data['data']:
num += int(value['value'])
print(num)
time.sleep(1)
# print(num)
if __name__ == '__main__':
get_url()
最终的效果


总结
so 层的混淆和 不混淆 其实 不太重要,只要是静态注册的,就可以直接通过hook java的 静态的注册的方法 找到函数 传入的数据进行分析
然后直接进行主动调用即可,不需要管SO层里面的算法进行了多么离谱的混淆加密
更多推荐



所有评论(0)