Bitcoin Core 31.99.0
P2P Digital Currency
url.cpp
Go to the documentation of this file.
1// Copyright (c) 2015-present 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 <common/url.h>
6
7#include <charconv>
8#include <cstddef>
9#include <string>
10#include <string_view>
11#include <system_error>
12
13std::string UrlDecode(std::string_view url_encoded)
14{
15 std::string res;
16 res.reserve(url_encoded.size());
17
18 for (size_t i = 0; i < url_encoded.size(); ++i) {
19 char c = url_encoded[i];
20 // Special handling for percent which should be followed by two hex digits
21 // representing an octet values, see RFC 3986, Section 2.1 Percent-Encoding
22 if (c == '%' && i + 2 < url_encoded.size()) {
23 unsigned int decoded_value{0};
24 auto [p, ec] = std::from_chars(url_encoded.data() + i + 1, url_encoded.data() + i + 3, decoded_value, 16);
25
26 // Only if there is no error and the pointer is set to the end of
27 // the string, we can be sure both characters were valid hex
28 if (ec == std::errc{} && p == url_encoded.data() + i + 3) {
29 res += static_cast<char>(decoded_value);
30 // Next two characters are part of the percent encoding
31 i += 2;
32 continue;
33 }
34 // In case of invalid percent encoding, add the '%' and continue
35 }
36 res += c;
37 }
38
39 return res;
40}
41
42std::string UrlEncode(std::string_view str)
43{
44 std::string res;
45 res.reserve(str.size() * 3); // worst case: every char needs encoding
46
47 for (char ch : str) {
48 auto c = static_cast<unsigned char>(ch);
49 // Unreserved characters per RFC 3986, Section 2.3
50 if ((c >= 'A' && c <= 'Z') || (c >= 'a' && c <= 'z') ||
51 (c >= '0' && c <= '9') || c == '-' || c == '_' || c == '.' || c == '~') {
52 res += ch;
53 } else {
54 // Percent-encode all other characters
55 res += '%';
56 constexpr char hex_chars[] = "0123456789ABCDEF";
57 res += hex_chars[(c >> 4) & 0xF];
58 res += hex_chars[c & 0xF];
59 }
60 }
61 return res;
62}
std::string UrlDecode(std::string_view url_encoded)
Definition: url.cpp:13
std::string UrlEncode(std::string_view str)
Definition: url.cpp:42