diff options
-rw-r--r-- | include/inspsocket.h | 14 | ||||
-rw-r--r-- | include/message.h | 1 | ||||
-rw-r--r-- | src/inspsocket.cpp | 20 | ||||
-rw-r--r-- | src/message.cpp | 5 | ||||
-rw-r--r-- | src/modules/m_spanningtree.cpp | 54 | ||||
-rw-r--r-- | src/socket.cpp | 41 |
6 files changed, 51 insertions, 84 deletions
diff --git a/include/inspsocket.h b/include/inspsocket.h index 077f20a65..b644151dc 100644 --- a/include/inspsocket.h +++ b/include/inspsocket.h @@ -59,10 +59,6 @@ class InspSocket : public Extensible int fd; /** - * The resolver for this socket - */ - - /** * The hostname connected to */ char host[MAXBUF]; @@ -184,15 +180,15 @@ class InspSocket : public Extensible /** * This constructor is used to create a new * socket, either listening for connections, or an outbound connection to another host. - * Note that if you specify a hostname in the 'host' parameter, then there will be an extra - * step involved (a nonblocking DNS lookup) which will cause your connection to be established - * slower than if it was an IP. Therefore, use an IP address where it is available instead. - * @param host The hostname to connect to, or bind to + * Note that if you specify a hostname in the 'ipaddr' parameter, this class will not + * connect. You must resolve your hostnames before passing them to InspSocket. To do so, + * you should use the nonblocking class 'Resolver'. + * @param ipaddr The IP to connect to, or bind to * @param port The port number to connect to, or bind to * @param listening true to listen on the given host:port pair, or false to connect to them * @param maxtime Number of seconds to wait, if connecting, before the connection times out and an OnTimeout() event is generated */ - InspSocket(const std::string &host, int port, bool listening, unsigned long maxtime); + InspSocket(const std::string &ipaddr, int port, bool listening, unsigned long maxtime); /** * This method is called when an outbound diff --git a/include/message.h b/include/message.h index fd9d47ff2..f7fcba278 100644 --- a/include/message.h +++ b/include/message.h @@ -31,7 +31,6 @@ int common_channels(userrec *u, userrec *u2); void Blocking(int s); void NonBlocking(int s); -int CleanAndResolve(char *resolvedHost, const char *unresolvedHost, bool forward, unsigned long timeout); int c_count(userrec* u); void ChangeName(userrec* user, const char* gecos); void ChangeDisplayedHost(userrec* user, const char* host); diff --git a/src/inspsocket.cpp b/src/inspsocket.cpp index f443873e5..f738835a8 100644 --- a/src/inspsocket.cpp +++ b/src/inspsocket.cpp @@ -57,9 +57,9 @@ InspSocket::InspSocket(int newfd, const char* ip) } } -InspSocket::InspSocket(const std::string &ahost, int aport, bool listening, unsigned long maxtime) : fd(-1) +InspSocket::InspSocket(const std::string &ipaddr, int aport, bool listening, unsigned long maxtime) : fd(-1) { - strlcpy(host,ahost.c_str(),MAXBUF); + strlcpy(host,ipaddr.c_str(),MAXBUF); this->ClosePending = false; if (listening) { if ((this->fd = OpenTCPSocket()) == ERROR) @@ -73,7 +73,7 @@ InspSocket::InspSocket(const std::string &ahost, int aport, bool listening, unsi } else { - if (!BindSocket(this->fd,this->client,this->server,aport,(char*)ahost.c_str())) + if (!BindSocket(this->fd,this->client,this->server,aport,(char*)ipaddr.c_str())) { log(DEBUG,"BindSocket() error %s",strerror(errno)); this->Close(); @@ -98,7 +98,7 @@ InspSocket::InspSocket(const std::string &ahost, int aport, bool listening, unsi } else { - strlcpy(this->host,ahost.c_str(),MAXBUF); + strlcpy(this->host,ipaddr.c_str(),MAXBUF); this->port = aport; if (insp_aton(host,&addy) < 1) @@ -170,18 +170,6 @@ bool InspSocket::BindAddr() if ((IP != "*") && (IP != "127.0.0.1") && (IP != "")) { insp_sockaddr s; - char resolved_addr[MAXBUF]; - - if (insp_aton(IP.c_str(),&n) < 1) - { - /* If they gave a hostname, bind to the IP it resolves to */ - log(DEBUG,"Resolving host %s",IP.c_str()); - if (CleanAndResolve(resolved_addr, IP.c_str(), true, 1)) - { - log(DEBUG,"Resolved host %s to %s",IP.c_str(),resolved_addr); - IP = resolved_addr; - } - } if (insp_aton(IP.c_str(),&n) > 0) { diff --git a/src/message.cpp b/src/message.cpp index 96b540db4..268cc6554 100644 --- a/src/message.cpp +++ b/src/message.cpp @@ -95,11 +95,6 @@ void NonBlocking(int s) fcntl(s, F_SETFL, flags | O_NONBLOCK); } -int CleanAndResolve (char *resolvedHost, const char *unresolvedHost, bool forward, unsigned long timeout) -{ - return 0; -} - int c_count(userrec* u) { int z = 0; diff --git a/src/modules/m_spanningtree.cpp b/src/modules/m_spanningtree.cpp index d4bc5360e..3a811d1fa 100644 --- a/src/modules/m_spanningtree.cpp +++ b/src/modules/m_spanningtree.cpp @@ -139,6 +139,8 @@ extern std::vector<ZLine> pzlines; extern std::vector<QLine> pqlines; extern std::vector<ELine> pelines; +std::vector<std::string> ValidIPs; + class UserManager : public classbase { uid_hash uids; @@ -3032,27 +3034,8 @@ class TreeSocket : public InspSocket * IPs for which we don't have a link block. */ bool found = false; - char resolved_host[MAXBUF]; vector<Link>::iterator i; - for (i = LinkBlocks.begin(); i != LinkBlocks.end(); i++) - { - if (i->IPAddr == ip) - { - found = true; - break; - } - /* XXX: Fixme: blocks for a very short amount of time, - * we should cache these on rehash/startup - */ - if (CleanAndResolve(resolved_host,i->IPAddr.c_str(),true,1)) - { - if (std::string(resolved_host) == ip) - { - found = true; - break; - } - } - } + found = (std::find(ValidIPs.begin(), ValidIPs.end(), ip) != ValidIPs.end()); if (!found) { WriteOpers("Server connection from %s denied (no link blocks with that IP address)", ip); @@ -3116,6 +3099,26 @@ class ServernameResolver : public Resolver } }; +class SecurityIPResolver : public Resolver +{ + private: + Link MyLink; + public: + SecurityIPResolver(const std::string &hostname, Link x) : Resolver(hostname, true), MyLink(x) + { + } + + void OnLookupComplete(const std::string &result) + { + log(DEBUG,"Security IP cache: Adding IP address '%s' for Link '%s'",result.c_str(),MyLink.Name.c_str()); + ValidIPs.push_back(result); + } + + void OnError(ResolverError e) + { + log(DEBUG,"Could not resolve IP associated with Link '%s'!",MyLink.Name.c_str()); + } +}; void AddThisServer(TreeServer* server, std::deque<TreeServer*> &list) { @@ -3322,6 +3325,7 @@ void ReadConfiguration(bool rebind) FlatLinks = Conf->ReadFlag("options","flatlinks",0); HideULines = Conf->ReadFlag("options","hideulines",0); LinkBlocks.clear(); + ValidIPs.clear(); for (int j =0; j < Conf->Enumerate("link"); j++) { Link L; @@ -3337,6 +3341,16 @@ void ReadConfiguration(bool rebind) /* Bugfix by brain, do not allow people to enter bad configurations */ if ((L.IPAddr != "") && (L.RecvPass != "") && (L.SendPass != "") && (L.Name != "") && (L.Port)) { + ValidIPs.push_back(L.IPAddr); + + /* Needs resolving */ + insp_inaddr binip; + if (insp_aton(L.IPAddr.c_str(), &binip) < 1) + { + SecurityIPResolver* sr = new SecurityIPResolver(L.IPAddr, L); + Srv->AddResolver(sr); + } + LinkBlocks.push_back(L); log(DEBUG,"m_spanningtree: Read server %s with host %s:%d",L.Name.c_str(),L.IPAddr.c_str(),L.Port); } diff --git a/src/socket.cpp b/src/socket.cpp index ff460c473..e386e8188 100644 --- a/src/socket.cpp +++ b/src/socket.cpp @@ -43,51 +43,26 @@ bool BindSocket(int sockfd, insp_sockaddr client, insp_sockaddr server, int port if (*addr == '*') *addr = 0; - - if (*addr && (insp_aton(addr,&addy) < 1)) - { - /* If they gave a hostname, bind to the IP it resolves to */ - if (CleanAndResolve(resolved_addr, addr, true, 1)) - { - insp_aton(resolved_addr,&addy); - log(DEFAULT,"Resolved binding '%s' -> '%s'",addr,resolved_addr); -#ifdef IPV6 - /* Todo: Deal with resolution of IPV6 */ - server.sin6_addr = addy; -#else - server.sin_addr = addy; -#endif - resolved = true; - } - else - { - log(DEFAULT,"WARNING: Could not resolve '%s' to an IP for binding to on port %d",addr,port); - return false; - } - } #ifdef IPV6 server.sin6_family = AF_FAMILY; #else server.sin_family = AF_FAMILY; #endif - if (!resolved) + if (!*addr) { - if (!*addr) - { #ifdef IPV6 - memcpy(&addy, &server.sin6_addr, sizeof(in6_addr)); + memcpy(&addy, &server.sin6_addr, sizeof(in6_addr)); #else - server.sin_addr.s_addr = htonl(INADDR_ANY); + server.sin_addr.s_addr = htonl(INADDR_ANY); #endif - } - else - { + } + else + { #ifdef IPV6 - memcpy(&addy, &server.sin6_addr, sizeof(in6_addr)); + memcpy(&addy, &server.sin6_addr, sizeof(in6_addr)); #else - server.sin_addr = addy; + server.sin_addr = addy; #endif - } } #ifdef IPV6 server.sin6_port = htons(port); |