1

I have a .net / c# command line application that takes a couple parameters in the format like:

some.exe -p1:value -p2:someothervalue

etc

A complete sample call looks like this:

JobWorker.exe -j:b38815af-68ce-4cb9-a858-3c016cc3c033 -cs:fors37ca -ch:384 
-s:fors37ea -dp:667 -op:B:\ 
-ci:"d:\TFS\iRMA-4.2-P1\Applications.JobExecutor\bin\x86\Debug\Image Cache\" 
-cas:fors35fa -cap:333 -gs:fors395a -gb:gibraltar -gt:5 
-jn:"DocumentJob #iRMA FSP #Some User Name #Open #6/16/2011"

Now for some reason the -ci:"d:...." part breaks the string[] args up weirdly, see with the -ci: one:

full command line including the -ci: part

vs without: command line without the -ci: part

Everything past the -ci: part gets messed up.. for some reason & I am wondering what it is? Any ideas?

Kyle Trauberman
  • 25,414
  • 13
  • 85
  • 121
Jörg Battermann
  • 4,044
  • 5
  • 42
  • 79
  • possible duplicate of [Passing command line arguments in C#](http://stackoverflow.com/questions/653563/passing-command-line-arguments-in-c) – H H Jun 16 '11 at 21:20
  • You have to escape backslashes that preceed a quote. Strange rule(s), see the dupe. – H H Jun 16 '11 at 21:22
  • Oh my... never saw that before / knew about it.. and yep, sounds a lot like a duplicate of the Q Henk mentioned. Thanks liho1eye / Henk and the others aswell! – Jörg Battermann Jun 16 '11 at 21:28
  • I am curious how you are spawning this process - you say it is from another program, but this issue would indicate it's doing shell expansion on the text. There might be better ways to pass your args (as an explicit list, for instance). – jwd Jun 16 '11 at 22:07

3 Answers3

0

I think liho1eye has it right in the comment.

This really has nothing to do with .NET and more to do with what method you're using to pass the args to your program.

Are you running it from a CMD.exe shell?

The fix is to either get rid of the trailing backslash, or double it, like so:

-ci:"d:\TFS\iRMA-4.2-P1\Applications.JobExecutor\bin\x86\Debug\Image Cache\\" 
jwd
  • 10,837
  • 3
  • 43
  • 67
0

Per msdn

A double quotation mark preceded by a backslash (\") is interpreted as a literal double quotation mark character (")

http://msdn.microsoft.com/en-us/library/78f4aasd(v=vs.80).aspx

It sees it as a literal and doesn't close the argument.

Chris Cap
  • 1,056
  • 3
  • 13
  • 21
  • 3
    That link muddies the waters a little bit since it talks about how "the C# compiler" processes args, but it is mixing those with how the shell processes args. This problem has nothing to do with C# or .NET, afaik. – jwd Jun 16 '11 at 21:24
0

You have a very complex command line that takes a lot of arguments and it is probably generated programmatically (I hope so anyway.) Since it is complex and you're needing to allow troublesome characters then I would suggest passing a single, base64-encoded block as an argument that contains all of the parameter information. It's a sort of poor-man's serializer but, it protects your command from a lot of weirdness that comes from passing args via command line and the dozen or so special characters such as pipes and angle braces: | < > and several others. You can decode and parse out the base64 block inside your logic without worrying about special characters.

So with base64 encoding your command would look like:

JobWorker.exe LWo6YjM4ODE1YWYtNjhjZS00Y2I5LWE4NTgtM2MwMTZjYzNjMDMzIC1jczpmb3JzMzdjYSAtY2g6Mzg0IA0KLXM6Zm9yczM3ZWEgLWRwOjY2NyAtb3A6QjpcIA0KLWNpOiJkOlxURlNcaVJNQS00LjItUDFcQXBwbGljYXRpb25zLkpvYkV4ZWN1dG9yXGJpblx4ODZcRGVidWdcSW1hZ2UgQ2FjaGVcIiANCi1jYXM6Zm9yczM1ZmEgLWNhcDozMzMgLWdzOmZvcnMzOTVhIC1nYjpnaWJyYWx0YXIgLWd0OjUgDQotam46IkRvY3VtZW50Sm9iICNpUk1BIEZTUCAjU29tZSBVc2VyIE5hbWUgI09wZW4gIzYvMTYvMjAxMSI=

You can verify the en/decoding here, and many other online locations.

Paul Sasik
  • 79,492
  • 20
  • 149
  • 189
  • Clever, but makes it rather harder to call the program from a .bat file or elsewhere. This trick locks your program into only *ever* being called from another program. – jwd Jun 16 '11 at 21:27
  • Unfortunately not an option in this case. The parameters are in fact generated during runtime and call this .exe, but one of the requirements is/was that the parameters need to be human readable for administrators (this .exe is spawned multiple times in parallel), base64 makes that a tad hard. Not really elegant, I know. – Jörg Battermann Jun 16 '11 at 21:30
  • @jwd: That's right. I wouldn't suggest this solution except that the complexity of the command makes me think that it's generated elsewhere and passed to the commandline programmatically. – Paul Sasik Jun 16 '11 at 21:31
  • @Jörg B.: I encoutered the same resistance when I suggested this alternative recently. Yes, it is not immediately human readable, though you could argue that it's hardl;y human readable at all. And all you have to do is copy and paste the block into an online decoder and you have the text. They are common. Another way to get this through is to promise to log the arguments into Console or log file. And guess what... you can format it much nicer that way and improve the readability significantly. – Paul Sasik Jun 16 '11 at 21:33
  • Interesting. Then, however, you might as well use a configuration file of sorts, that you pass as a/the single command line parameter. Both solutions require you to change your code (from normal argument processing), but a plain-text file doesn't require any additional tools to read (except an editor or good old "type" ;-) – Christian.K Jun 17 '11 at 05:49
  • Oh, just recalled one more problem that could be rather nasty. The problem is that `FOR` loop of `CMD.EXE` treats a `=` as a delimiter. Thus if you try to capture the output of your command like so `FOR /F usebackq %i IN (\`my.exe DEADB=\`) echo %i`, which is a common way to do that in batch files, the trailing `=` padding of the base64 block is being removed by CMD.EXE before passed to `my.exe`. This results in an invalid base64 block. You'd have to write it like this `my.exe DEADB^=`. Ugh! – Christian.K Jun 17 '11 at 05:54
  • @Christian: Those are valid points but using files to transfer data has its own issues such as unique naming, folder security, availability (avoiding locks) etc. – Paul Sasik Jun 17 '11 at 06:01