JDK-7028124 : ProcessBuilder doesn't handle empty command arguments
  • Type: Bug
  • Component: core-libs
  • Sub-Component: java.lang
  • Affected Version: 6u24
  • Priority: P4
  • Status: Closed
  • Resolution: Duplicate
  • OS: windows_7
  • CPU: x86
  • Submitted: 2011-03-16
  • Updated: 2012-03-20
  • Resolved: 2011-05-17
Related Reports
Duplicate :  
Description
FULL PRODUCT VERSION :
java version "1.6.0_20"
Java(TM) SE Runtime Environment (build 1.6.0_20-b02)
Java HotSpot(TM) 64-Bit Server VM (build 16.3-b01, mixed mode)

ADDITIONAL OS VERSION INFORMATION :
Microsoft Windows [Version 6.1.7600]

Haven't tried other OSes but likely they are affected too, at least other versions of Windows.

A DESCRIPTION OF THE PROBLEM :
ProcessBuilder (actually ProcessImpl) doesn't correctly encode/escape empty arguments, so they are not passed to the command when creating a new process.

STEPS TO FOLLOW TO REPRODUCE THE PROBLEM :
Create a file named test.bat with the following content and put it in the current working directory:

@rem ------- test.bat ----------
@echo off
echo "Arg one is %1"
echo "Arg two is %2"
echo "Arg three is %3"
@rem ------- test.bat ----------

Then run the attached executable test case.

EXPECTED VERSUS ACTUAL BEHAVIOR :
EXPECTED -
I expect the java program to print this output to stdout:

"Arg one is arg1"
"Arg two is "
"Arg three is arg3"

ACTUAL -
The java program prints to stdout:

"Arg one is arg1"
"Arg two is arg3"
"Arg three is "


REPRODUCIBILITY :
This bug can be reproduced always.

---------- BEGIN SOURCE ----------
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;

/**
 * Note this test case requires test.bat as described in "Steps to reproduce"
 */
public class Test {

	public static void main(String[] args) throws IOException {
		ProcessBuilder processBuilder = new ProcessBuilder("test.bat", "arg1", "", "arg3");
		Process process = processBuilder.start();
		BufferedReader reader = new BufferedReader(new InputStreamReader(process.getInputStream()));
		
		String line = reader.readLine();
		while (line != null) {
			System.out.println(line);
			line = reader.readLine();
		}
	}
}

---------- END SOURCE ----------

CUSTOMER SUBMITTED WORKAROUND :
If I replace the empty argument "" with "\"\"", the test prints out:

"Arg one is arg1"
"Arg two is """
"Arg three is arg3"

I don't think this is quite the correct answer either, but it seems to work for my application.