Android移动安全第十一章_SSRF与网络安全
字数 4044
更新时间 2026-05-22 12:39:33
Android移动安全第十一章:SSRF原理、危害与防护
1. SSRF 概述
SSRF(Server-Side Request Forgery,服务端请求伪造)是一种经典的安全漏洞。其核心是攻击者能够利用服务器(在Android场景中,是客户端App)作为代理,向任意目标发起网络请求。在Android移动安全领域,SSRF问题的本质是:App在根据外部输入(如用户输入、Intent数据、剪切板、扫描结果等)构造网络请求时,如果未能对目标URL进行充分的校验和过滤,攻击者就可以操控App去访问本不应被访问的网络资源。
2. Android SSRF 与 Web SSRF 的异同
虽然SSRF概念源于Web安全,但在Android客户端中,其表现形式和利用场景存在显著差异:
-
相同点:
- 核心漏洞原理相同:都是利用“服务器”(在Android中,发起请求的主体是App进程)去发起非预期的网络请求。
- 危害的本质相似:都可能用于访问内网服务、探测端口、攻击本地应用或第三方服务。
-
不同点:
- 攻击面与触发点:
- Web SSRF:通常由服务端代码(如PHP的
file_get_contents()、curl等)处理用户可控的URL参数触发。 - Android SSRF:触发点更为多样,包括:
- WebView:通过
WebViewClient.shouldOverrideUrlLoading或WebViewClient.shouldInterceptRequest加载攻击者控制的URL。 - 深度链接(Deep Links)与 App Links:通过
<intent-filter>定义的Scheme或HTTP/HTTPS链接,传递恶意URL给App处理。 - Intent:通过
Intent.setData(Uri)传递一个包含URL的Uri,被目标组件的onCreate或onHandleIntent等方法解析并使用。 - 文件协议:处理
file://、content://等协议时,可能导致本地文件读取或跨应用资源访问。 - 第三方SDK:广告、分享、统计等SDK在请求其服务器时,如果参数可控,可能成为SSRF的跳板。
- WebView:通过
- Web SSRF:通常由服务端代码(如PHP的
- 请求上下文:
- Web SSRF:请求从服务器IP发出,带有服务器的网络权限和身份。
- Android SSRF:请求从用户设备的App发出,携带该App的权限、Cookie、认证令牌、客户端证书、用户代理(UA) 等。这使得Android App可能成为一个“特权”的请求发起者,可以访问一些对普通网络请求不可见但对App开放的内网接口或云服务API。
- 可利用的协议:
- Android支持多种URI Scheme,除了常见的
http(s)://,还可能包括file://、content://、ftp://等,攻击者可利用这些协议进行更广泛的攻击,如读取本地敏感文件、访问Content Provider等。
- Android支持多种URI Scheme,除了常见的
- 攻击面与触发点:
3. Android SSRF 的主要危害
-
内网资产探测与攻击:
- 攻击者可以利用存在漏洞的App作为跳板,扫描和访问移动设备所在内网(如Wi-Fi网络)中的其他设备和服务(如路由器管理界面、打印机、NAS、数据库、Redis等),绕过网络边界防护。
-
访问本地服务(Localhost):
- Android设备上运行着许多本地服务(监听在
127.0.0.1或localhost)。通过SSRF,攻击者可以操控App访问这些服务,例如:http://127.0.0.1:8080/(可能存在的开发调试服务)http://localhost:6379/(可能存在的Redis服务)- 这可用于信息泄露、甚至远程代码执行(如果本地服务存在漏洞)。
- Android设备上运行着许多本地服务(监听在
-
利用App身份访问受限API:
- 这是Android SSRF最具威胁的场景之一。许多App在发起请求时会自动携带用于身份认证的Token、Cookie或Session。攻击者通过SSRF,可以让App以自己的“合法身份”去访问其后台系统的内部API、管理接口或其他本应受权限控制的端点,从而进行越权操作、窃取敏感数据。
-
协议滥用与文件读取:
- 通过
file://协议,尝试读取App沙箱内或系统敏感文件(如/proc/self/cmdline、/etc/hosts等)。 - 通过
content://协议,攻击其他应用的Content Provider,可能导致敏感数据泄露。
- 通过
-
作为其他攻击的跳板:
- 结合其他漏洞(如URL解析差异、重定向、CRLF注入等),可以扩大攻击影响,例如实现反射型XSS(如果响应在WebView中渲染)或服务器端请求伪造链。
4. Android SSRF 漏洞挖掘与检测
-
静态分析:
- 搜索关键API:在代码中搜索网络请求相关的类和方法,如
HttpURLConnection、OkHttpClient、HttpClient、WebView.loadUrl、Intent.parseUri等。 - 跟踪数据流:分析用户可控的输入源(如
getIntent().getData()、getIntent().getStringExtra()、SharedPreferences、剪切板、扫描二维码结果等)是否最终流入上述网络请求API的URL参数中。 - 检查校验逻辑:查看在拼接或使用URL前,是否存在严格的白名单校验、黑名单过滤、域名解析与重定向控制等防护代码。常见的缺陷包括仅检查URL是否以
http://或https://开头,而忽略了其中可能包含的@、#、?等用于绕过检查的字符。
- 搜索关键API:在代码中搜索网络请求相关的类和方法,如
-
动态测试与Fuzzing:
- 使用代理工具:配置设备代理(如Burp Suite、Fiddler),监控App的所有网络请求。尝试修改请求参数、路径,观察App是否向非预期的地址发起请求。
- 构造恶意Payload:在可控制的输入点(如Deep Link、Intent参数、表单输入)尝试注入以下类型的URL:
- 内网地址:
http://192.168.1.1/admin - 本地回环:
http://127.0.0.1:8080 - 域名重绑定:利用DNS重绑定技术,使一个域名在解析时先返回一个合法IP通过校验,随后解析为内网IP。
- 特殊格式绕过:
http://attacker.com@192.168.1.1、http://attacker.com#@192.168.1.1、http://012.0.0.1(八进制IP)、http://0x7f.0.0.1(十六进制IP)。 - 非HTTP协议:
file:///etc/passwd、gopher://、dict://(取决于底層库的支持情况)。
- 内网地址:
5. Android SSRF 防护方案
-
输入校验与白名单机制:
- 强白名单校验:对用户输入的URL,不仅校验协议,更要校验主机名(host)和端口。建立一个允许访问的域名或IP地址白名单,只有完全符合白名单规则的请求才被允许执行。这是最有效的防护手段。
- 避免黑名单:不要仅依赖黑名单过滤(如禁止
10.0.0.0/8、192.168.0.0/16、127.0.0.0/8、172.16.0.0/12、0.0.0.0、localhost等),攻击者很容易通过进制转换、域名重绑定、指向攻击者控制的公网服务器再跳转等方式绕过。
-
统一网络请求网关:
- 在App内封装一个统一的、安全的网络请求模块。所有外部发起的网络请求都必须通过此模块,在该模块中集中实施URL校验、日志记录和访问控制策略。
-
禁用危险的协议和重定向:
- 根据业务需求,明确只允许
http://和https://协议,禁用file://、ftp://、gopher://、dict://等不必要的协议。 - 严格控制HTTP重定向。对于服务器返回的
3xx状态码,应校验重定向目标URL,防止跳转到内网地址。
- 根据业务需求,明确只允许
-
使用安全的URL解析库:
- 使用
java.net.URI而不是java.net.URL进行解析,因为URI更严格。在获取host之前,确保对URL进行规范化(canonicalization),防止利用@、#等符号的绕过。 - 示例:
public static String getHost(String urlString) { try { URI uri = new URI(urlString); String host = uri.getHost(); if (host != null) { return host.toLowerCase(); } } catch (URISyntaxException e) { // 处理异常,拒绝请求 } return null; }
- 使用
-
最小权限原则:
- App的网络权限应遵循最小化原则。如果业务不需要访问内网,可以考虑在AndroidManifest.xml中或通过网络安全配置限制网络访问范围(但这并非绝对可靠,需要结合代码层防护)。
-
对深度链接和Intent的防护:
- 在接收
Intent的Activity或Service中,对Intent.getData()获取的Uri进行严格校验,确认其主机和路径符合预期。 - 对于导出的组件,要特别小心,避免未授权访问。
- 在接收
-
服务端协同防护:
- 服务端API在设计时,应避免将内部、管理或敏感接口直接暴露给客户端App,或至少实施严格的IP白名单、二次认证等机制。
- 服务端不应信任客户端传来的完整URL进行跳转或请求,应只接收相对路径或资源ID,由服务端自己拼接完整的内部URL。
6. 总结
Android中的SSRF漏洞将移动客户端App转变为一个潜在的网络攻击代理,其危害因App自身的权限和上下文而放大。防御Android SSRF需要开发者建立“绝不信任任何外部输入URL”的安全意识,在客户端实施以白名单校验为核心的多层防护策略,并结合安全的编码实践和严格的组件暴露控制,才能有效降低风险。在移动应用安全测试中,SSRF应作为一项重要的检测项,通过动静结合的方法进行深度挖掘。
相似文章
相似文章