socket: handle binding to "host!<ip>"

Regression since 3060557af7 (shipped in 8.9.0)

Fixes #15553
Reported-by: marcos-ng on github
Closes #15583
This commit is contained in:
Daniel Stenberg 2024-11-16 18:53:56 +01:00
parent e9b9bbac22
commit 2dc54e3030
No known key found for this signature in database
GPG key ID: 5CC908FDB71E12C2

View file

@ -600,36 +600,39 @@ static CURLcode bindlocal(struct Curl_easy *data, struct connectdata *conn,
if(!iface && !host && !port)
/* no local kind of binding was requested */
return CURLE_OK;
else if(iface && (strlen(iface) >= 255) )
return CURLE_BAD_FUNCTION_ARGUMENT;
memset(&sa, 0, sizeof(struct Curl_sockaddr_storage));
if(iface && (strlen(iface) < 255) ) {
if(iface || host) {
char myhost[256] = "";
int done = 0; /* -1 for error, 1 for address found */
if2ip_result_t if2ip_result = IF2IP_NOT_FOUND;
/* interface */
#ifdef SO_BINDTODEVICE
/*
* This binds the local socket to a particular interface. This will
* force even requests to other local interfaces to go out the external
* interface. Only bind to the interface when specified as interface,
* not just as a hostname or ip address.
*
* The interface might be a VRF, eg: vrf-blue, which means it cannot be
* converted to an IP address and would fail Curl_if2ip. Simply try to
* use it straight away.
*/
if(setsockopt(sockfd, SOL_SOCKET, SO_BINDTODEVICE,
iface, (curl_socklen_t)strlen(iface) + 1) == 0) {
/* This is often "errno 1, error: Operation not permitted" if you are
* not running as root or another suitable privileged user. If it
* succeeds it means the parameter was a valid interface and not an IP
* address. Return immediately.
*/
if(!host_input) {
infof(data, "socket successfully bound to interface '%s'", iface);
return CURLE_OK;
if(iface) {
/*
* This binds the local socket to a particular interface. This will
* force even requests to other local interfaces to go out the external
* interface. Only bind to the interface when specified as interface,
* not just as a hostname or ip address.
*
* The interface might be a VRF, eg: vrf-blue, which means it cannot be
* converted to an IP address and would fail Curl_if2ip. Simply try to
* use it straight away.
*/
if(setsockopt(sockfd, SOL_SOCKET, SO_BINDTODEVICE,
iface, (curl_socklen_t)strlen(iface) + 1) == 0) {
/* This is often "errno 1, error: Operation not permitted" if you are
* not running as root or another suitable privileged user. If it
* succeeds it means the parameter was a valid interface and not an IP
* address. Return immediately.
*/
if(!host_input) {
infof(data, "socket successfully bound to interface '%s'", iface);
return CURLE_OK;
}
}
}
#endif