fixed uninitialized variable warning
[reactos.git] / reactos / ntoskrnl / ke / exception.c
1 /*
2 * COPYRIGHT: See COPYING in the top level directory
3 * PROJECT: ReactOS Kernel
4 * FILE: ntoskrnl/ke/exception.c
5 * PURPOSE: Platform independent exception handling
6 * PROGRAMMER: Alex Ionescu (alex@relsoft.net)
7 */
8
9 /* INCLUDES *****************************************************************/
10
11 #include <ntoskrnl.h>
12 #define NDEBUG
13 #include <internal/debug.h>
14
15 /* FUNCTIONS ****************************************************************/
16
17 VOID
18 NTAPI
19 KiContinuePreviousModeUser(IN PCONTEXT Context,
20 IN PKEXCEPTION_FRAME ExceptionFrame,
21 IN PKTRAP_FRAME TrapFrame)
22 {
23 CONTEXT LocalContext;
24
25 /* We'll have to make a copy and probe it */
26 ProbeForRead(Context, sizeof(CONTEXT), sizeof(ULONG));
27 RtlMoveMemory(&LocalContext, Context, sizeof(CONTEXT));
28 Context = &LocalContext;
29
30 /* Convert the context into Exception/Trap Frames */
31 KeContextToTrapFrame(&LocalContext, ExceptionFrame, TrapFrame, UserMode);
32 }
33
34 NTSTATUS
35 NTAPI
36 KiContinue(IN PCONTEXT Context,
37 IN PKEXCEPTION_FRAME ExceptionFrame,
38 IN PKTRAP_FRAME TrapFrame)
39 {
40 NTSTATUS Status = STATUS_SUCCESS;
41 KIRQL OldIrql = APC_LEVEL;
42 KPROCESSOR_MODE PreviousMode = KeGetPreviousMode();
43
44 /* Raise to APC_LEVEL, only if needed */
45 if (KeGetCurrentIrql() < APC_LEVEL)
46 {
47 /* Raise to APC_LEVEL */
48 KeRaiseIrql(APC_LEVEL, &OldIrql);
49 }
50
51 /* Set up SEH to validate the context */
52 _SEH_TRY
53 {
54 /* Check the previous mode */
55 if (PreviousMode != KernelMode)
56 {
57 /* Validate from user-mode */
58 KiContinuePreviousModeUser(Context,
59 ExceptionFrame,
60 TrapFrame);
61 }
62 else
63 {
64 /* Convert the context into Exception/Trap Frames */
65 KeContextToTrapFrame(Context, ExceptionFrame, TrapFrame, KernelMode);
66 }
67 }
68 _SEH_HANDLE
69 {
70 Status = _SEH_GetExceptionCode();
71 }
72 _SEH_END;
73
74 /* Lower the IRQL if needed */
75 if (OldIrql < APC_LEVEL) KeLowerIrql(OldIrql);
76
77 /* Return status */
78 return Status;
79 }
80
81 NTSTATUS
82 NTAPI
83 KiRaiseException(PEXCEPTION_RECORD ExceptionRecord,
84 PCONTEXT Context,
85 PKEXCEPTION_FRAME ExceptionFrame,
86 PKTRAP_FRAME TrapFrame,
87 BOOLEAN SearchFrames)
88 {
89 KPROCESSOR_MODE PreviousMode = KeGetPreviousMode();
90 CONTEXT LocalContext;
91 EXCEPTION_RECORD LocalExceptionRecord;
92 ULONG ParameterCount, Size;
93 NTSTATUS Status = STATUS_SUCCESS;
94 DPRINT1("KiRaiseException\n");
95
96 /* Set up SEH */
97 _SEH_TRY
98 {
99 /* Check the previous mode */
100 if (PreviousMode != KernelMode)
101 {
102 #if 0
103 /* Probe the context */
104 ProbeForRead(Context, sizeof(CONTEXT), sizeof(ULONG));
105
106 /* Probe the Exception Record */
107 ProbeForRead(ExceptionRecord,
108 FIELD_OFFSET(EXCEPTION_RECORD, NumberParameters) +
109 sizeof(ULONG),
110 sizeof(ULONG));
111 #endif
112 /* Validate the maximum parameters */
113 if ((ParameterCount = ExceptionRecord->NumberParameters) >
114 EXCEPTION_MAXIMUM_PARAMETERS)
115 {
116 /* Too large */
117 Status = STATUS_INVALID_PARAMETER;
118 _SEH_LEAVE;
119 }
120
121 /* Probe the entire parameters now*/
122 Size = (sizeof(EXCEPTION_RECORD) -
123 ((EXCEPTION_MAXIMUM_PARAMETERS - ParameterCount) * sizeof(ULONG)));
124 ProbeForRead(ExceptionRecord, Size, sizeof(ULONG));
125
126 /* Now make copies in the stack */
127 RtlMoveMemory(&LocalContext, Context, sizeof(CONTEXT));
128 RtlMoveMemory(&LocalExceptionRecord, ExceptionRecord, Size);
129 Context = &LocalContext;
130 ExceptionRecord = &LocalExceptionRecord;
131
132 /* Update the parameter count */
133 ExceptionRecord->NumberParameters = ParameterCount;
134 }
135 }
136 _SEH_HANDLE
137 {
138 Status = _SEH_GetExceptionCode();
139 }
140 _SEH_END;
141
142 if (NT_SUCCESS(Status))
143 {
144 /* Convert the context record */
145 KeContextToTrapFrame(Context, ExceptionFrame, TrapFrame, PreviousMode);
146
147 /* Dispatch the exception */
148 KiDispatchException(ExceptionRecord,
149 ExceptionFrame,
150 TrapFrame,
151 PreviousMode,
152 SearchFrames);
153 }
154
155 /* Return the status */
156 return Status;
157 }
158
159 /* EOF */