autofs4 - remove autofs4_lock
The autofs4_lock introduced by the rcu-walk changes has unnecessarily broad scope. The locking is better handled by the per-autofs super block lookup_lock. Signed-off-by: Ian Kent <raven@themaw.net> Acked-by: David Howells <dhowells@redhat.com> Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>
This commit is contained in:
@@ -61,8 +61,6 @@ do { \
|
|||||||
current->pid, __func__, ##args); \
|
current->pid, __func__, ##args); \
|
||||||
} while (0)
|
} while (0)
|
||||||
|
|
||||||
extern spinlock_t autofs4_lock;
|
|
||||||
|
|
||||||
/* Unified info structure. This is pointed to by both the dentry and
|
/* Unified info structure. This is pointed to by both the dentry and
|
||||||
inode structures. Each file in the filesystem has an instance of this
|
inode structures. Each file in the filesystem has an instance of this
|
||||||
structure. It holds a reference to the dentry, so dentries are never
|
structure. It holds a reference to the dentry, so dentries are never
|
||||||
|
@@ -92,10 +92,11 @@ done:
|
|||||||
static struct dentry *get_next_positive_subdir(struct dentry *prev,
|
static struct dentry *get_next_positive_subdir(struct dentry *prev,
|
||||||
struct dentry *root)
|
struct dentry *root)
|
||||||
{
|
{
|
||||||
|
struct autofs_sb_info *sbi = autofs4_sbi(root->d_sb);
|
||||||
struct list_head *next;
|
struct list_head *next;
|
||||||
struct dentry *p, *q;
|
struct dentry *p, *q;
|
||||||
|
|
||||||
spin_lock(&autofs4_lock);
|
spin_lock(&sbi->lookup_lock);
|
||||||
|
|
||||||
if (prev == NULL) {
|
if (prev == NULL) {
|
||||||
spin_lock(&root->d_lock);
|
spin_lock(&root->d_lock);
|
||||||
@@ -112,7 +113,7 @@ again:
|
|||||||
start:
|
start:
|
||||||
if (next == &root->d_subdirs) {
|
if (next == &root->d_subdirs) {
|
||||||
spin_unlock(&p->d_lock);
|
spin_unlock(&p->d_lock);
|
||||||
spin_unlock(&autofs4_lock);
|
spin_unlock(&sbi->lookup_lock);
|
||||||
dput(prev);
|
dput(prev);
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
@@ -129,7 +130,7 @@ start:
|
|||||||
dget_dlock(q);
|
dget_dlock(q);
|
||||||
spin_unlock(&q->d_lock);
|
spin_unlock(&q->d_lock);
|
||||||
spin_unlock(&p->d_lock);
|
spin_unlock(&p->d_lock);
|
||||||
spin_unlock(&autofs4_lock);
|
spin_unlock(&sbi->lookup_lock);
|
||||||
|
|
||||||
dput(prev);
|
dput(prev);
|
||||||
|
|
||||||
@@ -142,13 +143,14 @@ start:
|
|||||||
static struct dentry *get_next_positive_dentry(struct dentry *prev,
|
static struct dentry *get_next_positive_dentry(struct dentry *prev,
|
||||||
struct dentry *root)
|
struct dentry *root)
|
||||||
{
|
{
|
||||||
|
struct autofs_sb_info *sbi = autofs4_sbi(root->d_sb);
|
||||||
struct list_head *next;
|
struct list_head *next;
|
||||||
struct dentry *p, *ret;
|
struct dentry *p, *ret;
|
||||||
|
|
||||||
if (prev == NULL)
|
if (prev == NULL)
|
||||||
return dget(root);
|
return dget(root);
|
||||||
|
|
||||||
spin_lock(&autofs4_lock);
|
spin_lock(&sbi->lookup_lock);
|
||||||
relock:
|
relock:
|
||||||
p = prev;
|
p = prev;
|
||||||
spin_lock(&p->d_lock);
|
spin_lock(&p->d_lock);
|
||||||
@@ -160,7 +162,7 @@ again:
|
|||||||
|
|
||||||
if (p == root) {
|
if (p == root) {
|
||||||
spin_unlock(&p->d_lock);
|
spin_unlock(&p->d_lock);
|
||||||
spin_unlock(&autofs4_lock);
|
spin_unlock(&sbi->lookup_lock);
|
||||||
dput(prev);
|
dput(prev);
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
@@ -190,7 +192,7 @@ again:
|
|||||||
dget_dlock(ret);
|
dget_dlock(ret);
|
||||||
spin_unlock(&ret->d_lock);
|
spin_unlock(&ret->d_lock);
|
||||||
spin_unlock(&p->d_lock);
|
spin_unlock(&p->d_lock);
|
||||||
spin_unlock(&autofs4_lock);
|
spin_unlock(&sbi->lookup_lock);
|
||||||
|
|
||||||
dput(prev);
|
dput(prev);
|
||||||
|
|
||||||
@@ -459,13 +461,13 @@ found:
|
|||||||
ino->flags |= AUTOFS_INF_EXPIRING;
|
ino->flags |= AUTOFS_INF_EXPIRING;
|
||||||
init_completion(&ino->expire_complete);
|
init_completion(&ino->expire_complete);
|
||||||
spin_unlock(&sbi->fs_lock);
|
spin_unlock(&sbi->fs_lock);
|
||||||
spin_lock(&autofs4_lock);
|
spin_lock(&sbi->lookup_lock);
|
||||||
spin_lock(&expired->d_parent->d_lock);
|
spin_lock(&expired->d_parent->d_lock);
|
||||||
spin_lock_nested(&expired->d_lock, DENTRY_D_LOCK_NESTED);
|
spin_lock_nested(&expired->d_lock, DENTRY_D_LOCK_NESTED);
|
||||||
list_move(&expired->d_parent->d_subdirs, &expired->d_u.d_child);
|
list_move(&expired->d_parent->d_subdirs, &expired->d_u.d_child);
|
||||||
spin_unlock(&expired->d_lock);
|
spin_unlock(&expired->d_lock);
|
||||||
spin_unlock(&expired->d_parent->d_lock);
|
spin_unlock(&expired->d_parent->d_lock);
|
||||||
spin_unlock(&autofs4_lock);
|
spin_unlock(&sbi->lookup_lock);
|
||||||
return expired;
|
return expired;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@@ -23,8 +23,6 @@
|
|||||||
|
|
||||||
#include "autofs_i.h"
|
#include "autofs_i.h"
|
||||||
|
|
||||||
DEFINE_SPINLOCK(autofs4_lock);
|
|
||||||
|
|
||||||
static int autofs4_dir_symlink(struct inode *,struct dentry *,const char *);
|
static int autofs4_dir_symlink(struct inode *,struct dentry *,const char *);
|
||||||
static int autofs4_dir_unlink(struct inode *,struct dentry *);
|
static int autofs4_dir_unlink(struct inode *,struct dentry *);
|
||||||
static int autofs4_dir_rmdir(struct inode *,struct dentry *);
|
static int autofs4_dir_rmdir(struct inode *,struct dentry *);
|
||||||
@@ -125,15 +123,15 @@ static int autofs4_dir_open(struct inode *inode, struct file *file)
|
|||||||
* autofs file system so just let the libfs routines handle
|
* autofs file system so just let the libfs routines handle
|
||||||
* it.
|
* it.
|
||||||
*/
|
*/
|
||||||
spin_lock(&autofs4_lock);
|
spin_lock(&sbi->lookup_lock);
|
||||||
spin_lock(&dentry->d_lock);
|
spin_lock(&dentry->d_lock);
|
||||||
if (!d_mountpoint(dentry) && list_empty(&dentry->d_subdirs)) {
|
if (!d_mountpoint(dentry) && list_empty(&dentry->d_subdirs)) {
|
||||||
spin_unlock(&dentry->d_lock);
|
spin_unlock(&dentry->d_lock);
|
||||||
spin_unlock(&autofs4_lock);
|
spin_unlock(&sbi->lookup_lock);
|
||||||
return -ENOENT;
|
return -ENOENT;
|
||||||
}
|
}
|
||||||
spin_unlock(&dentry->d_lock);
|
spin_unlock(&dentry->d_lock);
|
||||||
spin_unlock(&autofs4_lock);
|
spin_unlock(&sbi->lookup_lock);
|
||||||
|
|
||||||
out:
|
out:
|
||||||
return dcache_dir_open(inode, file);
|
return dcache_dir_open(inode, file);
|
||||||
@@ -171,7 +169,6 @@ static struct dentry *autofs4_lookup_active(struct dentry *dentry)
|
|||||||
const unsigned char *str = name->name;
|
const unsigned char *str = name->name;
|
||||||
struct list_head *p, *head;
|
struct list_head *p, *head;
|
||||||
|
|
||||||
spin_lock(&autofs4_lock);
|
|
||||||
spin_lock(&sbi->lookup_lock);
|
spin_lock(&sbi->lookup_lock);
|
||||||
head = &sbi->active_list;
|
head = &sbi->active_list;
|
||||||
list_for_each(p, head) {
|
list_for_each(p, head) {
|
||||||
@@ -204,14 +201,12 @@ static struct dentry *autofs4_lookup_active(struct dentry *dentry)
|
|||||||
dget_dlock(active);
|
dget_dlock(active);
|
||||||
spin_unlock(&active->d_lock);
|
spin_unlock(&active->d_lock);
|
||||||
spin_unlock(&sbi->lookup_lock);
|
spin_unlock(&sbi->lookup_lock);
|
||||||
spin_unlock(&autofs4_lock);
|
|
||||||
return active;
|
return active;
|
||||||
}
|
}
|
||||||
next:
|
next:
|
||||||
spin_unlock(&active->d_lock);
|
spin_unlock(&active->d_lock);
|
||||||
}
|
}
|
||||||
spin_unlock(&sbi->lookup_lock);
|
spin_unlock(&sbi->lookup_lock);
|
||||||
spin_unlock(&autofs4_lock);
|
|
||||||
|
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
@@ -226,7 +221,6 @@ static struct dentry *autofs4_lookup_expiring(struct dentry *dentry)
|
|||||||
const unsigned char *str = name->name;
|
const unsigned char *str = name->name;
|
||||||
struct list_head *p, *head;
|
struct list_head *p, *head;
|
||||||
|
|
||||||
spin_lock(&autofs4_lock);
|
|
||||||
spin_lock(&sbi->lookup_lock);
|
spin_lock(&sbi->lookup_lock);
|
||||||
head = &sbi->expiring_list;
|
head = &sbi->expiring_list;
|
||||||
list_for_each(p, head) {
|
list_for_each(p, head) {
|
||||||
@@ -259,14 +253,12 @@ static struct dentry *autofs4_lookup_expiring(struct dentry *dentry)
|
|||||||
dget_dlock(expiring);
|
dget_dlock(expiring);
|
||||||
spin_unlock(&expiring->d_lock);
|
spin_unlock(&expiring->d_lock);
|
||||||
spin_unlock(&sbi->lookup_lock);
|
spin_unlock(&sbi->lookup_lock);
|
||||||
spin_unlock(&autofs4_lock);
|
|
||||||
return expiring;
|
return expiring;
|
||||||
}
|
}
|
||||||
next:
|
next:
|
||||||
spin_unlock(&expiring->d_lock);
|
spin_unlock(&expiring->d_lock);
|
||||||
}
|
}
|
||||||
spin_unlock(&sbi->lookup_lock);
|
spin_unlock(&sbi->lookup_lock);
|
||||||
spin_unlock(&autofs4_lock);
|
|
||||||
|
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
@@ -603,12 +595,12 @@ static int autofs4_dir_unlink(struct inode *dir, struct dentry *dentry)
|
|||||||
|
|
||||||
dir->i_mtime = CURRENT_TIME;
|
dir->i_mtime = CURRENT_TIME;
|
||||||
|
|
||||||
spin_lock(&autofs4_lock);
|
spin_lock(&sbi->lookup_lock);
|
||||||
autofs4_add_expiring(dentry);
|
__autofs4_add_expiring(dentry);
|
||||||
spin_lock(&dentry->d_lock);
|
spin_lock(&dentry->d_lock);
|
||||||
__d_drop(dentry);
|
__d_drop(dentry);
|
||||||
spin_unlock(&dentry->d_lock);
|
spin_unlock(&dentry->d_lock);
|
||||||
spin_unlock(&autofs4_lock);
|
spin_unlock(&sbi->lookup_lock);
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
@@ -677,20 +669,17 @@ static int autofs4_dir_rmdir(struct inode *dir, struct dentry *dentry)
|
|||||||
if (!autofs4_oz_mode(sbi))
|
if (!autofs4_oz_mode(sbi))
|
||||||
return -EACCES;
|
return -EACCES;
|
||||||
|
|
||||||
spin_lock(&autofs4_lock);
|
|
||||||
spin_lock(&sbi->lookup_lock);
|
spin_lock(&sbi->lookup_lock);
|
||||||
spin_lock(&dentry->d_lock);
|
spin_lock(&dentry->d_lock);
|
||||||
if (!list_empty(&dentry->d_subdirs)) {
|
if (!list_empty(&dentry->d_subdirs)) {
|
||||||
spin_unlock(&dentry->d_lock);
|
spin_unlock(&dentry->d_lock);
|
||||||
spin_unlock(&sbi->lookup_lock);
|
spin_unlock(&sbi->lookup_lock);
|
||||||
spin_unlock(&autofs4_lock);
|
|
||||||
return -ENOTEMPTY;
|
return -ENOTEMPTY;
|
||||||
}
|
}
|
||||||
__autofs4_add_expiring(dentry);
|
__autofs4_add_expiring(dentry);
|
||||||
spin_unlock(&sbi->lookup_lock);
|
|
||||||
__d_drop(dentry);
|
__d_drop(dentry);
|
||||||
spin_unlock(&dentry->d_lock);
|
spin_unlock(&dentry->d_lock);
|
||||||
spin_unlock(&autofs4_lock);
|
spin_unlock(&sbi->lookup_lock);
|
||||||
|
|
||||||
if (sbi->version < 5)
|
if (sbi->version < 5)
|
||||||
autofs_clear_leaf_automount_flags(dentry);
|
autofs_clear_leaf_automount_flags(dentry);
|
||||||
|
@@ -197,12 +197,12 @@ rename_retry:
|
|||||||
|
|
||||||
seq = read_seqbegin(&rename_lock);
|
seq = read_seqbegin(&rename_lock);
|
||||||
rcu_read_lock();
|
rcu_read_lock();
|
||||||
spin_lock(&autofs4_lock);
|
spin_lock(&sbi->fs_lock);
|
||||||
for (tmp = dentry ; tmp != root ; tmp = tmp->d_parent)
|
for (tmp = dentry ; tmp != root ; tmp = tmp->d_parent)
|
||||||
len += tmp->d_name.len + 1;
|
len += tmp->d_name.len + 1;
|
||||||
|
|
||||||
if (!len || --len > NAME_MAX) {
|
if (!len || --len > NAME_MAX) {
|
||||||
spin_unlock(&autofs4_lock);
|
spin_unlock(&sbi->fs_lock);
|
||||||
rcu_read_unlock();
|
rcu_read_unlock();
|
||||||
if (read_seqretry(&rename_lock, seq))
|
if (read_seqretry(&rename_lock, seq))
|
||||||
goto rename_retry;
|
goto rename_retry;
|
||||||
@@ -218,7 +218,7 @@ rename_retry:
|
|||||||
p -= tmp->d_name.len;
|
p -= tmp->d_name.len;
|
||||||
strncpy(p, tmp->d_name.name, tmp->d_name.len);
|
strncpy(p, tmp->d_name.name, tmp->d_name.len);
|
||||||
}
|
}
|
||||||
spin_unlock(&autofs4_lock);
|
spin_unlock(&sbi->fs_lock);
|
||||||
rcu_read_unlock();
|
rcu_read_unlock();
|
||||||
if (read_seqretry(&rename_lock, seq))
|
if (read_seqretry(&rename_lock, seq))
|
||||||
goto rename_retry;
|
goto rename_retry;
|
||||||
|
Reference in New Issue
Block a user