2 * Copyright 2000, International Business Machines Corporation and others.
5 * This software has been released under the terms of the IBM Public
6 * License. For details, see the LICENSE file in the top-level source
7 * directory or online at http://www.openafs.org/dl/license10.html
11 * Revision 2.3 91/08/09 18:10:56
12 * added a new param to afsconf_SuperUser
14 * Revision 2.2 90/08/29 15:10:43
16 * Reject security index #1: rxvab/bcrypt.
18 * Revision 2.1 90/08/07 18:52:21
19 * Start with clean version to sync test and dev trees.
22 #include <afs/param.h>
24 #include <afs/pthread_glock.h>
25 #include <sys/types.h>
32 #include <netinet/in.h>
36 #include <stdlib.h> /* for realpath() */
42 #include <afs/afsutil.h>
43 #include <afs/fileutil.h>
45 #ifdef AFS_ATHENA_STDENV
50 #include "cellconfig.h"
52 #include "afs/audit.h"
55 static GetNoAuthFlag(adir)
56 struct afsconf_dir *adir; {
57 if (access(AFSDIR_SERVER_NOAUTH_FILEPATH, 0) == 0) {
58 osi_audit ( NoAuthEvent, 0, AUD_END ); /* some random server is running noauth */
59 return 1; /* if /usr/afs/local/NoAuth file exists, allow access */
65 afsconf_GetNoAuthFlag(adir)
66 struct afsconf_dir *adir; {
70 rc = GetNoAuthFlag(adir);
75 afsconf_SetNoAuthFlag(adir, aflag)
76 struct afsconf_dir *adir;
78 register afs_int32 code;
83 /* turn off noauth flag */
84 code = ( unlink(AFSDIR_SERVER_NOAUTH_FILEPATH) ? errno : 0 );
85 osi_audit ( NoAuthDisableEvent, code, AUD_END );
88 /* try to create file */
89 code = open(AFSDIR_SERVER_NOAUTH_FILEPATH, O_CREAT | O_TRUNC | O_RDWR, 0666);
92 osi_audit ( NoAuthEnableEvent, 0, AUD_END );
95 osi_audit ( NoAuthEnableEvent, errno, AUD_END );
100 /* deletes a user from the UserList file */
101 afsconf_DeleteUser(adir, auser)
102 struct afsconf_dir *adir;
103 register char *auser; {
113 register afs_int32 code;
116 strcompose(tbuffer, sizeof tbuffer, adir->name, "/", AFSDIR_ULIST_FILE, NULL);
120 * We attempt to fully resolve this pathname, so that the rename
121 * of the temporary file will work even if UserList is a symlink
122 * into a different filesystem.
124 char resolved_path[1024];
126 if (realpath(tbuffer, resolved_path)) {
127 strcpy(tbuffer, resolved_path);
130 #endif /* AFS_NT40_ENV */
131 tf = fopen(tbuffer, "r");
136 code = stat(tbuffer, &tstat);
141 strcpy(nbuffer, tbuffer);
142 strcat(nbuffer, ".NXX");
143 nf = fopen(nbuffer, "w+");
152 /* check for our user id */
153 tp = fgets(nbuffer, sizeof(nbuffer), tf);
154 if (tp == (char *)0) break;
155 code = sscanf(nbuffer, "%64s", tname);
156 if (code == 1 && strcmp(tname, auser) == 0) {
157 /* found the guy, don't copy to output file */
161 /* otherwise copy original line to output */
162 fprintf(nf, "%s", nbuffer);
166 if (ferror(nf)) flag = 1;
167 if (fclose(nf) == EOF) flag = 1;
168 strcpy(nbuffer, tbuffer);
169 strcat(nbuffer, ".NXX"); /* generate new file name again */
172 flag = renamefile(nbuffer, tbuffer);
174 flag = chmod(tbuffer, tstat.st_mode);
176 else unlink(nbuffer);
178 /* finally, decide what to return to the caller */
180 if (flag) return EIO; /* something mysterious went wrong */
181 if (!found) return ENOENT; /* entry wasn't found, no changes made */
182 return 0; /* everything was fine */
185 /* returns nth super user from the UserList file */
186 afsconf_GetNthUser(adir, an, abuffer, abufferLen)
187 struct afsconf_dir *adir;
190 afs_int32 abufferLen; {
196 register afs_int32 code;
199 strcompose(tbuffer, sizeof tbuffer, adir->name, "/", AFSDIR_ULIST_FILE, NULL);
200 tf = fopen(tbuffer, "r");
207 /* check for our user id */
208 tp = fgets(tbuffer, sizeof(tbuffer), tf);
209 if (tp == (char *)0) break;
210 code = sscanf(tbuffer, "%64s", tname);
211 if (code == 1 && an-- == 0) {
216 if (flag == 0) strcpy(abuffer, tname);
222 /* returns true iff user is in the UserList file */
223 static FindUser(adir, auser)
224 struct afsconf_dir *adir;
225 register char *auser; {
231 register afs_int32 code;
234 strcompose(tbuffer, sizeof tbuffer, adir->name, "/", AFSDIR_ULIST_FILE, NULL);
235 bp = BufioOpen(tbuffer, O_RDONLY, 0);
239 /* check for our user id */
240 rc = BufioGets(bp, tbuffer, sizeof(tbuffer));
242 code = sscanf(tbuffer, "%64s", tname);
243 if (code == 1 && strcmp(tname, auser) == 0) {
252 /* add a user to the user list, checking for duplicates */
253 afsconf_AddUser(adir, aname)
254 struct afsconf_dir *adir;
257 register afs_int32 code;
261 if (FindUser(adir, aname)) {
263 return EEXIST; /* already in the list */
266 strcompose(tbuffer, sizeof tbuffer, adir->name, "/", AFSDIR_ULIST_FILE, NULL);
267 tf = fopen(tbuffer, "a+");
272 fprintf(tf, "%s\n", aname);
274 if (ferror(tf)) code = EIO;
275 if (fclose(tf)) code = EIO;
280 /* make sure user authenticated on rx call acall is in list of valid
283 afsconf_SuperUser(adir, acall, namep)
284 struct afsconf_dir *adir;
285 struct rx_call *acall;
287 register struct rx_connection *tconn;
288 register afs_int32 code;
296 if (afsconf_GetNoAuthFlag(adir)) {
297 if (namep) strcpy(namep, "<noauth>");
301 tconn = rx_ConnectionOf(acall);
302 code = rx_SecurityClassOf(tconn);
305 return 0; /* not authenticated at all, answer is no */
307 else if (code == 1) {
310 return 0; /* not supported any longer */
312 else if (code == 2) {
313 char tname[MAXKTCNAMELEN]; /* authentication from ticket */
314 char tinst[MAXKTCNAMELEN];
315 char tcell[MAXKTCREALMLEN];
316 char uname[MAXKTCNAMELEN]; /* name.instance */
317 int ilen; /* length of instance */
319 static char localcellname[MAXCELLCHARS] = "";
320 #if defined(AFS_ATHENA_STDENV) || defined(AFS_KERBREALM_ENV)
321 static char local_realm[AFS_REALM_SZ] = "";
325 code = rxkad_GetServerInfo
326 (acall->conn, (afs_int32 *) 0, &exp, tname, tinst, tcell, (afs_int32 *) 0);
329 return 0; /* bogus */
332 if (strlen (tcell)) {
333 if (!localcellname[0])
335 (adir, localcellname, sizeof(localcellname));
336 #if defined(AFS_ATHENA_STDENV) || defined(AFS_KERBREALM_ENV)
337 if (!local_realm[0]) {
338 if (afs_krb_get_lrealm(local_realm, 0) != 0/*KSUCCESS*/)
339 strncpy(local_realm, localcellname, AFS_REALM_SZ);
341 if (strcasecmp(local_realm, tcell) &&
342 (strcasecmp(localcellname, tcell)))
344 if (strcasecmp(localcellname, tcell))
351 ilen = strlen(tinst);
352 strncpy (uname, tname, sizeof(uname));
354 if (strlen(uname) + 1 + ilen >= sizeof(uname)) {
359 strcat (uname, tinst);
362 #ifdef AFS_PTHREAD_ENV
363 if (exp < clock_Sec()) {
365 if (exp < FT_ApproxTime()) {
368 return 0; /* expired tix */
370 if (strcmp(AUTH_SUPERUSER, uname) == 0) flag = 1;
371 else flag = FindUser(adir, uname); /* true iff in userlist file */
373 strcpy(namep, uname);
379 return 0; /* mysterious, just say no */