How to check all timestamps of a file?
Is there a command in Linux to check all timestamps of a file? I’m trying to see the last modified, created, and touched dates on the file.
Just to point out, Linux files don’t have birth dates. Thus, it’s not possible to determine the date a file was created.
@FatalError: Various filesystems already support birth/creation timestamps; the real trouble is in accessing such extra information. (One can’t just extend struct stat without breaking things, unfortunately. ) You can try out debugfs -R «stat » /dev/sdXY for ext4, replacing 1234 with an ino.
@grawity: Neat! I always wondered why no fs had it. but I guess they do, but like you said, can’t just go breaking the ABI for existing binaries. Thanks for the tip :).
@FatalError, Birth time can be displayed with Linux stat command, see How to find creation date of file? and What file systems on Linux store the creation time?.
2 Answers 2
$ stat test 234881026 41570368 -rw-r--r-- 1 werner staff 0 0 "Feb 7 16:03:06 2012" "Feb 7 16:03:06 2012" "Feb 7 16:03:06 2012" "Feb 7 16:03:06 2012" 4096 0 0 test
If you want to adjust the format, refer to the man pages, since the output is OS-specific and varies under Linux/Unix.
Generally, you can get the times through a normal directory listing as well:
- ls -l outputs last time the file content was modified, the mtime
- ls -lc outputs last time of file status modification, the ctime (What’s the difference?)
- ls -lu outputs last access time, the atime (although the usefulness of this concept is subject to discussion)
And of course, ctime does not record when a file was «created». The POSIX specification defines only three timestamps, but some Linux filesystems store Birth Time/Creation Time. How to find creation date of file? On such a supported configuration, one could use
stat --printf '%n\nmtime: %y\nctime: %z\natime: %x\ncrtime:%w\n'
stat is really detailed. But ls only needs one line. It would be good if it could also display seconds. However, when creating lists of files, the former one is perfectly suitable.
I’ve noticed that the result of ls -l can show a different date format when there is BusyBox installed (on Android). I think that without it , it’s like «2019-07-26 14:41» , and with it, it’s like «May 6 21:27» . How come the year is missing ? Is there a way to force it using the format of without it?
@androiddeveloper Like I said, the answer depends on the OS. I think you should open a new question. If you are talking about Android specifically, perhaps Stack Overflow or Android Enthusiasts would be more fitting.
@slhck Well it’s the same OS, just with BusyBox installed. I asked if it’s possible (meaning : is there a command to use) to get the format that will be shown.
There are only THREE distinct times values stored for each of your files, as defined by the POSIX Standard : http://pubs.opengroup.org/onlinepubs/9699919799/ (see Base Definitions section -> 4. General Concepts -> 4.8 File Times Update)
Each file has three distinct associated timestamps: the time of last data access, the time of last data modification, and the time the file status last changed. These values are returned in the file characteristics structure struct stat, as described in .
atime is for Last data access timestamp. mtime is for Last data modification timestamp. ctime is for Last file status change timestamp.
Following examples show the difference among the atime, mtime and ctime, these examples are in GNU/Linux BASH. You can use stat -x in Mac OS X or other BSD Dist. to see the similar output format.
$ stat --version stat (GNU coreutils) 8.4 Copyright (C) 2010 Free Software Foundation, Inc. License GPLv3+: GNU GPL version 3 or later . This is free software: you are free to change and redistribute it. There is NO WARRANTY, to the extent permitted by law. Written by Michael Meskes. $ $ touch test $ stat test File: `test' Size: 0 Blocks: 0 IO Block: 4096 regular empty file Device: 811h/2065d Inode: 98828525 Links: 1 Access: (0664/-rw-rw-r--) Uid: ( 514/ rank) Gid: ( 514/ rank) Access: 2014-03-16 10:58:28.609223953 +0800 Modify: 2014-03-16 10:58:28.609223953 +0800 Change: 2014-03-16 10:58:28.609223953 +0800
When the file just be created, three timestamps are the same.
1. atime
First, let’s access the file’s data by reading it ( less or vim ), printing it out ( cat ) or copy it to another file ( cp ).
$ cat test #Nothing will be printed out, since the file is empty $ stat test File: `test' Size: 0 Blocks: 0 IO Block: 4096 regular empty file Device: 811h/2065d Inode: 98828525 Links: 1 Access: (0664/-rw-rw-r--) Uid: ( 514/ rank) Gid: ( 514/ rank) Access: 2014-03-16 10:59:13.182301069 +0800
2. ctime
Now let's change the file status, by changing the permission ( chmod ) or renaming it ( mv )
$ chmod u+x test $ stat stet File: `test' Size: 0 Blocks: 0 IO Block: 4096 regular empty file Device: 811h/2065d Inode: 98828525 Links: 1 Access: (0764/-rwxrw-r--) Uid: ( 514/ rank) Gid: ( 514/ rank) Access: 2014-03-16 10:59:13.182301069 +0800 Modify: 2014-03-16 10:58:28.609223953 +0800 Change: 2014-03-16 11:04:10.178285430 +0800
Note that until now, the contents (data) of the file is still the same as when it created.
3. mtime
Finally, let's modify the contents of the file by editing the file.
$ echo 'Modify the DATA of the file' > testing $ echo 'Modify the DATA of the file also change the file status' > testing $ stat testing File: `testing' Size: 56 Blocks: 8 IO Block: 4096 regular file Device: 811h/2065d Inode: 98828525 Links: 1 Access: (0764/-rwxrw-r--) Uid: ( 514/ rank) Gid: ( 514/ rank) Access: 2014-03-16 10:59:13.182301069 +0800 Modify: 2014-03-16 11:09:48.247345148 +0800
4. birth time
Also note that the newer version of stat (e.g. stat --version 8.13 in Ubuntu 12.04) has 4th timestamp information - the Birth Time (file creation time). Although it may not show the correct time for now:
$ stat --version stat (GNU coreutils) 8.13 Copyright (C) 2011 Free Software Foundation, Inc. License GPLv3+: GNU GPL version 3 or later. This is free software: you are free to change and redistribute it. There is NO WARRANTY, to the extent permitted by law. Written by Michael Meskes. $ $ stat birth_time File: `birth_time' Size: 0 Blocks: 0 IO Block: 4096 regular empty file Device: 805h/2053d Inode: 4073946 Links: 1 Access: (0664/-rw-rw-r--) Uid: ( 1000/ bingyao) Gid: ( 1000/ bingyao) Access: 2014-03-16 10:46:48.838718970 +0800 Modify: 2014-03-16 10:46:48.838718970 +0800 Change: 2014-03-16 10:46:48.838718970 +0800 Birth: -
Get Last Modified Date of File in Linux
I'm new to Linux. I'm using the command-line. I'm trying to view the last modified date of a file. How do I do that in Linux from the Command Line?
@BrunoBieri It's the modification date. See man ls . Typical Linux file systems don't even track creation date -- see the accepted answer for the kinds of dates kept track of.
7 Answers 7
As mentioned by @edvinas.me, stat tells you various information about the file including the last modified date.
At first, I was confused with Modify and Change, just to clarify, stat output lists:
- Access shows the time of last data access (e.g. read).
- Modify shows the time of last data modification.
- Change shows the time the file status last changed.
~ $ touch foo ~ $ stat foo File: ‘foo’ Size: 0 Blocks: 0 IO Block: 4096 regular empty file Device: fc01h/64513d Inode: 410397 Links: 1 Access: (0644/-rw-r--r--) Uid: (80972/ etomort) Gid: (18429/ eem_tw) Access: 2015-09-21 12:06:11.343616258 +0200 Modify: 2015-09-21 12:06:11.343616258 +0200 Change: 2015-09-21 12:06:11.343616258 +0200 Birth: - ~ $ echo "Added bar to foo file" >> foo ~ $ stat foo File: ‘foo’ Size: 42 Blocks: 8 IO Block: 4096 regular file Device: fc01h/64513d Inode: 410654 Links: 1 Access: (0644/-rw-r--r--) Uid: (80972/ etomort) Gid: (18429/ eem_tw) Access: 2015-09-21 12:09:31.298712951 +0200 Modify: 2015-09-21 12:09:31.298712951 +0200 Change: 2015-09-21 12:09:31.302713093 +0200 Birth: - ~ $ chmod 444 foo ~ $ stat foo File: ‘foo’ Size: 42 Blocks: 8 IO Block: 4096 regular file Device: fc01h/64513d Inode: 410654 Links: 1 Access: (0444/-r--r--r--) Uid: (80972/ etomort) Gid: (18429/ eem_tw) Access: 2015-09-21 12:09:31.298712951 +0200 Modify: 2015-09-21 12:09:31.298712951 +0200 Change: 2015-09-21 12:10:16.040310543 +0200 Birth: -
Use stat command for that:
Another way that is more flexible is using date -r . From man date :
-r, --reference=FILE display the last modification time of FILE
This has the advantage of allowing you to specify the output format, e.g.
$ date -r foo Thu Aug 31 10:36:28 AEST 2017 $ date -r foo -R Thu, 31 Aug 2017 10:36:28 +1000 $ date -r foo -u Thu Aug 31 00:36:28 UTC 2017 $ date -r foo +%s 1504139788
Yes, very helpful, thanks. Here is a bash function that will rename a file to be prefixed by the modified time: function mvfilestime() < if [ x"$<1>" = "x" ] ; then echo "mvfilestime: Missing argument of file to mv" else f=$(date +"%Y-%m-%d-%H-%M" -r $<1>)-$ <1>echo mv $ <1>$ mv $ <1>$ fi >1>
#> ls -l /home/TEST/ total 16 -rw-r--r-- 1 rfmas1 nms 949 Nov 16 12:21 create_nd_lists.py -rw-r--r-- 1 rfmas1 nms 0 Nov 16 12:35 enb_list -rw-r--r-- 1 rfmas1 nms 0 Nov 16 12:35 nb_list -rw-r--r-- 1 rfmas1 nms 0 Nov 16 12:35 nodes_ip.txt -rw-r--r-- 1 rfmas1 nms 0 Nov 16 12:35 rnc_list
Building off of @Adam Taylor 's comment in @phoops 's answer and @Sparhawk 's answer.
To specifically just get the date (using October 3, 2019 for examples because it was my last birthday)
- stat -c %y file | cut -d' ' -f1 will give you 2019-10-03
- date +%F -r file will also give you 2019-10-03
- date +%D -r file will give you 10/03/19
- date +%x -r file will probably give either 10/03/2019 , or 10/03/19 if you're in the U.S. and either 03/10/2019 , or 03/10/19 if you're in the U.K., just to name a couple examples (of course there are more possibilities)
These date format options are, to my understanding, combinations of other format options. Here are some explanations from the man page:
%b locale's abbreviated month name (e.g., Jan)
%B locale's full month name (e.g., January)
.
%d day of month (e.g, 01)
%D date; same as %m/%d/%y
%e day of month, space padded; same as %_d
%F full date; same as %Y-%m-%d
.
%m month (01..12)
.
%x locale's date representation (e.g., 12/31/99)
.
%y last two digits of year (00..99)
%Y year
.
By default, date pads numeric fields with zeroes.
The following optional flags may follow `%':
- (hyphen) do not pad the field
_ (underscore) pad with spaces
0 (zero) pad with zeros
^ use upper case if possible
use opposite case if possible
N.B.: These flags don't work on the "combo formats" like %F , %D and %x . They are for the "singular field formats".
Apparently this last flag (#) does not work as I'd expect (e.g., if date +%b gives Oct , date +%#b gives OCT as opposed to oCT ) I guess this would be useless, but I'd think a lower case option would be more useful. date +%#p does turn date +%p which might give PM or AM into pm or am , respectively. So I guess it's not a 'per-character' case switch but sets the case of all the characters in the string to the opposite case of the majority of the characters? Also date +%P gives pm or am , but neither date +%^P nor date +%#P change its output. My guess for this case is that %P is just an alias for %#p , and it seems that whenever you add more than one flag, the behavior is undefined/unpredictable ( e.g., date +%0-e gives the same as date +%-e : 3 and date +%-0e gives the same as date +%0e : 03 , which makes you think that only the flag next to the letter works or that it goes left to right, but both date +%#^p and date +%^#p give pm or am , [depending on the time of course] ) unless there's some hidden order of operations? Sorry for digressing.
Also, if you run the command locale -k LC_TIME | grep ^d_fmt , you can see the combo for the specific locale of your system (e.g., d_fmt="%m/%d/%Y" ).
And you can make your own combo. For example,