Andy Whitcroft <apw@xxxxxxxxxxxxx> writes: > We need to be able to check inode permissions (but not filesystem implied > permissions) for stackable filesystems. Now that permissions involve > checking with the security LSM, cgroups and basic inode permissions it is > easy to miss a key permission check and introduce a security vunerability. > Expose a new interface for these checks. > > Signed-off-by: Andy Whitcroft <apw@xxxxxxxxxxxxx> > --- > fs/namei.c | 34 +++++++++++++++++++++++++--------- > include/linux/fs.h | 1 + > 2 files changed, 26 insertions(+), 9 deletions(-) > > diff --git a/fs/namei.c b/fs/namei.c > index e2ba628..16c77a4 100644 > --- a/fs/namei.c > +++ b/fs/namei.c > @@ -328,6 +328,30 @@ static inline int do_inode_permission(struct inode *inode, int mask) > } > > /** > + * inode_only_permission - check access rights to a given inode only > + * @inode: inode to check permissions on > + * @mask: right to check for (%MAY_READ, %MAY_WRITE, %MAY_EXEC, ...) > + * > + * Uses to check read/write/execute permissions on an inode directly, we do > + * not check filesystem permissions. > + */ > +int inode_only_permission(struct inode *inode, int mask) > +{ > + int retval; > + IS_IMMUTABLE() is per-inode. So I think only the IS_RDONLY() check needs to be left out. Thanks, Miklos > + retval = do_inode_permission(inode, mask); > + if (retval) > + return retval; > + > + retval = devcgroup_inode_permission(inode, mask); > + if (retval) > + return retval; > + > + return security_inode_permission(inode, mask); > +} > +EXPORT_SYMBOL(inode_only_permission); > + > +/** > * inode_permission - check for access rights to a given inode > * @inode: inode to check permission on > * @mask: right to check for (%MAY_READ, %MAY_WRITE, %MAY_EXEC, ...) > @@ -360,15 +384,7 @@ int inode_permission(struct inode *inode, int mask) > return -EACCES; > } > > - retval = do_inode_permission(inode, mask); > - if (retval) > - return retval; > - > - retval = devcgroup_inode_permission(inode, mask); > - if (retval) > - return retval; > - > - return security_inode_permission(inode, mask); > + return inode_only_permission(inode, mask); > } > > /** > diff --git a/include/linux/fs.h b/include/linux/fs.h > index 871c87f..b06a3b4 100644 > --- a/include/linux/fs.h > +++ b/include/linux/fs.h > @@ -2228,6 +2228,7 @@ extern sector_t bmap(struct inode *, sector_t); > #endif > extern int notify_change(struct dentry *, struct iattr *); > extern int inode_permission(struct inode *, int); > +extern int inode_only_permission(struct inode *, int); > extern int generic_permission(struct inode *, int); > > static inline bool execute_ok(struct inode *inode) -- To unsubscribe from this list: send the line "unsubscribe linux-fsdevel" in the body of a message to majordomo@xxxxxxxxxxxxxxx More majordomo info at http://vger.kernel.org/majordomo-info.html