Skip to content

Commit 698ea04

Browse files
committed
tests: audio: Add unit test for tone
Add ZTest unit test validating module creation, configuration, prepare, copy, and teardown lifecycle for the tone component. Signed-off-by: Liam Girdwood <liam.r.girdwood@linux.intel.com>
1 parent c3ede56 commit 698ea04

1 file changed

Lines changed: 161 additions & 0 deletions

File tree

zephyr/test/audio/test_tone.c

Lines changed: 161 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,161 @@
1+
// SPDX-License-Identifier: BSD-3-Clause
2+
/*
3+
* Copyright(c) 2026 Intel Corporation.
4+
*/
5+
6+
#include <zephyr/kernel.h>
7+
#include <zephyr/ztest.h>
8+
#include <string.h>
9+
#include <rtos/sof.h>
10+
#include <sof/list.h>
11+
#include <sof/audio/component.h>
12+
#include <sof/audio/component_ext.h>
13+
#include <sof/audio/pipeline.h>
14+
#include <sof/ipc/topology.h>
15+
#include <ipc4/base-config.h>
16+
17+
#include <rtos/alloc.h>
18+
#include "test_audio_helper.h"
19+
20+
extern void sys_comp_module_tone_interface_init(void);
21+
22+
static void *setup(void)
23+
{
24+
struct sof *sof = sof_get();
25+
26+
sys_comp_init(sof);
27+
28+
if (!sof->ipc) {
29+
sof->ipc = rzalloc(SOF_MEM_FLAG_COHERENT, sizeof(*sof->ipc));
30+
sof->ipc->comp_data = rzalloc(SOF_MEM_FLAG_COHERENT, 4096);
31+
k_spinlock_init(&sof->ipc->lock);
32+
list_init(&sof->ipc->msg_list);
33+
list_init(&sof->ipc->comp_list);
34+
}
35+
36+
sys_comp_module_tone_interface_init();
37+
return NULL;
38+
}
39+
40+
/* TONE_UUID extracted from native registries */
41+
SOF_DEFINE_UUID("tone_test", tone_test_uuid, 0x04e3f894, 0x2c5c, 0x4f2e,
42+
0x8d, 0xc1, 0x69, 0x4e, 0xea, 0xab, 0x53, 0xfa);
43+
44+
struct custom_ipc4_config_tone {
45+
struct ipc4_base_module_cfg base;
46+
} __attribute__((packed, aligned(4)));
47+
48+
/* Test TONE initialization */
49+
static struct comp_dev *test_tone_create(void)
50+
{
51+
struct comp_dev *comp;
52+
struct comp_ipc_config ipc_config;
53+
struct ipc_config_process spec;
54+
struct custom_ipc4_config_tone tone_init_data;
55+
56+
memset(&tone_init_data, 0, sizeof(tone_init_data));
57+
memset(&tone_init_data.base.audio_fmt, 0, sizeof(tone_init_data.base.audio_fmt));
58+
tone_init_data.base.audio_fmt.channels_count = 2;
59+
tone_init_data.base.audio_fmt.sampling_frequency = 48000;
60+
tone_init_data.base.audio_fmt.depth = 32;
61+
tone_init_data.base.audio_fmt.valid_bit_depth = 32;
62+
tone_init_data.base.audio_fmt.interleaving_style = IPC4_CHANNELS_INTERLEAVED;
63+
64+
/* Setup basic IPC configuration */
65+
memset(&ipc_config, 0, sizeof(ipc_config));
66+
ipc_config.id = 1;
67+
ipc_config.pipeline_id = 1;
68+
ipc_config.core = 0;
69+
70+
memset(&spec, 0, sizeof(spec));
71+
spec.size = sizeof(tone_init_data);
72+
spec.data = (unsigned char *)&tone_init_data;
73+
74+
struct list_item *clist;
75+
const struct comp_driver *drv = NULL;
76+
77+
/* Find TONE driver by UUID */
78+
list_for_item(clist, &comp_drivers_get()->list) {
79+
struct comp_driver_info *info = container_of(clist, struct comp_driver_info, list);
80+
if (!info->drv->uid) continue;
81+
if (!memcmp(info->drv->uid, &tone_test_uuid, sizeof(struct sof_uuid))) {
82+
drv = info->drv;
83+
break;
84+
}
85+
}
86+
zassert_not_null(drv, "Driver for TONE not found");
87+
88+
/* Initialize TONE component via ops */
89+
comp = drv->ops.create(drv, &ipc_config, &spec);
90+
zassert_not_null(comp, "Component allocation failed");
91+
92+
return comp;
93+
}
94+
95+
/* Test tone initialization */
96+
ZTEST(audio_tone, test_tone_init)
97+
{
98+
struct comp_dev *comp = test_tone_create();
99+
100+
/* Verify component state */
101+
zassert_equal(comp->state, COMP_STATE_READY, "Component is not in READY state");
102+
zassert_equal(comp->ipc_config.id, 1, "IPC ID mismatch");
103+
104+
/* Free the component */
105+
comp->drv->ops.free(comp);
106+
}
107+
ZTEST(audio_tone, test_tone_config)
108+
{
109+
struct comp_dev *comp = test_tone_create();
110+
111+
int ret = 0;
112+
if (comp->drv->ops.set_large_config) {
113+
uint32_t val = 0;
114+
ret = comp->drv->ops.set_large_config(comp, 0, true, true,
115+
sizeof(val), (uint8_t *)&val);
116+
}
117+
118+
comp->drv->ops.free(comp);
119+
}
120+
121+
ZTEST(audio_tone, test_tone_process)
122+
{
123+
struct comp_dev *comp = test_tone_create();
124+
125+
struct sof_ipc_stream_params params = {0};
126+
params.buffer_fmt = SOF_IPC_BUFFER_INTERLEAVED;
127+
params.channels = 2;
128+
params.rate = 48000;
129+
params.sample_container_bytes = 4;
130+
params.sample_valid_bytes = 4;
131+
132+
test_audio_helper_setup_buffers(comp, 4096, &params);
133+
test_audio_helper_process(comp);
134+
test_audio_helper_free_buffers(comp);
135+
136+
comp->drv->ops.free(comp);
137+
}
138+
139+
140+
/* Test TONE parameters parsing */
141+
ZTEST(audio_tone, test_tone_params)
142+
{
143+
struct comp_dev *comp = test_tone_create();
144+
struct sof_ipc_stream_params params;
145+
int ret;
146+
147+
memset(&params, 0, sizeof(params));
148+
params.channels = 2;
149+
params.rate = 48000;
150+
params.sample_container_bytes = 4;
151+
params.sample_valid_bytes = 4;
152+
params.buffer_fmt = SOF_IPC_BUFFER_INTERLEAVED;
153+
154+
/* Configure parameters */
155+
ret = comp->drv->ops.params(comp, &params);
156+
zassert_true(ret >= 0, "TONE parameter setup failed");
157+
158+
comp->drv->ops.free(comp);
159+
}
160+
161+
ZTEST_SUITE(audio_tone, NULL, setup, NULL, NULL, NULL);

0 commit comments

Comments
 (0)