diff options
author | Miklos Szeredi <mszeredi@redhat.com> | 2018-07-18 15:44:41 +0200 |
---|---|---|
committer | Miklos Szeredi <mszeredi@redhat.com> | 2018-07-18 15:44:41 +0200 |
commit | 5812160eb50925d19c54be979c72d335fee17dbd (patch) | |
tree | f8e335159ecb1193219803c15829bc0591d30523 /fs | |
parent | 4f3572954a9d4cbf992072713af284d990b65d87 (diff) | |
download | linux-stable-5812160eb50925d19c54be979c72d335fee17dbd.tar.gz linux-stable-5812160eb50925d19c54be979c72d335fee17dbd.tar.bz2 linux-stable-5812160eb50925d19c54be979c72d335fee17dbd.zip |
Revert "Revert "ovl: get_write_access() in truncate""
This reverts commit 31c3a7069593b072bd57192b63b62f9a7e994e9a.
Re-add functionality dealing with i_writecount on truncate to overlayfs.
This patch shouldn't have any observable effects, since we just re-assert
the writecout that vfs_truncate() already got for us.
This is in preparation for moving overlay functionality out of the VFS.
Signed-off-by: Miklos Szeredi <mszeredi@redhat.com>
Diffstat (limited to 'fs')
-rw-r--r-- | fs/overlayfs/inode.c | 21 |
1 files changed, 21 insertions, 0 deletions
diff --git a/fs/overlayfs/inode.c b/fs/overlayfs/inode.c index 0fa48d5644e2..3f1e5bd0ba87 100644 --- a/fs/overlayfs/inode.c +++ b/fs/overlayfs/inode.c @@ -39,10 +39,27 @@ int ovl_setattr(struct dentry *dentry, struct iattr *attr) if (err) goto out; + if (attr->ia_valid & ATTR_SIZE) { + struct inode *realinode = d_inode(ovl_dentry_real(dentry)); + + err = -ETXTBSY; + if (atomic_read(&realinode->i_writecount) < 0) + goto out_drop_write; + } + err = ovl_copy_up(dentry); if (!err) { + struct inode *winode = NULL; + upperdentry = ovl_dentry_upper(dentry); + if (attr->ia_valid & ATTR_SIZE) { + winode = d_inode(upperdentry); + err = get_write_access(winode); + if (err) + goto out_drop_write; + } + if (attr->ia_valid & (ATTR_KILL_SUID|ATTR_KILL_SGID)) attr->ia_valid &= ~ATTR_MODE; @@ -53,7 +70,11 @@ int ovl_setattr(struct dentry *dentry, struct iattr *attr) if (!err) ovl_copyattr(upperdentry->d_inode, dentry->d_inode); inode_unlock(upperdentry->d_inode); + + if (winode) + put_write_access(winode); } +out_drop_write: ovl_drop_write(dentry); out: return err; |