Add a simple helper to chmod with a kernel space file name and switch the early init code over to it.
Unified · Split
| @@ -96,6 +96,19 @@ int __init init_chown(const char *filename, uid_t user, gid_t group, int flags) · 95 unmodified lines | |||
| 96 | return error; | 96 | return error; |
| 97 | } | 97 | } |
| 98 | 98 | ||
| 99 | int __init init_chmod(const char *filename, umode_t mode) | ||
| 100 | { | ||
| 101 | struct path path; | ||
| 102 | int error; | ||
| 103 | |||
| 104 | error = kern_path(filename, LOOKUP_FOLLOW, &path); | ||
| 105 | if (error) | ||
| 106 | return error; | ||
| 107 | error = chmod_common(&path, mode); | ||
| 108 | path_put(&path); | ||
| 109 | return error; | ||
| 110 | } | ||
| 111 | |||
| 99 | int __init init_unlink(const char *pathname) | 112 | int __init init_unlink(const char *pathname) |
| 100 | { | 113 | { |
| 101 | return do_unlinkat(AT_FDCWD, getname_kernel(pathname)); | 114 | return do_unlinkat(AT_FDCWD, getname_kernel(pathname)); |
| @@ -131,7 +131,7 @@ extern struct open_how build_open_how(int flags, umode_t mode); · 130 unmodified lines | |||
| 131 | extern int build_open_flags(const struct open_how *how, struct open_flags *op); | 131 | extern int build_open_flags(const struct open_how *how, struct open_flags *op); |
| 132 | 132 | ||
| 133 | long do_sys_ftruncate(unsigned int fd, loff_t length, int small); | 133 | long do_sys_ftruncate(unsigned int fd, loff_t length, int small); |
| 134 | int do_fchmodat(int dfd, const char __user *filename, umode_t mode); | 134 | int chmod_common(const struct path *path, umode_t mode); |
| 135 | int do_fchownat(int dfd, const char __user *filename, uid_t user, gid_t group, | 135 | int do_fchownat(int dfd, const char __user *filename, uid_t user, gid_t group, |
| 136 | int flag); | 136 | int flag); |
| 137 | int chown_common(const struct path *path, uid_t user, gid_t group); | 137 | int chown_common(const struct path *path, uid_t user, gid_t group); |
| @@ -563,7 +563,7 @@ out: · 562 unmodified lines | |||
| 563 | return error; | 563 | return error; |
| 564 | } | 564 | } |
| 565 | 565 | ||
| 566 | static int chmod_common(const struct path *path, umode_t mode) | 566 | int chmod_common(const struct path *path, umode_t mode) |
| 567 | { | 567 | { |
| 568 | struct inode *inode = path->dentry->d_inode; | 568 | struct inode *inode = path->dentry->d_inode; |
| 569 | struct inode *delegated_inode = NULL; | 569 | struct inode *delegated_inode = NULL; |
| @@ -610,7 +610,7 @@ SYSCALL_DEFINE2(fchmod, unsigned int, fd, umode_t, mode) · 40 unmodified lines | |||
| 610 | return err; | 610 | return err; |
| 611 | } | 611 | } |
| 612 | 612 | ||
| 613 | int do_fchmodat(int dfd, const char __user *filename, umode_t mode) | 613 | static int do_fchmodat(int dfd, const char __user *filename, umode_t mode) |
| 614 | { | 614 | { |
| 615 | struct path path; | 615 | struct path path; |
| 616 | int error; | 616 | int error; |
| @@ -6,5 +6,6 @@ int __init init_umount(const char *name, int flags); · 5 unmodified lines | |||
| 6 | int __init init_chdir(const char *filename); | 6 | int __init init_chdir(const char *filename); |
| 7 | int __init init_chroot(const char *filename); | 7 | int __init init_chroot(const char *filename); |
| 8 | int __init init_chown(const char *filename, uid_t user, gid_t group, int flags); | 8 | int __init init_chown(const char *filename, uid_t user, gid_t group, int flags); |
| 9 | int __init init_chmod(const char *filename, umode_t mode); | ||
| 9 | int __init init_unlink(const char *pathname); | 10 | int __init init_unlink(const char *pathname); |
| 10 | int __init init_rmdir(const char *pathname); | 11 | int __init init_rmdir(const char *pathname); |
| @@ -1304,13 +1304,6 @@ static inline long ksys_link(const char __user *oldname, · 1303 unmodified lines | |||
| 1304 | return do_linkat(AT_FDCWD, oldname, AT_FDCWD, newname, 0); | 1304 | return do_linkat(AT_FDCWD, oldname, AT_FDCWD, newname, 0); |
| 1305 | } | 1305 | } |
| 1306 | 1306 | ||
| 1307 | extern int do_fchmodat(int dfd, const char __user *filename, umode_t mode); | ||
| 1308 | |||
| 1309 | static inline int ksys_chmod(const char __user *filename, umode_t mode) | ||
| 1310 | { | ||
| 1311 | return do_fchmodat(AT_FDCWD, filename, mode); | ||
| 1312 | } | ||
| 1313 | |||
| 1314 | long do_faccessat(int dfd, const char __user *filename, int mode, int flags); | 1307 | long do_faccessat(int dfd, const char __user *filename, int mode, int flags); |
| 1315 | 1308 | ||
| 1316 | static inline long ksys_access(const char __user *filename, int mode) | 1309 | static inline long ksys_access(const char __user *filename, int mode) |
| @@ -350,14 +350,14 @@ static int __init do_name(void) · 349 unmodified lines | |||
| 350 | } else if (S_ISDIR(mode)) { | 350 | } else if (S_ISDIR(mode)) { |
| 351 | ksys_mkdir(collected, mode); | 351 | ksys_mkdir(collected, mode); |
| 352 | init_chown(collected, uid, gid, 0); | 352 | init_chown(collected, uid, gid, 0); |
| 353 | ksys_chmod(collected, mode); | 353 | init_chmod(collected, mode); |
| 354 | dir_add(collected, mtime); | 354 | dir_add(collected, mtime); |
| 355 | } else if (S_ISBLK(mode) || S_ISCHR(mode) || | 355 | } else if (S_ISBLK(mode) || S_ISCHR(mode) || |
| 356 | S_ISFIFO(mode) || S_ISSOCK(mode)) { | 356 | S_ISFIFO(mode) || S_ISSOCK(mode)) { |
| 357 | if (maybe_link() == 0) { | 357 | if (maybe_link() == 0) { |
| 358 | ksys_mknod(collected, mode, rdev); | 358 | ksys_mknod(collected, mode, rdev); |
| 359 | init_chown(collected, uid, gid, 0); | 359 | init_chown(collected, uid, gid, 0); |
| 360 | ksys_chmod(collected, mode); | 360 | init_chmod(collected, mode); |
| 361 | do_utime(collected, mtime); | 361 | do_utime(collected, mtime); |
| 362 | } | 362 | } |
| 363 | } | 363 | } |