update for HEAD-2002110701
[reactos.git] / ntoskrnl / mm / cont.c
1 /* $Id$
2  * 
3  * COPYRIGHT:       See COPYING in the top level directory
4  * PROJECT:         ReactOS kernel
5  * FILE:            ntoskrnl/mm/cont.c
6  * PURPOSE:         Manages continuous memory
7  * PROGRAMMER:      David Welch (welch@cwcom.net)
8  * UPDATE HISTORY:
9  *                  Created 22/05/98
10  */
11
12 /* INCLUDES *****************************************************************/
13
14 #include <ddk/ntddk.h>
15 #include <internal/mm.h>
16
17 #define NDEBUG
18 #include <internal/debug.h>
19
20 /* FUNCTIONS *****************************************************************/
21
22 VOID STATIC
23 MmFreeContinuousPage(PVOID Context, MEMORY_AREA* MemoryArea, PVOID Address, 
24                      PHYSICAL_ADDRESS PhysAddr, SWAPENTRY SwapEntry, 
25                      BOOLEAN Dirty)
26 {
27   assert(SwapEntry == 0);
28   if (PhysAddr.QuadPart != 0)
29     {
30       MmReleasePageMemoryConsumer(MC_NPPOOL, PhysAddr);
31     }
32 }
33
34 PVOID STDCALL
35 MmAllocateContiguousAlignedMemory(IN ULONG NumberOfBytes,
36                                   IN PHYSICAL_ADDRESS HighestAcceptableAddress,
37                                   IN ULONG Alignment)
38 {
39    PMEMORY_AREA MArea;
40    NTSTATUS Status;
41    PVOID BaseAddress = 0;
42    PHYSICAL_ADDRESS PBase;
43    ULONG i;
44    
45    MmLockAddressSpace(MmGetKernelAddressSpace());
46    Status = MmCreateMemoryArea(NULL,
47                                MmGetKernelAddressSpace(),
48                                MEMORY_AREA_CONTINUOUS_MEMORY,
49                                &BaseAddress,
50                                NumberOfBytes,
51                                0,
52                                &MArea,
53                                FALSE);
54    MmUnlockAddressSpace(MmGetKernelAddressSpace());
55
56    if (!NT_SUCCESS(Status))
57      {
58         return(NULL);
59      }
60    DPRINT( "Base = %x\n", BaseAddress );
61    PBase = MmGetContinuousPages(NumberOfBytes,
62                                 HighestAcceptableAddress,
63                                 Alignment);
64    if (PBase.QuadPart == 0LL)
65      {
66        MmLockAddressSpace(MmGetKernelAddressSpace());
67        MmFreeMemoryArea(MmGetKernelAddressSpace(),
68                         BaseAddress,
69                         0,
70                         NULL,
71                         NULL);
72        MmUnlockAddressSpace(MmGetKernelAddressSpace());
73        return(NULL);
74      }
75    for (i = 0; i < (PAGE_ROUND_UP(NumberOfBytes) / 4096); i++)
76      {
77         MmCreateVirtualMapping(NULL,
78                                BaseAddress + (i * 4096),
79                                PAGE_EXECUTE_READWRITE | PAGE_SYSTEM,
80                                (LARGE_INTEGER)(PBase.QuadPart + (i * 4096)),
81                                TRUE);
82      }
83    return(BaseAddress);
84 }
85
86 /**********************************************************************
87  * NAME                                                 EXPORTED
88  *      MmAllocateContiguousMemory@12
89  *
90  * DESCRIPTION
91  *      Allocates a range of physically contiguous cache aligned
92  *      memory from the non-paged pool.
93  *      
94  * ARGUMENTS
95  *      NumberOfBytes
96  *              Size of the memory block to allocate;
97  *              
98  *      HighestAcceptableAddress
99  *              Highest address valid for the caller.
100  *              
101  * RETURN VALUE
102  *      The virtual address of the memory block on success;
103  *      NULL on error.
104  *
105  * NOTE
106  *      Description taken from include/ddk/mmfuncs.h.
107  *      Code taken from ntoskrnl/mm/special.c.
108  *
109  * REVISIONS
110  *
111  */
112 PVOID STDCALL 
113 MmAllocateContiguousMemory (IN ULONG NumberOfBytes,
114                             IN PHYSICAL_ADDRESS HighestAcceptableAddress)
115 {
116   return(MmAllocateContiguousAlignedMemory(NumberOfBytes,
117                                            HighestAcceptableAddress,
118                                            PAGE_SIZE));
119 }
120
121
122 /**********************************************************************
123  * NAME                                                 EXPORTED
124  *      MmFreeContiguousMemory@4
125  *
126  * DESCRIPTION
127  *      Releases a range of physically contiguous memory allocated
128  *      with MmAllocateContiguousMemory.
129  *      
130  * ARGUMENTS
131  *      BaseAddress
132  *              Virtual address of the memory to be freed.
133  *
134  * RETURN VALUE
135  *      None.
136  *
137  * NOTE
138  *      Description taken from include/ddk/mmfuncs.h.
139  *      Code taken from ntoskrnl/mm/special.c.
140  *
141  * REVISIONS
142  *
143  */
144 VOID STDCALL 
145 MmFreeContiguousMemory(IN PVOID BaseAddress)
146 {
147    MmLockAddressSpace(MmGetKernelAddressSpace());
148    MmFreeMemoryArea(MmGetKernelAddressSpace(),
149                     BaseAddress,
150                     0,
151                     MmFreeContinuousPage,
152                     NULL);
153    MmUnlockAddressSpace(MmGetKernelAddressSpace());
154 }
155
156
157 /* EOF */