@@ -81,7 +81,11 @@ CTxDestination DecodeDestination(const std::string& str, const CChainParams& par
81
81
std::vector<unsigned char > data;
82
82
uint160 hash;
83
83
error_str = " " ;
84
- if (DecodeBase58Check (str, data, 21 )) {
84
+
85
+ // Note this will be false if it is a valid Bech32 address for a different network
86
+ bool is_bech32 = (ToLower (str.substr (0 , params.Bech32HRP ().size ())) == params.Bech32HRP ());
87
+
88
+ if (!is_bech32 && DecodeBase58Check (str, data, 21 )) {
85
89
// base58-encoded Bitcoin addresses.
86
90
// Public-key-hash-addresses have version 0 (or 111 testnet).
87
91
// The data vector contains RIPEMD160(SHA256(pubkey)), where pubkey is the serialized public key.
@@ -98,15 +102,27 @@ CTxDestination DecodeDestination(const std::string& str, const CChainParams& par
98
102
return ScriptHash (hash);
99
103
}
100
104
101
- // Set potential error message.
102
- // This message may be changed if the address can also be interpreted as a Bech32 address.
103
- error_str = " Invalid prefix for Base58-encoded address" ;
105
+ if (!std::equal (script_prefix.begin (), script_prefix.end (), data.begin ()) &&
106
+ !std::equal (pubkey_prefix.begin (), pubkey_prefix.end (), data.begin ())) {
107
+ error_str = " Invalid prefix for Base58-encoded address" ;
108
+ } else {
109
+ error_str = " Invalid length for Base58 address" ;
110
+ }
111
+ return CNoDestination ();
112
+ } else if (!is_bech32) {
113
+ // Try Base58 decoding without the checksum, using a much larger max length
114
+ if (!DecodeBase58 (str, data, 100 )) {
115
+ error_str = " Invalid HRP or Base58 character in address" ;
116
+ } else {
117
+ error_str = " Invalid checksum or length of Base58 address" ;
118
+ }
119
+ return CNoDestination ();
104
120
}
121
+
105
122
data.clear ();
106
123
const auto dec = bech32::Decode (str);
107
124
if ((dec.encoding == bech32::Encoding::BECH32 || dec.encoding == bech32::Encoding::BECH32M) && dec.data .size () > 0 ) {
108
125
// Bech32 decoding
109
- error_str = " " ;
110
126
if (dec.hrp != params.Bech32HRP ()) {
111
127
error_str = " Invalid prefix for Bech32 address" ;
112
128
return CNoDestination ();
@@ -168,8 +184,8 @@ CTxDestination DecodeDestination(const std::string& str, const CChainParams& par
168
184
}
169
185
}
170
186
171
- // Set error message if address can't be interpreted as Base58 or Bech32.
172
- if ( error_str. empty ()) error_str = " Invalid address format " ;
187
+ // TODO: locate Bech32 errors
188
+ error_str = " Error in Bech32 encoding " ;
173
189
174
190
return CNoDestination ();
175
191
}
0 commit comments