source: trunk/third/moira/reg_svr/kerberos.c @ 25817

Revision 25817, 5.1 KB checked in by jdreed, 11 years ago (diff)
In moira: * Re-snapshot moira at r4097 to pick up Status 10 (Suspended) (Trac: #1295) * Remove our addusr.1 and namespace.1 in favor of upstreams (Trac: #918) * Build-dep on OpenSSL and pass new configure flag per moira r4091
Line 
1/* $Id: kerberos.c 4091 2013-01-18 15:35:41Z zacheiss $
2 *
3 * Kerberos routines for registration server
4 *
5 * Copyright (C) 1998 by the Massachusetts Institute of Technology
6 * For copying and distribution information, please see the file
7 * <mit-copyright.h>.
8 *
9 */
10
11#include <mit-copyright.h>
12#include <moira.h>
13#include "reg_svr.h"
14
15#if !defined(KRB4) && !defined(KRB5)
16#define KRB5
17#endif
18
19#include <errno.h>
20#include <string.h>
21
22#include <com_err.h>
23
24#define KRB5_DEPRECATED 1
25#define KRB5_PRIVATE 1
26
27#ifdef KRB4
28#include <des.h>
29#include <kadm.h>
30#include <kadm_err.h>
31#include <krb.h>
32#endif
33
34#ifdef KRB5
35#include <kadm5/admin.h>
36#include <krb5.h>
37
38krb5_context context;
39#endif
40
41RCSID("$HeadURL: svn+ssh://svn.mit.edu/moira/trunk/moira/reg_svr/kerberos.c $ $Id: kerberos.c 4091 2013-01-18 15:35:41Z zacheiss $");
42
43extern char *hostname, *shorthostname;
44
45#ifdef KRB5
46long init_kerberos(void)
47{
48  krb5_error_code code;
49
50  /* Initialize Kerberos stuff. */
51  code = krb5_init_context(&context);
52  if (code)
53    return code;
54  return 0;
55}
56
57/* Check the kerberos database to see if a principal exists */
58long check_kerberos(char *username)
59{
60  void *kadm_server_handle = NULL;
61  kadm5_ret_t status;
62  krb5_principal princ;
63  kadm5_principal_ent_rec dprinc;
64  kadm5_config_params realm_params;
65  char admin_princ[256];
66#ifdef KERBEROS_TEST_REALM
67  char ubuf[256];
68
69  sprintf(ubuf, "%s@%s", username, KERBEROS_TEST_REALM);
70  username = ubuf;
71#else
72  strcpy(admin_princ, REG_SVR_PRINCIPAL);
73  realm_params.mask = 0;
74#endif
75
76  memset(&princ, 0, sizeof(princ));
77  memset(&dprinc, 0, sizeof(dprinc));
78
79  status = krb5_parse_name(context, username, &princ);
80  if (status)
81    return status;
82
83  status = kadm5_init_with_skey(admin_princ, NULL, KADM5_ADMIN_SERVICE,
84                                &realm_params, KADM5_STRUCT_VERSION,
85                                KADM5_API_VERSION_2, NULL, &kadm_server_handle);
86  if (status)
87    goto cleanup;
88
89  status =  kadm5_get_principal(kadm_server_handle, princ, &dprinc, KADM5_PRINCIPAL_NORMAL_MASK);
90
91 cleanup:
92  krb5_free_principal(context, princ);
93  if (kadm_server_handle)
94    kadm5_destroy(kadm_server_handle);
95
96  if (status == KADM5_OK)
97    return MR_IN_USE;
98  else if (status == KADM5_UNK_PRINC)
99    return MR_SUCCESS;
100  else
101    return MR_INTERNAL;
102}
103
104/* Create a new principal in Kerberos */
105long register_kerberos(char *username, char *password)
106{
107  void *kadm_server_handle = NULL;
108  kadm5_ret_t status;
109  kadm5_principal_ent_rec princ;
110  kadm5_policy_ent_rec defpol;
111  kadm5_config_params realm_params;
112  char admin_princ[256];
113  long mask = 0;
114#ifdef KERBEROS_TEST_REALM
115  char ubuf[256];
116
117  sprintf(admin_princ, "moira/%s@%s", hostname, KERBEROS_TEST_REALM);
118  sprintf(ubuf, "%s@%s", username, KERBEROS_TEST_REALM);
119  username = ubuf;
120  realm_params.realm = KERBEROS_TEST_REALM;
121  realm_params.mask = KADM5_CONFIG_REALM;
122#else
123  strcpy(admin_princ, REG_SVR_PRINCIPAL);
124  realm_params.mask = 0;
125#endif
126
127  memset(&princ, 0, sizeof(princ));
128
129  status = krb5_parse_name(context, username, &(princ.principal));
130  if (status)
131    return status;
132
133
134  status = kadm5_init_with_skey(admin_princ, NULL, KADM5_ADMIN_SERVICE,
135                                &realm_params, KADM5_STRUCT_VERSION,
136                                KADM5_API_VERSION_2, NULL, &kadm_server_handle);
137  if (status)
138    goto cleanup;
139
140  /* Assign "default" policy if it exists. */
141  if (!kadm5_get_policy(kadm_server_handle, "default", &defpol))
142    {
143      princ.policy = "default";
144      mask |= KADM5_POLICY;
145      (void) kadm5_free_policy_ent(kadm_server_handle, &defpol);
146    }
147
148  mask |= KADM5_PRINCIPAL | KADM5_ATTRIBUTES;
149  princ.attributes |= KRB5_KDB_REQUIRES_PRE_AUTH | KRB5_KDB_DISALLOW_SVR;
150  status = kadm5_create_principal(kadm_server_handle, &princ, mask, password);
151
152cleanup:
153  krb5_free_principal(context, princ.principal);
154  if (kadm_server_handle)
155    kadm5_destroy(kadm_server_handle);
156
157  if (status == KADM5_DUP)
158    return MR_IN_USE;
159  else if (status == KADM5_PASS_Q_TOOSHORT ||
160           status == KADM5_PASS_Q_CLASS ||
161           status == KADM5_PASS_Q_DICT)
162    return MR_QUALITY;
163  else return status;
164}
165#endif
166
167#ifdef KRB4
168char realm[REALM_SZ];
169
170long init_kerberos(void)
171{
172  return krb_get_lrealm(realm, 1);
173}
174
175long check_kerberos(char *username)
176{
177  long status;
178
179  status = krb_get_pw_in_tkt(username, "", realm, "krbtgt", realm, 1, "");
180  if (status == KDC_PR_UNKNOWN)
181    return MR_SUCCESS;
182  else
183    return MR_IN_USE;
184}
185
186long register_kerberos(char *username, char *password)
187{
188  long status;
189  Kadm_vals new;
190  des_cblock key;
191  unsigned long *lkey = (unsigned long *)key;
192
193  if ((status = krb_get_svc_in_tkt(MOIRA_SNAME, shorthostname, realm,
194                                   PWSERV_NAME, KADM_SINST, 3, KEYFILE)))
195    return status;
196
197  if ((status = kadm_init_link(PWSERV_NAME, KADM_SINST, realm)) !=
198      KADM_SUCCESS)
199    return status;
200
201  memset(&new, 0, sizeof(new));
202  SET_FIELD(KADM_DESKEY, new.fields);
203  SET_FIELD(KADM_NAME, new.fields);
204
205  des_string_to_key(password, key);
206  new.key_low = htonl(lkey[0]);
207  new.key_high = htonl(lkey[1]);
208  strcpy(new.name, username);
209
210  status = kadm_add(&new);
211  memset(&new, 0, sizeof(new));
212  dest_tkt();
213
214  if (status == KADM_INUSE)
215    return MR_IN_USE;
216  else
217    return status;
218}
219#endif
Note: See TracBrowser for help on using the repository browser.