aboutsummaryrefslogtreecommitdiff
path: root/src/link/Wasm.zig
AgeCommit message (Collapse)Author
2025-10-29compiler: update for introduction of std.IoAndrew Kelley
only thing remaining is using libc dns resolution when linking libc
2025-09-26compiler: move self-hosted backends from src/arch to src/codegenAlex Rønne Petersen
2025-09-21Elf2: create a new linker from scratchJacob Young
This iteration already has significantly better incremental support. Closes #24110
2025-08-29std.Io: delete GenericReaderAndrew Kelley
and delete deprecated alias std.io
2025-07-07std.fmt: fully remove format string from format methodsAndrew Kelley
Introduces `std.fmt.alt` which is a helper for calling alternate format methods besides one named "format".
2025-07-07compiler: update a bunch of format stringsAndrew Kelley
2025-07-02compiler: change canonical path for backend ABI source filesAndrew Kelley
2025-06-19Target: pass and use locals by pointer instead of by valueJacob Young
This struct is larger than 256 bytes and code that copies it consistently shows up in profiles of the compiler.
2025-06-12x86_64: remove air references from mirJacob Young
2025-06-12compiler: rework emit paths and cache modesmlugg
Previously, various doc comments heavily disagreed with the implementation on both what lives where on the filesystem at what time, and how that was represented in code. Notably, the combination of emit paths outside the cache and `disable_lld_caching` created a kind of ad-hoc "cache disable" mechanism -- which didn't actually *work* very well, 'most everything still ended up in this cache. There was also a long-standing issue where building using the LLVM backend would put a random object file in your cwd. This commit reworks how emit paths are specified in `Compilation.CreateOptions`, how they are represented internally, and how the cache usage is specified. There are now 3 options for `Compilation.CacheMode`: * `.none`: do not use the cache. The paths we have to emit to are relative to the compiler cwd (they're either user-specified, or defaults inferred from the root name). If we create any temporary files (e.g. the ZCU object when using the LLVM backend) they are emitted to a directory in `local_cache/tmp/`, which is deleted once the update finishes. * `.whole`: cache the compilation based on all inputs, including file contents. All emit paths are computed by the compiler (and will be stored as relative to the local cache directory); it is a CLI error to specify an explicit emit path. Artifacts (including temporary files) are written to a directory under `local_cache/tmp/`, which is later renamed to an appropriate `local_cache/o/`. The caller (who is using `--listen`; e.g. the build system) learns the name of this directory, and can get the artifacts from it. * `.incremental`: similar to `.whole`, but Zig source file contents, and anything else which incremental compilation can handle changes for, is not included in the cache manifest. We don't need to do the dance where the output directory is initially in `tmp/`, because our digest is computed entirely from CLI inputs. To be clear, the difference between `CacheMode.whole` and `CacheMode.incremental` is unchanged. `CacheMode.none` is new (previously it was sort of poorly imitated with `CacheMode.whole`). The defined behavior for temporary/intermediate files is new. `.none` is used for direct CLI invocations like `zig build-exe foo.zig`. The other cache modes are reserved for `--listen`, and the cache mode in use is currently just based on the presence of the `-fincremental` flag. There are two cases in which `CacheMode.whole` is used despite there being no `--listen` flag: `zig test` and `zig run`. Unless an explicit `-femit-bin=xxx` argument is passed on the CLI, these subcommands will use `CacheMode.whole`, so that they can put the output somewhere without polluting the cwd (plus, caching is potentially more useful for direct usage of these subcommands). Users of `--listen` (such as the build system) can now use `std.zig.EmitArtifact.cacheName` to find out what an output will be named. This avoids having to synchronize logic between the compiler and all users of `--listen`.
2025-06-12wasm: get self-hosted compiling, and supporting `separate_thread`mlugg
My original goal here was just to get the self-hosted Wasm backend compiling again after the pipeline change, but it turned out that from there it was pretty simple to entirely eliminate the shared state between `codegen.wasm` and `link.Wasm`. As such, this commit not only fixes the backend, but makes it the second backend (after CBE) to support the new 1:N:1 threading model.
2025-06-12link: divorce LLD from the self-hosted linkersmlugg
Similar to the previous commit, this commit untangles LLD integration from the self-hosted linkers. Despite the big network of functions which were involved, it turns out what was going on here is quite simple. The LLD linking logic is actually very self-contained; it requires a few flags from the `link.File.OpenOptions`, but that's really about it. We don't need any of the mutable state on `Elf`/`Coff`/`Wasm`, for instance. There was some legacy code trying to handle support for using self-hosted codegen with LLD, but that's not a supported use case, so I've just stripped it out. For now, I've just pasted the logic for linking the 3 targets we currently support using LLD for into this new linker implementation, `link.Lld`; however, it's almost certainly possible to combine some of the logic and simplify this file a bit. But to be honest, it's not actually that bad right now. This commit ends up eliminating the distinction between `flush` and `flushZcu` (formerly `flushModule`) in linkers, where the latter previously meant something along the lines of "flush, but if you're going to be linking with LLD, just flush the ZCU object file, don't actually link"?. The distinction here doesn't seem like it was properly defined, and most linkers seem to treat them as essentially identical anyway. Regardless, all calls to `flushZcu` are gone now, so it's deleted -- one `flush` to rule them all! The end result of this commit and the preceding one is that LLVM and LLD fit into the pipeline much more sanely: * If we're using LLVM for the ZCU, that state is on `zcu.llvm_object` * If we're using LLD to link, then the `link.File` is a `link.Lld` * Calls to "ZCU link functions" (e.g. `updateNav`) lower to calls to the LLVM object if it's available, or otherwise to the `link.File` if it's available (neither is available under `-fno-emit-bin`) * After everything is done, linking is finalized by calling `flush` on the `link.File`; for `link.Lld` this invokes LLD, for other linkers it flushes self-hosted linker state There's one messy thing remaining, and that's how self-hosted function codegen in a ZCU works; right now, we process AIR with a call sequence something like this: * `link.doTask` * `Zcu.PerThread.linkerUpdateFunc` * `link.File.updateFunc` * `link.Elf.updateFunc` * `link.Elf.ZigObject.updateFunc` * `codegen.generateFunction` * `arch.x86_64.CodeGen.generate` So, we start in the linker, take a scenic detour through `Zcu`, go back to the linker, into its implementation, and then... right back out, into code which is generic over the linker implementation, and then dispatch on the *backend* instead! Of course, within `arch.x86_64.CodeGen`, there are some more places which switch on the `link` implementation being used. This is all pretty silly... so it shall be my next target.
2025-06-12compiler: slightly untangle LLVM from the linkersmlugg
The main goal of this commit is to make it easier to decouple codegen from the linkers by being able to do LLVM codegen without going through the `link.File`; however, this ended up being a nice refactor anyway. Previously, every linker stored an optional `llvm.Object`, which was populated when using LLVM for the ZCU *and* linking an output binary; and `Zcu` also stored an optional `llvm.Object`, which was used only when we needed LLVM for the ZCU (e.g. for `-femit-llvm-bc`) but were not emitting a binary. This situation was incredibly silly. It meant there were N+1 places the LLVM object might be instead of just 1, and it meant that every linker had to start a bunch of methods by checking for an LLVM object, and just dispatching to the corresponding method on *it* instead if it was not `null`. Instead, we now always store the LLVM object on the `Zcu` -- which makes sense, because it corresponds to the object emitted by, well, the Zig Compilation Unit! The linkers now mostly don't make reference to LLVM. `Compilation` makes sure to emit the LLVM object if necessary before calling `flush`, so it is ready for the linker. Also, all of the `link.File` methods which act on the ZCU -- like `updateNav` -- now check for the LLVM object in `link.zig` instead of in every single individual linker implementation. Notably, the change to LLVM emit improves this rather ludicrous call chain in the `-fllvm -flld` case: * Compilation.flush * link.File.flush * link.Elf.flush * link.Elf.linkWithLLD * link.Elf.flushModule * link.emitLlvmObject * Compilation.emitLlvmObject * llvm.Object.emit Replacing it with this one: * Compilation.flush * llvm.Object.emit ...although we do currently still end up in `link.Elf.linkWithLLD` to do the actual linking. The logic for invoking LLD should probably also be unified at least somewhat; I haven't done that in this commit.
2025-06-06x86_64: add support for pie executablesJacob Young
2025-05-29Legalize: introduce a new pass before livenessJacob Young
Each target can opt into different sets of legalize features. By performing these transformations before liveness, instructions that become unreferenced will have up-to-date liveness information.
2025-05-10compiler: Move vendored library support to `libs` subdirectory.Alex Rønne Petersen
2025-05-01wasm-c-abi: llvm fix struct handling + reorganizePavel Verigo
I changed to `wasm/abi.zig`, this design is certainly better than the previous one. Still there is some conflict of interest between llvm and self-hosted backend, better design will appear when abi tests will be tested with self-hosted. Resolves: #23304 Resolves: #23305
2025-04-13link: Improve handling of --build-id when using LLD.Alex Rønne Petersen
2025-04-11Introduce libzigc for libc function implementations in Zig.Alex Rønne Petersen
This lays the groundwork for #2879. This library will be built and linked when a static libc is going to be linked into the compilation. Currently, that means musl, wasi-libc, and MinGW-w64. As a demonstration, this commit removes the musl C code for a few string functions and implements them in libzigc. This means that those libzigc functions are now load-bearing for musl and wasi-libc. Note that if a function has an implementation in compiler-rt already, libzigc should not implement it. Instead, as we recently did for memcpy/memmove, we should delete the libc copy and rely on the compiler-rt implementation. I repurposed the existing "universal libc" code to do this. That code hadn't seen development beyond basic string functions in years, and was only usable-ish on freestanding. I think that if we want to seriously pursue the idea of Zig providing a freestanding libc, we should do so only after defining clear goals (and non-goals) for it. See also #22240 for a similar case.
2025-04-04std.Target: Update CPU models/features for LLVM 20.Alex Rønne Petersen
Closes #21818.
2025-02-25move libubsan to `lib/` and integrate it into `-fubsan-rt`David Rubin
2025-02-17std.builtin: Rename CallingConvention.wasm_watc to wasm_mvp.Alex Rønne Petersen
2025-01-22link.Wasm.Feature: Make fromCpuFeature() and toCpuFeature() less cute.Alex Rønne Petersen
This is more verbose, but at least we now get a compile error instead of UB when a new feature is added to std.Target.wasm.Feature but not to link.Wasm.Feature.
2025-01-22wasm: Add a nontrapping_bulk_memory_len0 feature.Alex Rønne Petersen
This will mainly be used when targeting our wasm2c implementation which has no problem with zero-length bulk memory operations, as a non-standard extension.
2025-01-15wasm linker: change rules about symbol visibilityAndrew Kelley
export by default means export, as expected. if you want hidden visibility then use hidden visibility.
2025-01-15wasm linker: fix explicit exports not affecting object filesAndrew Kelley
2025-01-15wasm linker: ability to get data and functions from objectsAndrew Kelley
2025-01-15wasm-linker: remap function types during flushAndrew Kelley
this is technically not necessary, and loses value the bigger the output binary is, however it means a smaller output file, so let's do it.
2025-01-15wasm linker: correct export visibility logicAndrew Kelley
exports are hidden unless protected or rdynamic or explicitly asked for, matching master branch
2025-01-15wasm linker: always passive when importing memoryAndrew Kelley
and detect passive inits from Zcu don't forget to intern function type for __wasm_init_memory make that function the start function if it is present don't skip emitting passive data segment data to the binary
2025-01-15wasm linker: implement hidden visibilityAndrew Kelley
2025-01-15Compilation.saveState implement saving wasm linker stateAndrew Kelley
2025-01-15wasm linker: reset function exports after flushAndrew Kelley
2025-01-15wasm linker: track overaligned uavsAndrew Kelley
2025-01-15wasm linker: fix data segment namesAndrew Kelley
2025-01-15wasm linker: fix missed addend for uav and nav fixupsAndrew Kelley
2025-01-15wasm linker: fix bad export index mathAndrew Kelley
2025-01-15wasm linker: implement `@tagName` for sparse enumsAndrew Kelley
2025-01-15wasm linker: implement `@tagName` functions when tags are autoassignedAndrew Kelley
2025-01-15wasm linker: don't crash on ref to voidAndrew Kelley
2025-01-15wasm-linker: add updateFunc logAndrew Kelley
2025-01-15wasm linker: fix corruption of string bytesAndrew Kelley
if any fixups are emitted in lowering data, keep the string bytes allocated even if all zeroes because it is used as a fixup staging area.
2025-01-15wasm linker: handle function data references properlyAndrew Kelley
2025-01-15wasm linker: don't call init functions unless object includedAndrew Kelley
2025-01-15implement indirect function table for object functionsAndrew Kelley
2025-01-15wasm linker: handle weak globals in relocsAndrew Kelley
2025-01-15wasm linker: don't try to lower nav zcu data before updateNav is calledAndrew Kelley
2025-01-15wasm linker: don't assume nav callees are fully resolvedAndrew Kelley
codegen can be called which contains calls to navs which have only their type resolved. this means the indirect function table needs to track nav indexes not ip indexes.
2025-01-15wasm linker: distinguish symbol name vs import name, and implement weakAndrew Kelley
2025-01-15wasm linker: fix not merging object memoriesAndrew Kelley