summaryrefslogtreecommitdiff
path: root/sbin/dhclient/privsep.c
diff options
context:
space:
mode:
authorKenneth R Westerback <krw@cvs.openbsd.org>2012-10-30 18:39:45 +0000
committerKenneth R Westerback <krw@cvs.openbsd.org>2012-10-30 18:39:45 +0000
commit1721d77e423e622f2a9d018651a15c36a5f3a17e (patch)
treef6597ed300615a71bdb45bd274857071508779db /sbin/dhclient/privsep.c
parent1a882f5e4d6022913f24a2a3ba0c2f51fcde1e38 (diff)
Nuke dhclient-script and dhclient.conf 'script' directive. Do all
interface and route configuration via ioctl's and routing sockets. This will break configurations using local enhancements of dhclient-script, which will now require alternate arrangements. Committing early to allow time to identify and develop required alternatives. Several proddings by deraadt@.
Diffstat (limited to 'sbin/dhclient/privsep.c')
-rw-r--r--sbin/dhclient/privsep.c362
1 files changed, 267 insertions, 95 deletions
diff --git a/sbin/dhclient/privsep.c b/sbin/dhclient/privsep.c
index 9f755b6ee73..0044fd3f6c5 100644
--- a/sbin/dhclient/privsep.c
+++ b/sbin/dhclient/privsep.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: privsep.c,v 1.16 2011/04/04 11:14:52 krw Exp $ */
+/* $OpenBSD: privsep.c,v 1.17 2012/10/30 18:39:44 krw Exp $ */
/*
* Copyright (c) 2004 Henning Brauer <henning@openbsd.org>
@@ -94,118 +94,290 @@ void
dispatch_imsg(int fd)
{
struct imsg_hdr hdr;
- char *reason, *filename,
- *servername, *prefix;
- size_t reason_len, filename_len,
- servername_len, prefix_len, totlen;
- struct client_lease lease;
- int ret, i, optlen;
- struct buf *buf;
+ in_addr_t *mask;
+ char *ifname, *contents;
+ size_t totlen, len;
+ struct iaddr *addr, *gateway;
+ int rdomain;
buf_read(fd, &hdr, sizeof(hdr));
switch (hdr.code) {
- case IMSG_SCRIPT_INIT:
- if (hdr.len < sizeof(hdr) + sizeof(size_t))
- error("corrupted message received");
- buf_read(fd, &reason_len, sizeof(reason_len));
- if (hdr.len < reason_len + sizeof(hdr) + sizeof(size_t) ||
- reason_len == SIZE_T_MAX)
- error("corrupted message received");
- if (reason_len > 0) {
- if ((reason = calloc(1, reason_len + 1)) == NULL)
+ case IMSG_DELETE_ADDRESS:
+ totlen = sizeof(hdr);
+ ifname = NULL;
+ addr = NULL;
+ if (hdr.len < totlen + sizeof(len))
+ error("IMSG_DELETE_ADDRESS missing ifname length");
+ buf_read(fd, &len, sizeof(len));
+ totlen += sizeof(len);
+ if (len == SIZE_T_MAX) {
+ error("IMSG_DELETE_ADDRESS invalid ifname length");
+ } else if (len > 0) {
+ if (hdr.len < totlen + len)
+ error("IMSG_DELETE_ADDRESS short ifname");
+ if ((ifname = calloc(1, len + 1)) == NULL)
error("%m");
- buf_read(fd, reason, reason_len);
+ buf_read(fd, ifname, len);
+ totlen += len;
} else
- reason = NULL;
+ error("IMSG_DELETE_ADDRESS ifname missing");
- priv_script_init(reason);
- free(reason);
+ if (hdr.len < totlen + sizeof(len))
+ error("IMSG_DELETE_ADDRESS missing rdomain length");
+ buf_read(fd, &len, sizeof(len));
+ totlen += sizeof(len);
+ if (len == SIZE_T_MAX) {
+ error("IMSG_DELETE_ADDRESS invalid rdomain length");
+ } else if (len > 0) {
+ if (hdr.len < totlen + len)
+ error("IMSG_DELETE_ADDRESS short rdomain");
+ buf_read(fd, &rdomain, len);
+ totlen += len;
+ } else
+ error("IMSG_DELETE_ADDRESS rdomain missing");
+
+ if (hdr.len < totlen + sizeof(len))
+ error("IMSG_DELETE_ADDRESS missing addr length");
+ buf_read(fd, &len, sizeof(len));
+ totlen += sizeof(len);
+ if (len == SIZE_T_MAX) {
+ error("IMSG_DELETE_ADDRESS invalid addr");
+ } else if (len == sizeof(*addr)) {
+ if ((addr = calloc(1, len)) == NULL)
+ error("%m");
+ buf_read(fd, addr, len);
+ totlen += len;
+ } else {
+ error("IMSG_DELETE_ADDRESS addr missing %zu", len);
+ }
+
+ priv_delete_old_address(ifname, rdomain, *addr);
+ free(ifname);
+ free(addr);
break;
- case IMSG_SCRIPT_WRITE_PARAMS:
- bzero(&lease, sizeof lease);
- totlen = sizeof(hdr) + sizeof(lease) + sizeof(size_t);
- if (hdr.len < totlen)
- error("corrupted message received");
- buf_read(fd, &lease, sizeof(lease));
-
- buf_read(fd, &filename_len, sizeof(filename_len));
- totlen += filename_len + sizeof(size_t);
- if (hdr.len < totlen || filename_len == SIZE_T_MAX)
- error("corrupted message received");
- if (filename_len > 0) {
- if ((filename = calloc(1, filename_len + 1)) == NULL)
+
+ case IMSG_ADD_ADDRESS:
+ totlen = sizeof(hdr);
+ ifname = NULL;
+ addr = NULL;
+ mask = NULL;
+ if (hdr.len < totlen + sizeof(len))
+ error("IMSG_ADD_ADDRESS missing ifname length");
+ buf_read(fd, &len, sizeof(len));
+ totlen += sizeof(len);
+ if (len == SIZE_T_MAX) {
+ error("IMSG_ADD_ADDRESS invalid ifname length");
+ } else if (len > 0) {
+ if (hdr.len < totlen + len)
+ error("IMSG_ADD_ADDRESS short ifname");
+ if ((ifname = calloc(1, len + 1)) == NULL)
error("%m");
- buf_read(fd, filename, filename_len);
+ buf_read(fd, ifname, len);
+ totlen += len;
+ } else
+ error("IMSG_ADD_ADDRESS ifname missing");
+
+ if (hdr.len < totlen + sizeof(len))
+ error("IMSG_ADD_ADDRESS missing rdomain length");
+ buf_read(fd, &len, sizeof(len));
+ totlen += sizeof(len);
+ if (len == SIZE_T_MAX) {
+ error("IMSG_ADD_ADDRESS invalid rdomain length");
+ } else if (len > 0) {
+ if (hdr.len < totlen + len)
+ error("IMSG_ADD_ADDRESS short rdomain");
+ buf_read(fd, &rdomain, len);
+ totlen += len;
} else
- filename = NULL;
-
- buf_read(fd, &servername_len, sizeof(servername_len));
- totlen += servername_len + sizeof(size_t);
- if (hdr.len < totlen || servername_len == SIZE_T_MAX)
- error("corrupted message received");
- if (servername_len > 0) {
- if ((servername =
- calloc(1, servername_len + 1)) == NULL)
+ error("IMSG_ADD_ADDRESS rdomain missing");
+
+ if (hdr.len < totlen + sizeof(len))
+ error("IMSG_ADD_ADDRESS missing addr length");
+ buf_read(fd, &len, sizeof(len));
+ totlen += sizeof(len);
+ if (len == SIZE_T_MAX) {
+ error("IMSG_ADD_ADDRESS invalid addr");
+ } else if (len == sizeof(*addr)) {
+ if ((addr = calloc(1, len)) == NULL)
+ error("%m");
+ buf_read(fd, addr, len);
+ totlen += len;
+ } else {
+ error("IMSG_ADD_ADDRESS addr missing %zu", len);
+ }
+
+ if (hdr.len < totlen + sizeof(len))
+ error("IMSG_ADD_ADDRESS missing mask length");
+ buf_read(fd, &len, sizeof(len));
+ totlen += sizeof(len);
+ mask = NULL;
+ if (len == SIZE_T_MAX) {
+ error("IMSG_ADD_ADDRESS invalid mask");
+ } else if (len == sizeof(*mask)) {
+ if ((mask = calloc(1, len)) == NULL)
+ error("%m");
+ buf_read(fd, mask, len);
+ totlen += len;
+ } else {
+ error("IMSG_ADD_ADDRESS mask missing %zu", len);
+ }
+
+ priv_add_new_address(ifname, rdomain, *addr, *mask);
+ free(ifname);
+ free(addr);
+ free(mask);
+ break;
+
+ case IMSG_FLUSH_ROUTES:
+ totlen = sizeof(hdr);
+ ifname = NULL;
+ addr = NULL;
+ if (hdr.len < totlen + sizeof(len))
+ error("IMSG_FLUSH_ROUTES missing ifname length");
+ buf_read(fd, &len, sizeof(len));
+ totlen += sizeof(len);
+ if (len == SIZE_T_MAX) {
+ error("IMSG_FLUSH_ROUTES invalid ifname length");
+ } else if (len > 0) {
+ if (hdr.len < totlen + len)
+ error("IMSG_FLUSH_ROUTES short ifname");
+ if ((ifname = calloc(1, len + 1)) == NULL)
error("%m");
- buf_read(fd, servername, servername_len);
+ buf_read(fd, ifname, len);
+ totlen += len;
} else
- servername = NULL;
-
- buf_read(fd, &prefix_len, sizeof(prefix_len));
- totlen += prefix_len;
- if (hdr.len < totlen || prefix_len == SIZE_T_MAX)
- error("corrupted message received");
- if (prefix_len > 0) {
- if ((prefix = calloc(1, prefix_len + 1)) == NULL)
+ error("IMSG_FLUSH_ROUTES ifname missing");
+
+ if (hdr.len < totlen + sizeof(len))
+ error("IMSG_FLUSH_ROUTES missing rdomain length");
+ buf_read(fd, &len, sizeof(len));
+ totlen += sizeof(len);
+ if (len == SIZE_T_MAX) {
+ error("IMSG_FLUSH_ROUTES invalid rdomain length");
+ } else if (len > 0) {
+ if (hdr.len < totlen + len)
+ error("IMSG_FLUSH_ROUTES short rdomain");
+ buf_read(fd, &rdomain, len);
+ totlen += len;
+ } else
+ error("IMSG_FLUSH_ROUTES rdomain missing");
+
+ priv_flush_routes_and_arp_cache(ifname, rdomain);
+ free(ifname);
+ break;
+
+ case IMSG_ADD_DEFAULT_ROUTE:
+ totlen = sizeof(hdr);
+ ifname = NULL;
+ addr = NULL;
+ if (hdr.len < totlen + sizeof(len))
+ error("IMSG_ADD_DEFAULT_ROUTE missing ifname length");
+ buf_read(fd, &len, sizeof(len));
+ totlen += sizeof(len);
+ if (len == SIZE_T_MAX) {
+ error("IMSG_ADD_DEFAULT_ROUTE invalid ifname length");
+ } else if (len > 0) {
+ if (hdr.len < totlen + len)
+ error("IMSG_ADD_DEFAULT_ROUTE short ifname");
+ if ((ifname = calloc(1, len + 1)) == NULL)
error("%m");
- buf_read(fd, prefix, prefix_len);
+ buf_read(fd, ifname, len);
+ totlen += len;
} else
- prefix = NULL;
-
- for (i = 0; i < 256; i++) {
- totlen += sizeof(optlen);
- if (hdr.len < totlen)
- error("corrupted message received");
- buf_read(fd, &optlen, sizeof(optlen));
- lease.options[i].data = NULL;
- lease.options[i].len = optlen;
- if (optlen > 0) {
- totlen += optlen;
- if (hdr.len < totlen || optlen == SIZE_T_MAX)
- error("corrupted message received");
- lease.options[i].data =
- calloc(1, optlen + 1);
- if (lease.options[i].data == NULL)
- error("%m");
- buf_read(fd, lease.options[i].data, optlen);
- }
+ error("IMSG_ADD_DEFAULT_ROUTE ifname missing");
+
+ if (hdr.len < totlen + sizeof(len))
+ error("IMSG_ADD_DEFAULT_ROUTE missing rdomain length");
+ buf_read(fd, &len, sizeof(len));
+ totlen += sizeof(len);
+ if (len == SIZE_T_MAX) {
+ error("IMSG_ADD_DEFAULT_ROUTE invalid rdomain length");
+ } else if (len > 0) {
+ if (hdr.len < totlen + len)
+ error("IMSG_FLUSH_ROUTES short rdomain");
+ buf_read(fd, &rdomain, len);
+ totlen += len;
+ } else
+ error("IMSG_ADD_DEFAULT_ROUTE rdomain missing");
+
+ if (hdr.len < totlen + sizeof(len))
+ error("IMSG_ADD_DEFAULT_ROUTE missing addr length");
+ buf_read(fd, &len, sizeof(len));
+ totlen += sizeof(len);
+ if (len == SIZE_T_MAX) {
+ error("IMSG_ADD_DEFAULT_ROUTE invalid addr");
+ } else if (len == sizeof(*addr)) {
+ if ((addr = calloc(1, len)) == NULL)
+ error("%m");
+ buf_read(fd, addr, len);
+ totlen += len;
+ } else {
+ error("IMSG_ADD_DEFAULT_ROUTE addr missing %zu",
+ len);
}
- lease.server_name = servername;
- lease.filename = filename;
- priv_script_write_params(prefix, &lease);
+ if (hdr.len < totlen + sizeof(len))
+ error("IMSG_ADD_DEFAULT_ROUTE missing gateway length");
+ buf_read(fd, &len, sizeof(len));
+ totlen += sizeof(len);
+ gateway = NULL;
+ if (len == SIZE_T_MAX) {
+ error("IMSG_ADD_DEFAULT_ROUTE invalid gateway");
+ } else if (len == sizeof(*gateway)) {
+ if ((gateway = calloc(1, len)) == NULL)
+ error("%m");
+ buf_read(fd, gateway, len);
+ totlen += len;
+ } else {
+ error("IMSG_ADD_DEFAULT_ROUTE gateway missing %zu",
+ len);
+ }
- free(servername);
- free(filename);
- free(prefix);
- for (i = 0; i < 256; i++)
- if (lease.options[i].len > 0)
- free(lease.options[i].data);
+ priv_add_default_route(ifname, rdomain, *addr, *gateway);
+ free(ifname);
+ free(addr);
+ free(gateway);
break;
- case IMSG_SCRIPT_GO:
- if (hdr.len != sizeof(hdr))
- error("corrupted message received");
-
- ret = priv_script_go();
-
- hdr.code = IMSG_SCRIPT_GO_RET;
- hdr.len = sizeof(struct imsg_hdr) + sizeof(int);
- if ((buf = buf_open(hdr.len)) == NULL)
- error("buf_open: %m");
- buf_add(buf, &hdr, sizeof(hdr));
- buf_add(buf, &ret, sizeof(ret));
- buf_close(fd, buf);
+ case IMSG_NEW_RESOLV_CONF:
+ totlen = sizeof(hdr);
+ ifname = NULL;
+ contents = NULL;
+ if (hdr.len < totlen + sizeof(len))
+ error("IMSG_NEW_RESOLV_CONF missing ifname length");
+ buf_read(fd, &len, sizeof(len));
+ totlen += sizeof(len);
+ if (len == SIZE_T_MAX) {
+ error("IMSG_NEW_RESOLV_CONF invalid ifname length");
+ } else if (len > 0) {
+ if (hdr.len < totlen + len)
+ error("IMSG_NEW_RESOLV_CONF short ifname");
+ if ((ifname = calloc(1, len + 1)) == NULL)
+ error("%m");
+ buf_read(fd, ifname, len);
+ totlen += len;
+ } else
+ error("IMSG_NEW_RESOLV_CONF ifname missing");
+
+ if (hdr.len < totlen + sizeof(len))
+ error("IMSG_NEW_RESOLV_CONF missing contents length");
+ buf_read(fd, &len, sizeof(len));
+ totlen += sizeof(len);
+ if (len == SIZE_T_MAX) {
+ error("IMSG_NEW_RESOLV_CONF invalid contents length");
+ } else if (len > 0) {
+ if (hdr.len < totlen + len)
+ error("IMSG_NEW_RESOLV_CONF short contents");
+ if ((contents = calloc(1, len + 1)) == NULL)
+ error("%m");
+ buf_read(fd, contents, len);
+ totlen += len;
+ } else
+ error("IMSG_NEW_RESOLV_CONF contents missing");
+
+ priv_new_resolv_conf(ifname, contents);
+ free(ifname);
+ free(contents);
break;
default:
error("received unknown message, code %d", hdr.code);