Add new kadmin/ktutil --keep* and --enctypes opts
- Add --keepold/keepallold/pruneall options to various kadmin/ktutil commands. Default behavior to "prune old keys". - When setting keys for a service, we need to specify enctypes for it: - Always use kadm5_randkey_principal_3() instead of the older kadm5_randkey_principal(). - Add krb5_string_to_keysalts2(), like MIT's krb5_string_to_keysalts(), but with a context, and simpler. - Add --enctypes options to various kadmin/ktutil commands. - Add [libdefaults] supported_enctypes param with enctype[:salttype] list. - Add [realms] realm supported_enctypes param with enctype[:salttype] list. Default to aes128-cts-hmac-sha1-96:normal.
This commit is contained in:

committed by
Nico Williams

parent
7b76d6719f
commit
d8394c65b7
@@ -36,17 +36,23 @@
|
||||
RCSID("$Id$");
|
||||
|
||||
static krb5_error_code
|
||||
change_entry (krb5_keytab keytab,
|
||||
krb5_principal principal, krb5_kvno kvno,
|
||||
const char *realm, const char *admin_server, int server_port)
|
||||
change_entry(krb5_keytab keytab,
|
||||
krb5_principal principal,
|
||||
krb5_kvno kvno,
|
||||
int keep,
|
||||
size_t nkstuple,
|
||||
krb5_key_salt_tuple *kstuple,
|
||||
const char *realm,
|
||||
const char *admin_server,
|
||||
int server_port)
|
||||
{
|
||||
krb5_error_code ret;
|
||||
kadm5_config_params conf;
|
||||
void *kadm_handle;
|
||||
char *client_name;
|
||||
krb5_keyblock *keys;
|
||||
size_t i;
|
||||
int num_keys;
|
||||
int i;
|
||||
|
||||
ret = krb5_unparse_name (context, principal, &client_name);
|
||||
if (ret) {
|
||||
@@ -96,14 +102,15 @@ change_entry (krb5_keytab keytab,
|
||||
free (client_name);
|
||||
return ret;
|
||||
}
|
||||
ret = kadm5_randkey_principal (kadm_handle, principal, &keys, &num_keys);
|
||||
kadm5_destroy (kadm_handle);
|
||||
ret = kadm5_randkey_principal_3(kadm_handle, principal, keep, nkstuple,
|
||||
kstuple, &keys, &num_keys);
|
||||
kadm5_destroy(kadm_handle);
|
||||
if (ret) {
|
||||
krb5_warn(context, ret, "kadm5_randkey_principal: %s:", client_name);
|
||||
krb5_warn(context, ret, "kadm5_randkey_principal_3: %s:", client_name);
|
||||
free (client_name);
|
||||
return ret;
|
||||
}
|
||||
free (client_name);
|
||||
free(client_name);
|
||||
for (i = 0; i < num_keys; ++i) {
|
||||
krb5_keytab_entry new_entry;
|
||||
|
||||
@@ -131,16 +138,51 @@ struct change_set {
|
||||
};
|
||||
|
||||
int
|
||||
kt_change (struct change_options *opt, int argc, char **argv)
|
||||
kt_change(struct change_options *opt, int argc, char **argv)
|
||||
{
|
||||
krb5_error_code ret;
|
||||
krb5_keytab keytab;
|
||||
krb5_kt_cursor cursor;
|
||||
krb5_keytab_entry entry;
|
||||
int i, j, max;
|
||||
krb5_key_salt_tuple *kstuple = NULL;
|
||||
const char *enctype;
|
||||
size_t i, j, max, nkstuple;
|
||||
int keep = 0;
|
||||
struct change_set *changeset;
|
||||
int errors = 0;
|
||||
|
||||
i = 0;
|
||||
|
||||
if (opt->keepold_flag) {
|
||||
keep = 1;
|
||||
i++;
|
||||
}
|
||||
if (opt->keepallold_flag) {
|
||||
keep = 2;
|
||||
i++;
|
||||
}
|
||||
if (opt->pruneall_flag) {
|
||||
keep = 0;
|
||||
i++;
|
||||
}
|
||||
if (i > 1) {
|
||||
fprintf(stderr, "use only one of --keepold, --keepallold, or --pruneall\n");
|
||||
return EINVAL;
|
||||
}
|
||||
|
||||
enctype = opt->enctype_string;
|
||||
if (enctype == NULL || enctype[0] == '\0')
|
||||
enctype = krb5_config_get_string(context, NULL, "libdefaults",
|
||||
"supported_enctypes", NULL);
|
||||
if (enctype == NULL || enctype[0] == '\0')
|
||||
enctype = "aes128-cts-hmac-sha1-96";
|
||||
ret = krb5_string_to_keysalts2(context, enctype, &nkstuple, &kstuple);
|
||||
if (ret) {
|
||||
fprintf(stderr, "enctype(s) unknown\n");
|
||||
return ret;
|
||||
}
|
||||
|
||||
/* XXX Parameterize keytab name */
|
||||
if((keytab = ktutil_open_keytab()) == NULL)
|
||||
return 1;
|
||||
|
||||
@@ -232,11 +274,12 @@ kt_change (struct change_options *opt, int argc, char **argv)
|
||||
free(client_name);
|
||||
}
|
||||
}
|
||||
ret = change_entry (keytab,
|
||||
changeset[i].principal, changeset[i].kvno,
|
||||
opt->realm_string,
|
||||
opt->admin_server_string,
|
||||
opt->server_port_integer);
|
||||
ret = change_entry(keytab,
|
||||
changeset[i].principal, changeset[i].kvno,
|
||||
keep, nkstuple, kstuple,
|
||||
opt->realm_string,
|
||||
opt->admin_server_string,
|
||||
opt->server_port_integer);
|
||||
if (ret != 0)
|
||||
errors = 1;
|
||||
}
|
||||
@@ -247,6 +290,7 @@ kt_change (struct change_options *opt, int argc, char **argv)
|
||||
free (changeset);
|
||||
|
||||
out:
|
||||
free(kstuple);
|
||||
krb5_kt_close(context, keytab);
|
||||
return errors;
|
||||
}
|
||||
|
123
admin/get.c
123
admin/get.c
@@ -82,45 +82,84 @@ open_kadmin_connection(char *principal,
|
||||
return kadm_handle;
|
||||
}
|
||||
|
||||
static int
|
||||
parse_enctypes(struct get_options *opt,
|
||||
size_t *nks,
|
||||
krb5_key_salt_tuple **ks)
|
||||
{
|
||||
const char *str;
|
||||
char *s = NULL;
|
||||
char *tmp;
|
||||
size_t i;
|
||||
int ret;
|
||||
|
||||
*nks = 0;
|
||||
*ks = NULL;
|
||||
if (opt->enctypes_strings.num_strings == 0) {
|
||||
str = krb5_config_get_string(context, NULL, "libdefaults",
|
||||
"supported_enctypes", NULL);
|
||||
if (str == NULL)
|
||||
str = "aes128-cts-hmac-sha1-96";
|
||||
return krb5_string_to_keysalts2(context, str, nks, ks);
|
||||
}
|
||||
|
||||
for (i = 0; i < opt->enctypes_strings.num_strings; i++) {
|
||||
if (asprintf(&tmp, "%s%s%s", i ? s : "", i ? "," : "",
|
||||
opt->enctypes_strings.strings[i]) == -1) {
|
||||
free(s);
|
||||
return krb5_enomem(context);
|
||||
}
|
||||
s = tmp;
|
||||
}
|
||||
ret = krb5_string_to_keysalts2(context, s, nks, ks);
|
||||
free(s);
|
||||
return ret;
|
||||
}
|
||||
|
||||
int
|
||||
kt_get(struct get_options *opt, int argc, char **argv)
|
||||
{
|
||||
krb5_error_code ret = 0;
|
||||
krb5_keytab keytab;
|
||||
void *kadm_handle = NULL;
|
||||
krb5_enctype *etypes = NULL;
|
||||
size_t netypes = 0;
|
||||
krb5_key_salt_tuple *ks = NULL;
|
||||
size_t nks;
|
||||
size_t i;
|
||||
int a, j;
|
||||
int a, j, keep;
|
||||
unsigned int failed = 0;
|
||||
|
||||
if((keytab = ktutil_open_keytab()) == NULL)
|
||||
i = 0;
|
||||
keep = 0;
|
||||
if (opt->keepallold_flag) {
|
||||
keep = 2;
|
||||
i++;
|
||||
}
|
||||
if (opt->keepold_flag) {
|
||||
keep = 1;
|
||||
i++;
|
||||
}
|
||||
if (opt->pruneall_flag) {
|
||||
keep = 0;
|
||||
i++;
|
||||
}
|
||||
if (i > 1) {
|
||||
fprintf(stderr, "use only one of --keepold, --keepallold, or --pruneall\n");
|
||||
return EINVAL;
|
||||
}
|
||||
|
||||
if ((ret = parse_enctypes(opt, &nks, &ks))) {
|
||||
fprintf(stderr, "invalid enctype(s)\n");
|
||||
return ret;
|
||||
}
|
||||
|
||||
if((keytab = ktutil_open_keytab()) == NULL) {
|
||||
free(ks);
|
||||
return 1;
|
||||
}
|
||||
|
||||
if(opt->realm_string)
|
||||
krb5_set_default_realm(context, opt->realm_string);
|
||||
|
||||
if (opt->enctypes_strings.num_strings != 0) {
|
||||
|
||||
etypes = malloc (opt->enctypes_strings.num_strings * sizeof(*etypes));
|
||||
if (etypes == NULL) {
|
||||
krb5_warnx(context, "malloc failed");
|
||||
goto out;
|
||||
}
|
||||
netypes = opt->enctypes_strings.num_strings;
|
||||
for(i = 0; i < netypes; i++) {
|
||||
ret = krb5_string_to_enctype(context,
|
||||
opt->enctypes_strings.strings[i],
|
||||
&etypes[i]);
|
||||
if(ret) {
|
||||
krb5_warnx(context, "unrecognized enctype: %s",
|
||||
opt->enctypes_strings.strings[i]);
|
||||
goto out;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
for(a = 0; a < argc; a++){
|
||||
krb5_principal princ_ent;
|
||||
kadm5_principal_ent_rec princ;
|
||||
@@ -167,7 +206,8 @@ kt_get(struct get_options *opt, int argc, char **argv)
|
||||
failed++;
|
||||
continue;
|
||||
}
|
||||
ret = kadm5_randkey_principal(kadm_handle, princ_ent, &keys, &n_keys);
|
||||
ret = kadm5_randkey_principal_3(kadm_handle, princ_ent, keep, nks, ks,
|
||||
&keys, &n_keys);
|
||||
if (ret) {
|
||||
krb5_warn(context, ret, "kadm5_randkey_principal(%s)", argv[a]);
|
||||
krb5_free_principal(context, princ_ent);
|
||||
@@ -203,37 +243,22 @@ kt_get(struct get_options *opt, int argc, char **argv)
|
||||
continue;
|
||||
}
|
||||
for(j = 0; j < n_keys; j++) {
|
||||
int do_add = TRUE;
|
||||
|
||||
if (netypes) {
|
||||
size_t k;
|
||||
|
||||
do_add = FALSE;
|
||||
for (k = 0; k < netypes; ++k)
|
||||
if (keys[j].keytype == etypes[k]) {
|
||||
do_add = TRUE;
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (do_add) {
|
||||
entry.principal = princ_ent;
|
||||
entry.vno = princ.kvno;
|
||||
entry.keyblock = keys[j];
|
||||
entry.timestamp = time (NULL);
|
||||
ret = krb5_kt_add_entry(context, keytab, &entry);
|
||||
if (ret)
|
||||
krb5_warn(context, ret, "krb5_kt_add_entry");
|
||||
}
|
||||
entry.principal = princ_ent;
|
||||
entry.vno = princ.kvno;
|
||||
entry.keyblock = keys[j];
|
||||
entry.timestamp = time (NULL);
|
||||
ret = krb5_kt_add_entry(context, keytab, &entry);
|
||||
if (ret)
|
||||
krb5_warn(context, ret, "krb5_kt_add_entry");
|
||||
krb5_free_keyblock_contents(context, &keys[j]);
|
||||
}
|
||||
|
||||
kadm5_free_principal_ent(kadm_handle, &princ);
|
||||
krb5_free_principal(context, princ_ent);
|
||||
}
|
||||
out:
|
||||
free(etypes);
|
||||
if (kadm_handle)
|
||||
kadm5_destroy(kadm_handle);
|
||||
krb5_kt_close(context, keytab);
|
||||
free(ks);
|
||||
return ret != 0 || failed > 0;
|
||||
}
|
||||
|
@@ -54,7 +54,7 @@ command = {
|
||||
short = "e"
|
||||
type = "string"
|
||||
argument = "enctype"
|
||||
help = "encryption type"
|
||||
help = "encryption type(s)"
|
||||
}
|
||||
option = {
|
||||
long = "password"
|
||||
@@ -75,6 +75,21 @@ command = {
|
||||
type = "flag"
|
||||
help = "generate random key"
|
||||
}
|
||||
option = {
|
||||
long = "keepold"
|
||||
type = "flag"
|
||||
help = "keep old keys/password needed to decrypt extant tickets (default)"
|
||||
}
|
||||
option = {
|
||||
long = "keepallold"
|
||||
type = "flag"
|
||||
help = "keep all old keys/password"
|
||||
}
|
||||
option = {
|
||||
long = "pruneall"
|
||||
type = "flag"
|
||||
help = "delete all old keys"
|
||||
}
|
||||
option = {
|
||||
long = "hex"
|
||||
short = "H"
|
||||
@@ -94,6 +109,28 @@ command = {
|
||||
argument = "realm"
|
||||
help = "realm to use"
|
||||
}
|
||||
option = {
|
||||
long = "enctype"
|
||||
short = "e"
|
||||
type = "string"
|
||||
argument = "enctype"
|
||||
help = "encryption type(s)"
|
||||
}
|
||||
option = {
|
||||
long = "keepold"
|
||||
type = "flag"
|
||||
help = "keep old keys/password needed to decrypt extant tickets (default)"
|
||||
}
|
||||
option = {
|
||||
long = "keepallold"
|
||||
type = "flag"
|
||||
help = "keep all old keys/password"
|
||||
}
|
||||
option = {
|
||||
long = "pruneall"
|
||||
type = "flag"
|
||||
help = "delete all old keys"
|
||||
}
|
||||
option = {
|
||||
long = "admin-server"
|
||||
short = "a"
|
||||
@@ -136,6 +173,21 @@ command = {
|
||||
help = "encryption types to use"
|
||||
argument = "enctype"
|
||||
}
|
||||
option = {
|
||||
long = "keepold"
|
||||
type = "flag"
|
||||
help = "keep old keys/password needed to decrypt extant tickets (default)"
|
||||
}
|
||||
option = {
|
||||
long = "keepallold"
|
||||
type = "flag"
|
||||
help = "keep all old keys/password"
|
||||
}
|
||||
option = {
|
||||
long = "pruneall"
|
||||
type = "flag"
|
||||
help = "delete all old keys"
|
||||
}
|
||||
option = {
|
||||
long = "realm"
|
||||
short = "r"
|
||||
|
@@ -62,6 +62,7 @@ can be one of the following:
|
||||
.Bl -tag -width srvconvert
|
||||
.It add Oo Fl p Ar principal Oc Oo Fl Fl principal= Ns Ar principal Oc \
|
||||
Oo Fl V Ar kvno Oc Oo Fl Fl kvno= Ns Ar kvno Oc Oo Fl e Ar enctype Oc \
|
||||
Oo Fl Fl keepold | Fl Fl keepallold | Fl Fl pruneall Oc \
|
||||
Oo Fl Fl enctype= Ns Ar enctype Oc Oo Fl w Ar password Oc \
|
||||
Oo Fl Fl password= Ns Ar password Oc Oo Fl r Oc Oo Fl Fl random Oc \
|
||||
Oo Fl s Oc Oo Fl Fl no-salt Oc Oo Fl H Oc Op Fl Fl hex
|
||||
@@ -72,6 +73,8 @@ the keytab, you should consider the
|
||||
.Ar get
|
||||
command, which talks to the kadmin server.
|
||||
.It change Oo Fl r Ar realm Oc Oo Fl Fl realm= Ns Ar realm Oc \
|
||||
Oo Fl Fl keepold | Fl Fl keepallold | Fl Fl pruneall Oc \
|
||||
Oo Fl Fl enctype= Ns Ar enctype Oc \
|
||||
Oo Fl Fl a Ar host Oc Oo Fl Fl admin-server= Ns Ar host Oc \
|
||||
Oo Fl Fl s Ar port Oc Op Fl Fl server-port= Ns Ar port
|
||||
Update one or several keys to new versions. By default, use the admin
|
||||
@@ -86,6 +89,7 @@ to
|
||||
.Ar keytab-dest .
|
||||
.It get Oo Fl p Ar admin principal Oc \
|
||||
Oo Fl Fl principal= Ns Ar admin principal Oc Oo Fl e Ar enctype Oc \
|
||||
Oo Fl Fl keepold | Fl Fl keepallold | Fl Fl pruneall Oc \
|
||||
Oo Fl Fl enctypes= Ns Ar enctype Oc Oo Fl r Ar realm Oc \
|
||||
Oo Fl Fl realm= Ns Ar realm Oc Oo Fl a Ar admin server Oc \
|
||||
Oo Fl Fl admin-server= Ns Ar admin server Oc Oo Fl s Ar server port Oc \
|
||||
|
Reference in New Issue
Block a user