fcl-process: Un-deprecate TProcess.CommandLine on Windows
Summary
TProcess.CommandLine is marked as deprecated. This is a good thing for the Unix-like systems (Linux, FreeBSD, macOS, etc.) but is not good for Windows. I propose that FPC instead only remove it on the Unix-like systems.
First, an overview of how process arguments are passed on different systems.
- On Unix-like systems the environment block contains an
argv[]array, which corresponds nicely toTProcess.ExecutableandTProcess.Parameters. - On Windows however, an executable is handed a command-line string containing its name and the parameters, corresponding to the state of
TProcess.CommandLine. The executable itself needs to parse the string into an argument array. This is usually handled by the C/C++ runtime or whatever other language runtime is here, but parsing behavior varies wildly.
And it is the fact that parsing behavior varies wildly on Windows that makes TProcess.CommandLine indispensable.
- A lot of important Windows utilities define their own parsing, including
cmd.exe,msiexec, and many more. Among these, you definitely do not want to mess upcmd. - Because
cmddoes not expand wildcards, many third-party programs choose to expand wildcards themselves when it sees one in an unquoted argument. - Some of these third-party programs define their own parsing that is also incompatible with MSVC's. See the two links from 2019 and 2020 in https://cygwin.com/pipermail/cygwin-patches/2021q2/011367.html.
(I suspect OS/2 is similar, as Windows's behavior was inherited from DOS.)
Recommendation
- Keep
TProcess.CommandLinedeprecated on the Unix-like systems. The current emulation of it viaCommandToListcauses true Unix shell commands to break anyways, as the PeaZip people and I have recently discovered. - Retain
TProcess.CommandLineon Windows. - Make sure
TProcess.Parametersworks the same on Windows for typical C/C++ programs as it does for Linux. (#41329 (closed)) - Make sure
TProcess.Parametersis quoted in a way understood by FPC's own runtime library (it is currently not).
Details about current FPC RTL command line parsing
I don't want to open up another issue for that, but it will need to change.
- On Windows
setup_argumentscallsParseCommandLinewhich does the parsing using a similar (Delphi?) syntax toCommandToList. - On Darwin and WASI (not sure about other Linux),
setup_argumentseither does nothing or just copies fromargv.
As a result the situation of 41329 would also apply to two echo programs compiled with FPC. With TProcess.Parameters set to only have one member '"a"':
- On Windows it would also only receive
ain the parsed arguments because the command-line would bexxx.exe "a". - On Darwin and WASI it would receive
"a"in the parsed arguments because it is the exact form given in argv.
Edited by Mingye Wang