1/* dhcp.c
2
3   DHCP Protocol engine. */
4
5/*
6 * Copyright (c) 2004-2005 by Internet Systems Consortium, Inc. ("ISC")
7 * Copyright (c) 1995-2003 by Internet Software Consortium
8 *
9 * Permission to use, copy, modify, and distribute this software for any
10 * purpose with or without fee is hereby granted, provided that the above
11 * copyright notice and this permission notice appear in all copies.
12 *
13 * THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES
14 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
15 * MERCHANTABILITY AND FITNESS.  IN NO EVENT SHALL ISC BE LIABLE FOR
16 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
17 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
18 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT
19 * OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
20 *
21 *   Internet Systems Consortium, Inc.
22 *   950 Charter Street
23 *   Redwood City, CA 94063
24 *   <info@isc.org>
25 *   http://www.isc.org/
26 *
27 * This software has been written for Internet Systems Consortium
28 * by Ted Lemon in cooperation with Vixie Enterprises and Nominum, Inc.
29 * To learn more about Internet Systems Consortium, see
30 * ``http://www.isc.org/''.  To learn more about Vixie Enterprises,
31 * see ``http://www.vix.com''.   To learn more about Nominum, Inc., see
32 * ``http://www.nominum.com''.
33 */
34
35#ifndef lint
36static char copyright[] =
37"$Id: dhcp.c,v 1.13 2011/10/17 16:35:23 mbalmer Exp $ Copyright (c) 2004-2005 Internet Systems Consortium.  All rights reserved.\n";
38#endif /* not lint */
39
40#include "dhcpd.h"
41
42int outstanding_pings;
43
44static char dhcp_message [256];
45
46static const char *dhcp_type_names [] = {
47	"DHCPDISCOVER",
48	"DHCPOFFER",
49	"DHCPREQUEST",
50	"DHCPDECLINE",
51	"DHCPACK",
52	"DHCPNAK",
53	"DHCPRELEASE",
54	"DHCPINFORM"
55};
56const int dhcp_type_name_max = ((sizeof dhcp_type_names) / sizeof (char *));
57
58#if defined (TRACING)
59# define send_packet trace_packet_send
60#endif
61
62void dhcp (packet)
63	struct packet *packet;
64{
65	int ms_nulltp = 0;
66	struct option_cache *oc;
67	struct lease *lease = (struct lease *)0;
68	const char *errmsg;
69	struct data_string data;
70
71	if (!locate_network (packet) &&
72	    packet -> packet_type != DHCPREQUEST &&
73	    packet -> packet_type != DHCPINFORM) {
74		const char *s;
75		char typebuf [32];
76		errmsg = "unknown network segment";
77	      bad_packet:
78
79		if (packet -> packet_type > 0 &&
80		    packet -> packet_type < dhcp_type_name_max - 1) {
81			s = dhcp_type_names [packet -> packet_type - 1];
82		} else {
83			/* %Audit% Cannot exceed 28 bytes. %2004.06.17,Safe% */
84			sprintf (typebuf, "type %d", packet -> packet_type);
85			s = typebuf;
86		}
87
88		log_info ("%s from %s via %s: %s", s,
89			  (packet -> raw -> htype
90			   ? print_hw_addr (packet -> raw -> htype,
91					    packet -> raw -> hlen,
92					    packet -> raw -> chaddr)
93			   : "<no identifier>"),
94			  packet -> raw -> giaddr.s_addr
95			  ? inet_ntoa (packet -> raw -> giaddr)
96			  : packet -> interface -> name, errmsg);
97		goto out;
98	}
99
100	/* There is a problem with the relay agent information option,
101	   which is that in order for a normal relay agent to append
102	   this option, the relay agent has to have been involved in
103	   getting the packet from the client to the server.  Note
104	   that this is the software entity known as the relay agent,
105	   _not_ the hardware entity known as a router in which the
106	   relay agent may be running, so the fact that a router has
107	   forwarded a packet does not mean that the relay agent in
108	   the router was involved.
109
110	   So when the client is in INIT or INIT-REBOOT or REBINDING
111	   state, the relay agent gets to tack on its options, but
112	   when it's not, the relay agent doesn't get to do this,
113	   which means that any decisions the DHCP server may make
114	   based on the agent options will be made incorrectly.
115
116	   We work around this in the following way: if this is a
117	   DHCPREQUEST and doesn't have relay agent information
118	   options, we see if there's an existing lease for this IP
119	   address and this client that _does_ have stashed agent
120	   options.   If so, then we tack those options onto the
121	   packet as if they came from the client.   Later on, when we
122	   are deciding whether to steal the agent options from the
123	   packet, if the agent options stashed on the lease are the
124	   same as those stashed on the packet, we don't steal them -
125	   this ensures that the client never receives its agent
126	   options. */
127
128	if (packet -> packet_type == DHCPREQUEST &&
129	    packet -> raw -> ciaddr.s_addr &&
130	    !packet -> raw -> giaddr.s_addr &&
131	    packet -> options != NULL &&
132	    (packet -> options -> universe_count < agent_universe.index ||
133	     !packet -> options -> universes [agent_universe.index]))
134	{
135		struct iaddr cip;
136
137		cip.len = sizeof packet -> raw -> ciaddr;
138		memcpy (cip.iabuf, &packet -> raw -> ciaddr,
139			sizeof packet -> raw -> ciaddr);
140		if (!find_lease_by_ip_addr (&lease, cip, MDL))
141			goto nolease;
142
143		/* If there are no agent options on the lease, it's not
144		   interesting. */
145		if (!lease -> agent_options)
146			goto nolease;
147
148		/* The client should not be unicasting a renewal if its lease
149		   has expired, so make it go through the process of getting
150		   its agent options legally. */
151		if (lease -> ends < cur_time)
152			goto nolease;
153
154		if (lease -> uid_len) {
155			oc = lookup_option (&dhcp_universe, packet -> options,
156					    DHO_DHCP_CLIENT_IDENTIFIER);
157			if (!oc)
158				goto nolease;
159
160			memset (&data, 0, sizeof data);
161			if (!evaluate_option_cache (&data,
162						    packet, (struct lease *)0,
163						    (struct client_state *)0,
164						    packet -> options,
165						    (struct option_state *)0,
166						    &global_scope, oc, MDL))
167				goto nolease;
168			if (lease -> uid_len != data.len ||
169			    memcmp (lease -> uid, data.data, data.len)) {
170				data_string_forget (&data, MDL);
171				goto nolease;
172			}
173			data_string_forget (&data, MDL);
174		} else
175			if ((lease -> hardware_addr.hbuf [0] !=
176			     packet -> raw -> htype) ||
177			    (lease -> hardware_addr.hlen - 1 !=
178			     packet -> raw -> hlen) ||
179			    memcmp (&lease -> hardware_addr.hbuf [1],
180				    packet -> raw -> chaddr,
181				    packet -> raw -> hlen))
182				goto nolease;
183
184		/* Okay, so we found a lease that matches the client. */
185		option_chain_head_reference ((struct option_chain_head **)
186					     &(packet -> options -> universes
187					       [agent_universe.index]),
188					     lease -> agent_options, MDL);
189	}
190      nolease:
191
192	/* Classify the client. */
193	if ((oc = lookup_option (&dhcp_universe, packet -> options,
194				 DHO_HOST_NAME))) {
195		if (!oc -> expression)
196			while (oc -> data.len &&
197			       oc -> data.data [oc -> data.len - 1] == 0) {
198				ms_nulltp = 1;
199				oc -> data.len--;
200			}
201	}
202
203	classify_client (packet);
204
205	switch (packet -> packet_type) {
206	      case DHCPDISCOVER:
207		dhcpdiscover (packet, ms_nulltp);
208		break;
209
210	      case DHCPREQUEST:
211		dhcprequest (packet, ms_nulltp, lease);
212		break;
213
214	      case DHCPRELEASE:
215		dhcprelease (packet, ms_nulltp);
216		break;
217
218	      case DHCPDECLINE:
219		dhcpdecline (packet, ms_nulltp);
220		break;
221
222	      case DHCPINFORM:
223		dhcpinform (packet, ms_nulltp);
224		break;
225
226
227	      case DHCPACK:
228	      case DHCPOFFER:
229	      case DHCPNAK:
230		break;
231
232	      default:
233		errmsg = "unknown packet type";
234		goto bad_packet;
235	}
236      out:
237	if (lease)
238		lease_dereference (&lease, MDL);
239}
240
241void dhcpdiscover (packet, ms_nulltp)
242	struct packet *packet;
243	int ms_nulltp;
244{
245	struct lease *lease = (struct lease *)0;
246	char msgbuf [1024]; /* XXX */
247	TIME when;
248	const char *s;
249	int allocatedp = 0;
250	int peer_has_leases = 0;
251	int alloc_lease_called = 0;
252#if defined (FAILOVER_PROTOCOL)
253	dhcp_failover_state_t *peer;
254#endif
255
256	find_lease (&lease, packet, packet -> shared_network,
257		    0, &allocatedp, (struct lease *)0, MDL);
258
259	if (lease && lease -> client_hostname) {
260		if ((strlen (lease -> client_hostname) <= 64) &&
261		    db_printable (lease -> client_hostname))
262			s = lease -> client_hostname;
263		else
264			s = "Hostname Unsuitable for Printing";
265	} else
266		s = (char *)0;
267
268	/* %Audit% This is log output. %2004.06.17,Safe%
269	 * If we truncate we hope the user can get a hint from the log.
270	 */
271	snprintf (msgbuf, sizeof msgbuf, "DHCPDISCOVER from %s %s%s%svia %s",
272		 (packet -> raw -> htype
273		  ? print_hw_addr (packet -> raw -> htype,
274				   packet -> raw -> hlen,
275				   packet -> raw -> chaddr)
276		  : (lease
277		     ? print_hex_1 (lease -> uid_len, lease -> uid,
278				    lease -> uid_len)
279		     : "<no identifier>")),
280		  s ? "(" : "", s ? s : "", s ? ") " : "",
281		  packet -> raw -> giaddr.s_addr
282		  ? inet_ntoa (packet -> raw -> giaddr)
283		  : packet -> interface -> name);
284
285	/* Sourceless packets don't make sense here. */
286	if (!packet -> shared_network) {
287		log_info ("Packet from unknown subnet: %s",
288		      inet_ntoa (packet -> raw -> giaddr));
289		goto out;
290	}
291
292#if defined (FAILOVER_PROTOCOL)
293	if (lease && lease -> pool && lease -> pool -> failover_peer) {
294		peer = lease -> pool -> failover_peer;
295
296		/* If the lease is ours to allocate, then allocate it,
297		   but set the allocatedp flag. */
298		if (lease_mine_to_reallocate (lease))
299			allocatedp = 1;
300
301		/* If the lease is active, do load balancing to see who
302		   allocates the lease (if it's active, it already belongs
303		   to the client, or we wouldn't have gotten it from
304		   find_lease (). */
305		else if (lease -> binding_state == FTS_ACTIVE &&
306			 (peer -> service_state != cooperating ||
307			  load_balance_mine (packet, peer)))
308			;
309
310		/* Otherwise, we can't let the client have this lease. */
311		else {
312#if defined (DEBUG_FIND_LEASE)
313		    log_debug ("discarding %s - %s",
314			       piaddr (lease -> ip_addr),
315			       binding_state_print (lease -> binding_state));
316#endif
317		    lease_dereference (&lease, MDL);
318		}
319	}
320#endif
321
322	/* If we didn't find a lease, try to allocate one... */
323	if (!lease) {
324		if (!packet -> shared_network -> pools) {
325			log_info ("%s: network %s: no address pool",
326				  msgbuf, packet -> shared_network -> name);
327			return;
328		}
329		if (!allocate_lease (&lease, packet,
330				     packet -> shared_network -> pools,
331				     &peer_has_leases)) {
332			if (peer_has_leases)
333				log_error ("%s: peer holds all free leases",
334					   msgbuf);
335			else
336				log_error ("%s: network %s: no free leases",
337					   msgbuf,
338					   packet -> shared_network -> name);
339			return;
340		}
341#if defined (FAILOVER_PROTOCOL)
342		if (lease -> pool && lease -> pool -> failover_peer)
343			dhcp_failover_pool_check (lease -> pool);
344#endif
345		allocatedp = 1;
346		alloc_lease_called = 1;
347	}
348
349#if defined (FAILOVER_PROTOCOL)
350	if (lease && lease -> pool && lease -> pool -> failover_peer) {
351		peer = lease -> pool -> failover_peer;
352		if (peer -> service_state == not_responding ||
353		    peer -> service_state == service_startup) {
354			log_info ("%s: not responding%s",
355				  msgbuf, peer -> nrr);
356			goto out;
357		}
358	} else
359		peer = (dhcp_failover_state_t *)0;
360
361	/* Do load balancing if configured. */
362	/* If the lease is newly allocated, and we're not the server that
363	   the client would normally get with load balancing, and the
364	   failover protocol state is normal, let the other server get this.
365	   XXX Check protocol spec to make sure that predicating this on
366	   XXX allocatedp is okay - I'm doing this so that the client won't
367	   XXX be forced to switch servers (and IP addresses) just because
368	   XXX of bad luck, when it's possible for it to get the address it
369	   XXX is requesting.    Not sure this is allowed.  */
370	if (allocatedp && peer && (peer -> service_state == cooperating) &&
371	    !load_balance_mine (packet, peer)) {
372		/* peer_has_leases only has a chance to be set if we called
373		 * allocate_lease() above.
374		 */
375		if (!alloc_lease_called || peer_has_leases) {
376			log_debug ("%s: load balance to peer %s",
377				   msgbuf, peer -> name);
378			goto out;
379		} else {
380			log_debug ("cancel load balance to peer %s - %s",
381				   peer -> name, "no free leases");
382		}
383	}
384#endif
385
386	/* If it's an expired lease, get rid of any bindings. */
387	if (lease -> ends < cur_time && lease -> scope)
388		binding_scope_dereference (&lease -> scope, MDL);
389
390	/* Set the lease to really expire in 2 minutes, unless it has
391	   not yet expired, in which case leave its expiry time alone. */
392	when = cur_time + 120;
393	if (when < lease -> ends)
394		when = lease -> ends;
395
396	ack_lease (packet, lease, DHCPOFFER, when, msgbuf, ms_nulltp,
397		   (struct host_decl *)0);
398      out:
399	if (lease)
400		lease_dereference (&lease, MDL);
401}
402
403void dhcprequest (packet, ms_nulltp, ip_lease)
404	struct packet *packet;
405	int ms_nulltp;
406	struct lease *ip_lease;
407{
408	struct lease *lease;
409	struct iaddr cip;
410	struct iaddr sip;
411	struct subnet *subnet;
412	int ours = 0;
413	struct option_cache *oc;
414	struct data_string data;
415	char msgbuf [1024]; /* XXX */
416	const char *s;
417	char smbuf [19];
418#if defined (FAILOVER_PROTOCOL)
419	dhcp_failover_state_t *peer;
420#endif
421	int have_server_identifier = 0;
422	int have_requested_addr = 0;
423
424	oc = lookup_option (&dhcp_universe, packet -> options,
425			    DHO_DHCP_REQUESTED_ADDRESS);
426	memset (&data, 0, sizeof data);
427	if (oc &&
428	    evaluate_option_cache (&data, packet, (struct lease *)0,
429				   (struct client_state *)0,
430				   packet -> options, (struct option_state *)0,
431				   &global_scope, oc, MDL)) {
432		cip.len = 4;
433		memcpy (cip.iabuf, data.data, 4);
434		data_string_forget (&data, MDL);
435		have_requested_addr = 1;
436	} else {
437		oc = (struct option_cache *)0;
438		cip.len = 4;
439		memcpy (cip.iabuf, &packet -> raw -> ciaddr.s_addr, 4);
440	}
441
442	/* Find the lease that matches the address requested by the
443	   client. */
444
445	subnet = (struct subnet *)0;
446	lease = (struct lease *)0;
447	if (find_subnet (&subnet, cip, MDL))
448		find_lease (&lease, packet,
449			    subnet -> shared_network, &ours, 0, ip_lease, MDL);
450	/* XXX consider using allocatedp arg to find_lease to see
451	   XXX that this isn't a compliant DHCPREQUEST. */
452
453	if (lease && lease -> client_hostname) {
454		if ((strlen (lease -> client_hostname) <= 64) &&
455		    db_printable (lease -> client_hostname))
456			s = lease -> client_hostname;
457		else
458			s = "Hostname Unsuitable for Printing";
459	} else
460		s = (char *)0;
461
462	oc = lookup_option (&dhcp_universe, packet -> options,
463			    DHO_DHCP_SERVER_IDENTIFIER);
464	memset (&data, 0, sizeof data);
465	if (oc &&
466	    evaluate_option_cache (&data, packet, (struct lease *)0,
467				   (struct client_state *)0,
468				   packet -> options, (struct option_state *)0,
469				   &global_scope, oc, MDL)) {
470		sip.len = 4;
471		memcpy (sip.iabuf, data.data, 4);
472		data_string_forget (&data, MDL);
473		/* piaddr() should not return more than a 15 byte string.
474		 * safe.
475		 */
476		sprintf (smbuf, " (%s)", piaddr (sip));
477		have_server_identifier = 1;
478	} else
479		smbuf [0] = 0;
480
481	/* %Audit% This is log output. %2004.06.17,Safe%
482	 * If we truncate we hope the user can get a hint from the log.
483	 */
484	snprintf (msgbuf, sizeof msgbuf,
485		 "DHCPREQUEST for %s%s from %s %s%s%svia %s",
486		 piaddr (cip), smbuf,
487		 (packet -> raw -> htype
488		  ? print_hw_addr (packet -> raw -> htype,
489				   packet -> raw -> hlen,
490				   packet -> raw -> chaddr)
491		  : (lease
492		     ? print_hex_1 (lease -> uid_len, lease -> uid,
493				    lease -> uid_len)
494		     : "<no identifier>")),
495		 s ? "(" : "", s ? s : "", s ? ") " : "",
496		  packet -> raw -> giaddr.s_addr
497		  ? inet_ntoa (packet -> raw -> giaddr)
498		  : packet -> interface -> name);
499
500#if defined (FAILOVER_PROTOCOL)
501	if (lease && lease -> pool && lease -> pool -> failover_peer) {
502		peer = lease -> pool -> failover_peer;
503		if (peer -> service_state == not_responding ||
504		    peer -> service_state == service_startup) {
505			log_info ("%s: not responding%s",
506				  msgbuf, peer -> nrr);
507			goto out;
508		}
509
510		/* "load balance to peer" - is not done at all for request.
511		 *
512		 * If it's RENEWING, we are the only server to hear it, so
513		 * we have to serve it.   If it's REBINDING, it's out of
514		 * communication with the other server, so there's no point
515		 * in waiting to serve it.    However, if the lease we're
516		 * offering is not a free lease, then we may be the only
517		 * server that can offer it, so we can't load balance if
518		 * the lease isn't in the free or backup state.  If it is
519		 * in the free or backup state, then that state is what
520		 * mandates one server or the other should perform the
521		 * allocation, not the LBA...we know the peer cannot
522		 * allocate a request for an address in our free state.
523		 *
524		 * So our only compass is lease_mine_to_reallocate().  This
525		 * effects both load balancing, and a sanity-check that we
526		 * are not going to try to allocate a lease that isn't ours.
527		 */
528		if ((lease -> binding_state == FTS_FREE ||
529		     lease -> binding_state == FTS_BACKUP) &&
530		    !lease_mine_to_reallocate (lease)) {
531			log_debug ("%s: lease owned by peer", msgbuf);
532			goto out;
533		}
534
535		/* If the lease is in a transitional state, we can't
536		   renew it. */
537		if ((lease -> binding_state == FTS_RELEASED ||
538		     lease -> binding_state == FTS_EXPIRED) &&
539		    !lease_mine_to_reallocate (lease)) {
540			log_debug ("%s: lease in transition state %s", msgbuf,
541				   lease -> binding_state == FTS_RELEASED
542				   ? "released" : "expired");
543			goto out;
544		}
545
546		/* It's actually very unlikely that we'll ever get here,
547		   but if we do, tell the client to stop using the lease,
548		   because the administrator reset it. */
549		if (lease -> binding_state == FTS_RESET &&
550		    !lease_mine_to_reallocate (lease)) {
551			log_debug ("%s: lease reset by administrator", msgbuf);
552			nak_lease (packet, &cip);
553			goto out;
554		}
555
556		/* At this point it's possible that we will get a broadcast
557		   DHCPREQUEST for a lease that we didn't offer, because
558		   both we and the peer are in a position to offer it.
559		   In that case, we probably shouldn't answer.   In order
560		   to not answer, we would have to compare the server
561		   identifier sent by the client with the list of possible
562		   server identifiers we can send, and if the client's
563		   identifier isn't on the list, drop the DHCPREQUEST.
564		   We aren't currently doing that for two reasons - first,
565		   it's not clear that all clients do the right thing
566		   with respect to sending the client identifier, which
567		   could mean that we might simply not respond to a client
568		   that is depending on us to respond.   Secondly, we allow
569		   the user to specify the server identifier to send, and
570		   we don't enforce that the server identifier should be
571		   one of our IP addresses.   This is probably not a big
572		   deal, but it's theoretically an issue.
573
574		   The reason we care about this is that if both servers
575		   send a DHCPACK to the DHCPREQUEST, they are then going
576		   to send dueling BNDUPD messages, which could cause
577		   trouble.   I think it causes no harm, but it seems
578		   wrong. */
579	} else
580		peer = (dhcp_failover_state_t *)0;
581#endif
582
583	/* If a client on a given network REQUESTs a lease on an
584	   address on a different network, NAK it.  If the Requested
585	   Address option was used, the protocol says that it must
586	   have been broadcast, so we can trust the source network
587	   information.
588
589	   If ciaddr was specified and Requested Address was not, then
590	   we really only know for sure what network a packet came from
591	   if it came through a BOOTP gateway - if it came through an
592	   IP router, we'll just have to assume that it's cool.
593
594	   If we don't think we know where the packet came from, it
595	   came through a gateway from an unknown network, so it's not
596	   from a RENEWING client.  If we recognize the network it
597	   *thinks* it's on, we can NAK it even though we don't
598	   recognize the network it's *actually* on; otherwise we just
599	   have to ignore it.
600
601	   We don't currently try to take advantage of access to the
602	   raw packet, because it's not available on all platforms.
603	   So a packet that was unicast to us through a router from a
604	   RENEWING client is going to look exactly like a packet that
605	   was broadcast to us from an INIT-REBOOT client.
606
607	   Since we can't tell the difference between these two kinds
608	   of packets, if the packet appears to have come in off the
609	   local wire, we have to treat it as if it's a RENEWING
610	   client.  This means that we can't NAK a RENEWING client on
611	   the local wire that has a bogus address.  The good news is
612	   that we won't ACK it either, so it should revert to INIT
613	   state and send us a DHCPDISCOVER, which we *can* work with.
614
615	   Because we can't detect that a RENEWING client is on the
616	   wrong wire, it's going to sit there trying to renew until
617	   it gets to the REBIND state, when we *can* NAK it because
618	   the packet will get to us through a BOOTP gateway.  We
619	   shouldn't actually see DHCPREQUEST packets from RENEWING
620	   clients on the wrong wire anyway, since their idea of their
621	   local router will be wrong.  In any case, the protocol
622	   doesn't really allow us to NAK a DHCPREQUEST from a
623	   RENEWING client, so we can punt on this issue. */
624
625	if (!packet -> shared_network ||
626	    (packet -> raw -> ciaddr.s_addr &&
627	     packet -> raw -> giaddr.s_addr) ||
628	    (have_requested_addr && !packet -> raw -> ciaddr.s_addr)) {
629
630		/* If we don't know where it came from but we do know
631		   where it claims to have come from, it didn't come
632		   from there. */
633		if (!packet -> shared_network) {
634			if (subnet && subnet -> group -> authoritative) {
635				log_info ("%s: wrong network.", msgbuf);
636				nak_lease (packet, &cip);
637				goto out;
638			}
639			/* Otherwise, ignore it. */
640			log_info ("%s: ignored (%s).", msgbuf,
641				  (subnet
642				   ? "not authoritative" : "unknown subnet"));
643			goto out;
644		}
645
646		/* If we do know where it came from and it asked for an
647		   address that is not on that shared network, nak it. */
648		if (subnet)
649			subnet_dereference (&subnet, MDL);
650		if (!find_grouped_subnet (&subnet, packet -> shared_network,
651					  cip, MDL)) {
652			if (packet -> shared_network -> group -> authoritative)
653			{
654				log_info ("%s: wrong network.", msgbuf);
655				nak_lease (packet, &cip);
656				goto out;
657			}
658			log_info ("%s: ignored (not authoritative).", msgbuf);
659			return;
660		}
661	}
662
663	/* If the address the client asked for is ours, but it wasn't
664           available for the client, NAK it. */
665	if (!lease && ours) {
666		log_info ("%s: lease %s unavailable.", msgbuf, piaddr (cip));
667		nak_lease (packet, &cip);
668		goto out;
669	}
670
671	/* Otherwise, send the lease to the client if we found one. */
672	if (lease) {
673		ack_lease (packet, lease, DHCPACK, 0, msgbuf, ms_nulltp,
674			   (struct host_decl *)0);
675	} else
676		log_info ("%s: unknown lease %s.", msgbuf, piaddr (cip));
677
678      out:
679	if (subnet)
680		subnet_dereference (&subnet, MDL);
681	if (lease)
682		lease_dereference (&lease, MDL);
683	return;
684}
685
686void dhcprelease (packet, ms_nulltp)
687	struct packet *packet;
688	int ms_nulltp;
689{
690	struct lease *lease = (struct lease *)0, *next = (struct lease *)0;
691	struct iaddr cip;
692	struct option_cache *oc;
693	struct data_string data;
694	const char *s;
695	char msgbuf [1024], cstr[16]; /* XXX */
696
697
698	/* DHCPRELEASE must not specify address in requested-address
699           option, but old protocol specs weren't explicit about this,
700           so let it go. */
701	if ((oc = lookup_option (&dhcp_universe, packet -> options,
702				 DHO_DHCP_REQUESTED_ADDRESS))) {
703		log_info ("DHCPRELEASE from %s specified requested-address.",
704		      print_hw_addr (packet -> raw -> htype,
705				     packet -> raw -> hlen,
706				     packet -> raw -> chaddr));
707	}
708
709	oc = lookup_option (&dhcp_universe, packet -> options,
710			    DHO_DHCP_CLIENT_IDENTIFIER);
711	memset (&data, 0, sizeof data);
712	if (oc &&
713	    evaluate_option_cache (&data, packet, (struct lease *)0,
714				   (struct client_state *)0,
715				   packet -> options, (struct option_state *)0,
716				   &global_scope, oc, MDL)) {
717		find_lease_by_uid (&lease, data.data, data.len, MDL);
718		data_string_forget (&data, MDL);
719
720		/* See if we can find a lease that matches the IP address
721		   the client is claiming. */
722		while (lease) {
723			if (lease -> n_uid)
724				lease_reference (&next, lease -> n_uid, MDL);
725			if (!memcmp (&packet -> raw -> ciaddr,
726				     lease -> ip_addr.iabuf, 4)) {
727				break;
728			}
729			lease_dereference (&lease, MDL);
730			if (next) {
731				lease_reference (&lease, next, MDL);
732				lease_dereference (&next, MDL);
733			}
734		}
735		if (next)
736			lease_dereference (&next, MDL);
737	}
738
739	/* The client is supposed to pass a valid client-identifier,
740	   but the spec on this has changed historically, so try the
741	   IP address in ciaddr if the client-identifier fails. */
742	if (!lease) {
743		cip.len = 4;
744		memcpy (cip.iabuf, &packet -> raw -> ciaddr, 4);
745		find_lease_by_ip_addr (&lease, cip, MDL);
746	}
747
748
749	/* If the hardware address doesn't match, don't do the release. */
750	if (lease &&
751	    (lease -> hardware_addr.hlen != packet -> raw -> hlen + 1 ||
752	     lease -> hardware_addr.hbuf [0] != packet -> raw -> htype ||
753	     memcmp (&lease -> hardware_addr.hbuf [1],
754		     packet -> raw -> chaddr, packet -> raw -> hlen)))
755		lease_dereference (&lease, MDL);
756
757	if (lease && lease -> client_hostname) {
758		if ((strlen (lease -> client_hostname) <= 64) &&
759		    db_printable (lease -> client_hostname))
760			s = lease -> client_hostname;
761		else
762			s = "Hostname Unsuitable for Printing";
763	} else
764		s = (char *)0;
765
766	/* %Audit% Cannot exceed 16 bytes. %2004.06.17,Safe%
767	 * We copy this out to stack because we actually want to log two
768	 * inet_ntoa()'s in this message.
769	 */
770	strncpy(cstr, inet_ntoa (packet -> raw -> ciaddr), 15);
771	cstr[15] = '\0';
772
773	/* %Audit% This is log output. %2004.06.17,Safe%
774	 * If we truncate we hope the user can get a hint from the log.
775	 */
776	snprintf (msgbuf, sizeof msgbuf,
777		 "DHCPRELEASE of %s from %s %s%s%svia %s (%sfound)",
778		 cstr,
779		 (packet -> raw -> htype
780		  ? print_hw_addr (packet -> raw -> htype,
781				   packet -> raw -> hlen,
782				   packet -> raw -> chaddr)
783		  : (lease
784		     ? print_hex_1 (lease -> uid_len, lease -> uid,
785				    lease -> uid_len)
786		     : "<no identifier>")),
787		 s ? "(" : "", s ? s : "", s ? ") " : "",
788		 packet -> raw -> giaddr.s_addr
789		 ? inet_ntoa (packet -> raw -> giaddr)
790		 : packet -> interface -> name,
791		 lease ? "" : "not ");
792
793#if defined (FAILOVER_PROTOCOL)
794	if (lease && lease -> pool && lease -> pool -> failover_peer) {
795		dhcp_failover_state_t *peer = lease -> pool -> failover_peer;
796		if (peer -> service_state == not_responding ||
797		    peer -> service_state == service_startup) {
798			log_info ("%s: ignored%s",
799				  peer -> name, peer -> nrr);
800			goto out;
801		}
802
803		/* DHCPRELEASE messages are unicast, so if the client
804		   sent the DHCPRELEASE to us, it's not going to send it
805		   to the peer.   Not sure why this would happen, and
806		   if it does happen I think we still have to change the
807		   lease state, so that's what we're doing.
808		   XXX See what it says in the draft about this. */
809	}
810#endif
811
812	/* If we found a lease, release it. */
813	if (lease && lease -> ends > cur_time) {
814		release_lease (lease, packet);
815	}
816	log_info ("%s", msgbuf);
817      out:
818	if (lease)
819		lease_dereference (&lease, MDL);
820}
821
822void dhcpdecline (packet, ms_nulltp)
823	struct packet *packet;
824	int ms_nulltp;
825{
826	struct lease *lease = (struct lease *)0;
827	struct option_state *options = (struct option_state *)0;
828	int ignorep = 0;
829	int i;
830	const char *status;
831	const char *s;
832	char msgbuf [1024]; /* XXX */
833	struct iaddr cip;
834	struct option_cache *oc;
835	struct data_string data;
836
837	/* DHCPDECLINE must specify address. */
838	if (!(oc = lookup_option (&dhcp_universe, packet -> options,
839				  DHO_DHCP_REQUESTED_ADDRESS)))
840		return;
841	memset (&data, 0, sizeof data);
842	if (!evaluate_option_cache (&data, packet, (struct lease *)0,
843				    (struct client_state *)0,
844				    packet -> options,
845				    (struct option_state *)0,
846				    &global_scope, oc, MDL))
847		return;
848
849	cip.len = 4;
850	memcpy (cip.iabuf, data.data, 4);
851	data_string_forget (&data, MDL);
852	find_lease_by_ip_addr (&lease, cip, MDL);
853
854	if (lease && lease -> client_hostname) {
855		if ((strlen (lease -> client_hostname) <= 64) &&
856		    db_printable (lease -> client_hostname))
857			s = lease -> client_hostname;
858		else
859			s = "Hostname Unsuitable for Printing";
860	} else
861		s = (char *)0;
862
863	/* %Audit% This is log output. %2004.06.17,Safe%
864	 * If we truncate we hope the user can get a hint from the log.
865	 */
866	snprintf (msgbuf, sizeof msgbuf,
867		 "DHCPDECLINE of %s from %s %s%s%svia %s",
868		 piaddr (cip),
869		 (packet -> raw -> htype
870		  ? print_hw_addr (packet -> raw -> htype,
871				   packet -> raw -> hlen,
872				   packet -> raw -> chaddr)
873		  : (lease
874		     ? print_hex_1 (lease -> uid_len, lease -> uid,
875				    lease -> uid_len)
876		     : "<no identifier>")),
877		 s ? "(" : "", s ? s : "", s ? ") " : "",
878		 packet -> raw -> giaddr.s_addr
879		 ? inet_ntoa (packet -> raw -> giaddr)
880		 : packet -> interface -> name);
881
882	option_state_allocate (&options, MDL);
883
884	/* Execute statements in scope starting with the subnet scope. */
885	if (lease)
886		execute_statements_in_scope ((struct binding_value **)0,
887					     packet, (struct lease *)0,
888					     (struct client_state *)0,
889					     packet -> options, options,
890					     &global_scope,
891					     lease -> subnet -> group,
892					     (struct group *)0);
893
894	/* Execute statements in the class scopes. */
895	for (i = packet -> class_count; i > 0; i--) {
896		execute_statements_in_scope
897			((struct binding_value **)0, packet, (struct lease *)0,
898			 (struct client_state *)0, packet -> options, options,
899			 &global_scope, packet -> classes [i - 1] -> group,
900			 lease ? lease -> subnet -> group : (struct group *)0);
901	}
902
903	/* Drop the request if dhcpdeclines are being ignored. */
904	oc = lookup_option (&server_universe, options, SV_DECLINES);
905	if (!oc ||
906	    evaluate_boolean_option_cache (&ignorep, packet, lease,
907					   (struct client_state *)0,
908					   packet -> options, options,
909					   &lease -> scope, oc, MDL)) {
910	    /* If we found a lease, mark it as unusable and complain. */
911	    if (lease) {
912#if defined (FAILOVER_PROTOCOL)
913		if (lease -> pool && lease -> pool -> failover_peer) {
914		    dhcp_failover_state_t *peer =
915			    lease -> pool -> failover_peer;
916		    if (peer -> service_state == not_responding ||
917			peer -> service_state == service_startup) {
918			if (!ignorep)
919			    log_info ("%s: ignored%s",
920				      peer -> name, peer -> nrr);
921			goto out;
922		    }
923
924		    /* DHCPDECLINE messages are broadcast, so we can safely
925		       ignore the DHCPDECLINE if the peer has the lease.
926		       XXX Of course, at this point that information has been
927		       lost. */
928		}
929#endif
930
931		abandon_lease (lease, "declined.");
932		status = "abandoned";
933	    }
934	    status = "not found";
935	} else
936	    status = "ignored";
937
938	if (!ignorep)
939		log_info ("%s: %s", msgbuf, status);
940
941      out:
942	if (options)
943		option_state_dereference (&options, MDL);
944	if (lease)
945		lease_dereference (&lease, MDL);
946}
947
948void dhcpinform (packet, ms_nulltp)
949	struct packet *packet;
950	int ms_nulltp;
951{
952	char msgbuf [1024];
953	struct data_string d1, prl;
954	struct option_cache *oc;
955	struct option_state *options = (struct option_state *)0;
956	struct dhcp_packet raw;
957	struct packet outgoing;
958	unsigned char dhcpack = DHCPACK;
959	struct subnet *subnet = (struct subnet *)0;
960	struct iaddr cip;
961	unsigned i;
962	int nulltp;
963	struct sockaddr_in to;
964	struct in_addr from;
965
966	/* The client should set ciaddr to its IP address, but apparently
967	   it's common for clients not to do this, so we'll use their IP
968	   source address if they didn't set ciaddr. */
969	if (!packet -> raw -> ciaddr.s_addr) {
970		cip.len = 4;
971		memcpy (cip.iabuf, &packet -> client_addr.iabuf, 4);
972	} else {
973		cip.len = 4;
974		memcpy (cip.iabuf, &packet -> raw -> ciaddr, 4);
975	}
976
977	/* %Audit% This is log output. %2004.06.17,Safe%
978	 * If we truncate we hope the user can get a hint from the log.
979	 */
980	snprintf (msgbuf, sizeof msgbuf, "DHCPINFORM from %s via %s",
981		 piaddr (cip), packet -> interface -> name);
982
983	/* If the IP source address is zero, don't respond. */
984	if (!memcmp (cip.iabuf, "\0\0\0", 4)) {
985		log_info ("%s: ignored (null source address).", msgbuf);
986		return;
987	}
988
989	/* Find the subnet that the client is on. */
990	oc = (struct option_cache *)0;
991	find_subnet (&subnet , cip, MDL);
992
993	/* Sourceless packets don't make sense here. */
994	if (!subnet) {
995		log_info ("%s: unknown subnet %s",
996			  msgbuf, inet_ntoa (packet -> raw -> giaddr));
997		return;
998	}
999
1000	/* We don't respond to DHCPINFORM packets if we're not authoritative.
1001	   It would be nice if a per-host value could override this, but
1002	   there's overhead involved in checking this, so let's see how people
1003	   react first. */
1004	if (subnet && !subnet -> group -> authoritative) {
1005		static int eso = 0;
1006		log_info ("%s: not authoritative for subnet %s",
1007			  msgbuf, piaddr (subnet -> net));
1008		if (!eso) {
1009			log_info ("If this DHCP server is authoritative for%s",
1010				  " that subnet,");
1011			log_info ("please write an `authoritative;' directi%s",
1012				  "ve either in the");
1013			log_info ("subnet declaration or in some scope that%s",
1014				  " encloses the");
1015			log_info ("subnet declaration - for example, write %s",
1016				  "it at the top");
1017			log_info ("of the dhcpd.conf file.");
1018		}
1019		if (eso++ == 100)
1020			eso = 0;
1021		subnet_dereference (&subnet, MDL);
1022		return;
1023	}
1024
1025	memset (&d1, 0, sizeof d1);
1026	option_state_allocate (&options, MDL);
1027	memset (&outgoing, 0, sizeof outgoing);
1028	memset (&raw, 0, sizeof raw);
1029	outgoing.raw = &raw;
1030
1031	/* Execute statements in scope starting with the subnet scope. */
1032	if (subnet)
1033		execute_statements_in_scope ((struct binding_value **)0,
1034					     packet, (struct lease *)0,
1035					     (struct client_state *)0,
1036					     packet -> options, options,
1037					     &global_scope, subnet -> group,
1038					     (struct group *)0);
1039
1040	/* Execute statements in the class scopes. */
1041	for (i = packet -> class_count; i > 0; i--) {
1042		execute_statements_in_scope
1043			((struct binding_value **)0, packet, (struct lease *)0,
1044			 (struct client_state *)0, packet -> options, options,
1045			 &global_scope, packet -> classes [i - 1] -> group,
1046			 subnet ? subnet -> group : (struct group *)0);
1047	}
1048
1049	/* Figure out the filename. */
1050	memset (&d1, 0, sizeof d1);
1051	oc = lookup_option (&server_universe, options, SV_FILENAME);
1052	if (oc &&
1053	    evaluate_option_cache (&d1, packet, (struct lease *)0,
1054				   (struct client_state *)0,
1055				   packet -> options, (struct option_state *)0,
1056				   &global_scope, oc, MDL)) {
1057		i = d1.len;
1058		if (i > sizeof raw.file)
1059			i = sizeof raw.file;
1060		else
1061			raw.file [i] = 0;
1062		memcpy (raw.file, d1.data, i);
1063		data_string_forget (&d1, MDL);
1064	}
1065
1066	/* Choose a server name as above. */
1067	oc = lookup_option (&server_universe, options, SV_SERVER_NAME);
1068	if (oc &&
1069	    evaluate_option_cache (&d1, packet, (struct lease *)0,
1070				   (struct client_state *)0,
1071				   packet -> options, (struct option_state *)0,
1072				   &global_scope, oc, MDL)) {
1073		i = d1.len;
1074		if (i > sizeof raw.sname)
1075			i = sizeof raw.sname;
1076		else
1077			raw.sname [i] = 0;
1078		memcpy (raw.sname, d1.data, i);
1079		data_string_forget (&d1, MDL);
1080	}
1081
1082	/* Set a flag if this client is a lame Microsoft client that NUL
1083	   terminates string options and expects us to do likewise. */
1084	nulltp = 0;
1085	if ((oc = lookup_option (&dhcp_universe, packet -> options,
1086				 DHO_HOST_NAME))) {
1087		if (evaluate_option_cache (&d1, packet, (struct lease *)0,
1088					   (struct client_state *)0,
1089					   packet -> options, options,
1090					   &global_scope, oc, MDL)) {
1091			if (d1.data [d1.len - 1] == '\0')
1092				nulltp = 1;
1093			data_string_forget (&d1, MDL);
1094		}
1095	}
1096
1097	/* Put in DHCP-specific options. */
1098	i = DHO_DHCP_MESSAGE_TYPE;
1099	oc = (struct option_cache *)0;
1100	if (option_cache_allocate (&oc, MDL)) {
1101		if (make_const_data (&oc -> expression,
1102				     &dhcpack, 1, 0, 0, MDL)) {
1103			oc -> option = dhcp_universe.options [i];
1104			save_option (&dhcp_universe, options, oc);
1105		}
1106		option_cache_dereference (&oc, MDL);
1107	}
1108
1109	i = DHO_DHCP_SERVER_IDENTIFIER;
1110	if (!(oc = lookup_option (&dhcp_universe, options, i))) {
1111	      use_primary:
1112		oc = (struct option_cache *)0;
1113		if (option_cache_allocate (&oc, MDL)) {
1114			if (make_const_data
1115			    (&oc -> expression,
1116			     ((unsigned char *)
1117			      &packet -> interface -> primary_address),
1118			     sizeof packet -> interface -> primary_address,
1119			     0, 0, MDL)) {
1120				oc -> option =
1121					dhcp_universe.options [i];
1122				save_option (&dhcp_universe,
1123					     options, oc);
1124			}
1125			option_cache_dereference (&oc, MDL);
1126		}
1127		from = packet -> interface -> primary_address;
1128	} else {
1129		if (evaluate_option_cache (&d1, packet, (struct lease *)0,
1130					   (struct client_state *)0,
1131					   packet -> options, options,
1132					   &global_scope, oc, MDL)) {
1133			if (!d1.len || d1.len != sizeof from) {
1134				data_string_forget (&d1, MDL);
1135				goto use_primary;
1136			}
1137			memcpy (&from, d1.data, sizeof from);
1138			data_string_forget (&d1, MDL);
1139		} else
1140			goto use_primary;
1141	}
1142
1143	/* Use the subnet mask from the subnet declaration if no other
1144	   mask has been provided. */
1145	i = DHO_SUBNET_MASK;
1146	if (subnet && !lookup_option (&dhcp_universe, options, i)) {
1147		oc = (struct option_cache *)0;
1148		if (option_cache_allocate (&oc, MDL)) {
1149			if (make_const_data (&oc -> expression,
1150					     subnet -> netmask.iabuf,
1151					     subnet -> netmask.len,
1152					     0, 0, MDL)) {
1153				oc -> option = dhcp_universe.options [i];
1154				save_option (&dhcp_universe, options, oc);
1155			}
1156			option_cache_dereference (&oc, MDL);
1157		}
1158	}
1159
1160	/* If a site option space has been specified, use that for
1161	   site option codes. */
1162	i = SV_SITE_OPTION_SPACE;
1163	if ((oc = lookup_option (&server_universe, options, i)) &&
1164	    evaluate_option_cache (&d1, packet, (struct lease *)0,
1165				   (struct client_state *)0,
1166				   packet -> options, options,
1167				   &global_scope, oc, MDL)) {
1168		struct universe *u = (struct universe *)0;
1169
1170		if (!universe_hash_lookup (&u, universe_hash,
1171					   (const char *)d1.data, d1.len,
1172					   MDL)) {
1173			log_error ("unknown option space %s.", d1.data);
1174			option_state_dereference (&options, MDL);
1175			if (subnet)
1176				subnet_dereference (&subnet, MDL);
1177			return;
1178		}
1179
1180		options -> site_universe = u -> index;
1181		options -> site_code_min = 128; /* XXX */
1182		data_string_forget (&d1, MDL);
1183	} else {
1184		options -> site_universe = dhcp_universe.index;
1185		options -> site_code_min = 0; /* Trust me, it works. */
1186	}
1187
1188	memset (&prl, 0, sizeof prl);
1189
1190	/* Use the parameter list from the scope if there is one. */
1191	oc = lookup_option (&dhcp_universe, options,
1192			    DHO_DHCP_PARAMETER_REQUEST_LIST);
1193
1194	/* Otherwise, if the client has provided a list of options
1195	   that it wishes returned, use it to prioritize.  Otherwise,
1196	   prioritize based on the default priority list. */
1197
1198	if (!oc)
1199		oc = lookup_option (&dhcp_universe, packet -> options,
1200				    DHO_DHCP_PARAMETER_REQUEST_LIST);
1201
1202	if (oc)
1203		evaluate_option_cache (&prl, packet, (struct lease *)0,
1204				       (struct client_state *)0,
1205				       packet -> options, options,
1206				       &global_scope, oc, MDL);
1207
1208#ifdef DEBUG_PACKET
1209	dump_packet (packet);
1210	dump_raw ((unsigned char *)packet -> raw, packet -> packet_length);
1211#endif
1212
1213	log_info ("%s", msgbuf);
1214
1215	/* Figure out the address of the boot file server. */
1216	if ((oc =
1217	     lookup_option (&server_universe, options, SV_NEXT_SERVER))) {
1218		if (evaluate_option_cache (&d1, packet, (struct lease *)0,
1219					   (struct client_state *)0,
1220					   packet -> options, options,
1221					   &global_scope, oc, MDL)) {
1222			/* If there was more than one answer,
1223			   take the first. */
1224			if (d1.len >= 4 && d1.data)
1225				memcpy (&raw.siaddr, d1.data, 4);
1226			data_string_forget (&d1, MDL);
1227		}
1228	}
1229
1230	/* Set up the option buffer... */
1231	outgoing.packet_length =
1232		cons_options (packet, outgoing.raw, (struct lease *)0,
1233			      (struct client_state *)0,
1234			      0, packet -> options, options, &global_scope,
1235			      0, nulltp, 0,
1236			      prl.len ? &prl : (struct data_string *)0,
1237			      (char *)0);
1238	option_state_dereference (&options, MDL);
1239	data_string_forget (&prl, MDL);
1240
1241	/* Make sure that the packet is at least as big as a BOOTP packet. */
1242	if (outgoing.packet_length < BOOTP_MIN_LEN)
1243		outgoing.packet_length = BOOTP_MIN_LEN;
1244
1245	raw.giaddr = packet -> raw -> giaddr;
1246	raw.ciaddr = packet -> raw -> ciaddr;
1247	memcpy (raw.chaddr, packet -> raw -> chaddr, sizeof raw.chaddr);
1248	raw.hlen = packet -> raw -> hlen;
1249	raw.htype = packet -> raw -> htype;
1250
1251	raw.xid = packet -> raw -> xid;
1252	raw.secs = packet -> raw -> secs;
1253	raw.flags = packet -> raw -> flags;
1254	raw.hops = packet -> raw -> hops;
1255	raw.op = BOOTREPLY;
1256
1257	/* Report what we're sending... */
1258	log_info ("DHCPACK to %s", inet_ntoa (raw.ciaddr));
1259
1260#ifdef DEBUG_PACKET
1261	dump_packet (&outgoing);
1262	dump_raw ((unsigned char *)&raw, outgoing.packet_length);
1263#endif
1264
1265	/* Set up the common stuff... */
1266	memset (&to, 0, sizeof to);
1267	to.sin_family = AF_INET;
1268#ifdef HAVE_SA_LEN
1269	to.sin_len = sizeof to;
1270#endif
1271
1272	/* Use the IP address we derived for the client. */
1273	memcpy (&to.sin_addr, cip.iabuf, 4);
1274	to.sin_port = remote_port;
1275
1276	errno = 0;
1277	send_packet ((fallback_interface
1278		      ? fallback_interface : packet -> interface),
1279		     &outgoing, &raw, outgoing.packet_length,
1280		     from, &to, (struct hardware *)0);
1281	if (subnet)
1282		subnet_dereference (&subnet, MDL);
1283}
1284
1285void nak_lease (packet, cip)
1286	struct packet *packet;
1287	struct iaddr *cip;
1288{
1289	struct sockaddr_in to;
1290	struct in_addr from;
1291	int result;
1292	struct dhcp_packet raw;
1293	unsigned char nak = DHCPNAK;
1294	struct packet outgoing;
1295	struct hardware hto;
1296	unsigned i;
1297	struct data_string data;
1298	struct option_state *options = (struct option_state *)0;
1299	struct option_cache *oc = (struct option_cache *)0;
1300	struct iaddr myfrom;
1301
1302	option_state_allocate (&options, MDL);
1303	memset (&outgoing, 0, sizeof outgoing);
1304	memset (&raw, 0, sizeof raw);
1305	outgoing.raw = &raw;
1306
1307	/* Set DHCP_MESSAGE_TYPE to DHCPNAK */
1308	if (!option_cache_allocate (&oc, MDL)) {
1309		log_error ("No memory for DHCPNAK message type.");
1310		option_state_dereference (&options, MDL);
1311		return;
1312	}
1313	if (!make_const_data (&oc -> expression, &nak, sizeof nak,
1314			      0, 0, MDL)) {
1315		log_error ("No memory for expr_const expression.");
1316		option_cache_dereference (&oc, MDL);
1317		option_state_dereference (&options, MDL);
1318		return;
1319	}
1320	oc -> option = dhcp_universe.options [DHO_DHCP_MESSAGE_TYPE];
1321	save_option (&dhcp_universe, options, oc);
1322	option_cache_dereference (&oc, MDL);
1323
1324	/* Set DHCP_MESSAGE to whatever the message is */
1325	if (!option_cache_allocate (&oc, MDL)) {
1326		log_error ("No memory for DHCPNAK message type.");
1327		option_state_dereference (&options, MDL);
1328		return;
1329	}
1330	if (!make_const_data (&oc -> expression,
1331			      (unsigned char *)dhcp_message,
1332			      strlen (dhcp_message), 1, 0, MDL)) {
1333		log_error ("No memory for expr_const expression.");
1334		option_cache_dereference (&oc, MDL);
1335		option_state_dereference (&options, MDL);
1336		return;
1337	}
1338	oc -> option = dhcp_universe.options [DHO_DHCP_MESSAGE];
1339	save_option (&dhcp_universe, options, oc);
1340	option_cache_dereference (&oc, MDL);
1341
1342	i = DHO_DHCP_SERVER_IDENTIFIER;
1343	if (!(oc = lookup_option (&dhcp_universe, options, i))) {
1344	      use_primary:
1345		oc = (struct option_cache *)0;
1346		if (option_cache_allocate (&oc, MDL)) {
1347			if (make_const_data
1348			    (&oc -> expression,
1349			     ((unsigned char *)
1350			      &packet -> interface -> primary_address),
1351			     sizeof packet -> interface -> primary_address,
1352			     0, 0, MDL)) {
1353				oc -> option =
1354					dhcp_universe.options [i];
1355				save_option (&dhcp_universe, options, oc);
1356			}
1357			option_cache_dereference (&oc, MDL);
1358		}
1359		myfrom.len = sizeof packet -> interface -> primary_address;
1360		memcpy (myfrom.iabuf,
1361			&packet -> interface -> primary_address, myfrom.len);
1362	} else {
1363		memset (&data, 0, sizeof data);
1364		if (evaluate_option_cache (&data, packet, (struct lease *)0,
1365					   (struct client_state *)0,
1366					   packet -> options, options,
1367					   &global_scope, oc, MDL)) {
1368			if (!data.len ||
1369			    data.len > sizeof myfrom.iabuf) {
1370				data_string_forget (&data, MDL);
1371				goto use_primary;
1372			}
1373			memcpy (myfrom.iabuf, data.data, data.len);
1374			myfrom.len = data.len;
1375			data_string_forget (&data, MDL);
1376		} else
1377			goto use_primary;
1378	}
1379
1380	/* If there were agent options in the incoming packet, return
1381	   them. */
1382	if (packet -> raw -> giaddr.s_addr &&
1383	    packet -> options != NULL &&
1384	    packet -> options -> universe_count > agent_universe.index &&
1385	    packet -> options -> universes [agent_universe.index]) {
1386		option_chain_head_reference
1387		    ((struct option_chain_head **)
1388		     &(options -> universes [agent_universe.index]),
1389		     (struct option_chain_head *)
1390		     packet -> options -> universes [agent_universe.index],
1391		     MDL);
1392	}
1393
1394	/* Do not use the client's requested parameter list. */
1395	delete_option (&dhcp_universe, packet -> options,
1396		       DHO_DHCP_PARAMETER_REQUEST_LIST);
1397
1398	/* Set up the option buffer... */
1399	outgoing.packet_length =
1400		cons_options (packet, outgoing.raw, (struct lease *)0,
1401			      (struct client_state *)0,
1402			      0, packet -> options, options, &global_scope,
1403			      0, 0, 0, (struct data_string *)0, (char *)0);
1404	option_state_dereference (&options, MDL);
1405
1406/*	memset (&raw.ciaddr, 0, sizeof raw.ciaddr);*/
1407	raw.siaddr = packet -> interface -> primary_address;
1408	raw.giaddr = packet -> raw -> giaddr;
1409	memcpy (raw.chaddr, packet -> raw -> chaddr, sizeof raw.chaddr);
1410	raw.hlen = packet -> raw -> hlen;
1411	raw.htype = packet -> raw -> htype;
1412
1413	raw.xid = packet -> raw -> xid;
1414	raw.secs = packet -> raw -> secs;
1415	raw.flags = packet -> raw -> flags | htons (BOOTP_BROADCAST);
1416	raw.hops = packet -> raw -> hops;
1417	raw.op = BOOTREPLY;
1418
1419	/* Report what we're sending... */
1420	log_info ("DHCPNAK on %s to %s via %s",
1421	      piaddr (*cip),
1422	      print_hw_addr (packet -> raw -> htype,
1423			     packet -> raw -> hlen,
1424			     packet -> raw -> chaddr),
1425	      packet -> raw -> giaddr.s_addr
1426	      ? inet_ntoa (packet -> raw -> giaddr)
1427	      : packet -> interface -> name);
1428
1429
1430
1431#ifdef DEBUG_PACKET
1432	dump_packet (packet);
1433	dump_raw ((unsigned char *)packet -> raw, packet -> packet_length);
1434	dump_packet (&outgoing);
1435	dump_raw ((unsigned char *)&raw, outgoing.packet_length);
1436#endif
1437
1438#if 0
1439	hto.hbuf [0] = packet -> raw -> htype;
1440	hto.hlen = packet -> raw -> hlen;
1441	memcpy (&hto.hbuf [1], packet -> raw -> chaddr, hto.hlen);
1442	hto.hlen++;
1443#endif
1444
1445	/* Set up the common stuff... */
1446	memset (&to, 0, sizeof to);
1447	to.sin_family = AF_INET;
1448#ifdef HAVE_SA_LEN
1449	to.sin_len = sizeof to;
1450#endif
1451
1452	memcpy (&from, myfrom.iabuf, sizeof from);
1453
1454	/* Make sure that the packet is at least as big as a BOOTP packet. */
1455	if (outgoing.packet_length < BOOTP_MIN_LEN)
1456		outgoing.packet_length = BOOTP_MIN_LEN;
1457
1458	/* If this was gatewayed, send it back to the gateway.
1459	   Otherwise, broadcast it on the local network. */
1460	if (raw.giaddr.s_addr) {
1461		to.sin_addr = raw.giaddr;
1462		if (raw.giaddr.s_addr != htonl (INADDR_LOOPBACK))
1463			to.sin_port = local_port;
1464		else
1465			to.sin_port = remote_port; /* for testing. */
1466
1467		if (fallback_interface) {
1468			result = send_packet (fallback_interface,
1469					      packet, &raw,
1470					      outgoing.packet_length,
1471					      from, &to, &hto);
1472			return;
1473		}
1474	} else {
1475		to.sin_addr = limited_broadcast;
1476		to.sin_port = remote_port;
1477	}
1478
1479	errno = 0;
1480	result = send_packet (packet -> interface,
1481			      packet, &raw, outgoing.packet_length,
1482			      from, &to, (struct hardware *)0);
1483}
1484
1485void ack_lease (packet, lease, offer, when, msg, ms_nulltp, hp)
1486	struct packet *packet;
1487	struct lease *lease;
1488	unsigned int offer;
1489	TIME when;
1490	char *msg;
1491	int ms_nulltp;
1492	struct host_decl *hp;
1493{
1494	struct lease *lt;
1495	struct lease_state *state;
1496	struct lease *next;
1497	struct host_decl *host = (struct host_decl *)0;
1498	TIME lease_time;
1499	TIME offered_lease_time;
1500	struct data_string d1;
1501	TIME min_lease_time;
1502	TIME max_lease_time;
1503	TIME default_lease_time;
1504	struct option_cache *oc;
1505	isc_result_t result;
1506	TIME ping_timeout;
1507
1508	unsigned i, j;
1509	int s1;
1510	int ignorep;
1511
1512	s1 = 0;		/* XXXGCC -Wuninitialized [arm / sparc64] */
1513
1514	/* If we're already acking this lease, don't do it again. */
1515	if (lease -> state)
1516		return;
1517
1518	/* If the lease carries a host record, remember it. */
1519	if (hp)
1520		host_reference (&host, hp, MDL);
1521	else if (lease -> host)
1522		host_reference (&host, lease -> host, MDL);
1523
1524	/* Allocate a lease state structure... */
1525	state = new_lease_state (MDL);
1526	if (!state)
1527		log_fatal ("unable to allocate lease state!");
1528	state -> got_requested_address = packet -> got_requested_address;
1529	shared_network_reference (&state -> shared_network,
1530				  packet -> interface -> shared_network, MDL);
1531
1532	/* See if we got a server identifier option. */
1533	if (lookup_option (&dhcp_universe,
1534			   packet -> options, DHO_DHCP_SERVER_IDENTIFIER))
1535		state -> got_server_identifier = 1;
1536
1537	/* If there were agent options in the incoming packet, return
1538	   them.  Do not return the agent options if they were stashed
1539	   on the lease. */
1540	if (packet -> raw -> giaddr.s_addr &&
1541	    packet -> options != NULL &&
1542	    packet -> options -> universe_count > agent_universe.index &&
1543	    packet -> options -> universes [agent_universe.index] &&
1544	    (state -> options -> universe_count <= agent_universe.index ||
1545	     !state -> options -> universes [agent_universe.index]) &&
1546	    lease -> agent_options !=
1547	    ((struct option_chain_head *)
1548	     packet -> options -> universes [agent_universe.index])) {
1549		option_chain_head_reference
1550		    ((struct option_chain_head **)
1551		     &(state -> options -> universes [agent_universe.index]),
1552		     (struct option_chain_head *)
1553		     packet -> options -> universes [agent_universe.index],
1554		     MDL);
1555	}
1556
1557	/* If we are offering a lease that is still currently valid, preserve
1558	   the events.  We need to do this because if the client does not
1559	   REQUEST our offer, it will expire in 2 minutes, overriding the
1560	   expire time in the currently in force lease.  We want the expire
1561	   events to be executed at that point. */
1562	if (lease -> ends <= cur_time && offer != DHCPOFFER) {
1563		/* Get rid of any old expiry or release statements - by
1564		   executing the statements below, we will be inserting new
1565		   ones if there are any to insert. */
1566		if (lease -> on_expiry)
1567			executable_statement_dereference (&lease -> on_expiry,
1568							  MDL);
1569		if (lease -> on_commit)
1570			executable_statement_dereference (&lease -> on_commit,
1571							  MDL);
1572		if (lease -> on_release)
1573			executable_statement_dereference (&lease -> on_release,
1574							  MDL);
1575	}
1576
1577	/* Execute statements in scope starting with the subnet scope. */
1578	execute_statements_in_scope ((struct binding_value **)0,
1579				     packet, lease, (struct client_state *)0,
1580				     packet -> options,
1581				     state -> options, &lease -> scope,
1582				     lease -> subnet -> group,
1583				     (struct group *)0);
1584
1585	/* If the lease is from a pool, run the pool scope. */
1586	if (lease -> pool)
1587		(execute_statements_in_scope
1588		 ((struct binding_value **)0, packet, lease,
1589		  (struct client_state *)0, packet -> options,
1590		  state -> options, &lease -> scope, lease -> pool -> group,
1591		  lease -> pool -> shared_network -> group));
1592
1593	/* Execute statements from class scopes. */
1594	for (i = packet -> class_count; i > 0; i--) {
1595		execute_statements_in_scope
1596			((struct binding_value **)0,
1597			 packet, lease, (struct client_state *)0,
1598			 packet -> options, state -> options,
1599			 &lease -> scope, packet -> classes [i - 1] -> group,
1600			 (lease -> pool
1601			  ? lease -> pool -> group
1602			  : lease -> subnet -> group));
1603	}
1604
1605	/* See if the client is only supposed to have one lease at a time,
1606	   and if so, find its other leases and release them.    We can only
1607	   do this on DHCPREQUEST.    It's a little weird to do this before
1608	   looking at permissions, because the client might not actually
1609	   _get_ a lease after we've done the permission check, but the
1610	   assumption for this option is that the client has exactly one
1611	   network interface, and will only ever remember one lease.   So
1612	   if it sends a DHCPREQUEST, and doesn't get the lease, it's already
1613	   forgotten about its old lease, so we can too. */
1614	if (packet -> packet_type == DHCPREQUEST &&
1615	    (oc = lookup_option (&server_universe, state -> options,
1616				 SV_ONE_LEASE_PER_CLIENT)) &&
1617	    evaluate_boolean_option_cache (&ignorep,
1618					   packet, lease,
1619					   (struct client_state *)0,
1620					   packet -> options,
1621					   state -> options, &lease -> scope,
1622					   oc, MDL)) {
1623	    struct lease *seek;
1624	    if (lease -> uid_len) {
1625		do {
1626		    seek = (struct lease *)0;
1627		    find_lease_by_uid (&seek, lease -> uid,
1628				       lease -> uid_len, MDL);
1629		    if (!seek)
1630			break;
1631		    if (seek == lease && !seek -> n_uid) {
1632			lease_dereference (&seek, MDL);
1633			break;
1634		    }
1635		    next = (struct lease *)0;
1636
1637		    /* Don't release expired leases, and don't
1638		       release the lease we're going to assign. */
1639		    next = (struct lease *)0;
1640		    while (seek) {
1641			if (seek -> n_uid)
1642			    lease_reference (&next, seek -> n_uid, MDL);
1643			if (seek != lease &&
1644			    seek -> binding_state != FTS_RELEASED &&
1645			    seek -> binding_state != FTS_EXPIRED &&
1646			    seek -> binding_state != FTS_RESET &&
1647			    seek -> binding_state != FTS_FREE &&
1648			    seek -> binding_state != FTS_BACKUP)
1649				break;
1650			lease_dereference (&seek, MDL);
1651			if (next) {
1652			    lease_reference (&seek, next, MDL);
1653			    lease_dereference (&next, MDL);
1654			}
1655		    }
1656		    if (next)
1657			lease_dereference (&next, MDL);
1658		    if (seek) {
1659			release_lease (seek, packet);
1660			lease_dereference (&seek, MDL);
1661		    } else
1662			break;
1663		} while (1);
1664	    }
1665	    if (!lease -> uid_len ||
1666		(host &&
1667		 !host -> client_identifier.len &&
1668		 (oc = lookup_option (&server_universe, state -> options,
1669				      SV_DUPLICATES)) &&
1670		 !evaluate_boolean_option_cache (&ignorep, packet, lease,
1671						 (struct client_state *)0,
1672						 packet -> options,
1673						 state -> options,
1674						 &lease -> scope,
1675						 oc, MDL))) {
1676		do {
1677		    seek = (struct lease *)0;
1678		    find_lease_by_hw_addr
1679			    (&seek, lease -> hardware_addr.hbuf,
1680			     lease -> hardware_addr.hlen, MDL);
1681		    if (!seek)
1682			    break;
1683		    if (seek == lease && !seek -> n_hw) {
1684			    lease_dereference (&seek, MDL);
1685			    break;
1686		    }
1687		    next = (struct lease *)0;
1688		    while (seek) {
1689			if (seek -> n_hw)
1690			    lease_reference (&next, seek -> n_hw, MDL);
1691			if (seek != lease &&
1692			    seek -> binding_state != FTS_RELEASED &&
1693			    seek -> binding_state != FTS_EXPIRED &&
1694			    seek -> binding_state != FTS_RESET &&
1695			    seek -> binding_state != FTS_FREE &&
1696			    seek -> binding_state != FTS_BACKUP)
1697				break;
1698			lease_dereference (&seek, MDL);
1699			if (next) {
1700			    lease_reference (&seek, next, MDL);
1701			    lease_dereference (&next, MDL);
1702			}
1703		    }
1704		    if (next)
1705			lease_dereference (&next, MDL);
1706		    if (seek) {
1707			release_lease (seek, packet);
1708			lease_dereference (&seek, MDL);
1709		    } else
1710			break;
1711		} while (1);
1712	    }
1713	}
1714
1715
1716	/* Make sure this packet satisfies the configured minimum
1717	   number of seconds. */
1718	memset (&d1, 0, sizeof d1);
1719	if (offer == DHCPOFFER &&
1720	    (oc = lookup_option (&server_universe, state -> options,
1721				 SV_MIN_SECS))) {
1722		if (evaluate_option_cache (&d1, packet, lease,
1723					   (struct client_state *)0,
1724					   packet -> options, state -> options,
1725					   &lease -> scope, oc, MDL)) {
1726			if (d1.len &&
1727			    ntohs (packet -> raw -> secs) < d1.data [0]) {
1728				log_info ("%s: %d secs < %d", msg,
1729					  ntohs (packet -> raw -> secs),
1730					  d1.data [0]);
1731				data_string_forget (&d1, MDL);
1732				free_lease_state (state, MDL);
1733				if (host)
1734					host_dereference (&host, MDL);
1735				return;
1736			}
1737			data_string_forget (&d1, MDL);
1738		}
1739	}
1740
1741	/* Try to find a matching host declaration for this lease.
1742	 */
1743	if (!host) {
1744		struct host_decl *hp = (struct host_decl *)0;
1745		struct host_decl *h;
1746
1747		/* Try to find a host_decl that matches the client
1748		   identifier or hardware address on the packet, and
1749		   has no fixed IP address.   If there is one, hang
1750		   it off the lease so that its option definitions
1751		   can be used. */
1752		oc = lookup_option (&dhcp_universe, packet -> options,
1753				    DHO_DHCP_CLIENT_IDENTIFIER);
1754		if (oc &&
1755		    evaluate_option_cache (&d1, packet, lease,
1756					   (struct client_state *)0,
1757					   packet -> options, state -> options,
1758					   &lease -> scope, oc, MDL)) {
1759			find_hosts_by_uid (&hp, d1.data, d1.len, MDL);
1760			data_string_forget (&d1, MDL);
1761			for (h = hp; h; h = h -> n_ipaddr) {
1762				if (!h -> fixed_addr)
1763					break;
1764			}
1765			if (h)
1766				host_reference (&host, h, MDL);
1767		}
1768		if (!host) {
1769			if (hp)
1770				host_dereference (&hp, MDL);
1771			find_hosts_by_haddr (&hp,
1772					     packet -> raw -> htype,
1773					     packet -> raw -> chaddr,
1774					     packet -> raw -> hlen,
1775					     MDL);
1776			for (h = hp; h; h = h -> n_ipaddr) {
1777				if (!h -> fixed_addr)
1778					break;
1779			}
1780			if (h)
1781				host_reference (&host, h, MDL);
1782		}
1783		if (hp)
1784			host_dereference (&hp, MDL);
1785	}
1786
1787	/* If we have a host_decl structure, run the options associated
1788	   with its group.  Wether the host decl struct is old or not. */
1789	if (host)
1790		execute_statements_in_scope ((struct binding_value **)0,
1791					     packet, lease,
1792					     (struct client_state *)0,
1793					     packet -> options,
1794					     state -> options, &lease -> scope,
1795					     host -> group,
1796					     (lease -> pool
1797					      ? lease -> pool -> group
1798					      : lease -> subnet -> group));
1799
1800	/* Drop the request if it's not allowed for this client.   By
1801	   default, unknown clients are allowed. */
1802	if (!host &&
1803	    (oc = lookup_option (&server_universe, state -> options,
1804				 SV_BOOT_UNKNOWN_CLIENTS)) &&
1805	    !evaluate_boolean_option_cache (&ignorep,
1806					    packet, lease,
1807					    (struct client_state *)0,
1808					    packet -> options,
1809					    state -> options,
1810					    &lease -> scope, oc, MDL)) {
1811		if (!ignorep)
1812			log_info ("%s: unknown client", msg);
1813		free_lease_state (state, MDL);
1814		if (host)
1815			host_dereference (&host, MDL);
1816		return;
1817	}
1818
1819	/* Drop the request if it's not allowed for this client. */
1820	if (!offer &&
1821	    (oc = lookup_option (&server_universe, state -> options,
1822				   SV_ALLOW_BOOTP)) &&
1823	    !evaluate_boolean_option_cache (&ignorep,
1824					    packet, lease,
1825					    (struct client_state *)0,
1826					    packet -> options,
1827					    state -> options,
1828					    &lease -> scope, oc, MDL)) {
1829		if (!ignorep)
1830			log_info ("%s: bootp disallowed", msg);
1831		free_lease_state (state, MDL);
1832		if (host)
1833			host_dereference (&host, MDL);
1834		return;
1835	}
1836
1837	/* Drop the request if booting is specifically denied. */
1838	oc = lookup_option (&server_universe, state -> options,
1839			    SV_ALLOW_BOOTING);
1840	if (oc &&
1841	    !evaluate_boolean_option_cache (&ignorep,
1842					    packet, lease,
1843					    (struct client_state *)0,
1844					    packet -> options,
1845					    state -> options,
1846					    &lease -> scope, oc, MDL)) {
1847		if (!ignorep)
1848			log_info ("%s: booting disallowed", msg);
1849		free_lease_state (state, MDL);
1850		if (host)
1851			host_dereference (&host, MDL);
1852		return;
1853	}
1854
1855	/* If we are configured to do per-class billing, do it. */
1856	if (have_billing_classes && !(lease -> flags & STATIC_LEASE)) {
1857		/* See if the lease is currently being billed to a
1858		   class, and if so, whether or not it can continue to
1859		   be billed to that class. */
1860		if (lease -> billing_class) {
1861			for (i = 0; i < packet -> class_count; i++)
1862				if (packet -> classes [i] ==
1863				    lease -> billing_class)
1864					break;
1865			if (i == packet -> class_count)
1866				unbill_class (lease, lease -> billing_class);
1867		}
1868
1869		/* If we don't have an active billing, see if we need
1870		   one, and if we do, try to do so. */
1871		if (!lease -> billing_class) {
1872			for (i = 0; i < packet -> class_count; i++) {
1873				if (packet -> classes [i] -> lease_limit)
1874					break;
1875			}
1876			if (i != packet -> class_count) {
1877				for (i = 0; i < packet -> class_count; i++)
1878					if ((packet ->
1879					     classes [i] -> lease_limit) &&
1880					    bill_class (lease,
1881							packet -> classes [i]))
1882						break;
1883				if (i == packet -> class_count) {
1884					log_info ("%s: no available billing",
1885						  msg);
1886					free_lease_state (state, MDL);
1887					if (host)
1888						host_dereference (&host, MDL);
1889					/* XXX possibly not necessary: */
1890					return;
1891				}
1892			}
1893		}
1894	}
1895
1896	/* Figure out the filename. */
1897	oc = lookup_option (&server_universe, state -> options, SV_FILENAME);
1898	if (oc)
1899		evaluate_option_cache (&state -> filename, packet, lease,
1900				       (struct client_state *)0,
1901				       packet -> options, state -> options,
1902				       &lease -> scope, oc, MDL);
1903
1904	/* Choose a server name as above. */
1905	oc = lookup_option (&server_universe, state -> options,
1906			    SV_SERVER_NAME);
1907	if (oc)
1908		evaluate_option_cache (&state -> server_name, packet, lease,
1909				       (struct client_state *)0,
1910				       packet -> options, state -> options,
1911				       &lease -> scope, oc, MDL);
1912
1913	/* At this point, we have a lease that we can offer the client.
1914	   Now we construct a lease structure that contains what we want,
1915	   and call supersede_lease to do the right thing with it. */
1916	lt = (struct lease *)0;
1917	result = lease_allocate (&lt, MDL);
1918	if (result != ISC_R_SUCCESS) {
1919		log_info ("%s: can't allocate temporary lease structure: %s",
1920			  msg, isc_result_totext (result));
1921		free_lease_state (state, MDL);
1922		if (host)
1923			host_dereference (&host, MDL);
1924		return;
1925	}
1926
1927	/* Use the ip address of the lease that we finally found in
1928	   the database. */
1929	lt -> ip_addr = lease -> ip_addr;
1930
1931	/* Start now. */
1932	lt -> starts = cur_time;
1933
1934	/* Figure out how long a lease to assign.    If this is a
1935	   dynamic BOOTP lease, its duration must be infinite. */
1936	if (offer) {
1937		default_lease_time = DEFAULT_DEFAULT_LEASE_TIME;
1938		if ((oc = lookup_option (&server_universe, state -> options,
1939					 SV_DEFAULT_LEASE_TIME))) {
1940			if (evaluate_option_cache (&d1, packet, lease,
1941						   (struct client_state *)0,
1942						   packet -> options,
1943						   state -> options,
1944						   &lease -> scope, oc, MDL)) {
1945				if (d1.len == sizeof (u_int32_t))
1946					default_lease_time =
1947						getULong (d1.data);
1948				data_string_forget (&d1, MDL);
1949			}
1950		}
1951
1952		if ((oc = lookup_option (&dhcp_universe, packet -> options,
1953					 DHO_DHCP_LEASE_TIME)))
1954			s1 = evaluate_option_cache (&d1, packet, lease,
1955						    (struct client_state *)0,
1956						    packet -> options,
1957						    state -> options,
1958						    &lease -> scope, oc, MDL);
1959		else
1960			s1 = 0;
1961
1962		if (s1 && d1.len == sizeof (u_int32_t)) {
1963			lease_time = getULong (d1.data);
1964			data_string_forget (&d1, MDL);
1965		} else {
1966			if (s1)
1967				data_string_forget (&d1, MDL);
1968			lease_time = default_lease_time;
1969		}
1970
1971		/* See if there's a maximum lease time. */
1972		max_lease_time = DEFAULT_MAX_LEASE_TIME;
1973		if ((oc = lookup_option (&server_universe, state -> options,
1974					 SV_MAX_LEASE_TIME))) {
1975			if (evaluate_option_cache (&d1, packet, lease,
1976						   (struct client_state *)0,
1977						   packet -> options,
1978						   state -> options,
1979						   &lease -> scope, oc, MDL)) {
1980				if (d1.len == sizeof (u_int32_t))
1981					max_lease_time =
1982						getULong (d1.data);
1983				data_string_forget (&d1, MDL);
1984			}
1985		}
1986
1987		/* Enforce the maximum lease length. */
1988		if (lease_time < 0 /* XXX */
1989		    || lease_time > max_lease_time)
1990			lease_time = max_lease_time;
1991
1992		min_lease_time = DEFAULT_MIN_LEASE_TIME;
1993		if (min_lease_time > max_lease_time)
1994			min_lease_time = max_lease_time;
1995
1996		if ((oc = lookup_option (&server_universe, state -> options,
1997					 SV_MIN_LEASE_TIME))) {
1998			if (evaluate_option_cache (&d1, packet, lease,
1999						   (struct client_state *)0,
2000						   packet -> options,
2001						   state -> options,
2002						   &lease -> scope, oc, MDL)) {
2003				if (d1.len == sizeof (u_int32_t))
2004					min_lease_time = getULong (d1.data);
2005				data_string_forget (&d1, MDL);
2006			}
2007		}
2008
2009		if (lease_time < min_lease_time) {
2010			if (min_lease_time)
2011				lease_time = min_lease_time;
2012			else
2013				lease_time = default_lease_time;
2014		}
2015
2016#if defined (FAILOVER_PROTOCOL)
2017		/* Okay, we know the lease duration.   Now check the
2018		   failover state, if any. */
2019		if (lease -> tsfp) {
2020			lt ->tsfp = lease ->tsfp;
2021		}
2022		if (lease -> pool && lease -> pool -> failover_peer) {
2023			dhcp_failover_state_t *peer =
2024			    lease -> pool -> failover_peer;
2025
2026			/* If the lease time we arrived at exceeds what
2027			   the peer has, we can only issue a lease of
2028			   peer -> mclt, but we can tell the peer we
2029			   want something longer in the future. */
2030			/* XXX This may result in updates that only push
2031			   XXX the peer's expiry time for this lease up
2032			   XXX by a few seconds - think about this again
2033			   XXX later. */
2034			if (lease_time > peer -> mclt &&
2035			    cur_time + lease_time > lease -> tsfp) {
2036				/* Here we're assuming that if we don't have
2037				   to update tstp, there's already an update
2038				   queued.   May want to revisit this.  */
2039				if (peer -> me.state != partner_down &&
2040				    cur_time + lease_time > lease -> tstp)
2041					lt -> tstp = (cur_time + lease_time +
2042						      peer -> mclt / 2);
2043
2044				/* Now choose a lease time that is either
2045				   MCLT, for a lease that's never before been
2046				   assigned, or TSFP + MCLT for a lease that
2047				   has.
2048				   XXX Note that TSFP may be < cur_time.
2049				   XXX What do we do in this case?
2050				   XXX should the expiry timer on the lease
2051				   XXX set tsfp and tstp to zero? */
2052				if (lease -> tsfp < cur_time) {
2053					lease_time = peer -> mclt;
2054				} else {
2055					lease_time = (lease -> tsfp  - cur_time
2056						      + peer -> mclt);
2057				}
2058			} else {
2059				if (cur_time + lease_time > lease -> tsfp &&
2060				    lease_time > peer -> mclt / 2) {
2061					lt -> tstp = (cur_time + lease_time +
2062						      peer -> mclt / 2);
2063				} else {
2064					lt -> tstp = (cur_time + lease_time +
2065						      lease_time / 2);
2066				}
2067			}
2068
2069			lt -> cltt = cur_time;
2070		}
2071#endif /* FAILOVER_PROTOCOL */
2072
2073		/* If the lease duration causes the time value to wrap,
2074		   use the maximum expiry time. */
2075		if (cur_time + lease_time < cur_time)
2076			state -> offered_expiry = MAX_TIME - 1;
2077		else
2078			state -> offered_expiry = cur_time + lease_time;
2079		if (when)
2080			lt -> ends = when;
2081		else
2082			lt -> ends = state -> offered_expiry;
2083
2084		/* Don't make lease active until we actually get a
2085		   DHCPREQUEST. */
2086		if (offer == DHCPACK)
2087			lt -> next_binding_state = FTS_ACTIVE;
2088		else
2089			lt -> next_binding_state = lease -> binding_state;
2090	} else {
2091		lease_time = MAX_TIME - cur_time;
2092
2093		if ((oc = lookup_option (&server_universe, state -> options,
2094					 SV_BOOTP_LEASE_LENGTH))) {
2095			if (evaluate_option_cache (&d1, packet, lease,
2096						   (struct client_state *)0,
2097						   packet -> options,
2098						   state -> options,
2099						   &lease -> scope, oc, MDL)) {
2100				if (d1.len == sizeof (u_int32_t))
2101					lease_time = getULong (d1.data);
2102				data_string_forget (&d1, MDL);
2103			}
2104		}
2105
2106		if ((oc = lookup_option (&server_universe, state -> options,
2107					 SV_BOOTP_LEASE_CUTOFF))) {
2108			if (evaluate_option_cache (&d1, packet, lease,
2109						   (struct client_state *)0,
2110						   packet -> options,
2111						   state -> options,
2112						   &lease -> scope, oc, MDL)) {
2113				if (d1.len == sizeof (u_int32_t))
2114					lease_time = (getULong (d1.data) -
2115						      cur_time);
2116				data_string_forget (&d1, MDL);
2117			}
2118		}
2119
2120		lt -> ends = state -> offered_expiry = cur_time + lease_time;
2121		lt -> next_binding_state = FTS_ACTIVE;
2122	}
2123
2124	lt -> timestamp = cur_time;
2125
2126	/* Record the uid, if given... */
2127	oc = lookup_option (&dhcp_universe, packet -> options,
2128			    DHO_DHCP_CLIENT_IDENTIFIER);
2129	if (oc &&
2130	    evaluate_option_cache (&d1, packet, lease,
2131				   (struct client_state *)0,
2132				   packet -> options, state -> options,
2133				   &lease -> scope, oc, MDL)) {
2134		if (d1.len <= sizeof lt -> uid_buf) {
2135			memcpy (lt -> uid_buf, d1.data, d1.len);
2136			lt -> uid = lt -> uid_buf;
2137			lt -> uid_max = sizeof lt -> uid_buf;
2138			lt -> uid_len = d1.len;
2139		} else {
2140			unsigned char *tuid;
2141			lt -> uid_max = d1.len;
2142			lt -> uid_len = d1.len;
2143			tuid = (unsigned char *)dmalloc (lt -> uid_max, MDL);
2144			/* XXX inelegant */
2145			if (!tuid)
2146				log_fatal ("no memory for large uid.");
2147			memcpy (tuid, d1.data, lt -> uid_len);
2148			lt -> uid = tuid;
2149		}
2150		data_string_forget (&d1, MDL);
2151	}
2152
2153	if (host) {
2154		host_reference (&lt -> host, host, MDL);
2155		host_dereference (&host, MDL);
2156	}
2157	if (lease -> subnet)
2158		subnet_reference (&lt -> subnet, lease -> subnet, MDL);
2159	if (lease -> billing_class)
2160		class_reference (&lt -> billing_class,
2161				 lease -> billing_class, MDL);
2162
2163	/* Set a flag if this client is a broken client that NUL
2164	   terminates string options and expects us to do likewise. */
2165	if (ms_nulltp)
2166		lease -> flags |= MS_NULL_TERMINATION;
2167	else
2168		lease -> flags &= ~MS_NULL_TERMINATION;
2169
2170	/* Save any bindings. */
2171	if (lease -> scope) {
2172		binding_scope_reference (&lt -> scope, lease -> scope, MDL);
2173		binding_scope_dereference (&lease -> scope, MDL);
2174	}
2175	if (lease -> agent_options)
2176		option_chain_head_reference (&lt -> agent_options,
2177					     lease -> agent_options, MDL);
2178
2179	/* If we got relay agent information options, and the packet really
2180	   looks like it came through a relay agent, and if this feature is
2181	   not disabled, save the relay agent information options that came
2182	   in with the packet, so that we can use them at renewal time when
2183	   the packet won't have gone through a relay agent. */
2184	if (packet -> raw -> giaddr.s_addr &&
2185	    packet -> options != NULL &&
2186	    packet -> options -> universe_count > agent_universe.index &&
2187	    packet -> options -> universes [agent_universe.index] &&
2188	    (state -> options -> universe_count <= agent_universe.index ||
2189	     state -> options -> universes [agent_universe.index] ==
2190	     packet -> options -> universes [agent_universe.index])) {
2191	    oc = lookup_option (&server_universe, state -> options,
2192				SV_STASH_AGENT_OPTIONS);
2193	    if (!oc ||
2194		evaluate_boolean_option_cache (&ignorep, packet, lease,
2195					       (struct client_state *)0,
2196					       packet -> options,
2197					       state -> options,
2198					       &lease -> scope, oc, MDL)) {
2199		if (lt -> agent_options)
2200		    option_chain_head_dereference (&lt -> agent_options, MDL);
2201		option_chain_head_reference
2202			(&lt -> agent_options,
2203			 (struct option_chain_head *)
2204			 packet -> options -> universes [agent_universe.index],
2205			 MDL);
2206	    }
2207	}
2208
2209	/* Replace the old lease hostname with the new one, if it's changed. */
2210	oc = lookup_option (&dhcp_universe, packet -> options, DHO_HOST_NAME);
2211	if (oc)
2212		s1 = evaluate_option_cache (&d1, packet, (struct lease *)0,
2213					    (struct client_state *)0,
2214					    packet -> options,
2215					    (struct option_state *)0,
2216					    &global_scope, oc, MDL);
2217	else
2218		s1 = 0;
2219
2220	if (oc && s1 &&
2221	    lease -> client_hostname &&
2222	    strlen (lease -> client_hostname) == d1.len &&
2223	    !memcmp (lease -> client_hostname, d1.data, d1.len)) {
2224		/* Hasn't changed. */
2225		data_string_forget (&d1, MDL);
2226		lt -> client_hostname = lease -> client_hostname;
2227		lease -> client_hostname = (char *)0;
2228	} else if (oc && s1) {
2229		lt -> client_hostname = dmalloc (d1.len + 1, MDL);
2230		if (!lt -> client_hostname)
2231			log_error ("no memory for client hostname.");
2232		else {
2233			memcpy (lt -> client_hostname, d1.data, d1.len);
2234			lt -> client_hostname [d1.len] = 0;
2235		}
2236		data_string_forget (&d1, MDL);
2237	}
2238
2239	/* Record the hardware address, if given... */
2240	lt -> hardware_addr.hlen = packet -> raw -> hlen + 1;
2241	lt -> hardware_addr.hbuf [0] = packet -> raw -> htype;
2242	memcpy (&lt -> hardware_addr.hbuf [1], packet -> raw -> chaddr,
2243		sizeof packet -> raw -> chaddr);
2244
2245	lt -> flags = lease -> flags & ~PERSISTENT_FLAGS;
2246
2247	/* If there are statements to execute when the lease is
2248	   committed, execute them. */
2249	if (lease -> on_commit && (!offer || offer == DHCPACK)) {
2250		execute_statements ((struct binding_value **)0,
2251				    packet, lt, (struct client_state *)0,
2252				    packet -> options,
2253				    state -> options, &lt -> scope,
2254				    lease -> on_commit);
2255		if (lease -> on_commit)
2256			executable_statement_dereference (&lease -> on_commit,
2257							  MDL);
2258	}
2259
2260#ifdef NSUPDATE
2261	/* Perform DDNS updates, if configured to. */
2262	if ((!offer || offer == DHCPACK) &&
2263	    (!(oc = lookup_option (&server_universe, state -> options,
2264				   SV_DDNS_UPDATES)) ||
2265	     evaluate_boolean_option_cache (&ignorep, packet, lt,
2266					    (struct client_state *)0,
2267					    packet -> options,
2268					    state -> options,
2269					    &lt -> scope, oc, MDL))) {
2270		ddns_updates (packet, lt, lease, state);
2271	}
2272#endif /* NSUPDATE */
2273
2274	/* Don't call supersede_lease on a mocked-up lease. */
2275	if (lease -> flags & STATIC_LEASE) {
2276		/* Copy the hardware address into the static lease
2277		   structure. */
2278		lease -> hardware_addr.hlen = packet -> raw -> hlen + 1;
2279		lease -> hardware_addr.hbuf [0] = packet -> raw -> htype;
2280		memcpy (&lease -> hardware_addr.hbuf [1],
2281			packet -> raw -> chaddr,
2282			sizeof packet -> raw -> chaddr); /* XXX */
2283	} else {
2284		/* Install the new information about this lease in the
2285		   database.  If this is a DHCPACK or a dynamic BOOTREPLY
2286		   and we can't write the lease, don't ACK it (or BOOTREPLY
2287		   it) either. */
2288
2289		if (!supersede_lease (lease, lt, !offer || offer == DHCPACK,
2290				      offer == DHCPACK, offer == DHCPACK)) {
2291			log_info ("%s: database update failed", msg);
2292			free_lease_state (state, MDL);
2293			lease_dereference (&lt, MDL);
2294			return;
2295		}
2296	}
2297	lease_dereference (&lt, MDL);
2298
2299	/* Remember the interface on which the packet arrived. */
2300	state -> ip = packet -> interface;
2301
2302	/* Remember the giaddr, xid, secs, flags and hops. */
2303	state -> giaddr = packet -> raw -> giaddr;
2304	state -> ciaddr = packet -> raw -> ciaddr;
2305	state -> xid = packet -> raw -> xid;
2306	state -> secs = packet -> raw -> secs;
2307	state -> bootp_flags = packet -> raw -> flags;
2308	state -> hops = packet -> raw -> hops;
2309	state -> offer = offer;
2310
2311	/* If we're always supposed to broadcast to this client, set
2312	   the broadcast bit in the bootp flags field. */
2313	if ((oc = lookup_option (&server_universe, state -> options,
2314				SV_ALWAYS_BROADCAST)) &&
2315	    evaluate_boolean_option_cache (&ignorep, packet, lease,
2316					   (struct client_state *)0,
2317					   packet -> options, state -> options,
2318					   &lease -> scope, oc, MDL))
2319		state -> bootp_flags |= htons (BOOTP_BROADCAST);
2320
2321	/* Get the Maximum Message Size option from the packet, if one
2322	   was sent. */
2323	oc = lookup_option (&dhcp_universe, packet -> options,
2324			    DHO_DHCP_MAX_MESSAGE_SIZE);
2325	if (oc &&
2326	    evaluate_option_cache (&d1, packet, lease,
2327				   (struct client_state *)0,
2328				   packet -> options, state -> options,
2329				   &lease -> scope, oc, MDL)) {
2330		if (d1.len == sizeof (u_int16_t))
2331			state -> max_message_size = getUShort (d1.data);
2332		data_string_forget (&d1, MDL);
2333	} else {
2334		oc = lookup_option (&dhcp_universe, state -> options,
2335				    DHO_DHCP_MAX_MESSAGE_SIZE);
2336		if (oc &&
2337		    evaluate_option_cache (&d1, packet, lease,
2338					   (struct client_state *)0,
2339					   packet -> options, state -> options,
2340					   &lease -> scope, oc, MDL)) {
2341			if (d1.len == sizeof (u_int16_t))
2342				state -> max_message_size =
2343					getUShort (d1.data);
2344			data_string_forget (&d1, MDL);
2345		}
2346	}
2347
2348	/* Get the Subnet Selection option from the packet, if one
2349	   was sent. */
2350	if ((oc = lookup_option (&dhcp_universe, packet -> options,
2351				 DHO_SUBNET_SELECTION))) {
2352
2353		/* Make a copy of the data. */
2354		struct option_cache *noc = (struct option_cache *)0;
2355		if (option_cache_allocate (&noc, MDL)) {
2356			if (oc -> data.len)
2357				data_string_copy (&noc -> data,
2358						  &oc -> data, MDL);
2359			if (oc -> expression)
2360				expression_reference (&noc -> expression,
2361						      oc -> expression, MDL);
2362			if (oc -> option)
2363				noc -> option = oc -> option;
2364		}
2365
2366		save_option (&dhcp_universe, state -> options, noc);
2367		option_cache_dereference (&noc, MDL);
2368	}
2369
2370	/* Now, if appropriate, put in DHCP-specific options that
2371           override those. */
2372	if (state -> offer) {
2373		i = DHO_DHCP_MESSAGE_TYPE;
2374		oc = (struct option_cache *)0;
2375		if (option_cache_allocate (&oc, MDL)) {
2376			if (make_const_data (&oc -> expression,
2377					     &state -> offer, 1, 0, 0, MDL)) {
2378				oc -> option =
2379					dhcp_universe.options [i];
2380				save_option (&dhcp_universe,
2381					     state -> options, oc);
2382			}
2383			option_cache_dereference (&oc, MDL);
2384		}
2385		i = DHO_DHCP_SERVER_IDENTIFIER;
2386		if (!(oc = lookup_option (&dhcp_universe,
2387					  state -> options, i))) {
2388		 use_primary:
2389			oc = (struct option_cache *)0;
2390			if (option_cache_allocate (&oc, MDL)) {
2391				if (make_const_data
2392				    (&oc -> expression,
2393				     ((unsigned char *)
2394				      &state -> ip -> primary_address),
2395				     sizeof state -> ip -> primary_address,
2396				     0, 0, MDL)) {
2397					oc -> option =
2398						dhcp_universe.options [i];
2399					save_option (&dhcp_universe,
2400						     state -> options, oc);
2401				}
2402				option_cache_dereference (&oc, MDL);
2403			}
2404			state -> from.len =
2405				sizeof state -> ip -> primary_address;
2406			memcpy (state -> from.iabuf,
2407				&state -> ip -> primary_address,
2408				state -> from.len);
2409		} else {
2410			if (evaluate_option_cache (&d1, packet, lease,
2411						   (struct client_state *)0,
2412						   packet -> options,
2413						   state -> options,
2414						   &lease -> scope, oc, MDL)) {
2415				if (!d1.len ||
2416				    d1.len > sizeof state -> from.iabuf) {
2417					data_string_forget (&d1, MDL);
2418					goto use_primary;
2419				}
2420				memcpy (state -> from.iabuf, d1.data, d1.len);
2421				state -> from.len = d1.len;
2422				data_string_forget (&d1, MDL);
2423			} else
2424				goto use_primary;
2425		}
2426
2427		offered_lease_time =
2428			state -> offered_expiry - cur_time;
2429
2430		putULong ((unsigned char *)&state -> expiry,
2431			  (unsigned long)offered_lease_time);
2432		i = DHO_DHCP_LEASE_TIME;
2433		if (lookup_option (&dhcp_universe, state -> options, i))
2434			log_error ("dhcp-lease-time option for %s overridden.",
2435			      inet_ntoa (state -> ciaddr));
2436		oc = (struct option_cache *)0;
2437		if (option_cache_allocate (&oc, MDL)) {
2438			if (make_const_data (&oc -> expression,
2439					     (unsigned char *)&state -> expiry,
2440					     sizeof state -> expiry,
2441					     0, 0, MDL)) {
2442				oc -> option = dhcp_universe.options [i];
2443				save_option (&dhcp_universe,
2444					     state -> options, oc);
2445			}
2446			option_cache_dereference (&oc, MDL);
2447		}
2448
2449		/* Renewal time is lease time * 0.5. */
2450		offered_lease_time /= 2;
2451		putULong ((unsigned char *)&state -> renewal,
2452			  (unsigned long)offered_lease_time);
2453		i = DHO_DHCP_RENEWAL_TIME;
2454		if (lookup_option (&dhcp_universe, state -> options, i))
2455			log_error ("overriding dhcp-renewal-time for %s.",
2456				   inet_ntoa (state -> ciaddr));
2457		oc = (struct option_cache *)0;
2458		if (option_cache_allocate (&oc, MDL)) {
2459			if (make_const_data (&oc -> expression,
2460					     (unsigned char *)
2461					     &state -> renewal,
2462					     sizeof state -> renewal,
2463					     0, 0, MDL)) {
2464				oc -> option = dhcp_universe.options [i];
2465				save_option (&dhcp_universe,
2466					     state -> options, oc);
2467			}
2468			option_cache_dereference (&oc, MDL);
2469		}
2470
2471		/* Rebinding time is lease time * 0.875. */
2472		offered_lease_time += (offered_lease_time / 2
2473				       + offered_lease_time / 4);
2474		putULong ((unsigned char *)&state -> rebind,
2475			  (unsigned)offered_lease_time);
2476		i = DHO_DHCP_REBINDING_TIME;
2477		if (lookup_option (&dhcp_universe, state -> options, i))
2478			log_error ("overriding dhcp-rebinding-time for %s.",
2479			      inet_ntoa (state -> ciaddr));
2480		oc = (struct option_cache *)0;
2481		if (option_cache_allocate (&oc, MDL)) {
2482			if (make_const_data (&oc -> expression,
2483					     (unsigned char *)&state -> rebind,
2484					     sizeof state -> rebind,
2485					     0, 0, MDL)) {
2486				oc -> option = dhcp_universe.options [i];
2487				save_option (&dhcp_universe,
2488					     state -> options, oc);
2489			}
2490			option_cache_dereference (&oc, MDL);
2491		}
2492	} else {
2493		state -> from.len =
2494			sizeof state -> ip -> primary_address;
2495		memcpy (state -> from.iabuf,
2496			&state -> ip -> primary_address,
2497			state -> from.len);
2498	}
2499
2500	/* Figure out the address of the boot file server. */
2501	memset (&state -> siaddr, 0, sizeof state -> siaddr);
2502	if ((oc =
2503	     lookup_option (&server_universe,
2504			    state -> options, SV_NEXT_SERVER))) {
2505		if (evaluate_option_cache (&d1, packet, lease,
2506					   (struct client_state *)0,
2507					   packet -> options, state -> options,
2508					   &lease -> scope, oc, MDL)) {
2509			/* If there was more than one answer,
2510			   take the first. */
2511			if (d1.len >= 4 && d1.data)
2512				memcpy (&state -> siaddr, d1.data, 4);
2513			data_string_forget (&d1, MDL);
2514		}
2515	}
2516
2517	/* Use the subnet mask from the subnet declaration if no other
2518	   mask has been provided. */
2519	i = DHO_SUBNET_MASK;
2520	if (!lookup_option (&dhcp_universe, state -> options, i)) {
2521		oc = (struct option_cache *)0;
2522		if (option_cache_allocate (&oc, MDL)) {
2523			if (make_const_data (&oc -> expression,
2524					     lease -> subnet -> netmask.iabuf,
2525					     lease -> subnet -> netmask.len,
2526					     0, 0, MDL)) {
2527				oc -> option = dhcp_universe.options [i];
2528				save_option (&dhcp_universe,
2529					     state -> options, oc);
2530			}
2531			option_cache_dereference (&oc, MDL);
2532		}
2533	}
2534
2535	/* Use the hostname from the host declaration if there is one
2536	   and no hostname has otherwise been provided, and if the
2537	   use-host-decl-name flag is set. */
2538	i = DHO_HOST_NAME;
2539	j = SV_USE_HOST_DECL_NAMES;
2540	if (!lookup_option (&dhcp_universe, state -> options, i) &&
2541	    lease -> host && lease -> host -> name &&
2542	    (evaluate_boolean_option_cache
2543	     (&ignorep, packet, lease, (struct client_state *)0,
2544	      packet -> options, state -> options, &lease -> scope,
2545	      lookup_option (&server_universe, state -> options, j), MDL))) {
2546		oc = (struct option_cache *)0;
2547		if (option_cache_allocate (&oc, MDL)) {
2548			if (make_const_data (&oc -> expression,
2549					     ((unsigned char *)
2550					      lease -> host -> name),
2551					     strlen (lease -> host -> name),
2552					     1, 0, MDL)) {
2553				oc -> option = dhcp_universe.options [i];
2554				save_option (&dhcp_universe,
2555					     state -> options, oc);
2556			}
2557			option_cache_dereference (&oc, MDL);
2558		}
2559	}
2560
2561	/* If we don't have a hostname yet, and we've been asked to do
2562	   a reverse lookup to find the hostname, do it. */
2563	j = SV_GET_LEASE_HOSTNAMES;
2564	if (!lookup_option (&dhcp_universe, state -> options, i) &&
2565	    (evaluate_boolean_option_cache
2566	     (&ignorep, packet, lease, (struct client_state *)0,
2567	      packet -> options, state -> options, &lease -> scope,
2568	      lookup_option (&server_universe, state -> options, j), MDL))) {
2569		struct in_addr ia;
2570		struct hostent *h;
2571
2572		memcpy (&ia, lease -> ip_addr.iabuf, 4);
2573
2574		h = gethostbyaddr ((char *)&ia, sizeof ia, AF_INET);
2575		if (!h)
2576			log_error ("No hostname for %s", inet_ntoa (ia));
2577		else {
2578			oc = (struct option_cache *)0;
2579			if (option_cache_allocate (&oc, MDL)) {
2580				if (make_const_data (&oc -> expression,
2581						     ((unsigned char *)
2582						      h -> h_name),
2583						     strlen (h -> h_name) + 1,
2584						     1, 1, MDL)) {
2585					oc -> option =
2586						dhcp_universe.options [i];
2587					save_option (&dhcp_universe,
2588						     state -> options, oc);
2589				}
2590				option_cache_dereference (&oc, MDL);
2591			}
2592		}
2593	}
2594
2595	/* If so directed, use the leased IP address as the router address.
2596	   This supposedly makes Win95 machines ARP for all IP addresses,
2597	   so if the local router does proxy arp, you win. */
2598
2599	if (evaluate_boolean_option_cache
2600	    (&ignorep, packet, lease, (struct client_state *)0,
2601	     packet -> options, state -> options, &lease -> scope,
2602	     lookup_option (&server_universe, state -> options,
2603			    SV_USE_LEASE_ADDR_FOR_DEFAULT_ROUTE), MDL)) {
2604		i = DHO_ROUTERS;
2605		oc = lookup_option (&dhcp_universe, state -> options, i);
2606		if (!oc) {
2607			oc = (struct option_cache *)0;
2608			if (option_cache_allocate (&oc, MDL)) {
2609				if (make_const_data (&oc -> expression,
2610						     lease -> ip_addr.iabuf,
2611						     lease -> ip_addr.len,
2612						     0, 0, MDL)) {
2613					oc -> option =
2614						dhcp_universe.options [i];
2615					save_option (&dhcp_universe,
2616						     state -> options, oc);
2617				}
2618				option_cache_dereference (&oc, MDL);
2619			}
2620		}
2621	}
2622
2623	/* If a site option space has been specified, use that for
2624	   site option codes. */
2625	i = SV_SITE_OPTION_SPACE;
2626	if ((oc = lookup_option (&server_universe, state -> options, i)) &&
2627	    evaluate_option_cache (&d1, packet, lease,
2628				   (struct client_state *)0,
2629				   packet -> options, state -> options,
2630				   &lease -> scope, oc, MDL)) {
2631		struct universe *u = (struct universe *)0;
2632
2633		if (!universe_hash_lookup (&u, universe_hash,
2634					   (const char *)d1.data, d1.len,
2635					   MDL)) {
2636			log_error ("unknown option space %s.", d1.data);
2637			return;
2638		}
2639
2640		state -> options -> site_universe = u -> index;
2641		state -> options -> site_code_min = 128; /* XXX */
2642		data_string_forget (&d1, MDL);
2643	} else {
2644		state -> options -> site_code_min = 0;
2645		state -> options -> site_universe = dhcp_universe.index;
2646	}
2647
2648	/* If the client has provided a list of options that it wishes
2649	   returned, use it to prioritize.  If there's a parameter
2650	   request list in scope, use that in preference.  Otherwise
2651	   use the default priority list. */
2652
2653	oc = lookup_option (&dhcp_universe, state -> options,
2654			    DHO_DHCP_PARAMETER_REQUEST_LIST);
2655
2656	if (!oc)
2657		oc = lookup_option (&dhcp_universe, packet -> options,
2658				    DHO_DHCP_PARAMETER_REQUEST_LIST);
2659	if (oc)
2660		evaluate_option_cache (&state -> parameter_request_list,
2661				       packet, lease, (struct client_state *)0,
2662				       packet -> options, state -> options,
2663				       &lease -> scope, oc, MDL);
2664
2665#ifdef DEBUG_PACKET
2666	dump_packet (packet);
2667	dump_raw ((unsigned char *)packet -> raw, packet -> packet_length);
2668#endif
2669
2670	lease -> state = state;
2671
2672	log_info ("%s", msg);
2673
2674	/* Hang the packet off the lease state. */
2675	packet_reference (&lease -> state -> packet, packet, MDL);
2676
2677	/* If this is a DHCPOFFER, ping the lease address before actually
2678	   sending the offer. */
2679	if (offer == DHCPOFFER && !(lease -> flags & STATIC_LEASE) &&
2680	    cur_time - lease -> timestamp > 60 &&
2681	    (!(oc = lookup_option (&server_universe, state -> options,
2682				   SV_PING_CHECKS)) ||
2683	     evaluate_boolean_option_cache (&ignorep, packet, lease,
2684					    (struct client_state *)0,
2685					    packet -> options,
2686					    state -> options,
2687					    &lease -> scope, oc, MDL))) {
2688		lease -> timestamp = cur_time;
2689		icmp_echorequest (&lease -> ip_addr);
2690
2691		/* Determine whether to use configured or default ping timeout.
2692		 */
2693		if ((oc = lookup_option (&server_universe, state -> options,
2694						SV_PING_TIMEOUT)) &&
2695		    evaluate_option_cache (&d1, packet, lease, NULL,
2696						packet -> options,
2697						state -> options,
2698						&lease -> scope, oc, MDL)) {
2699			if (d1.len == sizeof (u_int32_t))
2700				ping_timeout = getULong (d1.data);
2701			else
2702				ping_timeout = DEFAULT_PING_TIMEOUT;
2703
2704			data_string_forget (&d1, MDL);
2705		} else
2706			ping_timeout = DEFAULT_PING_TIMEOUT;
2707
2708#ifdef DEBUG
2709		log_debug ("Ping timeout: %ld", (long)ping_timeout);
2710#endif
2711
2712		add_timeout (cur_time + ping_timeout, lease_ping_timeout, lease,
2713			     (tvref_t)lease_reference,
2714			     (tvunref_t)lease_dereference);
2715		++outstanding_pings;
2716	} else {
2717		lease -> timestamp = cur_time;
2718		dhcp_reply (lease);
2719	}
2720}
2721
2722void dhcp_reply (lease)
2723	struct lease *lease;
2724{
2725	int bufs = 0;
2726	unsigned packet_length;
2727	struct dhcp_packet raw;
2728	struct sockaddr_in to;
2729	struct in_addr from;
2730	struct hardware hto;
2731	int result;
2732	struct lease_state *state = lease -> state;
2733	int nulltp, bootpp, unicastp = 1;
2734	struct data_string d1;
2735	const char *s;
2736
2737	if (!state)
2738		log_fatal ("dhcp_reply was supplied lease with no state!");
2739
2740	/* Compose a response for the client... */
2741	memset (&raw, 0, sizeof raw);
2742	memset (&d1, 0, sizeof d1);
2743
2744	/* Copy in the filename if given; otherwise, flag the filename
2745	   buffer as available for options. */
2746	if (state -> filename.len && state -> filename.data) {
2747		memcpy (raw.file,
2748			state -> filename.data,
2749			state -> filename.len > sizeof raw.file
2750			? sizeof raw.file : state -> filename.len);
2751		if (sizeof raw.file > state -> filename.len)
2752			memset (&raw.file [state -> filename.len], 0,
2753				(sizeof raw.file) - state -> filename.len);
2754	} else
2755		bufs |= 1;
2756
2757	/* Copy in the server name if given; otherwise, flag the
2758	   server_name buffer as available for options. */
2759	if (state -> server_name.len && state -> server_name.data) {
2760		memcpy (raw.sname,
2761			state -> server_name.data,
2762			state -> server_name.len > sizeof raw.sname
2763			? sizeof raw.sname : state -> server_name.len);
2764		if (sizeof raw.sname > state -> server_name.len)
2765			memset (&raw.sname [state -> server_name.len], 0,
2766				(sizeof raw.sname) - state -> server_name.len);
2767	} else
2768		bufs |= 2; /* XXX */
2769
2770	memcpy (raw.chaddr,
2771		&lease -> hardware_addr.hbuf [1], sizeof raw.chaddr);
2772	raw.hlen = lease -> hardware_addr.hlen - 1;
2773	raw.htype = lease -> hardware_addr.hbuf [0];
2774
2775	/* See if this is a Microsoft client that NUL-terminates its
2776	   strings and expects us to do likewise... */
2777	if (lease -> flags & MS_NULL_TERMINATION)
2778		nulltp = 1;
2779	else
2780		nulltp = 0;
2781
2782	/* See if this is a bootp client... */
2783	if (state -> offer)
2784		bootpp = 0;
2785	else
2786		bootpp = 1;
2787
2788	/* Insert such options as will fit into the buffer. */
2789	packet_length = cons_options (state -> packet, &raw, lease,
2790				      (struct client_state *)0,
2791				      state -> max_message_size,
2792				      state -> packet -> options,
2793				      state -> options, &global_scope,
2794				      bufs, nulltp, bootpp,
2795				      &state -> parameter_request_list,
2796				      (char *)0);
2797
2798	memcpy (&raw.ciaddr, &state -> ciaddr, sizeof raw.ciaddr);
2799	memcpy (&raw.yiaddr, lease -> ip_addr.iabuf, 4);
2800	raw.siaddr = state -> siaddr;
2801	raw.giaddr = state -> giaddr;
2802
2803	raw.xid = state -> xid;
2804	raw.secs = state -> secs;
2805	raw.flags = state -> bootp_flags;
2806	raw.hops = state -> hops;
2807	raw.op = BOOTREPLY;
2808
2809	if (lease -> client_hostname) {
2810		if ((strlen (lease -> client_hostname) <= 64) &&
2811		    db_printable (lease -> client_hostname))
2812			s = lease -> client_hostname;
2813		else
2814			s = "Hostname Unsuitable for Printing";
2815	} else
2816		s = (char *)0;
2817
2818	/* Say what we're doing... */
2819	log_info ("%s on %s to %s %s%s%svia %s",
2820		  (state -> offer
2821		   ? (state -> offer == DHCPACK ? "DHCPACK" : "DHCPOFFER")
2822		   : "BOOTREPLY"),
2823		  piaddr (lease -> ip_addr),
2824		  (lease -> hardware_addr.hlen
2825		   ? print_hw_addr (lease -> hardware_addr.hbuf [0],
2826				    lease -> hardware_addr.hlen - 1,
2827				    &lease -> hardware_addr.hbuf [1])
2828		   : print_hex_1 (lease -> uid_len, lease -> uid,
2829				  lease -> uid_len)),
2830		  s ? "(" : "", s ? s : "", s ? ") " : "",
2831		  (state -> giaddr.s_addr
2832		   ? inet_ntoa (state -> giaddr)
2833		   : state -> ip -> name));
2834
2835	/* Set up the hardware address... */
2836	hto.hlen = lease -> hardware_addr.hlen;
2837	memcpy (hto.hbuf, lease -> hardware_addr.hbuf, hto.hlen);
2838
2839	memset(&to, 0, sizeof(to));
2840	to.sin_family = AF_INET;
2841#ifdef HAVE_SA_LEN
2842	to.sin_len = sizeof to;
2843#endif
2844
2845#ifdef DEBUG_PACKET
2846	dump_raw ((unsigned char *)&raw, packet_length);
2847#endif
2848
2849	/* Make sure outgoing packets are at least as big
2850	   as a BOOTP packet. */
2851	if (packet_length < BOOTP_MIN_LEN)
2852		packet_length = BOOTP_MIN_LEN;
2853
2854	/* If this was gatewayed, send it back to the gateway... */
2855	if (raw.giaddr.s_addr) {
2856		to.sin_addr = raw.giaddr;
2857		if (raw.giaddr.s_addr != htonl (INADDR_LOOPBACK))
2858			to.sin_port = local_port;
2859		else
2860			to.sin_port = remote_port; /* For debugging. */
2861
2862		if (fallback_interface) {
2863			result = send_packet (fallback_interface,
2864					      (struct packet *)0,
2865					      &raw, packet_length,
2866					      raw.siaddr, &to,
2867					      (struct hardware *)0);
2868
2869			free_lease_state (state, MDL);
2870			lease -> state = (struct lease_state *)0;
2871			return;
2872		}
2873
2874	/* If the client is RENEWING, unicast to the client using the
2875	   regular IP stack.  Some clients, particularly those that
2876	   follow RFC1541, are buggy, and send both ciaddr and server
2877	   identifier.  We deal with this situation by assuming that
2878	   if we got both dhcp-server-identifier and ciaddr, and
2879	   giaddr was not set, then the client is on the local
2880	   network, and we can therefore unicast or broadcast to it
2881	   successfully.  A client in REQUESTING state on another
2882	   network that's making this mistake will have set giaddr,
2883	   and will therefore get a relayed response from the above
2884	   code. */
2885	} else if (raw.ciaddr.s_addr &&
2886		   !((state -> got_server_identifier ||
2887		      (raw.flags & htons (BOOTP_BROADCAST))) &&
2888		     /* XXX This won't work if giaddr isn't zero, but it is: */
2889		     (state -> shared_network ==
2890		      lease -> subnet -> shared_network)) &&
2891		   state -> offer == DHCPACK) {
2892		to.sin_addr = raw.ciaddr;
2893		to.sin_port = remote_port;
2894
2895		if (fallback_interface) {
2896			result = send_packet (fallback_interface,
2897					      (struct packet *)0,
2898					      &raw, packet_length,
2899					      raw.siaddr, &to,
2900					      (struct hardware *)0);
2901			free_lease_state (state, MDL);
2902			lease -> state = (struct lease_state *)0;
2903			return;
2904		}
2905
2906	/* If it comes from a client that already knows its address
2907	   and is not requesting a broadcast response, and we can
2908	   unicast to a client without using the ARP protocol, sent it
2909	   directly to that client. */
2910	} else if (!(raw.flags & htons (BOOTP_BROADCAST)) &&
2911		   can_unicast_without_arp (state -> ip)) {
2912		to.sin_addr = raw.yiaddr;
2913		to.sin_port = remote_port;
2914
2915	/* Otherwise, broadcast it on the local network. */
2916	} else {
2917		to.sin_addr = limited_broadcast;
2918		to.sin_port = remote_port;
2919		if (!(lease -> flags & UNICAST_BROADCAST_HACK))
2920			unicastp = 0;
2921	}
2922
2923	memcpy (&from, state -> from.iabuf, sizeof from);
2924
2925	result = send_packet (state -> ip,
2926			      (struct packet *)0, &raw, packet_length,
2927			      from, &to,
2928			      unicastp ? &hto : (struct hardware *)0);
2929
2930	/* Free all of the entries in the option_state structure
2931	   now that we're done with them. */
2932
2933	free_lease_state (state, MDL);
2934	lease -> state = (struct lease_state *)0;
2935}
2936
2937int find_lease (struct lease **lp,
2938		struct packet *packet, struct shared_network *share, int *ours,
2939		int *allocatedp, struct lease *ip_lease_in,
2940		const char *file, int line)
2941{
2942	struct lease *uid_lease = (struct lease *)0;
2943	struct lease *ip_lease = (struct lease *)0;
2944	struct lease *hw_lease = (struct lease *)0;
2945	struct lease *lease = (struct lease *)0;
2946	struct iaddr cip;
2947	struct host_decl *hp = (struct host_decl *)0;
2948	struct host_decl *host = (struct host_decl *)0;
2949	struct lease *fixed_lease = (struct lease *)0;
2950	struct lease *next = (struct lease *)0;
2951	struct option_cache *oc;
2952	struct data_string d1;
2953	int have_client_identifier = 0;
2954	struct data_string client_identifier;
2955	struct hardware h;
2956
2957	if (packet -> raw -> ciaddr.s_addr) {
2958		cip.len = 4;
2959		memcpy (cip.iabuf, &packet -> raw -> ciaddr, 4);
2960	} else {
2961		/* Look up the requested address. */
2962		oc = lookup_option (&dhcp_universe, packet -> options,
2963				    DHO_DHCP_REQUESTED_ADDRESS);
2964		memset (&d1, 0, sizeof d1);
2965		if (oc &&
2966		    evaluate_option_cache (&d1, packet, (struct lease *)0,
2967					   (struct client_state *)0,
2968					   packet -> options,
2969					   (struct option_state *)0,
2970					   &global_scope, oc, MDL)) {
2971			packet -> got_requested_address = 1;
2972			cip.len = 4;
2973			memcpy (cip.iabuf, d1.data, cip.len);
2974			data_string_forget (&d1, MDL);
2975		} else
2976			cip.len = 0;
2977	}
2978
2979	/* Try to find a host or lease that's been assigned to the
2980	   specified unique client identifier. */
2981	oc = lookup_option (&dhcp_universe, packet -> options,
2982			    DHO_DHCP_CLIENT_IDENTIFIER);
2983	memset (&client_identifier, 0, sizeof client_identifier);
2984	if (oc &&
2985	    evaluate_option_cache (&client_identifier,
2986				   packet, (struct lease *)0,
2987				   (struct client_state *)0,
2988				   packet -> options, (struct option_state *)0,
2989				   &global_scope, oc, MDL)) {
2990		/* Remember this for later. */
2991		have_client_identifier = 1;
2992
2993		/* First, try to find a fixed host entry for the specified
2994		   client identifier... */
2995		if (find_hosts_by_uid (&hp, client_identifier.data,
2996				       client_identifier.len, MDL)) {
2997			/* Remember if we know of this client. */
2998			packet -> known = 1;
2999			mockup_lease (&fixed_lease, packet, share, hp);
3000		}
3001
3002#if defined (DEBUG_FIND_LEASE)
3003		if (fixed_lease) {
3004			log_info ("Found host for client identifier: %s.",
3005			      piaddr (fixed_lease -> ip_addr));
3006		}
3007#endif
3008		if (hp) {
3009			if (!fixed_lease) /* Save the host if we found one. */
3010				host_reference (&host, hp, MDL);
3011			host_dereference (&hp, MDL);
3012		}
3013
3014		find_lease_by_uid (&uid_lease, client_identifier.data,
3015				   client_identifier.len, MDL);
3016	}
3017
3018	/* If we didn't find a fixed lease using the uid, try doing
3019	   it with the hardware address... */
3020	if (!fixed_lease && !host) {
3021		if (find_hosts_by_haddr (&hp, packet -> raw -> htype,
3022					 packet -> raw -> chaddr,
3023					 packet -> raw -> hlen, MDL)) {
3024			/* Remember if we know of this client. */
3025			packet -> known = 1;
3026			if (host)
3027				host_dereference (&host, MDL);
3028			host_reference (&host, hp, MDL);
3029			host_dereference (&hp, MDL);
3030			mockup_lease (&fixed_lease, packet, share, host);
3031#if defined (DEBUG_FIND_LEASE)
3032			if (fixed_lease) {
3033				log_info ("Found host for link address: %s.",
3034				      piaddr (fixed_lease -> ip_addr));
3035			}
3036#endif
3037		}
3038	}
3039
3040	/* If fixed_lease is present but does not match the requested
3041	   IP address, and this is a DHCPREQUEST, then we can't return
3042	   any other lease, so we might as well return now. */
3043	if (packet -> packet_type == DHCPREQUEST && fixed_lease &&
3044	    (fixed_lease -> ip_addr.len != cip.len ||
3045	     memcmp (fixed_lease -> ip_addr.iabuf,
3046		     cip.iabuf, cip.len))) {
3047		if (ours)
3048			*ours = 1;
3049		strcpy (dhcp_message, "requested address is incorrect");
3050#if defined (DEBUG_FIND_LEASE)
3051		log_info ("Client's fixed-address %s doesn't match %s%s",
3052			  piaddr (fixed_lease -> ip_addr), "request ",
3053			  print_dotted_quads (cip.len, cip.iabuf));
3054#endif
3055		goto out;
3056	}
3057
3058	/* If we found leases matching the client identifier, loop through
3059	   the n_uid pointer looking for one that's actually valid.   We
3060	   can't do this until we get here because we depend on
3061	   packet -> known, which may be set by either the uid host
3062	   lookup or the haddr host lookup. */
3063	while (uid_lease) {
3064#if defined (DEBUG_FIND_LEASE)
3065		log_info ("trying next lease matching client id: %s",
3066			  piaddr (uid_lease -> ip_addr));
3067#endif
3068
3069#if defined (FAILOVER_PROTOCOL)
3070		/* When failover is active, it's possible that there could
3071		   be two "free" leases for the same uid, but only one of
3072		   them that's available for this failover peer to allocate. */
3073		if (uid_lease -> binding_state != FTS_ACTIVE &&
3074		    !lease_mine_to_reallocate (uid_lease)) {
3075#if defined (DEBUG_FIND_LEASE)
3076			log_info ("not mine to allocate: %s",
3077				  piaddr (uid_lease -> ip_addr));
3078#endif
3079			goto n_uid;
3080		}
3081#endif
3082
3083		if (uid_lease -> subnet -> shared_network != share) {
3084#if defined (DEBUG_FIND_LEASE)
3085			log_info ("wrong network segment: %s",
3086				  piaddr (uid_lease -> ip_addr));
3087#endif
3088			goto n_uid;
3089		}
3090
3091		if ((uid_lease -> pool -> prohibit_list &&
3092		     permitted (packet, uid_lease -> pool -> prohibit_list)) ||
3093		    (uid_lease -> pool -> permit_list &&
3094		     !permitted (packet, uid_lease -> pool -> permit_list))) {
3095#if defined (DEBUG_FIND_LEASE)
3096			log_info ("not permitted: %s",
3097				  piaddr (uid_lease -> ip_addr));
3098#endif
3099		       n_uid:
3100			if (uid_lease -> n_uid)
3101				lease_reference (&next,
3102						 uid_lease -> n_uid, MDL);
3103			if (!packet -> raw -> ciaddr.s_addr)
3104				release_lease (uid_lease, packet);
3105			lease_dereference (&uid_lease, MDL);
3106			if (next) {
3107				lease_reference (&uid_lease, next, MDL);
3108				lease_dereference (&next, MDL);
3109			}
3110			continue;
3111		}
3112		break;
3113	}
3114#if defined (DEBUG_FIND_LEASE)
3115	if (uid_lease)
3116		log_info ("Found lease for client id: %s.",
3117		      piaddr (uid_lease -> ip_addr));
3118#endif
3119
3120	/* Find a lease whose hardware address matches, whose client
3121	   identifier matches, that's permitted, and that's on the
3122	   correct subnet. */
3123	h.hlen = packet -> raw -> hlen + 1;
3124	h.hbuf [0] = packet -> raw -> htype;
3125	memcpy (&h.hbuf [1], packet -> raw -> chaddr, packet -> raw -> hlen);
3126	find_lease_by_hw_addr (&hw_lease, h.hbuf, h.hlen, MDL);
3127	while (hw_lease) {
3128#if defined (DEBUG_FIND_LEASE)
3129		log_info ("trying next lease matching hw addr: %s",
3130			  piaddr (hw_lease -> ip_addr));
3131#endif
3132#if defined (FAILOVER_PROTOCOL)
3133		/* When failover is active, it's possible that there could
3134		   be two "free" leases for the same uid, but only one of
3135		   them that's available for this failover peer to allocate. */
3136		if (hw_lease -> binding_state != FTS_ACTIVE &&
3137		    !lease_mine_to_reallocate (hw_lease)) {
3138#if defined (DEBUG_FIND_LEASE)
3139			log_info ("not mine to allocate: %s",
3140				  piaddr (hw_lease -> ip_addr));
3141#endif
3142			goto n_hw;
3143		}
3144#endif
3145
3146		if (hw_lease -> binding_state != FTS_FREE &&
3147		    hw_lease -> binding_state != FTS_BACKUP &&
3148		    hw_lease -> uid &&
3149		    (!have_client_identifier ||
3150		     hw_lease -> uid_len != client_identifier.len ||
3151		     memcmp (hw_lease -> uid, client_identifier.data,
3152			     hw_lease -> uid_len))) {
3153#if defined (DEBUG_FIND_LEASE)
3154			log_info ("wrong client identifier: %s",
3155				  piaddr (hw_lease -> ip_addr));
3156#endif
3157			goto n_hw;
3158			continue;
3159		}
3160		if (hw_lease -> subnet -> shared_network != share) {
3161#if defined (DEBUG_FIND_LEASE)
3162			log_info ("wrong network segment: %s",
3163				  piaddr (hw_lease -> ip_addr));
3164#endif
3165			goto n_hw;
3166			continue;
3167		}
3168		if ((hw_lease -> pool -> prohibit_list &&
3169		      permitted (packet, hw_lease -> pool -> prohibit_list)) ||
3170		    (hw_lease -> pool -> permit_list &&
3171		     !permitted (packet, hw_lease -> pool -> permit_list))) {
3172#if defined (DEBUG_FIND_LEASE)
3173			log_info ("not permitted: %s",
3174				  piaddr (hw_lease -> ip_addr));
3175#endif
3176			if (!packet -> raw -> ciaddr.s_addr)
3177				release_lease (hw_lease, packet);
3178		       n_hw:
3179			if (hw_lease -> n_hw)
3180				lease_reference (&next, hw_lease -> n_hw, MDL);
3181			lease_dereference (&hw_lease, MDL);
3182			if (next) {
3183				lease_reference (&hw_lease, next, MDL);
3184				lease_dereference (&next, MDL);
3185			}
3186			continue;
3187		}
3188		break;
3189	}
3190#if defined (DEBUG_FIND_LEASE)
3191	if (hw_lease)
3192		log_info ("Found lease for hardware address: %s.",
3193		      piaddr (hw_lease -> ip_addr));
3194#endif
3195
3196	/* Try to find a lease that's been allocated to the client's
3197	   IP address. */
3198	if (ip_lease_in)
3199		lease_reference (&ip_lease, ip_lease_in, MDL);
3200	else if (cip.len)
3201		find_lease_by_ip_addr (&ip_lease, cip, MDL);
3202
3203#if defined (DEBUG_FIND_LEASE)
3204	if (ip_lease)
3205		log_info ("Found lease for requested address: %s.",
3206		      piaddr (ip_lease -> ip_addr));
3207#endif
3208
3209	/* If ip_lease is valid at this point, set ours to one, so that
3210	   even if we choose a different lease, we know that the address
3211	   the client was requesting was ours, and thus we can NAK it. */
3212	if (ip_lease && ours)
3213		*ours = 1;
3214
3215	/* If the requested IP address isn't on the network the packet
3216	   came from, don't use it.  Allow abandoned leases to be matched
3217	   here - if the client is requesting it, there's a decent chance
3218	   that it's because the lease database got trashed and a client
3219	   that thought it had this lease answered an ARP or PING, causing the
3220	   lease to be abandoned.   If so, this request probably came from
3221	   that client. */
3222	if (ip_lease && (ip_lease -> subnet -> shared_network != share)) {
3223		if (ours)
3224			*ours = 1;
3225#if defined (DEBUG_FIND_LEASE)
3226		log_info ("...but it was on the wrong shared network.");
3227#endif
3228		strcpy (dhcp_message, "requested address on bad subnet");
3229		lease_dereference (&ip_lease, MDL);
3230	}
3231
3232	/* Toss ip_lease if it hasn't yet expired and doesn't belong to the
3233	   client. */
3234	if (ip_lease &&
3235	    (ip_lease -> uid ?
3236	     (!have_client_identifier ||
3237	      ip_lease -> uid_len != client_identifier.len ||
3238	      memcmp (ip_lease -> uid, client_identifier.data,
3239		      ip_lease -> uid_len)) :
3240	     (ip_lease -> hardware_addr.hbuf [0] != packet -> raw -> htype ||
3241	      ip_lease -> hardware_addr.hlen != packet -> raw -> hlen + 1 ||
3242	      memcmp (&ip_lease -> hardware_addr.hbuf [1],
3243		      packet -> raw -> chaddr,
3244		      (unsigned)(ip_lease -> hardware_addr.hlen - 1))))) {
3245		/* If we're not doing failover, the only state in which
3246		   we can allocate this lease to the client is FTS_FREE.
3247		   If we are doing failover, things are more complicated.
3248		   If the lease is free or backup, we let the caller decide
3249		   whether or not to give it out. */
3250		if (ip_lease -> binding_state != FTS_FREE &&
3251		    ip_lease -> binding_state != FTS_BACKUP) {
3252#if defined (DEBUG_FIND_LEASE)
3253			log_info ("rejecting lease for requested address.");
3254#endif
3255			/* If we're rejecting it because the peer has
3256			   it, don't set "ours", because we shouldn't NAK. */
3257			if (ours && ip_lease -> binding_state != FTS_ACTIVE)
3258				*ours = 0;
3259			lease_dereference (&ip_lease, MDL);
3260		} else
3261			if (allocatedp)
3262				*allocatedp = 1;
3263	}
3264
3265	/* If we got an ip_lease and a uid_lease or hw_lease, and ip_lease
3266	   is not active, and is not ours to reallocate, forget about it. */
3267	if (ip_lease && (uid_lease || hw_lease) &&
3268	    ip_lease -> binding_state != FTS_ACTIVE &&
3269	    !lease_mine_to_reallocate (ip_lease) &&
3270	    packet -> packet_type == DHCPDISCOVER) {
3271#if defined (DEBUG_FIND_LEASE)
3272		log_info ("ip lease not ours to offer.");
3273#endif
3274		lease_dereference (&ip_lease, MDL);
3275	}
3276
3277	/* If for some reason the client has more than one lease
3278	   on the subnet that matches its uid, pick the one that
3279	   it asked for and (if we can) free the other. */
3280	if (ip_lease &&
3281	    ip_lease -> binding_state == FTS_ACTIVE &&
3282	    ip_lease -> uid && ip_lease != uid_lease) {
3283		if (have_client_identifier &&
3284		    (ip_lease -> uid_len == client_identifier.len) &&
3285		    !memcmp (client_identifier.data,
3286			     ip_lease -> uid, ip_lease -> uid_len)) {
3287			if (uid_lease) {
3288			    if (uid_lease -> binding_state == FTS_ACTIVE) {
3289				log_error ("client %s has duplicate%s on %s",
3290					   (print_hw_addr
3291					    (packet -> raw -> htype,
3292					     packet -> raw -> hlen,
3293					     packet -> raw -> chaddr)),
3294					   " leases",
3295					   (ip_lease -> subnet ->
3296					    shared_network -> name));
3297
3298				/* If the client is REQUESTing the lease,
3299				   it shouldn't still be using the old
3300				   one, so we can free it for allocation. */
3301				if (uid_lease &&
3302				    uid_lease -> binding_state == FTS_ACTIVE &&
3303				    !packet -> raw -> ciaddr.s_addr &&
3304				    (share ==
3305				     uid_lease -> subnet -> shared_network) &&
3306				    packet -> packet_type == DHCPREQUEST)
3307					dissociate_lease (uid_lease);
3308			    }
3309			    lease_dereference (&uid_lease, MDL);
3310			    lease_reference (&uid_lease, ip_lease, MDL);
3311			}
3312		}
3313
3314		/* If we get to here and fixed_lease is not null, that means
3315		   that there are both a dynamic lease and a fixed-address
3316		   declaration for the same IP address. */
3317		if (packet -> packet_type == DHCPREQUEST && fixed_lease) {
3318			lease_dereference (&fixed_lease, MDL);
3319		      db_conflict:
3320			log_error ("Dynamic and static leases present for %s.",
3321				   piaddr (cip));
3322			log_error ("Remove host declaration %s or remove %s",
3323				   (fixed_lease && fixed_lease -> host
3324				    ? (fixed_lease -> host -> name
3325				       ? fixed_lease -> host -> name
3326				       : piaddr (cip))
3327				    : piaddr (cip)),
3328				    piaddr (cip));
3329			log_error ("from the dynamic address pool for %s",
3330				   ip_lease -> subnet -> shared_network -> name
3331				  );
3332			if (fixed_lease)
3333				lease_dereference (&ip_lease, MDL);
3334			strcpy (dhcp_message,
3335				"database conflict - call for help!");
3336		}
3337
3338		if (ip_lease && ip_lease != uid_lease) {
3339#if defined (DEBUG_FIND_LEASE)
3340			log_info ("requested address not available.");
3341#endif
3342			lease_dereference (&ip_lease, MDL);
3343		}
3344	}
3345
3346	/* If we get to here with both fixed_lease and ip_lease not
3347	   null, then we have a configuration file bug. */
3348	if (packet -> packet_type == DHCPREQUEST && fixed_lease && ip_lease)
3349		goto db_conflict;
3350
3351	/* Toss extra pointers to the same lease... */
3352	if (hw_lease && hw_lease == uid_lease) {
3353#if defined (DEBUG_FIND_LEASE)
3354		log_info ("hardware lease and uid lease are identical.");
3355#endif
3356		lease_dereference (&hw_lease, MDL);
3357	}
3358	if (ip_lease && ip_lease == hw_lease) {
3359		lease_dereference (&hw_lease, MDL);
3360#if defined (DEBUG_FIND_LEASE)
3361		log_info ("hardware lease and ip lease are identical.");
3362#endif
3363	}
3364	if (ip_lease && ip_lease == uid_lease) {
3365		lease_dereference (&uid_lease, MDL);
3366#if defined (DEBUG_FIND_LEASE)
3367		log_info ("uid lease and ip lease are identical.");
3368#endif
3369	}
3370
3371	/* Make sure the client is permitted to use the requested lease. */
3372	if (ip_lease &&
3373	    ((ip_lease -> pool -> prohibit_list &&
3374	      permitted (packet, ip_lease -> pool -> prohibit_list)) ||
3375	     (ip_lease -> pool -> permit_list &&
3376	      !permitted (packet, ip_lease -> pool -> permit_list)))) {
3377		if (!packet -> raw -> ciaddr.s_addr)
3378			release_lease (ip_lease, packet);
3379		lease_dereference (&ip_lease, MDL);
3380	}
3381
3382	if (uid_lease &&
3383	    ((uid_lease -> pool -> prohibit_list &&
3384	      permitted (packet, uid_lease -> pool -> prohibit_list)) ||
3385	     (uid_lease -> pool -> permit_list &&
3386	      !permitted (packet, uid_lease -> pool -> permit_list)))) {
3387		if (!packet -> raw -> ciaddr.s_addr)
3388			release_lease (uid_lease, packet);
3389		lease_dereference (&uid_lease, MDL);
3390	}
3391
3392	if (hw_lease &&
3393	    ((hw_lease -> pool -> prohibit_list &&
3394	      permitted (packet, hw_lease -> pool -> prohibit_list)) ||
3395	     (hw_lease -> pool -> permit_list &&
3396	      !permitted (packet, hw_lease -> pool -> permit_list)))) {
3397		if (!packet -> raw -> ciaddr.s_addr)
3398			release_lease (hw_lease, packet);
3399		lease_dereference (&hw_lease, MDL);
3400	}
3401
3402	/* If we've already eliminated the lease, it wasn't there to
3403	   begin with.   If we have come up with a matching lease,
3404	   set the message to bad network in case we have to throw it out. */
3405	if (!ip_lease) {
3406		strcpy (dhcp_message, "requested address not available");
3407	}
3408
3409	/* If this is a DHCPREQUEST, make sure the lease we're going to return
3410	   matches the requested IP address.   If it doesn't, don't return a
3411	   lease at all. */
3412	if (packet -> packet_type == DHCPREQUEST &&
3413	    !ip_lease && !fixed_lease) {
3414#if defined (DEBUG_FIND_LEASE)
3415		log_info ("no applicable lease found for DHCPREQUEST.");
3416#endif
3417		goto out;
3418	}
3419
3420	/* At this point, if fixed_lease is nonzero, we can assign it to
3421	   this client. */
3422	if (fixed_lease) {
3423		lease_reference (&lease, fixed_lease, MDL);
3424		lease_dereference (&fixed_lease, MDL);
3425#if defined (DEBUG_FIND_LEASE)
3426		log_info ("choosing fixed address.");
3427#endif
3428	}
3429
3430	/* If we got a lease that matched the ip address and don't have
3431	   a better offer, use that; otherwise, release it. */
3432	if (ip_lease) {
3433		if (lease) {
3434			if (!packet -> raw -> ciaddr.s_addr)
3435				release_lease (ip_lease, packet);
3436#if defined (DEBUG_FIND_LEASE)
3437			log_info ("not choosing requested address (!).");
3438#endif
3439		} else {
3440#if defined (DEBUG_FIND_LEASE)
3441			log_info ("choosing lease on requested address.");
3442#endif
3443			lease_reference (&lease, ip_lease, MDL);
3444			if (lease -> host)
3445				host_dereference (&lease -> host, MDL);
3446		}
3447		lease_dereference (&ip_lease, MDL);
3448	}
3449
3450	/* If we got a lease that matched the client identifier, we may want
3451	   to use it, but if we already have a lease we like, we must free
3452	   the lease that matched the client identifier. */
3453	if (uid_lease) {
3454		if (lease) {
3455			if (!packet -> raw -> ciaddr.s_addr &&
3456			    packet -> packet_type == DHCPREQUEST &&
3457			    uid_lease -> binding_state == FTS_ACTIVE)
3458				dissociate_lease (uid_lease);
3459#if defined (DEBUG_FIND_LEASE)
3460			log_info ("not choosing uid lease.");
3461#endif
3462		} else {
3463			lease_reference (&lease, uid_lease, MDL);
3464			if (lease -> host)
3465				host_dereference (&lease -> host, MDL);
3466#if defined (DEBUG_FIND_LEASE)
3467			log_info ("choosing uid lease.");
3468#endif
3469		}
3470		lease_dereference (&uid_lease, MDL);
3471	}
3472
3473	/* The lease that matched the hardware address is treated likewise. */
3474	if (hw_lease) {
3475		if (lease) {
3476#if defined (DEBUG_FIND_LEASE)
3477			log_info ("not choosing hardware lease.");
3478#endif
3479		} else {
3480			/* We're a little lax here - if the client didn't
3481			   send a client identifier and it's a bootp client,
3482			   but the lease has a client identifier, we still
3483			   let the client have a lease. */
3484			if (!hw_lease -> uid_len ||
3485			    (have_client_identifier
3486			     ? (hw_lease -> uid_len ==
3487				client_identifier.len &&
3488				!memcmp (hw_lease -> uid,
3489					 client_identifier.data,
3490					 client_identifier.len))
3491			     : packet -> packet_type == 0)) {
3492				lease_reference (&lease, hw_lease, MDL);
3493				if (lease -> host)
3494					host_dereference (&lease -> host, MDL);
3495#if defined (DEBUG_FIND_LEASE)
3496				log_info ("choosing hardware lease.");
3497#endif
3498			} else {
3499#if defined (DEBUG_FIND_LEASE)
3500				log_info ("not choosing hardware lease: %s.",
3501					  "uid mismatch");
3502#endif
3503			}
3504		}
3505		lease_dereference (&hw_lease, MDL);
3506	}
3507
3508	/* If we found a host_decl but no matching address, try to
3509	   find a host_decl that has no address, and if there is one,
3510	   hang it off the lease so that we can use the supplied
3511	   options. */
3512	if (lease && host && !lease -> host) {
3513		struct host_decl *p = (struct host_decl *)0;
3514		struct host_decl *n = (struct host_decl *)0;
3515		host_reference (&p, host, MDL);
3516		while (p) {
3517			if (!p -> fixed_addr) {
3518				host_reference (&lease -> host, p, MDL);
3519				host_dereference (&p, MDL);
3520				break;
3521			}
3522			if (p -> n_ipaddr)
3523				host_reference (&n, p -> n_ipaddr, MDL);
3524			host_dereference (&p, MDL);
3525			if (n) {
3526				host_reference (&p, n, MDL);
3527				host_dereference (&n, MDL);
3528			}
3529		}
3530	}
3531
3532	/* If we find an abandoned lease, but it's the one the client
3533	   requested, we assume that previous bugginess on the part
3534	   of the client, or a server database loss, caused the lease to
3535	   be abandoned, so we reclaim it and let the client have it. */
3536	if (lease &&
3537	    (lease -> binding_state == FTS_ABANDONED) &&
3538	    lease == ip_lease &&
3539	    packet -> packet_type == DHCPREQUEST) {
3540		log_error ("Reclaiming REQUESTed abandoned IP address %s.",
3541		      piaddr (lease -> ip_addr));
3542	} else if (lease && (lease -> binding_state == FTS_ABANDONED)) {
3543	/* Otherwise, if it's not the one the client requested, we do not
3544	   return it - instead, we claim it's ours, causing a DHCPNAK to be
3545	   sent if this lookup is for a DHCPREQUEST, and force the client
3546	   to go back through the allocation process. */
3547		if (ours)
3548			*ours = 1;
3549		lease_dereference (&lease, MDL);
3550	}
3551
3552	if (lease && allocatedp && lease -> ends <= cur_time)
3553		*allocatedp = 1;
3554
3555      out:
3556	if (have_client_identifier)
3557		data_string_forget (&client_identifier, MDL);
3558
3559	if (fixed_lease)
3560		lease_dereference (&fixed_lease, MDL);
3561	if (hw_lease)
3562		lease_dereference (&hw_lease, MDL);
3563	if (uid_lease)
3564		lease_dereference (&uid_lease, MDL);
3565	if (ip_lease)
3566		lease_dereference (&ip_lease, MDL);
3567	if (host)
3568		host_dereference (&host, MDL);
3569
3570	if (lease) {
3571#if defined (DEBUG_FIND_LEASE)
3572		log_info ("Returning lease: %s.",
3573		      piaddr (lease -> ip_addr));
3574#endif
3575		lease_reference (lp, lease, file, line);
3576		lease_dereference (&lease, MDL);
3577		return 1;
3578	}
3579#if defined (DEBUG_FIND_LEASE)
3580	log_info ("Not returning a lease.");
3581#endif
3582	return 0;
3583}
3584
3585/* Search the provided host_decl structure list for an address that's on
3586   the specified shared network.  If one is found, mock up and return a
3587   lease structure for it; otherwise return the null pointer. */
3588
3589int mockup_lease (struct lease **lp, struct packet *packet,
3590		  struct shared_network *share, struct host_decl *hp)
3591{
3592	struct lease *lease = (struct lease *)0;
3593	struct host_decl *rhp = (struct host_decl *)0;
3594
3595	if (lease_allocate (&lease, MDL) != ISC_R_SUCCESS)
3596		return 0;
3597	if (host_reference (&rhp, hp, MDL) != ISC_R_SUCCESS) {
3598		lease_dereference (&lease, MDL);
3599		return 0;
3600	}
3601	if (!find_host_for_network (&lease -> subnet,
3602				    &rhp, &lease -> ip_addr, share)) {
3603		lease_dereference (&lease, MDL);
3604		host_dereference (&rhp, MDL);
3605		return 0;
3606	}
3607	host_reference (&lease -> host, rhp, MDL);
3608	if (rhp -> client_identifier.len > sizeof lease -> uid_buf)
3609		lease -> uid = dmalloc (rhp -> client_identifier.len, MDL);
3610	else
3611		lease -> uid = lease -> uid_buf;
3612	if (!lease -> uid) {
3613		lease_dereference (&lease, MDL);
3614		host_dereference (&rhp, MDL);
3615		return 0;
3616	}
3617	memcpy (lease -> uid, rhp -> client_identifier.data,
3618		rhp -> client_identifier.len);
3619	lease -> uid_len = rhp -> client_identifier.len;
3620	lease -> hardware_addr = rhp -> interface;
3621	lease -> starts = lease -> timestamp = lease -> ends = MIN_TIME;
3622	lease -> flags = STATIC_LEASE;
3623	lease -> binding_state = FTS_FREE;
3624
3625	lease_reference (lp, lease, MDL);
3626
3627	lease_dereference (&lease, MDL);
3628	host_dereference (&rhp, MDL);
3629	return 1;
3630}
3631
3632/* Look through all the pools in a list starting with the specified pool
3633   for a free lease.   We try to find a virgin lease if we can.   If we
3634   don't find a virgin lease, we try to find a non-virgin lease that's
3635   free.   If we can't find one of those, we try to reclaim an abandoned
3636   lease.   If all of these possibilities fail to pan out, we don't return
3637   a lease at all. */
3638
3639int allocate_lease (struct lease **lp, struct packet *packet,
3640                    struct pool *pool, int *peer_has_leases)
3641{
3642	struct lease *lease = (struct lease *)0;
3643	struct lease *candl = (struct lease *)0;
3644
3645	for (; pool ; pool = pool -> next) {
3646		if ((pool -> prohibit_list &&
3647		     permitted (packet, pool -> prohibit_list)) ||
3648		    (pool -> permit_list &&
3649		     !permitted (packet, pool -> permit_list)))
3650			continue;
3651
3652#if defined (FAILOVER_PROTOCOL)
3653		/* Peer_has_leases just says that we found at least one
3654		   free lease.  If no free lease is returned, the caller
3655		   can deduce that this means the peer is hogging all the
3656		   free leases, so we can print a better error message. */
3657		/* XXX Do we need code here to ignore PEER_IS_OWNER and
3658		 * XXX just check tstp if we're in, e.g., PARTNER_DOWN?
3659		 * XXX Where do we deal with CONFLICT_DETECTED, et al? */
3660		/* XXX This should be handled by the lease binding "state
3661		 * XXX machine" - that is, when we get here, if a lease
3662		 * XXX could be allocated, it will have the correct
3663		 * XXX binding state so that the following code will
3664		 * XXX result in its being allocated. */
3665		/* Skip to the most expired lease in the pool that is not
3666		 * owned by a failover peer. */
3667		if (pool -> failover_peer) {
3668			if (pool -> failover_peer -> i_am == primary) {
3669				if (pool -> backup)
3670					*peer_has_leases = 1;
3671				candl = pool -> free;
3672				if (!candl)
3673					candl = pool -> abandoned;
3674			} else {
3675				if (pool -> free)
3676					*peer_has_leases = 1;
3677				candl = pool -> backup;
3678			}
3679		} else
3680#endif
3681		{
3682			if (pool -> free)
3683				candl = pool -> free;
3684			else
3685				candl = pool -> abandoned;
3686		}
3687
3688		if (!candl || (candl -> ends > cur_time))
3689			continue;
3690
3691		if (!lease) {
3692			lease = candl;
3693			continue;
3694		}
3695
3696		if ((lease -> binding_state == FTS_ABANDONED) &&
3697		    ((candl -> binding_state != FTS_ABANDONED) ||
3698		     (candl -> ends < lease -> ends))) {
3699			lease = candl;
3700			continue;
3701		} else if (candl -> binding_state == FTS_ABANDONED)
3702			continue;
3703
3704		if ((lease -> uid_len || lease -> hardware_addr.hlen) &&
3705		    ((!candl -> uid_len && !candl -> hardware_addr.hlen) ||
3706		     (candl -> ends < lease -> ends))) {
3707			lease = candl;
3708			continue;
3709		} else if (candl -> uid_len || candl -> hardware_addr.hlen)
3710			continue;
3711
3712		if (candl -> ends < lease -> ends)
3713			lease = candl;
3714	}
3715
3716	if (lease) {
3717		if (lease -> binding_state == FTS_ABANDONED)
3718			log_error ("Reclaiming abandoned lease %s.",
3719				   piaddr (lease -> ip_addr));
3720
3721		lease_reference (lp, lease, MDL);
3722		return 1;
3723	}
3724
3725	return 0;
3726}
3727
3728/* Determine whether or not a permit exists on a particular permit list
3729   that matches the specified packet, returning nonzero if so, zero if
3730   not. */
3731
3732int permitted (packet, permit_list)
3733	struct packet *packet;
3734	struct permit *permit_list;
3735{
3736	struct permit *p;
3737	int i;
3738
3739	for (p = permit_list; p; p = p -> next) {
3740		switch (p -> type) {
3741		      case permit_unknown_clients:
3742			if (!packet -> known)
3743				return 1;
3744			break;
3745
3746		      case permit_known_clients:
3747			if (packet -> known)
3748				return 1;
3749			break;
3750
3751		      case permit_authenticated_clients:
3752			if (packet -> authenticated)
3753				return 1;
3754			break;
3755
3756		      case permit_unauthenticated_clients:
3757			if (!packet -> authenticated)
3758				return 1;
3759			break;
3760
3761		      case permit_all_clients:
3762			return 1;
3763
3764		      case permit_dynamic_bootp_clients:
3765			if (!packet -> options_valid ||
3766			    !packet -> packet_type)
3767				return 1;
3768			break;
3769
3770		      case permit_class:
3771			for (i = 0; i < packet -> class_count; i++) {
3772				if (p -> class == packet -> classes [i])
3773					return 1;
3774				if (packet -> classes [i] &&
3775				    packet -> classes [i] -> superclass &&
3776				    (packet -> classes [i] -> superclass ==
3777				     p -> class))
3778					return 1;
3779			}
3780			break;
3781		}
3782	}
3783	return 0;
3784}
3785
3786int locate_network (packet)
3787	struct packet *packet;
3788{
3789	struct iaddr ia;
3790	struct data_string data;
3791	struct subnet *subnet = (struct subnet *)0;
3792	struct option_cache *oc;
3793
3794	/* See if there's a subnet selection option. */
3795	oc = lookup_option (&dhcp_universe, packet -> options,
3796			    DHO_SUBNET_SELECTION);
3797
3798	/* If there's no SSO and no giaddr, then use the shared_network
3799	   from the interface, if there is one.   If not, fail. */
3800	if (!oc && !packet -> raw -> giaddr.s_addr) {
3801		if (packet -> interface -> shared_network) {
3802			shared_network_reference
3803				(&packet -> shared_network,
3804				 packet -> interface -> shared_network, MDL);
3805			return 1;
3806		}
3807		return 0;
3808	}
3809
3810	/* If there's an SSO, and it's valid, use it to figure out the
3811	   subnet.    If it's not valid, fail. */
3812	if (oc) {
3813		memset (&data, 0, sizeof data);
3814		if (!evaluate_option_cache (&data, packet, (struct lease *)0,
3815					    (struct client_state *)0,
3816					    packet -> options,
3817					    (struct option_state *)0,
3818					    &global_scope, oc, MDL)) {
3819			return 0;
3820		}
3821		if (data.len != 4) {
3822			return 0;
3823		}
3824		ia.len = 4;
3825		memcpy (ia.iabuf, data.data, 4);
3826		data_string_forget (&data, MDL);
3827	} else {
3828		ia.len = 4;
3829		memcpy (ia.iabuf, &packet -> raw -> giaddr, 4);
3830	}
3831
3832	/* If we know the subnet on which the IP address lives, use it. */
3833	if (find_subnet (&subnet, ia, MDL)) {
3834		shared_network_reference (&packet -> shared_network,
3835					  subnet -> shared_network, MDL);
3836		subnet_dereference (&subnet, MDL);
3837		return 1;
3838	}
3839
3840	/* Otherwise, fail. */
3841	return 0;
3842}
3843