changeset 5203:9d2d76abda6a draft

privsep: Add function for indirect ioctl
author Roy Marples <roy@marples.name>
date Sun, 10 May 2020 12:19:59 +0100
parents 318cd9e48312
children 47f18579daae
files src/privsep-bsd.c src/privsep-root.h src/privsep.h
diffstat 3 files changed, 45 insertions(+), 7 deletions(-) [+]
line wrap: on
line diff
--- a/src/privsep-bsd.c	Sun May 10 11:05:23 2020 +0100
+++ b/src/privsep-bsd.c	Sun May 10 12:19:59 2020 +0100
@@ -29,6 +29,7 @@
 #include <sys/ioctl.h>
 
 #include <errno.h>
+#include <string.h>
 #include <unistd.h>
 
 #include "dhcpcd.h"
@@ -41,12 +42,30 @@
 	int s, err;
 
 	s = socket(domain, SOCK_DGRAM, 0);
-	if (s != -1)
-		err = ioctl(s, req, data, len);
-	else
-		err = -1;
-	if (s != -1)
-		close(s);
+	if (s == -1)
+		return -1;
+	err = ioctl(s, req, data, len);
+	close(s);
+	return err;
+}
+
+static ssize_t
+ps_root_doindirectioctl(unsigned long req, void *data, size_t len)
+{
+	char *p = data;
+	struct ifreq ifr = { .ifr_flags = 0 };
+	ssize_t err;
+
+	if (len < IFNAMSIZ) {
+		errno = EINVAL;
+		return -1;
+	}
+
+	strlcpy(ifr.ifr_name, p, IFNAMSIZ);
+	ifr.ifr_data = p + IFNAMSIZ;
+	err = ps_root_doioctldom(PF_INET, req, &ifr, sizeof(ifr));
+	if (err != -1)
+		memmove(data, ifr.ifr_data, len - IFNAMSIZ);
 	return err;
 }
 
@@ -78,6 +97,8 @@
 		return ps_root_doioctldom(PF_LINK, psm->ps_flags, data, len);
 	case PS_IOCTL6:
 		return ps_root_doioctldom(PF_INET6, psm->ps_flags, data, len);
+	case PS_IOCTLINDIRECT:
+		return ps_root_doindirectioctl(psm->ps_flags, data, len);
 	case PS_ROUTE:
 		return ps_root_doroute(data, len);
 	default:
@@ -114,6 +135,20 @@
 }
 
 ssize_t
+ps_root_indirectioctl(struct dhcpcd_ctx *ctx, unsigned long request,
+    const char *ifname, void *data, size_t len)
+{
+	char buf[PS_BUFLEN];
+
+	strlcpy(buf, ifname, IFNAMSIZ);
+	memcpy(buf + IFNAMSIZ, data, len);
+	if (ps_sendcmd(ctx, ctx->ps_root_fd, PS_IOCTLINDIRECT,
+	    request, buf, IFNAMSIZ + len) == -1)
+		return -1;
+	return ps_root_readerror(ctx, data, len);
+}
+
+ssize_t
 ps_root_route(struct dhcpcd_ctx *ctx, void *data, size_t len)
 {
 
--- a/src/privsep-root.h	Sun May 10 11:05:23 2020 +0100
+++ b/src/privsep-root.h	Sun May 10 12:19:59 2020 +0100
@@ -44,6 +44,8 @@
 ssize_t ps_root_route(struct dhcpcd_ctx *, void *, size_t);
 ssize_t ps_root_ioctllink(struct dhcpcd_ctx *, unsigned long, void *, size_t);
 ssize_t ps_root_ioctl6(struct dhcpcd_ctx *, unsigned long, void *, size_t);
+ssize_t ps_root_indirectioctl(struct dhcpcd_ctx *, unsigned long, const char *,
+    void *, size_t);
 #endif
 #ifdef __linux__
 ssize_t ps_root_sendnetlink(struct dhcpcd_ctx *, int, struct msghdr *);
--- a/src/privsep.h	Sun May 10 11:05:23 2020 +0100
+++ b/src/privsep.h	Sun May 10 12:19:59 2020 +0100
@@ -52,9 +52,10 @@
 /* BSD Commands */
 #define	PS_IOCTLLINK		0x15
 #define	PS_IOCTL6		0x16
+#define	PS_IOCTLINDIRECT	0x17
 
 /* Linux commands */
-#define	PS_WRITEPATHUINT	0x17
+#define	PS_WRITEPATHUINT	0x18
 
 #define	PS_DELETE		0x20
 #define	PS_START		0x40