Bash in Git for Windows: Weirdness when running a command with CMD.exe /C with args

自作多情 提交于 2019-11-28 05:53:10

This is actually documented in the ReleaseNotes file (in the top level folder of your installed Git for Windows)

Also, extra care has to be paid to pass Windows programs Windows paths, as they have no clue about MSys style POSIX paths -- You can use something like $(cmd //c echo "$POSIXPATH").

If you use cmd //c echo test it works as expected.

$ cmd //c echo test
test

The cause is to do with trying to ensure that posix paths end up being passed to the git utilities properly. For this reason, Git for Windows includes a modified MSYS layer that affects command arguments. You should note that it is not intended that the bash shell and tools provided with Git for Windows be used as general purpose unix tools for Windows. If you want a general purpose unix-style toolset then you should install MSYS or cygwin. The Git Bash shell is setup for working with git and sometimes that shows.

avb1003

After reading this article I've found solution which works for me:

$ cat gvim.sh
cmd << EOD
gvim $@
EOD
$

Windows 8.1, Git (version 1.9.5-preview20141217), GNU bash, version 3.1.20(4)-release (i686-pc-msys).

I am able to mostly reproduce the problem using gnu bash for Windows.

I can't quite establish a pattern with the first form without any quotes. It seems to work with the Windows ECHO command, but not with other commands like DIR. EDIT - It turns out gnu bash is putting quotes around my command, so echo test becomes "echo" "test". The quotes cause cmd.exe to look for an external command instead of the internal ECHO command. I happen to have "echo.exe", so it appears to run. The odd thing is the quotes around test are not displayed. When I attempt to run the DIR command, it fails entirely because there isn't any DIR.EXE.

The subsequent forms with quotes (except the last one), or escaped spaces, work the same as you are seeing - there is an unwanted trailing quote in the command.

I could not come up with a clean solution. However, I have an ugly hack that should give you the desired result. Simply concatenate a REM command at the end of your command. The REM will comment out the unwanted trailing quote. It is important that there be a space after REM, otherwise REM" will not be recognized as a valid command. Any of the following should work.

$ cmd '/c echo test&rem '
$ cmd "/c echo test&rem "
$ cmd /c\ echo\ test\&rem\ 

Note that the last command has a space after the backslash.

The technique should work for pretty much any command string that you might want to execute via CMD.EXE.

Michel de Ruiter

I noticed git-bash treats the /c argument like a C: drive:

C:\Windows\system32\cmd.exe C:/ echo test

As dbenham found double quotes are added. This echos test" for example:

cmd /c\ echo\ test

I needed the same line (script) to work in git-bash as well as Cygwin Bash. The only ways that work are

cmd /c\ echo\ test\&rem\ 

(note that this line needs to end in a space), and

cmd << EOC
echo test
EOC

So escape every space after the /c and add \&rem\  at the end of the line (including the trailing space), or just wrap the command in a here document.

All this probably depends on the version of git-bash and the specific commands. :-(

Because you mention that you're using the Git for Windows bundle, I figured I'd point out that it includes winpty, which seems to be quite readable.

$ winpty echo test
test

$ site="Default Web Site"
$ winpty 'C:\Windows\System32\inetsrv\appcmd' list site "${site}" /text:ID
1

This seems to work under 1.9.5.msysgit.1

!foo=`bar`
cmd //c \\\\unc-path\\with\\slashes -args \"Quoted Arguments $foo\"
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!