]> git.ipfire.org Git - thirdparty/util-linux.git/commitdiff
namei: fix relative symlinks evaluation
authorKarel Zak <kzak@redhat.com>
Fri, 20 Apr 2012 13:06:57 +0000 (15:06 +0200)
committerKarel Zak <kzak@redhat.com>
Fri, 20 Apr 2012 13:06:57 +0000 (15:06 +0200)
Fedora 17 (/bin is symlink to /usr/bin):

[root@intel ~]# /bin/namei /bin/namei
f: /bin/namei
 d /
 l bin -> usr/bin
usr - No such file or directory

Reported-by: Jan Stancek <jstancek@redhat.com>
Signed-off-by: Karel Zak <kzak@redhat.com>
misc-utils/namei.c

index 9b8ede901a9f56667893820e6f9ed029130dc5b4..b15d4f7b6505d20dd689dffc915dbb49be7889b3 100644 (file)
@@ -180,6 +180,7 @@ readlink_to_namei(struct namei *nm, const char *path)
 {
        char sym[PATH_MAX];
        ssize_t sz;
+       int isrel = 0;
 
        sz = readlink(path, sym, sizeof(sym));
        if (sz < 1)
@@ -187,20 +188,26 @@ readlink_to_namei(struct namei *nm, const char *path)
        if (*sym != '/') {
                char *p = strrchr(path, '/');
 
-               nm->relstart = p ? p - path : 0;
-               if (nm->relstart)
+               if (p) {
+                       isrel = 1;
+                       nm->relstart = p ? p - path : 0;
                        sz += nm->relstart + 1;
+               }
        }
        nm->abslink = xmalloc(sz + 1);
 
-       if (*sym != '/' && nm->relstart) {
+       if (*sym != '/' && isrel) {
                /* create the absolute path from the relative symlink */
                memcpy(nm->abslink, path, nm->relstart);
                *(nm->abslink + nm->relstart) = '/';
                nm->relstart++;
                memcpy(nm->abslink + nm->relstart, sym, sz - nm->relstart);
        } else
+               /* - absolute link (foo -> /path/bar)
+                * - or link without any subdir (foo -> bar)
+                */
                memcpy(nm->abslink, sym, sz);
+
        nm->abslink[sz] = '\0';
 }