cygpath unable to translate the *nix path to an NTFS junction point

Corinna Vinschen
Wed Nov 24 13:07:00 GMT 2010

On Nov 24 14:24, Pierce Morton wrote:
> I took a look at the behaviour of cygpath when using cygwin symlinks
> and I understand now why it does what it does with junction points.
> Consistency between the two seems reasonable if that was its existing
> behaviour before junction support was added.
> However, the behaviour of cygpath is not entirely consistent between
> junctions and symlinks.
> Let's say you have the structure
> c:\example\targ
> c:\example\targ\subfolder
> c:\example\junc
> c:\example\sym
> where targ and its child are real folders, junc is junction point
> leading to targ, and sym is a cygwin symlink leading to targ.
> cd /cygpath/c/example
> cygpath -w -a junc
> cygpath -w -a sym
> both cygpath calls produce
> c:\example\targ
> The same happens with calls like
> cygpath -w /cygdrive/c/example/junc
> cygpath -w /cygdrive/c/example/sym
> Go inside the subfolder via the junction point:
> cd /cygdrive/c/example/junc/subfolder
> and call cygpath again to find the absolute path:
> cygpath -w -a .
> and you're given:
> c:\example\junc\subfolder
> Try this with the symlink however:
> cd /cygdrive/c/example/sym/subfolder
> cygpath -w -a .
> and you'll get
> c:\example\targ\subfolder
> One uses the dereferenced path, and one uses the symbolic path.

That's not the fault of cygpath.  The core functionality is the
POSIX->Win32 path evaluation code in Cygwin.  In contrast to other POSIX
systems, Cygwin evaluates the path from right to left(*).  The
evaluation stops as soon as the path exists, or the entire path has been
evaluated.  The path exists, if a test using *Windows* functions returns
successfully.  Maybe you already suspect what happens, butI try to show:

In case of the Cygwin symlink:

  Incoming path  ->  /cygdrive/c/example/sym/subfolder

  - Convert slashes to backslashes
  - Mount point evaluation  ->  C:\example\sym\subfolder
  - File exists?  No. (because there's no directory called "sym" from
    the Windows perspective)
  - Strip basename  ->  C:\example\sym
  - File exists?  Yes.
  - Symlink?  Yes.
  - Replace path with symlink content  ->  /cygdrive/c/example/targ
  - Attach stripped part -> /cygdrive/c/example/targ/subfolder
  And restart

  - Convert slashes to backslashes
  - Mount point evaluation  ->  C:\example\targ\subfolder
  - File exists?  Yes.

In case of the junction:

  Incoming path  ->  /cygdrive/c/example/junc/subfolder

  - Convert slashes to backslashes
  - Mount point evaluation  ->  C:\example\junc\subfolder
  - File exists?  Yes.  (because the Windows function evaluates the
    junction point internally)


(*) Which is *wrong* from a POSIX POV.  It leads to subtil differences
    when evaluating symlinks, as in your example.  However, the core
    loop of the path evaluation code is very old, and to make it fully
    POSIX compliant requires a complete rewrite.  We just never got
    around to do that so far.

Corinna Vinschen                  Please, send mails regarding Cygwin to
Cygwin Project Co-Leader          cygwin AT cygwin DOT com
Red Hat

Problem reports:
Unsubscribe info:

More information about the Cygwin mailing list