Fortify不信任Java System属性



我正在尝试使用ProcessBuilder:派生进程

String classpath = System.getProperty("java.class.path");
String[] javaCmd = {"java", "-cp", classpath, ...};
ProcessBuilder builder = new ProcessBuilder();
// ...
builder.command(javaCmd)
// ...

Fortify报告命令注入漏洞,因为CCD_;由不可信数据构建";。Fortify是正确的,因为系统属性是相互的:System.setProperty(),这使得它们在运行系统命令时很危险。

我没能找到System.getProperty("java.class.path")的替代品,我想知道是否有人有主意?

谢谢

整个命令是一个巨大的行走漏洞。或者不是。安全不是非黑即白的。这是灰色的阴影。这段代码并不是完全是白色的,但它是浅灰色的(也就是说:它为攻击者提供了一些进入的路线,但这些路线通常在正确配置的系统上不可用,而"进入"的几种方式通常会更可怕、更直接,这使得打开的攻击面基本上没有意义)。

TL;DR:警告很愚蠢,告诉强化忽略这个,而且,你的安全流程可能需要更新。此外,此代码很可能并没有真正实现您想要的功能。不幸的是,没有一种简单的方法可以编写出可以随心所欲的代码;为自己带来坏消息而道歉。

更详细地说:

特别地;我将不完全按照一般分析来处理每一个强化警告,而只是写下我能想到的最接近的东西来消除它;是一种很好的方式,认为你已经写了安全的代码,而实际上并没有这么做

你必须了解强化的目的。然后,你必须弄清楚攻击面到底是什么,要么不接受这一点(因此更改/删除暴露它的ALL代码),要么接受它,并证明这个攻击面无关紧要。在这种情况下,第二种选择(接受它,记录它,然后继续前进)听起来对几乎所有可以想象的场景来说都是正确的。

在这个特定的例子中,您编写的代码有两个不同的攻击面:

磁盘访问导致被泄露

您正在运行java。就这样。相对路径。你不知道会运行什么java,也绝对不能保证它会是你当前JVM的同一个java。它很容易是一个恶意脚本。这需要攻击者找到一种方法,将该脚本放入路径上的文件夹中。对于非root用户,.通常在路径上,并且首先在路径上。因此,如果这是一台服务器,攻击者可以设法让服务器将文件保存在自己的目录中,那么boom。给你。您的服务器现在受到威胁。

强化措施并没有警告这是错误的;一般来说,相对路径是个坏主意,如果不是出于安全原因,那么出于稳定性原因:这在很多服务器上都不起作用。不幸的是,以独立于平台和部署的方式从第一个JVM可靠地调用第二个JVM基本上是不可能的。这就是为什么真正的解决方案通常是直接避免它,或者设置明确的操作系统绑定脚本来处理它(然后使用绝对路径运行脚本)。

损害系统属性

是的,如果sonme攻击者设法诱使您的JVM运行System.setProperty("java.class.path"),那么他们可以危害您的机器但这太荒谬了。你应该立刻忘记这个攻击面,因为它是零长度的。

您运行System.setProperty(untrustedUserInput, someOtherUntrustedUserInput);的可能性有多大?继续,搜索你的代码库。是的高度不太可能出现。某些攻击者可能会强迫您的服务器运行它想要的任何字节码(这需要一个开放的安全漏洞,例如有缓冲区溢出的PNG解析器或其他什么;这意味着它要么是一个0天的攻击者,要么是您确保服务器及时修补的进程被破坏,在这种情况下,您会遇到更大的问题)。如果攻击者能够做到这一点,他们可以设置属性,是的。

他们也可以随心所欲地直接使用ProcessBuilder,所以,这一点完全没有意义。你把注意力集中在这座大山旁边的岩石上,并将其定为陆地上的最高点。

因此,得出结论:在这种情况下,强化警告是愚蠢的,应该完全忽略。然而,这个代码IS肯定打开了一些攻击面;不过不是特别大的。特别是,如果没有人能够登录到这个框中,或者写入运行这个JVM进程的目录的用户(当然他们不应该这样做,或者编辑路径!),那么你就没事了。如果不是这样的话,你会遇到更大的问题。

这就是安全性的工作方式:你写下这些东西,并在整个过程中不断审查(不仅仅是代码、文档、检查,每两年对系统操作人员进行一次采访,以检查他们是否阅读了文档并遵循了指令)。你不可能关闭每一个攻击面。你只需要提高对它们的认识,确保它们不会被滥用。

我不认为有什么创造性的方法可以关闭强化(也许通过反射调用processbuilder,强化可能无法解决),但所做的只是降低安全性。这里唯一正确的解决方案是完全放弃强化(这可能有点激烈),或者按照应该使用的方式使用它:将它发现的地方作为非详尽的代码列表进行分析。而不是"这是我需要修复的东西的列表,然后我的代码是安全的"。这个分析应该足够了,因此,粘贴适当的注释或注释或任何它需要的东西来告诉强化,你已经手动接受了这个,它不应该再告诉你它

真正的解决方案

不要这样做。完全试着找到一种方法来做任何需要做的事情,而不需要调用新的JVM。如果这不在表上,请重新定义它的工作方式:与其"用与此VM相同的类路径克隆此VM",不如考虑"运行一个不一定是此VM克隆的新VM,因为我启动的实际JVM可能与此VM所支持的可执行文件不同,并且类路径是显式配置的,或者至少在其他地方配置的"。换言之,如果必须,请记录该服务器的正确设置需要在特定位置创建一个脚本,并适当配置访问权限,从而引导具有特定类路径的JVM。

相关内容

最新更新