From e42173c8fd1e11464b98b6e03324af6c421bd0aa Mon Sep 17 00:00:00 2001 From: Alex Ionescu Date: Mon, 7 Nov 2005 04:42:28 +0000 Subject: [PATCH] - Implement PFX_NTC_ROOT/PFX_NTC_CHILD deletions in RtlRemoveUnicodePrefix, if the entry isn't a case match. svn path=/trunk/; revision=19035 --- reactos/lib/rtl/unicodeprefix.c | 66 +++++++++++++++++++++++++++++++-- 1 file changed, 63 insertions(+), 3 deletions(-) diff --git a/reactos/lib/rtl/unicodeprefix.c b/reactos/lib/rtl/unicodeprefix.c index aca6c25314f..2d06fb9ae70 100644 --- a/reactos/lib/rtl/unicodeprefix.c +++ b/reactos/lib/rtl/unicodeprefix.c @@ -175,7 +175,8 @@ NTAPI RtlRemoveUnicodePrefix(PUNICODE_PREFIX_TABLE PrefixTable, PUNICODE_PREFIX_TABLE_ENTRY PrefixTableEntry) { - PUNICODE_PREFIX_TABLE_ENTRY Entry; + PUNICODE_PREFIX_TABLE_ENTRY Entry, RefEntry, NewEntry; + PRTL_SPLAY_LINKS SplayLinks; /* Erase the last entry */ PrefixTable->LastNextEntry = NULL; @@ -186,7 +187,7 @@ RtlRemoveUnicodePrefix(PUNICODE_PREFIX_TABLE PrefixTable, /* Get the case match entry */ Entry = PrefixTableEntry->CaseMatch; - /* Now loop until we find the one matching what the caller sent */ + /* Now loop until we find one referencing what the caller sent */ while (Entry->CaseMatch != PrefixTableEntry) Entry = Entry->CaseMatch; /* We found the entry that was sent, link them to delete this entry */ @@ -195,7 +196,66 @@ RtlRemoveUnicodePrefix(PUNICODE_PREFIX_TABLE PrefixTable, else if ((PrefixTableEntry->NodeTypeCode == PFX_NTC_ROOT) || (PrefixTableEntry->NodeTypeCode == PFX_NTC_CHILD)) { - /* FIXME */ + /* Check if this entry is a case match */ + if (PrefixTableEntry->CaseMatch != PrefixTableEntry) + { + /* FIXME */ + } + else + { + /* It's not a case match, so we'll delete the actual entry */ + SplayLinks = &PrefixTableEntry->Links; + + /* Find the root entry */ + while (!RtlIsRoot(SplayLinks)) SplayLinks = RtlParent(SplayLinks); + Entry = CONTAINING_RECORD(SplayLinks, + UNICODE_PREFIX_TABLE_ENTRY, + Links); + + /* Delete the entry and check if the whole tree is gone */ + SplayLinks = RtlDelete(&PrefixTableEntry->Links); + if (!SplayLinks) + { + /* The tree is also gone now, find the entry referencing us */ + RefEntry = Entry->NextPrefixTree; + while (RefEntry->NextPrefixTree != Entry) + { + /* Not this one, move to the next entry */ + RefEntry = RefEntry->NextPrefixTree; + } + + /* Link them so this entry stops being referenced */ + RefEntry->NextPrefixTree = Entry->NextPrefixTree; + } + else if (&Entry->Links != SplayLinks) + { + /* The tree is still here, but we got moved to a new one */ + NewEntry = CONTAINING_RECORD(SplayLinks, + UNICODE_PREFIX_TABLE_ENTRY, + Links); + + /* Find the entry referencing us */ + RefEntry = Entry->NextPrefixTree; + while (RefEntry->NextPrefixTree != Entry) + { + /* Not this one, move to the next entry */ + RefEntry = RefEntry->NextPrefixTree; + } + + /* Since we got moved, make us the new root entry */ + NewEntry->NodeTypeCode = PFX_NTC_ROOT; + + /* Link us with the entry referencing the old root */ + RefEntry->NextPrefixTree = NewEntry; + + /* And link us with the old tree */ + NewEntry->NextPrefixTree = Entry->NextPrefixTree; + + /* Set the old tree as a child */ + Entry->NodeTypeCode = PFX_NTC_CHILD; + Entry->NextPrefixTree = NULL; + } + } } } -- 2.17.1