由于 JumpServer 某些接口未做授权限制,攻击者可构造恶意请求获取到日志文件获取敏感信息,或者执行相关API操作控制其中所有机器。
JumpServer < v2.6.2
JumpServer < v2.5.4
JumpServer < v2.4.5
JumpServer = v1.5.9
处理器:4个
系统:CentOS7
内存:8G
系统语言:英文
安装过程中全部选择默认的选项,默认n就n,默认y就y,文件夹也默认。
>>>下载完很多docker镜像之后成功是这样的;
>>>启动环境:
$ cd /opt/jumpserver-installer-v2.6.1
$ ./jmsctl.sh start
这里还会下载很多images,下载完启动时可能遇到容器unhealthy的问题,重新start或者down了再start尝试,多试几次就成功了,(成功之后可能VmwareworkStation会变得很卡,因为还开着两台虚拟机……)如下:
需要网速、耐心和运气,启动之后可能遇到有些docker unhealthy,如果不影响使用的话可以忽略,下次就好了,如果有问题查一下解决方式就可以。
>>>之后访问http://your-ip:8080/,默认账号密码:admin/admin
登陆后要求重置密码:admin123123
Jumpserver完整环境很占资源,如果出现软死锁(soft lockup)的情况参考这篇文章:https://blog.csdn.net/jiangganwu/article/details/89711354
>>>登录之后由于是全新的服务器环境,需要创建有效资产,资产指的是通过堡垒机登录的主机/服务器,参考以下文章https://blog.csdn.net/weixin_44953658/article/details/110135596完整创建一个资产,建议只是复现漏洞的话选择一台Linux主机,该主机需要安装ssh-server;
注意用户名和密码(勾选更改密码)需要是该资产对应使用ssh登录的用户名和密码,才能使用web终端连接成功,这一步很重要,新环境连接成功了才能复现漏洞。
>>>安装chrome连接websocket的插件:(或者自行下载websocket king插件)
https://chrome.google.com/webstore/detail/websocket-test-client/fgponpodhbmadfljofbimhhlengambbn/related
打开下载的websocket插件,访问以下地址查看日志,可以找到一个UUID和task id (如果可以直接在这里取得task id和system_user_id以及asset_id的话,可以直接跳到执行脚本了)
复制这个id到task发送,可以看到一些信息,但是这些信息目前来说没有太大作用
>>>资产运行之后,访问原来的日志文件路径或者路径穿越访问,漏洞利用需要找到三个id分别是:user_id,asset_id,system_user_id,但是我在创建资产的时候未能成功连接,目前只能找到一个asset_id,如果资产配置成功的话,说不定找到三个id的过程会很顺利,于是我配置好资产的ssh server再试一下。
>>>继续查找system_user_id:
以上我的三个id与网络上一些的复现文章呈现的出现形式不一致,可以看到system_user_id是做了参数化,对应的prefer即是system_user_id,task id就是user_id,asset_id对应一致。
>>>查看一下web终端的交互请求
有这几个参数id就可以模拟登录。
之后通过`/api/v1/users/connection-token/?user-only=1`发送这三个id获取token,再通过ws访问`/koko/ws/token/?target_id=$token`执行命令。
>>>也可以直接用脚本文件获取id,脚本文件来源:
https://mp.weixin.qq.com/s/FMZm_2LhvnmfubjyKQAU3g
修改第二个脚本中的user_id,system_user_id,asset_id,user-only=1,执行脚本获取token,这个token只有20s有效,执行命令验证
建议修改脚本中main_logic(cmd)函数中for i in rang(x)中x的值,大一点可以看到返回的数据
这个漏洞过程是利用未授权访问漏洞获取三个id,再通过三个id获取到临时的token,把这些信息加到特定url中,以模拟web终端发包执行命令,也就是说后面模拟终端的流量是正常的,漏洞关键点的是未授权部分,建议从用websocket读取三个id这部分入手做防御。
这个协议跟平常的http协议不太一样,报文是以GET形式发送,先发送一个websocket连接的请求,返回101之后再在下一个报文里发送Request,并且如果Request报文里的mask位置1,那么会利用mask key加密payload。
参考文章:
https://mp.weixin.qq.com/s/FMZm_2LhvnmfubjyKQAU3g
https://blog.csdn.net/weixin_44953658/article/details/110135596
https://blog.csdn.net/m0_46257936/article/details/112841389
https://www.cnblogs.com/jiancanxuepiao/p/14301403.html
https://www.o2oxy.cn/2921.html