快速掌握任意 Android 应用的抓包

抓包是流量分析的基础,也是安全研究重要的一环。抓包软件有很多种,如 Burpsuite、mitmproxy 以及 Fiddle,抓包方式常见的有设置系统代理、AP 热点抓包、透明代理等。不同方式有不同优缺点,也有不同的应用场景。相信很多安全研究者一定会遇到各种无法抓取流量的问题,本次就来简单总结一下 Android 环境中常用的抓包技术,包括一些应用常用的 SSLpinning、不走系统代理等对抗逆向技术。

这里不会重复搬运大部分博客已经总结过的抓包原理和经验,主要是想总结一下如何抓取任意应用的流量包,按照常规思路,假设现在我们想抓取某个应用的流量。

本文总结了如下 4 种抓包方案:

  1. 设置系统代理,即传统中间人代理方法
  2. 利用 iptables 三层网络流量路由
  3. r0capture HOOK 抓包
  4. eCapture ,基于 eBPF 技术实现的抓包软件

1 设置系统代理

设置系统代理是最为常见的一种方法,Android 提供了相应的设置功能,将系统代理指向 Burpsuite 所在的 IP 地址,即可使用 Burpsuite 抓取流量。抓包步骤如下:

这种方式可以解决部分应用的抓包问题,但是如今很多应用使用了 SSL Pinning,即证书绑定,应用只会信任自己本地绑定的证书,并不会信任系统根证书,也就是即使导入了 CA,仍然可能无法抓包。

OWASP 安全验证标准中,将对抗逆向称之为韧性要求,属于额外的管控方法,根据应用敏感性,开发者选择需不需要添加。而 SSL Pinning 就属于对抗逆向的一种手段。

2 利用 iptables 设置透明代理

尽管绕过了 SSL pinning,仍然有可能无法抓到 App 的流量,这是因为应用开发者完全可以不使用系统或其他的 HTTP 库,不理睬系统变量如 HTTP_PROXY,也就是应用不会理会我们设置的系统代理。这个时候就可以使用终极方法了,iptables + Burpsuite 透明代理,步骤如下:

iptables 是一个在应用层实现内核框架 Netfilter 的工具,常见于防火墙配置,而 Netfilter 是内核处理网络数据包的模块。

通过如下命令,即可将内核 OUTPUT 数据转发到我们的目标设备上。

D:\> adb shell iptables -t nat -A OUTPUT -p tcp -j DNAT --to-destination 127.0.0.1:8080

此时再利用 adb 反向代理功能,将 Android 手机某个网卡流量通过 adb 的方式转发到我们使用的 PC 上。

D:\> adb reverse tcp:8080 tcp:8080

设置 Burpsuite 透明代理即可抓包。

扫描二维码关注公众号,回复: 17282208 查看本文章

Burpsuite设置透明代理

当然,也可以指定抓包特定应用,加入如下 iptables 参数即可

-m owner --uid-owner 4000

参数简介

iptables [-t table] {
    
    -A|-C|-D} chain rule-specification
-t nat,设置iptables表为网络地址地址转发
-A Append,附加后续规则到相应的表上
chain, PREROUTING/INPUT/OUTPUT/POSTROUTING,来源于内核中的Netfilter模块,OUTPUT表示所有从本地发往远端的数据包
rule-specification, -j DNAT, 修改数据包的目标地址

adb reverseadb forward 的区别就是,前者是反向代理,后者是正向代理,前者是将所有手机流量导入到 PC,后者是将所有 PC 流量导入到手机。

关于 iptables 的原理以及更多配置,透明代理入门iptables在Android抓包中的妙用 等文章已经给了很好的解释,不再赘述。frida-skeleton 就是一个典型的使用 iptables 抓包的工具,但是如果只是抓包,可能用不到 skeleton,且此工具在不同环境下兼容性一般,可能会出现一些奇怪的问题。

3 r0capture hook 抓包

r0capture 是一个典型的通过 hook SSL 类库实现抓包的工具。既然是 hook,离不开 Frida。

下载脚本

git clone https://github.com/r0ysue/r0capture.git

Attach 模式

python3 r0capture.py -U com.qiyi.video -v -p iqiyi.pcap

Spawn 模式

python3 r0capture.py -U -f com.qiyi.video -v

经过实际测试,虽然工具声称是安卓应用层抓包通杀脚本,无需考虑证书,但是还是有很多厂商的应用数据包无法解密。

在这里插入图片描述

4 基于 eBPF 技术实现的 eCapture

同样,eCapture 也是一个无需 CA 证书抓 https网络明文通讯的工具。直接下载编译好的二进制,放到 Android 设备上,即可使用。

./ecapture tls -i eth0 -w pcapng -p 443

由于 eCapture 基于 eBPF,需要内核支持该特性,依赖系统内核是否支持 eBPF。目前支持在操作系统上,支持了 X86_64\ARM64 的 Linux kernel 4.18以 上内核,支持了 ARM64 Android(Linux) kernel 5.4 以上版本。

绕过 SSL Pinning

在设置系统代理抓包无果后,需要继续尝试 SSL Pinning 绕过。绕过证书绑定并不难,但是需要有系统 root 权限,使用 Frida 对相应校验证书的函数进行 Hook。已有多个现成的 Frida 脚本 可以解决此问题,以下是一个简单示例。

// $ frida --codeshare pcipolloni/universal-android-ssl-pinning-bypass-with-frida -f YOUR_BINARY
setTimeout(function(){
    
    
    Java.perform(function (){
    
    
    	console.log("");
	    console.log("[.] Cert Pinning Bypass/Re-Pinning");

	    var CertificateFactory = Java.use("java.security.cert.CertificateFactory");
	    var FileInputStream = Java.use("java.io.FileInputStream");
	    var BufferedInputStream = Java.use("java.io.BufferedInputStream");
	    var X509Certificate = Java.use("java.security.cert.X509Certificate");
	    var KeyStore = Java.use("java.security.KeyStore");
	    var TrustManagerFactory = Java.use("javax.net.ssl.TrustManagerFactory");
	    var SSLContext = Java.use("javax.net.ssl.SSLContext");

	    // Load CAs from an InputStream
	    console.log("[+] Loading our CA...")
	    var cf = CertificateFactory.getInstance("X.509");
	    
	    try {
    
    
	    	var fileInputStream = FileInputStream.$new("/data/local/tmp/cert-der.crt");
	    }
	    catch(err) {
    
    
	    	console.log("[o] " + err);
	    }
	    
	    var bufferedInputStream = BufferedInputStream.$new(fileInputStream);
	  	var ca = cf.generateCertificate(bufferedInputStream);
	    bufferedInputStream.close();

		var certInfo = Java.cast(ca, X509Certificate);
	    console.log("[o] Our CA Info: " + certInfo.getSubjectDN());

	    // Create a KeyStore containing our trusted CAs
	    console.log("[+] Creating a KeyStore for our CA...");
	    var keyStoreType = KeyStore.getDefaultType();
	    var keyStore = KeyStore.getInstance(keyStoreType);
	    keyStore.load(null, null);
	    keyStore.setCertificateEntry("ca", ca);
	    
	    // Create a TrustManager that trusts the CAs in our KeyStore
	    console.log("[+] Creating a TrustManager that trusts the CA in our KeyStore...");
	    var tmfAlgorithm = TrustManagerFactory.getDefaultAlgorithm();
	    var tmf = TrustManagerFactory.getInstance(tmfAlgorithm);
	    tmf.init(keyStore);
	    console.log("[+] Our TrustManager is ready...");

	    console.log("[+] Hijacking SSLContext methods now...")
	    console.log("[-] Waiting for the app to invoke SSLContext.init()...")

	   	SSLContext.init.overload("[Ljavax.net.ssl.KeyManager;", "[Ljavax.net.ssl.TrustManager;", "java.security.SecureRandom").implementation = function(a,b,c) {
    
    
	   		console.log("[o] App invoked javax.net.ssl.SSLContext.init...");
	   		SSLContext.init.overload("[Ljavax.net.ssl.KeyManager;", "[Ljavax.net.ssl.TrustManager;", "java.security.SecureRandom").call(this, a, tmf.getTrustManagers(), c);
	   		console.log("[+] SSLContext initialized with our custom TrustManager!");
	   	}
    });
},0);

当然,笔者正常使用的方法是在 Linux 环境中,直接使用 objection,已经集成了绕过 SSL pinning 等多个有用的 Frida 脚本,两行脚本搞定 SSL Pinning。

objection -g com.android.phone explore
Using USB device `Android Emulator 5554`
Agent injected and responds ok!

     _   _         _   _
 ___| |_|_|___ ___| |_|_|___ ___
| . | . | | -_|  _|  _| | . |   |
|___|___| |___|___|_| |_|___|_|_|
      |___|(object)inject(ion) v1.11.0

     Runtime Mobile Exploration
        by: @leonjza from @sensepost

[tab] for command suggestions
com.android.phone on (Android: 11) [usb] # android sslpinning disable

总结

不同抓包方案各有利弊,如果你只是想抓所有应用的 HTTPS 报文,使用 iptables 路由转发可以解决绝大多数 HTTPS 抓包问题,且没有环境依赖;如果你拥有最新版本 Android,内核大于 5.4,那么可以直接使用 eCapture;如果你还想抓其他应用层协议报文,例如 Smtp,那么可以使用 r0capture。方案对比如下

抓包方案 HTTPS 其他应用层协议 上手难度 依赖工具 缺点
设置系统代理 部分 不支持 容易 Burpsuite 某些应用不使用系统代理,无法抓包
iptables 路由转发 全部 不支持 容易 Burpsuite
r0capture hook 抓包 部分 支持 容易 Wireshark 数据包部分混乱,缺失
基于 eBPF 技术实现的 eCapture 全部 不支持 容易 Wireshark 需要高版本内核支持

撰写本文最大目的在于,让我们快速掌握任意 Android 应用的抓包,因为现实场景中,往往会遇到常规方法无法抓包的问题。而只需要通过 iptables 即可解决绝大多数问题。除了设置系统代理、iptables路由转发,还可以通过 tcpdump + keylog 以及 SSL read/write 的方式,但是这两种都需要 Hook,因此,对于大多数安全研究者来说,掌握 iptables 设置透明代理的方式就足够了。

参考文献

  1. 终端应用安全之网络流量分析
  2. 快应用调试器研究1:前置知识
  3. 透明代理入门
  4. iptables在Android抓包中的妙用
  5. android手机安装burp证书
  6. 从原理到实战,全面总结 Android HTTPS 抓包
  7. Frida CodeShare

猜你喜欢

转载自blog.csdn.net/song_lee/article/details/128847729
今日推荐