Commit eb31e2f6 authored by Amir Goldstein's avatar Amir Goldstein Committed by Al Viro
Browse files

utimes: Clamp the timestamps in notify_change()



Push clamping timestamps into notify_change(), so in-kernel
callers like nfsd and overlayfs will get similar timestamp
set behavior as utimes.

AV: get rid of clamping in ->setattr() instances; we don't need
to bother with that there, with notify_change() doing normalization
in all cases now (it already did for implicit case, since current_time()
clamps).

Suggested-by: default avatarMiklos Szeredi <mszeredi@redhat.com>
Fixes: 42e729b9 ("utimes: Clamp the timestamps before update")
Cc: stable@vger.kernel.org # v5.4
Cc: Deepa Dinamani <deepa.kernel@gmail.com>
Cc: Jeff Layton <jlayton@kernel.org>
Signed-off-by: default avatarAmir Goldstein <amir73il@gmail.com>
Signed-off-by: default avatarAl Viro <viro@zeniv.linux.org.uk>
parent e42617b8
Loading
Loading
Loading
Loading
+11 −12
Original line number Diff line number Diff line
@@ -183,18 +183,12 @@ void setattr_copy(struct inode *inode, const struct iattr *attr)
		inode->i_uid = attr->ia_uid;
	if (ia_valid & ATTR_GID)
		inode->i_gid = attr->ia_gid;
	if (ia_valid & ATTR_ATIME) {
		inode->i_atime = timestamp_truncate(attr->ia_atime,
						  inode);
	}
	if (ia_valid & ATTR_MTIME) {
		inode->i_mtime = timestamp_truncate(attr->ia_mtime,
						  inode);
	}
	if (ia_valid & ATTR_CTIME) {
		inode->i_ctime = timestamp_truncate(attr->ia_ctime,
						  inode);
	}
	if (ia_valid & ATTR_ATIME)
		inode->i_atime = attr->ia_atime;
	if (ia_valid & ATTR_MTIME)
		inode->i_mtime = attr->ia_mtime;
	if (ia_valid & ATTR_CTIME)
		inode->i_ctime = attr->ia_ctime;
	if (ia_valid & ATTR_MODE) {
		umode_t mode = attr->ia_mode;

@@ -268,8 +262,13 @@ int notify_change(struct dentry * dentry, struct iattr * attr, struct inode **de
	attr->ia_ctime = now;
	if (!(ia_valid & ATTR_ATIME_SET))
		attr->ia_atime = now;
	else
		attr->ia_atime = timestamp_truncate(attr->ia_atime, inode);
	if (!(ia_valid & ATTR_MTIME_SET))
		attr->ia_mtime = now;
	else
		attr->ia_mtime = timestamp_truncate(attr->ia_mtime, inode);

	if (ia_valid & ATTR_KILL_PRIV) {
		error = security_inode_need_killpriv(dentry);
		if (error < 0)
+3 −6
Original line number Diff line number Diff line
@@ -76,14 +76,11 @@ int configfs_setattr(struct dentry * dentry, struct iattr * iattr)
	if (ia_valid & ATTR_GID)
		sd_iattr->ia_gid = iattr->ia_gid;
	if (ia_valid & ATTR_ATIME)
		sd_iattr->ia_atime = timestamp_truncate(iattr->ia_atime,
						      inode);
		sd_iattr->ia_atime = iattr->ia_atime;
	if (ia_valid & ATTR_MTIME)
		sd_iattr->ia_mtime = timestamp_truncate(iattr->ia_mtime,
						      inode);
		sd_iattr->ia_mtime = iattr->ia_mtime;
	if (ia_valid & ATTR_CTIME)
		sd_iattr->ia_ctime = timestamp_truncate(iattr->ia_ctime,
						      inode);
		sd_iattr->ia_ctime = iattr->ia_ctime;
	if (ia_valid & ATTR_MODE) {
		umode_t mode = iattr->ia_mode;

+6 −12
Original line number Diff line number Diff line
@@ -754,18 +754,12 @@ static void __setattr_copy(struct inode *inode, const struct iattr *attr)
		inode->i_uid = attr->ia_uid;
	if (ia_valid & ATTR_GID)
		inode->i_gid = attr->ia_gid;
	if (ia_valid & ATTR_ATIME) {
		inode->i_atime = timestamp_truncate(attr->ia_atime,
						  inode);
	}
	if (ia_valid & ATTR_MTIME) {
		inode->i_mtime = timestamp_truncate(attr->ia_mtime,
						  inode);
	}
	if (ia_valid & ATTR_CTIME) {
		inode->i_ctime = timestamp_truncate(attr->ia_ctime,
						  inode);
	}
	if (ia_valid & ATTR_ATIME)
		inode->i_atime = attr->ia_atime;
	if (ia_valid & ATTR_MTIME)
		inode->i_mtime = attr->ia_mtime;
	if (ia_valid & ATTR_CTIME)
		inode->i_ctime = attr->ia_ctime;
	if (ia_valid & ATTR_MODE) {
		umode_t mode = attr->ia_mode;

+6 −12
Original line number Diff line number Diff line
@@ -2899,18 +2899,12 @@ int ntfs_setattr(struct dentry *dentry, struct iattr *attr)
			ia_valid |= ATTR_MTIME | ATTR_CTIME;
		}
	}
	if (ia_valid & ATTR_ATIME) {
		vi->i_atime = timestamp_truncate(attr->ia_atime,
					       vi);
	}
	if (ia_valid & ATTR_MTIME) {
		vi->i_mtime = timestamp_truncate(attr->ia_mtime,
					       vi);
	}
	if (ia_valid & ATTR_CTIME) {
		vi->i_ctime = timestamp_truncate(attr->ia_ctime,
					       vi);
	}
	if (ia_valid & ATTR_ATIME)
		vi->i_atime = attr->ia_atime;
	if (ia_valid & ATTR_MTIME)
		vi->i_mtime = attr->ia_mtime;
	if (ia_valid & ATTR_CTIME)
		vi->i_ctime = attr->ia_ctime;
	mark_inode_dirty(vi);
out:
	return err;
+6 −12
Original line number Diff line number Diff line
@@ -1078,18 +1078,12 @@ static void do_attr_changes(struct inode *inode, const struct iattr *attr)
		inode->i_uid = attr->ia_uid;
	if (attr->ia_valid & ATTR_GID)
		inode->i_gid = attr->ia_gid;
	if (attr->ia_valid & ATTR_ATIME) {
		inode->i_atime = timestamp_truncate(attr->ia_atime,
						  inode);
	}
	if (attr->ia_valid & ATTR_MTIME) {
		inode->i_mtime = timestamp_truncate(attr->ia_mtime,
						  inode);
	}
	if (attr->ia_valid & ATTR_CTIME) {
		inode->i_ctime = timestamp_truncate(attr->ia_ctime,
						  inode);
	}
	if (attr->ia_valid & ATTR_ATIME)
		inode->i_atime = attr->ia_atime;
	if (attr->ia_valid & ATTR_MTIME)
		inode->i_mtime = attr->ia_mtime;
	if (attr->ia_valid & ATTR_CTIME)
		inode->i_ctime = attr->ia_ctime;
	if (attr->ia_valid & ATTR_MODE) {
		umode_t mode = attr->ia_mode;

Loading