From b081c10f8333bd68f4ebda09d72e1491259a478a Mon Sep 17 00:00:00 2001 From: hyung-hwan Date: Tue, 12 Dec 2017 03:17:02 +0000 Subject: [PATCH] fixed wrong cache handing in manipulating the attributes in raddic --- qse/include/qse/rad/raddic.h | 2 +- qse/lib/rad/raddic.c | 16 ++- qse/samples/rad/raddic01.c | 188 ++++++++++++++++++++--------------- 3 files changed, 125 insertions(+), 81 deletions(-) diff --git a/qse/include/qse/rad/raddic.h b/qse/include/qse/rad/raddic.h index 10b72edb..ada81379 100644 --- a/qse/include/qse/rad/raddic.h +++ b/qse/include/qse/rad/raddic.h @@ -96,7 +96,7 @@ struct qse_raddic_vendor_t 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_VENDOR(attr) (((attr) >> 8) & 0xFFFF) #define QSE_RADDIC_ATTR_VALUE(attr) ((attr) & 0xFF) #if defined(__cplusplus) diff --git a/qse/lib/rad/raddic.c b/qse/lib/rad/raddic.c index 1f3d0415..09520edd 100644 --- a/qse/lib/rad/raddic.c +++ b/qse/lib/rad/raddic.c @@ -500,7 +500,7 @@ int qse_raddic_deleteattrbyname (qse_raddic_t* dic, const qse_char_t* name) QSE_ASSERT (dv->attr == dv2->attr); QSE_ASSERT (dv->vendor == dv2->vendor); - /* when the attr of the given name is not the first one + /* when the attribute 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; @@ -515,11 +515,17 @@ int qse_raddic_deleteattrbyname (qse_raddic_t* dic, const qse_char_t* name) y = x; x = x->nexta; } + /* no need to update cache as the deleted item was not the first one formerly */ } else { /* this is the only attr with the attr ID. i can * safely remove it from the lookup table by value */ + if (dv->vendor == 0) + { + /* update the cache first */ + dic->base_attrs[dv->vendor] = QSE_NULL; + } qse_htl_delete (&dic->attrs_byvalue, dv); } @@ -535,6 +541,14 @@ int qse_raddic_deleteattrbyvalue (qse_raddic_t* dic, int attr) dv = qse_raddic_findattrbyvalue(dic, attr); if (!dv) return -1; + QSE_ASSERT (QSE_RADDIC_ATTR_VENDOR(attr) == dv->vendor); + + if (QSE_RADDIC_ATTR_VENDOR(attr) == 0) + { + /* update the cache */ + dic->base_attrs[QSE_RADDIC_ATTR_VALUE(attr)] = dv->nexta; + } + if (dv->nexta) { qse_htl_update (&dic->attrs_byvalue, dv->nexta); diff --git a/qse/samples/rad/raddic01.c b/qse/samples/rad/raddic01.c index c328d606..4a3767a9 100644 --- a/qse/samples/rad/raddic01.c +++ b/qse/samples/rad/raddic01.c @@ -35,15 +35,15 @@ static int test1 () _assert (vendor != QSE_NULL, "unable to add a duplicate id"); vendor = qse_raddic_findvendorbyname (dic, QSE_T("Abiyo.Net")); - _assert (vendor != QSE_NULL && vendor->vendorpec == 12365, "unabled to find a vendor named Abiyo.Net"); + _assert (vendor != QSE_NULL && vendor->vendorpec == 12365, "unable to find a vendor named Abiyo.Net"); vendor = qse_raddic_findvendorbyvalue (dic, 12365); - _assert (vendor != QSE_NULL && vendor->vendorpec == 12365, "unabled to find a vendor of value 12365"); - _assert (qse_strcasecmp(vendor->name, QSE_T("abiyo-aliased.net")) == 0, "unabled to find a vendor of value 12365"); + _assert (vendor != QSE_NULL && vendor->vendorpec == 12365, "unable to find a vendor of value 12365"); + _assert (qse_strcasecmp(vendor->name, QSE_T("abiyo-aliased.net")) == 0, "unable to find a vendor of value 12365"); vendor = qse_raddic_findvendorbyname (dic, QSE_T("Abiyo-aliased.Net")); - _assert (vendor != QSE_NULL && vendor->vendorpec == 12365, "unabled to find a vendor named Abiyo-aliased.Net"); - _assert (qse_strcasecmp(vendor->name, QSE_T("abiyo-aliased.net")) == 0, "unabled to find a vendor of value 12365"); + _assert (vendor != QSE_NULL && vendor->vendorpec == 12365, "unable to find a vendor named Abiyo-aliased.Net"); + _assert (qse_strcasecmp(vendor->name, QSE_T("abiyo-aliased.net")) == 0, "unable to find a vendor of value 12365"); #define COUNT1 600 #define COUNT2 700 @@ -201,105 +201,135 @@ static int test2 () _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"); + + attr = qse_raddic_findattrbyvalue (dic, QSE_RADDIC_ATTR_MAKE(j, i)); + _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++) + for (j = 0; j < 100; j++) { - 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) + for (i = 0; i <= 255; i++) { - v = qse_raddic_findattrbyvalue (dic, COUNT1); - _assert (v == QSE_NULL, "attr of COUNT1 found errorenously"); + qse_char_t tmp[64]; + qse_strxfmt(tmp, QSE_COUNTOF(tmp), QSE_T("testx%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"); + + qse_strxfmt(tmp, QSE_COUNTOF(tmp), QSE_T("testy%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"); } - else + } + + for (j = 0; j < 100; j++) + { + for (i = 0; i <= 255; i++) { - 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"); + qse_char_t tmp[64], tmpx[64], tmpy[64]; + qse_strxfmt(tmp, QSE_COUNTOF(tmp), QSE_T("test%d-%d"), j, i); + qse_strxfmt(tmpx, QSE_COUNTOF(tmpx), QSE_T("testx%d-%d"), j, i); + qse_strxfmt(tmpy, QSE_COUNTOF(tmpy), QSE_T("testy%d-%d"), j, i); - v = qse_raddic_findattrbyvalue (dic, COUNT1); - _assert (v != QSE_NULL && v->attr == COUNT1, "unable to find the attr of COUNT1"); + 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"); + + attr = qse_raddic_findattrbyname (dic, tmpx); + _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, tmpx) == 0, "wrong attr name"); + + attr = qse_raddic_findattrbyname (dic, tmpy); + _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, tmpy) == 0, "wrong attr name"); + + attr = qse_raddic_findattrbyvalue (dic, QSE_RADDIC_ATTR_MAKE(j, i)); + _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, tmpy) == 0, "wrong attr name"); + + _assert (attr->nexta != QSE_NULL, "unable to find an old attribute"); + _assert (attr->nexta->attr == QSE_RADDIC_ATTR_MAKE(j, i), "wrong attr value"); + _assert (qse_strcasecmp(attr->nexta->name, tmpx) == 0, "wrong attr name"); + + _assert (attr->nexta->nexta != QSE_NULL, "unable to find an old attribute"); + _assert (attr->nexta->nexta->attr == QSE_RADDIC_ATTR_MAKE(j, i), "wrong attr value"); + _assert (qse_strcasecmp(attr->nexta->nexta->name, tmp) == 0, "wrong attr name"); + + _assert (attr->nexta->nexta->nexta == QSE_NULL, "wrong attribute chian"); } } - for (i = 0; i < COUNT1; i++) + for (j = 0; j < 100; j++) { - qse_char_t tmp[64]; - int n; + for (i = 0; i <= 255; 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"); + qse_strxfmt(tmp, QSE_COUNTOF(tmp), QSE_T("testx%d-%d"), j, i); + n = qse_raddic_deleteattrbyname (dic, tmp); + _assert (n == 0, "erroreneous attribute deletion failure by name"); + } } - for (i = 0; i < COUNT1; i++) + for (j = 0; j < 100; j++) { - 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"); + for (i = 0; i <= 255; i++) + { + qse_char_t tmp[64], tmpx[64], tmpy[64]; + qse_strxfmt(tmp, QSE_COUNTOF(tmp), QSE_T("test%d-%d"), j, i); + qse_strxfmt(tmpy, QSE_COUNTOF(tmpy), QSE_T("testx%d-%d"), j, i); + qse_strxfmt(tmpy, QSE_COUNTOF(tmpy), QSE_T("testy%d-%d"), j, i); - 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"); + 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"); - 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"); + attr = qse_raddic_findattrbyname (dic, tmpx); + _assert (attr == QSE_NULL, "errorneous search success"); + + attr = qse_raddic_findattrbyname (dic, tmpy); + _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, tmpy) == 0, "wrong attr name"); + + + attr = qse_raddic_findattrbyvalue (dic, QSE_RADDIC_ATTR_MAKE(j, i)); + _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, tmpy) == 0, "wrong attr name"); + + _assert (attr->nexta != QSE_NULL, "unable to find an old attribute"); + _assert (attr->nexta->attr == QSE_RADDIC_ATTR_MAKE(j, i), "wrong attr value"); + _assert (qse_strcasecmp(attr->nexta->name, tmp) == 0, "wrong attr name"); + + _assert (attr->nexta->nexta == QSE_NULL, "wrong attribute chian"); + } } - 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, QSE_RADDIC_ATTR_MAKE(0, 0)); + _assert (n == 0, "errorneous deletion failure by value"); - n = qse_raddic_deleteattrbyvalue (dic, i); - _assert (n == 0, "unable to delete an attribute by value"); + n = qse_raddic_deleteattrbyvalue (dic, QSE_RADDIC_ATTR_MAKE(0, 0)); + _assert (n == 0, "errorneous deletion failure 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"); + n = qse_raddic_deleteattrbyvalue (dic, QSE_RADDIC_ATTR_MAKE(0, 0)); + _assert (n <= -1, "errorneous deletion success by value"); } -#endif qse_raddic_close (dic); return 0;