253 Commits

Author SHA1 Message Date
mlugg
93a5bd262d
frontend: removed resolved IES data for outdated functions
Without this, incremental updates which would change inferred error sets
fail, since they assume the IES is resolved and equals the old set,
resulting in false positive compile errors when e.g. coercing to an IES.
2024-08-18 18:10:59 +01:00
mlugg
9e6318a4ea compiler: add some doc comments 2024-08-17 18:50:10 -04:00
mlugg
84c2ebd6c6 frontend: incremental compilation progress
Another big commit, sorry! This commit makes all fixes necessary for
incremental updates of the compiler itself (specifically, adding a
breakpoint to `zirCompileLog`) to succeed, at least on the frontend.

The biggest change here is a reform to how types are handled. It works
like this:
* When a type is first created in `zirStructDecl` etc, its namespace is
  scanned. If the type requires resolution, an `interned` dependency is
  declared for the containing `AnalUnit`.
* `zirThis` also declared an `interned` dependency for its `AnalUnit` on
  the namespace's owner type.
* If the type's namespace changes, the surrounding source declaration
  changes hash, so `zirStructDecl` etc will be hit again. We check
  whether the namespace has been scanned this generation, and re-scan it
  if not.
* Namespace lookups also check whether the namespace in question
  requires a re-scan based on the generation. This is because there's no
  guarantee that the `zirStructDecl` is re-analyzed before the namespace
  lookup is re-analyzed.
* If a type's structure (essentially its fields) change, then the type's
  `Cau` is considered outdated. When the type is re-analyzed due to
  being outdated, or the `zirStructDecl` is re-analyzed by being
  transitively outdated, or a corresponding `zirThis` is re-analyzed by
  being transitively outdated, the struct type is recreated at a new
  `InternPool` index. The namespace's owner is updated (but not
  re-scanned, since that is handled by the mechanisms above), and the
  old type, while remaining a valid `Index`, is removed from the map
  metadata so it will never be found by lookups. `zirStructDecl` and
  `zirThis` store an `interned` dependency on the *new* type.
2024-08-17 18:50:10 -04:00
mlugg
46388d338a InternPool: don't remove outdated types
When a type becomes outdated, there will still be lingering references
to the old index -- for instance, any declaration whose value was that
type holds a reference to that index. These references may live for an
arbitrarily long time in some cases. So, we can't just remove the type
from the pool -- the old `Index` must remain valid!

Instead, we want to preserve the old `Index`, but avoid it from ever
appearing in lookups. (It's okay if analysis of something referencing
the old `Index` does weird stuff -- such analysis are guaranteed by the
incremental compilation model to always be unreferenced.) So, we use the
new `InternPool.putKeyReplace` to replace the shard entry for this index
with the newly-created index.
2024-08-17 18:50:10 -04:00
mlugg
895267c916 frontend: incremental progress
This commit makes more progress towards incremental compilation, fixing
some crashes in the frontend. Notably, it fixes the regressions introduced
by #20964. It also cleans up the "outdated file root" mechanism, by
virtue of deleting it: we now detect outdated file roots just after
updating ZIR refs, and re-scan their namespaces.
2024-08-17 18:50:10 -04:00
Jacob Young
ef11bc9899 Dwarf: rework self-hosted debug info from scratch
This is in preparation for incremental and actually being able to debug
executables built by the x86_64 backend.
2024-08-16 15:22:55 -04:00
mlugg
153e7d6235
frontend: give all container types namespaces
Eliding the namespace when a container type has no decls was an
experiment in saving memory, but it ended up causing more trouble than
it was worth in various places. So, take the small memory hit for
reified types, and just give every container type a namespace.
2024-08-11 07:30:21 +01:00
mlugg
548a087faf
compiler: split Decl into Nav and Cau
The type `Zcu.Decl` in the compiler is problematic: over time it has
gained many responsibilities. Every source declaration, container type,
generic instantiation, and `@extern` has a `Decl`. The functions of
these `Decl`s are in some cases entirely disjoint.

After careful analysis, I determined that the two main responsibilities
of `Decl` are as follows:
* A `Decl` acts as the "subject" of semantic analysis at comptime. A
  single unit of analysis is either a runtime function body, or a
  `Decl`. It registers incremental dependencies, tracks analysis errors,
  etc.
* A `Decl` acts as a "global variable": a pointer to it is consistent,
  and it may be lowered to a specific symbol by the codegen backend.

This commit eliminates `Decl` and introduces new types to model these
responsibilities: `Cau` (Comptime Analysis Unit) and `Nav` (Named
Addressable Value).

Every source declaration, and every container type requiring resolution
(so *not* including `opaque`), has a `Cau`. For a source declaration,
this `Cau` performs the resolution of its value. (When #131 is
implemented, it is unsolved whether type and value resolution will share
a `Cau` or have two distinct `Cau`s.) For a type, this `Cau` is the
context in which type resolution occurs.

Every non-`comptime` source declaration, every generic instantiation,
and every distinct `extern` has a `Nav`. These are sent to codegen/link:
the backends by definition do not care about `Cau`s.

This commit has some minor technically-breaking changes surrounding
`usingnamespace`. I don't think they'll impact anyone, since the changes
are fixes around semantics which were previously inconsistent (the
behavior changed depending on hashmap iteration order!).

Aside from that, this changeset has no significant user-facing changes.
Instead, it is an internal refactor which makes it easier to correctly
model the responsibilities of different objects, particularly regarding
incremental compilation. The performance impact should be negligible,
but I will take measurements before merging this work into `master`.

Co-authored-by: Jacob Young <jacobly0@users.noreply.github.com>
Co-authored-by: Jakub Konka <kubkon@jakubkonka.com>
2024-08-11 07:29:41 +01:00
Andrew Kelley
25198810c8 add new builtin: @disableInstrumentation
This is needed to ensure that start code does not try to access thread
local storage before it has set up thread local storage.
2024-07-22 13:07:02 -07:00
David Rubin
7591df5172 ip: use getExternFunc in getCoerced
`ip.get` specifically doesn't allow `extern_func` keys to access it.
2024-07-21 01:00:49 -07:00
Jacob Young
88bb0fd288
Merge pull request #20632 from jacobly0/codegen-thread
InternPool: enable separate codegen/linking thread
2024-07-16 14:49:49 -04:00
Jacob Young
00fdbf05f3 InternPool: enable separate codegen/linking thread
Let's see what happens :)
2024-07-16 06:28:42 -04:00
Jacob Young
9d1820d206 InternPool: reduce max tid width by one bit
@mlugg keeps stealing my bits!
2024-07-16 06:28:41 -04:00
Jacob Young
b0fe7eef54 InternPool: fix various data structure invariants 2024-07-16 05:14:38 -04:00
Jacob Young
7dbd2a6bb5 InternPool: fix DependencyIterator iteration 2024-07-16 02:24:16 -04:00
Wooster
888708ec8a
Sema: support pointer subtraction 2024-07-15 18:18:38 +00:00
Jacob Young
a1053e8e1d InternPool: add and use a mutate mutex for each list
This allows the mutate mutex to only be locked during actual grows,
which are rare. For the lists that didn't previously have a mutex, this
change has little effect since grows are rare and there is zero
contention on a mutex that is only ever locked by one thread.  This
change allows `extra` to be mutated without racing with a grow.
2024-07-13 04:47:38 -04:00
Jacob Young
77810f2882 InternPool: fix optimization assertion failure 2024-07-10 22:56:12 -04:00
Jacob Young
c2316c5228 InternPool: make global_error_set thread-safe 2024-07-10 21:39:55 -04:00
Jacob Young
98f3a262a7 InternPool: fix extra mutation races 2024-07-10 19:03:07 -04:00
Jacob Young
2c89f3b654 InternPool: make maps thread-safe 2024-07-10 19:02:55 -04:00
Jacob Young
afa66fa392 InternPool: make tracked_insts thread-safe 2024-07-10 14:42:50 -04:00
Jacob Young
f290b54f89 InternPool: make files more thread-safe 2024-07-10 11:20:08 -04:00
Jacob Young
8f292431b0 InternPool: fix undefined decl fully qualified name
This is now possible after moving `File.Index` to `*File` mapping into
intern pool.
2024-07-10 11:20:08 -04:00
Jacob Young
3d2dfbe828 InternPool: add FileIndex to *File mapping 2024-07-10 11:20:08 -04:00
Jacob Young
3aa48bf859 InternPool: fix race on struct flags 2024-07-10 11:10:49 -04:00
Jacob Young
9cf42b1036 InternPool: fix race on FuncInstance.branch_quota 2024-07-10 11:10:49 -04:00
Jacob Young
667b4f9054 Zcu: cache fully qualified name on Decl
This avoids needing to mutate the intern pool from backends.
2024-07-10 11:10:49 -04:00
Jacob Young
c5283eb49b InternPool: implement thread-safe allocated lists 2024-07-09 17:29:01 -04:00
Jacob Young
c36e2bb980 InternPool: fix multi-thread build 2024-07-08 07:02:53 -04:00
Jacob Young
14192019ff InternPool: fix dumping of simple types 2024-07-07 23:45:33 -04:00
Jacob Young
1abc904075 InternPool: start documenting new thread-safe fields 2024-07-07 23:23:30 -04:00
Jacob Young
bdae01ab04 InternPool: implement and use thread-safe list for extra and limbs 2024-07-07 22:59:52 -04:00
Jacob Young
49b25475ad InternPool: remove usage of data with simple indices
This allows them to be atomically replaced.
2024-07-07 22:59:52 -04:00
Jacob Young
383cffbfae InternPool: temporarily disable multi-threaded behavior
This reduces the cost of the new data structure until the multi-threaded
behavior is actually used.
2024-07-07 22:59:52 -04:00
Jacob Young
92ddb959a7 InternPool: implement and use thread-safe list for items 2024-07-07 22:59:52 -04:00
Jacob Young
8293ff94cf InternPool: implement and use thread-safe list for strings 2024-07-07 22:59:52 -04:00
Jacob Young
3e1b190fe6 InternPool: replace garbage with an arena
This was just a badly implemented arena anyway.
2024-07-07 22:59:52 -04:00
Jacob Young
c8b9364b30 InternPool: use thread-safe hash map for strings 2024-07-07 22:59:52 -04:00
Jacob Young
cda716ecc4 InternPool: implement thread-safe hash map 2024-07-07 22:59:52 -04:00
Jacob Young
ca02266157 Zcu: pass PerThread to intern pool string functions 2024-07-07 22:59:52 -04:00
Jacob Young
525f341f33 Zcu: introduce PerThread and pass to all the functions 2024-07-07 22:59:52 -04:00
Andrew Kelley
74346b0f79 frontend: TrackedInst stores FileIndex instead of path digest
The purpose of using path digest was to reference a file in a
serializable manner. Now that there is a stable index associated with
files, it is a superior way to accomplish that goal, since removes one
layer of indirection, and makes TrackedInst 8 bytes instead of 20.

The saved Zig Compiler State file for "hello world" goes from 1.3M to
1.2M with this change.
2024-07-04 17:56:01 -07:00
Andrew Kelley
30ec43a6c7 Zcu: extract permanent state from File
Primarily, this commit removes 2 fields from File, relying on the data
being stored in the `files` field, with the key as the path digest, and
the value as the struct decl corresponding to the File. This table is
serialized into the compiler state that survives between incremental
updates.

Meanwhile, the File struct remains ephemeral data that can be
reconstructed the first time it is needed by the compiler process, as
well as operated on by independent worker threads.

A key outcome of this commit is that there is now a stable index that
can be used to refer to a File. This will be needed when serializing
error messages to survive incremental compilation updates.
2024-07-04 17:51:35 -07:00
mlugg
bc8cd13598
compiler: rename AnalSubject to AnalUnit
I meant to call it this originally, I just got mixed up -- sorry!
2024-07-04 21:01:40 +01:00
mlugg
4cb5318088
InternPool: rename Depender to AnalSubject
This is essentially just a rename. I also changed the representation of
`AnalSubject` to use a `packed struct` rather than a non-exhaustive
enum, but that change is relatively trivial.
2024-06-26 05:28:04 +01:00
mlugg
5b523d0469
Zir: make src_line absolute for declaration instructions
We need special logic for updating line numbers anyway, so it's fine to
just use absolute numbers here. This eliminates a field from `Decl`.
2024-06-26 05:28:03 +01:00
Andrew Kelley
0fcd59eada rename src/Module.zig to src/Zcu.zig
This patch is a pure rename plus only changing the file path in
`@import` sites, so it is expected to not create version control
conflicts, even when rebasing.
2024-06-22 22:59:56 -04:00
mlugg
1eaeb4a0a8
Zcu: rework source locations
`LazySrcLoc` now stores a reference to the "base AST node" to which it
is relative. The previous tagged union is `LazySrcLoc.Offset`. To make
working with this structure convenient, `Sema.Block` contains a
convenience `src` method which takes an `Offset` and returns a
`LazySrcLoc`.

The "base node" of a source location is no longer given by a `Decl`, but
rather a `TrackedInst` representing either a `declaration`,
`struct_decl`, `union_decl`, `enum_decl`, or `opaque_decl`. This is a
more appropriate model, and removes an unnecessary responsibility from
`Decl` in preparation for the upcoming refactor which will split it into
`Nav` and `Cau`.

As a part of these `Decl` reworks, the `src_node` field is eliminated.
This change aids incremental compilation, and simplifies `Decl`. In some
cases -- particularly in backends -- the source location of a
declaration is desired. This was previously `Decl.srcLoc` and worked for
any `Decl`. Now, it is `Decl.navSrcLoc` in reference to the upcoming
refactor, since the set of `Decl`s this works for precisely corresponds
to what will in future become a `Nav` -- that is, source-level
declarations and generic function instantiations, but *not* type owner
Decls.

This commit introduces more tags to `LazySrcLoc.Offset` so as to
eliminate the concept of `error.NeededSourceLocation`. Now, `.unneeded`
should only be used to assert that an error path is unreachable. In the
future, uses of `.unneeded` can probably be replaced with `undefined`.

The `src_decl` field of `Sema.Block` no longer has a role in type
resolution. Its main remaining purpose is to handle namespacing of type
names. It will be eliminated entirely in a future commit to remove
another undue responsibility from `Decl`.

It is worth noting that in future, the `Zcu.SrcLoc` type should probably
be eliminated entirely in favour of storing `Zcu.LazySrcLoc` values.
This is because `Zcu.SrcLoc` is not valid across incremental updates,
and we want to be able to reuse error messages from previous updates
even if the source file in question changed. The error reporting logic
should instead simply resolve the location from the `LazySrcLoc` on the
fly.
2024-06-15 00:57:52 +01:00
mlugg
07a24bec9a
compiler: move LazySrcLoc out of std
This is in preparation for some upcoming changes to how we represent
source locations in the compiler. The bulk of the change here is dealing
with the removal of `src()` methods from `Zir` types.
2024-06-15 00:57:52 +01:00