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

[Libguestfs] [PATCH] fuse: resolve absolute links to relative ones



First it strips /sysroot and then finds common prefix aligned
on slashes. Next it produces ../ for each slash found in common
prefix and concatenates them with the rest of resolved link.

Fixes RHBZ#604041
---
 src/fuse.c | 33 ++++++++++++++++++++++++++++++++-
 1 file changed, 32 insertions(+), 1 deletion(-)

diff --git a/src/fuse.c b/src/fuse.c
index 3fdb1d4..6c7eee1 100644
--- a/src/fuse.c
+++ b/src/fuse.c
@@ -386,7 +386,38 @@ mount_local_readlink (const char *path, char *buf, size_t size)
   if (len > size - 1)
     len = size - 1;
 
-  memcpy (buf, r, len);
+  buf[0] = '\0';
+  size_t offset = 0;
+  if (STRPREFIX (r, "/sysroot")) {
+    offset = strlen ("/sysroot") + 1;
+    size_t i;
+    for (i = 0; (i < strlen (r+offset)) && (path[i] == r[i+offset-1]); i++);
+    /* Now i contains index where paths starts to differ
+     * (n.b. needs to be aligned on last slash). */
+
+    for (; path[i] != '/'; --i);
+    /* i is now aligned */
+
+    /* Count slashes in original path, so we can generate
+     * right amount of ../ */
+    size_t j; int cnt = 0;
+    for (j = i+1; j < strlen (r+offset); j++) {
+      if (path[j] == '/') cnt++;
+    }
+
+    /* For each slash create ../ in path */
+    for (int z = 0; z < cnt; z++) {
+      strcat (buf, "../");
+    }
+
+    /* In addition to /sysroot ne need to remove common path
+     * aligned on slashes */
+    offset += i;
+  }
+
+  /* There might already be something in buf (such as ../)
+   * so let's concatenate the rest of path */
+  strncat (buf, r + offset, len - offset + 1);
   buf[len] = '\0';
 
   if (free_it) {
-- 
1.9.3


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