coreutils
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: mkdir inside symlink creates wrong directory with relative parent


From: Loïc Le Loarer
Subject: Re: mkdir inside symlink creates wrong directory with relative parent
Date: Mon, 13 Jun 2011 18:40:36 +0200

Hi Oldřich,

2011/6/13 Oldřich Jedlička <oldium.pro@seznam.cz>
Dne pondělí 13 Červen 2011 16:51:54 Loïc Le Loarer napsal(a):
> This behavior is normal. The key here is the .. link in each directory, it
> always points to the parent directory.
> For example, in your situation, the ".." in z is x, and it cannot be
> something else.
> Even if you access to z using the path x/y/z which use the symbolic link,
> and then use ".." link, you go to x, not y.
>
> You may have the impression that this is not true if you follow the same
> path using your shell, because the shell remember the fact that you use the
> symbolic link and don't really use the ".." link. When you do "cd .." in
> the shell, it just removes the last element between / in the current path.

Thanks for the explanation, that made the things much clearer. I understand
now why the "test -d ../../something" doesn't work under the same conditions
(because the directory really doesn't exist for the program).

But what you say is only part of the story. The script/program has the full
knowledge of the current working directory and it can do the same trick with
the path traversing - remove the ".." in the same way as the shell would do.
This is normal when you canonicalize the path - remove the ".." from the path
and do not try to dereference. The key is that getcwd() returns really the
current working directory with symlinks unresolved - this is how the shell
sees it too.

I have tested this last sentence, and as far as I can see, getcwd is returning resolved path. You can check this by doing a small program calling getcwd system call or by  launching the command "stat /proc/self/cwd", it is doing the same.

In order to know if the current dir which canonical name is "x/z" has been accessed using "cd x/z" or cd "x/y/z", the shell store the access path in PWD. Any script or program can use the PWD variable to mimic the shell behavior (see man get_current_dir_name), but it is not what is expected from mkdir or other basic commands.

When you run the "mkdir ../../dir_xy" command, mkdir command is calling the mkdir system call with "../../dir_xy" argument, and each part of the relative part is resolved by the kernel, the first ".." is pointing to the "x" directory, not the "y". And that's it.

Best regards
Loïc


> I agree that it is a bit strange, but once you understand the fact that
> each directory contains a ".." link which points to one unique location
> and that when the path is interpreted by the kernel, it always follows
> those links, you understand how it works.

Yes. it is strange and the program has the full knowledge to do the right
thing (TM) :-) So I think this can be fixed actually.

Best regards,
Oldrich.

>
> Best regards
> Loïc
>
> 2011/6/13 Oldřich Jedlička <oldium.pro@seznam.cz>
>
> > Hi all,
> >
> > I was trying to search for any description helping me understand in what
> > I see, but actually I didn't find any, so I'm here. I discovered it by
> > using automake-1.11, because it uses relative paths a lot. So my
> > simplified testcase is as follows:
> >
> > Have a directory structure x/y and x/z/a. Have a symbolic link from x/y/z
> > that points to x/z.
> >
> >   mkdir -p x/y
> >   mkdir -p x/z/a
> >   ln -s ../z x/y/z
> >
> > Now go into x/y/z/a and try to create directory like that:
> >   cd x/y/z/a
> >   mkdir ../dir_xyz
> >   mkdir ../../dir_xy
> >   mkdir ../../../dir_x
> >
> > I would expet that there would be a directory like this:
> >   x/dir_x
> >   x/y/dir_xy
> >   x/y/z/dir_xyz (x/z/dir_xyz)
> >
> > But the result is completely different:
> >   dir_x
> >   x/dir_xy
> >   x/y/z/dir_xyz (x/z/dir_xyz)
> >
> > So when you want to create a directory in the parent structure from
> > within the symbolic link, you will fail in doing so, because the
> > symbolic link would be resolved during walking through parents, so you
> > can get to completely different tree while creating your directory. It
> > looks like a bug, because it is nowhere documented to behave like that
> > (and the behaviour is strange by itself).
> >
> > Verified on Debian 4.0/RedHat 5.4 with coreutils 5.97 and on Gentoo with
> > coreutils 8.12.
> >
> > Regards,
> > Oldrich.



--
Loïc

reply via email to

[Prev in Thread] Current Thread [Next in Thread]