利用PhpStudy进行搭建,配置数据库信息

开始代码审计,根据上面emlog pro提示 路径/admin/plugin.php存在任意文件上传漏洞,远程攻击者可利用该漏洞提交分外的要求,可上传恶意文件,以运用程序高下文实行任意代码。
先访问路径,看看页面是什么样的,这个是原生开拓的可以这样,如果是mvc的就弗成

挖掘文件上传这种漏洞就直接找功能点,这个页面的功能点只有一个安装插件

php远程文件存在emlog pro文件上传破绽审计CVE202344974CVE202344973 GraphQL

先正常的安装个插件走一下流程

利用burp抓包

知道了这个数据包是成功上传文件的

打开源码通过搜索全局upload_zip

根据上面的提示路径找到了这个文件

if ($action == 'upload_zip') { LoginAuth::checkToken(); $zipfile = isset($_FILES['pluzip']) ? $_FILES['pluzip'] : ''; if ($zipfile['error'] == 4) { emDirect("./plugin.php?error_d=1"); } if ($zipfile['error'] == 1) { emDirect("./plugin.php?error_g=1"); } if (!$zipfile || $zipfile['error'] >= 1 || empty($zipfile['tmp_name'])) { emMsg('插件上传失落败, 缺点码:' . $zipfile['error']); } if (getFileSuffix($zipfile['name']) != 'zip') { emDirect("./plugin.php?error_f=1"); } $ret = emUnZip($zipfile['tmp_name'], '../content/plugins/', 'plugin'); switch ($ret) { case 0: emDirect("./plugin.php?activate_install=1"); break; case -1: emDirect("./plugin.php?error_e=1"); break; case 1: case 2: emDirect("./plugin.php?error_b=1"); break; case 3: emDirect("./plugin.php?error_c=1"); break; }}

这段是可以绕过的,没什么问题获取文件后缀名zip

连续跟踪一下emUnZip,解压文件看看解压过程中有没有什么过滤

function emUnZip($zipfile, $path, $type = 'tpl') { if (!class_exists('ZipArchive', FALSE)) { return 3;//zip模块问题 } $zip = new ZipArchive(); if (<span class="label label-primary">@$zip-</span>>open($zipfile) !== TRUE) { return 2;//文件权限问题 } $r = explode('/', $zip->getNameIndex(0), 2); $dir = isset($r[0]) ? $r[0] . '/' : ''; switch ($type) { case 'tpl': $re = $zip->getFromName($dir . 'header.php'); if (false === $re) { return -2; } break; case 'plugin': $plugin_name = substr($dir, 0, -1); $re = $zip->getFromName($dir . $plugin_name . '.php'); if (false === $re) { return -1; } break; case 'backup': $sql_name = substr($dir, 0, -1); if (getFileSuffix($sql_name) != 'sql') { return -3; } break; case 'update': break; } if (true === <span class="label label-primary">@$zip-</span>>extractTo($path)) { $zip->close(); return 0; } return 1; //文件权限问题}

通过跟踪并没有什么过滤,emUnZip函数,可以创造他须要获取一个路径$dir,但是咱们的压缩包里面便是一个文件,安装正常的插件压缩包里面都有一个文件夹

去网上找了一个正常插件,上传,可以成功上传

然后在本地修正插件,创建一个php文件

写入内容

然后进行压缩上传,剖析上面代码,知道了上传解压没有对文件内的内容进行过滤,成功上传

查看本地文件夹是否存在phpinfo.php

网页访问路径

emlog pro /content/templates/任意文件上传漏洞 CVE-2023-44973

打开网站,还是先找功能点,根据上面的cnvd提示也知道是模板那个位置有问题

和上面第一则一样先上传个正常的文件上去,抓一下包

定位到代码位置

if ($action === 'upload_zip') { LoginAuth::checkToken(); // 检讨登录状态和令牌,确保安全性 $zipfile = isset($_FILES['tplzip']) ? $_FILES['tplzip'] : ''; // 获取上传的ZIP文件 if ($zipfile['error'] == 4) { emDirect("./template.php?error_d=1"); // 如果上传文件为空,重定向到缺点页面 } if ($zipfile['error'] == 1) { emDirect("./template.php?error_f=1"); // 如果上传文件超过了php.ini中的限定大小,重定向到缺点页面 } if (!$zipfile || $zipfile['error'] > 0 || empty($zipfile['tmp_name'])) { emMsg('模板上传失落败, 缺点码:' . $zipfile['error']); // 如果上传文件出错,显示缺点信息并返回 } if (getFileSuffix($zipfile['name']) != 'zip') { emDirect("./template.php?error_a=1"); // 如果上传文件不是ZIP文件,重定向到缺点页面 } $ret = emUnZip($zipfile['tmp_name'], '../content/templates/', 'tpl'); // 调用解压缩函数解压上传的ZIP文件 switch ($ret) { case 0: emDirect("./template.php?activate_install=1"); // 解压缩成功,重定向到激活安装页面 break; case -2: emDirect("./template.php?error_e=1"); // 找不到header.php文件,重定向到缺点页面 break; case 1: case 2: emDirect("./template.php?error_b=1"); // 文件权限问题或解压缩失落败,重定向到缺点页面 break; case 3: emDirect("./template.php?error_c=1"); // 短缺ZIP模块,重定向到缺点页面 break; }}

当action为upload_zip时,实行if后面的语句,LoginAuth::checkToken();是用来检测登录状态的。
$zipfile用来吸收tplzip上传上来的数据,然后对上传的数据进行各种缺点判断,判断成功后,实行下面的emUnZip函数进行解压,并把解压后的文件放到/content/templates/目录下,我们在追踪一下emUnZip函数看看是否有过滤等情形通过查看代码文件上传时会实行if后面的语句,$zipfile变量来吸收上传的数据,对数据进行判断,符合哀求实行解压函数emUnZip进行解压,以是我们连续跟踪emUnZip看看有没有过滤

function emUnZip($zipfile, $path, $type = 'tpl') { if (!class_exists('ZipArchive', FALSE)) { return 3; // 如果做事器上没有安装Zip模块,返回缺点码3,表示zip模块问题 } $zip = new ZipArchive(); // 创建一个ZipArchive工具 if (<span class="label label-primary">@$zip-</span>>open($zipfile) !== TRUE) { return 2; // 如果无法打开指定的压缩文件,返回缺点码2,表示文件权限问题 } $r = explode('/', $zip->getNameIndex(0), 2); // 获取压缩文件中的第一个文件的路径 $dir = isset($r[0]) ? $r[0] . '/' : ''; // 获取文件的目录路径 switch ($type) { case 'tpl': $re = $zip->getFromName($dir . 'header.php'); // 从压缩文件中获取名为header.php的文件内容 if (false === $re) { return -2; // 如果无法获取到header.php文件内容,返回缺点码-2 } break; case 'plugin': $plugin_name = substr($dir, 0, -1); // 获取插件的名称 $re = $zip->getFromName($dir . $plugin_name . '.php'); // 从压缩文件中获取与插件名称对应的php文件内容 if (false === $re) { return -1; // 如果无法获取到插件对应的php文件内容,返回缺点码-1 } break; case 'backup': $sql_name = substr($dir, 0, -1); // 获取备份文件的名称 if (getFileSuffix($sql_name) != 'sql') { // 判断备份文件的后缀名是否为sql return -3; // 如果备份文件的后缀名不为sql,返回缺点码-3 } break; case 'update': break; } if (true === <span class="label label-primary">@$zip-</span>>extractTo($path)) { // 将压缩文件内容解压到指定路径 $zip->close(); return 0; // 解压缩成功,返回0 } return 1; // 解压缩失落败,返回缺点码1,表示文件权限问题}

可以看出没有过滤,然后对上传的文件添加恶意文件

还是和上面一样,在正常的模板里面添加一个php文件,文件内容不为空,压缩上传

上传成功访问

这两个文件上传都是一样调用同一个文件