aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorNick Piggin <npiggin@kernel.dk>2011-01-07 01:50:07 -0500
committerNick Piggin <npiggin@kernel.dk>2011-01-07 01:50:32 -0500
commit4b936885ab04dc6e0bb0ef35e0e23c1a7364d9e5 (patch)
treea0173d27c1ce39f173be404d269c2f15144072ab
parent873feea09ebc980cbd3631b767356ce1eee65ec1 (diff)
fs: improve scalability of pseudo filesystems
Regardless of how much we possibly try to scale dcache, there is likely always going to be some fundamental contention when adding or removing children under the same parent. Pseudo filesystems do not seem need to have connected dentries because by definition they are disconnected. Signed-off-by: Nick Piggin <npiggin@kernel.dk>
-rw-r--r--fs/anon_inodes.c2
-rw-r--r--fs/dcache.c12
-rw-r--r--fs/pipe.c2
-rw-r--r--include/linux/dcache.h1
-rw-r--r--net/socket.c2
5 files changed, 16 insertions, 3 deletions
diff --git a/fs/anon_inodes.c b/fs/anon_inodes.c
index aca8806fa206..9d92b33da8a0 100644
--- a/fs/anon_inodes.c
+++ b/fs/anon_inodes.c
@@ -102,7 +102,7 @@ struct file *anon_inode_getfile(const char *name,
102 this.name = name; 102 this.name = name;
103 this.len = strlen(name); 103 this.len = strlen(name);
104 this.hash = 0; 104 this.hash = 0;
105 path.dentry = d_alloc(anon_inode_mnt->mnt_sb->s_root, &this); 105 path.dentry = d_alloc_pseudo(anon_inode_mnt->mnt_sb, &this);
106 if (!path.dentry) 106 if (!path.dentry)
107 goto err_module; 107 goto err_module;
108 108
diff --git a/fs/dcache.c b/fs/dcache.c
index 09ec945f3c98..9e6e6db76869 100644
--- a/fs/dcache.c
+++ b/fs/dcache.c
@@ -1330,6 +1330,18 @@ struct dentry *d_alloc(struct dentry * parent, const struct qstr *name)
1330} 1330}
1331EXPORT_SYMBOL(d_alloc); 1331EXPORT_SYMBOL(d_alloc);
1332 1332
1333struct dentry *d_alloc_pseudo(struct super_block *sb, const struct qstr *name)
1334{
1335 struct dentry *dentry = d_alloc(NULL, name);
1336 if (dentry) {
1337 dentry->d_sb = sb;
1338 dentry->d_parent = dentry;
1339 dentry->d_flags |= DCACHE_DISCONNECTED;
1340 }
1341 return dentry;
1342}
1343EXPORT_SYMBOL(d_alloc_pseudo);
1344
1333struct dentry *d_alloc_name(struct dentry *parent, const char *name) 1345struct dentry *d_alloc_name(struct dentry *parent, const char *name)
1334{ 1346{
1335 struct qstr q; 1347 struct qstr q;
diff --git a/fs/pipe.c b/fs/pipe.c
index 01a786567810..cfe3a7f2ee21 100644
--- a/fs/pipe.c
+++ b/fs/pipe.c
@@ -999,7 +999,7 @@ struct file *create_write_pipe(int flags)
999 goto err; 999 goto err;
1000 1000
1001 err = -ENOMEM; 1001 err = -ENOMEM;
1002 path.dentry = d_alloc(pipe_mnt->mnt_sb->s_root, &name); 1002 path.dentry = d_alloc_pseudo(pipe_mnt->mnt_sb, &name);
1003 if (!path.dentry) 1003 if (!path.dentry)
1004 goto err_inode; 1004 goto err_inode;
1005 path.mnt = mntget(pipe_mnt); 1005 path.mnt = mntget(pipe_mnt);
diff --git a/include/linux/dcache.h b/include/linux/dcache.h
index d719e4de8046..c0a2ca97c72f 100644
--- a/include/linux/dcache.h
+++ b/include/linux/dcache.h
@@ -211,6 +211,7 @@ extern void d_set_d_op(struct dentry *dentry, const struct dentry_operations *op
211 211
212/* allocate/de-allocate */ 212/* allocate/de-allocate */
213extern struct dentry * d_alloc(struct dentry *, const struct qstr *); 213extern struct dentry * d_alloc(struct dentry *, const struct qstr *);
214extern struct dentry * d_alloc_pseudo(struct super_block *, const struct qstr *);
214extern struct dentry * d_splice_alias(struct inode *, struct dentry *); 215extern struct dentry * d_splice_alias(struct inode *, struct dentry *);
215extern struct dentry * d_add_ci(struct dentry *, struct inode *, struct qstr *); 216extern struct dentry * d_add_ci(struct dentry *, struct inode *, struct qstr *);
216extern struct dentry * d_obtain_alias(struct inode *); 217extern struct dentry * d_obtain_alias(struct inode *);
diff --git a/net/socket.c b/net/socket.c
index 991e266bc7ae..0ee74c325320 100644
--- a/net/socket.c
+++ b/net/socket.c
@@ -361,7 +361,7 @@ static int sock_alloc_file(struct socket *sock, struct file **f, int flags)
361 if (unlikely(fd < 0)) 361 if (unlikely(fd < 0))
362 return fd; 362 return fd;
363 363
364 path.dentry = d_alloc(sock_mnt->mnt_sb->s_root, &name); 364 path.dentry = d_alloc_pseudo(sock_mnt->mnt_sb, &name);
365 if (unlikely(!path.dentry)) { 365 if (unlikely(!path.dentry)) {
366 put_unused_fd(fd); 366 put_unused_fd(fd);
367 return -ENOMEM; 367 return -ENOMEM;