dcache.c: new helper: __d_add()

d_add() with inode->i_lock already held; common to d_add() and
d_splice_alias().  All ->lookup() instances that end up hashing
the dentry they are given will hash it here.

This almost completes the preparations to parallel lookups
proper - the only remaining bit is taking security_d_instantiate()
past d_rehash() and doing rehashing without dropping ->d_lock.

Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>
This commit is contained in:
Al Viro 2016-03-09 19:52:39 -05:00
parent de689f5e36
commit ed782b5a70
1 changed files with 17 additions and 7 deletions

View File

@ -2360,6 +2360,19 @@ void d_rehash(struct dentry * entry)
} }
EXPORT_SYMBOL(d_rehash); EXPORT_SYMBOL(d_rehash);
/* inode->i_lock held if inode is non-NULL */
static inline void __d_add(struct dentry *dentry, struct inode *inode)
{
if (inode) {
__d_instantiate(dentry, inode);
spin_unlock(&inode->i_lock);
}
security_d_instantiate(dentry, inode);
d_rehash(dentry);
}
/** /**
* d_add - add dentry to hash queues * d_add - add dentry to hash queues
* @entry: dentry to add * @entry: dentry to add
@ -2371,8 +2384,9 @@ EXPORT_SYMBOL(d_rehash);
void d_add(struct dentry *entry, struct inode *inode) void d_add(struct dentry *entry, struct inode *inode)
{ {
d_instantiate(entry, inode); if (inode)
d_rehash(entry); spin_lock(&inode->i_lock);
__d_add(entry, inode);
} }
EXPORT_SYMBOL(d_add); EXPORT_SYMBOL(d_add);
@ -2798,12 +2812,8 @@ struct dentry *d_splice_alias(struct inode *inode, struct dentry *dentry)
return new; return new;
} }
} }
/* already taking inode->i_lock, so d_add() by hand */
__d_instantiate(dentry, inode);
spin_unlock(&inode->i_lock);
out: out:
security_d_instantiate(dentry, inode); __d_add(dentry, inode);
d_rehash(dentry);
return NULL; return NULL;
} }
EXPORT_SYMBOL(d_splice_alias); EXPORT_SYMBOL(d_splice_alias);