Skip to content

Commit 64c0039

Browse files
committed
tests: build OT RPC tests with Address Sanitizer
Enable detection of memory errors, such as use-after-free in unit tests of OpenThread RPC. Signed-off-by: Damian Krolik <damian.krolik@nordicsemi.no>
1 parent 73c2240 commit 64c0039

File tree

5 files changed

+78
-25
lines changed

5 files changed

+78
-25
lines changed

tests/subsys/net/openthread/rpc/client/prj.conf

+2
Original file line numberDiff line numberDiff line change
@@ -19,3 +19,5 @@ CONFIG_MOCK_NRF_RPC_TRANSPORT=y
1919

2020
CONFIG_KERNEL_MEM_POOL=y
2121
CONFIG_HEAP_MEM_POOL_SIZE=4096
22+
23+
CONFIG_ASAN=y

tests/subsys/net/openthread/rpc/server/prj.conf

+2
Original file line numberDiff line numberDiff line change
@@ -18,3 +18,5 @@ CONFIG_MOCK_NRF_RPC_TRANSPORT=y
1818

1919
CONFIG_KERNEL_MEM_POOL=y
2020
CONFIG_HEAP_MEM_POOL_SIZE=4096
21+
22+
CONFIG_ASAN=y

tests/subsys/net/openthread/rpc/server/src/ip6_suite.c

+43-16
Original file line numberDiff line numberDiff line change
@@ -136,72 +136,99 @@ ZTEST(ot_rpc_ip6, test_otIp6IsEnabled_true)
136136
* Test reception of otIp6SubscribeMulticastAddress(ff02::1) command.
137137
* Test serialization of the result: OT_ERROR_NONE.
138138
*/
139-
ZTEST(ot_rpc_ip6, test_otIp6SubscribeMulticastAddress)
139+
static otError subscribe_multicast_ff02_1_fake(otInstance *instance, const otIp6Address *addr)
140140
{
141-
const otIp6Address addr = {.mFields.m8 = {MADDR_FF02_1}};
141+
const otIp6Address exp_addr = {.mFields.m8 = {MADDR_FF02_1}};
142+
143+
zassert_mem_equal(addr, &exp_addr, sizeof(exp_addr));
144+
145+
return OT_ERROR_NONE;
146+
}
142147

143-
otIp6SubscribeMulticastAddress_fake.return_val = OT_ERROR_NONE;
148+
ZTEST(ot_rpc_ip6, test_otIp6SubscribeMulticastAddress)
149+
{
150+
otIp6SubscribeMulticastAddress_fake.custom_fake = subscribe_multicast_ff02_1_fake;
144151

145152
mock_nrf_rpc_tr_expect_add(RPC_RSP(0x00), NO_RSP);
146153
mock_nrf_rpc_tr_receive(RPC_CMD(OT_RPC_CMD_IP6_SUBSCRIBE_MADDR, 0x50, MADDR_FF02_1));
147154
mock_nrf_rpc_tr_expect_done();
148155

149156
zassert_equal(otIp6SubscribeMulticastAddress_fake.call_count, 1);
150-
zassert_mem_equal(otIp6SubscribeMulticastAddress_fake.arg1_val, &addr, sizeof(addr));
151157
}
152158

153159
/*
154160
* Test reception of otIp6SubscribeMulticastAddress(ff02::1) command.
155161
* Test serialization of the result: OT_ERROR_FAILED.
156162
*/
157-
ZTEST(ot_rpc_ip6, test_otIp6SubscribeMulticastAddress_failed)
163+
static otError subscribe_multicast_ff02_1_failed_fake(otInstance *instance,
164+
const otIp6Address *addr)
158165
{
159-
const otIp6Address addr = {.mFields.m8 = {MADDR_FF02_1}};
166+
const otIp6Address exp_addr = {.mFields.m8 = {MADDR_FF02_1}};
167+
168+
zassert_mem_equal(addr, &exp_addr, sizeof(exp_addr));
169+
170+
return OT_ERROR_FAILED;
171+
}
160172

161-
otIp6SubscribeMulticastAddress_fake.return_val = OT_ERROR_FAILED;
173+
ZTEST(ot_rpc_ip6, test_otIp6SubscribeMulticastAddress_failed)
174+
{
175+
otIp6SubscribeMulticastAddress_fake.custom_fake = subscribe_multicast_ff02_1_failed_fake;
162176

163177
mock_nrf_rpc_tr_expect_add(RPC_RSP(0x01), NO_RSP);
164178
mock_nrf_rpc_tr_receive(RPC_CMD(OT_RPC_CMD_IP6_SUBSCRIBE_MADDR, 0x50, MADDR_FF02_1));
165179
mock_nrf_rpc_tr_expect_done();
166180

167181
zassert_equal(otIp6SubscribeMulticastAddress_fake.call_count, 1);
168-
zassert_mem_equal(otIp6SubscribeMulticastAddress_fake.arg1_val, &addr, sizeof(addr));
169182
}
170183

171184
/*
172185
* Test reception of otIp6UnubscribeMulticastAddress(ff02::1) command.
173186
* Test serialization of the result: OT_ERROR_NONE.
174187
*/
175-
ZTEST(ot_rpc_ip6, test_otIp6UnsubscribeMulticastAddress)
188+
static otError unsubscribe_multicast_ff02_1_fake(otInstance *instance, const otIp6Address *addr)
176189
{
177-
const otIp6Address addr = {.mFields.m8 = {MADDR_FF02_1}};
190+
const otIp6Address exp_addr = {.mFields.m8 = {MADDR_FF02_1}};
191+
192+
zassert_mem_equal(addr, &exp_addr, sizeof(exp_addr));
193+
194+
return OT_ERROR_NONE;
195+
}
178196

179-
otIp6UnsubscribeMulticastAddress_fake.return_val = OT_ERROR_NONE;
197+
ZTEST(ot_rpc_ip6, test_otIp6UnsubscribeMulticastAddress)
198+
{
199+
otIp6UnsubscribeMulticastAddress_fake.custom_fake = unsubscribe_multicast_ff02_1_fake;
180200

181201
mock_nrf_rpc_tr_expect_add(RPC_RSP(0x00), NO_RSP);
182202
mock_nrf_rpc_tr_receive(RPC_CMD(OT_RPC_CMD_IP6_UNSUBSCRIBE_MADDR, 0x50, MADDR_FF02_1));
183203
mock_nrf_rpc_tr_expect_done();
184204

185205
zassert_equal(otIp6UnsubscribeMulticastAddress_fake.call_count, 1);
186-
zassert_mem_equal(otIp6UnsubscribeMulticastAddress_fake.arg1_val, &addr, sizeof(addr));
187206
}
188207

189208
/*
190209
* Test reception of otIp6UnubscribeMulticastAddress(ff02::1) command.
191210
* Test serialization of the result: OT_ERROR_FAILED.
192211
*/
193-
ZTEST(ot_rpc_ip6, test_otIp6UnsubscribeMulticastAddress_failed)
212+
static otError unsubscribe_multicast_ff02_1_failed_fake(otInstance *instance,
213+
const otIp6Address *addr)
194214
{
195-
const otIp6Address addr = {.mFields.m8 = {MADDR_FF02_1}};
215+
const otIp6Address exp_addr = {.mFields.m8 = {MADDR_FF02_1}};
216+
217+
zassert_mem_equal(addr, &exp_addr, sizeof(exp_addr));
218+
219+
return OT_ERROR_FAILED;
220+
}
196221

197-
otIp6UnsubscribeMulticastAddress_fake.return_val = OT_ERROR_FAILED;
222+
ZTEST(ot_rpc_ip6, test_otIp6UnsubscribeMulticastAddress_failed)
223+
{
224+
otIp6UnsubscribeMulticastAddress_fake.custom_fake =
225+
unsubscribe_multicast_ff02_1_failed_fake;
198226

199227
mock_nrf_rpc_tr_expect_add(RPC_RSP(0x01), NO_RSP);
200228
mock_nrf_rpc_tr_receive(RPC_CMD(OT_RPC_CMD_IP6_UNSUBSCRIBE_MADDR, 0x50, MADDR_FF02_1));
201229
mock_nrf_rpc_tr_expect_done();
202230

203231
zassert_equal(otIp6UnsubscribeMulticastAddress_fake.call_count, 1);
204-
zassert_mem_equal(otIp6UnsubscribeMulticastAddress_fake.arg1_val, &addr, sizeof(addr));
205232
}
206233

207234
/*

tests/subsys/net/openthread/rpc/server/src/message_suite.c

+23-4
Original file line numberDiff line numberDiff line change
@@ -43,6 +43,15 @@ static void tc_setup(void *f)
4343
FFF_RESET_HISTORY();
4444
}
4545

46+
static otMessage *udp_new_message_failed_fake(otInstance *instance,
47+
const otMessageSettings *settings)
48+
{
49+
zassert_true(settings->mLinkSecurityEnabled);
50+
zassert_equal(settings->mPriority, 40);
51+
52+
return NULL;
53+
}
54+
4655
ZTEST(ot_rpc_message, test_otUdpNewMessage_failing)
4756
{
4857
const uint8_t prio = 40;
@@ -52,15 +61,24 @@ ZTEST(ot_rpc_message, test_otUdpNewMessage_failing)
5261
mock_nrf_rpc_tr_expect_add(RPC_RSP(0), NO_RSP);
5362
mock_nrf_rpc_tr_receive(RPC_CMD(OT_RPC_CMD_UDP_NEW_MESSAGE, CBOR_NULL));
5463

64+
zassert_equal(otUdpNewMessage_fake.call_count, 1);
5565
zassert_is_null(otUdpNewMessage_fake.arg1_val);
5666

67+
otUdpNewMessage_fake.custom_fake = udp_new_message_failed_fake;
68+
5769
mock_nrf_rpc_tr_expect_add(RPC_RSP(0), NO_RSP);
5870
mock_nrf_rpc_tr_receive(RPC_CMD(OT_RPC_CMD_UDP_NEW_MESSAGE, CBOR_TRUE, CBOR_UINT8(prio)));
5971
mock_nrf_rpc_tr_expect_done();
6072

6173
zassert_equal(otUdpNewMessage_fake.call_count, 2);
62-
zassert_true(otUdpNewMessage_fake.arg1_val->mLinkSecurityEnabled);
63-
zassert_equal(otUdpNewMessage_fake.arg1_val->mPriority, prio);
74+
}
75+
76+
static otMessage *udp_new_message_free_fake(otInstance *instance, const otMessageSettings *settings)
77+
{
78+
zassert_true(settings->mLinkSecurityEnabled);
79+
zassert_equal(settings->mPriority, 40);
80+
81+
return (otMessage *)1;
6482
}
6583

6684
ZTEST(ot_rpc_message, test_otUdpNewMessage_free_working)
@@ -72,14 +90,15 @@ ZTEST(ot_rpc_message, test_otUdpNewMessage_free_working)
7290
mock_nrf_rpc_tr_expect_add(RPC_RSP(1), NO_RSP);
7391
mock_nrf_rpc_tr_receive(RPC_CMD(OT_RPC_CMD_UDP_NEW_MESSAGE, CBOR_NULL));
7492

93+
zassert_equal(otUdpNewMessage_fake.call_count, 1);
7594
zassert_is_null(otUdpNewMessage_fake.arg1_val);
7695

96+
otUdpNewMessage_fake.custom_fake = udp_new_message_free_fake;
97+
7798
mock_nrf_rpc_tr_expect_add(RPC_RSP(2), NO_RSP);
7899
mock_nrf_rpc_tr_receive(RPC_CMD(OT_RPC_CMD_UDP_NEW_MESSAGE, CBOR_TRUE, CBOR_UINT8(prio)));
79100

80101
zassert_equal(otUdpNewMessage_fake.call_count, 2);
81-
zassert_true(otUdpNewMessage_fake.arg1_val->mLinkSecurityEnabled);
82-
zassert_equal(otUdpNewMessage_fake.arg1_val->mPriority, prio);
83102

84103
mock_nrf_rpc_tr_expect_add(RPC_RSP(), NO_RSP);
85104
mock_nrf_rpc_tr_receive(RPC_CMD(OT_RPC_CMD_MESSAGE_FREE, 1));

tests/subsys/net/openthread/rpc/server/src/netdiag_suite.c

+8-5
Original file line numberDiff line numberDiff line change
@@ -50,25 +50,28 @@ static void tc_setup(void *f)
5050
#define TEST_STRING_SETTER(test_name, cmd, data, data_cbor, func_to_call, max_length, result_exp) \
5151
static otError fake_##test_name(otInstance *instance, const char *arg) \
5252
{ \
53+
char data_exp[] = data; \
54+
\
5355
ARG_UNUSED(instance); \
56+
\
5457
if (strlen(arg) > max_length) { \
5558
return OT_ERROR_INVALID_ARGS; \
5659
} \
5760
\
61+
zassert_str_equal(func_to_call##_fake.arg1_val, data_exp); \
62+
\
5863
return OT_ERROR_NONE; \
5964
} \
60-
\
65+
\
6166
ZTEST(ot_rpc_netdiag, test_name) \
6267
{ \
63-
char data_exp[] = data; \
6468
func_to_call##_fake.custom_fake = fake_##test_name; \
65-
\
69+
\
6670
mock_nrf_rpc_tr_expect_add(RPC_RSP(result_exp), NO_RSP); \
6771
mock_nrf_rpc_tr_receive(RPC_CMD(cmd, data_cbor)); \
6872
mock_nrf_rpc_tr_expect_done(); \
69-
\
73+
\
7074
zassert_equal(func_to_call##_fake.call_count, 1); \
71-
zassert_str_equal(func_to_call##_fake.arg1_val, data_exp); \
7275
}
7376

7477
#define TEST_STRING_GETTER(test_name, cmd, data, data_cbor, func_to_call) \

0 commit comments

Comments
 (0)