return 0;
}
+/** Add an alias to an integer attribute hashing the alias for the integer value
+ *
+ */
+int fr_dict_enum_add_alias_next(fr_dict_attr_t const *da, char const *alias)
+{
+ fr_value_box_t v = {
+ .type = da->type
+ };
+ fr_value_box_t s = {
+ .type = da->type
+ };
+
+ if (fr_dict_enum_by_alias(da, alias)) return 0;
+
+ switch (da->type) {
+ case FR_TYPE_INT8:
+ v.vb_int8 = s.vb_int8 = fr_hash_string(alias) & INT8_MAX;
+ break;
+
+ case FR_TYPE_INT16:
+ v.vb_int16 = s.vb_int16 = fr_hash_string(alias) & INT16_MAX;
+ break;
+
+ case FR_TYPE_INT32:
+ v.vb_int32 = s.vb_int32 = fr_hash_string(alias) & INT32_MAX;
+ break;
+
+ case FR_TYPE_INT64:
+ v.vb_int64 = s.vb_int64 = fr_hash_string(alias) & INT64_MAX;
+ break;
+
+ case FR_TYPE_UINT8:
+ v.vb_uint8 = s.vb_uint8 = fr_hash_string(alias) & UINT8_MAX;
+ break;
+
+ case FR_TYPE_UINT16:
+ v.vb_uint16 = s.vb_uint16 = fr_hash_string(alias) & UINT16_MAX;
+ break;
+
+ case FR_TYPE_UINT32:
+ v.vb_uint32 = s.vb_uint32 = fr_hash_string(alias) & UINT32_MAX;
+ break;
+
+ case FR_TYPE_UINT64:
+ v.vb_uint64 = s.vb_uint64 = fr_hash_string(alias) & UINT64_MAX;
+ break;
+
+ default:
+ fr_strerror_printf("Attribute is wrong type for auto-numbering, expected numeric type, got %s",
+ fr_int2str(dict_attr_types, da->type, "?Unknown?"));
+ return -1;
+ }
+
+ /*
+ * If there's no existing value, add an enum
+ * with the hash value of the alias.
+ *
+ * This helps with debugging as the values
+ * are consistent.
+ */
+ if (!fr_dict_enum_by_value(da, &v)) {
+ add:
+ return fr_dict_enum_add_alias(da, alias, &v, false, false);
+ }
+
+ for (;;) {
+ fr_value_box_increment(&v);
+
+ if (fr_value_box_cmp_op(T_OP_EQ, &v, &s) == 0) {
+ fr_strerror_printf("No free integer values for enumeration");
+ return -1;
+ }
+
+ if (!fr_dict_enum_by_value(da, &v)) goto add;
+ }
+
+ return 0;
+}
+
/** Copy a known or unknown attribute to produce an unknown attribute
*
* Will copy the complete hierarchy down to the first known attribute.