使用注入的环境变量构建命令¶
ID: java/exec-tainted-environment
Kind: path-problem
Security severity: 9.8
Severity: error
Precision: medium
Tags:
- security
- external/cwe/cwe-078
- external/cwe/cwe-088
- external/cwe/cwe-454
Query suites:
- java-security-extended.qls
- java-security-and-quality.qls
将未经验证的用户输入传递到子进程的环境变量中,可能会让攻击者执行恶意代码。
建议¶
如果可能,请使用硬编码字符串文字来指定环境变量或其值。不要将用户输入直接传递给进程或库函数,而是先检查用户输入,然后从硬编码字符串文字中进行选择。
如果无法在编译时确定适用的环境变量,则添加代码以在使用用户输入字符串之前验证其安全性。
示例¶
在以下(错误)示例中,环境变量 PATH
设置为用户输入 path
的值,但未进行验证。
public void doGet(HttpServletRequest request, HttpServletResponse response) {
String path = request.getParameter("path");
Map<String, String> env = processBuilder.environment();
// BAD: path is tainted and being added to the environment
env.put("PATH", path);
processBuilder.start();
}
在以下(错误)示例中,使用未经验证的用户输入 var
派生的名称设置环境变量。
public void doGet(HttpServletRequest request, HttpServletResponse response) {
String attr = request.getParameter("attribute");
String value = request.getParameter("value");
Map<String, String> env = processBuilder.environment();
// BAD: attr and value are tainted and being added to the environment
env.put(attr, value);
processBuilder.start();
}
在以下(正确)示例中,在用于设置环境变量之前会先验证用户输入。
String opt = request.getParameter("opt");
String value = request.getParameter("value");
Map<String, String> env = processBuilder.environment();
// GOOD: opt and value are checked before being added to the environment
if (permittedJavaOptions.contains(opt) && validOption(opt, value)) {
env.put(opt, value);
}
在以下(正确)示例中,会检查用户输入并用于确定要添加的环境变量。
Map<String, String> env = builder.environment();
String debug = request.getParameter("debug");
// GOOD: Checking the value and not tainting the variable added to the environment
if (debug != null) {
env.put("PYTHONDEBUG", "1");
}