summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--sys/netinet6/icmp6.c4
-rw-r--r--sys/netinet6/in6.c18
-rw-r--r--sys/netinet6/in6.h4
-rw-r--r--sys/netinet6/ip6_forward.c8
-rw-r--r--sys/netinet6/ip6_id.c4
-rw-r--r--sys/netinet6/ip6_mroute.c4
-rw-r--r--sys/netinet6/nd6.c10
-rw-r--r--sys/netinet6/nd6_rtr.c32
-rw-r--r--sys/sys/param.h2
-rw-r--r--usr.sbin/ndp/ndp.c76
-rw-r--r--usr.sbin/rtadvctl/rtadvctl.c32
-rw-r--r--usr.sbin/rtadvd/config.c20
-rw-r--r--usr.sbin/rtadvd/rrenum.c9
-rw-r--r--usr.sbin/rtadvd/rtadvd.c41
-rw-r--r--usr.sbin/rtadvd/rtadvd.h4
-rw-r--r--usr.sbin/rtadvd/timer.c45
-rw-r--r--usr.sbin/rtadvd/timer.h10
-rw-r--r--usr.sbin/rtadvd/timer_subr.c49
-rw-r--r--usr.sbin/rtadvd/timer_subr.h44
-rw-r--r--usr.sbin/rtsold/dump.c19
-rw-r--r--usr.sbin/rtsold/rtsol.c20
-rw-r--r--usr.sbin/rtsold/rtsold.c52
-rw-r--r--usr.sbin/rtsold/rtsold.h33
23 files changed, 287 insertions, 253 deletions
diff --git a/sys/netinet6/icmp6.c b/sys/netinet6/icmp6.c
index de1b0e6..28e7312 100644
--- a/sys/netinet6/icmp6.c
+++ b/sys/netinet6/icmp6.c
@@ -1931,8 +1931,8 @@ ni6_store_addrs(struct icmp6_nodeinfo *ni6, struct icmp6_nodeinfo *nni6,
ltime = ND6_INFINITE_LIFETIME;
else {
if (ifa6->ia6_lifetime.ia6t_expire >
- time_second)
- ltime = htonl(ifa6->ia6_lifetime.ia6t_expire - time_second);
+ time_uptime)
+ ltime = htonl(ifa6->ia6_lifetime.ia6t_expire - time_uptime);
else
ltime = 0;
}
diff --git a/sys/netinet6/in6.c b/sys/netinet6/in6.c
index a8930d7..9d99930 100644
--- a/sys/netinet6/in6.c
+++ b/sys/netinet6/in6.c
@@ -523,12 +523,12 @@ in6_control(struct socket *so, u_long cmd, caddr_t data,
/* sanity for overflow - beware unsigned */
lt = &ifr->ifr_ifru.ifru_lifetime;
if (lt->ia6t_vltime != ND6_INFINITE_LIFETIME &&
- lt->ia6t_vltime + time_second < time_second) {
+ lt->ia6t_vltime + time_uptime < time_uptime) {
error = EINVAL;
goto out;
}
if (lt->ia6t_pltime != ND6_INFINITE_LIFETIME &&
- lt->ia6t_pltime + time_second < time_second) {
+ lt->ia6t_pltime + time_uptime < time_uptime) {
error = EINVAL;
goto out;
}
@@ -632,12 +632,12 @@ in6_control(struct socket *so, u_long cmd, caddr_t data,
/* for sanity */
if (ia->ia6_lifetime.ia6t_vltime != ND6_INFINITE_LIFETIME) {
ia->ia6_lifetime.ia6t_expire =
- time_second + ia->ia6_lifetime.ia6t_vltime;
+ time_uptime + ia->ia6_lifetime.ia6t_vltime;
} else
ia->ia6_lifetime.ia6t_expire = 0;
if (ia->ia6_lifetime.ia6t_pltime != ND6_INFINITE_LIFETIME) {
ia->ia6_lifetime.ia6t_preferred =
- time_second + ia->ia6_lifetime.ia6t_pltime;
+ time_uptime + ia->ia6_lifetime.ia6t_pltime;
} else
ia->ia6_lifetime.ia6t_preferred = 0;
break;
@@ -1140,7 +1140,7 @@ in6_update_ifa(struct ifnet *ifp, struct in6_aliasreq *ifra,
ia->ia_ifa.ifa_addr = (struct sockaddr *)&ia->ia_addr;
ia->ia_addr.sin6_family = AF_INET6;
ia->ia_addr.sin6_len = sizeof(ia->ia_addr);
- ia->ia6_createtime = time_second;
+ ia->ia6_createtime = time_uptime;
if ((ifp->if_flags & (IFF_POINTOPOINT | IFF_LOOPBACK)) != 0) {
/*
* XXX: some functions expect that ifa_dstaddr is not
@@ -1167,7 +1167,7 @@ in6_update_ifa(struct ifnet *ifp, struct in6_aliasreq *ifra,
}
/* update timestamp */
- ia->ia6_updatetime = time_second;
+ ia->ia6_updatetime = time_uptime;
/* set prefix mask */
if (ifra->ifra_prefixmask.sin6_len) {
@@ -1217,12 +1217,12 @@ in6_update_ifa(struct ifnet *ifp, struct in6_aliasreq *ifra,
ia->ia6_lifetime = ifra->ifra_lifetime;
if (ia->ia6_lifetime.ia6t_vltime != ND6_INFINITE_LIFETIME) {
ia->ia6_lifetime.ia6t_expire =
- time_second + ia->ia6_lifetime.ia6t_vltime;
+ time_uptime + ia->ia6_lifetime.ia6t_vltime;
} else
ia->ia6_lifetime.ia6t_expire = 0;
if (ia->ia6_lifetime.ia6t_pltime != ND6_INFINITE_LIFETIME) {
ia->ia6_lifetime.ia6t_preferred =
- time_second + ia->ia6_lifetime.ia6t_pltime;
+ time_uptime + ia->ia6_lifetime.ia6t_pltime;
} else
ia->ia6_lifetime.ia6t_preferred = 0;
@@ -1240,7 +1240,7 @@ in6_update_ifa(struct ifnet *ifp, struct in6_aliasreq *ifra,
*/
if ((ifra->ifra_flags & IN6_IFF_DEPRECATED) != 0) {
ia->ia6_lifetime.ia6t_pltime = 0;
- ia->ia6_lifetime.ia6t_preferred = time_second;
+ ia->ia6_lifetime.ia6t_preferred = time_uptime;
}
/*
* Make the address tentative before joining multicast addresses,
diff --git a/sys/netinet6/in6.h b/sys/netinet6/in6.h
index 616f100..07ba290 100644
--- a/sys/netinet6/in6.h
+++ b/sys/netinet6/in6.h
@@ -361,11 +361,11 @@ extern const struct in6_addr in6addr_linklocal_allv2routers;
#define IFA6_IS_DEPRECATED(a) \
((a)->ia6_lifetime.ia6t_pltime != ND6_INFINITE_LIFETIME && \
- (u_int32_t)((time_second - (a)->ia6_updatetime)) > \
+ (u_int32_t)((time_uptime - (a)->ia6_updatetime)) > \
(a)->ia6_lifetime.ia6t_pltime)
#define IFA6_IS_INVALID(a) \
((a)->ia6_lifetime.ia6t_vltime != ND6_INFINITE_LIFETIME && \
- (u_int32_t)((time_second - (a)->ia6_updatetime)) > \
+ (u_int32_t)((time_uptime - (a)->ia6_updatetime)) > \
(a)->ia6_lifetime.ia6t_vltime)
#endif /* _KERNEL */
diff --git a/sys/netinet6/ip6_forward.c b/sys/netinet6/ip6_forward.c
index fa54fe43..2cc2741 100644
--- a/sys/netinet6/ip6_forward.c
+++ b/sys/netinet6/ip6_forward.c
@@ -137,8 +137,8 @@ ip6_forward(struct mbuf *m, int srcrt)
IN6_IS_ADDR_UNSPECIFIED(&ip6->ip6_src)) {
IP6STAT_INC(ip6s_cantforward);
/* XXX in6_ifstat_inc(rt->rt_ifp, ifs6_in_discard) */
- if (V_ip6_log_time + V_ip6_log_interval < time_second) {
- V_ip6_log_time = time_second;
+ if (V_ip6_log_time + V_ip6_log_interval < time_uptime) {
+ V_ip6_log_time = time_uptime;
log(LOG_DEBUG,
"cannot forward "
"from %s to %s nxt %d received on %s\n",
@@ -405,8 +405,8 @@ skip_routing:
IP6STAT_INC(ip6s_badscope);
in6_ifstat_inc(rt->rt_ifp, ifs6_in_discard);
- if (V_ip6_log_time + V_ip6_log_interval < time_second) {
- V_ip6_log_time = time_second;
+ if (V_ip6_log_time + V_ip6_log_interval < time_uptime) {
+ V_ip6_log_time = time_uptime;
log(LOG_DEBUG,
"cannot forward "
"src %s, dst %s, nxt %d, rcvif %s, outif %s\n",
diff --git a/sys/netinet6/ip6_id.c b/sys/netinet6/ip6_id.c
index fa7bc64..cf80806 100644
--- a/sys/netinet6/ip6_id.c
+++ b/sys/netinet6/ip6_id.c
@@ -221,7 +221,7 @@ initid(struct randomtab *p)
p->ru_g = pmod(p->ru_gen, j, p->ru_n);
p->ru_counter = 0;
- p->ru_reseed = time_second + p->ru_out;
+ p->ru_reseed = time_uptime + p->ru_out;
p->ru_msb = p->ru_msb ? 0 : (1U << (p->ru_bits - 1));
}
@@ -231,7 +231,7 @@ randomid(struct randomtab *p)
int i, n;
u_int32_t tmp;
- if (p->ru_counter >= p->ru_max || time_second > p->ru_reseed)
+ if (p->ru_counter >= p->ru_max || time_uptime > p->ru_reseed)
initid(p);
tmp = arc4random();
diff --git a/sys/netinet6/ip6_mroute.c b/sys/netinet6/ip6_mroute.c
index db614ec..194aaf5 100644
--- a/sys/netinet6/ip6_mroute.c
+++ b/sys/netinet6/ip6_mroute.c
@@ -1103,8 +1103,8 @@ X_ip6_mforward(struct ip6_hdr *ip6, struct ifnet *ifp, struct mbuf *m)
*/
if (IN6_IS_ADDR_UNSPECIFIED(&ip6->ip6_src)) {
IP6STAT_INC(ip6s_cantforward);
- if (V_ip6_log_time + V_ip6_log_interval < time_second) {
- V_ip6_log_time = time_second;
+ if (V_ip6_log_time + V_ip6_log_interval < time_uptime) {
+ V_ip6_log_time = time_uptime;
log(LOG_DEBUG,
"cannot forward "
"from %s to %s nxt %d received on %s\n",
diff --git a/sys/netinet6/nd6.c b/sys/netinet6/nd6.c
index 2c27c71..6ad787f 100644
--- a/sys/netinet6/nd6.c
+++ b/sys/netinet6/nd6.c
@@ -428,7 +428,7 @@ nd6_llinfo_settimer_locked(struct llentry *ln, long tick)
ln->ln_ntick = 0;
canceled = callout_stop(&ln->ln_timer_ch);
} else {
- ln->la_expire = time_second + tick / hz;
+ ln->la_expire = time_uptime + tick / hz;
LLE_ADDREF(ln);
if (tick > INT_MAX) {
ln->ln_ntick = tick - INT_MAX;
@@ -591,7 +591,7 @@ nd6_timer(void *arg)
/* expire default router list */
TAILQ_FOREACH_SAFE(dr, &V_nd_defrouter, dr_entry, ndr) {
- if (dr->expire && dr->expire < time_second)
+ if (dr->expire && dr->expire < time_uptime)
defrtrlist_del(dr);
}
@@ -675,7 +675,7 @@ nd6_timer(void *arg)
* prefix is not necessary.
*/
if (pr->ndpr_vltime != ND6_INFINITE_LIFETIME &&
- time_second - pr->ndpr_lastupdate > pr->ndpr_vltime) {
+ time_uptime - pr->ndpr_lastupdate > pr->ndpr_vltime) {
/*
* address expiration and prefix expiration are
@@ -1033,9 +1033,9 @@ nd6_free(struct llentry *ln, int gc)
* XXX: the check for ln_state would be redundant,
* but we intentionally keep it just in case.
*/
- if (dr->expire > time_second)
+ if (dr->expire > time_uptime)
nd6_llinfo_settimer_locked(ln,
- (dr->expire - time_second) * hz);
+ (dr->expire - time_uptime) * hz);
else
nd6_llinfo_settimer_locked(ln,
(long)V_nd6_gctimer * hz);
diff --git a/sys/netinet6/nd6_rtr.c b/sys/netinet6/nd6_rtr.c
index 03d06b4..0c8b587 100644
--- a/sys/netinet6/nd6_rtr.c
+++ b/sys/netinet6/nd6_rtr.c
@@ -282,7 +282,7 @@ nd6_ra_input(struct mbuf *m, int off, int icmp6len)
dr0.rtlifetime = 0;
else
dr0.rtlifetime = ntohs(nd_ra->nd_ra_router_lifetime);
- dr0.expire = time_second + dr0.rtlifetime;
+ dr0.expire = time_uptime + dr0.rtlifetime;
dr0.ifp = ifp;
/* unspecified or not? (RFC 2461 6.3.4) */
if (advreachable) {
@@ -874,7 +874,7 @@ nd6_prelist_add(struct nd_prefixctl *pr, struct nd_defrouter *dr,
free(new, M_IP6NDP);
return(error);
}
- new->ndpr_lastupdate = time_second;
+ new->ndpr_lastupdate = time_uptime;
if (newp != NULL)
*newp = new;
@@ -998,7 +998,7 @@ prelist_update(struct nd_prefixctl *new, struct nd_defrouter *dr,
pr->ndpr_vltime = new->ndpr_vltime;
pr->ndpr_pltime = new->ndpr_pltime;
(void)in6_init_prefix_ltimes(pr); /* XXX error case? */
- pr->ndpr_lastupdate = time_second;
+ pr->ndpr_lastupdate = time_uptime;
}
if (new->ndpr_raf_onlink &&
@@ -1136,7 +1136,7 @@ prelist_update(struct nd_prefixctl *new, struct nd_defrouter *dr,
if (lt6_tmp.ia6t_vltime == ND6_INFINITE_LIFETIME)
remaininglifetime = ND6_INFINITE_LIFETIME;
- else if (time_second - ifa6->ia6_updatetime >
+ else if (time_uptime - ifa6->ia6_updatetime >
lt6_tmp.ia6t_vltime) {
/*
* The case of "invalid" address. We should usually
@@ -1145,7 +1145,7 @@ prelist_update(struct nd_prefixctl *new, struct nd_defrouter *dr,
remaininglifetime = 0;
} else
remaininglifetime = lt6_tmp.ia6t_vltime -
- (time_second - ifa6->ia6_updatetime);
+ (time_uptime - ifa6->ia6_updatetime);
/* when not updating, keep the current stored lifetime. */
lt6_tmp.ia6t_vltime = remaininglifetime;
@@ -1181,18 +1181,18 @@ prelist_update(struct nd_prefixctl *new, struct nd_defrouter *dr,
u_int32_t maxvltime, maxpltime;
if (V_ip6_temp_valid_lifetime >
- (u_int32_t)((time_second - ifa6->ia6_createtime) +
+ (u_int32_t)((time_uptime - ifa6->ia6_createtime) +
V_ip6_desync_factor)) {
maxvltime = V_ip6_temp_valid_lifetime -
- (time_second - ifa6->ia6_createtime) -
+ (time_uptime - ifa6->ia6_createtime) -
V_ip6_desync_factor;
} else
maxvltime = 0;
if (V_ip6_temp_preferred_lifetime >
- (u_int32_t)((time_second - ifa6->ia6_createtime) +
+ (u_int32_t)((time_uptime - ifa6->ia6_createtime) +
V_ip6_desync_factor)) {
maxpltime = V_ip6_temp_preferred_lifetime -
- (time_second - ifa6->ia6_createtime) -
+ (time_uptime - ifa6->ia6_createtime) -
V_ip6_desync_factor;
} else
maxpltime = 0;
@@ -1207,7 +1207,7 @@ prelist_update(struct nd_prefixctl *new, struct nd_defrouter *dr,
}
}
ifa6->ia6_lifetime = lt6_tmp;
- ifa6->ia6_updatetime = time_second;
+ ifa6->ia6_updatetime = time_uptime;
}
IF_ADDR_RUNLOCK(ifp);
if (ia6_match == NULL && new->ndpr_vltime) {
@@ -1988,7 +1988,7 @@ in6_tmpifadd(const struct in6_ifaddr *ia0, int forcegen, int delay)
if (ia0->ia6_lifetime.ia6t_vltime != ND6_INFINITE_LIFETIME) {
vltime0 = IFA6_IS_INVALID(ia0) ? 0 :
(ia0->ia6_lifetime.ia6t_vltime -
- (time_second - ia0->ia6_updatetime));
+ (time_uptime - ia0->ia6_updatetime));
if (vltime0 > V_ip6_temp_valid_lifetime)
vltime0 = V_ip6_temp_valid_lifetime;
} else
@@ -1996,7 +1996,7 @@ in6_tmpifadd(const struct in6_ifaddr *ia0, int forcegen, int delay)
if (ia0->ia6_lifetime.ia6t_pltime != ND6_INFINITE_LIFETIME) {
pltime0 = IFA6_IS_DEPRECATED(ia0) ? 0 :
(ia0->ia6_lifetime.ia6t_pltime -
- (time_second - ia0->ia6_updatetime));
+ (time_uptime - ia0->ia6_updatetime));
if (pltime0 > V_ip6_temp_preferred_lifetime - V_ip6_desync_factor){
pltime0 = V_ip6_temp_preferred_lifetime -
V_ip6_desync_factor;
@@ -2054,11 +2054,11 @@ in6_init_prefix_ltimes(struct nd_prefix *ndpr)
if (ndpr->ndpr_pltime == ND6_INFINITE_LIFETIME)
ndpr->ndpr_preferred = 0;
else
- ndpr->ndpr_preferred = time_second + ndpr->ndpr_pltime;
+ ndpr->ndpr_preferred = time_uptime + ndpr->ndpr_pltime;
if (ndpr->ndpr_vltime == ND6_INFINITE_LIFETIME)
ndpr->ndpr_expire = 0;
else
- ndpr->ndpr_expire = time_second + ndpr->ndpr_vltime;
+ ndpr->ndpr_expire = time_uptime + ndpr->ndpr_vltime;
return 0;
}
@@ -2070,7 +2070,7 @@ in6_init_address_ltimes(struct nd_prefix *new, struct in6_addrlifetime *lt6)
if (lt6->ia6t_vltime == ND6_INFINITE_LIFETIME)
lt6->ia6t_expire = 0;
else {
- lt6->ia6t_expire = time_second;
+ lt6->ia6t_expire = time_uptime;
lt6->ia6t_expire += lt6->ia6t_vltime;
}
@@ -2078,7 +2078,7 @@ in6_init_address_ltimes(struct nd_prefix *new, struct in6_addrlifetime *lt6)
if (lt6->ia6t_pltime == ND6_INFINITE_LIFETIME)
lt6->ia6t_preferred = 0;
else {
- lt6->ia6t_preferred = time_second;
+ lt6->ia6t_preferred = time_uptime;
lt6->ia6t_preferred += lt6->ia6t_pltime;
}
}
diff --git a/sys/sys/param.h b/sys/sys/param.h
index 20fa2c8..d425fdc 100644
--- a/sys/sys/param.h
+++ b/sys/sys/param.h
@@ -58,7 +58,7 @@
* in the range 5 to 9.
*/
#undef __FreeBSD_version
-#define __FreeBSD_version 1000040 /* Master, propagated to newvers */
+#define __FreeBSD_version 1000041 /* Master, propagated to newvers */
/*
* __FreeBSD_kernel__ indicates that this system uses the kernel of FreeBSD,
diff --git a/usr.sbin/ndp/ndp.c b/usr.sbin/ndp/ndp.c
index 0449c12..ae1fbca 100644
--- a/usr.sbin/ndp/ndp.c
+++ b/usr.sbin/ndp/ndp.c
@@ -79,7 +79,6 @@
#include <sys/ioctl.h>
#include <sys/socket.h>
#include <sys/sysctl.h>
-#include <sys/time.h>
#include <sys/queue.h>
#include <net/if.h>
@@ -105,6 +104,7 @@
#include <paths.h>
#include <err.h>
#include <stdlib.h>
+#include <time.h>
#include <fcntl.h>
#include <unistd.h>
#include "gmt2local.h"
@@ -125,6 +125,7 @@ static int tflag;
static int32_t thiszone; /* time difference with gmt */
static int s = -1;
static int repeat = 0;
+static struct timespec ts, ts0;
char ntop_buf[INET6_ADDRSTRLEN]; /* inet_ntop() */
char host_buf[NI_MAXHOST]; /* getnameinfo() */
@@ -153,7 +154,7 @@ static void getdefif(void);
static void setdefif(char *);
#endif
static char *sec2str(time_t);
-static void ts_print(const struct timeval *);
+static void ts_print(const struct timespec *);
#ifdef ICMPV6CTL_ND6_DRLIST
static char *rtpref_str[] = {
@@ -164,6 +165,16 @@ static char *rtpref_str[] = {
};
#endif
+#define TS_SUB(tsp, usp, vsp) \
+ do { \
+ (vsp)->tv_sec = (tsp)->tv_sec - (usp)->tv_sec; \
+ (vsp)->tv_nsec = (tsp)->tv_nsec - (usp)->tv_nsec; \
+ if ((vsp)->tv_nsec < 0) { \
+ (vsp)->tv_sec--; \
+ (vsp)->tv_nsec += 1000000000L; \
+ } \
+ } while (0)
+
int mode = 0;
char *arg = NULL;
@@ -172,10 +183,14 @@ main(argc, argv)
int argc;
char **argv;
{
+ struct timespec now;
int ch;
pid = getpid();
thiszone = gmt2local(0);
+ clock_gettime(CLOCK_REALTIME_FAST, &now);
+ clock_gettime(CLOCK_MONOTONIC_FAST, &ts);
+ TS_SUB(&now, &ts, &ts0);
while ((ch = getopt(argc, argv, "acd:f:Ii:nprstA:HPR")) != -1)
switch (ch) {
case 'a':
@@ -367,7 +382,8 @@ getsocket()
struct sockaddr_in6 so_mask = {sizeof(so_mask), AF_INET6 };
struct sockaddr_in6 blank_sin = {sizeof(blank_sin), AF_INET6 }, sin_m;
struct sockaddr_dl blank_sdl = {sizeof(blank_sdl), AF_LINK }, sdl_m;
-int expire_time, flags, found_entry;
+static time_t expire_time;
+static int flags, found_entry;
struct {
struct rt_msghdr m_rtm;
char m_space[512];
@@ -412,10 +428,10 @@ set(argc, argv)
flags = expire_time = 0;
while (argc-- > 0) {
if (strncmp(argv[0], "temp", 4) == 0) {
- struct timeval time;
+ struct timespec now;
- gettimeofday(&time, 0);
- expire_time = time.tv_sec + 20 * 60;
+ clock_gettime(CLOCK_MONOTONIC_FAST, &now);
+ expire_time = now.tv_sec + 20 * 60;
} else if (strncmp(argv[0], "proxy", 5) == 0)
flags |= RTF_ANNOUNCE;
argv++;
@@ -566,7 +582,7 @@ dump(addr, cflag)
struct sockaddr_dl *sdl;
extern int h_errno;
struct in6_nbrinfo *nbi;
- struct timeval time;
+ struct timespec now;
int addrwidth;
int llwidth;
int ifwidth;
@@ -653,9 +669,9 @@ again:;
#endif
continue;
}
- gettimeofday(&time, 0);
+ clock_gettime(CLOCK_MONOTONIC_FAST, &now);
if (tflag)
- ts_print(&time);
+ ts_print(&now);
addrwidth = strlen(host_buf);
if (addrwidth < W_ADDR)
@@ -676,9 +692,9 @@ again:;
/* Print neighbor discovery specific informations */
nbi = getnbrinfo(&sin->sin6_addr, sdl->sdl_index, 1);
if (nbi) {
- if (nbi->expire > time.tv_sec) {
+ if (nbi->expire > now.tv_sec) {
printf(" %-9.9s",
- sec2str(nbi->expire - time.tv_sec));
+ sec2str(nbi->expire - now.tv_sec));
} else if (nbi->expire == 0)
printf(" %-9.9s", "permanent");
else
@@ -1075,7 +1091,7 @@ rtrlist()
char *buf;
struct in6_defrouter *p, *ep;
size_t l;
- struct timeval time;
+ struct timespec now;
if (sysctl(mib, sizeof(mib) / sizeof(mib[0]), NULL, &l, NULL, 0) < 0) {
err(1, "sysctl(ICMPV6CTL_ND6_DRLIST)");
@@ -1110,18 +1126,18 @@ rtrlist()
rtpref = ((p->flags & ND_RA_FLAG_RTPREF_MASK) >> 3) & 0xff;
printf(", pref=%s", rtpref_str[rtpref]);
- gettimeofday(&time, 0);
+ clock_gettime(CLOCK_MONOTONIC_FAST, &now);
if (p->expire == 0)
printf(", expire=Never\n");
else
printf(", expire=%s\n",
- sec2str(p->expire - time.tv_sec));
+ sec2str(p->expire - now.tv_sec));
}
free(buf);
#else
struct in6_drlist dr;
int s, i;
- struct timeval time;
+ struct timespec now;
if ((s = socket(AF_INET6, SOCK_DGRAM, 0)) < 0) {
err(1, "socket");
@@ -1150,12 +1166,12 @@ rtrlist()
printf(", flags=%s%s",
DR.flags & ND_RA_FLAG_MANAGED ? "M" : "",
DR.flags & ND_RA_FLAG_OTHER ? "O" : "");
- gettimeofday(&time, 0);
+ clock_gettime(CLOCK_MONOTONIC_FAST, &now);
if (DR.expire == 0)
printf(", expire=Never\n");
else
printf(", expire=%s\n",
- sec2str(DR.expire - time.tv_sec));
+ sec2str(DR.expire - now.tv_sec));
}
#undef DR
close(s);
@@ -1171,7 +1187,7 @@ plist()
struct in6_prefix *p, *ep, *n;
struct sockaddr_in6 *advrtr;
size_t l;
- struct timeval time;
+ struct timespec now;
const int niflags = NI_NUMERICHOST;
int ninflags = nflag ? NI_NUMERICHOST : 0;
char namebuf[NI_MAXHOST];
@@ -1202,7 +1218,7 @@ plist()
printf("%s/%d if=%s\n", namebuf, p->prefixlen,
if_indextoname(p->if_index, ifix_buf));
- gettimeofday(&time, 0);
+ clock_gettime(CLOCK_MONOTONIC_FAST, &now);
/*
* meaning of fields, especially flags, is very different
* by origin. notify the difference to the users.
@@ -1228,9 +1244,9 @@ plist()
printf(", pltime=%lu", (unsigned long)p->pltime);
if (p->expire == 0)
printf(", expire=Never");
- else if (p->expire >= time.tv_sec)
+ else if (p->expire >= now.tv_sec)
printf(", expire=%s",
- sec2str(p->expire - time.tv_sec));
+ sec2str(p->expire - now.tv_sec));
else
printf(", expired");
printf(", ref=%d", p->refcnt);
@@ -1278,9 +1294,9 @@ plist()
#else
struct in6_prlist pr;
int s, i;
- struct timeval time;
+ struct timespec now;
- gettimeofday(&time, 0);
+ clock_gettime(CLOCK_MONOTONIC_FAST, &now);
if ((s = socket(AF_INET6, SOCK_DGRAM, 0)) < 0) {
err(1, "socket");
@@ -1316,7 +1332,7 @@ plist()
printf("%s/%d if=%s\n", namebuf, PR.prefixlen,
if_indextoname(PR.if_index, ifix_buf));
- gettimeofday(&time, 0);
+ clock_gettime(CLOCK_MONOTONIC_FAST, &now);
/*
* meaning of fields, especially flags, is very different
* by origin. notify the difference to the users.
@@ -1352,9 +1368,9 @@ plist()
printf(", pltime=%lu", PR.pltime);
if (PR.expire == 0)
printf(", expire=Never");
- else if (PR.expire >= time.tv_sec)
+ else if (PR.expire >= now.tv_sec)
printf(", expire=%s",
- sec2str(PR.expire - time.tv_sec));
+ sec2str(PR.expire - now.tv_sec));
else
printf(", expired");
#ifdef NDPRF_ONLINK
@@ -1577,15 +1593,15 @@ sec2str(total)
* from tcpdump/util.c
*/
static void
-ts_print(tvp)
- const struct timeval *tvp;
+ts_print(tsp)
+ const struct timespec *tsp;
{
int s;
/* Default */
- s = (tvp->tv_sec + thiszone) % 86400;
+ s = (tsp->tv_sec + thiszone + ts0.tv_sec) % 86400;
(void)printf("%02d:%02d:%02d.%06u ",
- s / 3600, (s % 3600) / 60, s % 60, (u_int32_t)tvp->tv_usec);
+ s / 3600, (s % 3600) / 60, s % 60, (u_int32_t)tsp->tv_nsec / 1000);
}
#undef NEXTADDR
diff --git a/usr.sbin/rtadvctl/rtadvctl.c b/usr.sbin/rtadvctl/rtadvctl.c
index adc87b5..3f22518 100644
--- a/usr.sbin/rtadvctl/rtadvctl.c
+++ b/usr.sbin/rtadvctl/rtadvctl.c
@@ -55,6 +55,7 @@
#include <stdlib.h>
#include <stdarg.h>
#include <syslog.h>
+#include <time.h>
#include <err.h>
#include "pathnames.h"
@@ -416,6 +417,7 @@ action_show(int argc, char **argv)
char argv_dnssl[IFNAMSIZ + sizeof(":dnssl=")];
char ssbuf[SSBUFLEN];
+ struct timespec now, ts0, ts;
struct ctrl_msg_pl cp;
struct ifinfo *ifi;
TAILQ_HEAD(, ifinfo) ifl = TAILQ_HEAD_INITIALIZER(ifl);
@@ -464,6 +466,10 @@ action_show(int argc, char **argv)
}
}
+ clock_gettime(CLOCK_REALTIME_FAST, &now);
+ clock_gettime(CLOCK_MONOTONIC_FAST, &ts);
+ TS_SUB(&now, &ts, &ts0);
+
TAILQ_FOREACH(ifi, &ifl, ifi_next) {
struct ifinfo *ifi_s;
struct rtadvd_timer *rat;
@@ -615,12 +621,20 @@ action_show(int argc, char **argv)
rat = (struct rtadvd_timer *)cp.cp_val;
}
- printf("\tNext RA send: %s",
- (rat == NULL) ? "never\n" :
- ctime((time_t *)&rat->rat_tm.tv_sec));
- printf("\tLast RA sent: %s",
- (ifi_s->ifi_ra_lastsent.tv_sec == 0) ? "never\n" :
- ctime((time_t *)&ifi_s->ifi_ra_lastsent.tv_sec));
+ printf("\tNext RA send: ");
+ if (rat == NULL)
+ printf("never\n");
+ else {
+ ts.tv_sec = rat->rat_tm.tv_sec + ts0.tv_sec;
+ printf("%s", ctime(&ts.tv_sec));
+ }
+ printf("\tLast RA send: ");
+ if (ifi_s->ifi_ra_lastsent.tv_sec == 0)
+ printf("never\n");
+ else {
+ ts.tv_sec = ifi_s->ifi_ra_lastsent.tv_sec + ts0.tv_sec;
+ printf("%s", ctime(&ts.tv_sec));
+ }
if (rai->rai_clockskew)
printf("\tClock skew: %" PRIu16 "sec\n",
rai->rai_clockskew);
@@ -747,9 +761,9 @@ action_show_prefix(struct prefix *pfx)
{
char ntopbuf[INET6_ADDRSTRLEN];
char ssbuf[SSBUFLEN];
- struct timeval now;
+ struct timespec now;
- gettimeofday(&now, NULL);
+ clock_gettime(CLOCK_MONOTONIC_FAST, &now);
printf("\t %s/%d", inet_ntop(AF_INET6, &pfx->pfx_prefix,
ntopbuf, sizeof(ntopbuf)), pfx->pfx_prefixlen);
@@ -800,7 +814,7 @@ action_show_prefix(struct prefix *pfx)
printf("<none>");
if (pfx->pfx_timer) {
- struct timeval *rest;
+ struct timespec *rest;
rest = rtadvd_timer_rest(pfx->pfx_timer);
if (rest) { /* XXX: what if not? */
diff --git a/usr.sbin/rtadvd/config.c b/usr.sbin/rtadvd/config.c
index d10829a..bb4aaec 100644
--- a/usr.sbin/rtadvd/config.c
+++ b/usr.sbin/rtadvd/config.c
@@ -34,7 +34,6 @@
#include <sys/param.h>
#include <sys/ioctl.h>
#include <sys/socket.h>
-#include <sys/time.h>
#include <net/if.h>
#include <net/if_var.h>
@@ -58,6 +57,7 @@
#include <string.h>
#include <search.h>
#include <stdlib.h>
+#include <time.h>
#include <unistd.h>
#include <ifaddrs.h>
@@ -563,8 +563,9 @@ getconfig(struct ifinfo *ifi)
makeentry(entbuf, sizeof(entbuf), i, "vltimedecr");
if (agetflag(entbuf)) {
- struct timeval now;
- gettimeofday(&now, 0);
+ struct timespec now;
+
+ clock_gettime(CLOCK_MONOTONIC_FAST, &now);
pfx->pfx_vltimeexpire =
now.tv_sec + pfx->pfx_validlifetime;
}
@@ -583,8 +584,9 @@ getconfig(struct ifinfo *ifi)
makeentry(entbuf, sizeof(entbuf), i, "pltimedecr");
if (agetflag(entbuf)) {
- struct timeval now;
- gettimeofday(&now, 0);
+ struct timespec now;
+
+ clock_gettime(CLOCK_MONOTONIC_FAST, &now);
pfx->pfx_pltimeexpire =
now.tv_sec + pfx->pfx_preflifetime;
}
@@ -1164,7 +1166,7 @@ delete_prefix(struct prefix *pfx)
void
invalidate_prefix(struct prefix *pfx)
{
- struct timeval timo;
+ struct timespec timo;
struct rainfo *rai;
struct ifinfo *ifi;
char ntopbuf[INET6_ADDRSTRLEN];
@@ -1191,7 +1193,7 @@ invalidate_prefix(struct prefix *pfx)
delete_prefix(pfx);
}
timo.tv_sec = prefix_timo;
- timo.tv_usec = 0;
+ timo.tv_nsec = 0;
rtadvd_set_timer(&timo, pfx->pfx_timer);
}
@@ -1415,7 +1417,7 @@ make_packet(struct rainfo *rai)
TAILQ_FOREACH(pfx, &rai->rai_prefix, pfx_next) {
uint32_t vltime, pltime;
- struct timeval now;
+ struct timespec now;
ndopt_pi = (struct nd_opt_prefix_info *)buf;
ndopt_pi->nd_opt_pi_type = ND_OPT_PREFIX_INFORMATION;
@@ -1432,7 +1434,7 @@ make_packet(struct rainfo *rai)
vltime = 0;
else {
if (pfx->pfx_vltimeexpire || pfx->pfx_pltimeexpire)
- gettimeofday(&now, NULL);
+ clock_gettime(CLOCK_MONOTONIC_FAST, &now);
if (pfx->pfx_vltimeexpire == 0)
vltime = pfx->pfx_validlifetime;
else
diff --git a/usr.sbin/rtadvd/rrenum.c b/usr.sbin/rtadvd/rrenum.c
index a8fbbf2..0c97d98 100644
--- a/usr.sbin/rtadvd/rrenum.c
+++ b/usr.sbin/rtadvd/rrenum.c
@@ -49,6 +49,7 @@
#include <netdb.h>
#include <string.h>
#include <stdlib.h>
+#include <time.h>
#include <syslog.h>
#include "rtadvd.h"
#include "rrenum.h"
@@ -215,7 +216,7 @@ do_use_prefix(int len, struct rr_pco_match *rpm,
rai = ifi->ifi_rainfo;
TAILQ_FOREACH(pfx, &rai->rai_prefix, pfx_next) {
- struct timeval now;
+ struct timespec now;
if (prefix_match(&pfx->pfx_prefix,
pfx->pfx_prefixlen, &rpm->rpm_prefix,
@@ -226,14 +227,16 @@ do_use_prefix(int len, struct rr_pco_match *rpm,
pfx->pfx_preflifetime =
ntohl(rpu->rpu_pltime);
if (irr->irr_rrf_decrvalid) {
- gettimeofday(&now, 0);
+ clock_gettime(CLOCK_MONOTONIC_FAST,
+ &now);
pfx->pfx_vltimeexpire =
now.tv_sec +
pfx->pfx_validlifetime;
} else
pfx->pfx_vltimeexpire = 0;
if (irr->irr_rrf_decrprefd) {
- gettimeofday(&now, 0);
+ clock_gettime(CLOCK_MONOTONIC_FAST,
+ &now);
pfx->pfx_pltimeexpire =
now.tv_sec +
pfx->pfx_preflifetime;
diff --git a/usr.sbin/rtadvd/rtadvd.c b/usr.sbin/rtadvd/rtadvd.c
index c3420ef..ba71954 100644
--- a/usr.sbin/rtadvd/rtadvd.c
+++ b/usr.sbin/rtadvd/rtadvd.c
@@ -35,7 +35,6 @@
#include <sys/ioctl.h>
#include <sys/socket.h>
#include <sys/uio.h>
-#include <sys/time.h>
#include <sys/queue.h>
#include <sys/stat.h>
#include <sys/sysctl.h>
@@ -179,7 +178,7 @@ int
main(int argc, char *argv[])
{
struct pollfd set[PFD_MAX];
- struct timeval *timeout;
+ struct timespec *timeout;
int i, ch;
int fflag = 0, logopt;
int error;
@@ -331,7 +330,7 @@ main(int argc, char *argv[])
"<%s> set timer to %ld:%ld. waiting for "
"inputs or timeout", __func__,
(long int)timeout->tv_sec,
- (long int)timeout->tv_usec);
+ (long int)timeout->tv_nsec / 1000);
} else {
syslog(LOG_DEBUG,
"<%s> there's no timer. waiting for inputs",
@@ -339,7 +338,7 @@ main(int argc, char *argv[])
}
if ((i = poll(set, sizeof(set)/sizeof(set[0]),
timeout ? (timeout->tv_sec * 1000 +
- timeout->tv_usec / 1000) : INFTIM)) < 0) {
+ timeout->tv_nsec / 1000 / 1000) : INFTIM)) < 0) {
/* EINTR would occur if a signal was delivered */
if (errno != EINTR)
@@ -432,7 +431,7 @@ rtadvd_shutdown(void)
if (ifi->ifi_ra_timer == NULL)
continue;
if (ifi->ifi_ra_lastsent.tv_sec == 0 &&
- ifi->ifi_ra_lastsent.tv_usec == 0 &&
+ ifi->ifi_ra_lastsent.tv_nsec == 0 &&
ifi->ifi_ra_timer != NULL) {
/*
* When RA configured but never sent,
@@ -1006,7 +1005,7 @@ static void
set_short_delay(struct ifinfo *ifi)
{
long delay; /* must not be greater than 1000000 */
- struct timeval interval, now, min_delay, tm_tmp, *rest;
+ struct timespec interval, now, min_delay, tm_tmp, *rest;
if (ifi->ifi_ra_timer == NULL)
return;
@@ -1023,9 +1022,9 @@ set_short_delay(struct ifinfo *ifi)
delay = random() % MAX_RA_DELAY_TIME;
#endif
interval.tv_sec = 0;
- interval.tv_usec = delay;
+ interval.tv_nsec = delay * 1000;
rest = rtadvd_timer_rest(ifi->ifi_ra_timer);
- if (TIMEVAL_LT(rest, &interval)) {
+ if (TS_CMP(rest, &interval, <)) {
syslog(LOG_DEBUG, "<%s> random delay is larger than "
"the rest of the current timer", __func__);
interval = *rest;
@@ -1038,13 +1037,13 @@ set_short_delay(struct ifinfo *ifi)
* MIN_DELAY_BETWEEN_RAS plus the random value after the
* previous advertisement was sent.
*/
- gettimeofday(&now, NULL);
- TIMEVAL_SUB(&now, &ifi->ifi_ra_lastsent, &tm_tmp);
+ clock_gettime(CLOCK_MONOTONIC_FAST, &now);
+ TS_SUB(&now, &ifi->ifi_ra_lastsent, &tm_tmp);
min_delay.tv_sec = MIN_DELAY_BETWEEN_RAS;
- min_delay.tv_usec = 0;
- if (TIMEVAL_LT(&tm_tmp, &min_delay)) {
- TIMEVAL_SUB(&min_delay, &tm_tmp, &min_delay);
- TIMEVAL_ADD(&min_delay, &interval, &interval);
+ min_delay.tv_nsec = 0;
+ if (TS_CMP(&tm_tmp, &min_delay, <)) {
+ TS_SUB(&min_delay, &tm_tmp, &min_delay);
+ TS_ADD(&min_delay, &interval, &interval);
}
rtadvd_set_timer(&interval, ifi->ifi_ra_timer);
}
@@ -1242,7 +1241,7 @@ prefix_check(struct nd_opt_prefix_info *pinfo,
int inconsistent = 0;
char ntopbuf[INET6_ADDRSTRLEN];
char prefixbuf[INET6_ADDRSTRLEN];
- struct timeval now;
+ struct timespec now;
#if 0 /* impossible */
if (pinfo->nd_opt_pi_type != ND_OPT_PREFIX_INFORMATION)
@@ -1285,7 +1284,7 @@ prefix_check(struct nd_opt_prefix_info *pinfo,
* XXX: can we really expect that all routers on the link
* have synchronized clocks?
*/
- gettimeofday(&now, NULL);
+ clock_gettime(CLOCK_MONOTONIC_FAST, &now);
preferred_time += now.tv_sec;
if (!pfx->pfx_timer && rai->rai_clockskew &&
@@ -1318,7 +1317,7 @@ prefix_check(struct nd_opt_prefix_info *pinfo,
valid_time = ntohl(pinfo->nd_opt_pi_valid_time);
if (pfx->pfx_vltimeexpire) {
- gettimeofday(&now, NULL);
+ clock_gettime(CLOCK_MONOTONIC_FAST, &now);
valid_time += now.tv_sec;
if (!pfx->pfx_timer && rai->rai_clockskew &&
@@ -1784,7 +1783,7 @@ ra_output(struct ifinfo *ifi)
}
/* update timestamp */
- gettimeofday(&ifi->ifi_ra_lastsent, NULL);
+ clock_gettime(CLOCK_MONOTONIC_FAST, &ifi->ifi_ra_lastsent);
/* update counter */
ifi->ifi_rs_waitcount = 0;
@@ -1866,7 +1865,7 @@ ra_timeout(void *arg)
/* update RA timer */
void
-ra_timer_update(void *arg, struct timeval *tm)
+ra_timer_update(void *arg, struct timespec *tm)
{
uint16_t interval;
struct rainfo *rai;
@@ -1916,12 +1915,12 @@ ra_timer_update(void *arg, struct timeval *tm)
}
tm->tv_sec = interval;
- tm->tv_usec = 0;
+ tm->tv_nsec = 0;
syslog(LOG_DEBUG,
"<%s> RA timer on %s is set to %ld:%ld",
__func__, ifi->ifi_ifname,
- (long int)tm->tv_sec, (long int)tm->tv_usec);
+ (long int)tm->tv_sec, (long int)tm->tv_nsec / 1000);
return;
}
diff --git a/usr.sbin/rtadvd/rtadvd.h b/usr.sbin/rtadvd/rtadvd.h
index ac8ce99..e7ed87f 100644
--- a/usr.sbin/rtadvd/rtadvd.h
+++ b/usr.sbin/rtadvd/rtadvd.h
@@ -270,7 +270,7 @@ struct ifinfo {
uint32_t ifi_burstinterval;
struct rtadvd_timer *ifi_ra_timer;
/* timestamp when the latest RA was sent */
- struct timeval ifi_ra_lastsent;
+ struct timespec ifi_ra_lastsent;
uint16_t ifi_rs_waitcount;
/* statistics */
@@ -286,7 +286,7 @@ extern TAILQ_HEAD(ifilist_head_t, ifinfo) ifilist;
extern char *mcastif;
struct rtadvd_timer *ra_timeout(void *);
-void ra_timer_update(void *, struct timeval *);
+void ra_timer_update(void *, struct timespec *);
void ra_output(struct ifinfo *);
int prefix_match(struct in6_addr *, int,
diff --git a/usr.sbin/rtadvd/timer.c b/usr.sbin/rtadvd/timer.c
index 2ea77b5..faa541d 100644
--- a/usr.sbin/rtadvd/timer.c
+++ b/usr.sbin/rtadvd/timer.c
@@ -31,7 +31,6 @@
* SUCH DAMAGE.
*/
-#include <sys/time.h>
#include <sys/queue.h>
#include <sys/socket.h>
@@ -44,6 +43,7 @@
#include <stdlib.h>
#include <string.h>
#include <search.h>
+#include <time.h>
#include <netdb.h>
#include "rtadvd.h"
@@ -52,12 +52,17 @@
struct rtadvd_timer_head_t ra_timer =
TAILQ_HEAD_INITIALIZER(ra_timer);
-static struct timeval tm_limit = {0x7fffffff, 0x7fffffff};
-static struct timeval tm_max;
+static struct timespec tm_limit;
+static struct timespec tm_max;
void
rtadvd_timer_init(void)
{
+ /* Generate maximum time in timespec. */
+ memset(&tm_limit.tv_sec, 0xff, sizeof(tm_limit.tv_sec));
+ memset(&tm_limit.tv_nsec, 0xff, sizeof(tm_limit.tv_nsec));
+ tm_limit.tv_sec &= ~(1UL << (sizeof(tm_limit.tv_sec) * 8 - 1));
+ tm_limit.tv_nsec &= ~(1UL << (sizeof(tm_limit.tv_nsec) * 8 - 1));
tm_max = tm_limit;
TAILQ_INIT(&ra_timer);
@@ -102,7 +107,7 @@ rtadvd_update_timeout_handler(void)
struct rtadvd_timer *
rtadvd_add_timer(struct rtadvd_timer *(*timeout)(void *),
- void (*update)(void *, struct timeval *),
+ void (*update)(void *, struct timespec *),
void *timeodata, void *updatedata)
{
struct rtadvd_timer *rat;
@@ -149,48 +154,48 @@ rtadvd_remove_timer(struct rtadvd_timer *rat)
* call the expire function for the timer and update the timer.
* Return the next interval for select() call.
*/
-struct timeval *
+struct timespec *
rtadvd_check_timer(void)
{
- static struct timeval returnval;
- struct timeval now;
+ static struct timespec returnval;
+ struct timespec now;
struct rtadvd_timer *rat;
- gettimeofday(&now, NULL);
+ clock_gettime(CLOCK_MONOTONIC_FAST, &now);
tm_max = tm_limit;
TAILQ_FOREACH(rat, &ra_timer, rat_next) {
- if (TIMEVAL_LEQ(&rat->rat_tm, &now)) {
+ if (TS_CMP(&rat->rat_tm, &now, <=)) {
if (((*rat->rat_expire)(rat->rat_expire_data) == NULL))
continue; /* the timer was removed */
if (rat->rat_update)
(*rat->rat_update)(rat->rat_update_data, &rat->rat_tm);
- TIMEVAL_ADD(&rat->rat_tm, &now, &rat->rat_tm);
+ TS_ADD(&rat->rat_tm, &now, &rat->rat_tm);
}
- if (TIMEVAL_LT(&rat->rat_tm, &tm_max))
+ if (TS_CMP(&rat->rat_tm, &tm_max, <))
tm_max = rat->rat_tm;
}
- if (TIMEVAL_EQUAL(&tm_max, &tm_limit)) {
+ if (TS_CMP(&tm_max, &tm_limit, ==)) {
/* no need to timeout */
return (NULL);
- } else if (TIMEVAL_LT(&tm_max, &now)) {
+ } else if (TS_CMP(&tm_max, &now, <)) {
/* this may occur when the interval is too small */
- returnval.tv_sec = returnval.tv_usec = 0;
+ returnval.tv_sec = returnval.tv_nsec = 0;
} else
- TIMEVAL_SUB(&tm_max, &now, &returnval);
+ TS_SUB(&tm_max, &now, &returnval);
return (&returnval);
}
void
-rtadvd_set_timer(struct timeval *tm, struct rtadvd_timer *rat)
+rtadvd_set_timer(struct timespec *tm, struct rtadvd_timer *rat)
{
- struct timeval now;
+ struct timespec now;
/* reset the timer */
- gettimeofday(&now, NULL);
- TIMEVAL_ADD(&now, tm, &rat->rat_tm);
+ clock_gettime(CLOCK_MONOTONIC_FAST, &now);
+ TS_ADD(&now, tm, &rat->rat_tm);
/* update the next expiration time */
- if (TIMEVAL_LT(&rat->rat_tm, &tm_max))
+ if (TS_CMP(&rat->rat_tm, &tm_max, <))
tm_max = rat->rat_tm;
return;
diff --git a/usr.sbin/rtadvd/timer.h b/usr.sbin/rtadvd/timer.h
index f70e0d1..4498aaf 100644
--- a/usr.sbin/rtadvd/timer.h
+++ b/usr.sbin/rtadvd/timer.h
@@ -35,18 +35,18 @@ struct rtadvd_timer {
TAILQ_ENTRY(rtadvd_timer) rat_next;
struct rainfo *rat_rai;
- struct timeval rat_tm;
+ struct timespec rat_tm;
struct rtadvd_timer *(*rat_expire)(void *);
void *rat_expire_data;
- void (*rat_update)(void *, struct timeval *);
+ void (*rat_update)(void *, struct timespec *);
void *rat_update_data;
};
void rtadvd_timer_init(void);
void rtadvd_update_timeout_handler(void);
struct rtadvd_timer *rtadvd_add_timer(struct rtadvd_timer *(*)(void *),
- void (*)(void *, struct timeval *), void *, void *);
-void rtadvd_set_timer(struct timeval *,
+ void (*)(void *, struct timespec *), void *, void *);
+void rtadvd_set_timer(struct timespec *,
struct rtadvd_timer *);
void rtadvd_remove_timer(struct rtadvd_timer *);
-struct timeval *rtadvd_check_timer(void);
+struct timespec *rtadvd_check_timer(void);
diff --git a/usr.sbin/rtadvd/timer_subr.c b/usr.sbin/rtadvd/timer_subr.c
index 2bebdd3..0ddf0a4 100644
--- a/usr.sbin/rtadvd/timer_subr.c
+++ b/usr.sbin/rtadvd/timer_subr.c
@@ -30,69 +30,34 @@
* SUCH DAMAGE.
*/
-#include <sys/time.h>
#include <sys/queue.h>
#include <sys/socket.h>
#include <syslog.h>
#include <stdio.h>
#include <inttypes.h>
+#include <time.h>
#include "timer.h"
#include "timer_subr.h"
-struct timeval *
+struct timespec *
rtadvd_timer_rest(struct rtadvd_timer *rat)
{
- static struct timeval returnval, now;
+ static struct timespec returnval, now;
- gettimeofday(&now, NULL);
- if (TIMEVAL_LEQ(&rat->rat_tm, &now)) {
+ clock_gettime(CLOCK_MONOTONIC_FAST, &now);
+ if (TS_CMP(&rat->rat_tm, &now, <=)) {
syslog(LOG_DEBUG,
"<%s> a timer must be expired, but not yet",
__func__);
- returnval.tv_sec = returnval.tv_usec = 0;
+ returnval.tv_sec = returnval.tv_nsec = 0;
}
else
- TIMEVAL_SUB(&rat->rat_tm, &now, &returnval);
+ TS_SUB(&rat->rat_tm, &now, &returnval);
return (&returnval);
}
-/* result = a + b */
-void
-TIMEVAL_ADD(struct timeval *a, struct timeval *b, struct timeval *result)
-{
- long l;
-
- if ((l = a->tv_usec + b->tv_usec) < MILLION) {
- result->tv_usec = l;
- result->tv_sec = a->tv_sec + b->tv_sec;
- }
- else {
- result->tv_usec = l - MILLION;
- result->tv_sec = a->tv_sec + b->tv_sec + 1;
- }
-}
-
-/*
- * result = a - b
- * XXX: this function assumes that a >= b.
- */
-void
-TIMEVAL_SUB(struct timeval *a, struct timeval *b, struct timeval *result)
-{
- long l;
-
- if ((l = a->tv_usec - b->tv_usec) >= 0) {
- result->tv_usec = l;
- result->tv_sec = a->tv_sec - b->tv_sec;
- }
- else {
- result->tv_usec = MILLION + l;
- result->tv_sec = a->tv_sec - b->tv_sec - 1;
- }
-}
-
char *
sec2str(uint32_t s, char *buf)
{
diff --git a/usr.sbin/rtadvd/timer_subr.h b/usr.sbin/rtadvd/timer_subr.h
index 9ceddad..32e1bb1 100644
--- a/usr.sbin/rtadvd/timer_subr.h
+++ b/usr.sbin/rtadvd/timer_subr.h
@@ -31,27 +31,29 @@
*/
#define SSBUFLEN 1024
-#define MILLION 1000000
-/* a < b */
-#define TIMEVAL_LT(a, b) \
- (((a)->tv_sec < (b)->tv_sec) || \
- (((a)->tv_sec == (b)->tv_sec) && \
- ((a)->tv_usec < (b)->tv_usec)))
+#define TS_CMP(tsp, usp, cmp) \
+ (((tsp)->tv_sec == (usp)->tv_sec) ? \
+ ((tsp)->tv_nsec cmp (usp)->tv_nsec) : \
+ ((tsp)->tv_sec cmp (usp)->tv_sec))
+#define TS_ADD(tsp, usp, vsp) \
+ do { \
+ (vsp)->tv_sec = (tsp)->tv_sec + (usp)->tv_sec; \
+ (vsp)->tv_nsec = (tsp)->tv_nsec + (usp)->tv_nsec; \
+ if ((vsp)->tv_nsec >= 1000000000L) { \
+ (vsp)->tv_sec++; \
+ (vsp)->tv_nsec -= 1000000000L; \
+ } \
+ } while (0)
+#define TS_SUB(tsp, usp, vsp) \
+ do { \
+ (vsp)->tv_sec = (tsp)->tv_sec - (usp)->tv_sec; \
+ (vsp)->tv_nsec = (tsp)->tv_nsec - (usp)->tv_nsec; \
+ if ((vsp)->tv_nsec < 0) { \
+ (vsp)->tv_sec--; \
+ (vsp)->tv_nsec += 1000000000L; \
+ } \
+ } while (0)
-/* a <= b */
-#define TIMEVAL_LEQ(a, b) \
- (((a)->tv_sec < (b)->tv_sec) || \
- (((a)->tv_sec == (b)->tv_sec) && \
- ((a)->tv_usec <= (b)->tv_usec)))
-
-#define TIMEVAL_EQUAL(a,b) \
- (((a)->tv_sec == (b)->tv_sec) && \
- ((a)->tv_usec == (b)->tv_usec))
-
-struct timeval *rtadvd_timer_rest(struct rtadvd_timer *);
-void TIMEVAL_ADD(struct timeval *, struct timeval *,
- struct timeval *);
-void TIMEVAL_SUB(struct timeval *, struct timeval *,
- struct timeval *);
+struct timespec *rtadvd_timer_rest(struct rtadvd_timer *);
char *sec2str(uint32_t, char *buf);
diff --git a/usr.sbin/rtsold/dump.c b/usr.sbin/rtsold/dump.c
index 52d4b62..ddf0d3c 100644
--- a/usr.sbin/rtsold/dump.c
+++ b/usr.sbin/rtsold/dump.c
@@ -32,7 +32,6 @@
*/
#include <sys/types.h>
-#include <sys/time.h>
#include <sys/socket.h>
#include <sys/queue.h>
@@ -62,10 +61,10 @@ dump_interface_status(void)
struct ifinfo *ifi;
struct rainfo *rai;
struct ra_opt *rao;
- struct timeval now;
+ struct timespec now;
char ntopbuf[INET6_ADDRSTRLEN];
- gettimeofday(&now, NULL);
+ clock_gettime(CLOCK_MONOTONIC_FAST, &now);
TAILQ_FOREACH(ifi, &ifinfo_head, ifi_next) {
fprintf(fp, "Interface %s\n", ifi->ifname);
@@ -87,12 +86,12 @@ dump_interface_status(void)
fprintf(fp, " probes: %d, dadcount = %d\n",
ifi->probes, ifi->dadcount);
if (ifi->timer.tv_sec == tm_max.tv_sec &&
- ifi->timer.tv_usec == tm_max.tv_usec)
+ ifi->timer.tv_nsec == tm_max.tv_nsec)
fprintf(fp, " no timer\n");
else {
fprintf(fp, " timer: interval=%d:%d, expire=%s\n",
(int)ifi->timer.tv_sec,
- (int)ifi->timer.tv_usec,
+ (int)ifi->timer.tv_nsec / 1000,
(ifi->expire.tv_sec < now.tv_sec) ? "expired"
: sec2str(&ifi->expire));
}
@@ -137,7 +136,7 @@ rtsold_dump_file(const char *dumpfile)
}
const char *
-sec2str(const struct timeval *total)
+sec2str(const struct timespec *total)
{
static char result[256];
int days, hours, mins, secs;
@@ -145,14 +144,14 @@ sec2str(const struct timeval *total)
char *p = result;
char *ep = &result[sizeof(result)];
int n;
- struct timeval now;
+ struct timespec now;
time_t tsec;
- gettimeofday(&now, NULL);
+ clock_gettime(CLOCK_MONOTONIC_FAST, &now);
tsec = total->tv_sec;
- tsec += total->tv_usec / 1000000;
+ tsec += total->tv_nsec / 1000 / 1000000;
tsec -= now.tv_sec;
- tsec -= now.tv_usec / 1000000;
+ tsec -= now.tv_nsec / 1000 / 1000000;
days = tsec / 3600 / 24;
hours = (tsec / 3600) % 24;
diff --git a/usr.sbin/rtsold/rtsol.c b/usr.sbin/rtsold/rtsol.c
index 181012c..f7210f6 100644
--- a/usr.sbin/rtsold/rtsol.c
+++ b/usr.sbin/rtsold/rtsol.c
@@ -35,7 +35,6 @@
#include <sys/param.h>
#include <sys/socket.h>
#include <sys/uio.h>
-#include <sys/time.h>
#include <sys/queue.h>
#include <sys/wait.h>
#include <sys/stat.h>
@@ -58,6 +57,7 @@
#include <fcntl.h>
#include <unistd.h>
#include <stdio.h>
+#include <time.h>
#include <err.h>
#include <errno.h>
#include <string.h>
@@ -256,8 +256,8 @@ rtsol_input(int s)
size_t len;
char nsbuf[INET6_ADDRSTRLEN + 1 + IFNAMSIZ + 1];
char dname[NI_MAXHOST];
- struct timeval now;
- struct timeval lifetime;
+ struct timespec now;
+ struct timespec lifetime;
int newent_rai;
int newent_rao;
@@ -376,7 +376,7 @@ rtsol_input(int s)
ifi->otherconfig = 1;
CALL_SCRIPT(OTHER, NULL);
}
- gettimeofday(&now, NULL);
+ clock_gettime(CLOCK_MONOTONIC_FAST, &now);
newent_rai = 0;
rai = find_rainfo(ifi, &from);
if (rai == NULL) {
@@ -472,7 +472,7 @@ rtsol_input(int s)
memset(&lifetime, 0, sizeof(lifetime));
lifetime.tv_sec =
ntohl(rdnss->nd_opt_rdnss_lifetime);
- timeradd(&now, &lifetime, &rao->rao_expire);
+ TS_ADD(&now, &lifetime, &rao->rao_expire);
if (newent_rao)
TAILQ_INSERT_TAIL(&rai->rai_ra_opt,
@@ -531,7 +531,7 @@ rtsol_input(int s)
memset(&lifetime, 0, sizeof(lifetime));
lifetime.tv_sec =
ntohl(dnssl->nd_opt_dnssl_lifetime);
- timeradd(&now, &lifetime, &rao->rao_expire);
+ TS_ADD(&now, &lifetime, &rao->rao_expire);
if (newent_rao)
TAILQ_INSERT_TAIL(&rai->rai_ra_opt,
@@ -574,7 +574,7 @@ ra_opt_handler(struct ifinfo *ifi)
struct ra_opt *rao;
struct rainfo *rai;
struct script_msg *smp1, *smp2, *smp3;
- struct timeval now;
+ struct timespec now;
struct script_msg_head_t sm_rdnss_head =
TAILQ_HEAD_INITIALIZER(sm_rdnss_head);
struct script_msg_head_t sm_dnssl_head =
@@ -584,7 +584,7 @@ ra_opt_handler(struct ifinfo *ifi)
dcount = 0;
dlen = strlen(resstr_sh_prefix) + strlen(resstr_nl);
- gettimeofday(&now, NULL);
+ clock_gettime(CLOCK_MONOTONIC_FAST, &now);
/*
* All options from multiple RAs with the same or different
@@ -595,7 +595,7 @@ ra_opt_handler(struct ifinfo *ifi)
TAILQ_FOREACH(rao, &rai->rai_ra_opt, rao_next) {
switch (rao->rao_type) {
case ND_OPT_RDNSS:
- if (timercmp(&now, &rao->rao_expire, >)) {
+ if (TS_CMP(&now, &rao->rao_expire, >)) {
warnmsg(LOG_INFO, __func__,
"expired rdnss entry: %s",
(char *)rao->rao_msg);
@@ -617,7 +617,7 @@ ra_opt_handler(struct ifinfo *ifi)
break;
case ND_OPT_DNSSL:
- if (timercmp(&now, &rao->rao_expire, >)) {
+ if (TS_CMP(&now, &rao->rao_expire, >)) {
warnmsg(LOG_INFO, __func__,
"expired dnssl entry: %s",
(char *)rao->rao_msg);
diff --git a/usr.sbin/rtsold/rtsold.c b/usr.sbin/rtsold/rtsold.c
index d3d1289..2826c2c 100644
--- a/usr.sbin/rtsold/rtsold.c
+++ b/usr.sbin/rtsold/rtsold.c
@@ -33,7 +33,6 @@
#include <sys/types.h>
#include <sys/ioctl.h>
-#include <sys/time.h>
#include <sys/socket.h>
#include <sys/param.h>
@@ -54,6 +53,7 @@
#include <string.h>
#include <stdlib.h>
#include <stdio.h>
+#include <time.h>
#include <errno.h>
#include <err.h>
#include <stdarg.h>
@@ -68,7 +68,7 @@
#define RTSOL_PIDFILE "/var/run/rtsold.pid";
struct ifinfo *iflist;
-struct timeval tm_max = {0x7fffffff, 0x7fffffff};
+struct timespec tm_max;
static int log_upto = 999;
static int fflag = 0;
@@ -105,7 +105,7 @@ static int ifreconfig(char *);
#endif
static int make_packet(struct ifinfo *);
-static struct timeval *rtsol_check_timer(void);
+static struct timespec *rtsol_check_timer(void);
#ifndef SMALL
static void rtsold_set_dump_file(int);
@@ -116,7 +116,7 @@ int
main(int argc, char **argv)
{
int s, ch, once = 0;
- struct timeval *timeout;
+ struct timespec *timeout;
const char *opts;
#ifdef HAVE_POLL_H
struct pollfd set[2];
@@ -187,6 +187,12 @@ main(int argc, char **argv)
exit(1);
}
+ /* Generate maximum time in timespec. */
+ memset(&tm_max.tv_sec, 0xff, sizeof(tm_max.tv_sec));
+ memset(&tm_max.tv_nsec, 0xff, sizeof(tm_max.tv_nsec));
+ tm_max.tv_sec &= ~(1UL << (sizeof(tm_max.tv_sec) * 8 - 1));
+ tm_max.tv_nsec &= ~(1UL << (sizeof(tm_max.tv_nsec) * 8 - 1));
+
/* set log level */
if (dflag > 1)
log_upto = LOG_DEBUG;
@@ -363,7 +369,7 @@ main(int argc, char **argv)
break;
}
#ifdef HAVE_POLL_H
- e = poll(set, 2, timeout ? (timeout->tv_sec * 1000 + timeout->tv_usec / 1000) : INFTIM);
+ e = poll(set, 2, timeout ? (timeout->tv_sec * 1000 + timeout->tv_nsec / 1000 / 1000) : INFTIM);
#else
e = select(maxfd + 1, selectfdp, NULL, NULL, timeout);
#endif
@@ -603,22 +609,22 @@ make_packet(struct ifinfo *ifi)
return (0);
}
-static struct timeval *
+static struct timespec *
rtsol_check_timer(void)
{
- static struct timeval returnval;
- struct timeval now, rtsol_timer;
+ static struct timespec returnval;
+ struct timespec now, rtsol_timer;
struct ifinfo *ifi;
struct rainfo *rai;
struct ra_opt *rao;
int flags;
- gettimeofday(&now, NULL);
+ clock_gettime(CLOCK_MONOTONIC_FAST, &now);
rtsol_timer = tm_max;
TAILQ_FOREACH(ifi, &ifinfo_head, ifi_next) {
- if (timercmp(&ifi->expire, &now, <=)) {
+ if (TS_CMP(&ifi->expire, &now, <=)) {
warnmsg(LOG_DEBUG, __func__, "timer expiration on %s, "
"state = %d", ifi->ifname, ifi->state);
@@ -711,7 +717,7 @@ rtsol_check_timer(void)
"type=%d, msg=%s, expire=%s",
rao->rao_type, (char *)rao->rao_msg,
sec2str(&rao->rao_expire));
- if (timercmp(&now, &rao->rao_expire,
+ if (TS_CMP(&now, &rao->rao_expire,
>=)) {
warnmsg(LOG_DEBUG, __func__,
"RA expiration timer: "
@@ -728,21 +734,21 @@ rtsol_check_timer(void)
if (expire)
ra_opt_handler(ifi);
}
- if (timercmp(&ifi->expire, &rtsol_timer, <))
+ if (TS_CMP(&ifi->expire, &rtsol_timer, <))
rtsol_timer = ifi->expire;
}
- if (timercmp(&rtsol_timer, &tm_max, ==)) {
+ if (TS_CMP(&rtsol_timer, &tm_max, ==)) {
warnmsg(LOG_DEBUG, __func__, "there is no timer");
return (NULL);
- } else if (timercmp(&rtsol_timer, &now, <))
+ } else if (TS_CMP(&rtsol_timer, &now, <))
/* this may occur when the interval is too small */
- returnval.tv_sec = returnval.tv_usec = 0;
+ returnval.tv_sec = returnval.tv_nsec = 0;
else
- timersub(&rtsol_timer, &now, &returnval);
+ TS_SUB(&rtsol_timer, &now, &returnval);
now.tv_sec += returnval.tv_sec;
- now.tv_usec += returnval.tv_usec;
+ now.tv_nsec += returnval.tv_nsec;
warnmsg(LOG_DEBUG, __func__, "New timer is %s",
sec2str(&now));
@@ -755,7 +761,7 @@ rtsol_timer_update(struct ifinfo *ifi)
#define MILLION 1000000
#define DADRETRY 10 /* XXX: adhoc */
long interval;
- struct timeval now;
+ struct timespec now;
bzero(&ifi->timer, sizeof(ifi->timer));
@@ -783,7 +789,7 @@ rtsol_timer_update(struct ifinfo *ifi)
interval = arc4random_uniform(MAX_RTR_SOLICITATION_DELAY * MILLION);
#endif
ifi->timer.tv_sec = interval / MILLION;
- ifi->timer.tv_usec = interval % MILLION;
+ ifi->timer.tv_nsec = (interval % MILLION) * 1000;
break;
case IFS_PROBE:
if (ifi->probes < MAX_RTR_SOLICITATIONS)
@@ -807,16 +813,16 @@ rtsol_timer_update(struct ifinfo *ifi)
}
/* reset the timer */
- if (timercmp(&ifi->timer, &tm_max, ==)) {
+ if (TS_CMP(&ifi->timer, &tm_max, ==)) {
ifi->expire = tm_max;
warnmsg(LOG_DEBUG, __func__,
"stop timer for %s", ifi->ifname);
} else {
- gettimeofday(&now, NULL);
- timeradd(&now, &ifi->timer, &ifi->expire);
+ clock_gettime(CLOCK_MONOTONIC_FAST, &now);
+ TS_ADD(&now, &ifi->timer, &ifi->expire);
now.tv_sec += ifi->timer.tv_sec;
- now.tv_usec += ifi->timer.tv_usec;
+ now.tv_nsec += ifi->timer.tv_nsec;
warnmsg(LOG_DEBUG, __func__, "set timer for %s to %s",
ifi->ifname, sec2str(&now));
}
diff --git a/usr.sbin/rtsold/rtsold.h b/usr.sbin/rtsold/rtsold.h
index 3ab010f..69f9c35 100644
--- a/usr.sbin/rtsold/rtsold.h
+++ b/usr.sbin/rtsold/rtsold.h
@@ -43,7 +43,7 @@ struct ra_opt {
TAILQ_ENTRY(ra_opt) rao_next;
u_int8_t rao_type;
- struct timeval rao_expire;
+ struct timespec rao_expire;
size_t rao_len;
void *rao_msg;
};
@@ -73,8 +73,8 @@ struct ifinfo {
int state;
int probes;
int dadcount;
- struct timeval timer;
- struct timeval expire;
+ struct timespec timer;
+ struct timespec expire;
int errors; /* # of errors we've got - detect wedge */
#define IFI_DNSOPT_STATE_NOINFO 0
#define IFI_DNSOPT_STATE_RECEIVED 1
@@ -124,8 +124,31 @@ extern TAILQ_HEAD(ifinfo_head_t, ifinfo) ifinfo_head;
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02 }}}
#endif
+#define TS_CMP(tsp, usp, cmp) \
+ (((tsp)->tv_sec == (usp)->tv_sec) ? \
+ ((tsp)->tv_nsec cmp (usp)->tv_nsec) : \
+ ((tsp)->tv_sec cmp (usp)->tv_sec))
+#define TS_ADD(tsp, usp, vsp) \
+ do { \
+ (vsp)->tv_sec = (tsp)->tv_sec + (usp)->tv_sec; \
+ (vsp)->tv_nsec = (tsp)->tv_nsec + (usp)->tv_nsec; \
+ if ((vsp)->tv_nsec >= 1000000000L) { \
+ (vsp)->tv_sec++; \
+ (vsp)->tv_nsec -= 1000000000L; \
+ } \
+ } while (0)
+#define TS_SUB(tsp, usp, vsp) \
+ do { \
+ (vsp)->tv_sec = (tsp)->tv_sec - (usp)->tv_sec; \
+ (vsp)->tv_nsec = (tsp)->tv_nsec - (usp)->tv_nsec; \
+ if ((vsp)->tv_nsec < 0) { \
+ (vsp)->tv_sec--; \
+ (vsp)->tv_nsec += 1000000000L; \
+ } \
+ } while (0)
+
/* rtsold.c */
-extern struct timeval tm_max;
+extern struct timespec tm_max;
extern int dflag;
extern int aflag;
extern int Fflag;
@@ -163,7 +186,7 @@ extern void defrouter_probe(struct ifinfo *);
/* dump.c */
extern void rtsold_dump_file(const char *);
-extern const char *sec2str(const struct timeval *);
+extern const char *sec2str(const struct timespec *);
/* rtsock.c */
extern int rtsock_open(void);
OpenPOWER on IntegriCloud