//returns OS_SUCCESS if the host repsonds within timeout OsStatus OsUtil::checkDnsAvailability(char *dnsServer, OsTime timeout) { OsStatus retval = OS_SUCCESS; struct hostent* server; UtlString temp_output_address; # if defined(_VXWORKS) char hostentBuf[512]; # endif # if defined(_WIN32) || defined(__pingtel_on_posix__) server = gethostbyname(dnsServer); # elif defined(_VXWORKS) server = resolvGetHostByName((char*) dnsServer, hostentBuf, sizeof(hostentBuf)); # else # error Unsupported target platform. # endif //_VXWORKS if(! server) { osPrintf("DNS failed to lookup host: %s\n",dnsServer); retval = OS_DNS_UNAVAILABLE; } temp_output_address.remove(0); return retval; }
NetAddressList::NetAddressList(char const* hostname) : fNumAddresses(0), fAddressArray(NULL) { struct hostent* host; // Check first whether "hostname" is an IP address string: netAddressBits addr = our_inet_addr((char*)hostname); if (addr != INADDR_NONE) { // yes it was an IP address string //##### host = gethostbyaddr((char*)&addr, sizeof (netAddressBits), AF_INET); host = NULL; // don't bother calling gethostbyaddr(); we only want 1 addr if (host == NULL) { // For some unknown reason, gethostbyaddr() failed, so just // return a 1-element list with the address we were given: fNumAddresses = 1; fAddressArray = new NetAddress*[fNumAddresses]; if (fAddressArray == NULL) return; fAddressArray[0] = new NetAddress((u_int8_t*)&addr, sizeof (netAddressBits)); return; } } else { // Try resolving "hostname" as a real host name #if defined(VXWORKS) char hostentBuf[512]; host = (struct hostent*)resolvGetHostByName((char*)hostname,(char*)&hostentBuf,sizeof hostentBuf); #else host = our_gethostbyname((char*)hostname); #endif if (host == NULL) { // It was a host name, and we couldn't resolve it. We're SOL. return; } } u_int8_t const** const hAddrPtr = (u_int8_t const**)host->h_addr_list; if (hAddrPtr != NULL) { // First, count the number of addresses: u_int8_t const** hAddrPtr1 = hAddrPtr; while (*hAddrPtr1 != NULL) { ++fNumAddresses; ++hAddrPtr1; } // Next, set up the list: fAddressArray = new NetAddress*[fNumAddresses]; if (fAddressArray == NULL) return; for (unsigned i = 0; i < fNumAddresses; ++i) { fAddressArray[i] = new NetAddress(hAddrPtr[i], host->h_length); } } }
const HostEntry& DNS::hostByName(const std::string& hostname) { FastMutex::ScopedLock lock(_mutex); DNSCache::const_iterator it = _cache.find(hostname); if (it != _cache.end()) { return it->second; } else { #if defined(_WIN32) && defined(POCO_HAVE_IPv6) struct addrinfo* pAI; struct addrinfo hints; memset(&hints, 0, sizeof(hints)); hints.ai_flags = AI_CANONNAME; if (getaddrinfo(hostname.c_str(), NULL, &hints, &pAI) == 0) { std::pair<DNSCache::iterator, bool> res = _cache.insert(std::pair<std::string, HostEntry>(hostname, HostEntry(pAI))); freeaddrinfo(pAI); return res.first->second; } #elif defined(POCO_VXWORKS) static char buffer[2048]; struct hostent* he = resolvGetHostByName((char*) hostname.c_str(), buffer, sizeof(buffer)); if (he) { std::pair<DNSCache::iterator, bool> res = _cache.insert(std::pair<std::string, HostEntry>(hostname, HostEntry(he))); return res.first->second; } #else struct hostent* he = gethostbyname(hostname.c_str()); if (he) { std::pair<DNSCache::iterator, bool> res = _cache.insert(std::pair<std::string, HostEntry>(hostname, HostEntry(he))); return res.first->second; } #endif } error(lastError(), hostname); // will throw an appropriate exception throw NetException(); // to silence compiler }
NetAddressList::NetAddressList(char const* hostname) : fNumAddresses(0), fAddressArray(NULL) { // First, check whether "hostname" is an IP address string: netAddressBits addr = our_inet_addr((char*)hostname); if (addr != INADDR_NONE) { // Yes, it was an IP address string. Return a 1-element list with this address: fNumAddresses = 1; fAddressArray = new NetAddress*[fNumAddresses]; if (fAddressArray == NULL) return; fAddressArray[0] = new NetAddress((u_int8_t*)&addr, sizeof (netAddressBits)); return; } // "hostname" is not an IP address string; try resolving it as a real host name instead: #if defined(USE_GETHOSTBYNAME) || defined(VXWORKS) struct hostent* host; #if defined(VXWORKS) char hostentBuf[512]; host = (struct hostent*)resolvGetHostByName((char*)hostname, (char*)&hostentBuf, sizeof hostentBuf); #else host = gethostbyname((char*)hostname); #endif if (host == NULL || host->h_length != 4 || host->h_addr_list == NULL) return; // no luck u_int8_t const** const hAddrPtr = (u_int8_t const**)host->h_addr_list; // First, count the number of addresses: u_int8_t const** hAddrPtr1 = hAddrPtr; while (*hAddrPtr1 != NULL) { ++fNumAddresses; ++hAddrPtr1; } // Next, set up the list: fAddressArray = new NetAddress*[fNumAddresses]; if (fAddressArray == NULL) return; for (unsigned i = 0; i < fNumAddresses; ++i) { fAddressArray[i] = new NetAddress(hAddrPtr[i], host->h_length); } #else // Use "getaddrinfo()" (rather than the older, deprecated "gethostbyname()"): struct addrinfo addrinfoHints; memset(&addrinfoHints, 0, sizeof addrinfoHints); addrinfoHints.ai_family = AF_INET; // For now, we're interested in IPv4 addresses only struct addrinfo* addrinfoResultPtr = NULL; int result = getaddrinfo(hostname, NULL, &addrinfoHints, &addrinfoResultPtr); if (result != 0 || addrinfoResultPtr == NULL) return; // no luck // First, count the number of addresses: const struct addrinfo* p = addrinfoResultPtr; while (p != NULL) { if (p->ai_addrlen < 4) continue; // sanity check: skip over addresses that are too small ++fNumAddresses; p = p->ai_next; } // Next, set up the list: fAddressArray = new NetAddress*[fNumAddresses]; if (fAddressArray == NULL) return; unsigned i = 0; p = addrinfoResultPtr; while (p != NULL) { if (p->ai_addrlen < 4) continue; fAddressArray[i++] = new NetAddress((u_int8_t const*)&(((struct sockaddr_in*)p->ai_addr)->sin_addr.s_addr), 4); p = p->ai_next; } // Finally, free the data that we had allocated by calling "getaddrinfo()": freeaddrinfo(addrinfoResultPtr); #endif }
// Constructor OsMulticastSocket::OsMulticastSocket(int multicastPortNum, const char* multicastHost, int localHostPortNum, const char* localHost) { int error = 0; struct sockaddr_in localAddr; struct hostent* server = NULL; int iTmp = TRUE; socketDescriptor = OS_INVALID_SOCKET_DESCRIPTOR; localHostPort = localHostPortNum; if(localHost) { localHostName.append(localHost); } remoteHostPort = multicastPortNum; if(multicastHost) { remoteHostName.append(multicastHost); } if(!socketInit()) { goto EXIT; } # ifdef _VXWORKS char hostentBuf[512]; # endif // Create the socket socketDescriptor = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP); if(socketDescriptor == OS_INVALID_SOCKET_DESCRIPTOR) { error = OsSocketGetERRNO(); close(); perror("call to socket failed in OsMulticastSocket::OsMulticastSocket\n"); osPrintf("socket call failed with error in OsMulticastSocket::OsMulticastSocket: 0x%x\n", error); goto EXIT; } /* avoid EADDRINUSE error on bind() */ iTmp = TRUE; if(setsockopt(socketDescriptor, SOL_SOCKET, SO_REUSEADDR, (char *)&iTmp, sizeof(iTmp))) { error = OsSocketGetERRNO(); close(); perror("call to setsockopt failed\n"); osPrintf("setsockopt SO_REUSEADDR call failed with error: %d\n", error); goto EXIT; } localAddr.sin_family = AF_INET; localAddr.sin_port = htons(multicastPortNum); if(localHost == NULL) { localAddr.sin_addr.s_addr=OsSocket::getDefaultBindAddress(); // localAddr.sin_addr.s_addr=htonl(INADDR_ANY); // Allow IP in on // any of this hosts addresses or NICs. } else { // Should use host address specified, for now use any localAddr.sin_addr.s_addr=OsSocket::getDefaultBindAddress(); // localAddr.sin_addr.s_addr=htonl(INADDR_ANY); // Allow IP in on // any of this hosts addresses or NICs. } # if defined(_WIN32) error = bind( socketDescriptor, (const struct sockaddr*) &localAddr, sizeof(localAddr)); # elif defined(_VXWORKS) || defined(__pingtel_on_posix__) error = bind( socketDescriptor, (struct sockaddr*) &localAddr, sizeof(localAddr)); # else # error Unsupported target platform. # endif if(error == OS_INVALID_SOCKET_DESCRIPTOR) { // error = OsSocketGetERRNO(); close(); // perror("bind to socket failed\n"); goto EXIT; } // Setup multicast options # if defined(_WIN32) || defined(__pingtel_on_posix__) server = gethostbyname(multicastHost); # elif defined(_VXWORKS) server = resolvGetHostByName((char*) multicastHost, hostentBuf, sizeof(hostentBuf)); # else # error Unsupported target platform. # endif //_VXWORKS if(server == NULL) { error = OsSocketGetERRNO(); close(); perror("call to gethostbyname failed\n"); osPrintf("gethostbyname(%s) call failed with error: %d\n",multicastHost, error); goto EXIT; } struct ip_mreq mreq; mreq.imr_multiaddr = *((in_addr*) (server->h_addr)); mreq.imr_interface.s_addr = OsSocket::getDefaultBindAddress(); // mreq.imr_interface.s_addr = htonl(INADDR_ANY); if(setsockopt(socketDescriptor, IPPROTO_IP, IP_ADD_MEMBERSHIP, (char*) &mreq, sizeof(mreq))) { error = OsSocketGetERRNO(); close(); perror("call to setsockopt failed\n"); osPrintf("setsockopt call failed with error: %d\n", error); goto EXIT; } joinMulticast(multicastPortNum, multicastHost); EXIT: ; }
void OsDatagramSocket::doConnect(int remoteHostPortNum, const char* remoteHost, UtlBoolean simulateConnect) { struct hostent* server = NULL; mToSockaddrValid = FALSE; memset(mpToSockaddr, 0, sizeof(struct sockaddr_in)); remoteHostPort = remoteHostPortNum; // Store host name if(remoteHost) { remoteHostName = remoteHost ; getHostIpByName(remoteHostName, &mRemoteIpAddress); } else { remoteHostName.remove(0) ; } // Connect to a remote host if given if(portIsValid(remoteHostPort) && remoteHost && !simulateConnect) { #if defined(_WIN32) || defined(__pingtel_on_posix__) unsigned long ipAddr; ipAddr = inet_addr(remoteHost); if (ipAddr != INADDR_NONE) { server = gethostbyaddr((char * )&ipAddr,sizeof(ipAddr),AF_INET); } if ( server == NULL ) { server = gethostbyname(remoteHost); } #elif defined(_VXWORKS) char hostentBuf[512]; server = resolvGetHostByName((char*) remoteHost, hostentBuf, sizeof(hostentBuf)); #else # error Unsupported target platform. #endif //_VXWORKS if (server) { struct in_addr* serverAddr = (in_addr*) (server->h_addr); struct sockaddr_in serverSockAddr; serverSockAddr.sin_family = server->h_addrtype; serverSockAddr.sin_port = htons(remoteHostPort); serverSockAddr.sin_addr.s_addr = (serverAddr->s_addr); // Set the default destination address for the socket #if defined(_WIN32) || defined(__pingtel_on_posix__) if(connect(socketDescriptor, (const struct sockaddr*) &serverSockAddr, sizeof(serverSockAddr))) #elif defined(_VXWORKS) if(connect(socketDescriptor, (struct sockaddr*) &serverSockAddr, sizeof(serverSockAddr))) #else # error Unsupported target platform. #endif { int error = OsSocketGetERRNO(); close(); OsSysLog::add(FAC_KERNEL, PRI_DEBUG, "OsDatagramSocket::doConnect( %s:%d ) failed w/ errno %d)", remoteHost, remoteHostPortNum, error); } else { mIsConnected = TRUE; } } else { close(); OsSysLog::add(FAC_KERNEL, PRI_DEBUG, "OsDatagramSocket::doConnect( %s:%d ) failed host lookup)", remoteHost, remoteHostPortNum); goto EXIT; } } else if(portIsValid(remoteHostPort) && remoteHost && simulateConnect) { mIsConnected = TRUE; mSimulatedConnect = TRUE; } EXIT: ; }