From d2f9946f029bd0e41352a90058393217575153b4 Mon Sep 17 00:00:00 2001 From: Gerald Carter Date: Wed, 5 Feb 2003 15:56:10 +0000 Subject: [PATCH] apply smbumount lazy patch from Mandrake --- source/client/smbumount.c | 140 ++++++++++++++++++++++++++++++++++++++++++---- 1 file changed, 129 insertions(+), 11 deletions(-) diff --git a/source/client/smbumount.c b/source/client/smbumount.c index 20b6820fb76..2c2243528d6 100644 --- a/source/client/smbumount.c +++ b/source/client/smbumount.c @@ -15,6 +15,10 @@ #include #include +#include +#include +#include + /* This is a (hopefully) temporary hack due to the fact that sizeof( uid_t ) != sizeof( __kernel_uid_t ) under glibc. This may change in the future and smb.h may get fixed in the @@ -43,9 +47,9 @@ umount_ok(const char *mount_point) __kernel_uid_t mount_uid; if (fid == -1) { - fprintf(stderr, "Could not open %s: %s\n", - mount_point, strerror(errno)); - return -1; + /* fprintf(stderr, "Could not open %s: %s\n", + mount_point, strerror(errno)); */ + return 1; /* maybe try again */ } if (ioctl(fid, SMB_IOC_GETMOUNTUID, &mount_uid) != 0) { @@ -65,6 +69,92 @@ umount_ok(const char *mount_point) return 0; } +#define MAX_READLINKS 32 +/* myrealpath from mount, it could get REAL path under a broken connection */ +char *myrealpath(const char *path, char *resolved_path, int maxreslth) +{ + int readlinks = 0,m,n; + char *npath,*buf; + char link_path[PATH_MAX + 1]; + + npath = resolved_path; + + if(*path != '/') + { + if(!getcwd(npath, maxreslth - 2)) + return NULL; + npath += strlen(npath); + if(npath[-1] != '/') + *(npath++) = '/'; + else + { + *npath++ = '/'; + path++; + } + } + + while(*path != '\0') + { + if(*path == '/') + { + path++; + continue; + } + if(*path == '.' && (path[1] == '\0' || path[1] == '/')) + { + path++; + continue; + } + if(*path == '.' && path[1] == '.' && + (path[2] == '\0' || path[2] == '/')) + { + path += 2; + while(npath > resolved_path + 1 && + (--npath)[-1] != '/'); + continue; + } + while(*path != '\0' && *path != '/') + { + if(npath-resolved_path > maxreslth - 2) + return NULL; + *npath++ = *path++; + } + if(readlinks++ > MAX_READLINKS) + return NULL; + *npath = '\0'; + n = readlink(resolved_path, link_path, PATH_MAX); + if(n < 0) + { + if(errno != EINVAL) return NULL; + } + else + { + link_path[n] = '\0'; + if(*link_path == '/') + npath = resolved_path; + else while(*(--npath) != '/'); + m = strlen(path); + if((buf = malloc(m + n + 1)) == NULL) + { + fprintf(stderr,"Not enough memory.\n"); + return NULL; + } + memcpy(buf, link_path, n); + memcpy(buf + n, path, m + 1); + path = buf; + } + *npath++ = '/'; + } + if(npath != resolved_path + 1) + { + while(npath > resolved_path && npath[-1] == '/') + npath--; + if(npath == resolved_path) return NULL; + } + *npath = '\0'; + return resolved_path; +} + /* Make a canonical pathname from PATH. Returns a freshly malloced string. It is up the *caller* to ensure that the PATH is sensible. i.e. canonicalize ("/dev/fd0/.") returns "/dev/fd0" even though ``/dev/fd0/.'' @@ -73,7 +163,8 @@ umount_ok(const char *mount_point) static char * canonicalize (char *path) { - char *canonical = malloc (PATH_MAX + 1); + char *npath,*canonical = malloc (PATH_MAX + 1); + int i; if (!canonical) { fprintf(stderr, "Error! Not enough memory!\n"); @@ -87,11 +178,18 @@ canonicalize (char *path) if (path == NULL) return NULL; - - if (realpath (path, canonical)) + +/* if (realpath (path, canonical)) */ + if(myrealpath(path, canonical, PATH_MAX)) return canonical; pstrcpy (canonical, path); + if((i = strlen(canonical)) > 1 && i <= PATH_MAX) + { + path = canonical + i; + while(*(--path) == '/') + *path = '\0'; + } return canonical; } @@ -122,14 +220,34 @@ main(int argc, char *argv[]) exit(1); } - if (umount_ok(mount_point) != 0) { - exit(1); + if ((fd = umount_ok(mount_point)) != 0) { + if(fd == 1) + { + if((fd = umount_ok(mount_point)) != 0) + { + if(fd == 1) + { + fprintf(stderr, "Could not open %s: %s\n", + mount_point, strerror(errno)); + } + exit(1); + } + } + else exit(1); } +#if !defined(MNT_DETACH) + #define MNT_DETACH 2 +#endif + if (umount(mount_point) != 0) { - fprintf(stderr, "Could not umount %s: %s\n", - mount_point, strerror(errno)); - exit(1); + /* fprintf(stderr, "Could not umount %s: %s\n,Trying lazy umount.\n", + mount_point, strerror(errno)); */ + if(umount2(mount_point,MNT_DETACH) != 0) + { + fprintf(stderr, "Lazy umount failed.\n"); + return 1; + } } if ((fd = open(MOUNTED"~", O_RDWR|O_CREAT|O_EXCL, 0600)) == -1) -- 2.11.4.GIT