What is `cmd /s` for?

前端 未结 2 1715
南方客
南方客 2020-12-08 14:15

The Windows command prompt (cmd.exe) has an optional /s parameter, which modifies the behavior of /c (run a particular command and then exit) or

相关标签:
2条回答
  • 2020-12-08 14:31

    Cmd /S is very useful as it saves you having to worry about "quoting quotes". Recall that the /C argument means "execute this command as if I had typed it at the prompt, then quit".

    So if you have a complicated command which you want to pass to CMD.exe you either have to remember CMD's argument quoting rules, and properly escape all of the quotes, or use /S, which triggers a special non-parsing rule of "Strip first and last " and treat all other characters as the command to execute unchanged".

    You would use it where you want to take advantage of the capabilities of the CMD shell, rather than directly calling another program. For example environment variable expansion, output or input redirection, or using CMD.exe built-ins.

    Example:

    Use a shell built-in: This executes as-if you had typed DEL /Q/S "%TMP%\TestFile" at the prompt:

    CMD.exe /S /C " DEL /Q/S "%TMP%\TestFile" "
    

    This executes SomeCommand.exe redirecting standard output to a temp file and standard error to the same place:

    CMD.exe /S /C " "%UserProfile%\SomeCommand.exe" > "%TMP%\TestOutput.txt" 2>&1 "
    

    So what does /S give you extra? Mainly it saves you from having to worry about quoting the quotes. It also helps where you are unsure whether for example an environtment variable contains quote characters. Just say /S and put an extra quote at the beginning and end.

    Vaguely Related: $* in Bourne Shell.

    Some background

    Recall that the list of arguments to main() is a C-ism and Unix-ism. The Unix/Linux shell (e.g. Bourne Shell etc) interprets the command line, un-quotes the arguments, expands wildcards like * to lists of files, and passes a list of arguments to the called program.

    So if you say:

    $ vi *.txt
    

    The vi command sees for example these arguments:

    vi
    a.txt
    b.txt
    c.txt
    d.txt
    

    This is because unix/linux operates internally on the basis of "list of arguments".

    Windows, which derives ultimately from CP/M and VAX, does not use this system internally. To the operating system, the command line is just a single string of characters. It is the responsibility of the called program to interpret the command line, expand file globs (* etc) and deal with unquoting quoted arguments.

    So the arguments expected by C, have to be hacked up by the C runtime library. The operating system only supplies a single string with the arguments in, and if your language is not C (or even if it is) it may not be interpreted as space-separated arguments quoted according to shell rules, but as something completely different.

    0 讨论(0)
  • 2020-12-08 14:34

    Here's an example of how it can make a difference.

    Suppose you have two executables: c:\Program.exe and c:\Program Files\foo.exe.

    If you say

    cmd /c "c:\Program Files\foo"
    

    you'll run foo.exe (with no arguments) whereas if you say

    cmd /s /c "c:\Program Files\foo"
    

    you'll run Program.exe with Files\foo as the argument.

    (Oddly enough, in the first example, if foo.exe didn't exist, Program.exe would run instead.)

    Addendum: if you were to type

     c:\Program Files\foo
    

    at the command prompt, you would run Program.exe (as happens with cmd /s /c) rather than foo.exe (as happens with just cmd /c). So one reason for using /s would be if you want to make sure a command is parsed in exactly the same way as if it were being typed at the command prompt. This is probably more likely to be desirable in the scenario in the question Michael Burr linked to, where cmd.exe is being launched by CreateProcess rather than from a batch file or the command line itself..

    That is, if you say

    CreateProcess("cmd.exe", "cmd /s /c \"" MY_COMMAND "\"", ...)
    

    then the string MY_COMMAND will be parsed exactly as if it were typed at the command prompt. If you're taking command-line input from the user, or if you're a library processing a command line provided by an application, that's probably a good idea. For example, the C runtime library system() function might be implemented in this way.

    0 讨论(0)
提交回复
热议问题