difficult problem with symbolic link handling

Corinna Vinschen vinschen@redhat.com
Sun Apr 29 15:18:00 GMT 2001

Somehow your latest changes to path.cc break check_case.

Try to start a shell with CYGWIN=... check_case=adjust

and call `ls -ld .'

ls: .: No such file or directory.


On Sat, Apr 28, 2001 at 01:07:48PM -0400, Christopher Faylor wrote:
> [long explanation follows]
> Someone recently pointed out a problem with "1.3.1 symbolic link handling".
> In reality, AFAICT, this is a long-standing problem with cygwin's symbolic
> problem.  It's at least a year old and probably older.
> The pathological case was the /usr/lib/terminfo link.  /usr/lib/terminfo
> is a link to ../share/terminfo.
> The problem with that is that /usr/lib is a link to /lib.  So Cygwin's
> current symbolic link handling does this:
> 1) Convert /usr/lib/terminfo to (for example) f:\cygwin\lib\terminfo.
> 2) Read f:\cygwin\link\terminfo and retrieve the value ../share/terminfo.
> 3) Bite off the trailing path component and change this to:
>    f:\cygwin\lib\..\share\terminfo.
> 4) "Canonicalize" this path to f:\cygwin\share\terminfo.
> 5) Does this file exist?  No.  Return an error.
> As you can see this is an "error" in cygwin's file handling.
> I've "fixed" this problem by doing the following:
> 1) Canonicalize /usr/lib/terminfo -> /usr/lib/terminfo
> 2) Pass /usr/lib/terminfo to symlink lookup which converts this
>    to the MS-DOS equivalent f:\cygwin\lib\terminfo.
> 3) Return "../share/terminfo"
> 4) Bite off trailing path component and change this to:
>    "/usr/lib/../share/terminfo"
> 5) Goto 1, which converts this to "/usr/share/terminfo", eventually
>    exiting the loop with "success" when the file is found.
> On the face of it, this seems to be the right thing to do, but there are
> some problems.  One problem is that step 2 is called repeatedly in this
> new scenario.  This is a fairly expensive scan of cygwin's mount table
> (which involves a gratuitous canonicalize that was already done in step
> 1).  Another more serious problem is that there is ambiguity in the
> parsing.
> What if /usr/lib/terminfo had a mount table entry of:
> f:\foo\bar\blaz\terminfo
> and blaz was a symlink?  That would not be handled in my "improved"
> filename scanning above because f:\foo\bar\blaz\terminfo wouldn't
> actually exist.  That doesn't bother the current process but the
> "improved" process would notice that it didn't exist and start trying to
> find a prefix to /usr/lib/terminfo that did exist.
> So, it would do a:
> /usr/lib/terminfo
>     doesn't exist, try:
> 	/usr/lib
> 	    exists, is is a symbolic link?
> 		No, /usr/lib/terminfo doesn't exist
> So, basically, what this means is that symlinks won't work in the mount
> table, where they did before.
> Does anyone have any problems with this new behavior?  IMO, this new
> way is more correct but I have a nagging feeling that I may be missing
> something.
> cgf

Corinna Vinschen                  Please, send mails regarding Cygwin to
Cygwin Developer                                mailto:cygwin@cygwin.com
Red Hat, Inc.

More information about the Cygwin-developers mailing list