Skip to content

Commit 9d20c5c

Browse files
nordic-bamikartben
authored andcommitted
tests: susbys: Implement performance test for the NRFS
Add NRFS service handling performance test. Signed-off-by: Bartosz Miller <[email protected]>
1 parent 85dc17a commit 9d20c5c

File tree

9 files changed

+262
-0
lines changed

9 files changed

+262
-0
lines changed

tests/subsys/nrfs/CMakeLists.txt

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
#
2+
# Copyright (c) 2025 Nordic Semiconductor ASA
3+
#
4+
# SPDX-License-Identifier: Apache-2.0
5+
#
6+
7+
cmake_minimum_required(VERSION 3.20.0)
8+
9+
find_package(Zephyr REQUIRED HINTS $ENV{ZEPHYR_BASE})
10+
11+
if(NOT SYSBUILD)
12+
message(FATAL_ERROR
13+
" This is a multi-image application that should be built using sysbuild.\n"
14+
" Add --sysbuild argument to west build command to prepare all the images.")
15+
endif()
16+
17+
project(nrfs)
18+
19+
target_sources(app PRIVATE src/main.c)

tests/subsys/nrfs/Kconfig.sysbuild

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
# Copyright (c) 2025 Nordic Semiconductor ASA
2+
# SPDX-License-Identifier: Apache-2.0
3+
4+
source "${ZEPHYR_BASE}/share/sysbuild/Kconfig"
5+
6+
config REMOTE_BOARD
7+
string
8+
default "$(BOARD)/nrf54h20/cpurad" if SOC_NRF54H20_CPUAPP
9+
default "$(BOARD)/nrf54h20/cpuapp" if SOC_NRF54H20_CPURAD

tests/subsys/nrfs/README.txt

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
The purpose of this test suite is to validate
2+
NRFS services request handling performance.
3+
4+
These reaquest are propagated over IPC.
5+
6+
MRAM latency serivice and Temperature service
7+
are used as benchmarks.

tests/subsys/nrfs/prj.conf

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
CONFIG_ZTEST=y
2+
CONFIG_TEST_USERSPACE=y
3+
4+
CONFIG_HEAP_MEM_POOL_SIZE=2048
5+
CONFIG_ISR_STACK_SIZE=1024
6+
CONFIG_MAIN_STACK_SIZE=4096
7+
CONFIG_SYSTEM_WORKQUEUE_STACK_SIZE=2048
8+
9+
CONFIG_NRFS=y
10+
CONFIG_NRFS_MRAM_SERVICE_ENABLED=y
11+
CONFIG_NRFS_TEMP_SERVICE_ENABLED=y
12+
CONFIG_CLOCK_CONTROL=n
13+
14+
CONFIG_ASSERT=y
15+
16+
CONFIG_SERIAL=y
17+
CONFIG_PRINTK=y
18+
CONFIG_LOG=y
19+
CONFIG_LOG_MODE_IMMEDIATE=n
20+
CONFIG_CONSOLE=y
21+
CONFIG_UART_CONSOLE=y
Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
#
2+
# Copyright (c) 2025 Nordic Semiconductor ASA
3+
#
4+
# SPDX-License-Identifier: Apache-2.0
5+
#
6+
7+
cmake_minimum_required(VERSION 3.20.0)
8+
9+
find_package(Zephyr REQUIRED HINTS $ENV{ZEPHYR_BASE})
10+
project(remote)
11+
12+
target_sources(app PRIVATE ../src/main.c)

tests/subsys/nrfs/remote/prj.conf

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
CONFIG_ZTEST=y
2+
CONFIG_TEST_USERSPACE=y
3+
4+
CONFIG_HEAP_MEM_POOL_SIZE=2048
5+
CONFIG_ISR_STACK_SIZE=1024
6+
CONFIG_MAIN_STACK_SIZE=4096
7+
CONFIG_SYSTEM_WORKQUEUE_STACK_SIZE=2048
8+
9+
CONFIG_NRFS=y
10+
CONFIG_NRFS_MRAM_SERVICE_ENABLED=y
11+
CONFIG_NRFS_TEMP_SERVICE_ENABLED=y
12+
CONFIG_CLOCK_CONTROL=n
13+
14+
CONFIG_ASSERT=y
15+
16+
CONFIG_SERIAL=y
17+
CONFIG_PRINTK=y
18+
CONFIG_LOG=y
19+
CONFIG_LOG_MODE_IMMEDIATE=n
20+
CONFIG_CONSOLE=y
21+
CONFIG_UART_CONSOLE=y

tests/subsys/nrfs/src/main.c

Lines changed: 141 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,141 @@
1+
/*
2+
* Copyright (c) 2025 Nordic Semiconductor ASA
3+
*
4+
* SPDX-License-Identifier: Apache-2.0
5+
*/
6+
7+
#include <zephyr/device.h>
8+
#include <internal/nrfs_backend.h>
9+
#include <nrfs_backend_ipc_service.h>
10+
#include <nrfs_mram.h>
11+
#include <nrfs_temp.h>
12+
#include <zephyr/ztest.h>
13+
14+
#define IPC_BACKEND_CONNECTION_TIMEOUT_MS 5000
15+
#define NUM_OF_MRAM_REQUESTS 10000
16+
#define MRAM_REQUESTS_DEAD_TIME_MS 1
17+
#define NUM_OF_TEMP_REQUESTS 100
18+
#define TEMP_REQUESTS_DEAD_TIME_MS 100
19+
20+
struct ipc_perf_result {
21+
uint32_t sent_requests;
22+
uint32_t handled_requests;
23+
uint32_t failed_to_send;
24+
};
25+
26+
static volatile uint32_t tst_perf_served_mram_requests;
27+
static volatile uint32_t tst_perf_served_temp_meas_requests;
28+
29+
/*
30+
* Callback function for counting handled TEMP service requests
31+
*/
32+
static void temp_handler_for_performance_test(nrfs_temp_evt_t const *p_evt, void *context)
33+
{
34+
switch (p_evt->type) {
35+
case NRFS_TEMP_EVT_MEASURE_DONE:
36+
tst_perf_served_temp_meas_requests++;
37+
default:
38+
break;
39+
}
40+
}
41+
42+
/*
43+
* Callback function for counting handled MRAM service requests
44+
*/
45+
static void mram_latency_handler_for_performance_test(nrfs_mram_latency_evt_t const *p_evt,
46+
void *context)
47+
{
48+
switch (p_evt->type) {
49+
case NRFS_MRAM_LATENCY_REQ_APPLIED:
50+
tst_perf_served_mram_requests++;
51+
default:
52+
break;
53+
}
54+
}
55+
56+
/*
57+
* Test NRFS MRAM latency service requests handling performance
58+
*/
59+
ZTEST(nrfs_stress_test, test_mram_nrfs_requests_performance)
60+
{
61+
struct ipc_perf_result tst_ipc_perf_result;
62+
uint32_t request_counter = 0;
63+
volatile int32_t tst_ctx = 1;
64+
65+
TC_PRINT("START test_mram_nrfs_requests_performance\n");
66+
zassert_equal(nrfs_mram_init(mram_latency_handler_for_performance_test), NRFS_SUCCESS,
67+
"Failed to initialise NRFS MRAM latency service");
68+
memset(&tst_ipc_perf_result, 0, sizeof(tst_ipc_perf_result));
69+
while (request_counter < NUM_OF_MRAM_REQUESTS) {
70+
if (nrfs_mram_set_latency(true, (void *)tst_ctx) == NRFS_SUCCESS) {
71+
tst_ipc_perf_result.sent_requests++;
72+
} else {
73+
tst_ipc_perf_result.failed_to_send++;
74+
}
75+
k_msleep(MRAM_REQUESTS_DEAD_TIME_MS);
76+
tst_ctx++;
77+
request_counter++;
78+
}
79+
/* wait for any remaining requests responses */
80+
k_msleep(10 * MRAM_REQUESTS_DEAD_TIME_MS);
81+
tst_ipc_perf_result.handled_requests = tst_perf_served_mram_requests;
82+
TC_PRINT("STOP test_mram_nrfs_requests_performance\n");
83+
TC_PRINT("SENT: %d, HANDLED: %d, FAILED TO SEND: %d\n", tst_ipc_perf_result.sent_requests,
84+
tst_ipc_perf_result.handled_requests, tst_ipc_perf_result.failed_to_send);
85+
zassert_equal(tst_ipc_perf_result.sent_requests, tst_ipc_perf_result.handled_requests,
86+
"NRFS MRAM requests sent != served");
87+
}
88+
89+
/*
90+
* Test temperature service requests handling performance
91+
*/
92+
ZTEST(nrfs_stress_test, test_temperature_nrfs_requests_performance)
93+
{
94+
struct ipc_perf_result tst_ipc_perf_result;
95+
uint32_t request_counter = 0;
96+
volatile int32_t tst_ctx = 1;
97+
98+
TC_PRINT("START test_temperature_nrfs_requests_performance\n");
99+
zassert_equal(nrfs_temp_init(temp_handler_for_performance_test), NRFS_SUCCESS,
100+
"Failed to initialise NRFS temperature service");
101+
memset((void *)&tst_ipc_perf_result, 0, sizeof(tst_ipc_perf_result));
102+
while (request_counter < NUM_OF_TEMP_REQUESTS) {
103+
if (nrfs_temp_measure_request((void *)tst_ctx) == NRFS_SUCCESS) {
104+
tst_ipc_perf_result.sent_requests++;
105+
} else {
106+
tst_ipc_perf_result.failed_to_send++;
107+
}
108+
k_msleep(TEMP_REQUESTS_DEAD_TIME_MS);
109+
tst_ctx++;
110+
request_counter++;
111+
}
112+
/* wait for any remaining requests responses */
113+
k_msleep(10 * TEMP_REQUESTS_DEAD_TIME_MS);
114+
tst_ipc_perf_result.handled_requests = tst_perf_served_temp_meas_requests;
115+
TC_PRINT("STOP test_temperature_nrfs_requests_performance\n");
116+
TC_PRINT("SENT: %d, HANDLED: %d, FAILED TO SEND: %d\n", tst_ipc_perf_result.sent_requests,
117+
tst_ipc_perf_result.handled_requests, tst_ipc_perf_result.failed_to_send);
118+
zassert_equal(tst_ipc_perf_result.sent_requests, tst_ipc_perf_result.handled_requests,
119+
"NRFS TEMP requests sent != served");
120+
}
121+
122+
/*
123+
* Test setup
124+
*/
125+
static void *test_setup(void)
126+
{
127+
int ret;
128+
129+
tst_perf_served_mram_requests = 0;
130+
tst_perf_served_temp_meas_requests = 0;
131+
132+
TC_PRINT("Hello World! %s\n", CONFIG_BOARD_TARGET);
133+
TC_PRINT("Waiting for NRFS backend init\n");
134+
135+
/* Wait for IPC backend connection */
136+
ret = nrfs_backend_wait_for_connection(K_MSEC(IPC_BACKEND_CONNECTION_TIMEOUT_MS));
137+
zassert_equal(ret, 0, "Failed to establih NRFS backend connection. err: %d", ret);
138+
return NULL;
139+
}
140+
141+
ZTEST_SUITE(nrfs_stress_test, NULL, test_setup, NULL, NULL, NULL);

tests/subsys/nrfs/sysbuild.cmake

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
# Copyright (c) 2025 Nordic Semiconductor ASA
2+
# SPDX-License-Identifier: Apache-2.0
3+
4+
if("${SB_CONFIG_REMOTE_BOARD}" STREQUAL "")
5+
message(FATAL_ERROR "REMOTE_BOARD must be set to a valid board name")
6+
endif()
7+
8+
# Add remote project
9+
ExternalZephyrProject_Add(
10+
APPLICATION remote
11+
SOURCE_DIR ${APP_DIR}/remote
12+
BOARD ${SB_CONFIG_REMOTE_BOARD}
13+
BOARD_REVISION ${BOARD_REVISION}
14+
)
15+
16+
# Add a dependency so that the remote image will be built and flashed first
17+
add_dependencies(nrfs remote)
18+
sysbuild_add_dependencies(FLASH nrfs remote)

tests/subsys/nrfs/testcase.yaml

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
common:
2+
platform_allow:
3+
- nrf54h20dk/nrf54h20/cpuapp
4+
- nrf54h20dk/nrf54h20/cpurad
5+
integration_platforms:
6+
- nrf54h20dk/nrf54h20/cpuapp
7+
- nrf54h20dk/nrf54h20/cpurad
8+
tags:
9+
- nrfs
10+
harness: ztest
11+
sysbuild: true
12+
13+
tests:
14+
subsys.nrfs.stress_test: {}

0 commit comments

Comments
 (0)