Commit Graph

98 Commits

Author SHA1 Message Date
Jez Ng 001ba65375 [lld-macho] De-templatize mach_header operations
@thakis pointed out that `mach_header` and `mach_header_64`
actually have the same set of (used) fields, with the 64-bit version
having extra padding. So we can access the fields we need using the
single `mach_header` type instead of using templates to switch between
the two.

I also spotted a potential issue where hasObjCSection tries to parse a
file w/o checking if it does indeed match the target arch... As such,
I've added a quick magic number check to ensure we don't access invalid
memory during `findCommand()`.

Addresses PR50180.

Reviewed By: #lld-macho, thakis

Differential Revision: https://reviews.llvm.org/D101724
2021-05-03 18:31:23 -04:00
Jez Ng 05c5363b39 [lld-macho] Parse & emit the N_ARM_THUMB_DEF symbol flag
Eventually we'll use this flag to properly handle bl/blx
opcodes.

Reviewed By: #lld-macho, gkm

Differential Revision: https://reviews.llvm.org/D101558
2021-04-30 16:17:26 -04:00
Greg McGary 465204d63a [lld-macho][NFC] define more strings in section_names:: and segment_names::
As preparation for a subsequent diff that implements builtin section renaming, define more `constexpr` strings in namespaces `lld::macho::segment_names` and `lld::macho::section_names`, and use them to replace string literals.

Differential Revision: https://reviews.llvm.org/D101393
2021-04-27 17:48:45 -07:00
Nico Weber de266ce4f9 [lld/mac] Don't assert when using -exported_symbol with private symbol
When I added this assert in D93609, it asserted that a symbol that
is privateExtern is also isExternal().

In D98381 the privateExtern check moved into shouldExportSymbol()
but the assert didn't -- now it checked that _every_ non-exported
symbol is isExternal(), which isn't true. Move the assert into the
privateExtern check where it used to be.

Fixes PR50098.

Differential Revision: https://reviews.llvm.org/D101223
2021-04-24 10:21:51 -04:00
Jez Ng 035eb6d154 [lld-macho]][nfc] Fix some typos + rephrase a comment
I was a bit confused by the comment because I thought that "Tests
that..." was describing the tests contained within the same file.

Reviewed By: #lld-macho, thakis

Differential Revision: https://reviews.llvm.org/D101160
2021-04-23 18:05:48 -04:00
Jez Ng 2618eaf614 [lld-macho][nfc] Clean up some constructor declarations
Remove unnecessary default ctor + add `explicit` to others
2021-04-22 18:25:44 -04:00
Nico Weber c1b2a7bfbf [lld/mac] make a few "named parameter comments" more consistent
Most of LLVM and almost all of lld/MachO uses `/*foo=*/bar` style.
No behavior change.
2021-04-22 10:48:03 -04:00
Jez Ng ed4a4e3312 [lld-macho][nfc] Add accessors for commonly-used PlatformInfo fields
As discussed here: https://reviews.llvm.org/D100523#inline-951543

Reviewed By: #lld-macho, thakis, alexshap

Differential Revision: https://reviews.llvm.org/D100978
2021-04-21 15:43:56 -04:00
Jez Ng ab9c21bbab [lld-macho] Support LC_ENCRYPTION_INFO
This load command records a range spanning from the end of the load
commands to the end of the `__TEXT` segment. Presumably the kernel will encrypt
all this data.

Reviewed By: #lld-macho, thakis

Differential Revision: https://reviews.llvm.org/D100973
2021-04-21 13:39:56 -04:00
Alexander Shaposhnikov 5c835e1ae5 [lld][MachO] Add support for LC_VERSION_MIN_* load commands
This diff adds initial support for the legacy LC_VERSION_MIN_* load commands.

Test plan: make check-lld-macho

Differential revision: https://reviews.llvm.org/D100523
2021-04-21 05:41:14 -07:00
Jez Ng bb0e1ae7c4 [lld-macho] Add separator to error message 2021-04-16 17:01:14 -04:00
Jez Ng ca6751043d [lld-macho] Initial groundwork for -bitcode_bundle
This diff creates an empty XAR file and copies it into
`__LLVM,__bundle`. Follow-up work will actually populate the contents of
that XAR.

Reviewed By: #lld-macho, gkm

Differential Revision: https://reviews.llvm.org/D100650
2021-04-16 16:47:14 -04:00
Jez Ng c23b92acd0 [lld-macho] Support -add_ast_path
Swift builds seem to use it. All it requires is emitting the
corresponding paths as STABS.

Fixes llvm.org/PR49385.

Reviewed By: clayborg

Differential Revision: https://reviews.llvm.org/D100076
2021-04-08 14:12:55 -04:00
Jez Ng 174deb0539 [lld-macho] clang-format cleanup
find . -type f -name "*.cpp" -o -name "*.h" | xargs clang-format -i
2021-04-06 14:26:13 -04:00
Jez Ng 817d98d841 [lld-macho][nfc] Refactor in preparation for 32-bit support
The main challenge was handling the different on-disk structures (e.g.
`mach_header` vs `mach_header_64`). I tried to strike a balance between
sprinkling `target->wordSize == 8` checks everywhere (branchy = slow, and ugly)
and templatizing everything (causes code bloat, also ugly). I think I struck a
decent balance by judicious use of type erasure.

Note that LLD-ELF has a similar architecture, though it seems to use more templating.

Linking chromium_framework takes about the same time before and after this
change:

      N           Min           Max        Median           Avg        Stddev
  x  20          4.52          4.67         4.595        4.5945   0.044423204
  +  20           4.5          4.71         4.575         4.582   0.056344803
  No difference proven at 95.0% confidence

Reviewed By: #lld-macho, oontvoo

Differential Revision: https://reviews.llvm.org/D99633
2021-04-02 18:46:39 -04:00
Alexander Shaposhnikov f6ad045366 [lld][MachO] Make emitEndFunStab independent from .subsections_via_symbols
This diff addresses FIXME in SyntheticSections.cpp and removes
the dependency of emitEndFunStab on .subsections_via_symbols.

Test plan: make check-lld-macho

Differential revision: https://reviews.llvm.org/D99054
2021-04-01 17:48:09 -07:00
Vy Nguyen 6c1ae8f2dc [lld-macho][nfc] Fixed typo in comment
Missed this one from https://reviews.llvm.org/D97007?id=331759#inline-930034

Differential Revision: https://reviews.llvm.org/D98973
2021-03-19 14:19:36 -04:00
Vy Nguyen 66f340051a [lld-macho] Define __mh_*_header synthetic symbols.
Bug: https://bugs.llvm.org/show_bug.cgi?id=49290

    Differential Revision: https://reviews.llvm.org/D97007
2021-03-19 14:14:40 -04:00
Greg McGary 74b888baad [lld-macho][NFC] Minor refactor of Writer::run()
Move some functions closer to their uses. Move detailed address-assignment logic out of the otherwise abstract `Writer::run()`. This prepares the ground for a diff to implement branch range extension thunks.

* `SyntheticSections.cpp`
 ** move `needsBinding()` and `prepareBranchTarget()` into `Writer.cpp`
 ** move `addNonLazyBindingEntries()` adjacent to its use.

* `Writer.cpp`
 ** move address-assignment logic from `Writer::run()` into new function `Writer::assignAddresses()`
 ** move `needsBinding()` and `prepareBranchTarget()` from `SyntheticSections.cpp`

* `Target.h`
** remove orphaned decls of `prepareSymbolRelocation()` and `validateRelocationInfo()` which were moved to other files in earlier diffs.

Differential Revision: https://reviews.llvm.org/D98795
2021-03-17 15:13:43 -07:00
Greg McGary db1e845a96 [lld-macho] Handle error cases properly for -exported_symbol(s_list)
This fixes defects in D98223 [lld-macho] implement options -(un)exported_symbol(s_list):
* disallow export of hidden symbols
* verify that whitelisted literal names are defined in the symbol table
* reflect export-status overrides in `nlist` attribute of `N_EXT` or `N_PEXT`

Thanks to @thakis for raising these issues

Differential Revision: https://reviews.llvm.org/D98381
2021-03-16 21:20:39 -07:00
Jez Ng 04eec6f881 [lld-macho][nfc] Move list of section names into InputSection.h
They were previously in SyntheticSections.h, but now there are
a bunch of non-synthetic section names in the list.

Also renamed `__functionStarts` to `__func_starts` for uniformity with
other section names + keeps the name under 16 characters (in case we ever
want to write it out as a real section).

Reviewed By: #lld-macho, compnerd

Differential Revision: https://reviews.llvm.org/D98586
2021-03-13 17:41:50 -05:00
Jez Ng d8283d9ddc [lld-macho][nfc] Give every SyntheticSection a fake InputSection
Previously, it was difficult to write code that handled both synthetic
and regular sections generically. We solve this problem by creating a
fake InputSection at the start of every SyntheticSection.

This refactor allows us to handle DSOHandle like a regular Defined
symbol (since Defined symbols must be attached to an InputSection), and
paves the way for supporting `__mh_*header` symbols. Additionally, it
simplifies our binding/rebase code.

I did have to extend Defined a little -- it now has a `linkerInternal`
flag, to indicate that `___dso_handle` should not be in the final symbol
table.

I've also added some additional testing for `___dso_handle`.

Reviewed By: #lld-macho, oontvoo

Differential Revision: https://reviews.llvm.org/D98545
2021-03-12 17:26:27 -05:00
Jez Ng 1752f28506 [lld-macho][nfc] Remove `MachO::` prefix where possible
Previously, SyntheticSections.cpp did not have a top-level `using namespace
llvm::MachO` because it caused a naming conflict: `llvm::MachO::Symbol` would
collide with `lld::macho::Symbol`.

`MachO::Symbol` represents the symbols defined in InterfaceFiles (TBDs). By
moving the inclusion of InterfaceFile.h into our .cpp files, we can avoid this
name collision in other files where we are only dealing with LLD's own symbols.

Along the way, I removed all unnecessary "MachO::" prefixes in our code.

Cons of this approach: If TextAPI/MachO/Symbol.h gets included via some other
header file in the future, we could run into this collision again.

Alternative 1: Have either TextAPI/MachO or BinaryFormat/MachO.h use a different
namespace. Most of the benefit of `using namespace llvm::MachO` comes from being
able to use things in BinaryFormat/MachO.h conveniently; if TextAPI was under a
different (and fully-qualified) namespace like `llvm::tapi` that would solve our
problems. Cons: lots of files across llvm-project will need to be updated, and
folks who own the TextAPI code need to agree to the name change.

Alternative 2: Rename our Symbol to something like `LldSymbol`. I think this is
ugly.

Personally I think alternative #1 is ideal, but I'm not sure the effort to do it is
worthwhile, this diff's halfway solution seems good enough to me. Thoughts?

Reviewed By: #lld-macho, oontvoo, MaskRay

Differential Revision: https://reviews.llvm.org/D98149
2021-03-11 13:28:08 -05:00
Greg McGary 98fe9e41f7 [lld-macho][NFC] add const to pointer/reference induction variables of range-based for loops
Pointer and reference induction variables of range-based for loops are often const, and code authors often lax about qualifying them.

Differential Revision: https://reviews.llvm.org/D98317
2021-03-10 12:07:31 -08:00
Nico Weber 1aafaaca67 [lld/mac] Implement support for -mark_dead_strippable_dylib
lld doesn't read MH_DEAD_STRIPPABLE_DYLIB to strip dead dylibs yet,
but now it can produce dylibs with it set.

While here, also switch an existing test that looks only at the main Mach-O
header from --all-headers to --private-header.

Differential Revision: https://reviews.llvm.org/D98262
2021-03-10 08:57:46 -05:00
Greg McGary fdc0c21973 [lld-macho][NFC] when reasonable, replace auto keyword with type names
lld policy discourages `auto`. Replace it with a type name whenever reasonable. Retain `auto` to avoid ...
* redundancy, as for decls such as `auto *t = mumble_cast<TYPE *>` or similar that specifies the result type on the RHS
* verbosity, as for iterators
* gratuitous suffering, as for lambdas

Along the way, add `const` when appropriate.

Note: a future diff will ...
* add more `const` qualifiers
* remove `opt::` when we are already `using llvm::opt`

Differential Revision: https://reviews.llvm.org/D98313
2021-03-09 22:08:32 -08:00
Greg McGary 06c4aadeb6 [lld-macho] implement options -(un)exported_symbol(s_list)
Implement command-line options to alter a dylib's exported-symbols list:
* `-exported_symbol*` options override the default export list. The export list is compiled according to the command-line option(s) only.
* `-unexported_symbol*` options hide otherwise public symbols.
* `-*exported_symbol PATTERN` options specify a single literal or glob pattern.
* `-*exported_symbols_list FILE` options specify a file containing a series of lines containing symbol literals or glob patterns. Whitespace and `#`-prefix comments are stripped.

Note: This is a simple implementation of the primary use case. ld64 has much more complexity surrounding interactions with other options, many of which are obscure and undocumented. We will start simple and complexity as necessary.

Differential Revision: https://reviews.llvm.org/D98223
2021-03-09 18:43:39 -08:00
Alexander Shaposhnikov 9afdd3607a [lld][MachO] Add support for LC_FUNCTION_STARTS
Add first bits for emitting LC_FUNCTION_STARTS.

This is a recommit of f344dfeb with the adjusted test
which should address build bots breakages.

Test plan: make check-all

Differential revision: https://reviews.llvm.org/D97260
2021-03-08 22:08:36 -08:00
Alexander Shaposhnikov 1b0819e325 Revert "[lld][MachO] Add support for LC_FUNCTION_STARTS"
This reverts commit f344dfebdb.
2021-03-08 21:10:10 -08:00
Alexander Shaposhnikov f344dfebdb [lld][MachO] Add support for LC_FUNCTION_STARTS
Add first bits for emitting LC_FUNCTION_STARTS.

Test plan: make check-all

Differential revision: https://reviews.llvm.org/D97260
2021-03-08 20:42:24 -08:00
Jez Ng 3c19b4f34d [lld-macho] Skip over symbols in un-parsed debug info sections
clang appears to emit symbols in `__debug_aranges`, at least
for arm64... in the examples I've seen, it doesn't seem like those
symbols are referenced outside of `__DWARF`, so I think they're safe to
ignore. But hopefully @clayborg can confirm.

Reviewed By: clayborg

Differential Revision: https://reviews.llvm.org/D98073
2021-03-05 17:24:32 -05:00
Jez Ng 55a32812fa [lld-macho] Filter TAPI re-exports by target
Previously, we were loading re-exports without checking whether
they were compatible with our target. Prior to {D97209}, it meant that
we were defining dylib symbols that were invalid -- usually a silent
failure unless our binary actually used them. D97209 exposed this as an
explicit error.

Along the way, I've extended our TAPI compatibility check to cover the
platform as well, instead of just checking the arch. To this end, I've
replaced MachO::Architecture with MachO::Target in our Config struct.

Reviewed By: #lld-macho, oontvoo

Differential Revision: https://reviews.llvm.org/D97867
2021-03-04 14:36:47 -05:00
Mikael Holmen 85b67d5fa9 [lld][MachO] Silence "enumeral and non-enumeral type" warning from gcc
gcc complained with

[1110/1140] Building CXX object tools/lld/MachO/CMakeFiles/lldMachO2.dir/SyntheticSections.cpp.o
../../lld/MachO/SyntheticSections.cpp: In function 'int16_t ordinalForDylibSymbol(const lld::macho::DylibSymbol&)':
../../lld/MachO/SyntheticSections.cpp:287:14: warning: enumeral and non-enumeral type in conditional expression [-Wextra]
  286 |   return config->namespaceKind == NamespaceKind::flat || dysym.isDynamicLookup()
      |          ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  287 |              ? MachO::BIND_SPECIAL_DYLIB_FLAT_LOOKUP
      |              ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  288 |              : dysym.getFile()->ordinal;
      |              ~~~~~~~~~~~~~~~~~~~~~~~~~~
2021-03-03 10:39:35 +01:00
Nico Weber 8174f33dc9 [lld/mac] Add support for -flat_namespace
-flat_namespace makes lld emit binaries that use name lookup that's more in
line with other POSIX systems: Instead of looking up symbols as (dylib,name)
pairs by dyld, they're instead looked up just by name.

-flat_namespace has three effects:

1. MH_TWOLEVEL and MH_NNOUNDEFS are no longer set in the Mach-O header
2. All symbols use BIND_SPECIAL_DYLIB_FLAT_LOOKUP as ordinal
3. When a dylib is added to the link, its dependent dylibs are also added,
   so that lld can verify that no undefined symbols remain at the end of
   a link with -flat_namespace. These transitive dylibs are added for symbol
   resolution, but they are not emitted in LC_LOAD_COMMANDs.

-undefined with -flat_namespace still isn't implemented. Before this change,
it was impossible to hit that combination because -flat_namespace caused a
diagnostic. Now that it no longer does, emit a dedicated temporary diagnostic
when both flags are used.

Differential Revision: https://reviews.llvm.org/D97641
2021-03-01 15:25:10 -05:00
Nico Weber 860e862f34 [lld/mac] Simplify encodeDylibOrdinal() a bit
Only one of the two callers used the lastBinding parameter, so
do that work at that one call site. Extract a ordinalForDylibSymbol()
helper to make this tidy.

No behavior change.

Differential Revision: https://reviews.llvm.org/D97597
2021-02-28 09:16:45 -05:00
Nico Weber cafb6cd10c [lld/mac] Add some support for dynamic lookup symbols, and implement -U
Dynamic lookup symbols are symbols that work like dynamic symbols
in ELF: They're not bound to a dylib like normal Mach-O twolevel lookup
symbols, but they live in a global pool and dyld resolves them against
exported symbols from all loaded dylibs.

This adds support for dynamical lookup symbols to lld/mac. They are
represented as DylibSymbols with file set to nullptr.

This also uses this support to implement the -U flag, which makes
a specific symbol that's undefined at the end of the link a
dynamic lookup symbol.

For -U, it'd be sufficient to just to a pass over remaining undefined symbols
at the end of the link and to replace them with dynamic lookup symbols then.
But I'd like to use this code to implement flat_namespace too, and that will
require real support for resolving dynamic lookup symbols in SymbolTable. So
this patch adds this now already.

While writing tests for this, I noticed that we didn't set N_WEAK_DEF in the
symbol table for DylibSymbols, so this fixes that too.

Differential Revision: https://reviews.llvm.org/D97521
2021-02-26 16:50:53 -05:00
Greg McGary 151990dd94 [lld-macho] add code signature for native arm64 macOS
Differential Revision: https://reviews.llvm.org/D96164
2021-02-24 17:05:23 -08:00
Vy Nguyen 5a856f5b44 Reland [lld-macho]Implement bundle_loader
Reland 1a0afcf518
  https://reviews.llvm.org/D95913

New change: fix UB bug caused by copying empty path/name. (since the executable does not have a name)
2021-02-22 14:05:12 -05:00
Jez Ng 8c4638c367 [lld-macho] Clean up comments 2021-02-22 12:13:17 -05:00
Jez Ng 5bfdbdeb40 [lld-macho] Fix cpuSubtype for non-x86_64 archs
dyld on iOS will complain if the LIB64 bit is set.

Reviewed By: #lld-macho, thakis

Differential Revision: https://reviews.llvm.org/D96565
2021-02-22 12:13:17 -05:00
Vitaly Buka c17547df44 Revert "Implement -bundle_loader"
D95913 passes null pointer into memcpy

This reverts commit 1a0afcf518.
2021-02-19 17:40:07 -08:00
Vy Nguyen 1a0afcf518 Implement -bundle_loader
Differential Revision: https://reviews.llvm.org/D95913

Usage: -bundle_loader <executable>
This option specifies the executable that will load the build output file being linked.
When building a bundle, users can use the --bundle_loader  to specify an executable
that contains symbols referenced, but not implemented in the bundle.
2021-02-18 16:11:37 -05:00
Greg McGary 87104faac4 [lld-macho] Add ARM64 target arch
This is an initial base commit for ARM64 target arch support. I don't represent that it complete or bug-free, but wish to put it out for review now that some basic things like branch target & load/store address relocs are working.

I can add more tests to this base commit, or add them in follow-up commits.

It is not entirely clear whether I use the "ARM64" (Apple) or "AArch64" (non-Apple) naming convention. Guidance is appreciated.

Differential Revision: https://reviews.llvm.org/D88629
2021-02-08 18:14:07 -07:00
Jez Ng 525bfa10ec [lld-macho] Emit personalities in compact unwind
Note that there is a triple indirection involved with
personalities and compact unwind:

1. Two bits of each CU encoding are used as an offset into the
   personality array.
2. Each entry of the personality array is an offset from the image base.
   The resulting address (after adding the image base) should point within the
   GOT.
3. The corresponding GOT entry contains the actual pointer to the
   personality function.

To further complicate things, when the personality function is in the
object file (as opposed to a dylib), its references in
`__compact_unwind` may refer to it via a section + offset relocation
instead of a symbol relocation. Since our GOT implementation can only
create entries for symbols, we have to create a synthetic symbol at the
given section offset.

Reviewed By: clayborg

Differential Revision: https://reviews.llvm.org/D95809
2021-02-08 13:47:59 -05:00
Greg McGary c3e4f3b231 [lld-macho] Fix alignment & layout to match ld64 and satisfy kernel & codesign
The Mach kernel & codesign on arm64 macOS has strict requirements for alignment and sequence of segments and sections. Dyld probably is just as picky, though kernel & codesign reject malformed Mach-O files before dyld ever has a chance.

I developed this diff by incrementally changing alignments & sequences to match the output of ld64. I stopped when my hello-world test program started working: `codesign --verify` succeded, and `execve(2)` didn't immediately fail with `errno == EBADMACHO` = `"Malformed Mach-O file"`.

Differential Revision: https://reviews.llvm.org/D94935
2021-02-05 17:22:03 -07:00
Jez Ng 163dcd8513 [lld-macho] Associate each Symbol with an InputFile
This makes our error messages more informative. But the bigger motivation is for
LTO symbol resolution, which will be in an upcoming diff. The changes in this
one are largely mechanical.

Reviewed By: #lld-macho, smeenai

Differential Revision: https://reviews.llvm.org/D94316
2021-02-03 13:43:47 -05:00
Greg McGary 3a9d2f1488 [lld-macho][NFC] refactor relocation handling
Add per-reloc-type attribute bits and migrate code from per-target file into target independent code, driven by reloc attributes.

Many cleanups

Differential Revision: https://reviews.llvm.org/D95121
2021-02-02 10:54:53 -07:00
Fangrui Song 7916fd71e9 [lld-macho] Fix GCC -Wunused-variable in -DLLVM_ENABLE_ASSERTIONS=off build 2021-01-06 10:58:46 -08:00
Nico Weber 57ffbe020a glld/mac] Don't add names of unreferenced symbols to string table
Before this, a hello world program would contain many many unnecessary
entries in its string table.

No behavior change, just makes the string table in the output smaller
and more like ld64's.

Differential Revision: https://reviews.llvm.org/D93711
2020-12-22 15:52:33 -05:00
Nico Weber 13f439a187 [lld/mac] Implement support for private extern symbols
Private extern symbols are used for things scoped to the linkage unit.
They cause duplicate symbol errors (so they're in the symbol table,
unlike TU-scoped truly local symbols), but they don't make it into the
export trie. They are created e.g. by compiling with
-fvisibility=hidden.

If two weak symbols have differing privateness, the combined symbol is
non-private external. (Example: inline functions and some TUs that
include the header defining it were built with
-fvisibility-inlines-hidden and some weren't).

A weak private external symbol implicitly has its "weak" dropped and
behaves like a regular strong private external symbol: Weak is an export
trie concept, and private symbols are not in the export trie.

If a weak and a strong symbol have different privateness, the strong
symbol wins.

If two common symbols have differing privateness, the larger symbol
wins. If they have the same size, the privateness of the symbol seen
later during the link wins (!) -- this is a bit lame, but it matches
ld64 and this behavior takes 2 lines less to implement than the less
surprising "result is non-private external), so match ld64.
(Example: `int a` in two .c files, both built with -fcommon,
one built with -fvisibility=hidden and one without.)

This also makes `__dyld_private` a true TU-local symbol, matching ld64.
To make this work, make the `const char*` StringRefZ ctor to correctly
set `size` (without this, writing the string table crashed when calling
getName() on the __dyld_private symbol).

Mention in CommonSymbol's comment that common symbols are now disabled
by default in clang.

Mention in -keep_private_externs's HelpText that the flag only has an
effect with `-r` (which we don't implement yet -- so this patch here
doesn't regress any behavior around -r + -keep_private_externs)). ld64
doesn't explicitly document it, but the commit text of
http://reviews.llvm.org/rL216146 does, and ld64's
OutputFile::buildSymbolTable() checks `_options.outputKind() ==
Options::kObjectFile` before calling `_options.keepPrivateExterns()`
(the only reference to that function).

Fixes PR48536.

Differential Revision: https://reviews.llvm.org/D93609
2020-12-21 21:23:33 -05:00