Index: src/common/uid.c =================================================================== --- src/common/uid.c (revision 17072) +++ src/common/uid.c (revision 17170) @@ -111,6 +111,24 @@ } gid_t +gid_from_uid (uid_t uid) +{ + struct passwd pwd, *result; + char buffer[PW_BUF_SIZE]; + gid_t gid; + int rc; + + rc = getpwuid_r(uid, &pwd, buffer, PW_BUF_SIZE, &result); + if (result == NULL) { + gid = (gid_t) -1; + } else { + gid = result->pw_gid; + } + + return gid; +} + +gid_t gid_from_string (char *name) { struct group grp, *result; Index: src/common/uid.h =================================================================== --- src/common/uid.h (revision 17072) +++ src/common/uid.h (revision 17170) @@ -60,6 +60,12 @@ uid_t uid_from_string (char *name); /* + * Return the primary group id for a given user id, or + * (gid_t) -1 on failure. + */ +gid_t gid_from_uid (uid_t uid); + +/* * Same as uid_from_name(), but for group name/id. */ gid_t gid_from_string (char *name); Index: src/slurmd/slurmd/slurmd.c =================================================================== --- src/slurmd/slurmd/slurmd.c (revision 17072) +++ src/slurmd/slurmd/slurmd.c (revision 17170) @@ -160,6 +160,18 @@ (void) close(i); /* + * Drop supplementary groups. + */ + if (geteuid() == 0) { + if (setgroups(0, NULL) != 0) { + fatal("Failed to drop supplementary groups, " + "setgroups: %m"); + } + } else { + info("Not running as root. Can't drop supplementary groups"); + } + + /* * Create and set default values for the slurmd global * config variable "conf" */ Index: src/slurmd/slurmd/req.c =================================================================== --- src/slurmd/slurmd/req.c (revision 17072) +++ src/slurmd/slurmd/req.c (revision 17170) @@ -108,6 +108,7 @@ static void _job_limits_free(void *x); static int _job_limits_match(void *x, void *key); static bool _job_still_running(uint32_t job_id); +static int _init_groups(uid_t my_uid, gid_t my_gid); static int _kill_all_active_steps(uint32_t jobid, int sig, bool batch); static int _terminate_all_steps(uint32_t jobid, bool batch); static void _rpc_launch_tasks(slurm_msg_t *); @@ -1836,12 +1837,34 @@ } static int +_init_groups(uid_t my_uid, gid_t my_gid) +{ + char *user_name = uid_to_string(my_uid); + int rc; + + if (user_name == NULL) { + error("sbcast: Could not find uid %ld", (long)my_uid); + return -1; + } + + rc = initgroups(user_name, my_gid); + xfree(user_name); + if (rc) { + error("sbcast: Error in initgroups(%s, %ld): %m", + user_name, (long)my_gid); + return -1; + } + return 0; + +} + +static int _rpc_file_bcast(slurm_msg_t *msg) { file_bcast_msg_t *req = msg->data; int fd, flags, offset, inx, rc; uid_t req_uid = g_slurm_auth_get_uid(msg->auth_cred, NULL); - uid_t req_gid = g_slurm_auth_get_gid(msg->auth_cred, NULL); + gid_t req_gid = g_slurm_auth_get_gid(msg->auth_cred, NULL); pid_t child; #if 0 @@ -1867,6 +1890,10 @@ /* The child actually performs the I/O and exits with * a return code, do not return! */ + if (_init_groups(req_uid, req_gid) < 0) { + error("sbcast: initgroups(%u): %m", req_uid); + exit(errno); + } if (setgid(req_gid) < 0) { error("sbcast: uid:%u setgid(%u): %s", req_uid, req_gid, strerror(errno)); Index: src/slurmctld/controller.c =================================================================== --- src/slurmctld/controller.c (revision 17072) +++ src/slurmctld/controller.c (revision 17170) @@ -202,6 +202,7 @@ WRITE_LOCK, WRITE_LOCK, WRITE_LOCK, WRITE_LOCK }; assoc_init_args_t assoc_init_arg; pthread_t assoc_cache_thread; + gid_t slurm_user_gid; /* * Establish initial configuration @@ -224,19 +225,41 @@ */ _init_pidfile(); - /* Initialize supplementary group ID list for SlurmUser */ - if ((getuid() == 0) - && (slurmctld_conf.slurm_user_id != getuid()) - && initgroups(slurmctld_conf.slurm_user_name, - gid_from_string(slurmctld_conf.slurm_user_name))) { - error("initgroups: %m"); + /* Determine SlurmUser gid */ + slurm_user_gid = gid_from_uid(slurmctld_conf.slurm_user_id); + if (slurm_user_gid == (gid_t) -1) { + fatal("Failed to determine gid of SlurmUser(%d)", + slurm_user_gid); } - if ((slurmctld_conf.slurm_user_id != getuid()) - && (setuid(slurmctld_conf.slurm_user_id))) { + /* Initialize supplementary groups ID list for SlurmUser */ + if (getuid() == 0) { + /* root does not need supplementary groups */ + if ((slurmctld_conf.slurm_user_id == 0) && + (setgroups(0, NULL) != 0)) { + fatal("Failed to drop supplementary groups, " + "setgroups: %m"); + } else if ((slurmctld_conf.slurm_user_id != getuid()) && + initgroups(slurmctld_conf.slurm_user_name, + slurm_user_gid)) { + fatal("Failed to set supplementary groups, " + "initgroups: %m"); + } + } + + /* Set GID to GID of SlurmUser */ + if ((slurm_user_gid != getegid()) && + (setgid(slurm_user_gid))) { + fatal("Failed to set GID to %d", slurm_user_gid); + } + + /* Set UID to UID of SlurmUser */ + if ((slurmctld_conf.slurm_user_id != getuid()) && + (setuid(slurmctld_conf.slurm_user_id))) { fatal("Can not set uid to SlurmUser(%d): %m", - slurmctld_conf.slurm_user_id); + slurmctld_conf.slurm_user_id); } + if (stat(slurmctld_conf.mail_prog, &stat_buf) != 0) error("Configured MailProg is invalid"); Index: src/slurmctld/trigger_mgr.c =================================================================== --- src/slurmctld/trigger_mgr.c (revision 17072) +++ src/slurmctld/trigger_mgr.c (revision 17170) @@ -985,9 +985,18 @@ setpgrp(); #endif setsid(); - setuid(uid); - setgid(gid); - initgroups(user_name, -1); + if (initgroups(user_name, gid) == -1) { + error("trigger: initgroups: %m"); + exit(1); + } + if (setgid(gid) == -1) { + error("trigger: setgid: %m"); + exit(1); + } + if (setuid(uid) == -1) { + error("trigger: setuid: %m"); + exit(1); + } execl(program, arg0, arg1, NULL); exit(1); } else