我想做的是在 glibc 中修复 Y2038 问题。 我在 Ubuntu 18.04 VM 中使用 buildroot 2022.02.2 来交叉编译 32 位 ARM CPU。 我读到添加额外的标志 _FILE_OFFSET_BITS=64 和 _TIME_BITS=64 应该可以做到这一点,但我得到这样的构建错误
/tmp/cclzLgs6.s:汇编器消息: /tmp/cclzLgs6.s:138:错误:符号“__sigtimedwait64”是 已经定义了
2.34 中是否提供对 Y2038 问题的支持,还是正在进行中? 或者也许我做错了什么,比如缺少一些标志?
谢谢你, 卡塔林
您可以执行以下操作来获取 Y2038 安全 buildroot 32 位 ARM 系统:
例如,将此补丁作为 0002-time-bits.patch 放在 buildroot/package/libzlib/ 中:
--- a/gzguts.h
+++ b/gzguts.h
@@ -9,6 +9,7 @@
# endif
# ifdef _FILE_OFFSET_BITS
# undef _FILE_OFFSET_BITS
+# undef _TIME_BITS
# endif
#endif
这是必需的,因为 glibc 标头中有一个断言,当 _TIME_BITS 为 64 但 _FILE_OFFSET_BITS 不是 64 时会出错。
新发布的 zlib 1.3 版本包含上述补丁(https://github.com/madler/zlib/commit/a566e156b3fa07b566ddbf6801b517a9dba04fa3)。
我注意到的一件事是,可以从其网站下载的预编译 ARM 工具链与内核 v4.20.13 的 Linux 内核头文件捆绑在一起。在某些情况下,这些旧标头与 _TIME_BITS=64 不兼容,例如 SO_TIMESTAMP/SCM_TIMESTAMP 的使用,因为这些旧标头定义了不正确的(旧)整数。我在运行 btmon 记录器时通过看到损坏的时间戳注意到了这一点。我决定使用更新的 Linux 内核标头构建自己的工具链,目标是我实际使用的 Linux 内核版本。
幸运的是,由于自动构建脚本和 ARM 工具链每个版本提供的说明,从头开始构建工具链相对简单,可以通过单击相关下载部分底部的“版本说明”链接找到这些说明。这些说明可在“使用 Linaro 的 ABE 从源构建 Linux 托管工具链”下找到。该示例适用于
arm-gnu-toolchain-aarch64-none-elf
,但相应的说明也适用于 arm-gnu-toolchain-arm-none-linux-gnueabihf
。
在下载的manifest文件中,我将
linux_revision=v4.20.13
更改为linux_revision=v6.3
(这是我的目标内核版本)并删除了linux_md5sum
行(我懒得找出校验和)。由于一些非常奇怪的原因,示例清单中的 gcc_stage2_flags
与预编译发布的二进制文件中使用的明显不同。值得注意的是,由于示例清单文件中的 --disable-libatomic
,libatomic 未包含在内。但许多 buildroot 包都需要 libatomic,例如需要对大于 8 字节的对象执行“原子操作”,或者恰好链接到 libatomic.so 的包。为了更好地与二进制版本保持一致,我从 --disable-libatomic --without-cloog --without-isl --disable-libgomp --disable-libquadmath
中删除了 gcc_stage2_flags
(但没有触及 gcc_stage1_flags
)。用这个新工具链替换预编译的工具链后,btmon 现在显示正确的时间戳。
再次更新: