Clang的“ -z”选项是什么,为什么需要它?

时间:2019-10-25 06:52:44

标签: c macos linker clang

考虑以下Clang特定于链接器的选项:

-Wl,<arg>                Pass the comma separated arguments in <arg> to the linker
-Xlinker <arg>           Pass <arg> to the linker
-z <arg>                  Pass -z <arg> to the linker

Pass -z <arg> to the linker是什么意思,-z <arg>-Xlinker <arg>有何区别?

我有时会看到-z <arg>-Wl,<arg>一起使用,例如:

-Wl,-z,norelro

但是,如果-Wl的参数仅应以逗号分隔,为什么需要这样做?

1 个答案:

答案 0 :(得分:6)

  

为什么-z与-Wl一起使用

以下3个命令完全相同

clang main.c -o a.out -Wl,-z,norelro
clang main.c -o a.out -z norelro
clang main.c -o a.out -Xlinker -z -Xlinker norelro

它们都在最终链接阶段将-z norelro传递给链接器。

第一种形式是许多编译器的标准形式。第二种形式稍短一些,但实际上不应该使用(因为使用“标准”形式总是更好)。仅支持第三种形式以与GCC兼容。这是不必要的冗长。

更新

  

我们不能只写-Wl,norelro

否:会将“裸” norelro选项传递给链接器,该链接器会将其视为输入文件,并且会抱怨不存在这样的输入文件。 (显然)传递-z norelro与仅传递norelro之间是有区别的。

  

还考虑使用clang ./noaslr.c -Wl,-z,-no_pie ...

那只是一个伪指令。 -no-pie 一个链接器选项,不应以-z作为前缀。对于-z选项,它也是不是有效选项值。

更新2:

  

在哪里可以看到-z链接器选项的可能值?

在您要定位的操作系统上的ld 手册页中。例如,在Linux上,最新的BFD ld understands具有以下-z选项:bndpltcall-nop-prefix=...combreloc等,等等。< / p>

  

此外,您有什么线索为什么macOS上的man ld不显示-z链接器选项?

可能是因为它根本不支持该选项。