This is the mail archive of the cygwin mailing list for the Cygwin project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

1.5.21-1: CIFS symlinks on network share break Cygwin


Brief summary, before I get into details:  Cygwin 1.5.21-1 on WinXP SP2
was working perfectly, until a new CIFS server was installed on our LAN.
Since then, some apps won't run, directories won't list, and many
Cygwin-compiled applications are failing to recognize the correct file
size, including coreutils like ls, etc.  Because of this, many
applications aren't working properly anymore.  All native non-Cygwin
apps continue to function perfectly with the new server; however, Cygwin
stopped working properly - applications and shell scripts that used to
work perfectly were now falling over themselves.  The common factor to
all failures: they are all symbolic links on the CIFS server.  Typical
failure modes were as follows:

Running applications that are CIFS symlinks now fails:
jlanier@yoga-dog [~] > audpp
      8 [main] tcsh 5752! _pinfo::dup_proc_pipe: DuplicateHandle failed,
pid 5752, hProcess 0x701, wr_proc_pipe 0x75C, Win32 error 6 This program
cannot be run in DOS mode.

Directories that are CIFS symlinks can no longer be listed:
jlanier@yoga-dog [~] > ls -dl dirsymlink drwxr-xr-x 22 jlanier Domain
Users 0 Oct 20 22:35 dirsymlink jlanier@yoga-dog [~] > cd dirsymlink
jlanier@yoga-dog [~/dirsymlink] > ls
ls: .: No such file or directory

Under a CMD.EXE prompt, I could easily run the app and list the
directory, so it doesn't seem to be an OS or networking problem.

I checked the mailing list archives and found nothing similar; I also
scanned the web and found nothing.  I started to post a question here,
scanned for the etiquette, found something somewhere (which I since have
not been able to find) that said if I was a programmer I should try to
figure out more about the problem before posting (darn!), and I am, so I
did.  What I've discovered truly confounds me.  I'm posting what I've
figured out so far in the hopes that someone can replicate the problem,
and determine what is responsible.

First, you should know that we use a lot of *nix-based systems here;
they connect to the same CIFS-based server, and depend on the Unix
extended support to manage symlinks, etc.  This is all working
perfectly; I can create, manage, and delete symlinks on this server via
my Linux machine with no problem.  Windows sees these symlinked files on
the CIFS share as if they were native files - this also works perfectly.
In fact, we depend on using *nix machines to create and manage symlinks
that are accessed via WinXP machines as regular files; this is how we
manage version control for our development.

For some reason, when running a Cygwin-based application, calls to OS
file support functions are returning unexpected results.  Specifically,
Cygwin apps are seeing the file attributes and file size of the symlink,
not of the target of the symlink.  This causes the application failure
listed above whenever the application itself is a symlink; if the same
application is copied to a regular file, Cygwin then runs the file
correctly.  I believe that somehow, the Cygwin process responsible for
spawning the new application is failing to load the executable file due
to the fact that it appears truncated.  The failure to list the
directory contents was traced to a failure to have the
FILE_ATTRIBUTE_DIRECTORY bit set, due to the fact that a call to
GetFileAttributes() is returning 0x80 (FILE_ATTRIBUTE_NORMAL) for any
directory that is a symlink.  Using the ls command from a Cygwin shell
prompt always lists file sizes for symlinks as the symlink size, not the
file the link points to.  Using the CMD.EXE dir command always reports
the true file size, for the same file, even if it is a CIFS symlink.

How this is happening, I can't possibly imagine, as a native Win32 app
can't even see this information - Windows doesn't currently support
symlinks (ignoring junctions, and the future Longhorn), so I can't
imagine where Cygwin would even get this information.  After all, Cygwin
is just accessing the network via the WinXP SMB client.  So, I decided
to write a small application (see attached) to test calling the
GetFileAttributes() and GetFileAttributesEx() functions directly,
thinking I would bypass Cygwin1.dll and see if I could check the real
file size.  At the same time, I print out the results of stat(), which
does route through Cygwin, as a sanity check.  I built the application 3
ways: with with MSVC (cl filetest.cpp), gcc/Cygwin (gcc filetest.cpp),
and gcc/mingw (gcc -mno-cygwin filetest.cpp).  The results indicate that
both the MSVC and mingw versions match perfectly, and report the
expected information properly; the directory bit is set on directory
symlinks, and file sizes are the size of the final target of the link,
not the link itself.  However, the Cygwin version reports completely
different information, which is really surprising considering that
GetFileAttributes/Ex are imported directly from kernel32.dll.

Here is the resuling output from the 3 apps against a directory, then a
file, all from a CMD.EXE prompt (Cygwin behavior was identical when run
in a Cygwin shell):

Y:\test>vcfiletest y:\dirsymlink
Checking file "y:\dirsymlink"...
GetFileAttributesEx(): attr=0x00000010, size=0
stat(): mode=0x41ff, size=0

Y:\test>vcfiletest y:\filesymlink.exe
Checking file "y:\filesymlink.exe"...
GetFileAttributesEx(): attr=0x00000020, size=290816
stat(): mode=0x81ff, size=290816

Y:\test>mingwfiletest y:\dirsymlink
Checking file "y:\dirsymlink"...
GetFileAttributesEx(): attr=0x00000010, size=0
stat(): mode=0x41ff, size=0

Y:\test>mingwfiletest y:\filesymlink.exe Checking file
"y:\filesymlink.exe"...
GetFileAttributesEx(): attr=0x00000020, size=290816
stat(): mode=0x81ff, size=290816

Y:\test>cygfiletest y:\dirsymlink
Checking file "y:\dirsymlink"...
GetFileAttributesEx(): attr=0x00000080, size=25
stat(): mode=0x41ed, size=0

Y:\test>cygfiletest y:\filesymlink.exe
Checking file "y:\filesymlink.exe"...
GetFileAttributesEx(): attr=0x00000080, size=43
stat(): mode=0x81ed, size=43

Interesting points to note: If the executable symlink is renamed to
remove its extension, the file size reported returns to the orignal
expected size.  Also, the current documentation for the Win32 SDK on the
GetFileAttributes/Ex functions (http://tinyurl.com/uy6rw) has an
interesting statement in the "Remarks" section:

"Symbolic link behavior-If the path points to a symbolic link, the
function returns attributes for the symbolic link."

Huh.  That's nice.  Unfortunately, it is not desired behavior for a
Cygwin app; at a minimum, it clearly does not bode well for current
Cygwin compatibility on Longhorn, though it does raise the interesting
prospect of having proper native symlink support in the Windows OS that
might be possible to incorporate into some future version of Cygwin.  We
aren't using any Longhorn systems here at all; but, since our new server
is network-attached-storage using CIFS, it may be implementing newer
protocols.

I checked the PE headers for some kind of magic bit or something that
might clue Windows into enabling this behavior for certain apps, but I
found nothing.  So, unless Cygwin is mucking around with KERNEL32.DLL
exports (which I don't think it is), the behavior of
GetFileAttributes(), GetFileAttributesEx(), and probably several other
API functions, is completely different when running under Cygwin for no
reason that I can determine.

Does anyone know why the behavior of KERNEL32 API functions would behave
differently for Cygwin apps?  Is there any kind of behind-the-scenes
library hooking going on that I'm unaware of?  Can anyone repeat this
behavior?  I'm at a loss to provide any additional information, but
hopefully someone who knows more about the guts of Cygwin will get some
ideas based on what I've posted, and be able to dig deeper into the
problem.

Thanks,
- Jonathan Lanier

Attachment: filetext.src
Description: filetext.src

Attachment: cygcheck.out
Description: cygcheck.out

--
Unsubscribe info:      http://cygwin.com/ml/#unsubscribe-simple
Problem reports:       http://cygwin.com/problems.html
Documentation:         http://cygwin.com/docs.html
FAQ:                   http://cygwin.com/faq/

Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]