req->resolver->ups->data);
}
- rdns_request_unschedule (req);
+ rdns_request_unschedule (req, true);
if (!(rep->flags & RDNS_TRUNCATED)) {
req->state = RDNS_REQUEST_REPLIED;
if (req->state == RDNS_REQUEST_TCP) {
rep = rdns_make_reply (req, RDNS_RC_TIMEOUT);
- rdns_request_unschedule (req);
+ rdns_request_unschedule (req, true);
req->state = RDNS_REQUEST_REPLIED;
req->func (rep, req->arg);
REF_RELEASE (req);
if (req->retransmits == 0) {
rep = rdns_make_reply (req, RDNS_RC_TIMEOUT);
- rdns_request_unschedule (req);
+ rdns_request_unschedule (req, true);
req->state = RDNS_REQUEST_REPLIED;
req->func (rep, req->arg);
REF_RELEASE (req);
if (!IS_CHANNEL_ACTIVE(req->io) || cnt > 1) {
/* Do not reschedule IO requests on inactive sockets */
rdns_debug ("reschedule request with id: %d", (int)req->id);
- rdns_request_unschedule (req);
+ rdns_request_unschedule (req, true);
REF_RELEASE (req->io);
if (resolver->ups) {
}
void
-rdns_request_unschedule (struct rdns_request *req)
+rdns_request_unschedule (struct rdns_request *req, bool remove_from_hash)
{
if (req->async_event) {
if (req->state == RDNS_REQUEST_WAIT_REPLY) {
req->async->del_timer (req->async->data,
req->async_event);
- rdns_request_remove_from_hash(req);
+ if (remove_from_hash) {
+ rdns_request_remove_from_hash(req);
+ }
req->async_event = NULL;
}
else if (req->state == RDNS_REQUEST_WAIT_SEND) {
req->async->del_write (req->async->data,
req->async_event);
/* Remove from id hashes */
- rdns_request_remove_from_hash(req);
+ if (remove_from_hash) {
+ rdns_request_remove_from_hash(req);
+ }
req->async_event = NULL;
}
}
else if (req->state == RDNS_REQUEST_TCP) {
- rdns_request_remove_from_hash(req);
+ if (remove_from_hash) {
+ rdns_request_remove_from_hash(req);
+ }
req->async->del_timer(req->async->data,
req->async_event);
void
rdns_request_release (struct rdns_request *req)
{
- rdns_request_unschedule (req);
+ rdns_request_unschedule (req, true);
REF_RELEASE (req);
}
ioc->flags &= ~RDNS_CHANNEL_CONNECTED;
}
- if (ioc->sock != -1) {
- close (ioc->sock);
- ioc->sock = -1;
- }
- if (ioc->saddr) {
- free (ioc->saddr);
- ioc->saddr = NULL;
- }
-
/* Remove all requests pending as we are unable to complete them */
struct rdns_request *req;
kh_foreach_value(ioc->requests, req, {
struct rdns_reply *rep = rdns_make_reply (req, RDNS_RC_NETERR);
+ /*
+ * Unschedule request explicitly as we set state to RDNS_REQUEST_REPLIED
+ * that will prevent timer from being removed on req dtor.
+ *
+ * We skip hash removal here, as the hash will be cleared as a single
+ * operation afterwards.
+ */
+ rdns_request_unschedule(req, false);
req->state = RDNS_REQUEST_REPLIED;
req->func (rep, req->arg);
REF_RELEASE (req);
});
+ if (ioc->sock != -1) {
+ close (ioc->sock);
+ ioc->sock = -1;
+ }
+ if (ioc->saddr) {
+ free (ioc->saddr);
+ ioc->saddr = NULL;
+ }
+
kh_clear(rdns_requests_hash, ioc->requests);
}