1 Index: linux-2.6.16.i686/net/unix/af_unix.c
2 ===================================================================
3 --- linux-2.6.16.i686.orig/net/unix/af_unix.c 2006-03-20 13:53:29.000000000 +0800
4 +++ linux-2.6.16.i686/net/unix/af_unix.c 2006-05-30 22:27:40.000000000 +0800
8 if (sunname->sun_path[0]) {
9 + intent_init(&nd.intent, IT_LOOKUP);
10 err = path_lookup(sunname->sun_path, LOOKUP_FOLLOW, &nd);
13 Index: linux-2.6.16.i686/fs/open.c
14 ===================================================================
15 --- linux-2.6.16.i686.orig/fs/open.c 2006-05-30 22:10:06.000000000 +0800
16 +++ linux-2.6.16.i686/fs/open.c 2006-05-30 22:27:40.000000000 +0800
20 int do_truncate(struct dentry *dentry, loff_t length, unsigned int time_attrs,
22 + struct file *filp, int called_from_open)
25 + struct inode_operations *op = dentry->d_inode->i_op;
26 struct iattr newattrs;
28 /* Not pretty: "inode->i_size" shouldn't really be signed. But it is. */
32 mutex_lock(&dentry->d_inode->i_mutex);
33 - err = notify_change(dentry, &newattrs);
34 + if (called_from_open)
35 + newattrs.ia_valid |= ATTR_FROM_OPEN;
36 + if (op->setattr_raw) {
37 + newattrs.ia_valid |= ATTR_RAW;
38 + newattrs.ia_ctime = CURRENT_TIME;
39 + down_write(&dentry->d_inode->i_alloc_sem);
40 + err = op->setattr_raw(dentry->d_inode, &newattrs);
41 + up_write(&dentry->d_inode->i_alloc_sem);
43 + err = notify_change(dentry, &newattrs);
45 mutex_unlock(&dentry->d_inode->i_mutex);
49 error = locks_verify_truncate(inode, NULL, length);
52 - error = do_truncate(nd.dentry, length, 0, NULL);
53 + error = do_truncate(nd.dentry, length, 0, NULL, 0);
55 put_write_access(inode);
59 error = locks_verify_truncate(inode, file, length);
61 - error = do_truncate(dentry, length, 0, file);
62 + error = do_truncate(dentry, length, 0, file, 0);
67 (error = vfs_permission(&nd, MAY_WRITE)) != 0)
70 - mutex_lock(&inode->i_mutex);
71 - error = notify_change(nd.dentry, &newattrs);
72 - mutex_unlock(&inode->i_mutex);
73 + if (inode->i_op->setattr_raw) {
74 + struct inode_operations *op = nd.dentry->d_inode->i_op;
76 + newattrs.ia_valid |= ATTR_RAW;
77 + error = op->setattr_raw(inode, &newattrs);
78 + /* the file system wants to use normal vfs path now */
79 + if (error != -EOPNOTSUPP)
82 + mutex_lock(&inode->i_mutex);
83 + error = notify_change(nd.dentry, &newattrs);
84 + mutex_unlock(&inode->i_mutex);
93 EXPORT_SYMBOL_GPL(sys_chroot);
95 -asmlinkage long sys_fchmod(unsigned int fd, mode_t mode)
97 +int chmod_common(struct dentry *dentry, mode_t mode)
99 - struct inode * inode;
100 - struct dentry * dentry;
101 - struct file * file;
103 - struct iattr newattrs;
109 - dentry = file->f_dentry;
110 - inode = dentry->d_inode;
113 - if (IS_RDONLY(inode))
116 - if (IS_IMMUTABLE(inode) || IS_APPEND(inode))
118 + struct inode * inode = dentry->d_inode;
119 + struct iattr newattrs;
120 + int error = -EROFS;
122 + if (IS_RDONLY(inode))
125 + if (inode->i_op->setattr_raw) {
126 + struct inode_operations *op = dentry->d_inode->i_op;
128 + newattrs.ia_mode = mode;
129 + newattrs.ia_valid = ATTR_MODE | ATTR_CTIME;
130 + newattrs.ia_valid |= ATTR_RAW;
131 + error = op->setattr_raw(inode, &newattrs);
132 + /* the file system wants to use normal vfs path now */
133 + if (error != -EOPNOTSUPP)
138 + if (IS_IMMUTABLE(inode) || IS_APPEND(inode))
141 mutex_lock(&inode->i_mutex);
142 - if (mode == (mode_t) -1)
143 - mode = inode->i_mode;
144 - newattrs.ia_mode = (mode & S_IALLUGO) | (inode->i_mode & ~S_IALLUGO);
145 - newattrs.ia_valid = ATTR_MODE | ATTR_CTIME;
146 - err = notify_change(dentry, &newattrs);
147 + if (mode == (mode_t) -1)
148 + mode = inode->i_mode;
149 + newattrs.ia_mode = (mode & S_IALLUGO) | (inode->i_mode & ~S_IALLUGO);
150 + newattrs.ia_valid = ATTR_MODE | ATTR_CTIME;
151 + error = notify_change(dentry, &newattrs);
152 mutex_unlock(&inode->i_mutex);
159 +asmlinkage long sys_fchmod(unsigned int fd, mode_t mode)
161 + struct file * file;
168 + err = chmod_common(file->f_dentry, mode);
175 asmlinkage long sys_fchmodat(int dfd, const char __user *filename,
179 - struct inode * inode;
181 - struct iattr newattrs;
183 error = __user_walk_fd(dfd, filename, LOOKUP_FOLLOW, &nd);
186 - inode = nd.dentry->d_inode;
189 - if (IS_RDONLY(inode))
193 - if (IS_IMMUTABLE(inode) || IS_APPEND(inode))
196 - mutex_lock(&inode->i_mutex);
197 - if (mode == (mode_t) -1)
198 - mode = inode->i_mode;
199 - newattrs.ia_mode = (mode & S_IALLUGO) | (inode->i_mode & ~S_IALLUGO);
200 - newattrs.ia_valid = ATTR_MODE | ATTR_CTIME;
201 - error = notify_change(nd.dentry, &newattrs);
202 - mutex_unlock(&inode->i_mutex);
206 + error = chmod_common(nd.dentry, mode);
214 asmlinkage long sys_chmod(const char __user *filename, mode_t mode)
216 return sys_fchmodat(AT_FDCWD, filename, mode);
218 if (IS_RDONLY(inode))
221 + if (inode->i_op->setattr_raw) {
222 + struct inode_operations *op = dentry->d_inode->i_op;
224 + newattrs.ia_uid = user;
225 + newattrs.ia_gid = group;
226 + newattrs.ia_valid = ATTR_UID | ATTR_GID | ATTR_CTIME;
227 + newattrs.ia_valid |= ATTR_RAW;
228 + error = op->setattr_raw(inode, &newattrs);
229 + /* the file system wants to use normal vfs path now */
230 + if (error != -EOPNOTSUPP)
233 if (IS_IMMUTABLE(inode) || IS_APPEND(inode))
235 newattrs.ia_valid = ATTR_CTIME;
236 Index: linux-2.6.16.i686/fs/namei.c
237 ===================================================================
238 --- linux-2.6.16.i686.orig/fs/namei.c 2006-05-30 22:24:53.000000000 +0800
239 +++ linux-2.6.16.i686/fs/namei.c 2006-05-30 22:27:51.000000000 +0800
240 @@ -1644,7 +1644,7 @@
244 - error = do_truncate(dentry, 0, ATTR_MTIME|ATTR_CTIME, NULL);
245 + error = do_truncate(dentry, 0, ATTR_MTIME|ATTR_CTIME, NULL, 1);
247 put_write_access(inode);
249 @@ -1912,6 +1912,7 @@
251 struct dentry * dentry;
253 + intent_init(&nd.intent, IT_LOOKUP);
257 @@ -1922,6 +1923,15 @@
258 error = do_path_lookup(dfd, tmp, LOOKUP_PARENT, &nd);
262 + if (nd.dentry->d_inode->i_op->mknod_raw) {
263 + struct inode_operations *op = nd.dentry->d_inode->i_op;
264 + error = op->mknod_raw(&nd, mode, dev);
265 + /* the file system wants to use normal vfs path now */
266 + if (error != -EOPNOTSUPP)
270 dentry = lookup_create(&nd, 0);
271 error = PTR_ERR(dentry);
273 @@ -1948,6 +1958,7 @@
276 mutex_unlock(&nd.dentry->d_inode->i_mutex);
281 @@ -1993,9 +2004,18 @@
282 struct dentry *dentry;
285 + intent_init(&nd.intent, IT_LOOKUP);
286 error = do_path_lookup(dfd, tmp, LOOKUP_PARENT, &nd);
289 + if (nd.dentry->d_inode->i_op->mkdir_raw) {
290 + struct inode_operations *op = nd.dentry->d_inode->i_op;
291 + error = op->mkdir_raw(&nd, mode);
292 + /* the file system wants to use normal vfs path now */
293 + if (error != -EOPNOTSUPP)
297 dentry = lookup_create(&nd, 1);
298 error = PTR_ERR(dentry);
299 if (!IS_ERR(dentry)) {
300 @@ -2005,6 +2025,7 @@
303 mutex_unlock(&nd.dentry->d_inode->i_mutex);
308 @@ -2085,6 +2106,7 @@
310 struct dentry *dentry;
312 + intent_init(&nd.intent, IT_LOOKUP);
314 name = getname(pathname);
316 @@ -2105,6 +2127,14 @@
320 + if (nd.dentry->d_inode->i_op->rmdir_raw) {
321 + struct inode_operations *op = nd.dentry->d_inode->i_op;
323 + error = op->rmdir_raw(&nd);
324 + /* the file system wants to use normal vfs path now */
325 + if (error != -EOPNOTSUPP)
328 mutex_lock(&nd.dentry->d_inode->i_mutex);
329 dentry = lookup_hash(&nd);
330 error = PTR_ERR(dentry);
331 @@ -2168,6 +2198,7 @@
332 struct dentry *dentry;
334 struct inode *inode = NULL;
335 + intent_init(&nd.intent, IT_LOOKUP);
337 name = getname(pathname);
339 @@ -2179,6 +2210,13 @@
341 if (nd.last_type != LAST_NORM)
343 + if (nd.dentry->d_inode->i_op->unlink_raw) {
344 + struct inode_operations *op = nd.dentry->d_inode->i_op;
345 + error = op->unlink_raw(&nd);
346 + /* the file system wants to use normal vfs path now */
347 + if (error != -EOPNOTSUPP)
350 mutex_lock(&nd.dentry->d_inode->i_mutex);
351 dentry = lookup_hash(&nd);
352 error = PTR_ERR(dentry);
353 @@ -2261,9 +2299,17 @@
354 struct dentry *dentry;
357 + intent_init(&nd.intent, IT_LOOKUP);
358 error = do_path_lookup(newdfd, to, LOOKUP_PARENT, &nd);
361 + if (nd.dentry->d_inode->i_op->symlink_raw) {
362 + struct inode_operations *op = nd.dentry->d_inode->i_op;
363 + error = op->symlink_raw(&nd, from);
364 + /* the file system wants to use normal vfs path now */
365 + if (error != -EOPNOTSUPP)
368 dentry = lookup_create(&nd, 0);
369 error = PTR_ERR(dentry);
370 if (!IS_ERR(dentry)) {
371 @@ -2271,6 +2317,7 @@
374 mutex_unlock(&nd.dentry->d_inode->i_mutex);
379 @@ -2358,6 +2405,13 @@
381 if (old_nd.mnt != nd.mnt)
383 + if (nd.dentry->d_inode->i_op->link_raw) {
384 + struct inode_operations *op = nd.dentry->d_inode->i_op;
385 + error = op->link_raw(&old_nd, &nd);
386 + /* the file system wants to use normal vfs path now */
387 + if (error != -EOPNOTSUPP)
390 new_dentry = lookup_create(&nd, 0);
391 error = PTR_ERR(new_dentry);
392 if (!IS_ERR(new_dentry)) {
393 @@ -2534,6 +2588,8 @@
394 struct dentry * old_dentry, *new_dentry;
395 struct dentry * trap;
396 struct nameidata oldnd, newnd;
397 + intent_init(&oldnd.intent, IT_LOOKUP);
398 + intent_init(&newnd.intent, IT_LOOKUP);
400 error = do_path_lookup(olddfd, oldname, LOOKUP_PARENT, &oldnd);
402 @@ -2556,6 +2612,13 @@
403 if (newnd.last_type != LAST_NORM)
406 + if (old_dir->d_inode->i_op->rename_raw) {
407 + error = old_dir->d_inode->i_op->rename_raw(&oldnd, &newnd);
408 + /* the file system wants to use normal vfs path now */
409 + if (error != -EOPNOTSUPP)
413 trap = lock_rename(new_dir, old_dir);
415 old_dentry = lookup_hash(&oldnd);
416 @@ -2587,8 +2650,7 @@
417 if (new_dentry == trap)
420 - error = vfs_rename(old_dir->d_inode, old_dentry,
421 - new_dir->d_inode, new_dentry);
422 + error = vfs_rename(old_dir->d_inode, old_dentry, new_dir->d_inode, new_dentry);
426 Index: linux-2.6.16.i686/fs/exec.c
427 ===================================================================
428 --- linux-2.6.16.i686.orig/fs/exec.c 2006-05-30 21:33:00.000000000 +0800
429 +++ linux-2.6.16.i686/fs/exec.c 2006-05-30 22:27:40.000000000 +0800
430 @@ -1517,7 +1517,7 @@
432 if (!file->f_op->write)
434 - if (do_truncate(file->f_dentry, 0, 0, file) != 0)
435 + if (do_truncate(file->f_dentry, 0, 0, file, 0) != 0)
438 retval = binfmt->core_dump(signr, regs, file);
439 Index: linux-2.6.16.i686/include/linux/fs.h
440 ===================================================================
441 --- linux-2.6.16.i686.orig/include/linux/fs.h 2006-05-30 21:33:00.000000000 +0800
442 +++ linux-2.6.16.i686/include/linux/fs.h 2006-05-30 22:27:40.000000000 +0800
443 @@ -1035,13 +1035,20 @@
444 int (*create) (struct inode *,struct dentry *,int, struct nameidata *);
445 struct dentry * (*lookup) (struct inode *,struct dentry *, struct nameidata *);
446 int (*link) (struct dentry *,struct inode *,struct dentry *);
447 + int (*link_raw) (struct nameidata *,struct nameidata *);
448 int (*unlink) (struct inode *,struct dentry *);
449 + int (*unlink_raw) (struct nameidata *);
450 int (*symlink) (struct inode *,struct dentry *,const char *);
451 + int (*symlink_raw) (struct nameidata *,const char *);
452 int (*mkdir) (struct inode *,struct dentry *,int);
453 + int (*mkdir_raw) (struct nameidata *,int);
454 int (*rmdir) (struct inode *,struct dentry *);
455 + int (*rmdir_raw) (struct nameidata *);
456 int (*mknod) (struct inode *,struct dentry *,int,dev_t);
457 + int (*mknod_raw) (struct nameidata *,int,dev_t);
458 int (*rename) (struct inode *, struct dentry *,
459 struct inode *, struct dentry *);
460 + int (*rename_raw) (struct nameidata *, struct nameidata *);
461 int (*readlink) (struct dentry *, char __user *,int);
462 void * (*follow_link) (struct dentry *, struct nameidata *);
463 void (*put_link) (struct dentry *, struct nameidata *, void *);
464 @@ -1351,7 +1358,7 @@
467 extern int do_truncate(struct dentry *, loff_t start, unsigned int time_attrs,
468 - struct file *filp);
469 + struct file *filp, int called_from_open);
470 extern long do_sys_open(int fdf, const char __user *filename, int flags,
472 extern struct file *filp_open(const char *, int, int);