diff options
-rw-r--r-- | usr.sbin/dhcpd/confpars.c | 95 | ||||
-rw-r--r-- | usr.sbin/dhcpd/dhcp-options.5 | 23 | ||||
-rw-r--r-- | usr.sbin/dhcpd/dhcp.h | 3 | ||||
-rw-r--r-- | usr.sbin/dhcpd/dhcpd.h | 3 | ||||
-rw-r--r-- | usr.sbin/dhcpd/tables.c | 9 |
5 files changed, 107 insertions, 26 deletions
diff --git a/usr.sbin/dhcpd/confpars.c b/usr.sbin/dhcpd/confpars.c index 1dd4a55d2a2..4c1d986d174 100644 --- a/usr.sbin/dhcpd/confpars.c +++ b/usr.sbin/dhcpd/confpars.c @@ -1,4 +1,4 @@ -/* $OpenBSD: confpars.c,v 1.33 2017/04/24 14:58:36 krw Exp $ */ +/* $OpenBSD: confpars.c,v 1.34 2019/05/08 22:00:55 krw Exp $ */ /* * Copyright (c) 1995, 1996, 1997 The Internet Software Consortium. @@ -43,7 +43,9 @@ #include <net/if.h> +#include <limits.h> #include <netdb.h> +#include <resolv.h> #include <stdio.h> #include <stdlib.h> #include <string.h> @@ -1207,6 +1209,12 @@ parse_option_param(FILE *cfile, struct group *group) tree = tree_concat(tree, tree_const( buf, (cprefix + 7) / 8)); break; + case 'D': + t = parse_domain_and_comp(cfile); + if (!t) + return; + tree = tree_concat(tree, t); + break; default: log_warnx("Bad format %c in " "parse_option_param.", *fmt); @@ -1468,3 +1476,88 @@ parse_address_range(FILE *cfile, struct subnet *subnet) /* Create the new address range. */ new_address_range(low, high, subnet, dynamic); } + +static void +push_domain_list(char ***domains, size_t *count, char *domain) +{ + *domains = reallocarray(*domains, *count + 1, sizeof **domains); + if (!*domains) + fatalx("Can't allocate domain list"); + + (*domains)[*count] = domain; + ++*count; +} + +static void +free_domain_list(char **domains, size_t count) +{ + for (size_t i = 0; i < count; i++) + free(domains[i]); + free(domains); +} + +struct tree * +parse_domain_and_comp(FILE *cfile) +{ + struct tree *rv = NULL; + char **domains = NULL; + char *val, *domain; + unsigned char *buf = NULL; + unsigned char **bufptrs = NULL; + size_t bufsiz = 0, bufn = 0, count = 0; + int token = ';'; + + do { + if (token == ',') + token = next_token(&val, cfile); + + token = next_token(&val, cfile); + if (token != TOK_STRING) { + parse_warn("string expected"); + goto error; + } + domain = strdup(val); + if (domain == NULL) + fatalx("Can't allocate domain to compress"); + push_domain_list(&domains, &count, domain); + + /* + * openbsd.org normally compresses to [7]openbsd[3]org[0]. + * +2 to string length provides space for leading and + * trailing (root) prefix lengths not already accounted for + * by dots, and also provides sufficient space for pointer + * compression. + */ + bufsiz = bufsiz + 2 + strlen(domain); + token = peek_token(NULL, cfile); + } while (token == ','); + + buf = malloc(bufsiz); + if (!buf) + fatalx("Can't allocate compressed domain buffer"); + bufptrs = calloc(count + 1, sizeof *bufptrs); + if (!bufptrs) + fatalx("Can't allocate compressed pointer list"); + bufptrs[0] = buf; + + /* dn_comp takes an int for the output buffer size */ + if (!(bufsiz <= INT_MAX)) + fatalx("Size of compressed domain buffer too large"); + for (size_t i = 0; i < count; i++) { + int n; + + /* see bufsiz <= INT_MAX assertion, above */ + n = dn_comp(domains[i], &buf[bufn], bufsiz - bufn, bufptrs, + &bufptrs[count + 1]); + if (n == -1) + fatalx("Can't compress domain"); + bufn += (size_t)n; + } + + rv = tree_const(buf, bufn); +error: + free_domain_list(domains, count); + free(buf); + free(bufptrs); + return rv; +} diff --git a/usr.sbin/dhcpd/dhcp-options.5 b/usr.sbin/dhcpd/dhcp-options.5 index eea4c015481..c496a061904 100644 --- a/usr.sbin/dhcpd/dhcp-options.5 +++ b/usr.sbin/dhcpd/dhcp-options.5 @@ -1,4 +1,4 @@ -.\" $OpenBSD: dhcp-options.5,v 1.30 2019/04/02 03:21:21 krw Exp $ +.\" $OpenBSD: dhcp-options.5,v 1.31 2019/05/08 22:00:55 krw Exp $ .\" .\" Copyright (c) 1995, 1996, 1997, 1998 The Internet Software Consortium. .\" All rights reserved. @@ -36,7 +36,7 @@ .\" see ``http://www.isc.org/isc''. To learn more about Vixie .\" Enterprises, see ``http://www.vix.com''. .\" -.Dd $Mdocdate: April 2 2019 $ +.Dd $Mdocdate: May 8 2019 $ .Dt DHCP-OPTIONS 5 .Os .Sh NAME @@ -78,13 +78,6 @@ data type specifies a network in CIDR notion. e.g. 1.2.3/24. .Pp The -.Ar rfc1035 -data type specifies a list of domain names compressed -as described in Section 4.1.4 of RFC 1035. -The compressed list takes the form of a series of -octets specified in hexadecimal, separated by colons. -.Pp -The .Ar int32 data type specifies a signed 32-bit integer. The @@ -292,7 +285,7 @@ The option specifies a list of Domain Name System name servers available to the client. Servers should be listed in order of preference. -.It Ic option domain-search Ar rfc1035 ; | Ar string Oo , Ar string ... Oc ; +.It Ic option domain-search Ar string Oo , Ar string ... Oc ; The .Ic domain-search option specifies a list of the domain names that should be @@ -306,16 +299,6 @@ it will use this list of domains in preference to any information provided by the .Ic domain-name option. -.Pp -Note that -.Xr dhcpd 8 -calls this option -.Ic option-119 -instead of -.Ic domain-search -and only supports the -.Ar rfc1035 -variant. .It Ic option extensions-path Ar string ; A string to specify a file, retrievable via TFTP, which contains information which can be interpreted in the same way as the 64-octet vendor-extension diff --git a/usr.sbin/dhcpd/dhcp.h b/usr.sbin/dhcpd/dhcp.h index 9a52393a5fe..639e7a1aa69 100644 --- a/usr.sbin/dhcpd/dhcp.h +++ b/usr.sbin/dhcpd/dhcp.h @@ -1,4 +1,4 @@ -/* $OpenBSD: dhcp.h,v 1.10 2014/01/21 03:07:51 krw Exp $ */ +/* $OpenBSD: dhcp.h,v 1.11 2019/05/08 22:00:55 krw Exp $ */ /* Protocol structures... */ @@ -171,6 +171,7 @@ struct dhcp_packet { #define DHO_NDS_SERVERS 85 #define DHO_NDS_TREE_NAME 86 #define DHO_NDS_CONTEXT 87 +#define DHO_DOMAIN_SEARCH 119 #define DHO_CLASSLESS_STATIC_ROUTES 121 #define DHO_TFTP_CONFIG_FILE 144 #define DHO_VOIP_CONFIGURATION_SERVER 150 diff --git a/usr.sbin/dhcpd/dhcpd.h b/usr.sbin/dhcpd/dhcpd.h index 1d0fca699fe..7b0df421222 100644 --- a/usr.sbin/dhcpd/dhcpd.h +++ b/usr.sbin/dhcpd/dhcpd.h @@ -1,4 +1,4 @@ -/* $OpenBSD: dhcpd.h,v 1.66 2017/08/04 02:01:46 rob Exp $ */ +/* $OpenBSD: dhcpd.h,v 1.67 2019/05/08 22:00:55 krw Exp $ */ /* * Copyright (c) 1995, 1996, 1997, 1998, 1999 @@ -371,6 +371,7 @@ time_t parse_date(FILE *); unsigned char *parse_numeric_aggregate(FILE *, unsigned char *, int *, int, int, int); void convert_num(unsigned char *, char *, int, int); +struct tree *parse_domain_and_comp(FILE *); /* tree.c */ pair cons(caddr_t, pair); diff --git a/usr.sbin/dhcpd/tables.c b/usr.sbin/dhcpd/tables.c index 48763251eb7..6735a332a75 100644 --- a/usr.sbin/dhcpd/tables.c +++ b/usr.sbin/dhcpd/tables.c @@ -1,4 +1,4 @@ -/* $OpenBSD: tables.c,v 1.13 2017/02/13 19:13:14 krw Exp $ */ +/* $OpenBSD: tables.c,v 1.14 2019/05/08 22:00:55 krw Exp $ */ /* Tables of information... */ @@ -70,6 +70,8 @@ * t - ASCII text * f - flag (true or false) * A - array of whatever precedes (e.g., IA means array of IP addresses) + * X - hex octets + * D - comma separated list of domain names */ struct universe dhcp_universe; @@ -193,7 +195,7 @@ struct option dhcp_options[256] = { { "option-116", "X", &dhcp_universe, 116 }, { "option-117", "X", &dhcp_universe, 117 }, { "option-118", "X", &dhcp_universe, 118 }, - { "option-119", "X", &dhcp_universe, 119 }, + { "domain-search", "D", &dhcp_universe, 119 }, { "option-120", "X", &dhcp_universe, 120 }, { "classless-static-routes", "CIA", &dhcp_universe, 121 }, { "option-122", "X", &dhcp_universe, 122 }, @@ -367,6 +369,7 @@ unsigned char dhcp_option_default_priority_list[256] = { DHO_BOOT_SIZE, DHO_MERIT_DUMP, DHO_DOMAIN_NAME, + DHO_DOMAIN_SEARCH, DHO_SWAP_SERVER, DHO_ROOT_PATH, DHO_EXTENSIONS_PATH, @@ -412,7 +415,7 @@ unsigned char dhcp_option_default_priority_list[256] = { 80, 81, 83, 84, 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, 96, 97, 98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, - 110, 111, 112, 113, 114, 115, 116, 117, 118, 119, + 110, 111, 112, 113, 114, 115, 116, 117, 118, 120, 122, 123, 124, 125, 126, 127, 128, 129, 130, 131, 132, 133, 134, 135, 136, 137, 138, 139, 140, 141, 142, 143, 144, 145, 146, 147, 148, 149, |