Previously, Zig had inconsistent semantics for an enum like this:
`enum(u8){zero = 0}`
Although in theory this can only hold one possible value, the tag
`zero`, Zig no longer will treat the type this way. It will do loads and
stores, as if the type has runtime bits.
Closes#12619
Tests passed locally:
* test-behavior
* test-cases
Takes advantage of the pattern already established with
array_init_anon. Also upgrades array_init (non-anon) to the pattern.
Implements comptime struct value equality and pointer value hashing.
Introduced a new AIR instruction: `tag_name`. Reasons to do this
instead of lowering it in Sema to a switch, function call, array
lookup, or if-else tower:
* Sema is a bottleneck; do less work in Sema whenever possible.
* If any optimization passes run, and the operand to becomes
comptime-known, then it could change to have a comptime result
value instead of lowering to a function or array or something which
would then have to be garbage-collected.
* Backends may want to choose to use a function and a switch branch,
or they may want to use a different strategy.
Codegen for `@tagName` is implemented for the LLVM backend but not any
others yet.
Introduced some new `Type` tags:
* `const_slice_u8_sentinel_0`
* `manyptr_const_u8_sentinel_0`
The motivation for this was to make typeof() on the tag_name AIR
instruction non-allocating.
A bunch more enum tests are passing now.
* remove false positive "all prongs handled" compile error for
non-exhaustive enums.
* implement `@TypeInfo` for enums, except enums which have any
declarations is still TODO.
* `getBuiltin` uses nomespaceLookup/analyzeDeclVal rather than
namespaceLookupRef/analyzeLoad. Avoids a detour through an
unnecessary type, and adds a detour through a caching mechanism.
* `Value.eql`: add missing code to handle enum comparisons for
non-exhaustive enums. It works by converting the enum tags to numeric
values and comparing those.
* stage1: change the `@typeName` of `@TypeOf(undefined)`,
`@TypeOf(null)`, and `@TypeOf(.foo)` to match stage2.
* move passing behavior tests to the passing-for-stage2 section.
* Update AIR instruction `intcast` to allow the dest type to be an
enum.
* LLVM backend: update `intcast` to support when the bit counts of
operand and dest type are the same. This was already a requirement of
the instruction previously.
* Type: `intInfo` supports the case when the type is an enum, and
retrieves the info for the integer tag type. This makes it pretty
easy for backends to implement `intcast` without having to care
explicitly that the new type is an enum. As a bonus, simple enums
never have to go through the type system; their signedness and bit
count are computed directly.
The "int to enum" behavior test case is now passing for stage2 in the
LLVM backend.
Companion commit to 61a53a587558ff1fe1b0ec98bb424022885edccf.
This commit also moves over a bunch of behavior test cases to the
passing-for-stage2 section.
This is a backwards-compatible language change.
Previously, `@intToEnum` coerced its integer operand to the integer tag
type of the destination enum type, often requiring the callsite to
additionally wrap the operand in an `@intCast`. Now, the `@intCast` is
implicit, and any integer operand can be passed to `@intToEnum`.
The same as before, it is illegal behavior to pass any integer which does
not have a corresponding enum tag.
Conflicts:
* doc/langref.html.in
* lib/std/enums.zig
* lib/std/fmt.zig
* lib/std/hash/auto_hash.zig
* lib/std/math.zig
* lib/std/mem.zig
* lib/std/meta.zig
* test/behavior/alignof.zig
* test/behavior/bitcast.zig
* test/behavior/bugs/1421.zig
* test/behavior/cast.zig
* test/behavior/ptrcast.zig
* test/behavior/type_info.zig
* test/behavior/vector.zig
Master branch added `try` to a bunch of testing function calls, and some
lines also had changed how to refer to the native architecture and other
`@import("builtin")` stuff.