From fb5cd8df0dbd04dac4f610e68cba5b80a3cb8d48 Mon Sep 17 00:00:00 2001 From: Greg Hudson Date: Fri, 23 May 2014 19:58:41 -0400 Subject: Treat LDAP KrbKey salt field as optional Per the ASN.1 definition, the KrbKey salt field is optional. Since 1.7, we have been treating it as mandatory in the encoder; since 1.11, we have been treating it as mandatory in the decoder. Mostly by luck, we have been encoding a salt type of 0 when key_data_ver is 1, but we really should not be looking at key_data_type[1] or key_data_length[1] in this situation. Treat the salt field as optional in the encoder and decoder. Although the previous commit ensures that we continue to always encode a salt (without any dangerous assumptions about krb5_key_data constructors), this change will allow us to decode key data encoded by 1.6 without salt fields. This also fixes issue #7918, by properly setting key_data_ver to 2 if a salt type but no salt value is present. It is difficult to get the decoder to actually assign 2 to key_data_ver just because the salt field is there, so take care of that in asn1_decode_sequence_of_keys. Adjust kdbtest.c to match the new behavior by setting key_data_ver to 2 in both test keys. ticket: 7919 target_version: 1.12.2 tags: pullup --- src/lib/krb5/asn.1/ldap_key_seq.c | 19 ++++++++++++++++--- 1 file changed, 16 insertions(+), 3 deletions(-) (limited to 'src/lib') diff --git a/src/lib/krb5/asn.1/ldap_key_seq.c b/src/lib/krb5/asn.1/ldap_key_seq.c index 69ad847c2..deb47058d 100644 --- a/src/lib/krb5/asn.1/ldap_key_seq.c +++ b/src/lib/krb5/asn.1/ldap_key_seq.c @@ -57,14 +57,14 @@ DEFCOUNTEDSTRINGTYPE(ui2_octetstring, unsigned char *, krb5_ui_2, ASN1_OCTETSTRING); static int -is_salt_present(const void *p) +is_value_present(const void *p) { const krb5_key_data *val = p; return (val->key_data_length[1] != 0); } DEFCOUNTEDTYPE(krbsalt_salt, krb5_key_data, key_data_contents[1], key_data_length[1], ui2_octetstring); -DEFOPTIONALTYPE(krbsalt_salt_if_present, is_salt_present, NULL, krbsalt_salt); +DEFOPTIONALTYPE(krbsalt_salt_if_present, is_value_present, NULL, krbsalt_salt); DEFFIELD(krbsalt_0, krb5_key_data, key_data_type[1], 0, int16); DEFCTAGGEDTYPE(krbsalt_1, 1, krbsalt_salt_if_present); static const struct atype_info *krbsalt_fields[] = { @@ -80,7 +80,20 @@ static const struct atype_info *encryptionkey_fields[] = { }; DEFSEQTYPE(encryptionkey, krb5_key_data, encryptionkey_fields); -DEFCTAGGEDTYPE(key_data_0, 0, krbsalt); +static int +is_salt_present(const void *p) +{ + const krb5_key_data *val = p; + return val->key_data_ver > 1; +} +static void +no_salt(void *p) +{ + krb5_key_data *val = p; + val->key_data_ver = 1; +} +DEFOPTIONALTYPE(key_data_salt_if_present, is_salt_present, no_salt, krbsalt); +DEFCTAGGEDTYPE(key_data_0, 0, key_data_salt_if_present); DEFCTAGGEDTYPE(key_data_1, 1, encryptionkey); #if 0 /* We don't support this field currently. */ DEFCTAGGEDTYPE(key_data_2, 2, s2kparams), -- cgit