1 /*
2 * Copyright (c) 2022 Nordic Semiconductor ASA
3 *
4 * SPDX-License-Identifier: Apache-2.0
5 */
6
7 #include "mocks/adv.h"
8 #include "mocks/adv_expects.h"
9 #include "mocks/hci_core.h"
10 #include "mocks/hci_core_expects.h"
11 #include "testing_common_defs.h"
12
13 #include <zephyr/bluetooth/hci.h>
14 #include <zephyr/kernel.h>
15 #include <zephyr/ztest.h>
16
17 #include <host/hci_core.h>
18 #include <host/id.h>
19
20 ZTEST_SUITE(bt_id_reset_invalid_inputs, NULL, NULL, NULL, NULL, NULL);
21
22 /*
23 * Test resetting default ID which shouldn't be allowed
24 *
25 * Constraints:
26 * - BT_ID_DEFAULT value is used for the ID
27 * - Input address is NULL
28 * - Input IRK is NULL
29 *
30 * Expected behaviour:
31 * - '-EINVAL' error code is returned representing invalid values were used.
32 */
ZTEST(bt_id_reset_invalid_inputs,test_resetting_default_id)33 ZTEST(bt_id_reset_invalid_inputs, test_resetting_default_id)
34 {
35 int err;
36
37 err = bt_id_reset(BT_ID_DEFAULT, NULL, NULL);
38
39 zassert_true(err == -EINVAL, "Unexpected error code '%d' was returned", err);
40 }
41
42 /*
43 * Test resetting ID value that is equal to bt_dev.id_count
44 *
45 * Constraints:
46 * - bt_dev.id_count is greater than 0
47 * - ID value used is equal to bt_dev.id_count
48 * - Input address is NULL
49 * - Input IRK is NULL
50 *
51 * Expected behaviour:
52 * - '-EINVAL' error code is returned representing invalid values were used.
53 */
ZTEST(bt_id_reset_invalid_inputs,test_resetting_id_value_equal_to_dev_id_count)54 ZTEST(bt_id_reset_invalid_inputs, test_resetting_id_value_equal_to_dev_id_count)
55 {
56 int err;
57
58 bt_dev.id_count = 1;
59
60 err = bt_id_reset(bt_dev.id_count, NULL, NULL);
61
62 zassert_true(err == -EINVAL, "Unexpected error code '%d' was returned", err);
63 }
64
65 /*
66 * Test using a valid IRK pointer value while privacy isn't enabled
67 *
68 * Constraints:
69 * - BT_ID_DEFAULT is used for the ID
70 * - Input address is NULL
71 * - Input IRK isn't NULL
72 * - 'CONFIG_BT_PRIVACY' isn't enabled
73 *
74 * Expected behaviour:
75 * - '-EINVAL' error code is returned representing invalid values were used.
76 */
ZTEST(bt_id_reset_invalid_inputs,test_null_addr_valid_irk_no_privacy_enabled)77 ZTEST(bt_id_reset_invalid_inputs, test_null_addr_valid_irk_no_privacy_enabled)
78 {
79 int err;
80 uint8_t valid_irk_ptr[16];
81
82 err = bt_id_reset(BT_ID_DEFAULT, NULL, valid_irk_ptr);
83
84 zassert_true(err == -EINVAL, "Unexpected error code '%d' was returned", err);
85 }
86
87 /*
88 * Test invalid input arguments to bt_id_reset() by using a valid address of type public and using
89 * NULL value for the IRK.
90 *
91 * Constraints:
92 * - BT_ID_DEFAULT is used for the ID
93 * - A valid address of type public is used
94 * - Input IRK is NULL
95 *
96 * Expected behaviour:
97 * - '-EINVAL' error code is returned representing invalid values were used.
98 */
ZTEST(bt_id_reset_invalid_inputs,test_public_address)99 ZTEST(bt_id_reset_invalid_inputs, test_public_address)
100 {
101 int err;
102
103 err = bt_id_reset(BT_ID_DEFAULT, BT_LE_ADDR, NULL);
104
105 zassert_true(err == -EINVAL, "Unexpected error code '%d' was returned", err);
106 }
107
108 /*
109 * Test invalid input arguments to bt_id_reset() by using a valid address of type RPA and using
110 * NULL value for the IRK.
111 *
112 * Constraints:
113 * - BT_ID_DEFAULT is used for the ID
114 * - An RPA address of type random is used
115 * - Input IRK is NULL
116 *
117 * Expected behaviour:
118 * - '-EINVAL' error code is returned representing invalid values were used.
119 */
ZTEST(bt_id_reset_invalid_inputs,test_rpa_address)120 ZTEST(bt_id_reset_invalid_inputs, test_rpa_address)
121 {
122 int err;
123
124 err = bt_id_reset(BT_ID_DEFAULT, BT_RPA_LE_ADDR, NULL);
125
126 zassert_true(err == -EINVAL, "Unexpected error code '%d' was returned", err);
127 }
128
129 /*
130 * Test invalid input arguments to bt_id_reset() by using an address that already exists
131 * in the identity list.
132 *
133 * Constraints:
134 * - BT_ID_DEFAULT is used for the ID
135 * - A valid random static address is used
136 * - Input address already exists in the identity list
137 * - Input IRK is NULL
138 *
139 * Expected behaviour:
140 * - '-EALREADY' error code is returned representing invalid values were used.
141 */
ZTEST(bt_id_reset_invalid_inputs,test_pa_address_exists_in_id_list)142 ZTEST(bt_id_reset_invalid_inputs, test_pa_address_exists_in_id_list)
143 {
144 int err;
145
146 bt_dev.id_count = 1;
147 bt_addr_le_copy(&bt_dev.id_addr[0], BT_STATIC_RANDOM_LE_ADDR_1);
148
149 err = bt_id_reset(BT_ID_DEFAULT, BT_STATIC_RANDOM_LE_ADDR_1, NULL);
150
151 zassert_true(err == -EALREADY, "Unexpected error code '%d' was returned", err);
152 }
153
bt_le_ext_adv_foreach_custom_fake(void (* func)(struct bt_le_ext_adv * adv,void * data),void * data)154 static void bt_le_ext_adv_foreach_custom_fake(void (*func)(struct bt_le_ext_adv *adv, void *data),
155 void *data)
156 {
157 struct bt_le_ext_adv adv_params = {0};
158
159 __ASSERT_NO_MSG(func != NULL);
160 __ASSERT_NO_MSG(data != NULL);
161
162 if (IS_ENABLED(CONFIG_BT_EXT_ADV)) {
163 /* Only check if the ID is in use, as the advertiser can be
164 * started and stopped without reconfiguring parameters.
165 */
166 adv_params.id = bt_dev.id_count - 1;
167 } else {
168 atomic_set_bit(adv_params.flags, BT_ADV_ENABLED);
169 adv_params.id = bt_dev.id_count - 1;
170 }
171
172 func(&adv_params, data);
173 }
174
175 /*
176 * Test resetting an ID if the 'CONFIG_BT_BROADCASTER' is enabled and the same ID is already
177 * in use with the advertising data.
178 *
179 * Constraints:
180 * - A valid random static address is used
181 * - Input address doesn't exist in the identity list
182 * - Input IRK is NULL
183 * - 'CONFIG_BT_BROADCASTER' is enabled
184 *
185 * Expected behaviour:
186 * - '-EBUSY' error code is returned representing invalid values were used.
187 */
ZTEST(bt_id_reset_invalid_inputs,test_resetting_id_used_in_advertising)188 ZTEST(bt_id_reset_invalid_inputs, test_resetting_id_used_in_advertising)
189 {
190 int err;
191
192 Z_TEST_SKIP_IFNDEF(CONFIG_BT_BROADCASTER);
193
194 bt_dev.id_count = 2;
195
196 /* When bt_le_ext_adv_foreach() is called, this callback will be triggered and causes
197 * adv_id_check_func() to set the advertising enable flag to true.
198 */
199 bt_le_ext_adv_foreach_fake.custom_fake = bt_le_ext_adv_foreach_custom_fake;
200
201 err = bt_id_reset(bt_dev.id_count - 1, BT_STATIC_RANDOM_LE_ADDR_1, NULL);
202
203 expect_single_call_bt_le_ext_adv_foreach();
204
205 zassert_true(err == -EBUSY, "Unexpected error code '%d' was returned", err);
206 }
207
208 /*
209 * Test returning error when the ID used corresponds to an empty address and bt_unpair() fails
210 *
211 * Constraints:
212 * - A valid random static address is used
213 * - Input address doesn't exist in the identity list
214 * - Input IRK is NULL
215 * - 'CONFIG_BT_CONN' is enabled
216 * - bt_unpair() fails and returns a negative error code
217 *
218 * Expected behaviour:
219 * - '-EALREADY' error code is returned representing invalid values were used.
220 */
ZTEST(bt_id_reset_invalid_inputs,test_bt_unpair_fails)221 ZTEST(bt_id_reset_invalid_inputs, test_bt_unpair_fails)
222 {
223 int err;
224 uint8_t id;
225
226 Z_TEST_SKIP_IFNDEF(CONFIG_BT_CONN);
227
228 bt_dev.id_count = 2;
229 id = bt_dev.id_count - 1;
230
231 bt_addr_le_copy(&bt_dev.id_addr[0], BT_STATIC_RANDOM_LE_ADDR_1);
232 bt_addr_le_copy(&bt_dev.id_addr[1], BT_STATIC_RANDOM_LE_ADDR_1);
233
234 bt_unpair_fake.return_val = -1;
235
236 err = bt_id_reset(id, BT_STATIC_RANDOM_LE_ADDR_2, NULL);
237
238 expect_single_call_bt_unpair(id, NULL);
239
240 zassert_true(err < 0, "Unexpected error code '%d' was returned", err);
241 }
242