mirror of
https://github.com/isc-projects/bind9.git
synced 2026-02-23 09:51:03 -05:00
Add network manager based timer API
This commits adds API that allows to create arbitrary timers associated
with the network manager handles.
(cherry picked from commit 3c7b04d015)
This commit is contained in:
parent
c625e791af
commit
8b2ae8cc84
3 changed files with 143 additions and 0 deletions
|
|
@ -109,6 +109,7 @@ libisc_la_SOURCES = \
|
|||
netmgr/netmgr.c \
|
||||
netmgr/tcp.c \
|
||||
netmgr/tcpdns.c \
|
||||
netmgr/timer.c \
|
||||
netmgr/tlsdns.c \
|
||||
netmgr/udp.c \
|
||||
netmgr/uv-compat.c \
|
||||
|
|
|
|||
|
|
@ -700,3 +700,27 @@ isc__nm_force_tid(int tid);
|
|||
|
||||
void
|
||||
isc_nmhandle_setwritetimeout(isc_nmhandle_t *handle, uint64_t write_timeout);
|
||||
|
||||
/*
|
||||
* Timer related functions
|
||||
*/
|
||||
|
||||
typedef struct isc_nm_timer isc_nm_timer_t;
|
||||
|
||||
typedef void (*isc_nm_timer_cb)(void *, isc_result_t);
|
||||
|
||||
void
|
||||
isc_nm_timer_create(isc_nmhandle_t *, isc_nm_timer_cb, void *,
|
||||
isc_nm_timer_t **);
|
||||
|
||||
void
|
||||
isc_nm_timer_attach(isc_nm_timer_t *, isc_nm_timer_t **);
|
||||
|
||||
void
|
||||
isc_nm_timer_detach(isc_nm_timer_t **);
|
||||
|
||||
void
|
||||
isc_nm_timer_start(isc_nm_timer_t *, uint64_t);
|
||||
|
||||
void
|
||||
isc_nm_timer_stop(isc_nm_timer_t *);
|
||||
|
|
|
|||
118
lib/isc/netmgr/timer.c
Normal file
118
lib/isc/netmgr/timer.c
Normal file
|
|
@ -0,0 +1,118 @@
|
|||
/*
|
||||
* Copyright (C) Internet Systems Consortium, Inc. ("ISC")
|
||||
*
|
||||
* SPDX-License-Identifier: MPL-2.0
|
||||
*
|
||||
* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, you can obtain one at https://mozilla.org/MPL/2.0/.
|
||||
*
|
||||
* See the COPYRIGHT file distributed with this work for additional
|
||||
* information regarding copyright ownership.
|
||||
*/
|
||||
|
||||
#include <uv.h>
|
||||
|
||||
#include <isc/netmgr.h>
|
||||
#include <isc/util.h>
|
||||
|
||||
#include "netmgr-int.h"
|
||||
|
||||
struct isc_nm_timer {
|
||||
isc_refcount_t references;
|
||||
uv_timer_t timer;
|
||||
isc_nmhandle_t *handle;
|
||||
isc_nm_timer_cb cb;
|
||||
void *cbarg;
|
||||
};
|
||||
|
||||
void
|
||||
isc_nm_timer_create(isc_nmhandle_t *handle, isc_nm_timer_cb cb, void *cbarg,
|
||||
isc_nm_timer_t **timerp) {
|
||||
isc__networker_t *worker = NULL;
|
||||
isc_nmsocket_t *sock = NULL;
|
||||
isc_nm_timer_t *timer = NULL;
|
||||
int r;
|
||||
|
||||
REQUIRE(isc__nm_in_netthread());
|
||||
REQUIRE(VALID_NMHANDLE(handle));
|
||||
REQUIRE(VALID_NMSOCK(handle->sock));
|
||||
|
||||
sock = handle->sock;
|
||||
worker = &sock->mgr->workers[isc_nm_tid()];
|
||||
|
||||
timer = isc_mem_get(sock->mgr->mctx, sizeof(*timer));
|
||||
*timer = (isc_nm_timer_t){ .cb = cb, .cbarg = cbarg };
|
||||
isc_refcount_init(&timer->references, 1);
|
||||
isc_nmhandle_attach(handle, &timer->handle);
|
||||
|
||||
r = uv_timer_init(&worker->loop, &timer->timer);
|
||||
UV_RUNTIME_CHECK(uv_timer_init, r);
|
||||
|
||||
uv_handle_set_data((uv_handle_t *)&timer->timer, timer);
|
||||
|
||||
*timerp = timer;
|
||||
}
|
||||
|
||||
void
|
||||
isc_nm_timer_attach(isc_nm_timer_t *timer, isc_nm_timer_t **timerp) {
|
||||
REQUIRE(timer != NULL);
|
||||
REQUIRE(timerp != NULL && *timerp == NULL);
|
||||
|
||||
isc_refcount_increment(&timer->references);
|
||||
*timerp = timer;
|
||||
}
|
||||
|
||||
static void
|
||||
timer_destroy(uv_handle_t *uvhandle) {
|
||||
isc_nm_timer_t *timer = uv_handle_get_data(uvhandle);
|
||||
isc_nmhandle_t *handle = timer->handle;
|
||||
isc_mem_t *mctx = timer->handle->sock->mgr->mctx;
|
||||
|
||||
isc_mem_put(mctx, timer, sizeof(*timer));
|
||||
|
||||
isc_nmhandle_detach(&handle);
|
||||
}
|
||||
|
||||
void
|
||||
isc_nm_timer_detach(isc_nm_timer_t **timerp) {
|
||||
isc_nm_timer_t *timer = NULL;
|
||||
isc_nmhandle_t *handle = NULL;
|
||||
|
||||
REQUIRE(timerp != NULL && *timerp != NULL);
|
||||
|
||||
timer = *timerp;
|
||||
*timerp = NULL;
|
||||
|
||||
handle = timer->handle;
|
||||
|
||||
REQUIRE(isc__nm_in_netthread());
|
||||
REQUIRE(VALID_NMHANDLE(handle));
|
||||
REQUIRE(VALID_NMSOCK(handle->sock));
|
||||
|
||||
if (isc_refcount_decrement(&timer->references) == 1) {
|
||||
uv_timer_stop(&timer->timer);
|
||||
uv_close((uv_handle_t *)&timer->timer, timer_destroy);
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
timer_cb(uv_timer_t *uvtimer) {
|
||||
isc_nm_timer_t *timer = uv_handle_get_data((uv_handle_t *)uvtimer);
|
||||
|
||||
REQUIRE(timer->cb != NULL);
|
||||
|
||||
timer->cb(timer->cbarg, ISC_R_TIMEDOUT);
|
||||
}
|
||||
|
||||
void
|
||||
isc_nm_timer_start(isc_nm_timer_t *timer, uint64_t timeout) {
|
||||
int r = uv_timer_start(&timer->timer, timer_cb, timeout, 0);
|
||||
UV_RUNTIME_CHECK(uv_timer_start, r);
|
||||
}
|
||||
|
||||
void
|
||||
isc_nm_timer_stop(isc_nm_timer_t *timer) {
|
||||
int r = uv_timer_stop(&timer->timer);
|
||||
UV_RUNTIME_CHECK(uv_timer_stop, r);
|
||||
}
|
||||
Loading…
Reference in a new issue