Skip to content

Commit 3383589

Browse files
committed
Merge tag 'vfs-7.1-rc1.directory' of git://git.kernel.org/pub/scm/linux/kernel/git/vfs/vfs
Pull vfs directory updates from Christian Brauner: "Recently 'start_creating', 'start_removing', 'start_renaming' and related interfaces were added which combine the locking and the lookup. At that time many callers were changed to use the new interfaces. However there are still an assortment of places out side of the core vfs where the directory is locked explictly, whether with inode_lock() or lock_rename() or similar. These were missed in the first pass for an assortment of uninteresting reasons. This addresses the remaining places where explicit locking is used, and changes them to use the new interfaces, or otherwise removes the explicit locking. The biggest changes are in overlayfs. The other changes are quite simple, though maybe the cachefiles changes is the least simple of those" * tag 'vfs-7.1-rc1.directory' of git://git.kernel.org/pub/scm/linux/kernel/git/vfs/vfs: VFS: unexport lock_rename(), lock_rename_child(), unlock_rename() ovl: remove ovl_lock_rename_workdir() ovl: use is_subdir() for testing if one thing is a subdir of another ovl: change ovl_create_real() to get a new lock when re-opening created file. ovl: pass name buffer to ovl_start_creating_temp() cachefiles: change cachefiles_bury_object to use start_renaming_dentry() ovl: Simplify ovl_lookup_real_one() VFS: make lookup_one_qstr_excl() static. nfsd: switch purge_old() to use start_removing_noperm() selinux: Use simple_start_creating() / simple_done_creating() Apparmor: Use simple_start_creating() / simple_done_creating() libfs: change simple_done_creating() to use end_creating() VFS: move the start_dirop() kerndoc comment to before start_dirop() fs/proc: Don't lock root inode when creating "self" and "thread-self" VFS: note error returns in documentation for various lookup functions
2 parents c8db081 + 9c62536 commit 3383589

15 files changed

Lines changed: 184 additions & 238 deletions

File tree

Documentation/filesystems/porting.rst

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1361,3 +1361,17 @@ to match what strlen() would return if it was ran on the string.
13611361

13621362
However, if the string is freely accessible for the duration of inode's
13631363
lifetime, consider using inode_set_cached_link() instead.
1364+
1365+
---
1366+
1367+
**mandatory**
1368+
1369+
lookup_one_qstr_excl() is no longer exported - use start_creating() or
1370+
similar.
1371+
---
1372+
1373+
** mandatory**
1374+
1375+
lock_rename(), lock_rename_child(), unlock_rename() are no
1376+
longer available. Use start_renaming() or similar.
1377+

fs/cachefiles/namei.c

Lines changed: 32 additions & 61 deletions
Original file line numberDiff line numberDiff line change
@@ -270,7 +270,8 @@ int cachefiles_bury_object(struct cachefiles_cache *cache,
270270
struct dentry *rep,
271271
enum fscache_why_object_killed why)
272272
{
273-
struct dentry *grave, *trap;
273+
struct dentry *grave;
274+
struct renamedata rd = {};
274275
struct path path, path_to_graveyard;
275276
char nbuffer[8 + 8 + 1];
276277
int ret;
@@ -302,77 +303,55 @@ int cachefiles_bury_object(struct cachefiles_cache *cache,
302303
(uint32_t) ktime_get_real_seconds(),
303304
(uint32_t) atomic_inc_return(&cache->gravecounter));
304305

305-
/* do the multiway lock magic */
306-
trap = lock_rename(cache->graveyard, dir);
307-
if (IS_ERR(trap))
308-
return PTR_ERR(trap);
309-
310-
/* do some checks before getting the grave dentry */
311-
if (rep->d_parent != dir || IS_DEADDIR(d_inode(rep))) {
312-
/* the entry was probably culled when we dropped the parent dir
313-
* lock */
314-
unlock_rename(cache->graveyard, dir);
315-
_leave(" = 0 [culled?]");
316-
return 0;
317-
}
318-
319-
if (!d_can_lookup(cache->graveyard)) {
320-
unlock_rename(cache->graveyard, dir);
321-
cachefiles_io_error(cache, "Graveyard no longer a directory");
322-
return -EIO;
323-
}
306+
rd.mnt_idmap = &nop_mnt_idmap;
307+
rd.old_parent = dir;
308+
rd.new_parent = cache->graveyard;
309+
rd.flags = 0;
310+
ret = start_renaming_dentry(&rd, 0, rep, &QSTR(nbuffer));
311+
if (ret) {
312+
/* Some errors aren't fatal */
313+
if (ret == -EXDEV)
314+
/* double-lock failed */
315+
return ret;
316+
if (d_unhashed(rep) || rep->d_parent != dir || IS_DEADDIR(d_inode(rep))) {
317+
/* the entry was probably culled when we dropped the parent dir
318+
* lock */
319+
_leave(" = 0 [culled?]");
320+
return 0;
321+
}
322+
if (ret == -EINVAL || ret == -ENOTEMPTY) {
323+
cachefiles_io_error(cache, "May not make directory loop");
324+
return -EIO;
325+
}
326+
if (ret == -ENOMEM) {
327+
_leave(" = -ENOMEM");
328+
return -ENOMEM;
329+
}
324330

325-
if (trap == rep) {
326-
unlock_rename(cache->graveyard, dir);
327-
cachefiles_io_error(cache, "May not make directory loop");
331+
cachefiles_io_error(cache, "Lookup error %d", ret);
328332
return -EIO;
329333
}
330334

331335
if (d_mountpoint(rep)) {
332-
unlock_rename(cache->graveyard, dir);
336+
end_renaming(&rd);
333337
cachefiles_io_error(cache, "Mountpoint in cache");
334338
return -EIO;
335339
}
336340

337-
grave = lookup_one(&nop_mnt_idmap, &QSTR(nbuffer), cache->graveyard);
338-
if (IS_ERR(grave)) {
339-
unlock_rename(cache->graveyard, dir);
340-
trace_cachefiles_vfs_error(object, d_inode(cache->graveyard),
341-
PTR_ERR(grave),
342-
cachefiles_trace_lookup_error);
343-
344-
if (PTR_ERR(grave) == -ENOMEM) {
345-
_leave(" = -ENOMEM");
346-
return -ENOMEM;
347-
}
348-
349-
cachefiles_io_error(cache, "Lookup error %ld", PTR_ERR(grave));
350-
return -EIO;
351-
}
352-
341+
grave = rd.new_dentry;
353342
if (d_is_positive(grave)) {
354-
unlock_rename(cache->graveyard, dir);
355-
dput(grave);
343+
end_renaming(&rd);
356344
grave = NULL;
357345
cond_resched();
358346
goto try_again;
359347
}
360348

361349
if (d_mountpoint(grave)) {
362-
unlock_rename(cache->graveyard, dir);
363-
dput(grave);
350+
end_renaming(&rd);
364351
cachefiles_io_error(cache, "Mountpoint in graveyard");
365352
return -EIO;
366353
}
367354

368-
/* target should not be an ancestor of source */
369-
if (trap == grave) {
370-
unlock_rename(cache->graveyard, dir);
371-
dput(grave);
372-
cachefiles_io_error(cache, "May not make directory loop");
373-
return -EIO;
374-
}
375-
376355
/* attempt the rename */
377356
path.mnt = cache->mnt;
378357
path.dentry = dir;
@@ -382,13 +361,6 @@ int cachefiles_bury_object(struct cachefiles_cache *cache,
382361
if (ret < 0) {
383362
cachefiles_io_error(cache, "Rename security error %d", ret);
384363
} else {
385-
struct renamedata rd = {
386-
.mnt_idmap = &nop_mnt_idmap,
387-
.old_parent = dir,
388-
.old_dentry = rep,
389-
.new_parent = cache->graveyard,
390-
.new_dentry = grave,
391-
};
392364
trace_cachefiles_rename(object, d_inode(rep)->i_ino, why);
393365
ret = cachefiles_inject_read_error();
394366
if (ret == 0)
@@ -402,8 +374,7 @@ int cachefiles_bury_object(struct cachefiles_cache *cache,
402374
}
403375

404376
__cachefiles_unmark_inode_in_use(object, d_inode(rep));
405-
unlock_rename(cache->graveyard, dir);
406-
dput(grave);
377+
end_renaming(&rd);
407378
_leave(" = 0");
408379
return 0;
409380
}

fs/libfs.c

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2318,7 +2318,6 @@ EXPORT_SYMBOL(simple_start_creating);
23182318
/* parent must have been held exclusive since simple_start_creating() */
23192319
void simple_done_creating(struct dentry *child)
23202320
{
2321-
inode_unlock(child->d_parent->d_inode);
2322-
dput(child);
2321+
end_creating(child);
23232322
}
23242323
EXPORT_SYMBOL(simple_done_creating);

fs/namei.c

Lines changed: 46 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -1782,8 +1782,8 @@ static struct dentry *lookup_dcache(const struct qstr *name,
17821782
* Will return -ENOENT if name isn't found and LOOKUP_CREATE wasn't passed.
17831783
* Will return -EEXIST if name is found and LOOKUP_EXCL was passed.
17841784
*/
1785-
struct dentry *lookup_one_qstr_excl(const struct qstr *name,
1786-
struct dentry *base, unsigned int flags)
1785+
static struct dentry *lookup_one_qstr_excl(const struct qstr *name,
1786+
struct dentry *base, unsigned int flags)
17871787
{
17881788
struct dentry *dentry;
17891789
struct dentry *old;
@@ -1820,7 +1820,6 @@ struct dentry *lookup_one_qstr_excl(const struct qstr *name,
18201820
}
18211821
return dentry;
18221822
}
1823-
EXPORT_SYMBOL(lookup_one_qstr_excl);
18241823

18251824
/**
18261825
* lookup_fast - do fast lockless (but racy) lookup of a dentry
@@ -2899,20 +2898,6 @@ static int filename_parentat(int dfd, struct filename *name,
28992898
return __filename_parentat(dfd, name, flags, parent, last, type, NULL);
29002899
}
29012900

2902-
/**
2903-
* __start_dirop - begin a create or remove dirop, performing locking and lookup
2904-
* @parent: the dentry of the parent in which the operation will occur
2905-
* @name: a qstr holding the name within that parent
2906-
* @lookup_flags: intent and other lookup flags.
2907-
* @state: task state bitmask
2908-
*
2909-
* The lookup is performed and necessary locks are taken so that, on success,
2910-
* the returned dentry can be operated on safely.
2911-
* The qstr must already have the hash value calculated.
2912-
*
2913-
* Returns: a locked dentry, or an error.
2914-
*
2915-
*/
29162901
static struct dentry *__start_dirop(struct dentry *parent, struct qstr *name,
29172902
unsigned int lookup_flags,
29182903
unsigned int state)
@@ -2934,6 +2919,19 @@ static struct dentry *__start_dirop(struct dentry *parent, struct qstr *name,
29342919
return dentry;
29352920
}
29362921

2922+
/**
2923+
* start_dirop - begin a create or remove dirop, performing locking and lookup
2924+
* @parent: the dentry of the parent in which the operation will occur
2925+
* @name: a qstr holding the name within that parent
2926+
* @lookup_flags: intent and other lookup flags.
2927+
*
2928+
* The lookup is performed and necessary locks are taken so that, on success,
2929+
* the returned dentry can be operated on safely.
2930+
* The qstr must already have the hash value calculated.
2931+
*
2932+
* Returns: a locked dentry, or an error.
2933+
*
2934+
*/
29372935
struct dentry *start_dirop(struct dentry *parent, struct qstr *name,
29382936
unsigned int lookup_flags)
29392937
{
@@ -3130,14 +3128,20 @@ static int lookup_one_common(struct mnt_idmap *idmap,
31303128
* @base: base directory to lookup from
31313129
*
31323130
* Look up a dentry by name in the dcache, returning NULL if it does not
3133-
* currently exist. The function does not try to create a dentry and if one
3131+
* currently exist or an error if there is a problem with the name.
3132+
* The function does not try to create a dentry and if one
31343133
* is found it doesn't try to revalidate it.
31353134
*
31363135
* Note that this routine is purely a helper for filesystem usage and should
31373136
* not be called by generic code. It does no permission checking.
31383137
*
31393138
* No locks need be held - only a counted reference to @base is needed.
31403139
*
3140+
* Returns:
3141+
* - ref-counted dentry on success, or
3142+
* - %NULL if name could not be found, or
3143+
* - ERR_PTR(-EACCES) if name is dot or dotdot or contains a slash or nul, or
3144+
* - ERR_PTR() if fs provide ->d_hash, and this returned an error.
31413145
*/
31423146
struct dentry *try_lookup_noperm(struct qstr *name, struct dentry *base)
31433147
{
@@ -3214,6 +3218,11 @@ EXPORT_SYMBOL(lookup_one);
32143218
*
32153219
* Unlike lookup_one, it should be called without the parent
32163220
* i_rwsem held, and will take the i_rwsem itself if necessary.
3221+
*
3222+
* Returns: - A dentry, possibly negative, or
3223+
* - same errors as try_lookup_noperm() or
3224+
* - ERR_PTR(-ENOENT) if parent has been removed, or
3225+
* - ERR_PTR(-EACCES) if parent directory is not searchable.
32173226
*/
32183227
struct dentry *lookup_one_unlocked(struct mnt_idmap *idmap, struct qstr *name,
32193228
struct dentry *base)
@@ -3250,6 +3259,10 @@ EXPORT_SYMBOL(lookup_one_unlocked);
32503259
* It should be called without the parent i_rwsem held, and will take
32513260
* the i_rwsem itself if necessary. If a fatal signal is pending or
32523261
* delivered, it will return %-EINTR if the lock is needed.
3262+
*
3263+
* Returns: A dentry, possibly negative, or
3264+
* - same errors as lookup_one_unlocked() or
3265+
* - ERR_PTR(-EINTR) if a fatal signal is pending.
32533266
*/
32543267
struct dentry *lookup_one_positive_killable(struct mnt_idmap *idmap,
32553268
struct qstr *name,
@@ -3289,6 +3302,10 @@ EXPORT_SYMBOL(lookup_one_positive_killable);
32893302
* This can be used for in-kernel filesystem clients such as file servers.
32903303
*
32913304
* The helper should be called without i_rwsem held.
3305+
*
3306+
* Returns: A positive dentry, or
3307+
* - ERR_PTR(-ENOENT) if the name could not be found, or
3308+
* - same errors as lookup_one_unlocked().
32923309
*/
32933310
struct dentry *lookup_one_positive_unlocked(struct mnt_idmap *idmap,
32943311
struct qstr *name,
@@ -3317,6 +3334,10 @@ EXPORT_SYMBOL(lookup_one_positive_unlocked);
33173334
*
33183335
* Unlike try_lookup_noperm() it *does* revalidate the dentry if it already
33193336
* existed.
3337+
*
3338+
* Returns: A dentry, possibly negative, or
3339+
* - ERR_PTR(-ENOENT) if parent has been removed, or
3340+
* - same errors as try_lookup_noperm()
33203341
*/
33213342
struct dentry *lookup_noperm_unlocked(struct qstr *name, struct dentry *base)
33223343
{
@@ -3341,6 +3362,10 @@ EXPORT_SYMBOL(lookup_noperm_unlocked);
33413362
* _can_ become positive at any time, so callers of lookup_noperm_unlocked()
33423363
* need to be very careful; pinned positives have ->d_inode stable, so
33433364
* this one avoids such problems.
3365+
*
3366+
* Returns: A positive dentry, or
3367+
* - ERR_PTR(-ENOENT) if name cannot be found or parent has been removed, or
3368+
* - same errors as try_lookup_noperm()
33443369
*/
33453370
struct dentry *lookup_noperm_positive_unlocked(struct qstr *name,
33463371
struct dentry *base)
@@ -3756,7 +3781,7 @@ static struct dentry *lock_two_directories(struct dentry *p1, struct dentry *p2)
37563781
/*
37573782
* p1 and p2 should be directories on the same fs.
37583783
*/
3759-
struct dentry *lock_rename(struct dentry *p1, struct dentry *p2)
3784+
static struct dentry *lock_rename(struct dentry *p1, struct dentry *p2)
37603785
{
37613786
if (p1 == p2) {
37623787
inode_lock_nested(p1->d_inode, I_MUTEX_PARENT);
@@ -3766,12 +3791,11 @@ struct dentry *lock_rename(struct dentry *p1, struct dentry *p2)
37663791
mutex_lock(&p1->d_sb->s_vfs_rename_mutex);
37673792
return lock_two_directories(p1, p2);
37683793
}
3769-
EXPORT_SYMBOL(lock_rename);
37703794

37713795
/*
37723796
* c1 and p2 should be on the same fs.
37733797
*/
3774-
struct dentry *lock_rename_child(struct dentry *c1, struct dentry *p2)
3798+
static struct dentry *lock_rename_child(struct dentry *c1, struct dentry *p2)
37753799
{
37763800
if (READ_ONCE(c1->d_parent) == p2) {
37773801
/*
@@ -3808,17 +3832,15 @@ struct dentry *lock_rename_child(struct dentry *c1, struct dentry *p2)
38083832
mutex_unlock(&c1->d_sb->s_vfs_rename_mutex);
38093833
return NULL;
38103834
}
3811-
EXPORT_SYMBOL(lock_rename_child);
38123835

3813-
void unlock_rename(struct dentry *p1, struct dentry *p2)
3836+
static void unlock_rename(struct dentry *p1, struct dentry *p2)
38143837
{
38153838
inode_unlock(p1->d_inode);
38163839
if (p1 != p2) {
38173840
inode_unlock(p2->d_inode);
38183841
mutex_unlock(&p1->d_sb->s_vfs_rename_mutex);
38193842
}
38203843
}
3821-
EXPORT_SYMBOL(unlock_rename);
38223844

38233845
/**
38243846
* __start_renaming - lookup and lock names for rename

fs/nfsd/nfs4recover.c

Lines changed: 2 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -352,16 +352,14 @@ purge_old(struct dentry *parent, char *cname, struct nfsd_net *nn)
352352
if (nfs4_has_reclaimed_state(name, nn))
353353
goto out_free;
354354

355-
inode_lock_nested(d_inode(parent), I_MUTEX_PARENT);
356-
child = lookup_one(&nop_mnt_idmap, &QSTR(cname), parent);
355+
child = start_removing_noperm(parent, &QSTR(cname));
357356
if (!IS_ERR(child)) {
358357
status = vfs_rmdir(&nop_mnt_idmap, d_inode(parent), child, NULL);
359358
if (status)
360359
printk("failed to remove client recovery directory %pd\n",
361360
child);
362-
dput(child);
363361
}
364-
inode_unlock(d_inode(parent));
362+
end_removing(child);
365363

366364
out_free:
367365
kfree(name.data);

0 commit comments

Comments
 (0)