diff options
author | Miguel de Icaza <miguel@nuclecu.unam.mx> | 1997-08-06 19:14:48 +0000 |
---|---|---|
committer | Miguel de Icaza <miguel@nuclecu.unam.mx> | 1997-08-06 19:14:48 +0000 |
commit | e2819e52a162873ff5061de81bb749831bdb5de9 (patch) | |
tree | 6067ea700202750ba335a423696f2972700e5f76 /fs/dcache.c | |
parent | 17a005074429bbf143e40401f405ae4363e56828 (diff) |
Merge to 2.1.38.
IMPORTANT NOTE: I could not figure out what information is the
one that should be used for the following files (ie, those
that were in our tree, or those that came from Linus' patch),
please, check these:
include/asm-mips/jazz.h
include/asm-mips/jazzdma.h
include/asm-mips/ioctls.h
Diffstat (limited to 'fs/dcache.c')
-rw-r--r-- | fs/dcache.c | 50 |
1 files changed, 33 insertions, 17 deletions
diff --git a/fs/dcache.c b/fs/dcache.c index 97937822f..6e742ca7f 100644 --- a/fs/dcache.c +++ b/fs/dcache.c @@ -353,27 +353,43 @@ void d_move(struct dentry * dentry, struct dentry * newdir, struct qstr * newnam dentry->d_parent = newdir; d_insert_to_parent(dentry, newdir); } - /* - * This is broken in more ways than one. Unchecked recursion, - * unchecked buffer size. Get rid of it. + * "buflen" should be PAGE_SIZE or more. */ -int d_path(struct dentry * entry, struct dentry * chroot, char * buf) +char * d_path(struct dentry *dentry, char *buffer, int buflen) { - if (IS_ROOT(entry) || (chroot && entry == chroot)) { - *buf = '/'; - return 1; - } else { - int len = d_path(entry->d_covers->d_parent, chroot, buf); - - buf += len; - if (len > 1) { - *buf++ = '/'; - len++; - } - memcpy(buf, entry->d_name.name, entry->d_name.len); - return len + entry->d_name.len; + char * end = buffer+buflen; + char * retval; + struct dentry * root = current->fs->root; + + *--end = '\0'; + buflen--; + + /* Get '/' right */ + retval = end-1; + *retval = '/'; + + for (;;) { + struct dentry * parent; + int namelen; + + if (dentry == root) + break; + dentry = dentry->d_covers; + parent = dentry->d_parent; + if (dentry == parent) + break; + namelen = dentry->d_name.len; + buflen -= namelen + 1; + if (buflen < 0) + break; + end -= namelen; + memcpy(end, dentry->d_name.name, namelen); + *--end = '/'; + retval = end; + dentry = parent; } + return retval; } __initfunc(void dcache_init(void)) |