aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@linux-foundation.org>2019-05-07 23:03:32 -0400
committerLinus Torvalds <torvalds@linux-foundation.org>2019-05-07 23:03:32 -0400
commitd27fb65bc2389621040e5107baedb94b4cccf641 (patch)
tree4123a7b82dd048dc8b0602994a5db6f4b9885998
parentd3511f53bb2475f2a4e8460bee5a1ae6dea2a433 (diff)
parent795d673af1afae8146ac3070a2d77cfae5287c43 (diff)
Merge branch 'work.dcache' of git://git.kernel.org/pub/scm/linux/kernel/git/viro/vfs
Pull misc dcache updates from Al Viro: "Most of this pile is putting name length into struct name_snapshot and making use of it. The beginning of this series ("ovl_lookup_real_one(): don't bother with strlen()") ought to have been split in two (separate switch of name_snapshot to struct qstr from overlayfs reaping the trivial benefits of that), but I wanted to avoid a rebase - by the time I'd spotted that it was (a) in -next and (b) close to 5.1-final ;-/" * 'work.dcache' of git://git.kernel.org/pub/scm/linux/kernel/git/viro/vfs: audit_compare_dname_path(): switch to const struct qstr * audit_update_watch(): switch to const struct qstr * inotify_handle_event(): don't bother with strlen() fsnotify: switch send_to_group() and ->handle_event to const struct qstr * fsnotify(): switch to passing const struct qstr * for file_name switch fsnotify_move() to passing const struct qstr * for old_name ovl_lookup_real_one(): don't bother with strlen() sysv: bury the broken "quietly truncate the long filenames" logics nsfs: unobfuscate unexport d_alloc_pseudo()
-rw-r--r--Documentation/filesystems/porting5
-rw-r--r--fs/dcache.c18
-rw-r--r--fs/debugfs/inode.c2
-rw-r--r--fs/internal.h1
-rw-r--r--fs/kernfs/file.c6
-rw-r--r--fs/namei.c4
-rw-r--r--fs/notify/dnotify/dnotify.c2
-rw-r--r--fs/notify/fanotify/fanotify.c2
-rw-r--r--fs/notify/fsnotify.c8
-rw-r--r--fs/notify/inotify/inotify.h2
-rw-r--r--fs/notify/inotify/inotify_fsnotify.c6
-rw-r--r--fs/nsfs.c23
-rw-r--r--fs/overlayfs/export.c2
-rw-r--r--fs/sysv/namei.c15
-rw-r--r--fs/sysv/super.c3
-rw-r--r--fs/sysv/sysv.h3
-rw-r--r--include/linux/dcache.h3
-rw-r--r--include/linux/fsnotify.h10
-rw-r--r--include/linux/fsnotify_backend.h6
-rw-r--r--kernel/audit.h2
-rw-r--r--kernel/audit_fsnotify.c2
-rw-r--r--kernel/audit_tree.c2
-rw-r--r--kernel/audit_watch.c4
-rw-r--r--kernel/auditfilter.c6
-rw-r--r--kernel/auditsc.c4
25 files changed, 62 insertions, 79 deletions
diff --git a/Documentation/filesystems/porting b/Documentation/filesystems/porting
index d392d4b0c393..3bd1148d8bb6 100644
--- a/Documentation/filesystems/porting
+++ b/Documentation/filesystems/porting
@@ -668,3 +668,8 @@ in your dentry operations instead.
668 DCACHE_RCUACCESS is gone; having an RCU delay on dentry freeing is the 668 DCACHE_RCUACCESS is gone; having an RCU delay on dentry freeing is the
669 default. DCACHE_NORCU opts out, and only d_alloc_pseudo() has any 669 default. DCACHE_NORCU opts out, and only d_alloc_pseudo() has any
670 business doing so. 670 business doing so.
671--
672[mandatory]
673 d_alloc_pseudo() is internal-only; uses outside of alloc_file_pseudo() are
674 very suspect (and won't work in modules). Such uses are very likely to
675 be misspelled d_alloc_anon().
diff --git a/fs/dcache.c b/fs/dcache.c
index c663c602f9ef..982d97bbb72c 100644
--- a/fs/dcache.c
+++ b/fs/dcache.c
@@ -284,25 +284,23 @@ static inline int dname_external(const struct dentry *dentry)
284void take_dentry_name_snapshot(struct name_snapshot *name, struct dentry *dentry) 284void take_dentry_name_snapshot(struct name_snapshot *name, struct dentry *dentry)
285{ 285{
286 spin_lock(&dentry->d_lock); 286 spin_lock(&dentry->d_lock);
287 name->name = dentry->d_name;
287 if (unlikely(dname_external(dentry))) { 288 if (unlikely(dname_external(dentry))) {
288 struct external_name *p = external_name(dentry); 289 atomic_inc(&external_name(dentry)->u.count);
289 atomic_inc(&p->u.count);
290 spin_unlock(&dentry->d_lock);
291 name->name = p->name;
292 } else { 290 } else {
293 memcpy(name->inline_name, dentry->d_iname, 291 memcpy(name->inline_name, dentry->d_iname,
294 dentry->d_name.len + 1); 292 dentry->d_name.len + 1);
295 spin_unlock(&dentry->d_lock); 293 name->name.name = name->inline_name;
296 name->name = name->inline_name;
297 } 294 }
295 spin_unlock(&dentry->d_lock);
298} 296}
299EXPORT_SYMBOL(take_dentry_name_snapshot); 297EXPORT_SYMBOL(take_dentry_name_snapshot);
300 298
301void release_dentry_name_snapshot(struct name_snapshot *name) 299void release_dentry_name_snapshot(struct name_snapshot *name)
302{ 300{
303 if (unlikely(name->name != name->inline_name)) { 301 if (unlikely(name->name.name != name->inline_name)) {
304 struct external_name *p; 302 struct external_name *p;
305 p = container_of(name->name, struct external_name, name[0]); 303 p = container_of(name->name.name, struct external_name, name[0]);
306 if (unlikely(atomic_dec_and_test(&p->u.count))) 304 if (unlikely(atomic_dec_and_test(&p->u.count)))
307 kfree_rcu(p, u.head); 305 kfree_rcu(p, u.head);
308 } 306 }
@@ -1742,6 +1740,9 @@ struct dentry *d_alloc_cursor(struct dentry * parent)
1742 * never be anyone's children or parents. Unlike all other 1740 * never be anyone's children or parents. Unlike all other
1743 * dentries, these will not have RCU delay between dropping the 1741 * dentries, these will not have RCU delay between dropping the
1744 * last reference and freeing them. 1742 * last reference and freeing them.
1743 *
1744 * The only user is alloc_file_pseudo() and that's what should
1745 * be considered a public interface. Don't use directly.
1745 */ 1746 */
1746struct dentry *d_alloc_pseudo(struct super_block *sb, const struct qstr *name) 1747struct dentry *d_alloc_pseudo(struct super_block *sb, const struct qstr *name)
1747{ 1748{
@@ -1750,7 +1751,6 @@ struct dentry *d_alloc_pseudo(struct super_block *sb, const struct qstr *name)
1750 dentry->d_flags |= DCACHE_NORCU; 1751 dentry->d_flags |= DCACHE_NORCU;
1751 return dentry; 1752 return dentry;
1752} 1753}
1753EXPORT_SYMBOL(d_alloc_pseudo);
1754 1754
1755struct dentry *d_alloc_name(struct dentry *parent, const char *name) 1755struct dentry *d_alloc_name(struct dentry *parent, const char *name)
1756{ 1756{
diff --git a/fs/debugfs/inode.c b/fs/debugfs/inode.c
index 414fa4752047..acef14ad53db 100644
--- a/fs/debugfs/inode.c
+++ b/fs/debugfs/inode.c
@@ -818,7 +818,7 @@ struct dentry *debugfs_rename(struct dentry *old_dir, struct dentry *old_dentry,
818 goto exit; 818 goto exit;
819 } 819 }
820 d_move(old_dentry, dentry); 820 d_move(old_dentry, dentry);
821 fsnotify_move(d_inode(old_dir), d_inode(new_dir), old_name.name, 821 fsnotify_move(d_inode(old_dir), d_inode(new_dir), &old_name.name,
822 d_is_dir(old_dentry), 822 d_is_dir(old_dentry),
823 NULL, old_dentry); 823 NULL, old_dentry);
824 release_dentry_name_snapshot(&old_name); 824 release_dentry_name_snapshot(&old_name);
diff --git a/fs/internal.h b/fs/internal.h
index 82b78aec1ce9..17a8ae967493 100644
--- a/fs/internal.h
+++ b/fs/internal.h
@@ -155,6 +155,7 @@ extern struct dentry *__d_alloc(struct super_block *, const struct qstr *);
155extern int d_set_mounted(struct dentry *dentry); 155extern int d_set_mounted(struct dentry *dentry);
156extern long prune_dcache_sb(struct super_block *sb, struct shrink_control *sc); 156extern long prune_dcache_sb(struct super_block *sb, struct shrink_control *sc);
157extern struct dentry *d_alloc_cursor(struct dentry *); 157extern struct dentry *d_alloc_cursor(struct dentry *);
158extern struct dentry * d_alloc_pseudo(struct super_block *, const struct qstr *);
158 159
159/* 160/*
160 * read_write.c 161 * read_write.c
diff --git a/fs/kernfs/file.c b/fs/kernfs/file.c
index ae948aaa4c53..553ce0a92b05 100644
--- a/fs/kernfs/file.c
+++ b/fs/kernfs/file.c
@@ -885,6 +885,7 @@ repeat:
885 list_for_each_entry(info, &kernfs_root(kn)->supers, node) { 885 list_for_each_entry(info, &kernfs_root(kn)->supers, node) {
886 struct kernfs_node *parent; 886 struct kernfs_node *parent;
887 struct inode *inode; 887 struct inode *inode;
888 struct qstr name;
888 889
889 /* 890 /*
890 * We want fsnotify_modify() on @kn but as the 891 * We want fsnotify_modify() on @kn but as the
@@ -896,6 +897,7 @@ repeat:
896 if (!inode) 897 if (!inode)
897 continue; 898 continue;
898 899
900 name = (struct qstr)QSTR_INIT(kn->name, strlen(kn->name));
899 parent = kernfs_get_parent(kn); 901 parent = kernfs_get_parent(kn);
900 if (parent) { 902 if (parent) {
901 struct inode *p_inode; 903 struct inode *p_inode;
@@ -903,7 +905,7 @@ repeat:
903 p_inode = ilookup(info->sb, parent->id.ino); 905 p_inode = ilookup(info->sb, parent->id.ino);
904 if (p_inode) { 906 if (p_inode) {
905 fsnotify(p_inode, FS_MODIFY | FS_EVENT_ON_CHILD, 907 fsnotify(p_inode, FS_MODIFY | FS_EVENT_ON_CHILD,
906 inode, FSNOTIFY_EVENT_INODE, kn->name, 0); 908 inode, FSNOTIFY_EVENT_INODE, &name, 0);
907 iput(p_inode); 909 iput(p_inode);
908 } 910 }
909 911
@@ -911,7 +913,7 @@ repeat:
911 } 913 }
912 914
913 fsnotify(inode, FS_MODIFY, inode, FSNOTIFY_EVENT_INODE, 915 fsnotify(inode, FS_MODIFY, inode, FSNOTIFY_EVENT_INODE,
914 kn->name, 0); 916 &name, 0);
915 iput(inode); 917 iput(inode);
916 } 918 }
917 919
diff --git a/fs/namei.c b/fs/namei.c
index dede0147b3f6..5ebd64b21970 100644
--- a/fs/namei.c
+++ b/fs/namei.c
@@ -4498,10 +4498,10 @@ out:
4498 inode_unlock(target); 4498 inode_unlock(target);
4499 dput(new_dentry); 4499 dput(new_dentry);
4500 if (!error) { 4500 if (!error) {
4501 fsnotify_move(old_dir, new_dir, old_name.name, is_dir, 4501 fsnotify_move(old_dir, new_dir, &old_name.name, is_dir,
4502 !(flags & RENAME_EXCHANGE) ? target : NULL, old_dentry); 4502 !(flags & RENAME_EXCHANGE) ? target : NULL, old_dentry);
4503 if (flags & RENAME_EXCHANGE) { 4503 if (flags & RENAME_EXCHANGE) {
4504 fsnotify_move(new_dir, old_dir, old_dentry->d_name.name, 4504 fsnotify_move(new_dir, old_dir, &old_dentry->d_name,
4505 new_is_dir, NULL, new_dentry); 4505 new_is_dir, NULL, new_dentry);
4506 } 4506 }
4507 } 4507 }
diff --git a/fs/notify/dnotify/dnotify.c b/fs/notify/dnotify/dnotify.c
index 58d77dc696eb..250369d6901d 100644
--- a/fs/notify/dnotify/dnotify.c
+++ b/fs/notify/dnotify/dnotify.c
@@ -81,7 +81,7 @@ static void dnotify_recalc_inode_mask(struct fsnotify_mark *fsn_mark)
81static int dnotify_handle_event(struct fsnotify_group *group, 81static int dnotify_handle_event(struct fsnotify_group *group,
82 struct inode *inode, 82 struct inode *inode,
83 u32 mask, const void *data, int data_type, 83 u32 mask, const void *data, int data_type,
84 const unsigned char *file_name, u32 cookie, 84 const struct qstr *file_name, u32 cookie,
85 struct fsnotify_iter_info *iter_info) 85 struct fsnotify_iter_info *iter_info)
86{ 86{
87 struct fsnotify_mark *inode_mark = fsnotify_iter_inode_mark(iter_info); 87 struct fsnotify_mark *inode_mark = fsnotify_iter_inode_mark(iter_info);
diff --git a/fs/notify/fanotify/fanotify.c b/fs/notify/fanotify/fanotify.c
index 63c6bb1f8c4d..e6fde1a5c072 100644
--- a/fs/notify/fanotify/fanotify.c
+++ b/fs/notify/fanotify/fanotify.c
@@ -367,7 +367,7 @@ static __kernel_fsid_t fanotify_get_fsid(struct fsnotify_iter_info *iter_info)
367static int fanotify_handle_event(struct fsnotify_group *group, 367static int fanotify_handle_event(struct fsnotify_group *group,
368 struct inode *inode, 368 struct inode *inode,
369 u32 mask, const void *data, int data_type, 369 u32 mask, const void *data, int data_type,
370 const unsigned char *file_name, u32 cookie, 370 const struct qstr *file_name, u32 cookie,
371 struct fsnotify_iter_info *iter_info) 371 struct fsnotify_iter_info *iter_info)
372{ 372{
373 int ret = 0; 373 int ret = 0;
diff --git a/fs/notify/fsnotify.c b/fs/notify/fsnotify.c
index df06f3da166c..5433e37fb0c5 100644
--- a/fs/notify/fsnotify.c
+++ b/fs/notify/fsnotify.c
@@ -179,10 +179,10 @@ int __fsnotify_parent(const struct path *path, struct dentry *dentry, __u32 mask
179 take_dentry_name_snapshot(&name, dentry); 179 take_dentry_name_snapshot(&name, dentry);
180 if (path) 180 if (path)
181 ret = fsnotify(p_inode, mask, path, FSNOTIFY_EVENT_PATH, 181 ret = fsnotify(p_inode, mask, path, FSNOTIFY_EVENT_PATH,
182 name.name, 0); 182 &name.name, 0);
183 else 183 else
184 ret = fsnotify(p_inode, mask, dentry->d_inode, FSNOTIFY_EVENT_INODE, 184 ret = fsnotify(p_inode, mask, dentry->d_inode, FSNOTIFY_EVENT_INODE,
185 name.name, 0); 185 &name.name, 0);
186 release_dentry_name_snapshot(&name); 186 release_dentry_name_snapshot(&name);
187 } 187 }
188 188
@@ -195,7 +195,7 @@ EXPORT_SYMBOL_GPL(__fsnotify_parent);
195static int send_to_group(struct inode *to_tell, 195static int send_to_group(struct inode *to_tell,
196 __u32 mask, const void *data, 196 __u32 mask, const void *data,
197 int data_is, u32 cookie, 197 int data_is, u32 cookie,
198 const unsigned char *file_name, 198 const struct qstr *file_name,
199 struct fsnotify_iter_info *iter_info) 199 struct fsnotify_iter_info *iter_info)
200{ 200{
201 struct fsnotify_group *group = NULL; 201 struct fsnotify_group *group = NULL;
@@ -325,7 +325,7 @@ static void fsnotify_iter_next(struct fsnotify_iter_info *iter_info)
325 * notification event in whatever means they feel necessary. 325 * notification event in whatever means they feel necessary.
326 */ 326 */
327int fsnotify(struct inode *to_tell, __u32 mask, const void *data, int data_is, 327int fsnotify(struct inode *to_tell, __u32 mask, const void *data, int data_is,
328 const unsigned char *file_name, u32 cookie) 328 const struct qstr *file_name, u32 cookie)
329{ 329{
330 struct fsnotify_iter_info iter_info = {}; 330 struct fsnotify_iter_info iter_info = {};
331 struct super_block *sb = to_tell->i_sb; 331 struct super_block *sb = to_tell->i_sb;
diff --git a/fs/notify/inotify/inotify.h b/fs/notify/inotify/inotify.h
index 74ae60305189..3f246f7b8a92 100644
--- a/fs/notify/inotify/inotify.h
+++ b/fs/notify/inotify/inotify.h
@@ -27,7 +27,7 @@ extern void inotify_ignored_and_remove_idr(struct fsnotify_mark *fsn_mark,
27extern int inotify_handle_event(struct fsnotify_group *group, 27extern int inotify_handle_event(struct fsnotify_group *group,
28 struct inode *inode, 28 struct inode *inode,
29 u32 mask, const void *data, int data_type, 29 u32 mask, const void *data, int data_type,
30 const unsigned char *file_name, u32 cookie, 30 const struct qstr *file_name, u32 cookie,
31 struct fsnotify_iter_info *iter_info); 31 struct fsnotify_iter_info *iter_info);
32 32
33extern const struct fsnotify_ops inotify_fsnotify_ops; 33extern const struct fsnotify_ops inotify_fsnotify_ops;
diff --git a/fs/notify/inotify/inotify_fsnotify.c b/fs/notify/inotify/inotify_fsnotify.c
index ff30abd6a49b..7e8b131029f8 100644
--- a/fs/notify/inotify/inotify_fsnotify.c
+++ b/fs/notify/inotify/inotify_fsnotify.c
@@ -67,7 +67,7 @@ static int inotify_merge(struct list_head *list,
67int inotify_handle_event(struct fsnotify_group *group, 67int inotify_handle_event(struct fsnotify_group *group,
68 struct inode *inode, 68 struct inode *inode,
69 u32 mask, const void *data, int data_type, 69 u32 mask, const void *data, int data_type,
70 const unsigned char *file_name, u32 cookie, 70 const struct qstr *file_name, u32 cookie,
71 struct fsnotify_iter_info *iter_info) 71 struct fsnotify_iter_info *iter_info)
72{ 72{
73 struct fsnotify_mark *inode_mark = fsnotify_iter_inode_mark(iter_info); 73 struct fsnotify_mark *inode_mark = fsnotify_iter_inode_mark(iter_info);
@@ -89,7 +89,7 @@ int inotify_handle_event(struct fsnotify_group *group,
89 return 0; 89 return 0;
90 } 90 }
91 if (file_name) { 91 if (file_name) {
92 len = strlen(file_name); 92 len = file_name->len;
93 alloc_len += len + 1; 93 alloc_len += len + 1;
94 } 94 }
95 95
@@ -129,7 +129,7 @@ int inotify_handle_event(struct fsnotify_group *group,
129 event->sync_cookie = cookie; 129 event->sync_cookie = cookie;
130 event->name_len = len; 130 event->name_len = len;
131 if (len) 131 if (len)
132 strcpy(event->name, file_name); 132 strcpy(event->name, file_name->name);
133 133
134 ret = fsnotify_add_event(group, fsn_event, inotify_merge); 134 ret = fsnotify_add_event(group, fsn_event, inotify_merge);
135 if (ret) { 135 if (ret) {
diff --git a/fs/nsfs.c b/fs/nsfs.c
index 30d150a4f0c6..e3bf08c5af41 100644
--- a/fs/nsfs.c
+++ b/fs/nsfs.c
@@ -105,17 +105,16 @@ slow:
105void *ns_get_path_cb(struct path *path, ns_get_path_helper_t *ns_get_cb, 105void *ns_get_path_cb(struct path *path, ns_get_path_helper_t *ns_get_cb,
106 void *private_data) 106 void *private_data)
107{ 107{
108 struct ns_common *ns;
109 void *ret; 108 void *ret;
110 109
111again: 110 do {
112 ns = ns_get_cb(private_data); 111 struct ns_common *ns = ns_get_cb(private_data);
113 if (!ns) 112 if (!ns)
114 return ERR_PTR(-ENOENT); 113 return ERR_PTR(-ENOENT);
114
115 ret = __ns_get_path(path, ns);
116 } while (ret == ERR_PTR(-EAGAIN));
115 117
116 ret = __ns_get_path(path, ns);
117 if (IS_ERR(ret) && PTR_ERR(ret) == -EAGAIN)
118 goto again;
119 return ret; 118 return ret;
120} 119}
121 120
@@ -154,7 +153,7 @@ int open_related_ns(struct ns_common *ns,
154 if (fd < 0) 153 if (fd < 0)
155 return fd; 154 return fd;
156 155
157 while (1) { 156 do {
158 struct ns_common *relative; 157 struct ns_common *relative;
159 158
160 relative = get_ns(ns); 159 relative = get_ns(ns);
@@ -164,10 +163,8 @@ int open_related_ns(struct ns_common *ns,
164 } 163 }
165 164
166 err = __ns_get_path(&path, relative); 165 err = __ns_get_path(&path, relative);
167 if (IS_ERR(err) && PTR_ERR(err) == -EAGAIN) 166 } while (err == ERR_PTR(-EAGAIN));
168 continue; 167
169 break;
170 }
171 if (IS_ERR(err)) { 168 if (IS_ERR(err)) {
172 put_unused_fd(fd); 169 put_unused_fd(fd);
173 return PTR_ERR(err); 170 return PTR_ERR(err);
diff --git a/fs/overlayfs/export.c b/fs/overlayfs/export.c
index 54e5d17d7f3e..cc1c9e5606ba 100644
--- a/fs/overlayfs/export.c
+++ b/fs/overlayfs/export.c
@@ -398,7 +398,7 @@ static struct dentry *ovl_lookup_real_one(struct dentry *connected,
398 * pointer because we hold no lock on the real dentry. 398 * pointer because we hold no lock on the real dentry.
399 */ 399 */
400 take_dentry_name_snapshot(&name, real); 400 take_dentry_name_snapshot(&name, real);
401 this = lookup_one_len(name.name, connected, strlen(name.name)); 401 this = lookup_one_len(name.name.name, connected, name.name.len);
402 err = PTR_ERR(this); 402 err = PTR_ERR(this);
403 if (IS_ERR(this)) { 403 if (IS_ERR(this)) {
404 goto fail; 404 goto fail;
diff --git a/fs/sysv/namei.c b/fs/sysv/namei.c
index 4d5d20491ffd..ea2414b385ec 100644
--- a/fs/sysv/namei.c
+++ b/fs/sysv/namei.c
@@ -28,21 +28,6 @@ static int add_nondir(struct dentry *dentry, struct inode *inode)
28 return err; 28 return err;
29} 29}
30 30
31static int sysv_hash(const struct dentry *dentry, struct qstr *qstr)
32{
33 /* Truncate the name in place, avoids having to define a compare
34 function. */
35 if (qstr->len > SYSV_NAMELEN) {
36 qstr->len = SYSV_NAMELEN;
37 qstr->hash = full_name_hash(dentry, qstr->name, qstr->len);
38 }
39 return 0;
40}
41
42const struct dentry_operations sysv_dentry_operations = {
43 .d_hash = sysv_hash,
44};
45
46static struct dentry *sysv_lookup(struct inode * dir, struct dentry * dentry, unsigned int flags) 31static struct dentry *sysv_lookup(struct inode * dir, struct dentry * dentry, unsigned int flags)
47{ 32{
48 struct inode * inode = NULL; 33 struct inode * inode = NULL;
diff --git a/fs/sysv/super.c b/fs/sysv/super.c
index 89765ddfb738..d3b2f54d6449 100644
--- a/fs/sysv/super.c
+++ b/fs/sysv/super.c
@@ -312,7 +312,6 @@ static int complete_read_super(struct super_block *sb, int silent, int size)
312 312
313 flavour_setup[sbi->s_type](sbi, &sb->s_max_links); 313 flavour_setup[sbi->s_type](sbi, &sb->s_max_links);
314 314
315 sbi->s_truncate = 1;
316 sbi->s_ndatazones = sbi->s_nzones - sbi->s_firstdatazone; 315 sbi->s_ndatazones = sbi->s_nzones - sbi->s_firstdatazone;
317 sbi->s_inodes_per_block = bsize >> 6; 316 sbi->s_inodes_per_block = bsize >> 6;
318 sbi->s_inodes_per_block_1 = (bsize >> 6)-1; 317 sbi->s_inodes_per_block_1 = (bsize >> 6)-1;
@@ -334,8 +333,6 @@ static int complete_read_super(struct super_block *sb, int silent, int size)
334 sb->s_op = &sysv_sops; 333 sb->s_op = &sysv_sops;
335 if (sbi->s_forced_ro) 334 if (sbi->s_forced_ro)
336 sb->s_flags |= SB_RDONLY; 335 sb->s_flags |= SB_RDONLY;
337 if (sbi->s_truncate)
338 sb->s_d_op = &sysv_dentry_operations;
339 root_inode = sysv_iget(sb, SYSV_ROOT_INO); 336 root_inode = sysv_iget(sb, SYSV_ROOT_INO);
340 if (IS_ERR(root_inode)) { 337 if (IS_ERR(root_inode)) {
341 printk("SysV FS: get root inode failed\n"); 338 printk("SysV FS: get root inode failed\n");
diff --git a/fs/sysv/sysv.h b/fs/sysv/sysv.h
index e913698779c0..1cff585526b1 100644
--- a/fs/sysv/sysv.h
+++ b/fs/sysv/sysv.h
@@ -23,8 +23,6 @@ struct sysv_sb_info {
23 struct super_block *s_sb; /* VFS superblock */ 23 struct super_block *s_sb; /* VFS superblock */
24 int s_type; /* file system type: FSTYPE_{XENIX|SYSV|COH} */ 24 int s_type; /* file system type: FSTYPE_{XENIX|SYSV|COH} */
25 char s_bytesex; /* bytesex (le/be/pdp) */ 25 char s_bytesex; /* bytesex (le/be/pdp) */
26 char s_truncate; /* if 1: names > SYSV_NAMELEN chars are truncated */
27 /* if 0: they are disallowed (ENAMETOOLONG) */
28 unsigned int s_inodes_per_block; /* number of inodes per block */ 26 unsigned int s_inodes_per_block; /* number of inodes per block */
29 unsigned int s_inodes_per_block_1; /* inodes_per_block - 1 */ 27 unsigned int s_inodes_per_block_1; /* inodes_per_block - 1 */
30 unsigned int s_inodes_per_block_bits; /* log2(inodes_per_block) */ 28 unsigned int s_inodes_per_block_bits; /* log2(inodes_per_block) */
@@ -166,7 +164,6 @@ extern const struct file_operations sysv_file_operations;
166extern const struct file_operations sysv_dir_operations; 164extern const struct file_operations sysv_dir_operations;
167extern const struct address_space_operations sysv_aops; 165extern const struct address_space_operations sysv_aops;
168extern const struct super_operations sysv_sops; 166extern const struct super_operations sysv_sops;
169extern const struct dentry_operations sysv_dentry_operations;
170 167
171 168
172enum { 169enum {
diff --git a/include/linux/dcache.h b/include/linux/dcache.h
index 6e1e8e6602c6..73c3a8f90580 100644
--- a/include/linux/dcache.h
+++ b/include/linux/dcache.h
@@ -235,7 +235,6 @@ extern void d_set_d_op(struct dentry *dentry, const struct dentry_operations *op
235/* allocate/de-allocate */ 235/* allocate/de-allocate */
236extern struct dentry * d_alloc(struct dentry *, const struct qstr *); 236extern struct dentry * d_alloc(struct dentry *, const struct qstr *);
237extern struct dentry * d_alloc_anon(struct super_block *); 237extern struct dentry * d_alloc_anon(struct super_block *);
238extern struct dentry * d_alloc_pseudo(struct super_block *, const struct qstr *);
239extern struct dentry * d_alloc_parallel(struct dentry *, const struct qstr *, 238extern struct dentry * d_alloc_parallel(struct dentry *, const struct qstr *,
240 wait_queue_head_t *); 239 wait_queue_head_t *);
241extern struct dentry * d_splice_alias(struct inode *, struct dentry *); 240extern struct dentry * d_splice_alias(struct inode *, struct dentry *);
@@ -594,7 +593,7 @@ static inline struct inode *d_real_inode(const struct dentry *dentry)
594} 593}
595 594
596struct name_snapshot { 595struct name_snapshot {
597 const unsigned char *name; 596 struct qstr name;
598 unsigned char inline_name[DNAME_INLINE_LEN]; 597 unsigned char inline_name[DNAME_INLINE_LEN];
599}; 598};
600void take_dentry_name_snapshot(struct name_snapshot *, struct dentry *); 599void take_dentry_name_snapshot(struct name_snapshot *, struct dentry *);
diff --git a/include/linux/fsnotify.h b/include/linux/fsnotify.h
index 09587e2860b5..0c0ef3078a22 100644
--- a/include/linux/fsnotify.h
+++ b/include/linux/fsnotify.h
@@ -27,7 +27,7 @@ static inline int fsnotify_dirent(struct inode *dir, struct dentry *dentry,
27 __u32 mask) 27 __u32 mask)
28{ 28{
29 return fsnotify(dir, mask, d_inode(dentry), FSNOTIFY_EVENT_INODE, 29 return fsnotify(dir, mask, d_inode(dentry), FSNOTIFY_EVENT_INODE,
30 dentry->d_name.name, 0); 30 &dentry->d_name, 0);
31} 31}
32 32
33/* Notify this dentry's parent about a child's events. */ 33/* Notify this dentry's parent about a child's events. */
@@ -102,7 +102,7 @@ static inline void fsnotify_link_count(struct inode *inode)
102 * fsnotify_move - file old_name at old_dir was moved to new_name at new_dir 102 * fsnotify_move - file old_name at old_dir was moved to new_name at new_dir
103 */ 103 */
104static inline void fsnotify_move(struct inode *old_dir, struct inode *new_dir, 104static inline void fsnotify_move(struct inode *old_dir, struct inode *new_dir,
105 const unsigned char *old_name, 105 const struct qstr *old_name,
106 int isdir, struct inode *target, 106 int isdir, struct inode *target,
107 struct dentry *moved) 107 struct dentry *moved)
108{ 108{
@@ -111,7 +111,7 @@ static inline void fsnotify_move(struct inode *old_dir, struct inode *new_dir,
111 __u32 old_dir_mask = FS_MOVED_FROM; 111 __u32 old_dir_mask = FS_MOVED_FROM;
112 __u32 new_dir_mask = FS_MOVED_TO; 112 __u32 new_dir_mask = FS_MOVED_TO;
113 __u32 mask = FS_MOVE_SELF; 113 __u32 mask = FS_MOVE_SELF;
114 const unsigned char *new_name = moved->d_name.name; 114 const struct qstr *new_name = &moved->d_name;
115 115
116 if (old_dir == new_dir) 116 if (old_dir == new_dir)
117 old_dir_mask |= FS_DN_RENAME; 117 old_dir_mask |= FS_DN_RENAME;
@@ -178,7 +178,7 @@ static inline void fsnotify_nameremove(struct dentry *dentry, int isdir)
178 take_dentry_name_snapshot(&name, dentry); 178 take_dentry_name_snapshot(&name, dentry);
179 179
180 fsnotify(d_inode(parent), mask, d_inode(dentry), FSNOTIFY_EVENT_INODE, 180 fsnotify(d_inode(parent), mask, d_inode(dentry), FSNOTIFY_EVENT_INODE,
181 name.name, 0); 181 &name.name, 0);
182 182
183 release_dentry_name_snapshot(&name); 183 release_dentry_name_snapshot(&name);
184 dput(parent); 184 dput(parent);
@@ -218,7 +218,7 @@ static inline void fsnotify_link(struct inode *dir, struct inode *inode, struct
218 fsnotify_link_count(inode); 218 fsnotify_link_count(inode);
219 audit_inode_child(dir, new_dentry, AUDIT_TYPE_CHILD_CREATE); 219 audit_inode_child(dir, new_dentry, AUDIT_TYPE_CHILD_CREATE);
220 220
221 fsnotify(dir, FS_CREATE, inode, FSNOTIFY_EVENT_INODE, new_dentry->d_name.name, 0); 221 fsnotify(dir, FS_CREATE, inode, FSNOTIFY_EVENT_INODE, &new_dentry->d_name, 0);
222} 222}
223 223
224/* 224/*
diff --git a/include/linux/fsnotify_backend.h b/include/linux/fsnotify_backend.h
index dfc28fcb4de8..c28f6ed1f59b 100644
--- a/include/linux/fsnotify_backend.h
+++ b/include/linux/fsnotify_backend.h
@@ -117,7 +117,7 @@ struct fsnotify_ops {
117 int (*handle_event)(struct fsnotify_group *group, 117 int (*handle_event)(struct fsnotify_group *group,
118 struct inode *inode, 118 struct inode *inode,
119 u32 mask, const void *data, int data_type, 119 u32 mask, const void *data, int data_type,
120 const unsigned char *file_name, u32 cookie, 120 const struct qstr *file_name, u32 cookie,
121 struct fsnotify_iter_info *iter_info); 121 struct fsnotify_iter_info *iter_info);
122 void (*free_group_priv)(struct fsnotify_group *group); 122 void (*free_group_priv)(struct fsnotify_group *group);
123 void (*freeing_mark)(struct fsnotify_mark *mark, struct fsnotify_group *group); 123 void (*freeing_mark)(struct fsnotify_mark *mark, struct fsnotify_group *group);
@@ -350,7 +350,7 @@ struct fsnotify_mark {
350 350
351/* main fsnotify call to send events */ 351/* main fsnotify call to send events */
352extern int fsnotify(struct inode *to_tell, __u32 mask, const void *data, int data_is, 352extern int fsnotify(struct inode *to_tell, __u32 mask, const void *data, int data_is,
353 const unsigned char *name, u32 cookie); 353 const struct qstr *name, u32 cookie);
354extern int __fsnotify_parent(const struct path *path, struct dentry *dentry, __u32 mask); 354extern int __fsnotify_parent(const struct path *path, struct dentry *dentry, __u32 mask);
355extern void __fsnotify_inode_delete(struct inode *inode); 355extern void __fsnotify_inode_delete(struct inode *inode);
356extern void __fsnotify_vfsmount_delete(struct vfsmount *mnt); 356extern void __fsnotify_vfsmount_delete(struct vfsmount *mnt);
@@ -505,7 +505,7 @@ static inline void fsnotify_init_event(struct fsnotify_event *event,
505#else 505#else
506 506
507static inline int fsnotify(struct inode *to_tell, __u32 mask, const void *data, int data_is, 507static inline int fsnotify(struct inode *to_tell, __u32 mask, const void *data, int data_is,
508 const unsigned char *name, u32 cookie) 508 const struct qstr *name, u32 cookie)
509{ 509{
510 return 0; 510 return 0;
511} 511}
diff --git a/kernel/audit.h b/kernel/audit.h
index 958d5b8fc1b3..2071725a999f 100644
--- a/kernel/audit.h
+++ b/kernel/audit.h
@@ -231,7 +231,7 @@ extern int audit_comparator(const u32 left, const u32 op, const u32 right);
231extern int audit_uid_comparator(kuid_t left, u32 op, kuid_t right); 231extern int audit_uid_comparator(kuid_t left, u32 op, kuid_t right);
232extern int audit_gid_comparator(kgid_t left, u32 op, kgid_t right); 232extern int audit_gid_comparator(kgid_t left, u32 op, kgid_t right);
233extern int parent_len(const char *path); 233extern int parent_len(const char *path);
234extern int audit_compare_dname_path(const char *dname, const char *path, int plen); 234extern int audit_compare_dname_path(const struct qstr *dname, const char *path, int plen);
235extern struct sk_buff *audit_make_reply(int seq, int type, int done, int multi, 235extern struct sk_buff *audit_make_reply(int seq, int type, int done, int multi,
236 const void *payload, int size); 236 const void *payload, int size);
237extern void audit_panic(const char *message); 237extern void audit_panic(const char *message);
diff --git a/kernel/audit_fsnotify.c b/kernel/audit_fsnotify.c
index 37ae95cfb7f4..b5737b826951 100644
--- a/kernel/audit_fsnotify.c
+++ b/kernel/audit_fsnotify.c
@@ -164,7 +164,7 @@ static void audit_autoremove_mark_rule(struct audit_fsnotify_mark *audit_mark)
164static int audit_mark_handle_event(struct fsnotify_group *group, 164static int audit_mark_handle_event(struct fsnotify_group *group,
165 struct inode *to_tell, 165 struct inode *to_tell,
166 u32 mask, const void *data, int data_type, 166 u32 mask, const void *data, int data_type,
167 const unsigned char *dname, u32 cookie, 167 const struct qstr *dname, u32 cookie,
168 struct fsnotify_iter_info *iter_info) 168 struct fsnotify_iter_info *iter_info)
169{ 169{
170 struct fsnotify_mark *inode_mark = fsnotify_iter_inode_mark(iter_info); 170 struct fsnotify_mark *inode_mark = fsnotify_iter_inode_mark(iter_info);
diff --git a/kernel/audit_tree.c b/kernel/audit_tree.c
index abfb112f26aa..e49c912f862d 100644
--- a/kernel/audit_tree.c
+++ b/kernel/audit_tree.c
@@ -1040,7 +1040,7 @@ static void evict_chunk(struct audit_chunk *chunk)
1040static int audit_tree_handle_event(struct fsnotify_group *group, 1040static int audit_tree_handle_event(struct fsnotify_group *group,
1041 struct inode *to_tell, 1041 struct inode *to_tell,
1042 u32 mask, const void *data, int data_type, 1042 u32 mask, const void *data, int data_type,
1043 const unsigned char *file_name, u32 cookie, 1043 const struct qstr *file_name, u32 cookie,
1044 struct fsnotify_iter_info *iter_info) 1044 struct fsnotify_iter_info *iter_info)
1045{ 1045{
1046 return 0; 1046 return 0;
diff --git a/kernel/audit_watch.c b/kernel/audit_watch.c
index e8d1adeb2223..b50c574223fa 100644
--- a/kernel/audit_watch.c
+++ b/kernel/audit_watch.c
@@ -255,7 +255,7 @@ static void audit_watch_log_rule_change(struct audit_krule *r, struct audit_watc
255 255
256/* Update inode info in audit rules based on filesystem event. */ 256/* Update inode info in audit rules based on filesystem event. */
257static void audit_update_watch(struct audit_parent *parent, 257static void audit_update_watch(struct audit_parent *parent,
258 const char *dname, dev_t dev, 258 const struct qstr *dname, dev_t dev,
259 unsigned long ino, unsigned invalidating) 259 unsigned long ino, unsigned invalidating)
260{ 260{
261 struct audit_watch *owatch, *nwatch, *nextw; 261 struct audit_watch *owatch, *nwatch, *nextw;
@@ -482,7 +482,7 @@ void audit_remove_watch_rule(struct audit_krule *krule)
482static int audit_watch_handle_event(struct fsnotify_group *group, 482static int audit_watch_handle_event(struct fsnotify_group *group,
483 struct inode *to_tell, 483 struct inode *to_tell,
484 u32 mask, const void *data, int data_type, 484 u32 mask, const void *data, int data_type,
485 const unsigned char *dname, u32 cookie, 485 const struct qstr *dname, u32 cookie,
486 struct fsnotify_iter_info *iter_info) 486 struct fsnotify_iter_info *iter_info)
487{ 487{
488 struct fsnotify_mark *inode_mark = fsnotify_iter_inode_mark(iter_info); 488 struct fsnotify_mark *inode_mark = fsnotify_iter_inode_mark(iter_info);
diff --git a/kernel/auditfilter.c b/kernel/auditfilter.c
index 1bc6410413e6..303fb04770ce 100644
--- a/kernel/auditfilter.c
+++ b/kernel/auditfilter.c
@@ -1292,12 +1292,12 @@ int parent_len(const char *path)
1292 * @parentlen: length of the parent if known. Passing in AUDIT_NAME_FULL 1292 * @parentlen: length of the parent if known. Passing in AUDIT_NAME_FULL
1293 * here indicates that we must compute this value. 1293 * here indicates that we must compute this value.
1294 */ 1294 */
1295int audit_compare_dname_path(const char *dname, const char *path, int parentlen) 1295int audit_compare_dname_path(const struct qstr *dname, const char *path, int parentlen)
1296{ 1296{
1297 int dlen, pathlen; 1297 int dlen, pathlen;
1298 const char *p; 1298 const char *p;
1299 1299
1300 dlen = strlen(dname); 1300 dlen = dname->len;
1301 pathlen = strlen(path); 1301 pathlen = strlen(path);
1302 if (pathlen < dlen) 1302 if (pathlen < dlen)
1303 return 1; 1303 return 1;
@@ -1308,7 +1308,7 @@ int audit_compare_dname_path(const char *dname, const char *path, int parentlen)
1308 1308
1309 p = path + parentlen; 1309 p = path + parentlen;
1310 1310
1311 return strncmp(p, dname, dlen); 1311 return strncmp(p, dname->name, dlen);
1312} 1312}
1313 1313
1314int audit_filter(int msgtype, unsigned int listtype) 1314int audit_filter(int msgtype, unsigned int listtype)
diff --git a/kernel/auditsc.c b/kernel/auditsc.c
index 5371b59bde36..95ae27edd417 100644
--- a/kernel/auditsc.c
+++ b/kernel/auditsc.c
@@ -2047,7 +2047,7 @@ void __audit_inode_child(struct inode *parent,
2047{ 2047{
2048 struct audit_context *context = audit_context(); 2048 struct audit_context *context = audit_context();
2049 struct inode *inode = d_backing_inode(dentry); 2049 struct inode *inode = d_backing_inode(dentry);
2050 const char *dname = dentry->d_name.name; 2050 const struct qstr *dname = &dentry->d_name;
2051 struct audit_names *n, *found_parent = NULL, *found_child = NULL; 2051 struct audit_names *n, *found_parent = NULL, *found_child = NULL;
2052 struct audit_entry *e; 2052 struct audit_entry *e;
2053 struct list_head *list = &audit_filter_list[AUDIT_FILTER_FS]; 2053 struct list_head *list = &audit_filter_list[AUDIT_FILTER_FS];
@@ -2099,7 +2099,7 @@ void __audit_inode_child(struct inode *parent,
2099 (n->type != type && n->type != AUDIT_TYPE_UNKNOWN)) 2099 (n->type != type && n->type != AUDIT_TYPE_UNKNOWN))
2100 continue; 2100 continue;
2101 2101
2102 if (!strcmp(dname, n->name->name) || 2102 if (!strcmp(dname->name, n->name->name) ||
2103 !audit_compare_dname_path(dname, n->name->name, 2103 !audit_compare_dname_path(dname, n->name->name,
2104 found_parent ? 2104 found_parent ?
2105 found_parent->name_len : 2105 found_parent->name_len :