1
0
mirror of synced 2025-11-03 19:53:13 +03:00
This commit is contained in:
yhirose
2025-10-25 16:48:45 -04:00
parent db561f5552
commit bae40fcdf2
2 changed files with 143 additions and 33 deletions

View File

@@ -1052,6 +1052,9 @@ private:
ssize_t write_headers(Stream &strm, const Headers &headers);
std::string make_host_and_port_string(const std::string &host, int port,
bool is_ssl);
} // namespace detail
class Server {
@@ -1719,8 +1722,6 @@ private:
const std::string &boundary, const UploadFormDataItems &items,
const FormDataProviderItems &provider_items) const;
std::string adjust_host_string(const std::string &host) const;
virtual bool
process_socket(const Socket &socket,
std::chrono::time_point<std::chrono::steady_clock> start_time,
@@ -7261,6 +7262,30 @@ inline bool RegexMatcher::match(Request &request) const {
return std::regex_match(request.path, request.matches, regex_);
}
inline std::string make_host_and_port_string(const std::string &host, int port,
bool is_ssl) {
std::string result;
// Enclose IPv6 address in brackets (but not if already enclosed)
if (host.find(':') == std::string::npos ||
(!host.empty() && host[0] == '[')) {
// IPv4, hostname, or already bracketed IPv6
result = host;
} else {
// IPv6 address without brackets
result = "[" + host + "]";
}
// Append port if not default
if ((!is_ssl && port == 80) || (is_ssl && port == 443)) {
; // do nothing
} else {
result += ":" + std::to_string(port);
}
return result;
}
} // namespace detail
// HTTP server implementation
@@ -8522,7 +8547,7 @@ inline ClientImpl::ClientImpl(const std::string &host, int port,
const std::string &client_cert_path,
const std::string &client_key_path)
: host_(detail::escape_abstract_namespace_unix_domain(host)), port_(port),
host_and_port_(adjust_host_string(host_) + ":" + std::to_string(port)),
host_and_port_(detail::make_host_and_port_string(host_, port, is_ssl())),
client_cert_path_(client_cert_path), client_key_path_(client_key_path) {}
inline ClientImpl::~ClientImpl() {
@@ -8703,8 +8728,9 @@ inline bool ClientImpl::send_(Request &req, Response &res, Error &error) {
{
std::lock_guard<std::mutex> guard(socket_mutex_);
// Set this to false immediately - if it ever gets set to true by the end of
// the request, we know another thread instructed us to close the socket.
// Set this to false immediately - if it ever gets set to true by the end
// of the request, we know another thread instructed us to close the
// socket.
socket_should_be_closed_when_request_is_done_ = false;
auto is_alive = false;
@@ -8720,10 +8746,10 @@ inline bool ClientImpl::send_(Request &req, Response &res, Error &error) {
#endif
if (!is_alive) {
// Attempt to avoid sigpipe by shutting down non-gracefully if it seems
// like the other side has already closed the connection Also, there
// cannot be any requests in flight from other threads since we locked
// request_mutex_, so safe to close everything immediately
// Attempt to avoid sigpipe by shutting down non-gracefully if it
// seems like the other side has already closed the connection Also,
// there cannot be any requests in flight from other threads since we
// locked request_mutex_, so safe to close everything immediately
const bool shutdown_gracefully = false;
shutdown_ssl(socket_, shutdown_gracefully);
shutdown_socket(socket_);
@@ -9027,7 +9053,8 @@ inline bool ClientImpl::create_redirect_client(
}
}
// New method for robust client setup (based on basic_manual_redirect.cpp logic)
// New method for robust client setup (based on basic_manual_redirect.cpp
// logic)
template <typename ClientType>
inline void ClientImpl::setup_redirect_client(ClientType &client) {
// Copy basic settings first
@@ -9131,18 +9158,8 @@ inline bool ClientImpl::write_request(Stream &strm, Request &req,
// curl behavior)
if (address_family_ == AF_UNIX) {
req.set_header("Host", "localhost");
} else if (is_ssl()) {
if (port_ == 443) {
req.set_header("Host", host_);
} else {
req.set_header("Host", host_and_port_);
}
} else {
if (port_ == 80) {
req.set_header("Host", host_);
} else {
req.set_header("Host", host_and_port_);
}
req.set_header("Host", host_and_port_);
}
}
@@ -9409,12 +9426,6 @@ inline Result ClientImpl::send_with_content_provider(
#endif
}
inline std::string
ClientImpl::adjust_host_string(const std::string &host) const {
if (host.find(':') != std::string::npos) { return "[" + host + "]"; }
return host;
}
inline void ClientImpl::output_log(const Request &req,
const Response &res) const {
if (logger_) {
@@ -9538,8 +9549,8 @@ inline ContentProviderWithoutLength ClientImpl::get_multipart_content_provider(
const FormDataProviderItems &provider_items) const {
size_t cur_item = 0;
size_t cur_start = 0;
// cur_item and cur_start are copied to within the std::function and maintain
// state between successive calls
// cur_item and cur_start are copied to within the std::function and
// maintain state between successive calls
return [&, cur_item, cur_start](size_t offset,
DataSink &sink) mutable -> bool {
if (!offset && !items.empty()) {
@@ -10251,8 +10262,8 @@ inline void ClientImpl::stop() {
// If there is anything ongoing right now, the ONLY thread-safe thing we can
// do is to shutdown_socket, so that threads using this socket suddenly
// discover they can't read/write any more and error out. Everything else
// (closing the socket, shutting ssl down) is unsafe because these actions are
// not thread-safe.
// (closing the socket, shutting ssl down) is unsafe because these actions
// are not thread-safe.
if (socket_requests_in_flight_ > 0) {
shutdown_socket(socket_);
@@ -10889,7 +10900,8 @@ inline void SSLClient::set_ca_cert_store(X509_STORE *ca_cert_store) {
if (ca_cert_store) {
if (ctx_) {
if (SSL_CTX_get_cert_store(ctx_) != ca_cert_store) {
// Free memory allocated for old cert and use new store `ca_cert_store`
// Free memory allocated for old cert and use new store
// `ca_cert_store`
SSL_CTX_set_cert_store(ctx_, ca_cert_store);
ca_cert_store_ = ca_cert_store;
}
@@ -10914,7 +10926,8 @@ inline bool SSLClient::create_and_connect_socket(Socket &socket, Error &error) {
return is_valid() && ClientImpl::create_and_connect_socket(socket, error);
}
// Assumes that socket_mutex_ is locked and that there are no requests in flight
// Assumes that socket_mutex_ is locked and that there are no requests in
// flight
inline bool SSLClient::connect_with_proxy(
Socket &socket,
std::chrono::time_point<std::chrono::steady_clock> start_time,