overlayfs update for 4.19

This contains two new features:
 
  1) Stack file operations: this allows removal of several hacks from the
     VFS, proper interaction of read-only open files with copy-up,
     possibility to implement fs modifying ioctls properly, and others.
 
  2) Metadata only copy-up: when file is on lower layer and only metadata is
     modified (except size) then only copy up the metadata and continue to
     use the data from the lower file.
 -----BEGIN PGP SIGNATURE-----
 
 iHUEABYIAB0WIQSQHSd0lITzzeNWNm3h3BK/laaZPAUCW3srhAAKCRDh3BK/laaZ
 PC6tAQCP+KklcN+TvNp502f+O/kATahSpgnun4NY1/p4I8JV+AEAzdlkTN3+MiAO
 fn9brN6mBK7h59DO3hqedPLJy2vrgwg=
 =QDXH
 -----END PGP SIGNATURE-----

Merge tag 'ovl-update-4.19' of git://git.kernel.org/pub/scm/linux/kernel/git/mszeredi/vfs

Pull overlayfs updates from Miklos Szeredi:
 "This contains two new features:

   - Stack file operations: this allows removal of several hacks from
     the VFS, proper interaction of read-only open files with copy-up,
     possibility to implement fs modifying ioctls properly, and others.

   - Metadata only copy-up: when file is on lower layer and only
     metadata is modified (except size) then only copy up the metadata
     and continue to use the data from the lower file"

* tag 'ovl-update-4.19' of git://git.kernel.org/pub/scm/linux/kernel/git/mszeredi/vfs: (66 commits)
  ovl: Enable metadata only feature
  ovl: Do not do metacopy only for ioctl modifying file attr
  ovl: Do not do metadata only copy-up for truncate operation
  ovl: add helper to force data copy-up
  ovl: Check redirect on index as well
  ovl: Set redirect on upper inode when it is linked
  ovl: Set redirect on metacopy files upon rename
  ovl: Do not set dentry type ORIGIN for broken hardlinks
  ovl: Add an inode flag OVL_CONST_INO
  ovl: Treat metacopy dentries as type OVL_PATH_MERGE
  ovl: Check redirects for metacopy files
  ovl: Move some dir related ovl_lookup_single() code in else block
  ovl: Do not expose metacopy only dentry from d_real()
  ovl: Open file with data except for the case of fsync
  ovl: Add helper ovl_inode_realdata()
  ovl: Store lower data inode in ovl_inode
  ovl: Fix ovl_getattr() to get number of blocks from lower
  ovl: Add helper ovl_dentry_lowerdata() to get lower data dentry
  ovl: Copy up meta inode data from lowest data inode
  ovl: Modify ovl_lookup() and friends to lookup metacopy dentry
  ...
This commit is contained in:
Linus Torvalds 2018-08-21 18:19:09 -07:00
commit d9a185f8b4
33 changed files with 1619 additions and 595 deletions

View file

@ -1595,50 +1595,17 @@ sector_t bmap(struct inode *inode, sector_t block)
}
EXPORT_SYMBOL(bmap);
/*
* Update times in overlayed inode from underlying real inode
*/
static void update_ovl_inode_times(struct dentry *dentry, struct inode *inode,
bool rcu)
{
struct dentry *upperdentry;
/*
* Nothing to do if in rcu or if non-overlayfs
*/
if (rcu || likely(!(dentry->d_flags & DCACHE_OP_REAL)))
return;
upperdentry = d_real(dentry, NULL, 0, D_REAL_UPPER);
/*
* If file is on lower then we can't update atime, so no worries about
* stale mtime/ctime.
*/
if (upperdentry) {
struct inode *realinode = d_inode(upperdentry);
if ((!timespec64_equal(&inode->i_mtime, &realinode->i_mtime) ||
!timespec64_equal(&inode->i_ctime, &realinode->i_ctime))) {
inode->i_mtime = realinode->i_mtime;
inode->i_ctime = realinode->i_ctime;
}
}
}
/*
* With relative atime, only update atime if the previous atime is
* earlier than either the ctime or mtime or if at least a day has
* passed since the last atime update.
*/
static int relatime_need_update(const struct path *path, struct inode *inode,
struct timespec now, bool rcu)
static int relatime_need_update(struct vfsmount *mnt, struct inode *inode,
struct timespec now)
{
if (!(path->mnt->mnt_flags & MNT_RELATIME))
if (!(mnt->mnt_flags & MNT_RELATIME))
return 1;
update_ovl_inode_times(path->dentry, inode, rcu);
/*
* Is mtime younger than atime? If yes, update atime:
*/
@ -1709,8 +1676,7 @@ static int update_time(struct inode *inode, struct timespec64 *time, int flags)
* This function automatically handles read only file systems and media,
* as well as the "noatime" flag and inode specific "noatime" markers.
*/
bool __atime_needs_update(const struct path *path, struct inode *inode,
bool rcu)
bool atime_needs_update(const struct path *path, struct inode *inode)
{
struct vfsmount *mnt = path->mnt;
struct timespec64 now;
@ -1736,7 +1702,7 @@ bool __atime_needs_update(const struct path *path, struct inode *inode,
now = current_time(inode);
if (!relatime_need_update(path, inode, timespec64_to_timespec(now), rcu))
if (!relatime_need_update(mnt, inode, timespec64_to_timespec(now)))
return false;
if (timespec64_equal(&inode->i_atime, &now))
@ -1751,7 +1717,7 @@ void touch_atime(const struct path *path)
struct inode *inode = d_inode(path->dentry);
struct timespec64 now;
if (!__atime_needs_update(path, inode, false))
if (!atime_needs_update(path, inode))
return;
if (!sb_start_write_trylock(inode->i_sb))