
Shiro反序列化
Shiro550
环境搭建
- Tomcat 9.0.100
- jdk8u65
- Shiro 1.2.4
用 idea 打开后需要将依赖修改为下图所示 1.2
以漏洞发现角度分析
解密过程
登录时抓包可以看到一大长串 Cookie,很明显是加密过的,所以要找 Cookie 的加密过程
全局搜索Cookie,发现有个跟 Cookie 相关的类CookieRememberManager
base64 解码
在这个类中发现getRememberedSerializedIdentity()
继续往上找谁调了getRememberedSerializedIdentity(),找到AbstractRememberMeManager.getRememberedPrincipals()
这个方法把刚刚 base64 解码的值赋给了 bytes,然后又紧接着调用了convertBytesToPrincipals()
跟进看一下这个方法,很明显它进行了一个解密,一个反序列化
AES 解密
先进入descrpt()看一下,看到密钥服务又调用了一个decrypt(),而这个decrypt()是一个接口,它传了两个参数,一个是加密的数组,一个是 key
继续跟进传入的 key

看看哪里调用了 decryptionCipherKey

一直向上找,找到最后发现 key 是个常量

反序列化
跟进deserialize()
继续跟进发现有两个实现
找到入口类
以上就是整个解密过程,下面来看看加密
加密过程
在 onSuccessfulLogin 下断点,判断是否选 Rememberme
跟进 rememberIdentity(),这里进行的是一个保存用户名的操作

跟进 rememberIdentity()
跟进 rememberIdentity()
这里与解密相似,只不过就是反过来了 序列化&加密
这里就不跟进了,其实跟进的效果和上面解密是一样的,都是发现 key 是个常量
然后后面是 base64 编码
以上就是全过程了
漏洞利用
RCE的点都是在反序列化的时候触发的,所以重点攻击反序列化的部分
下面放一个加密的脚本
1 | import base64 |
这里就不用 urldns 链进行验证了,直接通过 CB 链攻击
重点重点!!(调了半天)
一开始直接用 CBWithCC 会这样报错,是因为 shiro 中的 commons-beanutils 中只包含了一部分的 commons-collections,不全,导致使用 shiro 时是不需要依赖 commons-collections 的,所以要用 CBWithoutCC 那条链
Java 在反序列化的时候提供了一个机制,序列化时会根据固定算法计算出一个当前类的serialVersionUID值,写入数据流中;反序列化时,如果发现对方的环境中这个类计算出的serialVersionUID不同,则反序列化就会异常退出,避免后续的未知隐患。
我们的 CBWithoutCC 那条链依赖本来是 CB1.8.3 & CB1.9.2,而shiro自带的是1.8.3版本,出现了 serialVersionUID 对应不上的问题。
所以 CBWithoutCC 的依赖就直接用 CB1.8.3 & CC3.2.1 即可
成功执行命令
指纹识别
判断应用是否用到了 shiro:
在请求包的 Cookie 中为 rememberMe 字段赋任意值,收到返回包的 Set-Cookie 中存在 rememberMe=deleteMe 字段,说明目标有使用 Shiro 框架,可以进一步测试。
Shiro721
与 shiro550 的区别:AES密钥修改成了动态生成,对于每一个 Cookie,都是使用不同的密钥进行加解密的。
攻击复杂程度变高
Apache Shiro Padding Oracle Attack 的漏洞利用必须满足如下前提条件:
- 开启 rememberMe 功能;
- rememberMe 值使用 AES-CBC 模式解密;
- 能获取到正常 Cookie,即用户正常登录的 Cookie 值;
- 密文可控;
利用的话可用这个工具





