because that’s the literal string I passed. If the quotes needed escaping that’s my job as the caller to do in the string I’m sending as arguments.
Different programs interpret layered quotes differently, some process them in sequence, others from the outside in. The library shouldn’t be assuming it knows better than me as the programmer (or should at least allow an args_raw() option)
And to be clear I’m not trying to lay that responsibility at your feet, it’s not your fault. I’m just working out how to clearly convey it’s actually a bug.
The way you build a string in Rust has absolutely no meaning. r#"""# and "\"" and "\x22" are 100% identical in all cases, there’s no trace of any difference anywhere. They all contain exactly one byte ", in all cases.
Command::arg() by design explicitly takes role of preserving the argument with any content you put in, and deliberately doesn’t require the programmer to escape anything.
It’s fair to argue that arg() is impossible to implement on Windows, because the entire concept of a command argument technically doesn’t exist on Windows. But Rust’s stdlib chooses the most sensible alternative of assuming arguments do exist in the way CommandLineToArgvW defines them. So in a sense Command only supports running executables using CommandLineToArgvW, and doesn’t support others.
notice the difference between the escaped and unescaped quotes?
compare the command line that gets passed here, to the one that get’s passed to notepad.exe above
Notice that \"test.e test.f\" come as separate arguments, not a single argument separated by a space. This is how rust CALLS other programs if I try to pass the "test.c test.d" style, which creates problems.
Interpretation of quoted arguments in Windows is optional, and left up to each individual application’s choice. I haven’t checked if notepad.exe chose to support quoted arguments. I wouldn’t be surprised if it assumed arguments are files, so quote isn’t a legal character, and has some half-assed custom parser. Same happens with dir.
The recommended interpretation of arguments is this:
My a "b c" d example is actually incorrect, as can be seen in the post above when I send \" rust’s argument parser swallows the \" and gives ", and if I send just " it swallows that and doesn’t hand them inside. There’s probably an alternate way of calling std::env::args that gives the actual raw arguments, but that doesn’t disprove the core of the problem which is that there doesn’t seem to be any way to reliable send nested double quotes in command line arguments to non-rust cli programs on windows.
there’s no way (that I’ve yet seen) to get rust to call this, which should give a list of installed software (that I could then digest looking for office versions for a microsoft audit) powershell -command "Get-WmiObject -class Win32_Product"
instead it will call this, which just echo’s back a string powershell -command \"Get-WmiObject -class Win32_Product\"
It may very well be it derives from microsoft’s api, not from rust’s internals, but that doesn’t mean it’s not real, nor that it’s not a bug
@kornel I found your updated post over on internals.rust and it seems like you’re agreed we may need a way to send exact strings without any additional (is “sugaring” the word?). I’ll move the discussion over there
Also sorry if my tone got contentious, it felt like I was having trouble convincing you it was actually escaping the quotes and that I wasn’t imagining things