struct list_head list[PER_LEVEL];
};
-static void *timer_default_alloc(size_t len, void *arg)
+static void *timer_default_alloc(struct timers *timers, size_t len)
{
return malloc(len);
}
-static void timer_default_free(const void *p, void *arg)
+static void timer_default_free(struct timers *timers, void *p)
{
- free((void *)p);
+ free(p);
}
-static void *(*timer_alloc)(size_t, void *) = timer_default_alloc;
-static void (*timer_free)(const void *, void *) = timer_default_free;
-static void *timer_arg;
+static void *(*timer_alloc)(struct timers *, size_t) = timer_default_alloc;
+static void (*timer_free)(struct timers *, void *) = timer_default_free;
-void timers_set_allocator(void *(*alloc)(size_t len, void *arg),
- void (*free)(const void *p, void *arg),
- void *arg)
+void timers_set_allocator(void *(*alloc)(struct timers *, size_t len),
+ void (*free)(struct timers *, void *p))
{
if (!alloc)
alloc = timer_default_alloc;
free = timer_default_free;
timer_alloc = alloc;
timer_free = free;
- timer_arg = arg;
}
static uint64_t time_to_grains(struct timemono t)
list_node_init(&t->list);
}
-static bool list_node_initted(const struct list_node *n)
+static inline bool list_node_initted(const struct list_node *n)
{
return n->prev == n;
}
t->time = time_to_grains(timemono_add(time_mono(), rel));
-#if TIME_HAVE_MONOTONIC
- assert(t->time >= timers->base);
-#else
/* Added in the past? Treat it as imminent. */
if (t->time < timers->base)
t->time = timers->base;
-#endif
+
if (t->time < timers->first)
timers->first = t->time;
unsigned int i;
struct list_head from_far;
- l = timer_alloc(sizeof(*l), timer_arg);
+ l = timer_alloc(timers, sizeof(*l));
if (!l)
return;
unsigned int off;
struct timer *t;
- assert(now >= timers->base);
+ /* This can happen without TIME_HAVE_MONOTONIC, but I also have
+ * a report of OpenBSD 6.8 under virtualbox doing this. */
+ if (now < timers->base) {
+ return NULL;
+ }
if (!timers->level[0]) {
if (list_empty(&timers->far))
unsigned int l;
for (l = 0; l < ARRAY_SIZE(timers->level); l++)
- timer_free(timers->level[l], timer_arg);
+ timer_free(timers, timers->level[l]);
}