From: Roy Marples Date: Fri, 9 May 2014 12:09:05 +0000 (+0000) Subject: controlgroup option changes group ownership of the control socket. X-Git-Tag: v6.4.0~53 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=a93e79c68f4641602be106a93f983ac71060d234;p=thirdparty%2Fdhcpcd.git controlgroup option changes group ownership of the control socket. --- diff --git a/control.c b/control.c index 2550da6b..958a32f6 100644 --- a/control.c +++ b/control.c @@ -173,6 +173,9 @@ control_start(struct dhcpcd_ctx *ctx, const char *ifname) if (bind(ctx->control_fd, (struct sockaddr *)&sun, len) == -1 || chmod(ctx->control_sock, S_IRUSR | S_IWUSR | S_IRGRP | S_IWGRP) == -1 || + (ctx->control_group && + chown(ctx->control_sock, + geteuid(), ctx->control_group) == -1) || listen(ctx->control_fd, sizeof(ctx->control_fds)) == -1) { close(ctx->control_fd); diff --git a/dhcpcd.conf.5.in b/dhcpcd.conf.5.in index b75af949..327fea3d 100644 --- a/dhcpcd.conf.5.in +++ b/dhcpcd.conf.5.in @@ -22,7 +22,7 @@ .\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF .\" SUCH DAMAGE. .\" -.Dd April 28, 2014 +.Dd May 9, 2014 .Dt DHCPCD.CONF 5 .Os .Sh NAME @@ -105,6 +105,11 @@ such as FireWire and InfiniBand. In most cases, .Nm dhcpcd will set this automatically. +.It Ic controlgroup Ar group +Sets the group ownership of +.Pa @RUNDIR@/dhcpcd.sock +so that users other than root can connect to +.Nm dhcpcd . .It Ic debug Echo debug messages to the stderr and syslog. .It Ic dev Ar value diff --git a/dhcpcd.h b/dhcpcd.h index 6554f693..7eadaa3b 100644 --- a/dhcpcd.h +++ b/dhcpcd.h @@ -96,6 +96,7 @@ struct dhcpcd_ctx { int control_fd; struct fd_list *control_fds; char control_sock[sizeof(CONTROLSOCKET) + IF_NAMESIZE]; + gid_t control_group; /* DHCP Enterprise options, RFC3925 */ struct dhcp_opt *vivso; diff --git a/if-options.c b/if-options.c index 90a28a29..b7f5c56f 100644 --- a/if-options.c +++ b/if-options.c @@ -36,6 +36,7 @@ #include #include #include +#include #include #include #include @@ -89,6 +90,7 @@ #define O_DHCP6 O_BASE + 31 #define O_IPV4 O_BASE + 32 #define O_IPV6 O_BASE + 33 +#define O_CONTROLGRP O_BASE + 34 const struct option cf_options[] = { {"background", no_argument, NULL, 'b'}, @@ -172,6 +174,7 @@ const struct option cf_options[] = { {"nodhcp", no_argument, NULL, O_NODHCP}, {"dhcp6", no_argument, NULL, O_DHCP6}, {"nodhcp6", no_argument, NULL, O_NODHCP6}, + {"controlgroup", required_argument, NULL, O_CONTROLGRP}, {NULL, 0, NULL, '\0'} }; @@ -615,7 +618,8 @@ static int parse_option(struct dhcpcd_ctx *ctx, const char *ifname, struct if_options *ifo, int opt, const char *arg, struct dhcp_opt **ldop, struct dhcp_opt **edop) { - int i, l, t; + int i, t; + long l; unsigned long u; char *p = NULL, *fp, *np, **nconf; ssize_t s; @@ -628,6 +632,11 @@ parse_option(struct dhcpcd_ctx *ctx, const char *ifname, struct if_options *ifo, size_t *dop_len, dl; struct vivco *vivco; struct token *token; + struct group *grp; +#ifdef _REENTRANT +#error foo + struct group grpbuf; +#endif #ifdef INET6 size_t sl; struct if_ia *ia; @@ -1774,6 +1783,58 @@ err_sla: case O_NODHCP6: ifo->options &= ~DHCPCD_DHCP6; break; + case O_CONTROLGRP: +#ifdef _REENTRANT + l = sysconf(_SC_GETGR_R_SIZE_MAX); + if (l == -1) + dl = 1024; + else + dl = (size_t)l; + p = malloc(dl); + if (p == NULL) { + syslog(LOG_ERR, "%s: malloc: %m", __func__); + return -1; + } + while ((i = getgrnam_r(arg, &grpbuf, p, (size_t)l, &grp)) == + ERANGE) + { + size_t nl = dl * 2; + if (nl < dl) { + syslog(LOG_ERR, "control_group: out of buffer"); + free(p); + return -1; + } + dl = nl; + np = realloc(p, dl); + if (np == NULL) { + syslog(LOG_ERR, "control_group: realloc: %m"); + free(p); + return -1; + } + p = np; + } + if (i != 0) { + errno = i; + syslog(LOG_ERR, "getgrnam_r: %m"); + free(p); + return -1; + } + if (grp == NULL) { + syslog(LOG_ERR, "controlgroup: %s: not found", arg); + free(p); + return -1; + } + ctx->control_group = grp->gr_gid; + free(p); +#else + grp = getgrnam(arg); + if (grp == NULL) { + syslog(LOG_ERR, "controlgroup: %s: not found", arg); + return -1; + } + ctx->control_group = grp->gr_gid; +#endif + break; default: return 0; }