1 /*****************************************************************************\
2 * src/slurmd/slurmstepd/pam_ses.c - functions to manage pam session
3 *****************************************************************************
4 * Copyright (C) 2006 The Regents of the University of California.
5 * Produced at Lawrence Livermore National Laboratory (cf, DISCLAIMER).
6 * Written by Donna Mecozzi <dmecozzi@llnl.gov>.
7 * CODE-OCEC-09-009. All rights reserved.
8 *
9 * This file is part of Slurm, a resource management program.
10 * For details, see <https://slurm.schedmd.com/>.
11 * Please also read the included file: DISCLAIMER.
12 *
13 * Slurm is free software; you can redistribute it and/or modify it under
14 * the terms of the GNU General Public License as published by the Free
15 * Software Foundation; either version 2 of the License, or (at your option)
16 * any later version.
17 *
18 * In addition, as a special exception, the copyright holders give permission
19 * to link the code of portions of this program with the OpenSSL library under
20 * certain conditions as described in each individual source file, and
21 * distribute linked combinations including the two. You must obey the GNU
22 * General Public License in all respects for all of the code used other than
23 * OpenSSL. If you modify file(s) with this exception, you may extend this
24 * exception to your version of the file(s), but you are not obligated to do
25 * so. If you do not wish to do so, delete this exception statement from your
26 * version. If you delete this exception statement from all source files in
27 * the program, then also delete it here.
28 *
29 * Slurm is distributed in the hope that it will be useful, but WITHOUT ANY
30 * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
31 * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more
32 * details.
33 *
34 * You should have received a copy of the GNU General Public License along
35 * with Slurm; if not, write to the Free Software Foundation, Inc.,
36 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
37 \*****************************************************************************/
38
39 #include "config.h"
40
41 #include "slurm/slurm_errno.h"
42 #include "src/slurmd/slurmstepd/pam_ses.h"
43 #include "src/common/log.h"
44 #include "src/slurmd/slurmd/slurmd.h"
45
46 #ifdef HAVE_PAM
47
48 #ifdef HAVE_PAM_PAM_APPL_H
49 # include <pam/pam_appl.h>
50 # include <pam/pam_misc.h>
51 #else
52 # include <security/pam_appl.h>
53 # include <security/pam_misc.h>
54 #endif
55
56 static pam_handle_t *pam_h = NULL;
57
58 /*
59 * A stack for slurmstepd must be set up in /etc/pam.d
60 */
61 #define SLURM_SERVICE_PAM "slurm"
62
63 /*
64 * As these functions are currently written, PAM initialization (pam_start)
65 * and cleanup (pam_end) are included. If other aspects of PAM are to be used
66 * sometime in the future, these calls should be moved because they should only
67 * be called once.
68 */
69
70 int
pam_setup(char * user,char * host)71 pam_setup (char *user, char *host)
72 {
73 /*
74 * Any application using PAM must provide a conversation function, which
75 * is used for direct communication between a loaded module and the
76 * application. In this case, Slurm does not need a communication mechanism,
77 * so the default (or null) conversation function may be used.
78 */
79 struct pam_conv conv = {misc_conv, NULL};
80 int rc = 0;
81
82 if (!conf->use_pam)
83 return SLURM_SUCCESS;
84 /*
85 * Slurm uses PAM to obtain resource limits established by the system
86 * administrator. PAM's session management library is responsible for
87 * handling resource limits. When a PAM session is opened on behalf of
88 * a user, the limits imposed by the sys admin are picked up. Opening
89 * a PAM session requires a PAM handle, which is obtained when the PAM
90 * interface is initialized. (PAM handles are required with essentially
91 * all PAM calls.) It's also necessary to have the user's PAM credentials
92 * to open a user session.
93 */
94 if ((rc = pam_start (SLURM_SERVICE_PAM, user, &conv, &pam_h))
95 != PAM_SUCCESS) {
96 error ("pam_start: %s", pam_strerror(NULL, rc));
97 goto fail1;
98 } else if ((rc = pam_set_item (pam_h, PAM_USER, user))
99 != PAM_SUCCESS) {
100 error ("pam_set_item USER: %s", pam_strerror(pam_h, rc));
101 goto fail2;
102 } else if ((rc = pam_set_item (pam_h, PAM_RUSER, user))
103 != PAM_SUCCESS) {
104 error ("pam_set_item RUSER: %s", pam_strerror(pam_h, rc));
105 goto fail2;
106 } else if ((rc = pam_set_item (pam_h, PAM_RHOST, host))
107 != PAM_SUCCESS) {
108 error ("pam_set_item HOST: %s", pam_strerror(pam_h, rc));
109 goto fail2;
110 } else if ((rc = pam_setcred (pam_h, PAM_ESTABLISH_CRED))
111 != PAM_SUCCESS) {
112 error ("pam_setcred ESTABLISH: %s", pam_strerror(pam_h, rc));
113 goto fail2;
114 } else if ((rc = pam_open_session (pam_h, 0)) != PAM_SUCCESS) {
115 error("pam_open_session: %s", pam_strerror(pam_h, rc));
116 goto fail3;
117 }
118
119 return SLURM_SUCCESS;
120
121 fail3:
122 pam_setcred (pam_h, PAM_DELETE_CRED);
123
124 fail2:
125 pam_end (pam_h, rc);
126
127 fail1:
128 pam_h = NULL;
129 return SLURM_ERROR;
130 }
131
132
133 void
pam_finish()134 pam_finish ()
135 {
136 int rc = 0;
137
138 /*
139 * Allow PAM to clean up its state by closing the user session and
140 * ending the association with PAM.
141 */
142
143 if (!conf->use_pam)
144 return;
145
146 if (pam_h != NULL) {
147 /*
148 * Log any errors, but there's no need to return a Slurm error.
149 */
150 if ((rc = pam_close_session (pam_h, 0)) != PAM_SUCCESS) {
151 error("pam_close_session: %s", pam_strerror(pam_h, rc));
152 }
153 if ((rc = pam_setcred (pam_h, PAM_DELETE_CRED)) != PAM_SUCCESS){
154 error("pam_setcred DELETE: %s", pam_strerror(pam_h,rc));
155 }
156 if ((rc = pam_end (pam_h, rc)) != PAM_SUCCESS) {
157 error("pam_end: %s", pam_strerror(NULL, rc));
158 }
159 pam_h = NULL;
160 }
161 }
162
163 #else /* HAVE_PAM */
164
pam_setup(char * user,char * host)165 int pam_setup (char *user, char *host)
166 {
167 /* Don't have PAM support, do nothing. */
168 return SLURM_SUCCESS;
169 }
170
pam_finish()171 void pam_finish ()
172 {
173 /* Don't have PAM support, do nothing. */
174 }
175
176 #endif /* HAVE_PAM */
177