当设置框架的
DYLIB_CURRENT_VERSION
大于65535时,Xcode会发出警告:
警告构建:截断 -current_version 以适应旧的 mach-o 格式使用的 32 位空间
如果当前版本空间定义为 32 位整数,为什么 Xcode 想要截断大于 16 位最大值的版本?
这是一个错误还是需要调整一些其他设置才能消除此警告?
我使用的Xcode版本是14.0.1。
因为这 32 位被分割了:
uint32_t version; /* X.Y.Z is encoded in nibbles xxxx.yy.zz */
这是来自不同的加载命令,但 Mach-O 中的所有 32 位版本字段都是这样工作的。这些能代表的最高版本是
65535.255.255
。
还要注意,从 LLVM 的角度来看,这可能是“旧的”,但 Mach-O 标头中的大多数结构和加载命令仍然使用 32 位版本,没有可用的替代版本,包括“当前”和“兼容”版本动态库。唯一的例外似乎是
LC_SOURCE_VERSION
/struct source_version_command
,它使用 64 位字段:
uint64_t version; /* A.B.C.D.E packed as a24.b10.c10.d10.e10 */
来自
ld
手册页:
-current_version number
指定库的当前版本号。库的用户可以通过编程方式获取库的当前版本,因此可以准确确定正在使用的库的版本。数字的格式为 X[.Y[.Z]],其中 X 必须是正非零数减去 小于或等于 65535,.Y 和 .Z 是可选的,如果存在,则必须是小于或等于 255 的非负数。如果未指定版本号,则其值为 0。此选项也称为-dylib_current_version 用于兼容性。
就我而言,我通过将版本设置为
1.3.268
来触发此警告。
-current_version 1.3.268
由于当我在二进制文件上运行
otool
时,268 大于 255,因此它的上限为 255
。
$ otool -L build/loader/libfoobar.dylib
libfoobar.1.dylib (compatibility version 1.0.0, current version 1.3.255)
^
这就是为什么
ld
警告您这一点。这可能会给您图书馆的用户带来困惑。