ANDROID: sdcardfs: override credential for ioctl to lower fs
authorJaegeuk Kim <jaegeuk@google.com>
Fri, 7 Jul 2017 02:12:22 +0000 (19:12 -0700)
committerDaniel Rosenberg <drosen@google.com>
Tue, 30 Jan 2018 03:40:11 +0000 (19:40 -0800)
Otherwise, lower_fs->ioctl() fails due to inode_owner_or_capable().

Signed-off-by: Jaegeuk Kim <jaegeuk@google.com>
Bug: 63260873
Change-Id: I623a6c7c5f8a3cbd7ec73ef89e18ddb093c43805

fs/sdcardfs/file.c

index 6076c342dae6406266678a33fc5acda1e7247ac9..5ac0b0bbb0ec1c10092e3b19bb272d24ad6bdd82 100644 (file)
@@ -104,12 +104,19 @@ static long sdcardfs_unlocked_ioctl(struct file *file, unsigned int cmd,
 {
        long err = -ENOTTY;
        struct file *lower_file;
+       const struct cred *saved_cred = NULL;
+       struct dentry *dentry = file->f_path.dentry;
+       struct sdcardfs_sb_info *sbi = SDCARDFS_SB(dentry->d_sb);
 
        lower_file = sdcardfs_lower_file(file);
 
        /* XXX: use vfs_ioctl if/when VFS exports it */
        if (!lower_file || !lower_file->f_op)
                goto out;
+
+       /* save current_cred and override it */
+       OVERRIDE_CRED(sbi, saved_cred, SDCARDFS_I(file_inode(file)));
+
        if (lower_file->f_op->unlocked_ioctl)
                err = lower_file->f_op->unlocked_ioctl(lower_file, cmd, arg);
 
@@ -117,6 +124,7 @@ static long sdcardfs_unlocked_ioctl(struct file *file, unsigned int cmd,
        if (!err)
                sdcardfs_copy_and_fix_attrs(file_inode(file),
                                      file_inode(lower_file));
+       REVERT_CRED(saved_cred);
 out:
        return err;
 }
@@ -127,15 +135,23 @@ static long sdcardfs_compat_ioctl(struct file *file, unsigned int cmd,
 {
        long err = -ENOTTY;
        struct file *lower_file;
+       const struct cred *saved_cred = NULL;
+       struct dentry *dentry = file->f_path.dentry;
+       struct sdcardfs_sb_info *sbi = SDCARDFS_SB(dentry->d_sb);
 
        lower_file = sdcardfs_lower_file(file);
 
        /* XXX: use vfs_ioctl if/when VFS exports it */
        if (!lower_file || !lower_file->f_op)
                goto out;
+
+       /* save current_cred and override it */
+       OVERRIDE_CRED(sbi, saved_cred, SDCARDFS_I(file_inode(file)));
+
        if (lower_file->f_op->compat_ioctl)
                err = lower_file->f_op->compat_ioctl(lower_file, cmd, arg);
 
+       REVERT_CRED(saved_cred);
 out:
        return err;
 }