https://github.com/michaeleisel/zld Skip to content Sign up * Why GitHub? Features - + Mobile - + Actions - + Codespaces - + Packages - + Security - + Code review - + Project management - + Integrations - + GitHub Sponsors - + Customer stories- * Team * Enterprise * Explore + Explore GitHub - Learn and contribute + Topics - + Collections - + Trending - + Learning Lab - + Open source guides - Connect with others + The ReadME Project - + Events - + Community forum - + GitHub Education - + GitHub Stars program - * Marketplace * Pricing Plans - + Compare plans - + Contact Sales - + Education - [ ] [search-key] * # In this repository All GitHub | Jump to | * No suggested jump to results * # In this repository All GitHub | Jump to | * # In this user All GitHub | Jump to | * # In this repository All GitHub | Jump to | Sign in Sign up {{ message }} michaeleisel / zld * Sponsor Sponsor michaeleisel/zld * Notifications * Star 792 * Fork 27 A faster version of Apple's linker MIT License 792 stars 27 forks Star Notifications * Code * Issues 5 * Pull requests 0 * Actions * Projects 0 * Wiki * Security * Insights More * Code * Issues * Pull requests * Actions * Projects * Wiki * Security * Insights master Switch branches/tags [ ] Branches Tags Could not load branches Nothing to show {{ refName }} default View all branches Could not load tags Nothing to show {{ refName }} default View all tags 48 branches 8 tags Code Clone HTTPS GitHub CLI [https://github.com/m] Use Git or checkout with SVN using the web URL. [gh repo clone michae] Work fast with our official CLI. Learn more. * Open with GitHub Desktop * Download ZIP Launching GitHub Desktop If nothing happens, download GitHub Desktop and try again. Go back Launching GitHub Desktop If nothing happens, download GitHub Desktop and try again. Go back Launching Xcode If nothing happens, download Xcode and try again. Go back Launching Visual Studio Code Your codespace will open once ready. There was a problem preparing your codespace, please try again. Latest commit @michaeleisel michaeleisel add rec for -Wl,-x ... a9668e5 Jun 4, 2021 add rec for -Wl,-x a9668e5 Git stats * 107 commits Files Permalink Failed to load latest commit information. Type Name Latest commit message Commit time .github Let GitHub build and publish a prebuilt release when a tag is push (# 79) Dec 31, 2020 corecrypto/include/corecrypto Upgrade to Xcode 12.0's ld (ld64-609) (#83) Mar 5, 2021 img update usage instructions Feb 25, 2020 ld Avoid mmap to fix signing issue (#85) Jun 4, 2021 misc ensure cmake is in system path before building Nov 17, 2020 patches Upgrade dyld to version 733 (#65) Oct 11, 2020 .gitignore Use precompiled libs to fix homebrew May 26, 2021 LICENSE change to MIT license Feb 27, 2020 Makefile Add homebrew building mode to the Makefile May 26, 2021 README.md add rec for -Wl,-x Jun 4, 2021 View code zld A faster version of Apple's linker As used by Introduction Performance Is it worth it for my project? Stability Installation Pre-built binary Building from source Usage If using Xcode: If using Bazel: If using Rust: Caching Why is it faster? Other things to speed up linking Contributing README.md zld A faster version of Apple's linker As used by Most of the really big third-party apps out there. Introduction For large projects, the linking phase (explanation) can significantly increase incremental build times. This project is a fork of the Apple linker, ld. It is a drop-in replacement that can substantially speed things up. Note: it is only intended for debug builds, to make debugging faster. Performance [benchmarks] Feel free to file an issue if you find that linking is not at least 40% faster for your case (make sure to run it twice in a row to ensure that caches have been generated). Further benchmark details can be found here. Is it worth it for my project? It all depends on your risk tolerance and how much you value the speedup in incremental build time. When linking takes more than one second, I'd cut that time in half as the estimated time with this new linker. If that difference is compelling to you, then it'd be worth trying out. Personally, I'd use it in projects with an existing link time of even 500ms (but I am an impatient tinkerer). Stability zld is forked from the most recently open-sourced version of ld. It's used by thousands of developers across many of the largest apps in the world. Without a few optimizations around hashing, it would produce byte-for-byte the same executables as the open-source one. Although it's not ideal to mix compiler and linker toolchain versions, the open-source one is fairly recent. zld will continue to be updated with each new version of ld as it is released. Installation Pre-built binary The pre-built binary for the latest release is here. Building from source * Install Xcode 12.2+ and run sudo xcode-select -s * Install cmake * Checkout the latest release of zld from master * Run make clean && make * See in the output where it built zld (probably build/Build/ Products/Release/zld). Usage If using Xcode: Get the path of zld from which zld, then add -fuse-ld= -Wl,-zld_original_ld_path,$(DT_TOOLCHAIN_DIR)/usr/bin/ld to "Other Linker Flags" in the build settings (debug configuration). That -zld_original_ld_path provides the path to the linker Xcode would otherwise use, which is important because there are certain known cases (e.g. arm64_32 and Catalyst) where zld knows that it has issues and will silently use that linker instead. Fixing these cases is a work-in-progress (largely blocked by Apple being slow to release source code). If using Bazel: Add these to your .bazelrc or pass them to your command line. build --linkopt=-fuse-ld= build --linkopt=-Wl,-zld_original_ld_path,__BAZEL_XCODE_DEVELOPER_DIR__/Toolchains/XcodeDefault.xctoolchain/usr/bin/ld Note that you will need to disable sandbox for this to work now. Additionally, to make the linking actions cacheable, the path to zld must be deterministic (e.g. /tmp/zld-09ea158, where 09ea158 is zld version). If using Rust: You can edit ~/.cargo/config to add a linker flag, e.g.: [target.x86_64-apple-darwin] rustflags = ["-C", "link-arg=-fuse-ld="] Caching By default, zld stores some metadata in /tmp/zld-... to speed things up. This is the first step towards making zld a truly incremental linker. Currently, the only things that are stored are object file and library names. Why is it faster? Apple's approach is a very reasonable one, using C++ with STL data structures. However, there are a number of ways in which zld has sped things up, for instance: * Using Swiss Tables instead of STL for hash maps and sets * Parallelizing in various places (the parsing of libraries, writing the output file, sorting, etc.) * Optimizations around the hashing of strings (caching the hashes, using a better hash function, etc.) Other things to speed up linking Whether you use this project or not, there are a number of things that can speed linking up (again, this is only for debug builds): * The linker flag -Wl,-random_uuid, which disables content hashing based UUID creation and instead uses a random UUID (using -no_uuid can decrease performance when lldb is attaching to the binary) * Turning off dead stripping (referred to as "Dead Code Stripping" in Xcode build settings) * For executables and xctest bundles, disable dyld exports trie creation with -Wl,-exported_symbols_list,/dev/null (cannot be used by test host apps that provide symbols to xctests) * -Wl,-no_deduplicate, which disables the deduplication pass. In Xcode, this flag is added by default for Debug builds. * -Wl,-no_compact_unwind, which disables the creation of compact unwind info. Note that Objective-C and C++ functions that have been linked without their compact unwind info can crash if an exception unwinds into them, rather than continuing the unwind. Swift functions, however, are not affected (even if an Objective-C/C++ exception unwinds into them). So, it's best for pure Swift projects. It can also break crash reporting. * -Wl,-x, which disables putting non-global symbols in the symbol table. This won't impact debugging as long as debug info is still enabled. * If you're not using zld, using -Wl,-force_load for libraries can sometimes speed things up * Linking with dynamic libraries instead of static ones Contributing The biggest way to contribute to zld is to file issues! If you encountered any problems, feel free to file an issue, and you can expect a prompt response. Special thanks to @dmaclach's ld64, which helped with building ld. About A faster version of Apple's linker Topics macos ios linker Resources Readme License MIT License Releases 8 1.3.0 Latest Mar 5, 2021 + 7 releases Sponsor this project Sponsor Learn more about GitHub Sponsors Packages 0 No packages published Contributors 7 * @michaeleisel * @rmaz * @thii * @kastiglione * @steipete * @keith * @woshiccm Languages * C++ 70.4% * Makefile 14.6% * C 9.8% * Roff 1.4% * Assembly 1.3% * Python 0.9% * Other 1.6% * (c) 2021 GitHub, Inc. * Terms * Privacy * Security * Status * Docs * Contact GitHub * Pricing * API * Training * Blog * About You can't perform that action at this time. You signed in with another tab or window. Reload to refresh your session. You signed out in another tab or window. Reload to refresh your session.