PHP 中的 zaproxy 扫描报告解决方案

zaproxy scan report solution in PHP

我正在使用 zaproxy 自动测试我的网站。扫描报告中有 P1 警报。我不知道如何纠正这个错误。有人可以帮我吗:-

https://example.com/index.php?id=1535&source=home&storyId=468&r=video%2Fview%22%26timeout+%2FT+5%26%22&mode=current

    Parameter

r

    Attack

video/view"&timeout /T 5&"

警报详细信息

高(中)远程OS 命令注入 说明

用于未经授权执行操作系统命令的攻击技术。当应用程序接受不受信任的输入以不安全的方式构建操作系统命令时,可能会发生这种攻击,包括不正确的数据清理、and/or 不正确的外部程序调用。

URL

https://example.com/index.php?id=1535&source=home&storyId=468&r=video%2Fview%22%26timeout+%2FT+5%26%22&mode=current

Parameter

r

Attack

video/view"&超时/T 5&"

URL

https://example.com/index.php?id=1535&source=home&storyId=468&r=video%2Fview&mode=current%22%7Ctimeout+%2FT+5

Parameter

模式

Attack

当前"|超时/T 5

URL

https://example.com/index.php?r=site/login

Parameter

用户时区

Attack

&睡眠 5s&

URL

https://example.com/js/tinymce/tinymce.min.js?version=1405493567%26sleep+%7B0%7Ds%26

Parameter

版本

Attack

1405493567&睡眠{0}&

URL

https://example.com/themes/sharperax/css/sh-style.css?version=1454508637%22%26sleep+5s%26%22

Parameter

版本

Attack

1454508637"&睡眠 5s&"

实例

5

解决方案

如果可能的话,使用库调用而不是外部进程来重新创建所需的功能。

运行 您的代码在 "jail" 或类似的沙箱环境中,在进程和操作系统之间强制执行严格的界限。这可能会有效地限制在特定目录中可以访问哪些文件或您的软件可以执行哪些命令。

OS 级别的示例包括 Unix chroot jail、AppArmor 和 SELinux。通常,托管代码可以提供一些保护。例如,java.io.FilePermission 中的 Java SecurityManager 允许您指定对文件操作的限制。

这可能不是一个可行的解决方案,它只是限制了对操作系统的影响;您的应用程序的其余部分可能仍会受到损害。

对于将用于生成要执行的命令的任何数据,请尽可能多地使这些数据不受外部控制。例如,在 Web 应用程序中,这可能需要将命令存储在本地会话状态中,而不是在隐藏的表单字段中将其发送到客户端。

使用经过审查的库或框架不允许出现此弱点或提供使此弱点更容易避免的结构。

例如,考虑使用 ESAPI 编码控件或类似的工具、库或框架。这些将帮助程序员以不易出错的方式对输出进行编码。

如果您不顾风险需要使用动态生成的查询字符串或命令,请正确引用参数并转义这些参数中的任何特殊字符。最保守的方法是转义或过滤所有未通过极其严格的白名单的字符(例如所有非字母数字或白色 space)。如果仍然需要一些特殊字符,例如白色 space,请在 escaping/filtering 步骤后将每个参数用引号引起来。小心参数注入。

如果要执行的程序允许在输入文件或标准输入中指定参数,则考虑使用该模式而不是命令行来传递参数。

如果可用,请使用结构化机制自动强制执行数据和代码之间的分离。这些机制可能能够自动提供相关的引用、编码和验证,而不是依赖开发人员在生成输出的每个点都提供此功能。

一些语言提供了多种可用于调用命令的函数。在可能的情况下,识别任何使用单个字符串调用命令 shell 的函数,并将其替换为需要单独参数的函数。这些函数通常执行适当的参数引用和过滤。例如,在 C 语言中,system() 函数接受一个包含要执行的整个命令的字符串,而 execl()、execve() 和其他函数需要一个字符串数组,每个参数一个。在 Windows 中,CreateProcess() 一次只接受一个命令。在 Perl 中,如果为 system() 提供了一个参数数组,那么它将引用每个参数。

假设所有输入都是恶意的。使用 "accept known good" 输入验证策略,即使用严格符合规范的可接受输入白名单。拒绝任何不严格符合规范的输入,或将其转换为符合规范的内容。不要完全依赖于寻找恶意或格式错误的输入(即,不要依赖黑名单)。但是,黑名单可用于检测潜在攻击或确定哪些输入格式错误以至于应将其彻底拒绝。

执行输入验证时,请考虑所有可能相关的属性,包括长度、输入类型、可接受值的全部范围、缺失或额外的输入、语法、相关字段之间的一致性以及对业务规则的遵从性。作为业务规则逻辑的示例,"boat" 在语法上可能是有效的,因为它仅包含字母数字字符,但如果您期望 "red" 或 "blue."[=27 等颜色,则它无效=]

构造OS命令字符串时,使用严格的白名单,根据请求中参数的预期值限制字符集。这将间接限制攻击的范围,但这种技术不如正确的输出编码和转义重要。

请注意,正确的输出编码、转义和引用是防止 OS 命令注入的最有效解决方案,尽管输入验证可能会提供一些纵深防御。这是因为它有效地限制了将出现在输出中的内容。输入验证并不总能防止 OS 命令注入,尤其是当您需要支持可能包含任意字符的自由格式文本字段时。例如,在调用邮件程序时,您可能需要允许主题字段包含其他危险的输入,如“;”和“>”字符,需要转义或以其他方式处理。在这种情况下,剥离字符可能会降低 OS 命令注入的风险,但它会产生不正确的行为,因为主题字段不会按用户预期的方式记录。这似乎是一个小小的不便,但当程序依赖结构良好的主题行来将消息传递给其他组件时,它可能会更加重要。

即使您在验证中犯了错误(例如忘记了 100 个输入字段中的一个),适当的编码仍然可以保护您免受基于注入的攻击。只要不是孤立地完成,输入验证仍然是一项有用的技术,因为它可以显着减少您的攻击面,允许您检测某些攻击,并提供适当编码无法解决的其他安全优势。

参考

http://cwe.mitre.org/data/definitions/78.html

https://www.owasp.org/index.php/Command_Injection

CWE ID

78

WASC 编号

31

好的,所以这是一个定时攻击。 如果服务器负载不足,这些很容易出现误报。

您应该始终尝试手动验证扫描工具(包括 ZAP)报告的任何潜在漏洞。

在这种情况下,打开浏览器中引用的 URLs - 加载需要大约 5 秒吗?然后将 URL 上的“5”更改为更大的值,例如“30”——现在需要 30 秒吗?

如果花费的时间大致相同,则这很可能是误报。