Command Injection bash using Runtime API

101 views Asked by At

I am trying to test the command injection vulnerability.

I use a servlet that executes the command ls, then I try to pass another command in the url to exploit the command injection vulnerability, but when I pass the new command nothing happens. This is my servlet code and the url I use to pass the new command:

@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");
        }
    }
    
}

and the url that I use http://localhost:8080/myproject/command?parameter=;ifconfig

1

There are 1 answers

2
John Bollinger On

You are trying to get two commands to run in place of one by injecting a semicolon(;) into the constructed command string. The significance of ; for separating commands is a feature of the shell, so that might work if the command were being run via a shell, analogous to C's system() function.

But Runtime.exec() does not work that way. Although it's more clear from some of the other overloads, this family of methods is patterned after and works similarly to the execve() function and its various wrapper functions. The semicolon has no special significance to them. The unary Runtime.exec() splits the provided string into an array by use of a StringTokenizer. The first element is then taken as the name of the command, and all of the rest as command-line arguments. That's not susceptible to the mode of command injection you're attempting to perform.