aboutsummaryrefslogtreecommitdiffstats
path: root/extlinux/main.c
diff options
context:
space:
mode:
authorH. Peter Anvin <hpa@linux.intel.com>2010-04-28 15:50:20 -0700
committerH. Peter Anvin <hpa@linux.intel.com>2010-04-28 15:50:20 -0700
commit593ca98d8795f1c97c1424e2b8648c643a4c18f8 (patch)
treee9c0fae288ec90b6a08b40ad61bc35cbf9ccc7f9 /extlinux/main.c
parent80889d3b8246678bafe6cbdd1abed969f669972f (diff)
downloadsyslinux-593ca98d8795f1c97c1424e2b8648c643a4c18f8.tar.gz
syslinux-593ca98d8795f1c97c1424e2b8648c643a4c18f8.tar.xz
syslinux-593ca98d8795f1c97c1424e2b8648c643a4c18f8.zip
extlinux: handle cases of a single level of directoriessyslinux-4.00-pre39
We had a boundary condition error where a single-level directory from the global root (e.g. /boot) would be incorrectly truncated; fix that. Signed-off-by: H. Peter Anvin <hpa@linux.intel.com>
Diffstat (limited to 'extlinux/main.c')
-rw-r--r--extlinux/main.c20
1 files changed, 16 insertions, 4 deletions
diff --git a/extlinux/main.c b/extlinux/main.c
index d1666718..e1d55964 100644
--- a/extlinux/main.c
+++ b/extlinux/main.c
@@ -441,7 +441,7 @@ int patch_file_and_bootblock(int fd, const char *dir, int devfd)
int i, dw, nptrs;
uint32_t csum;
int secptroffset, diroffset, dirlen, subvoloffset, subvollen;
- char *dirpath, *subpath;
+ char *dirpath, *subpath, *xdirpath, *xsubpath;
dirpath = realpath(dir, NULL);
if (!dirpath || stat(dir, &dirst)) {
@@ -457,10 +457,17 @@ int patch_file_and_bootblock(int fd, const char *dir, int devfd)
}
subpath = strchr(dirpath, '\0');
- while (--subpath >= dirpath) {
+ for (;;) {
if (*subpath == '/') {
- *subpath = '\0';
- if (lstat(dirpath, &xdst) || dirst.st_dev != xdst.st_dev) {
+ if (subpath > dirpath) {
+ *subpath = '\0';
+ xsubpath = subpath+1;
+ xdirpath = dirpath;
+ } else {
+ xsubpath = subpath;
+ xdirpath = "/";
+ }
+ if (lstat(xdirpath, &xdst) || dirst.st_dev != xdst.st_dev) {
subpath = strchr(subpath+1, '/');
if (!subpath)
subpath = "/"; /* It's the root of the filesystem */
@@ -468,6 +475,11 @@ int patch_file_and_bootblock(int fd, const char *dir, int devfd)
}
*subpath = '/';
}
+
+ if (subpath == dirpath)
+ break;
+
+ subpath--;
}
/* Now subpath should contain the path relative to the fs base */