#include "defs.h"
int supplyinterval;
void
timer(void)
{
struct rthash *rh;
struct rt_entry *rt;
boolean_t timetomulticast = _B_FALSE;
int i;
static int iftime;
static int mtime;
static int alarmtime = 0;
int mintime;
if (alarmtime == 0) {
supplyinterval = GET_RANDOM(MIN_SUPPLY_TIME, MAX_SUPPLY_TIME);
iftime = 0;
mtime = supplyinterval;
alarmtime = supplyinterval;
(void) alarm(alarmtime);
return;
}
mintime = INT_MAX;
(void) sighold(SIGHUP);
(void) sighold(SIGUSR1);
(void) sighold(SIGUSR2);
iftime += alarmtime;
if (iftime >= CHECK_INTERVAL) {
initifs();
iftime = 0;
}
mintime = min(mintime, CHECK_INTERVAL - iftime);
mtime += alarmtime;
if (mtime >= supplyinterval) {
if (supplier)
timetomulticast = _B_TRUE;
mtime = 0;
supplyinterval = GET_RANDOM(MIN_SUPPLY_TIME, MAX_SUPPLY_TIME);
}
mintime = min(mintime, supplyinterval - mtime);
for (i = IPV6_ABITS; i >= 0; i--) {
if (net_hashes[i] == NULL)
continue;
for (rh = net_hashes[i];
rh < &net_hashes[i][ROUTEHASHSIZ]; rh++) {
for (rt = rh->rt_forw; rt != (struct rt_entry *)rh;
rt = rt->rt_forw) {
rt->rt_state &= ~RTS_CHANGED;
if ((rt->rt_state & RTS_INTERFACE) != 0)
continue;
rt->rt_timer += alarmtime;
if (rt->rt_timer >= GARBAGE_TIME) {
rt = rt->rt_back;
rtdelete(rt->rt_forw);
continue;
}
if (rt->rt_timer >= EXPIRE_TIME) {
rtdown(rt);
mintime = min(mintime,
GARBAGE_TIME - rt->rt_timer);
} else {
mintime = min(mintime,
EXPIRE_TIME - rt->rt_timer);
}
}
}
}
if (timetomulticast) {
supplyall(&allrouters, 0, (struct interface *)NULL, _B_TRUE);
(void) gettimeofday(&now, (struct timezone *)NULL);
lastmcast = now;
lastfullupdate = now;
needupdate = _B_FALSE;
nextmcast.tv_sec = 0;
}
(void) sigrelse(SIGUSR2);
(void) sigrelse(SIGUSR1);
(void) sigrelse(SIGHUP);
alarmtime = mintime;
(void) alarm(alarmtime);
}
void
term(void)
{
struct rthash *rh;
struct rt_entry *rt;
int i;
if (!supplier)
exit(EXIT_SUCCESS);
for (i = IPV6_ABITS; i >= 0; i--) {
if (net_hashes[i] == NULL)
continue;
for (rh = net_hashes[i]; rh < &net_hashes[i][ROUTEHASHSIZ];
rh++) {
for (rt = rh->rt_forw; rt != (struct rt_entry *)rh;
rt = rt->rt_forw) {
rt->rt_metric = HOPCNT_INFINITY;
}
}
}
supplyall(&allrouters, 0, (struct interface *)NULL, _B_TRUE);
(void) unlink(PATH_PID);
exit(EXIT_SUCCESS);
}