记一次双向认证绕过

admin 2025年3月17日09:37:47评论4 views字数 2427阅读8分5秒阅读模式

前言

某次金融App测试,进行抓包时发现只能抓到请求包,不进行抓包是可以正常使用的,推测使用了双向认证,第一次遇到,折腾了好久终于绕过去了,简单记录一下解决过程。

0X01抓包分析

单向校验:客户端校验服务端证书

双向校验:在单向校验的基础上增加了服务端对客户端的校验

使用BurpSuite进行抓包,可直接抓取请求包,但是没有返回包,猜测是服务端对客户端证书做了校验,burp的证书不合法所以无法接受返回包

记一次双向认证绕过

0X02寻找证书

解压安装包,寻找是否有.p12/.fpx/.pem等文件

解压apk包,搜索发现存在多个p12证书

记一次双向认证绕过

利用openssl简单验证下是否存在空密码、弱密码(123456password等)等情况

openssl pkcs12 -info -in xxxx.p12

经过测试发现有三个证书使用了123456弱密码,依次导入BurpSuite中验证发现还是无法抓到返回包还剩一个xxx.com.p12文件密码未发现弱密码,文件名正好和抓包的host一致,校验的证书应该就是这个了,接下来只能通过逆向Hook去获取密码了

0X03寻找密码

定位证书加载入口

反编译apk,全局搜索证书文件名字,无果

记一次双向认证绕过

搜一下.p12后缀,定位到相关代码

记一次双向认证绕过

定位到关键代码

记一次双向认证绕过

利用AI简单分析下initClientKeyFileMap() 方法用于构建一个 mClientKeyFileMap 哈希表,使用HashMap存储主机名和对应的 .p12 文件,用于 SSL/TLS 双向认证场景中客户端密钥与证书的匹配。

追踪证书加载流程

查找用例,继续分析

记一次双向认证绕过
记一次双向认证绕过

上述代码初始化了一个HTTP客户端,并构建一个包含主机名与对应 HTTP 客户端实例的映射表mHttpClientMap 。同时,该方法还利用 mClientKeyFileMap (由 initClientKeyFileMap 方法初始化)中的密钥文件信息,为特定主机配置 SSL/TLS 双向认证的客户端

关键代码:

b0.a createHttpClientBuilder = createHttpClientBuilder();createHttpClientBuilder.Q0(b1.a.a(App.j().getAssets().open(value),EncryptNDK.a().getValue(value)), b1.a.b());

在 Q0 方法中, SSLSocketFactory 的初始化依赖证书和密码(见 b1.a.a(...) 调用)

调用链示例:

initClientKeyFileMap() → createHttpClientBuilder() → Q0(sslFactory,trustManager)

记一次双向认证绕过

b1.a.a 方法

  • 输入参数

CibApp.j().getAssets().open(value) :从 Android 应用的 assets 目录加载 .p12 证书文件输入流。

EncryptNDK.a().getValue(value) :通过 EncryptNDK.a().getValue(value) 获取密码,用于保护 .p12 文件。

  • 输出:返回包含客户端证书和私钥的 KeyStore 对象,用于构建 SSL 上下文

记一次双向认证绕过

继续查找用例

记一次双向认证绕过

定位到关键代码,使用 EncryptNDK.a().getValue(str) 方法处理得到密码, str 为主机名拼接 .p12 ,刚好为本地找到的那个p12证书文件名

记一次双向认证绕过

跟踪 EncryptNDK.a().getValue(str) 方法发现为native方法,so层不太会,先使用frida直接Hook试试

记一次双向认证绕过

脚本:

Java.perform(function () {let EncryptNDK = Java.use("com.xxxx.EncryptNDK");EncryptNDK["getValue"].implementation = function (str) {console.log(`EncryptNDK.getValue is called: str=${str}`);let result = this["getValue"](str);console.log(`EncryptNDK.getValue result=${result}`);return result;};});

Hook结果为SM4算法的keyiv,不是我想要的密码

记一次双向认证绕过

猜测使用SM4str进行加密得到密码,手动加密进行验证,发现密码无效

记一次双向认证绕过

到这一步有点僵住了,硬着头皮看了半天so,最后还是没搞明白

这个时候我想到了frida主动调用,不会写怎么办,交给AI

记一次双向认证绕过

脚本:

Java.perform(() => {// 严格匹配类路径const EncryptNDK = Java.use("com.xxxx.EncryptNDK");// 构造固定参数(用户明确传入的 str 值)const str = "xxxx.p12";// 调用单例方法 a() 获取实例const instance = EncryptNDK.a();12345678910Hook结果:qwe1230x04 抓包验证导入证书// 主动调用 getValue() 并输出结果const encryptedPassword = instance.getValue(str);console.log(`[*] P12 证书密码加密结果: ${encryptedPassword}`);});

Hook结果:qwe123

记一次双向认证绕过

0X04抓包验证

导入证书

记一次双向认证绕过
记一次双向认证绕过

成功抓包

记一次双向认证绕过

总结

感兴趣的可以公众号回答回复"深情哥"进群,有公开课会在群里面通知,包括审计和src。edu邀请码获取也可以联系深情哥。

内部edu+src培训,包括src挖掘,edu挖掘,小程序逆向,js逆向,app渗透,导师是挖洞过30w的奥特曼,edu上千分的带头大哥!!!联系深情哥即可。

记一次双向认证绕过

原文始发于微信公众号(实战安全研究):记一次双向认证绕过

免责声明:文章中涉及的程序(方法)可能带有攻击性,仅供安全研究与教学之用,读者将其信息做其他用途,由读者承担全部法律及连带责任,本站不承担任何法律及连带责任;如有问题可邮件联系(建议使用企业邮箱或有效邮箱,避免邮件被拦截,联系方式见首页),望知悉。
  • 左青龙
  • 微信扫一扫
  • weinxin
  • 右白虎
  • 微信扫一扫
  • weinxin
admin
  • 本文由 发表于 2025年3月17日09:37:47
  • 转载请保留本文链接(CN-SEC中文网:感谢原作者辛苦付出):
                   记一次双向认证绕过https://cn-sec.com/archives/3847802.html
                  免责声明:文章中涉及的程序(方法)可能带有攻击性,仅供安全研究与教学之用,读者将其信息做其他用途,由读者承担全部法律及连带责任,本站不承担任何法律及连带责任;如有问题可邮件联系(建议使用企业邮箱或有效邮箱,避免邮件被拦截,联系方式见首页),望知悉.

发表评论

匿名网友 填写信息