Fixed prototype for MmSetAddressRangeModified().
[reactos.git] / ntoskrnl / ke / process.c
1 /*
2  *  ReactOS kernel
3  *  Copyright (C) 1998, 1999, 2000, 2001 ReactOS Team
4  *
5  *  This program is free software; you can redistribute it and/or modify
6  *  it under the terms of the GNU General Public License as published by
7  *  the Free Software Foundation; either version 2 of the License, or
8  *  (at your option) any later version.
9  *
10  *  This program is distributed in the hope that it will be useful,
11  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
12  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13  *  GNU General Public License for more details.
14  *
15  *  You should have received a copy of the GNU General Public License
16  *  along with this program; if not, write to the Free Software
17  *  Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
18  */
19 /* $Id$
20  *
21  * PROJECT:         ReactOS kernel
22  * FILE:            ntoskrnl/ke/process.c
23  * PURPOSE:         Microkernel process management
24  * PROGRAMMER:      David Welch (welch@cwcom.net)
25  * PORTABILITY:     No.
26  * UPDATE HISTORY:
27  *                  Created 22/05/98
28  */
29
30 /* INCLUDES *****************************************************************/
31
32 #include <ddk/ntddk.h>
33 #include <internal/ke.h>
34 #include <internal/mm.h>
35 #include <internal/ps.h>
36
37 #define NDEBUG
38 #include <internal/debug.h>
39
40 /* FUNCTIONS *****************************************************************/
41
42 /*
43  * @implemented
44  */
45 VOID STDCALL
46 KeAttachProcess (PEPROCESS Process)
47 {
48    KIRQL oldlvl;
49    PETHREAD CurrentThread;
50    PULONG AttachedProcessPageDir;
51    ULONG PageDir;
52    
53    DPRINT("KeAttachProcess(Process %x)\n",Process);
54    
55    CurrentThread = PsGetCurrentThread();
56
57    if (CurrentThread->OldProcess != NULL)
58      {
59         DbgPrint("Invalid attach (thread is already attached)\n");
60         KEBUGCHECK(0);
61      }
62    
63    KeRaiseIrql(DISPATCH_LEVEL, &oldlvl);
64
65    /* The stack of the current process may be located in a page which is
66       not present in the page directory of the process we're attaching to.
67       That would lead to a page fault when this function returns. However,
68       since the processor can't call the page fault handler 'cause it can't
69       push EIP on the stack, this will show up as a stack fault which will
70       crash the entire system.
71       To prevent this, make sure the page directory of the process we're
72       attaching to is up-to-date. */
73
74    AttachedProcessPageDir = ExAllocatePageWithPhysPage(Process->Pcb.DirectoryTableBase);
75    MmUpdateStackPageDir(AttachedProcessPageDir, &CurrentThread->Tcb);
76    ExUnmapPage(AttachedProcessPageDir);
77
78    CurrentThread->OldProcess = PsGetCurrentProcess();
79    CurrentThread->ThreadsProcess = Process;
80    PageDir = Process->Pcb.DirectoryTableBase.u.LowPart;
81    DPRINT("Switching process context to %x\n",PageDir)
82    __asm__("movl %0,%%cr3\n\t"
83            : /* no outputs */
84            : "r" (PageDir));
85    
86    
87    KeLowerIrql(oldlvl);
88 }
89
90 /*
91  * @implemented
92  */
93 VOID STDCALL
94 KeDetachProcess (VOID)
95 {
96    KIRQL oldlvl;
97    PETHREAD CurrentThread;
98    ULONG PageDir;
99    
100    DPRINT("KeDetachProcess()\n");
101    
102    CurrentThread = PsGetCurrentThread();
103
104    if (CurrentThread->OldProcess == NULL)
105      {
106         DbgPrint("Invalid detach (thread was not attached)\n");
107         KEBUGCHECK(0);
108      }
109    
110    KeRaiseIrql(DISPATCH_LEVEL, &oldlvl);
111    
112    CurrentThread->ThreadsProcess = CurrentThread->OldProcess;
113    CurrentThread->OldProcess = NULL;
114    PageDir = CurrentThread->ThreadsProcess->Pcb.DirectoryTableBase.u.LowPart;
115    __asm__("movl %0,%%cr3\n\t"
116            : /* no inputs */
117            : "r" (PageDir));
118    
119    KeLowerIrql(oldlvl);
120 }
121
122 /* EOF */