Move execve's access time update functionality into a new

vfs_mark_atime() function, and use the new function for
performing efficient atime updates in mmap().

Reviewed by:	bde
MFC after:	2 weeks
This commit is contained in:
dds 2005-10-12 06:56:00 +00:00
parent 66b195cfae
commit 0fb2e655fd
5 changed files with 25 additions and 27 deletions

View File

@ -292,7 +292,7 @@ do_execve(td, args, mac_p)
register_t *stack_base;
int error, len, i;
struct image_params image_params, *imgp;
struct vattr atimeattr, attr;
struct vattr attr;
int (*img_first)(struct image_params *);
struct pargs *oldargs = NULL, *newargs = NULL;
struct sigacts *oldsigacts, *newsigacts;
@ -709,17 +709,7 @@ do_execve(td, args, mac_p)
exec_setregs(td, imgp->entry_addr,
(u_long)(uintptr_t)stack_base, imgp->ps_strings);
/*
* Here we should update the access time of the file. This must
* be implemented by the underlying filesystem in the same way as
* access timestamps for a VOP_READ() because we want to avoid
* blocking and/or I/O, and have not called vn_start_write().
*/
if ((imgp->vp->v_mount->mnt_flag & (MNT_NOATIME | MNT_RDONLY)) == 0) {
VATTR_NULL(&atimeattr);
atimeattr.va_vaflags |= VA_EXECVE_ATIME;
(void)VOP_SETATTR(imgp->vp, &atimeattr, td->td_ucred, td);
}
vfs_mark_atime(imgp->vp, td);
done1:
/*

View File

@ -3881,3 +3881,20 @@ vfs_read_dirent(struct vop_readdir_args *ap, struct dirent *dp, off_t off)
return (0);
}
/*
* Mark for update the access time of the file if the filesystem
* supports VA_MARK_ATIME. This functionality is used by execve
* and mmap, so we want to avoid the synchronous I/O implied by
* directly setting va_atime for the sake of efficiency.
*/
void
vfs_mark_atime(struct vnode *vp, struct thread *td)
{
struct vattr atimeattr;
if ((vp->v_mount->mnt_flag & (MNT_NOATIME | MNT_RDONLY)) == 0) {
VATTR_NULL(&atimeattr);
atimeattr.va_vaflags |= VA_MARK_ATIME;
(void)VOP_SETATTR(vp, &atimeattr, td->td_ucred, td);
}
}

View File

@ -285,7 +285,7 @@ struct vattr {
*/
#define VA_UTIMES_NULL 0x01 /* utimes argument was NULL */
#define VA_EXCLUSIVE 0x02 /* exclusive create request */
#define VA_EXECVE_ATIME 0x04 /* setting atime for execve */
#define VA_MARK_ATIME 0x04 /* setting atime for execve/mmap */
/*
* Flags for ioflag. (high 16 bits used to ask for read-ahead and
@ -727,6 +727,7 @@ void vfs_hash_rehash(struct vnode *vp, u_int hash);
void vfs_hash_remove(struct vnode *vp);
int vfs_kqfilter(struct vop_kqfilter_args *);
void vfs_mark_atime(struct vnode *vp, struct thread *td);
struct dirent;
int vfs_read_dirent(struct vop_readdir_args *ap, struct dirent *dp, off_t off);

View File

@ -437,13 +437,13 @@ ufs_setattr(ap)
return (EINVAL);
}
/*
* Update the file's access time when it has been executed. We are
* doing this here to specifically avoid some of the checks done
* Mark for update the file's access time for vfs_mark_atime().
* We are doing this here to avoid some of the checks done
* below -- this operation is done by request of the kernel and
* should bypass some security checks. Things like read-only
* checks get handled by other levels (e.g., ffs_update()).
*/
if (vap->va_vaflags & VA_EXECVE_ATIME) {
if (vap->va_vaflags & VA_MARK_ATIME) {
ip->i_flag |= IN_ACCESS;
return (0);
}

View File

@ -1164,18 +1164,8 @@ vm_mmap_vnode(struct thread *td, vm_size_t objsize,
}
*objp = obj;
*flagsp = flags;
vfs_mark_atime(vp, td);
/* Update access time. */
if ((vp->v_mount->mnt_flag & MNT_NOATIME) == 0) {
struct vattr vattr;
struct timespec ts;
VATTR_NULL(&vattr);
vfs_timestamp(&ts);
vattr.va_atime = ts;
(void)VOP_SETATTR(vp, &vattr, td->td_ucred, td);
}
done:
vput(vp);
VFS_UNLOCK_GIANT(vfslocked);