Skip to content

Commit 6537bc8

Browse files
Fix on domain resolver (#1090) (#1091) (#1092)
* Fix on domain resolver Co-authored-by: Coldwings <coldwings@me.com>
1 parent 6a8b499 commit 6537bc8

File tree

1 file changed

+33
-23
lines changed

1 file changed

+33
-23
lines changed

net/utils.cpp

Lines changed: 33 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -265,36 +265,46 @@ class DefaultResolver : public Resolver {
265265
struct IPAddrList : public intrusive_list<IPAddrNode>, spinlock {
266266
~IPAddrList() { delete_all(); }
267267
};
268+
struct ResolveCtx {
269+
std::string host;
270+
Delegate<bool, IPAddr> filter;
271+
spinlock lock;
272+
IPAddrList *addrs;
273+
photon::semaphore sem;
274+
};
268275
IPAddr do_resolve(std::string_view host, Delegate<bool, IPAddr> filter) {
269276
auto ctr = [&]() -> IPAddrList* {
270-
auto addrs = new IPAddrList();
271-
photon::semaphore sem;
272-
std::thread([&]() {
273-
auto now = std::chrono::steady_clock::now();
274-
IPAddrList ret;
277+
std::unique_ptr<IPAddrList> addrs(new IPAddrList());
278+
auto ctx = std::make_shared<ResolveCtx>();
279+
ctx->addrs = addrs.get();
280+
ctx->host = std::string(host);
281+
ctx->filter = filter;
282+
std::thread([ctx]() {
275283
auto cb = [&](IPAddr addr) -> int {
276-
if (filter && !filter.fire(addr))
277-
return 0;
278-
ret.push_back(new IPAddrNode(addr));
284+
SCOPED_LOCK(ctx->lock);
285+
if (ctx->filter && !ctx->filter.fire(addr)) return 0;
286+
if (ctx->addrs) {
287+
ctx->addrs->push_back(new IPAddrNode(addr));
288+
}
279289
return 0;
280290
};
281-
_gethostbyname(host, cb);
282-
auto time_elapsed = std::chrono::duration_cast<std::chrono::microseconds>(
283-
std::chrono::steady_clock::now() - now).count();
284-
if ((uint64_t)time_elapsed <= resolve_timeout_) {
285-
addrs->push_back(std::move(ret));
286-
sem.signal(1);
287-
} else {
288-
LOG_ERROR("resolve timeout");
289-
while(!ret.empty())
290-
delete ret.pop_front();
291-
}
291+
_gethostbyname(ctx->host, cb);
292+
ctx->sem.signal(1);
292293
}).detach();
293-
sem.wait(1, resolve_timeout_);
294-
return addrs;
294+
ctx->sem.wait(1, resolve_timeout_);
295+
SCOPED_LOCK(ctx->lock);
296+
ctx->addrs = nullptr;
297+
ctx->filter = {};
298+
if (addrs->empty()) {
299+
return nullptr;
300+
}
301+
return addrs.release();
295302
};
296-
auto ips = dnscache_.borrow(host, ctr);
297-
if (ips->empty()) LOG_ERRNO_RETURN(0, IPAddr(), "Domain resolution for '`' failed", host);
303+
auto ips = dnscache_.borrow(host, ctr, 1UL * 1000);
304+
if (!ips || ips->empty()) {
305+
ips.recycle(true);
306+
LOG_ERRNO_RETURN(0, IPAddr(), "Domain resolution for '`' failed", host);
307+
}
298308
SCOPED_LOCK(*ips);
299309
return ips->round_robin_next()->addr;
300310
}

0 commit comments

Comments
 (0)