From 6e88e0163a9e3c23963fcb37fe94c936d65dfcc3 Mon Sep 17 00:00:00 2001 From: Adam Dickmeiss Date: Wed, 23 Mar 2011 18:45:25 +0100 Subject: [PATCH] Fix dict_delete that could delete wrong entry dict_delete could delete entry X if entries XY (Y suffixes) were all removed. If prefix entry X was a real entry (not just a subptr entry) it would be removed too. dict_del_string now checks if X is a real entry or not before removing.. In case of real entry subptr is just set to 0. --- dict/delete.c | 26 +++++++++++++++++++------- 1 file changed, 19 insertions(+), 7 deletions(-) diff --git a/dict/delete.c b/dict/delete.c index f3d26cb..b8ac9da 100644 --- a/dict/delete.c +++ b/dict/delete.c @@ -207,19 +207,31 @@ static int dict_del_string(Dict dict, const Dict_char *str, Dict_ptr ptr, ((char*) p+DICT_bsize(p)-sizeof(short)); info = (char*)p - indxp[-mid]; + subptr = 0; /* avoid dict_del_subtree (end of function)*/ if (r == 2) - { /* subptr page is empty and already removed */ - hi = DICT_nodir(p)-1; - while (mid < hi) + { /* subptr page became empty and is removed */ + + /* see if this entry is a real one or if it just + serves as pointer to subptr */ + if (info[sizeof(Dict_ptr)+sizeof(Dict_char)]) { - indxp[-mid] = indxp[-mid-1]; - mid++; + /* this entry do exist, set subptr to 0 */ + memcpy(info, &subptr, sizeof(subptr)); + } + else + { + /* this entry ONLY points to subptr. remove it */ + hi = DICT_nodir(p)-1; + while (mid < hi) + { + indxp[-mid] = indxp[-mid-1]; + mid++; + } + (DICT_nodir(p))--; } - (DICT_nodir(p))--; dict_bf_touch(dict->dbf, ptr); r = 1; } - subptr = 0; /* prevent dict_del_subtree (below) */ } break; } -- 1.7.10.4