Commit 47ae32d6a54955a041cdc30b06d0bb16e75f68d5

Authored by Valerie Henson
Committed by Linus Torvalds
1 parent b227613841

[PATCH] relative atime

Add "relatime" (relative atime) support.  Relative atime only updates the
atime if the previous atime is older than the mtime or ctime.  Like
noatime, but useful for applications like mutt that need to know when a
file has been read since it was last modified.

A corresponding patch against mount(8) is available at
http://userweb.kernel.org/~akpm/mount-relative-atime.txt

Signed-off-by: Valerie Henson <val_henson@linux.intel.com>
Cc: Mark Fasheh <mark.fasheh@oracle.com>
Cc: Al Viro <viro@zeniv.linux.org.uk>
Cc: Christoph Hellwig <hch@lst.de>
Cc: Karel Zak <kzak@redhat.com>
Signed-off-by: Andrew Morton <akpm@osdl.org>
Signed-off-by: Linus Torvalds <torvalds@osdl.org>

Showing 4 changed files with 24 additions and 5 deletions Side-by-side Diff

... ... @@ -1177,13 +1177,27 @@
1177 1177 return;
1178 1178 if ((mnt->mnt_flags & MNT_NODIRATIME) && S_ISDIR(inode->i_mode))
1179 1179 return;
  1180 +
  1181 + if (mnt->mnt_flags & MNT_RELATIME) {
  1182 + /*
  1183 + * With relative atime, only update atime if the
  1184 + * previous atime is earlier than either the ctime or
  1185 + * mtime.
  1186 + */
  1187 + if (timespec_compare(&inode->i_mtime,
  1188 + &inode->i_atime) < 0 &&
  1189 + timespec_compare(&inode->i_ctime,
  1190 + &inode->i_atime) < 0)
  1191 + return;
  1192 + }
1180 1193 }
1181 1194  
1182 1195 now = current_fs_time(inode->i_sb);
1183   - if (!timespec_equal(&inode->i_atime, &now)) {
1184   - inode->i_atime = now;
1185   - mark_inode_dirty_sync(inode);
1186   - }
  1196 + if (timespec_equal(&inode->i_atime, &now))
  1197 + return;
  1198 +
  1199 + inode->i_atime = now;
  1200 + mark_inode_dirty_sync(inode);
1187 1201 }
1188 1202 EXPORT_SYMBOL(touch_atime);
1189 1203  
... ... @@ -368,6 +368,7 @@
368 368 { MNT_NOEXEC, ",noexec" },
369 369 { MNT_NOATIME, ",noatime" },
370 370 { MNT_NODIRATIME, ",nodiratime" },
  371 + { MNT_RELATIME, ",relatime" },
371 372 { 0, NULL }
372 373 };
373 374 struct proc_fs_info *fs_infop;
374 375  
... ... @@ -1405,9 +1406,11 @@
1405 1406 mnt_flags |= MNT_NOATIME;
1406 1407 if (flags & MS_NODIRATIME)
1407 1408 mnt_flags |= MNT_NODIRATIME;
  1409 + if (flags & MS_RELATIME)
  1410 + mnt_flags |= MNT_RELATIME;
1408 1411  
1409 1412 flags &= ~(MS_NOSUID | MS_NOEXEC | MS_NODEV | MS_ACTIVE |
1410   - MS_NOATIME | MS_NODIRATIME);
  1413 + MS_NOATIME | MS_NODIRATIME | MS_RELATIME);
1411 1414  
1412 1415 /* ... and get the mountpoint */
1413 1416 retval = path_lookup(dir_name, LOOKUP_FOLLOW, &nd);
... ... @@ -120,6 +120,7 @@
120 120 #define MS_PRIVATE (1<<18) /* change to private */
121 121 #define MS_SLAVE (1<<19) /* change to slave */
122 122 #define MS_SHARED (1<<20) /* change to shared */
  123 +#define MS_RELATIME (1<<21) /* Update atime relative to mtime/ctime. */
123 124 #define MS_ACTIVE (1<<30)
124 125 #define MS_NOUSER (1<<31)
125 126  
include/linux/mount.h
... ... @@ -27,6 +27,7 @@
27 27 #define MNT_NOEXEC 0x04
28 28 #define MNT_NOATIME 0x08
29 29 #define MNT_NODIRATIME 0x10
  30 +#define MNT_RELATIME 0x20
30 31  
31 32 #define MNT_SHRINKABLE 0x100
32 33