Branch data Line data Source code
1 : : // Copyright (c) 2019-2022 The Bitcoin Core developers 2 : : // Distributed under the MIT software license, see the accompanying 3 : : // file COPYING or http://www.opensource.org/licenses/mit-license.php. 4 : : 5 : : #include <tinyformat.h> 6 : : #include <util/bip32.h> 7 : : #include <util/strencodings.h> 8 : : 9 : : #include <cstdint> 10 : : #include <cstdio> 11 : : #include <sstream> 12 : : 13 : 0 : bool ParseHDKeypath(const std::string& keypath_str, std::vector<uint32_t>& keypath) 14 : : { 15 : 0 : std::stringstream ss(keypath_str); 16 : 0 : std::string item; 17 : 0 : bool first = true; 18 [ # # ][ # # ]: 0 : while (std::getline(ss, item, '/')) { [ # # ] 19 [ # # ]: 0 : if (item.compare("m") == 0) { 20 [ # # ]: 0 : if (first) { 21 : 0 : first = false; 22 : 0 : continue; 23 : : } 24 : 0 : return false; 25 : : } 26 : : // Finds whether it is hardened 27 : 0 : uint32_t path = 0; 28 : 0 : size_t pos = item.find('\''); 29 [ # # ]: 0 : if (pos != std::string::npos) { 30 : : // The hardened tick can only be in the last index of the string 31 [ # # ]: 0 : if (pos != item.size() - 1) { 32 : 0 : return false; 33 : : } 34 : 0 : path |= 0x80000000; 35 [ # # ]: 0 : item = item.substr(0, item.size() - 1); // Drop the last character which is the hardened tick 36 : 0 : } 37 : : 38 : : // Ensure this is only numbers 39 [ # # ]: 0 : if (item.find_first_not_of( "0123456789" ) != std::string::npos) { 40 : 0 : return false; 41 : : } 42 : : uint32_t number; 43 [ # # ][ # # ]: 0 : if (!ParseUInt32(item, &number)) { 44 : 0 : return false; 45 : : } 46 : 0 : path |= number; 47 : : 48 [ # # ]: 0 : keypath.push_back(path); 49 : 0 : first = false; 50 : : } 51 : 0 : return true; 52 : 0 : } 53 : : 54 : 0 : std::string FormatHDKeypath(const std::vector<uint32_t>& path, bool apostrophe) 55 : : { 56 : 0 : std::string ret; 57 [ # # ]: 0 : for (auto i : path) { 58 [ # # ][ # # ]: 0 : ret += strprintf("/%i", (i << 1) >> 1); 59 [ # # ][ # # ]: 0 : if (i >> 31) ret += apostrophe ? '\'' : 'h'; 60 : : } 61 : 0 : return ret; 62 [ # # ]: 0 : } 63 : : 64 : 0 : std::string WriteHDKeypath(const std::vector<uint32_t>& keypath, bool apostrophe) 65 : : { 66 [ # # ]: 0 : return "m" + FormatHDKeypath(keypath, apostrophe); 67 : 0 : }