可能重复:为什么Google会在(1)之前添加;他们的JSON回复?
Google会像这样返回json:
throw 1; <dont be evil> { foo: bar}
和Facebook的ajax有这样的json:
for(;;); {"error":0,"errorSummary": ""}
-
为什么他们放置会停止执行的代码并生成无效的json?
-
如果它无效,它们如何解析它,如果你试图评估它会崩溃?
-
他们只是从字符串中删除它(看起来很贵)?
-
这有什么安全优势吗?
为了安全起见,它是为了回应:
如果刮刀在另一个域上,则必须使用 script
标记来获取数据,因为XHR不能跨域工作 . 即使没有 for(;;);
攻击者如何获取数据?它只是被垃圾收集,因为它没有引用它?
基本上,为了获得数据跨域,他们必须这样做
<script src="http://target.com/json.js"></script>
但即使没有安装崩溃脚本,攻击者也无法使用任何Json数据而不将其分配给您可以全局访问的变量(在这些情况下不是这样) . 崩溃代码没有任何效果,因为即使没有它,他们也必须使用服务器端脚本来使用其站点上的数据 .
4 回答
攻击基于改变内置类型的行为,特别是
Object
和Array
,通过改变它们的构造函数或它的prototype
. 然后,当目标JSON使用{...}
或[...]
构造时,它们会自己拥有这些对象的版本,并且可能会出现意外行为 .例如,你可以将一个setter-property破解成
Object
,这会背叛用对象文字写的值:然后当
<script>
指向某个使用该属性名称的JSON时:值
"hello"
将被泄露 .数组和对象文字导致调用setter的方式是有争议的 . 为了响应对高知名度网站的公开攻击,Firefox删除了3.5版中的行为 . 然而在撰写本文时,Safari(4)和Chrome(5)仍然容易受到攻击 .
所有浏览器现在都不允许的另一个攻击是重新定义构造函数:
目前,IE8的属性实现(基于ECMAScript第五版标准和
Object.defineProperty
)目前不适用于Object.prototype
或Array.prototype
.但是,除了保护过去的浏览器之外,JavaScript的扩展可能会在未来导致类似类型的更多潜在泄漏,在这种情况下,箔条也应该防范这些泄漏 .
考虑一下,在检查您的GMail帐户后,您将访问我的恶意页面:
现在将会发生的是,来自谷歌的Javascript代码 - 提问者认为是良性且立即超出范围 - 实际上将被发布到我的邪恶网站 . 假设脚本标记中请求的URL发送(因为您的浏览器将显示正确的cookie,Google会正确地认为您已登录到您的收件箱):
现在,我将把这个对象的序列化版本发布到我的邪恶服务器上 . 谢谢!
防止这种情况发生的方法是摧毁您的JSON响应,并在您从同一域中操作该数据时将其解除 . 如果你喜欢这个答案,请接受bobince发布的那个 .
EDIT
这些字符串通常称为"unparseable cruft",它们用于修补影响JSON规范的信息泄漏漏洞 . 这次攻击是现实世界和a vulnerability in gmail was discovered by Jeremiah Grossman . Mozilla也认为这是JSON规范中的一个漏洞,它已经patched in Firefox 3 . 但是,由于此问题仍会影响其他浏览器,因此需要使用"unparseable cruft",因为它是兼容的修补程序 .
Bobice的回答是对此攻击的技术解释,这是正确的 .
这是一个功能,如果你尝试
eval
它会崩溃 .eval
允许任意JavaScript代码,可用于跨站点脚本攻击 .我想是这样的 . 可能类似于:
"don't be evil" cruft阻止开发人员直接使用
eval
而不是更安全的替代方案 .