aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/libslirp.h16
-rw-r--r--src/libslirp.map4
-rw-r--r--src/slirp.c17
-rw-r--r--src/slirp.h2
4 files changed, 38 insertions, 1 deletions
diff --git a/src/libslirp.h b/src/libslirp.h
index 546f2f9..8eb47a0 100644
--- a/src/libslirp.h
+++ b/src/libslirp.h
@@ -63,7 +63,8 @@ typedef struct SlirpCb {
void (*guest_error)(const char *msg, void *opaque);
/* Return the virtual clock value in nanoseconds */
int64_t (*clock_get_ns)(void *opaque);
- /* Create a new timer with the given callback and opaque data */
+ /* Create a new timer with the given callback and opaque data. Not
+ * needed if timer_new_opaque is provided. */
void *(*timer_new)(SlirpTimerCb cb, void *cb_opaque, void *opaque);
/* Remove and free a timer */
void (*timer_free)(void *timer, void *opaque);
@@ -76,6 +77,14 @@ typedef struct SlirpCb {
/* Kick the io-thread, to signal that new events may be processed because some TCP buffer
* can now receive more data, i.e. slirp_socket_can_recv will return 1. */
void (*notify)(void *opaque);
+
+ /*
+ * Fields introduced in SlirpConfig version 4 begin
+ */
+
+ /* Create a new timer. When the timer fires, the application passes
+ * the SlirpTimerId and cb_opaque to slirp_handle_timer. */
+ void *(*timer_new_opaque)(SlirpTimerId id, void *cb_opaque, void *opaque);
} SlirpCb;
#define SLIRP_CONFIG_VERSION_MIN 1
@@ -171,6 +180,11 @@ void slirp_pollfds_poll(Slirp *slirp, int select_error,
* guest network, to be interpreted by slirp. */
void slirp_input(Slirp *slirp, const uint8_t *pkt, int pkt_len);
+/* This is called by the application when a timer expires, if it provides
+ * the timer_new_opaque callback. It is not needed if the application only
+ * uses timer_new. */
+void slirp_handle_timer(Slirp *slirp, SlirpTimerId id, void *cb_opaque);
+
/* These set up / remove port forwarding between a host port in the real world
* and the guest network. */
int slirp_add_hostfwd(Slirp *slirp, int is_udp, struct in_addr host_addr,
diff --git a/src/libslirp.map b/src/libslirp.map
index 792b0a9..3921f8a 100644
--- a/src/libslirp.map
+++ b/src/libslirp.map
@@ -34,3 +34,7 @@ SLIRP_4.5 {
slirp_remove_hostxfwd;
slirp_neighbor_info;
} SLIRP_4.2;
+
+SLIRP_4.7 {
+ slirp_handle_timer;
+} SLIRP_4.5;
diff --git a/src/slirp.c b/src/slirp.c
index a2876f2..c92a9a9 100644
--- a/src/slirp.c
+++ b/src/slirp.c
@@ -535,10 +535,26 @@ static void ra_timer_handler_cb(void *opaque)
return ra_timer_handler(slirp, NULL);
}
+void slirp_handle_timer(Slirp *slirp, SlirpTimerId id, void *cb_opaque)
+{
+ g_return_if_fail(id >= 0 && id < SLIRP_TIMER_NUM);
+
+ switch (id) {
+ case SLIRP_TIMER_RA:
+ return ra_timer_handler(slirp, cb_opaque);
+ default:
+ abort();
+ }
+}
+
void *slirp_timer_new(Slirp *slirp, SlirpTimerId id, void *cb_opaque)
{
g_return_val_if_fail(id >= 0 && id < SLIRP_TIMER_NUM, NULL);
+ if (slirp->cfg_version >= 4 && slirp->cb->timer_new_opaque) {
+ return slirp->cb->timer_new_opaque(id, cb_opaque, slirp->opaque);
+ }
+
switch (id) {
case SLIRP_TIMER_RA:
g_return_val_if_fail(cb_opaque == NULL, NULL);
@@ -568,6 +584,7 @@ Slirp *slirp_new(const SlirpConfig *cfg, const SlirpCb *callbacks, void *opaque)
slirp_init_once();
+ slirp->cfg_version = cfg->version;
slirp->opaque = opaque;
slirp->cb = callbacks;
slirp->grand = g_rand_new();
diff --git a/src/slirp.h b/src/slirp.h
index bfe7b83..50e33a5 100644
--- a/src/slirp.h
+++ b/src/slirp.h
@@ -120,6 +120,8 @@ bool ndp_table_search(Slirp *slirp, struct in6_addr ip_addr,
uint8_t out_ethaddr[ETH_ALEN]);
struct Slirp {
+ int cfg_version;
+
unsigned time_fasttimo;
unsigned last_slowtimo;
bool do_slowtimo;