我只是在阅读Birthstat部分,似乎ext4应该支持它,但是即使我刚刚创建的文件也将其留空。

 ~  % touch test                                                       slave-iv
 ~  % stat test.pl                                                     slave-iv
  File: ‘test.pl’
  Size: 173             Blocks: 8          IO Block: 4096   regular file
Device: 903h/2307d      Inode: 41943086    Links: 1
Access: (0600/-rw-------)  Uid: ( 1000/xenoterracide)   Gid: (  100/   users)
Access: 2012-09-22 18:22:16.924634497 -0500
Modify: 2012-09-22 18:22:16.924634497 -0500
Change: 2012-09-22 18:22:16.947967935 -0500
 Birth: -

 ~  % sudo tune2fs -l /dev/md3 | psp4                                  slave-iv
tune2fs 1.42.5 (29-Jul-2012)
Filesystem volume name:   home
Last mounted on:          /home
Filesystem UUID:          ab2e39fb-acdd-416a-9e10-b501498056de
Filesystem magic number:  0xEF53
Filesystem revision #:    1 (dynamic)
Filesystem features:      has_journal ext_attr resize_inode dir_index filetype needs_recovery extent flex_bg sparse_super large_file huge_file uninit_bg dir_nlink extra_isize
Filesystem flags:         signed_directory_hash 
Default mount options:    journal_data
Filesystem state:         clean
Errors behavior:          Continue
Filesystem OS type:       Linux
Inode count:              59736064
Block count:              238920960
Reserved block count:     11946048
Free blocks:              34486248
Free inodes:              59610013
First block:              0
Block size:               4096
Fragment size:            4096
Reserved GDT blocks:      967
Blocks per group:         32768
Fragments per group:      32768
Inodes per group:         8192
Inode blocks per group:   512
RAID stride:              128
RAID stripe width:        256
Flex block group size:    16
Filesystem created:       Mon May 31 20:36:30 2010
Last mount time:          Sat Oct  6 11:01:01 2012
Last write time:          Sat Oct  6 11:01:01 2012
Mount count:              14
Maximum mount count:      34
Last checked:             Tue Jul 10 08:26:37 2012
Check interval:           15552000 (6 months)
Next check after:         Sun Jan  6 07:26:37 2013
Lifetime writes:          7255 GB
Reserved blocks uid:      0 (user root)
Reserved blocks gid:      0 (group root)
First inode:              11
Inode size:           256
Required extra isize:     28
Desired extra isize:      28
Journal inode:            8
First orphan inode:       55313243
Default directory hash:   half_md4
Directory Hash Seed:      442c66e8-8b67-4a8c-92a6-2e2d0c220044
Journal backup:           inode blocks


为什么我的ext4分区没有填充此字段?

#1 楼

coreutils stat不显示该字段(请参见下文)。显然,他们正在等待xstat()接口。

coreutils补丁-8月。 2012年-TODO


stat(1)和ls(1)支持出生时间。取决于内核提供的xstat()



您可以通过debugfs获得创建时间:




 debugfs -R 'stat <inode_number>' DEVICE
 


例如适用于/etc/profile上的我的/dev/sda2(请参阅如何找出文件所在的设备): > debugfs -R 'stat <398264>' /dev/sda2 debugfs 1.42.5 (29-Jul-2012) Inode: 398264 Type: regular Mode: 0644 Flags: 0x80000 Generation: 2058737571 Version: 0x00000000:00000001 User: 0 Group: 0 Size: 562 File ACL: 0 Directory ACL: 0 Links: 1 Blockcount: 8 Fragment: Address: 0 Number: 0 Size: 0 ctime: 0x506b860b:19fa3c34 -- Wed Oct 3 02:25:47 2012 atime: 0x50476677:dcd84978 -- Wed Sep 5 16:49:27 2012 mtime: 0x506b860b:19fa3c34 -- Wed Oct 3 02:25:47 2012 crtime: 0x50476677:dcd84978 -- Wed Sep 5 16:49:27 2012 Size of extra inode fields: 28 EXTENTS: (0):3308774

时间字段含义:



ctime:文件更改时间。

atime:文件访问时间。

mtime:文件修改时间。

crtime:文件创建时间。

1Linus对LKML线程的答复

评论


@Sparhawk:文件/ home / user / path / to / file也有这个问题,因为/ home在单独的分区上。在这种情况下,提供给stat的路径必须相对于/ home。示例:sudo debugfs -R'stat用户/路径/到/文件'/ dev / sda2。要摆脱路径处理,我们可以提供stat inode号而不是路径:sudo debugfs -R“ stat <$(stat -c%i / home / user / path / to / file)>” / dev / sda5

– jep
2014年4月17日下午2:39

可以用来从网络安装的文件系统中获取文件的创建时间吗?

– Taranaki
18-09-20在18:32

因此,这不是创建文件系统之外的时间戳。这意味着,如果文件是25年前创建的,并且通过许多不同的物理或安装的系统进行复制,则根本无法在任何元数据中找到创建日期的信息吗?因此,知道何时创建文件的唯一方法是将其键入文件名?还是里面的内容?这种看似奇怪的未实现是否有任何原因?

– sinekonata
19年1月1日,3:10

@sinekonata文件元数据非常依赖于系统(如此答案所示,操作系统的每一层都必须能够处理它),并且要使其在计算机之间的副本之间保持副本依赖于系统和复制工具对该元数据格式的支持。这意味着:如果您没有弄乱文件名,那么您很幸运。另外,有些文件格式允许您在文件中插入元数据(例如ID3),并且通常携带良好,但是许多格式没有这种功能。最后,您可以将文件放入存档文件中,例如

–安德烈·帕拉梅斯(AndréParamés)
19年4月4日在11:06

请注意,inode号周围的<和>是必需的。在示例中,它们通常用于包围应调整的变量,但在这种情况下,必须按字面值输入。没有它们,inode编号将被视为路径,并且您将得到ext2_lookup错误找不到的文件。

– mivk
19-10-15在15:49



#2 楼

我将其组合成一个简单的shell函数: br />
$ get_crtime foo foo/file /etc/
foo Wed May 21 17:11:08 2014
foo/file    Wed May 21 17:11:27 2014
/etc/   Wed Aug  1 20:42:03 2012


评论


它对我的覆盆子杰西不起作用。

–sergius
19/12/3在15:01

@sergius是的,rapsbian做一些奇怪的事情,并使df返回/ dev / root,这实际上并不存在。我不知道它在做什么,但是您可能想问一个新问题,为什么df $ HOME在raspbian上返回/ dev / root。这就是使失败的原因。有关/ dev / root的更多信息,请参见:为什么在某些Linux系统上,根文件系统在mtab中显示为/ dev / root而不是/ dev /?

– terdon♦
19年12月3日在16:00

你是对的。对于树莓派,正确的路径是/ dev / mmcblk0p2(当然在树莓派上)。谢谢,我将尽力对此进行更具体的说明。

–sergius
19/12/3在18:26



#3 楼

xstat函数从未合并到主线中。但是,稍后提出了新的statx调用,该调用已在Linux 4.11中合并。新的statx(2)系统调用的返回结构中确实包含创建时间。仅在2.28(2018年8月发布)中将statx(2)的包装程序添加到glibc中。 GNU coreutils 8.31(于2019年3月发布)中添加了对使用此包装器的支持:


stat现在在文件系统支持时显示文件创建时间,在GNU Linux上为
带有glibc> = 2.28和内核> = 4.11的系统。 (旧的glibc或coreutils)。直接在C程序中调用系统调用并不容易。通常,glibc提供了一个使工作容易的包装器,但是幸运的是,@ whotwagner编写了一个示例C程序,该程序演示了如何在x86和x86-64系统上使用statx系统调用。它的输出与statx(2)的默认格式相同,没有任何格式设置选项,但修改它以仅打印出生时间很简单。 (如果有足够新的glibc,则不需要它-您可以按照stat中的说明直接使用statx。)

首先,将其克隆:

% stat --version
stat (GNU coreutils) 8.31
Copyright (C) 2019 Free Software Foundation, Inc.
License GPLv3+: GNU GPL version 3 or later <https://gnu.org/licenses/gpl.html>.
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 /
  File: /
  Size: 4096            Blocks: 8          IO Block: 4096   directory
Device: b302h/45826d    Inode: 2           Links: 17
Access: (0755/drwxr-xr-x)  Uid: (    0/    root)   Gid: (    0/    root)
Access: 2019-06-06 20:03:12.898725626 +0900
Modify: 2019-05-28 05:15:44.452651395 +0900
Change: 2019-05-28 05:15:44.452651395 +0900
 Birth: 2018-06-07 20:35:54.000000000 +0900


您可以编译man 2 statx代码,或者,如果您只想要出生时间,请使用以下代码在克隆目录中创建statx.c(这是birth.c的最小版本,仅打印包括纳秒级的创建时间戳精度):

 statx.c 


然后:

git clone https://github.com/whotwagner/statx-fun


从理论上讲,这应该使创建时间可以在更多文件系统上访问,而不仅仅是ext *文件系统(#define _GNU_SOURCE #define _ATFILE_SOURCE #include <stdio.h> #include <stdlib.h> #include <sys/types.h> #include <unistd.h> #include <fcntl.h> #include "statx.h" #include <time.h> #include <getopt.h> #include <string.h> // does not (yet) provide a wrapper for the statx() system call #include <sys/syscall.h> /* this code works ony with x86 and x86_64 */ #if __x86_64__ #define __NR_statx 332 #else #define __NR_statx 383 #endif #define statx(a,b,c,d,e) syscall(__NR_statx,(a),(b),(c),(d),(e)) int main(int argc, char *argv[]) { int dirfd = AT_FDCWD; int flags = AT_SYMLINK_NOFOLLOW; unsigned int mask = STATX_ALL; struct statx stxbuf; long ret = 0; int opt = 0; while(( opt = getopt(argc, argv, "alfd")) != -1) { switch(opt) { case 'a': flags |= AT_NO_AUTOMOUNT; break; case 'l': flags &= ~AT_SYMLINK_NOFOLLOW; break; case 'f': flags &= ~AT_STATX_SYNC_TYPE; flags |= AT_STATX_FORCE_SYNC; break; case 'd': flags &= ~AT_STATX_SYNC_TYPE; flags |= AT_STATX_DONT_SYNC; break; default: exit(EXIT_SUCCESS); break; } } if (optind >= argc) { exit(EXIT_FAILURE); } for (; optind < argc; optind++) { memset(&stxbuf, 0xbf, sizeof(stxbuf)); ret = statx(dirfd, argv[optind], flags, mask, &stxbuf); if( ret < 0) { perror("statx"); return EXIT_FAILURE; } printf("%lld.%u\n", *&stxbuf.stx_btime.tv_sec, *&stxbuf.stx_btime.tv_nsec); } return EXIT_SUCCESS; } 是ext2 / 3/4文件系统的工具,而在其他文件系统上则不可用)。它确实适用于XFS系统,但不适用于NTFS和exfat。我猜那些的FUSE文件系统不包括创建时间。

#4 楼

还有另一种情况,出生时间将为空/零/破折号:Ext4的Inode大小必须至少为256bytes才能存储crtime。如果最初创建的文件系统小于512MB(默认的Inode大小为128字节,请参见/etc/mke2fs.confmkfs.ext4联机帮助页),则会出现问题。

stat -c '%n: %w' testfile
testfile: -  


和/或

stat -c '%n: %W' testfile
testfile: 0


现在检查文件系统索引节点(它足以存储crtime吗?):

tune2fs -l $(df . --output=source | grep ^/) | grep "Inode size:"
Inode size:           128


技术信息:在“ Ext4磁盘布局”页面上,请注意,inode表的某些属性超出了0x80(128)。

评论


正确(我记得在vger上阅读过此内容)。在mke2fs.c中的第1275行定义了512MB的限制

–don_crissti
2015年3月27日23:22



#5 楼

对于我值得的东西,我感觉很花哨,所以在stat周围写了一个bash包装器,以使用debugfs从底层ext4文件系统(如果有)中获取它来默默支持crtime。我希望它坚固。在此处找到它。

请注意,该脚本上记录了表面上针对Linux的待办事项列表的修复程序。因此,此包装器只有在完成此操作后才具有标称使用寿命,并且在可行范围内更多地是一项练习。

评论


请注意,xstat()最终已添加到Linux中,因此GNU libc并为其添加支持只是时间问题。

–StéphaneChazelas
17年3月3日在9:35

太棒了!确实是个好消息。

– Bernd Wechner
17年6月3日在10:18

出于道歉的态度,您似乎无法理解“ pedantic”的含义。

–尼克
17年9月22日在9:53

“过分关注细节或形式主义”-例如,可接受的答案很好,但是...让我们对其进行形式化。 ;-)

– Bernd Wechner
18年8月30日在7:09

#6 楼

从GNU coreutils的8.31版开始,stat“在文件系统支持的情况下,现在在glibc> = 2.28和内核> = 4.11的GNU Linux系统上显示文件创建时间。”

我的操作系统(Ubuntu Linux内核5.4.0-28和GLIBC 2.31附带的20.04仅与GNU coreutils 8.30一起提供,因此我不得不通过从源代码编译GNU coreutils的8.32版本来进行验证。

ls -l --time=birth --time-style=full-iso --no-group的输出:

$ ls -l --time=birth --time-style=full-iso --no-group
total 13477610
-rwxr--r-- 1 systemd-coredump 13801071714 2017-06-30 04:53:33.211517792 -0400  file


btrfs文件系统上stat的输出:

$ stat file
  File: /mnt/btrfs/file
  Size: 13801071714 Blocks: 26955224   IO Block: 4096   regular file
Device: 33h/51d Inode: 4998        Links: 1
Access: (0744/-rwxr--r--)  Uid: (  999/systemd-coredump)   Gid: (  999/systemd-coredump)
Access: 2020-05-04 12:21:51.640487614 -0400
Modify: 2016-01-19 10:32:19.272000000 -0500
Change: 2017-06-30 04:55:14.910839537 -0400
 Birth: 2017-06-30 04:53:33.211517792 -0400


(很奇怪,我无法尽管满足了上述所有要求,但仍可以获得使用虚拟ext4文件系统在Arch Linux上显示的任何出生时间。) ,从GNU coreutils的8.32版开始(稳定版本),statls都使用statx调用。

ls将显示创建/出生时间。 > **新功能

ls现在支持--time = birth选项来显示和排序通过
文件创建时间(如果有)。


并且大概也可以。stat也可以。


**改进

stat和ls现在在可用的情况下使用statx()系统调用,
仅检索请求的
属性即可更有效地运行。


崭新的品牌,仅在2020年3月5日发布,因此除非您使用的是Arch Linux之类的尖端发行版,否则可能要花一些时间。 (Arch Linux于2020年4月1日获得coreutils软件包的8.32-1版本)。

评论


stat本身已经显示了创建日期正弦8.31

–muru
20年4月30日在4:25

我刚启动并在系统上运行Ubuntu 20.04。不幸的是,它具有coreutils的8.30版本,并且没有显示出生时间,因此我至少可以确定8.30没有该功能。编辑:似乎已经在这里描述了savannah.gnu.org/forum/forum.php?forum_id=9394显然是一年前。

–李凯文
20-4-30在4:31



unix.stackexchange.com/a/407305/70524

–muru
20年4月30日下午5:00

请不要发布文字的屏幕截图。 unix.meta.stackexchange.com/q/4086/70524

–muru
20-5-4在4:56

@muru进行了更改。感谢您的单挑。

–李凯文
20-5-4在17:26