All of lore.kernel.org
 help / color / mirror / Atom feed
* linux-next: manual merge of the y2038 tree with the overlayfs tree
@ 2018-06-15  0:43 Stephen Rothwell
  2018-06-15  2:41 ` Stephen Rothwell
  0 siblings, 1 reply; 3+ messages in thread
From: Stephen Rothwell @ 2018-06-15  0:43 UTC (permalink / raw)
  To: Arnd Bergmann, Miklos Szeredi
  Cc: Linux-Next Mailing List, Linux Kernel Mailing List, Deepa Dinamani

[-- Attachment #1: Type: text/plain, Size: 17736 bytes --]

Hi Arnd,

Today's linux-next merge of the y2038 tree got conflicts in:

  fs/inode.c
  fs/overlayfs/inode.c
  fs/overlayfs/overlayfs.h

between various commits from the overlayfs tree and commits:

  8efd6894ff08 ("fs: add timespec64_truncate()")
  95582b008388 ("vfs: change inode times to use struct timespec64")

from the y2038 tree.

I fixed it up (I copied the resolutions that used to be in the merge of
the overlayfs into the y2038 tree - see below) and can carry the fix as
necessary. This is now fixed as far as linux-next is concerned, but any
non trivial conflicts should be mentioned to your upstream maintainer
when your tree is submitted for merging.  You may also want to consider
cooperating with the maintainer of the conflicting tree to minimise any
particularly complex conflicts.

-- 
Cheers,
Stephen Rothwell

diff --cc fs/inode.c
index 9a6fc2f2d220,9fe1f941be02..55373fcba3a5
--- a/fs/inode.c
+++ b/fs/inode.c
@@@ -1635,10 -1681,11 +1635,10 @@@ static int update_time(struct inode *in
   *	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 timespec now;
+ 	struct timespec64 now;
  
  	if (inode->i_flags & S_NOATIME)
  		return false;
@@@ -1661,10 -1708,10 +1661,10 @@@
  
  	now = current_time(inode);
  
- 	if (!relatime_need_update(mnt, inode, now))
 -	if (!relatime_need_update(path, inode, timespec64_to_timespec(now), rcu))
++	if (!relatime_need_update(mnt, inode, timespec64_to_timespec(now)))
  		return false;
  
- 	if (timespec_equal(&inode->i_atime, &now))
+ 	if (timespec64_equal(&inode->i_atime, &now))
  		return false;
  
  	return true;
@@@ -1674,9 -1721,9 +1674,9 @@@ void touch_atime(const struct path *pat
  {
  	struct vfsmount *mnt = path->mnt;
  	struct inode *inode = d_inode(path->dentry);
- 	struct timespec now;
+ 	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))
diff --cc fs/overlayfs/file.c
index f801e1175a0b,000000000000..c6bce11ac6d3
mode 100644,000000..100644
--- a/fs/overlayfs/file.c
+++ b/fs/overlayfs/file.c
@@@ -1,508 -1,0 +1,508 @@@
 +/*
 + * Copyright (C) 2017 Red Hat, Inc.
 + *
 + * This program is free software; you can redistribute it and/or modify it
 + * under the terms of the GNU General Public License version 2 as published by
 + * the Free Software Foundation.
 + */
 +
 +#include <linux/cred.h>
 +#include <linux/file.h>
 +#include <linux/mount.h>
 +#include <linux/xattr.h>
 +#include <linux/uio.h>
 +#include "overlayfs.h"
 +
 +static char ovl_whatisit(struct inode *inode, struct inode *realinode)
 +{
 +	if (realinode != ovl_inode_upper(inode))
 +		return 'l';
 +	if (ovl_has_upperdata(inode))
 +		return 'u';
 +	else
 +		return 'm';
 +}
 +
 +static struct file *ovl_open_realfile(const struct file *file,
 +				      struct inode *realinode)
 +{
 +	struct inode *inode = file_inode(file);
 +	struct file *realfile;
 +	const struct cred *old_cred;
 +
 +	old_cred = ovl_override_creds(inode->i_sb);
 +	realfile = path_open(&file->f_path, file->f_flags | O_NOATIME,
 +			     realinode, current_cred(), false);
 +	revert_creds(old_cred);
 +
 +	pr_debug("open(%p[%pD2/%c], 0%o) -> (%p, 0%o)\n",
 +		 file, file, ovl_whatisit(inode, realinode), file->f_flags,
 +		 realfile, IS_ERR(realfile) ? 0 : realfile->f_flags);
 +
 +	return realfile;
 +}
 +
 +#define OVL_SETFL_MASK (O_APPEND | O_NONBLOCK | O_NDELAY | O_DIRECT)
 +
 +static int ovl_change_flags(struct file *file, unsigned int flags)
 +{
 +	struct inode *inode = file_inode(file);
 +	int err;
 +
 +	/* No atime modificaton on underlying */
 +	flags |= O_NOATIME;
 +
 +	/* If some flag changed that cannot be changed then something's amiss */
 +	if (WARN_ON((file->f_flags ^ flags) & ~OVL_SETFL_MASK))
 +		return -EIO;
 +
 +	flags &= OVL_SETFL_MASK;
 +
 +	if (((flags ^ file->f_flags) & O_APPEND) && IS_APPEND(inode))
 +		return -EPERM;
 +
 +	if (flags & O_DIRECT) {
 +		if (!file->f_mapping->a_ops ||
 +		    !file->f_mapping->a_ops->direct_IO)
 +			return -EINVAL;
 +	}
 +
 +	if (file->f_op->check_flags) {
 +		err = file->f_op->check_flags(flags);
 +		if (err)
 +			return err;
 +	}
 +
 +	spin_lock(&file->f_lock);
 +	file->f_flags = (file->f_flags & ~OVL_SETFL_MASK) | flags;
 +	spin_unlock(&file->f_lock);
 +
 +	return 0;
 +}
 +
 +static int ovl_real_fdget_meta(const struct file *file, struct fd *real,
 +			       bool allow_meta)
 +{
 +	struct inode *inode = file_inode(file);
 +	struct inode *realinode;
 +
 +	real->flags = 0;
 +	real->file = file->private_data;
 +
 +	if (allow_meta)
 +		realinode = ovl_inode_real(inode);
 +	else
 +		realinode = ovl_inode_realdata(inode);
 +
 +	/* Has it been copied up since we'd opened it? */
 +	if (unlikely(file_inode(real->file) != realinode)) {
 +		real->flags = FDPUT_FPUT;
 +		real->file = ovl_open_realfile(file, realinode);
 +
 +		return PTR_ERR_OR_ZERO(real->file);
 +	}
 +
 +	/* Did the flags change since open? */
 +	if (unlikely((file->f_flags ^ real->file->f_flags) & ~O_NOATIME))
 +		return ovl_change_flags(real->file, file->f_flags);
 +
 +	return 0;
 +}
 +
 +static int ovl_real_fdget(const struct file *file, struct fd *real)
 +{
 +	return ovl_real_fdget_meta(file, real, false);
 +}
 +
 +static int ovl_open(struct inode *inode, struct file *file)
 +{
 +	struct dentry *dentry = file_dentry(file);
 +	struct file *realfile;
 +	int err;
 +
 +	err = ovl_open_maybe_copy_up(dentry, file->f_flags);
 +	if (err)
 +		return err;
 +
 +	/* No longer need these flags, so don't pass them on to underlying fs */
 +	file->f_flags &= ~(O_CREAT | O_EXCL | O_NOCTTY | O_TRUNC);
 +
 +	realfile = ovl_open_realfile(file, ovl_inode_realdata(inode));
 +	if (IS_ERR(realfile))
 +		return PTR_ERR(realfile);
 +
 +	/* For O_DIRECT dentry_open() checks f_mapping->a_ops->direct_IO */
 +	file->f_mapping = realfile->f_mapping;
 +
 +	file->private_data = realfile;
 +
 +	return 0;
 +}
 +
 +static int ovl_release(struct inode *inode, struct file *file)
 +{
 +	fput(file->private_data);
 +
 +	return 0;
 +}
 +
 +static loff_t ovl_llseek(struct file *file, loff_t offset, int whence)
 +{
 +	struct inode *realinode = ovl_inode_real(file_inode(file));
 +
 +	return generic_file_llseek_size(file, offset, whence,
 +					realinode->i_sb->s_maxbytes,
 +					i_size_read(realinode));
 +}
 +
 +static void ovl_file_accessed(struct file *file)
 +{
 +	struct inode *inode, *upperinode;
 +
 +	if (file->f_flags & O_NOATIME)
 +		return;
 +
 +	inode = file_inode(file);
 +	upperinode = ovl_inode_upper(inode);
 +
 +	if (!upperinode)
 +		return;
 +
- 	if ((!timespec_equal(&inode->i_mtime, &upperinode->i_mtime) ||
- 	     !timespec_equal(&inode->i_ctime, &upperinode->i_ctime))) {
++	if ((!timespec64_equal(&inode->i_mtime, &upperinode->i_mtime) ||
++	     !timespec64_equal(&inode->i_ctime, &upperinode->i_ctime))) {
 +		inode->i_mtime = upperinode->i_mtime;
 +		inode->i_ctime = upperinode->i_ctime;
 +	}
 +
 +	touch_atime(&file->f_path);
 +}
 +
 +static rwf_t ovl_iocb_to_rwf(struct kiocb *iocb)
 +{
 +	int ifl = iocb->ki_flags;
 +	rwf_t flags = 0;
 +
 +	if (ifl & IOCB_NOWAIT)
 +		flags |= RWF_NOWAIT;
 +	if (ifl & IOCB_HIPRI)
 +		flags |= RWF_HIPRI;
 +	if (ifl & IOCB_DSYNC)
 +		flags |= RWF_DSYNC;
 +	if (ifl & IOCB_SYNC)
 +		flags |= RWF_SYNC;
 +
 +	return flags;
 +}
 +
 +static ssize_t ovl_read_iter(struct kiocb *iocb, struct iov_iter *iter)
 +{
 +	struct file *file = iocb->ki_filp;
 +	struct fd real;
 +	const struct cred *old_cred;
 +	ssize_t ret;
 +
 +	if (!iov_iter_count(iter))
 +		return 0;
 +
 +	ret = ovl_real_fdget(file, &real);
 +	if (ret)
 +		return ret;
 +
 +	old_cred = ovl_override_creds(file_inode(file)->i_sb);
 +	ret = vfs_iter_read(real.file, iter, &iocb->ki_pos,
 +			    ovl_iocb_to_rwf(iocb));
 +	revert_creds(old_cred);
 +
 +	ovl_file_accessed(file);
 +
 +	fdput(real);
 +
 +	return ret;
 +}
 +
 +static ssize_t ovl_write_iter(struct kiocb *iocb, struct iov_iter *iter)
 +{
 +	struct file *file = iocb->ki_filp;
 +	struct inode *inode = file_inode(file);
 +	struct fd real;
 +	const struct cred *old_cred;
 +	ssize_t ret;
 +
 +	if (!iov_iter_count(iter))
 +		return 0;
 +
 +	inode_lock(inode);
 +	/* Update mode */
 +	ovl_copyattr(ovl_inode_real(inode), inode);
 +	ret = file_remove_privs(file);
 +	if (ret)
 +		goto out_unlock;
 +
 +	ret = ovl_real_fdget(file, &real);
 +	if (ret)
 +		goto out_unlock;
 +
 +	old_cred = ovl_override_creds(file_inode(file)->i_sb);
 +	ret = vfs_iter_write(real.file, iter, &iocb->ki_pos,
 +			     ovl_iocb_to_rwf(iocb));
 +	revert_creds(old_cred);
 +
 +	/* Update size */
 +	ovl_copyattr(ovl_inode_real(inode), inode);
 +
 +	fdput(real);
 +
 +out_unlock:
 +	inode_unlock(inode);
 +
 +	return ret;
 +}
 +
 +static int ovl_fsync(struct file *file, loff_t start, loff_t end, int datasync)
 +{
 +	struct fd real;
 +	const struct cred *old_cred;
 +	int ret;
 +
 +	ret = ovl_real_fdget_meta(file, &real, !datasync);
 +	if (ret)
 +		return ret;
 +
 +	/* Don't sync lower file for fear of receiving EROFS error */
 +	if (file_inode(real.file) == ovl_inode_upper(file_inode(file))) {
 +		old_cred = ovl_override_creds(file_inode(file)->i_sb);
 +		ret = vfs_fsync_range(real.file, start, end, datasync);
 +		revert_creds(old_cred);
 +	}
 +
 +	fdput(real);
 +
 +	return ret;
 +}
 +
 +static int ovl_mmap(struct file *file, struct vm_area_struct *vma)
 +{
 +	struct fd real;
 +	const struct cred *old_cred;
 +	int ret;
 +
 +	ret = ovl_real_fdget(file, &real);
 +	if (ret)
 +		return ret;
 +
 +	/* transfer ref: */
 +	fput(vma->vm_file);
 +	vma->vm_file = get_file(real.file);
 +	fdput(real);
 +
 +	if (!vma->vm_file->f_op->mmap)
 +		return -ENODEV;
 +
 +	old_cred = ovl_override_creds(file_inode(file)->i_sb);
 +	ret = call_mmap(vma->vm_file, vma);
 +	revert_creds(old_cred);
 +
 +	ovl_file_accessed(file);
 +
 +	return ret;
 +}
 +
 +static long ovl_fallocate(struct file *file, int mode, loff_t offset, loff_t len)
 +{
 +	struct inode *inode = file_inode(file);
 +	struct fd real;
 +	const struct cred *old_cred;
 +	int ret;
 +
 +	ret = ovl_real_fdget(file, &real);
 +	if (ret)
 +		return ret;
 +
 +	old_cred = ovl_override_creds(file_inode(file)->i_sb);
 +	ret = vfs_fallocate(real.file, mode, offset, len);
 +	revert_creds(old_cred);
 +
 +	/* Update size */
 +	ovl_copyattr(ovl_inode_real(inode), inode);
 +
 +	fdput(real);
 +
 +	return ret;
 +}
 +
 +static long ovl_real_ioctl(struct file *file, unsigned int cmd,
 +			   unsigned long arg)
 +{
 +	struct fd real;
 +	const struct cred *old_cred;
 +	long ret;
 +
 +	ret = ovl_real_fdget(file, &real);
 +	if (ret)
 +		return ret;
 +
 +	old_cred = ovl_override_creds(file_inode(file)->i_sb);
 +	ret = vfs_ioctl(real.file, cmd, arg);
 +	revert_creds(old_cred);
 +
 +	fdput(real);
 +
 +	return ret;
 +}
 +
 +static long ovl_ioctl(struct file *file, unsigned int cmd, unsigned long arg)
 +{
 +	long ret;
 +	struct inode *inode = file_inode(file);
 +
 +	switch (cmd) {
 +	case FS_IOC_GETFLAGS:
 +		ret = ovl_real_ioctl(file, cmd, arg);
 +		break;
 +
 +	case FS_IOC_SETFLAGS:
 +		if (!inode_owner_or_capable(inode))
 +			return -EACCES;
 +
 +		ret = mnt_want_write_file(file);
 +		if (ret)
 +			return ret;
 +
 +		ret = ovl_copy_up_with_data(file_dentry(file));
 +		if (!ret) {
 +			ret = ovl_real_ioctl(file, cmd, arg);
 +
 +			inode_lock(inode);
 +			ovl_copyflags(ovl_inode_real(inode), inode);
 +			inode_unlock(inode);
 +		}
 +
 +		mnt_drop_write_file(file);
 +		break;
 +
 +	default:
 +		ret = -ENOTTY;
 +	}
 +
 +	return ret;
 +}
 +
 +static long ovl_compat_ioctl(struct file *file, unsigned int cmd,
 +			     unsigned long arg)
 +{
 +	switch (cmd) {
 +	case FS_IOC32_GETFLAGS:
 +		cmd = FS_IOC_GETFLAGS;
 +		break;
 +
 +	case FS_IOC32_SETFLAGS:
 +		cmd = FS_IOC_SETFLAGS;
 +		break;
 +
 +	default:
 +		return -ENOIOCTLCMD;
 +	}
 +
 +	return ovl_ioctl(file, cmd, arg);
 +}
 +
 +enum ovl_copyop {
 +	OVL_COPY,
 +	OVL_CLONE,
 +	OVL_DEDUPE,
 +};
 +
 +static s64 ovl_copyfile(struct file *file_in, loff_t pos_in,
 +			struct file *file_out, loff_t pos_out,
 +			u64 len, unsigned int flags, enum ovl_copyop op)
 +{
 +	struct inode *inode_out = file_inode(file_out);
 +	struct fd real_in, real_out;
 +	const struct cred *old_cred;
 +	s64 ret;
 +
 +	ret = ovl_real_fdget(file_out, &real_out);
 +	if (ret)
 +		return ret;
 +
 +	ret = ovl_real_fdget(file_in, &real_in);
 +	if (ret) {
 +		fdput(real_out);
 +		return ret;
 +	}
 +
 +	old_cred = ovl_override_creds(file_inode(file_out)->i_sb);
 +	switch (op) {
 +	case OVL_COPY:
 +		ret = vfs_copy_file_range(real_in.file, pos_in,
 +					  real_out.file, pos_out, len, flags);
 +		break;
 +
 +	case OVL_CLONE:
 +		ret = vfs_clone_file_range(real_in.file, pos_in,
 +					   real_out.file, pos_out, len);
 +		break;
 +
 +	case OVL_DEDUPE:
 +		ret = vfs_dedupe_file_range_one(real_in.file, pos_in,
 +						real_out.file, pos_out, len);
 +		break;
 +	}
 +	revert_creds(old_cred);
 +
 +	/* Update size */
 +	ovl_copyattr(ovl_inode_real(inode_out), inode_out);
 +
 +	fdput(real_in);
 +	fdput(real_out);
 +
 +	return ret;
 +}
 +
 +static ssize_t ovl_copy_file_range(struct file *file_in, loff_t pos_in,
 +				   struct file *file_out, loff_t pos_out,
 +				   size_t len, unsigned int flags)
 +{
 +	return ovl_copyfile(file_in, pos_in, file_out, pos_out, len, flags,
 +			    OVL_COPY);
 +}
 +
 +static int ovl_clone_file_range(struct file *file_in, loff_t pos_in,
 +				struct file *file_out, loff_t pos_out, u64 len)
 +{
 +	return ovl_copyfile(file_in, pos_in, file_out, pos_out, len, 0,
 +			    OVL_CLONE);
 +}
 +
 +static loff_t ovl_dedupe_file_range(struct file *file_in, loff_t pos_in,
 +				    struct file *file_out, loff_t pos_out,
 +				    loff_t len)
 +{
 +	/*
 +	 * Don't copy up because of a dedupe request, this wouldn't make sense
 +	 * most of the time (data would be duplicated instead of deduplicated).
 +	 */
 +	if (!ovl_inode_upper(file_inode(file_in)) ||
 +	    !ovl_inode_upper(file_inode(file_out)))
 +		return -EPERM;
 +
 +	return ovl_copyfile(file_in, pos_in, file_out, pos_out, len, 0,
 +			    OVL_DEDUPE);
 +}
 +
 +const struct file_operations ovl_file_operations = {
 +	.open		= ovl_open,
 +	.release	= ovl_release,
 +	.llseek		= ovl_llseek,
 +	.read_iter	= ovl_read_iter,
 +	.write_iter	= ovl_write_iter,
 +	.fsync		= ovl_fsync,
 +	.mmap		= ovl_mmap,
 +	.fallocate	= ovl_fallocate,
 +	.unlocked_ioctl	= ovl_ioctl,
 +	.compat_ioctl	= ovl_compat_ioctl,
 +
 +	.copy_file_range	= ovl_copy_file_range,
 +	.clone_file_range	= ovl_clone_file_range,
 +	.dedupe_file_range	= ovl_dedupe_file_range,
 +};
diff --cc fs/overlayfs/inode.c
index e31d64206a01,d7cca60f28e6..e0bb217c01e2
--- a/fs/overlayfs/inode.c
+++ b/fs/overlayfs/inode.c
@@@ -439,7 -384,39 +439,7 @@@ struct posix_acl *ovl_get_acl(struct in
  	return acl;
  }
  
- int ovl_update_time(struct inode *inode, struct timespec *ts, int flags)
 -static bool ovl_open_need_copy_up(struct dentry *dentry, int flags)
 -{
 -	/* Copy up of disconnected dentry does not set upper alias */
 -	if (ovl_dentry_upper(dentry) &&
 -	    (ovl_dentry_has_upper_alias(dentry) ||
 -	     (dentry->d_flags & DCACHE_DISCONNECTED)))
 -		return false;
 -
 -	if (special_file(d_inode(dentry)->i_mode))
 -		return false;
 -
 -	if (!(OPEN_FMODE(flags) & FMODE_WRITE) && !(flags & O_TRUNC))
 -		return false;
 -
 -	return true;
 -}
 -
 -int ovl_open_maybe_copy_up(struct dentry *dentry, unsigned int file_flags)
 -{
 -	int err = 0;
 -
 -	if (ovl_open_need_copy_up(dentry, file_flags)) {
 -		err = ovl_want_write(dentry);
 -		if (!err) {
 -			err = ovl_copy_up_flags(dentry, file_flags);
 -			ovl_drop_write(dentry);
 -		}
 -	}
 -
 -	return err;
 -}
 -
+ int ovl_update_time(struct inode *inode, struct timespec64 *ts, int flags)
  {
  	if (flags & S_ATIME) {
  		struct ovl_fs *ofs = inode->i_sb->s_fs_info;
diff --cc fs/overlayfs/overlayfs.h
index ac9fbc3d08ea,9fe10247f9d4..f61839e1054c
--- a/fs/overlayfs/overlayfs.h
+++ b/fs/overlayfs/overlayfs.h
@@@ -349,18 -330,10 +349,18 @@@ int ovl_xattr_get(struct dentry *dentry
  		  void *value, size_t size);
  ssize_t ovl_listxattr(struct dentry *dentry, char *list, size_t size);
  struct posix_acl *ovl_get_acl(struct inode *inode, int type);
- int ovl_update_time(struct inode *inode, struct timespec *ts, int flags);
 -int ovl_open_maybe_copy_up(struct dentry *dentry, unsigned int file_flags);
+ int ovl_update_time(struct inode *inode, struct timespec64 *ts, int flags);
  bool ovl_is_private_xattr(const char *name);
  
 +struct ovl_inode_params {
 +	struct inode *newinode;
 +	struct dentry *upperdentry;
 +	struct ovl_path *lowerpath;
 +	struct dentry *index;
 +	unsigned int numlower;
 +	char *redirect;
 +	struct dentry *lowerdata;
 +};
  struct inode *ovl_new_inode(struct super_block *sb, umode_t mode, dev_t rdev);
  struct inode *ovl_lookup_inode(struct super_block *sb, struct dentry *real,
  			       bool is_upper);

[-- Attachment #2: OpenPGP digital signature --]
[-- Type: application/pgp-signature, Size: 488 bytes --]

^ permalink raw reply	[flat|nested] 3+ messages in thread

* Re: linux-next: manual merge of the y2038 tree with the overlayfs tree
  2018-06-15  0:43 linux-next: manual merge of the y2038 tree with the overlayfs tree Stephen Rothwell
@ 2018-06-15  2:41 ` Stephen Rothwell
  2018-06-15  7:44   ` Arnd Bergmann
  0 siblings, 1 reply; 3+ messages in thread
From: Stephen Rothwell @ 2018-06-15  2:41 UTC (permalink / raw)
  To: Miklos Szeredi
  Cc: Arnd Bergmann, Linux-Next Mailing List,
	Linux Kernel Mailing List, Deepa Dinamani

[-- Attachment #1: Type: text/plain, Size: 19312 bytes --]

Hi all,

This is now a conflict between the overlayfs tree and Linus' tree.  (I
restarted my merging after I noticed that Linus merged more stuff.)

On Fri, 15 Jun 2018 10:43:24 +1000 Stephen Rothwell <sfr@canb.auug.org.au> wrote:
>
> Today's linux-next merge of the y2038 tree got conflicts in:
> 
>   fs/inode.c
>   fs/overlayfs/inode.c
>   fs/overlayfs/overlayfs.h
> 
> between various commits from the overlayfs tree and commits:
> 
>   8efd6894ff08 ("fs: add timespec64_truncate()")
>   95582b008388 ("vfs: change inode times to use struct timespec64")
> 
> from the y2038 tree.
> 
> I fixed it up (I copied the resolutions that used to be in the merge of
> the overlayfs into the y2038 tree - see below) and can carry the fix as
> necessary. This is now fixed as far as linux-next is concerned, but any
> non trivial conflicts should be mentioned to your upstream maintainer
> when your tree is submitted for merging.  You may also want to consider
> cooperating with the maintainer of the conflicting tree to minimise any
> particularly complex conflicts.
> 
> -- 
> Cheers,
> Stephen Rothwell
> 
> diff --cc fs/inode.c
> index 9a6fc2f2d220,9fe1f941be02..55373fcba3a5
> --- a/fs/inode.c
> +++ b/fs/inode.c
> @@@ -1635,10 -1681,11 +1635,10 @@@ static int update_time(struct inode *in
>    *	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 timespec now;
> + 	struct timespec64 now;
>   
>   	if (inode->i_flags & S_NOATIME)
>   		return false;
> @@@ -1661,10 -1708,10 +1661,10 @@@
>   
>   	now = current_time(inode);
>   
> - 	if (!relatime_need_update(mnt, inode, now))
>  -	if (!relatime_need_update(path, inode, timespec64_to_timespec(now), rcu))
> ++	if (!relatime_need_update(mnt, inode, timespec64_to_timespec(now)))
>   		return false;
>   
> - 	if (timespec_equal(&inode->i_atime, &now))
> + 	if (timespec64_equal(&inode->i_atime, &now))
>   		return false;
>   
>   	return true;
> @@@ -1674,9 -1721,9 +1674,9 @@@ void touch_atime(const struct path *pat
>   {
>   	struct vfsmount *mnt = path->mnt;
>   	struct inode *inode = d_inode(path->dentry);
> - 	struct timespec now;
> + 	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))
> diff --cc fs/overlayfs/file.c
> index f801e1175a0b,000000000000..c6bce11ac6d3
> mode 100644,000000..100644
> --- a/fs/overlayfs/file.c
> +++ b/fs/overlayfs/file.c
> @@@ -1,508 -1,0 +1,508 @@@
>  +/*
>  + * Copyright (C) 2017 Red Hat, Inc.
>  + *
>  + * This program is free software; you can redistribute it and/or modify it
>  + * under the terms of the GNU General Public License version 2 as published by
>  + * the Free Software Foundation.
>  + */
>  +
>  +#include <linux/cred.h>
>  +#include <linux/file.h>
>  +#include <linux/mount.h>
>  +#include <linux/xattr.h>
>  +#include <linux/uio.h>
>  +#include "overlayfs.h"
>  +
>  +static char ovl_whatisit(struct inode *inode, struct inode *realinode)
>  +{
>  +	if (realinode != ovl_inode_upper(inode))
>  +		return 'l';
>  +	if (ovl_has_upperdata(inode))
>  +		return 'u';
>  +	else
>  +		return 'm';
>  +}
>  +
>  +static struct file *ovl_open_realfile(const struct file *file,
>  +				      struct inode *realinode)
>  +{
>  +	struct inode *inode = file_inode(file);
>  +	struct file *realfile;
>  +	const struct cred *old_cred;
>  +
>  +	old_cred = ovl_override_creds(inode->i_sb);
>  +	realfile = path_open(&file->f_path, file->f_flags | O_NOATIME,
>  +			     realinode, current_cred(), false);
>  +	revert_creds(old_cred);
>  +
>  +	pr_debug("open(%p[%pD2/%c], 0%o) -> (%p, 0%o)\n",
>  +		 file, file, ovl_whatisit(inode, realinode), file->f_flags,
>  +		 realfile, IS_ERR(realfile) ? 0 : realfile->f_flags);
>  +
>  +	return realfile;
>  +}
>  +
>  +#define OVL_SETFL_MASK (O_APPEND | O_NONBLOCK | O_NDELAY | O_DIRECT)
>  +
>  +static int ovl_change_flags(struct file *file, unsigned int flags)
>  +{
>  +	struct inode *inode = file_inode(file);
>  +	int err;
>  +
>  +	/* No atime modificaton on underlying */
>  +	flags |= O_NOATIME;
>  +
>  +	/* If some flag changed that cannot be changed then something's amiss */
>  +	if (WARN_ON((file->f_flags ^ flags) & ~OVL_SETFL_MASK))
>  +		return -EIO;
>  +
>  +	flags &= OVL_SETFL_MASK;
>  +
>  +	if (((flags ^ file->f_flags) & O_APPEND) && IS_APPEND(inode))
>  +		return -EPERM;
>  +
>  +	if (flags & O_DIRECT) {
>  +		if (!file->f_mapping->a_ops ||
>  +		    !file->f_mapping->a_ops->direct_IO)
>  +			return -EINVAL;
>  +	}
>  +
>  +	if (file->f_op->check_flags) {
>  +		err = file->f_op->check_flags(flags);
>  +		if (err)
>  +			return err;
>  +	}
>  +
>  +	spin_lock(&file->f_lock);
>  +	file->f_flags = (file->f_flags & ~OVL_SETFL_MASK) | flags;
>  +	spin_unlock(&file->f_lock);
>  +
>  +	return 0;
>  +}
>  +
>  +static int ovl_real_fdget_meta(const struct file *file, struct fd *real,
>  +			       bool allow_meta)
>  +{
>  +	struct inode *inode = file_inode(file);
>  +	struct inode *realinode;
>  +
>  +	real->flags = 0;
>  +	real->file = file->private_data;
>  +
>  +	if (allow_meta)
>  +		realinode = ovl_inode_real(inode);
>  +	else
>  +		realinode = ovl_inode_realdata(inode);
>  +
>  +	/* Has it been copied up since we'd opened it? */
>  +	if (unlikely(file_inode(real->file) != realinode)) {
>  +		real->flags = FDPUT_FPUT;
>  +		real->file = ovl_open_realfile(file, realinode);
>  +
>  +		return PTR_ERR_OR_ZERO(real->file);
>  +	}
>  +
>  +	/* Did the flags change since open? */
>  +	if (unlikely((file->f_flags ^ real->file->f_flags) & ~O_NOATIME))
>  +		return ovl_change_flags(real->file, file->f_flags);
>  +
>  +	return 0;
>  +}
>  +
>  +static int ovl_real_fdget(const struct file *file, struct fd *real)
>  +{
>  +	return ovl_real_fdget_meta(file, real, false);
>  +}
>  +
>  +static int ovl_open(struct inode *inode, struct file *file)
>  +{
>  +	struct dentry *dentry = file_dentry(file);
>  +	struct file *realfile;
>  +	int err;
>  +
>  +	err = ovl_open_maybe_copy_up(dentry, file->f_flags);
>  +	if (err)
>  +		return err;
>  +
>  +	/* No longer need these flags, so don't pass them on to underlying fs */
>  +	file->f_flags &= ~(O_CREAT | O_EXCL | O_NOCTTY | O_TRUNC);
>  +
>  +	realfile = ovl_open_realfile(file, ovl_inode_realdata(inode));
>  +	if (IS_ERR(realfile))
>  +		return PTR_ERR(realfile);
>  +
>  +	/* For O_DIRECT dentry_open() checks f_mapping->a_ops->direct_IO */
>  +	file->f_mapping = realfile->f_mapping;
>  +
>  +	file->private_data = realfile;
>  +
>  +	return 0;
>  +}
>  +
>  +static int ovl_release(struct inode *inode, struct file *file)
>  +{
>  +	fput(file->private_data);
>  +
>  +	return 0;
>  +}
>  +
>  +static loff_t ovl_llseek(struct file *file, loff_t offset, int whence)
>  +{
>  +	struct inode *realinode = ovl_inode_real(file_inode(file));
>  +
>  +	return generic_file_llseek_size(file, offset, whence,
>  +					realinode->i_sb->s_maxbytes,
>  +					i_size_read(realinode));
>  +}
>  +
>  +static void ovl_file_accessed(struct file *file)
>  +{
>  +	struct inode *inode, *upperinode;
>  +
>  +	if (file->f_flags & O_NOATIME)
>  +		return;
>  +
>  +	inode = file_inode(file);
>  +	upperinode = ovl_inode_upper(inode);
>  +
>  +	if (!upperinode)
>  +		return;
>  +
> - 	if ((!timespec_equal(&inode->i_mtime, &upperinode->i_mtime) ||
> - 	     !timespec_equal(&inode->i_ctime, &upperinode->i_ctime))) {
> ++	if ((!timespec64_equal(&inode->i_mtime, &upperinode->i_mtime) ||
> ++	     !timespec64_equal(&inode->i_ctime, &upperinode->i_ctime))) {
>  +		inode->i_mtime = upperinode->i_mtime;
>  +		inode->i_ctime = upperinode->i_ctime;
>  +	}
>  +
>  +	touch_atime(&file->f_path);
>  +}
>  +
>  +static rwf_t ovl_iocb_to_rwf(struct kiocb *iocb)
>  +{
>  +	int ifl = iocb->ki_flags;
>  +	rwf_t flags = 0;
>  +
>  +	if (ifl & IOCB_NOWAIT)
>  +		flags |= RWF_NOWAIT;
>  +	if (ifl & IOCB_HIPRI)
>  +		flags |= RWF_HIPRI;
>  +	if (ifl & IOCB_DSYNC)
>  +		flags |= RWF_DSYNC;
>  +	if (ifl & IOCB_SYNC)
>  +		flags |= RWF_SYNC;
>  +
>  +	return flags;
>  +}
>  +
>  +static ssize_t ovl_read_iter(struct kiocb *iocb, struct iov_iter *iter)
>  +{
>  +	struct file *file = iocb->ki_filp;
>  +	struct fd real;
>  +	const struct cred *old_cred;
>  +	ssize_t ret;
>  +
>  +	if (!iov_iter_count(iter))
>  +		return 0;
>  +
>  +	ret = ovl_real_fdget(file, &real);
>  +	if (ret)
>  +		return ret;
>  +
>  +	old_cred = ovl_override_creds(file_inode(file)->i_sb);
>  +	ret = vfs_iter_read(real.file, iter, &iocb->ki_pos,
>  +			    ovl_iocb_to_rwf(iocb));
>  +	revert_creds(old_cred);
>  +
>  +	ovl_file_accessed(file);
>  +
>  +	fdput(real);
>  +
>  +	return ret;
>  +}
>  +
>  +static ssize_t ovl_write_iter(struct kiocb *iocb, struct iov_iter *iter)
>  +{
>  +	struct file *file = iocb->ki_filp;
>  +	struct inode *inode = file_inode(file);
>  +	struct fd real;
>  +	const struct cred *old_cred;
>  +	ssize_t ret;
>  +
>  +	if (!iov_iter_count(iter))
>  +		return 0;
>  +
>  +	inode_lock(inode);
>  +	/* Update mode */
>  +	ovl_copyattr(ovl_inode_real(inode), inode);
>  +	ret = file_remove_privs(file);
>  +	if (ret)
>  +		goto out_unlock;
>  +
>  +	ret = ovl_real_fdget(file, &real);
>  +	if (ret)
>  +		goto out_unlock;
>  +
>  +	old_cred = ovl_override_creds(file_inode(file)->i_sb);
>  +	ret = vfs_iter_write(real.file, iter, &iocb->ki_pos,
>  +			     ovl_iocb_to_rwf(iocb));
>  +	revert_creds(old_cred);
>  +
>  +	/* Update size */
>  +	ovl_copyattr(ovl_inode_real(inode), inode);
>  +
>  +	fdput(real);
>  +
>  +out_unlock:
>  +	inode_unlock(inode);
>  +
>  +	return ret;
>  +}
>  +
>  +static int ovl_fsync(struct file *file, loff_t start, loff_t end, int datasync)
>  +{
>  +	struct fd real;
>  +	const struct cred *old_cred;
>  +	int ret;
>  +
>  +	ret = ovl_real_fdget_meta(file, &real, !datasync);
>  +	if (ret)
>  +		return ret;
>  +
>  +	/* Don't sync lower file for fear of receiving EROFS error */
>  +	if (file_inode(real.file) == ovl_inode_upper(file_inode(file))) {
>  +		old_cred = ovl_override_creds(file_inode(file)->i_sb);
>  +		ret = vfs_fsync_range(real.file, start, end, datasync);
>  +		revert_creds(old_cred);
>  +	}
>  +
>  +	fdput(real);
>  +
>  +	return ret;
>  +}
>  +
>  +static int ovl_mmap(struct file *file, struct vm_area_struct *vma)
>  +{
>  +	struct fd real;
>  +	const struct cred *old_cred;
>  +	int ret;
>  +
>  +	ret = ovl_real_fdget(file, &real);
>  +	if (ret)
>  +		return ret;
>  +
>  +	/* transfer ref: */
>  +	fput(vma->vm_file);
>  +	vma->vm_file = get_file(real.file);
>  +	fdput(real);
>  +
>  +	if (!vma->vm_file->f_op->mmap)
>  +		return -ENODEV;
>  +
>  +	old_cred = ovl_override_creds(file_inode(file)->i_sb);
>  +	ret = call_mmap(vma->vm_file, vma);
>  +	revert_creds(old_cred);
>  +
>  +	ovl_file_accessed(file);
>  +
>  +	return ret;
>  +}
>  +
>  +static long ovl_fallocate(struct file *file, int mode, loff_t offset, loff_t len)
>  +{
>  +	struct inode *inode = file_inode(file);
>  +	struct fd real;
>  +	const struct cred *old_cred;
>  +	int ret;
>  +
>  +	ret = ovl_real_fdget(file, &real);
>  +	if (ret)
>  +		return ret;
>  +
>  +	old_cred = ovl_override_creds(file_inode(file)->i_sb);
>  +	ret = vfs_fallocate(real.file, mode, offset, len);
>  +	revert_creds(old_cred);
>  +
>  +	/* Update size */
>  +	ovl_copyattr(ovl_inode_real(inode), inode);
>  +
>  +	fdput(real);
>  +
>  +	return ret;
>  +}
>  +
>  +static long ovl_real_ioctl(struct file *file, unsigned int cmd,
>  +			   unsigned long arg)
>  +{
>  +	struct fd real;
>  +	const struct cred *old_cred;
>  +	long ret;
>  +
>  +	ret = ovl_real_fdget(file, &real);
>  +	if (ret)
>  +		return ret;
>  +
>  +	old_cred = ovl_override_creds(file_inode(file)->i_sb);
>  +	ret = vfs_ioctl(real.file, cmd, arg);
>  +	revert_creds(old_cred);
>  +
>  +	fdput(real);
>  +
>  +	return ret;
>  +}
>  +
>  +static long ovl_ioctl(struct file *file, unsigned int cmd, unsigned long arg)
>  +{
>  +	long ret;
>  +	struct inode *inode = file_inode(file);
>  +
>  +	switch (cmd) {
>  +	case FS_IOC_GETFLAGS:
>  +		ret = ovl_real_ioctl(file, cmd, arg);
>  +		break;
>  +
>  +	case FS_IOC_SETFLAGS:
>  +		if (!inode_owner_or_capable(inode))
>  +			return -EACCES;
>  +
>  +		ret = mnt_want_write_file(file);
>  +		if (ret)
>  +			return ret;
>  +
>  +		ret = ovl_copy_up_with_data(file_dentry(file));
>  +		if (!ret) {
>  +			ret = ovl_real_ioctl(file, cmd, arg);
>  +
>  +			inode_lock(inode);
>  +			ovl_copyflags(ovl_inode_real(inode), inode);
>  +			inode_unlock(inode);
>  +		}
>  +
>  +		mnt_drop_write_file(file);
>  +		break;
>  +
>  +	default:
>  +		ret = -ENOTTY;
>  +	}
>  +
>  +	return ret;
>  +}
>  +
>  +static long ovl_compat_ioctl(struct file *file, unsigned int cmd,
>  +			     unsigned long arg)
>  +{
>  +	switch (cmd) {
>  +	case FS_IOC32_GETFLAGS:
>  +		cmd = FS_IOC_GETFLAGS;
>  +		break;
>  +
>  +	case FS_IOC32_SETFLAGS:
>  +		cmd = FS_IOC_SETFLAGS;
>  +		break;
>  +
>  +	default:
>  +		return -ENOIOCTLCMD;
>  +	}
>  +
>  +	return ovl_ioctl(file, cmd, arg);
>  +}
>  +
>  +enum ovl_copyop {
>  +	OVL_COPY,
>  +	OVL_CLONE,
>  +	OVL_DEDUPE,
>  +};
>  +
>  +static s64 ovl_copyfile(struct file *file_in, loff_t pos_in,
>  +			struct file *file_out, loff_t pos_out,
>  +			u64 len, unsigned int flags, enum ovl_copyop op)
>  +{
>  +	struct inode *inode_out = file_inode(file_out);
>  +	struct fd real_in, real_out;
>  +	const struct cred *old_cred;
>  +	s64 ret;
>  +
>  +	ret = ovl_real_fdget(file_out, &real_out);
>  +	if (ret)
>  +		return ret;
>  +
>  +	ret = ovl_real_fdget(file_in, &real_in);
>  +	if (ret) {
>  +		fdput(real_out);
>  +		return ret;
>  +	}
>  +
>  +	old_cred = ovl_override_creds(file_inode(file_out)->i_sb);
>  +	switch (op) {
>  +	case OVL_COPY:
>  +		ret = vfs_copy_file_range(real_in.file, pos_in,
>  +					  real_out.file, pos_out, len, flags);
>  +		break;
>  +
>  +	case OVL_CLONE:
>  +		ret = vfs_clone_file_range(real_in.file, pos_in,
>  +					   real_out.file, pos_out, len);
>  +		break;
>  +
>  +	case OVL_DEDUPE:
>  +		ret = vfs_dedupe_file_range_one(real_in.file, pos_in,
>  +						real_out.file, pos_out, len);
>  +		break;
>  +	}
>  +	revert_creds(old_cred);
>  +
>  +	/* Update size */
>  +	ovl_copyattr(ovl_inode_real(inode_out), inode_out);
>  +
>  +	fdput(real_in);
>  +	fdput(real_out);
>  +
>  +	return ret;
>  +}
>  +
>  +static ssize_t ovl_copy_file_range(struct file *file_in, loff_t pos_in,
>  +				   struct file *file_out, loff_t pos_out,
>  +				   size_t len, unsigned int flags)
>  +{
>  +	return ovl_copyfile(file_in, pos_in, file_out, pos_out, len, flags,
>  +			    OVL_COPY);
>  +}
>  +
>  +static int ovl_clone_file_range(struct file *file_in, loff_t pos_in,
>  +				struct file *file_out, loff_t pos_out, u64 len)
>  +{
>  +	return ovl_copyfile(file_in, pos_in, file_out, pos_out, len, 0,
>  +			    OVL_CLONE);
>  +}
>  +
>  +static loff_t ovl_dedupe_file_range(struct file *file_in, loff_t pos_in,
>  +				    struct file *file_out, loff_t pos_out,
>  +				    loff_t len)
>  +{
>  +	/*
>  +	 * Don't copy up because of a dedupe request, this wouldn't make sense
>  +	 * most of the time (data would be duplicated instead of deduplicated).
>  +	 */
>  +	if (!ovl_inode_upper(file_inode(file_in)) ||
>  +	    !ovl_inode_upper(file_inode(file_out)))
>  +		return -EPERM;
>  +
>  +	return ovl_copyfile(file_in, pos_in, file_out, pos_out, len, 0,
>  +			    OVL_DEDUPE);
>  +}
>  +
>  +const struct file_operations ovl_file_operations = {
>  +	.open		= ovl_open,
>  +	.release	= ovl_release,
>  +	.llseek		= ovl_llseek,
>  +	.read_iter	= ovl_read_iter,
>  +	.write_iter	= ovl_write_iter,
>  +	.fsync		= ovl_fsync,
>  +	.mmap		= ovl_mmap,
>  +	.fallocate	= ovl_fallocate,
>  +	.unlocked_ioctl	= ovl_ioctl,
>  +	.compat_ioctl	= ovl_compat_ioctl,
>  +
>  +	.copy_file_range	= ovl_copy_file_range,
>  +	.clone_file_range	= ovl_clone_file_range,
>  +	.dedupe_file_range	= ovl_dedupe_file_range,
>  +};
> diff --cc fs/overlayfs/inode.c
> index e31d64206a01,d7cca60f28e6..e0bb217c01e2
> --- a/fs/overlayfs/inode.c
> +++ b/fs/overlayfs/inode.c
> @@@ -439,7 -384,39 +439,7 @@@ struct posix_acl *ovl_get_acl(struct in
>   	return acl;
>   }
>   
> - int ovl_update_time(struct inode *inode, struct timespec *ts, int flags)
>  -static bool ovl_open_need_copy_up(struct dentry *dentry, int flags)
>  -{
>  -	/* Copy up of disconnected dentry does not set upper alias */
>  -	if (ovl_dentry_upper(dentry) &&
>  -	    (ovl_dentry_has_upper_alias(dentry) ||
>  -	     (dentry->d_flags & DCACHE_DISCONNECTED)))
>  -		return false;
>  -
>  -	if (special_file(d_inode(dentry)->i_mode))
>  -		return false;
>  -
>  -	if (!(OPEN_FMODE(flags) & FMODE_WRITE) && !(flags & O_TRUNC))
>  -		return false;
>  -
>  -	return true;
>  -}
>  -
>  -int ovl_open_maybe_copy_up(struct dentry *dentry, unsigned int file_flags)
>  -{
>  -	int err = 0;
>  -
>  -	if (ovl_open_need_copy_up(dentry, file_flags)) {
>  -		err = ovl_want_write(dentry);
>  -		if (!err) {
>  -			err = ovl_copy_up_flags(dentry, file_flags);
>  -			ovl_drop_write(dentry);
>  -		}
>  -	}
>  -
>  -	return err;
>  -}
>  -
> + int ovl_update_time(struct inode *inode, struct timespec64 *ts, int flags)
>   {
>   	if (flags & S_ATIME) {
>   		struct ovl_fs *ofs = inode->i_sb->s_fs_info;
> diff --cc fs/overlayfs/overlayfs.h
> index ac9fbc3d08ea,9fe10247f9d4..f61839e1054c
> --- a/fs/overlayfs/overlayfs.h
> +++ b/fs/overlayfs/overlayfs.h
> @@@ -349,18 -330,10 +349,18 @@@ int ovl_xattr_get(struct dentry *dentry
>   		  void *value, size_t size);
>   ssize_t ovl_listxattr(struct dentry *dentry, char *list, size_t size);
>   struct posix_acl *ovl_get_acl(struct inode *inode, int type);
> - int ovl_update_time(struct inode *inode, struct timespec *ts, int flags);
>  -int ovl_open_maybe_copy_up(struct dentry *dentry, unsigned int file_flags);
> + int ovl_update_time(struct inode *inode, struct timespec64 *ts, int flags);
>   bool ovl_is_private_xattr(const char *name);
>   
>  +struct ovl_inode_params {
>  +	struct inode *newinode;
>  +	struct dentry *upperdentry;
>  +	struct ovl_path *lowerpath;
>  +	struct dentry *index;
>  +	unsigned int numlower;
>  +	char *redirect;
>  +	struct dentry *lowerdata;
>  +};
>   struct inode *ovl_new_inode(struct super_block *sb, umode_t mode, dev_t rdev);
>   struct inode *ovl_lookup_inode(struct super_block *sb, struct dentry *real,
>   			       bool is_upper);



-- 
Cheers,
Stephen Rothwell

[-- Attachment #2: OpenPGP digital signature --]
[-- Type: application/pgp-signature, Size: 488 bytes --]

^ permalink raw reply	[flat|nested] 3+ messages in thread

* Re: linux-next: manual merge of the y2038 tree with the overlayfs tree
  2018-06-15  2:41 ` Stephen Rothwell
@ 2018-06-15  7:44   ` Arnd Bergmann
  0 siblings, 0 replies; 3+ messages in thread
From: Arnd Bergmann @ 2018-06-15  7:44 UTC (permalink / raw)
  To: Stephen Rothwell
  Cc: Miklos Szeredi, Linux-Next Mailing List,
	Linux Kernel Mailing List, Deepa Dinamani

On Fri, Jun 15, 2018 at 4:41 AM, Stephen Rothwell <sfr@canb.auug.org.au> wrote:
> Hi all,
>
> This is now a conflict between the overlayfs tree and Linus' tree.  (I
> restarted my merging after I noticed that Linus merged more stuff.)

Right, I had mentioned this in my pull request message to Linus. Until
yesterday, I had the conflict resolution against the overlayfs and NFS
trees in my y2038 tree and was waiting for both to get merged first
so I could send the pull request. NFS got merged earlier this week,
and when I looked at the mail thread about overlayfs, I concluded that
it wouldn't make it: the changes in the overlayfs tree in linux-next
are the version that got Nak'ed earlier, and the discussion about
trying to fix it ended without a positive conclusion.

This should be addressed as soon as Miklos rebases his changes on
top of 4.18-rc1 for the following merge window.

     Arnd

^ permalink raw reply	[flat|nested] 3+ messages in thread

end of thread, other threads:[~2018-06-15  7:44 UTC | newest]

Thread overview: 3+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2018-06-15  0:43 linux-next: manual merge of the y2038 tree with the overlayfs tree Stephen Rothwell
2018-06-15  2:41 ` Stephen Rothwell
2018-06-15  7:44   ` Arnd Bergmann

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.