Message ID | 155466884962.633834.14320700092446721044.stgit@magnolia (mailing list archive) |
---|---|
State | New, archived |
Headers | show |
Series | vfs: make immutable files actually immutable | expand |
Looks ok: Reviewed-by: Allison Henderson <allison.henderson@oracle.com> On 4/7/19 1:27 PM, Darrick J. Wong wrote: > From: Darrick J. Wong <darrick.wong@oracle.com> > > The chattr manpage has this to say about immutable files: > > "A file with the 'i' attribute cannot be modified: it cannot be deleted > or renamed, no link can be created to this file, most of the file's > metadata can not be modified, and the file can not be opened in write > mode." > > However, we don't actually check the immutable flag in the setattr code, > which means that we can update project ids and extent size hints on > supposedly immutable files. Therefore, reject a setattr call on an > immutable file except for the case where we're trying to unset > IMMUTABLE. > > Signed-off-by: Darrick J. Wong <darrick.wong@oracle.com> > --- > fs/xfs/xfs_ioctl.c | 8 ++++++++ > 1 file changed, 8 insertions(+) > > > diff --git a/fs/xfs/xfs_ioctl.c b/fs/xfs/xfs_ioctl.c > index 5a1b96dad901..1215713d7814 100644 > --- a/fs/xfs/xfs_ioctl.c > +++ b/fs/xfs/xfs_ioctl.c > @@ -1061,6 +1061,14 @@ xfs_ioctl_setattr_xflags( > !capable(CAP_LINUX_IMMUTABLE)) > return -EPERM; > > + /* > + * If immutable is set and we are not clearing it, we're not allowed > + * to change anything else in the inode. > + */ > + if ((ip->i_d.di_flags & XFS_DIFLAG_IMMUTABLE) && > + (fa->fsx_xflags & FS_XFLAG_IMMUTABLE)) > + return -EPERM; > + > /* diflags2 only valid for v3 inodes. */ > di_flags2 = xfs_flags2diflags2(ip, fa->fsx_xflags); > if (di_flags2 && ip->i_d.di_version < 3) >
On Sun, Apr 7, 2019 at 11:28 PM Darrick J. Wong <darrick.wong@oracle.com> wrote: > > From: Darrick J. Wong <darrick.wong@oracle.com> > > The chattr manpage has this to say about immutable files: > > "A file with the 'i' attribute cannot be modified: it cannot be deleted > or renamed, no link can be created to this file, most of the file's > metadata can not be modified, and the file can not be opened in write > mode." > > However, we don't actually check the immutable flag in the setattr code, > which means that we can update project ids and extent size hints on > supposedly immutable files. Therefore, reject a setattr call on an > immutable file except for the case where we're trying to unset > IMMUTABLE. > > Signed-off-by: Darrick J. Wong <darrick.wong@oracle.com> Did you miss my comment on v1, or do you not think this use case is going to hurt any application that is not a rootkit? chattr +i foo => OK chattr +i foo => -EPERM Thanks, Amir.
On Mon, Apr 08, 2019 at 09:20:47AM +0300, Amir Goldstein wrote: > On Sun, Apr 7, 2019 at 11:28 PM Darrick J. Wong <darrick.wong@oracle.com> wrote: > > > > From: Darrick J. Wong <darrick.wong@oracle.com> > > > > The chattr manpage has this to say about immutable files: > > > > "A file with the 'i' attribute cannot be modified: it cannot be deleted > > or renamed, no link can be created to this file, most of the file's > > metadata can not be modified, and the file can not be opened in write > > mode." > > > > However, we don't actually check the immutable flag in the setattr code, > > which means that we can update project ids and extent size hints on > > supposedly immutable files. Therefore, reject a setattr call on an > > immutable file except for the case where we're trying to unset > > IMMUTABLE. > > > > Signed-off-by: Darrick J. Wong <darrick.wong@oracle.com> > > Did you miss my comment on v1, or do you not think this use case > is going to hurt any application that is not a rootkit? > > chattr +i foo => OK > chattr +i foo => -EPERM Nah, I plain forgot to update the patch. :( Will send v2 where you're allowed to +i multiple times so long as that's the only thing you're changing. --D > Thanks, > Amir.
diff --git a/fs/xfs/xfs_ioctl.c b/fs/xfs/xfs_ioctl.c index 5a1b96dad901..1215713d7814 100644 --- a/fs/xfs/xfs_ioctl.c +++ b/fs/xfs/xfs_ioctl.c @@ -1061,6 +1061,14 @@ xfs_ioctl_setattr_xflags( !capable(CAP_LINUX_IMMUTABLE)) return -EPERM; + /* + * If immutable is set and we are not clearing it, we're not allowed + * to change anything else in the inode. + */ + if ((ip->i_d.di_flags & XFS_DIFLAG_IMMUTABLE) && + (fa->fsx_xflags & FS_XFLAG_IMMUTABLE)) + return -EPERM; + /* diflags2 only valid for v3 inodes. */ di_flags2 = xfs_flags2diflags2(ip, fa->fsx_xflags); if (di_flags2 && ip->i_d.di_version < 3)