2 * Copyright 2009 Sun Microsystems, Inc. All rights reserved.
3 * Use is subject to license terms.
7 * Copyright 1993 OpenVision Technologies, Inc., All Rights Reserved.
9 * $Id: kadm5_create.c,v 1.6 1998/10/30 02:52:37 marc Exp $
10 * $Source: /cvs/krbdev/krb5/src/kadmin/dbutil/kadm5_create.c,v $
14 * Copyright (C) 1998 by the FundsXpress, INC.
16 * All rights reserved.
18 * Export of this software from the United States of America may require
19 * a specific license from the United States Government. It is the
20 * responsibility of any person or organization contemplating export to
21 * obtain such a license before exporting.
23 * WITHIN THAT CONSTRAINT, permission to use, copy, modify, and
24 * distribute this software and its documentation for any purpose and
25 * without fee is hereby granted, provided that the above copyright
26 * notice appear in all copies and that both that copyright notice and
27 * this permission notice appear in supporting documentation, and that
28 * the name of FundsXpress. not be used in advertising or publicity pertaining
29 * to distribution of the software without specific, written prior
30 * permission. FundsXpress makes no representations about the suitability of
31 * this software for any purpose. It is provided "as is" without express
32 * or implied warranty.
34 * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR
35 * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
36 * WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
39 #include "string_table.h"
46 #include <kadm5/admin.h>
47 #include <krb5/adm_proto.h>
51 #include "kdb5_util.h"
55 add_admin_old_princ(void *handle
, krb5_context context
,
56 char *name
, char *realm
, int attrs
, int lifetime
);
58 add_admin_sname_princ(void *handle
, krb5_context context
,
59 char *sname
, int attrs
, int lifetime
);
61 add_admin_princ(void *handle
, krb5_context context
,
62 krb5_principal principal
, int attrs
, int lifetime
);
64 static int add_admin_princs(void *handle
, krb5_context context
, char *realm
);
69 #define ADMIN_LIFETIME 60*60*3 /* 3 hours */
70 #define CHANGEPW_LIFETIME 60*5 /* 5 minutes */
72 extern char *progname
;
75 * Function: kadm5_create
77 * Purpose: create admin principals in KDC database
79 * Arguments: params (r) configuration parameters to use
81 * Effects: Creates KADM5_ADMIN_SERVICE and KADM5_CHANGEPW_SERVICE
82 * principals in the KDC database and sets their attributes
85 int kadm5_create(kadm5_config_params
*params
)
90 kadm5_config_params lparams
;
92 if ((retval
= kadm5_init_krb5_context(&context
)))
95 (void) memset(&lparams
, 0, sizeof (kadm5_config_params
));
98 * The lock file has to exist before calling kadm5_init, but
99 * params->admin_lockfile may not be set yet...
101 if ((retval
= kadm5_get_config_params(context
, 1,
102 params
, &lparams
))) {
103 com_err(progname
, retval
, gettext("while looking up the Kerberos configuration"));
107 retval
= kadm5_create_magic_princs(&lparams
, context
);
109 kadm5_free_config_params(context
, &lparams
);
110 krb5_free_context(context
);
115 int kadm5_create_magic_princs(kadm5_config_params
*params
,
116 krb5_context context
)
121 retval
= krb5_klog_init(context
, "admin_server", progname
, 0);
124 if ((retval
= kadm5_init(progname
, NULL
, NULL
, params
,
125 KADM5_STRUCT_VERSION
,
129 com_err(progname
, retval
, gettext("while initializing the Kerberos admin interface"));
133 retval
= add_admin_princs(handle
, context
, params
->realm
);
135 kadm5_destroy(handle
);
137 krb5_klog_close(context
);
143 * Function: build_name_with_realm
145 * Purpose: concatenate a name and a realm to form a krb5 name
149 * name (input) the name
150 * realm (input) the realm
154 * pointer to name@realm, in allocated memory, or NULL if it
155 * cannot be allocated
157 * Requires: both strings are null-terminated
159 static char *build_name_with_realm(char *name
, char *realm
)
163 n
= (char *) malloc(strlen(name
) + strlen(realm
) + 2);
164 sprintf(n
, "%s@%s", name
, realm
);
169 * Function: add_admin_princs
171 * Purpose: create admin principals
175 * rseed (input) random seed
176 * realm (input) realm, or NULL for default realm
177 * <return value> (output) status, 0 for success, 1 for serious error
183 * add_admin_princs creates KADM5_ADMIN_SERVICE,
184 * KADM5_CHANGEPW_SERVICE. If any of these exist a message is
185 * printed. If any of these existing principal do not have the proper
186 * attributes, a warning message is printed.
188 static int add_admin_princs(void *handle
, krb5_context context
, char *realm
)
190 krb5_error_code ret
= 0;
194 * The kadmin/admin principal is unused on Solaris. This principal is used
195 * in AUTH_GSSAPI but Solaris doesn't support AUTH_GSSAPI. RPCSEC_GSS can only
196 * be used with host-based principals.
201 if ((ret
= add_admin_old_princ(handle
, context
,
202 KADM5_ADMIN_SERVICE
, realm
,
203 KRB5_KDB_DISALLOW_TGT_BASED
,
208 if ((ret
= add_admin_old_princ(handle
, context
,
209 KADM5_CHANGEPW_SERVICE
, realm
,
210 KRB5_KDB_DISALLOW_TGT_BASED
|
211 KRB5_KDB_PWCHANGE_SERVICE
,
215 if ((ret
= add_admin_sname_princ(handle
, context
,
216 KADM5_ADMIN_HOST_SERVICE
,
217 KRB5_KDB_DISALLOW_TGT_BASED
,
221 if ((ret
= add_admin_sname_princ(handle
, context
,
222 KADM5_CHANGEPW_HOST_SERVICE
,
223 KRB5_KDB_DISALLOW_TGT_BASED
|
224 KRB5_KDB_PWCHANGE_SERVICE
,
228 if ((ret
= add_admin_sname_princ(handle
, context
,
229 KADM5_KIPROP_HOST_SERVICE
,
230 KRB5_KDB_DISALLOW_TGT_BASED
,
240 * Function: add_admin_princ
244 * creator (r) principal to use as "mod_by"
245 * rseed (r) seed for random key generator
246 * principal (r) kerberos principal to add
247 * attrs (r) principal's attributes
248 * lifetime (r) principal's max life, or 0
249 * not_unique (r) error message for multiple entries, never used
250 * exists (r) warning message for principal exists
251 * wrong_attrs (r) warning message for wrong attributes
256 * ERR on serious errors
260 * If the principal is not unique, not_unique is printed (but this
261 * never happens). If the principal exists, then exists is printed
262 * and if the principals attributes != attrs, wrong_attrs is printed.
263 * Otherwise, the principal is created with mod_by creator and
264 * attributes attrs and max life of lifetime (if not zero).
267 static int add_admin_princ(void *handle
, krb5_context context
,
268 krb5_principal principal
, int attrs
, int lifetime
)
272 kadm5_principal_ent_rec ent
;
274 memset(&ent
, 0, sizeof(ent
));
276 if (krb5_unparse_name(context
, principal
, &fullname
))
279 ent
.principal
= principal
;
280 ent
.max_life
= lifetime
;
281 ent
.attributes
= attrs
| KRB5_KDB_DISALLOW_ALL_TIX
;
283 ret
= kadm5_create_principal(handle
, &ent
,
284 (KADM5_PRINCIPAL
| KADM5_MAX_LIFE
|
288 if (ret
!= KADM5_DUP
) {
289 com_err(progname
, ret
,
290 gettext(str_PUT_PRINC
), fullname
);
291 krb5_free_principal(context
, ent
.principal
);
296 /* only randomize key if we created the principal */
300 * Create kadmind principals with keys for all supported encryption types.
301 * Follows a similar pattern to add_principal() in keytab.c.
303 krb5_enctype
*tmpenc
, *enctype
= NULL
;
304 krb5_key_salt_tuple
*keysalt
;
306 krb5_int32 normalsalttype
;
308 ret
= krb5_get_permitted_enctypes(context
, &enctype
);
309 if (ret
|| *enctype
== NULL
) {
310 com_err(progname
, ret
,
311 gettext("while getting list of permitted encryption types"));
312 krb5_free_principal(context
, ent
.principal
);
317 /* Count the number of enc types */
318 for (tmpenc
= enctype
, num_ks
= 0; *tmpenc
; tmpenc
++)
321 keysalt
= malloc (sizeof (krb5_key_salt_tuple
) * num_ks
);
322 if (keysalt
== NULL
) {
323 com_err(progname
, ENOMEM
,
324 gettext("while generating list of key salt tuples"));
325 krb5_free_ktypes(context
, enctype
);
326 krb5_free_principal(context
, ent
.principal
);
331 ret
= krb5_string_to_salttype("normal", &normalsalttype
);
333 com_err(progname
, ret
,
334 gettext("while converting \"normal\" to a salttype"));
336 krb5_free_ktypes(context
, enctype
);
337 krb5_free_principal(context
, ent
.principal
);
342 /* Only create keys with "normal" salttype */
343 for (i
= 0; i
< num_ks
; i
++) {
344 keysalt
[i
].ks_enctype
= enctype
[i
];
345 keysalt
[i
].ks_salttype
= normalsalttype
;
348 ret
= kadm5_randkey_principal_3(handle
, ent
.principal
, FALSE
, num_ks
,
349 keysalt
, NULL
, NULL
);
351 krb5_free_ktypes (context
, enctype
);
355 com_err(progname
, ret
,
356 gettext(str_RANDOM_KEY
), fullname
);
357 krb5_free_principal(context
, ent
.principal
);
362 ent
.attributes
= attrs
;
363 ret
= kadm5_modify_principal(handle
, &ent
, KADM5_ATTRIBUTES
);
365 com_err(progname
, ret
,
366 gettext(str_PUT_PRINC
), fullname
);
367 krb5_free_principal(context
, ent
.principal
);
373 krb5_free_principal(context
, ent
.principal
);
380 add_admin_old_princ(void *handle
, krb5_context context
,
381 char *name
, char *realm
, int attrs
, int lifetime
)
385 krb5_principal principal
;
387 fullname
= build_name_with_realm(name
, realm
);
388 if (ret
= krb5_parse_name(context
, fullname
, &principal
)) {
389 com_err(progname
, ret
, gettext(str_PARSE_NAME
));
393 return (add_admin_princ(handle
, context
, principal
, attrs
, lifetime
));
397 add_admin_sname_princ(void *handle
, krb5_context context
,
398 char *sname
, int attrs
, int lifetime
)
401 krb5_principal principal
;
403 if (ret
= krb5_sname_to_principal(context
, NULL
, sname
,
404 KRB5_NT_SRV_HST
, &principal
)) {
405 com_err(progname
, ret
,
406 gettext("Could not get host based "
407 "service name for %s principal\n"), sname
);
410 return (add_admin_princ(handle
, context
, principal
, attrs
, lifetime
));