added qse_raddic_addattr(), qse_raddic_deleteattrbyname(), qes_raddic_deleteattrbyvalue(), qse_raddic_findattrbyname(), qse_raddic_findattrbyvalue()
This commit is contained in:
parent
c9bbd3c993
commit
80ade41ea9
@ -30,21 +30,21 @@
|
||||
#include <qse/types.h>
|
||||
#include <qse/macros.h>
|
||||
|
||||
#define QSE_RAD_ATTR_TYPE_STRING 0
|
||||
#define QSE_RAD_ATTR_TYPE_INTEGER 1
|
||||
#define QSE_RAD_ATTR_TYPE_IPADDR 2
|
||||
#define QSE_RAD_ATTR_TYPE_DATE 3
|
||||
#define QSE_RAD_ATTR_TYPE_ABINARY 4
|
||||
#define QSE_RAD_ATTR_TYPE_OCTETS 5
|
||||
#define QSE_RAD_ATTR_TYPE_IFID 6
|
||||
#define QSE_RAD_ATTR_TYPE_IPV6ADDR 7
|
||||
#define QSE_RAD_ATTR_TYPE_IPV6PREFIX 8
|
||||
#define QSE_RAD_ATTR_TYPE_BYTE 9
|
||||
#define QSE_RAD_ATTR_TYPE_SHORT 10
|
||||
#define QSE_RAD_ATTR_TYPE_ETHERNET 11
|
||||
#define QSE_RAD_ATTR_TYPE_SIGNED 12
|
||||
#define QSE_RAD_ATTR_TYPE_COMBO_IP 13
|
||||
#define QSE_RAD_ATTR_TYPE_TLV 14
|
||||
#define QSE_RADDIC_ATTR_TYPE_STRING 0
|
||||
#define QSE_RADDIC_ATTR_TYPE_INTEGER 1
|
||||
#define QSE_RADDIC_ATTR_TYPE_IPADDR 2
|
||||
#define QSE_RADDIC_ATTR_TYPE_DATE 3
|
||||
#define QSE_RADDIC_ATTR_TYPE_ABINARY 4
|
||||
#define QSE_RADDIC_ATTR_TYPE_OCTETS 5
|
||||
#define QSE_RADDIC_ATTR_TYPE_IFID 6
|
||||
#define QSE_RADDIC_ATTR_TYPE_IPV6ADDR 7
|
||||
#define QSE_RADDIC_ATTR_TYPE_IPV6PREFIX 8
|
||||
#define QSE_RADDIC_ATTR_TYPE_BYTE 9
|
||||
#define QSE_RADDIC_ATTR_TYPE_SHORT 10
|
||||
#define QSE_RADDIC_ATTR_TYPE_ETHERNET 11
|
||||
#define QSE_RADDIC_ATTR_TYPE_SIGNED 12
|
||||
#define QSE_RADDIC_ATTR_TYPE_COMBO_IP 13
|
||||
#define QSE_RADDIC_ATTR_TYPE_TLV 14
|
||||
|
||||
struct qse_raddic_attr_flags_t
|
||||
{
|
||||
@ -63,16 +63,16 @@ struct qse_raddic_attr_flags_t
|
||||
};
|
||||
typedef struct qse_raddic_attr_flags_t qse_raddic_attr_flags_t;
|
||||
|
||||
typedef struct qse_raddic_attr_t qse_raddic_attr_t;
|
||||
struct qse_raddic_attr_t
|
||||
{
|
||||
int attr;
|
||||
int type;
|
||||
int vendor;
|
||||
qse_raddic_attr_flags_t flags;
|
||||
qse_raddic_attr_t* nexta;
|
||||
qse_char_t name[1];
|
||||
};
|
||||
typedef struct qse_raddic_attr_t qse_raddic_attr_t;
|
||||
|
||||
|
||||
struct qse_raddic_value_t
|
||||
{
|
||||
@ -93,9 +93,12 @@ struct qse_raddic_vendor_t
|
||||
qse_char_t name[1];
|
||||
};
|
||||
|
||||
|
||||
typedef struct qse_raddic_t qse_raddic_t;
|
||||
|
||||
#define QSE_RADDIC_ATTR_MAKE(vendor,value) ((((vendor) & 0xFFFF) << 8) | (value))
|
||||
#define QSE_RADDIC_ATTR_VENDOR(attr) (((attr) >> 8) & 0xFFFF);
|
||||
#define QSE_RADDIC_ATTR_VALUE(attr) ((attr) & 0xFF)
|
||||
|
||||
#if defined(__cplusplus)
|
||||
extern "C" {
|
||||
#endif
|
||||
@ -122,7 +125,7 @@ QSE_EXPORT qse_raddic_vendor_t* qse_raddic_findvendorbyvalue (
|
||||
QSE_EXPORT qse_raddic_vendor_t* qse_raddic_addvendor (
|
||||
qse_raddic_t* dic,
|
||||
const qse_char_t* name,
|
||||
int value
|
||||
int vendorpec
|
||||
);
|
||||
|
||||
QSE_EXPORT int qse_raddic_deletevendorbyname (
|
||||
@ -132,7 +135,39 @@ QSE_EXPORT int qse_raddic_deletevendorbyname (
|
||||
|
||||
QSE_EXPORT int qse_raddic_deletevendorbyvalue (
|
||||
qse_raddic_t* dic,
|
||||
int value
|
||||
int vendorpec
|
||||
);
|
||||
|
||||
|
||||
|
||||
|
||||
QSE_EXPORT qse_raddic_attr_t* qse_raddic_findattrbyname (
|
||||
qse_raddic_t* dic,
|
||||
const qse_char_t* name
|
||||
);
|
||||
|
||||
QSE_EXPORT qse_raddic_attr_t* qse_raddic_findattrbyvalue (
|
||||
qse_raddic_t* dic,
|
||||
int attr
|
||||
);
|
||||
|
||||
QSE_EXPORT qse_raddic_attr_t* qse_raddic_addattr (
|
||||
qse_raddic_t* dic,
|
||||
const qse_char_t* name,
|
||||
int vendor,
|
||||
int type,
|
||||
int value,
|
||||
const qse_raddic_attr_flags_t* flags
|
||||
);
|
||||
|
||||
QSE_EXPORT int qse_raddic_deleteattrbyname (
|
||||
qse_raddic_t* dic,
|
||||
const qse_char_t* name
|
||||
);
|
||||
|
||||
QSE_EXPORT int qse_raddic_deleteattrbyvalue (
|
||||
qse_raddic_t* dic,
|
||||
int attr
|
||||
);
|
||||
|
||||
#if defined(__cplusplus)
|
||||
|
@ -58,12 +58,13 @@ struct qse_raddic_t
|
||||
|
||||
qse_htl_t vendors_byname;
|
||||
qse_htl_t vendors_byvalue;
|
||||
qse_htl_t attributes_byname;
|
||||
qse_htl_t attributes_byvalue;
|
||||
qse_htl_t attrs_byname;
|
||||
qse_htl_t attrs_byvalue;
|
||||
qse_htl_t values_byvalue;
|
||||
qse_htl_t values_byname;
|
||||
|
||||
qse_raddic_attr_t *last_attr;
|
||||
qse_raddic_attr_t* last_attr;
|
||||
qse_raddic_attr_t* base_attrs[256];
|
||||
};
|
||||
|
||||
|
||||
@ -76,24 +77,26 @@ struct name_id_t
|
||||
|
||||
static const name_id_t type_table[] =
|
||||
{
|
||||
{ "integer", QSE_RAD_ATTR_TYPE_INTEGER },
|
||||
{ "string", QSE_RAD_ATTR_TYPE_STRING },
|
||||
{ "ipaddr", QSE_RAD_ATTR_TYPE_IPADDR },
|
||||
{ "date", QSE_RAD_ATTR_TYPE_DATE },
|
||||
{ "abinary", QSE_RAD_ATTR_TYPE_ABINARY },
|
||||
{ "octets", QSE_RAD_ATTR_TYPE_OCTETS },
|
||||
{ "ifid", QSE_RAD_ATTR_TYPE_IFID },
|
||||
{ "ipv6addr", QSE_RAD_ATTR_TYPE_IPV6ADDR },
|
||||
{ "ipv6prefix", QSE_RAD_ATTR_TYPE_IPV6PREFIX },
|
||||
{ "byte", QSE_RAD_ATTR_TYPE_BYTE },
|
||||
{ "short", QSE_RAD_ATTR_TYPE_SHORT },
|
||||
{ "ether", QSE_RAD_ATTR_TYPE_ETHERNET },
|
||||
{ "combo-ip", QSE_RAD_ATTR_TYPE_COMBO_IP },
|
||||
{ "tlv", QSE_RAD_ATTR_TYPE_TLV },
|
||||
{ "signed", QSE_RAD_ATTR_TYPE_SIGNED },
|
||||
{ "integer", QSE_RADDIC_ATTR_TYPE_INTEGER },
|
||||
{ "string", QSE_RADDIC_ATTR_TYPE_STRING },
|
||||
{ "ipaddr", QSE_RADDIC_ATTR_TYPE_IPADDR },
|
||||
{ "date", QSE_RADDIC_ATTR_TYPE_DATE },
|
||||
{ "abinary", QSE_RADDIC_ATTR_TYPE_ABINARY },
|
||||
{ "octets", QSE_RADDIC_ATTR_TYPE_OCTETS },
|
||||
{ "ifid", QSE_RADDIC_ATTR_TYPE_IFID },
|
||||
{ "ipv6addr", QSE_RADDIC_ATTR_TYPE_IPV6ADDR },
|
||||
{ "ipv6prefix", QSE_RADDIC_ATTR_TYPE_IPV6PREFIX },
|
||||
{ "byte", QSE_RADDIC_ATTR_TYPE_BYTE },
|
||||
{ "short", QSE_RADDIC_ATTR_TYPE_SHORT },
|
||||
{ "ether", QSE_RADDIC_ATTR_TYPE_ETHERNET },
|
||||
{ "combo-ip", QSE_RADDIC_ATTR_TYPE_COMBO_IP },
|
||||
{ "tlv", QSE_RADDIC_ATTR_TYPE_TLV },
|
||||
{ "signed", QSE_RADDIC_ATTR_TYPE_SIGNED },
|
||||
{ QSE_NULL, 0 }
|
||||
};
|
||||
|
||||
/* -------------------------------------------------------------------------- */
|
||||
|
||||
static qse_uint32_t dict_vendor_name_hash (qse_htl_t* htl, const void *data)
|
||||
{
|
||||
return qse_strcasehash32(((const qse_raddic_vendor_t*)data)->name);
|
||||
@ -135,6 +138,57 @@ static int dict_vendor_value_cmp (qse_htl_t* htl, const void* one, const void* t
|
||||
return a->vendorpec - b->vendorpec;
|
||||
}
|
||||
|
||||
/* -------------------------------------------------------------------------- */
|
||||
|
||||
static qse_uint32_t dict_attr_name_hash (qse_htl_t* htl, const void *data)
|
||||
{
|
||||
return qse_strcasehash32(((const qse_raddic_attr_t*)data)->name);
|
||||
}
|
||||
|
||||
static int dict_attr_name_cmp (qse_htl_t* htl, const void* one, const void* two)
|
||||
{
|
||||
const qse_raddic_attr_t* a = one;
|
||||
const qse_raddic_attr_t* b = two;
|
||||
return qse_strcasecmp(a->name, b->name);
|
||||
}
|
||||
|
||||
static void dict_attr_name_free (qse_htl_t* htl, void* data)
|
||||
{
|
||||
QSE_MMGR_FREE (htl->mmgr, data);
|
||||
}
|
||||
|
||||
static qse_uint32_t dict_attr_name_hetero_hash (qse_htl_t* htl, const void* one)
|
||||
{
|
||||
return qse_strcasehash32((const qse_char_t*)one);
|
||||
}
|
||||
|
||||
static int dict_attr_name_hetero_cmp (qse_htl_t* htl, const void* one, const void* two)
|
||||
{
|
||||
const qse_raddic_attr_t* b = two;
|
||||
return qse_strcasecmp((const qse_char_t*)one, b->name);
|
||||
}
|
||||
|
||||
static qse_uint32_t dict_attr_value_hash (qse_htl_t* htl, const void* data)
|
||||
{
|
||||
const qse_raddic_attr_t* v = (const qse_raddic_attr_t*)data;
|
||||
qse_uint32_t hv;
|
||||
|
||||
hv = qse_genhash32(&v->vendor, QSE_SIZEOF(v->vendor));
|
||||
return qse_genhash32_update(&v->attr, QSE_SIZEOF(v->attr), hv);
|
||||
}
|
||||
|
||||
static int dict_attr_value_cmp (qse_htl_t* htl, const void* one, const void* two)
|
||||
{
|
||||
const qse_raddic_attr_t *a = one;
|
||||
const qse_raddic_attr_t *b = two;
|
||||
|
||||
if (a->vendor < b->vendor) return -1;
|
||||
if (a->vendor > b->vendor) return -1;
|
||||
return a->attr - b->attr;
|
||||
}
|
||||
|
||||
/* -------------------------------------------------------------------------- */
|
||||
|
||||
int qse_raddic_init (qse_raddic_t* dic, qse_mmgr_t* mmgr)
|
||||
{
|
||||
QSE_MEMSET (dic, 0, QSE_SIZEOF(*dic));
|
||||
@ -142,8 +196,8 @@ int qse_raddic_init (qse_raddic_t* dic, qse_mmgr_t* mmgr)
|
||||
|
||||
qse_htl_init (&dic->vendors_byname, mmgr, 1);
|
||||
qse_htl_init (&dic->vendors_byvalue, mmgr, 1);
|
||||
qse_htl_init (&dic->attributes_byname, mmgr, 1);
|
||||
qse_htl_init (&dic->attributes_byvalue, mmgr, 1);
|
||||
qse_htl_init (&dic->attrs_byname, mmgr, 1);
|
||||
qse_htl_init (&dic->attrs_byvalue, mmgr, 1);
|
||||
qse_htl_init (&dic->values_byname, mmgr, 1);
|
||||
qse_htl_init (&dic->values_byvalue, mmgr, 1);
|
||||
|
||||
@ -155,6 +209,15 @@ int qse_raddic_init (qse_raddic_t* dic, qse_mmgr_t* mmgr)
|
||||
qse_htl_setcomper (&dic->vendors_byvalue, dict_vendor_value_cmp);
|
||||
/* no freeer for dic->vendors_byvalue */
|
||||
|
||||
|
||||
qse_htl_sethasher (&dic->attrs_byname, dict_attr_name_hash);
|
||||
qse_htl_setcomper (&dic->attrs_byname, dict_attr_name_cmp);
|
||||
qse_htl_setfreeer (&dic->attrs_byname, dict_attr_name_free);
|
||||
|
||||
qse_htl_sethasher (&dic->attrs_byvalue, dict_attr_value_hash);
|
||||
qse_htl_setcomper (&dic->attrs_byvalue, dict_attr_value_cmp);
|
||||
/* no freeer for dic->attrs_byvalue */
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
@ -162,8 +225,8 @@ void qse_raddic_fini (qse_raddic_t* dic)
|
||||
{
|
||||
qse_htl_fini (&dic->vendors_byname);
|
||||
qse_htl_fini (&dic->vendors_byvalue);
|
||||
qse_htl_fini (&dic->attributes_byname);
|
||||
qse_htl_fini (&dic->attributes_byvalue);
|
||||
qse_htl_fini (&dic->attrs_byname);
|
||||
qse_htl_fini (&dic->attrs_byvalue);
|
||||
qse_htl_fini (&dic->values_byvalue);
|
||||
qse_htl_fini (&dic->values_byname);
|
||||
}
|
||||
@ -192,6 +255,7 @@ void qse_raddic_close (qse_raddic_t* dic)
|
||||
QSE_MMGR_FREE (dic->mmgr, dic);
|
||||
}
|
||||
|
||||
/* -------------------------------------------------------------------------- */
|
||||
qse_raddic_vendor_t* qse_raddic_findvendorbyname (qse_raddic_t* dic, const qse_char_t* name)
|
||||
{
|
||||
qse_htl_node_t* np;
|
||||
@ -214,13 +278,13 @@ qse_raddic_vendor_t* qse_raddic_findvendorbyvalue (qse_raddic_t* dic, int vendor
|
||||
return (qse_raddic_vendor_t*)np->data;
|
||||
}
|
||||
|
||||
qse_raddic_vendor_t* qse_raddic_addvendor (qse_raddic_t* dic, const qse_char_t* name, int value)
|
||||
qse_raddic_vendor_t* qse_raddic_addvendor (qse_raddic_t* dic, const qse_char_t* name, int vendorpec)
|
||||
{
|
||||
qse_size_t length;
|
||||
qse_raddic_vendor_t* dv, * old_dv;
|
||||
qse_htl_node_t* np;
|
||||
|
||||
if (value >= 65535) return QSE_NULL;
|
||||
if (vendorpec <= 0 || vendorpec > 65535) return QSE_NULL;
|
||||
|
||||
length = qse_strlen(name);
|
||||
|
||||
@ -229,7 +293,7 @@ qse_raddic_vendor_t* qse_raddic_addvendor (qse_raddic_t* dic, const qse_char_t*
|
||||
if (dv == QSE_NULL) return QSE_NULL;
|
||||
|
||||
qse_strcpy(dv->name, name);
|
||||
dv->vendorpec = value;
|
||||
dv->vendorpec = vendorpec;
|
||||
dv->type = dv->length = 1; /* defaults */
|
||||
dv->nextv = QSE_NULL;
|
||||
|
||||
@ -310,11 +374,11 @@ int qse_raddic_deletevendorbyname (qse_raddic_t* dic, const qse_char_t* name)
|
||||
return 0;
|
||||
}
|
||||
|
||||
int qse_raddic_deletevendorbyvalue (qse_raddic_t* dic, int value)
|
||||
int qse_raddic_deletevendorbyvalue (qse_raddic_t* dic, int vendorpec)
|
||||
{
|
||||
qse_raddic_vendor_t* dv;
|
||||
|
||||
dv = qse_raddic_findvendorbyvalue(dic, value);
|
||||
dv = qse_raddic_findvendorbyvalue(dic, vendorpec);
|
||||
if (!dv) return -1;
|
||||
|
||||
if (dv->nextv)
|
||||
@ -333,6 +397,162 @@ int qse_raddic_deletevendorbyvalue (qse_raddic_t* dic, int value)
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* -------------------------------------------------------------------------- */
|
||||
|
||||
qse_raddic_attr_t* qse_raddic_findattrbyname (qse_raddic_t* dic, const qse_char_t* name)
|
||||
{
|
||||
qse_htl_node_t* np;
|
||||
np = qse_htl_heterosearch (&dic->attrs_byname, name, dict_attr_name_hetero_hash, dict_attr_name_hetero_cmp);
|
||||
if (!np) return QSE_NULL;
|
||||
return (qse_raddic_attr_t*)np->data;
|
||||
}
|
||||
|
||||
qse_raddic_attr_t* qse_raddic_findattrbyvalue (qse_raddic_t* dic, int attr)
|
||||
{
|
||||
qse_htl_node_t* np;
|
||||
qse_raddic_attr_t dv;
|
||||
|
||||
/* simple cache lookup for basic attributes */
|
||||
if (attr >= 0 && attr <= 255) return dic->base_attrs[attr];
|
||||
|
||||
dv.attr = attr;
|
||||
dv.vendor = QSE_RADDIC_ATTR_VENDOR(attr);
|
||||
np = qse_htl_search (&dic->attrs_byvalue, &dv);
|
||||
if (!np) return QSE_NULL;
|
||||
return (qse_raddic_attr_t*)np->data;
|
||||
}
|
||||
|
||||
qse_raddic_attr_t* qse_raddic_addattr (qse_raddic_t* dic, const qse_char_t* name, int vendor, int type, int value, const qse_raddic_attr_flags_t* flags)
|
||||
{
|
||||
qse_size_t length;
|
||||
qse_raddic_attr_t* dv, * old_dv;
|
||||
qse_htl_node_t* np;
|
||||
|
||||
if (vendor < 0 || vendor > 65535) return QSE_NULL; /* 0 is allowed to mean no vendor */
|
||||
if (value < 0 || value > 255) return QSE_NULL;
|
||||
|
||||
length = qse_strlen(name);
|
||||
|
||||
if (vendor > 0)
|
||||
{
|
||||
/* TODO: validation ... */
|
||||
}
|
||||
|
||||
/* no +1 for the terminating null because dv->name is char[1] */
|
||||
dv = QSE_MMGR_ALLOC(dic->mmgr, QSE_SIZEOF(*dv) + (length * QSE_SIZEOF(*name)));
|
||||
if (dv == QSE_NULL) return QSE_NULL;
|
||||
|
||||
qse_strcpy(dv->name, name);
|
||||
dv->attr = QSE_RADDIC_ATTR_MAKE(vendor, value);
|
||||
dv->vendor = vendor;
|
||||
dv->type = type;
|
||||
dv->flags = *flags;
|
||||
dv->nexta = QSE_NULL;
|
||||
|
||||
/* return an existing item or insert a new item */
|
||||
np = qse_htl_ensert(&dic->attrs_byname, dv);
|
||||
if (!np || np->data != dv)
|
||||
{
|
||||
/* insertion failure or existing item found */
|
||||
QSE_MMGR_FREE (dic->mmgr, dv);
|
||||
return QSE_NULL;
|
||||
}
|
||||
|
||||
/* attempt to update the lookup table by value */
|
||||
np = qse_htl_upyank(&dic->attrs_byvalue, dv, (void**)&old_dv);
|
||||
if (np)
|
||||
{
|
||||
/* updated the existing item successfully.
|
||||
* link the old item to the current item */
|
||||
QSE_ASSERT (np->data == dv);
|
||||
QSE_ASSERT (dv->attr == old_dv->attr);
|
||||
dv->nexta = old_dv;
|
||||
}
|
||||
else
|
||||
{
|
||||
/* update failure, this entry must be new. try insertion */
|
||||
if (!qse_htl_insert (&dic->attrs_byvalue, dv))
|
||||
{
|
||||
qse_htl_delete (&dic->attrs_byname, dv);
|
||||
return QSE_NULL;
|
||||
}
|
||||
}
|
||||
|
||||
if (vendor == 0) dic->base_attrs[value] = dv; /* cache base attributes */
|
||||
return dv;
|
||||
}
|
||||
|
||||
int qse_raddic_deleteattrbyname (qse_raddic_t* dic, const qse_char_t* name)
|
||||
{
|
||||
qse_raddic_attr_t* dv, * dv2;
|
||||
|
||||
dv = qse_raddic_findattrbyname(dic, name);
|
||||
if (!dv) return -1;
|
||||
|
||||
dv2 = qse_raddic_findattrbyvalue(dic, dv->attr);
|
||||
QSE_ASSERT (dv2 != QSE_NULL);
|
||||
|
||||
if (dv != dv2)
|
||||
{
|
||||
qse_raddic_attr_t* x, * y;
|
||||
|
||||
QSE_ASSERT (qse_strcasecmp(dv->name, dv2->name) != 0);
|
||||
QSE_ASSERT (dv->attr == dv2->attr);
|
||||
QSE_ASSERT (dv->vendor == dv2->vendor);
|
||||
|
||||
/* when the attr of the given name is not the first one
|
||||
* referenced by value, i need to unlink the attr from the
|
||||
* attr chains with the same ID */
|
||||
x = dv2;
|
||||
y = QSE_NULL;
|
||||
while (x)
|
||||
{
|
||||
if (x == dv)
|
||||
{
|
||||
if (y) y->nexta = x->nexta;
|
||||
break;
|
||||
}
|
||||
y = x;
|
||||
x = x->nexta;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
/* this is the only attr with the attr ID. i can
|
||||
* safely remove it from the lookup table by value */
|
||||
qse_htl_delete (&dic->attrs_byvalue, dv);
|
||||
}
|
||||
|
||||
/* delete the attr from the lookup table by name */
|
||||
qse_htl_delete (&dic->attrs_byname, dv);
|
||||
return 0;
|
||||
}
|
||||
|
||||
int qse_raddic_deleteattrbyvalue (qse_raddic_t* dic, int attr)
|
||||
{
|
||||
qse_raddic_attr_t* dv;
|
||||
|
||||
dv = qse_raddic_findattrbyvalue(dic, attr);
|
||||
if (!dv) return -1;
|
||||
|
||||
if (dv->nexta)
|
||||
{
|
||||
qse_htl_update (&dic->attrs_byvalue, dv->nexta);
|
||||
}
|
||||
else
|
||||
{
|
||||
/* this is the only attr with the attr ID. i can
|
||||
* safely remove it from the lookup table by value */
|
||||
qse_htl_delete (&dic->attrs_byvalue, dv);
|
||||
}
|
||||
|
||||
/* delete the attr from the lookup table by name */
|
||||
qse_htl_delete (&dic->attrs_byname, dv);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* -------------------------------------------------------------------------- */
|
||||
|
||||
#if 0 // XXX
|
||||
/*
|
||||
* Get an attribute by its numerical value.
|
||||
@ -488,7 +708,7 @@ int dict_addvalue(qse_raddic_t* dic, const qse_char_t* namestr, const qse_char_t
|
||||
*/
|
||||
switch (dattr->type)
|
||||
{
|
||||
case QSE_RAD_ATTR_TYPE_BYTE:
|
||||
case QSE_RADDIC_ATTR_TYPE_BYTE:
|
||||
if (value > 255)
|
||||
{
|
||||
fr_pool_free(dval);
|
||||
@ -496,7 +716,7 @@ int dict_addvalue(qse_raddic_t* dic, const qse_char_t* namestr, const qse_char_t
|
||||
return -1;
|
||||
}
|
||||
break;
|
||||
case QSE_RAD_ATTR_TYPE_SHORT:
|
||||
case QSE_RADDIC_ATTR_TYPE_SHORT:
|
||||
if (value > 65535)
|
||||
{
|
||||
fr_pool_free(dval);
|
||||
@ -509,8 +729,8 @@ int dict_addvalue(qse_raddic_t* dic, const qse_char_t* namestr, const qse_char_t
|
||||
* Allow octets for now, because
|
||||
* of dictionary.cablelabs
|
||||
*/
|
||||
case QSE_RAD_ATTR_TYPE_OCTETS:
|
||||
case QSE_RAD_ATTR_TYPE_INTEGER:
|
||||
case QSE_RADDIC_ATTR_TYPE_OCTETS:
|
||||
case QSE_RADDIC_ATTR_TYPE_INTEGER:
|
||||
break;
|
||||
|
||||
default:
|
||||
@ -839,7 +1059,7 @@ static int load_file (qse_raddic_t* dic, const qse_char_t *dir, const qse_char_t
|
||||
goto oops;
|
||||
}
|
||||
|
||||
if (da->type != QSE_RAD_ATTR_TYPE_TLV)
|
||||
if (da->type != QSE_RADDIC_ATTR_TYPE_TLV)
|
||||
{
|
||||
fr_strerror_printf("dict_init: %s[%d]: attribute %s is not of type tlv", fn, line, argv[1]);
|
||||
goto oops;
|
||||
@ -980,21 +1200,21 @@ typedef struct value_fixup_t {
|
||||
static value_fixup_t *value_fixup = QSE_NULL;
|
||||
|
||||
static const FR_NAME_NUMBER type_table[] = {
|
||||
{ "integer", QSE_RAD_ATTR_TYPE_INTEGER },
|
||||
{ "string", QSE_RAD_ATTR_TYPE_STRING },
|
||||
{ "ipaddr", QSE_RAD_ATTR_TYPE_IPADDR },
|
||||
{ "date", QSE_RAD_ATTR_TYPE_DATE },
|
||||
{ "abinary", QSE_RAD_ATTR_TYPE_ABINARY },
|
||||
{ "octets", QSE_RAD_ATTR_TYPE_OCTETS },
|
||||
{ "ifid", QSE_RAD_ATTR_TYPE_IFID },
|
||||
{ "ipv6addr", QSE_RAD_ATTR_TYPE_IPV6ADDR },
|
||||
{ "ipv6prefix", QSE_RAD_ATTR_TYPE_IPV6PREFIX },
|
||||
{ "byte", QSE_RAD_ATTR_TYPE_BYTE },
|
||||
{ "short", QSE_RAD_ATTR_TYPE_SHORT },
|
||||
{ "ether", QSE_RAD_ATTR_TYPE_ETHERNET },
|
||||
{ "combo-ip", QSE_RAD_ATTR_TYPE_COMBO_IP },
|
||||
{ "tlv", QSE_RAD_ATTR_TYPE_TLV },
|
||||
{ "signed", QSE_RAD_ATTR_TYPE_SIGNED },
|
||||
{ "integer", QSE_RADDIC_ATTR_TYPE_INTEGER },
|
||||
{ "string", QSE_RADDIC_ATTR_TYPE_STRING },
|
||||
{ "ipaddr", QSE_RADDIC_ATTR_TYPE_IPADDR },
|
||||
{ "date", QSE_RADDIC_ATTR_TYPE_DATE },
|
||||
{ "abinary", QSE_RADDIC_ATTR_TYPE_ABINARY },
|
||||
{ "octets", QSE_RADDIC_ATTR_TYPE_OCTETS },
|
||||
{ "ifid", QSE_RADDIC_ATTR_TYPE_IFID },
|
||||
{ "ipv6addr", QSE_RADDIC_ATTR_TYPE_IPV6ADDR },
|
||||
{ "ipv6prefix", QSE_RADDIC_ATTR_TYPE_IPV6PREFIX },
|
||||
{ "byte", QSE_RADDIC_ATTR_TYPE_BYTE },
|
||||
{ "short", QSE_RADDIC_ATTR_TYPE_SHORT },
|
||||
{ "ether", QSE_RADDIC_ATTR_TYPE_ETHERNET },
|
||||
{ "combo-ip", QSE_RADDIC_ATTR_TYPE_COMBO_IP },
|
||||
{ "tlv", QSE_RADDIC_ATTR_TYPE_TLV },
|
||||
{ "signed", QSE_RADDIC_ATTR_TYPE_SIGNED },
|
||||
{ QSE_NULL, 0 }
|
||||
};
|
||||
|
||||
@ -1564,11 +1784,11 @@ static int process_attribute (
|
||||
flags.array = 1;
|
||||
|
||||
switch (type) {
|
||||
case QSE_RAD_ATTR_TYPE_IPADDR:
|
||||
case QSE_RAD_ATTR_TYPE_BYTE:
|
||||
case QSE_RAD_ATTR_TYPE_SHORT:
|
||||
case QSE_RAD_ATTR_TYPE_INTEGER:
|
||||
case QSE_RAD_ATTR_TYPE_DATE:
|
||||
case QSE_RADDIC_ATTR_TYPE_IPADDR:
|
||||
case QSE_RADDIC_ATTR_TYPE_BYTE:
|
||||
case QSE_RADDIC_ATTR_TYPE_SHORT:
|
||||
case QSE_RADDIC_ATTR_TYPE_INTEGER:
|
||||
case QSE_RADDIC_ATTR_TYPE_DATE:
|
||||
break;
|
||||
|
||||
default:
|
||||
@ -1599,8 +1819,8 @@ static int process_attribute (
|
||||
* Only string, octets, and integer can be tagged.
|
||||
*/
|
||||
switch (type) {
|
||||
case QSE_RAD_ATTR_TYPE_STRING:
|
||||
case QSE_RAD_ATTR_TYPE_INTEGER:
|
||||
case QSE_RADDIC_ATTR_TYPE_STRING:
|
||||
case QSE_RADDIC_ATTR_TYPE_INTEGER:
|
||||
break;
|
||||
|
||||
default:
|
||||
@ -1612,7 +1832,7 @@ static int process_attribute (
|
||||
}
|
||||
}
|
||||
|
||||
if (type == QSE_RAD_ATTR_TYPE_TLV) {
|
||||
if (type == QSE_RADDIC_ATTR_TYPE_TLV) {
|
||||
flags.has_tlv = 1;
|
||||
}
|
||||
|
||||
@ -2098,7 +2318,7 @@ static int my_dict_init(const char *dir, const char *fn,
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (da->type != QSE_RAD_ATTR_TYPE_TLV) {
|
||||
if (da->type != QSE_RADDIC_ATTR_TYPE_TLV) {
|
||||
fr_strerror_printf(
|
||||
"dict_init: %s[%d]: attribute %s is not of type tlv",
|
||||
fn, line, argv[1]);
|
||||
|
@ -17,6 +17,7 @@ static int test1 ()
|
||||
{
|
||||
qse_raddic_t* dic;
|
||||
qse_raddic_vendor_t* vendor, * v;
|
||||
qse_raddic_attr_t* attr, * a;
|
||||
int i;
|
||||
|
||||
dic = qse_raddic_open (QSE_MMGR_GETDFL(), 0);
|
||||
@ -47,7 +48,7 @@ static int test1 ()
|
||||
#define COUNT1 600
|
||||
#define COUNT2 700
|
||||
|
||||
for (i = 0; i < COUNT1; i++)
|
||||
for (i = 1; i < COUNT1; i++)
|
||||
{
|
||||
qse_char_t tmp[64];
|
||||
qse_strxfmt(tmp, QSE_COUNTOF(tmp), QSE_T("test%d"), i);
|
||||
@ -57,7 +58,7 @@ static int test1 ()
|
||||
_assert (qse_strcasecmp(vendor->name, tmp) == 0, "wrong vendor name");
|
||||
}
|
||||
|
||||
for (i = 0; i < COUNT1; i++)
|
||||
for (i = 1; i < COUNT1; i++)
|
||||
{
|
||||
qse_char_t tmp[64];
|
||||
qse_strxfmt(tmp, QSE_COUNTOF(tmp), QSE_T("test%d"), i);
|
||||
@ -67,7 +68,7 @@ static int test1 ()
|
||||
_assert (qse_strcasecmp(vendor->name, tmp) == 0, "wrong vendor name");
|
||||
}
|
||||
|
||||
for (i = 0; i < COUNT1; i++)
|
||||
for (i = 1; i < COUNT1; i++)
|
||||
{
|
||||
qse_char_t tmp[64];
|
||||
qse_strxfmt(tmp, QSE_COUNTOF(tmp), QSE_T("test%d"), i);
|
||||
@ -120,7 +121,7 @@ static int test1 ()
|
||||
}
|
||||
}
|
||||
|
||||
for (i = 0; i < COUNT1; i++)
|
||||
for (i = 1; i < COUNT1; i++)
|
||||
{
|
||||
qse_char_t tmp[64];
|
||||
int n;
|
||||
@ -130,7 +131,7 @@ static int test1 ()
|
||||
_assert (n == 0, "unable to delete a vendor");
|
||||
}
|
||||
|
||||
for (i = 0; i < COUNT1; i++)
|
||||
for (i = 1; i < COUNT1; i++)
|
||||
{
|
||||
qse_char_t tmp[64];
|
||||
qse_strxfmt(tmp, QSE_COUNTOF(tmp), QSE_T("test%d"), i);
|
||||
@ -146,7 +147,7 @@ static int test1 ()
|
||||
_assert (v != QSE_NULL && v->vendorpec == i, "unable to add a vendor");
|
||||
}
|
||||
|
||||
for (i = 0; i < COUNT1; i++)
|
||||
for (i = 1; i < COUNT1; i++)
|
||||
{
|
||||
int n;
|
||||
n = qse_raddic_deletevendorbyvalue (dic, i);
|
||||
@ -166,10 +167,149 @@ static int test1 ()
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
static int test2 ()
|
||||
{
|
||||
qse_raddic_t* dic;
|
||||
qse_raddic_attr_t* attr, * v;
|
||||
qse_raddic_attr_flags_t f;
|
||||
int i, j;
|
||||
|
||||
dic = qse_raddic_open (QSE_MMGR_GETDFL(), 0);
|
||||
_assert (dic != QSE_NULL, "unable to create a radius dictionary");
|
||||
|
||||
for (j = 0; j < 100; j++)
|
||||
{
|
||||
for (i = 0; i <= 255; i++)
|
||||
{
|
||||
qse_char_t tmp[64];
|
||||
qse_strxfmt(tmp, QSE_COUNTOF(tmp), QSE_T("test%d-%d"), j, i);
|
||||
attr = qse_raddic_addattr (dic, tmp, j, QSE_RADDIC_ATTR_TYPE_STRING, i, &f);
|
||||
_assert (attr != QSE_NULL, "unable to add an attribute");
|
||||
_assert (attr->attr == QSE_RADDIC_ATTR_MAKE(j, i), "wrong attr value");
|
||||
_assert (qse_strcasecmp(attr->name, tmp) == 0, "wrong attr name");
|
||||
}
|
||||
}
|
||||
|
||||
for (j = 0; j < 100; j++)
|
||||
{
|
||||
for (i = 0; i <= 255; i++)
|
||||
{
|
||||
qse_char_t tmp[64];
|
||||
qse_strxfmt(tmp, QSE_COUNTOF(tmp), QSE_T("test%d-%d"), j, i);
|
||||
attr = qse_raddic_findattrbyname (dic, tmp);
|
||||
_assert (attr != QSE_NULL, "unable to add an attribute");
|
||||
_assert (attr->attr == QSE_RADDIC_ATTR_MAKE(j, i), "wrong attr value");
|
||||
_assert (qse_strcasecmp(attr->name, tmp) == 0, "wrong attr name");
|
||||
}
|
||||
}
|
||||
|
||||
#if 0
|
||||
for (i = 0; i < COUNT1; i++)
|
||||
{
|
||||
qse_char_t tmp[64];
|
||||
qse_strxfmt(tmp, QSE_COUNTOF(tmp), QSE_T("test%d"), i);
|
||||
attr = qse_raddic_findattrbyvalue (dic, i);
|
||||
_assert (attr != QSE_NULL, "unable to find an attribute");
|
||||
_assert (attr->attr == i, "wrong attr value");
|
||||
_assert (qse_strcasecmp(attr->name, tmp) == 0, "wrong attr name");
|
||||
}
|
||||
|
||||
for (i = COUNT1; i < COUNT2; i++)
|
||||
{
|
||||
qse_char_t tmp[64];
|
||||
qse_strxfmt(tmp, QSE_COUNTOF(tmp), QSE_T("test%d"), i);
|
||||
attr = qse_raddic_addattr (dic, tmp, COUNT1);
|
||||
// insert different items with the same value
|
||||
_assert (attr != QSE_NULL, "unable to add an attribute");
|
||||
_assert (attr->attr == COUNT1, "wrong attr value");
|
||||
_assert (qse_strcasecmp(attr->name, tmp) == 0, "wrong attr name");
|
||||
|
||||
v = qse_raddic_findattrbyvalue (dic, COUNT1);
|
||||
_assert (attr == v, "unable to find a last added attr by value");
|
||||
}
|
||||
|
||||
for (i = COUNT1; i < COUNT2 - 1; i++)
|
||||
{
|
||||
qse_char_t tmp[64];
|
||||
int n;
|
||||
|
||||
qse_strxfmt(tmp, QSE_COUNTOF(tmp), QSE_T("test%d"), i);
|
||||
|
||||
n = qse_raddic_deleteattrbyname (dic, tmp);
|
||||
_assert (n == 0, "unable to delete an attribute");
|
||||
|
||||
v = qse_raddic_findattrbyname (dic, tmp);
|
||||
_assert (v == QSE_NULL, "attr found errorenously");
|
||||
|
||||
if (i == COUNT2 - 1)
|
||||
{
|
||||
v = qse_raddic_findattrbyvalue (dic, COUNT1);
|
||||
_assert (v == QSE_NULL, "attr of COUNT1 found errorenously");
|
||||
}
|
||||
else
|
||||
{
|
||||
qse_strxfmt(tmp, QSE_COUNTOF(tmp), QSE_T("test%d"), i + 1);
|
||||
v = qse_raddic_findattrbyname (dic, tmp);
|
||||
_assert (v != QSE_NULL && v->attr == COUNT1 && qse_strcasecmp(tmp, v->name) == 0, "unable to find an expected attr");
|
||||
|
||||
v = qse_raddic_findattrbyvalue (dic, COUNT1);
|
||||
_assert (v != QSE_NULL && v->attr == COUNT1, "unable to find the attr of COUNT1");
|
||||
}
|
||||
}
|
||||
|
||||
for (i = 0; i < COUNT1; i++)
|
||||
{
|
||||
qse_char_t tmp[64];
|
||||
int n;
|
||||
|
||||
qse_strxfmt(tmp, QSE_COUNTOF(tmp), QSE_T("test%d"), i);
|
||||
n = qse_raddic_deleteattrbyname (dic, tmp);
|
||||
_assert (n == 0, "unable to delete an attribute");
|
||||
}
|
||||
|
||||
for (i = 0; i < COUNT1; i++)
|
||||
{
|
||||
qse_char_t tmp[64];
|
||||
qse_strxfmt(tmp, QSE_COUNTOF(tmp), QSE_T("test%d"), i);
|
||||
v = qse_raddic_addattr (dic, tmp, i);
|
||||
_assert (v != QSE_NULL && v->attr == i, "unable to add an attribute");
|
||||
|
||||
qse_strxfmt(tmp, QSE_COUNTOF(tmp), QSE_T("testx%d"), i);
|
||||
v = qse_raddic_addattr (dic, tmp, i);
|
||||
_assert (v != QSE_NULL && v->attr == i, "unable to add an attribute");
|
||||
|
||||
qse_strxfmt(tmp, QSE_COUNTOF(tmp), QSE_T("testy%d"), i);
|
||||
v = qse_raddic_addattr (dic, tmp, i);
|
||||
_assert (v != QSE_NULL && v->attr == i, "unable to add an attribute");
|
||||
}
|
||||
|
||||
for (i = 0; i < COUNT1; i++)
|
||||
{
|
||||
int n;
|
||||
n = qse_raddic_deleteattrbyvalue (dic, i);
|
||||
_assert (n == 0, "unable to delete an attribute by value");
|
||||
|
||||
n = qse_raddic_deleteattrbyvalue (dic, i);
|
||||
_assert (n == 0, "unable to delete an attribute by value");
|
||||
|
||||
n = qse_raddic_deleteattrbyvalue (dic, i);
|
||||
_assert (n == 0, "unable to delete an attribute by value");
|
||||
|
||||
n = qse_raddic_deleteattrbyvalue (dic, i);
|
||||
_assert (n <= -1, "erroreneously successful attr deletion by value");
|
||||
}
|
||||
#endif
|
||||
|
||||
qse_raddic_close (dic);
|
||||
return 0;
|
||||
}
|
||||
|
||||
int main ()
|
||||
{
|
||||
qse_open_stdsios ();
|
||||
R (test1);
|
||||
R (test2);
|
||||
qse_close_stdsios ();
|
||||
return 0;
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user