]> andersk Git - moira.git/blob - server/mr_sauth.c
put back in backwards compatibility on kerberos principal
[moira.git] / server / mr_sauth.c
1 /*
2  *      $Source$
3  *      $Author$
4  *      $Header$
5  *
6  *      Copyright (C) 1987 by the Massachusetts Institute of Technology
7  *      For copying and distribution information, please see the file
8  *      <mit-copyright.h>.
9  *
10  */
11
12 #ifndef lint
13 static char *rcsid_sms_sauth_c = "$Header$";
14 #endif lint
15
16 #include <mit-copyright.h>
17 #include <strings.h>
18 #include "sms_server.h"
19 #include <ctype.h>
20 #include <krb_et.h>
21
22 extern char buf1[];
23 extern char *whoami;
24 extern char *malloc();
25
26 char *kname_unparse();
27
28 /*
29  * Handle a SMS_AUTH RPC request.
30  *
31  * argv[0] is a kerberos authenticator.  Decompose it, and if
32  * successful, store the name the user authenticated to in 
33  * cl->cl_name.
34  */
35
36 void
37 do_auth(cl)
38         client *cl;
39 {
40         KTEXT_ST auth;
41         AUTH_DAT ad;
42         int status, ok;
43         char buf[REALM_SZ+INST_SZ+ANAME_SZ], hostbuf[BUFSIZ], *host, *p;
44         extern int errno;
45
46         auth.length = cl->args->sms_argl[0];
47         bcopy(cl->args->sms_argv[0], (char *)auth.dat, auth.length);
48         auth.mbz = 0;
49         if (gethostname(hostbuf, sizeof(hostbuf)) < 0)
50           com_err(whoami, errno, "Unable to get local hostname");
51         host = canonicalize_hostname(strsave(hostbuf));
52         for (p = host; *p && *p != '.'; p++)
53           if (isupper(*p))
54             *p = tolower(*p);
55         *p = 0;
56
57         if ((status = krb_rd_req (&auth, MOIRA_SNAME, host, cl->haddr.sin_addr,
58                                  &ad, "")) != 0 &&
59             /* for backwards compatability with old clients */
60             (status = krb_rd_req (&auth, "sms", "sms", cl->haddr.sin_addr,
61                                  &ad, "")) != 0) {
62                 status += ERROR_TABLE_BASE_krb;
63                 cl->reply.sms_status = status;
64                 if (log_flags & LOG_RES)
65                         com_err(whoami, status, "(authentication failed)");
66                 return;
67         }
68         free(host);
69
70         bcopy(ad.pname, cl->kname.name, ANAME_SZ);
71         bcopy(ad.pinst, cl->kname.inst, INST_SZ);
72         bcopy(ad.prealm, cl->kname.realm, REALM_SZ);
73         strcpy(cl->clname, kname_unparse(ad.pname, ad.pinst, ad.prealm));
74
75         if (ad.pinst[0] == 0 && !strcmp(ad.prealm, krb_realm))
76           ok = 1;
77         else
78           ok = 0;
79         /* this is in a separate function because it accesses the database */
80         set_krb_mapping(cl->clname, ad.pname, ok,
81                         &cl->client_id, &cl->users_id);
82
83         if (cl->args->sms_version_no == SMS_VERSION_2) {
84             bcopy(cl->args->sms_argv[1], cl->entity, 8);
85             cl->entity[8] = 0;
86         } else {
87             strcpy(cl->entity, "???");
88         }
89         bzero(&ad, sizeof(ad)); /* Clean up session key, etc. */
90
91         if (log_flags & LOG_RES)
92             com_err(whoami, 0, "Auth to %s using %s, uid %d cid %d",
93                     cl->clname, cl->entity, cl->users_id, cl->client_id);
94         if (cl->users_id == 0)
95           cl->reply.sms_status = SMS_USER_AUTH;
96 }
97
98
99 /* Turn a principal, instance, realm triple into a single non-ambiguous 
100  * string.  This is the inverse of kname_parse().  It returns a pointer
101  * to a static buffer, or NULL on error.
102  */
103
104 char *kname_unparse(p, i, r)
105 char *p;
106 char *i;
107 char *r;
108 {
109     static char name[MAX_K_NAME_SZ];
110     char *s;
111
112     s = name;
113     if (!p || strlen(p) > ANAME_SZ)
114       return(NULL);
115     while (*p) {
116         switch (*p) {
117         case '@':
118             *s++ = '\\';
119             *s++ = '@';
120             break;
121         case '.':
122             *s++ = '\\';
123             *s++ = '.';
124             break;
125         case '\\':
126             *s++ = '\\';
127             *s++ = '\\';
128             break;
129         default:
130             *s++ = *p;
131         }
132         p++;
133     }
134     if (i && *i) {
135         if (strlen(i) > INST_SZ)
136           return(NULL);
137         *s++ = '.';
138         while (*i) {
139             switch (*i) {
140             case '@':
141                 *s++ = '\\';
142                 *s++ = '@';
143                 break;
144             case '.':
145                 *s++ = '\\';
146                 *s++ = '.';
147                 break;
148             case '\\':
149                 *s++ = '\\';
150                 *s++ = '\\';
151                 break;
152             default:
153                 *s++ = *i;
154             }
155             i++;
156         }
157     }
158     *s++ = '@';
159     if (!r || strlen(r) > REALM_SZ)
160       return(NULL);
161     while (*r) {
162         switch (*r) {
163         case '@':
164             *s++ = '\\';
165             *s++ = '@';
166             break;
167         case '\\':
168             *s++ = '\\';
169             *s++ = '\\';
170             break;
171         default:
172             *s++ = *r;
173         }
174         r++;
175     }
176     *s = '\0';
177     return(&name[0]);
178 }
This page took 0.050373 seconds and 5 git commands to generate.