lkml.org 
[lkml]   [2008]   [May]   [29]   [last100]   RSS Feed
Views: [wrap][no wrap]   [headers]  [forward] 
 
Messages in this thread
    Patch in this message
    /
    Date
    From
    Subject[patch 09/15] security: pass path to inode_setattr
    From: Miklos Szeredi <mszeredi@suse.cz>

    In the inode_setattr() security operation and related functions pass
    the path (vfsmount + dentry) instead of the dentry. AppArmor will need
    this.

    Signed-off-by: Miklos Szeredi <mszeredi@suse.cz>
    ---
    fs/attr.c | 9 +++++----
    fs/fat/file.c | 2 +-
    fs/namei.c | 2 +-
    fs/open.c | 17 +++++++++--------
    include/linux/fs.h | 4 ++--
    include/linux/security.h | 9 ++++-----
    mm/filemap.c | 14 ++++----------
    security/dummy.c | 2 +-
    security/security.c | 6 +++---
    security/selinux/hooks.c | 5 +++--
    security/smack/smack_lsm.c | 6 +++---
    11 files changed, 36 insertions(+), 40 deletions(-)

    Index: linux-2.6/fs/attr.c
    ===================================================================
    --- linux-2.6.orig/fs/attr.c 2008-05-29 12:20:15.000000000 +0200
    +++ linux-2.6/fs/attr.c 2008-05-29 12:20:56.000000000 +0200
    @@ -101,8 +101,9 @@ int inode_setattr(struct inode * inode,
    }
    EXPORT_SYMBOL(inode_setattr);

    -int notify_change(struct dentry * dentry, struct iattr * attr)
    +int notify_change(struct path *path, struct iattr *attr)
    {
    + struct dentry *dentry = path->dentry;
    struct inode *inode = dentry->d_inode;
    mode_t mode = inode->i_mode;
    int error;
    @@ -165,13 +166,13 @@ int notify_change(struct dentry * dentry
    down_write(&dentry->d_inode->i_alloc_sem);

    if (inode->i_op && inode->i_op->setattr) {
    - error = security_inode_setattr(dentry, attr);
    + error = security_inode_setattr(path, attr);
    if (!error)
    error = inode->i_op->setattr(dentry, attr);
    } else {
    error = inode_change_ok(inode, attr);
    if (!error)
    - error = security_inode_setattr(dentry, attr);
    + error = security_inode_setattr(path, attr);
    if (!error) {
    if ((ia_valid & ATTR_UID && attr->ia_uid != inode->i_uid) ||
    (ia_valid & ATTR_GID && attr->ia_gid != inode->i_gid))
    @@ -195,7 +196,7 @@ int path_setattr(struct path *path, stru
    int error = mnt_want_write(path->mnt);

    if (!error) {
    - error = notify_change(path->dentry, attr);
    + error = notify_change(path, attr);
    mnt_drop_write(path->mnt);
    }

    Index: linux-2.6/fs/open.c
    ===================================================================
    --- linux-2.6.orig/fs/open.c 2008-05-29 12:20:49.000000000 +0200
    +++ linux-2.6/fs/open.c 2008-05-29 12:20:56.000000000 +0200
    @@ -197,16 +197,17 @@ out:

    /*
    * do_truncate - truncate (or extend) an inode
    - * @dentry: the dentry to truncate
    + * @path: the path of the file to truncate
    * @length: the new length
    * @time_attrs: file times to be updated (e.g. ATTR_MTIME|ATTR_CTIME)
    * @filp: an open file or NULL (see file_truncate() as well)
    */
    -int do_truncate(struct dentry *dentry, loff_t length, unsigned int time_attrs,
    +int do_truncate(struct path *path, loff_t length, unsigned int time_attrs,
    struct file *filp)
    {
    int err;
    struct iattr newattrs;
    + struct inode *inode = path->dentry->d_inode;

    /* Not pretty: "inode->i_size" shouldn't really be signed. But it is. */
    if (length < 0)
    @@ -220,11 +221,11 @@ int do_truncate(struct dentry *dentry, l
    }

    /* Remove suid/sgid on truncate too */
    - newattrs.ia_valid |= should_remove_suid(dentry);
    + newattrs.ia_valid |= should_remove_suid(path->dentry);

    - mutex_lock(&dentry->d_inode->i_mutex);
    - err = notify_change(dentry, &newattrs);
    - mutex_unlock(&dentry->d_inode->i_mutex);
    + mutex_lock(&inode->i_mutex);
    + err = notify_change(path, &newattrs);
    + mutex_unlock(&inode->i_mutex);
    return err;
    }

    @@ -236,7 +237,7 @@ int do_truncate(struct dentry *dentry, l
    */
    int file_truncate(struct file *filp, loff_t length, unsigned int time_attrs)
    {
    - return do_truncate(filp->f_path.dentry, length, time_attrs, filp);
    + return do_truncate(&filp->f_path, length, time_attrs, filp);
    }

    static long do_sys_truncate(const char __user * path, loff_t length)
    @@ -290,7 +291,7 @@ static long do_sys_truncate(const char _
    error = locks_verify_truncate(inode, NULL, length);
    if (!error) {
    DQUOT_INIT(inode);
    - error = do_truncate(nd.path.dentry, length, 0, NULL);
    + error = do_truncate(&nd.path, length, 0, NULL);
    }

    put_write_and_out:
    Index: linux-2.6/include/linux/fs.h
    ===================================================================
    --- linux-2.6.orig/include/linux/fs.h 2008-05-29 12:20:51.000000000 +0200
    +++ linux-2.6/include/linux/fs.h 2008-05-29 12:20:56.000000000 +0200
    @@ -1628,7 +1628,7 @@ static inline int break_lease(struct ino

    /* fs/open.c */

    -extern int do_truncate(struct dentry *, loff_t start, unsigned int time_attrs,
    +extern int do_truncate(struct path *, loff_t start, unsigned int time_attrs,
    struct file *filp);
    extern int file_truncate(struct file *filp, loff_t start,
    unsigned int time_attrs);
    @@ -1785,7 +1785,7 @@ extern int do_remount_sb(struct super_bl
    #ifdef CONFIG_BLOCK
    extern sector_t bmap(struct inode *, sector_t);
    #endif
    -extern int notify_change(struct dentry *, struct iattr *);
    +extern int notify_change(struct path *, struct iattr *);
    extern int path_setattr(struct path *, struct iattr *);
    extern int generic_permission(struct inode *, int,
    int (*check_acl)(struct inode *, int));
    Index: linux-2.6/include/linux/security.h
    ===================================================================
    --- linux-2.6.orig/include/linux/security.h 2008-05-29 12:20:55.000000000 +0200
    +++ linux-2.6/include/linux/security.h 2008-05-29 12:20:56.000000000 +0200
    @@ -413,7 +413,7 @@ static inline void security_free_mnt_opt
    * call to notify_change is performed from several locations, whenever
    * file attributes change (such as when a file is truncated, chown/chmod
    * operations, transferring disk quotas, etc).
    - * @dentry contains the dentry structure for the file.
    + * @path contains the path to the file.
    * @attr is the iattr structure containing the new file attributes.
    * Return 0 if permission is granted.
    * @inode_getattr:
    @@ -1368,7 +1368,7 @@ struct security_operations {
    int (*inode_readlink) (struct dentry *dentry);
    int (*inode_follow_link) (struct dentry *dentry, struct nameidata *nd);
    int (*inode_permission) (struct inode *inode, int mask);
    - int (*inode_setattr) (struct dentry *dentry, struct iattr *attr);
    + int (*inode_setattr) (struct path *path, struct iattr *attr);
    int (*inode_getattr) (struct path *path);
    void (*inode_delete) (struct inode *inode);
    int (*inode_setxattr) (struct dentry *dentry, const char *name,
    @@ -1640,7 +1640,7 @@ int security_inode_rename(struct path *o
    int security_inode_readlink(struct dentry *dentry);
    int security_inode_follow_link(struct dentry *dentry, struct nameidata *nd);
    int security_inode_permission(struct inode *inode, int mask);
    -int security_inode_setattr(struct dentry *dentry, struct iattr *attr);
    +int security_inode_setattr(struct path *path, struct iattr *attr);
    int security_inode_getattr(struct path *path);
    void security_inode_delete(struct inode *inode);
    int security_inode_setxattr(struct dentry *dentry, const char *name,
    @@ -2035,8 +2035,7 @@ static inline int security_inode_permiss
    return 0;
    }

    -static inline int security_inode_setattr(struct dentry *dentry,
    - struct iattr *attr)
    +static inline int security_inode_setattr(struct path *path, struct iattr *attr)
    {
    return 0;
    }
    Index: linux-2.6/security/dummy.c
    ===================================================================
    --- linux-2.6.orig/security/dummy.c 2008-05-29 12:20:55.000000000 +0200
    +++ linux-2.6/security/dummy.c 2008-05-29 12:20:56.000000000 +0200
    @@ -348,7 +348,7 @@ static int dummy_inode_permission (struc
    return 0;
    }

    -static int dummy_inode_setattr (struct dentry *dentry, struct iattr *iattr)
    +static int dummy_inode_setattr(struct path *path, struct iattr *iattr)
    {
    return 0;
    }
    Index: linux-2.6/security/security.c
    ===================================================================
    --- linux-2.6.orig/security/security.c 2008-05-29 12:20:55.000000000 +0200
    +++ linux-2.6/security/security.c 2008-05-29 12:20:56.000000000 +0200
    @@ -471,11 +471,11 @@ int security_inode_permission(struct ino
    return security_ops->inode_permission(inode, mask);
    }

    -int security_inode_setattr(struct dentry *dentry, struct iattr *attr)
    +int security_inode_setattr(struct path *path, struct iattr *attr)
    {
    - if (unlikely(IS_PRIVATE(dentry->d_inode)))
    + if (unlikely(IS_PRIVATE(path->dentry->d_inode)))
    return 0;
    - return security_ops->inode_setattr(dentry, attr);
    + return security_ops->inode_setattr(path, attr);
    }
    EXPORT_SYMBOL_GPL(security_inode_setattr);

    Index: linux-2.6/security/selinux/hooks.c
    ===================================================================
    --- linux-2.6.orig/security/selinux/hooks.c 2008-05-29 12:20:55.000000000 +0200
    +++ linux-2.6/security/selinux/hooks.c 2008-05-29 12:20:56.000000000 +0200
    @@ -2579,11 +2579,12 @@ static int selinux_inode_permission(stru
    open_file_mask_to_av(inode->i_mode, mask), NULL);
    }

    -static int selinux_inode_setattr(struct dentry *dentry, struct iattr *iattr)
    +static int selinux_inode_setattr(struct path *path, struct iattr *iattr)
    {
    + struct dentry *dentry = path->dentry;
    int rc;

    - rc = secondary_ops->inode_setattr(dentry, iattr);
    + rc = secondary_ops->inode_setattr(path, iattr);
    if (rc)
    return rc;

    Index: linux-2.6/security/smack/smack_lsm.c
    ===================================================================
    --- linux-2.6.orig/security/smack/smack_lsm.c 2008-05-29 12:20:55.000000000 +0200
    +++ linux-2.6/security/smack/smack_lsm.c 2008-05-29 12:20:56.000000000 +0200
    @@ -534,12 +534,12 @@ static int smack_inode_permission(struct

    /**
    * smack_inode_setattr - Smack check for setting attributes
    - * @dentry: the object
    + * @path: the object
    * @iattr: for the force flag
    *
    * Returns 0 if access is permitted, an error code otherwise
    */
    -static int smack_inode_setattr(struct dentry *dentry, struct iattr *iattr)
    +static int smack_inode_setattr(struct path *path, struct iattr *iattr)
    {
    /*
    * Need to allow for clearing the setuid bit.
    @@ -547,7 +547,7 @@ static int smack_inode_setattr(struct de
    if (iattr->ia_valid & ATTR_FORCE)
    return 0;

    - return smk_curacc(smk_of_inode(dentry->d_inode), MAY_WRITE);
    + return smk_curacc(smk_of_inode(path->dentry->d_inode), MAY_WRITE);
    }

    /**
    Index: linux-2.6/fs/namei.c
    ===================================================================
    --- linux-2.6.orig/fs/namei.c 2008-05-29 12:20:56.000000000 +0200
    +++ linux-2.6/fs/namei.c 2008-05-29 12:20:56.000000000 +0200
    @@ -1691,7 +1691,7 @@ int may_open(struct nameidata *nd, int a
    if (!error) {
    DQUOT_INIT(inode);

    - error = do_truncate(dentry, 0,
    + error = do_truncate(&nd->path, 0,
    ATTR_MTIME|ATTR_CTIME|ATTR_OPEN,
    NULL);
    }
    Index: linux-2.6/fs/fat/file.c
    ===================================================================
    --- linux-2.6.orig/fs/fat/file.c 2008-05-29 12:20:15.000000000 +0200
    +++ linux-2.6/fs/fat/file.c 2008-05-29 12:20:56.000000000 +0200
    @@ -99,7 +99,7 @@ int fat_generic_ioctl(struct inode *inod
    * out the RO attribute for checking by the security
    * module, just because it maps to a file mode.
    */
    - err = security_inode_setattr(filp->f_path.dentry, &ia);
    + err = security_inode_setattr(&filp->f_path, &ia);
    if (err)
    goto up;

    Index: linux-2.6/mm/filemap.c
    ===================================================================
    --- linux-2.6.orig/mm/filemap.c 2008-05-29 12:20:51.000000000 +0200
    +++ linux-2.6/mm/filemap.c 2008-05-29 12:20:56.000000000 +0200
    @@ -1660,14 +1660,6 @@ int should_remove_suid(struct dentry *de
    }
    EXPORT_SYMBOL(should_remove_suid);

    -static int __remove_suid(struct dentry *dentry, int kill)
    -{
    - struct iattr newattrs;
    -
    - newattrs.ia_valid = ATTR_FORCE | kill;
    - return notify_change(dentry, &newattrs);
    -}
    -
    int file_remove_suid(struct file *file)
    {
    struct dentry *dentry = file->f_path.dentry;
    @@ -1679,8 +1671,10 @@ int file_remove_suid(struct file *file)
    return killpriv;
    if (killpriv)
    error = security_inode_killpriv(dentry);
    - if (!error && killsuid)
    - error = __remove_suid(dentry, killsuid);
    + if (!error && killsuid) {
    + struct iattr newattrs = {.ia_valid = ATTR_FORCE | killsuid };
    + error = notify_change(&file->f_path, &newattrs);
    + }

    return error;
    }
    --


    \
     
     \ /
      Last update: 2008-05-29 15:57    [W:4.415 / U:0.420 seconds]
    ©2003-2020 Jasper Spaans|hosted at Digital Ocean and TransIP|Read the blog|Advertise on this site