Commit Graph

540 Commits

Author SHA1 Message Date
Andrew Kelley bb526426e7 InternPool: remove memoized_decl
This is neither a type nor a value. Simplifies `addStrLit` as well as
the many places that switch on `InternPool.Key`.

This is a partial revert of bec29b9e498e08202679aa29a45dab2a06a69a1e.
2023-06-10 20:47:58 -07:00
mlugg a0d4ef0acf InternPool: add representation for value of empty enums and unions
This is a bit odd, because this value doesn't actually exist:
see #15909. This gets all the empty enum/union behavior tests passing.

Also adds an assertion to `Sema.analyzeBodyInner` which would have
helped figure out the issue here much more quickly.
2023-06-10 20:47:57 -07:00
Andrew Kelley 82f6f164a1 InternPool: improve hashing performance
Key.PtrType is now an extern struct so that hashing it can be done by
reinterpreting bytes directly. It also uses the same representation for
type_pointer Tag encoding and the Key. Accessing pointer attributes now
requires packed struct access, however, many operations are now a copy
of a u32 rather than several independent fields.

This function moves the top two most used Key variants - pointer types
and pointer values - to use a single-shot hash function that branches
for small keys instead of calling memcpy.

As a result, perf against merge-base went from 1.17x ± 0.04 slower to
1.12x ± 0.04 slower. After the pointer value hashing was changed, total
CPU instructions spent in memcpy went from 4.40% to 4.08%, and after
additionally improving pointer type hashing, it further decreased to
3.72%.
2023-06-10 20:47:57 -07:00
Jacob Young a702af062b x86_64: fix InternPool regressions 2023-06-10 20:47:56 -07:00
Jacob Young 3064d2aa7b behavior: additional llvm fixes 2023-06-10 20:47:56 -07:00
Jacob Young 3b6ca1d35b Module: move memoized data to the intern pool
This avoids memory management bugs with the previous implementation.
2023-06-10 20:47:56 -07:00
Jacob Young 2d5bc01469 behavior: get more test cases passing with llvm 2023-06-10 20:47:56 -07:00
Andrew Kelley fc358435cb C backend: InternPool fixes 2023-06-10 20:47:56 -07:00
Andrew Kelley d5f0ee0d62 codegen: fix lowering of constant structs 2023-06-10 20:47:55 -07:00
Jacob Young f2c716187c InternPool: fix more crashes 2023-06-10 20:47:55 -07:00
Jacob Young 9a738c0be5 Module: intern the values of decls when they are marked alive
I'm not sure if this is the right place for this to happen, and
it should become obsolete when comptime mutation is rewritten
and the remaining legacy value tags are remove, so keeping this
as a separate revertable commit.
2023-06-10 20:47:55 -07:00
Jacob Young 1a4626d2cf InternPool: remove more legacy values
Reinstate some tags that will be needed for comptime init.
2023-06-10 20:47:54 -07:00
Jacob Young 6e0de1d116 InternPool: port most of value tags 2023-06-10 20:47:54 -07:00
Andrew Kelley 9ff514b6a3 compiler: move error union types and error set types to InternPool
One change worth noting in this commit is that `module.global_error_set`
is no longer kept strictly up-to-date. The previous code reserved
integer error values when dealing with error set types, but this is no
longer needed because the integer values are not needed for semantic
analysis unless `@errorToInt` or `@intToError` are used and therefore
may be assigned lazily.
2023-06-10 20:47:53 -07:00
Andrew Kelley 7bf91fc79a compiler: eliminate legacy Type.Tag.pointer
Now pointer types are stored only in InternPool.
2023-06-10 20:47:53 -07:00
Andrew Kelley 17882162b3 stage2: move function types to InternPool 2023-06-10 20:47:53 -07:00
Andrew Kelley 88dbd62bcb stage2: move enum tag values into the InternPool
I'm seeing a new assertion trip: the call to `enumTagFieldIndex` in the
implementation of `@Type` is attempting to query the field index of an
union's enum tag, but the type of the enum tag value provided is not the
same as the union's tag type. Most likely this is a problem with type
coercion, since values are now typed.

Another problem is that I added some hacks in std.builtin because I
didn't see any convenient way to access them from Sema. That should
definitely be cleaned up before merging this branch.
2023-06-10 20:46:17 -07:00
Andrew Kelley 5881a2d637 stage2: move enum types into the InternPool
Unlike unions and structs, enums are actually *encoded* into the
InternPool directly, rather than using the SegmentedList trick. This
results in them being quite compact, and greatly improved the ergonomics
of using enum types throughout the compiler.

It did however require introducing a new concept to the InternPool which
is an "incomplete" item - something that is added to gain a permanent
Index, but which is then mutated in place. This was necessary because
enum tag values and tag types may reference the namespaces created by
the enum itself, which required constructing the namespace, decl, and
calling analyzeDecl on the decl, which required the decl value, which
required the enum type, which required an InternPool index to be
assigned and for it to be meaningful.

The API for updating enums in place turned out to be quite slick and
efficient - the methods directly populate pre-allocated arrays and
return the information necessary to output the same compilation errors
as before.
2023-06-10 20:42:30 -07:00
Andrew Kelley 3ba099bfba stage2: move union types and values to InternPool 2023-06-10 20:42:30 -07:00
Andrew Kelley 8297f28546 stage2: move struct types and aggregate values to InternPool 2023-06-10 20:42:30 -07:00
Andrew Kelley 4d88f825bc stage2: implement intTagType logic
This commit changes a lot of `*const Module` to `*Module` to make it
work, since accessing the integer tag type of an enum might need to
mutate the InternPool by adding a new integer type into it.

An alternate strategy would be to pre-heat the InternPool with the
integer tag type when creating an enum type, which would make it so that
intTagType could accept a const Module instead of a mutable one,
asserting that the InternPool already had the integer tag type.
2023-06-10 20:42:29 -07:00
mlugg 2ffef605c7 Replace uses of Value.zero, Value.one, Value.negative_one
This is a bit nasty, mainly because Type.onePossibleValue is now
errorable, which is a quite viral change.
2023-06-10 20:42:29 -07:00
Andrew Kelley 75900ec1b5 stage2: move integer values to InternPool 2023-06-10 20:42:29 -07:00
Andrew Kelley 31aee50c1a InternPool: add a slice encoding
This uses the data field to reference its pointer field type, which
allows for efficient and infallible access of a slice type's pointer
type.
2023-06-10 20:42:29 -07:00
Andrew Kelley 6ab8b6f8b2 stage2: move undef, unreach, null values to InternPool 2023-06-10 20:42:28 -07:00
Andrew Kelley 5e636643d2 stage2: move many Type encodings to InternPool
Notably, `vector`.

Additionally, all alternate encodings of `pointer`, `optional`, and
`array`.
2023-06-10 20:42:27 -07:00
Andrew Kelley 85c69c5194 Type.isSlice: make it InternPool aware 2023-06-10 20:40:04 -07:00
Andrew Kelley ca3cf93b21 stage2: move most simple values to InternPool 2023-06-10 20:40:04 -07:00
Andrew Kelley bcd4bb8afb stage2: move named int types to InternPool 2023-06-10 20:40:04 -07:00
Andrew Kelley 9aec2758cc stage2: start the InternPool transition
Instead of doing everything at once which is a hopelessly large task,
this introduces a piecemeal transition that can be done in small
increments at a time.

This is a minimal changeset that keeps the compiler compiling. It only
uses the InternPool for a small set of types.

Behavior tests are not passing.

Air.Inst.Ref and Zir.Inst.Ref are separated into different enums but
compile-time verified to have the same fields in the same order.

The large set of changes is mainly to deal with the fact that most Type
and Value methods now require a Module to be passed in, so that the
InternPool object can be accessed.
2023-06-10 20:40:03 -07:00
Luuk de Gram ebfd3450d9 codegen: Write padding bytes for unions
Previously we did not write any missing padding bytes after the smallest
field (either tag or payload, depending on alignment). This resulted in
writing too few bytes and not matching the full abisize of the union.
2023-05-31 18:04:33 +02:00
Veikka Tuominen ca16f1e8a7 std.Target adjustments
* move `ptrBitWidth` from Arch to Target since it needs to know about the abi
* double isn't always 8 bits
* AVR uses 1-byte alignment for everything in GCC
2023-05-26 21:42:19 -07:00
Jacob Young 60e69fdaa1 codegen: emit global vector padding 2023-05-18 20:42:38 -04:00
Jacob Young 57c38f6433 x86_64: implement global payload pointers 2023-05-15 03:07:51 -04:00
Jacob Young 81664f17d5 codegen: implement global enum_numbered 2023-05-15 03:07:51 -04:00
Jacob Young 31429a4e86 codegen: handle variable and decl_ref_mut consistently 2023-05-03 04:25:14 -04:00
Jacob Young f894ec264b codegen: fix global nested field_ptr 2023-05-03 04:25:14 -04:00
Jacob Young f56f5af403 x86_64: fix global slices 2023-05-03 04:25:14 -04:00
Jacob Young 47a34d038d x86_64: implement tagName 2023-05-01 19:22:52 -04:00
Jacob Young f37ca3fa73 link: cleanup lazy alignment
This gets the alignment from the code that creates a lazy symbol instead
of guessing it at every use.
2023-05-01 19:22:52 -04:00
Jacob Young db76ae8260 x86_64: fix emitting f80 globals 2023-05-01 19:22:52 -04:00
Jacob Young 4ec49da5f6 x86_64: implement a bunch of floating point stuff 2023-05-01 19:22:52 -04:00
Andrew Kelley 42973d73e6 compiler: use @memcpy instead of std.mem.copy 2023-04-28 13:24:43 -07:00
Jakub Konka 8a3ad3f620 elf: do not reserve a GOT slot for every Atom 2023-04-21 22:44:25 +02:00
Jakub Konka b82130709d x86_64: cleanup different memory load types
Split `MCValue.linker_load` into `.load_got`, `.load_direct`, and
`.lea_direct`.
2023-04-15 11:10:24 +02:00
Jakub Konka 179117c114 x86_64: split MCValue.tlv_reloc into .load_tlv and .lea_tlv
`.load_tlv` signifies we want to load the value of a TLV
`.lea_tlv` signifies we want to load effective address of a TLV
2023-04-15 00:57:23 +02:00
Jakub Konka 3f35d6984f x86_64: make TLV a separate MCValue 2023-04-13 16:35:45 +02:00
Jakub Konka fd52d4537a x86_64: emit pointer to TLV for macho 2023-04-13 11:47:51 +02:00
Jakub Konka 382de7bf1d codegen: use non-debug Type/Value formatting 2023-04-13 11:47:51 +02:00
Jacob Young caa3d6a4f4 x86_64: fix constant pointers to zero-bit types
These non-dereferencable pointers still need to have the correct
alignment and non-null-ness.
2023-04-13 04:17:47 -04:00