On Sun, 15 Nov 2015 09:41:38 -0700, "Todd C. Miller" wrote:

> This cleans up the remaining uses of stderr and perror() and uses
> warn/err and/or syslog depending on whether stderr is hooked up at
> the time.  Also removes closelog() which is not needed since we are
> headed for exec.

Here's the diff -uw version for easier reading.

 - todd

Index: usr.sbin/cron/atrun.c
===================================================================
RCS file: /cvs/src/usr.sbin/cron/atrun.c,v
retrieving revision 1.40
diff -u -p -u -w -r1.40 atrun.c
--- usr.sbin/cron/atrun.c       14 Nov 2015 13:09:14 -0000      1.40
+++ usr.sbin/cron/atrun.c       15 Nov 2015 21:24:59 -0000
@@ -29,6 +29,7 @@
 #include <bsd_auth.h>
 #include <ctype.h>
 #include <dirent.h>
+#include <err.h>
 #include <errno.h>
 #include <fcntl.h>
 #include <limits.h>
@@ -226,6 +227,8 @@ run_job(atjob *job, char *atfile)
 {
        struct stat sb;
        struct passwd *pw;
+       login_cap_t *lc;
+       auth_session_t *as;
        pid_t pid;
        long nuid, ngid;
        FILE *fp;
@@ -388,12 +391,9 @@ run_job(atjob *job, char *atfile)
                /* Write log message now that we have our real pid. */
                syslog(LOG_INFO, "(%s) ATJOB (%s)", pw->pw_name, atfile);
 
-               /* Close syslog file */
-               closelog();
-
                /* Connect grandchild's stdin to the at job file. */
                if (lseek(fd, 0, SEEK_SET) < 0) {
-                       perror("lseek");
+                       syslog(LOG_ERR, "(CRON) LSEEK (%m)");
                        _exit(EXIT_FAILURE);
                }
                if (fd != STDIN_FILENO) {
@@ -411,41 +411,50 @@ run_job(atjob *job, char *atfile)
 
                (void) setsid();
 
-               {
-                       login_cap_t *lc;
-                       auth_session_t *as;
+               /*
+                * From this point on, anything written to stderr will be
+                * mailed to the user as output.
+                */
+
+               /* Setup execution environment as per login.conf */
                        if ((lc = login_getclass(pw->pw_class)) == NULL) {
-                               fprintf(stderr,
-                                   "Cannot get login class for %s\n",
+                       warnx("unable to get login class for %s",
+                           pw->pw_name);
+                       syslog(LOG_ERR, "(CRON) CAN'T GET LOGIN CLASS (%s)",
                                    pw->pw_name);
                                _exit(EXIT_FAILURE);
 
                        }
-
                        if (setusercontext(lc, pw, pw->pw_uid, LOGIN_SETALL)) {
-                               fprintf(stderr,
-                                   "setusercontext failed for %s\n",
+                       warn("setusercontext failed for %s", pw->pw_name);
+                       syslog(LOG_ERR, "(%s) SETUSERCONTEXT FAILED (%m)",
                                    pw->pw_name);
                                _exit(EXIT_FAILURE);
                        }
+
+               /* Run any approval scripts. */
                        as = auth_open();
                        if (as == NULL || auth_setpwd(as, pw) != 0) {
-                               fprintf(stderr, "can't malloc\n");
+                       warn("auth_setpwd");
+                       syslog(LOG_ERR, "(%s) AUTH_SETPWD FAILED (%m)",
+                           pw->pw_name);
                                _exit(EXIT_FAILURE);
                        }
                        if (auth_approval(as, lc, pw->pw_name, "cron") <= 0) {
-                               fprintf(stderr, "approval failed for %s\n",
-                                   pw->pw_name);
+                       warnx("approval failed for %s", pw->pw_name);
+                       syslog(LOG_ERR, "(%s) APPROVAL FAILED (%s)",
+                           pw->pw_name, pw->pw_name);
                                _exit(EXIT_FAILURE);
                        }
                        auth_close(as);
                        login_close(lc);
-               }
 
                /* If this is a low priority job, nice ourself. */
-               if (job->queue > 'b')
-                       (void)setpriority(PRIO_PROCESS, 0, job->queue - 'b');
-
+               if (job->queue > 'b') {
+                       if (setpriority(PRIO_PROCESS, 0, job->queue - 'b') != 0)
+                               syslog(LOG_ERR, "(%s) CAN'T NICE (%m)",
+                                   pw->pw_name);
+               }
 
                (void) signal(SIGPIPE, SIG_DFL);
 
@@ -458,7 +467,9 @@ run_job(atjob *job, char *atfile)
                nargv[1] = NULL;
                nenvp[0] = NULL;
                if (execve(_PATH_BSHELL, nargv, nenvp) != 0) {
-                       perror("execve: " _PATH_BSHELL);
+                       warn("unable to execute %s", _PATH_BSHELL);
+                       syslog(LOG_ERR, "(%s) CAN'T EXEC (%s: %m)", pw->pw_name,
+                           _PATH_BSHELL);
                        _exit(EXIT_FAILURE);
                }
                break;
@@ -473,7 +484,7 @@ run_job(atjob *job, char *atfile)
 
        /* Read piped output (if any) from the at job. */
        if ((fp = fdopen(output_pipe[READ_PIPE], "r")) == NULL) {
-               perror("fdopen");
+               syslog(LOG_ERR, "(%s) FDOPEN (%m)", pw->pw_name);
                (void) _exit(EXIT_FAILURE);
        }
        nread = fread(buf, 1, sizeof(buf), fp);
@@ -489,11 +500,12 @@ run_job(atjob *job, char *atfile)
                        strlcpy(hostname, "unknown", sizeof(hostname));
                if (snprintf(mailcmd, sizeof mailcmd, MAILFMT,
                    MAILARG) >= sizeof mailcmd) {
-                       fprintf(stderr, "mailcmd too long\n");
+                       syslog(LOG_ERR, "(%s) ERROR (mailcmd too long)",
+                           pw->pw_name);
                        (void) _exit(EXIT_FAILURE);
                }
                if (!(mail = cron_popen(mailcmd, "w", pw, &mailpid))) {
-                       perror(mailcmd);
+                       syslog(LOG_ERR, "(%s) POPEN (%s)", pw->pw_name, 
mailcmd);
                        (void) _exit(EXIT_FAILURE);
                }
                fprintf(mail, "From: %s (Atrun Service)\n", pw->pw_name);
Index: usr.sbin/cron/cron.c
===================================================================
RCS file: /cvs/src/usr.sbin/cron/cron.c,v
retrieving revision 1.72
diff -u -p -u -w -r1.72 cron.c
--- usr.sbin/cron/cron.c        14 Nov 2015 13:11:32 -0000      1.72
+++ usr.sbin/cron/cron.c        15 Nov 2015 21:24:59 -0000
@@ -24,6 +24,7 @@
 #include <sys/wait.h>
 
 #include <bitstring.h>
+#include <err.h>
 #include <errno.h>
 #include <grp.h>
 #include <locale.h>
@@ -100,6 +101,7 @@ main(int argc, char *argv[])
 
        if (pledge("stdio rpath wpath cpath fattr getpw unix id dns proc exec",
            NULL) == -1) {
+               warn("pledge");
                syslog(LOG_ERR, "(CRON) PLEDGE (%m)");
                exit(EXIT_FAILURE);
        }
@@ -107,6 +109,7 @@ main(int argc, char *argv[])
        cronSock = open_socket();
 
        if (putenv("PATH="_PATH_DEFPATH) < 0) {
+               warn("putenv");
                syslog(LOG_ERR, "(CRON) DEATH (%m)");
                exit(EXIT_FAILURE);
        }
@@ -424,22 +427,21 @@ open_socket(void)
 
        sock = socket(AF_UNIX, SOCK_STREAM|SOCK_CLOEXEC|SOCK_NONBLOCK, 0);
        if (sock == -1) {
-               fprintf(stderr, "%s: can't create socket: %s\n",
-                   __progname, strerror(errno));
+               warn("socket");
                syslog(LOG_ERR, "(CRON) DEATH (can't create socket)");
                exit(EXIT_FAILURE);
        }
        bzero(&s_un, sizeof(s_un));
        if (strlcpy(s_un.sun_path, _PATH_CRON_SOCK, sizeof(s_un.sun_path))
            >= sizeof(s_un.sun_path)) {
-               fprintf(stderr, "%s: path too long\n", _PATH_CRON_SOCK);
+               warnc(ENAMETOOLONG, _PATH_CRON_SOCK);
                syslog(LOG_ERR, "(CRON) DEATH (socket path too long)");
                exit(EXIT_FAILURE);
        }
        s_un.sun_family = AF_UNIX;
 
        if (connect(sock, (struct sockaddr *)&s_un, sizeof(s_un)) == 0) {
-               fprintf(stderr, "%s: already running\n", __progname);
+               warnx("already running");
                syslog(LOG_ERR, "(CRON) DEATH (already running)");
                exit(EXIT_FAILURE);
        }
@@ -450,14 +452,12 @@ open_socket(void)
        rc = bind(sock, (struct sockaddr *)&s_un, sizeof(s_un));
        umask(omask);
        if (rc != 0) {
-               fprintf(stderr, "%s: can't bind socket: %s\n",
-                   __progname, strerror(errno));
+               warn("bind");
                syslog(LOG_ERR, "(CRON) DEATH (can't bind socket)");
                exit(EXIT_FAILURE);
        }
        if (listen(sock, SOMAXCONN)) {
-               fprintf(stderr, "%s: can't listen on socket: %s\n",
-                   __progname, strerror(errno));
+               warn("listen");
                syslog(LOG_ERR, "(CRON) DEATH (can't listen on socket)");
                exit(EXIT_FAILURE);
        }
@@ -513,8 +513,7 @@ parse_args(int argc, char *argv[])
                        batch_maxload = strtod(optarg, &ep);
                        if (*ep != '\0' || ep == optarg || errno == ERANGE ||
                            batch_maxload < 0) {
-                               fprintf(stderr, "Illegal load average: %s\n",
-                                   optarg);
+                               warnx("illegal load average: %s", optarg);
                                usage();
                        }
                        break;
Index: usr.sbin/cron/do_command.c
===================================================================
RCS file: /cvs/src/usr.sbin/cron/do_command.c,v
retrieving revision 1.54
diff -u -p -u -w -r1.54 do_command.c
--- usr.sbin/cron/do_command.c  14 Nov 2015 13:09:14 -0000      1.54
+++ usr.sbin/cron/do_command.c  15 Nov 2015 21:24:59 -0000
@@ -23,6 +23,7 @@
 #include <bitstring.h>         /* for structs.h */
 #include <bsd_auth.h>
 #include <ctype.h>
+#include <err.h>
 #include <errno.h>
 #include <fcntl.h>
 #include <limits.h>
@@ -76,8 +77,11 @@ child_process(entry *e, user *u)
 {
        FILE *in;
        int stdin_pipe[2], stdout_pipe[2];
-       char *input_data, *usernm;
+       char **p, *input_data, *usernm;
+       auth_session_t *as;
+       login_cap_t *lc;
        int children = 0;
+       extern char **environ;
 
        /* mark ourselves as different to PS command watchers */
        setproctitle("running job");
@@ -156,10 +160,6 @@ child_process(entry *e, user *u)
                        }
                }
 
-               /* that's the last thing we'll log.  close the log files.
-                */
-               closelog();
-
                /* get new pgrp, void tty, etc.
                 */
                (void) setsid();
@@ -186,36 +186,36 @@ child_process(entry *e, user *u)
                }
                dup2(STDOUT_FILENO, STDERR_FILENO);
 
-               /* set our directory, uid and gid.  Set gid first, since once
-                * we set uid, we've lost root privileges.
+               /*
+                * From this point on, anything written to stderr will be
+                * mailed to the user as output.
                 */
-               {
-                       auth_session_t *as;
-                       login_cap_t *lc;
-                       char **p;
-                       extern char **environ;
 
                        /* XXX - should just pass in a login_cap_t * */
                        if ((lc = login_getclass(e->pwd->pw_class)) == NULL) {
-                               fprintf(stderr,
-                                   "unable to get login class for %s\n",
+                       warnx("unable to get login class for %s",
+                           e->pwd->pw_name);
+                       syslog(LOG_ERR, "(CRON) CAN'T GET LOGIN CLASS (%s)",
                                    e->pwd->pw_name);
                                _exit(EXIT_FAILURE);
                        }
                        if (setusercontext(lc, e->pwd, e->pwd->pw_uid, 
LOGIN_SETALL) < 0) {
-                               fprintf(stderr,
-                                   "setusercontext failed for %s\n",
+                       warn("setusercontext failed for %s", e->pwd->pw_name);
+                       syslog(LOG_ERR, "(%s) SETUSERCONTEXT FAILED (%m)",
                                    e->pwd->pw_name);
                                _exit(EXIT_FAILURE);
                        }
                        as = auth_open();
                        if (as == NULL || auth_setpwd(as, e->pwd) != 0) {
-                               fprintf(stderr, "can't malloc\n");
+                       warn("auth_setpwd");
+                       syslog(LOG_ERR, "(%s) AUTH_SETPWD FAILED (%m)",
+                           e->pwd->pw_name);
                                _exit(EXIT_FAILURE);
                        }
                        if (auth_approval(as, lc, usernm, "cron") <= 0) {
-                               fprintf(stderr, "approval failed for %s\n",
-                                   e->pwd->pw_name);
+                       warnx("approval failed for %s", e->pwd->pw_name);
+                       syslog(LOG_ERR, "(%s) APPROVAL FAILED (%s)",
+                           e->pwd->pw_name, e->pwd->pw_name);
                                _exit(EXIT_FAILURE);
                        }
                        auth_close(as);
@@ -233,7 +233,6 @@ child_process(entry *e, user *u)
                                        }
                                }
                        }
-               }
                chdir(env_get("HOME", e->envp));
 
                (void) signal(SIGPIPE, SIG_DFL);
@@ -245,8 +244,9 @@ child_process(entry *e, user *u)
                        char    *shell = env_get("SHELL", e->envp);
 
                        execle(shell, shell, "-c", e->cmd, (char *)NULL, 
e->envp);
-                       fprintf(stderr, "execle: couldn't exec `%s'\n", shell);
-                       perror("execle");
+                       warn("unable to execute %s", shell);
+                       syslog(LOG_ERR, "(%s) CAN'T EXEC (%s: %m)",
+                           e->pwd->pw_name, shell);
                        _exit(EXIT_FAILURE);
                }
                break;
@@ -372,12 +372,15 @@ child_process(entry *e, user *u)
                                gethostname(hostname, sizeof(hostname));
                                if (snprintf(mailcmd, sizeof mailcmd,  MAILFMT,
                                    MAILARG) >= sizeof mailcmd) {
-                                       fprintf(stderr, "mailcmd too long\n");
+                                       syslog(LOG_ERR,
+                                           "(%s) ERROR (mailcmd too long)",
+                                           e->pwd->pw_name);
                                        (void) _exit(EXIT_FAILURE);
                                }
                                if (!(mail = cron_popen(mailcmd, "w", e->pwd,
                                    &mailpid))) {
-                                       perror(mailcmd);
+                                       syslog(LOG_ERR, "(%s) POPEN (%s)",
+                                           e->pwd->pw_name, mailcmd);
                                        (void) _exit(EXIT_FAILURE);
                                }
                                fprintf(mail, "From: root (Cron Daemon)\n");
Index: usr.sbin/cron/popen.c
===================================================================
RCS file: /cvs/src/usr.sbin/cron/popen.c,v
retrieving revision 1.29
diff -u -p -u -w -r1.29 popen.c
--- usr.sbin/cron/popen.c       4 Nov 2015 20:28:17 -0000       1.29
+++ usr.sbin/cron/popen.c       15 Nov 2015 21:24:59 -0000
@@ -41,6 +41,7 @@
 #include <sys/wait.h>
 
 #include <bitstring.h>         /* for structs.h */
+#include <err.h>
 #include <errno.h>
 #include <login_cap.h>
 #include <pwd.h>
@@ -48,6 +49,7 @@
 #include <stdio.h>
 #include <stdlib.h>
 #include <string.h>
+#include <syslog.h>
 #include <unistd.h>
 #include <time.h>              /* for structs.h */
 
@@ -91,8 +93,10 @@ cron_popen(char *program, char *type, st
        case 0:                         /* child */
                if (pw) {
                        if (setusercontext(0, pw, pw->pw_uid, LOGIN_SETALL) < 
0) {
-                               fprintf(stderr,
-                                   "setusercontext failed for %s\n",
+                               syslog(LOG_ERR,
+                                   "(%s) SETUSERCONTEXT FAILED (%m)",
+                                   pw->pw_name);
+                               warn("setusercontext failed for %s",
                                    pw->pw_name);
                                _exit(EXIT_FAILURE);
                        }
Index: usr.sbin/cron/user.c
===================================================================
RCS file: /cvs/src/usr.sbin/cron/user.c,v
retrieving revision 1.17
diff -u -p -u -w -r1.17 user.c
--- usr.sbin/cron/user.c        9 Nov 2015 01:12:27 -0000       1.17
+++ usr.sbin/cron/user.c        15 Nov 2015 21:24:59 -0000
@@ -22,9 +22,11 @@
 #include <bitstring.h>         /* for structs.h */
 #include <ctype.h>
 #include <errno.h>
+#include <pwd.h>
 #include <stdio.h>
 #include <stdlib.h>
 #include <string.h>
+#include <syslog.h>
 #include <time.h>              /* for structs.h */
 
 #include "macros.h"
@@ -55,7 +57,7 @@ load_user(int crontab_fd, struct passwd       
        char **envp, **tenvp;
 
        if (!(file = fdopen(crontab_fd, "r"))) {
-               perror("fdopen on crontab_fd in load_user");
+               syslog(LOG_ERR, "(%s) FDOPEN (%m)", pw->pw_name);
                return (NULL);
        }
 

Reply via email to