svn commit: r315862 - head/lib/libcasper/libcasper
Robert Watson
rwatson at FreeBSD.org
Thu Mar 23 14:35:22 UTC 2017
Author: rwatson
Date: Thu Mar 23 14:35:21 2017
New Revision: 315862
URL: https://svnweb.freebsd.org/changeset/base/315862
Log:
In libcasper, prefer to send a function index or service name over the IPC
channel to a zygote process, rather than sending a function pointer or
service pointer. This avoids transfering pointers between address spaces,
which while robust in this case (due to the zygote being forked() from the
parent) is not generally a good idea, especially in the presence of
increasingly popular control-flow integrity and pointer protection
mitigation schemes. With this change, ping(8) and other sandboxed tools
using libcasper for DNS resolution now work on architectures with tagged
memory again.
Reviewed by: oshogbo
MFC after: 1 week
Sponsored by: DARPA, AFRL
Modified:
head/lib/libcasper/libcasper/libcasper_service.c
head/lib/libcasper/libcasper/zygote.c
head/lib/libcasper/libcasper/zygote.h
Modified: head/lib/libcasper/libcasper/libcasper_service.c
==============================================================================
--- head/lib/libcasper/libcasper/libcasper_service.c Thu Mar 23 14:12:21 2017 (r315861)
+++ head/lib/libcasper/libcasper/libcasper_service.c Thu Mar 23 14:35:21 2017 (r315862)
@@ -1,11 +1,16 @@
/*-
* Copyright (c) 2012 The FreeBSD Foundation
* Copyright (c) 2015 Mariusz Zaborski <oshogbo at FreeBSD.org>
+ * Copyright (c) 2017 Robert N. M. Watson
* All rights reserved.
*
* This software was developed by Pawel Jakub Dawidek under sponsorship from
* the FreeBSD Foundation.
*
+ * This software was developed by SRI International and the University of
+ * Cambridge Computer Laboratory under DARPA/AFRL contract (FA8750-10-C-0237)
+ * ("CTSRD"), as part of the DARPA CRASH research programme.
+ *
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
@@ -130,18 +135,25 @@ casper_limit(const nvlist_t *oldlimits,
return (0);
}
-static void
+void
service_execute(int chanfd)
{
+ struct casper_service *casserv;
struct service *service;
+ const char *servname;
nvlist_t *nvl;
int procfd;
nvl = nvlist_recv(chanfd, 0);
if (nvl == NULL)
exit(1);
- service = (struct service *)(uintptr_t)nvlist_take_number(nvl,
- "service");
+ if (!nvlist_exists_string(nvl, "service"))
+ exit(1);
+ servname = nvlist_get_string(nvl, "service");
+ casserv = service_find(servname);
+ if (casserv == NULL)
+ exit(1);
+ service = casserv->cs_service;
procfd = nvlist_take_descriptor(nvl, "procfd");
nvlist_destroy(nvl);
@@ -172,12 +184,11 @@ casper_command(const char *cmd, const nv
if (!casper_allowed_service(limits, servname))
return (ENOTCAPABLE);
- if (zygote_clone(service_execute, &chanfd, &procfd) == -1)
+ if (zygote_clone_service_execute(&chanfd, &procfd) == -1)
return (errno);
nvl = nvlist_create(0);
- nvlist_add_number(nvl, "service",
- (uint64_t)(uintptr_t)casserv->cs_service);
+ nvlist_add_string(nvl, "service", servname);
nvlist_move_descriptor(nvl, "procfd", procfd);
if (nvlist_send(chanfd, nvl) == -1) {
error = errno;
Modified: head/lib/libcasper/libcasper/zygote.c
==============================================================================
--- head/lib/libcasper/libcasper/zygote.c Thu Mar 23 14:12:21 2017 (r315861)
+++ head/lib/libcasper/libcasper/zygote.c Thu Mar 23 14:35:21 2017 (r315862)
@@ -1,11 +1,16 @@
/*-
* Copyright (c) 2012 The FreeBSD Foundation
* Copyright (c) 2015 Mariusz Zaborski <oshogbo at FreeBSD.org>
- * All rights reserved.
+ * Copyright (c) 2017 Robert N. M. Watson
*
* This software was developed by Pawel Jakub Dawidek under sponsorship from
* the FreeBSD Foundation.
*
+ * All rights reserved.
+ * This software was developed by SRI International and the University of
+ * Cambridge Computer Laboratory under DARPA/AFRL contract (FA8750-10-C-0237)
+ * ("CTSRD"), as part of the DARPA CRASH research programme.
+ *
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
@@ -50,8 +55,10 @@ __FBSDID("$FreeBSD$");
/* Zygote info. */
static int zygote_sock = -1;
+#define ZYGOTE_SERVICE_EXECUTE 1
+
int
-zygote_clone(zygote_func_t *func, int *chanfdp, int *procfdp)
+zygote_clone(uint64_t funcidx, int *chanfdp, int *procfdp)
{
nvlist_t *nvl;
int error;
@@ -63,7 +70,7 @@ zygote_clone(zygote_func_t *func, int *c
}
nvl = nvlist_create(0);
- nvlist_add_number(nvl, "func", (uint64_t)(uintptr_t)func);
+ nvlist_add_number(nvl, "funcidx", funcidx);
nvl = nvlist_xfer(zygote_sock, nvl, 0);
if (nvl == NULL)
return (-1);
@@ -81,6 +88,13 @@ zygote_clone(zygote_func_t *func, int *c
return (0);
}
+int
+zygote_clone_service_execute(int *chanfdp, int *procfdp)
+{
+
+ return (zygote_clone(ZYGOTE_SERVICE_EXECUTE, chanfdp, procfdp));
+}
+
/*
* This function creates sandboxes on-demand whoever has access to it via
* 'sock' socket. Function sends two descriptors to the caller: process
@@ -93,6 +107,7 @@ zygote_main(int sock)
int error, procfd;
int chanfd[2];
nvlist_t *nvlin, *nvlout;
+ uint64_t funcidx;
zygote_func_t *func;
pid_t pid;
@@ -109,10 +124,17 @@ zygote_main(int sock)
}
continue;
}
- func = (zygote_func_t *)(uintptr_t)nvlist_get_number(nvlin,
- "func");
+ funcidx = nvlist_get_number(nvlin, "funcidx");
nvlist_destroy(nvlin);
+ switch (funcidx) {
+ case ZYGOTE_SERVICE_EXECUTE:
+ func = service_execute;
+ break;
+ default:
+ exit(0);
+ }
+
/*
* Someone is requesting a new process, create one.
*/
Modified: head/lib/libcasper/libcasper/zygote.h
==============================================================================
--- head/lib/libcasper/libcasper/zygote.h Thu Mar 23 14:12:21 2017 (r315861)
+++ head/lib/libcasper/libcasper/zygote.h Thu Mar 23 14:35:21 2017 (r315862)
@@ -36,6 +36,12 @@
typedef void zygote_func_t(int);
int zygote_init(void);
-int zygote_clone(zygote_func_t *func, int *chanfdp, int *procfdp);
+int zygote_clone(uint64_t funcidx, int *chanfdp, int *procfdp);
+int zygote_clone_service_execute(int *chanfdp, int *procfdp);
+
+/*
+ * Functions reachable via zygote_clone().
+ */
+zygote_func_t service_execute;
#endif /* !_ZYGOTE_H_ */
More information about the svn-src-all
mailing list