HTML5技术

【前端安全】JavaScript防http劫持与XSS - ChokCoco(4)

字号+ 作者:H5之家 来源:博客园 2016-08-19 17:00 我要评论( )

重写Element.prototype.setAttribute,就是首先保存原有接口,然后当有元素调用 setAttribute 时,检查传入的 src 是否存在于白名单中,存在则放行,不存在则视为可疑元素,进行上报并不予以执行。最后对放行的元素

重写 Element.prototype.setAttribute ,就是首先保存原有接口,然后当有元素调用 setAttribute 时,检查传入的 src 是否存在于白名单中,存在则放行,不存在则视为可疑元素,进行上报并不予以执行。最后对放行的元素执行原生的 setAttribute ,也就是 old_setAttribute.apply(this, arguments);。

上述的白名单匹配也可以换成黑名单匹配。

  重写嵌套 iframe 内的 Element.prototype.setAttribute

当然,上面的写法如果 old_setAttribute = Element.prototype.setAttribute 暴露给攻击者的话,直接使用old_setAttribute 就可以绕过我们重写的方法了,所以这段代码必须包在一个闭包内。

当然这样也不保险,虽然当前窗口下的 Element.prototype.setAttribute 已经被重写了。但是还是有手段可以拿到原生的 Element.prototype.setAttribute ,只需要一个新的 iframe 。

var newIframe = document.createElement('iframe'); document.body.appendChild(newIframe); Element.prototype.setAttribute = newIframe.contentWindow.Element.prototype.setAttribute;

通过这个方法,可以重新拿到原生的 Element.prototype.setAttribute ,因为 iframe 内的环境和外层 window 是完全隔离的。wtf?

怎么办?我们看到创建 iframe 用到了 createElement,那么是否可以重写原生 createElement 呢?但是除了createElement 还有 createElementNS ,还有可能是页面上已经存在 iframe,所以不合适。

那就在每当新创建一个新 iframe 时,对 setAttribute 进行保护重写,这里又有用到 MutationObserver :

/** * 使用 MutationObserver 对生成的 iframe 页面进行监控, * 防止调用内部原生 setAttribute 及 document.write * @return {[type]} [description] */ function defenseIframe() { // 先保护当前页面 installHook(window); } /** * 实现单个 window 窗口的 setAttribute保护 * @param {[BOM]} window [浏览器window对象] * @return {[type]} [description] */ function installHook(window) { // 重写单个 window 窗口的 setAttribute 属性 resetSetAttribute(window); // MutationObserver 的不同兼容性写法 var MutationObserver = window.MutationObserver || window.WebKitMutationObserver || window.MozMutationObserver; // 该构造函数用来实例化一个新的 Mutation 观察者对象 // Mutation 观察者对象能监听在某个范围内的 DOM 树变化 var observer = new MutationObserver(function(mutations) { mutations.forEach(function(mutation) { // 返回被添加的节点,或者为null. var nodes = mutation.addedNodes; // 逐个遍历 for (var i = 0; i < nodes.length; i++) { var node = nodes[i]; // 给生成的 iframe 里环境也装上重写的钩子 if (node.tagName == 'IFRAME') { installHook(node.contentWindow); } } }); }); observer.observe(document, { subtree: true, childList: true }); } /** * 重写单个 window 窗口的 setAttribute 属性 * @param {[BOM]} window [浏览器window对象] * @return {[type]} [description] */ function resetSetAttribute(window) { // 保存原有接口 var old_setAttribute = window.Element.prototype.setAttribute; // 重写 setAttribute 接口 window.Element.prototype.setAttribute = function(name, value) { ... }; } 

我们定义了一个 installHook 方法,参数是一个 window ,在这个方法里,我们将重写传入的 window 下的 setAttribute ,并且安装一个 MutationObserver ,并对此窗口下未来可能创建的 iframe 进行监听,如果未来在此 window 下创建了一个 iframe ,则对新的 iframe 也装上 installHook 方法,以此进行层层保护。

  重写 document.write

根据上述的方法,我们可以继续挖掘一下,还有什么方法可以重写,以便对页面进行更好的保护。

document.write 是一个很不错选择,注入攻击者,通常会使用这个方法,往页面上注入一些弹窗广告。

我们可以重写 document.write ,使用关键词黑名单对内容进行匹配。

什么比较适合当黑名单的关键字呢?我们可以看看一些广告很多的页面:

 

1.本站遵循行业规范,任何转载的稿件都会明确标注作者和来源;2.本站的原创文章,请转载时务必注明文章作者和来源,不尊重原创的行为我们将追究责任;3.作者投稿可能会经我们编辑修改或补充。

相关文章
  • web前端之HTML中元素的区分 - 紫竹六月

    web前端之HTML中元素的区分 - 紫竹六月

    2016-08-18 16:00

  • web前端之HTML的大框架(body元素与frameset元素) - 紫竹六月

    web前端之HTML的大框架(body元素与frameset元素) - 紫竹六月

    2016-08-14 17:00

  • CSS3 时钟 - 前端爱好者

    CSS3 时钟 - 前端爱好者

    2016-08-14 10:01

  • 移动端UC /QQ 浏览器的部分私有Meta 属性 - 前端小超人

    移动端UC /QQ 浏览器的部分私有Meta 属性 - 前端小超人

    2016-07-29 15:00

网友点评
s