This patch introduces a highly-shareable version of AVL trees both for RTL usage and for ARM3's MM_AVL_TABLE/MMADDRESS_NODE structures used by VADs on Windows (and soon, ReactOS):
[RTL]: Uncouple generic table from AVL table implementation into its own avltable.c
[RTL]: Get rid of "Austin" and fix prototypes of AVL table functions.
[RTL]: Re-implement AVL table functions, sharing as much code as possible with the SPLAY tree implementation which is pretty decent. Lookup, insert, enumeration are implemented, but not delete.
[RTL]: Make large part of the RTL AVL package into its own "support" file that can work both with MMADDRESS_NODE and RTL_BALANCED_LINKS structures. The former is used by ARM3 for VADs.
[NTOS]: Implement basic VAD AVL tree routines (Insert, LookupEmpty, GetPrevious, CheckForConflict, Locate). This is enough to insert VADs, find a free address range, and locate a VAD by address. No delete yet
Thanks to Timo Kreuzer for some clever definitions, Knuth for his genius, several online C implementations for ideas, the HPI kernel blog for insight on how Windows does it, and others.
svn path=/trunk/; revision=48173
2010-07-22 01:41:45 +00:00
|
|
|
/*
|
|
|
|
* PROJECT: ReactOS Kernel
|
|
|
|
* LICENSE: BSD - See COPYING.ARM in the top level directory
|
|
|
|
* FILE: ntoskrnl/mm/ARM3/vadnode.c
|
|
|
|
* PURPOSE: ARM Memory Manager VAD Node Algorithms
|
|
|
|
* PROGRAMMERS: ReactOS Portable Systems Group
|
2010-08-23 03:00:03 +00:00
|
|
|
* Timo Kreuzer (timo.kreuzer@reactos.org)
|
This patch introduces a highly-shareable version of AVL trees both for RTL usage and for ARM3's MM_AVL_TABLE/MMADDRESS_NODE structures used by VADs on Windows (and soon, ReactOS):
[RTL]: Uncouple generic table from AVL table implementation into its own avltable.c
[RTL]: Get rid of "Austin" and fix prototypes of AVL table functions.
[RTL]: Re-implement AVL table functions, sharing as much code as possible with the SPLAY tree implementation which is pretty decent. Lookup, insert, enumeration are implemented, but not delete.
[RTL]: Make large part of the RTL AVL package into its own "support" file that can work both with MMADDRESS_NODE and RTL_BALANCED_LINKS structures. The former is used by ARM3 for VADs.
[NTOS]: Implement basic VAD AVL tree routines (Insert, LookupEmpty, GetPrevious, CheckForConflict, Locate). This is enough to insert VADs, find a free address range, and locate a VAD by address. No delete yet
Thanks to Timo Kreuzer for some clever definitions, Knuth for his genius, several online C implementations for ideas, the HPI kernel blog for insight on how Windows does it, and others.
svn path=/trunk/; revision=48173
2010-07-22 01:41:45 +00:00
|
|
|
*/
|
|
|
|
|
|
|
|
/* INCLUDES *******************************************************************/
|
|
|
|
|
|
|
|
#include <ntoskrnl.h>
|
|
|
|
#define NDEBUG
|
|
|
|
#include <debug.h>
|
|
|
|
|
|
|
|
#line 15 "ARM³::VADNODE"
|
|
|
|
#define MODULE_INVOLVED_IN_ARM3
|
|
|
|
#include "../ARM3/miarm.h"
|
|
|
|
|
|
|
|
/* Include Mm version of AVL support */
|
|
|
|
#include "../ARM3/miavl.h"
|
|
|
|
#include "../../../lib/rtl/avlsupp.c"
|
|
|
|
|
|
|
|
/* FUNCTIONS ******************************************************************/
|
|
|
|
|
|
|
|
PMMVAD
|
|
|
|
NTAPI
|
|
|
|
MiLocateAddress(IN PVOID VirtualAddress)
|
|
|
|
{
|
|
|
|
PMMVAD FoundVad;
|
|
|
|
ULONG_PTR Vpn;
|
|
|
|
PMM_AVL_TABLE Table = &PsGetCurrentProcess()->VadRoot;
|
|
|
|
TABLE_SEARCH_RESULT SearchResult;
|
|
|
|
|
|
|
|
/* Start with the the hint */
|
|
|
|
FoundVad = (PMMVAD)Table->NodeHint;
|
|
|
|
if (!FoundVad) return NULL;
|
|
|
|
|
|
|
|
/* Check if this VPN is in the hint, if so, use it */
|
|
|
|
Vpn = (ULONG_PTR)VirtualAddress >> PAGE_SHIFT;
|
|
|
|
if ((Vpn >= FoundVad->StartingVpn) && (Vpn <= FoundVad->EndingVpn)) return FoundVad;
|
|
|
|
|
|
|
|
/* VAD hint didn't work, go look for it */
|
|
|
|
SearchResult = RtlpFindAvlTableNodeOrParent(Table,
|
|
|
|
(PVOID)Vpn,
|
|
|
|
(PMMADDRESS_NODE*)&FoundVad);
|
|
|
|
if (SearchResult != TableFoundNode) return NULL;
|
|
|
|
|
|
|
|
/* We found it, update the hint */
|
|
|
|
ASSERT(FoundVad != NULL);
|
|
|
|
ASSERT((Vpn >= FoundVad->StartingVpn) && (Vpn <= FoundVad->EndingVpn));
|
|
|
|
Table->NodeHint = FoundVad;
|
|
|
|
return FoundVad;
|
|
|
|
}
|
|
|
|
|
|
|
|
PMMADDRESS_NODE
|
|
|
|
NTAPI
|
|
|
|
MiCheckForConflictingNode(IN ULONG_PTR StartVpn,
|
|
|
|
IN ULONG_PTR EndVpn,
|
|
|
|
IN PMM_AVL_TABLE Table)
|
|
|
|
{
|
|
|
|
PMMADDRESS_NODE CurrentNode;
|
|
|
|
|
|
|
|
/* If the tree is empty, there is no conflict */
|
|
|
|
if (!Table->NumberGenericTableElements) return NULL;
|
|
|
|
|
|
|
|
/* Start looping from the right */
|
|
|
|
CurrentNode = RtlRightChildAvl(&Table->BalancedRoot);
|
|
|
|
ASSERT(CurrentNode != NULL);
|
|
|
|
while (CurrentNode)
|
|
|
|
{
|
|
|
|
/* This address comes after */
|
|
|
|
if (StartVpn > CurrentNode->EndingVpn)
|
|
|
|
{
|
|
|
|
/* Keep searching on the right */
|
|
|
|
CurrentNode = RtlRightChildAvl(CurrentNode);
|
|
|
|
}
|
|
|
|
else if (EndVpn < CurrentNode->StartingVpn)
|
|
|
|
{
|
|
|
|
/* This address ends before the node starts, search on the left */
|
|
|
|
CurrentNode = RtlLeftChildAvl(CurrentNode);
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
/* This address is part of this node, return it */
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Return either the conflicting node, or no node at all */
|
|
|
|
return CurrentNode;
|
|
|
|
}
|
|
|
|
|
|
|
|
VOID
|
|
|
|
NTAPI
|
2010-08-23 03:00:03 +00:00
|
|
|
MiInsertNode(
|
|
|
|
IN PMM_AVL_TABLE Table,
|
|
|
|
IN PMMADDRESS_NODE NewNode,
|
|
|
|
PMMADDRESS_NODE Parent,
|
|
|
|
TABLE_SEARCH_RESULT Result)
|
This patch introduces a highly-shareable version of AVL trees both for RTL usage and for ARM3's MM_AVL_TABLE/MMADDRESS_NODE structures used by VADs on Windows (and soon, ReactOS):
[RTL]: Uncouple generic table from AVL table implementation into its own avltable.c
[RTL]: Get rid of "Austin" and fix prototypes of AVL table functions.
[RTL]: Re-implement AVL table functions, sharing as much code as possible with the SPLAY tree implementation which is pretty decent. Lookup, insert, enumeration are implemented, but not delete.
[RTL]: Make large part of the RTL AVL package into its own "support" file that can work both with MMADDRESS_NODE and RTL_BALANCED_LINKS structures. The former is used by ARM3 for VADs.
[NTOS]: Implement basic VAD AVL tree routines (Insert, LookupEmpty, GetPrevious, CheckForConflict, Locate). This is enough to insert VADs, find a free address range, and locate a VAD by address. No delete yet
Thanks to Timo Kreuzer for some clever definitions, Knuth for his genius, several online C implementations for ideas, the HPI kernel blog for insight on how Windows does it, and others.
svn path=/trunk/; revision=48173
2010-07-22 01:41:45 +00:00
|
|
|
{
|
|
|
|
/* Insert it into the tree */
|
2010-08-23 03:00:03 +00:00
|
|
|
RtlpInsertAvlTreeNode(Table, NewNode, Parent, Result);
|
This patch introduces a highly-shareable version of AVL trees both for RTL usage and for ARM3's MM_AVL_TABLE/MMADDRESS_NODE structures used by VADs on Windows (and soon, ReactOS):
[RTL]: Uncouple generic table from AVL table implementation into its own avltable.c
[RTL]: Get rid of "Austin" and fix prototypes of AVL table functions.
[RTL]: Re-implement AVL table functions, sharing as much code as possible with the SPLAY tree implementation which is pretty decent. Lookup, insert, enumeration are implemented, but not delete.
[RTL]: Make large part of the RTL AVL package into its own "support" file that can work both with MMADDRESS_NODE and RTL_BALANCED_LINKS structures. The former is used by ARM3 for VADs.
[NTOS]: Implement basic VAD AVL tree routines (Insert, LookupEmpty, GetPrevious, CheckForConflict, Locate). This is enough to insert VADs, find a free address range, and locate a VAD by address. No delete yet
Thanks to Timo Kreuzer for some clever definitions, Knuth for his genius, several online C implementations for ideas, the HPI kernel blog for insight on how Windows does it, and others.
svn path=/trunk/; revision=48173
2010-07-22 01:41:45 +00:00
|
|
|
}
|
|
|
|
|
2010-07-24 04:00:22 +00:00
|
|
|
VOID
|
|
|
|
NTAPI
|
|
|
|
MiRemoveNode(IN PMMADDRESS_NODE Node,
|
|
|
|
IN PMM_AVL_TABLE Table)
|
|
|
|
{
|
|
|
|
/* Call the AVL code */
|
|
|
|
RtlpDeleteAvlTreeNode(Table, Node);
|
|
|
|
|
|
|
|
/* Decrease element count */
|
|
|
|
Table->NumberGenericTableElements--;
|
|
|
|
}
|
|
|
|
|
This patch introduces a highly-shareable version of AVL trees both for RTL usage and for ARM3's MM_AVL_TABLE/MMADDRESS_NODE structures used by VADs on Windows (and soon, ReactOS):
[RTL]: Uncouple generic table from AVL table implementation into its own avltable.c
[RTL]: Get rid of "Austin" and fix prototypes of AVL table functions.
[RTL]: Re-implement AVL table functions, sharing as much code as possible with the SPLAY tree implementation which is pretty decent. Lookup, insert, enumeration are implemented, but not delete.
[RTL]: Make large part of the RTL AVL package into its own "support" file that can work both with MMADDRESS_NODE and RTL_BALANCED_LINKS structures. The former is used by ARM3 for VADs.
[NTOS]: Implement basic VAD AVL tree routines (Insert, LookupEmpty, GetPrevious, CheckForConflict, Locate). This is enough to insert VADs, find a free address range, and locate a VAD by address. No delete yet
Thanks to Timo Kreuzer for some clever definitions, Knuth for his genius, several online C implementations for ideas, the HPI kernel blog for insight on how Windows does it, and others.
svn path=/trunk/; revision=48173
2010-07-22 01:41:45 +00:00
|
|
|
PMMADDRESS_NODE
|
|
|
|
NTAPI
|
|
|
|
MiGetPreviousNode(IN PMMADDRESS_NODE Node)
|
|
|
|
{
|
|
|
|
PMMADDRESS_NODE Parent;
|
|
|
|
|
|
|
|
/* Get the left child */
|
|
|
|
if (RtlLeftChildAvl(Node))
|
|
|
|
{
|
|
|
|
/* Get right-most child */
|
|
|
|
Node = RtlLeftChildAvl(Node);
|
|
|
|
while (RtlRightChildAvl(Node)) Node = RtlRightChildAvl(Node);
|
|
|
|
return Node;
|
|
|
|
}
|
|
|
|
|
|
|
|
Parent = RtlParentAvl(Node);
|
|
|
|
ASSERT(Parent != NULL);
|
|
|
|
while (Parent != Node)
|
|
|
|
{
|
|
|
|
/* The parent should be a right child, return the real predecessor */
|
|
|
|
if (RtlIsRightChildAvl(Node))
|
|
|
|
{
|
|
|
|
/* Return it unless it's the root */
|
|
|
|
if (Parent == RtlParentAvl(Parent)) Parent = NULL;
|
|
|
|
return Parent;
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Keep lopping until we find our parent */
|
|
|
|
Node = Parent;
|
|
|
|
Parent = RtlParentAvl(Node);
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Nothing found */
|
|
|
|
return NULL;
|
|
|
|
}
|
|
|
|
|
2010-08-23 03:00:03 +00:00
|
|
|
TABLE_SEARCH_RESULT
|
This patch introduces a highly-shareable version of AVL trees both for RTL usage and for ARM3's MM_AVL_TABLE/MMADDRESS_NODE structures used by VADs on Windows (and soon, ReactOS):
[RTL]: Uncouple generic table from AVL table implementation into its own avltable.c
[RTL]: Get rid of "Austin" and fix prototypes of AVL table functions.
[RTL]: Re-implement AVL table functions, sharing as much code as possible with the SPLAY tree implementation which is pretty decent. Lookup, insert, enumeration are implemented, but not delete.
[RTL]: Make large part of the RTL AVL package into its own "support" file that can work both with MMADDRESS_NODE and RTL_BALANCED_LINKS structures. The former is used by ARM3 for VADs.
[NTOS]: Implement basic VAD AVL tree routines (Insert, LookupEmpty, GetPrevious, CheckForConflict, Locate). This is enough to insert VADs, find a free address range, and locate a VAD by address. No delete yet
Thanks to Timo Kreuzer for some clever definitions, Knuth for his genius, several online C implementations for ideas, the HPI kernel blog for insight on how Windows does it, and others.
svn path=/trunk/; revision=48173
2010-07-22 01:41:45 +00:00
|
|
|
NTAPI
|
2010-08-23 03:00:03 +00:00
|
|
|
MiFindEmptyAddressRangeDownTree(
|
|
|
|
IN SIZE_T Length,
|
|
|
|
IN ULONG_PTR BoundaryAddress,
|
|
|
|
IN ULONG_PTR Alignment,
|
|
|
|
IN PMM_AVL_TABLE Table,
|
|
|
|
OUT PULONG_PTR Base,
|
|
|
|
OUT PMMADDRESS_NODE *Parent)
|
This patch introduces a highly-shareable version of AVL trees both for RTL usage and for ARM3's MM_AVL_TABLE/MMADDRESS_NODE structures used by VADs on Windows (and soon, ReactOS):
[RTL]: Uncouple generic table from AVL table implementation into its own avltable.c
[RTL]: Get rid of "Austin" and fix prototypes of AVL table functions.
[RTL]: Re-implement AVL table functions, sharing as much code as possible with the SPLAY tree implementation which is pretty decent. Lookup, insert, enumeration are implemented, but not delete.
[RTL]: Make large part of the RTL AVL package into its own "support" file that can work both with MMADDRESS_NODE and RTL_BALANCED_LINKS structures. The former is used by ARM3 for VADs.
[NTOS]: Implement basic VAD AVL tree routines (Insert, LookupEmpty, GetPrevious, CheckForConflict, Locate). This is enough to insert VADs, find a free address range, and locate a VAD by address. No delete yet
Thanks to Timo Kreuzer for some clever definitions, Knuth for his genius, several online C implementations for ideas, the HPI kernel blog for insight on how Windows does it, and others.
svn path=/trunk/; revision=48173
2010-07-22 01:41:45 +00:00
|
|
|
{
|
2010-08-23 03:00:03 +00:00
|
|
|
PMMADDRESS_NODE Node, LowestNode, Child;
|
|
|
|
ULONG LowVpn, HighVpn;
|
This patch introduces a highly-shareable version of AVL trees both for RTL usage and for ARM3's MM_AVL_TABLE/MMADDRESS_NODE structures used by VADs on Windows (and soon, ReactOS):
[RTL]: Uncouple generic table from AVL table implementation into its own avltable.c
[RTL]: Get rid of "Austin" and fix prototypes of AVL table functions.
[RTL]: Re-implement AVL table functions, sharing as much code as possible with the SPLAY tree implementation which is pretty decent. Lookup, insert, enumeration are implemented, but not delete.
[RTL]: Make large part of the RTL AVL package into its own "support" file that can work both with MMADDRESS_NODE and RTL_BALANCED_LINKS structures. The former is used by ARM3 for VADs.
[NTOS]: Implement basic VAD AVL tree routines (Insert, LookupEmpty, GetPrevious, CheckForConflict, Locate). This is enough to insert VADs, find a free address range, and locate a VAD by address. No delete yet
Thanks to Timo Kreuzer for some clever definitions, Knuth for his genius, several online C implementations for ideas, the HPI kernel blog for insight on how Windows does it, and others.
svn path=/trunk/; revision=48173
2010-07-22 01:41:45 +00:00
|
|
|
PFN_NUMBER PageCount;
|
|
|
|
|
|
|
|
/* Sanity checks */
|
|
|
|
ASSERT(BoundaryAddress);
|
|
|
|
ASSERT(BoundaryAddress <= ((ULONG_PTR)MM_HIGHEST_VAD_ADDRESS + 1));
|
|
|
|
|
|
|
|
/* Compute page length, make sure the boundary address is valid */
|
|
|
|
Length = PAGE_ROUND_UP(Length);
|
2010-08-23 03:00:03 +00:00
|
|
|
PageCount = Length >> PAGE_SHIFT;
|
This patch introduces a highly-shareable version of AVL trees both for RTL usage and for ARM3's MM_AVL_TABLE/MMADDRESS_NODE structures used by VADs on Windows (and soon, ReactOS):
[RTL]: Uncouple generic table from AVL table implementation into its own avltable.c
[RTL]: Get rid of "Austin" and fix prototypes of AVL table functions.
[RTL]: Re-implement AVL table functions, sharing as much code as possible with the SPLAY tree implementation which is pretty decent. Lookup, insert, enumeration are implemented, but not delete.
[RTL]: Make large part of the RTL AVL package into its own "support" file that can work both with MMADDRESS_NODE and RTL_BALANCED_LINKS structures. The former is used by ARM3 for VADs.
[NTOS]: Implement basic VAD AVL tree routines (Insert, LookupEmpty, GetPrevious, CheckForConflict, Locate). This is enough to insert VADs, find a free address range, and locate a VAD by address. No delete yet
Thanks to Timo Kreuzer for some clever definitions, Knuth for his genius, several online C implementations for ideas, the HPI kernel blog for insight on how Windows does it, and others.
svn path=/trunk/; revision=48173
2010-07-22 01:41:45 +00:00
|
|
|
if ((BoundaryAddress + 1) < Length) return STATUS_NO_MEMORY;
|
|
|
|
|
|
|
|
/* Check if the table is empty */
|
2010-08-23 03:00:03 +00:00
|
|
|
if (Table->NumberGenericTableElements == 0)
|
This patch introduces a highly-shareable version of AVL trees both for RTL usage and for ARM3's MM_AVL_TABLE/MMADDRESS_NODE structures used by VADs on Windows (and soon, ReactOS):
[RTL]: Uncouple generic table from AVL table implementation into its own avltable.c
[RTL]: Get rid of "Austin" and fix prototypes of AVL table functions.
[RTL]: Re-implement AVL table functions, sharing as much code as possible with the SPLAY tree implementation which is pretty decent. Lookup, insert, enumeration are implemented, but not delete.
[RTL]: Make large part of the RTL AVL package into its own "support" file that can work both with MMADDRESS_NODE and RTL_BALANCED_LINKS structures. The former is used by ARM3 for VADs.
[NTOS]: Implement basic VAD AVL tree routines (Insert, LookupEmpty, GetPrevious, CheckForConflict, Locate). This is enough to insert VADs, find a free address range, and locate a VAD by address. No delete yet
Thanks to Timo Kreuzer for some clever definitions, Knuth for his genius, several online C implementations for ideas, the HPI kernel blog for insight on how Windows does it, and others.
svn path=/trunk/; revision=48173
2010-07-22 01:41:45 +00:00
|
|
|
{
|
|
|
|
/* Tree is empty, the candidate address is already the best one */
|
2010-08-23 03:00:03 +00:00
|
|
|
*Base = ROUND_DOWN(BoundaryAddress + 1 - Length, Alignment);
|
|
|
|
return TableEmptyTree;
|
This patch introduces a highly-shareable version of AVL trees both for RTL usage and for ARM3's MM_AVL_TABLE/MMADDRESS_NODE structures used by VADs on Windows (and soon, ReactOS):
[RTL]: Uncouple generic table from AVL table implementation into its own avltable.c
[RTL]: Get rid of "Austin" and fix prototypes of AVL table functions.
[RTL]: Re-implement AVL table functions, sharing as much code as possible with the SPLAY tree implementation which is pretty decent. Lookup, insert, enumeration are implemented, but not delete.
[RTL]: Make large part of the RTL AVL package into its own "support" file that can work both with MMADDRESS_NODE and RTL_BALANCED_LINKS structures. The former is used by ARM3 for VADs.
[NTOS]: Implement basic VAD AVL tree routines (Insert, LookupEmpty, GetPrevious, CheckForConflict, Locate). This is enough to insert VADs, find a free address range, and locate a VAD by address. No delete yet
Thanks to Timo Kreuzer for some clever definitions, Knuth for his genius, several online C implementations for ideas, the HPI kernel blog for insight on how Windows does it, and others.
svn path=/trunk/; revision=48173
2010-07-22 01:41:45 +00:00
|
|
|
}
|
|
|
|
|
2010-08-23 03:00:03 +00:00
|
|
|
/* Calculate the initial upper margin */
|
|
|
|
HighVpn = BoundaryAddress >> PAGE_SHIFT;
|
This patch introduces a highly-shareable version of AVL trees both for RTL usage and for ARM3's MM_AVL_TABLE/MMADDRESS_NODE structures used by VADs on Windows (and soon, ReactOS):
[RTL]: Uncouple generic table from AVL table implementation into its own avltable.c
[RTL]: Get rid of "Austin" and fix prototypes of AVL table functions.
[RTL]: Re-implement AVL table functions, sharing as much code as possible with the SPLAY tree implementation which is pretty decent. Lookup, insert, enumeration are implemented, but not delete.
[RTL]: Make large part of the RTL AVL package into its own "support" file that can work both with MMADDRESS_NODE and RTL_BALANCED_LINKS structures. The former is used by ARM3 for VADs.
[NTOS]: Implement basic VAD AVL tree routines (Insert, LookupEmpty, GetPrevious, CheckForConflict, Locate). This is enough to insert VADs, find a free address range, and locate a VAD by address. No delete yet
Thanks to Timo Kreuzer for some clever definitions, Knuth for his genius, several online C implementations for ideas, the HPI kernel blog for insight on how Windows does it, and others.
svn path=/trunk/; revision=48173
2010-07-22 01:41:45 +00:00
|
|
|
|
2010-08-23 03:00:03 +00:00
|
|
|
/* Starting from the root, go down until the right-most child,
|
|
|
|
trying to stay below the boundary. */
|
|
|
|
LowestNode = Node = RtlRightChildAvl(&Table->BalancedRoot);
|
|
|
|
while ( (Child = RtlRightChildAvl(Node)) &&
|
|
|
|
Child->EndingVpn < HighVpn ) Node = Child;
|
This patch introduces a highly-shareable version of AVL trees both for RTL usage and for ARM3's MM_AVL_TABLE/MMADDRESS_NODE structures used by VADs on Windows (and soon, ReactOS):
[RTL]: Uncouple generic table from AVL table implementation into its own avltable.c
[RTL]: Get rid of "Austin" and fix prototypes of AVL table functions.
[RTL]: Re-implement AVL table functions, sharing as much code as possible with the SPLAY tree implementation which is pretty decent. Lookup, insert, enumeration are implemented, but not delete.
[RTL]: Make large part of the RTL AVL package into its own "support" file that can work both with MMADDRESS_NODE and RTL_BALANCED_LINKS structures. The former is used by ARM3 for VADs.
[NTOS]: Implement basic VAD AVL tree routines (Insert, LookupEmpty, GetPrevious, CheckForConflict, Locate). This is enough to insert VADs, find a free address range, and locate a VAD by address. No delete yet
Thanks to Timo Kreuzer for some clever definitions, Knuth for his genius, several online C implementations for ideas, the HPI kernel blog for insight on how Windows does it, and others.
svn path=/trunk/; revision=48173
2010-07-22 01:41:45 +00:00
|
|
|
|
2010-08-23 03:00:03 +00:00
|
|
|
/* Now loop the Vad nodes */
|
|
|
|
while (Node)
|
This patch introduces a highly-shareable version of AVL trees both for RTL usage and for ARM3's MM_AVL_TABLE/MMADDRESS_NODE structures used by VADs on Windows (and soon, ReactOS):
[RTL]: Uncouple generic table from AVL table implementation into its own avltable.c
[RTL]: Get rid of "Austin" and fix prototypes of AVL table functions.
[RTL]: Re-implement AVL table functions, sharing as much code as possible with the SPLAY tree implementation which is pretty decent. Lookup, insert, enumeration are implemented, but not delete.
[RTL]: Make large part of the RTL AVL package into its own "support" file that can work both with MMADDRESS_NODE and RTL_BALANCED_LINKS structures. The former is used by ARM3 for VADs.
[NTOS]: Implement basic VAD AVL tree routines (Insert, LookupEmpty, GetPrevious, CheckForConflict, Locate). This is enough to insert VADs, find a free address range, and locate a VAD by address. No delete yet
Thanks to Timo Kreuzer for some clever definitions, Knuth for his genius, several online C implementations for ideas, the HPI kernel blog for insight on how Windows does it, and others.
svn path=/trunk/; revision=48173
2010-07-22 01:41:45 +00:00
|
|
|
{
|
2010-08-23 03:00:03 +00:00
|
|
|
/* Keep track of the lowest node */
|
|
|
|
LowestNode = Node;
|
|
|
|
|
|
|
|
/* Calculate the lower margin */
|
|
|
|
LowVpn = ROUND_UP(Node->EndingVpn + 1, Alignment >> PAGE_SHIFT);
|
|
|
|
|
|
|
|
/* Check if the current bounds are suitable */
|
|
|
|
if ((HighVpn > LowVpn) && ((HighVpn - LowVpn) >= PageCount))
|
This patch introduces a highly-shareable version of AVL trees both for RTL usage and for ARM3's MM_AVL_TABLE/MMADDRESS_NODE structures used by VADs on Windows (and soon, ReactOS):
[RTL]: Uncouple generic table from AVL table implementation into its own avltable.c
[RTL]: Get rid of "Austin" and fix prototypes of AVL table functions.
[RTL]: Re-implement AVL table functions, sharing as much code as possible with the SPLAY tree implementation which is pretty decent. Lookup, insert, enumeration are implemented, but not delete.
[RTL]: Make large part of the RTL AVL package into its own "support" file that can work both with MMADDRESS_NODE and RTL_BALANCED_LINKS structures. The former is used by ARM3 for VADs.
[NTOS]: Implement basic VAD AVL tree routines (Insert, LookupEmpty, GetPrevious, CheckForConflict, Locate). This is enough to insert VADs, find a free address range, and locate a VAD by address. No delete yet
Thanks to Timo Kreuzer for some clever definitions, Knuth for his genius, several online C implementations for ideas, the HPI kernel blog for insight on how Windows does it, and others.
svn path=/trunk/; revision=48173
2010-07-22 01:41:45 +00:00
|
|
|
{
|
2010-08-23 03:00:03 +00:00
|
|
|
/* There is enough space to add our node */
|
|
|
|
LowVpn = HighVpn - PageCount;
|
|
|
|
*Base = LowVpn << PAGE_SHIFT;
|
|
|
|
|
|
|
|
/* Can we use the current node as parent? */
|
|
|
|
Child = RtlRightChildAvl(Node);
|
|
|
|
if (!Child)
|
This patch introduces a highly-shareable version of AVL trees both for RTL usage and for ARM3's MM_AVL_TABLE/MMADDRESS_NODE structures used by VADs on Windows (and soon, ReactOS):
[RTL]: Uncouple generic table from AVL table implementation into its own avltable.c
[RTL]: Get rid of "Austin" and fix prototypes of AVL table functions.
[RTL]: Re-implement AVL table functions, sharing as much code as possible with the SPLAY tree implementation which is pretty decent. Lookup, insert, enumeration are implemented, but not delete.
[RTL]: Make large part of the RTL AVL package into its own "support" file that can work both with MMADDRESS_NODE and RTL_BALANCED_LINKS structures. The former is used by ARM3 for VADs.
[NTOS]: Implement basic VAD AVL tree routines (Insert, LookupEmpty, GetPrevious, CheckForConflict, Locate). This is enough to insert VADs, find a free address range, and locate a VAD by address. No delete yet
Thanks to Timo Kreuzer for some clever definitions, Knuth for his genius, several online C implementations for ideas, the HPI kernel blog for insight on how Windows does it, and others.
svn path=/trunk/; revision=48173
2010-07-22 01:41:45 +00:00
|
|
|
{
|
2010-08-23 03:00:03 +00:00
|
|
|
/* Node has no right child, so use it as parent */
|
|
|
|
*Parent = Node;
|
|
|
|
return TableInsertAsRight;
|
This patch introduces a highly-shareable version of AVL trees both for RTL usage and for ARM3's MM_AVL_TABLE/MMADDRESS_NODE structures used by VADs on Windows (and soon, ReactOS):
[RTL]: Uncouple generic table from AVL table implementation into its own avltable.c
[RTL]: Get rid of "Austin" and fix prototypes of AVL table functions.
[RTL]: Re-implement AVL table functions, sharing as much code as possible with the SPLAY tree implementation which is pretty decent. Lookup, insert, enumeration are implemented, but not delete.
[RTL]: Make large part of the RTL AVL package into its own "support" file that can work both with MMADDRESS_NODE and RTL_BALANCED_LINKS structures. The former is used by ARM3 for VADs.
[NTOS]: Implement basic VAD AVL tree routines (Insert, LookupEmpty, GetPrevious, CheckForConflict, Locate). This is enough to insert VADs, find a free address range, and locate a VAD by address. No delete yet
Thanks to Timo Kreuzer for some clever definitions, Knuth for his genius, several online C implementations for ideas, the HPI kernel blog for insight on how Windows does it, and others.
svn path=/trunk/; revision=48173
2010-07-22 01:41:45 +00:00
|
|
|
}
|
2010-08-23 03:00:03 +00:00
|
|
|
else
|
This patch introduces a highly-shareable version of AVL trees both for RTL usage and for ARM3's MM_AVL_TABLE/MMADDRESS_NODE structures used by VADs on Windows (and soon, ReactOS):
[RTL]: Uncouple generic table from AVL table implementation into its own avltable.c
[RTL]: Get rid of "Austin" and fix prototypes of AVL table functions.
[RTL]: Re-implement AVL table functions, sharing as much code as possible with the SPLAY tree implementation which is pretty decent. Lookup, insert, enumeration are implemented, but not delete.
[RTL]: Make large part of the RTL AVL package into its own "support" file that can work both with MMADDRESS_NODE and RTL_BALANCED_LINKS structures. The former is used by ARM3 for VADs.
[NTOS]: Implement basic VAD AVL tree routines (Insert, LookupEmpty, GetPrevious, CheckForConflict, Locate). This is enough to insert VADs, find a free address range, and locate a VAD by address. No delete yet
Thanks to Timo Kreuzer for some clever definitions, Knuth for his genius, several online C implementations for ideas, the HPI kernel blog for insight on how Windows does it, and others.
svn path=/trunk/; revision=48173
2010-07-22 01:41:45 +00:00
|
|
|
{
|
2010-08-23 03:00:03 +00:00
|
|
|
/* Node has a right child, find most left grand child */
|
|
|
|
Node = Child;
|
|
|
|
while ((Child = RtlLeftChildAvl(Node))) Node = Child;
|
|
|
|
*Parent = Node;
|
|
|
|
return TableInsertAsLeft;
|
This patch introduces a highly-shareable version of AVL trees both for RTL usage and for ARM3's MM_AVL_TABLE/MMADDRESS_NODE structures used by VADs on Windows (and soon, ReactOS):
[RTL]: Uncouple generic table from AVL table implementation into its own avltable.c
[RTL]: Get rid of "Austin" and fix prototypes of AVL table functions.
[RTL]: Re-implement AVL table functions, sharing as much code as possible with the SPLAY tree implementation which is pretty decent. Lookup, insert, enumeration are implemented, but not delete.
[RTL]: Make large part of the RTL AVL package into its own "support" file that can work both with MMADDRESS_NODE and RTL_BALANCED_LINKS structures. The former is used by ARM3 for VADs.
[NTOS]: Implement basic VAD AVL tree routines (Insert, LookupEmpty, GetPrevious, CheckForConflict, Locate). This is enough to insert VADs, find a free address range, and locate a VAD by address. No delete yet
Thanks to Timo Kreuzer for some clever definitions, Knuth for his genius, several online C implementations for ideas, the HPI kernel blog for insight on how Windows does it, and others.
svn path=/trunk/; revision=48173
2010-07-22 01:41:45 +00:00
|
|
|
}
|
|
|
|
}
|
2010-08-23 03:00:03 +00:00
|
|
|
|
|
|
|
/* Update the upper margin if neccessary */
|
|
|
|
if (Node->StartingVpn < HighVpn) HighVpn = Node->StartingVpn;
|
|
|
|
|
|
|
|
/* Go to the next lower node */
|
|
|
|
Node = MiGetPreviousNode(Node);
|
This patch introduces a highly-shareable version of AVL trees both for RTL usage and for ARM3's MM_AVL_TABLE/MMADDRESS_NODE structures used by VADs on Windows (and soon, ReactOS):
[RTL]: Uncouple generic table from AVL table implementation into its own avltable.c
[RTL]: Get rid of "Austin" and fix prototypes of AVL table functions.
[RTL]: Re-implement AVL table functions, sharing as much code as possible with the SPLAY tree implementation which is pretty decent. Lookup, insert, enumeration are implemented, but not delete.
[RTL]: Make large part of the RTL AVL package into its own "support" file that can work both with MMADDRESS_NODE and RTL_BALANCED_LINKS structures. The former is used by ARM3 for VADs.
[NTOS]: Implement basic VAD AVL tree routines (Insert, LookupEmpty, GetPrevious, CheckForConflict, Locate). This is enough to insert VADs, find a free address range, and locate a VAD by address. No delete yet
Thanks to Timo Kreuzer for some clever definitions, Knuth for his genius, several online C implementations for ideas, the HPI kernel blog for insight on how Windows does it, and others.
svn path=/trunk/; revision=48173
2010-07-22 01:41:45 +00:00
|
|
|
}
|
|
|
|
|
2010-08-23 03:00:03 +00:00
|
|
|
/* Check if there's enough space before the lowest Vad */
|
|
|
|
LowVpn = ROUND_UP((ULONG_PTR)MI_LOWEST_VAD_ADDRESS, Alignment) >> PAGE_SHIFT;
|
|
|
|
if ((HighVpn > LowVpn) && ((HighVpn - LowVpn) >= PageCount))
|
This patch introduces a highly-shareable version of AVL trees both for RTL usage and for ARM3's MM_AVL_TABLE/MMADDRESS_NODE structures used by VADs on Windows (and soon, ReactOS):
[RTL]: Uncouple generic table from AVL table implementation into its own avltable.c
[RTL]: Get rid of "Austin" and fix prototypes of AVL table functions.
[RTL]: Re-implement AVL table functions, sharing as much code as possible with the SPLAY tree implementation which is pretty decent. Lookup, insert, enumeration are implemented, but not delete.
[RTL]: Make large part of the RTL AVL package into its own "support" file that can work both with MMADDRESS_NODE and RTL_BALANCED_LINKS structures. The former is used by ARM3 for VADs.
[NTOS]: Implement basic VAD AVL tree routines (Insert, LookupEmpty, GetPrevious, CheckForConflict, Locate). This is enough to insert VADs, find a free address range, and locate a VAD by address. No delete yet
Thanks to Timo Kreuzer for some clever definitions, Knuth for his genius, several online C implementations for ideas, the HPI kernel blog for insight on how Windows does it, and others.
svn path=/trunk/; revision=48173
2010-07-22 01:41:45 +00:00
|
|
|
{
|
2010-08-23 03:00:03 +00:00
|
|
|
/* There is enough space to add our address */
|
|
|
|
LowVpn = HighVpn - PageCount;
|
|
|
|
*Base = LowVpn << PAGE_SHIFT;
|
|
|
|
*Parent = LowestNode;
|
|
|
|
return TableInsertAsLeft;
|
This patch introduces a highly-shareable version of AVL trees both for RTL usage and for ARM3's MM_AVL_TABLE/MMADDRESS_NODE structures used by VADs on Windows (and soon, ReactOS):
[RTL]: Uncouple generic table from AVL table implementation into its own avltable.c
[RTL]: Get rid of "Austin" and fix prototypes of AVL table functions.
[RTL]: Re-implement AVL table functions, sharing as much code as possible with the SPLAY tree implementation which is pretty decent. Lookup, insert, enumeration are implemented, but not delete.
[RTL]: Make large part of the RTL AVL package into its own "support" file that can work both with MMADDRESS_NODE and RTL_BALANCED_LINKS structures. The former is used by ARM3 for VADs.
[NTOS]: Implement basic VAD AVL tree routines (Insert, LookupEmpty, GetPrevious, CheckForConflict, Locate). This is enough to insert VADs, find a free address range, and locate a VAD by address. No delete yet
Thanks to Timo Kreuzer for some clever definitions, Knuth for his genius, several online C implementations for ideas, the HPI kernel blog for insight on how Windows does it, and others.
svn path=/trunk/; revision=48173
2010-07-22 01:41:45 +00:00
|
|
|
}
|
2010-08-23 03:00:03 +00:00
|
|
|
|
This patch introduces a highly-shareable version of AVL trees both for RTL usage and for ARM3's MM_AVL_TABLE/MMADDRESS_NODE structures used by VADs on Windows (and soon, ReactOS):
[RTL]: Uncouple generic table from AVL table implementation into its own avltable.c
[RTL]: Get rid of "Austin" and fix prototypes of AVL table functions.
[RTL]: Re-implement AVL table functions, sharing as much code as possible with the SPLAY tree implementation which is pretty decent. Lookup, insert, enumeration are implemented, but not delete.
[RTL]: Make large part of the RTL AVL package into its own "support" file that can work both with MMADDRESS_NODE and RTL_BALANCED_LINKS structures. The former is used by ARM3 for VADs.
[NTOS]: Implement basic VAD AVL tree routines (Insert, LookupEmpty, GetPrevious, CheckForConflict, Locate). This is enough to insert VADs, find a free address range, and locate a VAD by address. No delete yet
Thanks to Timo Kreuzer for some clever definitions, Knuth for his genius, several online C implementations for ideas, the HPI kernel blog for insight on how Windows does it, and others.
svn path=/trunk/; revision=48173
2010-07-22 01:41:45 +00:00
|
|
|
/* No address space left at all */
|
2010-08-23 03:00:03 +00:00
|
|
|
*Base = 0;
|
|
|
|
*Parent = NULL;
|
|
|
|
return TableFoundNode;
|
This patch introduces a highly-shareable version of AVL trees both for RTL usage and for ARM3's MM_AVL_TABLE/MMADDRESS_NODE structures used by VADs on Windows (and soon, ReactOS):
[RTL]: Uncouple generic table from AVL table implementation into its own avltable.c
[RTL]: Get rid of "Austin" and fix prototypes of AVL table functions.
[RTL]: Re-implement AVL table functions, sharing as much code as possible with the SPLAY tree implementation which is pretty decent. Lookup, insert, enumeration are implemented, but not delete.
[RTL]: Make large part of the RTL AVL package into its own "support" file that can work both with MMADDRESS_NODE and RTL_BALANCED_LINKS structures. The former is used by ARM3 for VADs.
[NTOS]: Implement basic VAD AVL tree routines (Insert, LookupEmpty, GetPrevious, CheckForConflict, Locate). This is enough to insert VADs, find a free address range, and locate a VAD by address. No delete yet
Thanks to Timo Kreuzer for some clever definitions, Knuth for his genius, several online C implementations for ideas, the HPI kernel blog for insight on how Windows does it, and others.
svn path=/trunk/; revision=48173
2010-07-22 01:41:45 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
/* EOF */
|