summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorReyk Floeter <reyk@cvs.openbsd.org>2015-10-02 13:13:06 +0000
committerReyk Floeter <reyk@cvs.openbsd.org>2015-10-02 13:13:06 +0000
commitb06b2ea67d222340d2e40aeff851389a75603ac4 (patch)
tree7054ca0693baa9bc4d4cd0c8e9881b23e92bd073
parent1f8d5025b9e8267e9705d1aa74204150cb5c70c5 (diff)
Adopt smtpd's imsg_read_nofd() to mitigate the risk of user-injected
file descriptor leakage from the optional world-writable _restricted_ control socket. OK gilles@ blambert@
-rw-r--r--usr.sbin/snmpd/control.c28
1 files changed, 26 insertions, 2 deletions
diff --git a/usr.sbin/snmpd/control.c b/usr.sbin/snmpd/control.c
index 43468ab69c3..77915764f5b 100644
--- a/usr.sbin/snmpd/control.c
+++ b/usr.sbin/snmpd/control.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: control.c,v 1.29 2015/05/28 17:08:09 florian Exp $ */
+/* $OpenBSD: control.c,v 1.30 2015/10/02 13:13:05 reyk Exp $ */
/*
* Copyright (c) 2010-2013 Reyk Floeter <reyk@openbsd.org>
@@ -47,6 +47,7 @@ void control_dispatch_imsg(int, short, void *);
void control_dispatch_agentx(int, short, void *);
void control_imsg_forward(struct imsg *);
void control_event_add(struct ctl_conn *, int, int, struct timeval *);
+ssize_t imsg_read_nofd(struct imsgbuf *);
int
control_init(struct privsep *ps, struct control_sock *cs)
@@ -231,7 +232,7 @@ control_dispatch_imsg(int fd, short event, void *arg)
int n, v, i;
if (event & EV_READ) {
- if ((n = imsg_read(&c->iev.ibuf)) == -1 || n == 0) {
+ if ((n = imsg_read_nofd(&c->iev.ibuf)) == -1 || n == 0) {
control_close(c);
return;
}
@@ -663,3 +664,26 @@ control_event_add(struct ctl_conn *c, int fd, int wflag, struct timeval *tv)
event_set(&c->iev.ev, fd, EV_READ|wflag, control_dispatch_agentx, c);
event_add(&c->iev.ev, tv);
}
+
+/* This should go into libutil, from smtpd/mproc.c */
+ssize_t
+imsg_read_nofd(struct imsgbuf *ibuf)
+{
+ ssize_t n;
+ char *buf;
+ size_t len;
+
+ buf = ibuf->r.buf + ibuf->r.wpos;
+ len = sizeof(ibuf->r.buf) - ibuf->r.wpos;
+
+ again:
+ if ((n = recv(ibuf->fd, buf, len, 0)) == -1) {
+ if (errno != EINTR && errno != EAGAIN)
+ goto fail;
+ goto again;
+ }
+
+ ibuf->r.wpos += n;
+ fail:
+ return (n);
+}