From de2d3e3bec7087dccb2efa3f08b174cd6f9c6a6d Mon Sep 17 00:00:00 2001 From: Divy Srivastava Date: Tue, 14 May 2024 11:22:12 +0530 Subject: [PATCH] Add comments --- .cargo/config.toml | 2 ++ tools/lzld/README.md | 44 +++++++++++++++++++++++++++++++------ tools/lzld/liblzld_arm64.a | Bin 13976 -> 1680 bytes tools/lzld/lzld | 6 +++++ tools/lzld/lzld.m | 12 ++++++++++ 5 files changed, 57 insertions(+), 7 deletions(-) diff --git a/.cargo/config.toml b/.cargo/config.toml index ed02fc7a7c..1dfd5a3416 100644 --- a/.cargo/config.toml +++ b/.cargo/config.toml @@ -18,6 +18,8 @@ rustflags = [ ] [target.aarch64-apple-darwin] +# The purpose of lzld is to reduce startup time on Mac +# by lazy loading frameworks. See tools/lzld/README.md linker = "tools/lzld/lzld" rustflags = [ "-C", diff --git a/tools/lzld/README.md b/tools/lzld/README.md index 3bef668e08..ebb6334ea2 100644 --- a/tools/lzld/README.md +++ b/tools/lzld/README.md @@ -1,4 +1,40 @@ -A `ld -lazy_framework` for macOS. Designed to build Deno. +# `lzld` + +This tools implements an alternative of the (deprecated) `ld -lazy_framework` to lazy load frameworks as needed. Symbols used are manually +added to `lzld.m`. + +The purpose of this ld wrapper is to improve startup time on Mac. Because Deno includes WebGPU, it needs to link to Metal and QuartzCore. +We've observed that loading frameworks during startup can cost as much as 8ms of startup time. + +## Adding a new symbol binding + +Add a binding for the used symbol in `lzld.m`, eg: + +```diff +void *(*MTLCopyAllDevices_)(void) = 0; ++void *(*MTLSomethingSomething_)(void) = 0; + +void loadMetalFramework() { + void *handle = dlopen("/System/Library/Frameworks/Metal.framework/Metal", RTLD_LAZY); + if (handle) { + MTLCopyAllDevices_ = dlsym(handle, "MTLCopyAllDevices"); ++ MTLSomethingSomething_ = dlsym(handle, "MTLSomethingSomething"); + } +} + + ++extern void *MTLSomethingSomething(void) { ++ if (MTLSomethingSomething_ == 0) { ++ loadMetalFramework(); ++ } ++ ++ return MTLSomethingSomething_(); ++} + +extern void *MTLCopyAllDevices(void) { +``` + +then build the static library with `make liblzld_arm64.a`. ## Usage @@ -28,9 +64,3 @@ framework via `dlopen` when needed. Rest of the arguments are passed as-is to `lld`. - diff --git a/tools/lzld/liblzld_arm64.a b/tools/lzld/liblzld_arm64.a index e376c4bec7bb5eb13933ced4c053726db1e65037..4a96f7a4fc19a2fc6b59ff37e8e38243a0ebc880 100644 GIT binary patch literal 1680 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 G9R3dn*F`%3 diff --git a/tools/lzld/lzld b/tools/lzld/lzld index 5833e68dee..d77d62eb2d 100755 --- a/tools/lzld/lzld +++ b/tools/lzld/lzld @@ -1,4 +1,10 @@ #!/bin/bash +# +# This script is a wrapper around the `lld` linker that adds the path to the +# `liblzld` static library to the linker search path and links against it. +# +# Additionally, this script strips out `-framework` arguments + arch=$(uname -m) # Find the path to the `lld` binary. diff --git a/tools/lzld/lzld.m b/tools/lzld/lzld.m index a9b4ec9424..bf9f0d29fa 100644 --- a/tools/lzld/lzld.m +++ b/tools/lzld/lzld.m @@ -1,3 +1,15 @@ +/* + lzld - lazy loading of OSX frmeworks + + This is compiled as a static library and linked against the binary via `lzld` script. + This code dynamically load frameworks when symbol is called using dlopen and dlsym. + + Dependencies: + - dlfcn.h: Header file providing functions for dynamic linking. + - QuartzCore.framework: Provides graphics rendering support. (WebGPU) + - Metal.framework: Framework for high-performance GPU-accelerated graphics and computing. (WebGPU) +*/ + #import // -- QuartzCore.framework