aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--fs/overlayfs/inode.c18
1 files changed, 14 insertions, 4 deletions
diff --git a/fs/overlayfs/inode.c b/fs/overlayfs/inode.c
index a574108f52a8..f84492ff505d 100644
--- a/fs/overlayfs/inode.c
+++ b/fs/overlayfs/inode.c
@@ -113,6 +113,7 @@ int ovl_permission(struct inode *inode, int mask)
bool is_upper;
struct dentry *realdentry = ovl_entry_real(oe, &is_upper);
struct inode *realinode;
+ const struct cred *old_cred;
int err;
if (ovl_is_default_permissions(inode)) {
@@ -166,7 +167,19 @@ int ovl_permission(struct inode *inode, int mask)
return -EROFS;
}
- return __inode_permission(realinode, mask);
+ /*
+ * Check overlay inode with the creds of task and underlying inode
+ * with creds of mounter
+ */
+ err = generic_permission(inode, mask);
+ if (err)
+ return err;
+
+ old_cred = ovl_override_creds(inode->i_sb);
+ err = __inode_permission(realinode, mask);
+ revert_creds(old_cred);
+
+ return err;
}
static const char *ovl_get_link(struct dentry *dentry,
@@ -314,9 +327,6 @@ struct posix_acl *ovl_get_acl(struct inode *inode, int type)
{
struct inode *realinode = ovl_inode_real(inode);
- if (!realinode)
- return ERR_PTR(-ENOENT);
-
if (!IS_POSIXACL(realinode))
return NULL;