aboutsummaryrefslogtreecommitdiff
path: root/fs/namei.c
diff options
context:
space:
mode:
Diffstat (limited to 'fs/namei.c')
-rw-r--r--fs/namei.c48
1 files changed, 31 insertions, 17 deletions
diff --git a/fs/namei.c b/fs/namei.c
index f09edf3eeef..caf090c4862 100644
--- a/fs/namei.c
+++ b/fs/namei.c
@@ -315,6 +315,36 @@ 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;
+
+ /*
+ * Nobody gets write access to an immutable file.
+ */
+ if (unlikely(mask & MAY_WRITE) && IS_IMMUTABLE(inode))
+ 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);
+}
+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, ...)
@@ -328,8 +358,6 @@ static inline int do_inode_permission(struct inode *inode, int mask)
*/
int inode_permission(struct inode *inode, int mask)
{
- int retval;
-
if (unlikely(mask & MAY_WRITE)) {
umode_t mode = inode->i_mode;
@@ -339,23 +367,9 @@ int inode_permission(struct inode *inode, int mask)
if (IS_RDONLY(inode) &&
(S_ISREG(mode) || S_ISDIR(mode) || S_ISLNK(mode)))
return -EROFS;
-
- /*
- * Nobody gets write access to an immutable file.
- */
- if (IS_IMMUTABLE(inode))
- 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);
}
/**