diff --git a/src/config.hpp b/src/config.hpp index 9a7861070..9930cde47 100644 --- a/src/config.hpp +++ b/src/config.hpp @@ -70,7 +70,6 @@ class Config { , max_reusable_write_objects_(CASS_DEFAULT_MAX_REUSABLE_WRITE_OBJECTS) , prepare_on_all_hosts_(CASS_DEFAULT_PREPARE_ON_ALL_HOSTS) , prepare_on_up_or_add_host_(CASS_DEFAULT_PREPARE_ON_UP_OR_ADD_HOST) - , local_address_(CASS_DEFAULT_LOCAL_ADDRESS, CASS_DEFAULT_LOCAL_ADDRESS_PORT) , no_compact_(CASS_DEFAULT_NO_COMPACT) , is_client_id_set_(false) , host_listener_(new DefaultHostListener()) diff --git a/src/constants.hpp b/src/constants.hpp index 89586a353..2d2a743a7 100644 --- a/src/constants.hpp +++ b/src/constants.hpp @@ -119,8 +119,6 @@ #define CASS_DEFAULT_NUM_CONNECTIONS_PER_HOST 1 #define CASS_DEFAULT_PREPARE_ON_ALL_HOSTS true #define CASS_DEFAULT_PREPARE_ON_UP_OR_ADD_HOST true -#define CASS_DEFAULT_LOCAL_ADDRESS "0.0.0.0" -#define CASS_DEFAULT_LOCAL_ADDRESS_PORT 0 #define CASS_DEFAULT_PORT 9042 #define CASS_DEFAULT_QUEUE_SIZE_IO 8192 #define CASS_DEFAULT_CONSTANT_RECONNECT_WAIT_TIME_MS 2000u diff --git a/src/socket_connector.cpp b/src/socket_connector.cpp index 2b13082ed..59887181b 100644 --- a/src/socket_connector.cpp +++ b/src/socket_connector.cpp @@ -177,6 +177,7 @@ void SocketConnector::internal_connect(uv_loop_t* loop) { // This needs to be done after setting the socket to properly cleanup. const Address& local_address = settings_.local_address; if (local_address.is_valid()) { + // use configured local address Address::SocketStorage storage; LOG_DEBUG("Binding socket. local_address=%s, remote=%s", local_address.to_string(true).c_str(), socket_->address().to_string(true).c_str()); @@ -187,7 +188,34 @@ void SocketConnector::internal_connect(uv_loop_t* loop) { return; } } else { - LOG_WARN("Cannot bind to an invalid `local_address` %s:%d", local_address.to_string().c_str(), local_address.port()); + // determine local address matching resolved addresses family + if (resolved_address_.family() == Address::IPv4) { + Address::SocketStorage storage; + storage.addr_in()->sin_family = AF_INET; + storage.addr_in()->sin_addr.s_addr = INADDR_ANY; + storage.addr_in()->sin_port = local_address.port(); + int rc = uv_tcp_bind(socket->handle(), storage.addr(), 0); + if (rc != 0) { + on_error(SOCKET_ERROR_BIND, "Unable to bind local address: " + String(uv_strerror(rc))); + + return; + } + } else if (resolved_address_.family() == Address::IPv6) { + Address::SocketStorage storage; + storage.addr_in6()->sin6_family = AF_INET6; + storage.addr_in6()->sin6_addr = in6addr_any; + storage.addr_in6()->sin6_port = local_address.port(); + storage.addr_in6()->sin6_flowinfo = 0; + storage.addr_in6()->sin6_scope_id = 0; + int rc = uv_tcp_bind(socket->handle(), storage.addr(), 0); + if (rc != 0) { + on_error(SOCKET_ERROR_BIND, "Unable to bind local address: " + String(uv_strerror(rc))); + + return; + } + } else { + LOG_WARN("Cannot bind to local address for unknown family (%d) of resolved address %s.", resolved_address_.family(), resolved_address_.to_string().c_str()); + } } if (settings_.ssl_context) {