summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorKenneth R Westerback <krw@cvs.openbsd.org>2012-08-26 23:33:32 +0000
committerKenneth R Westerback <krw@cvs.openbsd.org>2012-08-26 23:33:32 +0000
commitc6dcd37e27207731126e652a1cb1f8777734b6da (patch)
tree104ae4cd3109c7da0f9f807d4cb7c38b4326baa9
parentca9af048616b912f9b274db3f8941db823852133 (diff)
Junk global cur_time, and use time(NULL) or local variables where
time is checked multiple times. Add a set_timeout_interval() function to allow setting a timeout based on an interval from current time. Fixes issues with initial startup where the global cur_time was always old and caused initial DHCPDISCOVER or DHCPREQUEST packets to be sent multiple times. And probably other timeout related oddities. Tested by naddy@
-rw-r--r--sbin/dhclient/clparse.c4
-rw-r--r--sbin/dhclient/dhclient.c42
-rw-r--r--sbin/dhclient/dhcpd.h4
-rw-r--r--sbin/dhclient/dispatch.c14
4 files changed, 39 insertions, 25 deletions
diff --git a/sbin/dhclient/clparse.c b/sbin/dhclient/clparse.c
index 5f361dce498..9119943c496 100644
--- a/sbin/dhclient/clparse.c
+++ b/sbin/dhclient/clparse.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: clparse.c,v 1.39 2012/08/22 00:14:42 tedu Exp $ */
+/* $OpenBSD: clparse.c,v 1.40 2012/08/26 23:33:29 krw Exp $ */
/* Parser for dhclient config and lease files... */
@@ -471,7 +471,7 @@ parse_client_lease_statement(FILE *cfile, int is_static)
* active.
*/
if (client->active) {
- if (client->active->expiry < cur_time)
+ if (client->active->expiry < time(NULL))
free_client_lease(client->active);
else if (addr_eq(client->active->address, lease->address))
free_client_lease(client->active);
diff --git a/sbin/dhclient/dhclient.c b/sbin/dhclient/dhclient.c
index 6afab56706d..ec4793ce1f4 100644
--- a/sbin/dhclient/dhclient.c
+++ b/sbin/dhclient/dhclient.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: dhclient.c,v 1.151 2012/08/22 00:14:42 tedu Exp $ */
+/* $OpenBSD: dhclient.c,v 1.152 2012/08/26 23:33:29 krw Exp $ */
/*
* Copyright 2004 Henning Brauer <henning@openbsd.org>
@@ -66,8 +66,6 @@
#define DEFAULT_LEASE_TIME 43200 /* 12 hours... */
#define TIME_MAX 2147483647
-time_t cur_time;
-
char *path_dhclient_conf = _PATH_DHCLIENT_CONF;
char *path_dhclient_db = NULL;
@@ -220,7 +218,7 @@ routehandler(void)
ifam->ifam_addrs) != AF_INET)
break;
/* XXX check addrs like RTM_NEWADDR instead of this? */
- if (scripttime == 0 || cur_time < scripttime + 10)
+ if (scripttime == 0 || time(NULL) < scripttime + 10)
break;
errmsg = "interface address deleted";
goto die;
@@ -325,7 +323,6 @@ main(int argc, char *argv[])
log_perror = 0;
tzset();
- time(&cur_time);
memset(&sockaddr_broadcast, 0, sizeof(sockaddr_broadcast));
sockaddr_broadcast.sin_family = AF_INET;
@@ -487,7 +484,7 @@ state_reboot(void)
flags. */
make_request(client->active);
client->destination = iaddr_broadcast;
- client->first_sending = cur_time;
+ client->first_sending = time(NULL);
client->interval = 0;
/* Send out the first DHCPREQUEST packet. */
@@ -507,7 +504,7 @@ state_init(void)
client->xid = client->packet.xid;
client->destination = iaddr_broadcast;
client->state = S_SELECTING;
- client->first_sending = cur_time;
+ client->first_sending = time(NULL);
client->interval = 0;
/* Add an immediate timeout to cause the first DHCPDISCOVER packet
@@ -523,6 +520,7 @@ void
state_selecting(void)
{
struct client_lease *lp, *next, *picked;
+ time_t cur_time;
/* Cancel state_selecting and send_discover timeouts, since either
one could have got us here. */
@@ -554,6 +552,8 @@ state_selecting(void)
picked->next = NULL;
+ time(&cur_time);
+
/* If it was a BOOTREPLY, we can just take the address right now. */
if (!picked->options[DHO_DHCP_MESSAGE_TYPE].len) {
client->new = picked;
@@ -592,6 +592,7 @@ void
dhcpack(struct iaddr client_addr, struct option_data *options)
{
struct client_lease *lease;
+ time_t cur_time;
if (client->state != S_REBOOTING &&
client->state != S_REQUESTING &&
@@ -640,6 +641,8 @@ dhcpack(struct iaddr client_addr, struct option_data *options)
client->new->rebind = client->new->renewal +
client->new->renewal / 2 + client->new->renewal / 4;
+ time(&cur_time);
+
client->new->expiry += cur_time;
/* Lease lengths can never be negative. */
if (client->new->expiry < cur_time)
@@ -680,7 +683,7 @@ bind_lease(void)
note("bound to %s -- renewal in %lld seconds.",
piaddr(client->active->address),
- (long long)(client->active->renewal - cur_time));
+ (long long)(client->active->renewal - time(NULL)));
client->state = S_BOUND;
reinitialize_interface();
go_daemon();
@@ -707,7 +710,7 @@ state_bound(void)
} else
client->destination = iaddr_broadcast;
- client->first_sending = cur_time;
+ client->first_sending = time(NULL);
client->interval = 0;
client->state = S_RENEWING;
@@ -784,7 +787,7 @@ dhcpoffer(struct iaddr client_addr, struct option_data *options)
/* If the selecting interval has expired, go immediately to
state_selecting(). Otherwise, time out into
state_selecting at the select interval. */
- if (stop_selecting <= cur_time)
+ if (stop_selecting <= time(NULL))
state_selecting();
else {
set_timeout(stop_selecting, state_selecting);
@@ -897,8 +900,11 @@ dhcpnak(struct iaddr client_addr, struct option_data *options)
void
send_discover(void)
{
+ time_t cur_time;
int interval, increase = 1;
+ time(&cur_time);
+
/* Figure out how long it's been since we started transmitting. */
interval = cur_time - client->first_sending;
@@ -953,7 +959,7 @@ send_discover(void)
/* Send out a packet. */
send_packet(inaddr_any, &sockaddr_broadcast, NULL);
- set_timeout(cur_time + client->interval, send_discover);
+ set_timeout_interval(client->interval, send_discover);
}
/*
@@ -967,6 +973,7 @@ state_panic(void)
{
struct client_lease *loop = client->active;
struct client_lease *lp;
+ time_t cur_time;
note("No DHCPOFFERS received.");
@@ -976,6 +983,7 @@ state_panic(void)
goto activate_next;
/* Run through the list of leases and see if one can be used. */
+ time(&cur_time);
while (client->active) {
if (client->active->expiry > cur_time) {
note("Trying recorded lease %s",
@@ -989,8 +997,7 @@ state_panic(void)
yet need renewal, go into BOUND state and
timeout at the renewal time. */
if (!script_go()) {
- if (cur_time <
- client->active->renewal) {
+ if (cur_time < client->active->renewal) {
client->state = S_BOUND;
note("bound: renewal in %lld seconds.",
(long long)(client->active->renewal
@@ -1042,7 +1049,7 @@ activate_next:
script_init("FAIL");
script_go();
client->state = S_INIT;
- set_timeout(cur_time + config->retry_interval, state_init);
+ set_timeout_interval(config->retry_interval, state_init);
go_daemon();
}
@@ -1051,10 +1058,13 @@ send_request(void)
{
struct sockaddr_in destination;
struct in_addr from;
+ time_t cur_time;
int interval;
+ time(&cur_time);
+
/* Figure out how long it's been since we started transmitting. */
- interval = cur_time - client->first_sending;
+ interval = (int)(cur_time - client->first_sending);
/* If we're in the INIT-REBOOT or REQUESTING state and we're
past the reboot timeout, go to INIT and see if we can
@@ -1142,7 +1152,7 @@ send_request(void)
/* Send out a packet. */
send_packet(from, &destination, NULL);
- set_timeout(cur_time + client->interval, send_request);
+ set_timeout_interval(client->interval, send_request);
}
void
diff --git a/sbin/dhclient/dhcpd.h b/sbin/dhclient/dhcpd.h
index a08fabad817..96a8bf941c5 100644
--- a/sbin/dhclient/dhcpd.h
+++ b/sbin/dhclient/dhcpd.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: dhcpd.h,v 1.78 2012/08/22 00:14:42 tedu Exp $ */
+/* $OpenBSD: dhcpd.h,v 1.79 2012/08/26 23:33:30 krw Exp $ */
/*
* Copyright (c) 2004 Henning Brauer <henning@openbsd.org>
@@ -252,6 +252,7 @@ void reinitialize_interface(void);
void dispatch(void);
void got_one(void);
void set_timeout(time_t, void (*)(void));
+void set_timeout_interval(time_t, void (*)(void));
void cancel_timeout(void);
int interface_status(char *);
int interface_link_forceup(char *);
@@ -279,7 +280,6 @@ char *piaddr(struct iaddr);
/* dhclient.c */
extern char *path_dhclient_conf;
extern char *path_dhclient_db;
-extern time_t cur_time;
extern int log_perror;
extern int routefd;
diff --git a/sbin/dhclient/dispatch.c b/sbin/dhclient/dispatch.c
index c117479bd7e..a63bf088a95 100644
--- a/sbin/dhclient/dispatch.c
+++ b/sbin/dhclient/dispatch.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: dispatch.c,v 1.54 2012/08/18 00:20:01 krw Exp $ */
+/* $OpenBSD: dispatch.c,v 1.55 2012/08/26 23:33:31 krw Exp $ */
/*
* Copyright 2004 Henning Brauer <henning@openbsd.org>
@@ -122,7 +122,7 @@ dispatch(void)
{
int count, to_msec;
struct pollfd fds[2];
- time_t howlong;
+ time_t cur_time, howlong;
void (*func)(void);
do {
@@ -174,9 +174,6 @@ another:
/* Wait for a packet or a timeout... XXX */
count = poll(fds, 2, to_msec);
- /* Time may have moved on while we polled! */
- time(&cur_time);
-
/* Not likely to be transitory... */
if (count == -1) {
if (errno == EAGAIN || errno == EINTR) {
@@ -323,6 +320,13 @@ set_timeout(time_t when, void (*where)(void))
}
void
+set_timeout_interval(time_t secs, void (*where)(void))
+{
+ timeout.when = time(NULL) + secs;
+ timeout.func = where;
+}
+
+void
cancel_timeout(void)
{
timeout.when = 0;