Repository navigation
OpenBSD and Windows: make ci portability batch - #3645
Merged
Merged
Conversation
OpenBSD's userland differs from GNU/macOS/FreeBSD in ways a test script must not depend on, and each showed up as a failure that read as a product bug: - tests/lib/syslibs.sh: -ldl and -lrt only on Linux (BSDs and macOS have dlopen and shm in libc; the linker fails outright on -ldl there). - tests/lib/portable.sh: head_c (no head -c), sha256_of (no shasum), copy_listed (no tar -T), dyn_syms (nm -D/-gU/-g), file_desc (file prints "data" for wasm/COFF/Mach-O and "AArch64"), od_uint (od zero-pads -tu). - 75 `grep "a\|b"` became `grep -E "a|b"`: OpenBSD's grep reads `\|` as a literal pipe, so the warnings filter of ~35 tests let warnings into compared output and positive matches never matched. - `\b`, `\s` became POSIX classes; `grep -r --exclude=NAME` became find. - http_proxy_direct_equivalence compares Content-Length after the port rewrite (the echoed body holds the port; OpenBSD's ephemeral range includes four-digit ports). Co-Authored-By: Claude <noreply@anthropic.com>
… stdio slot, LibreSSL SSL_CERT_FILE Four gaps the test suite exposed (see the changelog fragment): - ae: the -ldl codegen's link table names for std.audio is dropped on OpenBSD (dlopen is in libc; no libdl exists). - ae checksec: __retguard_* / __stack_smash_handler count as the stack canary; OpenBSD's clang emits no __stack_chk_fail for a plain array. - std.os: on OpenBSD/NetBSD a pipe's stat is dev 0/ino 0 and its time is a 10 ms clock, so a spawn pipe that took a closed stdout's number within a tick of process start passed for the stream and was handed to the child. A stream that was not close-on-exec at start no longer matches one that is. - std.http client: LibreSSL ignores SSL_CERT_FILE/SSL_CERT_DIR in SSL_CTX_set_default_verify_paths; name them explicitly, as OpenSSL and the pure-Aether client do. Co-Authored-By: Claude <noreply@anthropic.com>
- x509 -req signs with SHA-1 under LibreSSL, which the pure TLS stack
rightly refuses ("does not chain to a trusted anchor"): pass -sha256.
- s_client's LibreSSL output names the version "TLSv1/SSLv3" on success and
"(NONE)" on failure: https_tls_backend_select reads that.
- openssl_is_libressl / openssl_has_option (tests/lib/test_openssl_conf.sh):
skip, naming the reason, what needs ssl_conf (https_openssl_policy),
s_server -cert_chain (https_partial_chain), s_client -sigalgs
(crypto_tls13_signature_check and a case of https_pure_server_keys) or
Ed25519 certificates in TLS (a case of https_pure_server_keys).
Co-Authored-By: Claude <noreply@anthropic.com>
- ae_download_api_fallback: no release build for the host ("Platform: unsupported").
- musl targets (cross_linux_musl, cross_riscv64_loongarch64, sqlite_vendored_cross,
and the cross legs of c_include_directive and source_directive): only when
zig reports it could not build musl's libc.a, which it cannot on OpenBSD.
- cross_emit_lib: no target triple whose binary runs on OpenBSD/NetBSD.
- http_ipv6: OpenBSD's sockets are IPv6-only, so "::" is not dual-stack.
- string_into_c_memory / ownership_grid: no malloc_usable_size on OpenBSD.
- sandbox_toolchain: spawn_sandboxed is Linux and FreeBSD only.
- checksec_hardening: libc has no __*_chk, so FORTIFY is asserted to be "no".
- killed_compiler_diagnostic: kill the stand-in with SIGKILL; ksh answers a
SIGTERM to itself with exit 143, which is an exit, not a signal death.
Co-Authored-By: Claude <noreply@anthropic.com>
The nesting scan read each line with substr($0, i, 1). The awk of OpenBSD rescans the line from its start on every call, and these lines hold 1000-link constant chains: 5m52s alone, past the 420s per-test limit once the suite ran in parallel. One split() per line: 10s. Co-Authored-By: Claude <noreply@anthropic.com>
The test pushed the C command line past cmd.exe's 8191 cap with 25 --extra paths of a fixed deep directory. Under a temp directory like MSYS2's C:/msys64/tmp each path came to about 270 characters, past Windows' MAX_PATH, so cc1 could open them only where long paths are enabled machine-wide (LongPathsEnabled, set on GitHub's runners, off by default and on the win11 lab host): there it failed "No such file or directory" on every part, before the response file the test is about was ever in question. The deep directory is now sized from the temp directory's own length, so each path is about 240 characters wherever TMP is, and as many parts are added as keep the --extra list under ae's 8 KiB cap. The build runs --verbose and the test checks ae says it wrote a response file, so the command line is shown to be past the cap rather than assumed to be. Co-Authored-By: Claude <noreply@anthropic.com>
…e's name The avcodec check is meant to stay off Windows (ae links -static there and MSYS2's static FFmpeg needs its whole dependency closure), and was gated on $EXE being ".exe". $EXE came from a name probe, `[ ! -x build/ae ]`, which MSYS2 answers true for build/ae.exe, so it stayed empty and the check ran wherever MSYS2's FFmpeg is installed: on the win11 lab host it failed with undefined soxr_* references from libswresample.a. CI's Windows job installs no FFmpeg, so it never got that far. Gated on uname now, as the other Windows-aware tests are. $EXE is left as it was, so the direct-link check, which passes on Windows, still runs there. Co-Authored-By: Claude <noreply@anthropic.com>
… gsub
max_seq_depth stripped every non-bracket from each generated line with
gsub(/[^][(){}]/, ""). MSYS2's gawk 5.4.0 takes 32 s for that on one of the
150 KB lines of the 1000-link chains (5.4.1 takes 0.4 s), and the test reads
seven such lines: it ran 262 s alone on the win11 lab host and past the
sweep's 420 s limit under load. The macros are now spelled out by sed and
the brackets kept by tr, so awk only walks the brackets: 12 s on the same
host with gawk 5.4.0 (181 s before), the same depths on macOS (2 4 5 5 5 5 8 7 5 5).
Co-Authored-By: Claude <noreply@anthropic.com>
…ndshake server.ae and kuserver.ae closed the socket of a refused handshake with tcp.close, while the library's own entry closes it with tcp.close_drained (#3465). What the client sent after the refused record is still unread then (in "server HRR: two change_cipher_spec records", the second CCS), so the close ends with a reset, and on Windows that reset can take the alert from the client before it reads it: the case saw "HRR CLOSED" for "HRR ALERT 10". On the win11 lab host, 25 runs of that case: 8 failed with the plain close, none drained. Co-Authored-By: Claude <noreply@anthropic.com>
Each program is the whole pure TLS stack in one C file. GCC on Windows compiled each in 18-23 s at -O2 (2-4 s on macOS), one after another, so the builds alone took 168 s of the test's 440 on the win11 lab host (468 s with its older MSYS2), past the sweep's 420 s limit under load; CI's 4-core runner took 311 s. They now build in parallel with --quick (-O0 -g): 7-9 s each there, and the cases, which check the bytes on the wire, take the same time (about 1 s a handshake either way). The whole test: 242 s on win11 from a cold cache, 90 s on macOS (101 before). Every build is waited for before a failed one ends the test, so none still writes into $TMP as it is removed. Co-Authored-By: Claude <noreply@anthropic.com>
deep_constants, deep_nesting, block_nesting_cc and operator_chain_nesting measure the bracket depth of generated C with an awk loop that takes substr($0, i, 1) for each character. Under a UTF-8 locale (MSYS2's default, en_US.UTF-8, and CI's Windows runner) gawk's substr counts characters from the start of the line on every call, so the walk is quadratic in a line. deep_constants' consts.c has lines of 245 KB: its awk took 361 s on the win11 lab host (the test 367 s alone, 771 s beside three others, past the sweep's 420 s limit) and the test 292 s on CI's Windows runner. With LC_ALL=C the same awk takes 6 s and the test 14 s on win11. The walks only compare ASCII characters, which no byte of a UTF-8 multibyte character equals, so the depths are the same (51, 1018, and the rest, on macOS and win11). Co-Authored-By: Claude <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
One batch, a commit per fix, from running
make cion OpenBSD 8.0 and Windows 11 (MSYS2) lab hosts.OpenBSD (65 failures to 0: 2153 pass, 67 skip)
Product fixes (842e5fe):
std.audiolinks without-ldlwhere libc carriesdlopen.checksecreads RETGUARD as the stack-protector evidence.SSL_CERT_FILEis honoured under LibreSSL.Tests:
grep "a\|b").openssl.deep_constantsscans its C bysplit, notsubstrper character.Windows
Test fixes only:
win_batch_compiler_long_cmdlinekeeps each path under MAX_PATH.release_contrib_c_modulesskips avcodec on Windows byuname.operator_chain_nestingand the bracket-depth walks avoid slow gawk paths and run in the C locale.crypto_tls13_peerbuilds its seven programs at once at-O0, and its test servers drain before closing a refused handshake.Verification (
make cion this branch)-WerrorThe Windows failure is
no_threads_refsreaching the 420 s per-test limit during the full sweep. It is untouched by this branch and passes alone on the same VM in 382 s, so it is slow on that 4-core VM, not hung; left as is.Closes no issues.
🤖 Generated with Claude Code