Commit 36698206 authored by Linus Torvalds's avatar Linus Torvalds

Merge branch 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/viro/vfs-2.6

* 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/viro/vfs-2.6:
  devcgroup_inode_permission: take "is it a device node" checks to inlined wrapper
  fix comment in generic_permission()
  kill obsolete comment for follow_down()
  proc_sys_permission() is OK in RCU mode
  reiserfs_permission() doesn't need to bail out in RCU mode
  proc_fd_permission() is doesn't need to bail out in RCU mode
  nilfs2_permission() doesn't need to bail out in RCU mode
  logfs doesn't need ->permission() at all
  coda_ioctl_permission() is safe in RCU mode
  cifs_permission() doesn't need to bail out in RCU mode
  bad_inode_permission() is safe from RCU mode
  ubifs: dereferencing an ERR_PTR in ubifs_mount()
parents ef46222e 482e0cd3
...@@ -231,9 +231,6 @@ static int bad_inode_readlink(struct dentry *dentry, char __user *buffer, ...@@ -231,9 +231,6 @@ static int bad_inode_readlink(struct dentry *dentry, char __user *buffer,
static int bad_inode_permission(struct inode *inode, int mask, unsigned int flags) static int bad_inode_permission(struct inode *inode, int mask, unsigned int flags)
{ {
if (flags & IPERM_FLAG_RCU)
return -ECHILD;
return -EIO; return -EIO;
} }
......
...@@ -257,9 +257,6 @@ static int cifs_permission(struct inode *inode, int mask, unsigned int flags) ...@@ -257,9 +257,6 @@ static int cifs_permission(struct inode *inode, int mask, unsigned int flags)
{ {
struct cifs_sb_info *cifs_sb; struct cifs_sb_info *cifs_sb;
if (flags & IPERM_FLAG_RCU)
return -ECHILD;
cifs_sb = CIFS_SB(inode->i_sb); cifs_sb = CIFS_SB(inode->i_sb);
if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_NO_PERM) { if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_NO_PERM) {
......
...@@ -43,8 +43,6 @@ const struct file_operations coda_ioctl_operations = { ...@@ -43,8 +43,6 @@ const struct file_operations coda_ioctl_operations = {
/* the coda pioctl inode ops */ /* the coda pioctl inode ops */
static int coda_ioctl_permission(struct inode *inode, int mask, unsigned int flags) static int coda_ioctl_permission(struct inode *inode, int mask, unsigned int flags)
{ {
if (flags & IPERM_FLAG_RCU)
return -ECHILD;
return (mask & MAY_EXEC) ? -EACCES : 0; return (mask & MAY_EXEC) ? -EACCES : 0;
} }
......
...@@ -555,13 +555,6 @@ static int logfs_symlink(struct inode *dir, struct dentry *dentry, ...@@ -555,13 +555,6 @@ static int logfs_symlink(struct inode *dir, struct dentry *dentry,
return __logfs_create(dir, dentry, inode, target, destlen); return __logfs_create(dir, dentry, inode, target, destlen);
} }
static int logfs_permission(struct inode *inode, int mask, unsigned int flags)
{
if (flags & IPERM_FLAG_RCU)
return -ECHILD;
return generic_permission(inode, mask, flags, NULL);
}
static int logfs_link(struct dentry *old_dentry, struct inode *dir, static int logfs_link(struct dentry *old_dentry, struct inode *dir,
struct dentry *dentry) struct dentry *dentry)
{ {
...@@ -820,7 +813,6 @@ const struct inode_operations logfs_dir_iops = { ...@@ -820,7 +813,6 @@ const struct inode_operations logfs_dir_iops = {
.mknod = logfs_mknod, .mknod = logfs_mknod,
.rename = logfs_rename, .rename = logfs_rename,
.rmdir = logfs_rmdir, .rmdir = logfs_rmdir,
.permission = logfs_permission,
.symlink = logfs_symlink, .symlink = logfs_symlink,
.unlink = logfs_unlink, .unlink = logfs_unlink,
}; };
......
...@@ -238,7 +238,8 @@ int generic_permission(struct inode *inode, int mask, unsigned int flags, ...@@ -238,7 +238,8 @@ int generic_permission(struct inode *inode, int mask, unsigned int flags,
/* /*
* Read/write DACs are always overridable. * Read/write DACs are always overridable.
* Executable DACs are overridable if at least one exec bit is set. * Executable DACs are overridable for all directories and
* for non-directories that have least one exec bit set.
*/ */
if (!(mask & MAY_EXEC) || execute_ok(inode)) if (!(mask & MAY_EXEC) || execute_ok(inode))
if (ns_capable(inode_userns(inode), CAP_DAC_OVERRIDE)) if (ns_capable(inode_userns(inode), CAP_DAC_OVERRIDE))
...@@ -1011,9 +1012,6 @@ static int follow_dotdot_rcu(struct nameidata *nd) ...@@ -1011,9 +1012,6 @@ static int follow_dotdot_rcu(struct nameidata *nd)
* Follow down to the covering mount currently visible to userspace. At each * Follow down to the covering mount currently visible to userspace. At each
* point, the filesystem owning that dentry may be queried as to whether the * point, the filesystem owning that dentry may be queried as to whether the
* caller is permitted to proceed or not. * caller is permitted to proceed or not.
*
* Care must be taken as namespace_sem may be held (indicated by mounting_here
* being true).
*/ */
int follow_down(struct path *path) int follow_down(struct path *path)
{ {
......
...@@ -801,12 +801,7 @@ int nilfs_setattr(struct dentry *dentry, struct iattr *iattr) ...@@ -801,12 +801,7 @@ int nilfs_setattr(struct dentry *dentry, struct iattr *iattr)
int nilfs_permission(struct inode *inode, int mask, unsigned int flags) int nilfs_permission(struct inode *inode, int mask, unsigned int flags)
{ {
struct nilfs_root *root; struct nilfs_root *root = NILFS_I(inode)->i_root;
if (flags & IPERM_FLAG_RCU)
return -ECHILD;
root = NILFS_I(inode)->i_root;
if ((mask & MAY_WRITE) && root && if ((mask & MAY_WRITE) && root &&
root->cno != NILFS_CPTREE_CURRENT_CNO) root->cno != NILFS_CPTREE_CURRENT_CNO)
return -EROFS; /* snapshot is not writable */ return -EROFS; /* snapshot is not writable */
......
...@@ -2169,11 +2169,7 @@ static const struct file_operations proc_fd_operations = { ...@@ -2169,11 +2169,7 @@ static const struct file_operations proc_fd_operations = {
*/ */
static int proc_fd_permission(struct inode *inode, int mask, unsigned int flags) static int proc_fd_permission(struct inode *inode, int mask, unsigned int flags)
{ {
int rv; int rv = generic_permission(inode, mask, flags, NULL);
if (flags & IPERM_FLAG_RCU)
return -ECHILD;
rv = generic_permission(inode, mask, flags, NULL);
if (rv == 0) if (rv == 0)
return 0; return 0;
if (task_pid(current) == proc_pid(inode)) if (task_pid(current) == proc_pid(inode))
......
...@@ -304,9 +304,6 @@ static int proc_sys_permission(struct inode *inode, int mask,unsigned int flags) ...@@ -304,9 +304,6 @@ static int proc_sys_permission(struct inode *inode, int mask,unsigned int flags)
struct ctl_table *table; struct ctl_table *table;
int error; int error;
if (flags & IPERM_FLAG_RCU)
return -ECHILD;
/* Executable files are not allowed under /proc/sys/ */ /* Executable files are not allowed under /proc/sys/ */
if ((mask & MAY_EXEC) && S_ISREG(inode->i_mode)) if ((mask & MAY_EXEC) && S_ISREG(inode->i_mode))
return -EACCES; return -EACCES;
......
...@@ -954,8 +954,6 @@ static int xattr_mount_check(struct super_block *s) ...@@ -954,8 +954,6 @@ static int xattr_mount_check(struct super_block *s)
int reiserfs_permission(struct inode *inode, int mask, unsigned int flags) int reiserfs_permission(struct inode *inode, int mask, unsigned int flags)
{ {
if (flags & IPERM_FLAG_RCU)
return -ECHILD;
/* /*
* We don't do permission checks on the internal objects. * We don't do permission checks on the internal objects.
* Permissions are determined by the "owning" object. * Permissions are determined by the "owning" object.
......
...@@ -2146,6 +2146,7 @@ static struct dentry *ubifs_mount(struct file_system_type *fs_type, int flags, ...@@ -2146,6 +2146,7 @@ static struct dentry *ubifs_mount(struct file_system_type *fs_type, int flags,
if (IS_ERR(sb)) { if (IS_ERR(sb)) {
err = PTR_ERR(sb); err = PTR_ERR(sb);
kfree(c); kfree(c);
goto out_close;
} }
if (sb->s_root) { if (sb->s_root) {
......
...@@ -2,8 +2,16 @@ ...@@ -2,8 +2,16 @@
#include <linux/fs.h> #include <linux/fs.h>
#ifdef CONFIG_CGROUP_DEVICE #ifdef CONFIG_CGROUP_DEVICE
extern int devcgroup_inode_permission(struct inode *inode, int mask); extern int __devcgroup_inode_permission(struct inode *inode, int mask);
extern int devcgroup_inode_mknod(int mode, dev_t dev); extern int devcgroup_inode_mknod(int mode, dev_t dev);
static inline int devcgroup_inode_permission(struct inode *inode, int mask)
{
if (likely(!inode->i_rdev))
return 0;
if (!S_ISBLK(inode->i_mode) && !S_ISCHR(inode->i_mode))
return 0;
return __devcgroup_inode_permission(inode, mask);
}
#else #else
static inline int devcgroup_inode_permission(struct inode *inode, int mask) static inline int devcgroup_inode_permission(struct inode *inode, int mask)
{ return 0; } { return 0; }
......
...@@ -474,17 +474,11 @@ struct cgroup_subsys devices_subsys = { ...@@ -474,17 +474,11 @@ struct cgroup_subsys devices_subsys = {
.subsys_id = devices_subsys_id, .subsys_id = devices_subsys_id,
}; };
int devcgroup_inode_permission(struct inode *inode, int mask) int __devcgroup_inode_permission(struct inode *inode, int mask)
{ {
struct dev_cgroup *dev_cgroup; struct dev_cgroup *dev_cgroup;
struct dev_whitelist_item *wh; struct dev_whitelist_item *wh;
dev_t device = inode->i_rdev;
if (!device)
return 0;
if (!S_ISBLK(inode->i_mode) && !S_ISCHR(inode->i_mode))
return 0;
rcu_read_lock(); rcu_read_lock();
dev_cgroup = task_devcgroup(current); dev_cgroup = task_devcgroup(current);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment