Merge from vendor branch DHCP:
[dragonfly.git] / contrib / isc-dhcp / client / dhclient.c
1 /* dhclient.c
2
3    DHCP Client. */
4
5 /*
6  * Copyright (c) 1995-2002 Internet Software Consortium.
7  * All rights reserved.
8  *
9  * Redistribution and use in source and binary forms, with or without
10  * modification, are permitted provided that the following conditions
11  * are met:
12  *
13  * 1. Redistributions of source code must retain the above copyright
14  *    notice, this list of conditions and the following disclaimer.
15  * 2. Redistributions in binary form must reproduce the above copyright
16  *    notice, this list of conditions and the following disclaimer in the
17  *    documentation and/or other materials provided with the distribution.
18  * 3. Neither the name of Internet Software Consortium nor the names
19  *    of its contributors may be used to endorse or promote products derived
20  *    from this software without specific prior written permission.
21  *
22  * THIS SOFTWARE IS PROVIDED BY THE INTERNET SOFTWARE CONSORTIUM AND
23  * CONTRIBUTORS ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES,
24  * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
25  * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
26  * DISCLAIMED.  IN NO EVENT SHALL THE INTERNET SOFTWARE CONSORTIUM OR
27  * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
28  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
29  * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
30  * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
31  * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
32  * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
33  * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
34  * SUCH DAMAGE.
35  *
36  * This code is based on the original client state machine that was
37  * written by Elliot Poger.  The code has been extensively hacked on
38  * by Ted Lemon since then, so any mistakes you find are probably his
39  * fault and not Elliot's.
40  *
41  * $Id: dhclient.c,v 1.129.2.16 2003/04/26 21:51:39 dhankins Exp $ Copyright (c) 1995-2002 Internet Software Consortium.  All rights reserved.
42  * $FreeBSD: src/contrib/isc-dhcp/client/dhclient.c,v 1.34 2003/09/02 11:09:45 mbr Exp $
43  * $DragonFly: src/contrib/isc-dhcp/client/Attic/dhclient.c,v 1.4 2003/12/31 03:22:57 drhodus Exp $
44  */
45
46 #include "dhcpd.h"
47 #include "version.h"
48
49 #ifdef __FreeBSD__
50 #include <sys/ioctl.h>
51 #include <net/if_media.h>
52 #if defined(DRAGONFLY_FUTURE)
53 #include <net80211/ieee80211_ioctl.h>
54 #include <net80211/ieee80211.h>
55 #endif
56 #endif
57
58 TIME cur_time;
59 TIME default_lease_time = 43200; /* 12 hours... */
60 TIME max_lease_time = 86400; /* 24 hours... */
61
62 const char *path_dhclient_conf = _PATH_DHCLIENT_CONF;
63 const char *path_dhclient_db = _PATH_DHCLIENT_DB;
64 const char *path_dhclient_pid = _PATH_DHCLIENT_PID;
65 static char path_dhclient_script_array [] = _PATH_DHCLIENT_SCRIPT;
66 char *path_dhclient_script = path_dhclient_script_array;
67
68 int dhcp_max_agent_option_packet_length = 0;
69
70 int interfaces_requested = 0;
71
72 struct iaddr iaddr_broadcast = { 4, { 255, 255, 255, 255 } };
73 struct iaddr iaddr_any = { 4, { 0, 0, 0, 0 } };
74 struct in_addr inaddr_any;
75 struct sockaddr_in sockaddr_broadcast;
76 struct in_addr giaddr;
77
78 /* ASSERT_STATE() does nothing now; it used to be
79    assert (state_is == state_shouldbe). */
80 #define ASSERT_STATE(state_is, state_shouldbe) {}
81
82 static char copyright[] = "Copyright 1995-2002 Internet Software Consortium.";
83 static char arr [] = "All rights reserved.";
84 static char message [] = "Internet Software Consortium DHCP Client";
85 static char url [] = "For info, please visit http://www.isc.org/products/DHCP";
86
87 u_int16_t local_port=0;
88 u_int16_t remote_port=0;
89 int no_daemon=0;
90 struct string_list *client_env=NULL;
91 int client_env_count=0;
92 int onetry=0;
93 int quiet=1;
94 int nowait=0;
95 int doinitcheck=0;
96 #ifdef ENABLE_POLLING_MODE
97 int polling_interval = 5;
98 #endif
99
100 static void usage PROTO ((void));
101
102 void do_release(struct client_state *);
103
104 int main (argc, argv, envp)
105         int argc;
106         char **argv, **envp;
107 {
108         int i;
109         struct servent *ent;
110         struct interface_info *ip;
111         struct client_state *client;
112         unsigned seed;
113         char *server = (char *)0;
114         char *relay = (char *)0;
115         isc_result_t status;
116         int release_mode = 0;
117         omapi_object_t *listener;
118         isc_result_t result;
119         int persist = 0;
120         int omapi_port;
121         int no_dhclient_conf = 0;
122         int no_dhclient_db = 0;
123         int no_dhclient_pid = 0;
124         int no_dhclient_script = 0;
125         char *s;
126
127         /* Make sure we have stdin, stdout and stderr. */
128         i = open ("/dev/null", O_RDWR);
129         if (i == 0)
130                 i = open ("/dev/null", O_RDWR);
131         if (i == 1) {
132                 i = open ("/dev/null", O_RDWR);
133                 log_perror = 0; /* No sense logging to /dev/null. */
134         } else if (i != -1)
135                 close (i);
136
137 #ifdef SYSLOG_4_2
138         openlog ("dhclient", LOG_NDELAY);
139         log_priority = LOG_DAEMON;
140 #else
141         openlog ("dhclient", LOG_NDELAY, LOG_DAEMON);
142 #endif
143
144 #if !(defined (DEBUG) || defined (SYSLOG_4_2) || defined (__CYGWIN32__))
145         setlogmask (LOG_UPTO (LOG_INFO));
146 #endif  
147
148         /* Set up the OMAPI. */
149         status = omapi_init ();
150         if (status != ISC_R_SUCCESS)
151                 log_fatal ("Can't initialize OMAPI: %s",
152                            isc_result_totext (status));
153
154         /* Set up the OMAPI wrappers for various server database internal
155            objects. */
156         dhcp_common_objects_setup ();
157
158         dhcp_interface_discovery_hook = dhclient_interface_discovery_hook;
159         dhcp_interface_shutdown_hook = dhclient_interface_shutdown_hook;
160         dhcp_interface_startup_hook = dhclient_interface_startup_hook;
161
162         for (i = 1; i < argc; i++) {
163                 if (!strcmp (argv [i], "-r")) {
164                         release_mode = 1;
165                         no_daemon = 1;
166                 } else if (!strcmp (argv [i], "-p")) {
167                         if (++i == argc)
168                                 usage ();
169                         local_port = htons (atoi (argv [i]));
170                         log_debug ("binding to user-specified port %d",
171                                ntohs (local_port));
172                 } else if (!strcmp (argv [i], "-d")) {
173                         no_daemon = 1;
174                 } else if (!strcmp (argv [i], "-pf")) {
175                         if (++i == argc)
176                                 usage ();
177                         path_dhclient_pid = argv [i];
178                         no_dhclient_pid = 1;
179                 } else if (!strcmp (argv [i], "-cf")) {
180                         if (++i == argc)
181                                 usage ();
182                         path_dhclient_conf = argv [i];
183                         no_dhclient_conf = 1;
184                 } else if (!strcmp (argv [i], "-lf")) {
185                         if (++i == argc)
186                                 usage ();
187                         path_dhclient_db = argv [i];
188                         no_dhclient_db = 1;
189                 } else if (!strcmp (argv [i], "-sf")) {
190                         if (++i == argc)
191                                 usage ();
192                         path_dhclient_script = argv [i];
193                         no_dhclient_script = 1;
194                 } else if (!strcmp (argv [i], "-1")) {
195                         onetry = 1;
196                 } else if (!strcmp (argv [i], "-q")) {
197                         quiet = 1;
198                         quiet_interface_discovery = 1;
199                 } else if (!strcmp (argv [i], "-v")) {
200                         quiet = 0;
201                         quiet_interface_discovery = 0;
202                 } else if (!strcmp (argv [i], "-s")) {
203                         if (++i == argc)
204                                 usage ();
205                         server = argv [i];
206                 } else if (!strcmp (argv [i], "-g")) {
207                         if (++i == argc)
208                                 usage ();
209                         relay = argv [i];
210                 } else if (!strcmp (argv [i], "-nw")) {
211                         nowait = 1;
212                 } else if (!strcmp (argv [i], "-n")) {
213                         /* do not start up any interfaces */
214                         interfaces_requested = 1;
215 #ifdef ENABLE_POLLING_MODE
216                 } else if (!strcmp (argv [i], "-i")) {
217                         if (++i == argc)
218                                 usage ();
219                         polling_interval = (int)strtol (argv [i],
220                             (char **)NULL, 10);
221                         if (polling_interval <= 0) {
222                                 log_info ("Incorrect polling interval %d",
223                                     polling_interval);
224                                 log_info ("Using a default of 5 seconds");
225                                 polling_interval = 5;
226                         }
227 #endif
228                 } else if (!strcmp (argv [i], "-w")) {
229                         /* do not exit if there are no broadcast interfaces. */
230                         persist = 1;
231                 } else if (!strcmp (argv [i], "-e")) {
232                         struct string_list *tmp;
233                         if (++i == argc)
234                                 usage ();
235                         tmp = dmalloc (strlen (argv [i]) + sizeof *tmp, MDL);
236                         if (!tmp)
237                                 log_fatal ("No memory for %s", argv [i]);
238                         strcpy (tmp -> string, argv [i]);
239                         tmp -> next = client_env;
240                         client_env = tmp;
241                         client_env_count++;
242                 } else if (!strcmp (argv [i], "--version")) {
243                         log_info ("isc-dhclient-%s", DHCP_VERSION);
244                         exit (0);
245                 } else if (argv [i][0] == '-') {
246                     usage ();
247                 } else {
248                     struct interface_info *tmp = (struct interface_info *)0;
249                     status = interface_allocate (&tmp, MDL);
250                     if (status != ISC_R_SUCCESS)
251                         log_fatal ("Can't record interface %s:%s",
252                                    argv [i], isc_result_totext (status));
253                     if (strlen (argv [i]) > sizeof tmp -> name)
254                             log_fatal ("%s: interface name too long (max %ld)",
255                                        argv [i], (long)strlen (argv [i]));
256                     strlcpy (tmp -> name, argv [i], IFNAMSIZ);
257 #ifdef __FreeBSD__
258 #if defined(DRAGONFLY_FUTURE)
259                     set_ieee80211 (tmp);
260 #endif
261 #endif
262                     /* Init some interface vars, enable polling */
263 #ifdef ENABLE_POLLING_MODE
264                     tmp -> forcediscover = 0;
265                     tmp -> linkstate = HAVELINK;
266                     tmp -> polling = 1;
267 #endif /* ifdef ENABLE_POLLING_MODE */
268
269                     if (interfaces) {
270                             interface_reference (&tmp -> next,
271                                                  interfaces, MDL);
272                             interface_dereference (&interfaces, MDL);
273                     }
274                     interface_reference (&interfaces, tmp, MDL);
275                     tmp -> flags = INTERFACE_REQUESTED;
276                     interfaces_requested = 1;
277                 }
278         }
279
280         if (!no_dhclient_conf && (s = getenv ("PATH_DHCLIENT_CONF"))) {
281                 path_dhclient_conf = s;
282         }
283         if (!no_dhclient_db && (s = getenv ("PATH_DHCLIENT_DB"))) {
284                 path_dhclient_db = s;
285         }
286         if (!no_dhclient_pid && (s = getenv ("PATH_DHCLIENT_PID"))) {
287                 path_dhclient_pid = s;
288         }
289         if (!no_dhclient_script && (s = getenv ("PATH_DHCLIENT_SCRIPT"))) {
290                 path_dhclient_script = s;
291         }
292
293         /* first kill of any currently running client */
294         if (release_mode) {
295
296                 FILE *pidfd;
297                 pid_t oldpid;
298                 long temp;
299                 int e;
300
301                 oldpid = 0;
302                 if ((pidfd = fopen(path_dhclient_pid, "r")) != NULL) {
303                         e = fscanf(pidfd, "%ld\n", &temp);
304                         oldpid = (pid_t)temp;
305
306                         if (e != 0 && e != EOF) {
307                                 if (oldpid) {
308                                         if (kill(oldpid, SIGTERM) == 0)
309                                                 unlink(path_dhclient_pid);
310                                 }
311                         }
312                         fclose(pidfd);
313                 }
314         }
315
316         if (!quiet) {
317                 log_info ("%s %s", message, DHCP_VERSION);
318                 log_info (copyright);
319                 log_info (arr);
320                 log_info (url);
321                 log_info ("%s", "");
322         } else
323                 log_perror = 0;
324
325         /* If we're given a relay agent address to insert, for testing
326            purposes, figure out what it is. */
327         if (relay) {
328                 if (!inet_aton (relay, &giaddr)) {
329                         struct hostent *he;
330                         he = gethostbyname (relay);
331                         if (he) {
332                                 memcpy (&giaddr, he -> h_addr_list [0],
333                                         sizeof giaddr);
334                         } else {
335                                 log_fatal ("%s: no such host", relay);
336                         }
337                 }
338         }
339
340         /* Default to the DHCP/BOOTP port. */
341         if (!local_port) {
342                 /* If we're faking a relay agent, and we're not using loopback,
343                    use the server port, not the client port. */
344                 if (relay && giaddr.s_addr != htonl (INADDR_LOOPBACK)) {
345                         local_port = htons(67);
346                 } else {
347                         ent = getservbyname ("dhcpc", "udp");
348                         if (!ent)
349                                 local_port = htons (68);
350                         else
351                                 local_port = ent -> s_port;
352 #ifndef __CYGWIN32__
353                         endservent ();
354 #endif
355                 }
356         }
357
358         /* If we're faking a relay agent, and we're not using loopback,
359            we're using the server port, not the client port. */
360         if (relay && giaddr.s_addr != htonl (INADDR_LOOPBACK)) {
361                 remote_port = local_port;
362         } else
363                 remote_port = htons (ntohs (local_port) - 1);   /* XXX */
364
365         /* Get the current time... */
366         GET_TIME (&cur_time);
367
368         sockaddr_broadcast.sin_family = AF_INET;
369         sockaddr_broadcast.sin_port = remote_port;
370         if (server) {
371                 if (!inet_aton (server, &sockaddr_broadcast.sin_addr)) {
372                         struct hostent *he;
373                         he = gethostbyname (server);
374                         if (he) {
375                                 memcpy (&sockaddr_broadcast.sin_addr,
376                                         he -> h_addr_list [0],
377                                         sizeof sockaddr_broadcast.sin_addr);
378                         } else
379                                 sockaddr_broadcast.sin_addr.s_addr =
380                                         INADDR_BROADCAST;
381                 }
382         } else {
383                 sockaddr_broadcast.sin_addr.s_addr = INADDR_BROADCAST;
384         }
385
386         inaddr_any.s_addr = INADDR_ANY;
387
388         /* Discover all the network interfaces. */
389         discover_interfaces (DISCOVER_UNCONFIGURED);
390
391         /* Parse the dhclient.conf file. */
392         read_client_conf ();
393
394         /* Parse the lease database. */
395         read_client_leases ();
396
397         /* Rewrite the lease database... */
398         rewrite_client_leases ();
399
400         /* XXX */
401 /*      config_counter(&snd_counter, &rcv_counter); */
402
403         /* If no broadcast interfaces were discovered, call the script
404            and tell it so. */
405         if (!interfaces) {
406                 /* Call dhclient-script with the NBI flag, in case somebody
407                    cares. */
408                 script_init ((struct client_state *)0, "NBI",
409                              (struct string_list *)0);
410                 script_go ((struct client_state *)0);
411
412                 /* If we haven't been asked to persist, waiting for new
413                    interfaces, then just exit. */
414                 if (!persist) {
415                         /* Nothing more to do. */
416                         log_info ("No broadcast interfaces found - exiting.");
417                         exit (0);
418                 }
419         } else if (!release_mode) {
420                 /* Call the script with the list of interfaces. */
421                 for (ip = interfaces; ip; ip = ip -> next) {
422                         /* If interfaces were specified, don't configure
423                            interfaces that weren't specified! */
424                         if (interfaces_requested &&
425                             ((ip -> flags & (INTERFACE_REQUESTED |
426                                              INTERFACE_AUTOMATIC)) !=
427                              INTERFACE_REQUESTED))
428                                 continue;
429 #ifdef __FreeBSD__
430 #if defined(DRAGONFLY_FUTURE)
431                         set_ieee80211 (ip);
432 #endif
433 #endif
434 #ifdef ENABLE_POLLING_MODE
435                         ip -> forcediscover = 0;
436                         if (ip -> client -> config -> media != NULL)
437                                 ip -> havemedia = 1;
438                         else
439                                 ip -> havemedia = 0;
440 #endif
441                         script_init (ip -> client,
442                                      "PREINIT", (struct string_list *)0);
443                         if (ip -> client -> alias)
444                                 script_write_params (ip -> client, "alias_",
445                                                      ip -> client -> alias);
446                         script_go (ip -> client);
447                 }
448         }
449
450         /* At this point, all the interfaces that the script thinks
451            are relevant should be running, so now we once again call
452            discover_interfaces(), and this time ask it to actually set
453            up the interfaces. */
454         discover_interfaces (interfaces_requested
455                              ? DISCOVER_REQUESTED
456                              : DISCOVER_RUNNING);
457
458         /* Make up a seed for the random number generator from current
459            time plus the sum of the last four bytes of each
460            interface's hardware address interpreted as an integer.
461            Not much entropy, but we're booting, so we're not likely to
462            find anything better. */
463         seed = 0;
464         for (ip = interfaces; ip; ip = ip -> next) {
465                 int junk;
466                 memcpy (&junk,
467                         &ip -> hw_address.hbuf [ip -> hw_address.hlen -
468                                                sizeof seed], sizeof seed);
469                 seed += junk;
470         }
471         srandom (seed + cur_time);
472
473         /* Start a configuration state machine for each interface. */
474         for (ip = interfaces; ip; ip = ip -> next) {
475                 ip -> flags |= INTERFACE_RUNNING;
476                 for (client = ip -> client; client; client = client -> next) {
477                         if (release_mode)
478                                 do_release (client);
479                         else {
480                                 client -> state = S_INIT;
481                                 /* Set up a timeout to start the initialization
482                                    process. */
483 #ifdef ENABLE_POLLING_MODE
484                                 add_timeout (cur_time + random () % 5 + 2,
485                                              state_polling, client, 0, 0);
486 #else
487                                 add_timeout (cur_time + random () % 5,
488                                              state_reboot, client, 0, 0);
489 #endif
490                         }
491                 }
492         }
493
494         if (release_mode)
495                 return 0;
496
497         /* Start up a listener for the object management API protocol. */
498         if (top_level_config.omapi_port != -1) {
499                 listener = (omapi_object_t *)0;
500                 result = omapi_generic_new (&listener, MDL);
501                 if (result != ISC_R_SUCCESS)
502                         log_fatal ("Can't allocate new generic object: %s\n",
503                                    isc_result_totext (result));
504                 result = omapi_protocol_listen (listener,
505                                                 (unsigned)
506                                                 top_level_config.omapi_port,
507                                                 1);
508                 if (result != ISC_R_SUCCESS)
509                         log_fatal ("Can't start OMAPI protocol: %s",
510                                    isc_result_totext (result));
511         }
512
513         /* Set up the bootp packet handler... */
514         bootp_packet_handler = do_packet;
515
516 #if defined (DEBUG_MEMORY_LEAKAGE) || defined (DEBUG_MALLOC_POOL) || \
517                 defined (DEBUG_MEMORY_LEAKAGE_ON_EXIT)
518         dmalloc_cutoff_generation = dmalloc_generation;
519         dmalloc_longterm = dmalloc_outstanding;
520         dmalloc_outstanding = 0;
521 #endif
522
523         /* If we're not supposed to wait before getting the address,
524            don't. */
525         if (nowait)
526                 go_daemon ();
527
528         /* If we're not going to daemonize, write the pid file
529            now. */
530         if (no_daemon || nowait)
531                 write_client_pid_file ();
532
533         /* Start dispatching packets and timeouts... */
534         dispatch ();
535
536         /*NOTREACHED*/
537         return 0;
538 }
539
540 static void usage ()
541 {
542         log_info ("%s %s", message, DHCP_VERSION);
543         log_info (copyright);
544         log_info (arr);
545         log_info (url);
546
547         log_error ("Usage: dhclient [-1dqr] [-nw] [-p <port>] %s",
548                    "[-s server]");
549         log_error ("                [-cf config-file] [-lf lease-file]%s",
550                    "[-pf pid-file] [-e VAR=val]");
551         log_fatal ("                [-sf script-file] [interface]");
552 }
553
554 isc_result_t find_class (struct class **c,
555                 const char *s, const char *file, int line)
556 {
557         return 0;
558 }
559
560 int check_collection (packet, lease, collection)
561         struct packet *packet;
562         struct lease *lease;
563         struct collection *collection;
564 {
565         return 0;
566 }
567
568 void classify (packet, class)
569         struct packet *packet;
570         struct class *class;
571 {
572 }
573
574 int unbill_class (lease, class)
575         struct lease *lease;
576         struct class *class;
577 {
578         return 0;
579 }
580
581 int find_subnet (struct subnet **sp,
582                  struct iaddr addr, const char *file, int line)
583 {
584         return 0;
585 }
586
587 /* Individual States:
588  * 
589  * Each routine is called from the dhclient_state_machine() in one of
590  * these conditions:
591  * -> entering INIT state
592  * -> recvpacket_flag == 0: timeout in this state
593  * -> otherwise: received a packet in this state
594  *
595  * Return conditions as handled by dhclient_state_machine():
596  * Returns 1, sendpacket_flag = 1: send packet, reset timer.
597  * Returns 1, sendpacket_flag = 0: just reset the timer (wait for a milestone).
598  * Returns 0: finish the nap which was interrupted for no good reason.
599  *
600  * Several per-interface variables are used to keep track of the process:
601  *   active_lease: the lease that is being used on the interface
602  *                 (null pointer if not configured yet).
603  *   offered_leases: leases corresponding to DHCPOFFER messages that have
604  *                   been sent to us by DHCP servers.
605  *   acked_leases: leases corresponding to DHCPACK messages that have been
606  *                 sent to us by DHCP servers.
607  *   sendpacket: DHCP packet we're trying to send.
608  *   destination: IP address to send sendpacket to
609  * In addition, there are several relevant per-lease variables.
610  *   T1_expiry, T2_expiry, lease_expiry: lease milestones
611  * In the active lease, these control the process of renewing the lease;
612  * In leases on the acked_leases list, this simply determines when we
613  * can no longer legitimately use the lease.
614  */
615
616 void state_reboot (cpp)
617         void *cpp;
618 {
619         struct client_state *client = cpp;
620
621         /* If we don't remember an active lease, go straight to INIT. */
622         if (!client -> active ||
623             client -> active -> is_bootp ||
624             client -> active -> expiry <= cur_time) {
625                 state_init (client);
626                 return;
627         }
628
629         /* We are in the rebooting state. */
630         client -> state = S_REBOOTING;
631
632         /* make_request doesn't initialize xid because it normally comes
633            from the DHCPDISCOVER, but we haven't sent a DHCPDISCOVER,
634            so pick an xid now. */
635         client -> xid = random ();
636
637         /* Make a DHCPREQUEST packet, and set appropriate per-interface
638            flags. */
639         make_request (client, client -> active);
640         client -> destination = iaddr_broadcast;
641         client -> first_sending = cur_time;
642         client -> interval = client -> config -> initial_interval;
643
644         /* Zap the medium list... */
645         client -> medium = (struct string_list *)0;
646
647         /* Send out the first DHCPREQUEST packet. */
648         send_request (client);
649 }
650
651 /* Called when a lease has completely expired and we've been unable to
652    renew it. */
653
654 void state_init (cpp)
655         void *cpp;
656 {
657         struct client_state *client = cpp;
658
659         ASSERT_STATE(state, S_INIT);
660
661         /* Make a DHCPDISCOVER packet, and set appropriate per-interface
662            flags. */
663         make_discover (client, client -> active);
664         client -> xid = client -> packet.xid;
665         client -> destination = iaddr_broadcast;
666         client -> state = S_SELECTING;
667         client -> first_sending = cur_time;
668         client -> interval = client -> config -> initial_interval;
669
670         /* Add an immediate timeout to cause the first DHCPDISCOVER packet
671            to go out. */
672         send_discover (client);
673 }
674
675 /* state_selecting is called when one or more DHCPOFFER packets have been
676    received and a configurable period of time has passed. */
677
678 void state_selecting (cpp)
679         void *cpp;
680 {
681         struct client_state *client = cpp;
682         struct client_lease *lp, *next, *picked;
683
684
685         ASSERT_STATE(state, S_SELECTING);
686
687         /* Cancel state_selecting and send_discover timeouts, since either
688            one could have got us here. */
689         cancel_timeout (state_selecting, client);
690         cancel_timeout (send_discover, client);
691
692         /* We have received one or more DHCPOFFER packets.   Currently,
693            the only criterion by which we judge leases is whether or
694            not we get a response when we arp for them. */
695         picked = (struct client_lease *)0;
696         for (lp = client -> offered_leases; lp; lp = next) {
697                 next = lp -> next;
698
699                 /* Check to see if we got an ARPREPLY for the address
700                    in this particular lease. */
701                 if (!picked) {
702                         picked = lp;
703                         picked -> next = (struct client_lease *)0;
704                 } else {
705                       freeit:
706                         destroy_client_lease (lp);
707                 }
708         }
709         client -> offered_leases = (struct client_lease *)0;
710
711         /* If we just tossed all the leases we were offered, go back
712            to square one. */
713         if (!picked) {
714                 client -> state = S_INIT;
715                 state_init (client);
716                 return;
717         }
718
719         /* If it was a BOOTREPLY, we can just take the address right now. */
720         if (picked -> is_bootp) {
721                 client -> new = picked;
722
723                 /* Make up some lease expiry times
724                    XXX these should be configurable. */
725                 client -> new -> expiry = cur_time + 12000;
726                 client -> new -> renewal += cur_time + 8000;
727                 client -> new -> rebind += cur_time + 10000;
728
729                 client -> state = S_REQUESTING;
730
731                 /* Bind to the address we received. */
732                 bind_lease (client);
733                 return;
734         }
735
736         /* Go to the REQUESTING state. */
737         client -> destination = iaddr_broadcast;
738         client -> state = S_REQUESTING;
739         client -> first_sending = cur_time;
740         client -> interval = client -> config -> initial_interval;
741
742         /* Make a DHCPREQUEST packet from the lease we picked. */
743         make_request (client, picked);
744         client -> xid = client -> packet.xid;
745
746         /* Toss the lease we picked - we'll get it back in a DHCPACK. */
747         destroy_client_lease (picked);
748
749         /* Add an immediate timeout to send the first DHCPREQUEST packet. */
750         send_request (client);
751 }  
752
753 /* state_requesting is called when we receive a DHCPACK message after
754    having sent out one or more DHCPREQUEST packets. */
755
756 void dhcpack (packet)
757         struct packet *packet;
758 {
759         struct interface_info *ip = packet -> interface;
760         struct client_state *client;
761         struct client_lease *lease;
762         struct option_cache *oc;
763         struct data_string ds;
764         int i;
765         
766         /* If we're not receptive to an offer right now, or if the offer
767            has an unrecognizable transaction id, then just drop it. */
768         for (client = ip -> client; client; client = client -> next) {
769                 if (client -> xid == packet -> raw -> xid)
770                         break;
771         }
772         if (!client ||
773             (packet -> interface -> hw_address.hlen - 1 !=
774              packet -> raw -> hlen) ||
775             (memcmp (&packet -> interface -> hw_address.hbuf [1],
776                      packet -> raw -> chaddr, packet -> raw -> hlen))) {
777 #if defined (DEBUG)
778                 log_debug ("DHCPACK in wrong transaction.");
779 #endif
780                 return;
781         }
782
783         if (client -> state != S_REBOOTING &&
784             client -> state != S_REQUESTING &&
785             client -> state != S_RENEWING &&
786             client -> state != S_REBINDING) {
787 #if defined (DEBUG)
788                 log_debug ("DHCPACK in wrong state.");
789 #endif
790                 return;
791         }
792
793         log_info ("DHCPACK from %s", piaddr (packet -> client_addr));
794
795         lease = packet_to_lease (packet, client);
796         if (!lease) {
797                 log_info ("packet_to_lease failed.");
798                 return;
799         }
800
801         client -> new = lease;
802
803         /* Stop resending DHCPREQUEST. */
804         cancel_timeout (send_request, client);
805
806         /* Figure out the lease time. */
807         oc = lookup_option (&dhcp_universe, client -> new -> options,
808                             DHO_DHCP_LEASE_TIME);
809         memset (&ds, 0, sizeof ds);
810         if (oc &&
811             evaluate_option_cache (&ds, packet, (struct lease *)0, client,
812                                    packet -> options, client -> new -> options,
813                                    &global_scope, oc, MDL)) {
814                 if (ds.len > 3)
815                         client -> new -> expiry = getULong (ds.data);
816                 else
817                         client -> new -> expiry = 0;
818                 data_string_forget (&ds, MDL);
819         } else
820                         client -> new -> expiry = 0;
821
822         if (!client -> new -> expiry) {
823                 log_error ("no expiry time on offered lease.");
824                 /* XXX this is going to be bad - if this _does_
825                    XXX happen, we should probably dynamically 
826                    XXX disqualify the DHCP server that gave us the
827                    XXX bad packet from future selections and
828                    XXX then go back into the init state. */
829                 state_init (client);
830                 return;
831         }
832
833         /* A number that looks negative here is really just very large,
834            because the lease expiry offset is unsigned. */
835         if (client -> new -> expiry < 0)
836                 client -> new -> expiry = TIME_MAX;
837         /* Take the server-provided renewal time if there is one. */
838         oc = lookup_option (&dhcp_universe, client -> new -> options,
839                             DHO_DHCP_RENEWAL_TIME);
840         if (oc &&
841             evaluate_option_cache (&ds, packet, (struct lease *)0, client,
842                                    packet -> options, client -> new -> options,
843                                    &global_scope, oc, MDL)) {
844                 if (ds.len > 3)
845                         client -> new -> renewal = getULong (ds.data);
846                 else
847                         client -> new -> renewal = 0;
848                 data_string_forget (&ds, MDL);
849         } else
850                         client -> new -> renewal = 0;
851
852         /* If it wasn't specified by the server, calculate it. */
853         if (!client -> new -> renewal)
854                 client -> new -> renewal =
855                         client -> new -> expiry / 2;
856
857         /* Now introduce some randomness to the renewal time: */
858         client -> new -> renewal = (((client -> new -> renewal + 3) * 3 / 4) +
859                                     (random () % /* XXX NUMS */
860                                      ((client -> new -> renewal + 3) / 4)));
861
862         /* Same deal with the rebind time. */
863         oc = lookup_option (&dhcp_universe, client -> new -> options,
864                             DHO_DHCP_REBINDING_TIME);
865         if (oc &&
866             evaluate_option_cache (&ds, packet, (struct lease *)0, client,
867                                    packet -> options, client -> new -> options,
868                                    &global_scope, oc, MDL)) {
869                 if (ds.len > 3)
870                         client -> new -> rebind = getULong (ds.data);
871                 else
872                         client -> new -> rebind = 0;
873                 data_string_forget (&ds, MDL);
874         } else
875                         client -> new -> rebind = 0;
876
877         if (!client -> new -> rebind)
878                 client -> new -> rebind =
879                         (client -> new -> expiry * 7) / 8; /* XXX NUMS */
880
881         /* Make sure our randomness didn't run the renewal time past the
882            rebind time. */
883         if (client -> new -> renewal > client -> new -> rebind)
884                 client -> new -> renewal = (client -> new -> rebind * 3) / 4;
885
886         client -> new -> expiry += cur_time;
887         /* Lease lengths can never be negative. */
888         if (client -> new -> expiry < cur_time)
889                 client -> new -> expiry = TIME_MAX;
890         client -> new -> renewal += cur_time;
891         if (client -> new -> renewal < cur_time)
892                 client -> new -> renewal = TIME_MAX;
893         client -> new -> rebind += cur_time;
894         if (client -> new -> rebind < cur_time)
895                 client -> new -> rebind = TIME_MAX;
896
897         bind_lease (client);
898 }
899
900 void bind_lease (client)
901         struct client_state *client;
902 {
903         struct interface_info *ip = client -> interface;
904
905         /* Remember the medium. */
906         client -> new -> medium = client -> medium;
907
908         /* Run the client script with the new parameters. */
909         script_init (client, (client -> state == S_REQUESTING
910                           ? "BOUND"
911                           : (client -> state == S_RENEWING
912                              ? "RENEW"
913                              : (client -> state == S_REBOOTING
914                                 ? "REBOOT" : "REBIND"))),
915                      client -> new -> medium);
916         if (client -> active && client -> state != S_REBOOTING)
917                 script_write_params (client, "old_", client -> active);
918         script_write_params (client, "new_", client -> new);
919         if (client -> alias)
920                 script_write_params (client, "alias_", client -> alias);
921
922         /* If the BOUND/RENEW code detects another machine using the
923            offered address, it exits nonzero.  We need to send a
924            DHCPDECLINE and toss the lease. */
925         if (script_go (client)) {
926                 make_decline (client, client -> new);
927                 send_decline (client);
928                 destroy_client_lease (client -> new);
929                 client -> new = (struct client_lease *)0;
930                 state_init (client);
931                 return;
932         }
933
934         /* Write out the new lease. */
935         write_client_lease (client, client -> new, 0, 0);
936
937         /*
938          * It's now possible that state_reboot can be called
939          * after a interface link went down and is up again.
940          * To prevent tons of equal leases saved on disk, we rewrite
941          * them.
942          */
943         read_client_leases ();
944         rewrite_client_leases ();
945
946         /* Replace the old active lease with the new one. */
947         if (client -> active)
948                 destroy_client_lease (client -> active);
949         client -> active = client -> new;
950         client -> new = (struct client_lease *)0;
951
952         /* Set up a timeout to start the renewal process. */
953         add_timeout (client -> active -> renewal,
954                      state_bound, client, 0, 0);
955
956         log_info ("bound to %s -- renewal in %ld seconds.",
957               piaddr (client -> active -> address),
958               (long)(client -> active -> renewal - cur_time));
959         client -> state = S_BOUND;
960 #ifdef ENABLE_POLLING_MODE
961         /* Init some interface vars, enable polling */
962         client -> interface -> linkstate = HAVELINK;
963         client -> interface -> forcediscover = 0;
964         client -> interface -> polling = 1;
965 #endif /* ifdef ENABLE_POLLING_MODE */
966         reinitialize_interfaces ();
967         go_daemon ();
968         if (client -> config -> do_forward_update) {
969                 client -> dns_update_timeout = 1;
970                 add_timeout (cur_time + 1, client_dns_update_timeout,
971                              client, 0, 0);
972         }
973 }  
974
975 /* state_bound is called when we've successfully bound to a particular
976    lease, but the renewal time on that lease has expired.   We are
977    expected to unicast a DHCPREQUEST to the server that gave us our
978    original lease. */
979
980 void state_bound (cpp)
981         void *cpp;
982 {
983         struct client_state *client = cpp;
984         int i;
985         struct option_cache *oc;
986         struct data_string ds;
987
988         ASSERT_STATE(state, S_BOUND);
989
990         /* T1 has expired. */
991         make_request (client, client -> active);
992         client -> xid = client -> packet.xid;
993
994         memset (&ds, 0, sizeof ds);
995         oc = lookup_option (&dhcp_universe, client -> active -> options,
996                             DHO_DHCP_SERVER_IDENTIFIER);
997         if (oc &&
998             evaluate_option_cache (&ds, (struct packet *)0, (struct lease *)0,
999                                    client, (struct option_state *)0,
1000                                    client -> active -> options,
1001                                    &global_scope, oc, MDL)) {
1002                 if (ds.len > 3) {
1003                         memcpy (client -> destination.iabuf, ds.data, 4);
1004                         client -> destination.len = 4;
1005                 } else
1006                         client -> destination = iaddr_broadcast;
1007         } else
1008                 client -> destination = iaddr_broadcast;
1009
1010         client -> first_sending = cur_time;
1011         client -> interval = client -> config -> initial_interval;
1012         client -> state = S_RENEWING;
1013
1014         /* Send the first packet immediately. */
1015         send_request (client);
1016 }  
1017
1018 /* state_stop is called when we've been told to shut down.   We unconfigure
1019    the interfaces, and then stop operating until told otherwise. */
1020
1021 void state_stop (cpp)
1022         void *cpp;
1023 {
1024         struct client_state *client = cpp;
1025         int i;
1026
1027         /* Cancel all timeouts. */
1028         cancel_timeout (state_selecting, client);
1029         cancel_timeout (send_discover, client);
1030         cancel_timeout (send_request, client);
1031         cancel_timeout (state_bound, client);
1032
1033         /* If we have an address, unconfigure it. */
1034         if (client -> active) {
1035                 script_init (client, "STOP", client -> active -> medium);
1036                 script_write_params (client, "old_", client -> active);
1037                 if (client -> alias)
1038                         script_write_params (client, "alias_",
1039                                              client -> alias);
1040                 script_go (client);
1041         }
1042 }  
1043
1044 int commit_leases ()
1045 {
1046         return 0;
1047 }
1048
1049 int write_lease (lease)
1050         struct lease *lease;
1051 {
1052         return 0;
1053 }
1054
1055 int write_host (host)
1056         struct host_decl *host;
1057 {
1058         return 0;
1059 }
1060
1061 void db_startup (testp)
1062         int testp;
1063 {
1064 }
1065
1066 void bootp (packet)
1067         struct packet *packet;
1068 {
1069         struct iaddrlist *ap;
1070
1071         if (packet -> raw -> op != BOOTREPLY)
1072                 return;
1073
1074         /* If there's a reject list, make sure this packet's sender isn't
1075            on it. */
1076         for (ap = packet -> interface -> client -> config -> reject_list;
1077              ap; ap = ap -> next) {
1078                 if (addr_eq (packet -> client_addr, ap -> addr)) {
1079                         log_info ("BOOTREPLY from %s rejected.",
1080                               piaddr (ap -> addr));
1081                         return;
1082                 }
1083         }
1084         
1085         dhcpoffer (packet);
1086
1087 }
1088
1089 void dhcp (packet)
1090         struct packet *packet;
1091 {
1092         struct iaddrlist *ap;
1093         void (*handler) PROTO ((struct packet *));
1094         const char *type;
1095
1096         switch (packet -> packet_type) {
1097               case DHCPOFFER:
1098                 handler = dhcpoffer;
1099                 type = "DHCPOFFER";
1100                 break;
1101
1102               case DHCPNAK:
1103                 handler = dhcpnak;
1104                 type = "DHCPNACK";
1105                 break;
1106
1107               case DHCPACK:
1108                 handler = dhcpack;
1109                 type = "DHCPACK";
1110                 break;
1111
1112               default:
1113                 return;
1114         }
1115
1116         /* If there's a reject list, make sure this packet's sender isn't
1117            on it. */
1118         for (ap = packet -> interface -> client -> config -> reject_list;
1119              ap; ap = ap -> next) {
1120                 if (addr_eq (packet -> client_addr, ap -> addr)) {
1121                         log_info ("%s from %s rejected.",
1122                               type, piaddr (ap -> addr));
1123                         return;
1124                 }
1125         }
1126         (*handler) (packet);
1127 }
1128
1129 void dhcpoffer (packet)
1130         struct packet *packet;
1131 {
1132         struct interface_info *ip = packet -> interface;
1133         struct client_state *client;
1134         struct client_lease *lease, *lp;
1135         int i;
1136         int stop_selecting;
1137         const char *name = packet -> packet_type ? "DHCPOFFER" : "BOOTREPLY";
1138         struct iaddrlist *ap;
1139         struct option_cache *oc;
1140         char obuf [1024];
1141         
1142 #ifdef DEBUG_PACKET
1143         dump_packet (packet);
1144 #endif  
1145
1146         /* Find a client state that matches the xid... */
1147         for (client = ip -> client; client; client = client -> next)
1148                 if (client -> xid == packet -> raw -> xid)
1149                         break;
1150
1151         /* If we're not receptive to an offer right now, or if the offer
1152            has an unrecognizable transaction id, then just drop it. */
1153         if (!client ||
1154             client -> state != S_SELECTING ||
1155             (packet -> interface -> hw_address.hlen - 1 !=
1156              packet -> raw -> hlen) ||
1157             (memcmp (&packet -> interface -> hw_address.hbuf [1],
1158                      packet -> raw -> chaddr, packet -> raw -> hlen))) {
1159 #if defined (DEBUG)
1160                 log_debug ("%s in wrong transaction.", name);
1161 #endif
1162                 return;
1163         }
1164
1165         sprintf (obuf, "%s from %s", name, piaddr (packet -> client_addr));
1166
1167
1168         /* If this lease doesn't supply the minimum required parameters,
1169            blow it off. */
1170         if (client -> config -> required_options) {
1171             for (i = 0; client -> config -> required_options [i]; i++) {
1172                 if (!lookup_option
1173                     (&dhcp_universe, packet -> options,
1174                      client -> config -> required_options [i])) {
1175                     log_info ("%s: no %s option.",
1176                               obuf, (dhcp_universe.options
1177                                      [client -> config -> required_options [i]]
1178                                      -> name));
1179                                 return;
1180                         }
1181                 }
1182         }
1183
1184         /* If we've already seen this lease, don't record it again. */
1185         for (lease = client -> offered_leases; lease; lease = lease -> next) {
1186                 if (lease -> address.len == sizeof packet -> raw -> yiaddr &&
1187                     !memcmp (lease -> address.iabuf,
1188                              &packet -> raw -> yiaddr, lease -> address.len)) {
1189                         log_debug ("%s: already seen.", obuf);
1190                         return;
1191                 }
1192         }
1193
1194         lease = packet_to_lease (packet, client);
1195         if (!lease) {
1196                 log_info ("%s: packet_to_lease failed.", obuf);
1197                 return;
1198         }
1199
1200         /* If this lease was acquired through a BOOTREPLY, record that
1201            fact. */
1202         if (!packet -> options_valid || !packet -> packet_type)
1203                 lease -> is_bootp = 1;
1204
1205         /* Record the medium under which this lease was offered. */
1206         lease -> medium = client -> medium;
1207
1208         /* Figure out when we're supposed to stop selecting. */
1209         stop_selecting = (client -> first_sending +
1210                           client -> config -> select_interval);
1211
1212         /* If this is the lease we asked for, put it at the head of the
1213            list, and don't mess with the arp request timeout. */
1214         if (lease -> address.len == client -> requested_address.len &&
1215             !memcmp (lease -> address.iabuf,
1216                      client -> requested_address.iabuf,
1217                      client -> requested_address.len)) {
1218                 lease -> next = client -> offered_leases;
1219                 client -> offered_leases = lease;
1220         } else {
1221                 /* Put the lease at the end of the list. */
1222                 lease -> next = (struct client_lease *)0;
1223                 if (!client -> offered_leases)
1224                         client -> offered_leases = lease;
1225                 else {
1226                         for (lp = client -> offered_leases; lp -> next;
1227                              lp = lp -> next)
1228                                 ;
1229                         lp -> next = lease;
1230                 }
1231         }
1232
1233         /* If the selecting interval has expired, go immediately to
1234            state_selecting().  Otherwise, time out into
1235            state_selecting at the select interval. */
1236         if (stop_selecting <= 0)
1237                 state_selecting (client);
1238         else {
1239                 add_timeout (stop_selecting, state_selecting, client, 0, 0);
1240                 cancel_timeout (send_discover, client);
1241         }
1242         log_info ("%s", obuf);
1243 }
1244
1245 /* Allocate a client_lease structure and initialize it from the parameters
1246    in the specified packet. */
1247
1248 struct client_lease *packet_to_lease (packet, client)
1249         struct packet *packet;
1250         struct client_state *client;
1251 {
1252         struct client_lease *lease;
1253         unsigned i;
1254         struct option_cache *oc;
1255         struct data_string data;
1256
1257         lease = (struct client_lease *)new_client_lease (MDL);
1258
1259         if (!lease) {
1260                 log_error ("packet_to_lease: no memory to record lease.\n");
1261                 return (struct client_lease *)0;
1262         }
1263
1264         memset (lease, 0, sizeof *lease);
1265
1266         /* Copy the lease options. */
1267         option_state_reference (&lease -> options, packet -> options, MDL);
1268
1269         lease -> address.len = sizeof (packet -> raw -> yiaddr);
1270         memcpy (lease -> address.iabuf, &packet -> raw -> yiaddr,
1271                 lease -> address.len);
1272
1273         memset (&data, 0, sizeof data);
1274
1275         if (client -> config -> vendor_space_name) {
1276                 i = DHO_VENDOR_ENCAPSULATED_OPTIONS;
1277
1278                 /* See if there was a vendor encapsulation option. */
1279                 oc = lookup_option (&dhcp_universe, lease -> options, i);
1280                 if (oc &&
1281                     client -> config -> vendor_space_name &&
1282                     evaluate_option_cache (&data, packet,
1283                                            (struct lease *)0, client,
1284                                            packet -> options, lease -> options,
1285                                            &global_scope, oc, MDL)) {
1286                         if (data.len) {
1287                                 parse_encapsulated_suboptions
1288                                         (packet -> options, &dhcp_options [i],
1289                                          data.data, data.len, &dhcp_universe,
1290                                          client -> config -> vendor_space_name
1291                                                 );
1292                         }
1293                         data_string_forget (&data, MDL);
1294                 }
1295         } else
1296                 i = 0;
1297
1298         /* Figure out the overload flag. */
1299         oc = lookup_option (&dhcp_universe, lease -> options,
1300                             DHO_DHCP_OPTION_OVERLOAD);
1301         if (oc &&
1302             evaluate_option_cache (&data, packet, (struct lease *)0, client,
1303                                    packet -> options, lease -> options,
1304                                    &global_scope, oc, MDL)) {
1305                 if (data.len > 0)
1306                         i = data.data [0];
1307                 else
1308                         i = 0;
1309                 data_string_forget (&data, MDL);
1310         } else
1311                 i = 0;
1312
1313         /* If the server name was filled out, copy it. */
1314         if (!(i & 2) && packet -> raw -> sname [0]) {
1315                 unsigned len;
1316                 /* Don't count on the NUL terminator. */
1317                 for (len = 0; len < 64; len++)
1318                         if (!packet -> raw -> sname [len])
1319                                 break;
1320                 lease -> server_name = dmalloc (len + 1, MDL);
1321                 if (!lease -> server_name) {
1322                         log_error ("dhcpoffer: no memory for filename.\n");
1323                         destroy_client_lease (lease);
1324                         return (struct client_lease *)0;
1325                 } else {
1326                         memcpy (lease -> server_name,
1327                                 packet -> raw -> sname, len);
1328                         lease -> server_name [len] = 0;
1329                 }
1330         }
1331
1332         /* Ditto for the filename. */
1333         if (!(i & 1) && packet -> raw -> file [0]) {
1334                 unsigned len;
1335                 /* Don't count on the NUL terminator. */
1336                 for (len = 0; len < 64; len++)
1337                         if (!packet -> raw -> file [len])
1338                                 break;
1339                 lease -> filename = dmalloc (len + 1, MDL);
1340                 if (!lease -> filename) {
1341                         log_error ("dhcpoffer: no memory for filename.\n");
1342                         destroy_client_lease (lease);
1343                         return (struct client_lease *)0;
1344                 } else {
1345                         memcpy (lease -> filename,
1346                                 packet -> raw -> file, len);
1347                         lease -> filename [len] = 0;
1348                 }
1349         }
1350
1351         execute_statements_in_scope ((struct binding_value **)0,
1352                                      (struct packet *)packet,
1353                                      (struct lease *)0, client,
1354                                      lease -> options, lease -> options,
1355                                      &global_scope,
1356                                      client -> config -> on_receipt,
1357                                      (struct group *)0);
1358
1359         return lease;
1360 }       
1361
1362 void dhcpnak (packet)
1363         struct packet *packet;
1364 {
1365         struct interface_info *ip = packet -> interface;
1366         struct client_state *client;
1367
1368         /* Find a client state that matches the xid... */
1369         for (client = ip -> client; client; client = client -> next)
1370                 if (client -> xid == packet -> raw -> xid)
1371                         break;
1372
1373         /* If we're not receptive to an offer right now, or if the offer
1374            has an unrecognizable transaction id, then just drop it. */
1375         if (!client ||
1376             (packet -> interface -> hw_address.hlen - 1 !=
1377              packet -> raw -> hlen) ||
1378             (memcmp (&packet -> interface -> hw_address.hbuf [1],
1379                      packet -> raw -> chaddr, packet -> raw -> hlen))) {
1380 #if defined (DEBUG)
1381                 log_debug ("DHCPNAK in wrong transaction.");
1382 #endif
1383                 return;
1384         }
1385
1386         if (client -> state != S_REBOOTING &&
1387             client -> state != S_REQUESTING &&
1388             client -> state != S_RENEWING &&
1389             client -> state != S_REBINDING) {
1390 #if defined (DEBUG)
1391                 log_debug ("DHCPNAK in wrong state.");
1392 #endif
1393                 return;
1394         }
1395
1396         log_info ("DHCPNAK from %s", piaddr (packet -> client_addr));
1397
1398         if (!client -> active) {
1399 #if defined (DEBUG)
1400                 log_info ("DHCPNAK with no active lease.\n");
1401 #endif
1402                 return;
1403         }
1404
1405         destroy_client_lease (client -> active);
1406         client -> active = (struct client_lease *)0;
1407
1408         /* Stop sending DHCPREQUEST packets... */
1409         cancel_timeout (send_request, client);
1410
1411         client -> state = S_INIT;
1412         state_init (client);
1413 }
1414
1415 /* Send out a DHCPDISCOVER packet, and set a timeout to send out another
1416    one after the right interval has expired.  If we don't get an offer by
1417    the time we reach the panic interval, call the panic function. */
1418
1419 void send_discover (cpp)
1420         void *cpp;
1421 {
1422         struct client_state *client = cpp;
1423
1424         int result;
1425         int interval;
1426         int increase = 1;
1427
1428 #ifdef ENABLE_POLLING_MODE
1429         /* Disable polling for this interface */
1430         client -> interface -> polling = 0;
1431 #endif
1432
1433         /* Figure out how long it's been since we started transmitting. */
1434         interval = cur_time - client -> first_sending;
1435
1436         /* If we're past the panic timeout, call the script and tell it
1437            we haven't found anything for this interface yet. */
1438         if (interval > client -> config -> timeout) {
1439                 state_panic (client);
1440                 return;
1441         }
1442
1443         /* If we're selecting media, try the whole list before doing
1444            the exponential backoff, but if we've already received an
1445            offer, stop looping, because we obviously have it right. */
1446         if (!client -> offered_leases &&
1447             client -> config -> media) {
1448                 int fail = 0;
1449               again:
1450                 if (client -> medium) {
1451                         client -> medium = client -> medium -> next;
1452                         increase = 0;
1453                 } 
1454                 if (!client -> medium) {
1455                         if (fail)
1456                                 log_fatal ("No valid media types for %s!",
1457                                        client -> interface -> name);
1458                         client -> medium =
1459                                 client -> config -> media;
1460                         increase = 1;
1461                 }
1462                         
1463                 log_info ("Trying medium \"%s\" %d",
1464                           client -> medium -> string, increase);
1465                 script_init (client, "MEDIUM", client -> medium);
1466                 if (script_go (client)) {
1467                         fail = 1;
1468                         goto again;
1469                 }
1470         }
1471
1472         /* If we're supposed to increase the interval, do so.  If it's
1473            currently zero (i.e., we haven't sent any packets yet), set
1474            it to one; otherwise, add to it a random number between
1475            zero and two times itself.  On average, this means that it
1476            will double with every transmission. */
1477         if (increase) {
1478                 if (!client -> interval)
1479                         client -> interval =
1480                                 client -> config -> initial_interval;
1481                 else
1482                         client -> interval += ((random () >> 2) %
1483                                                (2 * client -> interval));
1484
1485                 /* Don't backoff past cutoff. */
1486                 if (client -> interval >
1487                     client -> config -> backoff_cutoff)
1488                         client -> interval =
1489                                 ((client -> config -> backoff_cutoff / 2)
1490                                  + ((random () >> 2) %
1491                                     client -> config -> backoff_cutoff));
1492         } else if (!client -> interval)
1493                 client -> interval = client -> config -> initial_interval;
1494                 
1495         /* If the backoff would take us to the panic timeout, just use that
1496            as the interval. */
1497         if (cur_time + client -> interval >
1498             client -> first_sending + client -> config -> timeout)
1499                 client -> interval =
1500                         (client -> first_sending +
1501                          client -> config -> timeout) - cur_time + 1;
1502
1503         /* Record the number of seconds since we started sending. */
1504         if (interval < 65536)
1505                 client -> packet.secs = htons (interval);
1506         else
1507                 client -> packet.secs = htons (65535);
1508         client -> secs = client -> packet.secs;
1509
1510         log_info ("DHCPDISCOVER on %s to %s port %d interval %ld",
1511               client -> name ? client -> name : client -> interface -> name,
1512               inet_ntoa (sockaddr_broadcast.sin_addr),
1513               ntohs (sockaddr_broadcast.sin_port), (long)(client -> interval));
1514
1515         /* Send out a packet. */
1516         result = send_packet (client -> interface, (struct packet *)0,
1517                               &client -> packet,
1518                               client -> packet_length,
1519                               inaddr_any, &sockaddr_broadcast,
1520                               (struct hardware *)0);
1521
1522         add_timeout (cur_time + client -> interval,
1523                      send_discover, client, 0, 0);
1524 }
1525
1526 /* state_panic gets called if we haven't received any offers in a preset
1527    amount of time.   When this happens, we try to use existing leases that
1528    haven't yet expired, and failing that, we call the client script and
1529    hope it can do something. */
1530
1531 void state_panic (cpp)
1532         void *cpp;
1533 {
1534         struct client_state *client = cpp;
1535         struct client_lease *loop;
1536         struct client_lease *lp;
1537
1538         if (client -> interface -> linkstate == NOLINK)
1539                 return;
1540
1541         loop = lp = client -> active;
1542
1543         log_info ("No DHCPOFFERS received.");
1544
1545         /* We may not have an active lease, but we may have some
1546            predefined leases that we can try. */
1547         if (!client -> active && client -> leases)
1548                 goto activate_next;
1549
1550         /* Run through the list of leases and see if one can be used. */
1551         while (client -> active) {
1552                 if (client -> active -> expiry > cur_time) {
1553                         log_info ("Trying recorded lease %s",
1554                               piaddr (client -> active -> address));
1555                         /* Run the client script with the existing
1556                            parameters. */
1557                         script_init (client, "TIMEOUT",
1558                                      client -> active -> medium);
1559                         script_write_params (client, "new_", client -> active);
1560                         if (client -> alias)
1561                                 script_write_params (client, "alias_",
1562                                                      client -> alias);
1563
1564                         /* If the old lease is still good and doesn't
1565                            yet need renewal, go into BOUND state and
1566                            timeout at the renewal time. */
1567                         if (!script_go (client)) {
1568                             if (cur_time < client -> active -> renewal) {
1569                                 client -> state = S_BOUND;
1570                                 log_info ("bound: renewal in %ld %s.",
1571                                           (long)(client -> active -> renewal -
1572                                                  cur_time), "seconds");
1573 #ifdef ENABLE_POLLING_MODE
1574                                 /* Enable polling for this interface */
1575                                 client -> interface -> polling = 1;
1576 #endif
1577                                 add_timeout (client -> active -> renewal,
1578                                              state_bound, client, 0, 0);
1579                             } else {
1580                                 client -> state = S_BOUND;
1581                                 log_info ("bound: immediate renewal.");
1582                                 state_bound (client);
1583                             }
1584                             /*
1585                              * Set the link status back to nolink, even
1586                              * if we have media settings.
1587                              */
1588                             client -> interface -> linkstate = NOLINK;
1589                             reinitialize_interfaces ();
1590                             go_daemon ();
1591                             return;
1592                         }
1593                 }
1594
1595                 /* If there are no other leases, give up. */
1596                 if (!client -> leases) {
1597                         client -> leases = client -> active;
1598                         client -> active = (struct client_lease *)0;
1599                         break;
1600                 }
1601
1602         activate_next:
1603                 /* Otherwise, put the active lease at the end of the
1604                    lease list, and try another lease.. */
1605                 for (lp = client -> leases; lp -> next; lp = lp -> next)
1606                         ;
1607                 lp -> next = client -> active;
1608                 if (lp -> next) {
1609                         lp -> next -> next = (struct client_lease *)0;
1610                 }
1611                 client -> active = client -> leases;
1612                 client -> leases = client -> leases -> next;
1613
1614                 /* If we already tried this lease, we've exhausted the
1615                    set of leases, so we might as well give up for
1616                    now. */
1617                 if (client -> active == loop)
1618                         break;
1619                 else if (!loop)
1620                         loop = client -> active;
1621         }
1622
1623         /* No leases were available, or what was available didn't work, so
1624            tell the shell script that we failed to allocate an address,
1625            and try again later. */
1626         if (onetry) {
1627                 if (!quiet)
1628                         log_info ("Unable to obtain a lease on first try.%s",
1629                                   "  Exiting.");
1630                 exit (2);
1631         }
1632
1633         log_info ("No working leases in persistent database - sleeping.");
1634
1635 #ifdef ENABLE_POLLING_MODE
1636         /* Enable polling for this interface */
1637         client -> interface -> polling = 1;
1638 #endif
1639
1640         script_init (client, "FAIL", (struct string_list *)0);
1641         if (client -> alias)
1642                 script_write_params (client, "alias_", client -> alias);
1643         script_go (client);
1644         client -> state = S_INIT;
1645         add_timeout (cur_time +
1646                      ((client -> config -> retry_interval + 1) / 2 +
1647                       (random () % client -> config -> retry_interval)),
1648                      state_init, client, 0, 0);
1649         go_daemon ();
1650 }
1651
1652 void send_request (cpp)
1653         void *cpp;
1654 {
1655         struct client_state *client = cpp;
1656
1657         int result;
1658         int interval;
1659         struct sockaddr_in destination;
1660         struct in_addr from;
1661
1662         /* Figure out how long it's been since we started transmitting. */
1663         interval = cur_time - client -> first_sending;
1664
1665         /* If we're in the INIT-REBOOT or REQUESTING state and we're
1666            past the reboot timeout, go to INIT and see if we can
1667            DISCOVER an address... */
1668         /* XXX In the INIT-REBOOT state, if we don't get an ACK, it
1669            means either that we're on a network with no DHCP server,
1670            or that our server is down.  In the latter case, assuming
1671            that there is a backup DHCP server, DHCPDISCOVER will get
1672            us a new address, but we could also have successfully
1673            reused our old address.  In the former case, we're hosed
1674            anyway.  This is not a win-prone situation. */
1675         if ((client -> state == S_REBOOTING ||
1676              client -> state == S_REQUESTING) &&
1677             interval > client -> config -> reboot_timeout) {
1678         cancel:
1679                 client -> state = S_INIT;
1680                 cancel_timeout (send_request, client);
1681                 state_init (client);
1682                 return;
1683         }
1684
1685         /* If we're in the reboot state, make sure the media is set up
1686            correctly. */
1687         if (client -> state == S_REBOOTING &&
1688             !client -> medium &&
1689             client -> active -> medium ) {
1690                 script_init (client, "MEDIUM", client -> active -> medium);
1691
1692                 /* If the medium we chose won't fly, go to INIT state. */
1693                 if (script_go (client))
1694                         goto cancel;
1695
1696                 /* Record the medium. */
1697                 client -> medium = client -> active -> medium;
1698         }
1699
1700         /* If the lease has expired, relinquish the address and go back
1701            to the INIT state. */
1702         if (client -> state != S_REQUESTING &&
1703             cur_time > client -> active -> expiry) {
1704                 /* Run the client script with the new parameters. */
1705                 script_init (client, "EXPIRE", (struct string_list *)0);
1706                 script_write_params (client, "old_", client -> active);
1707                 if (client -> alias)
1708                         script_write_params (client, "alias_",
1709                                              client -> alias);
1710                 script_go (client);
1711
1712                 /* Now do a preinit on the interface so that we can
1713                    discover a new address. */
1714                 script_init (client, "PREINIT", (struct string_list *)0);
1715                 if (client -> alias)
1716                         script_write_params (client, "alias_",
1717                                              client -> alias);
1718                 script_go (client);
1719
1720                 client -> state = S_INIT;
1721                 state_init (client);
1722                 return;
1723         }
1724
1725         /* Do the exponential backoff... */
1726         if (!client -> interval)
1727                 client -> interval = client -> config -> initial_interval;
1728         else {
1729                 client -> interval += ((random () >> 2) %
1730                                        (2 * client -> interval));
1731         }
1732         
1733         /* Don't backoff past cutoff. */
1734         if (client -> interval >
1735             client -> config -> backoff_cutoff)
1736                 client -> interval =
1737                         ((client -> config -> backoff_cutoff / 2)
1738                          + ((random () >> 2) % client -> interval));
1739
1740         /* If the backoff would take us to the expiry time, just set the
1741            timeout to the expiry time. */
1742         if (client -> state != S_REQUESTING &&
1743             cur_time + client -> interval > client -> active -> expiry)
1744                 client -> interval =
1745                         client -> active -> expiry - cur_time + 1;
1746
1747         /* If the lease T2 time has elapsed, or if we're not yet bound,
1748            broadcast the DHCPREQUEST rather than unicasting. */
1749         if (client -> state == S_REQUESTING ||
1750             client -> state == S_REBOOTING ||
1751             cur_time > client -> active -> rebind)
1752                 destination.sin_addr = sockaddr_broadcast.sin_addr;
1753         else
1754                 memcpy (&destination.sin_addr.s_addr,
1755                         client -> destination.iabuf,
1756                         sizeof destination.sin_addr.s_addr);
1757         destination.sin_port = remote_port;
1758         destination.sin_family = AF_INET;
1759 #ifdef HAVE_SA_LEN
1760         destination.sin_len = sizeof destination;
1761 #endif
1762
1763         if (client -> state == S_RENEWING ||
1764             client -> state == S_REBINDING)
1765                 memcpy (&from, client -> active -> address.iabuf,
1766                         sizeof from);
1767         else
1768                 from.s_addr = INADDR_ANY;
1769
1770         /* Record the number of seconds since we started sending. */
1771         if (client -> state == S_REQUESTING)
1772                 client -> packet.secs = client -> secs;
1773         else {
1774                 if (interval < 65536)
1775                         client -> packet.secs = htons (interval);
1776                 else
1777                         client -> packet.secs = htons (65535);
1778         }
1779
1780         log_info ("DHCPREQUEST on %s to %s port %d",
1781               client -> name ? client -> name : client -> interface -> name,
1782               inet_ntoa (destination.sin_addr),
1783               ntohs (destination.sin_port));
1784
1785         if (destination.sin_addr.s_addr != INADDR_BROADCAST &&
1786             fallback_interface)
1787                 result = send_packet (fallback_interface,
1788                                       (struct packet *)0,
1789                                       &client -> packet,
1790                                       client -> packet_length,
1791                                       from, &destination,
1792                                       (struct hardware *)0);
1793         else
1794                 /* Send out a packet. */
1795                 result = send_packet (client -> interface, (struct packet *)0,
1796                                       &client -> packet,
1797                                       client -> packet_length,
1798                                       from, &destination,
1799                                       (struct hardware *)0);
1800
1801         add_timeout (cur_time + client -> interval,
1802                      send_request, client, 0, 0);
1803 }
1804
1805 void send_decline (cpp)
1806         void *cpp;
1807 {
1808         struct client_state *client = cpp;
1809
1810         int result;
1811
1812         log_info ("DHCPDECLINE on %s to %s port %d",
1813               client -> name ? client -> name : client -> interface -> name,
1814               inet_ntoa (sockaddr_broadcast.sin_addr),
1815               ntohs (sockaddr_broadcast.sin_port));
1816
1817         /* Send out a packet. */
1818         result = send_packet (client -> interface, (struct packet *)0,
1819                               &client -> packet,
1820                               client -> packet_length,
1821                               inaddr_any, &sockaddr_broadcast,
1822                               (struct hardware *)0);
1823 }
1824
1825 void send_release (cpp)
1826         void *cpp;
1827 {
1828         struct client_state *client = cpp;
1829
1830         int result;
1831         struct sockaddr_in destination;
1832         struct in_addr from;
1833
1834         memcpy (&from, client -> active -> address.iabuf,
1835                 sizeof from);
1836         memcpy (&destination.sin_addr.s_addr,
1837                 client -> destination.iabuf,
1838                 sizeof destination.sin_addr.s_addr);
1839         destination.sin_port = remote_port;
1840         destination.sin_family = AF_INET;
1841 #ifdef HAVE_SA_LEN
1842         destination.sin_len = sizeof destination;
1843 #endif
1844
1845         /* Set the lease to end now, so that we don't accidentally
1846            reuse it if we restart before the old expiry time. */
1847         client -> active -> expiry =
1848                 client -> active -> renewal =
1849                 client -> active -> rebind = cur_time;
1850         if (!write_client_lease (client, client -> active, 1, 1)) {
1851                 log_error ("Can't release lease: lease write failed.");
1852                 return;
1853         }
1854
1855         log_info ("DHCPRELEASE on %s to %s port %d",
1856               client -> name ? client -> name : client -> interface -> name,
1857               inet_ntoa (destination.sin_addr),
1858               ntohs (destination.sin_port));
1859
1860         if (fallback_interface)
1861                 result = send_packet (fallback_interface,
1862                                       (struct packet *)0,
1863                                       &client -> packet,
1864                                       client -> packet_length,
1865                                       from, &destination,
1866                                       (struct hardware *)0);
1867         else
1868                 /* Send out a packet. */
1869                 result = send_packet (client -> interface, (struct packet *)0,
1870                                       &client -> packet,
1871                                       client -> packet_length,
1872                                       from, &destination,
1873                                       (struct hardware *)0);
1874 }
1875
1876 void make_client_options (client, lease, type, sid, rip, prl, op)
1877         struct client_state *client;
1878         struct client_lease *lease;
1879         u_int8_t *type;
1880         struct option_cache *sid;
1881         struct iaddr *rip;
1882         u_int32_t *prl;
1883         struct option_state **op;
1884 {
1885         unsigned i;
1886         struct option_cache *oc;
1887         struct buffer *bp = (struct buffer *)0;
1888
1889         /* If there are any leftover options, get rid of them. */
1890         if (*op)
1891                 option_state_dereference (op, MDL);
1892
1893         /* Allocate space for options. */
1894         option_state_allocate (op, MDL);
1895
1896         /* Send the server identifier if provided. */
1897         if (sid)
1898                 save_option (&dhcp_universe, *op, sid);
1899
1900         oc = (struct option_cache *)0;
1901
1902         /* Send the requested address if provided. */
1903         if (rip) {
1904                 client -> requested_address = *rip;
1905                 if (!(make_const_option_cache
1906                       (&oc, (struct buffer **)0, rip -> iabuf, rip -> len,
1907                        &dhcp_options [DHO_DHCP_REQUESTED_ADDRESS], MDL)))
1908                         log_error ("can't make requested address cache.");
1909                 else {
1910                         save_option (&dhcp_universe, *op, oc);
1911                         option_cache_dereference (&oc, MDL);
1912                 }
1913         } else {
1914                 client -> requested_address.len = 0;
1915         }
1916
1917         if (!(make_const_option_cache
1918               (&oc, (struct buffer **)0,
1919                type, 1, &dhcp_options [DHO_DHCP_MESSAGE_TYPE], MDL)))
1920                 log_error ("can't make message type.");
1921         else {
1922                 save_option (&dhcp_universe, *op, oc);
1923                 option_cache_dereference (&oc, MDL);
1924         }
1925
1926         if (prl) {
1927                 /* Figure out how many parameters were requested. */
1928                 for (i = 0; prl [i]; i++)
1929                         ;
1930                 if (!buffer_allocate (&bp, i, MDL))
1931                         log_error ("can't make parameter list buffer.");
1932                 else {
1933                         for (i = 0; prl [i]; i++)
1934                                 bp -> data [i] = prl [i];
1935                         if (!(make_const_option_cache
1936                               (&oc, &bp, (u_int8_t *)0, i,
1937                                &dhcp_options [DHO_DHCP_PARAMETER_REQUEST_LIST],
1938                                MDL)))
1939                                 log_error ("can't make option cache");
1940                         else {
1941                                 save_option (&dhcp_universe, *op, oc);
1942                                 option_cache_dereference (&oc, MDL);
1943                         }
1944                 }
1945         }
1946
1947         /* Run statements that need to be run on transmission. */
1948         if (client -> config -> on_transmission)
1949                 execute_statements_in_scope
1950                         ((struct binding_value **)0,
1951                          (struct packet *)0, (struct lease *)0, client,
1952                          (lease ? lease -> options : (struct option_state *)0),
1953                          *op, &global_scope,
1954                          client -> config -> on_transmission,
1955                          (struct group *)0);
1956 }
1957
1958 void make_discover (client, lease)
1959         struct client_state *client;
1960         struct client_lease *lease;
1961 {
1962         unsigned char discover = DHCPDISCOVER;
1963         int i;
1964         struct option_state *options = (struct option_state *)0;
1965
1966         memset (&client -> packet, 0, sizeof (client -> packet));
1967
1968         make_client_options (client,
1969                              lease, &discover, (struct option_cache *)0,
1970                              lease ? &lease -> address : (struct iaddr *)0,
1971                              client -> config -> requested_options,
1972                              &options);
1973
1974         /* Set up the option buffer... */
1975         client -> packet_length =
1976                 cons_options ((struct packet *)0, &client -> packet,
1977                               (struct lease *)0, client,
1978                               /* maximum packet size */1500,
1979                               (struct option_state *)0,
1980                               options,
1981                               /* scope */ &global_scope,
1982                               /* overload */ 0,
1983                               /* terminate */0,
1984                               /* bootpp    */0,
1985                               (struct data_string *)0,
1986                               client -> config -> vendor_space_name);
1987
1988         option_state_dereference (&options, MDL);
1989         if (client -> packet_length < BOOTP_MIN_LEN)
1990                 client -> packet_length = BOOTP_MIN_LEN;
1991
1992         client -> packet.op = BOOTREQUEST;
1993         client -> packet.htype = client -> interface -> hw_address.hbuf [0];
1994         client -> packet.hlen = client -> interface -> hw_address.hlen - 1;
1995         client -> packet.hops = 0;
1996         client -> packet.xid = random ();
1997         client -> packet.secs = 0; /* filled in by send_discover. */
1998
1999         if (can_receive_unicast_unconfigured (client -> interface))
2000                 client -> packet.flags = 0;
2001         else
2002                 client -> packet.flags = htons (BOOTP_BROADCAST);
2003
2004         memset (&(client -> packet.ciaddr),
2005                 0, sizeof client -> packet.ciaddr);
2006         memset (&(client -> packet.yiaddr),
2007                 0, sizeof client -> packet.yiaddr);
2008         memset (&(client -> packet.siaddr),
2009                 0, sizeof client -> packet.siaddr);
2010         client -> packet.giaddr = giaddr;
2011         if (client -> interface -> hw_address.hlen > 0)
2012             memcpy (client -> packet.chaddr,
2013                     &client -> interface -> hw_address.hbuf [1],
2014                     (unsigned)(client -> interface -> hw_address.hlen - 1));
2015
2016 #ifdef DEBUG_PACKET
2017         dump_raw ((unsigned char *)&client -> packet, client -> packet_length);
2018 #endif
2019 }
2020
2021
2022 void make_request (client, lease)
2023         struct client_state *client;
2024         struct client_lease *lease;
2025 {
2026         unsigned char request = DHCPREQUEST;
2027         int i, j;
2028         unsigned char *tmp, *digest;
2029         unsigned char *old_digest_loc;
2030         struct option_cache *oc;
2031
2032         memset (&client -> packet, 0, sizeof (client -> packet));
2033
2034         if (client -> state == S_REQUESTING)
2035                 oc = lookup_option (&dhcp_universe, lease -> options,
2036                                     DHO_DHCP_SERVER_IDENTIFIER);
2037         else
2038                 oc = (struct option_cache *)0;
2039
2040         make_client_options (client, lease, &request, oc,
2041                              ((client -> state == S_REQUESTING ||
2042                                client -> state == S_REBOOTING)
2043                               ? &lease -> address
2044                               : (struct iaddr *)0),
2045                              client -> config -> requested_options,
2046                              &client -> sent_options);
2047
2048         /* Set up the option buffer... */
2049         client -> packet_length =
2050                 cons_options ((struct packet *)0, &client -> packet,
2051                               (struct lease *)0, client,
2052                               /* maximum packet size */1500,
2053                               (struct option_state *)0,
2054                               client -> sent_options, 
2055                               /* scope */ &global_scope,
2056                               /* overload */ 0,
2057                               /* terminate */0,
2058                               /* bootpp    */0,
2059                               (struct data_string *)0,
2060                               client -> config -> vendor_space_name);
2061
2062         option_state_dereference (&client -> sent_options, MDL);
2063         if (client -> packet_length < BOOTP_MIN_LEN)
2064                 client -> packet_length = BOOTP_MIN_LEN;
2065
2066         client -> packet.op = BOOTREQUEST;
2067         client -> packet.htype = client -> interface -> hw_address.hbuf [0];
2068         client -> packet.hlen = client -> interface -> hw_address.hlen - 1;
2069         client -> packet.hops = 0;
2070         client -> packet.xid = client -> xid;
2071         client -> packet.secs = 0; /* Filled in by send_request. */
2072
2073         /* If we own the address we're requesting, put it in ciaddr;
2074            otherwise set ciaddr to zero. */
2075         if (client -> state == S_BOUND ||
2076             client -> state == S_RENEWING ||
2077             client -> state == S_REBINDING) {
2078                 memcpy (&client -> packet.ciaddr,
2079                         lease -> address.iabuf, lease -> address.len);
2080                 client -> packet.flags = 0;
2081         } else {
2082                 memset (&client -> packet.ciaddr, 0,
2083                         sizeof client -> packet.ciaddr);
2084                 if (can_receive_unicast_unconfigured (client -> interface))
2085                         client -> packet.flags = 0;
2086                 else
2087                         client -> packet.flags = htons (BOOTP_BROADCAST);
2088         }
2089
2090         memset (&client -> packet.yiaddr, 0,
2091                 sizeof client -> packet.yiaddr);
2092         memset (&client -> packet.siaddr, 0,
2093                 sizeof client -> packet.siaddr);
2094         if (client -> state != S_BOUND &&
2095             client -> state != S_RENEWING)
2096                 client -> packet.giaddr = giaddr;
2097         else
2098                 memset (&client -> packet.giaddr, 0,
2099                         sizeof client -> packet.giaddr);
2100         if (client -> interface -> hw_address.hlen > 0)
2101             memcpy (client -> packet.chaddr,
2102                     &client -> interface -> hw_address.hbuf [1],
2103                     (unsigned)(client -> interface -> hw_address.hlen - 1));
2104
2105 #ifdef DEBUG_PACKET
2106         dump_raw ((unsigned char *)&client -> packet, client -> packet_length);
2107 #endif
2108 }
2109
2110 void make_decline (client, lease)
2111         struct client_state *client;
2112         struct client_lease *lease;
2113 {
2114         unsigned char decline = DHCPDECLINE;
2115         int i;
2116         struct option_cache *oc;
2117
2118         struct option_state *options = (struct option_state *)0;
2119
2120         oc = lookup_option (&dhcp_universe, lease -> options,
2121                             DHO_DHCP_SERVER_IDENTIFIER);
2122         make_client_options (client, lease, &decline, oc,
2123                              &lease -> address, (u_int32_t *)0, &options);
2124
2125         /* Set up the option buffer... */
2126         memset (&client -> packet, 0, sizeof (client -> packet));
2127         client -> packet_length =
2128                 cons_options ((struct packet *)0, &client -> packet,
2129                               (struct lease *)0, client, 0,
2130                               (struct option_state *)0, options,
2131                               &global_scope, 0, 0, 0, (struct data_string *)0,
2132                               client -> config -> vendor_space_name);
2133         option_state_dereference (&options, MDL);
2134         if (client -> packet_length < BOOTP_MIN_LEN)
2135                 client -> packet_length = BOOTP_MIN_LEN;
2136         option_state_dereference (&options, MDL);
2137
2138         client -> packet.op = BOOTREQUEST;
2139         client -> packet.htype = client -> interface -> hw_address.hbuf [0];
2140         client -> packet.hlen = client -> interface -> hw_address.hlen - 1;
2141         client -> packet.hops = 0;
2142         client -> packet.xid = client -> xid;
2143         client -> packet.secs = 0; /* Filled in by send_request. */
2144         if (can_receive_unicast_unconfigured (client -> interface))
2145                 client -> packet.flags = 0;
2146         else
2147                 client -> packet.flags = htons (BOOTP_BROADCAST);
2148
2149         /* ciaddr must always be zero. */
2150         memset (&client -> packet.ciaddr, 0,
2151                 sizeof client -> packet.ciaddr);
2152         memset (&client -> packet.yiaddr, 0,
2153                 sizeof client -> packet.yiaddr);
2154         memset (&client -> packet.siaddr, 0,
2155                 sizeof client -> packet.siaddr);
2156         client -> packet.giaddr = giaddr;
2157         memcpy (client -> packet.chaddr,
2158                 &client -> interface -> hw_address.hbuf [1],
2159                 client -> interface -> hw_address.hlen);
2160
2161 #ifdef DEBUG_PACKET
2162         dump_raw ((unsigned char *)&client -> packet, client -> packet_length);
2163 #endif
2164 }
2165
2166 void make_release (client, lease)
2167         struct client_state *client;
2168         struct client_lease *lease;
2169 {
2170         unsigned char request = DHCPRELEASE;
2171         int i;
2172         struct option_cache *oc;
2173
2174         struct option_state *options = (struct option_state *)0;
2175
2176         memset (&client -> packet, 0, sizeof (client -> packet));
2177
2178         oc = lookup_option (&dhcp_universe, lease -> options,
2179                             DHO_DHCP_SERVER_IDENTIFIER);
2180         make_client_options (client, lease, &request, oc,
2181                              (struct iaddr *)0, (u_int32_t *)0,
2182                              &options);
2183
2184         /* Set up the option buffer... */
2185         client -> packet_length =
2186                 cons_options ((struct packet *)0, &client -> packet,
2187                               (struct lease *)0, client,
2188                               /* maximum packet size */1500,
2189                               (struct option_state *)0,
2190                               options,
2191                               /* scope */ &global_scope,
2192                               /* overload */ 0,
2193                               /* terminate */0,
2194                               /* bootpp    */0,
2195                               (struct data_string *)0,
2196                               client -> config -> vendor_space_name);
2197
2198         if (client -> packet_length < BOOTP_MIN_LEN)
2199                 client -> packet_length = BOOTP_MIN_LEN;
2200         option_state_dereference (&options, MDL);
2201
2202         client -> packet.op = BOOTREQUEST;
2203         client -> packet.htype = client -> interface -> hw_address.hbuf [0];
2204         client -> packet.hlen = client -> interface -> hw_address.hlen - 1;
2205         client -> packet.hops = 0;
2206         client -> packet.xid = random ();
2207         client -> packet.secs = 0;
2208         client -> packet.flags = 0;
2209         memcpy (&client -> packet.ciaddr,
2210                 lease -> address.iabuf, lease -> address.len);
2211         memset (&client -> packet.yiaddr, 0,
2212                 sizeof client -> packet.yiaddr);
2213         memset (&client -> packet.siaddr, 0,
2214                 sizeof client -> packet.siaddr);
2215         client -> packet.giaddr = giaddr;
2216         memcpy (client -> packet.chaddr,
2217                 &client -> interface -> hw_address.hbuf [1],
2218                 client -> interface -> hw_address.hlen);
2219
2220 #ifdef DEBUG_PACKET
2221         dump_raw ((unsigned char *)&client -> packet, client -> packet_length);
2222 #endif
2223 }
2224
2225 void destroy_client_lease (lease)
2226         struct client_lease *lease;
2227 {
2228         int i;
2229
2230         if (lease -> server_name)
2231                 dfree (lease -> server_name, MDL);
2232         if (lease -> filename)
2233                 dfree (lease -> filename, MDL);
2234         option_state_dereference (&lease -> options, MDL);
2235         free_client_lease (lease, MDL);
2236 }
2237
2238 FILE *leaseFile;
2239
2240 void rewrite_client_leases ()
2241 {
2242         struct interface_info *ip;
2243         struct client_state *client;
2244         struct client_lease *lp;
2245
2246         if (leaseFile)
2247                 fclose (leaseFile);
2248         leaseFile = fopen (path_dhclient_db, "w");
2249         if (!leaseFile) {
2250                 log_error ("can't create %s: %m", path_dhclient_db);
2251                 return;
2252         }
2253
2254         /* Write out all the leases attached to configured interfaces that
2255            we know about. */
2256         for (ip = interfaces; ip; ip = ip -> next) {
2257                 for (client = ip -> client; client; client = client -> next) {
2258                         for (lp = client -> leases; lp; lp = lp -> next) {
2259                                 write_client_lease (client, lp, 1, 0);
2260                         }
2261                         if (client -> active)
2262                                 write_client_lease (client,
2263                                                     client -> active, 1, 0);
2264                 }
2265         }
2266
2267         /* Write out any leases that are attached to interfaces that aren't
2268            currently configured. */
2269         for (ip = dummy_interfaces; ip; ip = ip -> next) {
2270                 for (client = ip -> client; client; client = client -> next) {
2271                         for (lp = client -> leases; lp; lp = lp -> next) {
2272                                 write_client_lease (client, lp, 1, 0);
2273                         }
2274                         if (client -> active)
2275                                 write_client_lease (client,
2276                                                     client -> active, 1, 0);
2277                 }
2278         }
2279         fflush (leaseFile);
2280 }
2281
2282 void write_lease_option (struct option_cache *oc,
2283                          struct packet *packet, struct lease *lease,
2284                          struct client_state *client_state,
2285                          struct option_state *in_options,
2286                          struct option_state *cfg_options,
2287                          struct binding_scope **scope,
2288                          struct universe *u, void *stuff)
2289 {
2290         const char *name, *dot;
2291         struct data_string ds;
2292         int status;
2293         struct client_state *client;
2294
2295         memset (&ds, 0, sizeof ds);
2296
2297         if (u != &dhcp_universe) {
2298                 name = u -> name;
2299                 dot = ".";
2300         } else {
2301                 name = "";
2302                 dot = "";
2303         }
2304         if (evaluate_option_cache (&ds, packet, lease, client_state,
2305                                    in_options, cfg_options, scope, oc, MDL)) {
2306                 fprintf (leaseFile,
2307                          "  option %s%s%s %s;\n",
2308                          name, dot, oc -> option -> name,
2309                          pretty_print_option (oc -> option,
2310                                               ds.data, ds.len, 1, 1));
2311                 data_string_forget (&ds, MDL);
2312         }
2313 }
2314
2315 int write_client_lease (client, lease, rewrite, makesure)
2316         struct client_state *client;
2317         struct client_lease *lease;
2318         int rewrite;
2319         int makesure;
2320 {
2321         int i;
2322         struct tm *t;
2323         static int leases_written;
2324         struct option_cache *oc;
2325         struct data_string ds;
2326         pair *hash;
2327         int errors = 0;
2328         char *s;
2329
2330         if (!rewrite) {
2331                 if (leases_written++ > 20) {
2332                         rewrite_client_leases ();
2333                         leases_written = 0;
2334                 }
2335         }
2336
2337         /* If the lease came from the config file, we don't need to stash
2338            a copy in the lease database. */
2339         if (lease -> is_static)
2340                 return 1;
2341
2342         if (!leaseFile) {       /* XXX */
2343                 leaseFile = fopen (path_dhclient_db, "w");
2344                 if (!leaseFile) {
2345                         log_error ("can't create %s: %m", path_dhclient_db);
2346                         return 0;
2347                 }
2348         }
2349
2350         errno = 0;
2351         fprintf (leaseFile, "lease {\n");
2352         if (lease -> is_bootp) {
2353                 fprintf (leaseFile, "  bootp;\n");
2354                 if (errno) {
2355                         ++errors;
2356                         errno = 0;
2357                 }
2358         }
2359         fprintf (leaseFile, "  interface \"%s\";\n",
2360                  client -> interface -> name);
2361         if (errno) {
2362                 ++errors;
2363                 errno = 0;
2364         }
2365         if (client -> name) {
2366                 fprintf (leaseFile, "  name \"%s\";\n", client -> name);
2367                 if (errno) {
2368                         ++errors;
2369                         errno = 0;
2370                 }
2371         }
2372         fprintf (leaseFile, "  fixed-address %s;\n",
2373                  piaddr (lease -> address));
2374         if (errno) {
2375                 ++errors;
2376                 errno = 0;
2377         }
2378         if (lease -> filename) {
2379                 s = quotify_string (lease -> filename, MDL);
2380                 if (s) {
2381                         fprintf (leaseFile, "  filename \"%s\";\n", s);
2382                         if (errno) {
2383                                 ++errors;
2384                                 errno = 0;
2385                         }
2386                         dfree (s, MDL);
2387                 } else
2388                         errors++;
2389
2390         }
2391         if (lease -> server_name) {
2392                 s = quotify_string (lease -> filename, MDL);
2393                 if (s) {
2394                         fprintf (leaseFile, "  server-name \"%s\";\n", s);
2395                         if (errno) {
2396                                 ++errors;
2397                                 errno = 0;
2398                         }
2399                         dfree (s, MDL);
2400                 } else
2401                         ++errors;
2402         }
2403         if (lease -> medium) {
2404                 s = quotify_string (lease -> medium -> string, MDL);
2405                 if (s) {
2406                         fprintf (leaseFile, "  medium \"%s\";\n", s);
2407                         if (errno) {
2408                                 ++errors;
2409                                 errno = 0;
2410                         }
2411                         dfree (s, MDL);
2412                 } else
2413                         errors++;
2414         }
2415         if (errno != 0) {
2416                 errors++;
2417                 errno = 0;
2418         }
2419
2420         memset (&ds, 0, sizeof ds);
2421
2422         for (i = 0; i < lease -> options -> universe_count; i++) {
2423                 option_space_foreach ((struct packet *)0, (struct lease *)0,
2424                                       client, (struct option_state *)0,
2425                                       lease -> options, &global_scope,
2426                                       universes [i],
2427                                       client, write_lease_option);
2428         }
2429
2430         /* Note: the following is not a Y2K bug - it's a Y1.9K bug.   Until
2431            somebody invents a time machine, I think we can safely disregard
2432            it. */
2433         t = gmtime (&lease -> renewal);
2434         fprintf (leaseFile,
2435                  "  renew %d %d/%d/%d %02d:%02d:%02d;\n",
2436                  t -> tm_wday, t -> tm_year + 1900,
2437                  t -> tm_mon + 1, t -> tm_mday,
2438                  t -> tm_hour, t -> tm_min, t -> tm_sec);
2439         if (errno != 0) {
2440                 errors++;
2441                 errno = 0;
2442         }
2443         t = gmtime (&lease -> rebind);
2444         fprintf (leaseFile,
2445                  "  rebind %d %d/%d/%d %02d:%02d:%02d;\n",
2446                  t -> tm_wday, t -> tm_year + 1900,
2447                  t -> tm_mon + 1, t -> tm_mday,
2448                  t -> tm_hour, t -> tm_min, t -> tm_sec);
2449         if (errno != 0) {
2450                 errors++;
2451                 errno = 0;
2452         }
2453         t = gmtime (&lease -> expiry);
2454         fprintf (leaseFile,
2455                  "  expire %d %d/%d/%d %02d:%02d:%02d;\n",
2456                  t -> tm_wday, t -> tm_year + 1900,
2457                  t -> tm_mon + 1, t -> tm_mday,
2458                  t -> tm_hour, t -> tm_min, t -> tm_sec);
2459         if (errno != 0) {
2460                 errors++;
2461                 errno = 0;
2462         }
2463         fprintf (leaseFile, "}\n");
2464         if (errno != 0) {
2465                 errors++;
2466                 errno = 0;
2467         }
2468         fflush (leaseFile);
2469         if (errno != 0) {
2470                 errors++;
2471                 errno = 0;
2472         }
2473         if (!errors && makesure) {
2474                 if (fsync (fileno (leaseFile)) < 0) {
2475                         log_info ("write_client_lease: %m");
2476                         return 0;
2477                 }
2478         }
2479         return errors ? 0 : 1;
2480 }
2481
2482 /* Variables holding name of script and file pointer for writing to
2483    script.   Needless to say, this is not reentrant - only one script
2484    can be invoked at a time. */
2485 char scriptName [256];
2486 FILE *scriptFile;
2487
2488 void script_init (client, reason, medium)
2489         struct client_state *client;
2490         const char *reason;
2491         struct string_list *medium;
2492 {
2493         struct string_list *sl, *next;
2494
2495         if (client) {
2496                 for (sl = client -> env; sl; sl = next) {
2497                         next = sl -> next;
2498                         dfree (sl, MDL);
2499                 }
2500                 client -> env = (struct string_list *)0;
2501                 client -> envc = 0;
2502                 
2503                 if (client -> interface) {
2504                         client_envadd (client, "", "interface", "%s",
2505                                        client -> interface -> name);
2506                 }
2507                 if (client -> name)
2508                         client_envadd (client,
2509                                        "", "client", "%s", client -> name);
2510                 if (medium)
2511                         client_envadd (client,
2512                                        "", "medium", "%s", medium -> string);
2513
2514                 client_envadd (client, "", "reason", "%s", reason);
2515                 client_envadd (client, "", "pid", "%ld", (long int)getpid ());
2516         }
2517 }
2518
2519 struct envadd_state {
2520         struct client_state *client;
2521         const char *prefix;
2522 };
2523
2524 void client_option_envadd (struct option_cache *oc,
2525                            struct packet *packet, struct lease *lease,
2526                            struct client_state *client_state,
2527                            struct option_state *in_options,
2528                            struct option_state *cfg_options,
2529                            struct binding_scope **scope,
2530                            struct universe *u, void *stuff)
2531 {
2532         struct envadd_state *es = stuff;
2533         struct data_string data;
2534         memset (&data, 0, sizeof data);
2535
2536         if (evaluate_option_cache (&data, packet, lease, client_state,
2537                                    in_options, cfg_options, scope, oc, MDL)) {
2538                 if (data.len) {
2539                         char name [256];
2540                         if (dhcp_option_ev_name (name, sizeof name,
2541                                                  oc -> option)) {
2542                                 client_envadd (es -> client, es -> prefix,
2543                                                name, "%s",
2544                                                (pretty_print_option
2545                                                 (oc -> option,
2546                                                  data.data, data.len,
2547                                                  0, 0)));
2548                                 data_string_forget (&data, MDL);
2549                         }
2550                 }
2551         }
2552 }
2553
2554 void script_write_params (client, prefix, lease)
2555         struct client_state *client;
2556         const char *prefix;
2557         struct client_lease *lease;
2558 {
2559         int i;
2560         struct data_string data;
2561         struct option_cache *oc;
2562         pair *hash;
2563         char *s, *t;
2564         struct envadd_state es;
2565
2566         es.client = client;
2567         es.prefix = prefix;
2568
2569         client_envadd (client,
2570                        prefix, "ip_address", "%s", piaddr (lease -> address));
2571
2572         /* For the benefit of Linux (and operating systems which may
2573            have similar needs), compute the network address based on
2574            the supplied ip address and netmask, if provided.  Also
2575            compute the broadcast address (the host address all ones
2576            broadcast address, not the host address all zeroes
2577            broadcast address). */
2578
2579         memset (&data, 0, sizeof data);
2580         oc = lookup_option (&dhcp_universe, lease -> options, DHO_SUBNET_MASK);
2581         if (oc && evaluate_option_cache (&data, (struct packet *)0,
2582                                          (struct lease *)0, client,
2583                                          (struct option_state *)0,
2584                                          lease -> options,
2585                                          &global_scope, oc, MDL)) {
2586                 if (data.len > 3) {
2587                         struct iaddr netmask, subnet, broadcast;
2588
2589                         memcpy (netmask.iabuf, data.data, data.len);
2590                         netmask.len = data.len;
2591                         data_string_forget (&data, MDL);
2592
2593                         subnet = subnet_number (lease -> address, netmask);
2594                         if (subnet.len) {
2595                             client_envadd (client, prefix, "network_number",
2596                                            "%s", piaddr (subnet));
2597
2598                             oc = lookup_option (&dhcp_universe,
2599                                                 lease -> options,
2600                                                 DHO_BROADCAST_ADDRESS);
2601                             if (!oc ||
2602                                 !(evaluate_option_cache
2603                                   (&data, (struct packet *)0,
2604                                    (struct lease *)0, client,
2605                                    (struct option_state *)0,
2606                                    lease -> options,
2607                                    &global_scope, oc, MDL))) {
2608                                 broadcast = broadcast_addr (subnet, netmask);
2609                                 if (broadcast.len) {
2610                                     client_envadd (client,
2611                                                    prefix, "broadcast_address",
2612                                                    "%s", piaddr (broadcast));
2613                                 }
2614                             }
2615                         }
2616                 }
2617                 data_string_forget (&data, MDL);
2618         }
2619
2620         if (lease -> filename)
2621                 client_envadd (client,
2622                                prefix, "filename", "%s", lease -> filename);
2623         if (lease -> server_name)
2624                 client_envadd (client, prefix, "server_name",
2625                                "%s", lease -> server_name);
2626
2627         for (i = 0; i < lease -> options -> universe_count; i++) {
2628                 option_space_foreach ((struct packet *)0, (struct lease *)0,
2629                                       client, (struct option_state *)0,
2630                                       lease -> options, &global_scope,
2631                                       universes [i],
2632                                       &es, client_option_envadd);
2633         }
2634         client_envadd (client, prefix, "expiry", "%d", (int)(lease -> expiry));
2635 }
2636
2637 int script_go (client)
2638         struct client_state *client;
2639 {
2640         int rval;
2641         char *scriptName;
2642         char *argv [2];
2643         char **envp;
2644         char *epp [3];
2645         char reason [] = "REASON=NBI";
2646         static char client_path [] = CLIENT_PATH;
2647         int i;
2648         struct string_list *sp, *next;
2649         int pid, wpid, wstatus;
2650
2651         if (client)
2652                 scriptName = client -> config -> script_name;
2653         else
2654                 scriptName = top_level_config.script_name;
2655
2656         envp = dmalloc (((client ? client -> envc : 2) +
2657                          client_env_count + 2) * sizeof (char *), MDL);
2658         if (!envp) {
2659                 log_error ("No memory for client script environment.");
2660                 return 0;
2661         }
2662         i = 0;
2663         /* Copy out the environment specified on the command line,
2664            if any. */
2665         for (sp = client_env; sp; sp = sp -> next) {
2666                 envp [i++] = sp -> string;
2667         }
2668         /* Copy out the environment specified by dhclient. */
2669         if (client) {
2670                 for (sp = client -> env; sp; sp = sp -> next) {
2671                         envp [i++] = sp -> string;
2672                 }
2673         } else {
2674                 envp [i++] = reason;
2675         }
2676         /* Set $PATH. */
2677         envp [i++] = client_path;
2678         envp [i] = (char *)0;
2679
2680         argv [0] = scriptName;
2681         argv [1] = (char *)0;
2682
2683         pid = fork ();
2684         if (pid < 0) {
2685                 log_error ("fork: %m");
2686                 wstatus = 0;
2687         } else if (pid) {
2688                 do {
2689                         wpid = wait (&wstatus);
2690                 } while (wpid != pid && wpid > 0);
2691                 if (wpid < 0) {
2692                         log_error ("wait: %m");
2693                         wstatus = 0;
2694                 }
2695         } else {
2696                 if ((i = open(_PATH_DEVNULL, O_RDWR)) != -1) {
2697                         dup2(i, STDIN_FILENO);
2698                         dup2(i, STDOUT_FILENO);
2699                         dup2(i, STDERR_FILENO);
2700                         if (i > STDERR_FILENO)
2701                                 close(i);
2702                 }
2703                 execve (scriptName, argv, envp);
2704                 log_error ("execve (%s, ...): %m", scriptName);
2705                 exit (0);
2706         }
2707
2708         if (client) {
2709                 for (sp = client -> env; sp; sp = next) {
2710                         next = sp -> next;
2711                         dfree (sp, MDL);
2712                 }
2713                 client -> env = (struct string_list *)0;
2714                 client -> envc = 0;
2715         }
2716         dfree (envp, MDL);
2717         GET_TIME (&cur_time);
2718         return (WIFEXITED (wstatus) ?
2719                 WEXITSTATUS (wstatus) : -WTERMSIG (wstatus));
2720 }
2721
2722 void client_envadd (struct client_state *client,
2723                     const char *prefix, const char *name, const char *fmt, ...)
2724 {
2725         char spbuf [1024];
2726         char *s;
2727         unsigned len, i;
2728         struct string_list *val;
2729         va_list list;
2730
2731         va_start (list, fmt);
2732         len = vsnprintf (spbuf, sizeof spbuf, fmt, list);
2733         va_end (list);
2734
2735         val = dmalloc (strlen (prefix) + strlen (name) + 1 /* = */ +
2736                        len + sizeof *val, MDL);
2737         if (!val)
2738                 return;
2739         s = val -> string;
2740         strcpy (s, prefix);
2741         strcat (s, name);
2742         s += strlen (s);
2743         *s++ = '=';
2744         if (len >= sizeof spbuf) {
2745                 va_start (list, fmt);
2746                 vsnprintf (s, len + 1, fmt, list);
2747                 va_end (list);
2748         } else
2749                 strcpy (s, spbuf);
2750         val -> next = client -> env;
2751         client -> env = val;
2752         client -> envc++;
2753 }
2754
2755 int dhcp_option_ev_name (buf, buflen, option)
2756         char *buf;
2757         size_t buflen;
2758         struct option *option;
2759 {
2760         int i, j;
2761         const char *s;
2762
2763         j = 0;
2764         if (option -> universe != &dhcp_universe) {
2765                 s = option -> universe -> name;
2766                 i = 0;
2767         } else { 
2768                 s = option -> name;
2769                 i = 1;
2770         }
2771
2772         do {
2773                 while (*s) {
2774                         if (j + 1 == buflen)
2775                                 return 0;
2776                         if (*s == '-')
2777                                 buf [j++] = '_';
2778                         else
2779                                 buf [j++] = *s;
2780                         ++s;
2781                 }
2782                 if (!i) {
2783                         s = option -> name;
2784                         if (j + 1 == buflen)
2785                                 return 0;
2786                         buf [j++] = '_';
2787                 }
2788                 ++i;
2789         } while (i != 2);
2790
2791         buf [j] = 0;
2792         return 1;
2793 }
2794
2795 void go_daemon ()
2796 {
2797         static int state = 0;
2798         int pid;
2799         int i;
2800
2801         /* Don't become a daemon if the user requested otherwise. */
2802         if (no_daemon) {
2803                 write_client_pid_file ();
2804                 return;
2805         }
2806
2807         /* Only do it once. */
2808         if (state)
2809                 return;
2810         state = 1;
2811
2812         /* Stop logging to stderr... */
2813         log_perror = 0;
2814
2815         /* Become a daemon... */
2816         if ((pid = fork ()) < 0)
2817                 log_fatal ("Can't fork daemon: %m");
2818         else if (pid)
2819                 exit (0);
2820         /* Become session leader and get pid... */
2821         pid = setsid ();
2822
2823         /* Close standard I/O descriptors. */
2824         close(0);
2825         close(1);
2826         close(2);
2827
2828         /* Reopen them on /dev/null. */
2829         i = open ("/dev/null", O_RDWR);
2830         if (i == 0)
2831                 i = open ("/dev/null", O_RDWR);
2832         if (i == 1) {
2833                 i = open ("/dev/null", O_RDWR);
2834                 log_perror = 0; /* No sense logging to /dev/null. */
2835         } else if (i != -1)
2836                 close (i);
2837
2838         write_client_pid_file ();
2839 }
2840
2841 void write_client_pid_file ()
2842 {
2843         FILE *pf;
2844         int pfdesc;
2845
2846         pfdesc = open (path_dhclient_pid, O_CREAT | O_TRUNC | O_WRONLY, 0644);
2847
2848         if (pfdesc < 0) {
2849                 log_error ("Can't create %s: %m", path_dhclient_pid);
2850                 return;
2851         }
2852
2853         pf = fdopen (pfdesc, "w");
2854         if (!pf)
2855                 log_error ("Can't fdopen %s: %m", path_dhclient_pid);
2856         else {
2857                 fprintf (pf, "%ld\n", (long)getpid ());
2858                 fclose (pf);
2859         }
2860 }
2861
2862 void client_location_changed ()
2863 {
2864         struct interface_info *ip;
2865         struct client_state *client;
2866
2867         for (ip = interfaces; ip; ip = ip -> next) {
2868                 for (client = ip -> client; client; client = client -> next) {
2869                         switch (client -> state) {
2870                               case S_SELECTING:
2871                                 cancel_timeout (send_discover, client);
2872                                 break;
2873
2874                               case S_BOUND:
2875                                 cancel_timeout (state_bound, client);
2876                                 break;
2877
2878                               case S_REBOOTING:
2879                               case S_REQUESTING:
2880                               case S_RENEWING:
2881                                 cancel_timeout (send_request, client);
2882                                 break;
2883
2884                               case S_INIT:
2885                               case S_REBINDING:
2886                               case S_STOPPED:
2887                                 break;
2888                         }
2889 #ifndef ENABLE_POLLING_MODE
2890                         client -> state = S_INIT;
2891                         state_reboot (client);
2892 #endif
2893                 }
2894         }
2895 }
2896
2897 void do_release(client) 
2898         struct client_state *client;
2899 {
2900         struct data_string ds;
2901         struct option_cache *oc;
2902
2903         /* Pick a random xid. */
2904         client -> xid = random ();
2905
2906         /* is there even a lease to release? */
2907         if (client -> active) {
2908                 /* Make a DHCPRELEASE packet, and set appropriate per-interface
2909                    flags. */
2910                 make_release (client, client -> active);
2911
2912                 memset (&ds, 0, sizeof ds);
2913                 oc = lookup_option (&dhcp_universe,
2914                                     client -> active -> options,
2915                                     DHO_DHCP_SERVER_IDENTIFIER);
2916                 if (oc &&
2917                     evaluate_option_cache (&ds, (struct packet *)0,
2918                                            (struct lease *)0, client,
2919                                            (struct option_state *)0,
2920                                            client -> active -> options,
2921                                            &global_scope, oc, MDL)) {
2922                         if (ds.len > 3) {
2923                                 memcpy (client -> destination.iabuf,
2924                                         ds.data, 4);
2925                                 client -> destination.len = 4;
2926                         } else
2927                                 client -> destination = iaddr_broadcast;
2928                 } else
2929                         client -> destination = iaddr_broadcast;
2930                 client -> first_sending = cur_time;
2931                 client -> interval = client -> config -> initial_interval;
2932         
2933                 /* Zap the medium list... */
2934                 client -> medium = (struct string_list *)0;
2935         
2936                 /* Send out the first and only DHCPRELEASE packet. */
2937                 send_release (client);
2938
2939                 /* Do the client script RELEASE operation. */
2940                 script_init (client,
2941                              "RELEASE", (struct string_list *)0);
2942                 if (client -> alias)
2943                         script_write_params (client, "alias_",
2944                                              client -> alias);
2945                 script_write_params (client, "old_", client -> active);
2946                 script_go (client);
2947         }
2948
2949         /* Cancel any timeouts. */
2950         cancel_timeout (state_bound, client);
2951         cancel_timeout (send_discover, client);
2952         cancel_timeout (state_init, client);
2953         cancel_timeout (send_request, client);
2954         cancel_timeout (state_reboot, client);
2955         client -> state = S_STOPPED;
2956 }
2957
2958 int dhclient_interface_shutdown_hook (struct interface_info *interface)
2959 {
2960         do_release (interface -> client);
2961
2962         return 1;
2963 }
2964
2965 int dhclient_interface_discovery_hook (struct interface_info *tmp)
2966 {
2967         struct interface_info *last, *ip;
2968         /* See if we can find the client from dummy_interfaces */
2969         last = 0;
2970         for (ip = dummy_interfaces; ip; ip = ip -> next) {
2971                 if (!strcmp (ip -> name, tmp -> name)) {
2972                         /* Remove from dummy_interfaces */
2973                         if (last) {
2974                                 ip = (struct interface_info *)0;
2975                                 interface_reference (&ip, last -> next, MDL);
2976                                 interface_dereference (&last -> next, MDL);
2977                                 if (ip -> next) {
2978                                         interface_reference (&last -> next,
2979                                                              ip -> next, MDL);
2980                                         interface_dereference (&ip -> next,
2981                                                                MDL);
2982                                 }
2983                         } else {
2984                                 ip = (struct interface_info *)0;
2985                                 interface_reference (&ip,
2986                                                      dummy_interfaces, MDL);
2987                                 interface_dereference (&dummy_interfaces, MDL);
2988                                 if (ip -> next) {
2989                                         interface_reference (&dummy_interfaces,
2990                                                              ip -> next, MDL);
2991                                         interface_dereference (&ip -> next,
2992                                                                MDL);
2993                                 }
2994                         }
2995                         /* Copy "client" to tmp */
2996                         if (ip -> client) {
2997                                 tmp -> client = ip -> client;
2998                                 tmp -> client -> interface = tmp;
2999                         }
3000                         interface_dereference (&ip, MDL);
3001                         break;
3002                 }
3003                 last = ip;
3004         }
3005         return 1;
3006 }
3007
3008 isc_result_t dhclient_interface_startup_hook (struct interface_info *interface)
3009 {
3010         struct interface_info *ip;
3011         struct client_state *client;
3012
3013         /* This code needs some rethinking.   It doesn't test against
3014            a signal name, and it just kind of bulls into doing something
3015            that may or may not be appropriate. */
3016
3017         if (interfaces) {
3018                 interface_reference (&interface -> next, interfaces, MDL);
3019                 interface_dereference (&interfaces, MDL);
3020         }
3021         interface_reference (&interfaces, interface, MDL);
3022
3023         discover_interfaces (DISCOVER_UNCONFIGURED);
3024
3025         for (ip = interfaces; ip; ip = ip -> next) {
3026                 /* If interfaces were specified, don't configure
3027                    interfaces that weren't specified! */
3028                 if (ip -> flags & INTERFACE_RUNNING ||
3029                    (ip -> flags & (INTERFACE_REQUESTED |
3030                                      INTERFACE_AUTOMATIC)) !=
3031                      INTERFACE_REQUESTED)
3032                         continue;
3033                 script_init (ip -> client,
3034                              "PREINIT", (struct string_list *)0);
3035                 if (ip -> client -> alias)
3036                         script_write_params (ip -> client, "alias_",
3037                                              ip -> client -> alias);
3038                 script_go (ip -> client);
3039         }
3040         
3041         discover_interfaces (interfaces_requested
3042                              ? DISCOVER_REQUESTED
3043                              : DISCOVER_RUNNING);
3044
3045         for (ip = interfaces; ip; ip = ip -> next) {
3046                 if (ip -> flags & INTERFACE_RUNNING)
3047                         continue;
3048                 ip -> flags |= INTERFACE_RUNNING;
3049                 for (client = ip -> client; client; client = client -> next) {
3050                         client -> state = S_INIT;
3051                         /* Set up a timeout to start the initialization
3052                            process. */
3053                         add_timeout (cur_time + random () % 5,
3054                                      state_reboot, client, 0, 0);
3055                 }
3056         }
3057         return ISC_R_SUCCESS;
3058 }
3059
3060 /* The client should never receive a relay agent information option,
3061    so if it does, log it and discard it. */
3062
3063 int parse_agent_information_option (packet, len, data)
3064         struct packet *packet;
3065         int len;
3066         u_int8_t *data;
3067 {
3068         return 1;
3069 }
3070
3071 /* The client never sends relay agent information options. */
3072
3073 unsigned cons_agent_information_options (cfg_options, outpacket,
3074                                          agentix, length)
3075         struct option_state *cfg_options;
3076         struct dhcp_packet *outpacket;
3077         unsigned agentix;
3078         unsigned length;
3079 {
3080         return length;
3081 }
3082
3083 static void shutdown_exit (void *foo)
3084 {
3085         exit (0);
3086 }
3087
3088 isc_result_t dhcp_set_control_state (control_object_state_t oldstate,
3089                                      control_object_state_t newstate)
3090 {
3091         struct interface_info *ip;
3092         struct client_state *client;
3093
3094         /* Do the right thing for each interface. */
3095         for (ip = interfaces; ip; ip = ip -> next) {
3096             for (client = ip -> client; client; client = client -> next) {
3097                 switch (newstate) {
3098                   case server_startup:
3099                     return ISC_R_SUCCESS;
3100
3101                   case server_running:
3102                     return ISC_R_SUCCESS;
3103
3104                   case server_shutdown:
3105                     if (client -> active &&
3106                         client -> active -> expiry > cur_time) {
3107                             if (client -> config -> do_forward_update)
3108                                     client_dns_update (client, 0, 0);
3109                             do_release (client);
3110                     }
3111                     break;
3112
3113                   case server_hibernate:
3114                     state_stop (client);
3115                     break;
3116
3117                   case server_awaken:
3118 #ifndef ENABLE_POLLING_MODE
3119                     state_reboot (client);
3120 #endif
3121                     break;
3122                 }
3123             }
3124         }
3125         if (newstate == server_shutdown)
3126                 add_timeout (cur_time + 1, shutdown_exit, 0, 0, 0);
3127         return ISC_R_SUCCESS;
3128 }
3129
3130 /* Called after a timeout if the DNS update failed on the previous try.
3131    Retries the update, and if it times out, schedules a retry after
3132    ten times as long of a wait. */
3133
3134 void client_dns_update_timeout (void *cp)
3135 {
3136         struct client_state *client = cp;
3137         isc_result_t status;
3138
3139         if (client -> active) {
3140                 status = client_dns_update (client, 1,
3141                                             (client -> active -> renewal -
3142                                              cur_time));
3143                 if (status == ISC_R_TIMEDOUT) {
3144                         client -> dns_update_timeout *= 10;
3145                         add_timeout (cur_time + client -> dns_update_timeout,
3146                                      client_dns_update_timeout, client, 0, 0);
3147                 }
3148         }
3149 }
3150                         
3151 /* See if we should do a DNS update, and if so, do it. */
3152
3153 isc_result_t client_dns_update (struct client_state *client, int addp, int ttl)
3154 {
3155         struct data_string ddns_fqdn, ddns_fwd_name,
3156                ddns_dhcid, client_identifier;
3157         struct option_cache *oc;
3158         int ignorep;
3159         int result;
3160         isc_result_t rcode;
3161
3162         /* If we didn't send an FQDN option, we certainly aren't going to
3163            be doing an update. */
3164         if (!client -> sent_options)
3165                 return ISC_R_SUCCESS;
3166
3167         /* If we don't have a lease, we can't do an update. */
3168         if (!client -> active)
3169                 return ISC_R_SUCCESS;
3170
3171         /* If we set the no client update flag, don't do the update. */
3172         if ((oc = lookup_option (&fqdn_universe, client -> sent_options,
3173                                   FQDN_NO_CLIENT_UPDATE)) &&
3174             evaluate_boolean_option_cache (&ignorep, (struct packet *)0,
3175                                            (struct lease *)0, client,
3176                                            client -> sent_options,
3177                                            (struct option_state *)0,
3178                                            &global_scope, oc, MDL))
3179                 return ISC_R_SUCCESS;
3180         
3181         /* If we set the "server, please update" flag, or didn't set it
3182            to false, don't do the update. */
3183         if (!(oc = lookup_option (&fqdn_universe, client -> sent_options,
3184                                   FQDN_SERVER_UPDATE)) ||
3185             evaluate_boolean_option_cache (&ignorep, (struct packet *)0,
3186                                            (struct lease *)0, client,
3187                                            client -> sent_options,
3188                                            (struct option_state *)0,
3189                                            &global_scope, oc, MDL))
3190                 return ISC_R_SUCCESS;
3191         
3192         /* If no FQDN option was supplied, don't do the update. */
3193         memset (&ddns_fwd_name, 0, sizeof ddns_fwd_name);
3194         if (!(oc = lookup_option (&fqdn_universe, client -> sent_options,
3195                                   FQDN_FQDN)) ||
3196             !evaluate_option_cache (&ddns_fwd_name, (struct packet *)0, 
3197                                     (struct lease *)0, client,
3198                                     client -> sent_options,
3199                                     (struct option_state *)0,
3200                                     &global_scope, oc, MDL))
3201                 return ISC_R_SUCCESS;
3202
3203         /* Make a dhcid string out of either the client identifier,
3204            if we are sending one, or the interface's MAC address,
3205            otherwise. */
3206         memset (&ddns_dhcid, 0, sizeof ddns_dhcid);
3207
3208         memset (&client_identifier, 0, sizeof client_identifier);
3209         if ((oc = lookup_option (&dhcp_universe, client -> sent_options,
3210                                  DHO_DHCP_CLIENT_IDENTIFIER)) &&
3211             evaluate_option_cache (&client_identifier, (struct packet *)0, 
3212                                    (struct lease *)0, client,
3213                                    client -> sent_options,
3214                                    (struct option_state *)0,
3215                                    &global_scope, oc, MDL)) {
3216                 result = get_dhcid (&ddns_dhcid,
3217                                     DHO_DHCP_CLIENT_IDENTIFIER,
3218                                     client_identifier.data,
3219                                     client_identifier.len);
3220                 data_string_forget (&client_identifier, MDL);
3221         } else
3222                 result = get_dhcid (&ddns_dhcid, 0,
3223                                     client -> interface -> hw_address.hbuf,
3224                                     client -> interface -> hw_address.hlen);
3225         if (!result) {
3226                 data_string_forget (&ddns_fwd_name, MDL);
3227                 return ISC_R_SUCCESS;
3228         }
3229
3230         /* Start the resolver, if necessary. */
3231         if (!resolver_inited) {
3232                 minires_ninit (&resolver_state);
3233                 resolver_inited = 1;
3234                 resolver_state.retrans = 1;
3235                 resolver_state.retry = 1;
3236         }
3237
3238         /*
3239          * Perform updates.
3240          */
3241         if (ddns_fwd_name.len && ddns_dhcid.len) {
3242                 if (addp)
3243                         rcode = ddns_update_a (&ddns_fwd_name,
3244                                                client -> active -> address,
3245                                                &ddns_dhcid, ttl,
3246                                                1);
3247                 else
3248                         rcode = ddns_remove_a (&ddns_fwd_name,
3249                                                client -> active -> address,
3250                                                &ddns_dhcid);
3251         }
3252         
3253         data_string_forget (&ddns_fwd_name, MDL);
3254         data_string_forget (&ddns_dhcid, MDL);
3255         return rcode;
3256 }
3257
3258 /* Check to see if there's a wire plugged in */
3259 int
3260 interface_active(struct interface_info *ip) {
3261 #ifdef __FreeBSD__
3262         struct ifmediareq ifmr;
3263         int *media_list, i;
3264         char *ifname;
3265         int sock;
3266
3267         ifname = ip -> name;
3268
3269         if ((sock = socket (AF_INET, SOCK_DGRAM, IPPROTO_UDP)) < 0)
3270                 log_fatal ("Can't create interface_active socket");
3271
3272         (void) memset (&ifmr, 0, sizeof (ifmr));
3273         (void) strncpy (ifmr.ifm_name, ifname, sizeof (ifmr.ifm_name));
3274
3275         if (ioctl (sock, SIOCGIFMEDIA, (caddr_t)&ifmr) < 0) {
3276                 /*
3277                  * Interface doesn't support SIOCGIFMEDIA, presume okay
3278                  */
3279                 close (sock);
3280                 return (HAVELINK);
3281         }
3282         close (sock);
3283
3284         if (ifmr.ifm_count == 0) {
3285                 /*
3286                  * Assume that this means interface
3287                  * does not support SIOCGIFMEDIA
3288                  */
3289                 log_fatal ("%s: no media types?", ifname);
3290                 return (HAVELINK);
3291         }
3292
3293         if (ifmr.ifm_status & IFM_AVALID) {
3294                 if (ip -> ieee80211) {
3295                         /*
3296                          * Wavelan devices need to be checked if they are
3297                          * associated.
3298                          */
3299                         if ((IFM_TYPE(ifmr.ifm_active) == IFM_IEEE80211) &&
3300                              (ifmr.ifm_status & IFM_ACTIVE)) {
3301                                 return (HAVELINK);
3302                         }
3303                 } else {
3304                         if (ifmr.ifm_status & IFM_ACTIVE) {
3305                                 return (HAVELINK);
3306                         }
3307                 }
3308                 /*
3309                  * We really have no link.
3310                  */
3311                 return (NOLINK);
3312         }
3313         /*
3314          * IFM_AVALID is not set. We cannot check
3315          * the link state. Assume HAVELINK.
3316          */
3317
3318 #endif /* Other OSs */
3319         /*
3320          * Always return a successful link if the OS
3321          * is not supported.
3322          */
3323         return (HAVELINK);
3324 }
3325
3326 #ifdef __FreeBSD__
3327 #if defined(DRAGONFLY_FUTURE)
3328 void
3329 set_ieee80211 (struct interface_info *ip) {
3330
3331         struct ieee80211req     ireq;
3332         u_int8_t                data[32];
3333         int                     associated = 0;
3334         int *media_list, i;
3335         char *ifname;
3336         int sock;
3337
3338         ifname = ip -> name;
3339
3340         if ((sock = socket (AF_INET, SOCK_DGRAM, IPPROTO_UDP)) < 0)
3341                 log_fatal ("Can't create interface_active socket");
3342
3343         (void) memset (&ireq, 0, sizeof (ireq));
3344         (void) strncpy (ireq.i_name, ifname, sizeof (ireq.i_name));
3345         ireq.i_data = &data;
3346         ireq.i_type = IEEE80211_IOC_SSID;
3347         ireq.i_val = -1;
3348         /*
3349          * If we can't get the SSID,
3350          * this isn't an 802.11 device.
3351          */
3352         if (ioctl (sock, SIOCG80211, &ireq) < 0)
3353                 ip -> ieee80211 = 0;
3354         else {
3355 #ifdef DEBUG
3356                 printf ("Device %s has 802.11\n", ifname);
3357 #endif
3358                 ip -> ieee80211 = 1;
3359         }
3360         close (sock);
3361 }
3362 #endif /* __FreeBSD__ */
3363 #endif
3364
3365 #ifdef ENABLE_POLLING_MODE
3366 /* Go to background after some time */
3367 void state_background (cpp)
3368         void *cpp;
3369 {
3370         go_daemon ();
3371 }
3372
3373 /* Check the state of the NICs if we have link */
3374 void state_polling (cpp)
3375         void *cpp;
3376 {
3377         struct interface_info *ip;
3378         struct client_state *client;
3379         int result;
3380
3381         for (ip = interfaces; ip; ip = ip -> next) {
3382                 if (! ip -> polling)
3383                         continue;
3384 #ifdef DEBUG
3385                 printf ("%s: Polling interface state\n", ip -> name);
3386                 for (client = ip -> client;
3387                      client; client = client -> next) {
3388                         printf ("%s: client state of %d\n", ip -> name, ip -> client -> state);
3389                         printf ("%s: link = %d\n", ip -> name, ip -> linkstate);
3390                 }
3391 #endif
3392
3393                 result = interface_active (ip);
3394                 /*
3395                  * If dhclient.conf contains media settings, we cannot
3396                  * abort if the interface is not set to active mode.
3397                  */
3398                 if (ip -> havemedia && ip -> client -> state != S_BOUND) {
3399                         if (result == HAVELINK)
3400                                 ip -> forcediscover = 1;
3401                         result = HAVELINK;
3402                 }
3403
3404                 /*
3405                  * The last status of the interface tells us
3406                  * the we've got no link ...
3407                  */
3408                 if (ip -> linkstate == NOLINK || ! doinitcheck) {
3409                         /*
3410                          * ... but we have now link. Let's send
3411                          * requests.
3412                          */
3413                         if (result == HAVELINK) {
3414 #ifdef DEBUG
3415                                 if (ip -> havemedia)
3416                                         printf ("%s: Trying media settings on interface\n",
3417                                                 ip -> name);
3418                                 else
3419                                         printf ("%s: Found Link on interface\n", ip -> name);
3420 #endif
3421                                 /*
3422                                  * Set the interface to state_reboot. But of
3423                                  * course we can not be sure that we really got link,
3424                                  * we just assume it.
3425                                  */
3426                                 for (client = ip -> client;
3427                                      client; client = client -> next) {
3428                                                 cancel_timeout (state_init, client);
3429                                                 cancel_timeout (state_reboot, client);
3430                                                 cancel_timeout (state_selecting, client);
3431                                                 add_timeout (cur_time + random () % 5,
3432                                                             state_reboot, client, 0, 0);
3433                                 }
3434                                 ip -> linkstate = HAVELINK;
3435                         } else {
3436 #ifdef DEBUG
3437                                 printf ("%s: No link on interface\n", ip -> name);
3438 #endif
3439                                 for (client = ip -> client;
3440                                      client; client = client -> next) {
3441                                         /*
3442                                          * Without this add_timout(), dhclient does
3443                                          * not poll on a interface if there
3444                                          * is no cable plugged in at startup
3445                                          * time. Because we add one additional second 
3446                                          * to the time of a normal timeout, we always
3447                                          * skip and block a running one. This prevents
3448                                          * that polling is done twice at the same time.
3449                                          */
3450                                         if (client -> state == S_INIT) {
3451                                                 add_timeout (cur_time + (polling_interval + 1),
3452                                                              state_polling, client, 0, 0);
3453                                         }
3454                                 }
3455                                 ip -> linkstate = NOLINK;
3456                                 /*
3457                                  * Automatically go into the background after
3458                                  * some time. Do this only if there are no
3459                                  * media options available for a interface.
3460                                  */
3461                                 if (! ip -> havemedia && ! doinitcheck) {
3462                                         add_timeout (cur_time + (polling_interval * 2),
3463                                                     state_background, client, 0, 0);
3464                                 }
3465                         }
3466                 }
3467
3468                 /*
3469                  * The last status of the interface tells us
3470                  * the we previously had link.
3471                  */
3472                 if (ip -> linkstate == HAVELINK && doinitcheck) {
3473                         if (result == NOLINK) {
3474                                 /*
3475                                  * We lost link on the interface, or it isn't
3476                                  * associated anymore.
3477                                  */
3478 #ifdef DEBUG
3479                                 printf ("%s: Lost Link on interface\n", ip -> name);
3480 #endif
3481                                 /*
3482                                  * After we lost link, cycle again through the
3483                                  * different media settings if available. Else
3484                                  * set NOLINK.
3485                                  */
3486                                 if (ip -> havemedia)
3487                                         ip -> forcediscover = 1;
3488                                 else
3489                                         ip -> linkstate = NOLINK;
3490                         }
3491                         /*
3492                          * If we happen to have a real link, but no
3493                          * active lease, force the interface into
3494                          * state_reboot. Do the same if media settings
3495                          * are available.
3496                          */
3497                         if (ip -> forcediscover) {
3498                                 for (client = ip -> client;
3499                                      client; client = client -> next) {
3500                                         if (client -> state != S_REBOOTING &&
3501                                             client -> state != S_SELECTING) {
3502                                                 add_timeout (cur_time + random () % 5,
3503                                                             state_reboot, client, 0, 0);
3504                                         }
3505                                 }
3506                                 ip -> forcediscover = 0;
3507                                 ip -> linkstate = HAVELINK;
3508                         }
3509                         /* We still have link, do nothing. */
3510                 }
3511         }
3512         doinitcheck = 1;
3513 }
3514 #endif /* ifdef ENABLE_POLLING_MODE */