ProgrammingThis forum is for all programming questions.
The question does not have to be directly related to Linux and any language is fair game.
Notices
Welcome to LinuxQuestions.org, a friendly and active Linux Community.
You are currently viewing LQ as a guest. By joining our community you will have the ability to post topics, receive our newsletter, use the advanced search, subscribe to threads and access many other special features. Registration is quick, simple and absolutely free. Join our community today!
Note that registered members see fewer ads, and ContentLink is completely disabled once you log in.
If you have any problems with the registration process or your account login, please contact us. If you need to reset your password, click here.
Having a problem logging in? Please visit this page to clear all LQ-related cookies.
Get a virtual cloud desktop with the Linux distro that you want in less than five minutes with Shells! With over 10 pre-installed distros to choose from, the worry-free installation life is here! Whether you are a digital nomad or just looking for flexibility, Shells can put your Linux machine on the device that you want to use.
Exclusive for LQ members, get up to 45% off per month. Click here for more info.
8. The curpath value shall then be converted to canonical form as follows, considering each component from beginning to end, in sequence:
...
b. For each dot-dot component, if there is a preceding component and it is neither root nor dot-dot, the preceding component, all slashes separating the pre-
ceding component from dot-dot, dot-dot and all slashes separating dot-dot from the following component shall be deleted.
I missed your suse response. That would probably indicate a difference between the two families of Linux. Your excerpt does make sense; if it is from the man page for cd on your system then I would say there is your answer.
I think /mnt/sdb8/sergei/AFSWD_debug/20120424/libproxy-0.4.7/.../ must exist for that to work. Unless SuSE applies some very unsafe patches to its path resolution code.
In particular, cd /foo/.../../bar/ does not work on any of my systems (Debian and RHEL variants, no SuSE), when /foo/bar/ exists but /foo/.../ does not. (The cd(1) man page does have the same dot-dot handling description.)
Last edited by Nominal Animal; 05-08-2012 at 09:58 PM.
I think /mnt/sdb8/sergei/AFSWD_debug/20120424/libproxy-0.4.7/.../ must exist for that to work. Unless SuSE applies some very unsafe patches to its path resolution code.
In particular, cd /foo/.../../bar/ does not work on any of my systems (Debian and RHEL variants, no SuSE), when /foo/bar/ exists but /foo/.../ does not. (The cd(1) man page does have the same dot-dot handling description.)
It apparently exists and shows up as a regular directory:
Code:
sergei@amdam2:~/junk> cd /mnt/sdb8/sergei/AFSWD_debug/20120424/libproxy-0.4.7/.../
sergei@amdam2:/mnt/sdb8/sergei/AFSWD_debug/20120424/libproxy-0.4.7/...> pwd
/mnt/sdb8/sergei/AFSWD_debug/20120424/libproxy-0.4.7/...
sergei@amdam2:/mnt/sdb8/sergei/AFSWD_debug/20120424/libproxy-0.4.7/...> ls
sergei@amdam2:/mnt/sdb8/sergei/AFSWD_debug/20120424/libproxy-0.4.7/...> ls -A
sergei@amdam2:/mnt/sdb8/sergei/AFSWD_debug/20120424/libproxy-0.4.7/...> cd
sergei@amdam2:~> cd /mnt/sdb8/sergei/AFSWD_debug/20120424/libproxy-0.4.7/.../
sergei@amdam2:/mnt/sdb8/sergei/AFSWD_debug/20120424/libproxy-0.4.7/...> pwd
/mnt/sdb8/sergei/AFSWD_debug/20120424/libproxy-0.4.7/...
sergei@amdam2:/mnt/sdb8/sergei/AFSWD_debug/20120424/libproxy-0.4.7/...> ls -a
. ..
sergei@amdam2:/mnt/sdb8/sergei/AFSWD_debug/20120424/libproxy-0.4.7/...> cd ..
sergei@amdam2:/mnt/sdb8/sergei/AFSWD_debug/20120424/libproxy-0.4.7> ls -F
___ALREADY_BUILT___.libproxy-0.4.7 bin/ binsh/ include/ lib/ libproxy-0.4.7.dirs_with_so_or_a_files.prl libproxy-0.4.7.PATH.txt libproxy.py share/
sergei@amdam2:/mnt/sdb8/sergei/AFSWD_debug/20120424/libproxy-0.4.7> ls -Fa
./ ../ .../ ___ALREADY_BUILT___.libproxy-0.4.7 bin/ binsh/ include/ lib/ libproxy-0.4.7.dirs_with_so_or_a_files.prl libproxy-0.4.7.PATH.txt libproxy.py share/
sergei@amdam2:/mnt/sdb8/sergei/AFSWD_debug/20120424/libproxy-0.4.7>
.
Maybe it is created as a temporary hidden directory by 'make install', and later on files are moved from there to their final destinations ?
I yet to have to parse the quoted manpage piece.
Last edited by Sergei Steshenko; 05-09-2012 at 05:19 AM.
Maybe it is created as a temporary hidden directory by 'make install', and later on files are moved from there to their final destinations ?
I think you are spot on. Usually, the temporary install directory is something like .libs , or .$builddir . Since this package is configured via cmake .. (I think), perhaps the temporary install directory name is constructed by prepending a dot to the parameter to configuring cmake, yielding ... simply by accident?!
Quote:
Originally Posted by Sergei Steshenko
I yet to have to parse the quoted manpage piece.
In any case, the quoted passage is incorrect in practice.
Path resolution does not simply apply s|/\+\([^/]+\)/\+\.\./\+|/|g (repeatedly) to the path to remove /../ components, because that would be a security risk.
In most cases, a path is assumed to be valid component-wise. That is, you should be able to trim a component off the end of the path, and end up in an existing, accessible directory, if the full path was accessible. If you allow nonexistent path components, that no longer applies.
The same rule applies when a component exists, but is inaccessible. Consider path /foo/bar/../baz/ where /foo/baz/ exists and is accessible, and /foo/bar/ also exists but is inaccessible. Because paths should be valid component-wise in practice, the original path should NOT be accessible.
I suspect this behaviour is implicitly standardized in POSIX; perhaps there is a passage that states that all components in a path must be accessible for the complete path to be accessible?
Unfortunately I'm too lazy to check. I first became aware of this almost a decade ago, when I was researching why Apache does so many directory lookups. (Partly due to this, partly due to .htaccess files and <Directory> directives.)
@AnanthaP: You mean old Novell Netware accepted paths like foo\bar\..\baz as long as foo\baz existed even if foo\bar did not?
As it turns out, POSIX.1-2008 (IEEE Std 1003.1™-2008) realpath() function (which applications are supposed to but not required to use to canonicalize a path before doing any manipulations to it), does specify the explicit behaviour that I described earlier -- that foo/bar/../baz is accessible only if both foo/bar and foo/baz exist and are accessible:
Quote:
The realpath() function shall fail if: Read or search permission was denied for a component of file_name [, or a] component of the path prefix is not a directory
In Linux, the kernel applies the same rule to all path resolution.
".." is a hard link to the parent directory, except in "/", which has ".." as a hard link to ".". While this might only be "simulated", processing the text of the pathname won't always be accurate. Suppose you had "/home/you/dir" -> "/". If you only went by the text, cd ~/dir/../home wouldn't work unless there was a "/home/you/home". Processing the text would also result in different behavior within C programs since presumably there isn't a kernel option to treat "..." specially. Also, I really wonder why there's a manpage for cd and why it could be different on another distro, since as far as I know cd can only work as a built-in (short of some procfs magic that I don't know about.) The manpage I have for cd is for a tcl built-in.
Kevin Barry
".." is a hard link to the parent directory, except in "/", which has ".." as a hard link to ".". While this might only be "simulated", processing the text of the pathname won't always be accurate.
If you process each component separately, building upon the path component by component, it will be logically correct.
Quote:
Originally Posted by ta0kira
Suppose you had "/home/you/dir" -> "/". If you only went by the text, cd ~/dir/../home wouldn't work unless there was a "/home/you/home".
I don't understand that statement. POSIX.1-2008 realpath() and the Linux kernel path resolution handles that just fine by the text. ~/dir/../home is expanded by the shell to /home/you/dir/../home (~ is not special to the kernel nor realpath()), which is resolved in five steps:
/home
/home/you
/home/you/dir
At this point, the resolved location is at / for both realpath() and the Linux kernel.
/home/you/dir/..
The parent directory always exists, even at root. The resolved location stays at root for both realpath() and the Linux kernel.
/home/you/dir/../home
Since the resolved location has a subdirectory home (as resolved already in the first step), this resolves to the exact same location as the first step.
I cannot find any contradiction between this behaviour and the POSIX.1-2008 text I quoted!
Quote:
Originally Posted by ta0kira
Processing the text would also result in different behavior within C programs since presumably there isn't a kernel option to treat "..." specially.
What? Like I said, every path component must exist and be accessible, for the path to exist and be accessible. This applies to both the Linux kernel, and POSIX.1-2008 realpath() function. (I have not bothered to check whether this is required by POSIX.1-2008 for all filesystems.)
Quote:
Originally Posted by ta0kira
Also, I really wonder why there's a manpage for cd and why it could be different on another distro, since as far as I know cd can only work as a built-in (short of some procfs magic that I don't know about.) The manpage I have for cd is for a tcl built-in.
Because the cd utility is in the POSIX standard. Regardless of how it is implemented, its functionality should be the same for users. This functionality is what the man page describes. (And as such, it is part of the POSIX man pages.)
LinuxQuestions.org is looking for people interested in writing
Editorials, Articles, Reviews, and more. If you'd like to contribute
content, let us know.