]> git.ipfire.org Git - thirdparty/dhcp.git/blame - server/dhcp.c
copy rights update
[thirdparty/dhcp.git] / server / dhcp.c
CommitLineData
d7837182
TL
1/* dhcp.c
2
b88e8e15 3 DHCP Protocol engine. */
d7837182
TL
4
5/*
49a7fb58 6 * Copyright (C) 2004-2022 Internet Systems Consortium, Inc. ("ISC")
98311e4b 7 * Copyright (c) 1995-2003 by Internet Software Consortium
d7837182 8 *
7512d88b
TM
9 * This Source Code Form is subject to the terms of the Mozilla Public
10 * License, v. 2.0. If a copy of the MPL was not distributed with this
11 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
d7837182 12 *
98311e4b
DH
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.
d7837182 20 *
98311e4b 21 * Internet Systems Consortium, Inc.
429a56d7
TM
22 * PO Box 360
23 * Newmarket, NH 03857 USA
98311e4b 24 * <info@isc.org>
2c85ac9b 25 * https://www.isc.org/
49733f31 26 *
d7837182
TL
27 */
28
d7837182 29#include "dhcpd.h"
fe5b0fdd
DH
30#include <errno.h>
31#include <limits.h>
f8cbf390
DH
32#include <sys/time.h>
33
a1308b64
DH
34static void maybe_return_agent_options(struct packet *packet,
35 struct option_state *options);
a5b21e16 36
f3a44c10
TM
37static int reuse_lease (struct packet* packet, struct lease* new_lease,
38 struct lease* lease, struct lease_state *state,
a5b21e16
TM
39 int offer, int* same_client);
40
41static int do_ping_check(struct packet* packet, struct lease_state* state,
42 struct lease* lease, TIME original_cltt,
43 int same_client);
44
785c1a51
FD
45#if defined(DHCPv6) && defined(DHCP4o6)
46static int locate_network6(struct packet *packet);
47#endif
d7837182 48
4b7df707
TL
49int outstanding_pings;
50
e422b8c7
TM
51#if defined(DELAYED_ACK)
52static void delayed_ack_enqueue(struct lease *);
53static void delayed_acks_timer(void *);
54
55
6368a1bd
DH
56struct leasequeue *ackqueue_head, *ackqueue_tail;
57static struct leasequeue *free_ackqueue;
0585235c
SR
58static struct timeval max_fsync;
59
6368a1bd
DH
60int outstanding_acks;
61int max_outstanding_acks = DEFAULT_DELAYED_ACK;
f8cbf390
DH
62int max_ack_delay_secs = DEFAULT_ACK_DELAY_SECS;
63int max_ack_delay_usecs = DEFAULT_ACK_DELAY_USECS;
0585235c 64int min_ack_delay_usecs = DEFAULT_MIN_ACK_DELAY_USECS;
e422b8c7 65#endif
6368a1bd 66
a7822eac 67static char dhcp_message [256];
2c9bf1f4
DH
68static int site_code_min;
69
70static int find_min_site_code(struct universe *);
71static isc_result_t lowest_site_code(const void *, unsigned, void *);
b88e8e15 72
a5b21e16 73static const char *dhcp_type_names [] = {
d758ad8c
TL
74 "DHCPDISCOVER",
75 "DHCPOFFER",
76 "DHCPREQUEST",
77 "DHCPDECLINE",
78 "DHCPACK",
79 "DHCPNAK",
80 "DHCPRELEASE",
6d103865 81 "DHCPINFORM",
51e7687f 82 "type 9",
6d103865
SK
83 "DHCPLEASEQUERY",
84 "DHCPLEASEUNASSIGNED",
85 "DHCPLEASEUNKNOWN",
86 "DHCPLEASEACTIVE"
d758ad8c
TL
87};
88const int dhcp_type_name_max = ((sizeof dhcp_type_names) / sizeof (char *));
89
27e90ede
TL
90#if defined (TRACING)
91# define send_packet trace_packet_send
92#endif
93
68507137
TM
94static TIME leaseTimeCheck(TIME calculated, TIME alternate);
95
51e7687f
EH
96void
97dhcp (struct packet *packet) {
5bc2e1f2 98 int ms_nulltp = 0;
c99a6692 99 struct option_cache *oc;
51e7687f 100 struct lease *lease = NULL;
9e383163
TL
101 const char *errmsg;
102 struct data_string data;
5bc2e1f2 103
51e7687f
EH
104 if (!locate_network(packet) &&
105 packet->packet_type != DHCPREQUEST &&
a5b21e16 106 packet->packet_type != DHCPINFORM &&
51e7687f 107 packet->packet_type != DHCPLEASEQUERY) {
9e383163 108 const char *s;
51e7687f 109 char typebuf[32];
9e383163
TL
110 errmsg = "unknown network segment";
111 bad_packet:
a5b21e16 112
51e7687f
EH
113 if (packet->packet_type > 0 &&
114 packet->packet_type <= dhcp_type_name_max) {
115 s = dhcp_type_names[packet->packet_type - 1];
9e383163 116 } else {
98311e4b 117 /* %Audit% Cannot exceed 28 bytes. %2004.06.17,Safe% */
51e7687f 118 sprintf(typebuf, "type %d", packet->packet_type);
9e383163
TL
119 s = typebuf;
120 }
a5b21e16 121
785c1a51
FD
122#if defined(DHCPv6) && defined(DHCP4o6)
123 if (dhcpv4_over_dhcpv6 && (packet->dhcp4o6_response != NULL)) {
124 log_info("DHCP4o6 %s from %s via %s: %s", s,
125 (packet->raw->htype
126 ? print_hw_addr(packet->raw->htype,
127 packet->raw->hlen,
128 packet->raw->chaddr)
129 : "<no identifier>"),
130 piaddr(packet->client_addr),
131 errmsg);
132 goto out;
133 }
134#endif
135
51e7687f
EH
136 log_info("%s from %s via %s: %s", s,
137 (packet->raw->htype
138 ? print_hw_addr(packet->raw->htype,
139 packet->raw->hlen,
140 packet->raw->chaddr)
141 : "<no identifier>"),
142 packet->raw->giaddr.s_addr
143 ? inet_ntoa(packet->raw->giaddr)
144 : packet->interface->name, errmsg);
9e383163
TL
145 goto out;
146 }
147
148 /* There is a problem with the relay agent information option,
9aa3f3a5
DH
149 * which is that in order for a normal relay agent to append
150 * this option, the relay agent has to have been involved in
151 * getting the packet from the client to the server. Note
152 * that this is the software entity known as the relay agent,
153 * _not_ the hardware entity known as a router in which the
154 * relay agent may be running, so the fact that a router has
155 * forwarded a packet does not mean that the relay agent in
156 * the router was involved.
157 *
158 * So when the client broadcasts (DHCPDISCOVER, or giaddr is set),
159 * we can be sure that there are either agent options in the
160 * packet, or there aren't supposed to be. When the giaddr is not
161 * set, it's still possible that the client is on a directly
162 * attached subnet, and agent options are being appended by an l2
163 * device that has no address, and so sets no giaddr.
164 *
165 * But in either case it's possible that the packets we receive
166 * from the client in RENEW state may not include the agent options,
167 * so if they are not in the packet we must "pretend" the last values
168 * we observed were provided.
169 */
170 if (packet->packet_type == DHCPREQUEST &&
171 packet->raw->ciaddr.s_addr && !packet->raw->giaddr.s_addr &&
172 (packet->options->universe_count <= agent_universe.index ||
173 packet->options->universes[agent_universe.index] == NULL))
9e383163
TL
174 {
175 struct iaddr cip;
176
177 cip.len = sizeof packet -> raw -> ciaddr;
178 memcpy (cip.iabuf, &packet -> raw -> ciaddr,
179 sizeof packet -> raw -> ciaddr);
180 if (!find_lease_by_ip_addr (&lease, cip, MDL))
181 goto nolease;
182
183 /* If there are no agent options on the lease, it's not
184 interesting. */
185 if (!lease -> agent_options)
186 goto nolease;
187
188 /* The client should not be unicasting a renewal if its lease
189 has expired, so make it go through the process of getting
190 its agent options legally. */
191 if (lease -> ends < cur_time)
192 goto nolease;
193
194 if (lease -> uid_len) {
195 oc = lookup_option (&dhcp_universe, packet -> options,
196 DHO_DHCP_CLIENT_IDENTIFIER);
197 if (!oc)
198 goto nolease;
199
200 memset (&data, 0, sizeof data);
201 if (!evaluate_option_cache (&data,
202 packet, (struct lease *)0,
203 (struct client_state *)0,
204 packet -> options,
205 (struct option_state *)0,
206 &global_scope, oc, MDL))
207 goto nolease;
208 if (lease -> uid_len != data.len ||
209 memcmp (lease -> uid, data.data, data.len)) {
210 data_string_forget (&data, MDL);
211 goto nolease;
212 }
213 data_string_forget (&data, MDL);
214 } else
215 if ((lease -> hardware_addr.hbuf [0] !=
216 packet -> raw -> htype) ||
217 (lease -> hardware_addr.hlen - 1 !=
218 packet -> raw -> hlen) ||
219 memcmp (&lease -> hardware_addr.hbuf [1],
220 packet -> raw -> chaddr,
221 packet -> raw -> hlen))
222 goto nolease;
223
224 /* Okay, so we found a lease that matches the client. */
bfe2d221
TL
225 option_chain_head_reference ((struct option_chain_head **)
226 &(packet -> options -> universes
227 [agent_universe.index]),
228 lease -> agent_options, MDL);
9aa3f3a5
DH
229
230 if (packet->options->universe_count <= agent_universe.index)
231 packet->options->universe_count =
232 agent_universe.index + 1;
233
234 packet->agent_options_stashed = ISC_TRUE;
9e383163
TL
235 }
236 nolease:
3a581108 237
88cd8aca
DH
238 /* If a client null terminates options it sends, it probably
239 * expects the server to reciprocate.
240 */
5bc2e1f2
TL
241 if ((oc = lookup_option (&dhcp_universe, packet -> options,
242 DHO_HOST_NAME))) {
243 if (!oc -> expression)
88cd8aca 244 ms_nulltp = oc->flags & OPTION_HAD_NULLS;
5bc2e1f2
TL
245 }
246
88cd8aca 247 /* Classify the client. */
b3f15965
TL
248 classify_client (packet);
249
ed8bcd8f
TL
250 switch (packet -> packet_type) {
251 case DHCPDISCOVER:
5bc2e1f2 252 dhcpdiscover (packet, ms_nulltp);
ed8bcd8f 253 break;
97ca1699 254
ed8bcd8f 255 case DHCPREQUEST:
9e383163 256 dhcprequest (packet, ms_nulltp, lease);
ed8bcd8f 257 break;
97ca1699 258
ed8bcd8f 259 case DHCPRELEASE:
5bc2e1f2 260 dhcprelease (packet, ms_nulltp);
ed8bcd8f 261 break;
97ca1699 262
b88e8e15 263 case DHCPDECLINE:
5bc2e1f2 264 dhcpdecline (packet, ms_nulltp);
b88e8e15
TL
265 break;
266
267 case DHCPINFORM:
5bc2e1f2 268 dhcpinform (packet, ms_nulltp);
b88e8e15
TL
269 break;
270
6d103865
SK
271 case DHCPLEASEQUERY:
272 dhcpleasequery(packet, ms_nulltp);
273 break;
9e383163
TL
274
275 case DHCPACK:
276 case DHCPOFFER:
277 case DHCPNAK:
6d103865
SK
278 case DHCPLEASEUNASSIGNED:
279 case DHCPLEASEUNKNOWN:
280 case DHCPLEASEACTIVE:
ed8bcd8f 281 break;
9e383163
TL
282
283 default:
284 errmsg = "unknown packet type";
285 goto bad_packet;
97ca1699 286 }
9e383163
TL
287 out:
288 if (lease)
289 lease_dereference (&lease, MDL);
ed8bcd8f 290}
97ca1699 291
5bc2e1f2 292void dhcpdiscover (packet, ms_nulltp)
ed8bcd8f 293 struct packet *packet;
5bc2e1f2 294 int ms_nulltp;
ed8bcd8f 295{
20916cae 296 struct lease *lease = (struct lease *)0;
d9eefc5d 297 char msgbuf [1024]; /* XXX */
ffdcd127 298 TIME when;
98311e4b 299 const char *s;
33225687
TL
300 int peer_has_leases = 0;
301#if defined (FAILOVER_PROTOCOL)
302 dhcp_failover_state_t *peer;
303#endif
a8b53b42 304
bb0b00a5 305 find_lease (&lease, packet, packet -> shared_network,
88cd8aca 306 0, &peer_has_leases, (struct lease *)0, MDL);
5941275a 307
98311e4b
DH
308 if (lease && lease -> client_hostname) {
309 if ((strlen (lease -> client_hostname) <= 64) &&
28868515 310 db_printable((unsigned char *)lease->client_hostname))
98311e4b
DH
311 s = lease -> client_hostname;
312 else
313 s = "Hostname Unsuitable for Printing";
314 } else
d9eefc5d
TL
315 s = (char *)0;
316
98311e4b
DH
317 /* %Audit% This is log output. %2004.06.17,Safe%
318 * If we truncate we hope the user can get a hint from the log.
319 */
785c1a51
FD
320#if defined(DHCPv6) && defined(DHCP4o6)
321 if (dhcpv4_over_dhcpv6 && (packet->dhcp4o6_response != NULL)) {
322 snprintf (msgbuf, sizeof msgbuf,
323 "DHCP4o6 DHCPDISCOVER from %s %s%s%svia %s",
324 (packet -> raw -> htype
325 ? print_hw_addr (packet -> raw -> htype,
326 packet -> raw -> hlen,
327 packet -> raw -> chaddr)
328 : (lease
329 ? print_hex_1(lease->uid_len, lease->uid, 60)
330 : "<no identifier>")),
331 s ? "(" : "", s ? s : "", s ? ") " : "",
332 piaddr(packet->client_addr));
333 } else
334#endif
98311e4b 335 snprintf (msgbuf, sizeof msgbuf, "DHCPDISCOVER from %s %s%s%svia %s",
d9eefc5d
TL
336 (packet -> raw -> htype
337 ? print_hw_addr (packet -> raw -> htype,
338 packet -> raw -> hlen,
fdd46b53 339 packet -> raw -> chaddr)
d9eefc5d 340 : (lease
6d103865 341 ? print_hex_1(lease->uid_len, lease->uid, 60)
d9eefc5d
TL
342 : "<no identifier>")),
343 s ? "(" : "", s ? s : "", s ? ") " : "",
344 packet -> raw -> giaddr.s_addr
345 ? inet_ntoa (packet -> raw -> giaddr)
346 : packet -> interface -> name);
347
15c00bba
TL
348 /* Sourceless packets don't make sense here. */
349 if (!packet -> shared_network) {
785c1a51
FD
350#if defined(DHCPv6) && defined(DHCP4o6)
351 if (dhcpv4_over_dhcpv6 && (packet->dhcp4o6_response != NULL)) {
352 log_info ("DHCP4o6 packet from unknown subnet: %s",
353 piaddr(packet->client_addr));
354 } else
355#endif
8ae2d595 356 log_info ("Packet from unknown subnet: %s",
15c00bba 357 inet_ntoa (packet -> raw -> giaddr));
20916cae 358 goto out;
15c00bba
TL
359 }
360
d758ad8c
TL
361#if defined (FAILOVER_PROTOCOL)
362 if (lease && lease -> pool && lease -> pool -> failover_peer) {
363 peer = lease -> pool -> failover_peer;
364
fdfebedf
DH
365 /*
366 * If the lease is ours to (re)allocate, then allocate it.
367 *
2426234f 368 * If the lease is active, it belongs to the client. This
88cd8aca 369 * is the right lease, if we are to offer one. We decide
98bd7ca0 370 * whether or not to offer later on.
fdfebedf
DH
371 *
372 * If the lease was last active, and we've reached this
373 * point, then it was last active with the same client. We
374 * can safely re-activate the lease with this client.
88cd8aca 375 */
2426234f 376 if (lease->binding_state == FTS_ACTIVE ||
fdfebedf 377 lease->rewind_binding_state == FTS_ACTIVE ||
2426234f 378 lease_mine_to_reallocate(lease)) {
88cd8aca 379 ; /* This space intentionally left blank. */
d758ad8c
TL
380
381 /* Otherwise, we can't let the client have this lease. */
88cd8aca 382 } else {
d758ad8c
TL
383#if defined (DEBUG_FIND_LEASE)
384 log_debug ("discarding %s - %s",
385 piaddr (lease -> ip_addr),
386 binding_state_print (lease -> binding_state));
387#endif
388 lease_dereference (&lease, MDL);
389 }
390 }
391#endif
392
97ca1699
TL
393 /* If we didn't find a lease, try to allocate one... */
394 if (!lease) {
20916cae 395 if (!allocate_lease (&lease, packet,
a5b21e16 396 packet -> shared_network -> pools,
20916cae 397 &peer_has_leases)) {
33225687 398 if (peer_has_leases)
98311e4b
DH
399 log_error ("%s: peer holds all free leases",
400 msgbuf);
33225687 401 else
98311e4b
DH
402 log_error ("%s: network %s: no free leases",
403 msgbuf,
404 packet -> shared_network -> name);
97ca1699
TL
405 return;
406 }
97ca1699
TL
407 }
408
150cedd0 409#if defined (FAILOVER_PROTOCOL)
f8f34940
TL
410 if (lease && lease -> pool && lease -> pool -> failover_peer) {
411 peer = lease -> pool -> failover_peer;
412 if (peer -> service_state == not_responding ||
413 peer -> service_state == service_startup) {
414 log_info ("%s: not responding%s",
415 msgbuf, peer -> nrr);
416 goto out;
417 }
418 } else
419 peer = (dhcp_failover_state_t *)0;
420
150cedd0 421 /* Do load balancing if configured. */
88cd8aca 422 if (peer && (peer -> service_state == cooperating) &&
98311e4b 423 !load_balance_mine (packet, peer)) {
88cd8aca 424 if (peer_has_leases) {
98311e4b
DH
425 log_debug ("%s: load balance to peer %s",
426 msgbuf, peer -> name);
427 goto out;
428 } else {
88cd8aca
DH
429 log_debug ("%s: cancel load balance to peer %s - %s",
430 msgbuf, peer -> name, "no free leases");
33225687 431 }
150cedd0
TL
432 }
433#endif
434
12c9957e 435 /* If it's an expired lease, get rid of any bindings. */
6ceb9118
TL
436 if (lease -> ends < cur_time && lease -> scope)
437 binding_scope_dereference (&lease -> scope, MDL);
12c9957e 438
ffdcd127
TL
439 /* Set the lease to really expire in 2 minutes, unless it has
440 not yet expired, in which case leave its expiry time alone. */
441 when = cur_time + 120;
442 if (when < lease -> ends)
443 when = lease -> ends;
444
c75473d8
DH
445 ack_lease (packet, lease, DHCPOFFER, when, msgbuf, ms_nulltp,
446 (struct host_decl *)0);
20916cae
TL
447 out:
448 if (lease)
449 lease_dereference (&lease, MDL);
ed8bcd8f
TL
450}
451
9e383163 452void dhcprequest (packet, ms_nulltp, ip_lease)
ed8bcd8f 453 struct packet *packet;
5bc2e1f2 454 int ms_nulltp;
9e383163 455 struct lease *ip_lease;
ed8bcd8f 456{
15c00bba 457 struct lease *lease;
b88e8e15 458 struct iaddr cip;
4f767627 459 struct iaddr sip;
7a049f2c 460 struct subnet *subnet;
fa97acc1 461 int ours = 0;
5d25508c
TL
462 struct option_cache *oc;
463 struct data_string data;
d9eefc5d 464 char msgbuf [1024]; /* XXX */
98311e4b 465 const char *s;
4f767627 466 char smbuf [19];
bb0b00a5
TL
467#if defined (FAILOVER_PROTOCOL)
468 dhcp_failover_state_t *peer;
469#endif
27e90ede 470 int have_requested_addr = 0;
5d25508c 471
951323fe 472 oc = lookup_option (&dhcp_universe, packet -> options,
5d25508c
TL
473 DHO_DHCP_REQUESTED_ADDRESS);
474 memset (&data, 0, sizeof data);
475 if (oc &&
ca1c700e 476 evaluate_option_cache (&data, packet, (struct lease *)0,
9e383163 477 (struct client_state *)0,
ca1c700e 478 packet -> options, (struct option_state *)0,
12c9957e 479 &global_scope, oc, MDL)) {
b88e8e15 480 cip.len = 4;
5d25508c 481 memcpy (cip.iabuf, data.data, 4);
4bd8800e 482 data_string_forget (&data, MDL);
27e90ede 483 have_requested_addr = 1;
a8b53b42 484 } else {
5d25508c 485 oc = (struct option_cache *)0;
a8b53b42
TL
486 cip.len = 4;
487 memcpy (cip.iabuf, &packet -> raw -> ciaddr.s_addr, 4);
488 }
489
15c00bba
TL
490 /* Find the lease that matches the address requested by the
491 client. */
44b2e3ad 492
20916cae
TL
493 subnet = (struct subnet *)0;
494 lease = (struct lease *)0;
495 if (find_subnet (&subnet, cip, MDL))
496 find_lease (&lease, packet,
9e383163 497 subnet -> shared_network, &ours, 0, ip_lease, MDL);
007e3ee4 498
98311e4b
DH
499 if (lease && lease -> client_hostname) {
500 if ((strlen (lease -> client_hostname) <= 64) &&
28868515 501 db_printable((unsigned char *)lease->client_hostname))
98311e4b
DH
502 s = lease -> client_hostname;
503 else
504 s = "Hostname Unsuitable for Printing";
505 } else
d9eefc5d
TL
506 s = (char *)0;
507
4f767627
TL
508 oc = lookup_option (&dhcp_universe, packet -> options,
509 DHO_DHCP_SERVER_IDENTIFIER);
510 memset (&data, 0, sizeof data);
511 if (oc &&
512 evaluate_option_cache (&data, packet, (struct lease *)0,
513 (struct client_state *)0,
514 packet -> options, (struct option_state *)0,
515 &global_scope, oc, MDL)) {
516 sip.len = 4;
517 memcpy (sip.iabuf, data.data, 4);
518 data_string_forget (&data, MDL);
98311e4b
DH
519 /* piaddr() should not return more than a 15 byte string.
520 * safe.
521 */
4f767627 522 sprintf (smbuf, " (%s)", piaddr (sip));
f8380d3f 523 } else {
4f767627 524 smbuf [0] = 0;
f8380d3f
SR
525 sip.len = 0;
526 }
4f767627 527
98311e4b
DH
528 /* %Audit% This is log output. %2004.06.17,Safe%
529 * If we truncate we hope the user can get a hint from the log.
530 */
785c1a51
FD
531#if defined(DHCPv6) && defined(DHCP4o6)
532 if (dhcpv4_over_dhcpv6 && (packet->dhcp4o6_response != NULL)) {
533 snprintf (msgbuf, sizeof msgbuf,
534 "DHCP4o6 DHCPREQUEST for %s%s from %s %s%s%svia %s",
535 piaddr (cip), smbuf,
536 (packet -> raw -> htype
537 ? print_hw_addr (packet -> raw -> htype,
538 packet -> raw -> hlen,
539 packet -> raw -> chaddr)
540 : (lease
541 ? print_hex_1(lease->uid_len, lease->uid, 60)
542 : "<no identifier>")),
543 s ? "(" : "", s ? s : "", s ? ") " : "",
544 piaddr(packet->client_addr));
545 } else
546#endif
98311e4b
DH
547 snprintf (msgbuf, sizeof msgbuf,
548 "DHCPREQUEST for %s%s from %s %s%s%svia %s",
4f767627 549 piaddr (cip), smbuf,
d9eefc5d
TL
550 (packet -> raw -> htype
551 ? print_hw_addr (packet -> raw -> htype,
552 packet -> raw -> hlen,
fdd46b53 553 packet -> raw -> chaddr)
d9eefc5d 554 : (lease
6d103865 555 ? print_hex_1(lease->uid_len, lease->uid, 60)
d9eefc5d
TL
556 : "<no identifier>")),
557 s ? "(" : "", s ? s : "", s ? ") " : "",
558 packet -> raw -> giaddr.s_addr
c4924529 559 ? inet_ntoa (packet -> raw -> giaddr)
d9eefc5d 560 : packet -> interface -> name);
a69f4fd3 561
007e3ee4 562#if defined (FAILOVER_PROTOCOL)
bb0b00a5
TL
563 if (lease && lease -> pool && lease -> pool -> failover_peer) {
564 peer = lease -> pool -> failover_peer;
565 if (peer -> service_state == not_responding ||
566 peer -> service_state == service_startup) {
567 log_info ("%s: not responding%s",
f8f34940 568 msgbuf, peer -> nrr);
bb0b00a5
TL
569 goto out;
570 }
31bbee78 571
98311e4b
DH
572 /* "load balance to peer" - is not done at all for request.
573 *
574 * If it's RENEWING, we are the only server to hear it, so
575 * we have to serve it. If it's REBINDING, it's out of
576 * communication with the other server, so there's no point
577 * in waiting to serve it. However, if the lease we're
578 * offering is not a free lease, then we may be the only
579 * server that can offer it, so we can't load balance if
580 * the lease isn't in the free or backup state. If it is
581 * in the free or backup state, then that state is what
582 * mandates one server or the other should perform the
583 * allocation, not the LBA...we know the peer cannot
584 * allocate a request for an address in our free state.
585 *
586 * So our only compass is lease_mine_to_reallocate(). This
587 * effects both load balancing, and a sanity-check that we
588 * are not going to try to allocate a lease that isn't ours.
589 */
d758ad8c
TL
590 if ((lease -> binding_state == FTS_FREE ||
591 lease -> binding_state == FTS_BACKUP) &&
592 !lease_mine_to_reallocate (lease)) {
593 log_debug ("%s: lease owned by peer", msgbuf);
31bbee78
TL
594 goto out;
595 }
d758ad8c 596
fdfebedf
DH
597 /*
598 * If the lease is in a transitional state, we can't
599 * renew it unless we can rewind it to a non-transitional
600 * state (active, free, or backup). lease_mine_to_reallocate()
601 * checks for free/backup, so we only need to check for active.
602 */
603 if ((lease->binding_state == FTS_RELEASED ||
604 lease->binding_state == FTS_EXPIRED) &&
605 lease->rewind_binding_state != FTS_ACTIVE &&
606 !lease_mine_to_reallocate(lease)) {
607 log_debug("%s: lease in transition state %s", msgbuf,
608 (lease->binding_state == FTS_RELEASED)
98311e4b
DH
609 ? "released" : "expired");
610 goto out;
611 }
612
613 /* It's actually very unlikely that we'll ever get here,
614 but if we do, tell the client to stop using the lease,
615 because the administrator reset it. */
616 if (lease -> binding_state == FTS_RESET &&
617 !lease_mine_to_reallocate (lease)) {
618 log_debug ("%s: lease reset by administrator", msgbuf);
e046c826 619 nak_lease (packet, &cip, lease->subnet->group);
98311e4b
DH
620 goto out;
621 }
622
7116a34f
TM
623 /* If server-id-check is enabled, verify that the client's
624 * server source address (sip from incoming packet) is ours.
625 * To avoid problems with confused clients we do some sanity
626 * checks to verify sip's length and that it isn't all zeros.
627 * We then get the server id we would likely use for this
628 * packet and compare them. If they don't match it we assume
629 * we didn't send the offer and so we don't process the
630 * request. */
631 if ((server_id_check == 1) && (sip.len == 4) &&
f8380d3f
SR
632 (memcmp(sip.iabuf, "\0\0\0\0", sip.len) != 0)) {
633 struct in_addr from;
e046c826
TM
634 struct option_state *eval_options = NULL;
635
636 eval_network_statements(&eval_options, packet, NULL);
7116a34f
TM
637 get_server_source_address(&from, eval_options,
638 NULL, packet);
e046c826 639 option_state_dereference (&eval_options, MDL);
f8380d3f
SR
640 if (memcmp(sip.iabuf, &from, sip.len) != 0) {
641 log_debug("%s: not our server id", msgbuf);
642 goto out;
643 }
644 }
f8380d3f 645
d758ad8c
TL
646 /* At this point it's possible that we will get a broadcast
647 DHCPREQUEST for a lease that we didn't offer, because
648 both we and the peer are in a position to offer it.
649 In that case, we probably shouldn't answer. In order
650 to not answer, we would have to compare the server
651 identifier sent by the client with the list of possible
652 server identifiers we can send, and if the client's
653 identifier isn't on the list, drop the DHCPREQUEST.
654 We aren't currently doing that for two reasons - first,
655 it's not clear that all clients do the right thing
656 with respect to sending the client identifier, which
657 could mean that we might simply not respond to a client
658 that is depending on us to respond. Secondly, we allow
659 the user to specify the server identifier to send, and
660 we don't enforce that the server identifier should be
661 one of our IP addresses. This is probably not a big
662 deal, but it's theoretically an issue.
663
664 The reason we care about this is that if both servers
665 send a DHCPACK to the DHCPREQUEST, they are then going
666 to send dueling BNDUPD messages, which could cause
667 trouble. I think it causes no harm, but it seems
668 wrong. */
bb0b00a5
TL
669 } else
670 peer = (dhcp_failover_state_t *)0;
007e3ee4
TL
671#endif
672
44b2e3ad
TL
673 /* If a client on a given network REQUESTs a lease on an
674 address on a different network, NAK it. If the Requested
675 Address option was used, the protocol says that it must
676 have been broadcast, so we can trust the source network
677 information.
15c00bba
TL
678
679 If ciaddr was specified and Requested Address was not, then
680 we really only know for sure what network a packet came from
681 if it came through a BOOTP gateway - if it came through an
3d789c23 682 IP router, we'll just have to assume that it's cool.
15c00bba 683
44b2e3ad
TL
684 If we don't think we know where the packet came from, it
685 came through a gateway from an unknown network, so it's not
686 from a RENEWING client. If we recognize the network it
687 *thinks* it's on, we can NAK it even though we don't
688 recognize the network it's *actually* on; otherwise we just
689 have to ignore it.
690
691 We don't currently try to take advantage of access to the
692 raw packet, because it's not available on all platforms.
693 So a packet that was unicast to us through a router from a
694 RENEWING client is going to look exactly like a packet that
695 was broadcast to us from an INIT-REBOOT client.
696
697 Since we can't tell the difference between these two kinds
698 of packets, if the packet appears to have come in off the
699 local wire, we have to treat it as if it's a RENEWING
700 client. This means that we can't NAK a RENEWING client on
701 the local wire that has a bogus address. The good news is
702 that we won't ACK it either, so it should revert to INIT
703 state and send us a DHCPDISCOVER, which we *can* work with.
704
705 Because we can't detect that a RENEWING client is on the
706 wrong wire, it's going to sit there trying to renew until
707 it gets to the REBIND state, when we *can* NAK it because
708 the packet will get to us through a BOOTP gateway. We
709 shouldn't actually see DHCPREQUEST packets from RENEWING
710 clients on the wrong wire anyway, since their idea of their
711 local router will be wrong. In any case, the protocol
712 doesn't really allow us to NAK a DHCPREQUEST from a
713 RENEWING client, so we can punt on this issue. */
714
715 if (!packet -> shared_network ||
1d8b8d99
TL
716 (packet -> raw -> ciaddr.s_addr &&
717 packet -> raw -> giaddr.s_addr) ||
27e90ede 718 (have_requested_addr && !packet -> raw -> ciaddr.s_addr)) {
a5b21e16 719
15c00bba
TL
720 /* If we don't know where it came from but we do know
721 where it claims to have come from, it didn't come
3d789c23 722 from there. */
15c00bba 723 if (!packet -> shared_network) {
027f46cb 724 if (subnet && subnet -> group -> authoritative) {
8ae2d595 725 log_info ("%s: wrong network.", msgbuf);
e046c826 726 nak_lease (packet, &cip, NULL);
3d789c23 727 goto out;
15c00bba 728 }
4fbcd991 729 /* Otherwise, ignore it. */
797d58b3
TL
730 log_info ("%s: ignored (%s).", msgbuf,
731 (subnet
732 ? "not authoritative" : "unknown subnet"));
20916cae 733 goto out;
b88e8e15 734 }
15c00bba 735
44b2e3ad
TL
736 /* If we do know where it came from and it asked for an
737 address that is not on that shared network, nak it. */
20916cae
TL
738 if (subnet)
739 subnet_dereference (&subnet, MDL);
740 if (!find_grouped_subnet (&subnet, packet -> shared_network,
741 cip, MDL)) {
027f46cb
TL
742 if (packet -> shared_network -> group -> authoritative)
743 {
8ae2d595 744 log_info ("%s: wrong network.", msgbuf);
e046c826 745 nak_lease (packet, &cip, NULL);
3d789c23 746 goto out;
027f46cb 747 }
e89a5afe 748 log_info ("%s: ignored (not authoritative).", msgbuf);
b88e8e15
TL
749 return;
750 }
751 }
ed8bcd8f 752
0c11afbc 753 /* If the address the client asked for is ours, but it wasn't
65cf86d7 754 available for the client, NAK it. */
0c11afbc 755 if (!lease && ours) {
8ae2d595 756 log_info ("%s: lease %s unavailable.", msgbuf, piaddr (cip));
e046c826 757 nak_lease (packet, &cip, (subnet ? subnet->group : NULL));
20916cae 758 goto out;
0c11afbc
TL
759 }
760
6dadd610 761 /* Otherwise, send the lease to the client if we found one. */
eeea1395 762 if (lease) {
c75473d8
DH
763 ack_lease (packet, lease, DHCPACK, 0, msgbuf, ms_nulltp,
764 (struct host_decl *)0);
eeea1395 765 } else
74f45f96 766 log_info ("%s: unknown lease %s.", msgbuf, piaddr (cip));
20916cae
TL
767
768 out:
769 if (subnet)
770 subnet_dereference (&subnet, MDL);
771 if (lease)
772 lease_dereference (&lease, MDL);
773 return;
ed8bcd8f
TL
774}
775
5bc2e1f2 776void dhcprelease (packet, ms_nulltp)
ed8bcd8f 777 struct packet *packet;
5bc2e1f2 778 int ms_nulltp;
ed8bcd8f 779{
cb8176c4 780 struct lease *lease = (struct lease *)0, *next = (struct lease *)0;
2b260752 781 struct iaddr cip;
5d25508c
TL
782 struct option_cache *oc;
783 struct data_string data;
98311e4b
DH
784 const char *s;
785 char msgbuf [1024], cstr[16]; /* XXX */
fa97acc1 786
bb0b00a5 787
2ba8b7cd 788 /* DHCPRELEASE must not specify address in requested-address
65cf86d7
EH
789 option, but old protocol specs weren't explicit about this,
790 so let it go. */
951323fe 791 if ((oc = lookup_option (&dhcp_universe, packet -> options,
5d25508c 792 DHO_DHCP_REQUESTED_ADDRESS))) {
8ae2d595 793 log_info ("DHCPRELEASE from %s specified requested-address.",
2ba8b7cd
TL
794 print_hw_addr (packet -> raw -> htype,
795 packet -> raw -> hlen,
796 packet -> raw -> chaddr));
fa97acc1
TL
797 }
798
951323fe 799 oc = lookup_option (&dhcp_universe, packet -> options,
5d25508c
TL
800 DHO_DHCP_CLIENT_IDENTIFIER);
801 memset (&data, 0, sizeof data);
802 if (oc &&
ca1c700e 803 evaluate_option_cache (&data, packet, (struct lease *)0,
9e383163 804 (struct client_state *)0,
ca1c700e 805 packet -> options, (struct option_state *)0,
12c9957e 806 &global_scope, oc, MDL)) {
20916cae 807 find_lease_by_uid (&lease, data.data, data.len, MDL);
4bd8800e 808 data_string_forget (&data, MDL);
ed8bcd8f 809
73a4b6e5
TL
810 /* See if we can find a lease that matches the IP address
811 the client is claiming. */
b7d47627 812 while (lease) {
cb8176c4
TL
813 if (lease -> n_uid)
814 lease_reference (&next, lease -> n_uid, MDL);
73a4b6e5
TL
815 if (!memcmp (&packet -> raw -> ciaddr,
816 lease -> ip_addr.iabuf, 4)) {
817 break;
818 }
cb8176c4
TL
819 lease_dereference (&lease, MDL);
820 if (next) {
821 lease_reference (&lease, next, MDL);
822 lease_dereference (&next, MDL);
823 }
73a4b6e5 824 }
cb8176c4
TL
825 if (next)
826 lease_dereference (&next, MDL);
20916cae 827 }
12c9957e
TL
828
829 /* The client is supposed to pass a valid client-identifier,
830 but the spec on this has changed historically, so try the
831 IP address in ciaddr if the client-identifier fails. */
832 if (!lease) {
db2ed553
TL
833 cip.len = 4;
834 memcpy (cip.iabuf, &packet -> raw -> ciaddr, 4);
20916cae 835 find_lease_by_ip_addr (&lease, cip, MDL);
2ba8b7cd
TL
836 }
837
838
98311e4b
DH
839 /* If the hardware address doesn't match, don't do the release. */
840 if (lease &&
841 (lease -> hardware_addr.hlen != packet -> raw -> hlen + 1 ||
842 lease -> hardware_addr.hbuf [0] != packet -> raw -> htype ||
843 memcmp (&lease -> hardware_addr.hbuf [1],
844 packet -> raw -> chaddr, packet -> raw -> hlen)))
845 lease_dereference (&lease, MDL);
846
847 if (lease && lease -> client_hostname) {
848 if ((strlen (lease -> client_hostname) <= 64) &&
28868515 849 db_printable((unsigned char *)lease->client_hostname))
98311e4b
DH
850 s = lease -> client_hostname;
851 else
852 s = "Hostname Unsuitable for Printing";
853 } else
d9eefc5d
TL
854 s = (char *)0;
855
98311e4b
DH
856 /* %Audit% Cannot exceed 16 bytes. %2004.06.17,Safe%
857 * We copy this out to stack because we actually want to log two
858 * inet_ntoa()'s in this message.
859 */
860 strncpy(cstr, inet_ntoa (packet -> raw -> ciaddr), 15);
861 cstr[15] = '\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 */
785c1a51
FD
866#if defined(DHCPv6) && defined(DHCP4o6)
867 if (dhcpv4_over_dhcpv6 && (packet->dhcp4o6_response != NULL)) {
868 snprintf (msgbuf, sizeof msgbuf,
869 "DHCP4o6 DHCPRELEASE of %s from %s %s%s%svia "
870 "%s (%sfound)",
871 cstr,
872 (packet -> raw -> htype
873 ? print_hw_addr (packet -> raw -> htype,
874 packet -> raw -> hlen,
875 packet -> raw -> chaddr)
876 : (lease
877 ? print_hex_1(lease->uid_len, lease->uid, 60)
878 : "<no identifier>")),
879 s ? "(" : "", s ? s : "", s ? ") " : "",
880 piaddr(packet->client_addr),
881 lease ? "" : "not ");
882 } else
883#endif
98311e4b 884 snprintf (msgbuf, sizeof msgbuf,
007e3ee4 885 "DHCPRELEASE of %s from %s %s%s%svia %s (%sfound)",
98311e4b 886 cstr,
007e3ee4
TL
887 (packet -> raw -> htype
888 ? print_hw_addr (packet -> raw -> htype,
889 packet -> raw -> hlen,
890 packet -> raw -> chaddr)
891 : (lease
6d103865 892 ? print_hex_1(lease->uid_len, lease->uid, 60)
007e3ee4
TL
893 : "<no identifier>")),
894 s ? "(" : "", s ? s : "", s ? ") " : "",
895 packet -> raw -> giaddr.s_addr
896 ? inet_ntoa (packet -> raw -> giaddr)
897 : packet -> interface -> name,
898 lease ? "" : "not ");
899
900#if defined (FAILOVER_PROTOCOL)
bb0b00a5
TL
901 if (lease && lease -> pool && lease -> pool -> failover_peer) {
902 dhcp_failover_state_t *peer = lease -> pool -> failover_peer;
903 if (peer -> service_state == not_responding ||
904 peer -> service_state == service_startup) {
905 log_info ("%s: ignored%s",
906 peer -> name, peer -> nrr);
907 goto out;
908 }
909
007e3ee4
TL
910 /* DHCPRELEASE messages are unicast, so if the client
911 sent the DHCPRELEASE to us, it's not going to send it
912 to the peer. Not sure why this would happen, and
913 if it does happen I think we still have to change the
bb0b00a5 914 lease state, so that's what we're doing.
007e3ee4 915 XXX See what it says in the draft about this. */
007e3ee4
TL
916 }
917#endif
a8b53b42 918
b88e8e15 919 /* If we found a lease, release it. */
20916cae 920 if (lease && lease -> ends > cur_time) {
43f23dcc 921 release_lease (lease, packet);
a5b21e16 922 }
6c608437 923 log_info ("%s", msgbuf);
66cebfcb 924#if defined(FAILOVER_PROTOCOL)
007e3ee4 925 out:
66cebfcb 926#endif
007e3ee4
TL
927 if (lease)
928 lease_dereference (&lease, MDL);
ed8bcd8f
TL
929}
930
5bc2e1f2 931void dhcpdecline (packet, ms_nulltp)
b88e8e15 932 struct packet *packet;
5bc2e1f2 933 int ms_nulltp;
b88e8e15 934{
20916cae 935 struct lease *lease = (struct lease *)0;
19654922 936 struct option_state *options = (struct option_state *)0;
bb0b00a5 937 int ignorep = 0;
19654922
TL
938 int i;
939 const char *status;
98311e4b 940 const char *s;
007e3ee4 941 char msgbuf [1024]; /* XXX */
9e383163
TL
942 struct iaddr cip;
943 struct option_cache *oc;
944 struct data_string data;
a8b53b42 945
fa97acc1 946 /* DHCPDECLINE must specify address. */
951323fe 947 if (!(oc = lookup_option (&dhcp_universe, packet -> options,
5d25508c
TL
948 DHO_DHCP_REQUESTED_ADDRESS)))
949 return;
950 memset (&data, 0, sizeof data);
ca1c700e 951 if (!evaluate_option_cache (&data, packet, (struct lease *)0,
9e383163 952 (struct client_state *)0,
ca1c700e
TL
953 packet -> options,
954 (struct option_state *)0,
12c9957e 955 &global_scope, oc, MDL))
fa97acc1 956 return;
a8b53b42 957
fa97acc1 958 cip.len = 4;
5d25508c 959 memcpy (cip.iabuf, data.data, 4);
4bd8800e 960 data_string_forget (&data, MDL);
20916cae 961 find_lease_by_ip_addr (&lease, cip, MDL);
fa97acc1 962
98311e4b
DH
963 if (lease && lease -> client_hostname) {
964 if ((strlen (lease -> client_hostname) <= 64) &&
28868515 965 db_printable((unsigned char *)lease->client_hostname))
98311e4b
DH
966 s = lease -> client_hostname;
967 else
968 s = "Hostname Unsuitable for Printing";
969 } else
007e3ee4
TL
970 s = (char *)0;
971
98311e4b
DH
972 /* %Audit% This is log output. %2004.06.17,Safe%
973 * If we truncate we hope the user can get a hint from the log.
974 */
785c1a51
FD
975#if defined(DHCPv6) && defined(DHCP4o6)
976 if (dhcpv4_over_dhcpv6 && (packet->dhcp4o6_response != NULL)) {
977 snprintf (msgbuf, sizeof msgbuf,
978 "DHCP4o6 DHCPDECLINE of %s from %s %s%s%svia %s",
979 piaddr (cip),
980 (packet -> raw -> htype
981 ? print_hw_addr (packet -> raw -> htype,
982 packet -> raw -> hlen,
983 packet -> raw -> chaddr)
984 : (lease
985 ? print_hex_1(lease->uid_len, lease->uid, 60)
986 : "<no identifier>")),
987 s ? "(" : "", s ? s : "", s ? ") " : "",
988 piaddr(packet->client_addr));
989 } else
990#endif
98311e4b
DH
991 snprintf (msgbuf, sizeof msgbuf,
992 "DHCPDECLINE of %s from %s %s%s%svia %s",
007e3ee4
TL
993 piaddr (cip),
994 (packet -> raw -> htype
995 ? print_hw_addr (packet -> raw -> htype,
996 packet -> raw -> hlen,
997 packet -> raw -> chaddr)
998 : (lease
6d103865 999 ? print_hex_1(lease->uid_len, lease->uid, 60)
007e3ee4
TL
1000 : "<no identifier>")),
1001 s ? "(" : "", s ? s : "", s ? ") " : "",
1002 packet -> raw -> giaddr.s_addr
1003 ? inet_ntoa (packet -> raw -> giaddr)
1004 : packet -> interface -> name);
1005
4bd8800e 1006 option_state_allocate (&options, MDL);
a69f4fd3 1007
19654922
TL
1008 /* Execute statements in scope starting with the subnet scope. */
1009 if (lease)
a7341359
SR
1010 execute_statements_in_scope(NULL, packet, NULL, NULL,
1011 packet->options, options,
1012 &global_scope,
1013 lease->subnet->group,
1014 NULL, NULL);
19654922
TL
1015
1016 /* Execute statements in the class scopes. */
1017 for (i = packet -> class_count; i > 0; i--) {
1018 execute_statements_in_scope
a7341359
SR
1019 (NULL, packet, NULL, NULL, packet->options, options,
1020 &global_scope, packet->classes[i - 1]->group,
1021 lease ? lease->subnet->group : NULL, NULL);
b88e8e15 1022 }
19654922
TL
1023
1024 /* Drop the request if dhcpdeclines are being ignored. */
1025 oc = lookup_option (&server_universe, options, SV_DECLINES);
1026 if (!oc ||
12c9957e 1027 evaluate_boolean_option_cache (&ignorep, packet, lease,
9e383163 1028 (struct client_state *)0,
12c9957e
TL
1029 packet -> options, options,
1030 &lease -> scope, oc, MDL)) {
bb0b00a5
TL
1031 /* If we found a lease, mark it as unusable and complain. */
1032 if (lease) {
1033#if defined (FAILOVER_PROTOCOL)
1034 if (lease -> pool && lease -> pool -> failover_peer) {
1035 dhcp_failover_state_t *peer =
1036 lease -> pool -> failover_peer;
1037 if (peer -> service_state == not_responding ||
1038 peer -> service_state == service_startup) {
1039 if (!ignorep)
1040 log_info ("%s: ignored%s",
1041 peer -> name, peer -> nrr);
1042 goto out;
1043 }
1044
1045 /* DHCPDECLINE messages are broadcast, so we can safely
1046 ignore the DHCPDECLINE if the peer has the lease.
1047 XXX Of course, at this point that information has been
1048 lost. */
19654922 1049 }
bb0b00a5
TL
1050#endif
1051
1052 abandon_lease (lease, "declined.");
1053 status = "abandoned";
a4ffedd1
DH
1054 } else {
1055 status = "not found";
bb0b00a5 1056 }
19654922 1057 } else
bb0b00a5 1058 status = "ignored";
19654922 1059
007e3ee4
TL
1060 if (!ignorep)
1061 log_info ("%s: %s", msgbuf, status);
66cebfcb
DH
1062
1063#if defined(FAILOVER_PROTOCOL)
007e3ee4 1064 out:
66cebfcb 1065#endif
007e3ee4
TL
1066 if (options)
1067 option_state_dereference (&options, MDL);
20916cae
TL
1068 if (lease)
1069 lease_dereference (&lease, MDL);
b88e8e15
TL
1070}
1071
563f0b8a
FD
1072#if defined(RELAY_PORT)
1073u_int16_t dhcp_check_relayport(packet)
1074 struct packet *packet;
1075{
1076 if (lookup_option(&agent_universe,
1077 packet->options,
1078 RAI_RELAY_PORT) != NULL) {
1079 return (packet->client_port);
1080 }
1081
1082 return (0);
1083}
1084#endif
1085
5bc2e1f2 1086void dhcpinform (packet, ms_nulltp)
b88e8e15 1087 struct packet *packet;
5bc2e1f2 1088 int ms_nulltp;
b88e8e15 1089{
4d079f0e
SR
1090 char msgbuf[1024], *addr_type;
1091 struct data_string d1, prl, fixed_addr;
e77892f5 1092 struct option_cache *oc;
4d079f0e 1093 struct option_state *options = NULL;
e77892f5
TL
1094 struct dhcp_packet raw;
1095 struct packet outgoing;
3175ee90 1096 unsigned char dhcpack = DHCPACK;
49f61135 1097 struct subnet *subnet = NULL;
4d079f0e 1098 struct iaddr cip, gip, sip;
28868515 1099 unsigned i;
b1b7b521 1100 int nulltp;
e77892f5
TL
1101 struct sockaddr_in to;
1102 struct in_addr from;
49f61135 1103 isc_boolean_t zeroed_ciaddr;
dd9237c3 1104 struct interface_info *interface;
4d079f0e
SR
1105 int result, h_m_client_ip = 0;
1106 struct host_decl *host = NULL, *hp = NULL, *h;
27058b3e 1107#if defined(RELAY_PORT)
563f0b8a 1108 u_int16_t relay_port = 0;
27058b3e 1109#endif
4d079f0e
SR
1110#if defined (DEBUG_INFORM_HOST)
1111 int h_w_fixed_addr = 0;
1112#endif
49f61135 1113
cdc336ab
TL
1114 /* The client should set ciaddr to its IP address, but apparently
1115 it's common for clients not to do this, so we'll use their IP
1116 source address if they didn't set ciaddr. */
4d079f0e 1117 if (!packet->raw->ciaddr.s_addr) {
49f61135 1118 zeroed_ciaddr = ISC_TRUE;
785c1a51
FD
1119 /* With DHCPv4-over-DHCPv6 it can be an IPv6 address
1120 so we check its length. */
1121 if (packet->client_addr.len == 4) {
1122 cip.len = 4;
1123 memcpy(cip.iabuf, &packet->client_addr.iabuf, 4);
1124 addr_type = "source";
1125 } else {
1126 cip.len = 0;
1127 memset(cip.iabuf, 0, 4);
1128 addr_type = "v4o6";
1129 }
cdc336ab 1130 } else {
49f61135 1131 zeroed_ciaddr = ISC_FALSE;
cdc336ab 1132 cip.len = 4;
4d079f0e
SR
1133 memcpy(cip.iabuf, &packet->raw->ciaddr, 4);
1134 addr_type = "client";
cdc336ab 1135 }
4d079f0e
SR
1136 sip.len = 4;
1137 memcpy(sip.iabuf, cip.iabuf, 4);
cdc336ab 1138
88cd8aca
DH
1139 if (packet->raw->giaddr.s_addr) {
1140 gip.len = 4;
1141 memcpy(gip.iabuf, &packet->raw->giaddr, 4);
4d079f0e
SR
1142 if (zeroed_ciaddr == ISC_TRUE) {
1143 addr_type = "relay";
1144 memcpy(sip.iabuf, gip.iabuf, 4);
1145 }
88cd8aca
DH
1146 } else
1147 gip.len = 0;
1148
98311e4b
DH
1149 /* %Audit% This is log output. %2004.06.17,Safe%
1150 * If we truncate we hope the user can get a hint from the log.
1151 */
785c1a51
FD
1152#if defined(DHCPv6) && defined(DHCP4o6)
1153 if (dhcpv4_over_dhcpv6 && (packet->dhcp4o6_response != NULL)) {
1154 snprintf(msgbuf, sizeof(msgbuf),
1155 "DHCP4o6 DHCPINFORM from %s via %s",
1156 piaddr(cip),
1157 piaddr(packet->client_addr));
1158 } else
1159#endif
4d079f0e
SR
1160 snprintf(msgbuf, sizeof(msgbuf), "DHCPINFORM from %s via %s",
1161 piaddr(cip),
1162 packet->raw->giaddr.s_addr ?
1163 inet_ntoa(packet->raw->giaddr) :
1164 packet->interface->name);
cdc336ab
TL
1165
1166 /* If the IP source address is zero, don't respond. */
4d079f0e
SR
1167 if (!memcmp(cip.iabuf, "\0\0\0", 4)) {
1168 log_info("%s: ignored (null source address).", msgbuf);
cdc336ab
TL
1169 return;
1170 }
e77892f5 1171
563f0b8a
FD
1172#if defined(RELAY_PORT)
1173 relay_port = dhcp_check_relayport(packet);
1174#endif
1175
a5b21e16 1176 /* Find the subnet that the client is on.
4d079f0e
SR
1177 * CC: Do the link selection / subnet selection
1178 */
1179
1180 option_state_allocate(&options, MDL);
1181
1182 if ((oc = lookup_option(&agent_universe, packet->options,
1183 RAI_LINK_SELECT)) == NULL)
1184 oc = lookup_option(&dhcp_universe, packet->options,
1185 DHO_SUBNET_SELECTION);
49f61135 1186
4d079f0e
SR
1187 memset(&d1, 0, sizeof d1);
1188 if (oc && evaluate_option_cache(&d1, packet, NULL, NULL,
1189 packet->options, NULL,
1190 &global_scope, oc, MDL)) {
1191 struct option_cache *noc = NULL;
1192
1193 if (d1.len != 4) {
1194 log_info("%s: ignored (invalid subnet selection option).", msgbuf);
1195 option_state_dereference(&options, MDL);
0cd94b5e 1196 data_string_forget(&d1, MDL);
49f61135
DH
1197 return;
1198 }
e77892f5 1199
4d079f0e
SR
1200 memcpy(sip.iabuf, d1.data, 4);
1201 data_string_forget(&d1, MDL);
1202
1203 /* Make a copy of the data. */
1204 if (option_cache_allocate(&noc, MDL)) {
1205 if (oc->data.len)
1206 data_string_copy(&noc->data, &oc->data, MDL);
1207 if (oc->expression)
1208 expression_reference(&noc->expression,
1209 oc->expression, MDL);
1210 if (oc->option)
1211 option_reference(&(noc->option), oc->option,
1212 MDL);
49f61135 1213 }
4d079f0e
SR
1214 save_option(&dhcp_universe, options, noc);
1215 option_cache_dereference(&noc, MDL);
1216
1217 if ((zeroed_ciaddr == ISC_TRUE) && (gip.len != 0))
1218 addr_type = "relay link select";
1219 else
1220 addr_type = "selected";
1221 }
1222
1223 find_subnet(&subnet, sip, MDL);
1224
1225 if (subnet == NULL) {
1226 log_info("%s: unknown subnet for %s address %s",
1227 msgbuf, addr_type, piaddr(sip));
a07d99bb 1228 option_state_dereference(&options, MDL);
4d079f0e 1229 return;
e77892f5
TL
1230 }
1231
e89a5afe
TL
1232 /* We don't respond to DHCPINFORM packets if we're not authoritative.
1233 It would be nice if a per-host value could override this, but
1234 there's overhead involved in checking this, so let's see how people
1235 react first. */
a07d99bb 1236 if (!subnet->group->authoritative) {
20916cae 1237 static int eso = 0;
a07d99bb 1238 log_info("%s: not authoritative for subnet %s",
e89a5afe 1239 msgbuf, piaddr (subnet -> net));
20916cae 1240 if (!eso) {
a07d99bb 1241 log_info("If this DHCP server is authoritative for%s",
20916cae 1242 " that subnet,");
a07d99bb 1243 log_info("please write an `authoritative;' directi%s",
20916cae 1244 "ve either in the");
a07d99bb 1245 log_info("subnet declaration or in some scope that%s",
98311e4b 1246 " encloses the");
a07d99bb 1247 log_info("subnet declaration - for example, write %s",
20916cae 1248 "it at the top");
a07d99bb 1249 log_info("of the dhcpd.conf file.");
20916cae
TL
1250 }
1251 if (eso++ == 100)
1252 eso = 0;
a07d99bb
TM
1253 subnet_dereference(&subnet, MDL);
1254 option_state_dereference(&options, MDL);
e89a5afe
TL
1255 return;
1256 }
a5b21e16 1257
a07d99bb
TM
1258 memset(&outgoing, 0, sizeof outgoing);
1259 memset(&raw, 0, sizeof raw);
e77892f5
TL
1260 outgoing.raw = &raw;
1261
a1308b64
DH
1262 maybe_return_agent_options(packet, options);
1263
0aa74669
TM
1264 /* Execute statements network statements starting at the subnet level */
1265 execute_statements_in_scope(NULL, packet, NULL, NULL,
1266 packet->options, options,
1267 &global_scope, subnet->group,
1268 NULL, NULL);
1269
e0735300
TM
1270 /* If we have ciaddr, find its lease so we can find its pool. */
1271 if (zeroed_ciaddr == ISC_FALSE) {
0aa74669
TM
1272 struct lease* cip_lease = NULL;
1273
e0735300 1274 find_lease_by_ip_addr (&cip_lease, cip, MDL);
a5b21e16
TM
1275
1276 /* Overlay with pool options if ciaddr mapped to a lease. */
0aa74669
TM
1277 if (cip_lease) {
1278 if (cip_lease->pool && cip_lease->pool->group) {
1279 execute_statements_in_scope(
1280 NULL, packet, NULL, NULL,
1281 packet->options, options,
1282 &global_scope,
1283 cip_lease->pool->group,
1284 cip_lease->pool->shared_network->group,
1285 NULL);
1286 }
e0735300 1287
0aa74669
TM
1288 lease_dereference (&cip_lease, MDL);
1289 }
e0735300 1290 }
a5b21e16 1291
e77892f5 1292 /* Execute statements in the class scopes. */
a07d99bb 1293 for (i = packet->class_count; i > 0; i--) {
a7341359
SR
1294 execute_statements_in_scope(NULL, packet, NULL, NULL,
1295 packet->options, options,
1296 &global_scope,
1297 packet->classes[i - 1]->group,
a07d99bb 1298 subnet->group,
a7341359 1299 NULL);
e77892f5
TL
1300 }
1301
4d079f0e 1302 /*
a5b21e16 1303 * Process host declarations during DHCPINFORM,
4d079f0e
SR
1304 * Try to find a matching host declaration by cli ID or HW addr.
1305 *
1306 * Look through the host decls for one that matches the
1307 * client identifer or the hardware address. The preference
1308 * order is:
1309 * client id with matching ip address
1310 * hardware address with matching ip address
1311 * client id without a ip fixed address
1312 * hardware address without a fixed ip address
1313 * If found, set host to use its option definitions.
1314 */
1315 oc = lookup_option(&dhcp_universe, packet->options,
1316 DHO_DHCP_CLIENT_IDENTIFIER);
1317 memset(&d1, 0, sizeof(d1));
1318 if (oc &&
1319 evaluate_option_cache(&d1, packet, NULL, NULL,
1320 packet->options, NULL,
1321 &global_scope, oc, MDL)) {
1322 find_hosts_by_uid(&hp, d1.data, d1.len, MDL);
1323 data_string_forget(&d1, MDL);
1324
1325#if defined (DEBUG_INFORM_HOST)
1326 if (hp)
1327 log_debug ("dhcpinform: found host by ID "
1328 "-- checking fixed-address match");
1329#endif
1330 /* check if we have one with fixed-address
1331 * matching the client ip first */
1332 for (h = hp; !h_m_client_ip && h; h = h->n_ipaddr) {
1333 if (!h->fixed_addr)
1334 continue;
1335
1336 memset(&fixed_addr, 0, sizeof(fixed_addr));
1337 if (!evaluate_option_cache (&fixed_addr, NULL,
1338 NULL, NULL, NULL, NULL,
1339 &global_scope,
1340 h->fixed_addr, MDL))
1341 continue;
1342
1343#if defined (DEBUG_INFORM_HOST)
1344 h_w_fixed_addr++;
1345#endif
1346 for (i = 0;
1347 (i + cip.len) <= fixed_addr.len;
1348 i += cip.len) {
1349 if (memcmp(fixed_addr.data + i,
1350 cip.iabuf, cip.len) == 0) {
1351#if defined (DEBUG_INFORM_HOST)
1352 log_debug ("dhcpinform: found "
1353 "host with matching "
1354 "fixed-address by ID");
1355#endif
1356 host_reference(&host, h, MDL);
1357 h_m_client_ip = 1;
1358 break;
1359 }
1360 }
1361 data_string_forget(&fixed_addr, MDL);
1362 }
1363
1364 /* fallback to a host without fixed-address */
1365 for (h = hp; !host && h; h = h->n_ipaddr) {
1366 if (h->fixed_addr)
1367 continue;
1368
1369#if defined (DEBUG_INFORM_HOST)
1370 log_debug ("dhcpinform: found host "
1371 "without fixed-address by ID");
1372#endif
1373 host_reference(&host, h, MDL);
1374 break;
1375 }
1376 if (hp)
1377 host_dereference (&hp, MDL);
1378 }
1379 if (!host || !h_m_client_ip) {
1380 find_hosts_by_haddr(&hp, packet->raw->htype,
1381 packet->raw->chaddr,
1382 packet->raw->hlen, MDL);
1383
1384#if defined (DEBUG_INFORM_HOST)
1385 if (hp)
1386 log_debug ("dhcpinform: found host by HW "
1387 "-- checking fixed-address match");
1388#endif
1389
1390 /* check if we have one with fixed-address
1391 * matching the client ip first */
1392 for (h = hp; !h_m_client_ip && h; h = h->n_ipaddr) {
1393 if (!h->fixed_addr)
1394 continue;
1395
1396 memset (&fixed_addr, 0, sizeof(fixed_addr));
1397 if (!evaluate_option_cache (&fixed_addr, NULL,
1398 NULL, NULL, NULL, NULL,
1399 &global_scope,
1400 h->fixed_addr, MDL))
1401 continue;
1402
1403#if defined (DEBUG_INFORM_HOST)
1404 h_w_fixed_addr++;
1405#endif
1406 for (i = 0;
1407 (i + cip.len) <= fixed_addr.len;
1408 i += cip.len) {
1409 if (memcmp(fixed_addr.data + i,
1410 cip.iabuf, cip.len) == 0) {
1411#if defined (DEBUG_INFORM_HOST)
1412 log_debug ("dhcpinform: found "
1413 "host with matching "
1414 "fixed-address by HW");
1415#endif
1416 /*
1417 * Hmm.. we've found one
1418 * without IP by ID and now
1419 * (better) one with IP by HW.
1420 */
1421 if(host)
1422 host_dereference(&host, MDL);
1423 host_reference(&host, h, MDL);
1424 h_m_client_ip = 1;
1425 break;
1426 }
1427 }
1428 data_string_forget(&fixed_addr, MDL);
1429 }
1430 /* fallback to a host without fixed-address */
1431 for (h = hp; !host && h; h = h->n_ipaddr) {
1432 if (h->fixed_addr)
1433 continue;
1434
1435#if defined (DEBUG_INFORM_HOST)
1436 log_debug ("dhcpinform: found host without "
1437 "fixed-address by HW");
1438#endif
1439 host_reference (&host, h, MDL);
1440 break;
1441 }
1442
1443 if (hp)
1444 host_dereference (&hp, MDL);
1445 }
a5b21e16 1446
4d079f0e
SR
1447#if defined (DEBUG_INFORM_HOST)
1448 /* Hmm..: what when there is a host with a fixed-address,
1449 * that matches by hw or id, but the fixed-addresses
1450 * didn't match client ip?
1451 */
1452 if (h_w_fixed_addr && !h_m_client_ip) {
1453 log_info ("dhcpinform: matching host with "
1454 "fixed-address different than "
1455 "client IP detected?!");
1456 }
1457#endif
1458
1459 /* If we have a host_decl structure, run the options
1460 * associated with its group. Whether the host decl
1461 * struct is old or not. */
1462 if (host) {
1463#if defined (DEBUG_INFORM_HOST)
1464 log_info ("dhcpinform: applying host (group) options");
1465#endif
1466 execute_statements_in_scope(NULL, packet, NULL, NULL,
1467 packet->options, options,
1468 &global_scope, host->group,
dd9738aa 1469 subnet->group,
4d079f0e
SR
1470 NULL);
1471 host_dereference (&host, MDL);
1472 }
1473
1474 /* CC: end of host entry processing.... */
a5b21e16 1475
e77892f5 1476 /* Figure out the filename. */
cdc336ab 1477 memset (&d1, 0, sizeof d1);
e77892f5 1478 oc = lookup_option (&server_universe, options, SV_FILENAME);
ca1c700e
TL
1479 if (oc &&
1480 evaluate_option_cache (&d1, packet, (struct lease *)0,
9e383163 1481 (struct client_state *)0,
ca1c700e 1482 packet -> options, (struct option_state *)0,
12c9957e 1483 &global_scope, oc, MDL)) {
e77892f5 1484 i = d1.len;
66be0ad1
SR
1485 if (i >= sizeof(raw.file)) {
1486 log_info("file name longer than packet field "
a5b21e16 1487 "truncated - field: %lu name: %d %.*s",
4176a700
MA
1488 (unsigned long)sizeof(raw.file), i,
1489 (int)i, d1.data);
66be0ad1
SR
1490 i = sizeof(raw.file);
1491 } else
1492 raw.file[i] = 0;
e77892f5 1493 memcpy (raw.file, d1.data, i);
4bd8800e 1494 data_string_forget (&d1, MDL);
e77892f5
TL
1495 }
1496
1497 /* Choose a server name as above. */
10553ccb 1498 oc = lookup_option (&server_universe, options, SV_SERVER_NAME);
ca1c700e 1499 if (oc &&
9e383163
TL
1500 evaluate_option_cache (&d1, packet, (struct lease *)0,
1501 (struct client_state *)0,
ca1c700e 1502 packet -> options, (struct option_state *)0,
12c9957e 1503 &global_scope, oc, MDL)) {
e77892f5 1504 i = d1.len;
66be0ad1
SR
1505 if (i >= sizeof(raw.sname)) {
1506 log_info("server name longer than packet field "
a5b21e16 1507 "truncated - field: %lu name: %d %.*s",
4176a700
MA
1508 (unsigned long)sizeof(raw.sname), i,
1509 (int)i, d1.data);
66be0ad1
SR
1510 i = sizeof(raw.sname);
1511 } else
1512 raw.sname[i] = 0;
e77892f5 1513 memcpy (raw.sname, d1.data, i);
4bd8800e 1514 data_string_forget (&d1, MDL);
e77892f5
TL
1515 }
1516
1517 /* Set a flag if this client is a lame Microsoft client that NUL
1518 terminates string options and expects us to do likewise. */
1519 nulltp = 0;
1520 if ((oc = lookup_option (&dhcp_universe, packet -> options,
1521 DHO_HOST_NAME))) {
88cd8aca
DH
1522 if (!oc->expression)
1523 nulltp = oc->flags & OPTION_HAD_NULLS;
e77892f5
TL
1524 }
1525
1526 /* Put in DHCP-specific options. */
1527 i = DHO_DHCP_MESSAGE_TYPE;
1528 oc = (struct option_cache *)0;
4bd8800e 1529 if (option_cache_allocate (&oc, MDL)) {
d758ad8c
TL
1530 if (make_const_data (&oc -> expression,
1531 &dhcpack, 1, 0, 0, MDL)) {
f7fdb216
DH
1532 option_code_hash_lookup(&oc->option,
1533 dhcp_universe.code_hash,
1534 &i, 0, MDL);
e77892f5
TL
1535 save_option (&dhcp_universe, options, oc);
1536 }
4bd8800e 1537 option_cache_dereference (&oc, MDL);
e77892f5
TL
1538 }
1539
f8380d3f 1540 get_server_source_address(&from, options, options, packet);
e77892f5
TL
1541
1542 /* Use the subnet mask from the subnet declaration if no other
1543 mask has been provided. */
1544 i = DHO_SUBNET_MASK;
10553ccb 1545 if (subnet && !lookup_option (&dhcp_universe, options, i)) {
cdc336ab 1546 oc = (struct option_cache *)0;
4bd8800e 1547 if (option_cache_allocate (&oc, MDL)) {
e77892f5
TL
1548 if (make_const_data (&oc -> expression,
1549 subnet -> netmask.iabuf,
d758ad8c
TL
1550 subnet -> netmask.len,
1551 0, 0, MDL)) {
f7fdb216
DH
1552 option_code_hash_lookup(&oc->option,
1553 dhcp_universe.code_hash,
1554 &i, 0, MDL);
e77892f5
TL
1555 save_option (&dhcp_universe, options, oc);
1556 }
4bd8800e 1557 option_cache_dereference (&oc, MDL);
e77892f5
TL
1558 }
1559 }
1560
10553ccb
TL
1561 /* If a site option space has been specified, use that for
1562 site option codes. */
1563 i = SV_SITE_OPTION_SPACE;
0af446bc 1564 if ((oc = lookup_option (&server_universe, options, i)) &&
ca1c700e 1565 evaluate_option_cache (&d1, packet, (struct lease *)0,
9e383163 1566 (struct client_state *)0,
12c9957e
TL
1567 packet -> options, options,
1568 &global_scope, oc, MDL)) {
20916cae 1569 struct universe *u = (struct universe *)0;
dd9237c3 1570
20916cae 1571 if (!universe_hash_lookup (&u, universe_hash,
165bce70
TL
1572 (const char *)d1.data, d1.len,
1573 MDL)) {
10553ccb 1574 log_error ("unknown option space %s.", d1.data);
4bd8800e 1575 option_state_dereference (&options, MDL);
20916cae
TL
1576 if (subnet)
1577 subnet_dereference (&subnet, MDL);
0cd94b5e 1578 data_string_forget (&d1, MDL);
10553ccb
TL
1579 return;
1580 }
1581
1582 options -> site_universe = u -> index;
2c9bf1f4 1583 options->site_code_min = find_min_site_code(u);
4bd8800e 1584 data_string_forget (&d1, MDL);
10553ccb
TL
1585 } else {
1586 options -> site_universe = dhcp_universe.index;
1587 options -> site_code_min = 0; /* Trust me, it works. */
1588 }
1589
cdc336ab 1590 memset (&prl, 0, sizeof prl);
431693d1
TL
1591
1592 /* Use the parameter list from the scope if there is one. */
1593 oc = lookup_option (&dhcp_universe, options,
e77892f5
TL
1594 DHO_DHCP_PARAMETER_REQUEST_LIST);
1595
431693d1
TL
1596 /* Otherwise, if the client has provided a list of options
1597 that it wishes returned, use it to prioritize. Otherwise,
1598 prioritize based on the default priority list. */
1599
cdc336ab 1600 if (!oc)
431693d1 1601 oc = lookup_option (&dhcp_universe, packet -> options,
cdc336ab
TL
1602 DHO_DHCP_PARAMETER_REQUEST_LIST);
1603
1604 if (oc)
ca1c700e 1605 evaluate_option_cache (&prl, packet, (struct lease *)0,
9e383163 1606 (struct client_state *)0,
12c9957e
TL
1607 packet -> options, options,
1608 &global_scope, oc, MDL);
e77892f5
TL
1609
1610#ifdef DEBUG_PACKET
1611 dump_packet (packet);
1612 dump_raw ((unsigned char *)packet -> raw, packet -> packet_length);
1613#endif
1614
1615 log_info ("%s", msgbuf);
1616
10553ccb 1617 /* Figure out the address of the boot file server. */
10553ccb
TL
1618 if ((oc =
1619 lookup_option (&server_universe, options, SV_NEXT_SERVER))) {
ca1c700e 1620 if (evaluate_option_cache (&d1, packet, (struct lease *)0,
9e383163 1621 (struct client_state *)0,
12c9957e
TL
1622 packet -> options, options,
1623 &global_scope, oc, MDL)) {
10553ccb
TL
1624 /* If there was more than one answer,
1625 take the first. */
1626 if (d1.len >= 4 && d1.data)
1627 memcpy (&raw.siaddr, d1.data, 4);
4bd8800e 1628 data_string_forget (&d1, MDL);
10553ccb
TL
1629 }
1630 }
1631
1e05d095
SR
1632 /*
1633 * Remove any time options, per section 3.4 RFC 2131
1634 */
1635 delete_option(&dhcp_universe, options, DHO_DHCP_LEASE_TIME);
1636 delete_option(&dhcp_universe, options, DHO_DHCP_RENEWAL_TIME);
1637 delete_option(&dhcp_universe, options, DHO_DHCP_REBINDING_TIME);
1638
e77892f5
TL
1639 /* Set up the option buffer... */
1640 outgoing.packet_length =
da38df14 1641 cons_options (packet, outgoing.raw, (struct lease *)0,
9e383163 1642 (struct client_state *)0,
12c9957e
TL
1643 0, packet -> options, options, &global_scope,
1644 0, nulltp, 0,
9030b313
TL
1645 prl.len ? &prl : (struct data_string *)0,
1646 (char *)0);
4bd8800e
TL
1647 option_state_dereference (&options, MDL);
1648 data_string_forget (&prl, MDL);
e77892f5
TL
1649
1650 /* Make sure that the packet is at least as big as a BOOTP packet. */
1651 if (outgoing.packet_length < BOOTP_MIN_LEN)
1652 outgoing.packet_length = BOOTP_MIN_LEN;
1653
e77892f5 1654 raw.giaddr = packet -> raw -> giaddr;
cdc336ab 1655 raw.ciaddr = packet -> raw -> ciaddr;
e77892f5
TL
1656 memcpy (raw.chaddr, packet -> raw -> chaddr, sizeof raw.chaddr);
1657 raw.hlen = packet -> raw -> hlen;
1658 raw.htype = packet -> raw -> htype;
1659
1660 raw.xid = packet -> raw -> xid;
1661 raw.secs = packet -> raw -> secs;
1662 raw.flags = packet -> raw -> flags;
1663 raw.hops = packet -> raw -> hops;
1664 raw.op = BOOTREPLY;
1665
e77892f5
TL
1666#ifdef DEBUG_PACKET
1667 dump_packet (&outgoing);
1668 dump_raw ((unsigned char *)&raw, outgoing.packet_length);
1669#endif
1670
785c1a51
FD
1671#if defined(DHCPv6) && defined(DHCP4o6)
1672 if (dhcpv4_over_dhcpv6 && (packet->dhcp4o6_response != NULL)) {
1673 /* Report what we're sending. */
1674 snprintf(msgbuf, sizeof msgbuf,
1675 "DHCP4o6 DHCPACK to %s (%s) via", piaddr(cip),
1676 (packet->raw->htype && packet->raw->hlen) ?
1677 print_hw_addr(packet->raw->htype, packet->raw->hlen,
1678 packet->raw->chaddr) :
1679 "<no client hardware address>");
1680 log_info("%s %s", msgbuf, piaddr(packet->client_addr));
1681
1682 /* fill dhcp4o6_response */
1683 packet->dhcp4o6_response->len = outgoing.packet_length;
1684 packet->dhcp4o6_response->buffer = NULL;
1685 if (!buffer_allocate(&packet->dhcp4o6_response->buffer,
1686 outgoing.packet_length, MDL)) {
1687 log_fatal("No memory to store DHCP4o6 reply.");
1688 }
1689 packet->dhcp4o6_response->data =
1690 packet->dhcp4o6_response->buffer->data;
1691 memcpy(packet->dhcp4o6_response->buffer->data,
1692 outgoing.raw, outgoing.packet_length);
1693
1694 /* done */
1695 if (subnet)
1696 subnet_dereference (&subnet, MDL);
1697 return;
1698 }
1699#endif
1700
e77892f5
TL
1701 /* Set up the common stuff... */
1702 to.sin_family = AF_INET;
1703#ifdef HAVE_SA_LEN
1704 to.sin_len = sizeof to;
1705#endif
1706 memset (to.sin_zero, 0, sizeof to.sin_zero);
1707
3496e9bc 1708 /* RFC2131 states the server SHOULD unicast to ciaddr.
88cd8aca 1709 * There are two wrinkles - relays, and when ciaddr is zero.
87a08ccc
DH
1710 * There's actually no mention of relays at all in rfc2131 in
1711 * regard to DHCPINFORM, except to say we might get packets from
1712 * clients via them. Note: relays unicast to clients to the
1713 * "yiaddr" address, which servers are forbidden to set when
1714 * answering an inform.
88cd8aca 1715 *
87a08ccc
DH
1716 * The solution: If ciaddr is zero, and giaddr is set, go via the
1717 * relay with the broadcast flag set to help the relay (with no
1718 * yiaddr and very likely no chaddr, it will have no idea where to
1719 * send the packet).
88cd8aca 1720 *
87a08ccc
DH
1721 * If the ciaddr is zero and giaddr is not set, go via the source
1722 * IP address (but you are permitted to barf on their shoes).
88cd8aca 1723 *
87a08ccc 1724 * If ciaddr is not zero, send the packet there always.
88cd8aca 1725 */
87a08ccc 1726 if (!raw.ciaddr.s_addr && gip.len) {
88cd8aca 1727 memcpy(&to.sin_addr, gip.iabuf, 4);
27058b3e 1728#if defined(RELAY_PORT)
563f0b8a 1729 to.sin_port = relay_port ? relay_port : local_port;
27058b3e
FD
1730#else
1731 to.sin_port = local_port;
1732#endif
87a08ccc 1733 raw.flags |= htons(BOOTP_BROADCAST);
88cd8aca 1734 } else {
87a08ccc 1735 gip.len = 0;
88cd8aca
DH
1736 memcpy(&to.sin_addr, cip.iabuf, 4);
1737 to.sin_port = remote_port;
1738 }
1739
1740 /* Report what we're sending. */
1741 snprintf(msgbuf, sizeof msgbuf, "DHCPACK to %s (%s) via", piaddr(cip),
1742 (packet->raw->htype && packet->raw->hlen) ?
1743 print_hw_addr(packet->raw->htype, packet->raw->hlen,
1744 packet->raw->chaddr) :
1745 "<no client hardware address>");
1746 log_info("%s %s", msgbuf, gip.len ? piaddr(gip) :
1747 packet->interface->name);
e77892f5
TL
1748
1749 errno = 0;
dd9237c3
TM
1750 interface = (fallback_interface ? fallback_interface
1751 : packet -> interface);
1752 result = send_packet(interface, &outgoing, &raw,
1753 outgoing.packet_length, from, &to, NULL);
1754 if (result < 0) {
1755 log_error ("%s:%d: Failed to send %d byte long packet over %s "
1756 "interface.", MDL, outgoing.packet_length,
1757 interface->name);
1758 }
1759
1760
20916cae
TL
1761 if (subnet)
1762 subnet_dereference (&subnet, MDL);
b88e8e15
TL
1763}
1764
e046c826
TM
1765/*!
1766 * \brief Constructs and sends a DHCP Nak
1767 *
1768 * In order to populate options such as dhcp-server-id and
1769 * dhcp-client-identifier, the function creates a temporary option cache
1770 * and evaluates options based on the packet's shared-network or the
1771 * network_group in its absence, as well as the packet->clasess (if any).
1772 *
1773 * \param packet inbound packet received from the client
1774 * \param cip address requested by the client
1775 * \param network_group optional scope for use in setting up options
1776 */
1777void nak_lease (packet, cip, network_group)
ed8bcd8f 1778 struct packet *packet;
a8b53b42 1779 struct iaddr *cip;
e046c826 1780 struct group *network_group; /* scope to use for options */
ed8bcd8f
TL
1781{
1782 struct sockaddr_in to;
4fbcd991 1783 struct in_addr from;
ed8bcd8f
TL
1784 int result;
1785 struct dhcp_packet raw;
1786 unsigned char nak = DHCPNAK;
1787 struct packet outgoing;
20916cae 1788 unsigned i;
27058b3e 1789#if defined(RELAY_PORT)
563f0b8a 1790 u_int16_t relay_port = 0;
27058b3e 1791#endif
951323fe 1792 struct option_state *options = (struct option_state *)0;
5d25508c 1793 struct option_cache *oc = (struct option_cache *)0;
e046c826 1794 struct option_state *eval_options = NULL;
ed8bcd8f 1795
4bd8800e 1796 option_state_allocate (&options, MDL);
ed8bcd8f
TL
1797 memset (&outgoing, 0, sizeof outgoing);
1798 memset (&raw, 0, sizeof raw);
1799 outgoing.raw = &raw;
1800
1801 /* Set DHCP_MESSAGE_TYPE to DHCPNAK */
4bd8800e 1802 if (!option_cache_allocate (&oc, MDL)) {
8ae2d595 1803 log_error ("No memory for DHCPNAK message type.");
4bd8800e 1804 option_state_dereference (&options, MDL);
5d25508c
TL
1805 return;
1806 }
d758ad8c
TL
1807 if (!make_const_data (&oc -> expression, &nak, sizeof nak,
1808 0, 0, MDL)) {
8ae2d595 1809 log_error ("No memory for expr_const expression.");
4bd8800e
TL
1810 option_cache_dereference (&oc, MDL);
1811 option_state_dereference (&options, MDL);
5d25508c
TL
1812 return;
1813 }
f7fdb216
DH
1814 i = DHO_DHCP_MESSAGE_TYPE;
1815 option_code_hash_lookup(&oc->option, dhcp_universe.code_hash,
1816 &i, 0, MDL);
951323fe 1817 save_option (&dhcp_universe, options, oc);
4bd8800e 1818 option_cache_dereference (&oc, MDL);
a5b21e16 1819
563f0b8a
FD
1820#if defined(RELAY_PORT)
1821 relay_port = dhcp_check_relayport(packet);
1822#endif
1823
b88e8e15 1824 /* Set DHCP_MESSAGE to whatever the message is */
4bd8800e 1825 if (!option_cache_allocate (&oc, MDL)) {
8ae2d595 1826 log_error ("No memory for DHCPNAK message type.");
4bd8800e 1827 option_state_dereference (&options, MDL);
5d25508c
TL
1828 return;
1829 }
1830 if (!make_const_data (&oc -> expression,
c5b0f529 1831 (unsigned char *)dhcp_message,
d758ad8c 1832 strlen (dhcp_message), 1, 0, MDL)) {
8ae2d595 1833 log_error ("No memory for expr_const expression.");
4bd8800e
TL
1834 option_cache_dereference (&oc, MDL);
1835 option_state_dereference (&options, MDL);
5d25508c
TL
1836 return;
1837 }
f7fdb216
DH
1838 i = DHO_DHCP_MESSAGE;
1839 option_code_hash_lookup(&oc->option, dhcp_universe.code_hash,
1840 &i, 0, MDL);
951323fe 1841 save_option (&dhcp_universe, options, oc);
4bd8800e 1842 option_cache_dereference (&oc, MDL);
d56788df 1843
e046c826
TM
1844 /* Setup the options at the global and subnet scopes. These
1845 * may be used to locate sever id option if enabled as well
1846 * for echo-client-id further on. (This allocates eval_options). */
1847 eval_network_statements(&eval_options, packet, network_group);
1848
f8380d3f 1849#if defined(SERVER_ID_FOR_NAK)
e046c826
TM
1850 /* Pass in the evaluated options so they can be searched for
1851 * server-id, otherwise source address comes from the interface
1852 * address. */
1853 get_server_source_address(&from, eval_options, options, packet);
f8380d3f 1854#else
e046c826 1855 /* Get server source address from the interface address */
f8380d3f 1856 get_server_source_address(&from, NULL, options, packet);
d56788df
SR
1857#endif /* if defined(SERVER_ID_FOR_NAK) */
1858
98311e4b 1859 /* If there were agent options in the incoming packet, return
02428754
DH
1860 * them. We do not check giaddr to detect the presence of a
1861 * relay, as this excludes "l2" relay agents which have no
1862 * giaddr to set.
1863 */
1864 if (packet->options->universe_count > agent_universe.index &&
1865 packet->options->universes [agent_universe.index]) {
98311e4b
DH
1866 option_chain_head_reference
1867 ((struct option_chain_head **)
1868 &(options -> universes [agent_universe.index]),
1869 (struct option_chain_head *)
1870 packet -> options -> universes [agent_universe.index],
1871 MDL);
1872 }
1873
e046c826
TM
1874 /* echo-client-id can specified at the class level so add class-scoped
1875 * options into eval_options. */
1876 for (i = packet->class_count; i > 0; i--) {
1877 execute_statements_in_scope(NULL, packet, NULL, NULL,
1878 packet->options, eval_options,
1879 &global_scope,
1880 packet->classes[i - 1]->group,
1881 NULL, NULL);
1882 }
1883
1884 /* Echo client id if we received and it's enabled */
1885 echo_client_id(packet, NULL, eval_options, options);
1886 option_state_dereference (&eval_options, MDL);
1887
b88e8e15 1888 /* Do not use the client's requested parameter list. */
951323fe 1889 delete_option (&dhcp_universe, packet -> options,
5d25508c 1890 DHO_DHCP_PARAMETER_REQUEST_LIST);
b88e8e15 1891
ed8bcd8f 1892 /* Set up the option buffer... */
a4cb16ca 1893 outgoing.packet_length =
da38df14 1894 cons_options (packet, outgoing.raw, (struct lease *)0,
9e383163 1895 (struct client_state *)0,
12c9957e 1896 0, packet -> options, options, &global_scope,
9030b313 1897 0, 0, 0, (struct data_string *)0, (char *)0);
4bd8800e 1898 option_state_dereference (&options, MDL);
ed8bcd8f 1899
b88e8e15 1900/* memset (&raw.ciaddr, 0, sizeof raw.ciaddr);*/
ed8bcd8f 1901 raw.giaddr = packet -> raw -> giaddr;
b88e8e15
TL
1902 memcpy (raw.chaddr, packet -> raw -> chaddr, sizeof raw.chaddr);
1903 raw.hlen = packet -> raw -> hlen;
1904 raw.htype = packet -> raw -> htype;
ed8bcd8f
TL
1905
1906 raw.xid = packet -> raw -> xid;
1907 raw.secs = packet -> raw -> secs;
b88e8e15 1908 raw.flags = packet -> raw -> flags | htons (BOOTP_BROADCAST);
ed8bcd8f
TL
1909 raw.hops = packet -> raw -> hops;
1910 raw.op = BOOTREPLY;
1911
785c1a51
FD
1912 /* Make sure that the packet is at least as big as a BOOTP packet. */
1913 if (outgoing.packet_length < BOOTP_MIN_LEN)
1914 outgoing.packet_length = BOOTP_MIN_LEN;
1915
7a049f2c 1916 /* Report what we're sending... */
785c1a51
FD
1917#if defined(DHCPv6) && defined(DHCP4o6)
1918 if (dhcpv4_over_dhcpv6 && (packet->dhcp4o6_response != NULL)) {
1919 log_info ("DHCP4o6 DHCPNAK on %s to %s via %s",
1920 piaddr (*cip),
1921 print_hw_addr (packet -> raw -> htype,
1922 packet -> raw -> hlen,
1923 packet -> raw -> chaddr),
1924 piaddr(packet->client_addr));
1925 } else
1926#endif
8ae2d595 1927 log_info ("DHCPNAK on %s to %s via %s",
7a049f2c
TL
1928 piaddr (*cip),
1929 print_hw_addr (packet -> raw -> htype,
1930 packet -> raw -> hlen,
a69f4fd3
TL
1931 packet -> raw -> chaddr),
1932 packet -> raw -> giaddr.s_addr
1933 ? inet_ntoa (packet -> raw -> giaddr)
1934 : packet -> interface -> name);
1935
7a049f2c
TL
1936#ifdef DEBUG_PACKET
1937 dump_packet (packet);
1938 dump_raw ((unsigned char *)packet -> raw, packet -> packet_length);
1939 dump_packet (&outgoing);
1940 dump_raw ((unsigned char *)&raw, outgoing.packet_length);
1941#endif
1942
785c1a51
FD
1943#if defined(DHCPv6) && defined(DHCP4o6)
1944 if (dhcpv4_over_dhcpv6 && (packet->dhcp4o6_response != NULL)) {
1945 /* fill dhcp4o6_response */
1946 packet->dhcp4o6_response->len = outgoing.packet_length;
1947 packet->dhcp4o6_response->buffer = NULL;
1948 if (!buffer_allocate(&packet->dhcp4o6_response->buffer,
1949 outgoing.packet_length, MDL)) {
1950 log_fatal("No memory to store DHCP4o6 reply.");
1951 }
1952 packet->dhcp4o6_response->data =
1953 packet->dhcp4o6_response->buffer->data;
1954 memcpy(packet->dhcp4o6_response->buffer->data,
1955 outgoing.raw, outgoing.packet_length);
1956 return;
1957 }
1958#endif
1959
7a049f2c
TL
1960 /* Set up the common stuff... */
1961 to.sin_family = AF_INET;
1962#ifdef HAVE_SA_LEN
1963 to.sin_len = sizeof to;
1964#endif
1965 memset (to.sin_zero, 0, sizeof to.sin_zero);
1966
b88e8e15
TL
1967 /* If this was gatewayed, send it back to the gateway.
1968 Otherwise, broadcast it on the local network. */
1969 if (raw.giaddr.s_addr) {
ed8bcd8f 1970 to.sin_addr = raw.giaddr;
bfe2d221 1971 if (raw.giaddr.s_addr != htonl (INADDR_LOOPBACK))
27058b3e 1972#if defined(RELAY_PORT)
563f0b8a 1973 to.sin_port = relay_port ? relay_port : local_port;
27058b3e
FD
1974#else
1975 to.sin_port = local_port;
1976#endif
1b871100
TL
1977 else
1978 to.sin_port = remote_port; /* for testing. */
7a049f2c 1979
027f46cb 1980 if (fallback_interface) {
3c941d42
DH
1981 result = send_packet(fallback_interface, packet, &raw,
1982 outgoing.packet_length, from, &to,
1983 NULL);
dd9237c3
TM
1984 if (result < 0) {
1985 log_error ("%s:%d: Failed to send %d byte long "
1986 "packet over %s interface.", MDL,
1987 outgoing.packet_length,
1988 fallback_interface->name);
1989 }
1990
027f46cb
TL
1991 return;
1992 }
b88e8e15 1993 } else {
71df44f5 1994 to.sin_addr = limited_broadcast;
44b2e3ad 1995 to.sin_port = remote_port;
b88e8e15 1996 }
ed8bcd8f 1997
ed8bcd8f 1998 errno = 0;
3c941d42
DH
1999 result = send_packet(packet->interface, packet, &raw,
2000 outgoing.packet_length, from, &to, NULL);
dd9237c3
TM
2001 if (result < 0) {
2002 log_error ("%s:%d: Failed to send %d byte long packet over %s "
2003 "interface.", MDL, outgoing.packet_length,
2004 packet->interface->name);
2005 }
2006
ed8bcd8f
TL
2007}
2008
e046c826
TM
2009/*!
2010 * \brief Adds a dhcp-client-id option to a set of options
2011 * Given a set of input options, it searches for echo-client-id. If it is
2012 * defined and enabled, the given packet is searched for dhcp-client-id. If
2013 * the option is found it is replicated into the given set of output options.
2014 * This allows us to provide compliance with RFC 6842. It is called when we ack
2015 * or nak a lease. In the latter case we may or may not have created the
2016 * requisite scope to lookup echo-client-id.
2017 *
2018 * Note the flag packet.sv_echo_client_id is set to reflect the configuration
2019 * option. This bypases inaccessiblity of server_universe in cons_options()
2020 * which must amend the PRL (when not empty) if echoing is enabled.
2021 *
2022 * \param packet inbound packet received from the client
2023 * \param lease lease associated with this client (if one)
2024 * \param in_options options in which to search for echo-client-id
2025 * \param out_options options to which to save the client-id
2026 */
2027void echo_client_id(packet, lease, in_options, out_options)
2028 struct packet *packet;
2029 struct lease *lease;
2030 struct option_state *in_options;
2031 struct option_state *out_options;
2032{
2033 struct option_cache *oc;
2034 int ignorep;
2035
2036 /* Check if echo-client-id is enabled */
2037 oc = lookup_option(&server_universe, in_options, SV_ECHO_CLIENT_ID);
2038 if (oc && evaluate_boolean_option_cache(&ignorep, packet, lease,
2039 NULL, packet->options,
2040 in_options,
2041 (lease ? &lease->scope : NULL),
2042 oc, MDL)) {
2043 struct data_string client_id;
2044 unsigned int opcode = DHO_DHCP_CLIENT_IDENTIFIER;
2045
2046 /* Save knowledge that echo is enabled to the packet */
2047 packet->sv_echo_client_id = ISC_TRUE;
2048
2049 /* Now see if inbound packet contains client-id */
2050 oc = lookup_option(&dhcp_universe, packet->options, opcode);
2051 memset(&client_id, 0, sizeof client_id);
2052 if (oc && evaluate_option_cache(&client_id,
2053 packet, NULL, NULL,
2054 packet->options, NULL,
2055 (lease ? &lease->scope : NULL),
2056 oc, MDL)) {
2057 /* Packet contained client-id, add it to out_options. */
2058 oc = NULL;
2059 if (option_cache_allocate(&oc, MDL)) {
2060 if (make_const_data(&oc->expression,
2061 client_id.data,
2062 client_id.len,
2063 1, 0, MDL)) {
2064 option_code_hash_lookup(&oc->option,
2065 dhcp_universe.
2066 code_hash,
2067 &opcode,
2068 0, MDL);
2069 save_option(&dhcp_universe,
2070 out_options, oc);
2071 }
2072 option_cache_dereference(&oc, MDL);
2073 }
2074 }
2075 }
2076}
2077
250f7134
SR
2078void check_pool_threshold (packet, lease, state)
2079 struct packet *packet;
2080 struct lease *lease;
2081 struct lease_state *state;
2082
2083{
2084
2085 struct pool *pool = lease->pool;
2086 int used, count, high_threshold, poolhigh = 0, poollow = 0;
2087 char *shared_name = "no name";
2088
2089 if (pool == NULL)
2090 return;
2091
2092 /* get a pointer to the name if we have one */
2093 if ((pool->shared_network != NULL) &&
2094 (pool->shared_network->name != NULL)) {
2095 shared_name = pool->shared_network->name;
2096 }
2097
2098 count = pool->lease_count;
2099 used = count - (pool->free_leases + pool->backup_leases);
2100
2101 /* The logged flag indicates if we have already crossed the high
2102 * threshold and emitted a log message. If it is set we check to
2103 * see if we have re-crossed the low threshold and need to reset
2104 * things. When we cross the high threshold we determine what
2105 * the low threshold is and save it into the low_threshold value.
2106 * When we cross that threshold we reset the logged flag and
2107 * the low_threshold to 0 which allows the high threshold message
2108 * to be emitted once again.
2109 * if we haven't recrossed the boundry we don't need to do anything.
2110 */
2111 if (pool->logged !=0) {
2112 if (used <= pool->low_threshold) {
2113 pool->low_threshold = 0;
2114 pool->logged = 0;
2115 log_error("Pool threshold reset - shared subnet: %s; "
2116 "address: %s; low threshold %d/%d.",
2117 shared_name, piaddr(lease->ip_addr),
2118 used, count);
2119 }
2120 return;
2121 }
2122
2123 /* find the high threshold */
2124 if (get_option_int(&poolhigh, &server_universe, packet, lease, NULL,
2125 packet->options, state->options, state->options,
2126 &lease->scope, SV_LOG_THRESHOLD_HIGH, MDL) == 0) {
2127 /* no threshold bail out */
2128 return;
2129 }
2130
2131 /* We do have a threshold for this pool, see if its valid */
2132 if ((poolhigh <= 0) || (poolhigh > 100)) {
2133 /* not valid */
2134 return;
2135 }
2136
2137 /* we have a valid value, have we exceeded it */
2138 high_threshold = FIND_PERCENT(count, poolhigh);
2139 if (used < high_threshold) {
2140 /* nope, no more to do */
2141 return;
2142 }
2143
2144 /* we've exceeded it, output a message */
2145 log_error("Pool threshold exceeded - shared subnet: %s; "
2146 "address: %s; high threshold %d%% %d/%d.",
2147 shared_name, piaddr(lease->ip_addr),
2148 poolhigh, used, count);
2149
2150 /* handle the low threshold now, if we don't
2151 * have a valid one we default to 0. */
2152 if ((get_option_int(&poollow, &server_universe, packet, lease, NULL,
2153 packet->options, state->options, state->options,
2154 &lease->scope, SV_LOG_THRESHOLD_LOW, MDL) == 0) ||
2155 (poollow > 100)) {
2156 poollow = 0;
2157 }
2158
2159 /*
2160 * If the low theshold is higher than the high threshold we continue to log
2161 * If it isn't then we set the flag saying we already logged and determine
2162 * what the reset threshold is.
2163 */
2164 if (poollow < poolhigh) {
2165 pool->logged = 1;
2166 pool->low_threshold = FIND_PERCENT(count, poollow);
2167 }
2168}
2169
c75473d8 2170void ack_lease (packet, lease, offer, when, msg, ms_nulltp, hp)
ed8bcd8f
TL
2171 struct packet *packet;
2172 struct lease *lease;
a7822eac 2173 unsigned int offer;
ed8bcd8f 2174 TIME when;
c4924529 2175 char *msg;
5bc2e1f2 2176 int ms_nulltp;
c75473d8 2177 struct host_decl *hp;
ed8bcd8f 2178{
20916cae 2179 struct lease *lt;
9cc3ad7f 2180 struct lease_state *state;
cb8176c4 2181 struct lease *next;
98311e4b 2182 struct host_decl *host = (struct host_decl *)0;
ed8bcd8f 2183 TIME lease_time;
4ecd2958 2184 TIME offered_lease_time;
b1dd98c9 2185 struct data_string d1;
eeea1395
TL
2186 TIME min_lease_time;
2187 TIME max_lease_time;
2188 TIME default_lease_time;
5d25508c 2189 struct option_cache *oc;
20916cae 2190 isc_result_t result;
a5b21e16 2191 TIME original_cltt;
6d103865 2192 struct in_addr from;
b1d3778c
DH
2193 TIME remaining_time;
2194 struct iaddr cip;
700e3fca 2195#if defined(DELAYED_ACK)
8cd88e20
SR
2196 /* By default we don't do the enqueue */
2197 isc_boolean_t enqueue = ISC_FALSE;
929a2364
TM
2198#endif
2199 int use_old_lease = 0;
a5b21e16 2200 int same_client = 0;
ed8bcd8f 2201
b1b7b521 2202 unsigned i, j;
28868515 2203 int s1;
19654922 2204 int ignorep;
b88e8e15 2205
9cc3ad7f 2206 /* If we're already acking this lease, don't do it again. */
c4924529 2207 if (lease -> state)
9cc3ad7f 2208 return;
9cc3ad7f 2209
6d103865 2210 /* Save original cltt for comparison later. */
a5b21e16 2211 original_cltt = lease->cltt;
6d103865 2212
98311e4b 2213 /* If the lease carries a host record, remember it. */
c75473d8
DH
2214 if (hp)
2215 host_reference (&host, hp, MDL);
2216 else if (lease -> host)
98311e4b
DH
2217 host_reference (&host, lease -> host, MDL);
2218
a52d8045 2219 /* Allocate a lease state structure... */
4bd8800e 2220 state = new_lease_state (MDL);
a52d8045 2221 if (!state)
8ae2d595 2222 log_fatal ("unable to allocate lease state!");
cdc336ab 2223 state -> got_requested_address = packet -> got_requested_address;
20916cae
TL
2224 shared_network_reference (&state -> shared_network,
2225 packet -> interface -> shared_network, MDL);
cdc336ab
TL
2226
2227 /* See if we got a server identifier option. */
2228 if (lookup_option (&dhcp_universe,
2229 packet -> options, DHO_DHCP_SERVER_IDENTIFIER))
2230 state -> got_server_identifier = 1;
a52d8045 2231
a1308b64 2232 maybe_return_agent_options(packet, state->options);
b1dd98c9 2233
d9eefc5d
TL
2234 /* If we are offering a lease that is still currently valid, preserve
2235 the events. We need to do this because if the client does not
2236 REQUEST our offer, it will expire in 2 minutes, overriding the
2237 expire time in the currently in force lease. We want the expire
2238 events to be executed at that point. */
a7341359 2239 if (lease->ends <= cur_time && offer != DHCPOFFER) {
d9eefc5d
TL
2240 /* Get rid of any old expiry or release statements - by
2241 executing the statements below, we will be inserting new
2242 ones if there are any to insert. */
a7341359
SR
2243 if (lease->on_star.on_expiry)
2244 executable_statement_dereference
2245 (&lease->on_star.on_expiry, MDL);
2246 if (lease->on_star.on_commit)
2247 executable_statement_dereference
2248 (&lease->on_star.on_commit, MDL);
2249 if (lease->on_star.on_release)
2250 executable_statement_dereference
2251 (&lease->on_star.on_release, MDL);
d9eefc5d 2252 }
ed2529e5 2253
10553ccb 2254 /* Execute statements in scope starting with the subnet scope. */
a7341359
SR
2255 execute_statements_in_scope (NULL, packet, lease,
2256 NULL, packet->options,
2257 state->options, &lease->scope,
2258 lease->subnet->group, NULL, NULL);
b1dd98c9 2259
10553ccb 2260 /* If the lease is from a pool, run the pool scope. */
a7341359
SR
2261 if (lease->pool)
2262 (execute_statements_in_scope(NULL, packet, lease, NULL,
2263 packet->options, state->options,
2264 &lease->scope, lease->pool->group,
2265 lease->pool->
2266 shared_network->group,
2267 NULL));
10553ccb
TL
2268
2269 /* Execute statements from class scopes. */
fa661adb 2270 for (i = packet -> class_count; i > 0; i--) {
a7341359
SR
2271 execute_statements_in_scope(NULL, packet, lease, NULL,
2272 packet->options, state->options,
2273 &lease->scope,
2274 packet->classes[i - 1]->group,
2275 (lease->pool ? lease->pool->group
2276 : lease->subnet->group),
2277 NULL);
b1dd98c9
TL
2278 }
2279
e8e6a30f
TL
2280 /* See if the client is only supposed to have one lease at a time,
2281 and if so, find its other leases and release them. We can only
2282 do this on DHCPREQUEST. It's a little weird to do this before
2283 looking at permissions, because the client might not actually
2284 _get_ a lease after we've done the permission check, but the
2285 assumption for this option is that the client has exactly one
2286 network interface, and will only ever remember one lease. So
2287 if it sends a DHCPREQUEST, and doesn't get the lease, it's already
2288 forgotten about its old lease, so we can too. */
3db5bf9c 2289 if (packet -> packet_type == DHCPREQUEST &&
e8e6a30f
TL
2290 (oc = lookup_option (&server_universe, state -> options,
2291 SV_ONE_LEASE_PER_CLIENT)) &&
19654922 2292 evaluate_boolean_option_cache (&ignorep,
9e383163
TL
2293 packet, lease,
2294 (struct client_state *)0,
2295 packet -> options,
12c9957e
TL
2296 state -> options, &lease -> scope,
2297 oc, MDL)) {
d758ad8c
TL
2298 struct lease *seek;
2299 if (lease -> uid_len) {
2300 do {
2301 seek = (struct lease *)0;
2302 find_lease_by_uid (&seek, lease -> uid,
2303 lease -> uid_len, MDL);
2304 if (!seek)
2305 break;
2306 if (seek == lease && !seek -> n_uid) {
2307 lease_dereference (&seek, MDL);
2308 break;
2309 }
2310 next = (struct lease *)0;
2311
2312 /* Don't release expired leases, and don't
2313 release the lease we're going to assign. */
2314 next = (struct lease *)0;
2315 while (seek) {
2316 if (seek -> n_uid)
2317 lease_reference (&next, seek -> n_uid, MDL);
2318 if (seek != lease &&
2319 seek -> binding_state != FTS_RELEASED &&
2320 seek -> binding_state != FTS_EXPIRED &&
2321 seek -> binding_state != FTS_RESET &&
2322 seek -> binding_state != FTS_FREE &&
2323 seek -> binding_state != FTS_BACKUP)
2324 break;
2325 lease_dereference (&seek, MDL);
2326 if (next) {
2327 lease_reference (&seek, next, MDL);
2328 lease_dereference (&next, MDL);
2329 }
2330 }
2331 if (next)
2332 lease_dereference (&next, MDL);
2333 if (seek) {
2334 release_lease (seek, packet);
2335 lease_dereference (&seek, MDL);
2336 } else
2337 break;
2338 } while (1);
2339 }
2340 if (!lease -> uid_len ||
98311e4b
DH
2341 (host &&
2342 !host -> client_identifier.len &&
d758ad8c
TL
2343 (oc = lookup_option (&server_universe, state -> options,
2344 SV_DUPLICATES)) &&
2345 !evaluate_boolean_option_cache (&ignorep, packet, lease,
2346 (struct client_state *)0,
2347 packet -> options,
2348 state -> options,
2349 &lease -> scope,
2350 oc, MDL))) {
2351 do {
2352 seek = (struct lease *)0;
2353 find_lease_by_hw_addr
2354 (&seek, lease -> hardware_addr.hbuf,
2355 lease -> hardware_addr.hlen, MDL);
2356 if (!seek)
2357 break;
2358 if (seek == lease && !seek -> n_hw) {
2359 lease_dereference (&seek, MDL);
2360 break;
2361 }
2362 next = (struct lease *)0;
2363 while (seek) {
2364 if (seek -> n_hw)
2365 lease_reference (&next, seek -> n_hw, MDL);
2366 if (seek != lease &&
2367 seek -> binding_state != FTS_RELEASED &&
2368 seek -> binding_state != FTS_EXPIRED &&
2369 seek -> binding_state != FTS_RESET &&
2370 seek -> binding_state != FTS_FREE &&
2371 seek -> binding_state != FTS_BACKUP)
2372 break;
2373 lease_dereference (&seek, MDL);
2374 if (next) {
2375 lease_reference (&seek, next, MDL);
2376 lease_dereference (&next, MDL);
2377 }
2378 }
2379 if (next)
2380 lease_dereference (&next, MDL);
2381 if (seek) {
2382 release_lease (seek, packet);
2383 lease_dereference (&seek, MDL);
2384 } else
2385 break;
2386 } while (1);
2387 }
e8e6a30f 2388 }
a5b21e16 2389
e8e6a30f 2390
b1dd98c9
TL
2391 /* Make sure this packet satisfies the configured minimum
2392 number of seconds. */
d73e855d 2393 memset (&d1, 0, sizeof d1);
2540af04 2394 if (offer == DHCPOFFER &&
951323fe 2395 (oc = lookup_option (&server_universe, state -> options,
5d25508c 2396 SV_MIN_SECS))) {
ca1c700e 2397 if (evaluate_option_cache (&d1, packet, lease,
9e383163 2398 (struct client_state *)0,
ca1c700e 2399 packet -> options, state -> options,
12c9957e 2400 &lease -> scope, oc, MDL)) {
6c608437
TL
2401 if (d1.len &&
2402 ntohs (packet -> raw -> secs) < d1.data [0]) {
00638355
DH
2403 log_info("%s: configured min-secs value (%d) "
2404 "is greater than secs field (%d). "
2405 "message dropped.", msg, d1.data[0],
2406 ntohs(packet->raw->secs));
4bd8800e
TL
2407 data_string_forget (&d1, MDL);
2408 free_lease_state (state, MDL);
98311e4b
DH
2409 if (host)
2410 host_dereference (&host, MDL);
5d25508c
TL
2411 return;
2412 }
4bd8800e 2413 data_string_forget (&d1, MDL);
5d25508c
TL
2414 }
2415 }
2416
98311e4b
DH
2417 /* Try to find a matching host declaration for this lease.
2418 */
2419 if (!host) {
007e3ee4
TL
2420 struct host_decl *hp = (struct host_decl *)0;
2421 struct host_decl *h;
5d25508c
TL
2422
2423 /* Try to find a host_decl that matches the client
2424 identifier or hardware address on the packet, and
2425 has no fixed IP address. If there is one, hang
2426 it off the lease so that its option definitions
2427 can be used. */
951323fe 2428 oc = lookup_option (&dhcp_universe, packet -> options,
5d25508c
TL
2429 DHO_DHCP_CLIENT_IDENTIFIER);
2430 if (oc &&
ca1c700e 2431 evaluate_option_cache (&d1, packet, lease,
9e383163 2432 (struct client_state *)0,
ca1c700e 2433 packet -> options, state -> options,
12c9957e 2434 &lease -> scope, oc, MDL)) {
20916cae 2435 find_hosts_by_uid (&hp, d1.data, d1.len, MDL);
4bd8800e 2436 data_string_forget (&d1, MDL);
98311e4b
DH
2437 for (h = hp; h; h = h -> n_ipaddr) {
2438 if (!h -> fixed_addr)
2439 break;
2440 }
2441 if (h)
2442 host_reference (&host, h, MDL);
95f5d38c
DH
2443 if (hp != NULL)
2444 host_dereference(&hp, MDL);
007e3ee4 2445 }
98311e4b 2446 if (!host) {
007e3ee4
TL
2447 find_hosts_by_haddr (&hp,
2448 packet -> raw -> htype,
2449 packet -> raw -> chaddr,
2450 packet -> raw -> hlen,
2451 MDL);
20916cae
TL
2452 for (h = hp; h; h = h -> n_ipaddr) {
2453 if (!h -> fixed_addr)
5d25508c
TL
2454 break;
2455 }
20916cae 2456 if (h)
98311e4b 2457 host_reference (&host, h, MDL);
95f5d38c
DH
2458 if (hp != NULL)
2459 host_dereference(&hp, MDL);
007e3ee4 2460 }
bd0b98c1 2461 if (!host) {
a7341359
SR
2462 find_hosts_by_option(&hp, packet,
2463 packet->options, MDL);
bd0b98c1
SR
2464 for (h = hp; h; h = h -> n_ipaddr) {
2465 if (!h -> fixed_addr)
2466 break;
2467 }
2468 if (h)
2469 host_reference (&host, h, MDL);
2470 if (hp != NULL)
2471 host_dereference(&hp, MDL);
2472 }
b1dd98c9
TL
2473 }
2474
98311e4b 2475 /* If we have a host_decl structure, run the options associated
a55ccdd0 2476 with its group. Whether the host decl struct is old or not. */
98311e4b 2477 if (host)
a7341359
SR
2478 execute_statements_in_scope (NULL, packet, lease, NULL,
2479 packet->options, state->options,
2480 &lease->scope, host->group,
2481 (lease->pool
2482 ? lease->pool->group
2483 : lease->subnet->group),
2484 NULL);
98311e4b 2485
ddb4c2ac
TL
2486 /* Drop the request if it's not allowed for this client. By
2487 default, unknown clients are allowed. */
98311e4b 2488 if (!host &&
951323fe 2489 (oc = lookup_option (&server_universe, state -> options,
ddb4c2ac 2490 SV_BOOT_UNKNOWN_CLIENTS)) &&
19654922 2491 !evaluate_boolean_option_cache (&ignorep,
9e383163
TL
2492 packet, lease,
2493 (struct client_state *)0,
2494 packet -> options,
12c9957e
TL
2495 state -> options,
2496 &lease -> scope, oc, MDL)) {
19654922
TL
2497 if (!ignorep)
2498 log_info ("%s: unknown client", msg);
4bd8800e 2499 free_lease_state (state, MDL);
98311e4b
DH
2500 if (host)
2501 host_dereference (&host, MDL);
ddb4c2ac 2502 return;
a5b21e16 2503 }
b1dd98c9
TL
2504
2505 /* Drop the request if it's not allowed for this client. */
2506 if (!offer &&
951323fe 2507 (oc = lookup_option (&server_universe, state -> options,
ddb4c2ac 2508 SV_ALLOW_BOOTP)) &&
19654922 2509 !evaluate_boolean_option_cache (&ignorep,
9e383163
TL
2510 packet, lease,
2511 (struct client_state *)0,
2512 packet -> options,
12c9957e
TL
2513 state -> options,
2514 &lease -> scope, oc, MDL)) {
19654922
TL
2515 if (!ignorep)
2516 log_info ("%s: bootp disallowed", msg);
4bd8800e 2517 free_lease_state (state, MDL);
98311e4b
DH
2518 if (host)
2519 host_dereference (&host, MDL);
ddb4c2ac 2520 return;
a5b21e16 2521 }
b1dd98c9 2522
5d25508c 2523 /* Drop the request if booting is specifically denied. */
951323fe
TL
2524 oc = lookup_option (&server_universe, state -> options,
2525 SV_ALLOW_BOOTING);
5d25508c 2526 if (oc &&
19654922 2527 !evaluate_boolean_option_cache (&ignorep,
9e383163
TL
2528 packet, lease,
2529 (struct client_state *)0,
2530 packet -> options,
12c9957e
TL
2531 state -> options,
2532 &lease -> scope, oc, MDL)) {
19654922 2533 if (!ignorep)
8ae2d595 2534 log_info ("%s: booting disallowed", msg);
4bd8800e 2535 free_lease_state (state, MDL);
98311e4b
DH
2536 if (host)
2537 host_dereference (&host, MDL);
19654922 2538 return;
b1dd98c9
TL
2539 }
2540
c4924529 2541 /* If we are configured to do per-class billing, do it. */
3acf1dca 2542 if (have_billing_classes && !(lease -> flags & STATIC_LEASE)) {
c4924529
TL
2543 /* See if the lease is currently being billed to a
2544 class, and if so, whether or not it can continue to
2545 be billed to that class. */
2546 if (lease -> billing_class) {
2547 for (i = 0; i < packet -> class_count; i++)
2548 if (packet -> classes [i] ==
2549 lease -> billing_class)
2550 break;
f3a44c10 2551 if (i == packet -> class_count) {
6a39bcf0 2552 unbill_class(lease);
f3a44c10
TM
2553 /* Active lease billing change negates reuse */
2554 if (lease->binding_state == FTS_ACTIVE) {
2555 lease->cannot_reuse = 1;
2556 }
2557 }
c4924529 2558 }
65cf86d7 2559
c4924529
TL
2560 /* If we don't have an active billing, see if we need
2561 one, and if we do, try to do so. */
65cf86d7 2562 if (lease->billing_class == NULL) {
6980ae03 2563 char *cname = "";
65cf86d7 2564 int bill = 0;
6980ae03 2565
65cf86d7 2566 for (i = 0; i < packet->class_count; i++) {
fce94f06 2567 struct class *billclass, *superclass;
6980ae03
SR
2568
2569 billclass = packet->classes[i];
2570 if (billclass->lease_limit) {
65cf86d7 2571 bill++;
6980ae03 2572 if (bill_class(lease, billclass))
c4924529 2573 break;
6980ae03 2574
fce94f06
TM
2575 superclass = billclass->superclass;
2576 if (superclass != NULL)
2577 cname = superclass->name;
6980ae03
SR
2578 else
2579 cname = billclass->name;
c4924529
TL
2580 }
2581 }
65cf86d7
EH
2582 if (bill != 0 && i == packet->class_count) {
2583 log_info("%s: no available billing: lease "
2584 "limit reached in all matching "
6980ae03 2585 "classes (last: '%s')", msg, cname);
65cf86d7
EH
2586 free_lease_state(state, MDL);
2587 if (host)
2588 host_dereference(&host, MDL);
2589 return;
2590 }
1b2ab55f 2591
6980ae03
SR
2592 /*
2593 * If this is an offer, undo the billing. We go
1b2ab55f
DH
2594 * through all the steps above to bill a class so
2595 * we can hit the 'no available billing' mark and
2596 * abort without offering. But it just doesn't make
2597 * sense to permanently bill a class for a non-active
2598 * lease. This means on REQUEST, we will bill this
2599 * lease again (if there is a REQUEST).
2600 */
2601 if (offer == DHCPOFFER &&
2602 lease->billing_class != NULL &&
c36d062e 2603 lease->binding_state != FTS_ACTIVE)
6a39bcf0 2604 unbill_class(lease);
f3a44c10
TM
2605
2606 /* Lease billing change negates reuse */
2607 if (lease->billing_class != NULL) {
2608 lease->cannot_reuse = 1;
2609 }
c4924529
TL
2610 }
2611 }
2612
b1dd98c9 2613 /* Figure out the filename. */
951323fe 2614 oc = lookup_option (&server_universe, state -> options, SV_FILENAME);
5d25508c 2615 if (oc)
ca1c700e 2616 evaluate_option_cache (&state -> filename, packet, lease,
9e383163 2617 (struct client_state *)0,
ca1c700e 2618 packet -> options, state -> options,
12c9957e 2619 &lease -> scope, oc, MDL);
ed8bcd8f 2620
7a049f2c 2621 /* Choose a server name as above. */
951323fe
TL
2622 oc = lookup_option (&server_universe, state -> options,
2623 SV_SERVER_NAME);
5d25508c 2624 if (oc)
ca1c700e 2625 evaluate_option_cache (&state -> server_name, packet, lease,
9e383163 2626 (struct client_state *)0,
ca1c700e 2627 packet -> options, state -> options,
12c9957e 2628 &lease -> scope, oc, MDL);
7a049f2c 2629
97ca1699
TL
2630 /* At this point, we have a lease that we can offer the client.
2631 Now we construct a lease structure that contains what we want,
2632 and call supersede_lease to do the right thing with it. */
20916cae
TL
2633 lt = (struct lease *)0;
2634 result = lease_allocate (&lt, MDL);
2635 if (result != ISC_R_SUCCESS) {
2636 log_info ("%s: can't allocate temporary lease structure: %s",
2637 msg, isc_result_totext (result));
2638 free_lease_state (state, MDL);
98311e4b
DH
2639 if (host)
2640 host_dereference (&host, MDL);
20916cae
TL
2641 return;
2642 }
a5b21e16 2643
97ca1699
TL
2644 /* Use the ip address of the lease that we finally found in
2645 the database. */
20916cae 2646 lt -> ip_addr = lease -> ip_addr;
97ca1699
TL
2647
2648 /* Start now. */
20916cae 2649 lt -> starts = cur_time;
97ca1699 2650
7a049f2c
TL
2651 /* Figure out how long a lease to assign. If this is a
2652 dynamic BOOTP lease, its duration must be infinite. */
2653 if (offer) {
a55ccdd0
DH
2654 lt->flags &= ~BOOTP_LEASE;
2655
eeea1395 2656 default_lease_time = DEFAULT_DEFAULT_LEASE_TIME;
951323fe 2657 if ((oc = lookup_option (&server_universe, state -> options,
eeea1395 2658 SV_DEFAULT_LEASE_TIME))) {
ca1c700e 2659 if (evaluate_option_cache (&d1, packet, lease,
9e383163 2660 (struct client_state *)0,
da38df14 2661 packet -> options,
12c9957e
TL
2662 state -> options,
2663 &lease -> scope, oc, MDL)) {
eeea1395
TL
2664 if (d1.len == sizeof (u_int32_t))
2665 default_lease_time =
2666 getULong (d1.data);
4bd8800e 2667 data_string_forget (&d1, MDL);
eeea1395
TL
2668 }
2669 }
2670
951323fe 2671 if ((oc = lookup_option (&dhcp_universe, packet -> options,
1ffcdd2a 2672 DHO_DHCP_LEASE_TIME)))
ca1c700e 2673 s1 = evaluate_option_cache (&d1, packet, lease,
9e383163 2674 (struct client_state *)0,
da38df14 2675 packet -> options,
12c9957e
TL
2676 state -> options,
2677 &lease -> scope, oc, MDL);
1ffcdd2a
TL
2678 else
2679 s1 = 0;
98311e4b 2680
a55ccdd0
DH
2681 if (s1 && (d1.len == 4)) {
2682 u_int32_t ones = 0xffffffff;
2683
2684 /* One potential use of reserved leases is to allow
2685 * clients to signal reservation of their lease. They
2686 * can kinda sorta do this, if you squint hard enough,
2687 * by supplying an 'infinite' requested-lease-time
2688 * option. This is generally bad practice...you want
2689 * clients to return to the server on at least some
2690 * period (days, months, years) to get up-to-date
2691 * config state. So;
2692 *
2693 * 1) A client requests 0xffffffff lease-time.
2694 * 2) The server reserves the lease, and assigns a
2695 * <= max_lease_time lease-time to the client, which
2696 * we presume is much smaller than 0xffffffff.
2697 * 3) The client ultimately fails to renew its lease
2698 * (all clients go offline at some point).
2699 * 4) The server retains the reservation, although
2700 * the lease expires and passes through those states
2701 * as normal, it's placed in the 'reserved' queue,
2702 * and is under no circumstances allocated to any
2703 * clients.
2704 *
2705 * Whether the client knows its reserving its lease or
2706 * not, this can be a handy tool for a sysadmin.
2707 */
2708 if ((memcmp(d1.data, &ones, 4) == 0) &&
2709 (oc = lookup_option(&server_universe,
2710 state->options,
2711 SV_RESERVE_INFINITE)) &&
2712 evaluate_boolean_option_cache(&ignorep, packet,
2713 lease, NULL, packet->options,
2714 state->options, &lease->scope,
2715 oc, MDL)) {
2716 lt->flags |= RESERVED_LEASE;
2717 if (!ignorep)
2718 log_info("Infinite-leasetime "
2719 "reservation made on %s.",
2720 piaddr(lt->ip_addr));
2721 }
2722
5d25508c 2723 lease_time = getULong (d1.data);
a55ccdd0 2724 } else
eeea1395 2725 lease_time = default_lease_time;
a55ccdd0
DH
2726
2727 if (s1)
2728 data_string_forget(&d1, MDL);
98311e4b 2729
daa1b24f
TL
2730 /* See if there's a maximum lease time. */
2731 max_lease_time = DEFAULT_MAX_LEASE_TIME;
2732 if ((oc = lookup_option (&server_universe, state -> options,
2733 SV_MAX_LEASE_TIME))) {
ca1c700e 2734 if (evaluate_option_cache (&d1, packet, lease,
9e383163 2735 (struct client_state *)0,
daa1b24f 2736 packet -> options,
12c9957e
TL
2737 state -> options,
2738 &lease -> scope, oc, MDL)) {
daa1b24f
TL
2739 if (d1.len == sizeof (u_int32_t))
2740 max_lease_time =
2741 getULong (d1.data);
4bd8800e 2742 data_string_forget (&d1, MDL);
daa1b24f
TL
2743 }
2744 }
2745
10553ccb 2746 /* Enforce the maximum lease length. */
daa1b24f
TL
2747 if (lease_time < 0 /* XXX */
2748 || lease_time > max_lease_time)
10553ccb 2749 lease_time = max_lease_time;
a5b21e16 2750
eeea1395 2751 min_lease_time = DEFAULT_MIN_LEASE_TIME;
00855426
TL
2752 if (min_lease_time > max_lease_time)
2753 min_lease_time = max_lease_time;
2754
951323fe 2755 if ((oc = lookup_option (&server_universe, state -> options,
5d25508c 2756 SV_MIN_LEASE_TIME))) {
ca1c700e 2757 if (evaluate_option_cache (&d1, packet, lease,
9e383163 2758 (struct client_state *)0,
da38df14 2759 packet -> options,
12c9957e
TL
2760 state -> options,
2761 &lease -> scope, oc, MDL)) {
5d25508c 2762 if (d1.len == sizeof (u_int32_t))
eeea1395 2763 min_lease_time = getULong (d1.data);
4bd8800e 2764 data_string_forget (&d1, MDL);
5d25508c 2765 }
421563ea
TL
2766 }
2767
b22de500
DH
2768 /* CC: If there are less than
2769 adaptive-lease-time-threshold % free leases,
2770 hand out only short term leases */
2771
2772 memset(&d1, 0, sizeof(d1));
2773 if (lease->pool &&
2774 (oc = lookup_option(&server_universe, state->options,
2775 SV_ADAPTIVE_LEASE_TIME_THRESHOLD)) &&
2776 evaluate_option_cache(&d1, packet, lease, NULL,
2777 packet->options, state->options,
2778 &lease->scope, oc, MDL)) {
2779 if (d1.len == 1 && d1.data[0] > 0 &&
2780 d1.data[0] < 100) {
2781 TIME adaptive_time;
2782 int poolfilled, total, count;
2783
2784 if (min_lease_time)
2785 adaptive_time = min_lease_time;
2786 else
2787 adaptive_time = DEFAULT_MIN_LEASE_TIME;
2788
2789 /* Allow the client to keep its lease. */
2790 if (lease->ends - cur_time > adaptive_time)
2791 adaptive_time = lease->ends - cur_time;
2792
2793 count = lease->pool->lease_count;
2794 total = count - (lease->pool->free_leases +
2795 lease->pool->backup_leases);
2796
2797 poolfilled = (total > (INT_MAX / 100)) ?
2798 total / (count / 100) :
2799 (total * 100) / count;
2800
2801 log_debug("Adap-lease: Total: %d, Free: %d, "
2802 "Ends: %d, Adaptive: %d, Fill: %d, "
2803 "Threshold: %d",
2804 lease->pool->lease_count,
2805 lease->pool->free_leases,
2806 (int)(lease->ends - cur_time),
2807 (int)adaptive_time, poolfilled,
2808 d1.data[0]);
2809
2810 if (poolfilled >= d1.data[0] &&
2811 lease_time > adaptive_time) {
2812 log_info("Pool over threshold, time "
2813 "for %s reduced from %d to "
2814 "%d.", piaddr(lease->ip_addr),
2815 (int)lease_time,
2816 (int)adaptive_time);
2817
2818 lease_time = adaptive_time;
2819 }
2820 }
2821 data_string_forget(&d1, MDL);
2822 }
2823
250f7134
SR
2824
2825 /*
2826 * If this is an ack check to see if we have used enough of
2827 * the pool to want to log a message
2828 */
2829 if (offer == DHCPACK)
2830 check_pool_threshold(packet, lease, state);
2831
b1d3778c 2832 /* a client requests an address which is not yet active*/
a5b21e16 2833 if (lease->pool && lease->pool->valid_from &&
b1d3778c
DH
2834 cur_time < lease->pool->valid_from) {
2835 /* NAK leases before pool activation date */
2836 cip.len = 4;
2837 memcpy (cip.iabuf, &lt->ip_addr.iabuf, 4);
e046c826 2838 nak_lease(packet, &cip, lease->subnet->group);
b1d3778c
DH
2839 free_lease_state (state, MDL);
2840 lease_dereference (&lt, MDL);
2841 if (host)
2842 host_dereference (&host, MDL);
2843 return;
a5b21e16 2844
b1d3778c
DH
2845 }
2846
2847 /* CC:
2848 a) NAK current lease if past the expiration date
2849 b) extend lease only up to the expiration date, but not
2850 below min-lease-time
2851 Setting min-lease-time is essential for this to work!
250f7134 2852 The value of min-lease-time determines the length
b1d3778c
DH
2853 of the transition window:
2854 A client renewing a second before the deadline will
2855 get a min-lease-time lease. Since the current ip might not
2856 be routable after the deadline, the client will
2857 be offline until it DISCOVERS again. Otherwise it will
2858 receive a NAK at T/2.
2859 A min-lease-time of 6 seconds effectively switches over
2860 all clients in this pool very quickly.
2861 */
a5b21e16 2862
b1d3778c
DH
2863 if (lease->pool && lease->pool->valid_until) {
2864 if (cur_time >= lease->pool->valid_until) {
2865 /* NAK leases after pool expiration date */
2866 cip.len = 4;
2867 memcpy (cip.iabuf, &lt->ip_addr.iabuf, 4);
e046c826 2868 nak_lease(packet, &cip, lease->subnet->group);
b1d3778c
DH
2869 free_lease_state (state, MDL);
2870 lease_dereference (&lt, MDL);
2871 if (host)
2872 host_dereference (&host, MDL);
2873 return;
2874 }
2875 remaining_time = lease->pool->valid_until - cur_time;
2876 if (lease_time > remaining_time)
2877 lease_time = remaining_time;
2878 }
a5b21e16 2879
eeea1395
TL
2880 if (lease_time < min_lease_time) {
2881 if (min_lease_time)
2882 lease_time = min_lease_time;
2883 else
2884 lease_time = default_lease_time;
2885 }
b1dd98c9 2886
b1d3778c 2887
2cbc0e48
TL
2888#if defined (FAILOVER_PROTOCOL)
2889 /* Okay, we know the lease duration. Now check the
2890 failover state, if any. */
20916cae 2891 if (lease -> pool && lease -> pool -> failover_peer) {
88cd8aca 2892 TIME new_lease_time = lease_time;
2cbc0e48
TL
2893 dhcp_failover_state_t *peer =
2894 lease -> pool -> failover_peer;
2895
88cd8aca
DH
2896 /* Copy previous lease failover ack-state. */
2897 lt->tsfp = lease->tsfp;
2898 lt->atsfp = lease->atsfp;
2899
6d103865 2900 /* cltt set below */
88cd8aca
DH
2901
2902 /* Lease times less than MCLT are not a concern. */
2903 if (lease_time > peer->mclt) {
2904 /* Each server can only offer a lease time
2905 * that is either equal to MCLT (at least),
2906 * or up to TSFP+MCLT. Only if the desired
2907 * lease time falls within TSFP+MCLT, can
2908 * the server allow it.
2909 */
2910 if (lt->tsfp <= cur_time)
2911 new_lease_time = peer->mclt;
2912 else if ((cur_time + lease_time) >
2913 (lt->tsfp + peer->mclt))
2914 new_lease_time = (lt->tsfp - cur_time)
2915 + peer->mclt;
2cbc0e48 2916 }
5b01171a 2917
88cd8aca 2918 /* Update potential expiry. Allow for the desired
98bd7ca0 2919 * lease time plus one half the actual (whether
88cd8aca
DH
2920 * modified downward or not) lease time, which is
2921 * actually an estimate of when the client will
2922 * renew. This way, the client will be able to get
2923 * the desired lease time upon renewal.
2924 */
2925 if (offer == DHCPACK) {
68507137
TM
2926 if (lease_time == INFINITE_TIME) {
2927 lt->tstp = MAX_TIME;
2928 } else {
2929 lt->tstp =
2930 leaseTimeCheck(
2931 (cur_time + lease_time
2932 + (new_lease_time / 2)),
2933 MAX_TIME - 1);
2934 }
88cd8aca
DH
2935
2936 /* If we reduced the potential expiry time,
2937 * make sure we don't offer an old-expiry-time
2938 * lease for this lease before the change is
2939 * ack'd.
2940 */
2941 if (lt->tstp < lt->tsfp)
2942 lt->tsfp = lt->tstp;
2943 } else
2944 lt->tstp = lease->tstp;
2945
2946 /* Use failover-modified lease time. */
2947 lease_time = new_lease_time;
2cbc0e48
TL
2948 }
2949#endif /* FAILOVER_PROTOCOL */
2950
68507137
TM
2951 if (lease_time == INFINITE_TIME) {
2952 state->offered_expiry = MAX_TIME;
2953 } else {
2954 /* If the lease duration causes the time value to wrap,
2955 use the maximum expiry time. */
2956 state->offered_expiry
2957 = leaseTimeCheck(cur_time + lease_time,
2958 MAX_TIME - 1);
2959 }
2960
7a049f2c 2961 if (when)
20916cae 2962 lt -> ends = when;
7a049f2c 2963 else
20916cae 2964 lt -> ends = state -> offered_expiry;
d758ad8c
TL
2965
2966 /* Don't make lease active until we actually get a
2967 DHCPREQUEST. */
2968 if (offer == DHCPACK)
2969 lt -> next_binding_state = FTS_ACTIVE;
2970 else
2971 lt -> next_binding_state = lease -> binding_state;
7a049f2c 2972 } else {
a55ccdd0
DH
2973 lt->flags |= BOOTP_LEASE;
2974
b1dd98c9
TL
2975 lease_time = MAX_TIME - cur_time;
2976
951323fe 2977 if ((oc = lookup_option (&server_universe, state -> options,
5d25508c 2978 SV_BOOTP_LEASE_LENGTH))) {
ca1c700e 2979 if (evaluate_option_cache (&d1, packet, lease,
9e383163 2980 (struct client_state *)0,
ca1c700e
TL
2981 packet -> options,
2982 state -> options,
12c9957e 2983 &lease -> scope, oc, MDL)) {
5d25508c
TL
2984 if (d1.len == sizeof (u_int32_t))
2985 lease_time = getULong (d1.data);
4bd8800e 2986 data_string_forget (&d1, MDL);
5d25508c 2987 }
b1dd98c9
TL
2988 }
2989
951323fe 2990 if ((oc = lookup_option (&server_universe, state -> options,
5d25508c 2991 SV_BOOTP_LEASE_CUTOFF))) {
ca1c700e 2992 if (evaluate_option_cache (&d1, packet, lease,
9e383163 2993 (struct client_state *)0,
da38df14 2994 packet -> options,
ca1c700e 2995 state -> options,
12c9957e 2996 &lease -> scope, oc, MDL)) {
5d25508c
TL
2997 if (d1.len == sizeof (u_int32_t))
2998 lease_time = (getULong (d1.data) -
2999 cur_time);
4bd8800e 3000 data_string_forget (&d1, MDL);
5d25508c 3001 }
b1dd98c9
TL
3002 }
3003
20916cae 3004 lt -> ends = state -> offered_expiry = cur_time + lease_time;
98311e4b 3005 lt -> next_binding_state = FTS_ACTIVE;
7a049f2c 3006 }
97ca1699 3007
6d103865
SK
3008 /* Update Client Last Transaction Time. */
3009 lt->cltt = cur_time;
97ca1699 3010
38ee81bd
SR
3011 /* See if we want to record the uid for this client */
3012 oc = lookup_option(&server_universe, state->options,
3013 SV_IGNORE_CLIENT_UIDS);
3014 if ((oc == NULL) ||
3015 !evaluate_boolean_option_cache(&ignorep, packet, lease, NULL,
3016 packet->options, state->options,
3017 &lease->scope, oc, MDL)) {
a5b21e16 3018
38ee81bd
SR
3019 /* Record the uid, if given... */
3020 oc = lookup_option (&dhcp_universe, packet -> options,
3021 DHO_DHCP_CLIENT_IDENTIFIER);
3022 if (oc &&
3023 evaluate_option_cache(&d1, packet, lease, NULL,
3024 packet->options, state->options,
3025 &lease->scope, oc, MDL)) {
3026 if (d1.len <= sizeof(lt->uid_buf)) {
3027 memcpy(lt->uid_buf, d1.data, d1.len);
3028 lt->uid = lt->uid_buf;
3029 lt->uid_max = sizeof(lt->uid_buf);
3030 lt->uid_len = d1.len;
3031 } else {
3032 unsigned char *tuid;
3033 lt->uid_max = d1.len;
3034 lt->uid_len = d1.len;
3035 tuid = (unsigned char *)dmalloc(lt->uid_max,
3036 MDL);
3037 /* XXX inelegant */
3038 if (!tuid)
3039 log_fatal ("no memory for large uid.");
3040 memcpy(tuid, d1.data, lt->uid_len);
3041 lt->uid = tuid;
3042 }
3043 data_string_forget (&d1, MDL);
11b37280 3044 }
97ca1699
TL
3045 }
3046
98311e4b
DH
3047 if (host) {
3048 host_reference (&lt -> host, host, MDL);
3049 host_dereference (&host, MDL);
3050 }
20916cae
TL
3051 if (lease -> subnet)
3052 subnet_reference (&lt -> subnet, lease -> subnet, MDL);
3053 if (lease -> billing_class)
3054 class_reference (&lt -> billing_class,
3055 lease -> billing_class, MDL);
97ca1699 3056
9e0e9ed8
TL
3057 /* Set a flag if this client is a broken client that NUL
3058 terminates string options and expects us to do likewise. */
5bc2e1f2
TL
3059 if (ms_nulltp)
3060 lease -> flags |= MS_NULL_TERMINATION;
3061 else
8c8e27c5 3062 lease -> flags &= ~MS_NULL_TERMINATION;
9e0e9ed8 3063
12c9957e 3064 /* Save any bindings. */
6ceb9118
TL
3065 if (lease -> scope) {
3066 binding_scope_reference (&lt -> scope, lease -> scope, MDL);
3067 binding_scope_dereference (&lease -> scope, MDL);
3068 }
bfe2d221
TL
3069 if (lease -> agent_options)
3070 option_chain_head_reference (&lt -> agent_options,
3071 lease -> agent_options, MDL);
12c9957e 3072
656b1ece
TM
3073 /* Save the vendor-class-identifier for DHCPLEASEQUERY. */
3074 oc = lookup_option(&dhcp_universe, packet->options,
3075 DHO_VENDOR_CLASS_IDENTIFIER);
3076 if (oc != NULL &&
3077 evaluate_option_cache(&d1, packet, NULL, NULL, packet->options,
f3a44c10 3078 NULL, &lt->scope, oc, MDL)) {
656b1ece 3079 if (d1.len != 0) {
f3a44c10 3080 bind_ds_value(&lt->scope, "vendor-class-identifier",
656b1ece
TM
3081 &d1);
3082 }
3083
3084 data_string_forget(&d1, MDL);
3085 }
3086
9aa3f3a5
DH
3087 /* If we got relay agent information options from the packet, then
3088 * cache them for renewal in case the relay agent can't supply them
3089 * when the client unicasts. The options may be from an addressed
3090 * "l3" relay, or from an unaddressed "l2" relay which does not set
3091 * giaddr.
02428754 3092 */
9aa3f3a5 3093 if (!packet->agent_options_stashed &&
8bd96ccb 3094 (packet->options != NULL) &&
9aa3f3a5
DH
3095 packet->options->universe_count > agent_universe.index &&
3096 packet->options->universes[agent_universe.index] != NULL) {
9e383163
TL
3097 oc = lookup_option (&server_universe, state -> options,
3098 SV_STASH_AGENT_OPTIONS);
3099 if (!oc ||
3100 evaluate_boolean_option_cache (&ignorep, packet, lease,
3101 (struct client_state *)0,
3102 packet -> options,
3103 state -> options,
3104 &lease -> scope, oc, MDL)) {
de528760
TL
3105 if (lt -> agent_options)
3106 option_chain_head_dereference (&lt -> agent_options, MDL);
bfe2d221 3107 option_chain_head_reference
9e383163 3108 (&lt -> agent_options,
bfe2d221 3109 (struct option_chain_head *)
9e383163
TL
3110 packet -> options -> universes [agent_universe.index],
3111 MDL);
3112 }
3113 }
3114
d73e855d
TL
3115 /* Replace the old lease hostname with the new one, if it's changed. */
3116 oc = lookup_option (&dhcp_universe, packet -> options, DHO_HOST_NAME);
3117 if (oc)
3118 s1 = evaluate_option_cache (&d1, packet, (struct lease *)0,
9e383163 3119 (struct client_state *)0,
d73e855d
TL
3120 packet -> options,
3121 (struct option_state *)0,
3122 &global_scope, oc, MDL);
98311e4b
DH
3123 else
3124 s1 = 0;
3125
d73e855d
TL
3126 if (oc && s1 &&
3127 lease -> client_hostname &&
3128 strlen (lease -> client_hostname) == d1.len &&
3129 !memcmp (lease -> client_hostname, d1.data, d1.len)) {
3130 /* Hasn't changed. */
3131 data_string_forget (&d1, MDL);
3132 lt -> client_hostname = lease -> client_hostname;
3133 lease -> client_hostname = (char *)0;
3134 } else if (oc && s1) {
3135 lt -> client_hostname = dmalloc (d1.len + 1, MDL);
3136 if (!lt -> client_hostname)
3137 log_error ("no memory for client hostname.");
3138 else {
3139 memcpy (lt -> client_hostname, d1.data, d1.len);
3140 lt -> client_hostname [d1.len] = 0;
3141 }
3142 data_string_forget (&d1, MDL);
3abc5708
SR
3143 /* hostname changed, can't reuse lease */
3144 lease->cannot_reuse = 1;
d73e855d
TL
3145 }
3146
b992d7e2
DN
3147 /* Record the hardware address, if given... */
3148 lt -> hardware_addr.hlen = packet -> raw -> hlen + 1;
3149 lt -> hardware_addr.hbuf [0] = packet -> raw -> htype;
3150 memcpy (&lt -> hardware_addr.hbuf [1], packet -> raw -> chaddr,
3151 sizeof packet -> raw -> chaddr);
3152
606f2720
TM
3153 /*
3154 * If client has requested the lease become infinite, then it
3155 * doens't qualify for reuse even if it's younger than the
3156 * dhcp-cache-threshold.
3157 */
3158 if ((lt->flags & RESERVED_LEASE) && !(lease->flags & RESERVED_LEASE)) {
3159 log_debug ("Cannot reuse: lease is changing to RESERVED");
3160 lease->cannot_reuse = 1;
3161 }
3162
3163 lt->flags |= lease->flags & ~PERSISTENT_FLAGS;
c6708cba 3164
39ae5027
TL
3165 /* If there are statements to execute when the lease is
3166 committed, execute them. */
a7341359
SR
3167 if (lease->on_star.on_commit && (!offer || offer == DHCPACK)) {
3168 execute_statements (NULL, packet, lt, NULL, packet->options,
3169 state->options, &lt->scope,
3170 lease->on_star.on_commit, NULL);
3171 if (lease->on_star.on_commit)
3172 executable_statement_dereference
3173 (&lease->on_star.on_commit, MDL);
39ae5027
TL
3174 }
3175
b992d7e2
DN
3176#ifdef NSUPDATE
3177 /* Perform DDNS updates, if configured to. */
3178 if ((!offer || offer == DHCPACK) &&
bf9d9d27
TL
3179 (!(oc = lookup_option (&server_universe, state -> options,
3180 SV_DDNS_UPDATES)) ||
3181 evaluate_boolean_option_cache (&ignorep, packet, lt,
3182 (struct client_state *)0,
3183 packet -> options,
3184 state -> options,
3185 &lt -> scope, oc, MDL))) {
98bd7ca0 3186 ddns_updates(packet, lt, lease, NULL, NULL, state->options);
b992d7e2
DN
3187 }
3188#endif /* NSUPDATE */
3189
7a049f2c 3190 /* Don't call supersede_lease on a mocked-up lease. */
ec8d21a7
TL
3191 if (lease -> flags & STATIC_LEASE) {
3192 /* Copy the hardware address into the static lease
3193 structure. */
2cbc0e48
TL
3194 lease -> hardware_addr.hlen = packet -> raw -> hlen + 1;
3195 lease -> hardware_addr.hbuf [0] = packet -> raw -> htype;
3196 memcpy (&lease -> hardware_addr.hbuf [1],
3197 packet -> raw -> chaddr,
3c893bb6 3198 sizeof packet -> raw -> chaddr); /* XXX */
ec8d21a7 3199 } else {
929a2364 3200 int commit = (!offer || (offer == DHCPACK));
929a2364 3201
f3a44c10
TM
3202 /* If dhcp-cache-threshold is enabled, see if "lease" can
3203 * be reused. */
a5b21e16
TM
3204 use_old_lease = reuse_lease(packet, lt, lease, state, offer,
3205 &same_client);
f3a44c10
TM
3206 if (use_old_lease == 1) {
3207 commit = 0;
929a2364
TM
3208 }
3209
700e3fca 3210#if !defined(DELAYED_ACK)
6368a1bd 3211 /* Install the new information on 'lt' onto the lease at
fbcee149
DH
3212 * 'lease'. If this is a DHCPOFFER, it is a 'soft' promise,
3213 * if it is a DHCPACK, it is a 'hard' binding, so it needs
3214 * to be recorded and propogated immediately. If the update
3215 * fails, don't ACK it (or BOOTREPLY) either; we may give
3216 * the same lease to another client later, and that would be
3217 * a conflict.
3218 */
8cd88e20
SR
3219 if ((use_old_lease == 0) &&
3220 !supersede_lease(lease, lt, commit,
491bf4a2 3221 offer == DHCPACK, offer == DHCPACK, 0)) {
700e3fca 3222#else /* defined(DELAYED_ACK) */
929a2364
TM
3223 /*
3224 * If there already isn't a need for a lease commit, and we
3225 * can just answer right away, set a flag to indicate this.
3226 */
8cd88e20 3227 if (commit)
929a2364 3228 enqueue = ISC_TRUE;
929a2364 3229
fbcee149 3230 /* Install the new information on 'lt' onto the lease at
f8380d3f 3231 * 'lease'. We will not 'commit' this information to disk
fbcee149
DH
3232 * yet (fsync()), we will 'propogate' the information if
3233 * this is BOOTP or a DHCPACK, but we will not 'pimmediate'ly
3234 * transmit failover binding updates (this is delayed until
3235 * after the fsync()). If the update fails, don't ACK it (or
3236 * BOOTREPLY either); we may give the same lease out to a
3237 * different client, and that would be a conflict.
3238 */
8cd88e20
SR
3239 if ((use_old_lease == 0) &&
3240 !supersede_lease(lease, lt, 0,
491bf4a2 3241 !offer || offer == DHCPACK, 0, 0)) {
fbcee149 3242#endif
8ae2d595 3243 log_info ("%s: database update failed", msg);
4bd8800e 3244 free_lease_state (state, MDL);
20916cae 3245 lease_dereference (&lt, MDL);
7a049f2c 3246 return;
c4924529 3247 }
ec8d21a7 3248 }
20916cae 3249 lease_dereference (&lt, MDL);
97ca1699 3250
11b37280 3251 /* Remember the interface on which the packet arrived. */
9cc3ad7f 3252 state -> ip = packet -> interface;
685963dc 3253
11b37280 3254 /* Remember the giaddr, xid, secs, flags and hops. */
9cc3ad7f 3255 state -> giaddr = packet -> raw -> giaddr;
44b2e3ad 3256 state -> ciaddr = packet -> raw -> ciaddr;
9cc3ad7f
TL
3257 state -> xid = packet -> raw -> xid;
3258 state -> secs = packet -> raw -> secs;
3259 state -> bootp_flags = packet -> raw -> flags;
3260 state -> hops = packet -> raw -> hops;
3261 state -> offer = offer;
685963dc 3262
6dadd610
TL
3263 /* If we're always supposed to broadcast to this client, set
3264 the broadcast bit in the bootp flags field. */
e3b5f7f8
TL
3265 if ((oc = lookup_option (&server_universe, state -> options,
3266 SV_ALWAYS_BROADCAST)) &&
19654922 3267 evaluate_boolean_option_cache (&ignorep, packet, lease,
9e383163 3268 (struct client_state *)0,
ca1c700e 3269 packet -> options, state -> options,
12c9957e 3270 &lease -> scope, oc, MDL))
6dadd610
TL
3271 state -> bootp_flags |= htons (BOOTP_BROADCAST);
3272
3c893bb6
TL
3273 /* Get the Maximum Message Size option from the packet, if one
3274 was sent. */
951323fe 3275 oc = lookup_option (&dhcp_universe, packet -> options,
5d25508c
TL
3276 DHO_DHCP_MAX_MESSAGE_SIZE);
3277 if (oc &&
ca1c700e 3278 evaluate_option_cache (&d1, packet, lease,
9e383163 3279 (struct client_state *)0,
12c9957e
TL
3280 packet -> options, state -> options,
3281 &lease -> scope, oc, MDL)) {
5d25508c
TL
3282 if (d1.len == sizeof (u_int16_t))
3283 state -> max_message_size = getUShort (d1.data);
4bd8800e 3284 data_string_forget (&d1, MDL);
c76aff91
TL
3285 } else {
3286 oc = lookup_option (&dhcp_universe, state -> options,
3287 DHO_DHCP_MAX_MESSAGE_SIZE);
3288 if (oc &&
3289 evaluate_option_cache (&d1, packet, lease,
9e383163 3290 (struct client_state *)0,
c76aff91
TL
3291 packet -> options, state -> options,
3292 &lease -> scope, oc, MDL)) {
3293 if (d1.len == sizeof (u_int16_t))
3294 state -> max_message_size =
3295 getUShort (d1.data);
3296 data_string_forget (&d1, MDL);
3297 }
3c893bb6
TL
3298 }
3299
98311e4b
DH
3300 /* Get the Subnet Selection option from the packet, if one
3301 was sent. */
3302 if ((oc = lookup_option (&dhcp_universe, packet -> options,
3303 DHO_SUBNET_SELECTION))) {
3304
3305 /* Make a copy of the data. */
3306 struct option_cache *noc = (struct option_cache *)0;
3307 if (option_cache_allocate (&noc, MDL)) {
3308 if (oc -> data.len)
3309 data_string_copy (&noc -> data,
3310 &oc -> data, MDL);
3311 if (oc -> expression)
3312 expression_reference (&noc -> expression,
3313 oc -> expression, MDL);
3314 if (oc -> option)
66c8f734
DH
3315 option_reference(&(noc->option), oc->option,
3316 MDL);
98311e4b 3317
d56788df
SR
3318 save_option (&dhcp_universe, state -> options, noc);
3319 option_cache_dereference (&noc, MDL);
3320 }
98311e4b
DH
3321 }
3322
7a049f2c 3323 /* Now, if appropriate, put in DHCP-specific options that
65cf86d7 3324 override those. */
9cc3ad7f 3325 if (state -> offer) {
11b37280 3326 i = DHO_DHCP_MESSAGE_TYPE;
5d25508c 3327 oc = (struct option_cache *)0;
4bd8800e 3328 if (option_cache_allocate (&oc, MDL)) {
5d25508c 3329 if (make_const_data (&oc -> expression,
d758ad8c 3330 &state -> offer, 1, 0, 0, MDL)) {
f7fdb216
DH
3331 option_code_hash_lookup(&oc->option,
3332 dhcp_universe.code_hash,
3333 &i, 0, MDL);
951323fe
TL
3334 save_option (&dhcp_universe,
3335 state -> options, oc);
5d25508c 3336 }
4bd8800e 3337 option_cache_dereference (&oc, MDL);
5d25508c 3338 }
6d103865 3339
f8380d3f
SR
3340 get_server_source_address(&from, state->options,
3341 state->options, packet);
6d103865
SK
3342 memcpy(state->from.iabuf, &from, sizeof(from));
3343 state->from.len = sizeof(from);
7a049f2c 3344
b1dd98c9
TL
3345 offered_lease_time =
3346 state -> offered_expiry - cur_time;
b88e8e15 3347
dcc557db 3348 putULong(state->expiry, (u_int32_t)offered_lease_time);
11b37280 3349 i = DHO_DHCP_LEASE_TIME;
5d25508c 3350 oc = (struct option_cache *)0;
4bd8800e 3351 if (option_cache_allocate (&oc, MDL)) {
dcc557db
DH
3352 if (make_const_data(&oc->expression, state->expiry,
3353 4, 0, 0, MDL)) {
f7fdb216
DH
3354 option_code_hash_lookup(&oc->option,
3355 dhcp_universe.code_hash,
3356 &i, 0, MDL);
951323fe
TL
3357 save_option (&dhcp_universe,
3358 state -> options, oc);
5d25508c 3359 }
4bd8800e 3360 option_cache_dereference (&oc, MDL);
5d25508c 3361 }
7a049f2c 3362
5a671e87
DH
3363 /*
3364 * Validate any configured renew or rebinding times against
3365 * the determined lease time. Do rebinding first so that
3366 * the renew time can be validated against the rebind time.
3367 */
3368 if ((oc = lookup_option(&dhcp_universe, state->options,
3369 DHO_DHCP_REBINDING_TIME)) != NULL &&
3370 evaluate_option_cache(&d1, packet, lease, NULL,
3371 packet->options, state->options,
3372 &lease->scope, oc, MDL)) {
3373 TIME rebind_time = getULong(d1.data);
3374
3375 /* Drop the configured (invalid) rebinding time. */
3376 if (rebind_time >= offered_lease_time)
3377 delete_option(&dhcp_universe, state->options,
3378 DHO_DHCP_REBINDING_TIME);
3379 else /* XXX: variable is reused. */
3380 offered_lease_time = rebind_time;
3381
3382 data_string_forget(&d1, MDL);
5d25508c 3383 }
4ecd2958 3384
5a671e87
DH
3385 if ((oc = lookup_option(&dhcp_universe, state->options,
3386 DHO_DHCP_RENEWAL_TIME)) != NULL &&
3387 evaluate_option_cache(&d1, packet, lease, NULL,
3388 packet->options, state->options,
3389 &lease->scope, oc, MDL)) {
3390 if (getULong(d1.data) >= offered_lease_time)
3391 delete_option(&dhcp_universe, state->options,
3392 DHO_DHCP_RENEWAL_TIME);
3393
3394 data_string_forget(&d1, MDL);
5d25508c 3395 }
10553ccb 3396 } else {
6d103865 3397 /* XXXSK: should we use get_server_source_address() here? */
98bd7ca0
DH
3398 if (state -> ip -> address_count) {
3399 state -> from.len =
3400 sizeof state -> ip -> addresses [0];
3401 memcpy (state -> from.iabuf,
3402 &state -> ip -> addresses [0],
3403 state -> from.len);
3404 }
10553ccb
TL
3405 }
3406
3407 /* Figure out the address of the boot file server. */
98311e4b 3408 memset (&state -> siaddr, 0, sizeof state -> siaddr);
10553ccb
TL
3409 if ((oc =
3410 lookup_option (&server_universe,
3411 state -> options, SV_NEXT_SERVER))) {
ca1c700e 3412 if (evaluate_option_cache (&d1, packet, lease,
9e383163 3413 (struct client_state *)0,
ca1c700e 3414 packet -> options, state -> options,
12c9957e 3415 &lease -> scope, oc, MDL)) {
10553ccb
TL
3416 /* If there was more than one answer,
3417 take the first. */
3418 if (d1.len >= 4 && d1.data)
46904800 3419 memcpy (&state -> siaddr, d1.data, 4);
4bd8800e 3420 data_string_forget (&d1, MDL);
10553ccb 3421 }
7a049f2c 3422 }
685963dc 3423
4ecd2958
TL
3424 /* Use the subnet mask from the subnet declaration if no other
3425 mask has been provided. */
11b37280 3426 i = DHO_SUBNET_MASK;
951323fe 3427 if (!lookup_option (&dhcp_universe, state -> options, i)) {
4d0aaa17 3428 oc = (struct option_cache *)0;
4bd8800e 3429 if (option_cache_allocate (&oc, MDL)) {
5d25508c
TL
3430 if (make_const_data (&oc -> expression,
3431 lease -> subnet -> netmask.iabuf,
3432 lease -> subnet -> netmask.len,
d758ad8c 3433 0, 0, MDL)) {
f7fdb216
DH
3434 option_code_hash_lookup(&oc->option,
3435 dhcp_universe.code_hash,
3436 &i, 0, MDL);
951323fe
TL
3437 save_option (&dhcp_universe,
3438 state -> options, oc);
5d25508c 3439 }
4bd8800e 3440 option_cache_dereference (&oc, MDL);
5d25508c 3441 }
b1dd98c9
TL
3442 }
3443
0a7e1a8a 3444 /* Use the name of the host declaration if there is one
a5b21e16 3445 and no hostname has otherwise been provided, and if the
b1dd98c9 3446 use-host-decl-name flag is set. */
0a7e1a8a 3447 use_host_decl_name(packet, lease, state->options);
b1dd98c9 3448
e046c826
TM
3449 /* Send client_id back if we received it and echo-client-id is on. */
3450 echo_client_id(packet, lease, state->options, state->options);
3451
b1dd98c9
TL
3452 /* If we don't have a hostname yet, and we've been asked to do
3453 a reverse lookup to find the hostname, do it. */
524705e5 3454 i = DHO_HOST_NAME;
5d25508c 3455 j = SV_GET_LEASE_HOSTNAMES;
524705e5
DH
3456 if (!lookup_option(&dhcp_universe, state->options, i) &&
3457 evaluate_boolean_option_cache
3458 (&ignorep, packet, lease, NULL,
3459 packet->options, state->options, &lease->scope,
3460 lookup_option (&server_universe, state->options, j), MDL)) {
5d25508c
TL
3461 struct in_addr ia;
3462 struct hostent *h;
a5b21e16 3463
5d25508c 3464 memcpy (&ia, lease -> ip_addr.iabuf, 4);
a5b21e16 3465
5d25508c
TL
3466 h = gethostbyaddr ((char *)&ia, sizeof ia, AF_INET);
3467 if (!h)
8ae2d595 3468 log_error ("No hostname for %s", inet_ntoa (ia));
5d25508c
TL
3469 else {
3470 oc = (struct option_cache *)0;
4bd8800e 3471 if (option_cache_allocate (&oc, MDL)) {
5d25508c 3472 if (make_const_data (&oc -> expression,
c5b0f529
TL
3473 ((unsigned char *)
3474 h -> h_name),
5d25508c 3475 strlen (h -> h_name) + 1,
d758ad8c 3476 1, 1, MDL)) {
f7fdb216
DH
3477 option_code_hash_lookup(&oc->option,
3478 dhcp_universe.code_hash,
3479 &i, 0, MDL);
951323fe
TL
3480 save_option (&dhcp_universe,
3481 state -> options, oc);
5d25508c 3482 }
4bd8800e 3483 option_cache_dereference (&oc, MDL);
b1dd98c9
TL
3484 }
3485 }
4ecd2958
TL
3486 }
3487
421563ea
TL
3488 /* If so directed, use the leased IP address as the router address.
3489 This supposedly makes Win95 machines ARP for all IP addresses,
3490 so if the local router does proxy arp, you win. */
b1dd98c9 3491
5d25508c 3492 if (evaluate_boolean_option_cache
9e383163
TL
3493 (&ignorep, packet, lease, (struct client_state *)0,
3494 packet -> options, state -> options, &lease -> scope,
951323fe 3495 lookup_option (&server_universe, state -> options,
12c9957e 3496 SV_USE_LEASE_ADDR_FOR_DEFAULT_ROUTE), MDL)) {
5d25508c 3497 i = DHO_ROUTERS;
951323fe 3498 oc = lookup_option (&dhcp_universe, state -> options, i);
027f46cb
TL
3499 if (!oc) {
3500 oc = (struct option_cache *)0;
4bd8800e 3501 if (option_cache_allocate (&oc, MDL)) {
027f46cb
TL
3502 if (make_const_data (&oc -> expression,
3503 lease -> ip_addr.iabuf,
3504 lease -> ip_addr.len,
d758ad8c 3505 0, 0, MDL)) {
f7fdb216
DH
3506 option_code_hash_lookup(&oc->option,
3507 dhcp_universe.code_hash,
3508 &i, 0, MDL);
951323fe
TL
3509 save_option (&dhcp_universe,
3510 state -> options, oc);
027f46cb 3511 }
a5b21e16 3512 option_cache_dereference (&oc, MDL);
5d25508c 3513 }
b1dd98c9 3514 }
421563ea
TL
3515 }
3516
10553ccb
TL
3517 /* If a site option space has been specified, use that for
3518 site option codes. */
3519 i = SV_SITE_OPTION_SPACE;
0af446bc 3520 if ((oc = lookup_option (&server_universe, state -> options, i)) &&
ca1c700e 3521 evaluate_option_cache (&d1, packet, lease,
9e383163 3522 (struct client_state *)0,
12c9957e
TL
3523 packet -> options, state -> options,
3524 &lease -> scope, oc, MDL)) {
20916cae
TL
3525 struct universe *u = (struct universe *)0;
3526
3527 if (!universe_hash_lookup (&u, universe_hash,
165bce70
TL
3528 (const char *)d1.data, d1.len,
3529 MDL)) {
10553ccb 3530 log_error ("unknown option space %s.", d1.data);
0cd94b5e 3531 data_string_forget (&d1, MDL);
10553ccb
TL
3532 return;
3533 }
3534
3535 state -> options -> site_universe = u -> index;
2c9bf1f4 3536 state->options->site_code_min = find_min_site_code(u);
4bd8800e 3537 data_string_forget (&d1, MDL);
10553ccb
TL
3538 } else {
3539 state -> options -> site_code_min = 0;
3540 state -> options -> site_universe = dhcp_universe.index;
3541 }
3542
eddb16f4 3543 /* If the client has provided a list of options that it wishes
431693d1
TL
3544 returned, use it to prioritize. If there's a parameter
3545 request list in scope, use that in preference. Otherwise
3546 use the default priority list. */
eddb16f4 3547
431693d1 3548 oc = lookup_option (&dhcp_universe, state -> options,
eddb16f4
TL
3549 DHO_DHCP_PARAMETER_REQUEST_LIST);
3550
cdc336ab 3551 if (!oc)
431693d1 3552 oc = lookup_option (&dhcp_universe, packet -> options,
cdc336ab 3553 DHO_DHCP_PARAMETER_REQUEST_LIST);
eddb16f4
TL
3554 if (oc)
3555 evaluate_option_cache (&state -> parameter_request_list,
9e383163 3556 packet, lease, (struct client_state *)0,
ca1c700e 3557 packet -> options, state -> options,
12c9957e 3558 &lease -> scope, oc, MDL);
eddb16f4 3559
11b37280
TL
3560#ifdef DEBUG_PACKET
3561 dump_packet (packet);
3562 dump_raw ((unsigned char *)packet -> raw, packet -> packet_length);
3563#endif
3564
9cc3ad7f 3565 lease -> state = state;
4b7df707 3566
8ae2d595 3567 log_info ("%s", msg);
c4924529 3568
ca1c700e 3569 /* Hang the packet off the lease state. */
4bd8800e 3570 packet_reference (&lease -> state -> packet, packet, MDL);
ca1c700e 3571
a5b21e16
TM
3572 /* If this is a DHCPOFFER, send a ping (if appropriate) to the
3573 * lease address before actually we send the offer. */
3574 if ((offer == DHCPOFFER) &&
3575 do_ping_check(packet, state, lease, original_cltt, same_client)) {
4b7df707
TL
3576 ++outstanding_pings;
3577 } else {
6368a1bd 3578 lease->cltt = cur_time;
700e3fca 3579#if defined(DELAYED_ACK)
6826003b 3580 if (enqueue)
6368a1bd 3581 delayed_ack_enqueue(lease);
a5b21e16 3582 else
fbcee149 3583#endif
6368a1bd
DH
3584 dhcp_reply(lease);
3585 }
3586}
3587
a5b21e16
TM
3588/*
3589 * \brief Sends a ping to the lease ip_addr when appropriate
3590 *
3591 * A ping will be sent if all of the following are true:
3592 *
3593 * 1. Ping checks are enabled
3594 * 2. The lease is neither active nor static
3595 * 3. Any of the following is true:
3596 * a. The lease state is ABANDONED
3597 * b. This is the first offer of this lease (CLTT = 0)
3598 * c. The lease is being offered to a client other than its previous
3599 * owner
3600 * d. The lease is being offered to its previous owner and more than
3601 * cltt-secs have elapsed since CLTT of the original lease.
3602 *
3603 * \param packet inbound packet received from the client
3604 * \param state lease options state
3605 * \param lease lease to be offered (if one)
3606 * \param original_cltt CLTT of the original lease
3607 * \param same_client flag indicating if the client to be offered the
3608 * lease is its previous owner
3609 * \return Returns 1 if ping has been sent, 0 otherwise
3610 */
3611int do_ping_check(struct packet* packet, struct lease_state* state,
3612 struct lease* lease, TIME original_cltt,
3613 int same_client) {
3614 TIME ping_timeout = DEFAULT_PING_TIMEOUT;
e6eccd10 3615 TIME ping_timeout_ms = DEFAULT_PING_TIMEOUT_MS;
a5b21e16
TM
3616 struct option_cache *oc = NULL;
3617 struct data_string ds;
3618 struct timeval tv;
3619 int ignorep;
e6eccd10
TM
3620 int timeout_secs;
3621 int timeout_ms;
a5b21e16
TM
3622
3623 // Don't go any further if lease is active or static.
3624 if (lease->binding_state == FTS_ACTIVE || lease->flags & STATIC_LEASE) {
3625 return (0);
3626 }
3627
3628 // If pings aren't enabled, punt.
3629 oc = lookup_option (&server_universe, state -> options, SV_PING_CHECKS);
3630 if (oc &&
3631 !(evaluate_boolean_option_cache (&ignorep, packet, lease,
3632 0, packet->options, state->options,
3633 &lease->scope, oc, MDL))) {
3634 return (0);
3635 }
3636
3637 // If it's not the first time for the same client and not an
3638 // abandoned lease, we need to check the cltt threshold
3639 if (same_client && original_cltt &&
3640 lease->binding_state != FTS_ABANDONED) {
3641 TIME cltt_secs = DEFAULT_PING_CLTT_SECS;
3642 memset(&ds, 0, sizeof(ds));
3643 oc = lookup_option (&server_universe, state->options,
3644 SV_PING_CLTT_SECS);
3645 if (oc &&
3646 (evaluate_option_cache (&ds, packet, lease, 0,
3647 packet->options, state->options,
3648 &lease->scope, oc, MDL))) {
3649 if (ds.len == sizeof (u_int32_t)) {
3650 cltt_secs = getULong (ds.data);
3651 }
3652
3653 data_string_forget (&ds, MDL);
3654 }
3655
3656 // Punt if it is too soon.
3657 if (cur_time - original_cltt < cltt_secs) {
3658 return (0);
3659 }
3660 }
3661
3662 // Send the ping.
3663 icmp_echorequest (&lease->ip_addr);
3664
3665 /* Determine whether to use configured or default ping timeout. */
3666 memset(&ds, 0, sizeof(ds));
e6eccd10 3667
a5b21e16
TM
3668 oc = lookup_option (&server_universe, state->options, SV_PING_TIMEOUT);
3669 if (oc &&
3670 (evaluate_option_cache (&ds, packet, lease, 0,
3671 packet->options, state->options,
3672 &lease->scope, oc, MDL))) {
3673 if (ds.len == sizeof (u_int32_t)) {
3674 ping_timeout = getULong (ds.data);
3675 }
3676
3677 data_string_forget (&ds, MDL);
3678 }
3679
e6eccd10
TM
3680 oc = lookup_option (&server_universe, state->options, SV_PING_TIMEOUT_MS);
3681 if (oc &&
3682 (evaluate_option_cache (&ds, packet, lease, 0,
3683 packet->options, state->options,
3684 &lease->scope, oc, MDL))) {
3685 if (ds.len == sizeof (u_int32_t)) {
3686 ping_timeout_ms = getULong (ds.data);
3687 }
3688
3689 data_string_forget (&ds, MDL);
3690 }
3691
3692 /*
3693 * Set the timeout for the ping to the current timeval plus
3694 * the configured time out. Use ping-timeout-ms if it is > 0.
3695 * This overrides ping-timeout allowing users to specify it in
3696 * milliseconds.
3697 */
3698 if (ping_timeout_ms > 0) {
3699 timeout_secs = ping_timeout_ms / 1000;
3700 timeout_ms = ping_timeout_ms % 1000;
3701 } else {
3702 timeout_secs = ping_timeout;
3703 timeout_ms = 0;
3704
3705 }
3706
3707 tv.tv_sec = cur_tv.tv_sec + timeout_secs;
3708 tv.tv_usec = cur_tv.tv_usec + (timeout_ms * 1000);
3709
a5b21e16
TM
3710#ifdef DEBUG
3711 log_debug ("Pinging:%s, state: %d, same client? %s, "
e6eccd10 3712 " orig_cltt %s, elasped: %ld, timeout in: %d.%d secs" ,
a5b21e16
TM
3713 piaddr(lease->ip_addr),
3714 lease->binding_state,
3715 (same_client ? "y" : "n"),
3716 (original_cltt ? print_time(original_cltt) : "0"),
e6eccd10
TM
3717 (original_cltt ? (long)(cur_time - original_cltt) : 0),
3718 timeout_secs, timeout_ms);
a5b21e16 3719
e6eccd10 3720#endif
5918b493
TM
3721
3722 add_timeout (&tv, lease_ping_timeout, lease, (tvref_t)lease_reference,
3723 (tvunref_t)lease_dereference);
3724
a5b21e16
TM
3725 return (1);
3726}
3727
3728
e422b8c7
TM
3729#if defined(DELAYED_ACK)
3730
0585235c
SR
3731/*
3732 * CC: queue single ACK:
3733 * - write the lease (but do not fsync it yet)
3734 * - add to double linked list
3735 * - commit if more than xx ACKs pending
3736 * - if necessary set the max timer and bump the next timer
3737 * but only up to the max timer value.
6368a1bd
DH
3738 */
3739
e422b8c7 3740static void
6368a1bd
DH
3741delayed_ack_enqueue(struct lease *lease)
3742{
3743 struct leasequeue *q;
f8cbf390 3744
a5b21e16 3745 if (!write_lease(lease))
6368a1bd
DH
3746 return;
3747 if (free_ackqueue) {
3748 q = free_ackqueue;
3749 free_ackqueue = q->next;
3750 } else {
3751 q = ((struct leasequeue *)
3752 dmalloc(sizeof(struct leasequeue), MDL));
3753 if (!q)
3754 log_fatal("delayed_ack_enqueue: no memory!");
4b7df707 3755 }
6368a1bd
DH
3756 memset(q, 0, sizeof *q);
3757 /* prepend to ackqueue*/
087b8f18 3758 lease_reference(&q->lease, lease, MDL);
6368a1bd
DH
3759 q->next = ackqueue_head;
3760 ackqueue_head = q;
a5b21e16 3761 if (!ackqueue_tail)
6368a1bd
DH
3762 ackqueue_tail = q;
3763 else
3764 q->next->prev = q;
3765
3766 outstanding_acks++;
0585235c 3767 if (outstanding_acks > max_outstanding_acks) {
e422b8c7
TM
3768 /* Cancel any pending timeout and call handler directly */
3769 cancel_timeout(delayed_acks_timer, NULL);
3770 delayed_acks_timer(NULL);
0585235c
SR
3771 } else {
3772 struct timeval next_fsync;
3773
3774 if (max_fsync.tv_sec == 0 && max_fsync.tv_usec == 0) {
3775 /* set the maximum time we'll wait */
3776 max_fsync.tv_sec = cur_tv.tv_sec + max_ack_delay_secs;
3777 max_fsync.tv_usec = cur_tv.tv_usec +
3778 max_ack_delay_usecs;
f8cbf390 3779
0585235c
SR
3780 if (max_fsync.tv_usec >= 1000000) {
3781 max_fsync.tv_sec++;
3782 max_fsync.tv_usec -= 1000000;
3783 }
3784 }
3785
3786 /* Set the timeout */
3787 next_fsync.tv_sec = cur_tv.tv_sec;
3788 next_fsync.tv_usec = cur_tv.tv_usec + min_ack_delay_usecs;
f8cbf390
DH
3789 if (next_fsync.tv_usec >= 1000000) {
3790 next_fsync.tv_sec++;
3791 next_fsync.tv_usec -= 1000000;
3792 }
0585235c
SR
3793 /* but not more than the max */
3794 if ((next_fsync.tv_sec > max_fsync.tv_sec) ||
3795 ((next_fsync.tv_sec == max_fsync.tv_sec) &&
3796 (next_fsync.tv_usec > max_fsync.tv_usec))) {
3797 next_fsync.tv_sec = max_fsync.tv_sec;
3798 next_fsync.tv_usec = max_fsync.tv_usec;
3799 }
f8cbf390 3800
e422b8c7 3801 add_timeout(&next_fsync, delayed_acks_timer, NULL,
6368a1bd
DH
3802 (tvref_t) NULL, (tvunref_t) NULL);
3803 }
11b37280
TL
3804}
3805
e422b8c7
TM
3806/* Processes any delayed acks:
3807 * Commits the leases and then for each delayed ack:
3808 * - Update the failover peer if we're in failover
3809 * - Send the REPLY to the client
3810 */
f8cbf390 3811static void
e422b8c7 3812delayed_acks_timer(void *foo)
f8cbf390 3813{
e422b8c7
TM
3814 struct leasequeue *ack, *p;
3815
3816 /* Reset max fsync */
3817 memset(&max_fsync, 0, sizeof(max_fsync));
f8cbf390 3818
e422b8c7
TM
3819 if (!outstanding_acks) {
3820 /* Nothing to do, so punt, shouldn't happen? */
3821 return;
f8cbf390 3822 }
6368a1bd 3823
e422b8c7
TM
3824 /* Commit the leases first */
3825 commit_leases();
3826
3827 /* Now process the delayed ACKs
3828 - update failover peer
3829 - send out the ACK packets
3830 - move the queue slots to the free list
3831 */
3832
6368a1bd 3833 /* process from bottom to retain packet order */
a5b21e16 3834 for (ack = ackqueue_tail ; ack ; ack = p) {
6368a1bd 3835 p = ack->prev;
087b8f18 3836
e422b8c7
TM
3837#if defined(FAILOVER_PROTOCOL)
3838 /* If we're in failover we need to send any deferred
3839 * bind updates as well as the replies */
3840 if (ack->lease->pool) {
3841 dhcp_failover_state_t *fpeer;
3842
3843 fpeer = ack->lease->pool->failover_peer;
3844 if (fpeer && fpeer->link_to_peer) {
3845 dhcp_failover_send_updates(fpeer);
3846 }
3847 }
3848#endif
3849
087b8f18
DH
3850 /* dhcp_reply() requires that the reply state still be valid */
3851 if (ack->lease->state == NULL)
3852 log_error("delayed ack for %s has gone stale",
3853 piaddr(ack->lease->ip_addr));
e422b8c7 3854 else {
087b8f18 3855 dhcp_reply(ack->lease);
e422b8c7 3856 }
087b8f18
DH
3857
3858 lease_dereference(&ack->lease, MDL);
6368a1bd
DH
3859 ack->next = free_ackqueue;
3860 free_ackqueue = ack;
3861 }
e422b8c7 3862
6368a1bd
DH
3863 ackqueue_head = NULL;
3864 ackqueue_tail = NULL;
3865 outstanding_acks = 0;
3866}
3867
3868#if defined (DEBUG_MEMORY_LEAKAGE_ON_EXIT)
3869void
3870relinquish_ackqueue(void)
3871{
3872 struct leasequeue *q, *n;
a5b21e16 3873
95fd7038 3874 for (q = ackqueue_head ; q ; q = n) {
6368a1bd
DH
3875 n = q->next;
3876 dfree(q, MDL);
3877 }
3878 for (q = free_ackqueue ; q ; q = n) {
3879 n = q->next;
3880 dfree(q, MDL);
3881 }
3882}
3883#endif
3884
e422b8c7
TM
3885#endif /* defined(DELAYED_ACK) */
3886
11b37280
TL
3887void dhcp_reply (lease)
3888 struct lease *lease;
3889{
3890 int bufs = 0;
b1b7b521 3891 unsigned packet_length;
11b37280
TL
3892 struct dhcp_packet raw;
3893 struct sockaddr_in to;
3894 struct in_addr from;
3895 struct hardware hto;
3896 int result;
9cc3ad7f 3897 struct lease_state *state = lease -> state;
bca94423 3898 int nulltp, bootpp, unicastp = 1;
27058b3e 3899#if defined(RELAY_PORT)
563f0b8a 3900 u_int16_t relay_port = 0;
27058b3e 3901#endif
b1dd98c9 3902 struct data_string d1;
98311e4b 3903 const char *s;
9cc3ad7f
TL
3904
3905 if (!state)
8ae2d595 3906 log_fatal ("dhcp_reply was supplied lease with no state!");
11b37280 3907
9cc3ad7f 3908 /* Compose a response for the client... */
11b37280 3909 memset (&raw, 0, sizeof raw);
5d25508c 3910 memset (&d1, 0, sizeof d1);
11b37280
TL
3911
3912 /* Copy in the filename if given; otherwise, flag the filename
3913 buffer as available for options. */
b1dd98c9
TL
3914 if (state -> filename.len && state -> filename.data) {
3915 memcpy (raw.file,
3916 state -> filename.data,
3917 state -> filename.len > sizeof raw.file
3918 ? sizeof raw.file : state -> filename.len);
3919 if (sizeof raw.file > state -> filename.len)
3920 memset (&raw.file [state -> filename.len], 0,
3921 (sizeof raw.file) - state -> filename.len);
a5b21e16 3922 else
66be0ad1 3923 log_info("file name longer than packet field "
a5b21e16 3924 "truncated - field: %lu name: %d %.*s",
228e4447 3925 (unsigned long)sizeof(raw.file),
4176a700 3926 state->filename.len, (int)state->filename.len,
228e4447 3927 state->filename.data);
b1dd98c9 3928 } else
11b37280
TL
3929 bufs |= 1;
3930
3931 /* Copy in the server name if given; otherwise, flag the
3932 server_name buffer as available for options. */
b1dd98c9
TL
3933 if (state -> server_name.len && state -> server_name.data) {
3934 memcpy (raw.sname,
3935 state -> server_name.data,
3936 state -> server_name.len > sizeof raw.sname
3937 ? sizeof raw.sname : state -> server_name.len);
3938 if (sizeof raw.sname > state -> server_name.len)
3939 memset (&raw.sname [state -> server_name.len], 0,
3940 (sizeof raw.sname) - state -> server_name.len);
a5b21e16 3941 else
66be0ad1 3942 log_info("server name longer than packet field "
a5b21e16 3943 "truncated - field: %lu name: %d %.*s",
228e4447
MA
3944 (unsigned long)sizeof(raw.sname),
3945 state->server_name.len,
4176a700 3946 (int)state->server_name.len,
66be0ad1 3947 state->server_name.data);
b1dd98c9 3948 } else
11b37280
TL
3949 bufs |= 2; /* XXX */
3950
2cbc0e48
TL
3951 memcpy (raw.chaddr,
3952 &lease -> hardware_addr.hbuf [1], sizeof raw.chaddr);
3953 raw.hlen = lease -> hardware_addr.hlen - 1;
3954 raw.htype = lease -> hardware_addr.hbuf [0];
11b37280 3955
c34fcd38
TL
3956 /* See if this is a Microsoft client that NUL-terminates its
3957 strings and expects us to do likewise... */
11b37280 3958 if (lease -> flags & MS_NULL_TERMINATION)
a52d8045 3959 nulltp = 1;
c34fcd38 3960 else
a52d8045
TL
3961 nulltp = 0;
3962
3963 /* See if this is a bootp client... */
3964 if (state -> offer)
3965 bootpp = 0;
3966 else
3967 bootpp = 1;
3968
3969 /* Insert such options as will fit into the buffer. */
ca1c700e 3970 packet_length = cons_options (state -> packet, &raw, lease,
9e383163 3971 (struct client_state *)0,
3c893bb6 3972 state -> max_message_size,
ca1c700e 3973 state -> packet -> options,
12c9957e 3974 state -> options, &global_scope,
eddb16f4 3975 bufs, nulltp, bootpp,
9030b313
TL
3976 &state -> parameter_request_list,
3977 (char *)0);
11b37280 3978
9cc3ad7f 3979 memcpy (&raw.ciaddr, &state -> ciaddr, sizeof raw.ciaddr);
685963dc 3980 memcpy (&raw.yiaddr, lease -> ip_addr.iabuf, 4);
10553ccb 3981 raw.siaddr = state -> siaddr;
9cc3ad7f 3982 raw.giaddr = state -> giaddr;
685963dc 3983
9cc3ad7f
TL
3984 raw.xid = state -> xid;
3985 raw.secs = state -> secs;
3986 raw.flags = state -> bootp_flags;
3987 raw.hops = state -> hops;
685963dc
TL
3988 raw.op = BOOTREPLY;
3989
98311e4b
DH
3990 if (lease -> client_hostname) {
3991 if ((strlen (lease -> client_hostname) <= 64) &&
28868515 3992 db_printable((unsigned char *)lease->client_hostname))
98311e4b
DH
3993 s = lease -> client_hostname;
3994 else
3995 s = "Hostname Unsuitable for Printing";
3996 } else
d9eefc5d
TL
3997 s = (char *)0;
3998
785c1a51
FD
3999 /* Make sure outgoing packets are at least as big
4000 as a BOOTP packet. */
4001 if (packet_length < BOOTP_MIN_LEN)
4002 packet_length = BOOTP_MIN_LEN;
4003
4004#if defined(DHCPv6) && defined(DHCP4o6)
4005 if (dhcpv4_over_dhcpv6 && (state->packet->dhcp4o6_response != NULL)) {
4006 /* Say what we're doing... */
4007 log_info ("DHCP4o6 %s on %s to %s %s%s%svia %s",
4008 (state -> offer
4009 ? (state -> offer == DHCPACK
4010 ? "DHCPACK" : "DHCPOFFER")
4011 : "BOOTREPLY"),
4012 piaddr (lease -> ip_addr),
4013 (lease -> hardware_addr.hlen
4014 ? print_hw_addr (lease -> hardware_addr.hbuf [0],
4015 lease -> hardware_addr.hlen - 1,
4016 &lease -> hardware_addr.hbuf [1])
4017 : print_hex_1(lease->uid_len, lease->uid, 60)),
4018 s ? "(" : "", s ? s : "", s ? ") " : "",
4019 piaddr(state->packet->client_addr));
4020
4021 /* fill dhcp4o6_response */
4022 state->packet->dhcp4o6_response->len = packet_length;
4023 state->packet->dhcp4o6_response->buffer = NULL;
4024 if (!buffer_allocate(&state->packet->dhcp4o6_response->buffer,
4025 packet_length, MDL)) {
4026 log_fatal("No memory to store DHCP4o6 reply.");
4027 }
4028 state->packet->dhcp4o6_response->data =
4029 state->packet->dhcp4o6_response->buffer->data;
4030 memcpy(state->packet->dhcp4o6_response->buffer->data,
4031 &raw, packet_length);
4032
4033 /* done */
4034 free_lease_state (state, MDL);
4035 lease -> state = (struct lease_state *)0;
4036
4037 return;
4038 }
4039#endif
4040
7a049f2c 4041 /* Say what we're doing... */
d9eefc5d 4042 log_info ("%s on %s to %s %s%s%svia %s",
86bbcc1c
TL
4043 (state -> offer
4044 ? (state -> offer == DHCPACK ? "DHCPACK" : "DHCPOFFER")
4045 : "BOOTREPLY"),
4046 piaddr (lease -> ip_addr),
2cbc0e48
TL
4047 (lease -> hardware_addr.hlen
4048 ? print_hw_addr (lease -> hardware_addr.hbuf [0],
4049 lease -> hardware_addr.hlen - 1,
4050 &lease -> hardware_addr.hbuf [1])
6d103865 4051 : print_hex_1(lease->uid_len, lease->uid, 60)),
fdd46b53
TL
4052 s ? "(" : "", s ? s : "", s ? ") " : "",
4053 (state -> giaddr.s_addr
4054 ? inet_ntoa (state -> giaddr)
4055 : state -> ip -> name));
7a049f2c 4056
785c1a51
FD
4057#ifdef DEBUG_PACKET
4058 dump_raw ((unsigned char *)&raw, packet_length);
4059#endif
4060
7a049f2c 4061 /* Set up the hardware address... */
11b37280 4062 hto.hlen = lease -> hardware_addr.hlen;
2cbc0e48 4063 memcpy (hto.hbuf, lease -> hardware_addr.hbuf, hto.hlen);
7a049f2c
TL
4064
4065 to.sin_family = AF_INET;
4066#ifdef HAVE_SA_LEN
4067 to.sin_len = sizeof to;
4068#endif
4069 memset (to.sin_zero, 0, sizeof to.sin_zero);
4070
563f0b8a
FD
4071#if defined(RELAY_PORT)
4072 relay_port = dhcp_check_relayport(state->packet);
4073#endif
4074
ed8bcd8f 4075 /* If this was gatewayed, send it back to the gateway... */
b88e8e15 4076 if (raw.giaddr.s_addr) {
ed8bcd8f 4077 to.sin_addr = raw.giaddr;
bfe2d221 4078 if (raw.giaddr.s_addr != htonl (INADDR_LOOPBACK))
27058b3e 4079#if defined(RELAY_PORT)
563f0b8a 4080 to.sin_port = relay_port ? relay_port : local_port;
27058b3e
FD
4081#else
4082 to.sin_port = local_port;
4083#endif
1b871100
TL
4084 else
4085 to.sin_port = remote_port; /* For debugging. */
8ec97099 4086
027f46cb 4087 if (fallback_interface) {
dd9237c3
TM
4088 result = send_packet(fallback_interface, NULL, &raw,
4089 packet_length, raw.siaddr, &to,
4090 NULL);
4091 if (result < 0) {
4092 log_error ("%s:%d: Failed to send %d byte long "
4093 "packet over %s interface.", MDL,
4094 packet_length,
4095 fallback_interface->name);
4096 }
4097
9cc3ad7f 4098
4bd8800e 4099 free_lease_state (state, MDL);
027f46cb
TL
4100 lease -> state = (struct lease_state *)0;
4101 return;
4102 }
b88e8e15 4103
566ecd40 4104 /* If the client is RENEWING, unicast to the client using the
cdc336ab
TL
4105 regular IP stack. Some clients, particularly those that
4106 follow RFC1541, are buggy, and send both ciaddr and server
4107 identifier. We deal with this situation by assuming that
4108 if we got both dhcp-server-identifier and ciaddr, and
4109 giaddr was not set, then the client is on the local
4110 network, and we can therefore unicast or broadcast to it
4111 successfully. A client in REQUESTING state on another
4112 network that's making this mistake will have set giaddr,
4113 and will therefore get a relayed response from the above
4114 code. */
4115 } else if (raw.ciaddr.s_addr &&
0af446bc
TL
4116 !((state -> got_server_identifier ||
4117 (raw.flags & htons (BOOTP_BROADCAST))) &&
4118 /* XXX This won't work if giaddr isn't zero, but it is: */
cdc336ab
TL
4119 (state -> shared_network ==
4120 lease -> subnet -> shared_network)) &&
4121 state -> offer == DHCPACK) {
531fa185 4122 to.sin_addr = raw.ciaddr;
566ecd40 4123 to.sin_port = remote_port;
b88e8e15 4124
027f46cb 4125 if (fallback_interface) {
dd9237c3
TM
4126 result = send_packet(fallback_interface, NULL, &raw,
4127 packet_length, raw.siaddr, &to,
4128 NULL);
4129 if (result < 0) {
4130 log_error("%s:%d: Failed to send %d byte long"
4131 " packet over %s interface.", MDL,
4132 packet_length,
4133 fallback_interface->name);
4134 }
4135
4bd8800e 4136 free_lease_state (state, MDL);
027f46cb
TL
4137 lease -> state = (struct lease_state *)0;
4138 return;
4139 }
e2cb6d53 4140
566ecd40
TL
4141 /* If it comes from a client that already knows its address
4142 and is not requesting a broadcast response, and we can
4143 unicast to a client without using the ARP protocol, sent it
4144 directly to that client. */
4145 } else if (!(raw.flags & htons (BOOTP_BROADCAST)) &&
531fa185
TL
4146 can_unicast_without_arp (state -> ip)) {
4147 to.sin_addr = raw.yiaddr;
566ecd40
TL
4148 to.sin_port = remote_port;
4149
ed8bcd8f 4150 /* Otherwise, broadcast it on the local network. */
b88e8e15 4151 } else {
71df44f5 4152 to.sin_addr = limited_broadcast;
566ecd40 4153 to.sin_port = remote_port;
bca94423
TL
4154 if (!(lease -> flags & UNICAST_BROADCAST_HACK))
4155 unicastp = 0;
b88e8e15 4156 }
ed8bcd8f 4157
5d25508c 4158 memcpy (&from, state -> from.iabuf, sizeof from);
fde927d2 4159
dd9237c3
TM
4160 result = send_packet(state->ip, NULL, &raw, packet_length,
4161 from, &to, unicastp ? &hto : NULL);
4162 if (result < 0) {
4163 log_error ("%s:%d: Failed to send %d byte long "
4164 "packet over %s interface.", MDL,
4165 packet_length, state->ip->name);
4166 }
4167
9cc3ad7f 4168
10553ccb
TL
4169 /* Free all of the entries in the option_state structure
4170 now that we're done with them. */
4171
4bd8800e 4172 free_lease_state (state, MDL);
9cc3ad7f 4173 lease -> state = (struct lease_state *)0;
d7837182 4174}
ed8bcd8f 4175
20916cae
TL
4176int find_lease (struct lease **lp,
4177 struct packet *packet, struct shared_network *share, int *ours,
88cd8aca 4178 int *peer_has_leases, struct lease *ip_lease_in,
9e383163 4179 const char *file, int line)
ed8bcd8f 4180{
20916cae
TL
4181 struct lease *uid_lease = (struct lease *)0;
4182 struct lease *ip_lease = (struct lease *)0;
4183 struct lease *hw_lease = (struct lease *)0;
7a049f2c 4184 struct lease *lease = (struct lease *)0;
ed8bcd8f 4185 struct iaddr cip;
20916cae
TL
4186 struct host_decl *hp = (struct host_decl *)0;
4187 struct host_decl *host = (struct host_decl *)0;
4188 struct lease *fixed_lease = (struct lease *)0;
4f767627 4189 struct lease *next = (struct lease *)0;
5d25508c
TL
4190 struct option_cache *oc;
4191 struct data_string d1;
4192 int have_client_identifier = 0;
4193 struct data_string client_identifier;
4d0aaa17 4194 struct hardware h;
ed8bcd8f 4195
66cebfcb 4196#if defined(FAILOVER_PROTOCOL)
88cd8aca
DH
4197 /* Quick check to see if the peer has leases. */
4198 if (peer_has_leases) {
4199 struct pool *pool;
4200
4201 for (pool = share->pools ; pool ; pool = pool->next) {
4202 dhcp_failover_state_t *peer = pool->failover_peer;
4203
4204 if (peer &&
4205 ((peer->i_am == primary && pool->backup_leases) ||
4206 (peer->i_am == secondary && pool->free_leases))) {
4207 *peer_has_leases = 1;
4208 break;
4209 }
4210 }
4211 }
66cebfcb 4212#endif /* FAILOVER_PROTOCOL */
88cd8aca 4213
9e383163 4214 if (packet -> raw -> ciaddr.s_addr) {
74f45f96
TL
4215 cip.len = 4;
4216 memcpy (cip.iabuf, &packet -> raw -> ciaddr, 4);
9e383163
TL
4217 } else {
4218 /* Look up the requested address. */
4219 oc = lookup_option (&dhcp_universe, packet -> options,
4220 DHO_DHCP_REQUESTED_ADDRESS);
4221 memset (&d1, 0, sizeof d1);
4222 if (oc &&
4223 evaluate_option_cache (&d1, packet, (struct lease *)0,
4224 (struct client_state *)0,
4225 packet -> options,
4226 (struct option_state *)0,
4227 &global_scope, oc, MDL)) {
4228 packet -> got_requested_address = 1;
4229 cip.len = 4;
4230 memcpy (cip.iabuf, d1.data, cip.len);
4231 data_string_forget (&d1, MDL);
a5b21e16 4232 } else
9e383163
TL
4233 cip.len = 0;
4234 }
74f45f96 4235
7a049f2c
TL
4236 /* Try to find a host or lease that's been assigned to the
4237 specified unique client identifier. */
951323fe 4238 oc = lookup_option (&dhcp_universe, packet -> options,
5d25508c
TL
4239 DHO_DHCP_CLIENT_IDENTIFIER);
4240 memset (&client_identifier, 0, sizeof client_identifier);
4241 if (oc &&
4242 evaluate_option_cache (&client_identifier,
ca1c700e 4243 packet, (struct lease *)0,
9e383163 4244 (struct client_state *)0,
ca1c700e 4245 packet -> options, (struct option_state *)0,
12c9957e 4246 &global_scope, oc, MDL)) {
5d25508c
TL
4247 /* Remember this for later. */
4248 have_client_identifier = 1;
4249
7a049f2c
TL
4250 /* First, try to find a fixed host entry for the specified
4251 client identifier... */
20916cae
TL
4252 if (find_hosts_by_uid (&hp, client_identifier.data,
4253 client_identifier.len, MDL)) {
f63b4929
TL
4254 /* Remember if we know of this client. */
4255 packet -> known = 1;
20916cae
TL
4256 mockup_lease (&fixed_lease, packet, share, hp);
4257 }
5d25508c 4258
5d25508c 4259#if defined (DEBUG_FIND_LEASE)
74f45f96 4260 if (fixed_lease) {
8ae2d595 4261 log_info ("Found host for client identifier: %s.",
5d25508c 4262 piaddr (fixed_lease -> ip_addr));
74f45f96 4263 }
5d25508c 4264#endif
7f65aa81
TL
4265 if (hp) {
4266 if (!fixed_lease) /* Save the host if we found one. */
4267 host_reference (&host, hp, MDL);
20916cae 4268 host_dereference (&hp, MDL);
7f65aa81 4269 }
5d25508c 4270
20916cae
TL
4271 find_lease_by_uid (&uid_lease, client_identifier.data,
4272 client_identifier.len, MDL);
7a049f2c
TL
4273 }
4274
4275 /* If we didn't find a fixed lease using the uid, try doing
4276 it with the hardware address... */
5d25508c 4277 if (!fixed_lease && !host) {
20916cae
TL
4278 if (find_hosts_by_haddr (&hp, packet -> raw -> htype,
4279 packet -> raw -> chaddr,
4280 packet -> raw -> hlen, MDL)) {
f63b4929
TL
4281 /* Remember if we know of this client. */
4282 packet -> known = 1;
20916cae
TL
4283 if (host)
4284 host_dereference (&host, MDL);
4285 host_reference (&host, hp, MDL);
4286 host_dereference (&hp, MDL);
4287 mockup_lease (&fixed_lease, packet, share, host);
5d25508c
TL
4288#if defined (DEBUG_FIND_LEASE)
4289 if (fixed_lease) {
74f45f96 4290 log_info ("Found host for link address: %s.",
5d25508c
TL
4291 piaddr (fixed_lease -> ip_addr));
4292 }
4293#endif
7a049f2c
TL
4294 }
4295 }
ed8bcd8f 4296
bd0b98c1
SR
4297 /* Finally, if we haven't found anything yet try again with the
4298 * host-identifier option ... */
4299 if (!fixed_lease && !host) {
4300 if (find_hosts_by_option(&hp, packet,
4301 packet->options, MDL) == 1) {
4302 packet->known = 1;
4303 if (host)
4304 host_dereference(&host, MDL);
4305 host_reference(&host, hp, MDL);
4306 host_dereference(&hp, MDL);
4307 mockup_lease (&fixed_lease, packet, share, host);
4308#if defined (DEBUG_FIND_LEASE)
4309 if (fixed_lease) {
4310 log_info ("Found host via host-identifier");
4311 }
4312#endif
4313 }
4314 }
4315
74f45f96
TL
4316 /* If fixed_lease is present but does not match the requested
4317 IP address, and this is a DHCPREQUEST, then we can't return
4318 any other lease, so we might as well return now. */
4319 if (packet -> packet_type == DHCPREQUEST && fixed_lease &&
4320 (fixed_lease -> ip_addr.len != cip.len ||
4321 memcmp (fixed_lease -> ip_addr.iabuf,
4322 cip.iabuf, cip.len))) {
4323 if (ours)
4324 *ours = 1;
4325 strcpy (dhcp_message, "requested address is incorrect");
4326#if defined (DEBUG_FIND_LEASE)
4327 log_info ("Client's fixed-address %s doesn't match %s%s",
4328 piaddr (fixed_lease -> ip_addr), "request ",
4329 print_dotted_quads (cip.len, cip.iabuf));
4330#endif
4331 goto out;
4332 }
4333
fdfebedf
DH
4334 /*
4335 * If we found leases matching the client identifier, loop through
d5b6835f
DH
4336 * the n_uid pointer looking for one that's actually valid. We
4337 * can't do this until we get here because we depend on
4338 * packet -> known, which may be set by either the uid host
4339 * lookup or the haddr host lookup.
4340 *
4341 * Note that the n_uid lease chain is sorted in order of
4342 * preference, so the first one is the best one.
4343 */
20916cae 4344 while (uid_lease) {
3210786b 4345 isc_boolean_t do_release = !packet->raw->ciaddr.s_addr;
74f45f96
TL
4346#if defined (DEBUG_FIND_LEASE)
4347 log_info ("trying next lease matching client id: %s",
4348 piaddr (uid_lease -> ip_addr));
4349#endif
d758ad8c
TL
4350
4351#if defined (FAILOVER_PROTOCOL)
fdfebedf
DH
4352 /*
4353 * When we lookup a lease by uid, we know the client identifier
4354 * matches the lease's record. If it is active, or was last
4355 * active with the same client, we can trivially extend it.
4356 * If is not or was not active, we can allocate it to this
4357 * client if it matches the usual free/backup criteria (which
4358 * is contained in lease_mine_to_reallocate()).
4359 */
4360 if (uid_lease->binding_state != FTS_ACTIVE &&
4361 uid_lease->rewind_binding_state != FTS_ACTIVE &&
4362 !lease_mine_to_reallocate(uid_lease)) {
d758ad8c 4363#if defined (DEBUG_FIND_LEASE)
fdfebedf
DH
4364 log_info("not active or not mine to allocate: %s",
4365 piaddr(uid_lease->ip_addr));
d758ad8c
TL
4366#endif
4367 goto n_uid;
4368 }
4369#endif
4370
74f45f96
TL
4371 if (uid_lease -> subnet -> shared_network != share) {
4372#if defined (DEBUG_FIND_LEASE)
4373 log_info ("wrong network segment: %s",
4374 piaddr (uid_lease -> ip_addr));
4375#endif
3210786b
TM
4376 /* Allow multiple leases using the same UID
4377 on different subnetworks. */
4378 do_release = ISC_FALSE;
d758ad8c 4379 goto n_uid;
74f45f96 4380 }
d758ad8c 4381
74f45f96 4382 if ((uid_lease -> pool -> prohibit_list &&
951323fe 4383 permitted (packet, uid_lease -> pool -> prohibit_list)) ||
74f45f96
TL
4384 (uid_lease -> pool -> permit_list &&
4385 !permitted (packet, uid_lease -> pool -> permit_list))) {
4386#if defined (DEBUG_FIND_LEASE)
4387 log_info ("not permitted: %s",
4388 piaddr (uid_lease -> ip_addr));
4389#endif
d758ad8c 4390 n_uid:
bfe2d221
TL
4391 if (uid_lease -> n_uid)
4392 lease_reference (&next,
4393 uid_lease -> n_uid, MDL);
3210786b 4394 if (do_release)
43f23dcc 4395 release_lease (uid_lease, packet);
20916cae 4396 lease_dereference (&uid_lease, MDL);
bfe2d221
TL
4397 if (next) {
4398 lease_reference (&uid_lease, next, MDL);
4399 lease_dereference (&next, MDL);
4400 }
74f45f96
TL
4401 continue;
4402 }
4403 break;
4404 }
4405#if defined (DEBUG_FIND_LEASE)
4406 if (uid_lease)
4407 log_info ("Found lease for client id: %s.",
4408 piaddr (uid_lease -> ip_addr));
4409#endif
4410
4411 /* Find a lease whose hardware address matches, whose client
d5b6835f
DH
4412 * identifier matches (or equally doesn't have one), that's
4413 * permitted, and that's on the correct subnet.
4414 *
4415 * Note that the n_hw chain is sorted in order of preference, so
4416 * the first one found is the best one.
4417 */
4d0aaa17
TL
4418 h.hlen = packet -> raw -> hlen + 1;
4419 h.hbuf [0] = packet -> raw -> htype;
4420 memcpy (&h.hbuf [1], packet -> raw -> chaddr, packet -> raw -> hlen);
20916cae
TL
4421 find_lease_by_hw_addr (&hw_lease, h.hbuf, h.hlen, MDL);
4422 while (hw_lease) {
74f45f96
TL
4423#if defined (DEBUG_FIND_LEASE)
4424 log_info ("trying next lease matching hw addr: %s",
4425 piaddr (hw_lease -> ip_addr));
4426#endif
d758ad8c 4427#if defined (FAILOVER_PROTOCOL)
fdfebedf
DH
4428 /*
4429 * When we lookup a lease by chaddr, we know the MAC address
4430 * matches the lease record (we will check if the lease has a
4431 * client-id the client does not next). If the lease is
4432 * currently active or was last active with this client, we can
4433 * trivially extend it. Otherwise, there are a set of rules
4434 * that govern if we can reallocate this lease to any client
4435 * ("lease_mine_to_reallocate()") including this one.
4436 */
4437 if (hw_lease->binding_state != FTS_ACTIVE &&
4438 hw_lease->rewind_binding_state != FTS_ACTIVE &&
4439 !lease_mine_to_reallocate(hw_lease)) {
d758ad8c 4440#if defined (DEBUG_FIND_LEASE)
fdfebedf
DH
4441 log_info("not active or not mine to allocate: %s",
4442 piaddr(hw_lease->ip_addr));
d758ad8c
TL
4443#endif
4444 goto n_hw;
4445 }
4446#endif
4447
fdfebedf
DH
4448 /*
4449 * This conditional skips "potentially active" leases (leases
4450 * we think are expired may be extended by the peer, etc) that
4451 * may be assigned to a differently /client-identified/ client
4452 * with the same MAC address.
4453 */
d758ad8c
TL
4454 if (hw_lease -> binding_state != FTS_FREE &&
4455 hw_lease -> binding_state != FTS_BACKUP &&
74f45f96
TL
4456 hw_lease -> uid &&
4457 (!have_client_identifier ||
4458 hw_lease -> uid_len != client_identifier.len ||
4459 memcmp (hw_lease -> uid, client_identifier.data,
4460 hw_lease -> uid_len))) {
4461#if defined (DEBUG_FIND_LEASE)
4462 log_info ("wrong client identifier: %s",
4463 piaddr (hw_lease -> ip_addr));
4464#endif
d758ad8c 4465 goto n_hw;
74f45f96
TL
4466 }
4467 if (hw_lease -> subnet -> shared_network != share) {
4468#if defined (DEBUG_FIND_LEASE)
4469 log_info ("wrong network segment: %s",
4470 piaddr (hw_lease -> ip_addr));
4471#endif
d758ad8c 4472 goto n_hw;
355bf452 4473 }
74f45f96
TL
4474 if ((hw_lease -> pool -> prohibit_list &&
4475 permitted (packet, hw_lease -> pool -> prohibit_list)) ||
4476 (hw_lease -> pool -> permit_list &&
4477 !permitted (packet, hw_lease -> pool -> permit_list))) {
4478#if defined (DEBUG_FIND_LEASE)
4479 log_info ("not permitted: %s",
4480 piaddr (hw_lease -> ip_addr));
4481#endif
74f45f96 4482 if (!packet -> raw -> ciaddr.s_addr)
43f23dcc 4483 release_lease (hw_lease, packet);
d758ad8c
TL
4484 n_hw:
4485 if (hw_lease -> n_hw)
4486 lease_reference (&next, hw_lease -> n_hw, MDL);
20916cae 4487 lease_dereference (&hw_lease, MDL);
bfe2d221
TL
4488 if (next) {
4489 lease_reference (&hw_lease, next, MDL);
4490 lease_dereference (&next, MDL);
4491 }
74f45f96
TL
4492 continue;
4493 }
4494 break;
355bf452 4495 }
5d25508c
TL
4496#if defined (DEBUG_FIND_LEASE)
4497 if (hw_lease)
8ae2d595 4498 log_info ("Found lease for hardware address: %s.",
5d25508c
TL
4499 piaddr (hw_lease -> ip_addr));
4500#endif
ed8bcd8f
TL
4501
4502 /* Try to find a lease that's been allocated to the client's
4503 IP address. */
9e383163
TL
4504 if (ip_lease_in)
4505 lease_reference (&ip_lease, ip_lease_in, MDL);
4506 else if (cip.len)
20916cae 4507 find_lease_by_ip_addr (&ip_lease, cip, MDL);
5d25508c
TL
4508
4509#if defined (DEBUG_FIND_LEASE)
4510 if (ip_lease)
8ae2d595 4511 log_info ("Found lease for requested address: %s.",
5d25508c
TL
4512 piaddr (ip_lease -> ip_addr));
4513#endif
ed8bcd8f 4514
fa97acc1
TL
4515 /* If ip_lease is valid at this point, set ours to one, so that
4516 even if we choose a different lease, we know that the address
4517 the client was requesting was ours, and thus we can NAK it. */
be6b4b2a 4518 if (ip_lease && ours)
fa97acc1
TL
4519 *ours = 1;
4520
4fbcd991 4521 /* If the requested IP address isn't on the network the packet
c54885bd
TL
4522 came from, don't use it. Allow abandoned leases to be matched
4523 here - if the client is requesting it, there's a decent chance
4524 that it's because the lease database got trashed and a client
4525 that thought it had this lease answered an ARP or PING, causing the
4526 lease to be abandoned. If so, this request probably came from
4527 that client. */
027f46cb 4528 if (ip_lease && (ip_lease -> subnet -> shared_network != share)) {
74f45f96
TL
4529 if (ours)
4530 *ours = 1;
4531#if defined (DEBUG_FIND_LEASE)
8ae2d595 4532 log_info ("...but it was on the wrong shared network.");
74f45f96
TL
4533#endif
4534 strcpy (dhcp_message, "requested address on bad subnet");
20916cae 4535 lease_dereference (&ip_lease, MDL);
5d25508c 4536 }
4fbcd991 4537
fdfebedf
DH
4538 /*
4539 * If the requested address is in use (or potentially in use) by
4540 * a different client, it can't be granted.
4541 *
4542 * This first conditional only detects if the lease is currently
4543 * identified to a different client (client-id and/or chaddr
4544 * mismatch). In this case we may not want to give the client the
4545 * lease, if doing so may potentially be an addressing conflict.
4546 */
f8cd781e 4547 if (ip_lease &&
bb0b00a5
TL
4548 (ip_lease -> uid ?
4549 (!have_client_identifier ||
4550 ip_lease -> uid_len != client_identifier.len ||
4551 memcmp (ip_lease -> uid, client_identifier.data,
4552 ip_lease -> uid_len)) :
d642c2a6
TL
4553 (ip_lease -> hardware_addr.hbuf [0] != packet -> raw -> htype ||
4554 ip_lease -> hardware_addr.hlen != packet -> raw -> hlen + 1 ||
4555 memcmp (&ip_lease -> hardware_addr.hbuf [1],
4556 packet -> raw -> chaddr,
4557 (unsigned)(ip_lease -> hardware_addr.hlen - 1))))) {
fdfebedf
DH
4558 /*
4559 * A lease is unavailable for allocation to a new client if
4560 * it is not in the FREE or BACKUP state. There may be
4561 * leases that are in the expired state with a rewinding
4562 * state that is free or backup, but these will be processed
4563 * into the free or backup states by expiration processes, so
4564 * checking for them here is superfluous.
4565 */
d758ad8c
TL
4566 if (ip_lease -> binding_state != FTS_FREE &&
4567 ip_lease -> binding_state != FTS_BACKUP) {
5d25508c 4568#if defined (DEBUG_FIND_LEASE)
8ae2d595 4569 log_info ("rejecting lease for requested address.");
5d25508c 4570#endif
dbc855c9
TL
4571 /* If we're rejecting it because the peer has
4572 it, don't set "ours", because we shouldn't NAK. */
4573 if (ours && ip_lease -> binding_state != FTS_ACTIVE)
4574 *ours = 0;
007e3ee4 4575 lease_dereference (&ip_lease, MDL);
88cd8aca 4576 }
5d25508c
TL
4577 }
4578
fdfebedf
DH
4579 /*
4580 * If we got an ip_lease and a uid_lease or hw_lease, and ip_lease
4581 * is/was not active, and is not ours to reallocate, forget about it.
4582 */
d758ad8c 4583 if (ip_lease && (uid_lease || hw_lease) &&
fdfebedf
DH
4584 ip_lease->binding_state != FTS_ACTIVE &&
4585 ip_lease->rewind_binding_state != FTS_ACTIVE &&
66cebfcb 4586#if defined(FAILOVER_PROTOCOL)
fdfebedf 4587 !lease_mine_to_reallocate(ip_lease) &&
66cebfcb 4588#endif
fdfebedf 4589 packet->packet_type == DHCPDISCOVER) {
d758ad8c 4590#if defined (DEBUG_FIND_LEASE)
fdfebedf 4591 log_info("ip lease not active or not ours to offer.");
d758ad8c 4592#endif
fdfebedf 4593 lease_dereference(&ip_lease, MDL);
d758ad8c
TL
4594 }
4595
5d25508c
TL
4596 /* If for some reason the client has more than one lease
4597 on the subnet that matches its uid, pick the one that
4598 it asked for and (if we can) free the other. */
a55ccdd0
DH
4599 if (ip_lease && ip_lease->binding_state == FTS_ACTIVE &&
4600 ip_lease->uid && ip_lease != uid_lease) {
74f45f96 4601 if (have_client_identifier &&
5d25508c
TL
4602 (ip_lease -> uid_len == client_identifier.len) &&
4603 !memcmp (client_identifier.data,
599c23c1 4604 ip_lease -> uid, ip_lease -> uid_len)) {
eeea1395 4605 if (uid_lease) {
a55ccdd0 4606 if (uid_lease->binding_state == FTS_ACTIVE) {
74f45f96 4607 log_error ("client %s has duplicate%s on %s",
74f45f96
TL
4608 (print_hw_addr
4609 (packet -> raw -> htype,
4610 packet -> raw -> hlen,
4611 packet -> raw -> chaddr)),
12c9957e
TL
4612 " leases",
4613 (ip_lease -> subnet ->
4614 shared_network -> name));
48984237 4615
eeea1395
TL
4616 /* If the client is REQUESTing the lease,
4617 it shouldn't still be using the old
4618 one, so we can free it for allocation. */
4619 if (uid_lease &&
a55ccdd0 4620 uid_lease->binding_state == FTS_ACTIVE &&
eeea1395
TL
4621 !packet -> raw -> ciaddr.s_addr &&
4622 (share ==
a1e9fabd
TL
4623 uid_lease -> subnet -> shared_network) &&
4624 packet -> packet_type == DHCPREQUEST)
88cd8aca 4625 release_lease (uid_lease, packet);
eeea1395 4626 }
20916cae
TL
4627 lease_dereference (&uid_lease, MDL);
4628 lease_reference (&uid_lease, ip_lease, MDL);
eeea1395 4629 }
599c23c1 4630 }
f8cd781e 4631
74f45f96
TL
4632 /* If we get to here and fixed_lease is not null, that means
4633 that there are both a dynamic lease and a fixed-address
4634 declaration for the same IP address. */
4635 if (packet -> packet_type == DHCPREQUEST && fixed_lease) {
20916cae 4636 lease_dereference (&fixed_lease, MDL);
74f45f96 4637 db_conflict:
c5b0f529
TL
4638 log_error ("Dynamic and static leases present for %s.",
4639 piaddr (cip));
4640 log_error ("Remove host declaration %s or remove %s",
4641 (fixed_lease && fixed_lease -> host
4642 ? (fixed_lease -> host -> name
4643 ? fixed_lease -> host -> name
4644 : piaddr (cip))
4645 : piaddr (cip)),
4646 piaddr (cip));
4647 log_error ("from the dynamic address pool for %s",
4648 ip_lease -> subnet -> shared_network -> name
4649 );
74f45f96 4650 if (fixed_lease)
20916cae 4651 lease_dereference (&ip_lease, MDL);
74f45f96
TL
4652 strcpy (dhcp_message,
4653 "database conflict - call for help!");
4654 }
9e383163
TL
4655
4656 if (ip_lease && ip_lease != uid_lease) {
4657#if defined (DEBUG_FIND_LEASE)
4658 log_info ("requested address not available.");
4659#endif
4660 lease_dereference (&ip_lease, MDL);
4661 }
5d25508c 4662 }
f8cd781e 4663
74f45f96
TL
4664 /* If we get to here with both fixed_lease and ip_lease not
4665 null, then we have a configuration file bug. */
4666 if (packet -> packet_type == DHCPREQUEST && fixed_lease && ip_lease)
4667 goto db_conflict;
4668
74f45f96 4669 /* Toss extra pointers to the same lease... */
20916cae 4670 if (hw_lease && hw_lease == uid_lease) {
5d25508c 4671#if defined (DEBUG_FIND_LEASE)
8ae2d595 4672 log_info ("hardware lease and uid lease are identical.");
5d25508c 4673#endif
20916cae 4674 lease_dereference (&hw_lease, MDL);
5d25508c 4675 }
20916cae
TL
4676 if (ip_lease && ip_lease == hw_lease) {
4677 lease_dereference (&hw_lease, MDL);
74f45f96
TL
4678#if defined (DEBUG_FIND_LEASE)
4679 log_info ("hardware lease and ip lease are identical.");
4680#endif
4681 }
20916cae
TL
4682 if (ip_lease && ip_lease == uid_lease) {
4683 lease_dereference (&uid_lease, MDL);
5d25508c 4684#if defined (DEBUG_FIND_LEASE)
8ae2d595 4685 log_info ("uid lease and ip lease are identical.");
5d25508c
TL
4686#endif
4687 }
ed8bcd8f 4688
007e3ee4
TL
4689 /* Make sure the client is permitted to use the requested lease. */
4690 if (ip_lease &&
4691 ((ip_lease -> pool -> prohibit_list &&
4692 permitted (packet, ip_lease -> pool -> prohibit_list)) ||
4693 (ip_lease -> pool -> permit_list &&
4694 !permitted (packet, ip_lease -> pool -> permit_list)))) {
88cd8aca
DH
4695 if (!packet->raw->ciaddr.s_addr &&
4696 (ip_lease->binding_state == FTS_ACTIVE))
007e3ee4 4697 release_lease (ip_lease, packet);
88cd8aca 4698
007e3ee4
TL
4699 lease_dereference (&ip_lease, MDL);
4700 }
4701
4702 if (uid_lease &&
4703 ((uid_lease -> pool -> prohibit_list &&
4704 permitted (packet, uid_lease -> pool -> prohibit_list)) ||
4705 (uid_lease -> pool -> permit_list &&
4706 !permitted (packet, uid_lease -> pool -> permit_list)))) {
4707 if (!packet -> raw -> ciaddr.s_addr)
4708 release_lease (uid_lease, packet);
4709 lease_dereference (&uid_lease, MDL);
4710 }
4711
4712 if (hw_lease &&
4713 ((hw_lease -> pool -> prohibit_list &&
4714 permitted (packet, hw_lease -> pool -> prohibit_list)) ||
4715 (hw_lease -> pool -> permit_list &&
4716 !permitted (packet, hw_lease -> pool -> permit_list)))) {
4717 if (!packet -> raw -> ciaddr.s_addr)
4718 release_lease (hw_lease, packet);
4719 lease_dereference (&hw_lease, MDL);
4720 }
4721
b88e8e15
TL
4722 /* If we've already eliminated the lease, it wasn't there to
4723 begin with. If we have come up with a matching lease,
4724 set the message to bad network in case we have to throw it out. */
74f45f96 4725 if (!ip_lease) {
b88e8e15 4726 strcpy (dhcp_message, "requested address not available");
b88e8e15
TL
4727 }
4728
74f45f96
TL
4729 /* If this is a DHCPREQUEST, make sure the lease we're going to return
4730 matches the requested IP address. If it doesn't, don't return a
4731 lease at all. */
4732 if (packet -> packet_type == DHCPREQUEST &&
4733 !ip_lease && !fixed_lease) {
5d25508c 4734#if defined (DEBUG_FIND_LEASE)
74f45f96 4735 log_info ("no applicable lease found for DHCPREQUEST.");
5d25508c 4736#endif
74f45f96 4737 goto out;
ed8bcd8f
TL
4738 }
4739
7a049f2c 4740 /* At this point, if fixed_lease is nonzero, we can assign it to
ed8bcd8f 4741 this client. */
4fbcd991 4742 if (fixed_lease) {
20916cae
TL
4743 lease_reference (&lease, fixed_lease, MDL);
4744 lease_dereference (&fixed_lease, MDL);
5d25508c 4745#if defined (DEBUG_FIND_LEASE)
8ae2d595 4746 log_info ("choosing fixed address.");
5d25508c 4747#endif
4fbcd991 4748 }
7a049f2c
TL
4749
4750 /* If we got a lease that matched the ip address and don't have
4751 a better offer, use that; otherwise, release it. */
4752 if (ip_lease) {
4753 if (lease) {
74f45f96 4754 if (!packet -> raw -> ciaddr.s_addr)
43f23dcc 4755 release_lease (ip_lease, packet);
5d25508c 4756#if defined (DEBUG_FIND_LEASE)
8ae2d595 4757 log_info ("not choosing requested address (!).");
5d25508c 4758#endif
6b797e44 4759 lease_dereference (&ip_lease, MDL);
7a049f2c 4760 } else {
5d25508c 4761#if defined (DEBUG_FIND_LEASE)
8ae2d595 4762 log_info ("choosing lease on requested address.");
5d25508c 4763#endif
20916cae
TL
4764 lease_reference (&lease, ip_lease, MDL);
4765 if (lease -> host)
4766 host_dereference (&lease -> host, MDL);
7a049f2c
TL
4767 }
4768 }
ed8bcd8f
TL
4769
4770 /* If we got a lease that matched the client identifier, we may want
4771 to use it, but if we already have a lease we like, we must free
4772 the lease that matched the client identifier. */
4773 if (uid_lease) {
4774 if (lease) {
88cd8aca
DH
4775 log_error("uid lease %s for client %s is duplicate "
4776 "on %s",
4777 piaddr(uid_lease->ip_addr),
4778 print_hw_addr(packet->raw->htype,
4779 packet->raw->hlen,
4780 packet->raw->chaddr),
4781 uid_lease->subnet->shared_network->name);
4782
a1e9fabd 4783 if (!packet -> raw -> ciaddr.s_addr &&
d758ad8c 4784 packet -> packet_type == DHCPREQUEST &&
a55ccdd0 4785 uid_lease -> binding_state == FTS_ACTIVE)
88cd8aca 4786 release_lease(uid_lease, packet);
5d25508c 4787#if defined (DEBUG_FIND_LEASE)
8ae2d595 4788 log_info ("not choosing uid lease.");
5d25508c 4789#endif
7a049f2c 4790 } else {
20916cae
TL
4791 lease_reference (&lease, uid_lease, MDL);
4792 if (lease -> host)
4793 host_dereference (&lease -> host, MDL);
5d25508c 4794#if defined (DEBUG_FIND_LEASE)
8ae2d595 4795 log_info ("choosing uid lease.");
5d25508c 4796#endif
7a049f2c 4797 }
20916cae 4798 lease_dereference (&uid_lease, MDL);
ed8bcd8f
TL
4799 }
4800
4801 /* The lease that matched the hardware address is treated likewise. */
4802 if (hw_lease) {
4803 if (lease) {
5d25508c 4804#if defined (DEBUG_FIND_LEASE)
8ae2d595 4805 log_info ("not choosing hardware lease.");
5d25508c 4806#endif
7a049f2c 4807 } else {
7f65aa81
TL
4808 /* We're a little lax here - if the client didn't
4809 send a client identifier and it's a bootp client,
4810 but the lease has a client identifier, we still
4811 let the client have a lease. */
4812 if (!hw_lease -> uid_len ||
4813 (have_client_identifier
4814 ? (hw_lease -> uid_len ==
4815 client_identifier.len &&
4816 !memcmp (hw_lease -> uid,
4817 client_identifier.data,
4818 client_identifier.len))
4819 : packet -> packet_type == 0)) {
4820 lease_reference (&lease, hw_lease, MDL);
4821 if (lease -> host)
4822 host_dereference (&lease -> host, MDL);
5d25508c 4823#if defined (DEBUG_FIND_LEASE)
7f65aa81 4824 log_info ("choosing hardware lease.");
5d25508c 4825#endif
7f65aa81
TL
4826 } else {
4827#if defined (DEBUG_FIND_LEASE)
4828 log_info ("not choosing hardware lease: %s.",
4829 "uid mismatch");
4830#endif
4831 }
7a049f2c 4832 }
20916cae 4833 lease_dereference (&hw_lease, MDL);
7a049f2c
TL
4834 }
4835
ea75d544
DH
4836 /*
4837 * If we found a host_decl but no matching address, try to
4838 * find a host_decl that has no address, and if there is one,
4839 * hang it off the lease so that we can use the supplied
4840 * options.
4841 */
4842 if (lease && host && !lease->host) {
4843 struct host_decl *p = NULL;
4844 struct host_decl *n = NULL;
4845
4846 host_reference(&p, host, MDL);
4847 while (p != NULL) {
4848 if (!p->fixed_addr) {
4849 /*
4850 * If the lease is currently active, then it
4851 * must be allocated to the present client.
4852 * We store a reference to the host record on
4853 * the lease to save a lookup later (in
4854 * ack_lease()). We mustn't refer to the host
4855 * record on non-active leases because the
4856 * client may be denied later.
4857 *
4858 * XXX: Not having this reference (such as in
4859 * DHCPDISCOVER/INIT) means ack_lease will have
4860 * to perform this lookup a second time. This
4861 * hopefully isn't a problem as DHCPREQUEST is
4862 * more common than DHCPDISCOVER.
4863 */
4864 if (lease->binding_state == FTS_ACTIVE)
4865 host_reference(&lease->host, p, MDL);
4866
4867 host_dereference(&p, MDL);
7a049f2c
TL
4868 break;
4869 }
ea75d544
DH
4870 if (p->n_ipaddr != NULL)
4871 host_reference(&n, p->n_ipaddr, MDL);
4872 host_dereference(&p, MDL);
4873 if (n != NULL) {
4874 host_reference(&p, n, MDL);
4875 host_dereference(&n, MDL);
225fed91 4876 }
7a049f2c 4877 }
ed8bcd8f
TL
4878 }
4879
027f46cb
TL
4880 /* If we find an abandoned lease, but it's the one the client
4881 requested, we assume that previous bugginess on the part
4882 of the client, or a server database loss, caused the lease to
4883 be abandoned, so we reclaim it and let the client have it. */
007e3ee4
TL
4884 if (lease &&
4885 (lease -> binding_state == FTS_ABANDONED) &&
4886 lease == ip_lease &&
027f46cb 4887 packet -> packet_type == DHCPREQUEST) {
8ae2d595 4888 log_error ("Reclaiming REQUESTed abandoned IP address %s.",
c54885bd 4889 piaddr (lease -> ip_addr));
007e3ee4 4890 } else if (lease && (lease -> binding_state == FTS_ABANDONED)) {
027f46cb
TL
4891 /* Otherwise, if it's not the one the client requested, we do not
4892 return it - instead, we claim it's ours, causing a DHCPNAK to be
4893 sent if this lookup is for a DHCPREQUEST, and force the client
4894 to go back through the allocation process. */
4895 if (ours)
4896 *ours = 1;
20916cae 4897 lease_dereference (&lease, MDL);
c54885bd
TL
4898 }
4899
74f45f96
TL
4900 out:
4901 if (have_client_identifier)
4bd8800e 4902 data_string_forget (&client_identifier, MDL);
74f45f96 4903
20916cae
TL
4904 if (fixed_lease)
4905 lease_dereference (&fixed_lease, MDL);
4906 if (hw_lease)
4907 lease_dereference (&hw_lease, MDL);
4908 if (uid_lease)
4909 lease_dereference (&uid_lease, MDL);
4910 if (ip_lease)
4911 lease_dereference (&ip_lease, MDL);
4912 if (host)
4913 host_dereference (&host, MDL);
4914
4915 if (lease) {
74f45f96 4916#if defined (DEBUG_FIND_LEASE)
74f45f96
TL
4917 log_info ("Returning lease: %s.",
4918 piaddr (lease -> ip_addr));
74f45f96 4919#endif
20916cae
TL
4920 lease_reference (lp, lease, file, line);
4921 lease_dereference (&lease, MDL);
4922 return 1;
4923 }
4924#if defined (DEBUG_FIND_LEASE)
4925 log_info ("Not returning a lease.");
4926#endif
4927 return 0;
ed8bcd8f 4928}
7a049f2c
TL
4929
4930/* Search the provided host_decl structure list for an address that's on
4931 the specified shared network. If one is found, mock up and return a
4932 lease structure for it; otherwise return the null pointer. */
4933
20916cae
TL
4934int mockup_lease (struct lease **lp, struct packet *packet,
4935 struct shared_network *share, struct host_decl *hp)
7a049f2c 4936{
20916cae 4937 struct lease *lease = (struct lease *)0;
79f3c35c 4938 struct host_decl *rhp = (struct host_decl *)0;
a5b21e16 4939
98311e4b 4940 if (lease_allocate (&lease, MDL) != ISC_R_SUCCESS)
20916cae 4941 return 0;
98311e4b
DH
4942 if (host_reference (&rhp, hp, MDL) != ISC_R_SUCCESS) {
4943 lease_dereference (&lease, MDL);
79f3c35c 4944 return 0;
98311e4b 4945 }
20916cae 4946 if (!find_host_for_network (&lease -> subnet,
79f3c35c 4947 &rhp, &lease -> ip_addr, share)) {
20916cae 4948 lease_dereference (&lease, MDL);
98311e4b 4949 host_dereference (&rhp, MDL);
20916cae
TL
4950 return 0;
4951 }
79f3c35c
TL
4952 host_reference (&lease -> host, rhp, MDL);
4953 if (rhp -> client_identifier.len > sizeof lease -> uid_buf)
4954 lease -> uid = dmalloc (rhp -> client_identifier.len, MDL);
fb6297b1 4955 else
20916cae
TL
4956 lease -> uid = lease -> uid_buf;
4957 if (!lease -> uid) {
4958 lease_dereference (&lease, MDL);
79f3c35c 4959 host_dereference (&rhp, MDL);
20916cae
TL
4960 return 0;
4961 }
79f3c35c
TL
4962 memcpy (lease -> uid, rhp -> client_identifier.data,
4963 rhp -> client_identifier.len);
4964 lease -> uid_len = rhp -> client_identifier.len;
4965 lease -> hardware_addr = rhp -> interface;
6d103865 4966 lease -> starts = lease -> cltt = lease -> ends = MIN_TIME;
20916cae 4967 lease -> flags = STATIC_LEASE;
007e3ee4 4968 lease -> binding_state = FTS_FREE;
98311e4b 4969
20916cae 4970 lease_reference (lp, lease, MDL);
98311e4b 4971
20916cae 4972 lease_dereference (&lease, MDL);
79f3c35c 4973 host_dereference (&rhp, MDL);
20916cae 4974 return 1;
7a049f2c 4975}
f63b4929
TL
4976
4977/* Look through all the pools in a list starting with the specified pool
4978 for a free lease. We try to find a virgin lease if we can. If we
4979 don't find a virgin lease, we try to find a non-virgin lease that's
4980 free. If we can't find one of those, we try to reclaim an abandoned
4981 lease. If all of these possibilities fail to pan out, we don't return
4982 a lease at all. */
4983
20916cae 4984int allocate_lease (struct lease **lp, struct packet *packet,
65cf86d7 4985 struct pool *pool, int *peer_has_leases)
f63b4929 4986{
3933e2aa
SR
4987 struct lease *lease = NULL;
4988 struct lease *candl = NULL;
f63b4929 4989
98311e4b
DH
4990 for (; pool ; pool = pool -> next) {
4991 if ((pool -> prohibit_list &&
4992 permitted (packet, pool -> prohibit_list)) ||
4993 (pool -> permit_list &&
4994 !permitted (packet, pool -> permit_list)))
4995 continue;
f63b4929 4996
2cbc0e48 4997#if defined (FAILOVER_PROTOCOL)
98311e4b
DH
4998 /* Peer_has_leases just says that we found at least one
4999 free lease. If no free lease is returned, the caller
5000 can deduce that this means the peer is hogging all the
5001 free leases, so we can print a better error message. */
5002 /* XXX Do we need code here to ignore PEER_IS_OWNER and
5003 * XXX just check tstp if we're in, e.g., PARTNER_DOWN?
5004 * XXX Where do we deal with CONFLICT_DETECTED, et al? */
5005 /* XXX This should be handled by the lease binding "state
5006 * XXX machine" - that is, when we get here, if a lease
5007 * XXX could be allocated, it will have the correct
5008 * XXX binding state so that the following code will
5009 * XXX result in its being allocated. */
5010 /* Skip to the most expired lease in the pool that is not
5011 * owned by a failover peer. */
8fbb55ff 5012 if (pool->failover_peer != NULL) {
5cc6f201 5013 struct lease *peerl = NULL;
8fbb55ff 5014 if (pool->failover_peer->i_am == primary) {
3933e2aa 5015 candl = LEASE_GET_FIRST(pool->free);
8fbb55ff
DH
5016
5017 /*
5018 * In normal operation, we never want to touch
a5b21e16 5019 * the peer's leases. In partner-down
8fbb55ff
DH
5020 * operation, we need to be able to pick up
5021 * the peer's leases after STOS+MCLT.
5022 */
3933e2aa
SR
5023 peerl = LEASE_GET_FIRST(pool->backup);
5024 if (peerl != NULL) {
8fbb55ff 5025 if (((candl == NULL) ||
3933e2aa
SR
5026 (candl->ends > peerl->ends)) &&
5027 lease_mine_to_reallocate(peerl)) {
5028 candl = peerl;
8fbb55ff
DH
5029 } else {
5030 *peer_has_leases = 1;
5031 }
5032 }
98311e4b 5033 } else {
3933e2aa 5034 candl = LEASE_GET_FIRST(pool->backup);
8fbb55ff 5035
3933e2aa
SR
5036 peerl = LEASE_GET_FIRST(pool->free);
5037 if (peerl != NULL) {
8fbb55ff 5038 if (((candl == NULL) ||
3933e2aa
SR
5039 (candl->ends > peerl->ends)) &&
5040 lease_mine_to_reallocate(peerl)) {
5041 candl = peerl;
8fbb55ff
DH
5042 } else {
5043 *peer_has_leases = 1;
5044 }
5045 }
98311e4b 5046 }
8fbb55ff 5047
fdfebedf 5048 /* Try abandoned leases as a last resort. */
3933e2aa
SR
5049 peerl = LEASE_GET_FIRST(pool->abandoned);
5050 if ((candl == NULL) && (peerl != NULL) &&
5051 lease_mine_to_reallocate(peerl))
5052 candl = peerl;
98311e4b
DH
5053 } else
5054#endif
5055 {
3933e2aa
SR
5056 if (LEASE_NOT_EMPTY(pool->free))
5057 candl = LEASE_GET_FIRST(pool->free);
98311e4b 5058 else
3933e2aa 5059 candl = LEASE_GET_FIRST(pool->abandoned);
007e3ee4 5060 }
98311e4b 5061
8fbb55ff
DH
5062 /*
5063 * XXX: This may not match with documented expectation.
5064 * It's expected that when we OFFER a lease, we set its
5065 * ends time forward 2 minutes so that it gets sorted to
5066 * the end of its free list (avoiding a similar allocation
5067 * to another client). It is not expected that we issue a
5068 * "no free leases" error when the last lease has been
5069 * offered, but it's not exactly broken either.
5070 */
a5252220
TM
5071 if (!candl ||
5072 (candl->binding_state != FTS_ABANDONED &&
5073 (candl->ends > cur_time))) {
98311e4b 5074 continue;
a5252220 5075 }
98311e4b
DH
5076
5077 if (!lease) {
5078 lease = candl;
5079 continue;
f63b4929 5080 }
98311e4b 5081
fdfebedf
DH
5082 /*
5083 * There are tiers of lease state preference, listed here in
5084 * reverse order (least to most preferential):
5085 *
5086 * ABANDONED
5087 * FREE/BACKUP
5088 *
5089 * If the selected lease and candidate are both of the same
5090 * state, select the oldest (longest ago) expiration time
5091 * between the two. If the candidate lease is of a higher
5092 * preferred grade over the selected lease, use it.
5093 */
98311e4b
DH
5094 if ((lease -> binding_state == FTS_ABANDONED) &&
5095 ((candl -> binding_state != FTS_ABANDONED) ||
5096 (candl -> ends < lease -> ends))) {
5097 lease = candl;
5098 continue;
5099 } else if (candl -> binding_state == FTS_ABANDONED)
5100 continue;
5101
5102 if ((lease -> uid_len || lease -> hardware_addr.hlen) &&
5103 ((!candl -> uid_len && !candl -> hardware_addr.hlen) ||
5104 (candl -> ends < lease -> ends))) {
5105 lease = candl;
5106 continue;
5107 } else if (candl -> uid_len || candl -> hardware_addr.hlen)
5108 continue;
5109
5110 if (candl -> ends < lease -> ends)
5111 lease = candl;
f63b4929
TL
5112 }
5113
ea75d544
DH
5114 if (lease != NULL) {
5115 if (lease->binding_state == FTS_ABANDONED)
5116 log_error("Reclaiming abandoned lease %s.",
5117 piaddr(lease->ip_addr));
5118
5119 /*
5120 * XXX: For reliability, we go ahead and remove the host
5121 * record and try to move on. For correctness, if there
5122 * are any other stale host vectors, we want to find them.
5123 */
5124 if (lease->host != NULL) {
5125 log_debug("soft impossible condition (%s:%d): stale "
5126 "host \"%s\" found on lease %s", MDL,
5127 lease->host->name,
5128 piaddr(lease->ip_addr));
5129 host_dereference(&lease->host, MDL);
5130 }
f63b4929 5131
98311e4b
DH
5132 lease_reference (lp, lease, MDL);
5133 return 1;
f63b4929
TL
5134 }
5135
98311e4b 5136 return 0;
f63b4929
TL
5137}
5138
5139/* Determine whether or not a permit exists on a particular permit list
5140 that matches the specified packet, returning nonzero if so, zero if
5141 not. */
5142
5143int permitted (packet, permit_list)
5144 struct packet *packet;
5145 struct permit *permit_list;
5146{
5147 struct permit *p;
5148 int i;
5149
5150 for (p = permit_list; p; p = p -> next) {
5151 switch (p -> type) {
5152 case permit_unknown_clients:
5153 if (!packet -> known)
5154 return 1;
5155 break;
5156
5157 case permit_known_clients:
5158 if (packet -> known)
5159 return 1;
5160 break;
5161
5162 case permit_authenticated_clients:
5163 if (packet -> authenticated)
5164 return 1;
5165 break;
5166
5167 case permit_unauthenticated_clients:
5168 if (!packet -> authenticated)
5169 return 1;
5170 break;
5171
5172 case permit_all_clients:
5173 return 1;
5174
5175 case permit_dynamic_bootp_clients:
5176 if (!packet -> options_valid ||
5177 !packet -> packet_type)
5178 return 1;
5179 break;
a5b21e16 5180
f63b4929 5181 case permit_class:
00855426 5182 for (i = 0; i < packet -> class_count; i++) {
f63b4929
TL
5183 if (p -> class == packet -> classes [i])
5184 return 1;
00855426
TL
5185 if (packet -> classes [i] &&
5186 packet -> classes [i] -> superclass &&
5187 (packet -> classes [i] -> superclass ==
5188 p -> class))
5189 return 1;
5190 }
f63b4929 5191 break;
b1d3778c
DH
5192
5193 case permit_after:
5194 if (cur_time > p->after)
5195 return 1;
5196 break;
f63b4929
TL
5197 }
5198 }
5199 return 0;
5200}
5201
785c1a51
FD
5202#if defined(DHCPv6) && defined(DHCP4o6)
5203static int locate_network6 (packet)
5204 struct packet *packet;
5205{
5206 const struct packet *chk_packet;
5207 const struct in6_addr *link_addr, *first_link_addr;
5208 struct iaddr ia;
5209 struct data_string data;
5210 struct subnet *subnet = NULL;
5211 struct option_cache *oc;
5212
5213 /* from locate_network() */
5214
5215 /* See if there's a Relay Agent Link Selection Option, or a
5216 * Subnet Selection Option. The Link-Select and Subnet-Select
5217 * are formatted and used precisely the same, but we must prefer
5218 * the link-select over the subnet-select.
5219 * BTW in DHCPv4 over DHCPv6 no cross version relay was specified
5220 * so it is unlikely to see a link-select.
5221 */
5222 if ((oc = lookup_option(&agent_universe, packet->options,
5223 RAI_LINK_SELECT)) == NULL)
5224 oc = lookup_option(&dhcp_universe, packet->options,
5225 DHO_SUBNET_SELECTION);
5226
5227 /* If there's an option indicating link connection or subnet
5228 * selection, and it's valid, use it to figure out the subnet.
5229 * If it's not valid, fail.
5230 */
5231 if (oc) {
5232 memset(&data, 0, sizeof data);
5233 if (!evaluate_option_cache(&data, packet, NULL, NULL,
5234 packet->options, NULL,
5235 &global_scope, oc, MDL)) {
5236 return (0);
5237 }
5238 if (data.len == 0) {
5239 return (0);
5240 }
5241 if (data.len != 4) {
5242 data_string_forget(&data, MDL);
5243 return (0);
5244 }
5245 ia.len = 4;
5246 memcpy(ia.iabuf, data.data, 4);
5247 data_string_forget(&data, MDL);
5248
5249 if (find_subnet(&subnet, ia, MDL)) {
5250 shared_network_reference(&packet->shared_network,
5251 subnet->shared_network, MDL);
5252 subnet_dereference(&subnet, MDL);
5253 return (1);
5254 }
5255 return (0);
5256 }
5257
5258 /* See if there is a giaddr (still unlikely), if there is one
5259 * use it to figure out the subnet. If it's not valid, fail.
5260 */
5261 if (packet->raw->giaddr.s_addr) {
5262 ia.len = 4;
5263 memcpy(ia.iabuf, &packet->raw->giaddr, 4);
5264
5265 if (find_subnet(&subnet, ia, MDL)) {
5266 shared_network_reference(&packet->shared_network,
5267 subnet->shared_network, MDL);
5268 subnet_dereference(&subnet, MDL);
5269 return (1);
5270 }
5271 return (0);
5272 }
5273
5274 /* from shared_network_from_packet6() */
5275
5276 /* First, find the link address where the packet from the client
5277 * first appeared (if this packet was relayed).
5278 */
5279 first_link_addr = NULL;
5280 chk_packet = packet->dhcpv6_container_packet;
5281 while (chk_packet != NULL) {
5282 link_addr = &chk_packet->dhcpv6_link_address;
5283 if (!IN6_IS_ADDR_UNSPECIFIED(link_addr) &&
5284 !IN6_IS_ADDR_LINKLOCAL(link_addr)) {
5285 first_link_addr = link_addr;
5286 break;
5287 }
5288 chk_packet = chk_packet->dhcpv6_container_packet;
5289 }
5290
5291 /* If there is a relayed link address, find the subnet associated
5292 * with that, and use that to get the appropriate shared_network.
5293 */
5294 if (first_link_addr != NULL) {
5295 ia.len = sizeof(*first_link_addr);
5296 memcpy(ia.iabuf, first_link_addr, sizeof(*first_link_addr));
5297 if (find_subnet (&subnet, ia, MDL)) {
5298 shared_network_reference(&packet->shared_network,
5299 subnet->shared_network, MDL);
5300 subnet_dereference(&subnet, MDL);
5301 return (1);
5302 }
5303 return (0);
5304 }
5305
5306 /* If there is no link address, we will use the interface
5307 * that this packet came in on to pick the shared_network.
5308 */
5309 if (packet->interface != NULL) {
5310 if (packet->interface->shared_network == NULL)
5311 return (0);
5312 shared_network_reference(&packet->shared_network,
5313 packet->interface->shared_network,
5314 MDL);
5315 return (1);
5316 }
5317
5318 /* We shouldn't be able to get here but if there is no link
5319 * address and no interface we don't know where to get the
5320 * shared_network from, log an error and return an error.
5321 */
5322 log_error("No interface and no link address "
5323 "can't determine DHCP4o6 shared network");
5324 return (0);
5325}
5326#endif
5327
e2c5cba2
TL
5328int locate_network (packet)
5329 struct packet *packet;
5330{
5331 struct iaddr ia;
1a634d56 5332 struct data_string data;
20916cae 5333 struct subnet *subnet = (struct subnet *)0;
1a634d56 5334 struct option_cache *oc;
e2c5cba2 5335
785c1a51
FD
5336#if defined(DHCPv6) && defined(DHCP4o6)
5337 if (dhcpv4_over_dhcpv6 && (packet->dhcp4o6_response != NULL)) {
5338 return (locate_network6 (packet));
5339 }
5340#endif
5341
334bf491
DH
5342 /* See if there's a Relay Agent Link Selection Option, or a
5343 * Subnet Selection Option. The Link-Select and Subnet-Select
5344 * are formatted and used precisely the same, but we must prefer
5345 * the link-select over the subnet-select.
5346 */
5347 if ((oc = lookup_option(&agent_universe, packet->options,
5348 RAI_LINK_SELECT)) == NULL)
5349 oc = lookup_option(&dhcp_universe, packet->options,
5350 DHO_SUBNET_SELECTION);
1a634d56
TL
5351
5352 /* If there's no SSO and no giaddr, then use the shared_network
5353 from the interface, if there is one. If not, fail. */
5354 if (!oc && !packet -> raw -> giaddr.s_addr) {
20916cae
TL
5355 if (packet -> interface -> shared_network) {
5356 shared_network_reference
5357 (&packet -> shared_network,
5358 packet -> interface -> shared_network, MDL);
1a634d56 5359 return 1;
20916cae 5360 }
1a634d56
TL
5361 return 0;
5362 }
5363
334bf491
DH
5364 /* If there's an option indicating link connection, and it's valid,
5365 * use it to figure out the subnet. If it's not valid, fail.
5366 */
1a634d56
TL
5367 if (oc) {
5368 memset (&data, 0, sizeof data);
5369 if (!evaluate_option_cache (&data, packet, (struct lease *)0,
9e383163 5370 (struct client_state *)0,
1a634d56
TL
5371 packet -> options,
5372 (struct option_state *)0,
5373 &global_scope, oc, MDL)) {
1a634d56
TL
5374 return 0;
5375 }
0cd94b5e 5376
1a634d56 5377 if (data.len != 4) {
785c1a51 5378 data_string_forget (&data, MDL);
1a634d56
TL
5379 return 0;
5380 }
0cd94b5e 5381
1a634d56
TL
5382 ia.len = 4;
5383 memcpy (ia.iabuf, data.data, 4);
5384 data_string_forget (&data, MDL);
e2c5cba2 5385 } else {
1a634d56
TL
5386 ia.len = 4;
5387 memcpy (ia.iabuf, &packet -> raw -> giaddr, 4);
e2c5cba2 5388 }
1a634d56
TL
5389
5390 /* If we know the subnet on which the IP address lives, use it. */
20916cae
TL
5391 if (find_subnet (&subnet, ia, MDL)) {
5392 shared_network_reference (&packet -> shared_network,
5393 subnet -> shared_network, MDL);
5394 subnet_dereference (&subnet, MDL);
e2c5cba2 5395 return 1;
1a634d56
TL
5396 }
5397
5398 /* Otherwise, fail. */
e2c5cba2
TL
5399 return 0;
5400}
6d103865
SK
5401
5402/*
5403 * Try to figure out the source address to send packets from.
5404 *
f8380d3f
SR
5405 * from is the address structure we use to return any address
5406 * we find.
5407 *
5408 * options is the option cache to search. This may include
5409 * options from the incoming packet and configuration information.
6d103865 5410 *
f8380d3f 5411 * out_options is the outgoing option cache. This cache
e046c826 5412 * may be the same as options. If out_options isn't NULL
f8380d3f 5413 * we may save the server address option into it. We do so
e046c826 5414 * if out_options is different than options or if the option
f8380d3f
SR
5415 * wasn't in options and we needed to find the address elsewhere.
5416 *
5417 * packet is the state structure for the incoming packet
5418 *
5419 * When finding the address we first check to see if it is
5420 * in the options list. If it isn't we use the first address
5421 * from the interface.
5422 *
5423 * While this is slightly more complicated than I'd like it allows
5424 * us to use the same code in several different places. ack,
5425 * inform and lease query use it to find the address and fill
5426 * in the options if we get the address from the interface.
5427 * nack uses it to find the address and copy it to the outgoing
5428 * cache. dhcprequest uses it to find the address for comparison
5429 * and doesn't need to add it to an outgoing list.
6d103865 5430 */
f8380d3f 5431
6d103865
SK
5432void
5433get_server_source_address(struct in_addr *from,
5434 struct option_state *options,
f8380d3f 5435 struct option_state *out_options,
6d103865 5436 struct packet *packet) {
e889ded1 5437 unsigned option_num;
f8380d3f 5438 struct option_cache *oc = NULL;
e889ded1 5439 struct data_string d;
f8380d3f
SR
5440 struct in_addr *a = NULL;
5441 isc_boolean_t found = ISC_FALSE;
5442 int allocate = 0;
e889ded1
DH
5443
5444 memset(&d, 0, sizeof(d));
f8380d3f 5445 memset(from, 0, sizeof(*from));
6d103865
SK
5446
5447 option_num = DHO_DHCP_SERVER_IDENTIFIER;
5448 oc = lookup_option(&dhcp_universe, options, option_num);
1b601efa 5449 if (oc != NULL) {
a5b21e16
TM
5450 if (evaluate_option_cache(&d, packet, NULL, NULL,
5451 packet->options, options,
1b601efa
TM
5452 &global_scope, oc, MDL)) {
5453 if (d.len == sizeof(*from)) {
f8380d3f 5454 found = ISC_TRUE;
1b601efa 5455 memcpy(from, d.data, sizeof(*from));
f8380d3f
SR
5456
5457 /*
5458 * Arrange to save a copy of the data
5459 * to the outgoing list.
5460 */
5461 if ((out_options != NULL) &&
5462 (options != out_options)) {
5463 a = from;
5464 allocate = 1;
5465 }
1b601efa 5466 }
6d103865 5467 data_string_forget(&d, MDL);
6d103865 5468 }
1b601efa 5469 oc = NULL;
6d103865
SK
5470 }
5471
f8380d3f
SR
5472 if ((found == ISC_FALSE) &&
5473 (packet->interface->address_count > 0)) {
5474 *from = packet->interface->addresses[0];
5475
5476 if (out_options != NULL) {
98bd7ca0 5477 a = &packet->interface->addresses[0];
6d103865 5478 }
6d103865 5479 }
f8380d3f
SR
5480
5481 if ((a != NULL) &&
5482 (option_cache_allocate(&oc, MDL))) {
5483 if (make_const_data(&oc->expression,
5484 (unsigned char *)a, sizeof(*a),
5485 0, allocate, MDL)) {
a5b21e16 5486 option_code_hash_lookup(&oc->option,
f8380d3f
SR
5487 dhcp_universe.code_hash,
5488 &option_num, 0, MDL);
5489 save_option(&dhcp_universe, out_options, oc);
5490 }
5491 option_cache_dereference(&oc, MDL);
5492 }
5493
5494 return;
5495}
5496
e046c826
TM
5497/*!
5498 * \brief Builds option set from statements at the global and network scope
f8380d3f 5499 *
e046c826
TM
5500 * Set up an option state list based on the global and network scopes.
5501 * These are primarily used by NAK logic to locate dhcp-server-id and
5502 * echo-client-id.
5503 *
5504 * We don't go through all possible options - in particualr we skip the hosts
5505 * and we don't include the lease to avoid making changes to it. This means
5506 * that using these, we won't get the correct server id if the admin puts them
5507 * on hosts or builds the server id with information from the lease.
5508 *
5509 * As this is a fallback function (used to handle NAKs or sort out server id
5510 * mismatch in failover) and requires configuration by the admin, it should be
5511 * okay.
5512 *
5513 * \param network_options option_state to which options will be added. If it
5514 * refers to NULL, it will be allocated. Caller is responsible to delete it.
5515 * \param packet inbound packet
5516 * \param network_group scope group to use if packet->shared_network is null.
f8380d3f 5517 */
f8380d3f 5518void
e046c826
TM
5519eval_network_statements(struct option_state **network_options,
5520 struct packet *packet,
5521 struct group *network_group) {
f8380d3f 5522
e046c826
TM
5523 if (*network_options == NULL) {
5524 option_state_allocate (network_options, MDL);
5525 }
f8380d3f 5526
e046c826
TM
5527 /* Use the packet's shared_network if it has one. If not use
5528 * network_group and if it is null then use global scope. */
f8380d3f 5529 if (packet->shared_network != NULL) {
f8380d3f
SR
5530 /*
5531 * If we have a subnet and group start with that else start
5532 * with the shared network group. The first will recurse and
5533 * include the second.
5534 */
5535 if ((packet->shared_network->subnets != NULL) &&
5536 (packet->shared_network->subnets->group != NULL)) {
5537 execute_statements_in_scope(NULL, packet, NULL, NULL,
e046c826 5538 packet->options, *network_options,
f8380d3f
SR
5539 &global_scope,
5540 packet->shared_network->subnets->group,
a7341359 5541 NULL, NULL);
f8380d3f
SR
5542 } else {
5543 execute_statements_in_scope(NULL, packet, NULL, NULL,
e046c826 5544 packet->options, *network_options,
f8380d3f
SR
5545 &global_scope,
5546 packet->shared_network->group,
a7341359 5547 NULL, NULL);
f8380d3f
SR
5548 }
5549
5550 /* do the pool if there is one */
5551 if (packet->shared_network->pools != NULL) {
5552 execute_statements_in_scope(NULL, packet, NULL, NULL,
e046c826 5553 packet->options, *network_options,
f8380d3f
SR
5554 &global_scope,
5555 packet->shared_network->pools->group,
a7341359
SR
5556 packet->shared_network->group,
5557 NULL);
f8380d3f 5558 }
e046c826
TM
5559 } else if (network_group != NULL) {
5560 execute_statements_in_scope(NULL, packet, NULL, NULL,
5561 packet->options, *network_options,
5562 &global_scope, network_group,
5563 NULL, NULL);
5564 } else {
5565 execute_statements_in_scope(NULL, packet, NULL, NULL,
5566 packet->options, *network_options,
5567 &global_scope, root_group,
5568 NULL, NULL);
5569 }
6d103865
SK
5570}
5571
2c9bf1f4
DH
5572/*
5573 * Look for the lowest numbered site code number and
5574 * apply a log warning if it is less than 224. Do not
5575 * permit site codes less than 128 (old code never did).
5576 *
5577 * Note that we could search option codes 224 down to 128
5578 * on the hash table, but the table is (probably) smaller
5579 * than that if it was declared as a standalone table with
5580 * defaults. So we traverse the option code hash.
5581 */
5582static int
5583find_min_site_code(struct universe *u)
5584{
5585 if (u->site_code_min)
5586 return u->site_code_min;
5587
5588 /*
5589 * Note that site_code_min has to be global as we can't pass an
5590 * argument through hash_foreach(). The value 224 is taken from
5591 * RFC 3942.
5592 */
5593 site_code_min = 224;
5594 option_code_hash_foreach(u->code_hash, lowest_site_code);
5595
5596 if (site_code_min < 224) {
5597 log_error("WARNING: site-local option codes less than 224 have "
5598 "been deprecated by RFC3942. You have options "
5599 "listed in site local space %s that number as low as "
5600 "%d. Please investigate if these should be declared "
5601 "as regular options rather than site-local options, "
5602 "or migrated up past 224.",
5603 u->name, site_code_min);
5604 }
5605
5606 /*
5607 * don't even bother logging, this is just silly, and never worked
5608 * on any old version of software.
5609 */
5610 if (site_code_min < 128)
5611 site_code_min = 128;
5612
5613 /*
5614 * Cache the determined minimum site code on the universe structure.
5615 * Note that due to the < 128 check above, a value of zero is
5616 * impossible.
5617 */
5618 u->site_code_min = site_code_min;
5619
5620 return site_code_min;
5621}
5622
5623static isc_result_t
5624lowest_site_code(const void *key, unsigned len, void *object)
5625{
5626 struct option *option = object;
5627
5628 if (option->code < site_code_min)
5629 site_code_min = option->code;
5630
5631 return ISC_R_SUCCESS;
5632}
5633
a1308b64
DH
5634static void
5635maybe_return_agent_options(struct packet *packet, struct option_state *options)
5636{
5637 /* If there were agent options in the incoming packet, return
5638 * them. Do not return the agent options if they were stashed
5639 * on the lease. We do not check giaddr to detect the presence of
5640 * a relay, as this excludes "l2" relay agents which have no giaddr
5641 * to set.
5642 *
5643 * XXX: If the user configures options for the relay agent information
5644 * (state->options->universes[agent_universe.index] is not NULL),
5645 * we're still required to duplicate other values provided by the
5646 * relay agent. So we need to merge the old values not configured
5647 * by the user into the new state, not just give up.
5648 */
5649 if (!packet->agent_options_stashed &&
8bd96ccb 5650 (packet->options != NULL) &&
a1308b64
DH
5651 packet->options->universe_count > agent_universe.index &&
5652 packet->options->universes[agent_universe.index] != NULL &&
5653 (options->universe_count <= agent_universe.index ||
5654 options->universes[agent_universe.index] == NULL)) {
5655 option_chain_head_reference
5656 ((struct option_chain_head **)
5657 &(options->universes[agent_universe.index]),
5658 (struct option_chain_head *)
5659 packet->options->universes[agent_universe.index], MDL);
5660
5661 if (options->universe_count <= agent_universe.index)
5662 options->universe_count = agent_universe.index + 1;
5663 }
5664}
0a7e1a8a
TM
5665
5666/*!
5667 * \brief Adds hostname option when use-host-decl-names is enabled.
5668 *
5669 * Constructs a hostname option from the name of the host declaration if
5670 * there is one and no hostname has otherwise been provided and the
5671 * use-host-decl-names flag is set, then adds the new option to the given
5672 * option_state. This funciton is used for both bootp and dhcp.
5673 *
5674 * \param packet inbound packet received from the client
5675 * \param lease lease associated with the client
5676 * \param options option state to search and update
5677 */
5678void use_host_decl_name(struct packet* packet,
5679 struct lease *lease,
5680 struct option_state *options) {
5681 unsigned int ocode = SV_USE_HOST_DECL_NAMES;
5682 if ((lease->host && lease->host->name) &&
5683 !lookup_option(&dhcp_universe, options, DHO_HOST_NAME) &&
5684 (evaluate_boolean_option_cache(NULL, packet, lease, NULL,
5685 packet->options, options,
5686 &lease->scope,
5687 lookup_option(&server_universe,
5688 options, ocode),
5689 MDL))) {
5690 struct option_cache *oc = NULL;
5691 if (option_cache_allocate (&oc, MDL)) {
5692 if (make_const_data(&oc -> expression,
5693 ((unsigned char*)lease->host->name),
5694 strlen(lease->host->name),
5695 1, 0, MDL)) {
5696 ocode = DHO_HOST_NAME;
5697 option_code_hash_lookup(&oc->option,
5698 dhcp_universe.code_hash,
5699 &ocode, 0, MDL);
5700 save_option(&dhcp_universe, options, oc);
5701 }
5702 option_cache_dereference(&oc, MDL);
5703 }
5704 }
5705}
f3a44c10
TM
5706
5707/*!
5708 * \brief Checks and preps for lease resuse based on dhcp-cache-threshold
5709 *
5710 * If dhcp-cache-threshold is enabled (i.e. greater than zero), this function
5711 * determines if the current lease is young enough to be reused. If the lease
5712 * can be resused the function returns 1, O if not. This function is called
5713 * by ack_lease when responding to both DISCOVERs and REQUESTS.
5714 *
5715 * The current lease can be reused only if all of the following are true:
5716 * a. dhcp-cache-threshold is > 0
5717 * b. The current lease is active
5718 * c. The lease "age" is less than that allowed by the threshold
5719 * d. DNS updates are not being performed on the new lease.
5720 * e. Lease has not been otherwise disqualified for reuse (Ex: billing class
3abc5708
SR
5721 * or hostname changed)
5722 * f. The host declaration has changed (either a new one was added
5723 * or an older one was found due to something like a change in the uid)
5724 * g. The UID or hardware address have changed.
f3a44c10
TM
5725 *
5726 * Clients may renew leases using full DORA cycles or just RAs. This means
5727 * that reusability must be checked when acking both DISCOVERs and REQUESTs.
5728 * When a lease cannot be reused, ack_lease() calls supersede_lease() which
5729 * updates the lease start time (among other things). If this occurs on the
5730 * DISCOVER, then the lease will virtually always be seen as young enough to
5731 * reuse on the ensuing REQUEST and the lease updates will not get committed
5732 * to the lease file. The lease.cannot_reuse flag is used to handle this
5733 * this situation.
5734 *
5735 * \param packet inbound packet received from the client
5736 * \param new_lease candidate new lease to associate with the client
5737 * \param lease current lease associated with the client
a5b21e16
TM
5738 * \param lease_state lease state to search and update
5739 * \param offer type of DHCP response we're building
5740 * \param[out] same_client pointer to int, that will be set to 1 if
5741 * the two leases refer to the same client, 0 if not. Must NOT be null.
3abc5708
SR
5742 *
5743 * \return 1 if the lease can be reused.
f3a44c10
TM
5744 */
5745int
5746reuse_lease (struct packet* packet,
5747 struct lease* new_lease,
5748 struct lease* lease,
5749 struct lease_state *state,
a5b21e16
TM
5750 int offer,
5751 int *same_client) {
f3a44c10
TM
5752 int reusable = 0;
5753
5754 /* To even consider reuse all of the following must be true:
5755 * 1 - reuse hasn't already disqualified
5756 * 2 - current lease is active
3abc5708
SR
5757 * 3 - DNS info hasn't changed
5758 * 4 - the host declaration hasn't changed
5759 * 5 - the uid hasn't changed
5760 * 6 - the hardware address hasn't changed */
a5b21e16
TM
5761
5762 /* Check client equality separately so we can pass the result out. */
5763 *same_client =
5764 (((lease->host == new_lease->host) &&
5765 (lease->uid_len == new_lease->uid_len) &&
5766 (memcmp(lease->uid, new_lease->uid, new_lease->uid_len) == 0) &&
5767 (lease->hardware_addr.hlen == new_lease->hardware_addr.hlen) &&
5768 (memcmp(&lease->hardware_addr.hbuf[0],
5769 &new_lease->hardware_addr.hbuf[0],
5770 lease->hardware_addr.hlen) == 0)) ? 1 : 0);
5771
f3a44c10
TM
5772 if ((lease->cannot_reuse == 0) &&
5773 (lease->binding_state == FTS_ACTIVE) &&
a5b21e16 5774 (new_lease->ddns_cb == NULL) && *same_client) {
f3a44c10
TM
5775 int thresh = DEFAULT_CACHE_THRESHOLD;
5776 struct option_cache* oc = NULL;
5777 struct data_string d1;
5778
5779 /* Look up threshold value */
5780 memset(&d1, 0, sizeof(struct data_string));
5781 if ((oc = lookup_option(&server_universe, state->options,
5782 SV_CACHE_THRESHOLD)) &&
5783 (evaluate_option_cache(&d1, packet, new_lease, NULL,
5784 packet->options, state->options,
5785 &new_lease->scope, oc, MDL))) {
5786 if (d1.len == 1 && (d1.data[0] < 100))
5787 thresh = d1.data[0];
5788
5789 data_string_forget(&d1, MDL);
5790 }
5791
5792 /* If threshold is enabled, check lease age */
5793 if (thresh > 0) {
5794 int limit = 0;
5795 int lease_length = 0;
5796 long lease_age = 0;
5797
5798 /* Calculate limit in seconds */
5799 lease_length = lease->ends - lease->starts;
5800 if (lease_length <= (INT_MAX / thresh))
5801 limit = lease_length * thresh / 100;
5802 else
5803 limit = lease_length / 100 * thresh;
5804
5805 /* Note new_lease->starts is really just cur_time */
5806 lease_age = new_lease->starts - lease->starts;
5807
3abc5708 5808 /* Is the lease young enough to reuse? */
f3a44c10
TM
5809 if (lease_age <= limit) {
5810 /* Restore expiry to its original value */
5811 state->offered_expiry = lease->ends;
5812
5813 /* Restore bindings. This fixes 37368. */
5814 if (new_lease->scope != NULL) {
5815 if (lease->scope != NULL) {
5816 binding_scope_dereference(
5817 &lease->scope,
5818 MDL);
5819 }
5820
5821 binding_scope_reference(&lease->scope,
5822 new_lease->scope, MDL);
5823 }
5824
3abc5708
SR
5825 /* restore client hostname, fixes 42849. */
5826 if (new_lease->client_hostname) {
5827 lease->client_hostname =
5828 new_lease->client_hostname;
5829 new_lease->client_hostname = NULL;
5830 }
5831
f3a44c10 5832 /* We're cleared to reuse it */
59990751
TM
5833 log_debug("reuse_lease: lease age %ld (secs)"
5834 " under %d%% threshold, reply with "
20931f53
TM
5835 "unaltered, existing lease for %s",
5836 lease_age, thresh, piaddr(lease->ip_addr));
59990751 5837
f3a44c10
TM
5838 reusable = 1;
5839 }
5840 }
5841 }
5842
5843 /* If we can't reuse it and this is an offer disqualify reuse for
5844 * ensuing REQUEST, otherwise clear the flag. */
5845 lease->cannot_reuse = (!reusable && offer == DHCPOFFER);
5846 return (reusable);
5847}
68507137
TM
5848
5849/* \brief Validates a proposed value for use as a lease time
5850 *
5851 * Convenience function used for catching calculeated lease
5852 * times that overflow 4-byte times used in v4 protocol.
5853 *
5854 * We use variables of type TIME in lots of places, which on
5855 * 64-bit systems is 8 bytes while on 32-bit OSs it is int32_t,
5856 * so we have all sorts of fun places to mess things up.
5857 * This function checks a calculated lease time for and if it
5858 * is unsuitable for use as a lease time, the given alternate
5859 * value is returned.
5860 * \param calculated
5861 * \param alternate
5862 *
5863 * \returen either the calculated value if it is valid, or
5864 * the alternate value supplied
5865 */
5866TIME leaseTimeCheck(TIME calculated, TIME alternate) {
5867 if ((sizeof(TIME) > 4 && calculated >= INFINITE_TIME) ||
5868 (calculated < cur_time)) {
5869 return (alternate);
5870 }
5871
5872 return (calculated);
5873}