Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions .github/workflows/coverage.yml
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,7 @@ jobs:
# this is a visibility job, not a gate.
run: |
cargo llvm-cov --workspace --no-fail-fast \
--exclude perry-doc-fixture-my-bindings \
--exclude perry-ui-macos \
--exclude perry-ui-ios \
--exclude perry-ui-visionos \
Expand All @@ -64,6 +65,7 @@ jobs:
--exclude perry-ui-windows \
--html --output-dir target/llvm-cov-html
cargo llvm-cov report --no-fail-fast \
--exclude perry-doc-fixture-my-bindings \
--exclude perry-ui-macos \
--exclude perry-ui-ios \
--exclude perry-ui-visionos \
Expand All @@ -74,6 +76,7 @@ jobs:
--exclude perry-ui-windows \
--lcov --output-path target/lcov.info
cargo llvm-cov report --no-fail-fast \
--exclude perry-doc-fixture-my-bindings \
--exclude perry-ui-macos \
--exclude perry-ui-ios \
--exclude perry-ui-visionos \
Expand Down
45 changes: 34 additions & 11 deletions .github/workflows/test.yml
Original file line number Diff line number Diff line change
Expand Up @@ -189,18 +189,41 @@ jobs:
RUST_TEST_THREADS=1 cargo test -p perry-runtime
# The remaining workspace includes large `perry` / `perry-stdlib`
# test binaries. Keep Cargo build jobs serialized so the runner
# does not link several of those large test binaries at once.
# does not link several of those large test binaries at once, then
# run packages one at a time and prune linked test executables so
# target/debug/deps does not exhaust the runner disk mid-job.
export CARGO_BUILD_JOBS=1
cargo test --workspace \
--exclude perry-runtime \
--exclude perry-ui-macos \
--exclude perry-ui-ios \
--exclude perry-ui-visionos \
--exclude perry-ui-tvos \
--exclude perry-ui-watchos \
--exclude perry-ui-gtk4 \
--exclude perry-ui-android \
--exclude perry-ui-windows
workspace_packages="$(
cargo metadata --no-deps --format-version 1 | python3 -c '
import json
import sys

excluded = {
"perry-runtime",
"perry-ui-macos",
"perry-ui-ios",
"perry-ui-visionos",
"perry-ui-tvos",
"perry-ui-watchos",
"perry-ui-gtk4",
"perry-ui-android",
"perry-ui-windows",
"perry-doc-fixture-my-bindings",
}
metadata = json.load(sys.stdin)
workspace_members = set(metadata["workspace_members"])
for package in metadata["packages"]:
if package["id"] in workspace_members and package["name"] not in excluded:
print(package["name"])
'
)"

for package in $workspace_packages; do
echo "::group::cargo test -p $package"
cargo test -p "$package"
echo "::endgroup::"
find target/debug/deps -maxdepth 1 -type f -perm -111 ! -name '*.so' -delete
done

# ---------------------------------------------------------------------------
# Compiler-output regression gate
Expand Down
202 changes: 202 additions & 0 deletions crates/perry-api-manifest/src/entries.rs
Original file line number Diff line number Diff line change
Expand Up @@ -71,6 +71,7 @@ pub const NATIVE_MODULES: &[&str] = &[
"path/posix",
"path/win32",
"console",
"constants",
"util",
"util/types",
"url",
Expand Down Expand Up @@ -2144,6 +2145,207 @@ pub static API_MANIFEST: &[ApiEntry] = &[
// get_native_module_constant in perry-runtime/src/object.rs.
property("os", "constants"),
property("crypto", "constants"),
// Deprecated `node:constants` flat alias. It mirrors the fs/os/crypto
// constants that Perry already exposes under module-specific
// `*.constants` namespaces.
property("constants", "F_OK"),
property("constants", "R_OK"),
property("constants", "W_OK"),
property("constants", "X_OK"),
property("constants", "O_RDONLY"),
property("constants", "O_WRONLY"),
property("constants", "O_RDWR"),
property("constants", "O_NOFOLLOW"),
property("constants", "O_CREAT"),
property("constants", "O_TRUNC"),
property("constants", "O_APPEND"),
property("constants", "O_EXCL"),
property("constants", "COPYFILE_EXCL"),
property("constants", "COPYFILE_FICLONE"),
property("constants", "COPYFILE_FICLONE_FORCE"),
property("constants", "S_IRUSR"),
property("constants", "S_IWUSR"),
property("constants", "S_IXUSR"),
property("constants", "S_IRGRP"),
property("constants", "S_IWGRP"),
property("constants", "S_IXGRP"),
property("constants", "S_IROTH"),
property("constants", "S_IWOTH"),
property("constants", "S_IXOTH"),
property("constants", "SIGHUP"),
property("constants", "SIGINT"),
property("constants", "SIGQUIT"),
property("constants", "SIGILL"),
property("constants", "SIGTRAP"),
property("constants", "SIGABRT"),
property("constants", "SIGIOT"),
property("constants", "SIGBUS"),
property("constants", "SIGFPE"),
property("constants", "SIGKILL"),
property("constants", "SIGUSR1"),
property("constants", "SIGSEGV"),
property("constants", "SIGUSR2"),
property("constants", "SIGPIPE"),
property("constants", "SIGALRM"),
property("constants", "SIGTERM"),
property("constants", "SIGCHLD"),
property("constants", "SIGCONT"),
property("constants", "SIGSTOP"),
property("constants", "SIGTSTP"),
property("constants", "SIGTTIN"),
property("constants", "SIGTTOU"),
property("constants", "SIGURG"),
property("constants", "SIGXCPU"),
property("constants", "SIGXFSZ"),
property("constants", "SIGVTALRM"),
property("constants", "SIGPROF"),
property("constants", "SIGWINCH"),
property("constants", "SIGIO"),
property("constants", "SIGSYS"),
property("constants", "E2BIG"),
property("constants", "EACCES"),
property("constants", "EADDRINUSE"),
property("constants", "EADDRNOTAVAIL"),
property("constants", "EAFNOSUPPORT"),
property("constants", "EAGAIN"),
property("constants", "EALREADY"),
property("constants", "EBADF"),
property("constants", "EBADMSG"),
property("constants", "EBUSY"),
property("constants", "ECANCELED"),
property("constants", "ECHILD"),
property("constants", "ECONNABORTED"),
property("constants", "ECONNREFUSED"),
property("constants", "ECONNRESET"),
property("constants", "EDEADLK"),
property("constants", "EDESTADDRREQ"),
property("constants", "EDOM"),
property("constants", "EDQUOT"),
property("constants", "EEXIST"),
property("constants", "EFAULT"),
property("constants", "EFBIG"),
property("constants", "EHOSTUNREACH"),
property("constants", "EIDRM"),
property("constants", "EILSEQ"),
property("constants", "EINPROGRESS"),
property("constants", "EINTR"),
property("constants", "EINVAL"),
property("constants", "EIO"),
property("constants", "EISCONN"),
property("constants", "EISDIR"),
property("constants", "ELOOP"),
property("constants", "EMFILE"),
property("constants", "EMLINK"),
property("constants", "EMSGSIZE"),
property("constants", "EMULTIHOP"),
property("constants", "ENAMETOOLONG"),
property("constants", "ENETDOWN"),
property("constants", "ENETRESET"),
property("constants", "ENETUNREACH"),
property("constants", "ENFILE"),
property("constants", "ENOBUFS"),
property("constants", "ENODATA"),
property("constants", "ENODEV"),
property("constants", "ENOENT"),
property("constants", "ENOEXEC"),
property("constants", "ENOLCK"),
property("constants", "ENOLINK"),
property("constants", "ENOMEM"),
property("constants", "ENOMSG"),
property("constants", "ENOPROTOOPT"),
property("constants", "ENOSPC"),
property("constants", "ENOSR"),
property("constants", "ENOSTR"),
property("constants", "ENOSYS"),
property("constants", "ENOTCONN"),
property("constants", "ENOTDIR"),
property("constants", "ENOTEMPTY"),
property("constants", "ENOTSOCK"),
property("constants", "ENOTSUP"),
property("constants", "ENOTTY"),
property("constants", "ENXIO"),
property("constants", "EOPNOTSUPP"),
property("constants", "EOVERFLOW"),
property("constants", "EPERM"),
property("constants", "EPIPE"),
property("constants", "EPROTO"),
property("constants", "EPROTONOSUPPORT"),
property("constants", "EPROTOTYPE"),
property("constants", "ERANGE"),
property("constants", "EROFS"),
property("constants", "ESPIPE"),
property("constants", "ESRCH"),
property("constants", "ESTALE"),
property("constants", "ETIME"),
property("constants", "ETIMEDOUT"),
property("constants", "ETXTBSY"),
property("constants", "EWOULDBLOCK"),
property("constants", "EXDEV"),
property("constants", "PRIORITY_LOW"),
property("constants", "PRIORITY_BELOW_NORMAL"),
property("constants", "PRIORITY_NORMAL"),
property("constants", "PRIORITY_ABOVE_NORMAL"),
property("constants", "PRIORITY_HIGH"),
property("constants", "PRIORITY_HIGHEST"),
property("constants", "RTLD_LAZY"),
property("constants", "RTLD_NOW"),
property("constants", "RTLD_GLOBAL"),
property("constants", "RTLD_LOCAL"),
property("constants", "RTLD_DEEPBIND"),
property("constants", "OPENSSL_VERSION_NUMBER"),
property("constants", "SSL_OP_ALL"),
property("constants", "SSL_OP_ALLOW_NO_DHE_KEX"),
property("constants", "SSL_OP_ALLOW_UNSAFE_LEGACY_RENEGOTIATION"),
property("constants", "SSL_OP_CIPHER_SERVER_PREFERENCE"),
property("constants", "SSL_OP_CISCO_ANYCONNECT"),
property("constants", "SSL_OP_COOKIE_EXCHANGE"),
property("constants", "SSL_OP_CRYPTOPRO_TLSEXT_BUG"),
property("constants", "SSL_OP_DONT_INSERT_EMPTY_FRAGMENTS"),
property("constants", "SSL_OP_LEGACY_SERVER_CONNECT"),
property("constants", "SSL_OP_NO_COMPRESSION"),
property("constants", "SSL_OP_NO_ENCRYPT_THEN_MAC"),
property("constants", "SSL_OP_NO_QUERY_MTU"),
property("constants", "SSL_OP_NO_RENEGOTIATION"),
property("constants", "SSL_OP_NO_SESSION_RESUMPTION_ON_RENEGOTIATION"),
property("constants", "SSL_OP_NO_SSLv2"),
property("constants", "SSL_OP_NO_SSLv3"),
property("constants", "SSL_OP_NO_TICKET"),
property("constants", "RSA_PKCS1_PADDING"),
property("constants", "SSL_OP_NO_TLSv1"),
property("constants", "SSL_OP_NO_TLSv1_1"),
property("constants", "SSL_OP_NO_TLSv1_2"),
property("constants", "SSL_OP_NO_TLSv1_3"),
property("constants", "SSL_OP_PRIORITIZE_CHACHA"),
property("constants", "SSL_OP_TLS_ROLLBACK_BUG"),
property("constants", "ENGINE_METHOD_RSA"),
property("constants", "ENGINE_METHOD_DSA"),
property("constants", "ENGINE_METHOD_DH"),
property("constants", "ENGINE_METHOD_RAND"),
property("constants", "ENGINE_METHOD_EC"),
property("constants", "ENGINE_METHOD_CIPHERS"),
property("constants", "ENGINE_METHOD_DIGESTS"),
property("constants", "ENGINE_METHOD_PKEY_METHS"),
property("constants", "ENGINE_METHOD_PKEY_ASN1_METHS"),
property("constants", "ENGINE_METHOD_ALL"),
property("constants", "ENGINE_METHOD_NONE"),
property("constants", "DH_CHECK_P_NOT_SAFE_PRIME"),
property("constants", "DH_CHECK_P_NOT_PRIME"),
property("constants", "DH_UNABLE_TO_CHECK_GENERATOR"),
property("constants", "DH_NOT_SUITABLE_GENERATOR"),
property("constants", "RSA_NO_PADDING"),
property("constants", "RSA_PKCS1_OAEP_PADDING"),
property("constants", "RSA_X931_PADDING"),
property("constants", "RSA_PKCS1_PSS_PADDING"),
property("constants", "RSA_PSS_SALTLEN_DIGEST"),
property("constants", "RSA_PSS_SALTLEN_MAX_SIGN"),
property("constants", "RSA_PSS_SALTLEN_AUTO"),
property("constants", "TLS1_VERSION"),
property("constants", "TLS1_1_VERSION"),
property("constants", "TLS1_2_VERSION"),
property("constants", "TLS1_3_VERSION"),
property("constants", "POINT_CONVERSION_COMPRESSED"),
property("constants", "POINT_CONVERSION_UNCOMPRESSED"),
property("constants", "POINT_CONVERSION_HYBRID"),
// path — methods mapped to Expr::Path* in expr_call.rs.
method("path", "join", false, None),
method("path", "dirname", false, None),
Expand Down
21 changes: 21 additions & 0 deletions crates/perry-api-manifest/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -299,6 +299,27 @@ mod tests {
assert!(matches!(entry.returns, TypeSpec::Bool));
}

#[test]
fn deprecated_constants_alias_has_manifest_entries() {
for name in [
"F_OK",
"SIGTERM",
"SIGINT",
"EACCES",
"PRIORITY_NORMAL",
"RTLD_DEEPBIND",
"RSA_PKCS1_PADDING",
"SSL_OP_NO_SSLv2",
"SSL_OP_NO_TLSv1",
"POINT_CONVERSION_COMPRESSED",
"POINT_CONVERSION_UNCOMPRESSED",
] {
let entry = module_has_symbol("node:constants", name)
.expect("node:constants representative property should be in the manifest");
assert!(matches!(entry.kind, ApiKind::Property));
}
}

#[test]
fn known_modules_consistent_with_manifest() {
// Every entry's module must appear in NATIVE_MODULES.
Expand Down
15 changes: 11 additions & 4 deletions crates/perry-codegen/src/ext_registry.rs
Original file line number Diff line number Diff line change
Expand Up @@ -317,13 +317,17 @@ pub fn take_used_providers() -> HashSet<OwnerKind> {
mod tests {
use super::*;

static PROVIDER_TEST_LOCK: Mutex<()> = Mutex::new(());

// `USED_PROVIDERS` is a process-wide static; other tests in the same
// process may concurrently insert into it via `LlBlock::call`. We
// therefore check membership rather than exact set equality. The
// non-registered-FFI check uses a deliberately unique symbol name
// that no other test will ever insert.
// process may concurrently insert into it via `LlBlock::call`, and these
// module tests drain it. Serialize the explicit drain/record assertions so
// one test cannot steal another test's providers.
#[test]
fn registry_dispatch_routes_to_correct_owner() {
let _guard = PROVIDER_TEST_LOCK
.lock()
.expect("provider test lock poisoned");
// Drain anything left over from prior tests.
let _ = take_used_providers();

Expand Down Expand Up @@ -380,6 +384,9 @@ mod tests {
/// `Undefined symbols: _js_node_http_create_server_with_options`.
#[test]
fn emitted_create_server_symbol_routes_to_http() {
let _guard = PROVIDER_TEST_LOCK
.lock()
.expect("provider test lock poisoned");
let _ = take_used_providers();
record_ffi_call("js_node_http_create_server_with_options");
let got = take_used_providers();
Expand Down
Loading