1 /******************************************************************************
2 *
3 * Copyright 2018 The Android Open Source Project
4 *
5 * Licensed under the Apache License, Version 2.0 (the "License");
6 * you may not use this file except in compliance with the License.
7 * You may obtain a copy of the License at:
8 *
9 * http://www.apache.org/licenses/LICENSE-2.0
10 *
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
16 *
17 ******************************************************************************/
18
19 #include <gmock/gmock.h>
20 #include <gtest/gtest.h>
21
22 #include "stack/crypto_toolbox/aes.h"
23 #include "stack/crypto_toolbox/crypto_toolbox.h"
24
25 #include <base/logging.h>
26 #include <base/strings/string_number_conversions.h>
27 #include <vector>
28
29 using ::testing::ElementsAreArray;
30
31 namespace crypto_toolbox {
32
33 // BT Spec 5.0 | Vol 3, Part H D.1
TEST(CryptoToolboxTest,bt_spec_test_d_1_test)34 TEST(CryptoToolboxTest, bt_spec_test_d_1_test) {
35 uint8_t k[] = {0x2b, 0x7e, 0x15, 0x16, 0x28, 0xae, 0xd2, 0xa6,
36 0xab, 0xf7, 0x15, 0x88, 0x09, 0xcf, 0x4f, 0x3c};
37
38 uint8_t m[] = {0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
39 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00};
40
41 uint8_t aes_cmac_k_m[] = {0x7d, 0xf7, 0x6b, 0x0c, 0x1a, 0xb8, 0x99, 0xb3,
42 0x3e, 0x42, 0xf0, 0x47, 0xb9, 0x1b, 0x54, 0x6f};
43
44 uint8_t output[16];
45 aes_context ctx;
46 aes_set_key(k, sizeof(k), &ctx);
47 aes_encrypt(m, output, &ctx); /* outputs in byte 48 to byte 63 */
48
49 EXPECT_THAT(output, ElementsAreArray(aes_cmac_k_m, OCTET16_LEN));
50
51 // useful for debugging
52 // LOG(INFO) << "k " << base::HexEncode(k, OCTET16_LEN);
53 // LOG(INFO) << "m " << base::HexEncode(m, sizeof(m));
54 // LOG(INFO) << "output " << base::HexEncode(output, OCTET16_LEN);
55 }
56
57 // BT Spec 5.0 | Vol 3, Part H D.1.1
TEST(CryptoToolboxTest,bt_spec_example_d_1_1_test)58 TEST(CryptoToolboxTest, bt_spec_example_d_1_1_test) {
59 Octet16 k{0x2b, 0x7e, 0x15, 0x16, 0x28, 0xae, 0xd2, 0xa6,
60 0xab, 0xf7, 0x15, 0x88, 0x09, 0xcf, 0x4f, 0x3c};
61
62 Octet16 aes_cmac_k_m{0xbb, 0x1d, 0x69, 0x29, 0xe9, 0x59, 0x37, 0x28,
63 0x7f, 0xa3, 0x7d, 0x12, 0x9b, 0x75, 0x67, 0x46};
64
65 // algorithm expect all input to be in little endian format, so reverse
66 std::reverse(std::begin(k), std::end(k));
67 std::reverse(std::begin(aes_cmac_k_m), std::end(aes_cmac_k_m));
68
69 Octet16 output = aes_cmac(k, nullptr /* empty message */, 0);
70
71 EXPECT_EQ(output, aes_cmac_k_m);
72
73 // useful for debugging
74 // LOG(INFO) << "k " << base::HexEncode(k.data(), k.size());
75 // LOG(INFO) << "aes_cmac(k,nullptr) "
76 // << base::HexEncode(output.data(), output.size());
77 }
78
79 // BT Spec 5.0 | Vol 3, Part H D.1.2
TEST(CryptoToolboxTest,bt_spec_example_d_1_2_test)80 TEST(CryptoToolboxTest, bt_spec_example_d_1_2_test) {
81 Octet16 k{0x2b, 0x7e, 0x15, 0x16, 0x28, 0xae, 0xd2, 0xa6,
82 0xab, 0xf7, 0x15, 0x88, 0x09, 0xcf, 0x4f, 0x3c};
83
84 Octet16 m = {0x6b, 0xc1, 0xbe, 0xe2, 0x2e, 0x40, 0x9f, 0x96,
85 0xe9, 0x3d, 0x7e, 0x11, 0x73, 0x93, 0x17, 0x2a};
86
87 Octet16 aes_cmac_k_m{0x07, 0x0a, 0x16, 0xb4, 0x6b, 0x4d, 0x41, 0x44,
88 0xf7, 0x9b, 0xdd, 0x9d, 0xd0, 0x4a, 0x28, 0x7c};
89
90 // algorithm expect all input to be in little endian format, so reverse
91 std::reverse(std::begin(k), std::end(k));
92 std::reverse(std::begin(m), std::end(m));
93 std::reverse(std::begin(aes_cmac_k_m), std::end(aes_cmac_k_m));
94
95 Octet16 output = aes_cmac(k, m);
96
97 EXPECT_EQ(output, aes_cmac_k_m);
98
99 // useful for debugging
100 // LOG(INFO) << "k " << base::HexEncode(k.data(), k.size());
101 // LOG(INFO) << "m " << base::HexEncode(m, sizeof(m));
102 // LOG(INFO) << "aes_cmac(k,m) "
103 // << base::HexEncode(output.data(), output.size());
104 }
105
106 // BT Spec 5.0 | Vol 3, Part H D.1.3
TEST(CryptoToolboxTest,bt_spec_example_d_1_3_test)107 TEST(CryptoToolboxTest, bt_spec_example_d_1_3_test) {
108 Octet16 k{0x2b, 0x7e, 0x15, 0x16, 0x28, 0xae, 0xd2, 0xa6,
109 0xab, 0xf7, 0x15, 0x88, 0x09, 0xcf, 0x4f, 0x3c};
110
111 uint8_t m[] = {0x6b, 0xc1, 0xbe, 0xe2, 0x2e, 0x40, 0x9f, 0x96, 0xe9, 0x3d,
112 0x7e, 0x11, 0x73, 0x93, 0x17, 0x2a, 0xae, 0x2d, 0x8a, 0x57,
113 0x1e, 0x03, 0xac, 0x9c, 0x9e, 0xb7, 0x6f, 0xac, 0x45, 0xaf,
114 0x8e, 0x51, 0x30, 0xc8, 0x1c, 0x46, 0xa3, 0x5c, 0xe4, 0x11};
115
116 Octet16 aes_cmac_k_m{0xdf, 0xa6, 0x67, 0x47, 0xde, 0x9a, 0xe6, 0x30,
117 0x30, 0xca, 0x32, 0x61, 0x14, 0x97, 0xc8, 0x27};
118
119 // algorithm expect all input to be in little endian format, so reverse
120 std::reverse(std::begin(k), std::end(k));
121 std::reverse(std::begin(m), std::end(m));
122 std::reverse(std::begin(aes_cmac_k_m), std::end(aes_cmac_k_m));
123
124 Octet16 output = aes_cmac(k, m, sizeof(m));
125 EXPECT_EQ(output, aes_cmac_k_m);
126 }
127
128 // BT Spec 5.0 | Vol 3, Part H D.1.4
TEST(CryptoToolboxTest,bt_spec_example_d_1_4_test)129 TEST(CryptoToolboxTest, bt_spec_example_d_1_4_test) {
130 Octet16 k{0x2b, 0x7e, 0x15, 0x16, 0x28, 0xae, 0xd2, 0xa6,
131 0xab, 0xf7, 0x15, 0x88, 0x09, 0xcf, 0x4f, 0x3c};
132
133 uint8_t m[] = {0x6b, 0xc1, 0xbe, 0xe2, 0x2e, 0x40, 0x9f, 0x96, 0xe9, 0x3d,
134 0x7e, 0x11, 0x73, 0x93, 0x17, 0x2a, 0xae, 0x2d, 0x8a, 0x57,
135 0x1e, 0x03, 0xac, 0x9c, 0x9e, 0xb7, 0x6f, 0xac, 0x45, 0xaf,
136 0x8e, 0x51, 0x30, 0xc8, 0x1c, 0x46, 0xa3, 0x5c, 0xe4, 0x11,
137 0xe5, 0xfb, 0xc1, 0x19, 0x1a, 0x0a, 0x52, 0xef, 0xf6, 0x9f,
138 0x24, 0x45, 0xdf, 0x4f, 0x9b, 0x17, 0xad, 0x2b, 0x41, 0x7b,
139 0xe6, 0x6c, 0x37, 0x10};
140
141 Octet16 aes_cmac_k_m{0x51, 0xf0, 0xbe, 0xbf, 0x7e, 0x3b, 0x9d, 0x92,
142 0xfc, 0x49, 0x74, 0x17, 0x79, 0x36, 0x3c, 0xfe};
143
144 // algorithm expect all input to be in little endian format, so reverse
145 std::reverse(std::begin(k), std::end(k));
146 std::reverse(std::begin(m), std::end(m));
147 std::reverse(std::begin(aes_cmac_k_m), std::end(aes_cmac_k_m));
148
149 Octet16 output = aes_cmac(k, m, sizeof(m));
150
151 EXPECT_EQ(output, aes_cmac_k_m);
152 }
153
154 // BT Spec 5.0 | Vol 3, Part H D.2
TEST(CryptoToolboxTest,bt_spec_example_d_2_test)155 TEST(CryptoToolboxTest, bt_spec_example_d_2_test) {
156 std::vector<uint8_t> u{0x20, 0xb0, 0x03, 0xd2, 0xf2, 0x97, 0xbe, 0x2c,
157 0x5e, 0x2c, 0x83, 0xa7, 0xe9, 0xf9, 0xa5, 0xb9,
158 0xef, 0xf4, 0x91, 0x11, 0xac, 0xf4, 0xfd, 0xdb,
159 0xcc, 0x03, 0x01, 0x48, 0x0e, 0x35, 0x9d, 0xe6};
160 std::vector<uint8_t> v{0x55, 0x18, 0x8b, 0x3d, 0x32, 0xf6, 0xbb, 0x9a,
161 0x90, 0x0a, 0xfc, 0xfb, 0xee, 0xd4, 0xe7, 0x2a,
162 0x59, 0xcb, 0x9a, 0xc2, 0xf1, 0x9d, 0x7c, 0xfb,
163 0x6b, 0x4f, 0xdd, 0x49, 0xf4, 0x7f, 0xc5, 0xfd};
164 Octet16 x{0xd5, 0xcb, 0x84, 0x54, 0xd1, 0x77, 0x73, 0x3e,
165 0xff, 0xff, 0xb2, 0xec, 0x71, 0x2b, 0xae, 0xab};
166 uint8_t z = 0x00;
167
168 Octet16 aes_cmac_k_m{0xf2, 0xc9, 0x16, 0xf1, 0x07, 0xa9, 0xbd, 0x1c,
169 0xf1, 0xed, 0xa1, 0xbe, 0xa9, 0x74, 0x87, 0x2d};
170
171 // algorithm expect all input to be in little endian format, so reverse
172 std::reverse(std::begin(u), std::end(u));
173 std::reverse(std::begin(v), std::end(v));
174 std::reverse(std::begin(x), std::end(x));
175 std::reverse(std::begin(aes_cmac_k_m), std::end(aes_cmac_k_m));
176
177 Octet16 output = f4(u.data(), v.data(), x, z);
178
179 EXPECT_EQ(output, aes_cmac_k_m);
180 }
181
182 // BT Spec 5.0 | Vol 3, Part H D.3
TEST(CryptoToolboxTest,bt_spec_example_d_3_test)183 TEST(CryptoToolboxTest, bt_spec_example_d_3_test) {
184 std::array<uint8_t, 32> dhkey_w{
185 0xec, 0x02, 0x34, 0xa3, 0x57, 0xc8, 0xad, 0x05, 0x34, 0x10, 0x10,
186 0xa6, 0x0a, 0x39, 0x7d, 0x9b, 0x99, 0x79, 0x6b, 0x13, 0xb4, 0xf8,
187 0x66, 0xf1, 0x86, 0x8d, 0x34, 0xf3, 0x73, 0xbf, 0xa6, 0x98};
188 Octet16 n1{0xd5, 0xcb, 0x84, 0x54, 0xd1, 0x77, 0x73, 0x3e,
189 0xff, 0xff, 0xb2, 0xec, 0x71, 0x2b, 0xae, 0xab};
190 Octet16 n2{0xa6, 0xe8, 0xe7, 0xcc, 0x25, 0xa7, 0x5f, 0x6e,
191 0x21, 0x65, 0x83, 0xf7, 0xff, 0x3d, 0xc4, 0xcf};
192 std::array<uint8_t, 7> a1{0x00, 0x56, 0x12, 0x37, 0x37, 0xbf, 0xce};
193 std::array<uint8_t, 7> a2{0x00, 0xa7, 0x13, 0x70, 0x2d, 0xcf, 0xc1};
194
195 Octet16 expected_ltk{0x69, 0x86, 0x79, 0x11, 0x69, 0xd7, 0xcd, 0x23,
196 0x98, 0x05, 0x22, 0xb5, 0x94, 0x75, 0x0a, 0x38};
197 Octet16 expected_mac_key{0x29, 0x65, 0xf1, 0x76, 0xa1, 0x08, 0x4a, 0x02,
198 0xfd, 0x3f, 0x6a, 0x20, 0xce, 0x63, 0x6e, 0x20};
199
200 // algorithm expect all input to be in little endian format, so reverse
201 std::reverse(std::begin(dhkey_w), std::end(dhkey_w));
202 std::reverse(std::begin(n1), std::end(n1));
203 std::reverse(std::begin(n2), std::end(n2));
204 std::reverse(std::begin(a1), std::end(a1));
205 std::reverse(std::begin(a2), std::end(a2));
206 std::reverse(std::begin(expected_ltk), std::end(expected_ltk));
207 std::reverse(std::begin(expected_mac_key), std::end(expected_mac_key));
208
209 Octet16 mac_key, ltk;
210 f5(dhkey_w.data(), n1, n2, a1.data(), a2.data(), &mac_key, <k);
211
212 EXPECT_EQ(mac_key, expected_mac_key);
213 EXPECT_EQ(ltk, expected_ltk);
214 }
215
216 // BT Spec 5.0 | Vol 3, Part H D.4
TEST(CryptoToolboxTest,bt_spec_example_d_4_test)217 TEST(CryptoToolboxTest, bt_spec_example_d_4_test) {
218 Octet16 n1{0xd5, 0xcb, 0x84, 0x54, 0xd1, 0x77, 0x73, 0x3e,
219 0xff, 0xff, 0xb2, 0xec, 0x71, 0x2b, 0xae, 0xab};
220 Octet16 n2{0xa6, 0xe8, 0xe7, 0xcc, 0x25, 0xa7, 0x5f, 0x6e,
221 0x21, 0x65, 0x83, 0xf7, 0xff, 0x3d, 0xc4, 0xcf};
222 Octet16 r{0x12, 0xa3, 0x34, 0x3b, 0xb4, 0x53, 0xbb, 0x54,
223 0x08, 0xda, 0x42, 0xd2, 0x0c, 0x2d, 0x0f, 0xc8};
224 std::vector<uint8_t> IOcap{0x01, 0x01, 0x02};
225 std::vector<uint8_t> a1{0x00, 0x56, 0x12, 0x37, 0x37, 0xbf, 0xce};
226 std::vector<uint8_t> a2{0x00, 0xa7, 0x13, 0x70, 0x2d, 0xcf, 0xc1};
227
228 Octet16 MacKey{0x29, 0x65, 0xf1, 0x76, 0xa1, 0x08, 0x4a, 0x02,
229 0xfd, 0x3f, 0x6a, 0x20, 0xce, 0x63, 0x6e, 0x20};
230
231 Octet16 expected_aes_cmac{0xe3, 0xc4, 0x73, 0x98, 0x9c, 0xd0, 0xe8, 0xc5,
232 0xd2, 0x6c, 0x0b, 0x09, 0xda, 0x95, 0x8f, 0x61};
233
234 // algorithm expect all input to be in little endian format, so reverse
235 std::reverse(std::begin(n1), std::end(n1));
236 std::reverse(std::begin(n2), std::end(n2));
237 std::reverse(std::begin(r), std::end(r));
238 std::reverse(std::begin(IOcap), std::end(IOcap));
239 std::reverse(std::begin(a1), std::end(a1));
240 std::reverse(std::begin(a2), std::end(a2));
241 std::reverse(std::begin(MacKey), std::end(MacKey));
242 std::reverse(std::begin(expected_aes_cmac), std::end(expected_aes_cmac));
243
244 Octet16 aes_cmac = f6(MacKey, n1, n2, r, IOcap.data(), a1.data(), a2.data());
245
246 EXPECT_EQ(aes_cmac, expected_aes_cmac);
247 }
248
249 // BT Spec 5.0 | Vol 3, Part H D.5
TEST(CryptoToolboxTest,bt_spec_example_d_5_test)250 TEST(CryptoToolboxTest, bt_spec_example_d_5_test) {
251 std::array<uint8_t, 32> u{0x20, 0xb0, 0x03, 0xd2, 0xf2, 0x97, 0xbe, 0x2c,
252 0x5e, 0x2c, 0x83, 0xa7, 0xe9, 0xf9, 0xa5, 0xb9,
253 0xef, 0xf4, 0x91, 0x11, 0xac, 0xf4, 0xfd, 0xdb,
254 0xcc, 0x03, 0x01, 0x48, 0x0e, 0x35, 0x9d, 0xe6};
255 std::array<uint8_t, 32> v{0x55, 0x18, 0x8b, 0x3d, 0x32, 0xf6, 0xbb, 0x9a,
256 0x90, 0x0a, 0xfc, 0xfb, 0xee, 0xd4, 0xe7, 0x2a,
257 0x59, 0xcb, 0x9a, 0xc2, 0xf1, 0x9d, 0x7c, 0xfb,
258 0x6b, 0x4f, 0xdd, 0x49, 0xf4, 0x7f, 0xc5, 0xfd};
259
260 Octet16 x{0xd5, 0xcb, 0x84, 0x54, 0xd1, 0x77, 0x73, 0x3e,
261 0xff, 0xff, 0xb2, 0xec, 0x71, 0x2b, 0xae, 0xab};
262 Octet16 y{0xa6, 0xe8, 0xe7, 0xcc, 0x25, 0xa7, 0x5f, 0x6e,
263 0x21, 0x65, 0x83, 0xf7, 0xff, 0x3d, 0xc4, 0xcf};
264
265 // algorithm expect all input to be in little endian format, so reverse
266 std::reverse(std::begin(u), std::end(u));
267 std::reverse(std::begin(v), std::end(v));
268 std::reverse(std::begin(x), std::end(x));
269 std::reverse(std::begin(y), std::end(y));
270
271 uint32_t val = g2(u.data(), v.data(), x, y);
272
273 /* the returned value is already mod 1000000, so do mod on the test result
274 * value too */
275 EXPECT_EQ(val, 0x2f9ed5baU % 1000000);
276 }
277
278 // BT Spec 5.0 | Vol 3, Part H D.6
TEST(CryptoToolboxTest,bt_spec_example_d_6_test)279 TEST(CryptoToolboxTest, bt_spec_example_d_6_test) {
280 Octet16 key{0xec, 0x02, 0x34, 0xa3, 0x57, 0xc8, 0xad, 0x05,
281 0x34, 0x10, 0x10, 0xa6, 0x0a, 0x39, 0x7d, 0x9b};
282 std::array<uint8_t, 4> keyID{0x6c, 0x65, 0x62, 0x72};
283 Octet16 expected_aes_cmac{0x2d, 0x9a, 0xe1, 0x02, 0xe7, 0x6d, 0xc9, 0x1c,
284 0xe8, 0xd3, 0xa9, 0xe2, 0x80, 0xb1, 0x63, 0x99};
285
286 // algorithm expect all input to be in little endian format, so reverse
287 std::reverse(std::begin(key), std::end(key));
288 std::reverse(std::begin(keyID), std::end(keyID));
289 std::reverse(std::begin(expected_aes_cmac), std::end(expected_aes_cmac));
290
291 Octet16 aes_cmac = h6(key, keyID);
292 EXPECT_EQ(aes_cmac, expected_aes_cmac);
293 }
294
295 // BT Spec 5.0 | Vol 3, Part H D.7
TEST(CryptoToolboxTest,bt_spec_example_d_7_test)296 TEST(CryptoToolboxTest, bt_spec_example_d_7_test) {
297 Octet16 IRK{0xec, 0x02, 0x34, 0xa3, 0x57, 0xc8, 0xad, 0x05,
298 0x34, 0x10, 0x10, 0xa6, 0x0a, 0x39, 0x7d, 0x9b};
299 Octet16 prand{0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
300 0x00, 0x00, 0x00, 0x00, 0x00, 0x70, 0x81, 0x94};
301 Octet16 expected_aes_128{0x15, 0x9d, 0x5f, 0xb7, 0x2e, 0xbe, 0x23, 0x11,
302 0xa4, 0x8c, 0x1b, 0xdc, 0xc4, 0x0d, 0xfb, 0xaa};
303 std::array<uint8_t, 3> expected_ah{0x0d, 0xfb, 0xaa};
304
305 // algorithm expect all input to be in little endian format, so reverse
306 std::reverse(std::begin(IRK), std::end(IRK));
307 std::reverse(std::begin(prand), std::end(prand));
308 std::reverse(std::begin(expected_aes_128), std::end(expected_aes_128));
309 std::reverse(std::begin(expected_ah), std::end(expected_ah));
310
311 Octet16 result = aes_128(IRK, prand.data(), 3);
312 EXPECT_EQ(expected_aes_128, result);
313
314 // little/big endian 24 bits
315 EXPECT_EQ(result[0], expected_ah[0]);
316 EXPECT_EQ(result[1], expected_ah[1]);
317 EXPECT_EQ(result[2], expected_ah[2]);
318 }
319
320 // BT Spec 5.0 | Vol 3, Part H D.8
TEST(CryptoToolboxTest,bt_spec_example_d_8_test)321 TEST(CryptoToolboxTest, bt_spec_example_d_8_test) {
322 Octet16 Key{0xec, 0x02, 0x34, 0xa3, 0x57, 0xc8, 0xad, 0x05,
323 0x34, 0x10, 0x10, 0xa6, 0x0a, 0x39, 0x7d, 0x9b};
324 Octet16 SALT{0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
325 0x00, 0x00, 0x00, 0x00, 0x74, 0x6D, 0x70, 0x31};
326 Octet16 expected_aes_cmac{0xfb, 0x17, 0x35, 0x97, 0xc6, 0xa3, 0xc0, 0xec,
327 0xd2, 0x99, 0x8c, 0x2a, 0x75, 0xa5, 0x70, 0x11};
328
329 // algorithm expect all input to be in little endian format, so reverse
330 std::reverse(std::begin(Key), std::end(Key));
331 std::reverse(std::begin(SALT), std::end(SALT));
332 std::reverse(std::begin(expected_aes_cmac), std::end(expected_aes_cmac));
333
334 Octet16 aes_cmac = h7(SALT, Key);
335 EXPECT_EQ(expected_aes_cmac, aes_cmac);
336 }
337
338 extern Octet16 smp_calculate_ltk_to_link_key(const Octet16& ltk, bool use_h7);
339
340 // BT Spec 5.0 | Vol 3, Part H D.9
TEST(CryptoToolboxTest,bt_spec_example_d_9_test)341 TEST(CryptoToolboxTest, bt_spec_example_d_9_test) {
342 Octet16 LTK{0x36, 0x8d, 0xf9, 0xbc, 0xe3, 0x26, 0x4b, 0x58,
343 0xbd, 0x06, 0x6c, 0x33, 0x33, 0x4f, 0xbf, 0x64};
344 Octet16 expected_link_key{0x28, 0x7a, 0xd3, 0x79, 0xdc, 0xa4, 0x02, 0x53,
345 0x0a, 0x39, 0xf1, 0xf4, 0x30, 0x47, 0xb8, 0x35};
346
347 // algorithm expect all input to be in little endian format, so reverse
348 std::reverse(std::begin(LTK), std::end(LTK));
349 std::reverse(std::begin(expected_link_key), std::end(expected_link_key));
350
351 Octet16 link_key = ltk_to_link_key(LTK, true);
352 EXPECT_EQ(expected_link_key, link_key);
353 }
354
355 // BT Spec 5.0 | Vol 3, Part H D.10
TEST(CryptoToolboxTest,bt_spec_example_d_10_test)356 TEST(CryptoToolboxTest, bt_spec_example_d_10_test) {
357 Octet16 LTK{0x36, 0x8d, 0xf9, 0xbc, 0xe3, 0x26, 0x4b, 0x58,
358 0xbd, 0x06, 0x6c, 0x33, 0x33, 0x4f, 0xbf, 0x64};
359 Octet16 expected_link_key{0xbc, 0x1c, 0xa4, 0xef, 0x63, 0x3f, 0xc1, 0xbd,
360 0x0d, 0x82, 0x30, 0xaf, 0xee, 0x38, 0x8f, 0xb0};
361
362 // algorithm expect all input to be in little endian format, so reverse
363 std::reverse(std::begin(LTK), std::end(LTK));
364 std::reverse(std::begin(expected_link_key), std::end(expected_link_key));
365
366 Octet16 link_key = ltk_to_link_key(LTK, false);
367 EXPECT_EQ(expected_link_key, link_key);
368 }
369
370 // // BT Spec 5.0 | Vol 3, Part H D.11
TEST(CryptoToolboxTest,bt_spec_example_d_11_test)371 TEST(CryptoToolboxTest, bt_spec_example_d_11_test) {
372 Octet16 link_key{0x05, 0x04, 0x03, 0x02, 0x01, 0x00, 0x09, 0x08,
373 0x07, 0x06, 0x05, 0x04, 0x03, 0x02, 0x01, 0x00};
374 Octet16 expected_ltk{0xe8, 0x5e, 0x09, 0xeb, 0x5e, 0xcc, 0xb3, 0xe2,
375 0x69, 0x41, 0x8a, 0x13, 0x32, 0x11, 0xbc, 0x79};
376
377 // algorithm expect all input to be in little endian format, so reverse
378 std::reverse(std::begin(link_key), std::end(link_key));
379 std::reverse(std::begin(expected_ltk), std::end(expected_ltk));
380
381 Octet16 ltk = link_key_to_ltk(link_key, true);
382 EXPECT_EQ(expected_ltk, ltk);
383 }
384
385 // BT Spec 5.0 | Vol 3, Part H D.12
TEST(CryptoToolboxTest,bt_spec_example_d_12_test)386 TEST(CryptoToolboxTest, bt_spec_example_d_12_test) {
387 Octet16 link_key{0x05, 0x04, 0x03, 0x02, 0x01, 0x00, 0x09, 0x08,
388 0x07, 0x06, 0x05, 0x04, 0x03, 0x02, 0x01, 0x00};
389 Octet16 expected_ltk{0xa8, 0x13, 0xfb, 0x72, 0xf1, 0xa3, 0xdf, 0xa1,
390 0x8a, 0x2c, 0x9a, 0x43, 0xf1, 0x0d, 0x0a, 0x30};
391
392 // algorithm expect all input to be in little endian format, so reverse
393 std::reverse(std::begin(link_key), std::end(link_key));
394 std::reverse(std::begin(expected_ltk), std::end(expected_ltk));
395
396 Octet16 ltk = link_key_to_ltk(link_key, false);
397 EXPECT_EQ(expected_ltk, ltk);
398 }
399
400 } // namespace crypto_toolbox
401