Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

Merge tag 'pull-revalidate' of git://git.kernel.org/pub/scm/linux/kernel/git/viro/vfs

Pull vfs d_revalidate updates from Al Viro:
"Provide stable parent and name to ->d_revalidate() instances

Most of the filesystem methods where we care about dentry name and
parent have their stability guaranteed by the callers;
->d_revalidate() is the major exception.

It's easy enough for callers to supply stable values for expected name
and expected parent of the dentry being validated. That kills quite a
bit of boilerplate in ->d_revalidate() instances, along with a bunch
of races where they used to access ->d_name without sufficient
precautions"

* tag 'pull-revalidate' of git://git.kernel.org/pub/scm/linux/kernel/git/viro/vfs:
9p: fix ->rename_sem exclusion
orangefs_d_revalidate(): use stable parent inode and name passed by caller
ocfs2_dentry_revalidate(): use stable parent inode and name passed by caller
nfs: fix ->d_revalidate() UAF on ->d_name accesses
nfs{,4}_lookup_validate(): use stable parent inode passed by caller
gfs2_drevalidate(): use stable parent inode and name passed by caller
fuse_dentry_revalidate(): use stable parent inode and name passed by caller
vfat_revalidate{,_ci}(): use stable parent inode passed by caller
exfat_d_revalidate(): use stable parent inode passed by caller
fscrypt_d_revalidate(): use stable parent inode passed by caller
ceph_d_revalidate(): propagate stable name down into request encoding
ceph_d_revalidate(): use stable parent inode passed by caller
afs_d_revalidate(): use stable name and parent inode passed by caller
Pass parent directory inode and expected name to ->d_revalidate()
generic_ci_d_compare(): use shortname_storage
ext4 fast_commit: make use of name_snapshot primitives
dissolve external_name.u into separate members
make take_dentry_name_snapshot() lockless
dcache: back inline names with a struct-wrapped array of unsigned long
make sure that DNAME_INLINE_LEN is a multiple of word size

+359 -307
+6 -1
Documentation/filesystems/locking.rst
··· 17 17 18 18 prototypes:: 19 19 20 - int (*d_revalidate)(struct dentry *, unsigned int); 20 + int (*d_revalidate)(struct inode *, const struct qstr *, 21 + struct dentry *, unsigned int); 21 22 int (*d_weak_revalidate)(struct dentry *, unsigned int); 22 23 int (*d_hash)(const struct dentry *, struct qstr *); 23 24 int (*d_compare)(const struct dentry *, ··· 31 30 struct vfsmount *(*d_automount)(struct path *path); 32 31 int (*d_manage)(const struct path *, bool); 33 32 struct dentry *(*d_real)(struct dentry *, enum d_real_type type); 33 + bool (*d_unalias_trylock)(const struct dentry *); 34 + void (*d_unalias_unlock)(const struct dentry *); 34 35 35 36 locking rules: 36 37 ··· 52 49 d_automount: no no yes no 53 50 d_manage: no no yes (ref-walk) maybe 54 51 d_real no no yes no 52 + d_unalias_trylock yes no no no 53 + d_unalias_unlock yes no no no 55 54 ================== =========== ======== ============== ======== 56 55 57 56 inode_operations
+16
Documentation/filesystems/porting.rst
··· 1141 1141 1142 1142 set_blocksize() takes opened struct file instead of struct block_device now 1143 1143 and it *must* be opened exclusive. 1144 + 1145 + --- 1146 + 1147 + ** mandatory** 1148 + 1149 + ->d_revalidate() gets two extra arguments - inode of parent directory and 1150 + name our dentry is expected to have. Both are stable (dir is pinned in 1151 + non-RCU case and will stay around during the call in RCU case, and name 1152 + is guaranteed to stay unchanging). Your instance doesn't have to use 1153 + either, but it often helps to avoid a lot of painful boilerplate. 1154 + Note that while name->name is stable and NUL-terminated, it may (and 1155 + often will) have name->name[name->len] equal to '/' rather than '\0' - 1156 + in normal case it points into the pathname being looked up. 1157 + NOTE: if you need something like full path from the root of filesystem, 1158 + you are still on your own - this assists with simple cases, but it's not 1159 + magic.
+23 -1
Documentation/filesystems/vfs.rst
··· 1251 1251 .. code-block:: c 1252 1252 1253 1253 struct dentry_operations { 1254 - int (*d_revalidate)(struct dentry *, unsigned int); 1254 + int (*d_revalidate)(struct inode *, const struct qstr *, 1255 + struct dentry *, unsigned int); 1255 1256 int (*d_weak_revalidate)(struct dentry *, unsigned int); 1256 1257 int (*d_hash)(const struct dentry *, struct qstr *); 1257 1258 int (*d_compare)(const struct dentry *, ··· 1265 1264 struct vfsmount *(*d_automount)(struct path *); 1266 1265 int (*d_manage)(const struct path *, bool); 1267 1266 struct dentry *(*d_real)(struct dentry *, enum d_real_type type); 1267 + bool (*d_unalias_trylock)(const struct dentry *); 1268 + void (*d_unalias_unlock)(const struct dentry *); 1268 1269 }; 1269 1270 1270 1271 ``d_revalidate`` ··· 1429 1426 hosting the file's data or metadata respectively. 1430 1427 1431 1428 For non-regular files, the 'dentry' argument is returned. 1429 + 1430 + ``d_unalias_trylock`` 1431 + if present, will be called by d_splice_alias() before moving a 1432 + preexisting attached alias. Returning false prevents __d_move(), 1433 + making d_splice_alias() fail with -ESTALE. 1434 + 1435 + Rationale: setting FS_RENAME_DOES_D_MOVE will prevent d_move() 1436 + and d_exchange() calls from the outside of filesystem methods; 1437 + however, it does not guarantee that attached dentries won't 1438 + be renamed or moved by d_splice_alias() finding a preexisting 1439 + alias for a directory inode. Normally we would not care; 1440 + however, something that wants to stabilize the entire path to 1441 + root over a blocking operation might need that. See 9p for one 1442 + (and hopefully only) example. 1443 + 1444 + ``d_unalias_unlock`` 1445 + should be paired with ``d_unalias_trylock``; that one is called after 1446 + __d_move() call in __d_unalias(). 1447 + 1432 1448 1433 1449 Each dentry has a pointer to its parent dentry, as well as a hash list 1434 1450 of child dentries. Child dentries are basically like files in a
+1 -1
fs/9p/v9fs.h
··· 202 202 return inode->i_sb->s_fs_info; 203 203 } 204 204 205 - static inline struct v9fs_session_info *v9fs_dentry2v9ses(struct dentry *dentry) 205 + static inline struct v9fs_session_info *v9fs_dentry2v9ses(const struct dentry *dentry) 206 206 { 207 207 return dentry->d_sb->s_fs_info; 208 208 }
+24 -2
fs/9p/vfs_dentry.c
··· 61 61 p9_fid_put(hlist_entry(p, struct p9_fid, dlist)); 62 62 } 63 63 64 - static int v9fs_lookup_revalidate(struct dentry *dentry, unsigned int flags) 64 + static int __v9fs_lookup_revalidate(struct dentry *dentry, unsigned int flags) 65 65 { 66 66 struct p9_fid *fid; 67 67 struct inode *inode; ··· 99 99 return 1; 100 100 } 101 101 102 + static int v9fs_lookup_revalidate(struct inode *dir, const struct qstr *name, 103 + struct dentry *dentry, unsigned int flags) 104 + { 105 + return __v9fs_lookup_revalidate(dentry, flags); 106 + } 107 + 108 + static bool v9fs_dentry_unalias_trylock(const struct dentry *dentry) 109 + { 110 + struct v9fs_session_info *v9ses = v9fs_dentry2v9ses(dentry); 111 + return down_write_trylock(&v9ses->rename_sem); 112 + } 113 + 114 + static void v9fs_dentry_unalias_unlock(const struct dentry *dentry) 115 + { 116 + struct v9fs_session_info *v9ses = v9fs_dentry2v9ses(dentry); 117 + up_write(&v9ses->rename_sem); 118 + } 119 + 102 120 const struct dentry_operations v9fs_cached_dentry_operations = { 103 121 .d_revalidate = v9fs_lookup_revalidate, 104 - .d_weak_revalidate = v9fs_lookup_revalidate, 122 + .d_weak_revalidate = __v9fs_lookup_revalidate, 105 123 .d_delete = v9fs_cached_dentry_delete, 106 124 .d_release = v9fs_dentry_release, 125 + .d_unalias_trylock = v9fs_dentry_unalias_trylock, 126 + .d_unalias_unlock = v9fs_dentry_unalias_unlock, 107 127 }; 108 128 109 129 const struct dentry_operations v9fs_dentry_operations = { 110 130 .d_delete = always_delete_dentry, 111 131 .d_release = v9fs_dentry_release, 132 + .d_unalias_trylock = v9fs_dentry_unalias_trylock, 133 + .d_unalias_unlock = v9fs_dentry_unalias_unlock, 112 134 };
+12 -28
fs/afs/dir.c
··· 23 23 unsigned int flags); 24 24 static int afs_dir_open(struct inode *inode, struct file *file); 25 25 static int afs_readdir(struct file *file, struct dir_context *ctx); 26 - static int afs_d_revalidate(struct dentry *dentry, unsigned int flags); 26 + static int afs_d_revalidate(struct inode *dir, const struct qstr *name, 27 + struct dentry *dentry, unsigned int flags); 27 28 static int afs_d_delete(const struct dentry *dentry); 28 29 static void afs_d_iput(struct dentry *dentry, struct inode *inode); 29 30 static bool afs_lookup_one_filldir(struct dir_context *ctx, const char *name, int nlen, ··· 598 597 * Do a lookup of a single name in a directory 599 598 * - just returns the FID the dentry name maps to if found 600 599 */ 601 - static int afs_do_lookup_one(struct inode *dir, struct dentry *dentry, 600 + static int afs_do_lookup_one(struct inode *dir, const struct qstr *name, 602 601 struct afs_fid *fid, 603 602 afs_dataversion_t *_dir_version) 604 603 { 605 604 struct afs_super_info *as = dir->i_sb->s_fs_info; 606 605 struct afs_lookup_one_cookie cookie = { 607 606 .ctx.actor = afs_lookup_one_filldir, 608 - .name = dentry->d_name, 607 + .name = *name, 609 608 .fid.vid = as->volume->vid 610 609 }; 611 610 int ret; 612 611 613 - _enter("{%lu},%p{%pd},", dir->i_ino, dentry, dentry); 612 + _enter("{%lu},{%.*s},", dir->i_ino, name->len, name->name); 614 613 615 614 /* search the directory */ 616 615 ret = afs_dir_iterate(dir, &cookie.ctx, NULL, _dir_version); ··· 1024 1023 /* 1025 1024 * Check the validity of a dentry under RCU conditions. 1026 1025 */ 1027 - static int afs_d_revalidate_rcu(struct dentry *dentry) 1026 + static int afs_d_revalidate_rcu(struct afs_vnode *dvnode, struct dentry *dentry) 1028 1027 { 1029 - struct afs_vnode *dvnode; 1030 - struct dentry *parent; 1031 - struct inode *dir; 1032 1028 long dir_version, de_version; 1033 1029 1034 1030 _enter("%p", dentry); 1035 1031 1036 - /* Check the parent directory is still valid first. */ 1037 - parent = READ_ONCE(dentry->d_parent); 1038 - dir = d_inode_rcu(parent); 1039 - if (!dir) 1040 - return -ECHILD; 1041 - dvnode = AFS_FS_I(dir); 1042 1032 if (test_bit(AFS_VNODE_DELETED, &dvnode->flags)) 1043 1033 return -ECHILD; 1044 1034 ··· 1057 1065 * - NOTE! the hit can be a negative hit too, so we can't assume we have an 1058 1066 * inode 1059 1067 */ 1060 - static int afs_d_revalidate(struct dentry *dentry, unsigned int flags) 1068 + static int afs_d_revalidate(struct inode *parent_dir, const struct qstr *name, 1069 + struct dentry *dentry, unsigned int flags) 1061 1070 { 1062 - struct afs_vnode *vnode, *dir; 1071 + struct afs_vnode *vnode, *dir = AFS_FS_I(parent_dir); 1063 1072 struct afs_fid fid; 1064 - struct dentry *parent; 1065 1073 struct inode *inode; 1066 1074 struct key *key; 1067 1075 afs_dataversion_t dir_version, invalid_before; ··· 1069 1077 int ret; 1070 1078 1071 1079 if (flags & LOOKUP_RCU) 1072 - return afs_d_revalidate_rcu(dentry); 1080 + return afs_d_revalidate_rcu(dir, dentry); 1073 1081 1074 1082 if (d_really_is_positive(dentry)) { 1075 1083 vnode = AFS_FS_I(d_inode(dentry)); ··· 1084 1092 if (IS_ERR(key)) 1085 1093 key = NULL; 1086 1094 1087 - /* Hold the parent dentry so we can peer at it */ 1088 - parent = dget_parent(dentry); 1089 - dir = AFS_FS_I(d_inode(parent)); 1090 - 1091 1095 /* validate the parent directory */ 1092 1096 ret = afs_validate(dir, key); 1093 1097 if (ret == -ERESTARTSYS) { 1094 - dput(parent); 1095 1098 key_put(key); 1096 1099 return ret; 1097 1100 } ··· 1114 1127 afs_stat_v(dir, n_reval); 1115 1128 1116 1129 /* search the directory for this vnode */ 1117 - ret = afs_do_lookup_one(&dir->netfs.inode, dentry, &fid, &dir_version); 1130 + ret = afs_do_lookup_one(&dir->netfs.inode, name, &fid, &dir_version); 1118 1131 switch (ret) { 1119 1132 case 0: 1120 1133 /* the filename maps to something */ ··· 1158 1171 goto out_valid; 1159 1172 1160 1173 default: 1161 - _debug("failed to iterate dir %pd: %d", 1162 - parent, ret); 1174 + _debug("failed to iterate parent %pd2: %d", dentry, ret); 1163 1175 goto not_found; 1164 1176 } 1165 1177 1166 1178 out_valid: 1167 1179 dentry->d_fsdata = (void *)(unsigned long)dir_version; 1168 1180 out_valid_noupdate: 1169 - dput(parent); 1170 1181 key_put(key); 1171 1182 _leave(" = 1 [valid]"); 1172 1183 return 1; 1173 1184 1174 1185 not_found: 1175 1186 _debug("dropping dentry %pd2", dentry); 1176 - dput(parent); 1177 1187 key_put(key); 1178 1188 1179 1189 _leave(" = 0 [bad]");
+7 -18
fs/ceph/dir.c
··· 1940 1940 /* 1941 1941 * Check if cached dentry can be trusted. 1942 1942 */ 1943 - static int ceph_d_revalidate(struct dentry *dentry, unsigned int flags) 1943 + static int ceph_d_revalidate(struct inode *dir, const struct qstr *name, 1944 + struct dentry *dentry, unsigned int flags) 1944 1945 { 1945 1946 struct ceph_mds_client *mdsc = ceph_sb_to_fs_client(dentry->d_sb)->mdsc; 1946 1947 struct ceph_client *cl = mdsc->fsc->client; 1947 1948 int valid = 0; 1948 - struct dentry *parent; 1949 - struct inode *dir, *inode; 1949 + struct inode *inode; 1950 1950 1951 - valid = fscrypt_d_revalidate(dentry, flags); 1951 + valid = fscrypt_d_revalidate(dir, name, dentry, flags); 1952 1952 if (valid <= 0) 1953 1953 return valid; 1954 1954 1955 - if (flags & LOOKUP_RCU) { 1956 - parent = READ_ONCE(dentry->d_parent); 1957 - dir = d_inode_rcu(parent); 1958 - if (!dir) 1959 - return -ECHILD; 1960 - inode = d_inode_rcu(dentry); 1961 - } else { 1962 - parent = dget_parent(dentry); 1963 - dir = d_inode(parent); 1964 - inode = d_inode(dentry); 1965 - } 1955 + inode = d_inode_rcu(dentry); 1966 1956 1967 1957 doutc(cl, "%p '%pd' inode %p offset 0x%llx nokey %d\n", 1968 1958 dentry, dentry, inode, ceph_dentry(dentry)->offset, ··· 1998 2008 req->r_parent = dir; 1999 2009 ihold(dir); 2000 2010 2011 + req->r_dname = name; 2012 + 2001 2013 mask = CEPH_STAT_CAP_INODE | CEPH_CAP_AUTH_SHARED; 2002 2014 if (ceph_security_xattr_wanted(dir)) 2003 2015 mask |= CEPH_CAP_XATTR_SHARED; ··· 2030 2038 doutc(cl, "%p '%pd' %s\n", dentry, dentry, valid ? "valid" : "invalid"); 2031 2039 if (!valid) 2032 2040 ceph_dir_clear_complete(dir); 2033 - 2034 - if (!(flags & LOOKUP_RCU)) 2035 - dput(parent); 2036 2041 return valid; 2037 2042 } 2038 2043
+6 -3
fs/ceph/mds_client.c
··· 2621 2621 { 2622 2622 struct inode *dir = req->r_parent; 2623 2623 struct dentry *dentry = req->r_dentry; 2624 + const struct qstr *name = req->r_dname; 2624 2625 u8 *cryptbuf = NULL; 2625 2626 u32 len = 0; 2626 2627 int ret = 0; ··· 2642 2641 if (!fscrypt_has_encryption_key(dir)) 2643 2642 goto success; 2644 2643 2645 - if (!fscrypt_fname_encrypted_size(dir, dentry->d_name.len, NAME_MAX, 2646 - &len)) { 2644 + if (!name) 2645 + name = &dentry->d_name; 2646 + 2647 + if (!fscrypt_fname_encrypted_size(dir, name->len, NAME_MAX, &len)) { 2647 2648 WARN_ON_ONCE(1); 2648 2649 return ERR_PTR(-ENAMETOOLONG); 2649 2650 } ··· 2660 2657 if (!cryptbuf) 2661 2658 return ERR_PTR(-ENOMEM); 2662 2659 2663 - ret = fscrypt_fname_encrypt(dir, &dentry->d_name, cryptbuf, len); 2660 + ret = fscrypt_fname_encrypt(dir, name, cryptbuf, len); 2664 2661 if (ret) { 2665 2662 kfree(cryptbuf); 2666 2663 return ERR_PTR(ret);
+2
fs/ceph/mds_client.h
··· 299 299 struct inode *r_target_inode; /* resulting inode */ 300 300 struct inode *r_new_inode; /* new inode (for creates) */ 301 301 302 + const struct qstr *r_dname; /* stable name (for ->d_revalidate) */ 303 + 302 304 #define CEPH_MDS_R_DIRECT_IS_HASH (1) /* r_direct_hash is valid */ 303 305 #define CEPH_MDS_R_ABORTED (2) /* call was aborted */ 304 306 #define CEPH_MDS_R_GOT_UNSAFE (3) /* got an unsafe reply */
+2 -1
fs/coda/dir.c
··· 445 445 } 446 446 447 447 /* called when a cache lookup succeeds */ 448 - static int coda_dentry_revalidate(struct dentry *de, unsigned int flags) 448 + static int coda_dentry_revalidate(struct inode *dir, const struct qstr *name, 449 + struct dentry *de, unsigned int flags) 449 450 { 450 451 struct inode *inode; 451 452 struct coda_inode_info *cii;
+6 -16
fs/crypto/fname.c
··· 574 574 * Validate dentries in encrypted directories to make sure we aren't potentially 575 575 * caching stale dentries after a key has been added. 576 576 */ 577 - int fscrypt_d_revalidate(struct dentry *dentry, unsigned int flags) 577 + int fscrypt_d_revalidate(struct inode *dir, const struct qstr *name, 578 + struct dentry *dentry, unsigned int flags) 578 579 { 579 - struct dentry *dir; 580 580 int err; 581 - int valid; 582 581 583 582 /* 584 583 * Plaintext names are always valid, since fscrypt doesn't support ··· 590 591 /* 591 592 * No-key name; valid if the directory's key is still unavailable. 592 593 * 593 - * Although fscrypt forbids rename() on no-key names, we still must use 594 - * dget_parent() here rather than use ->d_parent directly. That's 595 - * because a corrupted fs image may contain directory hard links, which 596 - * the VFS handles by moving the directory's dentry tree in the dcache 597 - * each time ->lookup() finds the directory and it already has a dentry 598 - * elsewhere. Thus ->d_parent can be changing, and we must safely grab 599 - * a reference to some ->d_parent to prevent it from being freed. 594 + * Note in RCU mode we have to bail if we get here - 595 + * fscrypt_get_encryption_info() may block. 600 596 */ 601 597 602 598 if (flags & LOOKUP_RCU) 603 599 return -ECHILD; 604 600 605 - dir = dget_parent(dentry); 606 601 /* 607 602 * Pass allow_unsupported=true, so that files with an unsupported 608 603 * encryption policy can be deleted. 609 604 */ 610 - err = fscrypt_get_encryption_info(d_inode(dir), true); 611 - valid = !fscrypt_has_encryption_key(d_inode(dir)); 612 - dput(dir); 613 - 605 + err = fscrypt_get_encryption_info(dir, true); 614 606 if (err < 0) 615 607 return err; 616 608 617 - return valid; 609 + return !fscrypt_has_encryption_key(dir); 618 610 } 619 611 EXPORT_SYMBOL_GPL(fscrypt_d_revalidate);
+60 -43
fs/dcache.c
··· 295 295 return dentry_string_cmp(cs, ct, tcount); 296 296 } 297 297 298 + /* 299 + * long names are allocated separately from dentry and never modified. 300 + * Refcounted, freeing is RCU-delayed. See take_dentry_name_snapshot() 301 + * for the reason why ->count and ->head can't be combined into a union. 302 + * dentry_string_cmp() relies upon ->name[] being word-aligned. 303 + */ 298 304 struct external_name { 299 - union { 300 - atomic_t count; 301 - struct rcu_head head; 302 - } u; 303 - unsigned char name[]; 305 + atomic_t count; 306 + struct rcu_head head; 307 + unsigned char name[] __aligned(sizeof(unsigned long)); 304 308 }; 305 309 306 310 static inline struct external_name *external_name(struct dentry *dentry) ··· 328 324 329 325 static inline int dname_external(const struct dentry *dentry) 330 326 { 331 - return dentry->d_name.name != dentry->d_iname; 327 + return dentry->d_name.name != dentry->d_shortname.string; 332 328 } 333 329 334 330 void take_dentry_name_snapshot(struct name_snapshot *name, struct dentry *dentry) 335 331 { 336 - spin_lock(&dentry->d_lock); 337 - name->name = dentry->d_name; 338 - if (unlikely(dname_external(dentry))) { 339 - atomic_inc(&external_name(dentry)->u.count); 332 + unsigned seq; 333 + const unsigned char *s; 334 + 335 + rcu_read_lock(); 336 + retry: 337 + seq = read_seqcount_begin(&dentry->d_seq); 338 + s = READ_ONCE(dentry->d_name.name); 339 + name->name.hash_len = dentry->d_name.hash_len; 340 + name->name.name = name->inline_name.string; 341 + if (likely(s == dentry->d_shortname.string)) { 342 + name->inline_name = dentry->d_shortname; 340 343 } else { 341 - memcpy(name->inline_name, dentry->d_iname, 342 - dentry->d_name.len + 1); 343 - name->name.name = name->inline_name; 344 + struct external_name *p; 345 + p = container_of(s, struct external_name, name[0]); 346 + // get a valid reference 347 + if (unlikely(!atomic_inc_not_zero(&p->count))) 348 + goto retry; 349 + name->name.name = s; 344 350 } 345 - spin_unlock(&dentry->d_lock); 351 + if (read_seqcount_retry(&dentry->d_seq, seq)) { 352 + release_dentry_name_snapshot(name); 353 + goto retry; 354 + } 355 + rcu_read_unlock(); 346 356 } 347 357 EXPORT_SYMBOL(take_dentry_name_snapshot); 348 358 349 359 void release_dentry_name_snapshot(struct name_snapshot *name) 350 360 { 351 - if (unlikely(name->name.name != name->inline_name)) { 361 + if (unlikely(name->name.name != name->inline_name.string)) { 352 362 struct external_name *p; 353 363 p = container_of(name->name.name, struct external_name, name[0]); 354 - if (unlikely(atomic_dec_and_test(&p->u.count))) 355 - kfree_rcu(p, u.head); 364 + if (unlikely(atomic_dec_and_test(&p->count))) 365 + kfree_rcu(p, head); 356 366 } 357 367 } 358 368 EXPORT_SYMBOL(release_dentry_name_snapshot); ··· 404 386 WARN_ON(!hlist_unhashed(&dentry->d_u.d_alias)); 405 387 if (unlikely(dname_external(dentry))) { 406 388 struct external_name *p = external_name(dentry); 407 - if (likely(atomic_dec_and_test(&p->u.count))) { 389 + if (likely(atomic_dec_and_test(&p->count))) { 408 390 call_rcu(&dentry->d_u.d_rcu, __d_free_external); 409 391 return; 410 392 } ··· 1672 1654 * will still always have a NUL at the end, even if we might 1673 1655 * be overwriting an internal NUL character 1674 1656 */ 1675 - dentry->d_iname[DNAME_INLINE_LEN-1] = 0; 1657 + dentry->d_shortname.string[DNAME_INLINE_LEN-1] = 0; 1676 1658 if (unlikely(!name)) { 1677 1659 name = &slash_name; 1678 - dname = dentry->d_iname; 1660 + dname = dentry->d_shortname.string; 1679 1661 } else if (name->len > DNAME_INLINE_LEN-1) { 1680 1662 size_t size = offsetof(struct external_name, name[1]); 1681 1663 struct external_name *p = kmalloc(size + name->len, ··· 1685 1667 kmem_cache_free(dentry_cache, dentry); 1686 1668 return NULL; 1687 1669 } 1688 - atomic_set(&p->u.count, 1); 1670 + atomic_set(&p->count, 1); 1689 1671 dname = p->name; 1690 1672 } else { 1691 - dname = dentry->d_iname; 1673 + dname = dentry->d_shortname.string; 1692 1674 } 1693 1675 1694 1676 dentry->d_name.len = name->len; ··· 2746 2728 * dentry:internal, target:external. Steal target's 2747 2729 * storage and make target internal. 2748 2730 */ 2749 - memcpy(target->d_iname, dentry->d_name.name, 2750 - dentry->d_name.len + 1); 2751 2731 dentry->d_name.name = target->d_name.name; 2752 - target->d_name.name = target->d_iname; 2732 + target->d_shortname = dentry->d_shortname; 2733 + target->d_name.name = target->d_shortname.string; 2753 2734 } 2754 2735 } else { 2755 2736 if (unlikely(dname_external(dentry))) { ··· 2756 2739 * dentry:external, target:internal. Give dentry's 2757 2740 * storage to target and make dentry internal 2758 2741 */ 2759 - memcpy(dentry->d_iname, target->d_name.name, 2760 - target->d_name.len + 1); 2761 2742 target->d_name.name = dentry->d_name.name; 2762 - dentry->d_name.name = dentry->d_iname; 2743 + dentry->d_shortname = target->d_shortname; 2744 + dentry->d_name.name = dentry->d_shortname.string; 2763 2745 } else { 2764 2746 /* 2765 2747 * Both are internal. 2766 2748 */ 2767 - unsigned int i; 2768 - BUILD_BUG_ON(!IS_ALIGNED(DNAME_INLINE_LEN, sizeof(long))); 2769 - for (i = 0; i < DNAME_INLINE_LEN / sizeof(long); i++) { 2770 - swap(((long *) &dentry->d_iname)[i], 2771 - ((long *) &target->d_iname)[i]); 2772 - } 2749 + for (int i = 0; i < DNAME_INLINE_WORDS; i++) 2750 + swap(dentry->d_shortname.words[i], 2751 + target->d_shortname.words[i]); 2773 2752 } 2774 2753 } 2775 2754 swap(dentry->d_name.hash_len, target->d_name.hash_len); ··· 2777 2764 if (unlikely(dname_external(dentry))) 2778 2765 old_name = external_name(dentry); 2779 2766 if (unlikely(dname_external(target))) { 2780 - atomic_inc(&external_name(target)->u.count); 2767 + atomic_inc(&external_name(target)->count); 2781 2768 dentry->d_name = target->d_name; 2782 2769 } else { 2783 - memcpy(dentry->d_iname, target->d_name.name, 2784 - target->d_name.len + 1); 2785 - dentry->d_name.name = dentry->d_iname; 2770 + dentry->d_shortname = target->d_shortname; 2771 + dentry->d_name.name = dentry->d_shortname.string; 2786 2772 dentry->d_name.hash_len = target->d_name.hash_len; 2787 2773 } 2788 - if (old_name && likely(atomic_dec_and_test(&old_name->u.count))) 2789 - kfree_rcu(old_name, u.head); 2774 + if (old_name && likely(atomic_dec_and_test(&old_name->count))) 2775 + kfree_rcu(old_name, head); 2790 2776 } 2791 2777 2792 2778 /* ··· 2966 2954 goto out_err; 2967 2955 m2 = &alias->d_parent->d_inode->i_rwsem; 2968 2956 out_unalias: 2957 + if (alias->d_op->d_unalias_trylock && 2958 + !alias->d_op->d_unalias_trylock(alias)) 2959 + goto out_err; 2969 2960 __d_move(alias, dentry, false); 2961 + if (alias->d_op->d_unalias_unlock) 2962 + alias->d_op->d_unalias_unlock(alias); 2970 2963 ret = 0; 2971 2964 out_err: 2972 2965 if (m2) ··· 3119 3102 { 3120 3103 struct dentry *dentry = file->f_path.dentry; 3121 3104 3122 - BUG_ON(dentry->d_name.name != dentry->d_iname || 3105 + BUG_ON(dname_external(dentry) || 3123 3106 !hlist_unhashed(&dentry->d_u.d_alias) || 3124 3107 !d_unlinked(dentry)); 3125 3108 spin_lock(&dentry->d_parent->d_lock); 3126 3109 spin_lock_nested(&dentry->d_lock, DENTRY_D_LOCK_NESTED); 3127 - dentry->d_name.len = sprintf(dentry->d_iname, "#%llu", 3110 + dentry->d_name.len = sprintf(dentry->d_shortname.string, "#%llu", 3128 3111 (unsigned long long)inode->i_ino); 3129 3112 spin_unlock(&dentry->d_lock); 3130 3113 spin_unlock(&dentry->d_parent->d_lock); ··· 3212 3195 */ 3213 3196 dentry_cache = KMEM_CACHE_USERCOPY(dentry, 3214 3197 SLAB_RECLAIM_ACCOUNT|SLAB_PANIC|SLAB_ACCOUNT, 3215 - d_iname); 3198 + d_shortname.string); 3216 3199 3217 3200 /* Hash may have been set up in dcache_init_early */ 3218 3201 if (!hashdist)
+14 -4
fs/ecryptfs/dentry.c
··· 17 17 18 18 /** 19 19 * ecryptfs_d_revalidate - revalidate an ecryptfs dentry 20 - * @dentry: The ecryptfs dentry 20 + * @dir: inode of expected parent 21 + * @name: expected name 22 + * @dentry: dentry to revalidate 21 23 * @flags: lookup flags 22 24 * 23 25 * Called when the VFS needs to revalidate a dentry. This ··· 30 28 * Returns 1 if valid, 0 otherwise. 31 29 * 32 30 */ 33 - static int ecryptfs_d_revalidate(struct dentry *dentry, unsigned int flags) 31 + static int ecryptfs_d_revalidate(struct inode *dir, const struct qstr *name, 32 + struct dentry *dentry, unsigned int flags) 34 33 { 35 34 struct dentry *lower_dentry = ecryptfs_dentry_to_lower(dentry); 36 35 int rc = 1; ··· 39 36 if (flags & LOOKUP_RCU) 40 37 return -ECHILD; 41 38 42 - if (lower_dentry->d_flags & DCACHE_OP_REVALIDATE) 43 - rc = lower_dentry->d_op->d_revalidate(lower_dentry, flags); 39 + if (lower_dentry->d_flags & DCACHE_OP_REVALIDATE) { 40 + struct inode *lower_dir = ecryptfs_inode_to_lower(dir); 41 + struct name_snapshot n; 42 + 43 + take_dentry_name_snapshot(&n, lower_dentry); 44 + rc = lower_dentry->d_op->d_revalidate(lower_dir, &n.name, 45 + lower_dentry, flags); 46 + release_dentry_name_snapshot(&n); 47 + } 44 48 45 49 if (d_really_is_positive(dentry)) { 46 50 struct inode *inode = d_inode(dentry);
+3 -8
fs/exfat/namei.c
··· 31 31 * If it happened, the negative dentry isn't actually negative anymore. So, 32 32 * drop it. 33 33 */ 34 - static int exfat_d_revalidate(struct dentry *dentry, unsigned int flags) 34 + static int exfat_d_revalidate(struct inode *dir, const struct qstr *name, 35 + struct dentry *dentry, unsigned int flags) 35 36 { 36 - int ret; 37 - 38 37 if (flags & LOOKUP_RCU) 39 38 return -ECHILD; 40 39 ··· 57 58 if (flags & (LOOKUP_CREATE | LOOKUP_RENAME_TARGET)) 58 59 return 0; 59 60 60 - spin_lock(&dentry->d_lock); 61 - ret = inode_eq_iversion(d_inode(dentry->d_parent), 62 - exfat_d_version(dentry)); 63 - spin_unlock(&dentry->d_lock); 64 - return ret; 61 + return inode_eq_iversion(dir, exfat_d_version(dentry)); 65 62 } 66 63 67 64 /* returns the length of a struct qstr, ignoring trailing dots if necessary */
+5 -24
fs/ext4/fast_commit.c
··· 322 322 WARN_ON(!list_empty(&ei->i_fc_dilist)); 323 323 spin_unlock(&sbi->s_fc_lock); 324 324 325 - if (fc_dentry->fcd_name.name && 326 - fc_dentry->fcd_name.len > DNAME_INLINE_LEN) 327 - kfree(fc_dentry->fcd_name.name); 325 + release_dentry_name_snapshot(&fc_dentry->fcd_name); 328 326 kmem_cache_free(ext4_fc_dentry_cachep, fc_dentry); 329 327 330 328 return; ··· 447 449 node->fcd_op = dentry_update->op; 448 450 node->fcd_parent = dir->i_ino; 449 451 node->fcd_ino = inode->i_ino; 450 - if (dentry->d_name.len > DNAME_INLINE_LEN) { 451 - node->fcd_name.name = kmalloc(dentry->d_name.len, GFP_NOFS); 452 - if (!node->fcd_name.name) { 453 - kmem_cache_free(ext4_fc_dentry_cachep, node); 454 - ext4_fc_mark_ineligible(sb, EXT4_FC_REASON_NOMEM, handle); 455 - mutex_lock(&ei->i_fc_lock); 456 - return -ENOMEM; 457 - } 458 - memcpy((u8 *)node->fcd_name.name, dentry->d_name.name, 459 - dentry->d_name.len); 460 - } else { 461 - memcpy(node->fcd_iname, dentry->d_name.name, 462 - dentry->d_name.len); 463 - node->fcd_name.name = node->fcd_iname; 464 - } 465 - node->fcd_name.len = dentry->d_name.len; 452 + take_dentry_name_snapshot(&node->fcd_name, dentry); 466 453 INIT_LIST_HEAD(&node->fcd_dilist); 467 454 spin_lock(&sbi->s_fc_lock); 468 455 if (sbi->s_journal->j_flags & JBD2_FULL_COMMIT_ONGOING || ··· 815 832 { 816 833 struct ext4_fc_dentry_info fcd; 817 834 struct ext4_fc_tl tl; 818 - int dlen = fc_dentry->fcd_name.len; 835 + int dlen = fc_dentry->fcd_name.name.len; 819 836 u8 *dst = ext4_fc_reserve_space(sb, 820 837 EXT4_FC_TAG_BASE_LEN + sizeof(fcd) + dlen, crc); 821 838 ··· 830 847 dst += EXT4_FC_TAG_BASE_LEN; 831 848 memcpy(dst, &fcd, sizeof(fcd)); 832 849 dst += sizeof(fcd); 833 - memcpy(dst, fc_dentry->fcd_name.name, dlen); 850 + memcpy(dst, fc_dentry->fcd_name.name.name, dlen); 834 851 835 852 return true; 836 853 } ··· 1311 1328 list_del_init(&fc_dentry->fcd_dilist); 1312 1329 spin_unlock(&sbi->s_fc_lock); 1313 1330 1314 - if (fc_dentry->fcd_name.name && 1315 - fc_dentry->fcd_name.len > DNAME_INLINE_LEN) 1316 - kfree(fc_dentry->fcd_name.name); 1331 + release_dentry_name_snapshot(&fc_dentry->fcd_name); 1317 1332 kmem_cache_free(ext4_fc_dentry_cachep, fc_dentry); 1318 1333 spin_lock(&sbi->s_fc_lock); 1319 1334 }
+1 -2
fs/ext4/fast_commit.h
··· 109 109 int fcd_op; /* Type of update create / unlink / link */ 110 110 int fcd_parent; /* Parent inode number */ 111 111 int fcd_ino; /* Inode number */ 112 - struct qstr fcd_name; /* Dirent name */ 113 - unsigned char fcd_iname[DNAME_INLINE_LEN]; /* Dirent name string */ 112 + struct name_snapshot fcd_name; /* Dirent name */ 114 113 struct list_head fcd_list; 115 114 struct list_head fcd_dilist; 116 115 };
+8 -11
fs/fat/namei_vfat.c
··· 43 43 * If it happened, the negative dentry isn't actually negative 44 44 * anymore. So, drop it. 45 45 */ 46 - static int vfat_revalidate_shortname(struct dentry *dentry) 46 + static bool vfat_revalidate_shortname(struct dentry *dentry, struct inode *dir) 47 47 { 48 - int ret = 1; 49 - spin_lock(&dentry->d_lock); 50 - if (!inode_eq_iversion(d_inode(dentry->d_parent), vfat_d_version(dentry))) 51 - ret = 0; 52 - spin_unlock(&dentry->d_lock); 53 - return ret; 48 + return inode_eq_iversion(dir, vfat_d_version(dentry)); 54 49 } 55 50 56 - static int vfat_revalidate(struct dentry *dentry, unsigned int flags) 51 + static int vfat_revalidate(struct inode *dir, const struct qstr *name, 52 + struct dentry *dentry, unsigned int flags) 57 53 { 58 54 if (flags & LOOKUP_RCU) 59 55 return -ECHILD; ··· 57 61 /* This is not negative dentry. Always valid. */ 58 62 if (d_really_is_positive(dentry)) 59 63 return 1; 60 - return vfat_revalidate_shortname(dentry); 64 + return vfat_revalidate_shortname(dentry, dir); 61 65 } 62 66 63 - static int vfat_revalidate_ci(struct dentry *dentry, unsigned int flags) 67 + static int vfat_revalidate_ci(struct inode *dir, const struct qstr *name, 68 + struct dentry *dentry, unsigned int flags) 64 69 { 65 70 if (flags & LOOKUP_RCU) 66 71 return -ECHILD; ··· 94 97 if (flags & (LOOKUP_CREATE | LOOKUP_RENAME_TARGET)) 95 98 return 0; 96 99 97 - return vfat_revalidate_shortname(dentry); 100 + return vfat_revalidate_shortname(dentry, dir); 98 101 } 99 102 100 103 /* returns the length of a struct qstr, ignoring trailing dots */
+9 -11
fs/fuse/dir.c
··· 175 175 memset(outarg, 0, sizeof(struct fuse_entry_out)); 176 176 args->opcode = FUSE_LOOKUP; 177 177 args->nodeid = nodeid; 178 - args->in_numargs = 2; 178 + args->in_numargs = 3; 179 179 fuse_set_zero_arg0(args); 180 - args->in_args[1].size = name->len + 1; 180 + args->in_args[1].size = name->len; 181 181 args->in_args[1].value = name->name; 182 + args->in_args[2].size = 1; 183 + args->in_args[2].value = ""; 182 184 args->out_numargs = 1; 183 185 args->out_args[0].size = sizeof(struct fuse_entry_out); 184 186 args->out_args[0].value = outarg; ··· 195 193 * the lookup once more. If the lookup results in the same inode, 196 194 * then refresh the attributes, timeouts and mark the dentry valid. 197 195 */ 198 - static int fuse_dentry_revalidate(struct dentry *entry, unsigned int flags) 196 + static int fuse_dentry_revalidate(struct inode *dir, const struct qstr *name, 197 + struct dentry *entry, unsigned int flags) 199 198 { 200 199 struct inode *inode; 201 - struct dentry *parent; 202 200 struct fuse_mount *fm; 203 201 struct fuse_inode *fi; 204 202 int ret; ··· 230 228 231 229 attr_version = fuse_get_attr_version(fm->fc); 232 230 233 - parent = dget_parent(entry); 234 - fuse_lookup_init(fm->fc, &args, get_node_id(d_inode(parent)), 235 - &entry->d_name, &outarg); 231 + fuse_lookup_init(fm->fc, &args, get_node_id(dir), 232 + name, &outarg); 236 233 ret = fuse_simple_request(fm, &args); 237 - dput(parent); 238 234 /* Zero nodeid is same as -ENOENT */ 239 235 if (!ret && !outarg.nodeid) 240 236 ret = -ENOENT; ··· 266 266 if (test_bit(FUSE_I_INIT_RDPLUS, &fi->state)) 267 267 return -ECHILD; 268 268 } else if (test_and_clear_bit(FUSE_I_INIT_RDPLUS, &fi->state)) { 269 - parent = dget_parent(entry); 270 - fuse_advise_use_readdirplus(d_inode(parent)); 271 - dput(parent); 269 + fuse_advise_use_readdirplus(dir); 272 270 } 273 271 } 274 272 ret = 1;
+13 -18
fs/gfs2/dentry.c
··· 21 21 22 22 /** 23 23 * gfs2_drevalidate - Check directory lookup consistency 24 - * @dentry: the mapping to check 24 + * @dir: expected parent directory inode 25 + * @name: expexted name 26 + * @dentry: dentry to check 25 27 * @flags: lookup flags 26 28 * 27 29 * Check to make sure the lookup necessary to arrive at this inode from its ··· 32 30 * Returns: 1 if the dentry is ok, 0 if it isn't 33 31 */ 34 32 35 - static int gfs2_drevalidate(struct dentry *dentry, unsigned int flags) 33 + static int gfs2_drevalidate(struct inode *dir, const struct qstr *name, 34 + struct dentry *dentry, unsigned int flags) 36 35 { 37 - struct dentry *parent; 38 - struct gfs2_sbd *sdp; 39 - struct gfs2_inode *dip; 36 + struct gfs2_sbd *sdp = GFS2_SB(dir); 37 + struct gfs2_inode *dip = GFS2_I(dir); 40 38 struct inode *inode; 41 39 struct gfs2_holder d_gh; 42 40 struct gfs2_inode *ip = NULL; 43 - int error, valid = 0; 41 + int error, valid; 44 42 int had_lock = 0; 45 43 46 44 if (flags & LOOKUP_RCU) 47 45 return -ECHILD; 48 46 49 - parent = dget_parent(dentry); 50 - sdp = GFS2_SB(d_inode(parent)); 51 - dip = GFS2_I(d_inode(parent)); 52 47 inode = d_inode(dentry); 53 48 54 49 if (inode) { 55 50 if (is_bad_inode(inode)) 56 - goto out; 51 + return 0; 57 52 ip = GFS2_I(inode); 58 53 } 59 54 60 - if (sdp->sd_lockstruct.ls_ops->lm_mount == NULL) { 61 - valid = 1; 62 - goto out; 63 - } 55 + if (sdp->sd_lockstruct.ls_ops->lm_mount == NULL) 56 + return 1; 64 57 65 58 had_lock = (gfs2_glock_is_locked_by_me(dip->i_gl) != NULL); 66 59 if (!had_lock) { 67 60 error = gfs2_glock_nq_init(dip->i_gl, LM_ST_SHARED, 0, &d_gh); 68 61 if (error) 69 - goto out; 62 + return 0; 70 63 } 71 64 72 - error = gfs2_dir_check(d_inode(parent), &dentry->d_name, ip); 65 + error = gfs2_dir_check(dir, name, ip); 73 66 valid = inode ? !error : (error == -ENOENT); 74 67 75 68 if (!had_lock) 76 69 gfs2_glock_dq_uninit(&d_gh); 77 - out: 78 - dput(parent); 79 70 return valid; 80 71 } 81 72
+2 -1
fs/hfs/sysdep.c
··· 13 13 14 14 /* dentry case-handling: just lowercase everything */ 15 15 16 - static int hfs_revalidate_dentry(struct dentry *dentry, unsigned int flags) 16 + static int hfs_revalidate_dentry(struct inode *dir, const struct qstr *name, 17 + struct dentry *dentry, unsigned int flags) 17 18 { 18 19 struct inode *inode; 19 20 int diff;
+2 -1
fs/jfs/namei.c
··· 1576 1576 return result; 1577 1577 } 1578 1578 1579 - static int jfs_ci_revalidate(struct dentry *dentry, unsigned int flags) 1579 + static int jfs_ci_revalidate(struct inode *dir, const struct qstr *name, 1580 + struct dentry *dentry, unsigned int flags) 1580 1581 { 1581 1582 /* 1582 1583 * This is not negative dentry. Always valid.
+2 -1
fs/kernfs/dir.c
··· 1109 1109 return ERR_PTR(rc); 1110 1110 } 1111 1111 1112 - static int kernfs_dop_revalidate(struct dentry *dentry, unsigned int flags) 1112 + static int kernfs_dop_revalidate(struct inode *dir, const struct qstr *name, 1113 + struct dentry *dentry, unsigned int flags) 1113 1114 { 1114 1115 struct kernfs_node *kn; 1115 1116 struct kernfs_root *root;
+8 -7
fs/libfs.c
··· 1782 1782 { 1783 1783 const struct dentry *parent; 1784 1784 const struct inode *dir; 1785 - char strbuf[DNAME_INLINE_LEN]; 1785 + union shortname_store strbuf; 1786 1786 struct qstr qstr; 1787 1787 1788 1788 /* ··· 1802 1802 if (!dir || !IS_CASEFOLDED(dir)) 1803 1803 return 1; 1804 1804 1805 + qstr.len = len; 1806 + qstr.name = str; 1805 1807 /* 1806 1808 * If the dentry name is stored in-line, then it may be concurrently 1807 1809 * modified by a rename. If this happens, the VFS will eventually retry 1808 1810 * the lookup, so it doesn't matter what ->d_compare() returns. 1809 1811 * However, it's unsafe to call utf8_strncasecmp() with an unstable 1810 1812 * string. Therefore, we have to copy the name into a temporary buffer. 1813 + * As above, len is guaranteed to match str, so the shortname case 1814 + * is exactly when str points to ->d_shortname. 1811 1815 */ 1812 - if (len <= DNAME_INLINE_LEN - 1) { 1813 - memcpy(strbuf, str, len); 1814 - strbuf[len] = 0; 1815 - str = strbuf; 1816 + if (qstr.name == dentry->d_shortname.string) { 1817 + strbuf = dentry->d_shortname; // NUL is guaranteed to be in there 1818 + qstr.name = strbuf.string; 1816 1819 /* prevent compiler from optimizing out the temporary buffer */ 1817 1820 barrier(); 1818 1821 } 1819 - qstr.len = len; 1820 - qstr.name = str; 1821 1822 1822 1823 return utf8_strncasecmp(dentry->d_sb->s_encoding, name, &qstr); 1823 1824 }
+10 -8
fs/namei.c
··· 921 921 return false; 922 922 } 923 923 924 - static inline int d_revalidate(struct dentry *dentry, unsigned int flags) 924 + static inline int d_revalidate(struct inode *dir, const struct qstr *name, 925 + struct dentry *dentry, unsigned int flags) 925 926 { 926 927 if (unlikely(dentry->d_flags & DCACHE_OP_REVALIDATE)) 927 - return dentry->d_op->d_revalidate(dentry, flags); 928 + return dentry->d_op->d_revalidate(dir, name, dentry, flags); 928 929 else 929 930 return 1; 930 931 } ··· 1653 1652 { 1654 1653 struct dentry *dentry = d_lookup(dir, name); 1655 1654 if (dentry) { 1656 - int error = d_revalidate(dentry, flags); 1655 + int error = d_revalidate(dir->d_inode, name, dentry, flags); 1657 1656 if (unlikely(error <= 0)) { 1658 1657 if (!error) 1659 1658 d_invalidate(dentry); ··· 1738 1737 if (read_seqcount_retry(&parent->d_seq, nd->seq)) 1739 1738 return ERR_PTR(-ECHILD); 1740 1739 1741 - status = d_revalidate(dentry, nd->flags); 1740 + status = d_revalidate(nd->inode, &nd->last, dentry, nd->flags); 1742 1741 if (likely(status > 0)) 1743 1742 return dentry; 1744 1743 if (!try_to_unlazy_next(nd, dentry)) 1745 1744 return ERR_PTR(-ECHILD); 1746 1745 if (status == -ECHILD) 1747 1746 /* we'd been told to redo it in non-rcu mode */ 1748 - status = d_revalidate(dentry, nd->flags); 1747 + status = d_revalidate(nd->inode, &nd->last, 1748 + dentry, nd->flags); 1749 1749 } else { 1750 1750 dentry = __d_lookup(parent, &nd->last); 1751 1751 if (unlikely(!dentry)) 1752 1752 return NULL; 1753 - status = d_revalidate(dentry, nd->flags); 1753 + status = d_revalidate(nd->inode, &nd->last, dentry, nd->flags); 1754 1754 } 1755 1755 if (unlikely(status <= 0)) { 1756 1756 if (!status) ··· 1779 1777 if (IS_ERR(dentry)) 1780 1778 return dentry; 1781 1779 if (unlikely(!d_in_lookup(dentry))) { 1782 - int error = d_revalidate(dentry, flags); 1780 + int error = d_revalidate(inode, name, dentry, flags); 1783 1781 if (unlikely(error <= 0)) { 1784 1782 if (!error) { 1785 1783 d_invalidate(dentry); ··· 3577 3575 if (d_in_lookup(dentry)) 3578 3576 break; 3579 3577 3580 - error = d_revalidate(dentry, nd->flags); 3578 + error = d_revalidate(dir_inode, &nd->last, dentry, nd->flags); 3581 3579 if (likely(error > 0)) 3582 3580 break; 3583 3581 if (error)
+25 -37
fs/nfs/dir.c
··· 1672 1672 return nfs_lookup_revalidate_done(dir, dentry, inode, 1); 1673 1673 } 1674 1674 1675 - static int nfs_lookup_revalidate_dentry(struct inode *dir, 1675 + static int nfs_lookup_revalidate_dentry(struct inode *dir, const struct qstr *name, 1676 1676 struct dentry *dentry, 1677 1677 struct inode *inode, unsigned int flags) 1678 1678 { ··· 1690 1690 goto out; 1691 1691 1692 1692 dir_verifier = nfs_save_change_attribute(dir); 1693 - ret = NFS_PROTO(dir)->lookup(dir, dentry, fhandle, fattr); 1693 + ret = NFS_PROTO(dir)->lookup(dir, dentry, name, fhandle, fattr); 1694 1694 if (ret < 0) 1695 1695 goto out; 1696 1696 ··· 1732 1732 * cached dentry and do a new lookup. 1733 1733 */ 1734 1734 static int 1735 - nfs_do_lookup_revalidate(struct inode *dir, struct dentry *dentry, 1736 - unsigned int flags) 1735 + nfs_do_lookup_revalidate(struct inode *dir, const struct qstr *name, 1736 + struct dentry *dentry, unsigned int flags) 1737 1737 { 1738 1738 struct inode *inode; 1739 1739 int error = 0; ··· 1775 1775 if (NFS_STALE(inode)) 1776 1776 goto out_bad; 1777 1777 1778 - return nfs_lookup_revalidate_dentry(dir, dentry, inode, flags); 1778 + return nfs_lookup_revalidate_dentry(dir, name, dentry, inode, flags); 1779 1779 out_valid: 1780 1780 return nfs_lookup_revalidate_done(dir, dentry, inode, 1); 1781 1781 out_bad: ··· 1785 1785 } 1786 1786 1787 1787 static int 1788 - __nfs_lookup_revalidate(struct dentry *dentry, unsigned int flags, 1789 - int (*reval)(struct inode *, struct dentry *, unsigned int)) 1788 + __nfs_lookup_revalidate(struct dentry *dentry, unsigned int flags) 1790 1789 { 1791 - struct dentry *parent; 1792 - struct inode *dir; 1793 - int ret; 1794 - 1795 1790 if (flags & LOOKUP_RCU) { 1796 1791 if (dentry->d_fsdata == NFS_FSDATA_BLOCKED) 1797 - return -ECHILD; 1798 - parent = READ_ONCE(dentry->d_parent); 1799 - dir = d_inode_rcu(parent); 1800 - if (!dir) 1801 - return -ECHILD; 1802 - ret = reval(dir, dentry, flags); 1803 - if (parent != READ_ONCE(dentry->d_parent)) 1804 1792 return -ECHILD; 1805 1793 } else { 1806 1794 /* Wait for unlink to complete - see unblock_revalidate() */ 1807 1795 wait_var_event(&dentry->d_fsdata, 1808 1796 smp_load_acquire(&dentry->d_fsdata) 1809 1797 != NFS_FSDATA_BLOCKED); 1810 - parent = dget_parent(dentry); 1811 - ret = reval(d_inode(parent), dentry, flags); 1812 - dput(parent); 1813 1798 } 1814 - return ret; 1799 + return 0; 1815 1800 } 1816 1801 1817 - static int nfs_lookup_revalidate(struct dentry *dentry, unsigned int flags) 1802 + static int nfs_lookup_revalidate(struct inode *dir, const struct qstr *name, 1803 + struct dentry *dentry, unsigned int flags) 1818 1804 { 1819 - return __nfs_lookup_revalidate(dentry, flags, nfs_do_lookup_revalidate); 1805 + if (__nfs_lookup_revalidate(dentry, flags)) 1806 + return -ECHILD; 1807 + return nfs_do_lookup_revalidate(dir, name, dentry, flags); 1820 1808 } 1821 1809 1822 1810 static void block_revalidate(struct dentry *dentry) ··· 1970 1982 1971 1983 dir_verifier = nfs_save_change_attribute(dir); 1972 1984 trace_nfs_lookup_enter(dir, dentry, flags); 1973 - error = NFS_PROTO(dir)->lookup(dir, dentry, fhandle, fattr); 1985 + error = NFS_PROTO(dir)->lookup(dir, dentry, &dentry->d_name, 1986 + fhandle, fattr); 1974 1987 if (error == -ENOENT) { 1975 1988 if (nfs_server_capable(dir, NFS_CAP_CASE_INSENSITIVE)) 1976 1989 dir_verifier = inode_peek_iversion_raw(dir); ··· 2014 2025 EXPORT_SYMBOL_GPL(nfs_d_prune_case_insensitive_aliases); 2015 2026 2016 2027 #if IS_ENABLED(CONFIG_NFS_V4) 2017 - static int nfs4_lookup_revalidate(struct dentry *, unsigned int); 2028 + static int nfs4_lookup_revalidate(struct inode *, const struct qstr *, 2029 + struct dentry *, unsigned int); 2018 2030 2019 2031 const struct dentry_operations nfs4_dentry_operations = { 2020 2032 .d_revalidate = nfs4_lookup_revalidate, ··· 2204 2214 EXPORT_SYMBOL_GPL(nfs_atomic_open); 2205 2215 2206 2216 static int 2207 - nfs4_do_lookup_revalidate(struct inode *dir, struct dentry *dentry, 2208 - unsigned int flags) 2217 + nfs4_lookup_revalidate(struct inode *dir, const struct qstr *name, 2218 + struct dentry *dentry, unsigned int flags) 2209 2219 { 2210 2220 struct inode *inode; 2221 + 2222 + if (__nfs_lookup_revalidate(dentry, flags)) 2223 + return -ECHILD; 2211 2224 2212 2225 trace_nfs_lookup_revalidate_enter(dir, dentry, flags); 2213 2226 ··· 2247 2254 reval_dentry: 2248 2255 if (flags & LOOKUP_RCU) 2249 2256 return -ECHILD; 2250 - return nfs_lookup_revalidate_dentry(dir, dentry, inode, flags); 2257 + return nfs_lookup_revalidate_dentry(dir, name, dentry, inode, flags); 2251 2258 2252 2259 full_reval: 2253 - return nfs_do_lookup_revalidate(dir, dentry, flags); 2254 - } 2255 - 2256 - static int nfs4_lookup_revalidate(struct dentry *dentry, unsigned int flags) 2257 - { 2258 - return __nfs_lookup_revalidate(dentry, flags, 2259 - nfs4_do_lookup_revalidate); 2260 + return nfs_do_lookup_revalidate(dir, name, dentry, flags); 2260 2261 } 2261 2262 2262 2263 #endif /* CONFIG_NFSV4 */ ··· 2306 2319 d_drop(dentry); 2307 2320 2308 2321 if (fhandle->size == 0) { 2309 - error = NFS_PROTO(dir)->lookup(dir, dentry, fhandle, fattr); 2322 + error = NFS_PROTO(dir)->lookup(dir, dentry, &dentry->d_name, 2323 + fhandle, fattr); 2310 2324 if (error) 2311 2325 goto out_error; 2312 2326 }
+1 -1
fs/nfs/namespace.c
··· 308 308 int err; 309 309 310 310 /* Look it up again to get its attributes */ 311 - err = server->nfs_client->rpc_ops->lookup(d_inode(parent), dentry, 311 + err = server->nfs_client->rpc_ops->lookup(d_inode(parent), dentry, &dentry->d_name, 312 312 ctx->mntfh, ctx->clone_data.fattr); 313 313 dput(parent); 314 314 if (err != 0)
+2 -3
fs/nfs/nfs3proc.c
··· 192 192 } 193 193 194 194 static int 195 - nfs3_proc_lookup(struct inode *dir, struct dentry *dentry, 195 + nfs3_proc_lookup(struct inode *dir, struct dentry *dentry, const struct qstr *name, 196 196 struct nfs_fh *fhandle, struct nfs_fattr *fattr) 197 197 { 198 198 unsigned short task_flags = 0; ··· 202 202 task_flags |= RPC_TASK_TIMEOUT; 203 203 204 204 dprintk("NFS call lookup %pd2\n", dentry); 205 - return __nfs3_proc_lookup(dir, dentry->d_name.name, 206 - dentry->d_name.len, fhandle, fattr, 205 + return __nfs3_proc_lookup(dir, name->name, name->len, fhandle, fattr, 207 206 task_flags); 208 207 } 209 208
+10 -10
fs/nfs/nfs4proc.c
··· 4544 4544 } 4545 4545 4546 4546 static int _nfs4_proc_lookup(struct rpc_clnt *clnt, struct inode *dir, 4547 - struct dentry *dentry, struct nfs_fh *fhandle, 4548 - struct nfs_fattr *fattr) 4547 + struct dentry *dentry, const struct qstr *name, 4548 + struct nfs_fh *fhandle, struct nfs_fattr *fattr) 4549 4549 { 4550 4550 struct nfs_server *server = NFS_SERVER(dir); 4551 4551 int status; 4552 4552 struct nfs4_lookup_arg args = { 4553 4553 .bitmask = server->attr_bitmask, 4554 4554 .dir_fh = NFS_FH(dir), 4555 - .name = &dentry->d_name, 4555 + .name = name, 4556 4556 }; 4557 4557 struct nfs4_lookup_res res = { 4558 4558 .server = server, ··· 4594 4594 } 4595 4595 4596 4596 static int nfs4_proc_lookup_common(struct rpc_clnt **clnt, struct inode *dir, 4597 - struct dentry *dentry, struct nfs_fh *fhandle, 4598 - struct nfs_fattr *fattr) 4597 + struct dentry *dentry, const struct qstr *name, 4598 + struct nfs_fh *fhandle, struct nfs_fattr *fattr) 4599 4599 { 4600 4600 struct nfs4_exception exception = { 4601 4601 .interruptible = true, 4602 4602 }; 4603 4603 struct rpc_clnt *client = *clnt; 4604 - const struct qstr *name = &dentry->d_name; 4605 4604 int err; 4606 4605 do { 4607 - err = _nfs4_proc_lookup(client, dir, dentry, fhandle, fattr); 4606 + err = _nfs4_proc_lookup(client, dir, dentry, name, fhandle, fattr); 4608 4607 trace_nfs4_lookup(dir, name, err); 4609 4608 switch (err) { 4610 4609 case -NFS4ERR_BADNAME: ··· 4638 4639 return err; 4639 4640 } 4640 4641 4641 - static int nfs4_proc_lookup(struct inode *dir, struct dentry *dentry, 4642 + static int nfs4_proc_lookup(struct inode *dir, struct dentry *dentry, const struct qstr *name, 4642 4643 struct nfs_fh *fhandle, struct nfs_fattr *fattr) 4643 4644 { 4644 4645 int status; 4645 4646 struct rpc_clnt *client = NFS_CLIENT(dir); 4646 4647 4647 - status = nfs4_proc_lookup_common(&client, dir, dentry, fhandle, fattr); 4648 + status = nfs4_proc_lookup_common(&client, dir, dentry, name, fhandle, fattr); 4648 4649 if (client != NFS_CLIENT(dir)) { 4649 4650 rpc_shutdown_client(client); 4650 4651 nfs_fixup_secinfo_attributes(fattr); ··· 4659 4660 struct rpc_clnt *client = NFS_CLIENT(dir); 4660 4661 int status; 4661 4662 4662 - status = nfs4_proc_lookup_common(&client, dir, dentry, fhandle, fattr); 4663 + status = nfs4_proc_lookup_common(&client, dir, dentry, &dentry->d_name, 4664 + fhandle, fattr); 4663 4665 if (status < 0) 4664 4666 return ERR_PTR(status); 4665 4667 return (client == NFS_CLIENT(dir)) ? rpc_clone_client(client) : client;
+3 -3
fs/nfs/proc.c
··· 153 153 } 154 154 155 155 static int 156 - nfs_proc_lookup(struct inode *dir, struct dentry *dentry, 156 + nfs_proc_lookup(struct inode *dir, struct dentry *dentry, const struct qstr *name, 157 157 struct nfs_fh *fhandle, struct nfs_fattr *fattr) 158 158 { 159 159 struct nfs_diropargs arg = { 160 160 .fh = NFS_FH(dir), 161 - .name = dentry->d_name.name, 162 - .len = dentry->d_name.len 161 + .name = name->name, 162 + .len = name->len 163 163 }; 164 164 struct nfs_diropok res = { 165 165 .fh = fhandle,
+5 -9
fs/ocfs2/dcache.c
··· 32 32 } 33 33 34 34 35 - static int ocfs2_dentry_revalidate(struct dentry *dentry, unsigned int flags) 35 + static int ocfs2_dentry_revalidate(struct inode *dir, const struct qstr *name, 36 + struct dentry *dentry, unsigned int flags) 36 37 { 37 38 struct inode *inode; 38 39 int ret = 0; /* if all else fails, just return false */ ··· 45 44 inode = d_inode(dentry); 46 45 osb = OCFS2_SB(dentry->d_sb); 47 46 48 - trace_ocfs2_dentry_revalidate(dentry, dentry->d_name.len, 49 - dentry->d_name.name); 47 + trace_ocfs2_dentry_revalidate(dentry, name->len, name->name); 50 48 51 49 /* For a negative dentry - 52 50 * check the generation number of the parent and compare with the ··· 53 53 */ 54 54 if (inode == NULL) { 55 55 unsigned long gen = (unsigned long) dentry->d_fsdata; 56 - unsigned long pgen; 57 - spin_lock(&dentry->d_lock); 58 - pgen = OCFS2_I(d_inode(dentry->d_parent))->ip_dir_lock_gen; 59 - spin_unlock(&dentry->d_lock); 60 - trace_ocfs2_dentry_revalidate_negative(dentry->d_name.len, 61 - dentry->d_name.name, 56 + unsigned long pgen = OCFS2_I(dir)->ip_dir_lock_gen; 57 + trace_ocfs2_dentry_revalidate_negative(name->len, name->name, 62 58 pgen, gen); 63 59 if (gen != pgen) 64 60 goto bail;
+10 -12
fs/orangefs/dcache.c
··· 13 13 #include "orangefs-kernel.h" 14 14 15 15 /* Returns 1 if dentry can still be trusted, else 0. */ 16 - static int orangefs_revalidate_lookup(struct dentry *dentry) 16 + static int orangefs_revalidate_lookup(struct inode *parent_inode, const struct qstr *name, 17 + struct dentry *dentry) 17 18 { 18 - struct dentry *parent_dentry = dget_parent(dentry); 19 - struct inode *parent_inode = parent_dentry->d_inode; 20 19 struct orangefs_inode_s *parent = ORANGEFS_I(parent_inode); 21 20 struct inode *inode = dentry->d_inode; 22 21 struct orangefs_kernel_op_s *new_op; ··· 25 26 gossip_debug(GOSSIP_DCACHE_DEBUG, "%s: attempting lookup.\n", __func__); 26 27 27 28 new_op = op_alloc(ORANGEFS_VFS_OP_LOOKUP); 28 - if (!new_op) { 29 - ret = -ENOMEM; 30 - goto out_put_parent; 31 - } 29 + if (!new_op) 30 + return -ENOMEM; 32 31 33 32 new_op->upcall.req.lookup.sym_follow = ORANGEFS_LOOKUP_LINK_NO_FOLLOW; 34 33 new_op->upcall.req.lookup.parent_refn = parent->refn; 35 - strscpy(new_op->upcall.req.lookup.d_name, dentry->d_name.name); 34 + /* op_alloc() leaves ->upcall zeroed */ 35 + memcpy(new_op->upcall.req.lookup.d_name, name->name, 36 + min(name->len, ORANGEFS_NAME_MAX - 1)); 36 37 37 38 gossip_debug(GOSSIP_DCACHE_DEBUG, 38 39 "%s:%s:%d interrupt flag [%d]\n", ··· 77 78 ret = 1; 78 79 out_release_op: 79 80 op_release(new_op); 80 - out_put_parent: 81 - dput(parent_dentry); 82 81 return ret; 83 82 out_drop: 84 83 gossip_debug(GOSSIP_DCACHE_DEBUG, "%s:%s:%d revalidate failed\n", ··· 89 92 * 90 93 * Should return 1 if dentry can still be trusted, else 0. 91 94 */ 92 - static int orangefs_d_revalidate(struct dentry *dentry, unsigned int flags) 95 + static int orangefs_d_revalidate(struct inode *dir, const struct qstr *name, 96 + struct dentry *dentry, unsigned int flags) 93 97 { 94 98 int ret; 95 99 unsigned long time = (unsigned long) dentry->d_fsdata; ··· 112 114 * If this passes, the positive dentry still exists or the negative 113 115 * dentry still does not exist. 114 116 */ 115 - if (!orangefs_revalidate_lookup(dentry)) 117 + if (!orangefs_revalidate_lookup(dir, name, dentry)) 116 118 return 0; 117 119 118 120 /* We do not need to continue with negative dentries. */
+20 -2
fs/overlayfs/super.c
··· 91 91 if (d->d_flags & DCACHE_OP_WEAK_REVALIDATE) 92 92 ret = d->d_op->d_weak_revalidate(d, flags); 93 93 } else if (d->d_flags & DCACHE_OP_REVALIDATE) { 94 - ret = d->d_op->d_revalidate(d, flags); 94 + struct dentry *parent; 95 + struct inode *dir; 96 + struct name_snapshot n; 97 + 98 + if (flags & LOOKUP_RCU) { 99 + parent = READ_ONCE(d->d_parent); 100 + dir = d_inode_rcu(parent); 101 + if (!dir) 102 + return -ECHILD; 103 + } else { 104 + parent = dget_parent(d); 105 + dir = d_inode(parent); 106 + } 107 + take_dentry_name_snapshot(&n, d); 108 + ret = d->d_op->d_revalidate(dir, &n.name, d, flags); 109 + release_dentry_name_snapshot(&n); 110 + if (!(flags & LOOKUP_RCU)) 111 + dput(parent); 95 112 if (!ret) { 96 113 if (!(flags & LOOKUP_RCU)) 97 114 d_invalidate(d); ··· 144 127 return ret; 145 128 } 146 129 147 - static int ovl_dentry_revalidate(struct dentry *dentry, unsigned int flags) 130 + static int ovl_dentry_revalidate(struct inode *dir, const struct qstr *name, 131 + struct dentry *dentry, unsigned int flags) 148 132 { 149 133 return ovl_dentry_revalidate_common(dentry, flags, false); 150 134 }
+4 -2
fs/proc/base.c
··· 2058 2058 * performed a setuid(), etc. 2059 2059 * 2060 2060 */ 2061 - static int pid_revalidate(struct dentry *dentry, unsigned int flags) 2061 + static int pid_revalidate(struct inode *dir, const struct qstr *name, 2062 + struct dentry *dentry, unsigned int flags) 2062 2063 { 2063 2064 struct inode *inode; 2064 2065 struct task_struct *task; ··· 2192 2191 return 0; 2193 2192 } 2194 2193 2195 - static int map_files_d_revalidate(struct dentry *dentry, unsigned int flags) 2194 + static int map_files_d_revalidate(struct inode *dir, const struct qstr *name, 2195 + struct dentry *dentry, unsigned int flags) 2196 2196 { 2197 2197 unsigned long vm_start, vm_end; 2198 2198 bool exact_vma_exists = false;
+2 -1
fs/proc/fd.c
··· 140 140 security_task_to_inode(task, inode); 141 141 } 142 142 143 - static int tid_fd_revalidate(struct dentry *dentry, unsigned int flags) 143 + static int tid_fd_revalidate(struct inode *dir, const struct qstr *name, 144 + struct dentry *dentry, unsigned int flags) 144 145 { 145 146 struct task_struct *task; 146 147 struct inode *inode;
+4 -2
fs/proc/generic.c
··· 216 216 ida_free(&proc_inum_ida, inum - PROC_DYNAMIC_FIRST); 217 217 } 218 218 219 - static int proc_misc_d_revalidate(struct dentry *dentry, unsigned int flags) 219 + static int proc_misc_d_revalidate(struct inode *dir, const struct qstr *name, 220 + struct dentry *dentry, unsigned int flags) 220 221 { 221 222 if (flags & LOOKUP_RCU) 222 223 return -ECHILD; ··· 344 343 .iterate_shared = proc_readdir, 345 344 }; 346 345 347 - static int proc_net_d_revalidate(struct dentry *dentry, unsigned int flags) 346 + static int proc_net_d_revalidate(struct inode *dir, const struct qstr *name, 347 + struct dentry *dentry, unsigned int flags) 348 348 { 349 349 return 0; 350 350 }
+2 -1
fs/proc/proc_sysctl.c
··· 884 884 .getattr = proc_sys_getattr, 885 885 }; 886 886 887 - static int proc_sys_revalidate(struct dentry *dentry, unsigned int flags) 887 + static int proc_sys_revalidate(struct inode *dir, const struct qstr *name, 888 + struct dentry *dentry, unsigned int flags) 888 889 { 889 890 if (flags & LOOKUP_RCU) 890 891 return -ECHILD;
+2 -1
fs/smb/client/dir.c
··· 737 737 } 738 738 739 739 static int 740 - cifs_d_revalidate(struct dentry *direntry, unsigned int flags) 740 + cifs_d_revalidate(struct inode *dir, const struct qstr *name, 741 + struct dentry *direntry, unsigned int flags) 741 742 { 742 743 struct inode *inode; 743 744 int rc;
+2 -1
fs/tracefs/inode.c
··· 457 457 eventfs_d_release(dentry); 458 458 } 459 459 460 - static int tracefs_d_revalidate(struct dentry *dentry, unsigned int flags) 460 + static int tracefs_d_revalidate(struct inode *inode, const struct qstr *name, 461 + struct dentry *dentry, unsigned int flags) 461 462 { 462 463 struct eventfs_inode *ei = dentry->d_fsdata; 463 464
+2 -1
fs/vboxsf/dir.c
··· 192 192 * This is called during name resolution/lookup to check if the @dentry in 193 193 * the cache is still valid. the job is handled by vboxsf_inode_revalidate. 194 194 */ 195 - static int vboxsf_dentry_revalidate(struct dentry *dentry, unsigned int flags) 195 + static int vboxsf_dentry_revalidate(struct inode *dir, const struct qstr *name, 196 + struct dentry *dentry, unsigned int flags) 196 197 { 197 198 if (flags & LOOKUP_RCU) 198 199 return -ECHILD;
+17 -6
include/linux/dcache.h
··· 68 68 * large memory footprint increase). 69 69 */ 70 70 #ifdef CONFIG_64BIT 71 - # define DNAME_INLINE_LEN 40 /* 192 bytes */ 71 + # define DNAME_INLINE_WORDS 5 /* 192 bytes */ 72 72 #else 73 73 # ifdef CONFIG_SMP 74 - # define DNAME_INLINE_LEN 36 /* 128 bytes */ 74 + # define DNAME_INLINE_WORDS 9 /* 128 bytes */ 75 75 # else 76 - # define DNAME_INLINE_LEN 44 /* 128 bytes */ 76 + # define DNAME_INLINE_WORDS 11 /* 128 bytes */ 77 77 # endif 78 78 #endif 79 79 80 + #define DNAME_INLINE_LEN (DNAME_INLINE_WORDS*sizeof(unsigned long)) 81 + 82 + union shortname_store { 83 + unsigned char string[DNAME_INLINE_LEN]; 84 + unsigned long words[DNAME_INLINE_WORDS]; 85 + }; 86 + 80 87 #define d_lock d_lockref.lock 88 + #define d_iname d_shortname.string 81 89 82 90 struct dentry { 83 91 /* RCU lookup touched fields */ ··· 96 88 struct qstr d_name; 97 89 struct inode *d_inode; /* Where the name belongs to - NULL is 98 90 * negative */ 99 - unsigned char d_iname[DNAME_INLINE_LEN]; /* small names */ 91 + union shortname_store d_shortname; 100 92 /* --- cacheline 1 boundary (64 bytes) was 32 bytes ago --- */ 101 93 102 94 /* Ref lookup also touches following */ ··· 144 136 }; 145 137 146 138 struct dentry_operations { 147 - int (*d_revalidate)(struct dentry *, unsigned int); 139 + int (*d_revalidate)(struct inode *, const struct qstr *, 140 + struct dentry *, unsigned int); 148 141 int (*d_weak_revalidate)(struct dentry *, unsigned int); 149 142 int (*d_hash)(const struct dentry *, struct qstr *); 150 143 int (*d_compare)(const struct dentry *, ··· 159 150 struct vfsmount *(*d_automount)(struct path *); 160 151 int (*d_manage)(const struct path *, bool); 161 152 struct dentry *(*d_real)(struct dentry *, enum d_real_type type); 153 + bool (*d_unalias_trylock)(const struct dentry *); 154 + void (*d_unalias_unlock)(const struct dentry *); 162 155 } ____cacheline_aligned; 163 156 164 157 /* ··· 600 589 601 590 struct name_snapshot { 602 591 struct qstr name; 603 - unsigned char inline_name[DNAME_INLINE_LEN]; 592 + union shortname_store inline_name; 604 593 }; 605 594 void take_dentry_name_snapshot(struct name_snapshot *, struct dentry *); 606 595 void release_dentry_name_snapshot(struct name_snapshot *);
+4 -3
include/linux/fscrypt.h
··· 192 192 unsigned int *num_devs); 193 193 }; 194 194 195 - int fscrypt_d_revalidate(struct dentry *dentry, unsigned int flags); 195 + int fscrypt_d_revalidate(struct inode *dir, const struct qstr *name, 196 + struct dentry *dentry, unsigned int flags); 196 197 197 198 static inline struct fscrypt_inode_info * 198 199 fscrypt_get_inode_info(const struct inode *inode) ··· 712 711 return 0; 713 712 } 714 713 715 - static inline int fscrypt_d_revalidate(struct dentry *dentry, 716 - unsigned int flags) 714 + static inline int fscrypt_d_revalidate(struct inode *dir, const struct qstr *name, 715 + struct dentry *dentry, unsigned int flags) 717 716 { 718 717 return 1; 719 718 }
+1 -1
include/linux/nfs_xdr.h
··· 1781 1781 struct nfs_fattr *, struct inode *); 1782 1782 int (*setattr) (struct dentry *, struct nfs_fattr *, 1783 1783 struct iattr *); 1784 - int (*lookup) (struct inode *, struct dentry *, 1784 + int (*lookup) (struct inode *, struct dentry *, const struct qstr *, 1785 1785 struct nfs_fh *, struct nfs_fattr *); 1786 1786 int (*lookupp) (struct inode *, struct nfs_fh *, 1787 1787 struct nfs_fattr *);
+1 -1
tools/testing/selftests/bpf/progs/find_vma.c
··· 25 25 { 26 26 if (vma->vm_file) 27 27 bpf_probe_read_kernel_str(d_iname, DNAME_INLINE_LEN - 1, 28 - vma->vm_file->f_path.dentry->d_iname); 28 + vma->vm_file->f_path.dentry->d_shortname.string); 29 29 30 30 /* check for VM_EXEC */ 31 31 if (vma->vm_flags & VM_EXEC)