]> granicus.if.org Git - cronie/commitdiff
Set only groups in the process handling PAM calls. Keep uids at 0
authorTomas Mraz <tmraz@fedoraproject.org>
Mon, 7 Mar 2011 13:27:46 +0000 (14:27 +0100)
committerTomas Mraz <tmraz@fedoraproject.org>
Mon, 7 Mar 2011 13:27:46 +0000 (14:27 +0100)
so the process is not killable by the user.

src/do_command.c
src/funcs.h
src/popen.c
src/security.c

index 1a80f48c689e2578fc19f8a9e13526d2f4c232cd..e664d4c41b1331725dd6110faed7dd7f401b5d4d 100644 (file)
@@ -166,9 +166,6 @@ static int child_process(entry * e, user * u, char **jobenv) {
        case 0:
                Debug(DPROC, ("[%ld] grandchild process fork()'ed\n", (long) getpid()))
 
-               if (cron_change_user_permanently(e->pwd, env_get("HOME", jobenv)) < 0)
-                       _exit(ERROR_EXIT);
-               
                /* write a log message.  we've waited this long to do it
                 * because it was not until now that we knew the PID that
                 * the actual user command shell was going to get and the
@@ -181,9 +178,8 @@ static int child_process(entry * e, user * u, char **jobenv) {
                        free(x);
                }
 
-               /* that's the last thing we'll log.  close the log files.
-                */
-               log_close();
+               if (cron_change_user_permanently(e->pwd, env_get("HOME", jobenv)) < 0)
+                       _exit(ERROR_EXIT);
 
                /* get new pgrp, void tty, etc.
                 */
@@ -414,12 +410,11 @@ static int child_process(entry * e, user * u, char **jobenv) {
                                gethostname(hostname, MAXHOSTNAMELEN);
 
                                if (MailCmd[0] == '\0') {
-                                       if (strlens(MAILFMT, MAILARG, mailfrom, NULL) + 1
+                                       if (snprintf(mailcmd, sizeof mailcmd, MAILFMT, MAILARG, mailfrom)
                                                >= sizeof mailcmd) {
                                                fprintf(stderr, "mailcmd too long\n");
                                                (void) _exit(ERROR_EXIT);
                                        }
-                                       (void) sprintf(mailcmd, MAILFMT, MAILARG, mailfrom);
                                }
                                else {
                                        strncpy(mailcmd, MailCmd, MAX_COMMAND);
index fabd0b27a28f49bcb9f413d549ab9facc1b67362..f0e576e82dd9bcde4aa843ed96cfa097eedcb35e 100644 (file)
@@ -93,7 +93,7 @@ int cron_open_security_session( struct passwd *pw );
 
 void cron_close_security_session( void );
 
-int cron_change_user( struct passwd *pw );
+int cron_change_groups( struct passwd *pw );
 
 int cron_change_user_permanently( struct passwd *pw, char *homedir );
 
index 48afbb274e29bd667a1442259c9bf2c93a27517a..baf0724d752cfcacef254179f3c6f0adb3d79b21 100644 (file)
@@ -108,6 +108,9 @@ FILE *cron_popen(char *program, const char *type, struct passwd *pw) {
                sa.sa_handler = SIG_DFL;
                sigaction(SIGPIPE, &sa, NULL);
 
+               if (cron_change_user_permanently(pw, pw->pw_dir) != 0)
+                       _exit(2);
+
                if (execvp(argv[0], argv) < 0) {
                        int save_errno = errno;
 
index 6f6ff39a988eb643263e179287ad953485f1b357..581620524380fd8fd2ddabaac351864448ba2bee 100644 (file)
@@ -142,13 +142,10 @@ int cron_set_job_security_context(entry * e, user * u, char ***jobenv) {
        }
 #endif
 
-       if (cron_change_user(e->pwd) != 0) {
-               log_it(e->pwd->pw_name, getpid(), "ERROR", "failed to change user", 0);
+       if (cron_change_groups(e->pwd) != 0) {
                return -1;
        }
 
-       log_close();
-
        time_t job_run_time = time(0L);
 
        if ((minutely_time > 0) && ((job_run_time / 60) != (minutely_time / 60))) {
@@ -211,11 +208,9 @@ void cron_close_pam(void) {
 #endif
 }
 
-int cron_change_user(struct passwd *pw) {
+int cron_change_groups(struct passwd *pw) {
        pid_t pid = getpid();
-       /* set our directory, uid and gid.  Set gid first, since once
-        * we set uid, we've lost root privledges.
-        */
+
        if (setgid(pw->pw_gid) != 0) {
                log_it("CRON", pid, "ERROR", "setgid failed", errno);
                return -1;
@@ -226,10 +221,11 @@ int cron_change_user(struct passwd *pw) {
                return -1;
        }
 
-       if (setreuid(pw->pw_uid, -1) != 0) {
-               log_it("CRON", pid, "ERROR", "setreuid failed", errno);
-               return -1;
-       }
+#if defined(WITH_PAM)
+       /* credentials may take form of supplementary groups so reinitialize
+        * them here */
+       pam_setcred(pamh, PAM_REINITIALIZE_CRED | PAM_SILENT);
+#endif
 
        return 0;
 }
@@ -239,11 +235,14 @@ int cron_change_user_permanently(struct passwd *pw, char *homedir) {
                log_it("CRON", getpid(), "ERROR", "setreuid failed", errno);
                return -1;
        }
+
        if (chdir(homedir) == -1) {
                log_it("CRON", getpid(), "ERROR chdir failed", homedir, errno);
                return -1;
        }
 
+       log_close();
+
        return 0;
 }