aboutsummaryrefslogtreecommitdiff
path: root/lib/libcasper
diff options
context:
space:
mode:
authorMariusz Zaborski <oshogbo@FreeBSD.org>2016-06-08 02:03:53 +0000
committerMariusz Zaborski <oshogbo@FreeBSD.org>2016-06-08 02:03:53 +0000
commit920be817aaee95cbe5c3bc11b33426c22b773a3f (patch)
tree74015184429330b04a80b62cced41040be403e3b /lib/libcasper
parent311219368ae8a18c86f8dca5e4d8dfb5f56b02b2 (diff)
Notes
Diffstat (limited to 'lib/libcasper')
-rw-r--r--lib/libcasper/libcasper/libcasper_impl.h4
-rw-r--r--lib/libcasper/libcasper/libcasper_service.c10
-rw-r--r--lib/libcasper/libcasper/libcasper_service.h12
-rw-r--r--lib/libcasper/libcasper/service.c60
-rw-r--r--lib/libcasper/libcasper/zygote.c30
-rw-r--r--lib/libcasper/services/cap_dns/cap_dns.c2
-rw-r--r--lib/libcasper/services/cap_grp/cap_grp.c2
-rw-r--r--lib/libcasper/services/cap_pwd/cap_pwd.c2
-rw-r--r--lib/libcasper/services/cap_random/cap_random.c2
-rw-r--r--lib/libcasper/services/cap_sysctl/cap_sysctl.c2
10 files changed, 79 insertions, 47 deletions
diff --git a/lib/libcasper/libcasper/libcasper_impl.h b/lib/libcasper/libcasper/libcasper_impl.h
index bf2e6cee3bc0..89f244d0b87d 100644
--- a/lib/libcasper/libcasper/libcasper_impl.h
+++ b/lib/libcasper/libcasper/libcasper_impl.h
@@ -46,11 +46,11 @@ bool fd_is_valid(int fd);
/* Private service functions. */
struct service *service_alloc(const char *name,
service_limit_func_t *limitfunc,
- service_command_func_t *commandfunc);
+ service_command_func_t *commandfunc, uint64_t flags);
void service_free(struct service *service);
void service_message(struct service *service,
struct service_connection *sconn);
-void service_start(struct service *service, int sock);
+void service_start(struct service *service, int sock, int procfd);
const char *service_name(struct service *service);
/* Private service connection functions. */
diff --git a/lib/libcasper/libcasper/libcasper_service.c b/lib/libcasper/libcasper/libcasper_service.c
index 5b1c7c852478..1f9e8d6fcd76 100644
--- a/lib/libcasper/libcasper/libcasper_service.c
+++ b/lib/libcasper/libcasper/libcasper_service.c
@@ -73,7 +73,7 @@ service_find(const char *name)
struct casper_service *
service_register(const char *name, service_limit_func_t *limitfunc,
- service_command_func_t *commandfunc)
+ service_command_func_t *commandfunc, uint64_t flags)
{
struct casper_service *casserv;
@@ -88,7 +88,8 @@ service_register(const char *name, service_limit_func_t *limitfunc,
if (casserv == NULL)
return (NULL);
- casserv->cs_service = service_alloc(name, limitfunc, commandfunc);
+ casserv->cs_service = service_alloc(name, limitfunc, commandfunc,
+ flags);
if (casserv->cs_service == NULL) {
free(casserv);
return (NULL);
@@ -141,11 +142,10 @@ service_execute(int chanfd)
exit(1);
service = (struct service *)(uintptr_t)nvlist_take_number(nvl,
"service");
- //XXX: We should remove this?
procfd = nvlist_take_descriptor(nvl, "procfd");
nvlist_destroy(nvl);
- service_start(service, chanfd);
+ service_start(service, chanfd, procfd);
/* Not reached. */
exit(1);
}
@@ -199,7 +199,7 @@ service_register_core(int fd)
struct service_connection *sconn;
casserv = service_register(CORE_CASPER_NAME, casper_limit,
- casper_command);
+ casper_command, 0);
sconn = service_connection_add(casserv->cs_service, fd, NULL);
if (sconn == NULL) {
close(fd);
diff --git a/lib/libcasper/libcasper/libcasper_service.h b/lib/libcasper/libcasper/libcasper_service.h
index 4efbeb24d345..a66c88efe898 100644
--- a/lib/libcasper/libcasper/libcasper_service.h
+++ b/lib/libcasper/libcasper/libcasper_service.h
@@ -40,21 +40,25 @@ struct nvlist;
typedef struct nvlist nvlist_t;
#endif
+#define CASPER_SERVICE_STDIO 0x00000001
+#define CASPER_SERVICE_FD 0x00000002
+
typedef int service_limit_func_t(const nvlist_t *, const nvlist_t *);
typedef int service_command_func_t(const char *cmd, const nvlist_t *,
nvlist_t *, nvlist_t *);
struct casper_service *service_register(const char *name,
- service_limit_func_t *limitfunc, service_command_func_t *commandfunc);
+ service_limit_func_t *limitfunc, service_command_func_t *commandfunc,
+ uint64_t flags);
#define __constructor __attribute__((constructor))
-#define CREATE_SERVICE(name, limit_func, command_func) \
+#define CREATE_SERVICE(name, limit_func, command_func, flags) \
static __constructor void \
init_casper_service(void) \
{ \
\
- (void)service_register(name, limit_func, \
- command_func); \
+ (void)service_register(name, limit_func, command_func, \
+ flags); \
}
#endif /* !_LIBCASPER_SERVICE_H_ */
diff --git a/lib/libcasper/libcasper/service.c b/lib/libcasper/libcasper/service.c
index e02d7d90f0d6..52318121cbb0 100644
--- a/lib/libcasper/libcasper/service.c
+++ b/lib/libcasper/libcasper/service.c
@@ -41,6 +41,7 @@ __FBSDID("$FreeBSD$");
#include <err.h>
#include <errno.h>
#include <fcntl.h>
+#include <paths.h>
#include <stdbool.h>
#include <stdio.h>
#include <stdlib.h>
@@ -78,6 +79,7 @@ struct service_connection {
struct service {
int s_magic;
char *s_name;
+ uint64_t s_flags;
service_limit_func_t *s_limit;
service_command_func_t *s_command;
TAILQ_HEAD(, service_connection) s_connections;
@@ -85,7 +87,7 @@ struct service {
struct service *
service_alloc(const char *name, service_limit_func_t *limitfunc,
- service_command_func_t *commandfunc)
+ service_command_func_t *commandfunc, uint64_t flags)
{
struct service *service;
@@ -99,6 +101,7 @@ service_alloc(const char *name, service_limit_func_t *limitfunc,
}
service->s_limit = limitfunc;
service->s_command = commandfunc;
+ service->s_flags = flags;
TAILQ_INIT(&service->s_connections);
service->s_magic = SERVICE_MAGIC;
@@ -338,8 +341,59 @@ service_name(struct service *service)
return (service->s_name);
}
+static void
+stdnull(void)
+{
+ int fd;
+
+ fd = open(_PATH_DEVNULL, O_RDWR);
+ if (fd == -1)
+ errx(1, "Unable to open %s", _PATH_DEVNULL);
+
+ if (setsid() == -1)
+ errx(1, "Unable to detach from session");
+
+ if (dup2(fd, STDIN_FILENO) == -1)
+ errx(1, "Unable to cover stdin");
+ if (dup2(fd, STDOUT_FILENO) == -1)
+ errx(1, "Unable to cover stdout");
+ if (dup2(fd, STDERR_FILENO) == -1)
+ errx(1, "Unable to cover stderr");
+
+ close(fd);
+}
+
+static void
+service_clean(int sock, int procfd, uint64_t flags)
+{
+ int fd, maxfd, minfd;
+
+ assert(sock > STDERR_FILENO);
+ assert(procfd > STDERR_FILENO);
+ assert(sock != procfd);
+
+ if ((flags & CASPER_SERVICE_STDIO) == 0)
+ stdnull();
+
+ if ((flags & CASPER_SERVICE_FD) == 0) {
+ if (procfd > sock) {
+ maxfd = procfd;
+ minfd = sock;
+ } else {
+ maxfd = sock;
+ minfd = procfd;
+ }
+
+ for (fd = STDERR_FILENO + 1; fd < maxfd; fd++) {
+ if (fd != minfd)
+ close(fd);
+ }
+ closefrom(maxfd + 1);
+ }
+}
+
void
-service_start(struct service *service, int sock)
+service_start(struct service *service, int sock, int procfd)
{
struct service_connection *sconn, *sconntmp;
fd_set fds;
@@ -348,6 +402,8 @@ service_start(struct service *service, int sock)
assert(service != NULL);
assert(service->s_magic == SERVICE_MAGIC);
setproctitle("%s", service->s_name);
+ service_clean(sock, procfd, service->s_flags);
+
if (service_connection_add(service, sock, NULL) == NULL)
exit(1);
diff --git a/lib/libcasper/libcasper/zygote.c b/lib/libcasper/libcasper/zygote.c
index e554a3eee761..feeb1537af87 100644
--- a/lib/libcasper/libcasper/zygote.c
+++ b/lib/libcasper/libcasper/zygote.c
@@ -40,7 +40,6 @@ __FBSDID("$FreeBSD$");
#include <assert.h>
#include <err.h>
#include <errno.h>
-#include <paths.h>
#include <stdbool.h>
#include <stdlib.h>
#include <strings.h>
@@ -51,28 +50,6 @@ __FBSDID("$FreeBSD$");
/* Zygote info. */
static int zygote_sock = -1;
-static void
-stdnull(void)
-{
- int fd;
-
- fd = open(_PATH_DEVNULL, O_RDWR);
- if (fd == -1)
- errx(1, "Unable to open %s", _PATH_DEVNULL);
-
- if (setsid() == -1)
- errx(1, "Unable to detach from session");
-
- if (dup2(fd, STDIN_FILENO) == -1)
- errx(1, "Unable to cover stdin");
- if (dup2(fd, STDOUT_FILENO) == -1)
- errx(1, "Unable to cover stdout");
- if (dup2(fd, STDERR_FILENO) == -1)
- errx(1, "Unable to cover stderr");
-
- close(fd);
-}
-
int
zygote_clone(zygote_func_t *func, int *chanfdp, int *procfdp)
{
@@ -113,7 +90,7 @@ zygote_clone(zygote_func_t *func, int *chanfdp, int *procfdp)
static void
zygote_main(int sock)
{
- int error, fd, procfd;
+ int error, procfd;
int chanfd[2];
nvlist_t *nvlin, *nvlout;
zygote_func_t *func;
@@ -123,11 +100,6 @@ zygote_main(int sock)
setproctitle("zygote");
- stdnull();
- for (fd = STDERR_FILENO + 1; fd < sock; fd++)
- close(fd);
- closefrom(sock + 1);
-
for (;;) {
nvlin = nvlist_recv(sock, 0);
if (nvlin == NULL) {
diff --git a/lib/libcasper/services/cap_dns/cap_dns.c b/lib/libcasper/services/cap_dns/cap_dns.c
index 0ecf047027b2..4837d7d0fb6c 100644
--- a/lib/libcasper/services/cap_dns/cap_dns.c
+++ b/lib/libcasper/services/cap_dns/cap_dns.c
@@ -759,4 +759,4 @@ dns_command(const char *cmd, const nvlist_t *limits, nvlist_t *nvlin,
return (error);
}
-CREATE_SERVICE("system.dns", dns_limit, dns_command);
+CREATE_SERVICE("system.dns", dns_limit, dns_command, 0);
diff --git a/lib/libcasper/services/cap_grp/cap_grp.c b/lib/libcasper/services/cap_grp/cap_grp.c
index 54a022f76cec..4e3701d68cd7 100644
--- a/lib/libcasper/services/cap_grp/cap_grp.c
+++ b/lib/libcasper/services/cap_grp/cap_grp.c
@@ -786,4 +786,4 @@ grp_command(const char *cmd, const nvlist_t *limits, nvlist_t *nvlin,
return (error);
}
-CREATE_SERVICE("system.grp", grp_limit, grp_command);
+CREATE_SERVICE("system.grp", grp_limit, grp_command, 0);
diff --git a/lib/libcasper/services/cap_pwd/cap_pwd.c b/lib/libcasper/services/cap_pwd/cap_pwd.c
index 254e2441426b..195f3e0256e0 100644
--- a/lib/libcasper/services/cap_pwd/cap_pwd.c
+++ b/lib/libcasper/services/cap_pwd/cap_pwd.c
@@ -780,4 +780,4 @@ pwd_command(const char *cmd, const nvlist_t *limits, nvlist_t *nvlin,
return (error);
}
-CREATE_SERVICE("system.pwd", pwd_limit, pwd_command);
+CREATE_SERVICE("system.pwd", pwd_limit, pwd_command, 0);
diff --git a/lib/libcasper/services/cap_random/cap_random.c b/lib/libcasper/services/cap_random/cap_random.c
index d19fe960ea3a..56bd6596d5c5 100644
--- a/lib/libcasper/services/cap_random/cap_random.c
+++ b/lib/libcasper/services/cap_random/cap_random.c
@@ -114,4 +114,4 @@ random_command(const char *cmd, const nvlist_t *limits __unused,
return (0);
}
-CREATE_SERVICE("system.random", NULL, random_command);
+CREATE_SERVICE("system.random", NULL, random_command, 0);
diff --git a/lib/libcasper/services/cap_sysctl/cap_sysctl.c b/lib/libcasper/services/cap_sysctl/cap_sysctl.c
index 7611d647f11a..8ee7310c13de 100644
--- a/lib/libcasper/services/cap_sysctl/cap_sysctl.c
+++ b/lib/libcasper/services/cap_sysctl/cap_sysctl.c
@@ -290,4 +290,4 @@ sysctl_command(const char *cmd, const nvlist_t *limits, nvlist_t *nvlin,
return (0);
}
-CREATE_SERVICE("system.sysctl", sysctl_limit, sysctl_command);
+CREATE_SERVICE("system.sysctl", sysctl_limit, sysctl_command, 0);