xref: /minix/external/bsd/dhcp/dist/common/options.c (revision bb9622b5)
1 /*	$NetBSD: options.c,v 1.1.1.3 2014/07/12 11:57:46 spz Exp $	*/
2 /* options.c
3 
4    DHCP options parsing and reassembly. */
5 
6 /*
7  * Copyright (c) 2004-2012,2014 by Internet Systems Consortium, Inc. ("ISC")
8  * Copyright (c) 1995-2003 by Internet Software Consortium
9  *
10  * Permission to use, copy, modify, and distribute this software for any
11  * purpose with or without fee is hereby granted, provided that the above
12  * copyright notice and this permission notice appear in all copies.
13  *
14  * THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES
15  * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
16  * MERCHANTABILITY AND FITNESS.  IN NO EVENT SHALL ISC BE LIABLE FOR
17  * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
18  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
19  * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT
20  * OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
21  *
22  *   Internet Systems Consortium, Inc.
23  *   950 Charter Street
24  *   Redwood City, CA 94063
25  *   <info@isc.org>
26  *   https://www.isc.org/
27  *
28  */
29 
30 #include <sys/cdefs.h>
31 __RCSID("$NetBSD: options.c,v 1.1.1.3 2014/07/12 11:57:46 spz Exp $");
32 
33 #define DHCP_OPTION_DATA
34 #include "dhcpd.h"
35 #include <omapip/omapip_p.h>
36 #include <limits.h>
37 
38 struct option *vendor_cfg_option;
39 
40 static int pretty_text(char **, char *, const unsigned char **,
41 			 const unsigned char *, int);
42 static int pretty_domain(char **, char *, const unsigned char **,
43 			 const unsigned char *);
44 static int prepare_option_buffer(struct universe *universe, struct buffer *bp,
45 				 unsigned char *buffer, unsigned length,
46 				 unsigned code, int terminatep,
47 				 struct option_cache **opp);
48 
49 /* Parse all available options out of the specified packet. */
50 
51 int parse_options (packet)
52 	struct packet *packet;
53 {
54 	struct option_cache *op = (struct option_cache *)0;
55 
56 	/* Allocate a new option state. */
57 	if (!option_state_allocate (&packet -> options, MDL)) {
58 		packet -> options_valid = 0;
59 		return 0;
60 	}
61 
62 	/* If we don't see the magic cookie, there's nothing to parse. */
63 	if (memcmp (packet -> raw -> options, DHCP_OPTIONS_COOKIE, 4)) {
64 		packet -> options_valid = 0;
65 		return 1;
66 	}
67 
68 	/* Go through the options field, up to the end of the packet
69 	   or the End field. */
70 	if (!parse_option_buffer (packet -> options,
71 				  &packet -> raw -> options [4],
72 				  (packet -> packet_length -
73 				   DHCP_FIXED_NON_UDP - 4),
74 				  &dhcp_universe)) {
75 
76 		/* STSN servers have a bug where they send a mangled
77 		   domain-name option, and whatever is beyond that in
78 		   the packet is junk.   Microsoft clients accept this,
79 		   which is probably why whoever implemented the STSN
80 		   server isn't aware of the problem yet.   To work around
81 		   this, we will accept corrupt packets from the server if
82 		   they contain a valid DHCP_MESSAGE_TYPE option, but
83 		   will not accept any corrupt client packets (the ISC DHCP
84 		   server is sufficiently widely used that it is probably
85 		   beneficial for it to be picky) and will not accept
86 		   packets whose type can't be determined. */
87 
88 		if ((op = lookup_option (&dhcp_universe, packet -> options,
89 					 DHO_DHCP_MESSAGE_TYPE))) {
90 			if (!op -> data.data ||
91 			    (op -> data.data [0] != DHCPOFFER &&
92 			     op -> data.data [0] != DHCPACK &&
93 			     op -> data.data [0] != DHCPNAK))
94 				return 0;
95 		} else
96 			return 0;
97 	}
98 
99 	/* If we parsed a DHCP Option Overload option, parse more
100 	   options out of the buffer(s) containing them. */
101 	if ((op = lookup_option (&dhcp_universe, packet -> options,
102 				 DHO_DHCP_OPTION_OVERLOAD))) {
103 		if (op -> data.data [0] & 1) {
104 			if (!parse_option_buffer
105 			    (packet -> options,
106 			     (unsigned char *)packet -> raw -> file,
107 			     sizeof packet -> raw -> file,
108 			     &dhcp_universe))
109 				return 0;
110 		}
111 		if (op -> data.data [0] & 2) {
112 			if (!parse_option_buffer
113 			    (packet -> options,
114 			     (unsigned char *)packet -> raw -> sname,
115 			     sizeof packet -> raw -> sname,
116 			     &dhcp_universe))
117 				return 0;
118 		}
119 	}
120 	packet -> options_valid = 1;
121 	return 1;
122 }
123 
124 /* Parse options out of the specified buffer, storing addresses of option
125  * values in packet->options.
126  */
127 int parse_option_buffer (options, buffer, length, universe)
128 	struct option_state *options;
129 	const unsigned char *buffer;
130 	unsigned length;
131 	struct universe *universe;
132 {
133 	unsigned len, offset;
134 	unsigned code;
135 	struct option_cache *op = NULL, *nop = NULL;
136 	struct buffer *bp = (struct buffer *)0;
137 	struct option *option = NULL;
138 	char *reason = "general failure";
139 
140 	if (!buffer_allocate (&bp, length, MDL)) {
141 		log_error ("no memory for option buffer.");
142 		return 0;
143 	}
144 	memcpy (bp -> data, buffer, length);
145 
146 	for (offset = 0;
147 	     (offset + universe->tag_size) <= length &&
148 	     (code = universe->get_tag(buffer + offset)) != universe->end; ) {
149 		offset += universe->tag_size;
150 
151 		/* Pad options don't have a length - just skip them. */
152 		if (code == DHO_PAD)
153 			continue;
154 
155 		/* Don't look for length if the buffer isn't that big. */
156 		if ((offset + universe->length_size) > length) {
157 			reason = "code tag at end of buffer - missing "
158 				 "length field";
159 			goto bogus;
160 		}
161 
162 		/* All other fields (except PAD and END handled above)
163 		 * have a length field, unless it's a DHCPv6 zero-length
164 		 * options space (eg any of the enterprise-id'd options).
165 		 *
166 		 * Zero-length-size option spaces basically consume the
167 		 * entire options buffer, so have at it.
168 		 */
169 		if (universe->get_length != NULL)
170 			len = universe->get_length(buffer + offset);
171 		else if (universe->length_size == 0)
172 			len = length - universe->tag_size;
173 		else {
174 			log_fatal("Improperly configured option space(%s): "
175 				  "may not have a nonzero length size "
176 				  "AND a NULL get_length function.",
177 				  universe->name);
178 
179 			/* Silence compiler warnings. */
180 			return 0;
181 		}
182 
183 		offset += universe->length_size;
184 
185 		option_code_hash_lookup(&option, universe->code_hash, &code,
186 					0, MDL);
187 
188 		/* If the length is outrageous, the options are bad. */
189 		if (offset + len > length) {
190 			reason = "option length exceeds option buffer length";
191 		      bogus:
192 			log_error("parse_option_buffer: malformed option "
193 				  "%s.%s (code %u): %s.", universe->name,
194 				  option ? option->name : "<unknown>",
195 				  code, reason);
196 			buffer_dereference (&bp, MDL);
197 			return 0;
198 		}
199 
200 		/* If the option contains an encapsulation, parse it.   If
201 		   the parse fails, or the option isn't an encapsulation (by
202 		   far the most common case), or the option isn't entirely
203 		   an encapsulation, keep the raw data as well. */
204 		if (!(option &&
205 		      (option->format[0] == 'e' ||
206 		       option->format[0] == 'E') &&
207 		      (parse_encapsulated_suboptions(options, option,
208 						     bp->data + offset, len,
209 						     universe, NULL)))) {
210 			op = lookup_option(universe, options, code);
211 
212 			if (op != NULL && universe->concat_duplicates) {
213 				struct data_string new;
214 				memset(&new, 0, sizeof new);
215 				if (!buffer_allocate(&new.buffer,
216 						     op->data.len + len,
217 						     MDL)) {
218 					log_error("parse_option_buffer: "
219 						  "No memory.");
220 					buffer_dereference(&bp, MDL);
221 					return 0;
222 				}
223 				/* Copy old option to new data object. */
224 				memcpy(new.buffer->data, op->data.data,
225 					op->data.len);
226 				/* Concat new option behind old. */
227 				memcpy(new.buffer->data + op->data.len,
228 					bp->data + offset, len);
229 				new.len = op->data.len + len;
230 				new.data = new.buffer->data;
231 				/* Save new concat'd object. */
232 				data_string_forget(&op->data, MDL);
233 				data_string_copy(&op->data, &new, MDL);
234 				data_string_forget(&new, MDL);
235 			} else if (op != NULL) {
236 				/* We must append this statement onto the
237 				 * end of the list.
238 				 */
239 				while (op->next != NULL)
240 					op = op->next;
241 
242 				if (!option_cache_allocate(&nop, MDL)) {
243 					log_error("parse_option_buffer: "
244 						  "No memory.");
245 					buffer_dereference(&bp, MDL);
246 					return 0;
247 				}
248 
249 				option_reference(&nop->option, op->option, MDL);
250 
251 				nop->data.buffer = NULL;
252 				buffer_reference(&nop->data.buffer, bp, MDL);
253 				nop->data.data = bp->data + offset;
254 				nop->data.len = len;
255 
256 				option_cache_reference(&op->next, nop, MDL);
257 				option_cache_dereference(&nop, MDL);
258 			} else {
259 				if (save_option_buffer(universe, options, bp,
260 						       bp->data + offset, len,
261 						       code, 1) == 0) {
262 					log_error("parse_option_buffer: "
263 						  "save_option_buffer failed");
264 					buffer_dereference(&bp, MDL);
265 					return 0;
266 				}
267 			}
268 		}
269 		option_dereference(&option, MDL);
270 		offset += len;
271 	}
272 	buffer_dereference (&bp, MDL);
273 	return 1;
274 }
275 
276 /* If an option in an option buffer turns out to be an encapsulation,
277    figure out what to do.   If we don't know how to de-encapsulate it,
278    or it's not well-formed, return zero; otherwise, return 1, indicating
279    that we succeeded in de-encapsulating it. */
280 
281 struct universe *find_option_universe (struct option *eopt, const char *uname)
282 {
283 	int i;
284 	char *s, *t;
285 	struct universe *universe = (struct universe *)0;
286 
287 	/* Look for the E option in the option format. */
288 	s = strchr (eopt -> format, 'E');
289 	if (!s) {
290 		log_error ("internal encapsulation format error 1.");
291 		return 0;
292 	}
293 	/* Look for the universe name in the option format. */
294 	t = strchr (++s, '.');
295 	/* If there was no trailing '.', or there's something after the
296 	   trailing '.', the option is bogus and we can't use it. */
297 	if (!t || t [1]) {
298 		log_error ("internal encapsulation format error 2.");
299 		return 0;
300 	}
301 	if (t == s && uname) {
302 		for (i = 0; i < universe_count; i++) {
303 			if (!strcmp (universes [i] -> name, uname)) {
304 				universe = universes [i];
305 				break;
306 			}
307 		}
308 	} else if (t != s) {
309 		for (i = 0; i < universe_count; i++) {
310 			if (strlen (universes [i] -> name) == t - s &&
311 			    !memcmp (universes [i] -> name,
312 				     s, (unsigned)(t - s))) {
313 				universe = universes [i];
314 				break;
315 			}
316 		}
317 	}
318 	return universe;
319 }
320 
321 /* If an option in an option buffer turns out to be an encapsulation,
322    figure out what to do.   If we don't know how to de-encapsulate it,
323    or it's not well-formed, return zero; otherwise, return 1, indicating
324    that we succeeded in de-encapsulating it. */
325 
326 int parse_encapsulated_suboptions (struct option_state *options,
327 				   struct option *eopt,
328 				   const unsigned char *buffer,
329 				   unsigned len, struct universe *eu,
330 				   const char *uname)
331 {
332 	int i;
333 	struct universe *universe = find_option_universe (eopt, uname);
334 
335 	/* If we didn't find the universe, we can't do anything with it
336 	   right now (e.g., we can't decode vendor options until we've
337 	   decoded the packet and executed the scopes that it matches). */
338 	if (!universe)
339 		return 0;
340 
341 	/* If we don't have a decoding function for it, we can't decode
342 	   it. */
343 	if (!universe -> decode)
344 		return 0;
345 
346 	i = (*universe -> decode) (options, buffer, len, universe);
347 
348 	/* If there is stuff before the suboptions, we have to keep it. */
349 	if (eopt -> format [0] != 'E')
350 		return 0;
351 	/* Otherwise, return the status of the decode function. */
352 	return i;
353 }
354 
355 int fqdn_universe_decode (struct option_state *options,
356 			  const unsigned char *buffer,
357 			  unsigned length, struct universe *u)
358 {
359 	struct buffer *bp = (struct buffer *)0;
360 
361 	/* FQDN options have to be at least four bytes long. */
362 	if (length < 3)
363 		return 0;
364 
365 	/* Save the contents of the option in a buffer. */
366 	if (!buffer_allocate (&bp, length + 4, MDL)) {
367 		log_error ("no memory for option buffer.");
368 		return 0;
369 	}
370 	memcpy (&bp -> data [3], buffer + 1, length - 1);
371 
372 	if (buffer [0] & 4)	/* encoded */
373 		bp -> data [0] = 1;
374 	else
375 		bp -> data [0] = 0;
376 	if (!save_option_buffer(&fqdn_universe, options, bp,
377 				bp->data, 1, FQDN_ENCODED, 0)) {
378 	      bad:
379 		buffer_dereference (&bp, MDL);
380 		return 0;
381 	}
382 
383 	if (buffer [0] & 1)	/* server-update */
384 		bp -> data [2] = 1;
385 	else
386 		bp -> data [2] = 0;
387 	if (buffer [0] & 2)	/* no-client-update */
388 		bp -> data [1] = 1;
389 	else
390 		bp -> data [1] = 0;
391 
392 	/* XXX Ideally we should store the name in DNS format, so if the
393 	   XXX label isn't in DNS format, we convert it to DNS format,
394 	   XXX rather than converting labels specified in DNS format to
395 	   XXX the plain ASCII representation.   But that's hard, so
396 	   XXX not now. */
397 
398 	/* Not encoded using DNS format? */
399 	if (!bp -> data [0]) {
400 		unsigned i;
401 
402 		/* Some broken clients NUL-terminate this option. */
403 		if (buffer [length - 1] == 0) {
404 			--length;
405 			bp -> data [1] = 1;
406 		}
407 
408 		/* Determine the length of the hostname component of the
409 		   name.  If the name contains no '.' character, it
410 		   represents a non-qualified label. */
411 		for (i = 3; i < length && buffer [i] != '.'; i++);
412 		i -= 3;
413 
414 		/* Note: If the client sends a FQDN, the first '.' will
415 		   be used as a NUL terminator for the hostname. */
416 		if (i && (!save_option_buffer(&fqdn_universe, options, bp,
417 					      &bp->data[5], i,
418 					      FQDN_HOSTNAME, 0)))
419 			goto bad;
420 		/* Note: If the client sends a single label, the
421 		   FQDN_DOMAINNAME option won't be set. */
422 		if (length > 4 + i &&
423 		    (!save_option_buffer(&fqdn_universe, options, bp,
424 					 &bp -> data[6 + i], length - 4 - i,
425 					 FQDN_DOMAINNAME, 1)))
426 			goto bad;
427 		/* Also save the whole name. */
428 		if (length > 3) {
429 			if (!save_option_buffer(&fqdn_universe, options, bp,
430 						&bp -> data [5], length - 3,
431 						FQDN_FQDN, 1))
432 				goto bad;
433 		}
434 	} else {
435 		unsigned len;
436 		unsigned total_len = 0;
437 		unsigned first_len = 0;
438 		int terminated = 0;
439 		unsigned char *s;
440 
441 		s = &bp -> data[5];
442 
443 		while (s < &bp -> data[0] + length + 2) {
444 			len = *s;
445 			if (len > 63) {
446 				log_info ("fancy bits in fqdn option");
447 				return 0;
448 			}
449 			if (len == 0) {
450 				terminated = 1;
451 				break;
452 			}
453 			if (s + len > &bp -> data [0] + length + 3) {
454 				log_info ("fqdn tag longer than buffer");
455 				return 0;
456 			}
457 
458 			if (first_len == 0) {
459 				first_len = len;
460 			}
461 
462 			*s = '.';
463 			s += len + 1;
464 			total_len += len + 1;
465 		}
466 
467 		/* We wind up with a length that's one too many because
468 		   we shouldn't increment for the last label, but there's
469 		   no way to tell we're at the last label until we exit
470 		   the loop.   :'*/
471 		if (total_len > 0)
472 			total_len--;
473 
474 		if (!terminated) {
475 			first_len = total_len;
476 		}
477 
478 		if (first_len > 0 &&
479 		    !save_option_buffer(&fqdn_universe, options, bp,
480 					&bp -> data[6], first_len,
481 					FQDN_HOSTNAME, 0))
482 			goto bad;
483 		if (total_len > 0 && first_len != total_len) {
484 			if (!save_option_buffer(&fqdn_universe, options, bp,
485 						&bp->data[6 + first_len],
486 						total_len - first_len,
487 						FQDN_DOMAINNAME, 1))
488 				goto bad;
489 		}
490 		if (total_len > 0)
491 			if (!save_option_buffer (&fqdn_universe, options, bp,
492 						 &bp -> data [6], total_len,
493 						 FQDN_FQDN, 1))
494 				goto bad;
495 	}
496 
497 	if (!save_option_buffer (&fqdn_universe, options, bp,
498 				 &bp -> data [1], 1,
499 				 FQDN_NO_CLIENT_UPDATE, 0))
500 	    goto bad;
501 	if (!save_option_buffer (&fqdn_universe, options, bp,
502 				 &bp -> data [2], 1,
503 				 FQDN_SERVER_UPDATE, 0))
504 		goto bad;
505 
506 	if (!save_option_buffer (&fqdn_universe, options, bp,
507 				 &bp -> data [3], 1,
508 				 FQDN_RCODE1, 0))
509 		goto bad;
510 	if (!save_option_buffer (&fqdn_universe, options, bp,
511 				 &bp -> data [4], 1,
512 				 FQDN_RCODE2, 0))
513 		goto bad;
514 
515 	buffer_dereference (&bp, MDL);
516 	return 1;
517 }
518 
519 /*
520  * Load all options into a buffer, and then split them out into the three
521  * separate fields in the dhcp packet (options, file, and sname) where
522  * options can be stored.
523  *
524  * returns 0 on error, length of packet on success
525  */
526 int
527 cons_options(struct packet *inpacket, struct dhcp_packet *outpacket,
528 	     struct lease *lease, struct client_state *client_state,
529 	     int mms, struct option_state *in_options,
530 	     struct option_state *cfg_options,
531 	     struct binding_scope **scope,
532 	     int overload_avail, int terminate, int bootpp,
533 	     struct data_string *prl, const char *vuname)
534 {
535 #define PRIORITY_COUNT 300
536 	unsigned priority_list[PRIORITY_COUNT];
537 	int priority_len;
538 	unsigned char buffer[4096], agentopts[1024];
539 	unsigned index = 0;
540 	unsigned mb_size = 0, mb_max = 0;
541 	unsigned option_size = 0, agent_size = 0;
542 	unsigned length;
543 	int i;
544 	struct option_cache *op;
545 	struct data_string ds;
546 	pair pp, *hash;
547 	int overload_used = 0;
548 	int of1 = 0, of2 = 0;
549 
550 	memset(&ds, 0, sizeof ds);
551 
552 	/*
553 	 * If there's a Maximum Message Size option in the incoming packet
554 	 * and no alternate maximum message size has been specified, or
555 	 * if the one specified in the packet is shorter than the
556 	 * alternative, take the one in the packet.
557 	 */
558 
559 	if (inpacket &&
560 	    (op = lookup_option(&dhcp_universe, inpacket->options,
561 				DHO_DHCP_MAX_MESSAGE_SIZE)) &&
562 	    (evaluate_option_cache(&ds, inpacket, lease,
563 				   client_state, in_options,
564 				   cfg_options, scope, op, MDL) != 0)) {
565 		if (ds.len >= sizeof (u_int16_t)) {
566 			i = getUShort(ds.data);
567 			if(!mms || (i < mms))
568 				mms = i;
569 		}
570 		data_string_forget(&ds, MDL);
571 	}
572 
573 	/*
574 	 * If the client has provided a maximum DHCP message size,
575 	 * use that, up to the MTU limit.  Otherwise, if it's BOOTP,
576 	 * only 64 bytes; otherwise use up to the minimum IP MTU size
577 	 * (576 bytes).
578 	 *
579 	 * XXX if a BOOTP client specifies a max message size, we will
580 	 * honor it.
581 	 */
582 	if (mms) {
583 		if (mms < DHCP_MTU_MIN)
584 		        /* Enforce minimum packet size, per RFC 2132 */
585 			mb_size = DHCP_MIN_OPTION_LEN;
586 		else if (mms > DHCP_MTU_MAX)
587 			/*
588 			 * TODO: Packets longer than 1500 bytes really
589 			 * should be allowed, but it requires upstream
590 			 * changes to the way the packet is allocated.  For
591 			 * now, we forbid them.  They won't be needed very
592 			 * often anyway.
593 			 */
594 			mb_size = DHCP_MAX_OPTION_LEN;
595 		else
596 			mb_size = mms - DHCP_FIXED_LEN;
597 	} else if (bootpp) {
598 		mb_size = 64;
599 		if (inpacket != NULL &&
600 		    (inpacket->packet_length >= 64 + DHCP_FIXED_NON_UDP))
601 			mb_size = inpacket->packet_length - DHCP_FIXED_NON_UDP;
602 	} else
603 		mb_size = DHCP_MIN_OPTION_LEN;
604 
605 	/*
606 	 * If answering a client message, see whether any relay agent
607 	 * options were included with the message.  If so, save them
608 	 * to copy back in later, and make space in the main buffer
609 	 * to accommodate them
610 	 */
611 	if (client_state == NULL) {
612 		priority_list[0] = DHO_DHCP_AGENT_OPTIONS;
613 		priority_len = 1;
614 		agent_size = store_options(NULL, agentopts, 0,
615 					   sizeof(agentopts),
616 					   inpacket, lease, client_state,
617 					   in_options, cfg_options, scope,
618 					   priority_list, priority_len,
619 					   0, 0, 0, NULL);
620 
621 		mb_size += agent_size;
622 		if (mb_size > DHCP_MAX_OPTION_LEN)
623 			mb_size = DHCP_MAX_OPTION_LEN;
624 	}
625 
626 	/*
627 	 * Set offsets for buffer data to be copied into filename
628 	 * and servername fields
629 	 */
630 	mb_max = mb_size;
631 
632 	if (overload_avail & 1) {
633 		of1 = mb_max;
634 		mb_max += DHCP_FILE_LEN;
635 	}
636 
637 	if (overload_avail & 2) {
638 		of2 = mb_max;
639 		mb_max += DHCP_SNAME_LEN;
640 	}
641 
642 	/*
643 	 * Preload the option priority list with protocol-mandatory options.
644 	 * This effectively gives these options the highest priority.
645 	 * This provides the order for any available options, the option
646 	 * must be in the option cache in order to actually be included.
647 	 */
648 	priority_len = 0;
649 	priority_list[priority_len++] = DHO_DHCP_MESSAGE_TYPE;
650 	priority_list[priority_len++] = DHO_DHCP_SERVER_IDENTIFIER;
651 	priority_list[priority_len++] = DHO_DHCP_LEASE_TIME;
652 	priority_list[priority_len++] = DHO_DHCP_RENEWAL_TIME;
653 	priority_list[priority_len++] = DHO_DHCP_REBINDING_TIME;
654 	priority_list[priority_len++] = DHO_DHCP_MESSAGE;
655 	priority_list[priority_len++] = DHO_DHCP_REQUESTED_ADDRESS;
656 	priority_list[priority_len++] = DHO_ASSOCIATED_IP;
657 
658 	if (prl != NULL && prl->len > 0) {
659 		if ((op = lookup_option(&dhcp_universe, cfg_options,
660 					 DHO_SUBNET_SELECTION))) {
661 			if (priority_len < PRIORITY_COUNT)
662 				priority_list[priority_len++] =
663 					DHO_SUBNET_SELECTION;
664 		}
665 
666 		data_string_truncate(prl, (PRIORITY_COUNT - priority_len));
667 
668 		/*
669 		 * Copy the client's PRL onto the priority_list after our high
670 		 * priority header.
671 		 */
672 		for (i = 0; i < prl->len; i++) {
673 			/*
674 			 * Prevent client from changing order of delivery
675 			 * of relay agent information option.
676 			 */
677 			if (prl->data[i] != DHO_DHCP_AGENT_OPTIONS)
678 				priority_list[priority_len++] = prl->data[i];
679 		}
680 
681 		/*
682 		 * If the client doesn't request the FQDN option explicitly,
683 		 * to indicate priority, consider it lowest priority.  Fit
684 		 * in the packet if there is space.  Note that the option
685 		 * may only be included if the client supplied one.
686 		 */
687 		if ((inpacket != NULL) && (priority_len < PRIORITY_COUNT) &&
688 		    (lookup_option(&fqdn_universe, inpacket->options,
689 				   FQDN_ENCODED) != NULL))
690 			priority_list[priority_len++] = DHO_FQDN;
691 
692 		/*
693 		 * Some DHCP Servers will give the subnet-mask option if
694 		 * it is not on the parameter request list - so some client
695 		 * implementations have come to rely on this - so we will
696 		 * also make sure we supply this, at lowest priority.
697 		 *
698 		 * This is only done in response to DHCPDISCOVER or
699 		 * DHCPREQUEST messages, to avoid providing the option on
700 		 * DHCPINFORM or DHCPLEASEQUERY responses (if the client
701 		 * didn't request it).
702 		 */
703 		if ((inpacket != NULL) && (priority_len < PRIORITY_COUNT) &&
704 		    ((inpacket->packet_type == DHCPDISCOVER) ||
705 		     (inpacket->packet_type == DHCPREQUEST)))
706 			priority_list[priority_len++] = DHO_SUBNET_MASK;
707 	} else {
708 		/*
709 		 * First, hardcode some more options that ought to be
710 		 * sent first...these are high priority to have in the
711 		 * packet.
712 		 */
713 		priority_list[priority_len++] = DHO_SUBNET_MASK;
714 		priority_list[priority_len++] = DHO_ROUTERS;
715 		priority_list[priority_len++] = DHO_DOMAIN_NAME_SERVERS;
716 		priority_list[priority_len++] = DHO_HOST_NAME;
717 		priority_list[priority_len++] = DHO_FQDN;
718 
719 		/*
720 		 * Append a list of the standard DHCP options from the
721 		 * standard DHCP option space.  Actually, if a site
722 		 * option space hasn't been specified, we wind up
723 		 * treating the dhcp option space as the site option
724 		 * space, and the first for loop is skipped, because
725 		 * it's slightly more general to do it this way,
726 		 * taking the 1Q99 DHCP futures work into account.
727 		 */
728 		if (cfg_options->site_code_min) {
729 		    for (i = 0; i < OPTION_HASH_SIZE; i++) {
730 			hash = cfg_options->universes[dhcp_universe.index];
731 			if (hash) {
732 			    for (pp = hash[i]; pp; pp = pp->cdr) {
733 				op = (struct option_cache *)(pp->car);
734 				if (op->option->code <
735 				     cfg_options->site_code_min &&
736 				    priority_len < PRIORITY_COUNT &&
737 				    op->option->code != DHO_DHCP_AGENT_OPTIONS)
738 					priority_list[priority_len++] =
739 						op->option->code;
740 			    }
741 			}
742 		    }
743 		}
744 
745 		/*
746 		 * Now cycle through the site option space, or if there
747 		 * is no site option space, we'll be cycling through the
748 		 * dhcp option space.
749 		 */
750 		for (i = 0; i < OPTION_HASH_SIZE; i++) {
751 		    hash = cfg_options->universes[cfg_options->site_universe];
752 		    if (hash != NULL)
753 			for (pp = hash[i]; pp; pp = pp->cdr) {
754 				op = (struct option_cache *)(pp->car);
755 				if (op->option->code >=
756 				     cfg_options->site_code_min &&
757 				    priority_len < PRIORITY_COUNT &&
758 				    op->option->code != DHO_DHCP_AGENT_OPTIONS)
759 					priority_list[priority_len++] =
760 						op->option->code;
761 			}
762 		}
763 
764 		/*
765 		 * Put any spaces that are encapsulated on the list,
766 		 * sort out whether they contain values later.
767 		 */
768 		for (i = 0; i < cfg_options->universe_count; i++) {
769 		    if (universes[i]->enc_opt &&
770 			priority_len < PRIORITY_COUNT &&
771 			universes[i]->enc_opt->universe == &dhcp_universe) {
772 			    if (universes[i]->enc_opt->code !=
773 				DHO_DHCP_AGENT_OPTIONS)
774 				    priority_list[priority_len++] =
775 					    universes[i]->enc_opt->code;
776 		    }
777 		}
778 
779 		/*
780 		 * The vendor option space can't stand on its own, so always
781 		 * add it to the list.
782 		 */
783 		if (priority_len < PRIORITY_COUNT)
784 			priority_list[priority_len++] =
785 				DHO_VENDOR_ENCAPSULATED_OPTIONS;
786 	}
787 
788 	/* Put the cookie up front... */
789 	memcpy(buffer, DHCP_OPTIONS_COOKIE, 4);
790 	index += 4;
791 
792 	/* Copy the options into the big buffer... */
793 	option_size = store_options(&overload_used, buffer, index, mb_max,
794 				    inpacket, lease, client_state,
795 				    in_options, cfg_options, scope,
796 				    priority_list, priority_len,
797 				    of1, of2, terminate, vuname);
798 
799 	/* If store_options() failed */
800 	if (option_size == 0)
801 		return 0;
802 
803 	/* How much was stored in the main buffer? */
804 	index += option_size;
805 
806 	/*
807 	 * If we're going to have to overload, store the overload
808 	 * option first.
809 	 */
810 	if (overload_used) {
811 		if (mb_size - agent_size - index < 3)
812 			return 0;
813 
814 		buffer[index++] = DHO_DHCP_OPTION_OVERLOAD;
815 		buffer[index++] = 1;
816 		buffer[index++] = overload_used;
817 
818 		if (overload_used & 1)
819 			memcpy(outpacket->file, &buffer[of1], DHCP_FILE_LEN);
820 
821 		if (overload_used & 2)
822 			memcpy(outpacket->sname, &buffer[of2], DHCP_SNAME_LEN);
823 	}
824 
825 	/* Now copy in preserved agent options, if any */
826 	if (agent_size) {
827 		if (mb_size - index >= agent_size) {
828 			memcpy(&buffer[index], agentopts, agent_size);
829 			index += agent_size;
830 		} else
831 			log_error("Unable to store relay agent information "
832 				  "in reply packet.");
833 	}
834 
835 	/* Tack a DHO_END option onto the packet if we need to. */
836 	if (index < mb_size)
837 		buffer[index++] = DHO_END;
838 
839 	/* Copy main buffer into the options buffer of the packet */
840 	memcpy(outpacket->options, buffer, index);
841 
842 	/* Figure out the length. */
843 	length = DHCP_FIXED_NON_UDP + index;
844 	return length;
845 }
846 
847 /*
848  * XXX: We currently special case collecting VSIO options.
849  *      We should be able to handle this in a more generic fashion, by
850  *      including any encapsulated options that are present and desired.
851  *      This will look something like the VSIO handling VSIO code.
852  *      We may also consider handling the ORO-like options within
853  *      encapsulated spaces.
854  */
855 
856 struct vsio_state {
857 	char *buf;
858 	int buflen;
859 	int bufpos;
860 };
861 
862 static void
863 vsio_options(struct option_cache *oc,
864 	     struct packet *packet,
865 	     struct lease *dummy_lease,
866 	     struct client_state *dummy_client_state,
867 	     struct option_state *dummy_opt_state,
868 	     struct option_state *opt_state,
869 	     struct binding_scope **dummy_binding_scope,
870 	     struct universe *universe,
871 	     void *void_vsio_state) {
872 	struct vsio_state *vs = (struct vsio_state *)void_vsio_state;
873 	struct data_string ds;
874 	int total_len;
875 
876 	memset(&ds, 0, sizeof(ds));
877 	if (evaluate_option_cache(&ds, packet, NULL,
878 				  NULL, opt_state, NULL,
879 				  &global_scope, oc, MDL)) {
880 		total_len = ds.len + universe->tag_size + universe->length_size;
881 		if (total_len <= (vs->buflen - vs->bufpos)) {
882 			if (universe->tag_size == 1) {
883 				vs->buf[vs->bufpos++] = oc->option->code;
884 			} else if (universe->tag_size == 2) {
885 				putUShort((unsigned char *)vs->buf+vs->bufpos,
886 					  oc->option->code);
887 				vs->bufpos += 2;
888 			} else if (universe->tag_size == 4) {
889 				putULong((unsigned char *)vs->buf+vs->bufpos,
890 					 oc->option->code);
891 				vs->bufpos += 4;
892 			}
893 			if (universe->length_size == 1) {
894 				vs->buf[vs->bufpos++] = ds.len;
895 			} else if (universe->length_size == 2) {
896 				putUShort((unsigned char *)vs->buf+vs->bufpos,
897 					  ds.len);
898 				vs->bufpos += 2;
899 			} else if (universe->length_size == 4) {
900 				putULong((unsigned char *)vs->buf+vs->bufpos,
901 					 ds.len);
902 				vs->bufpos += 4;
903 			}
904 			memcpy(vs->buf + vs->bufpos, ds.data, ds.len);
905 			vs->bufpos += ds.len;
906 		} else {
907 			log_debug("No space for option %d in VSIO space %s.",
908 		  		oc->option->code, universe->name);
909 		}
910 		data_string_forget(&ds, MDL);
911 	} else {
912 		log_error("Error evaluating option %d in VSIO space %s.",
913 		  	oc->option->code, universe->name);
914 	}
915 }
916 
917 /*
918  * Stores the options from the DHCPv6 universe into the buffer given.
919  *
920  * Required options are given as a 0-terminated list of option codes.
921  * Once those are added, the ORO is consulted.
922  */
923 
924 int
925 store_options6(char *buf, int buflen,
926 	       struct option_state *opt_state,
927 	       struct packet *packet,
928 	       const int *required_opts,
929 	       struct data_string *oro) {
930 	int i, j;
931 	struct option_cache *oc;
932 	struct option *o;
933 	struct data_string ds;
934 	int bufpos;
935 	int oro_size;
936 	u_int16_t code;
937 	int in_required_opts;
938 	int vsio_option_code;
939 	int vsio_wanted;
940 	struct vsio_state vs;
941 	unsigned char *tmp;
942 
943 	bufpos = 0;
944 	vsio_wanted = 0;
945 
946 	/*
947 	 * Find the option code for the VSIO universe.
948 	 */
949 	vsio_option_code = 0;
950 	o = vsio_universe.enc_opt;
951 	while (o != NULL) {
952 		if (o->universe == &dhcpv6_universe) {
953 			vsio_option_code = o->code;
954 			break;
955 		}
956 		o = o->universe->enc_opt;
957 	}
958 	if (vsio_option_code == 0) {
959 		log_fatal("No VSIO option code found.");
960 	}
961 
962 	if (required_opts != NULL) {
963 		for (i=0; required_opts[i] != 0; i++) {
964 			if (required_opts[i] == vsio_option_code) {
965 				vsio_wanted = 1;
966 			}
967 
968 			oc = lookup_option(&dhcpv6_universe,
969 					   opt_state, required_opts[i]);
970 			if (oc == NULL) {
971 				continue;
972 			}
973 			memset(&ds, 0, sizeof(ds));
974 			for (; oc != NULL ; oc = oc->next) {
975 				if (evaluate_option_cache(&ds, packet, NULL,
976 							  NULL, opt_state,
977 							  NULL, &global_scope,
978 							  oc, MDL)) {
979 					if ((ds.len + 4) <=
980 					    (buflen - bufpos)) {
981 						tmp = (unsigned char *)buf;
982 						tmp += bufpos;
983 						/* option tag */
984 						putUShort(tmp,
985 							  required_opts[i]);
986 						/* option length */
987 						putUShort(tmp+2, ds.len);
988 						/* option data */
989 						memcpy(tmp+4, ds.data, ds.len);
990 						/* update position */
991 						bufpos += (4 + ds.len);
992 					} else {
993 						log_debug("No space for "
994 							  "option %d",
995 							  required_opts[i]);
996 					}
997 					data_string_forget(&ds, MDL);
998 				} else {
999 					log_error("Error evaluating option %d",
1000 					  	required_opts[i]);
1001 				}
1002 			}
1003 		}
1004 	}
1005 
1006 	if (oro == NULL) {
1007 		oro_size = 0;
1008 	} else {
1009 		oro_size = oro->len / 2;
1010 	}
1011 	for (i=0; i<oro_size; i++) {
1012 		memcpy(&code, oro->data+(i*2), 2);
1013 		code = ntohs(code);
1014 
1015 		/*
1016 		 * See if we've already included this option because
1017 		 * it is required.
1018 		 */
1019 		in_required_opts = 0;
1020 		if (required_opts != NULL) {
1021 			for (j=0; required_opts[j] != 0; j++) {
1022 				if (required_opts[j] == code) {
1023 					in_required_opts = 1;
1024 					break;
1025 				}
1026 			}
1027 		}
1028 		if (in_required_opts) {
1029 			continue;
1030 		}
1031 
1032 		/*
1033 		 * See if this is the VSIO option.
1034 		 */
1035 		if (code == vsio_option_code) {
1036 			vsio_wanted = 1;
1037 		}
1038 
1039 		/*
1040 		 * Not already added, find this option.
1041 		 */
1042 		oc = lookup_option(&dhcpv6_universe, opt_state, code);
1043 		memset(&ds, 0, sizeof(ds));
1044 		for (; oc != NULL ; oc = oc->next) {
1045 			if (evaluate_option_cache(&ds, packet, NULL, NULL,
1046 						  opt_state, NULL,
1047 						  &global_scope, oc, MDL)) {
1048 				if ((ds.len + 4) <= (buflen - bufpos)) {
1049 					tmp = (unsigned char *)buf + bufpos;
1050 					/* option tag */
1051 					putUShort(tmp, code);
1052 					/* option length */
1053 					putUShort(tmp+2, ds.len);
1054 					/* option data */
1055 					memcpy(tmp+4, ds.data, ds.len);
1056 					/* update position */
1057 					bufpos += (4 + ds.len);
1058 				} else {
1059 					log_debug("No space for option %d",
1060 						  code);
1061 				}
1062 				data_string_forget(&ds, MDL);
1063 			} else {
1064 				log_error("Error evaluating option %d", code);
1065 			}
1066 		}
1067 	}
1068 
1069 	if (vsio_wanted) {
1070 		for (i=0; i < opt_state->universe_count; i++) {
1071 			if (opt_state->universes[i] != NULL) {
1072 		    		o = universes[i]->enc_opt;
1073 				if ((o != NULL) &&
1074 				    (o->universe == &vsio_universe)) {
1075 					/*
1076 					 * Add the data from this VSIO option.
1077 					 */
1078 					vs.buf = buf;
1079 					vs.buflen = buflen;
1080 					vs.bufpos = bufpos+8;
1081 					option_space_foreach(packet, NULL,
1082 							     NULL,
1083 							     NULL, opt_state,
1084 			     				     NULL,
1085 							     universes[i],
1086 							     (void *)&vs,
1087 			     				     vsio_options);
1088 
1089 					/*
1090 					 * If there was actually data here,
1091 					 * add the "header".
1092 					 */
1093 					if (vs.bufpos > bufpos+8) {
1094 						tmp = (unsigned char *)buf +
1095 						      bufpos;
1096 						putUShort(tmp,
1097 							  vsio_option_code);
1098 						putUShort(tmp+2,
1099 							  vs.bufpos-bufpos-4);
1100 						putULong(tmp+4, o->code);
1101 
1102 						bufpos = vs.bufpos;
1103 					}
1104 				}
1105 			}
1106 		}
1107 	}
1108 
1109 	return bufpos;
1110 }
1111 
1112 /*
1113  * Store all the requested options into the requested buffer.
1114  * XXX: ought to be static
1115  */
1116 int
1117 store_options(int *ocount,
1118 	      unsigned char *buffer, unsigned index, unsigned buflen,
1119 	      struct packet *packet, struct lease *lease,
1120 	      struct client_state *client_state,
1121 	      struct option_state *in_options,
1122 	      struct option_state *cfg_options,
1123 	      struct binding_scope **scope,
1124 	      unsigned *priority_list, int priority_len,
1125 	      unsigned first_cutoff, int second_cutoff, int terminate,
1126 	      const char *vuname)
1127 {
1128 	int bufix = 0, six = 0, tix = 0;
1129 	int i;
1130 	int ix;
1131 	int tto;
1132 	int bufend, sbufend;
1133 	struct data_string od;
1134 	struct option_cache *oc;
1135 	struct option *option = NULL;
1136 	unsigned code;
1137 
1138 	/*
1139 	 * These arguments are relative to the start of the buffer, so
1140 	 * reduce them by the current buffer index, and advance the
1141 	 * buffer pointer to where we're going to start writing.
1142 	 */
1143 	buffer = &buffer[index];
1144 	buflen -= index;
1145 	if (first_cutoff)
1146 		first_cutoff -= index;
1147 	if (second_cutoff)
1148 		second_cutoff -= index;
1149 
1150 	/* Calculate the start and end of each section of the buffer */
1151 	bufend = sbufend = buflen;
1152 	if (first_cutoff) {
1153 	    if (first_cutoff >= buflen)
1154 		log_fatal("%s:%d:store_options: Invalid first cutoff.", MDL);
1155 	    bufend = first_cutoff;
1156 
1157 	    if (second_cutoff) {
1158 	        if (second_cutoff >= buflen)
1159 		    log_fatal("%s:%d:store_options: Invalid second cutoff.",
1160 			      MDL);
1161 	        sbufend = second_cutoff;
1162 	    }
1163 	} else if (second_cutoff) {
1164 	    if (second_cutoff >= buflen)
1165 		log_fatal("%s:%d:store_options: Invalid second cutoff.", MDL);
1166 	    bufend = second_cutoff;
1167 	}
1168 
1169 	memset (&od, 0, sizeof od);
1170 
1171 	/* Eliminate duplicate options from the parameter request list.
1172 	 * Enforce RFC-mandated ordering of options that are present.
1173 	 */
1174 	for (i = 0; i < priority_len - 1; i++) {
1175 		/* Eliminate duplicates. */
1176 		tto = 0;
1177 		for (ix = i + 1; ix < priority_len + tto; ix++) {
1178 			if (tto)
1179 				priority_list [ix - tto] =
1180 					priority_list [ix];
1181 			if (priority_list [i] == priority_list [ix]) {
1182 				tto++;
1183 				priority_len--;
1184 			}
1185 		}
1186 
1187 		/* Enforce ordering of SUBNET_MASK options, according to
1188 		 * RFC2132 Section 3.3:
1189 		 *
1190 		 *   If both the subnet mask and the router option are
1191 		 *   specified in a DHCP reply, the subnet mask option MUST
1192 		 *   be first.
1193 		 *
1194 		 * This guidance does not specify what to do if the client
1195 		 * PRL explicitly requests the options out of order, it is
1196 		 * a general statement.
1197 		 */
1198 		if (priority_list[i] == DHO_SUBNET_MASK) {
1199 			for (ix = i - 1 ; ix >= 0 ; ix--) {
1200 				if (priority_list[ix] == DHO_ROUTERS) {
1201                                         /* swap */
1202 					priority_list[ix] = DHO_SUBNET_MASK;
1203 					priority_list[i] = DHO_ROUTERS;
1204 					break;
1205 				}
1206 			}
1207 		}
1208 	}
1209 
1210 	/* Copy out the options in the order that they appear in the
1211 	   priority list... */
1212 	for (i = 0; i < priority_len; i++) {
1213 	    /* Number of bytes left to store (some may already
1214 	       have been stored by a previous pass). */
1215 	    unsigned length;
1216 	    int optstart, soptstart, toptstart;
1217 	    struct universe *u;
1218 	    int have_encapsulation = 0;
1219 	    struct data_string encapsulation;
1220 	    int splitup;
1221 
1222 	    memset (&encapsulation, 0, sizeof encapsulation);
1223 	    have_encapsulation = 0;
1224 
1225 	    if (option != NULL)
1226 		option_dereference(&option, MDL);
1227 
1228 	    /* Code for next option to try to store. */
1229 	    code = priority_list [i];
1230 
1231 	    /* Look up the option in the site option space if the code
1232 	       is above the cutoff, otherwise in the DHCP option space. */
1233 	    if (code >= cfg_options -> site_code_min)
1234 		    u = universes [cfg_options -> site_universe];
1235 	    else
1236 		    u = &dhcp_universe;
1237 
1238 	    oc = lookup_option (u, cfg_options, code);
1239 
1240 	    if (oc && oc->option)
1241 		option_reference(&option, oc->option, MDL);
1242 	    else
1243 		option_code_hash_lookup(&option, u->code_hash, &code, 0, MDL);
1244 
1245 	    /* If it's a straight encapsulation, and the user supplied a
1246 	     * value for the entire option, use that.  Otherwise, search
1247 	     * the encapsulated space.
1248 	     *
1249 	     * If it's a limited encapsulation with preceding data, and the
1250 	     * user supplied values for the preceding bytes, search the
1251 	     * encapsulated space.
1252 	     */
1253 	    if ((option != NULL) &&
1254 		(((oc == NULL) && (option->format[0] == 'E')) ||
1255 		 ((oc != NULL) && (option->format[0] == 'e')))) {
1256 		static char *s, *t;
1257 		struct option_cache *tmp;
1258 		struct data_string name;
1259 
1260 		s = strchr (option->format, 'E');
1261 		if (s)
1262 		    t = strchr (++s, '.');
1263 		if (s && t) {
1264 		    memset (&name, 0, sizeof name);
1265 
1266 		    /* A zero-length universe name means the vendor
1267 		       option space, if one is defined. */
1268 		    if (t == s) {
1269 			if (vendor_cfg_option) {
1270 			    tmp = lookup_option (vendor_cfg_option -> universe,
1271 						 cfg_options,
1272 						 vendor_cfg_option -> code);
1273 			    if (tmp)
1274 				/* No need to check the return as we check name.len below */
1275 				(void) evaluate_option_cache (&name, packet, lease,
1276 							      client_state,
1277 							      in_options,
1278 							      cfg_options,
1279 							      scope, tmp, MDL);
1280 			} else if (vuname) {
1281 			    name.data = (unsigned char *)s;
1282 			    name.len = strlen (s);
1283 			}
1284 		    } else {
1285 			name.data = (unsigned char *)s;
1286 			name.len = t - s;
1287 		    }
1288 
1289 		    /* If we found a universe, and there are options configured
1290 		       for that universe, try to encapsulate it. */
1291 		    if (name.len) {
1292 			have_encapsulation =
1293 				(option_space_encapsulate
1294 				 (&encapsulation, packet, lease, client_state,
1295 				  in_options, cfg_options, scope, &name));
1296 			data_string_forget (&name, MDL);
1297 		    }
1298 		}
1299 	    }
1300 
1301 	    /* In order to avoid memory leaks, we have to get to here
1302 	       with any option cache that we allocated in tmp not being
1303 	       referenced by tmp, and whatever option cache is referenced
1304 	       by oc being an actual reference.   lookup_option doesn't
1305 	       generate a reference (this needs to be fixed), so the
1306 	       preceding goop ensures that if we *didn't* generate a new
1307 	       option cache, oc still winds up holding an actual reference. */
1308 
1309 	    /* If no data is available for this option, skip it. */
1310 	    if (!oc && !have_encapsulation) {
1311 		    continue;
1312 	    }
1313 
1314 	    /* Find the value of the option... */
1315 	    od.len = 0;
1316 	    if (oc) {
1317 		/* No need to check the return as we check od.len below */
1318 		(void) evaluate_option_cache (&od, packet,
1319 					      lease, client_state, in_options,
1320 					      cfg_options, scope, oc, MDL);
1321 
1322 		/* If we have encapsulation for this option, and an oc
1323 		 * lookup succeeded, but the evaluation failed, it is
1324 		 * either because this is a complex atom (atoms before
1325 		 * E on format list) and the top half of the option is
1326 		 * not configured, or this is a simple encapsulated
1327 		 * space and the evaluator is giving us a NULL.  Prefer
1328 		 * the evaluator's opinion over the subspace.
1329 		 */
1330 		if (!od.len) {
1331 		    data_string_forget (&encapsulation, MDL);
1332 		    data_string_forget (&od, MDL);
1333 		    continue;
1334 		}
1335 	    }
1336 
1337 	    /* We should now have a constant length for the option. */
1338 	    length = od.len;
1339 	    if (have_encapsulation) {
1340 		    length += encapsulation.len;
1341 
1342 		    /* od.len can be nonzero if we got here without an
1343 		     * oc (cache lookup failed), but did have an encapsulated
1344 		     * simple encapsulation space.
1345 		     */
1346 		    if (!od.len) {
1347 			    data_string_copy (&od, &encapsulation, MDL);
1348 			    data_string_forget (&encapsulation, MDL);
1349 		    } else {
1350 			    struct buffer *bp = (struct buffer *)0;
1351 			    if (!buffer_allocate (&bp, length, MDL)) {
1352 				    option_cache_dereference (&oc, MDL);
1353 				    data_string_forget (&od, MDL);
1354 				    data_string_forget (&encapsulation, MDL);
1355 				    continue;
1356 			    }
1357 			    memcpy (&bp -> data [0], od.data, od.len);
1358 			    memcpy (&bp -> data [od.len], encapsulation.data,
1359 				    encapsulation.len);
1360 			    data_string_forget (&od, MDL);
1361 			    data_string_forget (&encapsulation, MDL);
1362 			    od.data = &bp -> data [0];
1363 			    buffer_reference (&od.buffer, bp, MDL);
1364 			    buffer_dereference (&bp, MDL);
1365 			    od.len = length;
1366 			    od.terminated = 0;
1367 		    }
1368 	    }
1369 
1370 	    /* Do we add a NUL? */
1371 	    if (terminate && option && format_has_text(option->format)) {
1372 		    length++;
1373 		    tto = 1;
1374 	    } else {
1375 		    tto = 0;
1376 	    }
1377 
1378 	    /* Try to store the option. */
1379 
1380 	    /* If the option's length is more than 255, we must store it
1381 	       in multiple hunks.   Store 255-byte hunks first.  However,
1382 	       in any case, if the option data will cross a buffer
1383 	       boundary, split it across that boundary. */
1384 
1385 	    if (length > 255)
1386 		splitup = 1;
1387 	    else
1388 		splitup = 0;
1389 
1390 	    ix = 0;
1391 	    optstart = bufix;
1392 	    soptstart = six;
1393 	    toptstart = tix;
1394 	    while (length) {
1395 		    unsigned incr = length;
1396 		    int *pix;
1397 		    unsigned char *base;
1398 
1399 		    /* Try to fit it in the options buffer. */
1400 		    if (!splitup &&
1401 			((!six && !tix && (i == priority_len - 1) &&
1402 			  (bufix + 2 + length < bufend)) ||
1403 			 (bufix + 5 + length < bufend))) {
1404 			base = buffer;
1405 			pix = &bufix;
1406 		    /* Try to fit it in the second buffer. */
1407 		    } else if (!splitup && first_cutoff &&
1408 			       (first_cutoff + six + 3 + length < sbufend)) {
1409 			base = &buffer[first_cutoff];
1410 			pix = &six;
1411 		    /* Try to fit it in the third buffer. */
1412 		    } else if (!splitup && second_cutoff &&
1413 			       (second_cutoff + tix + 3 + length < buflen)) {
1414 			base = &buffer[second_cutoff];
1415 			pix = &tix;
1416 		    /* Split the option up into the remaining space. */
1417 		    } else {
1418 			splitup = 1;
1419 
1420 			/* Use any remaining options space. */
1421 			if (bufix + 6 < bufend) {
1422 			    incr = bufend - bufix - 5;
1423 			    base = buffer;
1424 			    pix = &bufix;
1425 			/* Use any remaining first_cutoff space. */
1426 			} else if (first_cutoff &&
1427 				   (first_cutoff + six + 4 < sbufend)) {
1428 			    incr = sbufend - (first_cutoff + six) - 3;
1429 			    base = &buffer[first_cutoff];
1430 			    pix = &six;
1431 			/* Use any remaining second_cutoff space. */
1432 			} else if (second_cutoff &&
1433 				   (second_cutoff + tix + 4 < buflen)) {
1434 			    incr = buflen - (second_cutoff + tix) - 3;
1435 			    base = &buffer[second_cutoff];
1436 			    pix = &tix;
1437 			/* Give up, roll back this option. */
1438 			} else {
1439 			    bufix = optstart;
1440 			    six = soptstart;
1441 			    tix = toptstart;
1442 			    break;
1443 			}
1444 		    }
1445 
1446 		    if (incr > length)
1447 			incr = length;
1448 		    if (incr > 255)
1449 			incr = 255;
1450 
1451 		    /* Everything looks good - copy it in! */
1452 		    base [*pix] = code;
1453 		    base [*pix + 1] = (unsigned char)incr;
1454 		    if (tto && incr == length) {
1455 			    if (incr > 1)
1456 				memcpy (base + *pix + 2,
1457 					od.data + ix, (unsigned)(incr - 1));
1458 			    base [*pix + 2 + incr - 1] = 0;
1459 		    } else {
1460 			    memcpy (base + *pix + 2,
1461 				    od.data + ix, (unsigned)incr);
1462 		    }
1463 		    length -= incr;
1464 		    ix += incr;
1465 		    *pix += 2 + incr;
1466 	    }
1467 	    data_string_forget (&od, MDL);
1468 	}
1469 
1470 	if (option != NULL)
1471 	    option_dereference(&option, MDL);
1472 
1473 	/* If we can overload, and we have, then PAD and END those spaces. */
1474 	if (first_cutoff && six) {
1475 	    if ((first_cutoff + six + 1) < sbufend)
1476 		memset (&buffer[first_cutoff + six + 1], DHO_PAD,
1477 			sbufend - (first_cutoff + six + 1));
1478 	    else if (first_cutoff + six >= sbufend)
1479 		log_fatal("Second buffer overflow in overloaded options.");
1480 
1481 	    buffer[first_cutoff + six] = DHO_END;
1482 	    if (ocount != NULL)
1483 	    	*ocount |= 1; /* So that caller knows there's data there. */
1484 	}
1485 
1486 	if (second_cutoff && tix) {
1487 	    if (second_cutoff + tix + 1 < buflen) {
1488 		memset (&buffer[second_cutoff + tix + 1], DHO_PAD,
1489 			buflen - (second_cutoff + tix + 1));
1490 	    } else if (second_cutoff + tix >= buflen)
1491 		log_fatal("Third buffer overflow in overloaded options.");
1492 
1493 	    buffer[second_cutoff + tix] = DHO_END;
1494 	    if (ocount != NULL)
1495 	    	*ocount |= 2; /* So that caller knows there's data there. */
1496 	}
1497 
1498 	if ((six || tix) && (bufix + 3 > bufend))
1499 	    log_fatal("Not enough space for option overload option.");
1500 
1501 	return bufix;
1502 }
1503 
1504 /* Return true if the format string has a variable length text option
1505  * ("t"), return false otherwise.
1506  */
1507 
1508 int
1509 format_has_text(format)
1510 	const char *format;
1511 {
1512 	const char *p;
1513 
1514 	p = format;
1515 	while (*p != '\0') {
1516 		switch (*p++) {
1517 		    case 'd':
1518 		    case 't':
1519 			return 1;
1520 
1521 			/* These symbols are arbitrary, not fixed or
1522 			 * determinable length...text options with them is
1523 			 * invalid (whatever the case, they are never NULL
1524 			 * terminated).
1525 			 */
1526 		    case 'A':
1527 		    case 'a':
1528 		    case 'X':
1529 		    case 'x':
1530 		    case 'D':
1531 			return 0;
1532 
1533 		    case 'c':
1534 			/* 'c' only follows 'D' atoms, and indicates that
1535 			 * compression may be used.  If there was a 'D'
1536 			 * atom already, we would have returned.  So this
1537 			 * is an error, but continue looking for 't' anyway.
1538 			 */
1539 			log_error("format_has_text(%s): 'c' atoms are illegal "
1540 				  "except after 'D' atoms.", format);
1541 			break;
1542 
1543 			/* 'E' is variable length, but not arbitrary...you
1544 			 * can find its length if you can find an END option.
1545 			 * N is (n)-byte in length but trails a name of a
1546 			 * space defining the enumeration values.  So treat
1547 			 * both the same - valid, fixed-length fields.
1548 			 */
1549 		    case 'E':
1550 		    case 'N':
1551 			/* Consume the space name. */
1552 			while ((*p != '\0') && (*p++ != '.'))
1553 				;
1554 			break;
1555 
1556 		    default:
1557 			break;
1558 		}
1559 	}
1560 
1561 	return 0;
1562 }
1563 
1564 /* Determine the minimum length of a DHCP option prior to any variable
1565  * or inconsistent length formats, according to its configured format
1566  * variable (and possibly from supplied option cache contents for variable
1567  * length format symbols).
1568  */
1569 
1570 int
1571 format_min_length(format, oc)
1572 	const char *format;
1573 	struct option_cache *oc;
1574 {
1575 	const char *p, *name;
1576 	int min_len = 0;
1577 	int last_size = 0;
1578 	struct enumeration *espace;
1579 
1580 	p = format;
1581 	while (*p != '\0') {
1582 		switch (*p++) {
1583 		    case '6': /* IPv6 Address */
1584 			min_len += 16;
1585 			last_size = 16;
1586 			break;
1587 
1588 		    case 'I': /* IPv4 Address */
1589 		    case 'l': /* int32_t */
1590 		    case 'L': /* uint32_t */
1591 		    case 'T': /* Lease Time, uint32_t equivalent */
1592 			min_len += 4;
1593 			last_size = 4;
1594 			break;
1595 
1596 		    case 's': /* int16_t */
1597 		    case 'S': /* uint16_t */
1598 			min_len += 2;
1599 			last_size = 2;
1600 			break;
1601 
1602 		    case 'N': /* Enumeration value. */
1603 			/* Consume space name. */
1604 			name = p;
1605 			p = strchr(p, '.');
1606 			if (p == NULL)
1607 				log_fatal("Corrupt format: %s", format);
1608 
1609 			espace = find_enumeration(name, p - name);
1610 			if (espace == NULL) {
1611 				log_error("Unknown enumeration: %s", format);
1612 				/* Max is safest value to return. */
1613 				return INT_MAX;
1614 			}
1615 
1616 			min_len += espace->width;
1617 			last_size = espace->width;
1618 			p++;
1619 
1620 			break;
1621 
1622 		    case 'b': /* int8_t */
1623 		    case 'B': /* uint8_t */
1624 		    case 'F': /* Flag that is always true. */
1625 		    case 'f': /* Flag */
1626 			min_len++;
1627 			last_size = 1;
1628 			break;
1629 
1630 		    case 'o': /* Last argument is optional. */
1631 			min_len -= last_size;
1632 
1633 		    /* XXX: It MAY be possible to sense the end of an
1634 		     * encapsulated space, but right now this is too
1635 		     * hard to support.  Return a safe value.
1636 		     */
1637 		    case 'e': /* Encapsulation hint (there is an 'E' later). */
1638 		    case 'E': /* Encapsulated options. */
1639 			return min_len;
1640 
1641 		    case 'd': /* "Domain name" */
1642 		    case 'D': /* "rfc1035 formatted names" */
1643 		    case 't': /* "ASCII Text" */
1644 		    case 'X': /* "ASCII or Hex Conditional */
1645 		    case 'x': /* "Hex" */
1646 		    case 'A': /* Array of all that precedes. */
1647 		    case 'a': /* Array of preceding symbol. */
1648 		    case 'Z': /* nothing. */
1649 			return min_len;
1650 
1651 		    case 'c': /* Compress flag for D atom. */
1652 			log_error("format_min_length(%s): 'c' atom is illegal "
1653 				  "except after 'D' atom.", format);
1654 			return INT_MAX;
1655 
1656 		    default:
1657 			/* No safe value is known. */
1658 			log_error("format_min_length(%s): No safe value "
1659 				  "for unknown format symbols.", format);
1660 			return INT_MAX;
1661 		}
1662 	}
1663 
1664 	return min_len;
1665 }
1666 
1667 
1668 /* Format the specified option so that a human can easily read it. */
1669 
1670 const char *pretty_print_option (option, data, len, emit_commas, emit_quotes)
1671 	struct option *option;
1672 	const unsigned char *data;
1673 	unsigned len;
1674 	int emit_commas;
1675 	int emit_quotes;
1676 {
1677 	static char optbuf [32768]; /* XXX */
1678 	static char *endbuf = &optbuf[sizeof(optbuf)];
1679 	int hunksize = 0;
1680 	int opthunk = 0;
1681 	int hunkinc = 0;
1682 	int numhunk = -1;
1683 	int numelem = 0;
1684 	int count;
1685 	int i, j, k, l;
1686 	char fmtbuf[32] = "";
1687 	struct iaddr iaddr;
1688 	struct enumeration *enumbuf[32]; /* MUST be same as fmtbuf */
1689 	char *op = optbuf;
1690 	const unsigned char *dp = data;
1691 	char comma;
1692 	unsigned long tval;
1693 	isc_boolean_t a_array = ISC_FALSE;
1694 	int len_used;
1695 
1696 	if (emit_commas)
1697 		comma = ',';
1698 	else
1699 		comma = ' ';
1700 
1701 	memset (enumbuf, 0, sizeof enumbuf);
1702 
1703 	/* Figure out the size of the data. */
1704 	for (l = i = 0; option -> format [i]; i++, l++) {
1705 		if (l >= sizeof(fmtbuf) - 1)
1706 			log_fatal("Bounds failure on internal buffer at "
1707 				  "%s:%d", MDL);
1708 
1709 		if (!numhunk) {
1710 			log_error ("%s: Extra codes in format string: %s",
1711 				   option -> name,
1712 				   &(option -> format [i]));
1713 			break;
1714 		}
1715 		numelem++;
1716 		fmtbuf [l] = option -> format [i];
1717 		switch (option -> format [i]) {
1718 		      case 'a':
1719 			a_array = ISC_TRUE;
1720 			/* Fall through */
1721 		      case 'A':
1722 			--numelem;
1723 			fmtbuf [l] = 0;
1724 			numhunk = 0;
1725 			break;
1726 		      case 'E':
1727 			/* Skip the universe name. */
1728 			while (option -> format [i] &&
1729 			       option -> format [i] != '.')
1730 				i++;
1731 			/* Fall Through! */
1732 		      case 'X':
1733 			for (k = 0; k < len; k++) {
1734 				if (!isascii (data [k]) ||
1735 				    !isprint (data [k]))
1736 					break;
1737 			}
1738 			/* If we found no bogus characters, or the bogus
1739 			   character we found is a trailing NUL, it's
1740 			   okay to print this option as text. */
1741 			if (k == len || (k + 1 == len && data [k] == 0)) {
1742 				fmtbuf [l] = 't';
1743 				numhunk = -2;
1744 			} else {
1745 				fmtbuf [l] = 'x';
1746 				hunksize++;
1747 				comma = ':';
1748 				numhunk = 0;
1749 				a_array = ISC_TRUE;
1750 				hunkinc = 1;
1751 			}
1752 			fmtbuf [l + 1] = 0;
1753 			break;
1754 		      case 'c':
1755 			/* The 'c' atom is a 'D' modifier only. */
1756 			log_error("'c' atom not following D atom in format "
1757 				  "string: %s", option->format);
1758 			break;
1759 		      case 'D':
1760 			/*
1761 			 * Skip the 'c' atom, if present.  It does not affect
1762 			 * how we convert wire->text format (if compression is
1763 			 * present either way, we still process it).
1764 			 */
1765 			if (option->format[i+1] == 'c')
1766 				i++;
1767 			fmtbuf[l + 1] = 0;
1768 			numhunk = -2;
1769 			break;
1770 		      case 'd':
1771 			fmtbuf[l] = 't';
1772 			/* Fall Through ! */
1773 		      case 't':
1774 			fmtbuf[l + 1] = 0;
1775 			numhunk = -2;
1776 			break;
1777 		      case 'N':
1778 			k = i;
1779 			while (option -> format [i] &&
1780 			       option -> format [i] != '.')
1781 				i++;
1782 			enumbuf [l] =
1783 				find_enumeration (&option -> format [k] + 1,
1784 						  i - k - 1);
1785 			if (enumbuf[l] == NULL) {
1786 				hunksize += 1;
1787 				hunkinc = 1;
1788 			} else {
1789 				hunksize += enumbuf[l]->width;
1790 				hunkinc = enumbuf[l]->width;
1791 			}
1792 			break;
1793 		      case '6':
1794 			hunksize += 16;
1795 			hunkinc = 16;
1796 			break;
1797 		      case 'I':
1798 		      case 'l':
1799 		      case 'L':
1800 		      case 'T':
1801 			hunksize += 4;
1802 			hunkinc = 4;
1803 			break;
1804 		      case 's':
1805 		      case 'S':
1806 			hunksize += 2;
1807 			hunkinc = 2;
1808 			break;
1809 		      case 'b':
1810 		      case 'B':
1811 		      case 'f':
1812 		      case 'F':
1813 			hunksize++;
1814 			hunkinc = 1;
1815 			break;
1816 		      case 'e':
1817 		      case 'Z':
1818 			break;
1819 		      case 'o':
1820 			opthunk += hunkinc;
1821 			break;
1822 		      default:
1823 			log_error ("%s: garbage in format string: %s",
1824 			      option -> name,
1825 			      &(option -> format [i]));
1826 			break;
1827 		}
1828 	}
1829 
1830 	/* Check for too few bytes... */
1831 	if (hunksize - opthunk > len) {
1832 		log_error ("%s: expecting at least %d bytes; got %d",
1833 		      option -> name,
1834 		      hunksize, len);
1835 		return "<error>";
1836 	}
1837 	/* Check for too many bytes... */
1838 	if (numhunk == -1 && hunksize < len)
1839 		log_error ("%s: %d extra bytes",
1840 		      option -> name,
1841 		      len - hunksize);
1842 
1843 	/* If this is an array, compute its size. */
1844 	if (numhunk == 0) {
1845 		if (a_array == ISC_TRUE) {
1846 			/*
1847 			 * It is an 'a' type array - we repeat the
1848 			 * last format type.  A binary string for 'X'
1849 			 * is also like this.  hunkinc is the size
1850 			 * of the last format type and we add 1 to
1851 			 * cover the entire first record.
1852 			 */
1853 			numhunk = ((len - hunksize) / hunkinc) + 1;
1854 			len_used = hunksize + ((numhunk - 1) * hunkinc);
1855 		} else {
1856 			/*
1857 			 * It is an 'A' type array - we repeat the
1858 			 * entire record
1859 			 */
1860 			numhunk = len / hunksize;
1861 			len_used = numhunk * hunksize;
1862 		}
1863 
1864 		/* See if we got an exact number of hunks. */
1865 		if (len_used < len) {
1866 			log_error ("%s: %d extra bytes at end of array\n",
1867 				   option -> name,
1868 				   len - len_used);
1869 		}
1870 	}
1871 
1872 
1873 	/* A one-hunk array prints the same as a single hunk. */
1874 	if (numhunk < 0)
1875 		numhunk = 1;
1876 
1877 	/* Cycle through the array (or hunk) printing the data. */
1878 	for (i = 0; i < numhunk; i++) {
1879 		if ((a_array == ISC_TRUE) && (i != 0) && (numelem > 0)) {
1880 			/*
1881 			 * For 'a' type of arrays we repeat
1882 			 * only the last format character
1883 			 * We should never hit the case of numelem == 0
1884 			 * but let's include the check to be safe.
1885 			 */
1886 			j = numelem - 1;
1887 		} else {
1888 			/*
1889 			 * for other types of arrays or the first
1890 			 * time through for 'a' types, we go through
1891 			 * the entire set of format characters.
1892 			 */
1893 			j = 0;
1894 		}
1895 
1896 		for (; j < numelem; j++) {
1897 			switch (fmtbuf [j]) {
1898 			      case 't':
1899 				/* endbuf-1 leaves room for NULL. */
1900 				k = pretty_text(&op, endbuf - 1, &dp,
1901 						data + len, emit_quotes);
1902 				if (k == -1) {
1903 					log_error("Error printing text.");
1904 					break;
1905 				}
1906 				*op = 0;
1907 				break;
1908 			      case 'D': /* RFC1035 format name list */
1909 				for( ; dp < (data + len) ; dp += k) {
1910 					unsigned char nbuff[NS_MAXCDNAME];
1911 					const unsigned char *nbp, *nend;
1912 
1913 					nend = &nbuff[sizeof(nbuff)];
1914 
1915 					/* If this is for ISC DHCP consumption
1916 					 * (emit_quotes), lay it out as a list
1917 					 * of STRING tokens.  Otherwise, it is
1918 					 * a space-separated list of DNS-
1919 					 * escaped names as /etc/resolv.conf
1920 					 * might digest.
1921 					 */
1922 					if (dp != data) {
1923 						if (op + 2 > endbuf)
1924 							break;
1925 
1926 						if (emit_quotes)
1927 							*op++ = ',';
1928 						*op++ = ' ';
1929 					}
1930 
1931 					/* XXX: if fmtbuf[j+1] != 'c', we
1932 					 * should warn if the data was
1933 					 * compressed anyway.
1934 					 */
1935 					k = MRns_name_unpack(data,
1936 							     data + len,
1937 							     dp, nbuff,
1938 							     sizeof(nbuff));
1939 
1940 					if (k == -1) {
1941 						log_error("Invalid domain "
1942 							  "list.");
1943 						break;
1944 					}
1945 
1946 					/* If emit_quotes, then use ISC DHCP
1947 					 * escapes.  Otherwise, rely only on
1948 					 * ns_name_ntop().
1949 					 */
1950 					if (emit_quotes) {
1951 						nbp = nbuff;
1952 						pretty_domain(&op, endbuf-1,
1953 							      &nbp, nend);
1954 					} else {
1955 						/* ns_name_ntop() includes
1956 						 * a trailing NUL in its
1957 						 * count.
1958 						 */
1959 						count = MRns_name_ntop(
1960 								nbuff, op,
1961 								(endbuf-op)-1);
1962 
1963 						if (count <= 0) {
1964 							log_error("Invalid "
1965 								"domain name.");
1966 							break;
1967 						}
1968 
1969 						/* Consume all but the trailing
1970 						 * NUL.
1971 						 */
1972 						op += count - 1;
1973 
1974 						/* Replace the trailing NUL
1975 						 * with the implicit root
1976 						 * (in the unlikely event the
1977 						 * domain name /is/ the root).
1978 						 */
1979 						*op++ = '.';
1980 					}
1981 				}
1982 				*op = '\0';
1983 				break;
1984 				/* pretty-printing an array of enums is
1985 				   going to get ugly. */
1986 			      case 'N':
1987 				if (!enumbuf [j]) {
1988 					tval = *dp++;
1989 					goto enum_as_num;
1990 				}
1991 
1992 				switch (enumbuf[j]->width) {
1993 				      case 1:
1994 					tval = getUChar(dp);
1995 					break;
1996 
1997 				     case 2:
1998 					tval = getUShort(dp);
1999 					break;
2000 
2001 				    case 4:
2002 					tval = getULong(dp);
2003 					break;
2004 
2005 				    default:
2006 					log_fatal("Impossible case at %s:%d.",
2007 						  MDL);
2008 					return "<double impossible condition>";
2009 				}
2010 
2011 				for (i = 0; ;i++) {
2012 					if (!enumbuf [j] -> values [i].name)
2013 						goto enum_as_num;
2014 					if (enumbuf [j] -> values [i].value ==
2015 					    tval)
2016 						break;
2017 				}
2018 				strcpy (op, enumbuf [j] -> values [i].name);
2019 				dp += enumbuf[j]->width;
2020 				break;
2021 
2022 			      enum_as_num:
2023 				sprintf(op, "%lu", tval);
2024 				break;
2025 
2026 			      case 'I':
2027 				iaddr.len = 4;
2028 				memcpy(iaddr.iabuf, dp, 4);
2029 				strcpy(op, piaddr(iaddr));
2030 				dp += 4;
2031 				break;
2032 			      case '6':
2033 				iaddr.len = 16;
2034 				memcpy(iaddr.iabuf, dp, 16);
2035 				strcpy(op, piaddr(iaddr));
2036 				dp += 16;
2037 				break;
2038 			      case 'l':
2039 				sprintf (op, "%ld", (long)getLong (dp));
2040 				dp += 4;
2041 				break;
2042 			      case 'T':
2043 				tval = getULong (dp);
2044 				if (tval == -1)
2045 					sprintf (op, "%s", "infinite");
2046 				else
2047 					sprintf(op, "%lu", tval);
2048 				break;
2049 			      case 'L':
2050 				sprintf(op, "%lu",
2051 					(unsigned long)getULong(dp));
2052 				dp += 4;
2053 				break;
2054 			      case 's':
2055 				sprintf (op, "%d", (int)getShort (dp));
2056 				dp += 2;
2057 				break;
2058 			      case 'S':
2059 				sprintf(op, "%u", (unsigned)getUShort(dp));
2060 				dp += 2;
2061 				break;
2062 			      case 'b':
2063 				sprintf (op, "%d", *(const char *)dp++);
2064 				break;
2065 			      case 'B':
2066 				sprintf (op, "%d", *dp++);
2067 				break;
2068 			      case 'X':
2069 			      case 'x':
2070 				sprintf (op, "%x", *dp++);
2071 				break;
2072 			      case 'f':
2073 				strcpy (op, *dp++ ? "true" : "false");
2074 				break;
2075 			      case 'F':
2076 				strcpy (op, "true");
2077 				break;
2078 			      case 'e':
2079 			      case 'Z':
2080 				*op = '\0';
2081 				break;
2082 			      default:
2083 				log_error ("Unexpected format code %c",
2084 					   fmtbuf [j]);
2085 			}
2086 			op += strlen (op);
2087 			if (dp == data + len)
2088 				break;
2089 			if (j + 1 < numelem && comma != ':')
2090 				*op++ = ' ';
2091 		}
2092 		if (i + 1 < numhunk) {
2093 			*op++ = comma;
2094 		}
2095 		if (dp == data + len)
2096 			break;
2097 	}
2098 	return optbuf;
2099 }
2100 
2101 int get_option (result, universe, packet, lease, client_state,
2102 		in_options, cfg_options, options, scope, code, file, line)
2103 	struct data_string *result;
2104 	struct universe *universe;
2105 	struct packet *packet;
2106 	struct lease *lease;
2107 	struct client_state *client_state;
2108 	struct option_state *in_options;
2109 	struct option_state *cfg_options;
2110 	struct option_state *options;
2111 	struct binding_scope **scope;
2112 	unsigned code;
2113 	const char *file;
2114 	int line;
2115 {
2116 	struct option_cache *oc;
2117 
2118 	if (!universe -> lookup_func)
2119 		return 0;
2120 	oc = ((*universe -> lookup_func) (universe, options, code));
2121 	if (!oc)
2122 		return 0;
2123 	if (!evaluate_option_cache (result, packet, lease, client_state,
2124 				    in_options, cfg_options, scope, oc,
2125 				    file, line))
2126 		return 0;
2127 	return 1;
2128 }
2129 
2130 void set_option (universe, options, option, op)
2131 	struct universe *universe;
2132 	struct option_state *options;
2133 	struct option_cache *option;
2134 	enum statement_op op;
2135 {
2136 	struct option_cache *oc, *noc;
2137 
2138 	switch (op) {
2139 	      case if_statement:
2140 	      case add_statement:
2141 	      case eval_statement:
2142 	      case break_statement:
2143 	      default:
2144 		log_error ("bogus statement type in set_option.");
2145 		break;
2146 
2147 	      case default_option_statement:
2148 		oc = lookup_option (universe, options,
2149 				    option -> option -> code);
2150 		if (oc)
2151 			break;
2152 		save_option (universe, options, option);
2153 		break;
2154 
2155 	      case supersede_option_statement:
2156 	      case send_option_statement:
2157 		/* Install the option, replacing any existing version. */
2158 		save_option (universe, options, option);
2159 		break;
2160 
2161 	      case append_option_statement:
2162 	      case prepend_option_statement:
2163 		oc = lookup_option (universe, options,
2164 				    option -> option -> code);
2165 		if (!oc) {
2166 			save_option (universe, options, option);
2167 			break;
2168 		}
2169 		/* If it's not an expression, make it into one. */
2170 		if (!oc -> expression && oc -> data.len) {
2171 			if (!expression_allocate (&oc -> expression, MDL)) {
2172 				log_error ("Can't allocate const expression.");
2173 				break;
2174 			}
2175 			oc -> expression -> op = expr_const_data;
2176 			data_string_copy
2177 				(&oc -> expression -> data.const_data,
2178 				 &oc -> data, MDL);
2179 			data_string_forget (&oc -> data, MDL);
2180 		}
2181 		noc = (struct option_cache *)0;
2182 		if (!option_cache_allocate (&noc, MDL))
2183 			break;
2184 		if (op == append_option_statement) {
2185 			if (!make_concat (&noc -> expression,
2186 					  oc -> expression,
2187 					  option -> expression)) {
2188 				option_cache_dereference (&noc, MDL);
2189 				break;
2190 			}
2191 		} else {
2192 			if (!make_concat (&noc -> expression,
2193 					  option -> expression,
2194 					  oc -> expression)) {
2195 				option_cache_dereference (&noc, MDL);
2196 				break;
2197 			}
2198 		}
2199 		option_reference(&(noc->option), oc->option, MDL);
2200 		save_option (universe, options, noc);
2201 		option_cache_dereference (&noc, MDL);
2202 		break;
2203 	}
2204 }
2205 
2206 struct option_cache *lookup_option (universe, options, code)
2207 	struct universe *universe;
2208 	struct option_state *options;
2209 	unsigned code;
2210 {
2211 	if (!options)
2212 		return (struct option_cache *)0;
2213 	if (universe -> lookup_func)
2214 		return (*universe -> lookup_func) (universe, options, code);
2215 	else
2216 		log_error ("can't look up options in %s space.",
2217 			   universe -> name);
2218 	return (struct option_cache *)0;
2219 }
2220 
2221 struct option_cache *lookup_hashed_option (universe, options, code)
2222 	struct universe *universe;
2223 	struct option_state *options;
2224 	unsigned code;
2225 {
2226 	int hashix;
2227 	pair bptr;
2228 	pair *hash;
2229 
2230 	/* Make sure there's a hash table. */
2231 	if (universe -> index >= options -> universe_count ||
2232 	    !(options -> universes [universe -> index]))
2233 		return (struct option_cache *)0;
2234 
2235 	hash = options -> universes [universe -> index];
2236 
2237 	hashix = compute_option_hash (code);
2238 	for (bptr = hash [hashix]; bptr; bptr = bptr -> cdr) {
2239 		if (((struct option_cache *)(bptr -> car)) -> option -> code ==
2240 		    code)
2241 			return (struct option_cache *)(bptr -> car);
2242 	}
2243 	return (struct option_cache *)0;
2244 }
2245 
2246 /* Save a specified buffer into an option cache. */
2247 int
2248 save_option_buffer(struct universe *universe, struct option_state *options,
2249 		   struct buffer *bp, unsigned char *buffer, unsigned length,
2250 		   unsigned code, int terminatep)
2251 {
2252 	struct option_cache *op = NULL;
2253 	int status = 1;
2254 
2255 	status = prepare_option_buffer(universe, bp, buffer, length, code,
2256 				       terminatep, &op);
2257 
2258 	if (status == 0)
2259 		goto cleanup;
2260 
2261 	save_option(universe, options, op);
2262 
2263     cleanup:
2264 	if (op != NULL)
2265 		option_cache_dereference(&op, MDL);
2266 
2267 	return status;
2268 }
2269 
2270 /* Append a specified buffer onto the tail of an option cache. */
2271 int
2272 append_option_buffer(struct universe *universe, struct option_state *options,
2273 		     struct buffer *bp, unsigned char *buffer, unsigned length,
2274 		     unsigned code, int terminatep)
2275 {
2276 	struct option_cache *op = NULL;
2277 	int status = 1;
2278 
2279 	status = prepare_option_buffer(universe, bp, buffer, length, code,
2280 				       terminatep, &op);
2281 
2282 	if (status == 0)
2283 		goto cleanup;
2284 
2285 	also_save_option(universe, options, op);
2286 
2287       cleanup:
2288 	if (op != NULL)
2289 		option_cache_dereference(&op, MDL);
2290 
2291 	return status;
2292 }
2293 
2294 /* Create/copy a buffer into a new option cache. */
2295 static int
2296 prepare_option_buffer(struct universe *universe, struct buffer *bp,
2297 		      unsigned char *buffer, unsigned length, unsigned code,
2298 		      int terminatep, struct option_cache **opp)
2299 {
2300 	struct buffer *lbp = NULL;
2301 	struct option *option = NULL;
2302 	struct option_cache *op;
2303 	int status = 1;
2304 
2305 	/* Code sizes of 8, 16, and 32 bits are allowed. */
2306 	switch(universe->tag_size) {
2307 	      case 1:
2308 		if (code > 0xff)
2309 			return 0;
2310 		break;
2311 	      case 2:
2312 		if (code > 0xffff)
2313 			return 0;
2314 		break;
2315 	      case 4:
2316 		if (code > 0xffffffff)
2317 			return 0;
2318 		break;
2319 
2320 	      default:
2321 		log_fatal("Inconsistent universe tag size at %s:%d.", MDL);
2322 	}
2323 
2324 	option_code_hash_lookup(&option, universe->code_hash, &code, 0, MDL);
2325 
2326 	/* If we created an option structure for each option a client
2327 	 * supplied, it's possible we may create > 2^32 option structures.
2328 	 * That's not feasible.  So by failing to enter these option
2329 	 * structures into the code and name hash tables, references will
2330 	 * never be more than 1 - when the option cache is destroyed, this
2331 	 * will be cleaned up.
2332 	 */
2333 	if (!option) {
2334 		char nbuf[sizeof("unknown-4294967295")];
2335 
2336 		sprintf(nbuf, "unknown-%u", code);
2337 
2338 		option = new_option(nbuf, MDL);
2339 
2340 		if (!option)
2341 			return 0;
2342 
2343 		option->format = default_option_format;
2344 		option->universe = universe;
2345 		option->code = code;
2346 
2347 		/* new_option() doesn't set references, pretend. */
2348 		option->refcnt = 1;
2349 	}
2350 
2351 	if (!option_cache_allocate (opp, MDL)) {
2352 		log_error("No memory for option code %s.%s.",
2353 			  universe->name, option->name);
2354 		status = 0;
2355 		goto cleanup;
2356 	}
2357 
2358 	/* Pointer rather than double pointer makes for less parens. */
2359 	op = *opp;
2360 
2361 	option_reference(&op->option, option, MDL);
2362 
2363 	/* If we weren't passed a buffer in which the data are saved and
2364 	   refcounted, allocate one now. */
2365 	if (!bp) {
2366 		if (!buffer_allocate (&lbp, length + terminatep, MDL)) {
2367 			log_error ("no memory for option buffer.");
2368 
2369 			status = 0;
2370 			goto cleanup;
2371 		}
2372 		memcpy (lbp -> data, buffer, length + terminatep);
2373 		bp = lbp;
2374 		buffer = &bp -> data [0]; /* Refer to saved buffer. */
2375 	}
2376 
2377 	/* Reference buffer copy to option cache. */
2378 	op -> data.buffer = (struct buffer *)0;
2379 	buffer_reference (&op -> data.buffer, bp, MDL);
2380 
2381 	/* Point option cache into buffer. */
2382 	op -> data.data = buffer;
2383 	op -> data.len = length;
2384 
2385 	if (terminatep) {
2386 		/* NUL terminate (we can get away with this because we (or
2387 		   the caller!) allocated one more than the buffer size, and
2388 		   because the byte following the end of an option is always
2389 		   the code of the next option, which the caller is getting
2390 		   out of the *original* buffer. */
2391 		buffer [length] = 0;
2392 		op -> data.terminated = 1;
2393 	} else
2394 		op -> data.terminated = 0;
2395 
2396 	/* If this option is ultimately a text option, null determinate to
2397 	 * comply with RFC2132 section 2.  Mark a flag so this can be sensed
2398 	 * later to echo NULLs back to clients that supplied them (they
2399 	 * probably expect them).
2400 	 */
2401 	if (format_has_text(option->format)) {
2402 		int min_len = format_min_length(option->format, op);
2403 
2404 		while ((op->data.len > min_len) &&
2405 		       (op->data.data[op->data.len-1] == '\0')) {
2406 			op->data.len--;
2407 			op->flags |= OPTION_HAD_NULLS;
2408 		}
2409 	}
2410 
2411 	/* And let go of our references. */
2412       cleanup:
2413 	if (lbp != NULL)
2414 		buffer_dereference(&lbp, MDL);
2415 	option_dereference(&option, MDL);
2416 
2417 	return status;
2418 }
2419 
2420 static void
2421 count_options(struct option_cache *dummy_oc,
2422 	      struct packet *dummy_packet,
2423 	      struct lease *dummy_lease,
2424 	      struct client_state *dummy_client_state,
2425 	      struct option_state *dummy_opt_state,
2426 	      struct option_state *opt_state,
2427 	      struct binding_scope **dummy_binding_scope,
2428 	      struct universe *dummy_universe,
2429 	      void *void_accumulator) {
2430 	int *accumulator = (int *)void_accumulator;
2431 
2432 	*accumulator += 1;
2433 }
2434 
2435 static void
2436 collect_oro(struct option_cache *oc,
2437 	    struct packet *dummy_packet,
2438 	    struct lease *dummy_lease,
2439 	    struct client_state *dummy_client_state,
2440 	    struct option_state *dummy_opt_state,
2441 	    struct option_state *opt_state,
2442 	    struct binding_scope **dummy_binding_scope,
2443 	    struct universe *dummy_universe,
2444 	    void *void_oro) {
2445 	struct data_string *oro = (struct data_string *)void_oro;
2446 
2447 	putUShort(oro->buffer->data + oro->len, oc->option->code);
2448 	oro->len += 2;
2449 }
2450 
2451 /* build_server_oro() is presently unusued, but may be used at a future date
2452  * with support for Reconfigure messages (as a hint to the client about new
2453  * option value contents).
2454  */
2455 void
2456 build_server_oro(struct data_string *server_oro,
2457 		 struct option_state *options,
2458 		 const char *file, int line) {
2459 	int num_opts;
2460 	int i;
2461 	struct option *o;
2462 
2463 	/*
2464 	 * Count the number of options, so we can allocate enough memory.
2465 	 * We want to mention sub-options too, so check all universes.
2466 	 */
2467 	num_opts = 0;
2468 	option_space_foreach(NULL, NULL, NULL, NULL, options,
2469 			     NULL, &dhcpv6_universe, (void *)&num_opts,
2470 			     count_options);
2471 	for (i=0; i < options->universe_count; i++) {
2472 		if (options->universes[i] != NULL) {
2473 		    	o = universes[i]->enc_opt;
2474 			while (o != NULL) {
2475 				if (o->universe == &dhcpv6_universe) {
2476 					num_opts++;
2477 					break;
2478 				}
2479 				o = o->universe->enc_opt;
2480 			}
2481 		}
2482 	}
2483 
2484 	/*
2485 	 * Allocate space.
2486 	 */
2487 	memset(server_oro, 0, sizeof(*server_oro));
2488 	if (!buffer_allocate(&server_oro->buffer, num_opts * 2, MDL)) {
2489 		log_fatal("no memory to build server ORO");
2490 	}
2491 	server_oro->data = server_oro->buffer->data;
2492 
2493 	/*
2494 	 * Copy the data in.
2495 	 * We want to mention sub-options too, so check all universes.
2496 	 */
2497 	server_oro->len = 0; 	/* gets set in collect_oro */
2498 	option_space_foreach(NULL, NULL, NULL, NULL, options,
2499 			     NULL, &dhcpv6_universe, (void *)server_oro,
2500 			     collect_oro);
2501 	for (i=0; i < options->universe_count; i++) {
2502 		if (options->universes[i] != NULL) {
2503 		    	o = universes[i]->enc_opt;
2504 			while (o != NULL) {
2505 				if (o->universe == &dhcpv6_universe) {
2506 					unsigned char *tmp;
2507 					tmp = server_oro->buffer->data;
2508 					putUShort(tmp + server_oro->len,
2509 						  o->code);
2510 					server_oro->len += 2;
2511 					break;
2512 				}
2513 				o = o->universe->enc_opt;
2514 			}
2515 		}
2516 	}
2517 }
2518 
2519 /* Wrapper function to put an option cache into an option state. */
2520 void
2521 save_option(struct universe *universe, struct option_state *options,
2522 	    struct option_cache *oc)
2523 {
2524 	if (universe->save_func)
2525 		(*universe->save_func)(universe, options, oc, ISC_FALSE);
2526 	else
2527 		log_error("can't store options in %s space.", universe->name);
2528 }
2529 
2530 /* Wrapper function to append an option cache into an option state's list. */
2531 void
2532 also_save_option(struct universe *universe, struct option_state *options,
2533 		 struct option_cache *oc)
2534 {
2535 	if (universe->save_func)
2536 		(*universe->save_func)(universe, options, oc, ISC_TRUE);
2537 	else
2538 		log_error("can't store options in %s space.", universe->name);
2539 }
2540 
2541 void
2542 save_hashed_option(struct universe *universe, struct option_state *options,
2543 		   struct option_cache *oc, isc_boolean_t appendp)
2544 {
2545 	int hashix;
2546 	pair bptr;
2547 	pair *hash = options -> universes [universe -> index];
2548 	struct option_cache **ocloc;
2549 
2550 	if (oc -> refcnt == 0)
2551 		abort ();
2552 
2553 	/* Compute the hash. */
2554 	hashix = compute_option_hash (oc -> option -> code);
2555 
2556 	/* If there's no hash table, make one. */
2557 	if (!hash) {
2558 		hash = (pair *)dmalloc (OPTION_HASH_SIZE * sizeof *hash, MDL);
2559 		if (!hash) {
2560 			log_error ("no memory to store %s.%s",
2561 				   universe -> name, oc -> option -> name);
2562 			return;
2563 		}
2564 		memset (hash, 0, OPTION_HASH_SIZE * sizeof *hash);
2565 		options -> universes [universe -> index] = (void *)hash;
2566 	} else {
2567 		/* Try to find an existing option matching the new one. */
2568 		for (bptr = hash [hashix]; bptr; bptr = bptr -> cdr) {
2569 			if (((struct option_cache *)
2570 			     (bptr -> car)) -> option -> code ==
2571 			    oc -> option -> code)
2572 				break;
2573 		}
2574 
2575 		/* Deal with collisions on the hash list. */
2576 		if (bptr) {
2577 			ocloc = (struct option_cache **)&bptr->car;
2578 
2579 			/*
2580 			 * If appendp is set, append it onto the tail of the
2581 			 * ->next list.  If it is not set, rotate it into
2582 			 * position at the head of the list.
2583 			 */
2584 			if (appendp) {
2585 				do {
2586 					ocloc = &(*ocloc)->next;
2587 				} while (*ocloc != NULL);
2588 			} else {
2589 				option_cache_dereference(ocloc, MDL);
2590 			}
2591 
2592 			option_cache_reference(ocloc, oc, MDL);
2593 			return;
2594 		}
2595 	}
2596 
2597 	/* Otherwise, just put the new one at the head of the list. */
2598 	bptr = new_pair (MDL);
2599 	if (!bptr) {
2600 		log_error ("No memory for option_cache reference.");
2601 		return;
2602 	}
2603 	bptr -> cdr = hash [hashix];
2604 	bptr -> car = 0;
2605 	option_cache_reference ((struct option_cache **)&bptr -> car, oc, MDL);
2606 	hash [hashix] = bptr;
2607 }
2608 
2609 void delete_option (universe, options, code)
2610 	struct universe *universe;
2611 	struct option_state *options;
2612 	int code;
2613 {
2614 	if (universe -> delete_func)
2615 		(*universe -> delete_func) (universe, options, code);
2616 	else
2617 		log_error ("can't delete options from %s space.",
2618 			   universe -> name);
2619 }
2620 
2621 void delete_hashed_option (universe, options, code)
2622 	struct universe *universe;
2623 	struct option_state *options;
2624 	int code;
2625 {
2626 	int hashix;
2627 	pair bptr, prev = (pair)0;
2628 	pair *hash = options -> universes [universe -> index];
2629 
2630 	/* There may not be any options in this space. */
2631 	if (!hash)
2632 		return;
2633 
2634 	/* Try to find an existing option matching the new one. */
2635 	hashix = compute_option_hash (code);
2636 	for (bptr = hash [hashix]; bptr; bptr = bptr -> cdr) {
2637 		if (((struct option_cache *)(bptr -> car)) -> option -> code
2638 		    == code)
2639 			break;
2640 		prev = bptr;
2641 	}
2642 	/* If we found one, wipe it out... */
2643 	if (bptr) {
2644 		if (prev)
2645 			prev -> cdr = bptr -> cdr;
2646 		else
2647 			hash [hashix] = bptr -> cdr;
2648 		option_cache_dereference
2649 			((struct option_cache **)(&bptr -> car), MDL);
2650 		free_pair (bptr, MDL);
2651 	}
2652 }
2653 
2654 extern struct option_cache *free_option_caches; /* XXX */
2655 
2656 int option_cache_dereference (ptr, file, line)
2657 	struct option_cache **ptr;
2658 	const char *file;
2659 	int line;
2660 {
2661 	if (!ptr || !*ptr) {
2662 		log_error ("Null pointer in option_cache_dereference: %s(%d)",
2663 			   file, line);
2664 #if defined (POINTER_DEBUG)
2665 		abort ();
2666 #else
2667 		return 0;
2668 #endif
2669 	}
2670 
2671 	(*ptr) -> refcnt--;
2672 	rc_register (file, line, ptr, *ptr, (*ptr) -> refcnt, 1, RC_MISC);
2673 	if (!(*ptr) -> refcnt) {
2674 		if ((*ptr) -> data.buffer)
2675 			data_string_forget (&(*ptr) -> data, file, line);
2676 		if ((*ptr)->option)
2677 			option_dereference(&(*ptr)->option, MDL);
2678 		if ((*ptr) -> expression)
2679 			expression_dereference (&(*ptr) -> expression,
2680 						file, line);
2681 		if ((*ptr) -> next)
2682 			option_cache_dereference (&((*ptr) -> next),
2683 						  file, line);
2684 		/* Put it back on the free list... */
2685 		(*ptr) -> expression = (struct expression *)free_option_caches;
2686 		free_option_caches = *ptr;
2687 		dmalloc_reuse (free_option_caches, (char *)0, 0, 0);
2688 	}
2689 	if ((*ptr) -> refcnt < 0) {
2690 		log_error ("%s(%d): negative refcnt!", file, line);
2691 #if defined (DEBUG_RC_HISTORY)
2692 		dump_rc_history (*ptr);
2693 #endif
2694 #if defined (POINTER_DEBUG)
2695 		abort ();
2696 #else
2697 		*ptr = (struct option_cache *)0;
2698 		return 0;
2699 #endif
2700 	}
2701 	*ptr = (struct option_cache *)0;
2702 	return 1;
2703 
2704 }
2705 
2706 int hashed_option_state_dereference (universe, state, file, line)
2707 	struct universe *universe;
2708 	struct option_state *state;
2709 	const char *file;
2710 	int line;
2711 {
2712 	pair *heads;
2713 	pair cp, next;
2714 	int i;
2715 
2716 	/* Get the pointer to the array of hash table bucket heads. */
2717 	heads = (pair *)(state -> universes [universe -> index]);
2718 	if (!heads)
2719 		return 0;
2720 
2721 	/* For each non-null head, loop through all the buckets dereferencing
2722 	   the attached option cache structures and freeing the buckets. */
2723 	for (i = 0; i < OPTION_HASH_SIZE; i++) {
2724 		for (cp = heads [i]; cp; cp = next) {
2725 			next = cp -> cdr;
2726 			option_cache_dereference
2727 				((struct option_cache **)&cp -> car,
2728 				 file, line);
2729 			free_pair (cp, file, line);
2730 		}
2731 	}
2732 
2733 	dfree (heads, file, line);
2734 	state -> universes [universe -> index] = (void *)0;
2735 	return 1;
2736 }
2737 
2738 /* The 'data_string' primitive doesn't have an appension mechanism.
2739  * This function must then append a new option onto an existing buffer
2740  * by first duplicating the original buffer and appending the desired
2741  * values, followed by coping the new value into place.
2742  */
2743 int
2744 append_option(struct data_string *dst, struct universe *universe,
2745 	      struct option *option, struct data_string *src)
2746 {
2747 	struct data_string tmp;
2748 
2749 	if (src->len == 0 && option->format[0] != 'Z')
2750 		return 0;
2751 
2752 	memset(&tmp, 0, sizeof(tmp));
2753 
2754 	/* Allocate a buffer to hold existing data, the current option's
2755 	 * tag and length, and the option's content.
2756 	 */
2757 	if (!buffer_allocate(&tmp.buffer,
2758 			     (dst->len + universe->length_size +
2759 			      universe->tag_size + src->len), MDL)) {
2760 		/* XXX: This kills all options presently stored in the
2761 		 * destination buffer.  This is the way the original code
2762 		 * worked, and assumes an 'all or nothing' approach to
2763 		 * eg encapsulated option spaces.  It may or may not be
2764 		 * desirable.
2765 		 */
2766 		data_string_forget(dst, MDL);
2767 		return 0;
2768 	}
2769 	tmp.data = tmp.buffer->data;
2770 
2771 	/* Copy the existing data off the destination. */
2772 	if (dst->len != 0)
2773 		memcpy(tmp.buffer->data, dst->data, dst->len);
2774 	tmp.len = dst->len;
2775 
2776 	/* Place the new option tag and length. */
2777 	(*universe->store_tag)(tmp.buffer->data + tmp.len, option->code);
2778 	tmp.len += universe->tag_size;
2779 	(*universe->store_length)(tmp.buffer->data + tmp.len, src->len);
2780 	tmp.len += universe->length_size;
2781 
2782 	/* Copy the option contents onto the end. */
2783 	memcpy(tmp.buffer->data + tmp.len, src->data, src->len);
2784 	tmp.len += src->len;
2785 
2786 	/* Play the shell game. */
2787 	data_string_forget(dst, MDL);
2788 	data_string_copy(dst, &tmp, MDL);
2789 	data_string_forget(&tmp, MDL);
2790 	return 1;
2791 }
2792 
2793 int
2794 store_option(struct data_string *result, struct universe *universe,
2795 	     struct packet *packet, struct lease *lease,
2796 	     struct client_state *client_state,
2797 	     struct option_state *in_options, struct option_state *cfg_options,
2798 	     struct binding_scope **scope, struct option_cache *oc)
2799 {
2800 	struct data_string tmp;
2801 	struct universe *subu=NULL;
2802 	int status;
2803 	char *start, *end;
2804 
2805 	memset(&tmp, 0, sizeof(tmp));
2806 
2807 	if (evaluate_option_cache(&tmp, packet, lease, client_state,
2808 				  in_options, cfg_options, scope, oc, MDL)) {
2809 		/* If the option is an extended 'e'ncapsulation (not a
2810 		 * direct 'E'ncapsulation), append the encapsulated space
2811 		 * onto the currently prepared value.
2812 		 */
2813 		do {
2814 			if (oc->option->format &&
2815 			    oc->option->format[0] == 'e') {
2816 				/* Skip forward to the universe name. */
2817 				start = strchr(oc->option->format, 'E');
2818 				if (start == NULL)
2819 					break;
2820 
2821 				/* Locate the name-terminating '.'. */
2822 				end = strchr(++start, '.');
2823 
2824 				/* A zero-length name is not allowed in
2825 				 * these kinds of encapsulations.
2826 				 */
2827 				if (end == NULL || start == end)
2828 					break;
2829 
2830 				universe_hash_lookup(&subu, universe_hash,
2831 						     start, end - start, MDL);
2832 
2833 				if (subu == NULL) {
2834 					log_error("store_option: option %d "
2835 						  "refers to unknown "
2836 						  "option space '%.*s'.",
2837 						  oc->option->code,
2838 						  (int)(end - start), start);
2839 					break;
2840 				}
2841 
2842 				/* Append encapsulations, if any.  We
2843 				 * already have the prepended values, so
2844 				 * we send those even if there are no
2845 				 * encapsulated options (and ->encapsulate()
2846 				 * returns zero).
2847 				 */
2848 				subu->encapsulate(&tmp, packet, lease,
2849 						  client_state, in_options,
2850 						  cfg_options, scope, subu);
2851 				subu = NULL;
2852 			}
2853 		} while (ISC_FALSE);
2854 
2855 		status = append_option(result, universe, oc->option, &tmp);
2856 		data_string_forget(&tmp, MDL);
2857 
2858 		return status;
2859 	}
2860 
2861 	return 0;
2862 }
2863 
2864 int option_space_encapsulate (result, packet, lease, client_state,
2865 			      in_options, cfg_options, scope, name)
2866 	struct data_string *result;
2867 	struct packet *packet;
2868 	struct lease *lease;
2869 	struct client_state *client_state;
2870 	struct option_state *in_options;
2871 	struct option_state *cfg_options;
2872 	struct binding_scope **scope;
2873 	struct data_string *name;
2874 {
2875 	struct universe *u = NULL;
2876 	int status = 0;
2877 
2878 	universe_hash_lookup(&u, universe_hash,
2879 			     (const char *)name->data, name->len, MDL);
2880 	if (u == NULL) {
2881 		log_error("option_space_encapsulate: option space '%.*s' does "
2882 			  "not exist, but is configured.",
2883 			  (int)name->len, name->data);
2884 		return status;
2885 	}
2886 
2887 	if (u->encapsulate != NULL) {
2888 		if (u->encapsulate(result, packet, lease, client_state,
2889 				   in_options, cfg_options, scope, u))
2890 			status = 1;
2891 	} else
2892 		log_error("encapsulation requested for '%s' with no support.",
2893 			  name->data);
2894 
2895 	return status;
2896 }
2897 
2898 /* Attempt to store any 'E'ncapsulated options that have not yet been
2899  * placed on the option buffer by the above (configuring a value in
2900  * the space over-rides any values in the child universe).
2901  *
2902  * Note that there are far fewer universes than there will ever be
2903  * options in any universe.  So it is faster to traverse the
2904  * configured universes, checking if each is encapsulated in the
2905  * current universe, and if so attempting to do so.
2906  *
2907  * For each configured universe for this configuration option space,
2908  * which is encapsulated within the current universe, can not be found
2909  * by the lookup function (the universe-specific encapsulation
2910  * functions would already have stored such a value), and encapsulates
2911  * at least one option, append it.
2912  */
2913 static int
2914 search_subencapsulation(struct data_string *result, struct packet *packet,
2915 			struct lease *lease, struct client_state *client_state,
2916 			struct option_state *in_options,
2917 			struct option_state *cfg_options,
2918 			struct binding_scope **scope,
2919 			struct universe *universe)
2920 {
2921 	struct data_string sub;
2922 	struct universe *subu;
2923 	int i, status = 0;
2924 
2925 	memset(&sub, 0, sizeof(sub));
2926 	for (i = 0 ; i < cfg_options->universe_count ; i++) {
2927 		subu = universes[i];
2928 
2929 		if (subu == NULL)
2930 			log_fatal("Impossible condition at %s:%d.", MDL);
2931 
2932 		if (subu->enc_opt != NULL &&
2933 		    subu->enc_opt->universe == universe &&
2934 		    subu->enc_opt->format != NULL &&
2935 		    subu->enc_opt->format[0] == 'E' &&
2936 		    lookup_option(universe, cfg_options,
2937 				  subu->enc_opt->code) == NULL &&
2938 		    subu->encapsulate(&sub, packet, lease, client_state,
2939 				      in_options, cfg_options,
2940 				      scope, subu)) {
2941 			if (append_option(result, universe,
2942 					  subu->enc_opt, &sub))
2943 				status = 1;
2944 
2945 			data_string_forget(&sub, MDL);
2946 		}
2947 	}
2948 
2949 	return status;
2950 }
2951 
2952 int hashed_option_space_encapsulate (result, packet, lease, client_state,
2953 				     in_options, cfg_options, scope, universe)
2954 	struct data_string *result;
2955 	struct packet *packet;
2956 	struct lease *lease;
2957 	struct client_state *client_state;
2958 	struct option_state *in_options;
2959 	struct option_state *cfg_options;
2960 	struct binding_scope **scope;
2961 	struct universe *universe;
2962 {
2963 	pair p, *hash;
2964 	int status;
2965 	int i;
2966 
2967 	if (universe -> index >= cfg_options -> universe_count)
2968 		return 0;
2969 
2970 	hash = cfg_options -> universes [universe -> index];
2971 	if (!hash)
2972 		return 0;
2973 
2974 	/* For each hash bucket, and each configured option cache within
2975 	 * that bucket, append the option onto the buffer in encapsulated
2976 	 * format appropriate to the universe.
2977 	 */
2978 	status = 0;
2979 	for (i = 0; i < OPTION_HASH_SIZE; i++) {
2980 		for (p = hash [i]; p; p = p -> cdr) {
2981 			if (store_option(result, universe, packet, lease,
2982 					 client_state, in_options, cfg_options,
2983 					 scope, (struct option_cache *)p->car))
2984 				status = 1;
2985 		}
2986 	}
2987 
2988 	if (search_subencapsulation(result, packet, lease, client_state,
2989 				    in_options, cfg_options, scope, universe))
2990 		status = 1;
2991 
2992 	return status;
2993 }
2994 
2995 int nwip_option_space_encapsulate (result, packet, lease, client_state,
2996 				   in_options, cfg_options, scope, universe)
2997 	struct data_string *result;
2998 	struct packet *packet;
2999 	struct lease *lease;
3000 	struct client_state *client_state;
3001 	struct option_state *in_options;
3002 	struct option_state *cfg_options;
3003 	struct binding_scope **scope;
3004 	struct universe *universe;
3005 {
3006 	pair ocp;
3007 	int status;
3008 	static struct option_cache *no_nwip;
3009 	struct data_string ds;
3010 	struct option_chain_head *head;
3011 
3012 	if (universe -> index >= cfg_options -> universe_count)
3013 		return 0;
3014 	head = ((struct option_chain_head *)
3015 		cfg_options -> universes [nwip_universe.index]);
3016 	if (!head)
3017 		return 0;
3018 
3019 	status = 0;
3020 	for (ocp = head -> first; ocp; ocp = ocp -> cdr) {
3021 		if (store_option (result, universe, packet,
3022 				  lease, client_state, in_options,
3023 				  cfg_options, scope,
3024 				  (struct option_cache *)ocp -> car))
3025 			status = 1;
3026 	}
3027 
3028 	/* If there's no data, the nwip suboption is supposed to contain
3029 	   a suboption saying there's no data. */
3030 	if (!status) {
3031 		if (!no_nwip) {
3032 			unsigned one = 1;
3033 			static unsigned char nni [] = { 1, 0 };
3034 
3035 			memset (&ds, 0, sizeof ds);
3036 			ds.data = nni;
3037 			ds.len = 2;
3038 			if (option_cache_allocate (&no_nwip, MDL))
3039 				data_string_copy (&no_nwip -> data, &ds, MDL);
3040 			if (!option_code_hash_lookup(&no_nwip->option,
3041 						     nwip_universe.code_hash,
3042 						     &one, 0, MDL))
3043 				log_fatal("Nwip option hash does not contain "
3044 					  "1 (%s:%d).", MDL);
3045 		}
3046 		if (no_nwip) {
3047 			if (store_option (result, universe, packet, lease,
3048 					  client_state, in_options,
3049 					  cfg_options, scope, no_nwip))
3050 				status = 1;
3051 		}
3052 	} else {
3053 		memset (&ds, 0, sizeof ds);
3054 
3055 		/* If we have nwip options, the first one has to be the
3056 		   nwip-exists-in-option-area option. */
3057 		if (!buffer_allocate (&ds.buffer, result -> len + 2, MDL)) {
3058 			data_string_forget (result, MDL);
3059 			return 0;
3060 		}
3061 		ds.data = &ds.buffer -> data [0];
3062 		ds.buffer -> data [0] = 2;
3063 		ds.buffer -> data [1] = 0;
3064 		memcpy (&ds.buffer -> data [2], result -> data, result -> len);
3065 		data_string_forget (result, MDL);
3066 		data_string_copy (result, &ds, MDL);
3067 		data_string_forget (&ds, MDL);
3068 	}
3069 
3070 	return status;
3071 }
3072 
3073 /* We don't want to use ns_name_pton()...it doesn't tell us how many bytes
3074  * it has consumed, and it plays havoc with our escapes.
3075  *
3076  * So this function does DNS encoding, and returns either the number of
3077  * octects consumed (on success), or -1 on failure.
3078  */
3079 static int
3080 fqdn_encode(unsigned char *dst, int dstlen, const unsigned char *src,
3081 	    int srclen)
3082 {
3083 	unsigned char *out;
3084 	int i, j, len, outlen=0;
3085 
3086 	out = dst;
3087 	for (i = 0, j = 0 ; i < srclen ; i = j) {
3088 		while ((j < srclen) && (src[j] != '.') && (src[j] != '\0'))
3089 			j++;
3090 
3091 		len = j - i;
3092 		if ((outlen + 1 + len) > dstlen)
3093 			return -1;
3094 
3095 		*out++ = len;
3096 		outlen++;
3097 
3098 		/* We only do one FQDN, ending in one root label. */
3099 		if (len == 0)
3100 			return outlen;
3101 
3102 		memcpy(out, src + i, len);
3103 		out += len;
3104 		outlen += len;
3105 
3106 		/* Advance past the root label. */
3107 		j++;
3108 	}
3109 
3110 	if ((outlen + 1) > dstlen)
3111 		return -1;
3112 
3113 	/* Place the root label. */
3114 	*out++ = 0;
3115 	outlen++;
3116 
3117 	return outlen;
3118 }
3119 
3120 int fqdn_option_space_encapsulate (result, packet, lease, client_state,
3121 				   in_options, cfg_options, scope, universe)
3122 	struct data_string *result;
3123 	struct packet *packet;
3124 	struct lease *lease;
3125 	struct client_state *client_state;
3126 	struct option_state *in_options;
3127 	struct option_state *cfg_options;
3128 	struct binding_scope **scope;
3129 	struct universe *universe;
3130 {
3131 	pair ocp;
3132 	struct data_string results [FQDN_SUBOPTION_COUNT + 1];
3133 	int status = 1;
3134 	int i;
3135 	unsigned len;
3136 	struct buffer *bp = (struct buffer *)0;
3137 	struct option_chain_head *head;
3138 
3139 	/* If there's no FQDN universe, don't encapsulate. */
3140 	if (fqdn_universe.index >= cfg_options -> universe_count)
3141 		return 0;
3142 	head = ((struct option_chain_head *)
3143 		cfg_options -> universes [fqdn_universe.index]);
3144 	if (!head)
3145 		return 0;
3146 
3147 	/* Figure out the values of all the suboptions. */
3148 	memset (results, 0, sizeof results);
3149 	for (ocp = head -> first; ocp; ocp = ocp -> cdr) {
3150 		struct option_cache *oc = (struct option_cache *)(ocp -> car);
3151 		if (oc -> option -> code > FQDN_SUBOPTION_COUNT)
3152 			continue;
3153 		/* No need to check the return code, we check the length later */
3154 		(void) evaluate_option_cache (&results[oc->option->code],
3155 					      packet, lease, client_state,
3156 					      in_options, cfg_options, scope,
3157 					      oc, MDL);
3158 	}
3159 	/* We add a byte for the flags field.
3160 	 * We add two bytes for the two RCODE fields.
3161 	 * We add a byte because we will prepend a label count.
3162 	 * We add a byte because the input len doesn't count null termination,
3163 	 * and we will add a root label.
3164 	 */
3165 	len = 5 + results [FQDN_FQDN].len;
3166 	/* Save the contents of the option in a buffer. */
3167 	if (!buffer_allocate (&bp, len, MDL)) {
3168 		log_error ("no memory for option buffer.");
3169 		status = 0;
3170 		goto exit;
3171 	}
3172 	buffer_reference (&result -> buffer, bp, MDL);
3173 	result -> len = 3;
3174 	result -> data = &bp -> data [0];
3175 
3176 	memset (&bp -> data [0], 0, len);
3177 	/* XXX: The server should set bit 4 (yes, 4, not 3) to 1 if it is
3178 	 * not going to perform any ddns updates.  The client should set the
3179 	 * bit if it doesn't want the server to perform any updates.
3180 	 * The problem is at this layer of abstraction we have no idea if
3181 	 * the caller is a client or server.
3182 	 *
3183 	 * See RFC4702, Section 3.1, 'The "N" bit'.
3184 	 *
3185 	 * if (?)
3186 	 *	bp->data[0] |= 8;
3187 	 */
3188 	if (results [FQDN_NO_CLIENT_UPDATE].len &&
3189 	    results [FQDN_NO_CLIENT_UPDATE].data [0])
3190 		bp -> data [0] |= 2;
3191 	if (results [FQDN_SERVER_UPDATE].len &&
3192 	    results [FQDN_SERVER_UPDATE].data [0])
3193 		bp -> data [0] |= 1;
3194 	if (results [FQDN_RCODE1].len)
3195 		bp -> data [1] = results [FQDN_RCODE1].data [0];
3196 	if (results [FQDN_RCODE2].len)
3197 		bp -> data [2] = results [FQDN_RCODE2].data [0];
3198 
3199 	if (results [FQDN_ENCODED].len &&
3200 	    results [FQDN_ENCODED].data [0]) {
3201 		bp->data[0] |= 4;
3202 		if (results [FQDN_FQDN].len) {
3203 			i = fqdn_encode(&bp->data[3], len - 3,
3204 					results[FQDN_FQDN].data,
3205 					results[FQDN_FQDN].len);
3206 
3207 			if (i < 0) {
3208 				status = 0;
3209 				goto exit;
3210 			}
3211 
3212 			result->len += i;
3213 			result->terminated = 0;
3214 		}
3215 	} else {
3216 		if (results [FQDN_FQDN].len) {
3217 			memcpy (&bp -> data [3], results [FQDN_FQDN].data,
3218 				results [FQDN_FQDN].len);
3219 			result -> len += results [FQDN_FQDN].len;
3220 			result -> terminated = 0;
3221 		}
3222 	}
3223       exit:
3224 	for (i = 1; i <= FQDN_SUBOPTION_COUNT; i++) {
3225 		if (results [i].len)
3226 			data_string_forget (&results [i], MDL);
3227 	}
3228 	buffer_dereference (&bp, MDL);
3229 	if (!status)
3230 		data_string_forget(result, MDL);
3231 	return status;
3232 }
3233 
3234 /*
3235  * Trap invalid attempts to inspect FQND6 contents.
3236  */
3237 struct option_cache *
3238 lookup_fqdn6_option(struct universe *universe, struct option_state *options,
3239 		    unsigned code)
3240 {
3241 	log_fatal("Impossible condition at %s:%d.", MDL);
3242 	return NULL;
3243 }
3244 
3245 /*
3246  * Trap invalid attempts to save options directly to FQDN6 rather than FQDN.
3247  */
3248 void
3249 save_fqdn6_option(struct universe *universe, struct option_state *options,
3250 		  struct option_cache *oc, isc_boolean_t appendp)
3251 {
3252 	log_fatal("Impossible condition at %s:%d.", MDL);
3253 }
3254 
3255 /*
3256  * Trap invalid attempts to delete an option out of the FQDN6 universe.
3257  */
3258 void
3259 delete_fqdn6_option(struct universe *universe, struct option_state *options,
3260 		    int code)
3261 {
3262 	log_fatal("Impossible condition at %s:%d.", MDL);
3263 }
3264 
3265 /* Shill to the DHCPv4 fqdn option cache any attempts to traverse the
3266  * V6's option cache entry.
3267  *
3268  * This function is called speculatively by dhclient to setup
3269  * environment variables.  But it would have already called the
3270  * foreach on the normal fqdn universe, so this is superfluous.
3271  */
3272 void
3273 fqdn6_option_space_foreach(struct packet *packet, struct lease *lease,
3274 			   struct client_state *client_state,
3275 			   struct option_state *in_options,
3276 			   struct option_state *cfg_options,
3277 			   struct binding_scope **scope,
3278 			   struct universe *u, void *stuff,
3279 			   void (*func)(struct option_cache *,
3280 					struct packet *,
3281 					struct lease *,
3282 					struct client_state *,
3283 					struct option_state *,
3284 					struct option_state *,
3285 					struct binding_scope **,
3286 					struct universe *, void *))
3287 {
3288 	/* Pretend it is empty. */
3289 	return;
3290 }
3291 
3292 /* Turn the FQDN option space into a DHCPv6 FQDN option buffer.
3293  */
3294 int
3295 fqdn6_option_space_encapsulate(struct data_string *result,
3296 			       struct packet *packet, struct lease *lease,
3297 			       struct client_state *client_state,
3298 			       struct option_state *in_options,
3299 			       struct option_state *cfg_options,
3300 			       struct binding_scope **scope,
3301 			       struct universe *universe)
3302 {
3303 	pair ocp;
3304 	struct option_chain_head *head;
3305 	struct option_cache *oc;
3306 	unsigned char *data;
3307 	int i, len, rval = 0, count;
3308 	struct data_string results[FQDN_SUBOPTION_COUNT + 1];
3309 
3310 	if (fqdn_universe.index >= cfg_options->universe_count)
3311 		return 0;
3312 	head = ((struct option_chain_head *)
3313 		cfg_options->universes[fqdn_universe.index]);
3314 	if (head == NULL)
3315 		return 0;
3316 
3317 	memset(results, 0, sizeof(results));
3318 	for (ocp = head->first ; ocp != NULL ; ocp = ocp->cdr) {
3319 		oc = (struct option_cache *)(ocp->car);
3320 		if (oc->option->code > FQDN_SUBOPTION_COUNT)
3321 			log_fatal("Impossible condition at %s:%d.", MDL);
3322 		/* No need to check the return code, we check the length later */
3323 		(void) evaluate_option_cache(&results[oc->option->code], packet,
3324 					     lease, client_state, in_options,
3325 					     cfg_options, scope, oc, MDL);
3326 	}
3327 
3328 	/* We add a byte for the flags field at the start of the option.
3329 	 * We add a byte because we will prepend a label count.
3330 	 * We add a byte because the input length doesn't include a trailing
3331 	 * NULL, and we will add a root label.
3332 	 */
3333 	len = results[FQDN_FQDN].len + 3;
3334 	if (!buffer_allocate(&result->buffer, len, MDL)) {
3335 		log_error("No memory for virtual option buffer.");
3336 		goto exit;
3337 	}
3338 	data = result->buffer->data;
3339 	result->data = data;
3340 
3341 	/* The first byte is the flags field. */
3342 	result->len = 1;
3343 	data[0] = 0;
3344 	/* XXX: The server should set bit 3 (yes, 3, not 4) to 1 if we
3345 	 * are not going to perform any DNS updates.  The problem is
3346 	 * that at this layer of abstraction, we do not know if the caller
3347 	 * is the client or the server.
3348 	 *
3349 	 * See RFC4704 Section 4.1, 'The "N" bit'.
3350 	 *
3351 	 * if (?)
3352 	 *	data[0] |= 4;
3353 	 */
3354 	if (results[FQDN_NO_CLIENT_UPDATE].len &&
3355 	    results[FQDN_NO_CLIENT_UPDATE].data[0])
3356 		data[0] |= 2;
3357 	if (results[FQDN_SERVER_UPDATE].len &&
3358 	    results[FQDN_SERVER_UPDATE].data[0])
3359 		data[0] |= 1;
3360 
3361 	/* If there is no name, we're done. */
3362 	if (results[FQDN_FQDN].len == 0) {
3363 		rval = 1;
3364 		goto exit;
3365 	}
3366 
3367 	/* Convert textual representation to DNS format. */
3368 	count = fqdn_encode(data + 1, len - 1,
3369 			    results[FQDN_FQDN].data, results[FQDN_FQDN].len);
3370 
3371 	if (count < 0) {
3372 		rval = 0;
3373 		data_string_forget(result, MDL);
3374 		goto exit;
3375 	}
3376 
3377 	result->len += count;
3378 	result->terminated = 0;
3379 
3380 	/* Success! */
3381 	rval = 1;
3382 
3383       exit:
3384 	for (i = 1 ; i <= FQDN_SUBOPTION_COUNT ; i++) {
3385 		if (result[i].len)
3386 			data_string_forget(&results[i], MDL);
3387 	}
3388 
3389 	return rval;
3390 }
3391 
3392 /* Read the DHCPv6 FQDN option's contents into the FQDN virtual space.
3393  */
3394 int
3395 fqdn6_universe_decode(struct option_state *options,
3396 		      const unsigned char *buffer, unsigned length,
3397 		      struct universe *u)
3398 {
3399 	struct buffer *bp = NULL;
3400 	unsigned char *first_dot;
3401 	int len, hlen, dlen;
3402 
3403 	/* The FQDN option has to be at least 1 byte long. */
3404 	if (length < 1)
3405 		return 0;
3406 
3407 	/* Save the contents of the option in a buffer.  There are 3
3408 	 * one-byte values we record from the packet, so we go ahead
3409 	 * and allocate a bigger buffer to accommodate them.  But the
3410 	 * 'length' we got (because it is a DNS encoded string) is
3411 	 * one longer than we need...so we only add two extra octets.
3412 	 */
3413 	if (!buffer_allocate(&bp, length + 2, MDL)) {
3414 		log_error("No memory for dhcp6.fqdn option buffer.");
3415 		return 0;
3416 	}
3417 
3418 	/* The v6 FQDN is always 'encoded' per DNS. */
3419 	bp->data[0] = 1;
3420 	if (!save_option_buffer(&fqdn_universe, options, bp,
3421 				bp->data, 1, FQDN_ENCODED, 0))
3422 		goto error;
3423 
3424 	/* XXX: We need to process 'The "N" bit'. */
3425 
3426 	if (buffer[0] & 1) /* server-update. */
3427 		bp->data[2] = 1;
3428 	else
3429 		bp->data[2] = 0;
3430 
3431 	if (!save_option_buffer(&fqdn_universe, options, bp, bp->data + 2, 1,
3432 				FQDN_SERVER_UPDATE, 0))
3433 		goto error;
3434 
3435 	if (buffer[0] & 2) /* no-client-update. */
3436 		bp->data[1] = 1;
3437 	else
3438 		bp->data[1] = 0;
3439 
3440 	if (!save_option_buffer(&fqdn_universe, options, bp, bp->data + 1, 1,
3441 				FQDN_NO_CLIENT_UPDATE, 0))
3442 		goto error;
3443 
3444 	/* Convert the domain name to textual representation for config. */
3445 	len = MRns_name_ntop(buffer + 1, (char *)bp->data + 3, length - 1);
3446 	if (len == -1) {
3447 		log_error("Unable to convert dhcp6.fqdn domain name to "
3448 			  "printable form.");
3449 		goto error;
3450 	}
3451 
3452 	/* Save the domain name. */
3453 	if (len > 0) {
3454 		unsigned char *fqdn_start = bp->data + 3;
3455 
3456 		if (!save_option_buffer(&fqdn_universe, options, bp,
3457 					fqdn_start, len, FQDN_FQDN, 1))
3458 			goto error;
3459 
3460 		first_dot = (unsigned char *)strchr((char *)fqdn_start, '.');
3461 
3462 		if (first_dot != NULL) {
3463 			hlen = first_dot - fqdn_start;
3464 			dlen = len - hlen;
3465 		} else {
3466 			hlen = len;
3467 			dlen = 0;
3468 		}
3469 
3470 		if (!save_option_buffer(&fqdn_universe, options, bp,
3471 					fqdn_start, len, FQDN_FQDN, 1) ||
3472 		    ((hlen > 0) &&
3473 		     !save_option_buffer(&fqdn_universe, options, bp,
3474 					 fqdn_start, hlen,
3475 					 FQDN_HOSTNAME, 0)) ||
3476 		    ((dlen > 0) &&
3477 		     !save_option_buffer(&fqdn_universe, options, bp,
3478 					 first_dot, dlen, FQDN_DOMAINNAME, 0)))
3479 				goto error;
3480 	}
3481 
3482 	buffer_dereference(&bp, MDL);
3483 	return 1;
3484 
3485       error:
3486 	buffer_dereference(&bp, MDL);
3487 	return 0;
3488 }
3489 
3490 void option_space_foreach (struct packet *packet, struct lease *lease,
3491 			   struct client_state *client_state,
3492 			   struct option_state *in_options,
3493 			   struct option_state *cfg_options,
3494 			   struct binding_scope **scope,
3495 			   struct universe *u, void *stuff,
3496 			   void (*func) (struct option_cache *,
3497 					 struct packet *,
3498 					 struct lease *, struct client_state *,
3499 					 struct option_state *,
3500 					 struct option_state *,
3501 					 struct binding_scope **,
3502 					 struct universe *, void *))
3503 {
3504 	if (u -> foreach)
3505 		(*u -> foreach) (packet, lease, client_state, in_options,
3506 				 cfg_options, scope, u, stuff, func);
3507 }
3508 
3509 void suboption_foreach (struct packet *packet, struct lease *lease,
3510 			struct client_state *client_state,
3511 			struct option_state *in_options,
3512 			struct option_state *cfg_options,
3513 			struct binding_scope **scope,
3514 			struct universe *u, void *stuff,
3515 			void (*func) (struct option_cache *,
3516 				      struct packet *,
3517 				      struct lease *, struct client_state *,
3518 				      struct option_state *,
3519 				      struct option_state *,
3520 				      struct binding_scope **,
3521 				      struct universe *, void *),
3522 			struct option_cache *oc,
3523 			const char *vsname)
3524 {
3525 	struct universe *universe = find_option_universe (oc -> option,
3526 							  vsname);
3527 	if (universe -> foreach)
3528 		(*universe -> foreach) (packet, lease, client_state,
3529 					in_options, cfg_options,
3530 					scope, universe, stuff, func);
3531 }
3532 
3533 void hashed_option_space_foreach (struct packet *packet, struct lease *lease,
3534 				  struct client_state *client_state,
3535 				  struct option_state *in_options,
3536 				  struct option_state *cfg_options,
3537 				  struct binding_scope **scope,
3538 				  struct universe *u, void *stuff,
3539 				  void (*func) (struct option_cache *,
3540 						struct packet *,
3541 						struct lease *,
3542 						struct client_state *,
3543 						struct option_state *,
3544 						struct option_state *,
3545 						struct binding_scope **,
3546 						struct universe *, void *))
3547 {
3548 	pair *hash;
3549 	int i;
3550 	struct option_cache *oc;
3551 
3552 	if (cfg_options -> universe_count <= u -> index)
3553 		return;
3554 
3555 	hash = cfg_options -> universes [u -> index];
3556 	if (!hash)
3557 		return;
3558 	for (i = 0; i < OPTION_HASH_SIZE; i++) {
3559 		pair p;
3560 		/* XXX save _all_ options! XXX */
3561 		for (p = hash [i]; p; p = p -> cdr) {
3562 			oc = (struct option_cache *)p -> car;
3563 			(*func) (oc, packet, lease, client_state,
3564 				 in_options, cfg_options, scope, u, stuff);
3565 		}
3566 	}
3567 }
3568 
3569 void
3570 save_linked_option(struct universe *universe, struct option_state *options,
3571 		   struct option_cache *oc, isc_boolean_t appendp)
3572 {
3573 	pair *tail;
3574 	struct option_chain_head *head;
3575 	struct option_cache **ocloc;
3576 
3577 	if (universe -> index >= options -> universe_count)
3578 		return;
3579 	head = ((struct option_chain_head *)
3580 		options -> universes [universe -> index]);
3581 	if (!head) {
3582 		if (!option_chain_head_allocate (((struct option_chain_head **)
3583 						  &options -> universes
3584 						  [universe -> index]), MDL))
3585 			return;
3586 		head = ((struct option_chain_head *)
3587 			options -> universes [universe -> index]);
3588 	}
3589 
3590 	/* Find the tail of the list. */
3591 	for (tail = &head -> first; *tail; tail = &((*tail) -> cdr)) {
3592 		ocloc = (struct option_cache **)&(*tail)->car;
3593 
3594 		if (oc->option->code == (*ocloc)->option->code) {
3595 			if (appendp) {
3596 				do {
3597 					ocloc = &(*ocloc)->next;
3598 				} while (*ocloc != NULL);
3599 			} else {
3600 				option_cache_dereference(ocloc, MDL);
3601 			}
3602 			option_cache_reference(ocloc, oc, MDL);
3603 			return;
3604 		}
3605 	}
3606 
3607 	*tail = cons (0, 0);
3608 	if (*tail) {
3609 		option_cache_reference ((struct option_cache **)
3610 					(&(*tail) -> car), oc, MDL);
3611 	}
3612 }
3613 
3614 int linked_option_space_encapsulate (result, packet, lease, client_state,
3615 				    in_options, cfg_options, scope, universe)
3616 	struct data_string *result;
3617 	struct packet *packet;
3618 	struct lease *lease;
3619 	struct client_state *client_state;
3620 	struct option_state *in_options;
3621 	struct option_state *cfg_options;
3622 	struct binding_scope **scope;
3623 	struct universe *universe;
3624 {
3625 	int status = 0;
3626 	pair oc;
3627 	struct option_chain_head *head;
3628 
3629 	if (universe -> index >= cfg_options -> universe_count)
3630 		return status;
3631 	head = ((struct option_chain_head *)
3632 		cfg_options -> universes [universe -> index]);
3633 	if (!head)
3634 		return status;
3635 
3636 	for (oc = head -> first; oc; oc = oc -> cdr) {
3637 		if (store_option (result, universe, packet,
3638 				  lease, client_state, in_options, cfg_options,
3639 				  scope, (struct option_cache *)(oc -> car)))
3640 			status = 1;
3641 	}
3642 
3643 	if (search_subencapsulation(result, packet, lease, client_state,
3644 				    in_options, cfg_options, scope, universe))
3645 		status = 1;
3646 
3647 	return status;
3648 }
3649 
3650 void delete_linked_option (universe, options, code)
3651 	struct universe *universe;
3652 	struct option_state *options;
3653 	int code;
3654 {
3655 	pair *tail, tmp = (pair)0;
3656 	struct option_chain_head *head;
3657 
3658 	if (universe -> index >= options -> universe_count)
3659 		return;
3660 	head = ((struct option_chain_head *)
3661 		options -> universes [universe -> index]);
3662 	if (!head)
3663 		return;
3664 
3665 	for (tail = &head -> first; *tail; tail = &((*tail) -> cdr)) {
3666 		if (code ==
3667 		    ((struct option_cache *)(*tail) -> car) -> option -> code)
3668 		{
3669 			tmp = (*tail) -> cdr;
3670 			option_cache_dereference ((struct option_cache **)
3671 						  (&(*tail) -> car), MDL);
3672 			dfree (*tail, MDL);
3673 			(*tail) = tmp;
3674 			break;
3675 		}
3676 	}
3677 }
3678 
3679 struct option_cache *lookup_linked_option (universe, options, code)
3680 	struct universe *universe;
3681 	struct option_state *options;
3682 	unsigned code;
3683 {
3684 	pair oc;
3685 	struct option_chain_head *head;
3686 
3687 	if (universe -> index >= options -> universe_count)
3688 		return 0;
3689 	head = ((struct option_chain_head *)
3690 		options -> universes [universe -> index]);
3691 	if (!head)
3692 		return 0;
3693 
3694 	for (oc = head -> first; oc; oc = oc -> cdr) {
3695 		if (code ==
3696 		    ((struct option_cache *)(oc -> car)) -> option -> code) {
3697 			return (struct option_cache *)(oc -> car);
3698 		}
3699 	}
3700 
3701 	return (struct option_cache *)0;
3702 }
3703 
3704 int linked_option_state_dereference (universe, state, file, line)
3705 	struct universe *universe;
3706 	struct option_state *state;
3707 	const char *file;
3708 	int line;
3709 {
3710 	return (option_chain_head_dereference
3711 		((struct option_chain_head **)
3712 		 (&state -> universes [universe -> index]), MDL));
3713 }
3714 
3715 void linked_option_space_foreach (struct packet *packet, struct lease *lease,
3716 				  struct client_state *client_state,
3717 				  struct option_state *in_options,
3718 				  struct option_state *cfg_options,
3719 				  struct binding_scope **scope,
3720 				  struct universe *u, void *stuff,
3721 				  void (*func) (struct option_cache *,
3722 						struct packet *,
3723 						struct lease *,
3724 						struct client_state *,
3725 						struct option_state *,
3726 						struct option_state *,
3727 						struct binding_scope **,
3728 						struct universe *, void *))
3729 {
3730 	pair car;
3731 	struct option_chain_head *head;
3732 
3733 	if (u -> index >= cfg_options -> universe_count)
3734 		return;
3735 	head = ((struct option_chain_head *)
3736 		cfg_options -> universes [u -> index]);
3737 	if (!head)
3738 		return;
3739 	for (car = head -> first; car; car = car -> cdr) {
3740 		(*func) ((struct option_cache *)(car -> car),
3741 			 packet, lease, client_state,
3742 			 in_options, cfg_options, scope, u, stuff);
3743 	}
3744 }
3745 
3746 void do_packet (interface, packet, len, from_port, from, hfrom)
3747 	struct interface_info *interface;
3748 	struct dhcp_packet *packet;
3749 	unsigned len;
3750 	unsigned int from_port;
3751 	struct iaddr from;
3752 	struct hardware *hfrom;
3753 {
3754 	struct option_cache *op;
3755 	struct packet *decoded_packet;
3756 #if defined (DEBUG_MEMORY_LEAKAGE)
3757 	unsigned long previous_outstanding = dmalloc_outstanding;
3758 #endif
3759 
3760 #if defined (TRACING)
3761 	trace_inpacket_stash(interface, packet, len, from_port, from, hfrom);
3762 #endif
3763 
3764 	decoded_packet = NULL;
3765 	if (!packet_allocate(&decoded_packet, MDL)) {
3766 		log_error("do_packet: no memory for incoming packet!");
3767 		return;
3768 	}
3769 	decoded_packet->raw = packet;
3770 	decoded_packet->packet_length = len;
3771 	decoded_packet->client_port = from_port;
3772 	decoded_packet->client_addr = from;
3773 	interface_reference(&decoded_packet->interface, interface, MDL);
3774 	decoded_packet->haddr = hfrom;
3775 
3776 	if (packet->hlen > sizeof packet->chaddr) {
3777 		packet_dereference(&decoded_packet, MDL);
3778 		log_info("Discarding packet with bogus hlen.");
3779 		return;
3780 	}
3781 
3782 	/* If there's an option buffer, try to parse it. */
3783 	if (decoded_packet->packet_length >= DHCP_FIXED_NON_UDP + 4) {
3784 		if (!parse_options(decoded_packet)) {
3785 			if (decoded_packet->options)
3786 				option_state_dereference
3787 					(&decoded_packet->options, MDL);
3788 			packet_dereference (&decoded_packet, MDL);
3789 			return;
3790 		}
3791 
3792 		if (decoded_packet->options_valid &&
3793 		    (op = lookup_option(&dhcp_universe,
3794 					decoded_packet->options,
3795 					DHO_DHCP_MESSAGE_TYPE))) {
3796 			struct data_string dp;
3797 			memset(&dp, 0, sizeof dp);
3798 			evaluate_option_cache(&dp, decoded_packet, NULL, NULL,
3799 					      decoded_packet->options, NULL,
3800 					      NULL, op, MDL);
3801 			if (dp.len > 0)
3802 				decoded_packet->packet_type = dp.data[0];
3803 			else
3804 				decoded_packet->packet_type = 0;
3805 			data_string_forget(&dp, MDL);
3806 		}
3807 	}
3808 
3809 	if (validate_packet(decoded_packet) != 0) {
3810 		if (decoded_packet->packet_type)
3811 			dhcp(decoded_packet);
3812 		else
3813 			bootp(decoded_packet);
3814 	}
3815 
3816 	/* If the caller kept the packet, they'll have upped the refcnt. */
3817 	packet_dereference(&decoded_packet, MDL);
3818 
3819 #if defined (DEBUG_MEMORY_LEAKAGE)
3820 	log_info("generation %ld: %ld new, %ld outstanding, %ld long-term",
3821 		 dmalloc_generation,
3822 		 dmalloc_outstanding - previous_outstanding,
3823 		 dmalloc_outstanding, dmalloc_longterm);
3824 	dmalloc_dump_outstanding();
3825 #endif
3826 #if defined (DEBUG_RC_HISTORY_EXHAUSTIVELY)
3827 	dump_rc_history(0);
3828 #endif
3829 }
3830 
3831 int
3832 packet6_len_okay(const char *packet, int len) {
3833 	if (len < 1) {
3834 		return 0;
3835 	}
3836 	if ((packet[0] == DHCPV6_RELAY_FORW) ||
3837 	    (packet[0] == DHCPV6_RELAY_REPL)) {
3838 		if (len >= offsetof(struct dhcpv6_relay_packet, options)) {
3839 			return 1;
3840 		} else {
3841 			return 0;
3842 		}
3843 	} else {
3844 		if (len >= offsetof(struct dhcpv6_packet, options)) {
3845 			return 1;
3846 		} else {
3847 			return 0;
3848 		}
3849 	}
3850 }
3851 
3852 #ifdef DHCPv6
3853 void
3854 do_packet6(struct interface_info *interface, const char *packet,
3855 	   int len, int from_port, const struct iaddr *from,
3856 	   isc_boolean_t was_unicast) {
3857 	unsigned char msg_type;
3858 	const struct dhcpv6_packet *msg;
3859 	const struct dhcpv6_relay_packet *relay;
3860 	struct packet *decoded_packet;
3861 #if defined (DEBUG_MEMORY_LEAKAGE)
3862 	unsigned long previous_outstanding = dmalloc_outstanding;
3863 #endif
3864 
3865 	if (!packet6_len_okay(packet, len)) {
3866 		log_info("do_packet6: "
3867 			 "short packet from %s port %d, len %d, dropped",
3868 			 piaddr(*from), from_port, len);
3869 		return;
3870 	}
3871 
3872 	decoded_packet = NULL;
3873 	if (!packet_allocate(&decoded_packet, MDL)) {
3874 		log_error("do_packet6: no memory for incoming packet.");
3875 		return;
3876 	}
3877 
3878 	if (!option_state_allocate(&decoded_packet->options, MDL)) {
3879 		log_error("do_packet6: no memory for options.");
3880 		packet_dereference(&decoded_packet, MDL);
3881 		return;
3882 	}
3883 
3884 	/* IPv4 information, already set to 0 */
3885 	/* decoded_packet->packet_type = 0; */
3886 	/* memset(&decoded_packet->haddr, 0, sizeof(decoded_packet->haddr)); */
3887 	/* decoded_packet->circuit_id = NULL; */
3888 	/* decoded_packet->circuit_id_len = 0; */
3889 	/* decoded_packet->remote_id = NULL; */
3890 	/* decoded_packet->remote_id_len = 0; */
3891 	decoded_packet->raw = (struct dhcp_packet *)packet;
3892 	decoded_packet->packet_length = (unsigned)len;
3893 	decoded_packet->client_port = from_port;
3894 	decoded_packet->client_addr = *from;
3895 	interface_reference(&decoded_packet->interface, interface, MDL);
3896 
3897 	decoded_packet->unicast = was_unicast;
3898 
3899 	msg_type = packet[0];
3900 	if ((msg_type == DHCPV6_RELAY_FORW) ||
3901 	    (msg_type == DHCPV6_RELAY_REPL)) {
3902 		int relaylen = (int)(offsetof(struct dhcpv6_relay_packet, options));
3903 		relay = (const struct dhcpv6_relay_packet *)packet;
3904 		decoded_packet->dhcpv6_msg_type = relay->msg_type;
3905 
3906 		/* relay-specific data */
3907 		decoded_packet->dhcpv6_hop_count = relay->hop_count;
3908 		memcpy(&decoded_packet->dhcpv6_link_address,
3909 		       relay->link_address, sizeof(relay->link_address));
3910 		memcpy(&decoded_packet->dhcpv6_peer_address,
3911 		       relay->peer_address, sizeof(relay->peer_address));
3912 
3913 		if (!parse_option_buffer(decoded_packet->options,
3914 					 relay->options, len - relaylen,
3915 					 &dhcpv6_universe)) {
3916 			/* no logging here, as parse_option_buffer() logs all
3917 			   cases where it fails */
3918 			packet_dereference(&decoded_packet, MDL);
3919 			return;
3920 		}
3921 	} else {
3922 		int msglen = (int)(offsetof(struct dhcpv6_packet, options));
3923 		msg = (const struct dhcpv6_packet *)packet;
3924 		decoded_packet->dhcpv6_msg_type = msg->msg_type;
3925 
3926 		/* message-specific data */
3927 		memcpy(decoded_packet->dhcpv6_transaction_id,
3928 		       msg->transaction_id,
3929 		       sizeof(decoded_packet->dhcpv6_transaction_id));
3930 
3931 		if (!parse_option_buffer(decoded_packet->options,
3932 					 msg->options, len - msglen,
3933 					 &dhcpv6_universe)) {
3934 			/* no logging here, as parse_option_buffer() logs all
3935 			   cases where it fails */
3936 			packet_dereference(&decoded_packet, MDL);
3937 			return;
3938 		}
3939 	}
3940 
3941 	dhcpv6(decoded_packet);
3942 
3943 	packet_dereference(&decoded_packet, MDL);
3944 
3945 #if defined (DEBUG_MEMORY_LEAKAGE)
3946 	log_info("generation %ld: %ld new, %ld outstanding, %ld long-term",
3947 		 dmalloc_generation,
3948 		 dmalloc_outstanding - previous_outstanding,
3949 		 dmalloc_outstanding, dmalloc_longterm);
3950 	dmalloc_dump_outstanding();
3951 #endif
3952 #if defined (DEBUG_RC_HISTORY_EXHAUSTIVELY)
3953 	dump_rc_history(0);
3954 #endif
3955 }
3956 #endif /* DHCPv6 */
3957 
3958 int
3959 pretty_escape(char **dst, char *dend, const unsigned char **src,
3960 	      const unsigned char *send)
3961 {
3962 	int count = 0;
3963 
3964 	/* If there aren't as many bytes left as there are in the source
3965 	 * buffer, don't even bother entering the loop.
3966 	 */
3967 	if (dst == NULL || dend == NULL || src == NULL || send == NULL ||
3968 	    *dst == NULL || *src == NULL || (*dst >= dend) || (*src > send) ||
3969 	    ((send - *src) > (dend - *dst)))
3970 		return -1;
3971 
3972 	for ( ; *src < send ; (*src)++) {
3973 		if (!isascii (**src) || !isprint (**src)) {
3974 			/* Skip trailing NUL. */
3975 			if ((*src + 1) != send || **src != '\0') {
3976 				if (*dst + 4 > dend)
3977 					return -1;
3978 
3979 				sprintf(*dst, "\\%03o",
3980 					**src);
3981 				(*dst) += 4;
3982 				count += 4;
3983 			}
3984 		} else if (**src == '"' || **src == '\'' || **src == '$' ||
3985 			   **src == '`' || **src == '\\' || **src == '|' ||
3986 			   **src == '&') {
3987 			if (*dst + 2 > dend)
3988 				return -1;
3989 
3990 			**dst = '\\';
3991 			(*dst)++;
3992 			**dst = **src;
3993 			(*dst)++;
3994 			count += 2;
3995 		} else {
3996 			if (*dst + 1 > dend)
3997 				return -1;
3998 
3999 			**dst = **src;
4000 			(*dst)++;
4001 			count++;
4002 		}
4003 	}
4004 
4005 	return count;
4006 }
4007 
4008 static int
4009 pretty_text(char **dst, char *dend, const unsigned char **src,
4010 	    const unsigned char *send, int emit_quotes)
4011 {
4012 	int count;
4013 
4014 	if (dst == NULL || dend == NULL || src == NULL || send == NULL ||
4015 	    *dst == NULL || *src == NULL ||
4016 	    ((*dst + (emit_quotes ? 2 : 0)) > dend) || (*src > send))
4017 		return -1;
4018 
4019 	if (emit_quotes) {
4020 		**dst = '"';
4021 		(*dst)++;
4022 	}
4023 
4024 	/* dend-1 leaves 1 byte for the closing quote. */
4025 	count = pretty_escape(dst, dend - (emit_quotes ? 1 : 0), src, send);
4026 
4027 	if (count == -1)
4028 		return -1;
4029 
4030 	if (emit_quotes && (*dst < dend)) {
4031 		**dst = '"';
4032 		(*dst)++;
4033 
4034 		/* Includes quote prior to pretty_escape(); */
4035 		count += 2;
4036 	}
4037 
4038 	return count;
4039 }
4040 
4041 static int
4042 pretty_domain(char **dst, char *dend, const unsigned char **src,
4043 	      const unsigned char *send)
4044 {
4045 	const unsigned char *tend;
4046 	int count = 2;
4047 	int tsiz, status;
4048 
4049 	if (dst == NULL || dend == NULL || src == NULL || send == NULL ||
4050 	    *dst == NULL || *src == NULL ||
4051 	    ((*dst + 2) > dend) || (*src >= send))
4052 		return -1;
4053 
4054 	**dst = '"';
4055 	(*dst)++;
4056 
4057 	do {
4058 		/* Continue loop until end of src buffer. */
4059 		if (*src >= send)
4060 			break;
4061 
4062 		/* Consume tag size. */
4063 		tsiz = **src;
4064 		(*src)++;
4065 
4066 		/* At root, finis. */
4067 		if (tsiz == 0)
4068 			break;
4069 
4070 		tend = (*src) + tsiz;
4071 
4072 		/* If the tag exceeds the source buffer, it's illegal.
4073 		 * This should also trap compression pointers (which should
4074 		 * not be in these buffers).
4075 		 */
4076 		if (tend > send)
4077 			return -1;
4078 
4079 		/* dend-2 leaves room for a trailing dot and quote. */
4080 		status = pretty_escape(dst, dend-2, src, tend);
4081 
4082 		if ((status == -1) || ((*dst + 2) > dend))
4083 			return -1;
4084 
4085 		**dst = '.';
4086 		(*dst)++;
4087 		count += status + 1;
4088 	}
4089 	while(1);
4090 
4091 	**dst = '"';
4092 	(*dst)++;
4093 
4094 	return count;
4095 }
4096 
4097 /*
4098  * Add the option identified with the option number and data to the
4099  * options state.
4100  */
4101 int
4102 add_option(struct option_state *options,
4103 	   unsigned int option_num,
4104 	   void *data,
4105 	   unsigned int data_len)
4106 {
4107 	struct option_cache *oc;
4108 	struct option *option;
4109 
4110 	/* INSIST(options != NULL); */
4111 	/* INSIST(data != NULL); */
4112 
4113 	option = NULL;
4114 	if (!option_code_hash_lookup(&option, dhcp_universe.code_hash,
4115 				     &option_num, 0, MDL)) {
4116 		log_error("Attempting to add unknown option %d.", option_num);
4117 		return 0;
4118 	}
4119 
4120 	oc = NULL;
4121 	if (!option_cache_allocate(&oc, MDL)) {
4122 		log_error("No memory for option cache adding %s (option %d).",
4123 			  option->name, option_num);
4124 		return 0;
4125 	}
4126 
4127 	if (!make_const_data(&oc->expression,
4128 			     data,
4129 			     data_len,
4130 			     0,
4131 			     0,
4132 			     MDL)) {
4133 		log_error("No memory for constant data adding %s (option %d).",
4134 			  option->name, option_num);
4135 		option_cache_dereference(&oc, MDL);
4136 		return 0;
4137 	}
4138 
4139 	option_reference(&(oc->option), option, MDL);
4140 	save_option(&dhcp_universe, options, oc);
4141 	option_cache_dereference(&oc, MDL);
4142 
4143 	return 1;
4144 }
4145 
4146 /**
4147  *  Checks if received BOOTP/DHCPv4 packet is sane
4148  *
4149  * @param packet received, decoded packet
4150  *
4151  * @return 1 if packet is sane, 0 if it is not
4152  */
4153 int validate_packet(struct packet *packet)
4154 {
4155 	struct option_cache *oc = NULL;
4156 
4157 	oc = lookup_option (&dhcp_universe, packet->options,
4158 			    DHO_DHCP_CLIENT_IDENTIFIER);
4159 	if (oc) {
4160 		/* Let's check if client-identifier is sane */
4161 		if (oc->data.len == 0) {
4162 			log_debug("Dropped DHCPv4 packet with zero-length client-id");
4163 			return (0);
4164 
4165 		} else if (oc->data.len == 1) {
4166 			/*
4167 			 * RFC2132, section 9.14 states that minimum length of client-id
4168 			 * is 2.  We will allow single-character client-ids for now (for
4169 			 * backwards compatibility), but warn the user that support for
4170 			 * this is against the standard.
4171 			 */
4172 			log_debug("Accepted DHCPv4 packet with one-character client-id - "
4173 				"a future version of ISC DHCP will reject this");
4174 		}
4175 	} else {
4176 		/*
4177 		 * If hlen is 0 we don't have any identifier, we warn the user
4178 		 * but continue processing the packet as we can.
4179 		 */
4180 		if (packet->raw->hlen == 0) {
4181 			log_debug("Received DHCPv4 packet without client-id"
4182 				  " option and empty hlen field.");
4183 		}
4184 	}
4185 
4186 	/* @todo: Add checks for other received options */
4187 
4188 	return (1);
4189 }
4190