我对此有点担心。这被称为“2038 年问题”。截至 12.04,Linux 内核或 Ubuntu 是否已准备好处理此之后的日期?
答案1
不会,它不会失败。在最坏的情况下,从程序员的角度来看,它会按预期工作:它将被重置为日期 1901-12-13 20:45:52:
以防万一发生这种情况,您不会更新当前的分布。”更新很容易。其中一个更新肯定会包含修复。“ 喜欢乔科拜说。
我记得 2000 年之前的 16 位机器也存在同样的问题,但最终没有任何问题。
来自 Wikipedia 的解决方案:
大多数设计用于 64 位硬件的操作系统已经使用了有符号的 64 位
time_t
整数。使用有符号的 64 位值会引入一个新的回绕日期,该日期比宇宙的估计年龄大 20 多倍:距今约 2920 亿年,即 292,277,026,596 年 12 月 4 日星期日 15:30:08。由于使用从 1900 年开始的有符号 32 位 int 值,因此计算日期的能力受到限制tm_year
。这将年份限制为最大值 2,147,485,547(2,147,483,647 + 1900)。虽然这解决了执行程序的问题,但它并没有解决在二进制数据文件中存储日期值的问题,其中许多文件采用严格的存储格式。它也没有解决在兼容层下运行的 32 位程序的问题,也可能无法解决将时间值错误地存储在除 之外的其他类型的变量中的程序的问题time_t
。
我使用 64 位 Ubuntu 13.04,出于好奇,我手动将时间更改为 2038-01-19 03:13:00。03:14:08 之后什么也没有发生:
因此,没有必要担心这个问题。
更多关于:
答案2
您可以使用以下 Perl 脚本检查您的计算机时间是否会崩溃:
#!/usr/bin/perl
use POSIX;
$ENV{'TZ'} = "GMT";
for ($clock = 2147483641; $clock < 2147483651; $clock++) {
print ctime($clock);
}
如果你的计算机没有问题,你将会得到以下信息:
Tue Jan 19 03:14:01 2038
Tue Jan 19 03:14:02 2038
Tue Jan 19 03:14:03 2038
Tue Jan 19 03:14:04 2038
Tue Jan 19 03:14:05 2038
Tue Jan 19 03:14:06 2038
Tue Jan 19 03:14:07 2038 <-- Last second in 32-bit Unix systems
Tue Jan 19 03:14:08 2038
Tue Jan 19 03:14:09 2038
Tue Jan 19 03:14:10 2038
如果你的计算机和我的一样,它将会像这样循环:
Tue Jan 19 03:14:01 2038
Tue Jan 19 03:14:02 2038
Tue Jan 19 03:14:03 2038
Tue Jan 19 03:14:04 2038
Tue Jan 19 03:14:05 2038
Tue Jan 19 03:14:06 2038
Tue Jan 19 03:14:07 2038
Fri Dec 13 20:45:52 1901
Fri Dec 13 20:45:52 1901
Fri Dec 13 20:45:52 1901
它还可以这样做:
Tue Jan 19 03:14:01 2038
Tue Jan 19 03:14:02 2038
Tue Jan 19 03:14:03 2038
Tue Jan 19 03:14:04 2038
Tue Jan 19 03:14:05 2038
Tue Jan 19 03:14:06 2038
Tue Jan 19 03:14:07 2038
Tue Jan 19 03:14:07 2038
Tue Jan 19 03:14:07 2038
Tue Jan 19 03:14:07 2038
答案3
早在 1996 年,我就撰写并发表了一篇关于此问题的短文。其中包括一个简短的 C 程序来演示它。我还通过电子邮件与 David Mills 讨论了 NTP(网络时间协议)的类似问题。在我的 Ubuntu 14.04 64 位笔记本电脑上,perl 代码没有表现出这种限制,因此底层的 64 位库一定已被修改。
但是,运行我很久以前的测试代码确实显示时间回溯到了 UNIX 纪元。因此,过去的 32 位代码并非一帆风顺。
我的 1996 年论文,UNIX 时间将于 2038 年耗尽!自 2000 年左右以来一直存在于我的网站上。其变体“UNIX 时间”于 1998 年在“2000 年 Y2K 千禧年计算最佳实践”ISBN 0136465064 中发布。
答案4
64 位 Linux 已经准备就绪,至少如果您谈论的是核心操作系统接口(当然,单个应用程序仍然会搞砸它)。time_t 传统上被定义为“long”的别名,64 位 Linux 上的“long”就是 64 位。
32 位 Linux(以及 64 位 Linux 上 32 位二进制文件的兼容层)的情况就不那么乐观了。它已经损坏,在不破坏所有现有二进制文件的情况下修复它并非易事。一大堆 API 使用 time_t,而且在许多情况下,它被嵌入为数据结构的一部分,因此不仅必须复制 API,还必须复制它们使用的数据结构。
即使存在某种程度的向后兼容性,所有想要获取正确时间的二进制文件都需要重建才能使用新的 64 位时间接口。
已经完成了一些工作(例如https://lwn.net/Articles/643234/和http://www.sourceware.org/ml/libc-alpha/2015-10/msg00893.html) 但据我所知,我们距离完整的解决方案还有很长的路要走。目前还不清楚是否会有通用的 32 位发行版可以解决 Y2K38 问题。