使用Runtime API测试Bash命令注入漏洞无效果,求排查
命令注入测试无响应问题排查
我在测试命令注入漏洞时,使用了一个执行ls命令的Servlet,尝试通过URL传入额外命令来利用该漏洞,但传入新命令后无任何反应。
Servlet代码
@WebServlet("/command") public class CommandInjectionServlet extends HttpServlet { private static final long serialVersionUID = 1L; protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { try { String comm = "/bin/bash -c ls " + request.getParameter("parameter"); Process process = Runtime.getRuntime().exec(comm); BufferedReader stdInput = new BufferedReader( new InputStreamReader(process.getInputStream(), StandardCharsets.UTF_8)); String s = null; while ((s = stdInput.readLine()) != null) { response.getWriter().println(s); } } catch (IOException e) { e.printStackTrace(); System.out.println("Error executing command"); } } }
测试URL
http://localhost:8080/myproject/command?parameter=;ifconfig
问题原因
核心问题在于/bin/bash -c的参数传递逻辑:bash的-c选项仅接受单个字符串参数作为要执行的命令。你当前的写法/bin/bash -c ls ;ifconfig中,ls会被当成-c的唯一命令参数,后面的;ifconfig会被当作bash进程的额外参数,根本不会被shell执行。同时Runtime.exec()的字符串拆分逻辑也无法正确解析shell的分号语法,进一步导致注入的命令无法运行。
解决方法
修正命令拼接方式
将所有要执行的命令封装到-c的单个参数中,用引号包裹:String comm = "/bin/bash -c 'ls " + request.getParameter("parameter") + "'";此时测试URL的
;ifconfig会被包含在bash要执行的命令字符串中,两个命令都会被依次执行。使用数组传递参数(更可靠)
直接用数组形式传递命令和参数,避免Runtime.exec()的字符串拆分问题:String param = request.getParameter("parameter"); String[] comm = {"/bin/bash", "-c", "ls " + param}; Process process = Runtime.getRuntime().exec(comm);这种方式能确保
-c后面的整个字符串被bash当作命令执行。补充读取标准错误流
当前代码仅读取进程的标准输出,若命令执行出错,错误信息会输出到标准错误流,导致你无法看到执行失败的原因。建议添加标准错误流读取逻辑:// 在读取标准输出后添加 BufferedReader stdError = new BufferedReader( new InputStreamReader(process.getErrorStream(), StandardCharsets.UTF_8)); String errLine; while ((errLine = stdError.readLine()) != null) { response.getWriter().println("执行错误: " + errLine); }
内容的提问来源于stack exchange,提问作者mido med
相关产品推荐
相关产品推荐

