The WebAssembly spec requires signed LEB128 to be encoded up to a maximum number of bytes (max 5 bytes for i32, max 10 bytes for i64) and that "unused" bits are all 0 if the number is positive and all 1 if the number is negative. The Zig LEB128 implementation already enforces the max number of bytes and does check the unused bytes https://github.com/ziglang/zig/blob/master/lib/std/leb128.zig#L70-L79.
However, the WebAssembly test suite has a number of tests that were failing validation (expecting the wasm module to fail validation, but when running the tests, those examples were actually passing validation):
https://github.com/malcolmstill/foxwren/blob/master/test/testsuite/binary-leb128.wast#L893-L902https://github.com/malcolmstill/foxwren/blob/master/test/testsuite/binary-leb128.wast#L934-L943
Notably the failures are both cases of negative numbers and the top 4 bits of the last byte are zero. And I believe this is the issue: we're only currently checking the "unused" / remaining_bits if we overflow, but in the case of 0x0_ no overflow happens and so the bits go unchecked.
In other words:
\xff\xff\xff\xff\7f rightly successfully decodes (because it overflows and the remaining bits are 0b1111)
\xff\xff\xff\xff\6f rightly errors with overflow (because it overflows and the remaining bits are 0b1110)
\xff\xff\xff\xff\0f incorrectly decodes when it should error (because the top 4 bits are all 0, and so no overflow occurs and no check that the unused bits are 1 happens)
This PR adds a the remaining_bits check in an else branch of the @shlWithOverflow when we're looking at the last byte and the number being decoded is negative.
Note: this means a couple of the test cases in leb128.zig that are down as decoding shouldn't actually decode so I added the appropriate 1 bits.
I believe these are Linux specific so they will need to be os-gated
in `elf.zig` at some point, but I reckon it should be fine to have
them as-is right now since the ELF linker work will mainly be done
on x86-64 Linux at first.
* test runner is improved to respect `error.SkipZigTest`
* start code is improved to `@setAlignStack(16)` before calling main()
* the newly passing behavior test has a workaround for the fact that
stage2 cannot yet call `std.Target.x86.featureSetHas()` at comptime.
This is blocking on comptime closures. The workaround is that there
is a new decl `@import("builtin").stage2_x86_cx16` which is a `bool`.
* Implement `@setAlignStack`. This language feature should be re-evaluated
at some point - I'll file an issue for it.
* LLVM backend: apply/remove the cold attribute and noinline attribute
where appropriate.
* LLVM backend: loads and stores are properly annotated with alignment
and volatile attributes.
* LLVM backend: allocas are properly annotated with alignment.
* Type: fix integers reporting wrong alignment for 256-bit integers and
beyond. Once you get to 16 byte aligned, there is no further
alignment for larger integers.
Investigating hexops/zorex#4, I found that `--test-evented-io` is currently broken in
the latest Zig nightly. See #9779 for a small reproduction.
The issue is that allocation errors here are not correctly handled, as this function
returns `void` and all other error cases `@panic`, the allocation failure should also
use `@panic`.
Fixes#9779
Helps hexops/zorex#4
Signed-off-by: Stephen Gutekanst <stephen@hexops.com>
Some systems (Solaris, OpenBSD, AIX) change their definitions of
sockaddr_storage to be larger than 128 bytes. This comment adds a new
constant in the `sockaddr` that defines the size for every system.
Fixes#9759
The entire 'path' array would get written to the formatting function,
when it should instead be treated as a regular zero-terminated string.
Note that this doesn't handle abstract paths on Linux, those paths
*start* with a \0 byte and are hence treated as empty strings instead.
But fixing that would require more adjustments than just formatting, in
particular to getOsSockLen().
* add functions to decode an epoch timestamp
The code added here is alternative to the libc gmtime function. This function takes a unix epoch timestamp and decodes it into things like the year/day/time/etc. I looked at various libc implementations to see how it was implemented and this appears to be correct. I reorganized it so that applications can choose which data they need rather than calcualting it all in a single function. The data structures layout the order of operations required to decode various things like the year/month or time of day.
* set Month.jan to 1 instead of 0 to avoid +1 in conversion to numeric
* add another test
* remove unnecessary comptimeMod
Extract existing constants to do with TCP socket options into a 'TCP'
namespace.
Export 'MSG' and 'TCP' from std.os.{linux, windows} into std.c.
Fix compile errors to do with std.x.os.Socket methods related to setting
TCP socket options.
Handle errors in the case that an interface could not be resolved in an
IPv6 address on Windows. Tested using Wine with the loopback interface
disabled.
Have all instantiations of std.x.os.Socket on Windows instantiate an
overlapped socket descriptor. Fixes the '1ms read timeout' test in
std.x.net.tcp.Client. The test would previously deadlock, as read
timeouts only apply to overlapped sockets.
Windows documentation by default recommends that most instantiations of
sockets on Windows be overlapped sockets (s.t. they may operate in both
blocking or nonblocking mode when operated with WSA* syscalls). Refer to
the documentation for WSASocketA for more info.
OpenBSD doesn't implement EVFILT_USER filter for kqueue(2), so we couldn't use that for event loop.
instead, use a EVFILT_TIMER filter with EV_ONESHOT (trigger only once) and delay 0sec (which trigger immediatly).
it fits the usage of EVFILT_USER which is only used to "wakeup" the kevent(2) call from userland.
I incorrectly assumed that __kernel_timespec was used when not linking
libc, however that is not the case. `std.os.timespec` is used both for
libc and non-libc cases. `__kernel_timespec` is a special struct that is
used only for io_uring.
Tests with no names are executed when using `zig test` regardless of the
`--test-filter` used. Non-named tests should be used when simply
importing unit tests from another file. This allows `zig test` to find
all the appropriate tests, even when using `--test-filter`.