CmsEasy代码审计-PHP
字数 1248 2025-08-03 10:57:05

CmsEasy 7.7.4 代码审计报告

环境说明

  • 操作系统:Windows 10
  • 集成环境:phpstudy
  • PHP版本:7.3.4
  • MySQL版本:5.7.25
  • CMS版本:CmsEasy 7.7.4

目录结构

cmseasy/
|-- admin
|-- api
|-- apps
|-- cache
|-- cn
|-- common
|-- config
|-- data
|-- en
|-- html
|-- images
|-- install
|-- jp
|-- lang
|-- lib
|-- license
|-- readme
|-- sitemap
|-- sk
|-- template
|-- template_admin
|-- ueditor
|-- wap
`-- webscan360

漏洞分析

1. SQL注入漏洞

漏洞位置

  • 文件:lib/admin/database_admin.php 中的 dorestore_action() 方法
  • 文件:lib/table/tdatabase.php 中的 restoreTables() 函数

漏洞原理

  1. dorestore_action() 方法接收 GET 参数 db_dir 后使用 front::scan($dir) 函数获取该目录下的文件名
  2. 目录名与文件名传递给 tdatabase::getInstance()->restoreTables() 函数
  3. restoreTables() 函数使用 file_get_contents() 读取文件内容
  4. 文件内容经过字符替换与分割后直接传递给 $this->query() 执行
  5. 最终 SQL 语句通过 $this->db->query()$this->mysqli->query() 执行

利用条件

  • 需要配合文件上传功能
  • 上传的文件需要是目录下的第一个文件

利用步骤

  1. 上传一个包含 SQL 语句的文件
  2. 将静态文件目录设置为 /
  3. 触发 SQL 注入漏洞

漏洞修复建议

  • 对从文件读取的内容进行严格的 SQL 语句过滤
  • 限制可恢复的数据库文件目录
  • 对数据库操作进行参数化查询

2. 任意文件写入 GetShell 漏洞

漏洞位置

  • 文件:lib/admin/table_admin.php 中的 edit_action() 函数

漏洞原理

  1. edit_action() 函数使用 file_put_contents 进行文件写入操作
  2. 文件名后缀默认为 .php
  3. POST 所有内容序列化后放入 $tag_config 变量
  4. 虽然 POST 值被过滤,但参数名未被过滤
  5. 通过参数名可以写入恶意代码

利用步骤

  1. 构造特殊请求包,通过参数名写入 WebShell
  2. 访问预判的文件名执行 WebShell

漏洞修复建议

  • 对写入的文件内容进行严格过滤
  • 限制可写入的文件类型和目录
  • 对参数名也进行安全过滤
  • 避免将用户可控内容直接写入 PHP 文件

总结

  1. SQL注入漏洞

    • 从文件中获取 SQL 语句并直接执行
    • 需要结合文件上传功能利用
    • 展示了文件操作与数据库操作结合时的安全隐患
  2. 任意文件写入 GetShell

    • 通过参数名绕过值过滤写入恶意代码
    • 展示了序列化操作可能带来的安全问题
    • 参数过滤不全面导致的漏洞

审计建议

  1. 对所有文件操作进行严格权限控制和内容过滤
  2. 数据库操作应使用参数化查询
  3. 对用户输入进行全面过滤,包括参数名和参数值
  4. 避免将用户可控内容直接写入可执行文件
  5. 对序列化和反序列化操作进行安全检查
CmsEasy 7.7.4 代码审计报告 环境说明 操作系统:Windows 10 集成环境:phpstudy PHP版本:7.3.4 MySQL版本:5.7.25 CMS版本:CmsEasy 7.7.4 目录结构 漏洞分析 1. SQL注入漏洞 漏洞位置 文件: lib/admin/database_admin.php 中的 dorestore_action() 方法 文件: lib/table/tdatabase.php 中的 restoreTables() 函数 漏洞原理 dorestore_action() 方法接收 GET 参数 db_dir 后使用 front::scan($dir) 函数获取该目录下的文件名 目录名与文件名传递给 tdatabase::getInstance()->restoreTables() 函数 restoreTables() 函数使用 file_get_contents() 读取文件内容 文件内容经过字符替换与分割后直接传递给 $this->query() 执行 最终 SQL 语句通过 $this->db->query() 和 $this->mysqli->query() 执行 利用条件 需要配合文件上传功能 上传的文件需要是目录下的第一个文件 利用步骤 上传一个包含 SQL 语句的文件 将静态文件目录设置为 / 触发 SQL 注入漏洞 漏洞修复建议 对从文件读取的内容进行严格的 SQL 语句过滤 限制可恢复的数据库文件目录 对数据库操作进行参数化查询 2. 任意文件写入 GetShell 漏洞 漏洞位置 文件: lib/admin/table_admin.php 中的 edit_action() 函数 漏洞原理 edit_action() 函数使用 file_put_contents 进行文件写入操作 文件名后缀默认为 .php POST 所有内容序列化后放入 $tag_config 变量 虽然 POST 值被过滤,但参数名未被过滤 通过参数名可以写入恶意代码 利用步骤 构造特殊请求包,通过参数名写入 WebShell 访问预判的文件名执行 WebShell 漏洞修复建议 对写入的文件内容进行严格过滤 限制可写入的文件类型和目录 对参数名也进行安全过滤 避免将用户可控内容直接写入 PHP 文件 总结 SQL注入漏洞 : 从文件中获取 SQL 语句并直接执行 需要结合文件上传功能利用 展示了文件操作与数据库操作结合时的安全隐患 任意文件写入 GetShell : 通过参数名绕过值过滤写入恶意代码 展示了序列化操作可能带来的安全问题 参数过滤不全面导致的漏洞 审计建议 对所有文件操作进行严格权限控制和内容过滤 数据库操作应使用参数化查询 对用户输入进行全面过滤,包括参数名和参数值 避免将用户可控内容直接写入可执行文件 对序列化和反序列化操作进行安全检查