latest cygwin: 'run' problem

Achim Gratz
Tue Sep 9 09:15:00 GMT 2014

Gary Johnson writes:
> After much fiddling (programming by successive approximation),

You should drop the cargo-cult programming before it hurts you.

> I came up with this:
>     @START "" "C:\cygwin\bin\mintty.exe" /bin/bash --login -c "cd $(cygpath -u $0); exec bash -i" "%~p1\"

You want at least %~dp1 there (in an CMD window, type HELP CALL).  But
you can start mintty directly from the shortcut without any intervention
of START or run and you don't need a batch file or shell script either.
Things get a lot simpler if you cut out the intermediaries, although you
still need to be careful.  If you go through CMD or a shell script,
there are more levels of quoting involved and more processes to start.
Doing this through both a CMD and a shell script is seriously
overcomplicated and keeping track of what needs to go where is much more
difficult to figure out, so just don't do it.

> Using an explicit path to mintty lets me put the script itself
> someplace other than /bin.
> Because %~p1 ends with a backslash, I had to add another backslash
> before the closing quote to prevent the quote from being included in
> the path.  (See and
> I haven't tried it yet with a path that includes a space.  Tomorrow.

It won't work because you did not quote the result from cygpath.

If you want to get this right, you should work it out from the inside.
You want the cd command to get a directory name from a subcommand that
may contain spaces, so you need to quote the result:

cd "$( ... )"

Since the argument you're getting may actually be a filename, you need
to use the dirname command and quote its argument again:

cd "$(/bin/dirname "$(...)")"

and dirname gets its argument from cygpath, and the argument to cygpath
must itself be quoted again:

cd "$("$(/bin/dirname "$(/bin/cygpath -u "$1")")")"

If that suceeds you want to replace the current interpreter with an
interactive bash:

cd "$("$(/bin/dirname "$(/bin/cygpath -u "$1")")")" && exec /bin/bash -i

That is in entirety the command that you need to give to the "-c" option
of the outer bash invocation as a single argument.  The remaining
arguments are filled in from $0 and since I specified $1 to cygpath,
there's a dummy parameter to be placed, let's call it "BashHere".  So
that outer bash needs to get started like this:

/bin/bash -lc cmd_argument BashHere dir_argument

Since you're actually starting it from a shortcut, you need to keep in
mind that the quoting rules for the shortcut target are those of the MS
CRT, which means you need to wrap single arguments containing whitespace
in double quotes and then backslash escape any double quotes (and
backslashes, of which we don't have any) inside those arguments.  This
will then be put into argv from mintty, which will exec bash with those
arguments it didn't consume itself, which means there needs to be no
extra level of quoting.  So that shortcut target becomes (undo the

C:\Freeware\Cygwin\bin\mintty.exe -e
 "cd \"$(\"$(/bin/dirname \"$(/bin/cygpath -u \"$1\")\")\")\"
 && exec /bin/bash -i" BashHere

The dir_argument gets filled in as the last argument by the drag&drop or
SendTo operation.

+<[Q+ Matrix-12 WAVE#46+305 Neuron microQkb Andromeda XTk Blofeld]>+

Factory and User Sound Singles for Waldorf Blofeld:

Problem reports:
Unsubscribe info:

More information about the Cygwin mailing list