@select(
comptime T: type,
pred: std.meta.Vector(len, bool),
a: std.meta.Vector(len, T),
b: std.meta.Vector(len, T)
) std.meta.Vector(len, T)
Constructs a vector from a & b, based on the values in the predicate vector. For indices where the predicate value is true, the corresponding
element from the a vector is selected, and otherwise from b.
* There is now a main_pkg in addition to root_pkg. They are usually the
same. When using `zig test`, main_pkg is the user's source file and
root_pkg has the test runner.
* scanDecl no longer looks for test decls outside the package being
tested. honoring `--test-filter` is still TODO.
* test runner main function has a void return value rather than
`anyerror!void`
* Sema is improved to generate better AIR for for loops on slices.
* Sema: fix incorrect capacity calculation in zirBoolBr
* Sema: add compile errors for trying to use slice fields as an lvalue.
* Sema: fix type coercion for error unions
* Sema: fix analyzeVarRef generating garbage AIR
* C codegen: fix renderValue for error unions with 0 bit payload
* C codegen: implement function pointer calls
* CLI: fix usage text
Adds 4 new AIR instructions:
* slice_len, slice_ptr: to get the ptr and len fields of a slice.
* slice_elem_val, ptr_slice_elem_val: to get the element value of
a slice, and a pointer to a slice.
AstGen gains a new functionality:
* One of the unused flags of struct decls is now used to indicate
structs that are known to have non-zero size based on the AST alone.
* Breaking language change: inline assembly must use string literal
syntax. This is in preparation for inline assembly improvements that
involve more integration with the Zig language. This means we cannot
rely on text substitution.
* Liveness: properly handle inline assembly and function calls with
more than 3 operands.
- More than 35 operands is not yet supported. This is a low priority
to implement.
- This required implementation in codegen.zig as well.
* Liveness: fix bug causing incorrect tomb bits.
* Sema: enable switch expressions that are evaluated at compile-time.
- Runtime switch instructions still need to be reworked in this
branch. There was a TODO left here (by me) with a suggestion to do
some bigger changes as part of the AIR memory reworking. Now that
time has come and I plan to honor the suggestion in a future commit
before merging this branch.
* AIR printing: fix missing ')' on alive instructions.
We're back to "hello world" working for the x86_64 backend.
Additionally: ZIR encoding for floats now supports float literals up to
f64, not only f32. This is because we no longer need a source location
for this instruction.
Previously, this field was used because the Zir.Inst.Ref encoding
supported the concept of references to function parameters. However now
thanks to whole-file-astgen, the implementations of indexToRef and
refToIndex are trivial addition/subtraction of a comptime const integer.
AstGen had the then-else logic backwards for if expressions
on error unions. This commit fixes it.
Turns out AstGen only really needs `is_non_null` and `is_non_err`,
and does not need the `is_null` or `is_err` variants. So I removed the
`is_null{,_ptr}` and `is_err{,_ptr}` ZIR instructions (-4) and
added `is_non_err`, `is_non_err_ptr` ZIR instructions (+2) for
a total of (-2) ZIR instructions, giving us a tiny bit more headroom
within the 256 tag limit. This required swapping the order of
then/else blocks in a handful of cases, but ultimately means the
ZIR will be in the same as source order, which is convenient
when debugging.
AIR code on the other hand, gains the `is_non_err` and `is_non_err_ptr`
instructions.
Sema: fix logic in zirErrUnionCode and zirErrUnionCodePtr returning the
wrong result type.
* ZIR: add two instructions:
- ret_err_value_code
- ret_err_value
* AstGen: add countDefers and utilize it to emit more efficient ZIR for
return expressions in the presence of defers.
* AstGen: implement |err| payloads for `errdefer` syntax.
- There is not an "unused capture" error for it yet.
* AstGen: `return error.Foo` syntax gets a hot path in return
expressions, using the new ZIR instructions. This also is part of
implementing inferred error sets, since we need to tell Sema to add
an error value to the inferred error set before it gets coerced.
* Sema: implement `@setCold`.
- Implement `@setCold` support for C backend.
* `@panic` and regular safety panics such as `unreachable` now properly
invoke `std.builtin.panic`.
* C backend: improve pointer and function value rendering.
* C linker: fix redundant typedefs.
* Add Type.error_set_inferred.
* Fix Value.format for enum_literal, enum_field_index, bytes.
* Remove the C backend test that checks for identical text
I measured a 14% reduction in Total ZIR Bytes from master branch
for std/os.zig.
* Implement "initializing array with struct syntax"
* Implement "'_' used as an identifier without @\"_\" syntax"
* Fix source location of "missing parameter name"
* Update test cases where appropriate
In order to not regress the quality of compile errors, some improvements
had to be made.
* std.zig.parseCharLiteral is improved to return more detailed parse
failure information.
* tokenizer is improved to handle null bytes in the middle of strings,
character literals, and line comments.
* validating how many unicode escape digits in string literals is moved
to std.zig.parseStringLiteral rather than handled in the tokenizer.
* when a tokenizer error occurs, if the reported token is the 'invalid'
tag, an error note is added to point to the invalid byte location.
Further improvements would be:
- Mention the expected set of allowed bytes at this location.
- Display the invalid byte (if printable, print it, otherwise
escape-print it).
The motivation for this commit is that there exists source files which
produce ast-check errors, but crash stage1 or otherwise trigger stage1
bugs. Previously to this commit, Zig would run AstGen, collect the
compile errors, run stage1, report stage1 compile errors and exit if
any, and then report AstGen compile errors.
The main change in this commit is to report AstGen errors prior to
invoking stage1, and in fact if any AstGen errors occur, do not invoke
stage1 at all.
This caused most of the compile error tests to fail due to things such
as unused local variables and mismatched stage1/stage2 error messages.
It was taking a long time to update the test cases one-by-one, so I
took this opportunity to unify the stage1 and stage2 testing harness,
specifically with regards to compile errors. In this way we can start
keeping track of which tests pass for 1, 2, or both.
`zig build test-compile-errors` no longer works; it is now integrated
into `zig build test-stage2`.
This is one step closer to executing compile error tests in parallel; in
fact the ThreadPool object is already in scope.
There are some cases where the stage1 compile errors were actually
better; those are left failing in this commit, to be addressed in a
follow-up commit.
Other changes in this commit:
* build.zig: improve support for -Dstage1 used with the test step.
* AstGen: minor cosmetic changes to error messages.
* stage2: add -fstage1 and -fno-stage1 flags. This now allows one to
download a binary of the zig compiler and use the llvm backend of
self-hosted. This was also needed for hooking up the test harness.
However, I realized that stage1 calls exit() and also has memory
leaks, so had to complicate the test harness by not using this flag
after all and instead invoking as a child process.
- These CLI flags will disappear once we start shipping the
self-hosted compiler as the main compiler. Until then, they can be
used to try out the work-in-progress stage2.
* stage2: select the LLVM backend by default for release modes, as long
as the target architecture is supported by LLVM.
* test harness: support setting the optimize mode
When a local variable has an initialization expression of type
'noreturn', emit a compile error. This brings this branch closer
to parity with master branch.
* AstGen: implement "unreachable code" error for blocks. This works at
the statement level.
* stage1: remove the "unreachable code" error implementation, which
means removing the `is_gen` field from IrInstSrc. This is one small
step towards a smaller memory footprint for stage1. The benefits
won't be realized until a future commit because this flag took
advantage of padding.
There may be a regression here with "union has no associated enum"
error, and there is a regression with the following code:
```zig
const a = noreturn;
```
A future commit will address these regressions.
AstGen was calling findLineColumn() for every sibling Decl, using the
parent Decl as the starting point for the search for newlines. This
resulted in poor performance for large numbers of Decls with the same
parent.
The solution is simple: since AstGen progresses monotonically through
the AST, keep a single cursor into the source file, and whenever
line/column information is needed, advance the cursor. This guarantees
O(N) on the number of bytes in the file.
Perf:
As an example I ran ast-check on zigwin32/win32/everything.zig
(a 17 MiB file) in master branch, and after this commit.
With master branch, I killed the process after 17 seconds out of
boredom. With this commit, it completed in 300 milliseconds.
Closes#9234
Before this, the continue expression of a while loop did not have the
capture variable in it, making it incorrectly emit a compile error for
not using the capture, even if it was referenced.
* Remove parser error on double ampersand
* Add failing test for double ampersand case
* Add error when encountering double ampersand in AstGen
"Bit and" operator should not make sense when one of its operands
is an address.
* Check that 2 ampersands are adjacent to each other in source string
* Remove cases of unused variables in tests
`return` statements use a new function `nodeMayEvalToError` which does
some basic checks on the AST node to return never, always, or maybe.
Depending on this result, AstGen skips the errdefers, always includes
the errdefers, or emits a conditional branch to check whether the return
value is an error that Sema will have to evaluate.
Closes#8821
Unblocks #9047
The Zig language specification will support identifiers and field access
in order to refer to which declaration to export with `@export`.
This commit implements the change in AstGen and updates the language
reference.