Skip to content

Commit 97a5486

Browse files
bwhacksTrond Myklebust
authored and
Trond Myklebust
committed
nfs: Show original device name verbatim in /proc/*/mount{s,info}
Since commit c7f404b ('vfs: new superblock methods to override /proc/*/mount{s,info}'), nfs_path() is used to generate the mounted device name reported back to userland. nfs_path() always generates a trailing slash when the given dentry is the root of an NFS mount, but userland may expect the original device name to be returned verbatim (as it used to be). Make this canonicalisation optional and change the callers accordingly. [[email protected]: use flag instead of bool argument] Reported-and-tested-by: Chris Hiestand <[email protected]> Reference: http://bugs.debian.org/669314 Signed-off-by: Ben Hutchings <[email protected]> Cc: <[email protected]> # v2.6.39+ Signed-off-by: Jonathan Nieder <[email protected]> Signed-off-by: Trond Myklebust <[email protected]>
1 parent acce94e commit 97a5486

File tree

4 files changed

+20
-9
lines changed

4 files changed

+20
-9
lines changed

fs/nfs/internal.h

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -353,8 +353,9 @@ extern void nfs_sb_active(struct super_block *sb);
353353
extern void nfs_sb_deactive(struct super_block *sb);
354354

355355
/* namespace.c */
356+
#define NFS_PATH_CANONICAL 1
356357
extern char *nfs_path(char **p, struct dentry *dentry,
357-
char *buffer, ssize_t buflen);
358+
char *buffer, ssize_t buflen, unsigned flags);
358359
extern struct vfsmount *nfs_d_automount(struct path *path);
359360
struct vfsmount *nfs_submount(struct nfs_server *, struct dentry *,
360361
struct nfs_fh *, struct nfs_fattr *);
@@ -498,7 +499,7 @@ static inline char *nfs_devname(struct dentry *dentry,
498499
char *buffer, ssize_t buflen)
499500
{
500501
char *dummy;
501-
return nfs_path(&dummy, dentry, buffer, buflen);
502+
return nfs_path(&dummy, dentry, buffer, buflen, NFS_PATH_CANONICAL);
502503
}
503504

504505
/*

fs/nfs/namespace.c

Lines changed: 14 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -33,15 +33,22 @@ int nfs_mountpoint_expiry_timeout = 500 * HZ;
3333
* @dentry - pointer to dentry
3434
* @buffer - result buffer
3535
* @buflen - length of buffer
36+
* @flags - options (see below)
3637
*
3738
* Helper function for constructing the server pathname
3839
* by arbitrary hashed dentry.
3940
*
4041
* This is mainly for use in figuring out the path on the
4142
* server side when automounting on top of an existing partition
4243
* and in generating /proc/mounts and friends.
44+
*
45+
* Supported flags:
46+
* NFS_PATH_CANONICAL: ensure there is exactly one slash after
47+
* the original device (export) name
48+
* (if unset, the original name is returned verbatim)
4349
*/
44-
char *nfs_path(char **p, struct dentry *dentry, char *buffer, ssize_t buflen)
50+
char *nfs_path(char **p, struct dentry *dentry, char *buffer, ssize_t buflen,
51+
unsigned flags)
4552
{
4653
char *end;
4754
int namelen;
@@ -74,7 +81,7 @@ char *nfs_path(char **p, struct dentry *dentry, char *buffer, ssize_t buflen)
7481
rcu_read_unlock();
7582
goto rename_retry;
7683
}
77-
if (*end != '/') {
84+
if ((flags & NFS_PATH_CANONICAL) && *end != '/') {
7885
if (--buflen < 0) {
7986
spin_unlock(&dentry->d_lock);
8087
rcu_read_unlock();
@@ -91,9 +98,11 @@ char *nfs_path(char **p, struct dentry *dentry, char *buffer, ssize_t buflen)
9198
return end;
9299
}
93100
namelen = strlen(base);
94-
/* Strip off excess slashes in base string */
95-
while (namelen > 0 && base[namelen - 1] == '/')
96-
namelen--;
101+
if (flags & NFS_PATH_CANONICAL) {
102+
/* Strip off excess slashes in base string */
103+
while (namelen > 0 && base[namelen - 1] == '/')
104+
namelen--;
105+
}
97106
buflen -= namelen;
98107
if (buflen < 0) {
99108
spin_unlock(&dentry->d_lock);

fs/nfs/nfs4namespace.c

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -81,7 +81,8 @@ static char *nfs_path_component(const char *nfspath, const char *end)
8181
static char *nfs4_path(struct dentry *dentry, char *buffer, ssize_t buflen)
8282
{
8383
char *limit;
84-
char *path = nfs_path(&limit, dentry, buffer, buflen);
84+
char *path = nfs_path(&limit, dentry, buffer, buflen,
85+
NFS_PATH_CANONICAL);
8586
if (!IS_ERR(path)) {
8687
char *path_component = nfs_path_component(path, limit);
8788
if (path_component)

fs/nfs/super.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -771,7 +771,7 @@ int nfs_show_devname(struct seq_file *m, struct dentry *root)
771771
int err = 0;
772772
if (!page)
773773
return -ENOMEM;
774-
devname = nfs_path(&dummy, root, page, PAGE_SIZE);
774+
devname = nfs_path(&dummy, root, page, PAGE_SIZE, 0);
775775
if (IS_ERR(devname))
776776
err = PTR_ERR(devname);
777777
else

0 commit comments

Comments
 (0)