llvm-objcopy - 对象复制和编辑工具

概要

llvm-objcopy [选项] 输入文件 [输出文件]

描述

llvm-objcopy 是一个用于复制和操作对象的工具。在基本用法中,它会对输入文件进行语义复制到输出文件。如果指定了任何选项,则输出文件可能会在此过程中被修改,例如通过删除节。

如果没有指定输出文件,则输入文件将在原地修改。如果为输入文件指定了“ - ”,则输入将从程序的标准输入流读取。如果为输出文件指定了“ - ”,则输出将写入程序的标准输出流。

如果输入文件是归档文件,则任何请求的操作都将分别应用于每个归档成员。

该工具仍在积极开发中,但在大多数情况下,它可以作为 GNU 的 objcopy 的直接替换。

通用和跨平台选项

以下选项要么与文件格式无关,要么适用于多种文件格式。

向输出文件添加一个用于 <调试文件> 的 .gnu_debuglink 节。

--add-section <节=文件>

向输出文件添加一个名为 <节> 的节,其内容来自 <文件>。对于 ELF 对象,如果名称以“.note”开头,则该节的类型将为 SHT_NOTE。否则,其类型将为 SHT_PROGBITS。可以多次指定此选项以添加多个节。

对于 MachO 对象,<节> 必须格式化为 <段名称>,<节名称>

--binary-architecture <架构>, -B

出于兼容性考虑被忽略。

--disable-deterministic-archives, -U

更新归档成员头文件时使用 UID、GID 和时间戳的真实值。

--discard-all, -x

从输出中删除大多数局部符号。不同的文件格式可能会将此限制为局部符号的子集。例如,ELF 对象中的文件和节符号将不会被丢弃。此外,删除所有调试节。

--dump-section <节>=<文件>

将节 <节> 的内容转储到文件 <文件> 中。可以多次指定此选项以将多个节转储到不同的文件中。 <文件> 与提供给 llvm-objcopy 的输入和输出文件无关,因此仍将执行正常的复制和编辑操作。在转储节之前,不会对节执行任何操作。

对于 MachO 对象,<节> 必须格式化为 <段名称>,<节名称>

--enable-deterministic-archives, -D

复制归档文件时启用确定性模式,即对于归档成员头文件中的 UID、GID 和时间戳字段使用 0。默认情况下启用。

--help, -h

打印命令行选项的摘要。

--only-keep-debug

生成一个调试文件作为输出,该文件仅保留对调试有用的节的内容。

对于 ELF 对象,这会通过将不是 SHT_NOTESHF_ALLOC 节的内容设为 SHT_NOBITS 并尽可能缩小程序头来删除它们。

--only-section <节>, -j

从输出中删除所有节,除了名为 <节> 的节。可以多次指定此选项以保留多个节。

对于 MachO 对象,<节> 必须格式化为 <段名称>,<节名称>

--redefine-sym <旧名称>=<新名称>

将输出文件中名为 <旧名称> 的符号重命名为 <新名称>。可以多次指定此选项以重命名多个符号。

--redefine-syms <文件名>

根据文件 <文件名> 中的描述重命名输出文件中的符号。在文件中,每一行表示一个要重命名的符号,旧名称和新名称之间用空格分隔。开头和结尾的空格将被忽略,与 '#' 后面的任何内容一样。可以多次指定此选项以从多个文件中读取名称。

--regex

如果指定,则其他开关指定的符号和节名称将被视为扩展的 POSIX 正则表达式模式。

--remove-symbol-prefix <前缀>

从每个符号名称的开头删除 <前缀>。对于不以 <前缀> 开头的符号,此操作无效。

--remove-section <节>, -R

从输出中删除指定的节。可以多次指定此选项以同时删除多个节。

对于 MachO 对象,<节> 必须格式化为 <段名称>,<节名称>

--set-section-alignment <节>=<对齐方式>

将节 <节> 的对齐方式设置为 <对齐方式>。可以多次指定此选项以更新多个节。

--set-section-flags <节>=<标志>[,<标志>,...]

根据指定的 <标志> 值设置节 <节> 的输出中的节属性。可以多次指定此选项以更新多个节。

支持的标志名称为 allocloadnoloadreadonlyexcludedebugcodedataromsharecontentsmergestringslarge。并非所有标志对所有对象文件格式或目标架构都有意义。

对于 ELF 对象,这些标志具有以下效果

  • alloc = 添加 SHF_ALLOC 标志。

  • load = 如果该节的类型为 SHT_NOBITS,则将其标记为 SHT_PROGBITS 节。

  • readonly = 如果未指定此标志,则添加 SHF_WRITE 标志。

  • exclude = 添加 SHF_EXCLUDE 标志。

  • code = 添加 SHF_EXECINSTR 标志。

  • merge = 添加 SHF_MERGE 标志。

  • strings = 添加 SHF_STRINGS 标志。

  • contents = 如果该节的类型为 SHT_NOBITS,则将其标记为 SHT_PROGBITS 节。

  • large = 在 x86_64 上添加 SHF_X86_64_LARGE;如果目标架构不是 x86_64,则拒绝。

对于 COFF 对象,这些标志具有以下效果

  • alloc = 添加 IMAGE_SCN_CNT_UNINITIALIZED_DATAIMAGE_SCN_MEM_READ 标志,除非指定了 load 标志。

  • noload = 添加 IMAGE_SCN_LNK_REMOVEIMAGE_SCN_MEM_READ 标志。

  • readonly = 如果未指定此标志,则添加 IMAGE_SCN_MEM_WRITE 标志。

  • exclude = 添加 IMAGE_SCN_LNK_REMOVEIMAGE_SCN_MEM_READ 标志。

  • debug = 添加 IMAGE_SCN_CNT_INITIALIZED_DATAIMAGE_SCN_MEM_DISCARDABLEIMAGE_SCN_MEM_READ 标志。

  • code = 添加 IMAGE_SCN_CNT_CODEIMAGE_SCN_MEM_EXECUTEIMAGE_SCN_MEM_READ 标志。

  • data = 添加 IMAGE_SCN_CNT_INITIALIZED_DATAIMAGE_SCN_MEM_READ 标志。

  • share = 添加 IMAGE_SCN_MEM_SHAREDIMAGE_SCN_MEM_READ 标志。

--strip-all-gnu

从输出中删除所有符号、调试节和重定位。此选项等效于 GNU objcopy--strip-all 开关。

--strip-all, -S

对于 ELF 对象,从输出中删除所有符号和不在段内的非分配节,但 .gnu.warning、.ARM.attribute 节和节名称表除外。

对于 COFF 和 Mach-O 对象,从输出中删除所有符号、调试节和重定位。

--strip-debug, -g

从输出中删除所有调试节。

--strip-symbol <symbol>, -N

从输出中删除所有名为 <symbol> 的符号。可以多次指定以删除多个符号。

--strip-symbols <filename>

从输出中删除所有名称出现在文件 <filename> 中的符号。在文件中,每一行代表一个符号名称,忽略开头和结尾的空格,以及 '#' 之后的任何内容。可以多次指定以从多个文件中读取名称。

--strip-unneeded-symbol <symbol>

从输出中删除所有名为 <symbol> 的符号,这些符号是局部的或未定义的,并且任何重定位都不需要它们。

--strip-unneeded-symbols <filename>

从输出中删除所有名称出现在文件 <filename> 中的符号,如果它们是局部的或未定义的,并且任何重定位都不需要它们。在文件中,每一行代表一个符号名称,忽略开头和结尾的空格,以及 '#' 之后的任何内容。可以多次指定以从多个文件中读取名称。

--strip-unneeded

从输出中删除所有重定位不需要的局部或未定义符号。同时删除所有调试节。

--update-section <name>=<file>

用文件 <file> 中的内容替换节 <name> 的内容。如果节 <name> 是段的一部分,则新内容不能大于现有节。

--version, -V

显示 llvm-objcopy 可执行文件的版本。

--wildcard, -w

允许对与符号相关的标志使用通配符语法。对于与节相关的标志,默认情况下启用。与 –regex 不兼容。

通配符语法允许以下特殊符号

字符

含义

等效

*

任意数量的字符

.*

?

任意单个字符

.

\

转义下一个字符

\

[a-z]

字符类

[a-z]

[!a-z], [^a-z]

否定字符类

[^a-z]

此外,以 '!' 开头的通配符将阻止匹配,即使其他标志匹配也是如此。例如 -w -N '*' -N '!x' 将删除所有符号,除了 x

通配符的顺序无关紧要。例如,-w -N '*' -N '!x'-w -N '!x' -N '*' 相同。

@<FILE>

从响应文件 <FILE> 中读取命令行选项和命令。

ELF 特定选项

以下选项仅针对 ELF 对象实现。如果与其他对象一起使用,llvm-objcopy 将发出错误或静默忽略它们。

--add-symbol <name>=[<section>:]<value>[,<flags>]

向输出符号表中添加一个名为 <name> 的新符号,位于名为 <section> 的节中,值为 <value>。如果未指定 <section>,则该符号将作为绝对符号添加。 <flags> 影响符号属性。可接受的值为

  • global = 该符号将具有全局绑定。

  • local = 该符号将具有局部绑定。

  • weak = 该符号将具有弱绑定。

  • default = 该符号将具有默认可见性。

  • hidden = 该符号将具有隐藏可见性。

  • protected = 该符号将具有受保护的可见性。

  • file = 该符号将是 STT_FILE 符号。

  • section = 该符号将是 STT_SECTION 符号。

  • object = 该符号将是 STT_OBJECT 符号。

  • function = 该符号将是 STT_FUNC 符号。

  • indirect-function = 该符号将是 STT_GNU_IFUNC 符号。

此外,以下标志被接受但被忽略:debugconstructorwarningindirectsyntheticunique-objectbefore

可以多次指定以添加多个符号。

允许 llvm-objcopy 即使它会留下无效的节引用也删除节。任何无效的 sh_link 字段都将设置为零。

--change-section-lma \*{+-}<val>

将非零大小段的 LMA 移动 <val>

--change-section-address <section>{=+-}<val>, --adjust-section-vma

将与 <section> 模式匹配的节的地址更改为指定的值,或将 +<val>/-<val> 应用于当前值。可以多次指定以指定多个模式。每个节仅由一个 --change-section-address 参数修改。如果节名称与多个模式匹配,则应用最右边的更改。对象文件需要是 ET_REL 类型。

--change-start <incr>, --adjust-start

<incr> 添加到程序的起始地址。可以多次指定,在这种情况下,这些值将累积应用。

--compress-debug-sections [<format>]

使用指定的格式压缩输出中的 DWARF 调试节。支持的格式为 zlibzstd。如果省略了 <format>,则使用 zlib

--compress-sections <section>=<format>

使用指定的格式压缩或解压缩由<section>匹配的节。支持的格式包括zlibzstd。指定none用于解压缩。当一个节被多个选项匹配时,最后一个选项优先。以‘!’开头的通配符<section>是不允许的。段内的节不能被(解)压缩。

--decompress-debug-sections

解压缩输出中任何压缩的DWARF调试节。

--discard-locals, -X

从输出中移除以“.L”开头的局部符号。

--extract-dwo

从输出中移除所有不是DWARF .dwo节的节。

--extract-main-partition

从输出中提取主分区。

--extract-partition <name>

从输出中提取名为<name>的分区。

--gap-fill <value>

对于二进制输出,使用<value>而不是零填充节之间的间隙。该值必须是无符号的8位整数。

--globalize-symbol <symbol>

将输出中名为<symbol>的任何已定义符号标记为全局符号。可以多次指定以标记多个符号。

--globalize-symbols <filename>

从文件<filename>中读取名称列表,并将输出中具有这些名称的已定义符号标记为全局符号。在文件中,每一行代表一个符号,忽略开头和结尾的空格,以及“#”后面的任何内容。可以多次指定以从多个文件中读取名称。

--input-target <format>, -I

将输入读取为指定的格式。有关有效<format>值的列表,请参阅支持的格式。如果未指定,llvm-objcopy将尝试自动确定格式。

--keep-file-symbols

即使在其他情况下会被剥离,也保留类型为STT_FILE的符号。

--keep-global-symbol <symbol>, -G

将输出中的所有符号标记为局部符号,除了名为<symbol>的符号。可以多次指定以忽略多个符号。

--keep-global-symbols <filename>

将输出中的所有符号标记为局部符号,除了在文件<filename>中命名的符号。在文件中,每一行代表一个符号,忽略开头和结尾的空格,以及“#”后面的任何内容。可以多次指定以从多个文件中读取名称。

--keep-section <section>

从输出中移除节时,不要移除名为<section>的节。可以多次指定以保留多个节。

--keep-symbol <symbol>, -K

从输出中移除符号时,不要移除名为<symbol>的符号。可以多次指定以保留多个符号。

--keep-symbols <filename>

从输出中移除符号时,不要移除在文件<filename>中命名的符号。在文件中,每一行代表一个符号,忽略开头和结尾的空格,以及“#”后面的任何内容。可以多次指定以从多个文件中读取名称。

--localize-hidden

将输出中所有具有隐藏或内部可见性的符号标记为局部符号。

--localize-symbol <symbol>, -L

将输出中任何名为<symbol>的已定义非通用符号标记为局部符号。可以多次指定以将多个符号标记为局部符号。

--localize-symbols <filename>

从文件<filename>中读取名称列表,并将输出中具有这些名称的已定义非通用符号标记为局部符号。在文件中,每一行代表一个符号,忽略开头和结尾的空格,以及“#”后面的任何内容。可以多次指定以从多个文件中读取名称。

--new-symbol-visibility <visibility>

指定使用二进制输入或--add-symbol时自动创建的符号的可见性。有效选项包括:

  • 默认

  • 隐藏

  • 内部

  • 受保护

默认为默认

--no-verify-note-sections

添加注释节时,不要验证节格式是否有效。

--output-target <format>, -O

将输出写入指定的格式。有关有效<format>值的列表,请参阅支持的格式。如果未指定,则输出格式假定与为--input-target指定的值相同,或者如果该选项也未指定,则为输入文件的格式。

--pad-to <address>

对于二进制输出,使用零或--gap-fill指定的值将输出填充到加载地址<address>

--prefix-alloc-sections <prefix>

在输出中所有可分配节的名称前面添加<prefix>

--prefix-symbols <prefix>

在输出中每个符号名称前面添加<prefix>

--preserve-dates, -p

保留输出中的访问和修改时间戳。

--rename-section <old>=<new>[,<flag>,...]

将输出中名为<old>的节重命名为<new>,并应用任何指定的<flag>值。有关支持的标志列表,请参阅--set-section-flags。可以多次指定以重命名多个节。

--set-section-type <section>=<type>

将节区类型 <section> 设置为整数 <type>。可以多次指定以更新多个节区。

--set-start <addr>

将输出的起始地址设置为 <addr>。覆盖之前指定的任何 --change-start--adjust-start 选项。

--set-symbol-visibility <symbol>=<visibility>

将符号的可见性更改为指定的值。

--set-symbols-visibility <filename>=<visibility>

从 <filename> 读取符号列表,并将它们的可见性更改为指定的值。可见性值:default、internal、hidden、protected。

--skip-symbol <symbol>

在执行其他可以更改符号名称、绑定或可见性的选项时,不更改符号 <symbol> 的参数。

--skip-symbols <filename>

在执行其他可以更改符号名称、绑定或可见性的选项时,不更改文件中 <filename> 指定的符号的参数。在文件中,每一行表示一个符号,开头和结尾的空格将被忽略,‘#’后面的内容也将被忽略。可以多次指定以从多个文件中读取名称。

--split-dwo <dwo-file>

等效于使用 llvm-objcopy 运行 --extract-dwo 并将 <dwo-file> 作为输出文件,不使用其他选项,然后对输入文件使用 --strip-dwo

--strip-dwo

从输出中删除所有 DWARF .dwo 节区。

--strip-non-alloc

从输出中删除所有不在段中的不可分配节区。

--strip-sections

从输出中删除所有节区头和所有不在段中的节区数据。请注意,许多工具将无法使用没有节区头的对象。

--target <format>, -F

等效于对指定格式使用 --input-target--output-target。有关有效 <format> 值的列表,请参见 SUPPORTED FORMATS

--verify-note-sections

添加注释节区时,验证节区格式是否有效。默认情况下启用。

--weaken-symbol <symbol>, -W

将名为 <symbol> 的全局符号标记为输出中的弱符号。可以多次指定以将多个符号标记为弱符号。

--weaken-symbols <filename>

从文件 <filename> 读取名称列表,并将具有这些名称的全局符号标记为输出中的弱符号。在文件中,每一行表示一个符号,开头和结尾的空格将被忽略,‘#’后面的内容也将被忽略。可以多次指定以从多个文件中读取名称。

--weaken

将输出中所有已定义的全局符号标记为弱符号。

MACH-O 特定选项

--keep-undefined

保留未定义的符号,即使它们会被剥离。

COFF 特定选项

--subsystem <name>[:<version>]

设置 PE 子系统,并可选地设置子系统版本。

支持的格式

llvm-objcopy 当前支持以下值用于 --input-target--output-target--target 选项。为了与 GNU objcopy 兼容,所有值都是 bfdnames。

  • binary

  • ihex

  • elf32-i386

  • elf32-x86-64

  • elf64-x86-64

  • elf32-iamcu

  • elf32-littlearm

  • elf64-aarch64

  • elf64-littleaarch64

  • elf32-littleriscv

  • elf64-littleriscv

  • elf32-powerpc

  • elf32-powerpcle

  • elf64-powerpc

  • elf64-powerpcle

  • elf32-bigmips

  • elf32-ntradbigmips

  • elf32-ntradlittlemips

  • elf32-tradbigmips

  • elf32-tradlittlemips

  • elf64-tradbigmips

  • elf64-tradlittlemips

  • elf32-sparc

  • elf32-sparcel

  • elf32-hexagon

  • elf32-loongarch

  • elf64-loongarch

  • elf64-s390

以下格式受 llvm-objcopy 支持,仅用于 --output-target

  • srec

此外,除了 binaryihexsrec 之外的所有目标都可以使用 -freebsd 作为后缀。

二进制输入和输出

如果将 binary 用作 --input-target 的值,则输入文件将作为数据节嵌入到 ELF 可重定位对象中,符号 _binary_<file_name>_start_binary_<file_name>_end_binary_<file_name>_size 分别表示数据的开始、结束和大小,其中 <file_name> 是命令行上指定的输入文件的路径,非字母数字字符转换为 _

如果将 binary 用作 --output-target 的值,则输出文件将是一个原始二进制文件,包含输入文件的内存映像。符号和重定位信息将被丢弃。映像将从输出中第一个可加载节区的地址开始。

退出状态

llvm-objcopy 如果发生错误,则退出时返回非零退出代码。否则,它退出时返回代码 0。

错误

要报告错误,请访问 <https://github.com/llvm/llvm-project/labels/tools:llvm-objcopy/strip/>。

--input-target--target 存在一个已知问题,导致只有 binaryihex 格式才会生效。其他值将被忽略,并且 llvm-objcopy 将尝试猜测输入格式。

另请参阅

llvm-strip(1)