diff --git a/.bazelrc b/.bazelrc index 53b505bd8..03aaff9e1 100644 --- a/.bazelrc +++ b/.bazelrc @@ -57,8 +57,9 @@ build:toolchain_common --extra_toolchains=@score_toolchains_rust//toolchains/fer build:stub --@score_baselibs//score/mw/log/flags:KRemote_Logging=False build:stub --@score_baselibs//score/json:base_library=nlohmann -# Target configuration for running integration tests on localhost -build:host --define config=host +# Target configuration for running tests on localhost +build:host --//config:integration_mode=host +build:host --//config:unit_mode=host # Target configuration for CPU:x86-64|OS:Linux build (do not use it in case of system toolchains!) build:x86_64-linux --config=stub @@ -67,7 +68,9 @@ build:x86_64-linux --platforms=@score_bazel_platforms//:x86_64-linux-gcc_12.2.0- build:x86_64-linux --extra_toolchains=@score_gcc_x86_64_toolchain//:x86_64-linux-gcc_12.2.0 build:x86_64-linux --extra_toolchains=@score_toolchains_rust//toolchains/ferrocene:ferrocene_x86_64_unknown_linux_gnu build:x86_64-linux --extra_toolchains=@score_toolchains_rust//toolchains/ferrocene:ferrocene_x86_64_unknown_linux_gnu_miri -build:x86_64-linux --define config=x86_64-linux + +test:x86_64-linux --//config:integration_mode=docker +test:x86_64-linux --//config:unit_mode=host # Target configuration for CPU:AArch64|OS:Linux build (do not use it in case of system toolchains!) build:arm64-linux --config=stub @@ -79,6 +82,9 @@ build:arm64-linux --extra_toolchains=@score_toolchains_rust//toolchains/ferrocen build:arm64-linux --copt=-mno-outline-atomics build:arm64-linux --linkopt=-latomic +test:arm64-linux --//config:integration_mode=docker +test:arm64-linux --//config:unit_mode=host + # Target configuration for CPU:x86-64|OS:QNX build (do not use it in case of system toolchains!) build:x86_64-qnx --config=stub build:x86_64-qnx --config=toolchain_common @@ -86,9 +92,15 @@ build:x86_64-qnx --platforms=@score_bazel_platforms//:x86_64-qnx-sdp_8.0.0-posix build:x86_64-qnx --extra_toolchains=@score_qcc_x86_64_toolchain//:x86_64-qnx-sdp_8.0.0 build:x86_64-qnx --extra_toolchains=@score_toolchains_rust//toolchains/ferrocene:ferrocene_x86_64_pc_nto_qnx800 build:x86_64-qnx --extra_toolchains=@score_qnx_x86_64_ifs_toolchain//:ifs-x86_64-qnx-sdp_8.0.0 -test:x86_64-qnx --run_under=@score_qnx_unit_tests//src:run_under_qnx -test:x86_64-qnx --test_tag_filters=-skip_local # see https://github.com/eclipse-score/lifecycle/issues/272 -test:x86_64-qnx --test_lang_filters=cc,rust + +test:x86_64-qnx --//config:integration_mode=qemu +test:x86_64-qnx --//config:unit_mode=skip + +build:unit-tests-x86_64-qnx --config=x86_64-qnx + +test:unit-tests-x86_64-qnx --run_under=@score_qnx_unit_tests//src:run_under_qnx +test:unit-tests-x86_64-qnx --//config:integration_mode=skip +test:unit-tests-x86_64-qnx --//config:unit_mode=qemu # Target configuration for CPU:AArch64|OS:QNX build (do not use it in case of system toolchains!) build:arm64-qnx --config=stub @@ -98,11 +110,15 @@ build:arm64-qnx --platforms=@score_bazel_platforms//:aarch64-qnx-sdp_8.0.0-posix build:arm64-qnx --extra_toolchains=@score_qcc_aarch64_toolchain//:aarch64-qnx-sdp_8.0.0 build:arm64-qnx --extra_toolchains=@score_toolchains_rust//toolchains/ferrocene:ferrocene_aarch64_unknown_nto_qnx800 build:arm64-qnx --extra_toolchains=@score_qnx_aarch64_ifs_toolchain//:ifs-aarch64-qnx-sdp_8.0.0 -test:arm64-qnx --run_under=@score_qnx_unit_tests//src:run_under_qnx -test:arm64-qnx --test_tag_filters=-skip_local # see https://github.com/eclipse-score/lifecycle/issues/272 -test:arm64-qnx --test_timeout=300 -test:arm64-qnx --test_lang_filters=cc,rust +test:arm64-qnx --//config:integration_mode=qemu +test:arm64-qnx --//config:unit_mode=skip + +build:unit-tests-arm64-qnx --config=arm64-qnx + +test:unit-tests-arm64-qnx --run_under=@score_qnx_unit_tests//src:run_under_qnx +test:unit-tests-arm64-qnx --//config:integration_mode=skip +test:unit-tests-arm64-qnx --//config:unit_mode=qemu # Ferrocene Rust coverage config build:ferrocene-coverage --@rules_rust//rust/settings:extra_rustc_flag=-Cinstrument-coverage diff --git a/.github/workflows/qnx8.yml b/.github/workflows/qnx8.yml index b40d85d59..662a60b5f 100644 --- a/.github/workflows/qnx8.yml +++ b/.github/workflows/qnx8.yml @@ -29,11 +29,13 @@ jobs: matrix: include: - bazel-config: x86_64-qnx - bazel-test-target: >- - //score/... + bazel-test-target: //examples/... //score/... //tests/... + - bazel-config: unit-tests-x86_64-qnx + bazel-test-target: //examples/... //score/... //tests/... - bazel-config: arm64-qnx - bazel-test-target: >- - //score/... + bazel-test-target: //examples/... //score/... //tests/... + - bazel-config: unit-tests-arm64-qnx + bazel-test-target: //examples/... //score/... //tests/... extra-bazel-test-flags: "--test_timeout=120,600,1800,7200" # Increase test timeout due to QEMU emulation uses: eclipse-score/cicd-workflows/.github/workflows/qnx-build.yml@473c10b74361afb7506a5d35ea554030753d5594 permissions: diff --git a/BUILD b/BUILD index 0e81af46c..9cf660fb9 100644 --- a/BUILD +++ b/BUILD @@ -38,7 +38,6 @@ compile_pip_requirements( src = "requirements.in", data = [ "//scripts/config_mapping:pip_requirements", - "//tests/integration:pip_requirements", ], extra_args = [ "--no-annotate", diff --git a/MODULE.bazel b/MODULE.bazel index e6ededc57..fbc7db1a4 100644 --- a/MODULE.bazel +++ b/MODULE.bazel @@ -160,6 +160,10 @@ pip.parse( use_repo(pip, "score_lifecycle_pip") bazel_dep(name = "score_itf", version = "0.5.0", dev_dependency = True) +single_version_override( + module_name = "score_itf", + patches = ["//patches:itf.patch"], +) oci = use_extension("@rules_oci//oci:extensions.bzl", "oci", dev_dependency = True) oci.pull( diff --git a/README.md b/README.md index a417e163a..30198b92b 100644 --- a/README.md +++ b/README.md @@ -122,6 +122,22 @@ bazel build --config=x86_64-qnx //... bazel build --config=arm64-qnx //... ``` +Integration tests via [QEMU](https://www.qemu.org/): + +```sh +bazel test --config=x86_64-qnx //tests/integration/... +``` + +Unit tests via [QEMU](https://www.qemu.org/): + +```sh +bazel test --config=unit-tests-x86_64-qnx //score/... +``` + +A different flag is needed for unit tests because the emulation is configured +using `--run_under`, which applies to all targets, even those that should run +natively on the host. + **Linux** ```sh diff --git a/config/BUILD b/config/BUILD index 9805c683a..6e8b486c2 100644 --- a/config/BUILD +++ b/config/BUILD @@ -10,19 +10,72 @@ # # SPDX-License-Identifier: Apache-2.0 # ******************************************************************************* -load("@bazel_skylib//rules:common_settings.bzl", "bool_flag") +load("@bazel_skylib//rules:common_settings.bzl", "bool_flag", "string_flag") + +# How to run integration tests: +# +# - docker: in a Docker container +# - qemu: in a QEMU virtual machine +# - host: on the current machine +# - skip: do not run integration tests +string_flag( + name = "integration_mode", + build_setting_default = "host", + values = [ + "docker", + "qemu", + "host", + "skip", + ], +) config_setting( - name = "x86_64-linux", - define_values = { - "config": "x86_64-linux", + name = "integration_docker", + flag_values = { + ":integration_mode": "docker", }, ) config_setting( - name = "x86_64-qnx", - define_values = { - "config": "x86_64-qnx", + name = "integration_qemu", + flag_values = { + ":integration_mode": "qemu", + }, +) + +config_setting( + name = "integration_host", + flag_values = { + ":integration_mode": "host", + }, +) + +# How to run unit tests: +# +# - qemu: in a QEMU virtual machine +# - host: on the current machine +# - skip: do not run unit tests +string_flag( + name = "unit_mode", + build_setting_default = "host", + values = [ + "qemu", + "host", + "skip", + ], +) + +config_setting( + name = "unit_qemu", + flag_values = { + ":unit_mode": "qemu", + }, +) + +config_setting( + name = "unit_host", + flag_values = { + ":unit_mode": "host", }, ) diff --git a/examples/demo_verification/test_examples.py b/examples/demo_verification/test_examples.py index 70bdc7f7b..6b8ee53c9 100644 --- a/examples/demo_verification/test_examples.py +++ b/examples/demo_verification/test_examples.py @@ -138,7 +138,7 @@ def test_examples(target, setup_test, remote_test_dir): _assert_not_running(target, "cpp_supervised_app") _step("Stopping launch manager (SIGTERM)") - res, _ = target.execute(f"kill -15 -{lm_proc.pid()}") + res, _ = target.execute(f"kill -TERM {lm_proc.pid()}") assert res == 0, "Failed to send SIGTERM to launch manager process group" time.sleep(0.5) assert not lm_proc.is_running(), "Launch manager did not stop after SIGTERM" diff --git a/patches/itf.patch b/patches/itf.patch new file mode 100644 index 000000000..f00a6e869 --- /dev/null +++ b/patches/itf.patch @@ -0,0 +1,15 @@ +# https://github.com/eclipse-score/itf/pull/127 + +--- score/itf/plugins/qemu/qemu_target.py ++++ score/itf/plugins/qemu/qemu_target.py +@@ -173,9 +173,7 @@ def execute_async(self, binary_path, args=None, cwd="/", **kwargs) -> QemuAsyncP + transport = ssh_ctx.get_paramiko_client().get_transport() + channel = transport.open_session() + channel.set_combine_stderr(True) +- inner = ( +- f"[ -r /etc/profile ] && . /etc/profile >/dev/null 2>&1; echo $$; cd {shlex.quote(cwd)} && {command}" +- ) ++ inner = f"[ -r /etc/profile ] && . /etc/profile >/dev/null 2>&1; echo $$; cd {shlex.quote(cwd)} && exec {command}" + channel.exec_command(f"sh -lc {shlex.quote(inner)}") + + # Read the PID from the first line of output. diff --git a/requirements.in b/requirements.in index 0e423780f..704d2939b 100644 --- a/requirements.in +++ b/requirements.in @@ -1,5 +1,2 @@ # Python dependencies for generating lifecycle configuration files -r ./scripts/config_mapping/requirements.txt - --r ./tests/integration/requirements.txt - diff --git a/requirements_lock.txt b/requirements_lock.txt index bb48c8e32..bec97068f 100644 --- a/requirements_lock.txt +++ b/requirements_lock.txt @@ -16,9 +16,6 @@ jsonschema==4.23.0 \ jsonschema-specifications==2023.12.1 \ --hash=sha256:48a76787b3e70f5ed53f1160d2b81f586e4ca6d1548c5de7085d1682674764cc \ --hash=sha256:87e4fdf3a94858b8a2ba2778d9ba57d8a9cafca7c7489c46ba0d30a8bc6a9c3c -junitparser==5.0.0 \ - --hash=sha256:9e279f2214dc74b6a86b22db757abda2e8e66e819fe882dad5b392d57024cd26 \ - --hash=sha256:f15e292877258d7c5755d672ce86f82c3622c7ea4c2f44f55de44ed7518484d3 packaging==26.0 \ --hash=sha256:00243ae351a257117b6a241061796684b084ed1c516a08c48a3f7e147a9d80b4 \ --hash=sha256:b36f1fef9334a5588b4166f8bcd26a14e521f2b55e6b9de3aaa80d3ff7a37529 diff --git a/score/health_monitor/src/cpp/BUILD b/score/health_monitor/src/cpp/BUILD index 606d9c451..bfc87a25e 100644 --- a/score/health_monitor/src/cpp/BUILD +++ b/score/health_monitor/src/cpp/BUILD @@ -80,6 +80,11 @@ cc_gtest_unit_test( "@platforms//os:qnx": ["-lsocket"], "@platforms//os:linux": [], }), + target_compatible_with = select({ + "//config:unit_qemu": [], + "//config:unit_host": [], + "//conditions:default": ["@platforms//:incompatible"], + }), deps = [ "//score/health_monitor/src/cpp:health_monitoring_cc_stub_supervisor", "//score/health_monitor/src/cpp/details:log_init", @@ -96,6 +101,11 @@ cc_gtest_unit_test( "@platforms//os:linux": [], }), tags = ["no-tsan"], + target_compatible_with = select({ + "//config:unit_qemu": [], + "//config:unit_host": [], + "//conditions:default": ["@platforms//:incompatible"], + }), deps = [ "//score/health_monitor/src/cpp:health_monitoring_cc_stub_supervisor", "//score/health_monitor/src/cpp/details:log_init", diff --git a/score/health_monitor/src/rust/BUILD b/score/health_monitor/src/rust/BUILD index 76b5644cc..d6266e24a 100644 --- a/score/health_monitor/src/rust/BUILD +++ b/score/health_monitor/src/rust/BUILD @@ -72,8 +72,12 @@ rust_test( tags = [ "no-asan", "no-tsan", - "skip_local", # see https://github.com/eclipse-score/lifecycle/issues/272 ], + target_compatible_with = select({ + "//config:unit_qemu": ["@platforms//os:linux"], # see https://github.com/eclipse-score/lifecycle/issues/272 + "//config:unit_host": ["@platforms//os:linux"], # see https://github.com/eclipse-score/lifecycle/issues/272 + "//conditions:default": ["@platforms//:incompatible"], + }), deps = ["@score_baselibs//src/log/stdout_logger"], ) @@ -100,7 +104,11 @@ rust_test( "no-asan", "no-tsan", ], - target_compatible_with = ["@platforms//os:linux"], + target_compatible_with = select({ + "//config:unit_qemu": ["@platforms//os:linux"], + "//config:unit_host": ["@platforms//os:linux"], + "//conditions:default": ["@platforms//:incompatible"], + }), deps = [ "@score_baselibs//src/log/stdout_logger", "@score_crates//:loom", @@ -119,5 +127,9 @@ miri_test( "miri", "no-asan", ], - target_compatible_with = ["@platforms//os:linux"], + target_compatible_with = select({ + "//config:unit_qemu": ["@platforms//os:linux"], + "//config:unit_host": ["@platforms//os:linux"], + "//conditions:default": ["@platforms//:incompatible"], + }), ) diff --git a/score/launch_manager/src/daemon/src/common/BUILD b/score/launch_manager/src/daemon/src/common/BUILD index b8d9db8d1..78ae20afb 100644 --- a/score/launch_manager/src/daemon/src/common/BUILD +++ b/score/launch_manager/src/daemon/src/common/BUILD @@ -70,7 +70,7 @@ cc_library( visibility = ["//score/launch_manager/src/daemon:__subpackages__"], ) -cc_test( +lm_cc_test( name = "signal_safe_log_UT", srcs = ["signal_safe_log_UT.cpp"], deps = [ diff --git a/tests/integration/BUILD b/tests/integration/BUILD index b82493d65..ca5de742e 100644 --- a/tests/integration/BUILD +++ b/tests/integration/BUILD @@ -10,23 +10,3 @@ # # SPDX-License-Identifier: Apache-2.0 # ******************************************************************************* - -load("@rules_python//python:pip.bzl", "compile_pip_requirements") -load("@score_lifecycle_pip//:requirements.bzl", "requirement") -load("@score_tooling//python_basics:defs.bzl", "score_virtualenv") - -filegroup( - name = "pip_requirements", - srcs = ["requirements.txt"], - visibility = ["//:__pkg__"], -) - -# Only pass packages that don't overlap with pip_tooling (which already -# provides: iniconfig, packaging, pluggy, pygments, pytest). -score_virtualenv( - name = "python_tc_venv", - reqs = [ - requirement("junitparser"), - ], - venv_name = ".python_tc_venv", -) diff --git a/tests/integration/process_fd_leak/BUILD b/tests/integration/process_fd_leak/BUILD index 1cd769e83..4b146f235 100644 --- a/tests/integration/process_fd_leak/BUILD +++ b/tests/integration/process_fd_leak/BUILD @@ -20,6 +20,7 @@ cc_binary( "get_fds.hpp", "native.cpp", ], + target_compatible_with = ["@platforms//os:linux"], deps = [ "//tests/utils/test_helper", "@googletest//:gtest_main", @@ -34,6 +35,7 @@ cc_binary( "get_fds.hpp", "reporting.cpp", ], + target_compatible_with = ["@platforms//os:linux"], deps = [ "//score/launch_manager:lifecycle_cc", "//tests/utils/test_helper", @@ -48,6 +50,7 @@ cc_binary( "control_client.cpp", "get_fds.hpp", ], + target_compatible_with = ["@platforms//os:linux"], deps = [ "//score/launch_manager:control_cc", "//score/launch_manager:lifecycle_cc", diff --git a/tests/integration/requirements.txt b/tests/integration/requirements.txt deleted file mode 100644 index eb44c7019..000000000 --- a/tests/integration/requirements.txt +++ /dev/null @@ -1,2 +0,0 @@ -pytest -junitparser diff --git a/tests/utils/bazel/integration.bzl b/tests/utils/bazel/integration.bzl index 6267f513e..a67f060d0 100644 --- a/tests/utils/bazel/integration.bzl +++ b/tests/utils/bazel/integration.bzl @@ -69,39 +69,82 @@ def integration_test( pkg_tar(name = "environment", srcs = [":binaries", ":files"]) + final_deps = kwargs.pop("deps", []) + all_requirements + [ + "@score_tooling//python_basics/score_pytest:attribute_plugin", + "//tests/utils/testing_utils", + ] + final_data = kwargs.pop("data", []) + [":environment"] + select({ + "//config:integration_docker": [ + "//tests/utils/environments/x86_64-linux", + ], + "//config:integration_qemu": [ + "//tests/utils/environments/x86_64-qnx:qemu_config.json", + "//tests/utils/environments/x86_64-qnx:qemu_image", + ], + "//conditions:default": [], + }) + final_args = kwargs.pop("args", []) + [ + "--score-test-binary-path=$(locations :environment)", + "--score-test-remote-directory={}/tests/{}".format(install_prefix, name), + ] + select({ + "//config:integration_docker": [ + "--docker-image-bootstrap=$(location //tests/utils/environments/x86_64-linux)", + "--docker-image=score_itf_examples:latest", + ], + "//config:integration_qemu": [ + "--qemu-config=$(location //tests/utils/environments/x86_64-qnx:qemu_config.json)", + "--qemu-image=$(location //tests/utils/environments/x86_64-qnx:qemu_image)", + ], + "//config:integration_host": [ + "--local-dir=/tmp/score_itf_host/{}".format(name), + ], + }) + final_plugins = ["//tests/utils/plugins:integration_plugin"] + select({ + "//config:integration_docker": ["@score_itf//score/itf/plugins:docker_plugin"], + "//config:integration_qemu": ["@score_itf//score/itf/plugins:qemu_plugin"], + "//config:integration_host": ["//tests/utils/plugins:localhost_plugin"], + }) + + # The QEMU plugin uses a hardcoded port so we can only run one test at a time. + # See https://github.com/eclipse-score/itf/issues/125. + # However we should not unnecessarily slow down Docker tests by adding the + # exclusive tag all the time. Bazel does not allow select() to be used in tags. + # So we have to create two separate targets and skip whichever is not needed. + py_itf_test( name = name, srcs = srcs, - tags = kwargs.pop("tags", []) + [ + tags = [ "integration", "no-asan", # The test container does not ship the sanitizer runtime; daemon fails to start. ], - deps = kwargs.pop("deps", []) + all_requirements + [ - "@score_tooling//python_basics/score_pytest:attribute_plugin", - "//tests/utils/testing_utils", - ], - data = kwargs.pop("data", []) + [":environment"] + select({ - "//config:host": [], - "//conditions:default": ["//tests/utils/environments:test_environment"], - }), - args = kwargs.pop("args", []) + [ - "--score-test-binary-path=$(locations :environment)", - "--score-test-remote-directory={}/tests/{}".format(install_prefix, name), - ] + select({ - "//config:x86_64-linux": [ - "--docker-image-bootstrap=$(location //tests/utils/environments:test_environment)", - "--docker-image=score_itf_examples:latest", - ], - "//config:host": [ - "--local-dir=/tmp/score_itf_host/{}".format(name), - ], - "//conditions:default": [], + deps = final_deps, + data = final_data, + args = final_args, + plugins = final_plugins, + target_compatible_with = select({ + "//config:integration_docker": ["@platforms//os:linux"], + "//config:integration_host": [], + "//conditions:default": ["@platforms//:incompatible"], }), - plugins = ["//tests/utils/plugins:integration_plugin"] + select({ - "//config:x86_64-linux": ["@score_itf//score/itf/plugins:docker_plugin"], - "//config:x86_64-qnx": ["@score_itf//score/itf/plugins/qemu"], - "//config:host": ["//tests/utils/plugins:localhost_plugin"], - "//conditions:default": [], + **kwargs + ) + + py_itf_test( + name = "{}_qemu".format(name), + srcs = srcs, + tags = [ + "exclusive", # The QEMU plugin uses a hardcoded port so we can only run one test at a time. + "integration", + "no-asan", # The test container does not ship the sanitizer runtime; daemon fails to start. + ], + deps = final_deps, + data = final_data, + args = final_args, + plugins = final_plugins, + target_compatible_with = select({ + "//config:integration_qemu": ["@platforms//os:qnx"], + "//conditions:default": ["@platforms//:incompatible"], }), **kwargs ) diff --git a/tests/utils/bazel/unit_test.bzl b/tests/utils/bazel/unit_test.bzl index f04a5b62e..41a18c8b3 100644 --- a/tests/utils/bazel/unit_test.bzl +++ b/tests/utils/bazel/unit_test.bzl @@ -30,5 +30,10 @@ def lm_cc_test(name, deps = [], **kwargs): cc_test( name = name, deps = deps + ["//score/launch_manager/src/daemon/src/common:assertion_handler"], + target_compatible_with = kwargs.pop("target_compatible_with", []) + select({ + "//config:unit_qemu": [], + "//config:unit_host": [], + "//conditions:default": ["@platforms//:incompatible"], + }), **kwargs ) diff --git a/tests/utils/environments/BUILD b/tests/utils/environments/BUILD index 2c85cdb51..bf049e025 100644 --- a/tests/utils/environments/BUILD +++ b/tests/utils/environments/BUILD @@ -15,25 +15,3 @@ exports_files( ["ecu_logging_config.json"], visibility = ["//tests/utils/environments:__subpackages__"], ) - -# Empty target for native builds -filegroup( - name = "empty_target", - srcs = [], - visibility = [ - "//examples:__subpackages__", - "//tests:__subpackages__", - ], -) - -alias( - name = "test_environment", - actual = select({ - "//config:x86_64-linux": "//tests/utils/environments/x86_64-linux", - "//conditions:default": ":empty_target", - }), - visibility = [ - "//examples:__subpackages__", - "//tests:__subpackages__", - ], -) diff --git a/tests/utils/environments/x86_64-linux/BUILD b/tests/utils/environments/x86_64-linux/BUILD index 2a59e59ff..3faeeb227 100644 --- a/tests/utils/environments/x86_64-linux/BUILD +++ b/tests/utils/environments/x86_64-linux/BUILD @@ -29,6 +29,7 @@ pkg_tar( oci_image( name = "image", base = "@debian-test-runtime", + target_compatible_with = ["@platforms//os:linux"], tars = [":ecu_logging_config_layer"], ) @@ -36,6 +37,7 @@ oci_load( name = "x86_64-linux", image = ":image", repo_tags = ["score_itf_examples:latest"], + target_compatible_with = ["@platforms//os:linux"], visibility = [ "//examples:__subpackages__", "//tests:__subpackages__", diff --git a/tests/utils/environments/x86_64-qnx/BUILD b/tests/utils/environments/x86_64-qnx/BUILD new file mode 100644 index 000000000..afd23652c --- /dev/null +++ b/tests/utils/environments/x86_64-qnx/BUILD @@ -0,0 +1,40 @@ +# ******************************************************************************* +# Copyright (c) 2025 Contributors to the Eclipse Foundation +# +# See the NOTICE file(s) distributed with this work for additional +# information regarding copyright ownership. +# +# This program and the accompanying materials are made available under the +# terms of the Apache License Version 2.0 which is available at +# https://www.apache.org/licenses/LICENSE-2.0 +# +# SPDX-License-Identifier: Apache-2.0 +# ******************************************************************************* + +load("@rules_pkg//pkg:mappings.bzl", "pkg_files") +load("@score_rules_imagefs//rules/qnx:ifs.bzl", "qnx_ifs") + +exports_files( + ["qemu_config.json"], + visibility = [ + "//examples:__subpackages__", + "//tests:__subpackages__", + ], +) + +pkg_files( + name = "logging_config.json", + srcs = ["//tests/utils/environments:ecu_logging_config.json"], + prefix = "/etc", +) + +qnx_ifs( + name = "qemu_image", + srcs = [":logging_config.json"], + build_file = ":init.build", + target_compatible_with = ["@platforms//os:qnx"], + visibility = [ + "//examples:__subpackages__", + "//tests:__subpackages__", + ], +) diff --git a/tests/utils/environments/x86_64-qnx/init.build b/tests/utils/environments/x86_64-qnx/init.build new file mode 100644 index 000000000..2c651e270 --- /dev/null +++ b/tests/utils/environments/x86_64-qnx/init.build @@ -0,0 +1,414 @@ +# ******************************************************************************* +# Copyright (c) 2025 Contributors to the Eclipse Foundation +# +# See the NOTICE file(s) distributed with this work for additional +# information regarding copyright ownership. +# +# This program and the accompanying materials are made available under the +# terms of the Apache License Version 2.0 which is available at +# https://www.apache.org/licenses/LICENSE-2.0 +# +# SPDX-License-Identifier: Apache-2.0 +# ******************************************************************************* + +# This file originates from https://github.com/eclipse-score/communication/blob/8826549731f455fad66bd8f54292e3355bf046c3/quality/integration_testing/environments/qnx8_qemu/init_x86_64.build +# with some modifications + +[-optional] + +[image=0x3600000] +[virtual=x86_64,multiboot] boot = { + startup-x86 -v -D8250..115200 -zz + PATH=/proc/boot + LD_LIBRARY_PATH=/proc/boot + [+keeplinked] procnto-smp-instr +} + +[+script] startup-script = { + display_msg Welcome to QNX OS 8.0 on x86_64 tweaked for S-CORE! + # These env variables get inherited by all programs which follow + SYSNAME=nto + TERM=qansi + + devc-ser8250 & + waitfor /dev/ser1 + reopen /dev/ser1 + + /proc/boot/startup.sh + + [+session] /bin/sh & +} + +[uid=0 gid=0 perms=0700] startup.sh = { + # Enable logging via slogger2 + echo "---> Starting slogger2" + slogger2 -m -s 253952 -G 7 -V -g 486 + waitfor /dev/slog2 + + # PCI server required for virtio-net (QEMU networking) + echo "---> Starting PCI Services" + pci-server --config=/proc/boot/pci_server.cfg + waitfor /dev/pci + + # Required to support POSIX pipes (used e.g. by service discovery) + echo "---> Starting Pipe" + pipe + waitfor /dev/pipe + + # Start random number generator service (provides /dev/random + # needed by C++ std::random_device and other consumers). + echo "---> Starting Random" + random + waitfor /dev/random + + # Service discovery depends on inotify, which requires fsevmgr + echo "---> Starting fsevmgr" + fsevmgr + waitfor /dev/fsnotify + + # Create a RAM disk and mount it at /tmp + echo "---> Starting devb-ram" + devb-ram ram capacity=1 blk ramdisk=128m,cache=512k,vnode=256 2>/dev/null + waitfor /dev/ram0 + + echo "---> Mounting RAM disk" + mkqnx6fs -q /dev/ram0 + mount /dev/ram0 /tmp + chmod 777 /tmp + + # Pseudo-terminal driver needed by sshd + echo "---> Starting devc-pty" + devc-pty -n 32 + + # Networking stack for SSH-based ITF test harness communication + echo "---> Starting Networking" + io-sock -m phy -m pci -d vtnet_pci + waitfor /dev/socket + + echo "---> Configuring network interface" + if_up -p vtnet0 + ifconfig vtnet0 10.0.2.15 netmask 255.255.255.0 + sysctl -w net.inet.icmp.bmcastecho=1 + sysctl -w qnx.sec.droproot=33:33 + + echo "---> Setting hostname" + hostname qnx-score + + # SSH daemon - ITF test harness communicates via SSH + echo "---> Starting SSH daemon" + /proc/boot/sshd -f /var/ssh/sshd_config +} + +[uid=0 gid=0 perms=0444] /etc/qcrypto.conf { + # Minimal qcrypto configuration for the random service. + # Uses the OpenSSL 3 plugin for cryptographic operations. + # The library auto-prepends "qcrypto-" to the plugin name, + # so "openssl-3" resolves to "qcrypto-openssl-3.so". + [random] + openssl-3 tags=random +} + +# dynamic loader +/usr/lib/ldqnx-64.so.2=ldqnx-64.so.2 + +cam-disk.so # CAM disk driver for storage devices +fs-qnx6.so # QNX6 file system support +io-blk.so # Block I/O manager +libc++.so.2 # C++ standard library +libc.so # C standard library (essential) +libc.so.6 # Main C library (malloc, printf, file I/O, etc.) +libcam.so.2 # CAM library for device access +libcrypto.so.3 # OpenSSL 3 crypto library (needed by qcrypto-openssl-3 plugin) +libexpat.so.2 # XML parser library (needed by PCI subsystem) +libfsnotify.so.1 # File system notification library +libgcc_s.so.1 # GCC runtime support library +libiconv.so.1 # Character encoding conversion library +libjail.so.1 # Jail/sandbox library (needed by sshd) +libm.so # Math library +libpam.so.2 # PAM authentication library (needed by sshd) +libpci.so.3.0 # PCI access library (needed by pci-server) +libqcrypto.so.1.0 # QNX cryptographic library +libqh.so.1 # QNX helper library +libqnxnoexcept.so=${QNXNOEXCEPT_LIBRARY} +libregex.so.1 # Regular expression library +libsecpol.so.1 # Security policy library +libslog2.so.1 # System logging library (slog2_* functions) +libslog2parse.so.1 # System log parsing library +libsocket.so.4 # Socket library (needed by libcrypto) +libssl.so.3 # OpenSSL TLS library (needed by sshd) +libz.so # Zlib compression library + +# qcrypto plugin loaded by the random service at runtime +[search=${QNX_TARGET}/x86_64/lib/dll] qcrypto-openssl-3.so + +############################################# +### NETWORKING COMPONENTS ### +############################################# +io-sock # Network stack manager +mods-pci.so # PCI network module +mods-phy.so # PHY network module +devs-vtnet_pci.so # VirtIO network PCI driver (QEMU) + +[type=link] /bin/sh=/proc/boot/ksh # Create symbolic link: sh -> ksh (standard shell link) +[type=link] /bin/ls=/proc/boot/ls # Link ls to IFS version for compatibility + +toybox # Minimal Unix utilities collection (replaces many GNU tools) +[type=link] cp=toybox # Copy files and directories +[type=link] ls=toybox # List directory contents +[type=link] cat=toybox # Display file contents +[type=link] chmod=toybox # Change file permissions +[type=link] rm=toybox # Remove files and directories +[type=link] dd=toybox # Convert and copy files with specified I/O block size +[type=link] echo=toybox # Display text +[type=link] grep=toybox # Search text patterns in files +[type=link] mkdir=toybox # Create directories +[type=link] ascii=toybox # Display ASCII character set +[type=link] base64=toybox # Base64 encoding/decoding utility +[type=link] basename=toybox # Extract filename from path +[type=link] bc=toybox # Basic calculator +[type=link] bunzip2=toybox # Decompress bzip2 files +[type=link] bzcat=toybox # Display contents of bzip2 files +[type=link] cal=toybox # Display calendar +[type=link] chgrp=toybox # Change group ownership +[type=link] chown=toybox # Change file ownership +[type=link] cksum=toybox # Calculate checksums +[type=link] clear=toybox # Clear terminal screen +[type=link] cmp=toybox # Compare files byte by byte +[type=link] comm=toybox # Compare sorted files line by line +[type=link] cpio=toybox # Copy files to/from archives +[type=link] crc32=toybox # Calculate CRC32 checksums +[type=link] cut=toybox # Extract columns from files +[type=link] date=toybox # Display or set system date +[type=link] diff=toybox # Compare files line by line +[type=link] dirname=toybox # Extract directory from path +[type=link] dos2unix=toybox # Convert DOS line endings to Unix +[type=link] du=toybox # Display disk usage +[type=link] egrep=toybox # Extended grep with regular expressions +[type=link] env=toybox # Display or set environment variables +[type=link] expand=toybox # Convert tabs to spaces +[type=link] expr=toybox # Evaluate expressions +[type=link] false=toybox # Return false status +[type=link] fgrep=toybox # Fast grep for fixed strings +[type=link] file=toybox # Determine file type +[type=link] find=toybox # Search for files and directories +[type=link] fmt=toybox # Format text paragraphs +[type=link] groups=toybox # Display user group membership +[type=link] gunzip=toybox # Decompress gzip files +[type=link] gzip=toybox # Compress files with gzip +[type=link] hd=toybox # Hexadecimal dump (alias for hexdump) +[type=link] head=toybox # Display first lines of files +[type=link] hexdump=toybox # Display files in hexadecimal format +[type=link] id=toybox # Display user and group IDs +[type=link] install=toybox # Copy files and set attributes +[type=link] link=toybox # Create hard links +[type=link] logname=toybox # Display login name +[type=link] md5sum=toybox # Calculate MD5 checksums +[type=link] mkfifo=toybox # Create named pipes (FIFOs) +[type=link] mktemp=toybox # Create temporary files/directories +[type=link] more=toybox # Display files page by page +[type=link] mv=toybox # Move/rename files and directories +[type=link] nl=toybox # Number lines in files +[type=link] nohup=toybox # Run commands immune to hangups +[type=link] od=toybox # Dump files in octal format +[type=link] paste=toybox # Merge lines from files +[type=link] patch=toybox # Apply patches to files +[type=link] printenv=toybox # Print environment variables +[type=link] printf=toybox # Format and print data +[type=link] pwd=toybox # Print working directory +[type=link] readlink=toybox # Display target of symbolic links +[type=link] realpath=toybox # Display absolute path +[type=link] rmdir=toybox # Remove empty directories +[type=link] sed=toybox # Stream editor for filtering/transforming text +[type=link] seq=toybox # Generate sequences of numbers +[type=link] sha1sum=toybox # Calculate SHA1 checksums +[type=link] sleep=toybox # Suspend execution for specified time +[type=link] sort=toybox # Sort lines in text files +[type=link] split=toybox # Split files into pieces +[type=link] stat=toybox # Display file/filesystem status +[type=link] strings=toybox # Extract printable strings from files +[type=link] tail=toybox # Display last lines of files +[type=link] tar=toybox # Extract compressed archives +[type=link] tee=toybox # Copy input to files and stdout +[type=link] test=toybox # Evaluate conditional expressions +[type=link] time=toybox # Time command execution +[type=link] timeout=toybox # Run command with time limit +[type=link] touch=toybox # Update file timestamps +[type=link] tr=toybox # Translate or delete characters +[type=link] true=toybox # Return true status +[type=link] truncate=toybox # Truncate files to specified size +[type=link] tty=toybox # Display terminal name +[type=link] uname=toybox # Display system information +[type=link] uniq=toybox # Remove duplicate lines +[type=link] unix2dos=toybox # Convert Unix line endings to DOS +[type=link] unlink=toybox # Remove files (system call interface) +[type=link] uudecode=toybox # Decode uuencoded files +[type=link] uuencode=toybox # Encode files using uuencoding +[type=link] uuidgen=toybox # Generate UUIDs +[type=link] wc=toybox # Count lines, words, and characters +[type=link] which=toybox # Locate commands in PATH +[type=link] whoami=toybox # Display current username +[type=link] xargs=toybox # Execute commands from standard input +[type=link] xxd=toybox # Make hexdump or reverse +[type=link] yes=toybox # Output string repeatedly +[type=link] zcat=toybox # Display contents of compressed files +[type=link] nc=toybox # Netcat for network connections and packet streaming +[type=link] netcat=toybox # Netcat alias for network connections +[type=link] waitfor=on # Create symbolic link: waitfor -> on (waits for resources to become available) +[type=link] ability=on # Create symbolic link: ability -> on (manages process abilities/privileges) +[type=link] setconf=getconf # Create symbolic link: setconf -> getconf (sets configuration parameters) +[type=link] libslog2.so=libslog2.so.1 # Create version-neutral symbolic link +[type=link] libsocket.so=libsocket.so.4 # Create version-neutral symbolic link +[type=link] libqh.so=libqh.so.1 # Create version-neutral symbolic link +[type=link] qcrypto-openssl.so=qcrypto-openssl-3.so + +############################################# +### Tools ### +############################################# +devb-ram # RAM disk block device manager +devc-pty # Pseudo-terminal driver (needed by sshd) +devc-ser8250 # Serial port driver for 8250/16550 UART controllers (console access) +fsevmgr # File system event manager +getconf # Get system configuration values +hostname # Set/display system hostname +if_up # Bring network interface up +ifconfig # Configure network interfaces +ksh # Korn shell - provides command-line interface and scripting +ln # Create file links +mkqnx6fs # Create QNX6 file systems +mount # File system mount utility - mounts/unmounts file systems +on # Command execution utility - runs commands with specific options +pci-server # PCI server (required for virtio-net) +pdebug # Process debugger +pidin # Process information display - shows running processes (like 'ps' on Linux) +pipe # Named pipe manager +random # Random number generator service (/dev/random, /dev/urandom) +route # Manage network routing tables +slay # Kill or modify a process by name or ID +slog2info # System log viewer - displays logged messages +slogger2 # System logging daemon - collects and manages log messages +sshd # SSH daemon (ITF test harness communicates via SSH) +sysctl # View/modify kernel parameters + +/usr/lib/ssh/sftp-server=${QNX_TARGET}/${PROCESSOR}/usr/libexec/sftp-server # SFTP server (file transfer for ITF) +/usr/libexec/sshd-session=${QNX_TARGET}/${PROCESSOR}/usr/libexec/sshd-session # SSH session handler (required by OpenSSH 9.8+) + +############################################# +### PCI COMPONENTS ### +############################################# +pci/pci_hw-Intel_x86.so +pci/pci_slog2.so +pci/pci_cap-0x05.so +pci/pci_cap-0x10.so +pci/pci_cap-0x11.so +pci/pci_strings.so +pci/pci_bkwd_compat.so +pci/pci_debug2.so + +############################################# +### SYSTEM DIRECTORIES ### +############################################# +[gid=0 uid=0 dperms=755 type=dir] /var/chroot/sshd +[gid=0 uid=0 dperms=700 type=dir] /var/ssh + +[perms=0444] pci_server.cfg = { +[buscfg] +DO_BUS_CONFIG=no + +[envars] +PCI_DEBUG_MODULE=pci_debug2.so +PCI_HW_MODULE=pci_hw-Intel_x86.so +PCI_HW_CONFIG_FILE=/proc/boot/pci_hw.cfg +} + +[perms=0444] pci_hw.cfg = { +[interrupts] +B0:D17:F0 A 18 +B0:D17:F0 B 19 +B0:D17:F0 C 16 +B0:D17:F0 D 17 +B3:D0:F0 A 18 +B3:D0:F0 B 19 +B3:D0:F0 C 16 +B3:D0:F0 D 17 +} + +[uid=0 gid=0 perms=0444] /etc/passwd = { +root::0:0:Superuser:/:/bin/sh +qnxuser::1000:1000:QNX User:/:/bin/sh +sshd::15:6:sshd:/:/bin/false +} + +[uid=0 gid=0 perms=0444] /etc/group = { +root::0:root +qnxuser::1000:qnxuser +sshd::6:sshd +} + +[uid=0 gid=0 perms=0444] /etc/profile = { +export TERM=qansi +export PATH=/proc/boot +export LD_LIBRARY_PATH=/proc/boot +export MAGIC=/system/etc/magic +} + +[uid=0 gid=0 perms=0400] /var/ssh/ssh_host_rsa_key = { +-----BEGIN OPENSSH PRIVATE KEY----- +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 +Fu+/MLbJQuA1zpAAAAAAEC +-----END OPENSSH PRIVATE KEY----- +} + +[uid=0 gid=0 perms=0444] /var/ssh/sshd_config = { +Port 22 +Protocol 2 +HostKey /var/ssh/ssh_host_rsa_key +AllowTcpForwarding yes +Subsystem sftp /usr/lib/ssh/sftp-server +PasswordAuthentication yes +PermitEmptyPasswords yes +PubkeyAuthentication no +ChallengeResponseAuthentication no +HostbasedAuthentication no +PermitRootLogin yes +PermitUserEnvironment yes +PidFile none +LogLevel DEBUG +StrictModes no +UseDNS no +MaxAuthTries 3 +LoginGraceTime 30 +} \ No newline at end of file diff --git a/tests/utils/environments/x86_64-qnx/qemu_config.json b/tests/utils/environments/x86_64-qnx/qemu_config.json new file mode 100644 index 000000000..1b19d57ab --- /dev/null +++ b/tests/utils/environments/x86_64-qnx/qemu_config.json @@ -0,0 +1,18 @@ +{ + "networks": [ + { + "name": "lo", + "ip_address": "127.0.0.1", + "gateway": "127.0.0.1" + } + ], + "ssh_port": 2222, + "qemu_num_cores": 2, + "qemu_ram_size": "1G", + "port_forwarding": [ + { + "host_port": 2222, + "guest_port": 22 + } + ] +} \ No newline at end of file diff --git a/tests/utils/plugins/BUILD b/tests/utils/plugins/BUILD index 26ade5a61..858adf8c9 100644 --- a/tests/utils/plugins/BUILD +++ b/tests/utils/plugins/BUILD @@ -16,6 +16,7 @@ load("@score_itf//bazel:py_itf_plugin.bzl", "py_itf_plugin") py_library( name = "localhost", srcs = ["localhost.py"], + target_compatible_with = ["@platforms//os:linux"], visibility = ["//visibility:public"], deps = [ "@score_itf//score/itf/core/process", @@ -28,12 +29,14 @@ py_itf_plugin( name = "localhost_plugin", enabled_plugins = ["tests.utils.plugins.localhost"], py_library = ":localhost", + target_compatible_with = ["@platforms//os:linux"], visibility = ["//visibility:public"], ) py_library( name = "integration", srcs = ["integration.py"], + target_compatible_with = ["@platforms//os:linux"], visibility = ["//visibility:public"], deps = [ "@score_itf//score/itf/plugins:core", @@ -44,5 +47,6 @@ py_itf_plugin( name = "integration_plugin", enabled_plugins = ["tests.utils.plugins.integration"], py_library = ":integration", + target_compatible_with = ["@platforms//os:linux"], visibility = ["//visibility:public"], ) diff --git a/tests/utils/testing_utils/BUILD b/tests/utils/testing_utils/BUILD index 3cc5ad7a1..e24741ebc 100644 --- a/tests/utils/testing_utils/BUILD +++ b/tests/utils/testing_utils/BUILD @@ -11,7 +11,6 @@ # SPDX-License-Identifier: Apache-2.0 # ******************************************************************************* load("@rules_python//python:defs.bzl", "py_library") -load("@score_lifecycle_pip//:requirements.bzl", "requirement") py_library( name = "testing_utils", @@ -20,12 +19,12 @@ py_library( "setup_test.py", "test_results.py", ], + target_compatible_with = ["@platforms//os:linux"], visibility = [ "//examples:__subpackages__", "//tests:__subpackages__", ], deps = [ - requirement("junitparser"), "@score_itf//score/itf/core/process", "@score_itf//score/itf/core/target", ], diff --git a/tests/utils/testing_utils/run_until_file_deployed.py b/tests/utils/testing_utils/run_until_file_deployed.py index a16f9e3d1..a5ba530a8 100644 --- a/tests/utils/testing_utils/run_until_file_deployed.py +++ b/tests/utils/testing_utils/run_until_file_deployed.py @@ -65,7 +65,7 @@ def run_until_file_deployed( # Kill the entire process group so that children (e.g. the actual # daemon binary launched under fakeroot) receive SIGTERM and can # run their cleanup code before exiting. - kill_cmd = f"kill -15 -{proc.pid()}" + kill_cmd = f"kill -TERM {proc.pid()}" res, _ = target.execute(kill_cmd) assert res == 0, "Couldn't kill lcm with SIGTERM" try: diff --git a/tests/utils/testing_utils/setup_test.py b/tests/utils/testing_utils/setup_test.py index d5a1ef6b9..04cae0e0e 100644 --- a/tests/utils/testing_utils/setup_test.py +++ b/tests/utils/testing_utils/setup_test.py @@ -34,9 +34,7 @@ def setup_test(request, target): res, _ = target.execute(f"mkdir -p {extract_dir}") assert res != 1, f"Couldn't create directory {extract_dir}" - target.upload( - bin_path.resolve(), remote_tar - ) # Need to resolve for https://github.com/eclipse-score/itf/pull/71 + target.upload(str(bin_path), str(remote_tar)) res, _ = target.execute(f"tar -xf {remote_tar} -C {extract_dir}") assert res == 0, f"Couldn't extract tar {remote_tar}" diff --git a/tests/utils/testing_utils/test_results.py b/tests/utils/testing_utils/test_results.py index 083a7aea0..3eff9c29b 100644 --- a/tests/utils/testing_utils/test_results.py +++ b/tests/utils/testing_utils/test_results.py @@ -12,9 +12,9 @@ # ******************************************************************************* from pathlib import Path from typing import Iterable, Sequence, Set, Union +from xml.etree import ElementTree import pytest -from junitparser import JUnitXml def download_xml_results( @@ -57,8 +57,11 @@ def get_failing_files(path: Path): failing_files = set() all_files = set() for file in path.glob("*.xml"): - xml = JUnitXml.fromfile(str(file)) - if xml.failures > 0 or xml.errors > 0: + test_suites = ElementTree.parse(str(file)).getroot() + failures = int(test_suites.attrib["failures"]) + errors = int(test_suites.attrib["errors"]) + + if failures > 0 or errors > 0: failing_files.add(file.name) all_files.add(file.name)