diff --git a/tests/benchmarks/multicore/idle_ipc/CMakeLists.txt b/tests/benchmarks/multicore/idle_ipc/CMakeLists.txt new file mode 100644 index 000000000000..b33d0888efff --- /dev/null +++ b/tests/benchmarks/multicore/idle_ipc/CMakeLists.txt @@ -0,0 +1,19 @@ +# +# Copyright (c) 2024 Nordic Semiconductor ASA +# +# SPDX-License-Identifier: LicenseRef-Nordic-5-Clause +# + +cmake_minimum_required(VERSION 3.20.0) + +find_package(Zephyr REQUIRED HINTS $ENV{ZEPHYR_BASE}) + +if(NOT SYSBUILD) + message(FATAL_ERROR + " This is a multi-image application that should be built using sysbuild.\n" + " Add --sysbuild argument to west build command to prepare all the images.") +endif() + +project(idle_ipc) + +target_sources(app PRIVATE src/main.c) diff --git a/tests/benchmarks/multicore/idle_ipc/Kconfig b/tests/benchmarks/multicore/idle_ipc/Kconfig new file mode 100644 index 000000000000..e6e568f6d454 --- /dev/null +++ b/tests/benchmarks/multicore/idle_ipc/Kconfig @@ -0,0 +1,8 @@ +# +# Copyright (c) 2024 Nordic Semiconductor ASA +# +# SPDX-License-Identifier: LicenseRef-Nordic-5-Clause +# + +source "Kconfig.zephyr" +rsource "Kconfig.common" diff --git a/tests/benchmarks/multicore/idle_ipc/Kconfig.common b/tests/benchmarks/multicore/idle_ipc/Kconfig.common new file mode 100644 index 000000000000..a00d5be86f6b --- /dev/null +++ b/tests/benchmarks/multicore/idle_ipc/Kconfig.common @@ -0,0 +1,18 @@ +# +# Copyright (c) 2024 Nordic Semiconductor ASA +# +# SPDX-License-Identifier: LicenseRef-Nordic-5-Clause +# + +config APP_IPC_SERVICE_SEND_INTERVAL + int "Ipc service sending interval [us]" + default 70 + help + Time in micro seconds between sending subsequent data packages over + IPC service. Since kernel timeout has 1 ms resolution, the value is + rounded down. If value of this option is lower than 1000 us, busy + wait is used instead of sleep. + +config APP_IPC_SERVICE_MESSAGE_LEN + int "Length of single IPC message in bytes" + default 100 diff --git a/tests/benchmarks/multicore/idle_ipc/Kconfig.sysbuild b/tests/benchmarks/multicore/idle_ipc/Kconfig.sysbuild new file mode 100644 index 000000000000..da26dbe3dc09 --- /dev/null +++ b/tests/benchmarks/multicore/idle_ipc/Kconfig.sysbuild @@ -0,0 +1,10 @@ +# +# Copyright (c) 2023 Nordic Semiconductor ASA +# +# SPDX-License-Identifier: LicenseRef-Nordic-5-Clause +# + +source "${ZEPHYR_BASE}/share/sysbuild/Kconfig" + +config REMOTE_BOARD + string "The board used for remote target" diff --git a/tests/benchmarks/multicore/idle_ipc/boards/nrf54h20dk_nrf54h20_cpuapp.conf b/tests/benchmarks/multicore/idle_ipc/boards/nrf54h20dk_nrf54h20_cpuapp.conf new file mode 100644 index 000000000000..689f605dd46a --- /dev/null +++ b/tests/benchmarks/multicore/idle_ipc/boards/nrf54h20dk_nrf54h20_cpuapp.conf @@ -0,0 +1,4 @@ +# Copyright (c) 2024 Nordic Semiconductor ASA +# SPDX-License-Identifier: LicenseRef-Nordic-5-Clause + +CONFIG_APP_IPC_SERVICE_SEND_INTERVAL=900 diff --git a/tests/benchmarks/multicore/idle_ipc/boards/nrf54h20dk_nrf54h20_cpuapp_cpuppr.overlay b/tests/benchmarks/multicore/idle_ipc/boards/nrf54h20dk_nrf54h20_cpuapp_cpuppr.overlay new file mode 100644 index 000000000000..147c4640fcc2 --- /dev/null +++ b/tests/benchmarks/multicore/idle_ipc/boards/nrf54h20dk_nrf54h20_cpuapp_cpuppr.overlay @@ -0,0 +1,25 @@ +/* + * Copyright (c) 2024 Nordic Semiconductor ASA + * SPDX-License-Identifier: LicenseRef-Nordic-5-Clause + */ + +/* Replace default ipc0 instance */ +/delete-node/ &ipc0; + +ipc0: &cpuapp_cpuppr_ipc { + status = "okay"; +}; + +&cpuppr_vevif { + status = "okay"; +}; + +&cpuapp_bellboard { + status = "okay"; +}; + +/ { + chosen { + /delete-property/ zephyr,bt-hci; + }; +}; diff --git a/tests/benchmarks/multicore/idle_ipc/prj.conf b/tests/benchmarks/multicore/idle_ipc/prj.conf new file mode 100644 index 000000000000..7ab057b30e70 --- /dev/null +++ b/tests/benchmarks/multicore/idle_ipc/prj.conf @@ -0,0 +1,25 @@ +# Copyright (c) 2024 Nordic Semiconductor ASA +# SPDX-License-Identifier: LicenseRef-Nordic-5-Clause + +CONFIG_LOG_PROCESS_THREAD_PRIORITY=-15 +CONFIG_LOG_PROCESS_THREAD_CUSTOM_PRIORITY=y + +CONFIG_HEAP_MEM_POOL_SIZE=4096 + +CONFIG_MBOX=y + +CONFIG_IPC_SERVICE=y +CONFIG_IPC_SERVICE_LOG_LEVEL_INF=y + +CONFIG_PM=y +CONFIG_PM_S2RAM=y +CONFIG_PM_S2RAM_CUSTOM_MARKING=y +CONFIG_PM_DEVICE=y +CONFIG_POWEROFF=y +CONFIG_PM_DEVICE_RUNTIME=y + +# Enable for debugging pruposes only +CONFIG_PRINTK=y +CONFIG_LOG=y +CONFIG_CONSOLE=y +CONFIG_UART_CONSOLE=y diff --git a/tests/benchmarks/multicore/idle_ipc/remote/CMakeLists.txt b/tests/benchmarks/multicore/idle_ipc/remote/CMakeLists.txt new file mode 100644 index 000000000000..3f79e49afb26 --- /dev/null +++ b/tests/benchmarks/multicore/idle_ipc/remote/CMakeLists.txt @@ -0,0 +1,12 @@ +# +# Copyright (c) 2024 Nordic Semiconductor ASA +# +# SPDX-License-Identifier: LicenseRef-Nordic-5-Clause +# + +cmake_minimum_required(VERSION 3.20.0) + +find_package(Zephyr REQUIRED HINTS $ENV{ZEPHYR_BASE}) +project(remote) + +target_sources(app PRIVATE ../src/main.c) diff --git a/tests/benchmarks/multicore/idle_ipc/remote/Kconfig b/tests/benchmarks/multicore/idle_ipc/remote/Kconfig new file mode 100644 index 000000000000..ab0aabb5ad66 --- /dev/null +++ b/tests/benchmarks/multicore/idle_ipc/remote/Kconfig @@ -0,0 +1,8 @@ +# +# Copyright (c) 2024 Nordic Semiconductor ASA +# +# SPDX-License-Identifier: LicenseRef-Nordic-5-Clause +# + +source "Kconfig.zephyr" +rsource "../Kconfig.common" diff --git a/tests/benchmarks/multicore/idle_ipc/remote/boards/nrf54h20dk_nrf54h20_cpurad.conf b/tests/benchmarks/multicore/idle_ipc/remote/boards/nrf54h20dk_nrf54h20_cpurad.conf new file mode 100644 index 000000000000..689f605dd46a --- /dev/null +++ b/tests/benchmarks/multicore/idle_ipc/remote/boards/nrf54h20dk_nrf54h20_cpurad.conf @@ -0,0 +1,4 @@ +# Copyright (c) 2024 Nordic Semiconductor ASA +# SPDX-License-Identifier: LicenseRef-Nordic-5-Clause + +CONFIG_APP_IPC_SERVICE_SEND_INTERVAL=900 diff --git a/tests/benchmarks/multicore/idle_ipc/remote/boards/nrf54h20dk_nrf54h20_cpurad.overlay b/tests/benchmarks/multicore/idle_ipc/remote/boards/nrf54h20dk_nrf54h20_cpurad.overlay new file mode 100644 index 000000000000..7f559ea99440 --- /dev/null +++ b/tests/benchmarks/multicore/idle_ipc/remote/boards/nrf54h20dk_nrf54h20_cpurad.overlay @@ -0,0 +1,8 @@ +/* + * Copyright (c) 2024 Nordic Semiconductor ASA + * SPDX-License-Identifier: LicenseRef-Nordic-5-Clause + */ + +&uart135 { + /delete-property/ hw-flow-control; +}; diff --git a/tests/benchmarks/multicore/idle_ipc/remote/prj.conf b/tests/benchmarks/multicore/idle_ipc/remote/prj.conf new file mode 100644 index 000000000000..9b4706e33830 --- /dev/null +++ b/tests/benchmarks/multicore/idle_ipc/remote/prj.conf @@ -0,0 +1,24 @@ +# Copyright (c) 2024 Nordic Semiconductor ASA +# SPDX-License-Identifier: LicenseRef-Nordic-5-Clause + + +CONFIG_LOG_PROCESS_THREAD_PRIORITY=-15 +CONFIG_LOG_PROCESS_THREAD_CUSTOM_PRIORITY=y + +CONFIG_HEAP_MEM_POOL_SIZE=2048 + +CONFIG_IPC_SERVICE=y +CONFIG_IPC_SERVICE_LOG_LEVEL_INF=y + +CONFIG_MBOX=y + +CONFIG_PM=y +CONFIG_PM_DEVICE=y +CONFIG_POWEROFF=y +CONFIG_PM_DEVICE_RUNTIME=y + +# Enable for debugging pruposes only +CONFIG_PRINTK=y +CONFIG_LOG=y +CONFIG_CONSOLE=y +CONFIG_UART_CONSOLE=y \ No newline at end of file diff --git a/tests/benchmarks/multicore/idle_ipc/src/main.c b/tests/benchmarks/multicore/idle_ipc/src/main.c new file mode 100644 index 000000000000..dfe9eebdd014 --- /dev/null +++ b/tests/benchmarks/multicore/idle_ipc/src/main.c @@ -0,0 +1,135 @@ +/* + * Copyright (c) 2022 Nordic Semiconductor ASA + * + * SPDX-License-Identifier: LicenseRef-Nordic-5-Clause + */ + +#include +#include +#include +#include +#include +#include +#include + +#ifdef CONFIG_TEST_EXTRA_STACK_SIZE +#define STACKSIZE (1024 + CONFIG_TEST_EXTRA_STACK_SIZE) +#else +#define STACKSIZE (1024) +#endif + +K_THREAD_STACK_DEFINE(ipc0_stack, STACKSIZE); + +LOG_MODULE_REGISTER(host, LOG_LEVEL_INF); + +static const struct device *const console_dev = DEVICE_DT_GET(DT_CHOSEN(zephyr_console)); + +struct payload { + unsigned long cnt; + unsigned long size; + uint8_t data[]; +}; + +struct payload *p_payload; + +static K_SEM_DEFINE(bound_sem, 0, 1); + +static void ep_bound(void *priv) +{ + k_sem_give(&bound_sem); +} + +static void ep_recv(const void *data, size_t len, void *priv) +{ + uint8_t received_val = *((uint8_t *)data); + static uint8_t expected_val; + + if ((received_val != expected_val) || (len != CONFIG_APP_IPC_SERVICE_MESSAGE_LEN)) { + printk("Unexpected message received_val: %d , expected_val: %d\n", received_val, + expected_val); + } + + expected_val++; +} + +static struct ipc_ept_cfg ep_cfg = { + .name = "ep0", + .cb = + { + .bound = ep_bound, + .received = ep_recv, + }, +}; + +int main(void) +{ + const struct device *ipc0_instance; + struct ipc_ept ep; + int ret; + unsigned long last_cnt = 0; + unsigned long delta = 0; + + p_payload = (struct payload *)k_malloc(CONFIG_APP_IPC_SERVICE_MESSAGE_LEN); + if (!p_payload) { + printk("k_malloc() failure\n"); + return -ENOMEM; + } + + memset(p_payload->data, 0xA5, CONFIG_APP_IPC_SERVICE_MESSAGE_LEN - sizeof(struct payload)); + + p_payload->size = CONFIG_APP_IPC_SERVICE_MESSAGE_LEN; + p_payload->cnt = 0; + + printk("IPC-service %s demo started\n", CONFIG_BOARD_TARGET); + + ipc0_instance = DEVICE_DT_GET(DT_NODELABEL(ipc0)); + + ret = ipc_service_open_instance(ipc0_instance); + if ((ret < 0) && (ret != -EALREADY)) { + LOG_INF("ipc_service_open_instance() failure (%d)", ret); + return ret; + } + + ret = ipc_service_register_endpoint(ipc0_instance, &ep, &ep_cfg); + if (ret < 0) { + printf("ipc_service_register_endpoint() failure (%d)", ret); + return ret; + } + + if (IS_ENABLED(CONFIG_PM_DEVICE_RUNTIME)) { + pm_device_runtime_enable(console_dev); + pm_device_runtime_enable(ipc0_instance); + } + + // k_sem_take(&bound_sem, K_FOREVER); + + while (true) { + + printk("Hello\n"); + printk("Send data over IPC\n"); + + for (int counter = 0; counter < 10; counter++) { + ret = ipc_service_send(&ep, p_payload, CONFIG_APP_IPC_SERVICE_MESSAGE_LEN); + if (ret == -ENOMEM) { + /* No space in the buffer. Retry. */ + continue; + } else if (ret < 0) { + printk("send_message(%ld) failed with ret %d\n", p_payload->cnt, + ret); + break; + } + k_msleep(100); + + delta = p_payload->cnt - last_cnt; + printk("Δpkt: %ld (%ld B/pkt) | throughput: %ld bit/s\n", delta, + p_payload->size, delta * CONFIG_APP_IPC_SERVICE_MESSAGE_LEN * 8); + last_cnt = p_payload->cnt; + p_payload->cnt++; + } + + printk("Go to sleep (s2ram)\n"); + k_msleep(2000); + } + + return 0; +} diff --git a/tests/benchmarks/multicore/idle_ipc/sysbuild.cmake b/tests/benchmarks/multicore/idle_ipc/sysbuild.cmake new file mode 100644 index 000000000000..ee9464a85bf9 --- /dev/null +++ b/tests/benchmarks/multicore/idle_ipc/sysbuild.cmake @@ -0,0 +1,22 @@ +# +# Copyright (c) 2023 Nordic Semiconductor ASA +# +# SPDX-License-Identifier: LicenseRef-Nordic-5-Clause +# + +if("${SB_CONFIG_REMOTE_BOARD}" STREQUAL "") + message(FATAL_ERROR "REMOTE_BOARD must be set to a valid board name") +endif() + +# Add remote project +ExternalZephyrProject_Add( + APPLICATION remote + SOURCE_DIR ${APP_DIR}/remote + BOARD ${SB_CONFIG_REMOTE_BOARD} + BOARD_REVISION ${BOARD_REVISION} + ) + +# Add a dependency so that the remote image will be built and flashed first +add_dependencies(idle_ipc remote) +# Add dependency so that the remote image is flashed first. +sysbuild_add_dependencies(FLASH idle_ipc remote) diff --git a/tests/benchmarks/multicore/idle_ipc/sysbuild/nrf54h20dk_nrf54h20_cpurad.conf b/tests/benchmarks/multicore/idle_ipc/sysbuild/nrf54h20dk_nrf54h20_cpurad.conf new file mode 100644 index 000000000000..dd863e78d993 --- /dev/null +++ b/tests/benchmarks/multicore/idle_ipc/sysbuild/nrf54h20dk_nrf54h20_cpurad.conf @@ -0,0 +1 @@ +SB_CONFIG_REMOTE_BOARD="nrf54h20dk/nrf54h20/cpurad" diff --git a/tests/benchmarks/multicore/idle_ipc/testcase.yaml b/tests/benchmarks/multicore/idle_ipc/testcase.yaml new file mode 100644 index 000000000000..438b44a77d9a --- /dev/null +++ b/tests/benchmarks/multicore/idle_ipc/testcase.yaml @@ -0,0 +1,18 @@ +common: + sysbuild: true + tags: ci_build ci_tests_benchmarks_multicore ipc ppk_power_measure + +tests: + benchmarks.multicore.idle_ipc.nrf54h20dk_cpuapp_cpurad.s2ram: + # harness: pytest + platform_allow: + - nrf54h20dk/nrf54h20/cpuapp + integration_platforms: + - nrf54h20dk/nrf54h20/cpuapp + extra_args: + - SB_CONF_FILE=sysbuild/nrf54h20dk_nrf54h20_cpurad.conf + # harness_config: + # fixture: ppk_power_measure + # pytest_root: + # - "${CUSTOM_ROOT_TEST_DIR}/test_measure_power_consumption.py::test_measure_and_data_dump_power_consumption_uarte" +