rippled
Loading...
Searching...
No Matches
PublicKey_test.cpp
1#include <xrpl/beast/unit_test.h>
2#include <xrpl/protocol/PublicKey.h>
3#include <xrpl/protocol/SecretKey.h>
4
5#include <vector>
6
7namespace ripple {
8
10{
11public:
13
14 template <class FwdIter, class Container>
15 static void
16 hex_to_binary(FwdIter first, FwdIter last, Container& out)
17 {
18 struct Table
19 {
20 int val[256];
21 Table()
22 {
23 std::fill(val, val + 256, 0);
24 for (int i = 0; i < 10; ++i)
25 val['0' + i] = i;
26 for (int i = 0; i < 6; ++i)
27 {
28 val['A' + i] = 10 + i;
29 val['a' + i] = 10 + i;
30 }
31 }
32 int
33 operator[](int i)
34 {
35 return val[i];
36 }
37 };
38
39 static Table lut;
40 out.reserve(std::distance(first, last) / 2);
41 while (first != last)
42 {
43 auto const hi(lut[(*first++)]);
44 auto const lo(lut[(*first++)]);
45 out.push_back((hi * 16) + lo);
46 }
47 }
48
49 blob
50 sig(std::string const& hex)
51 {
52 blob b;
53 hex_to_binary(hex.begin(), hex.end(), b);
54 return b;
55 }
56
57 bool
59 {
60 return ecdsaCanonicality(makeSlice(sig(s))) == answer;
61 }
62
63 void
65 {
66 testcase("Canonical");
67
68 // Fully canonical
69 BEAST_EXPECT(check(
71 "3045"
72 "022100FF478110D1D4294471EC76E0157540C2181F47DEBD25D7F9E7DDCCCD47EE"
73 "E905"
74 "0220078F07CDAE6C240855D084AD91D1479609533C147C93B0AEF19BC9724D003F"
75 "28"));
76 BEAST_EXPECT(check(
78 "3045"
79 "0221009218248292F1762D8A51BE80F8A7F2CD288D810CE781D5955700DA1684DF"
80 "1D2D"
81 "022041A1EE1746BFD72C9760CC93A7AAA8047D52C8833A03A20EAAE92EA19717B4"
82 "54"));
83 BEAST_EXPECT(check(
85 "3044"
86 "02206A9E43775F73B6D1EC420E4DDD222A80D4C6DF5D1BEECC431A91B63C928B75"
87 "81"
88 "022023E9CC2D61DDA6F73EAA6BCB12688BEB0F434769276B3127E4044ED895C9D9"
89 "6B"));
90 BEAST_EXPECT(check(
92 "3044"
93 "022056E720007221F3CD4EFBB6352741D8E5A0968D48D8D032C2FBC4F6304AD1D0"
94 "4E"
95 "02201F39EB392C20D7801C3E8D81D487E742FA84A1665E923225BD6323847C7187"
96 "9F"));
97 BEAST_EXPECT(check(
99 "3045"
100 "022100FDFD5AD05518CEA0017A2DCB5C4DF61E7C73B6D3A38E7AE93210A1564E8C"
101 "2F12"
102 "0220214FF061CCC123C81D0BB9D0EDEA04CD40D96BF1425D311DA62A7096BB18EA"
103 "18"));
104
105 // Canonical but not fully canonical
106 BEAST_EXPECT(check(
108 "3046"
109 "022100F477B3FA6F31C7CB3A0D1AD94A231FDD24B8D78862EE334CEA7CD08F6CBC"
110 "0A1B"
111 "022100928E6BCF1ED2684679730C5414AEC48FD62282B090041C41453C1D064AF5"
112 "97A1"));
113 BEAST_EXPECT(check(
115 "3045"
116 "022063E7C7CA93CB2400E413A342C027D00665F8BAB9C22EF0A7B8AE3AAF092230"
117 "B6"
118 "0221008F2E8BB7D09521ABBC277717B14B93170AE6465C5A1B36561099319C4BEB"
119 "254C"));
120 BEAST_EXPECT(check(
122 "3046"
123 "02210099DCA1188663DDEA506A06A7B20C2B7D8C26AFF41DECE69D6C5F7C967D32"
124 "625F"
125 "022100897658A6B1F9EEE5D140D7A332DA0BD73BB98974EA53F6201B01C1B594F2"
126 "86EA"));
127 BEAST_EXPECT(check(
129 "3045"
130 "02200855DE366E4E323AA2CE2A25674401A7D11F72EC432770D07F7B57DF7387AE"
131 "C0"
132 "022100DA4C6ADDEA14888858DE2AC5B91ED9050D6972BB388DEF582628CEE32869"
133 "AE35"));
134
135 // valid
136 BEAST_EXPECT(check(
138 "3006"
139 "020101"
140 "020102"));
141 BEAST_EXPECT(check(
143 "3044"
144 "02203932c892e2e550f3af8ee4ce9c215a87f9bb831dcac87b2838e2c2eaa891df"
145 "0c"
146 "022030b61dd36543125d56b9f9f3a1f53189e5af33cdda8d77a5209aec03978fa0"
147 "01"));
148 BEAST_EXPECT(check(
150 "3045"
151 "0220076045be6f9eca28ff1ec606b833d0b87e70b2a630f5e3a496b110967a40f9"
152 "0a"
153 "0221008fffd599910eefe00bc803c688eca1d2ba7f6b180620eaa03488e6585db6"
154 "ba01"));
155 BEAST_EXPECT(check(
157 "3046"
158 "022100876045be6f9eca28ff1ec606b833d0b87e70b2a630f5e3a496b110967a40"
159 "f90a"
160 "0221008fffd599910eefe00bc803c688c2eca1d2ba7f6b180620eaa03488e6585d"
161 "b6ba"));
162
163 BEAST_EXPECT(check(
165 "3005"
166 "0201FF"
167 "0200"));
168 BEAST_EXPECT(check(
170 "3006"
171 "020101"
172 "020202"));
173 BEAST_EXPECT(check(
175 "3006"
176 "020701"
177 "020102"));
178 BEAST_EXPECT(check(
180 "3006"
181 "020401"
182 "020102"));
183 BEAST_EXPECT(check(
185 "3006"
186 "020501"
187 "020102"));
188 BEAST_EXPECT(check(
190 "3006"
191 "020201"
192 "020102"));
193 BEAST_EXPECT(check(
195 "3006"
196 "020301"
197 "020202"));
198 BEAST_EXPECT(check(
200 "3006"
201 "020401"
202 "020202"));
203 BEAST_EXPECT(check(
205 "3047"
206 "0221005990e0584b2b238e1dfaad8d6ed69ecc1a4a13ac85fc0b31d0df395eb1ba"
207 "6105"
208 "022200002d5876262c288beb511d061691bf26777344b702b00f8fe28621fe4e56"
209 "6695ed"));
210 BEAST_EXPECT(check(
212 "3144"
213 "02205990e0584b2b238e1dfaad8d6ed69ecc1a4a13ac85fc0b31d0df395eb1ba61"
214 "05"
215 "02202d5876262c288beb511d061691bf26777344b702b00f8fe28621fe4e566695"
216 "ed"));
217 BEAST_EXPECT(check(
219 "3045"
220 "02205990e0584b2b238e1dfaad8d6ed69ecc1a4a13ac85fc0b31d0df395eb1ba61"
221 "05"
222 "02202d5876262c288beb511d061691bf26777344b702b00f8fe28621fe4e566695"
223 "ed"));
224 BEAST_EXPECT(check(
226 "301F"
227 "01205990e0584b2b238e1dfaad8d6ed69ecc1a4a13ac85fc0b31d0df395eb1"));
228 BEAST_EXPECT(check(
230 "3045"
231 "02205990e0584b2b238e1dfaad8d6ed69ecc1a4a13ac85fc0b31d0df395eb1ba61"
232 "05"
233 "02202d5876262c288beb511d061691bf26777344b702b00f8fe28621fe4e566695"
234 "ed00"));
235 BEAST_EXPECT(check(
237 "3044"
238 "01205990e0584b2b238e1dfaad8d6ed69ecc1a4a13ac85fc0b31d0df395eb1ba61"
239 "05"
240 "02202d5876262c288beb511d061691bf26777344b702b00f8fe28621fe4e566695"
241 "ed"));
242 BEAST_EXPECT(check(
244 "3024"
245 "0200"
246 "02202d5876262c288beb511d061691bf26777344b702b00f8fe28621fe4e566695"
247 "ed"));
248 BEAST_EXPECT(check(
250 "3044"
251 "02208990e0584b2b238e1dfaad8d6ed69ecc1a4a13ac85fc0b31d0df395eb1ba61"
252 "05"
253 "02202d5876262c288beb511d061691bf26777344b702b00f8fe28621fe4e566695"
254 "ed"));
255 BEAST_EXPECT(check(
257 "3045"
258 "0221005990e0584b2b238e1dfaad8d6ed69ecc1a4a13ac85fc0b31d0df395eb1ba"
259 "6105"
260 "02202d5876262c288beb511d061691bf26777344b702b00f8fe28621fe4e566695"
261 "ed"));
262 BEAST_EXPECT(check(
264 "3044"
265 "02205990e0584b2b238e1dfaad8d6ed69ecc1a4a13ac85fc0b31d0df395eb1ba61"
266 "05012"
267 "02d5876262c288beb511d061691bf26777344b702b00f8fe28621fe4e566695e"
268 "d"));
269 BEAST_EXPECT(check(
271 "3024"
272 "02205990e0584b2b238e1dfaad8d6ed69ecc1a4a13ac85fc0b31d0df395eb1ba61"
273 "05"
274 "0200"));
275 BEAST_EXPECT(check(
277 "3044"
278 "02205990e0584b2b238e1dfaad8d6ed69ecc1a4a13ac85fc0b31d0df395eb1ba61"
279 "05"
280 "0220fd5876262c288beb511d061691bf26777344b702b00f8fe28621fe4e566695"
281 "ed"));
282 BEAST_EXPECT(check(
284 "3045"
285 "02205990e0584b2b238e1dfaad8d6ed69ecc1a4a13ac85fc0b31d0df395eb1ba61"
286 "05"
287 "0221002d5876262c288beb511d061691bf26777344b702b00f8fe28621fe4e5666"
288 "95ed"));
289 }
290
291 void
293 {
294 // Try converting short, long and malformed data
295 BEAST_EXPECT(!parseBase58<PublicKey>(TokenType::NodePublic, ""));
296 BEAST_EXPECT(!parseBase58<PublicKey>(TokenType::NodePublic, " "));
297 BEAST_EXPECT(
298 !parseBase58<PublicKey>(TokenType::NodePublic, "!ty89234gh45"));
299
300 auto const good = toBase58(
302
303 // Short (non-empty) strings
304 {
305 auto s = good;
306
307 // Remove all characters from the string in random order:
309
310 while (!s.empty())
311 {
312 s.erase(r(s) % s.size(), 1);
313 BEAST_EXPECT(!parseBase58<PublicKey>(TokenType::NodePublic, s));
314 }
315 }
316
317 // Long strings
318 for (std::size_t i = 1; i != 16; i++)
319 {
320 auto s = good;
321 s.resize(s.size() + i, s[i % s.size()]);
322 BEAST_EXPECT(!parseBase58<PublicKey>(TokenType::NodePublic, s));
323 }
324
325 // Strings with invalid Base58 characters
326 for (auto c : std::string("0IOl"))
327 {
328 for (std::size_t i = 0; i != good.size(); ++i)
329 {
330 auto s = good;
331 s[i % s.size()] = c;
332 BEAST_EXPECT(!parseBase58<PublicKey>(TokenType::NodePublic, s));
333 }
334 }
335
336 // Strings with incorrect prefix
337 {
338 auto s = good;
339
340 for (auto c : std::string("apsrJqtv7"))
341 {
342 s[0] = c;
343 BEAST_EXPECT(!parseBase58<PublicKey>(TokenType::NodePublic, s));
344 }
345 }
346
347 // Try some random secret keys
349 keys.reserve(32);
350
351 for (std::size_t i = 0; i != keys.capacity(); ++i)
353 BEAST_EXPECT(keys.size() == 32);
354
355 for (std::size_t i = 0; i != keys.size(); ++i)
356 {
357 auto const si = toBase58(TokenType::NodePublic, keys[i]);
358 BEAST_EXPECT(!si.empty());
359
360 auto const ski = parseBase58<PublicKey>(TokenType::NodePublic, si);
361 BEAST_EXPECT(ski && (keys[i] == *ski));
362
363 for (std::size_t j = i; j != keys.size(); ++j)
364 {
365 BEAST_EXPECT((keys[i] == keys[j]) == (i == j));
366
367 auto const sj = toBase58(TokenType::NodePublic, keys[j]);
368
369 BEAST_EXPECT((si == sj) == (i == j));
370
371 auto const skj =
372 parseBase58<PublicKey>(TokenType::NodePublic, sj);
373 BEAST_EXPECT(skj && (keys[j] == *skj));
374
375 BEAST_EXPECT((*ski == *skj) == (i == j));
376 }
377 }
378 }
379
380 void
382 {
383 testcase("Base58: secp256k1");
384
385 {
386 auto const pk1 = derivePublicKey(
389 KeyType::secp256k1, generateSeed("masterpassphrase")));
390
391 auto const pk2 = parseBase58<PublicKey>(
393 "n94a1u4jAz288pZLtw6yFWVbi89YamiC6JBXPVUj5zmExe5fTVg9");
394 BEAST_EXPECT(pk2);
395
396 BEAST_EXPECT(pk1 == *pk2);
397 }
398
400
401 testcase("Base58: ed25519");
402
403 {
404 auto const pk1 = derivePublicKey(
407 KeyType::ed25519, generateSeed("masterpassphrase")));
408
409 auto const pk2 = parseBase58<PublicKey>(
411 "nHUeeJCSY2dM71oxM8Cgjouf5ekTuev2mwDpc374aLMxzDLXNmjf");
412 BEAST_EXPECT(pk2);
413
414 BEAST_EXPECT(pk1 == *pk2);
415 }
416
418 }
419
420 void
422 {
423 testcase("Miscellaneous operations");
424
425 auto const pk1 = derivePublicKey(
428 KeyType::secp256k1, generateSeed("masterpassphrase")));
429
430 PublicKey pk2(pk1);
431 BEAST_EXPECT(pk1 == pk2);
432 BEAST_EXPECT(pk2 == pk1);
433
437 KeyType::secp256k1, generateSeed("arbitraryPassPhrase")));
438 // Testing the copy assignment operation of PublicKey class
439 pk3 = pk2;
440 BEAST_EXPECT(pk3 == pk2);
441 BEAST_EXPECT(pk1 == pk3);
442 }
443
444 void
445 run() override
446 {
447 testBase58();
450 }
451};
452
453BEAST_DEFINE_TESTSUITE(PublicKey, protocol, ripple);
454
455} // namespace ripple
T capacity(T... args)
A testsuite class.
Definition suite.h:52
testcase_t testcase
Memberspace for declaring test cases.
Definition suite.h:152
void testBase58(KeyType keyType)
std::vector< std::uint8_t > blob
blob sig(std::string const &hex)
void run() override
Runs the suite.
static void hex_to_binary(FwdIter first, FwdIter last, Container &out)
bool check(std::optional< ECDSACanonicality > answer, std::string const &s)
A public key.
Definition PublicKey.h:43
T distance(T... args)
T emplace_back(T... args)
T fill(T... args)
T is_same_v
Use hash_* containers for keys that do not need a cryptographically secure hashing algorithm.
Definition algorithm.h:6
std::optional< ECDSACanonicality > ecdsaCanonicality(Slice const &sig)
Determines the canonicality of a signature.
std::string toBase58(AccountID const &v)
Convert AccountID to base58 checked string.
Definition AccountID.cpp:95
PublicKey derivePublicKey(KeyType type, SecretKey const &sk)
Derive the public key from a secret key.
SecretKey generateSecretKey(KeyType type, Seed const &seed)
Generate a new secret key deterministically.
std::enable_if_t< std::is_same< T, char >::value||std::is_same< T, unsigned char >::value, Slice > makeSlice(std::array< T, N > const &a)
Definition Slice.h:225
SecretKey randomSecretKey()
Create a secret key using secure random numbers.
KeyType
Definition KeyType.h:9
Seed generateSeed(std::string const &passPhrase)
Generate a seed deterministically.
Definition Seed.cpp:57
T reserve(T... args)
T size(T... args)