From: Alan T. DeKok Date: Sun, 16 Feb 2025 22:39:20 +0000 (-0500) Subject: remove 'tagnum=' for flags. X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=4d20ffbdc071a07b7e434b7d66908364f37671e6;p=thirdparty%2Ffreeradius-server.git remove 'tagnum=' for flags. it was being used as a synonym for 'option=', and was therefore not needed. also remove 'class=', though it's just commented out. The only uses of it were at the same time as setting 'option=', and the option parser already sets the class --- diff --git a/share/dictionary/der/dictionary.common b/share/dictionary/der/dictionary.common index b0f696deb2a..9805fb55249 100644 --- a/share/dictionary/der/dictionary.common +++ b/share/dictionary/der/dictionary.common @@ -8,7 +8,7 @@ BEGIN GeneralName ATTRIBUTE otherName 0 sequence option=0 BEGIN otherName DEFINE type-id oid -DEFINE Value-thing sequence class=context-specific,tagnum=0 +DEFINE Value-thing sequence option=0 BEGIN Value-thing DEFINE userPrincipalName utf8string END Value-thing diff --git a/share/dictionary/der/dictionary.extensions b/share/dictionary/der/dictionary.extensions index c5af83b356a..087c962c30a 100644 --- a/share/dictionary/der/dictionary.extensions +++ b/share/dictionary/der/dictionary.extensions @@ -15,7 +15,7 @@ BEGIN accessLocation ATTRIBUTE otherName 0 sequence option=0 BEGIN otherName DEFINE type-id oid -DEFINE Value-thing sequence class=context-specific,tagnum=0 +DEFINE Value-thing sequence option=0 BEGIN Value-thing DEFINE userPrincipalName utf8string END Value-thing @@ -41,7 +41,7 @@ BEGIN accessLocation ATTRIBUTE otherName 0 sequence option=0 BEGIN otherName DEFINE type-id oid -DEFINE Value-thing sequence class=context-specific,tagnum=0 +DEFINE Value-thing sequence option=0 BEGIN Value-thing DEFINE userPrincipalName utf8string END Value-thing diff --git a/share/dictionary/der/dictionary.rfc2986 b/share/dictionary/der/dictionary.rfc2986 index 6253fc9166a..674a7c49c4c 100644 --- a/share/dictionary/der/dictionary.rfc2986 +++ b/share/dictionary/der/dictionary.rfc2986 @@ -30,7 +30,7 @@ END algorithm DEFINE subjectPublicKey bitstring END subjectPublicKeyInfo -DEFINE Attributes sequence class=context-specific,tagnum=0 +DEFINE Attributes sequence option=0 BEGIN Attributes DEFINE Attribute-thing tlv BEGIN Attribute-thing diff --git a/share/dictionary/der/dictionary.rfc5280 b/share/dictionary/der/dictionary.rfc5280 index e627dbb3e5e..95f1f7c3d46 100644 --- a/share/dictionary/der/dictionary.rfc5280 +++ b/share/dictionary/der/dictionary.rfc5280 @@ -7,7 +7,7 @@ BEGIN Certificate DEFINE tbsCertificate tlv BEGIN tbsCertificate -DEFINE version sequence class=context-specific,tagnum=0 +DEFINE version sequence option=0 BEGIN version DEFINE VersionNum integer END version diff --git a/src/protocols/der/base.c b/src/protocols/der/base.c index 2a7d4b4f342..754b5b20a4e 100644 --- a/src/protocols/der/base.c +++ b/src/protocols/der/base.c @@ -184,27 +184,7 @@ void fr_der_global_free(void) fr_dict_autofree(libfreeradius_der_dict); } -static int dict_flag_tagnum(fr_dict_attr_t **da_p, char const *value, UNUSED fr_dict_flag_parser_rule_t const *rules) -{ - fr_der_attr_flags_t *flags = fr_dict_attr_ext(*da_p, FR_DICT_ATTR_EXT_PROTOCOL_SPECIFIC); - unsigned long num; - char *end = NULL; - - /* - * We limit the allowed tag numbers to ones which fit into the - * 5 bits of the first byte. We don't support continued tags. - */ - num = strtoul(value, &end, 10); - if ((num > 0x1f) || *end) { - fr_strerror_printf("Invalid tag number '%s'", value); - return -1; - } - - flags->tagnum = num; - - return 0; -} - +#if 0 static int dict_flag_class(fr_dict_attr_t **da_p, char const *value, UNUSED fr_dict_flag_parser_rule_t const *rules) { static fr_table_num_sorted_t const table[] = { @@ -228,6 +208,7 @@ static int dict_flag_class(fr_dict_attr_t **da_p, char const *value, UNUSED fr_d return 0; } +#endif static int dict_flag_has_default(fr_dict_attr_t **da_p, UNUSED char const *value, UNUSED fr_dict_flag_parser_rule_t const *rules) { @@ -392,14 +373,17 @@ static int dict_flag_option(fr_dict_attr_t **da_p, UNUSED char const *value, UNU return -1; } + /* + * Don't over-ride 'class==foo,option=bar' + */ flags->class = FR_DER_CLASS_CONTEXT; - flags->tagnum = num; + flags->option = num; return 0; } -static fr_dict_flag_parser_t const der_flags[] = { - { L("class"), { .func = dict_flag_class } }, +static const fr_dict_flag_parser_t der_flags[] = { +// { L("class"), { .func = dict_flag_class } }, { L("der_type"), { .func = dict_flag_der_type, .needs_value = true } }, { L("has_default"), { .func = dict_flag_has_default } }, { L("is_choice"), { .func = dict_flag_is_choice } }, @@ -411,7 +395,6 @@ static fr_dict_flag_parser_t const der_flags[] = { { L("option"), { .func = dict_flag_option } }, { L("sequence_of"), { .func = dict_flag_sequence_of } }, { L("set_of"), { .func = dict_flag_set_of } }, - { L("tagnum"), { .func = dict_flag_tagnum } } }; static bool type_parse(fr_type_t *type_p,fr_dict_attr_t **da_p, char const *name) @@ -516,12 +499,18 @@ static bool type_parse(fr_type_t *type_p,fr_dict_attr_t **da_p, char const *name /* * If it is a collection of x509 extensions, we will set a few other flags * as per RFC 5280. + * + * @todo - this is hard-coded for RFC 5280 rules. Other + * things may have different rules. */ if (fr_type == FR_TYPE_GROUP) { - dict_flag_is_extensions(da_p, "true", NULL); - dict_flag_tagnum(da_p, "3", NULL); - dict_flag_class(da_p, "context-specific", NULL); - dict_flag_sequence_of(da_p, "sequence", NULL); + flags->is_extensions = true; + + flags->class = FR_DER_CLASS_CONTEXT; + flags->option = 3; + + flags->is_sequence_of = true; + flags->sequence_of = FR_DER_TAG_SEQUENCE; } flags->is_choice = (strcmp(name, "choice") == 0); diff --git a/src/protocols/der/decode.c b/src/protocols/der/decode.c index 260db9e7e19..e2136a51a3c 100644 --- a/src/protocols/der/decode.c +++ b/src/protocols/der/decode.c @@ -1597,11 +1597,11 @@ static ssize_t fr_der_decode_hdr(fr_dict_attr_t const *parent, fr_dbuff_t *in, u if (tag_class != fr_der_flag_class(parent)) { bad_tag: fr_strerror_printf("Invalid tag %u for attribute %s. Expected %" PRIu32, *tag, parent->name, - fr_der_flag_tagnum(parent)); + fr_der_flag_option(parent)); return -1; } - if (*tag != fr_der_flag_tagnum(parent)) goto bad_tag; + if (*tag != fr_der_flag_option(parent)) goto bad_tag; *tag = fr_der_flag_der_type(parent); } diff --git a/src/protocols/der/der.h b/src/protocols/der/der.h index 17d4a0e87b1..de74384e1af 100644 --- a/src/protocols/der/der.h +++ b/src/protocols/der/der.h @@ -64,7 +64,7 @@ typedef enum { #define DER_BOOLEAN_TRUE 0xff //!< DER encoded boolean true value. typedef struct { - uint8_t tagnum; + uint8_t option; //!< "attribute number" encoded in the tag field. fr_der_tag_class_t class; fr_der_tag_t der_type; union { @@ -87,7 +87,7 @@ static inline fr_der_attr_flags_t const *fr_der_attr_flags(fr_dict_attr_t const return fr_dict_attr_ext(da, FR_DICT_ATTR_EXT_PROTOCOL_SPECIFIC); } -#define fr_der_flag_tagnum(_da) (fr_der_attr_flags(_da)->tagnum) +#define fr_der_flag_option(_da) (fr_der_attr_flags(_da)->option) #define fr_der_flag_class(_da) (fr_der_attr_flags(_da)->class) #define fr_der_flag_der_type(_da) (fr_der_attr_flags(_da)->der_type) #define fr_der_flag_sequence_of(_da) (fr_der_attr_flags(_da)->sequence_of) diff --git a/src/protocols/der/encode.c b/src/protocols/der/encode.c index 873e7233e47..23ec4f2deac 100644 --- a/src/protocols/der/encode.c +++ b/src/protocols/der/encode.c @@ -1700,8 +1700,8 @@ static ssize_t encode_value(fr_dbuff_t *dbuff, UNUSED fr_da_stack_t *da_stack, U fr_pair_t const *vp; fr_dbuff_t our_dbuff = FR_DBUFF(dbuff); fr_dbuff_marker_t marker; - fr_der_tag_encode_t *tag_encode; - fr_der_tag_t tag_num; + fr_der_tag_encode_t *func; + fr_der_tag_t tag; fr_der_tag_class_t tag_class; fr_der_encode_ctx_t *uctx = encode_ctx; ssize_t slen = 0; @@ -1788,26 +1788,35 @@ static ssize_t encode_value(fr_dbuff_t *dbuff, UNUSED fr_da_stack_t *da_stack, U return fr_dbuff_set(dbuff, &our_dbuff); } - tag_num = fr_der_flag_der_type(vp->da) ? fr_der_flag_der_type(vp->da) : fr_type_to_der_tag_default(vp->vp_type); + tag = fr_der_flag_der_type(vp->da); + if (!tag) tag = fr_type_to_der_tag_default(vp->vp_type); - if (unlikely(tag_num == FR_DER_TAG_INVALID)) { - fr_strerror_printf("No tag number for type %" PRId32, vp->vp_type); + if (unlikely(tag == FR_DER_TAG_INVALID)) { + fr_strerror_printf("No tag defined for type %s", fr_type_to_str(vp->vp_type)); return -1; } - tag_encode = &tag_funcs[tag_num]; - if (!tag_encode->encode) { - fr_strerror_printf("No encoding function for type %" PRId32, vp->vp_type); + func = &tag_funcs[tag]; + if (!func->encode) { + fr_strerror_printf("No encoding function for type %s", fr_type_to_str(vp->vp_type)); return -1; } - tag_class = fr_der_flag_class(vp->da) ? fr_der_flag_class(vp->da) : FR_DER_CLASS_UNIVERSAL; + /* + * Default flag class is 0, which is FR_DER_CLASS_UNIVERSAL. + */ + tag_class = fr_der_flag_class(vp->da); + + /* + * We call the DER type encoding function based on its + * tag, but we might need to encode an option value + * instead of a tag. + */ + if (fr_der_flag_option(vp->da) | tag_class) tag = fr_der_flag_option(vp->da); fr_dbuff_marker(&uctx->encoding_start, &our_dbuff); - slen = fr_der_encode_tag(&our_dbuff, - fr_der_flag_tagnum(vp->da) | tag_class ? fr_der_flag_tagnum(vp->da) : tag_num, - tag_class, tag_encode->constructed); + slen = fr_der_encode_tag(&our_dbuff, tag, tag_class, func->constructed); if (slen < 0) { error: fr_dbuff_marker_release(&uctx->encoding_start); @@ -1825,7 +1834,7 @@ static ssize_t encode_value(fr_dbuff_t *dbuff, UNUSED fr_da_stack_t *da_stack, U if (fr_der_flag_is_extensions(vp->da)) { slen = fr_der_encode_X509_extensions(&our_dbuff, cursor, uctx); } else { - slen = tag_encode->encode(&our_dbuff, cursor, uctx); + slen = func->encode(&our_dbuff, cursor, uctx); } if (slen < 0) { fr_dbuff_marker_release(&marker); diff --git a/src/tests/unit/protocols/der/dictionary.test b/src/tests/unit/protocols/der/dictionary.test index f56d2f8edec..30b88291c7d 100644 --- a/src/tests/unit/protocols/der/dictionary.test +++ b/src/tests/unit/protocols/der/dictionary.test @@ -146,7 +146,7 @@ MEMBER Test-Bool bool MEMBER Test-Integer int64 END Set-Bool-Integer -DEFINE Test-Context-Specific bool class=context-specific,tagnum=0,der_type=boolean +DEFINE Test-Context-Specific bool option=0 DEFINE Test-Sequence-TLV sequence BEGIN Test-Sequence-TLV