/* */ #include "AsyncNameResolver.h" #include "Util.h" #include namespace aria2 { #ifdef HAVE_LIBCARES1_5 void callback(void* arg, int status, int timeouts, struct hostent* host) #else void callback(void* arg, int status, struct hostent* host) #endif // HAVE_LIBCARES1_5 { AsyncNameResolver* resolverPtr = reinterpret_cast(arg); #ifdef HAVE_LIBARES // This block is required since the assertion in ares_strerror fails // if status = ARES_EDESTRUCTION is passed to ares_strerror as 1st argument. // This does not happen in c-ares. if(status == ARES_EDESTRUCTION) { // we simply return in this case. return; } #endif if(status != ARES_SUCCESS) { #ifdef HAVE_LIBCARES resolverPtr->error = ares_strerror(status); #else resolverPtr->error = ares_strerror(status, 0); #endif // HAVE_LIBCARES resolverPtr->status = AsyncNameResolver::STATUS_ERROR; return; } for(char** ap = host->h_addr_list; *ap; ++ap) { resolverPtr->_resolvedAddresses.push_back (inet_ntoa(*reinterpret_cast(*ap))); } resolverPtr->status = AsyncNameResolver::STATUS_SUCCESS; } AsyncNameResolver::AsyncNameResolver(): status(STATUS_READY) { // TODO evaluate return value ares_init(&channel); } AsyncNameResolver::~AsyncNameResolver() { ares_destroy(channel); } void AsyncNameResolver::resolve(const std::string& name) { _hostname = name; status = STATUS_QUERYING; ares_gethostbyname(channel, name.c_str(), AF_INET, callback, this); } const std::deque& AsyncNameResolver::getResolvedAddresses() const { return _resolvedAddresses; } const std::string& AsyncNameResolver::getError() const { return error; } AsyncNameResolver::STATUS AsyncNameResolver::getStatus() const { return status; } int AsyncNameResolver::getFds(fd_set* rfdsPtr, fd_set* wfdsPtr) const { return ares_fds(channel, rfdsPtr, wfdsPtr); } void AsyncNameResolver::process(fd_set* rfdsPtr, fd_set* wfdsPtr) { ares_process(channel, rfdsPtr, wfdsPtr); } bool AsyncNameResolver::operator==(const AsyncNameResolver& resolver) const { return this == &resolver; } void AsyncNameResolver::reset() { _hostname = ""; _resolvedAddresses.clear(); status = STATUS_READY; ares_destroy(channel); // TODO evaluate return value ares_init(&channel); } const std::string& AsyncNameResolver::getHostname() const { return _hostname; } } // namespace aria2