This is the mail archive of the
mailing list for the Cygwin project.
Re: PATHEXT is fundamental to Windows and Should be recognised by CYGWIN
- From: Kaz Kylheku <kaz at kylheku dot com>
- To: Michel LaBarre <michel dot labarre at rogers dot com>
- Cc: cygwin at cygwin dot com
- Date: Wed, 03 Aug 2016 19:54:32 -0700
- Subject: Re: PATHEXT is fundamental to Windows and Should be recognised by CYGWIN
- Authentication-results: sourceware.org; auth=none
- References: <email@example.com>
On 03.08.2016 18:43, Michel LaBarre wrote:
Problem 1: Cygwin does not support PATHEXT and really should.
A casual websearch shows that this topic has come up before.
For instance, someone posted, some decade ago, to the Cygwin mailing
list, a patch against GNU Bash to make its command search algorithm
take PATHEXT into account.
Fundamental reason: from the Cygwin FAQ - What is it? "Cygwin is a
distribution of popular GNU and other Open Source tools running on
PATHEXT is as fundamental component of Windows program execution as
I can't find any reference anywhere to PATHEXT being used outside
of the CMD.EXE interpreter, which rather tends to make it substantially
less than fundamental to Windows, though noteworthy.
Certainly, CreateProcess does not use PATHEXT.
I can't find any documentation which says that ShellExecuteEx
uses PATHEXT, either. (Can anyone confirm?)
Everything points to it being a CMD.EXE "gizmo". If you want to execute
a command such that PATHEXT is taken into account, you have to spawn
CMD.EXE /C <yourcommand>.
Cygwin provides a POSIX environment on Windows. Users of a POSIX
environment don't expect a command "foo" to resolve to a file
"foo.bat". If they want to run "foo.bat" they use "foo.bat".
Without using extensions, bash can use execution privileges to
a file is executable. However, that does not work when invoking a
What does not work from CMD is Microsoft's problem, not Cygwin's.
Yes, even though you have a "myscript.sh" and you do "chmod a+x
inside Cygwin, the outside Windows world doesn't agree that myscript.sh
is now executable, and that it uses /bin/sh by default as its
if a #! line is absent, otherwise the interpreter nominated by the #!
Adding ".sh" to PATHEXT might work in causing CMD.EXE to resolve
"myscript" to "myscript.sh"; however, it will not then successfully
execute "myscript.sh", because the underlying CreateProcess API
will not find it executable.
CMD.EXE will probably *try* to execute it, and fail.
This means that when invoked from BASH, you name a command "ZOT"
but "ZOT.sh" (or similar) if invoked from CMD.
From CMD, you have do something explicit like this:
That is, you have to run Bash, and pass it the script as an argument.
Windows and CMD.EXE will not associate .sh with Bash and certainly
won't look at any #! line you may have in the script.
Not supporting arbitrary interpreters for scripts is a Windows
Cygwin overcomes that limitation within its "garden".
If you solve the entry point problem of how to invoke Cygwin code
from the outside, once you are in Cygwin land, you have no further
problems. Scripts marked executable and containing #! use their
respective interpreters and so on.
The published solutions in
the various FAQs are not satisfactory. Creating links between ZOT.sh
creates substantial overhead.
I don't think that will work, unless by "creating a link" you mean
that you create a ZOT.BAT file shim which invokes the neighboring
ZOT.sh by passing its full path to bash.exe.
If CYGWIN really intends to support Windows
it should support its fundamental execution framework. It should be
easy to invoke a bash script from a bash script or a CMD script.
What you need on Windows is a script-to-EXE application deployment tool,
which takes your "script.sh" and combines it with a copy of a special
binary executable, and writes out the combination to "script.exe".
Then even a raw CreateProcess Win32 API call can invoke "script.exe".
Problem 2: Cygwin does not support CR-LF delimiters. For the same
it is unfortunate that CYGWIN/bash does not cope with both types of
The way Cygwin deals with CR/LF has evolved over time, and there
are various ways to deal with this, depending on the specific
Firstly, the binary mode default treatment for files comes
from the mount table:
C:/Cygwin/bin on /usr/bin type ntfs (binary,auto)
C:/Cygwin/lib on /usr/lib type ntfs (binary,auto)
C:/Cygwin on / type ntfs (binary,auto)
C: on /cygdrive/c type ntfs (binary,posix=0,user,noumount,auto)
See how that /cygdrive/c is mounted "binary" (as is everything else?)
That's what causes text files to be treated as LF rather than CR/LF.
That can be altered; you can mount some Windows path into Cygwin's
POSIX file system view as text, and then CR/LF conversion is done.
Then, secondly, there are approaches for individual C programs.
If you're porting something written in C,
the C library in Cygwin supports the "t" flag in
fopen and related functions. This is similar to the Microsoft
extension, found in the Visual C run-time library.
In ISO C, if you omit the "b" mode, then a file is open in text
mode, but on POSIX that is the same as binary mode. In Cygwin, if
you specify "t", you get the Windows text mode, CR/LF. Without "t"
or "b", I think it defaults to the mode from the mount table. So if
you're working on porting a C program, that's one tool in your arsenal.
As an alternative to introducing "t" into C programs, there
is a link-time method. Cygwin provides several special .o
object files that can be specified when linking
a C program, which change its treatment of files in this regard.
Note that some standard utilities for processing text, though
written in C, do not use the C stdio library. So they don't
respond to these mechanisms. For instance GNU Awk does its
own I/O, and that is LF terminated.
Problem reports: http://cygwin.com/problems.html
Unsubscribe info: http://cygwin.com/ml/#unsubscribe-simple