On Wed, Jul 10, 2019 at 03:44:55PM +0100, Ricardo Mestre wrote:
> Hi,
>
> Since the last email I sent, mentioned at the bottom, dhclient(8) has dropped
> support for re-execing itself on SIGHUP and so what path, hardcoded or not,
> should be unveiled for the executable is out of this conversation.
>
> Please check a new diff which unveils /etc/resolv.conf with write/create
> permissions and /etc/resolv.conf.tail with read.
>
> Comments? OK?
>
> Index: dhclient.c
> ===================================================================
> RCS file: /cvs/src/sbin/dhclient/dhclient.c,v
> retrieving revision 1.641
> diff -u -p -u -r1.641 dhclient.c
> --- dhclient.c 1 Jul 2019 16:53:59 -0000 1.641
> +++ dhclient.c 10 Jul 2019 14:36:31 -0000
> @@ -2232,6 +2232,13 @@ fork_privchld(struct interface_info *ifi
> if ((routefd = socket(AF_ROUTE, SOCK_RAW, 0)) == -1)
> fatal("socket(AF_ROUTE, SOCK_RAW)");
>
> + if (unveil(_PATH_RESOLV_CONF, "wc") == -1)
> + fatal("unveil");
> + if (unveil(_PATH_RESOLV_CONF_TAIL, "r") == -1)
> + fatal("unveil");
> + if (unveil(NULL, NULL) == -1)
> + fatal("unveil");
> +
> while (quit == 0) {
> pfd[0].fd = priv_ibuf->fd;
> pfd[0].events = POLLIN;
> Index: dhcpd.h
> ===================================================================
> RCS file: /cvs/src/sbin/dhclient/dhcpd.h,v
> retrieving revision 1.278
> diff -u -p -u -r1.278 dhcpd.h
> --- dhcpd.h 22 May 2019 12:56:31 -0000 1.278
> +++ dhcpd.h 10 Jul 2019 14:36:31 -0000
> @@ -153,6 +153,8 @@ struct interface_info {
>
> #define _PATH_DHCLIENT_CONF "/etc/dhclient.conf"
> #define _PATH_LEASE_DB "/var/db/dhclient.leases"
> +#define _PATH_RESOLV_CONF "/etc/resolv.conf"
> +#define _PATH_RESOLV_CONF_TAIL "/etc/resolv.conf.tail"
>
> /* options.c */
> int pack_options(unsigned char *, int,
> Index: kroute.c
> ===================================================================
> RCS file: /cvs/src/sbin/dhclient/kroute.c,v
> retrieving revision 1.164
> diff -u -p -u -r1.164 kroute.c
> --- kroute.c 30 Jun 2019 19:19:08 -0000 1.164
> +++ kroute.c 10 Jul 2019 14:36:31 -0000
> @@ -655,31 +655,31 @@ char *
> resolv_conf_tail(void)
> {
> struct stat sb;
> - const char *tail_path = "/etc/resolv.conf.tail";
> char *tailcontents = NULL;
> ssize_t tailn;
> int tailfd;
>
> - tailfd = open(tail_path, O_RDONLY);
> + tailfd = open(_PATH_RESOLV_CONF_TAIL, O_RDONLY);
> if (tailfd == -1) {
> if (errno != ENOENT)
> - log_warn("%s: open(%s)", log_procname, tail_path);
> + log_warn("%s: open(%s)", log_procname,
> + _PATH_RESOLV_CONF_TAIL);
> } else if (fstat(tailfd, &sb) == -1) {
> - log_warn("%s: fstat(%s)", log_procname, tail_path);
> + log_warn("%s: fstat(%s)", log_procname, _PATH_RESOLV_CONF_TAIL);
> } else if (sb.st_size > 0 && sb.st_size < LLONG_MAX) {
> tailcontents = calloc(1, sb.st_size + 1);
> if (tailcontents == NULL)
> - fatal("%s contents", tail_path);
> + fatal("%s contents", _PATH_RESOLV_CONF_TAIL);
> tailn = read(tailfd, tailcontents, sb.st_size);
> if (tailn == -1)
> log_warn("%s: read(%s)", log_procname,
> - tail_path);
> + _PATH_RESOLV_CONF_TAIL);
> else if (tailn == 0)
> log_warnx("%s: got no data from %s",
> - log_procname,tail_path);
> + log_procname, _PATH_RESOLV_CONF_TAIL);
> else if (tailn != sb.st_size)
> log_warnx("%s: short read of %s",
> - log_procname, tail_path);
> + log_procname, _PATH_RESOLV_CONF_TAIL);
> else {
> close(tailfd);
> return tailcontents;
> @@ -861,7 +861,6 @@ void
> priv_write_resolv_conf(int index, int routefd, int rdomain, char *contents,
> int *lastidx)
> {
> - const char *path = "/etc/resolv.conf";
> ssize_t n;
> size_t sz;
> int fd, retries, newidx;
> @@ -878,21 +877,21 @@ priv_write_resolv_conf(int index, int ro
> return;
> *lastidx = newidx;
>
> - fd = open(path, O_WRONLY | O_CREAT | O_TRUNC,
> + fd = open(_PATH_RESOLV_CONF, O_WRONLY | O_CREAT | O_TRUNC,
> S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH);
>
> if (fd == -1) {
> - log_warn("%s: open(%s)", log_procname, path);
> + log_warn("%s: open(%s)", log_procname, _PATH_RESOLV_CONF);
> return;
> }
>
> sz = strlen(contents);
> n = write(fd, contents, sz);
> if (n == -1)
> - log_warn("%s: write(%s)", log_procname, path);
> + log_warn("%s: write(%s)", log_procname, _PATH_RESOLV_CONF);
> else if ((size_t)n < sz)
> log_warnx("%s: write(%s): %zd of %zu bytes", log_procname,
> - path, n, sz);
> + _PATH_RESOLV_CONF, n, sz);
>
> close(fd);
> }
>
This looks good to me.
ok brynet@