我想知道在移动 C 程序时可能遇到的问题,例如。服务器进程从 Tru64 Unix 到 Linux 64 位,为什么?由于两者都是 64 位平台,程序需要进行哪些可能的修改,或者只在新环境中重新编译源代码?我有点困惑,在我开始工作之前我必须知道。
3 回答
我在 90 年代初花了很多时间(天哪,我觉得自己老了……)将 32 位代码移植到Alpha 架构。当它被称为 OSF/1 时,它又回来了。
从 Alpha 到 x86_64 时,您不太可能遇到与位宽相关的任何困难。
例如,开发人员更清楚假设 导致的问题sizeof(int) == sizeof(void *)
。这是我在将代码移植到 Alpha 时遇到的最常见的问题。
您确实发现差异的地方在于两个系统在符合各种 API 规范(例如 POSIX、XOpen 等)方面的差异。也就是说,这些差异通常很容易解决。
如果 Alpha 代码使用了 SVR4 风格的 API(例如流),那么与使用更多类似 BSD 的 API 相比,您可能会遇到更多困难。
64 位架构只是架构分类的近似值。
理想情况下,您的代码将只对变量的所有描述使用“语义”类型,特别是对于大小size_t
和ptrdiff_t
指针算术以及[u]intXX_t
假定特定宽度的类型。
如果不是这种情况,重点是比较所有标准算术类型(所有整数类型、浮点类型和指针),如果它们在两个平台上映射到相同的概念。如果您发现差异,您就会知道潜在的问题点。
检查两个平台使用的64 位数据模型,大多数 64 位类 Unix 操作系统使用 LP64,因此您的目标平台很可能使用相同的数据模型。在这种情况下,鉴于代码本身可以编译和链接,您应该不会有什么问题。
如果您在两个平台上使用相同的编译器(例如 GCC),您也不必担心不兼容的编译器扩展或未定义或实现定义行为的差异。在任何情况下都应该避免这种行为——即使编译器是相同的,因为它可能在目标架构之间有所不同。如果您没有使用相同的编译器,那么您需要谨慎使用扩展。#pragma 指令是一个特殊的问题,因为允许编译器悄悄地忽略它无法识别的#pragma。
最后,为了编译和链接,C 标准库之外的任何库依赖项都需要在两个平台上都可用。大多数操作系统调用都将可用,因为 Unix 和 Linux 共享相同的 POSIX API。