00218 :
00219
00220 This function
is called to raise an exception. The exception can be
00221 raised as a first or second chance exception.
00222
00223 Arguments:
00224
00225 ExceptionRecord - Supplies a pointer to an exception record.
00226
00227 ContextRecord - Supplies a pointer to a context record.
00228
00229 ExceptionFrame - Supplies a pointer to an exception frame.
00230
00231 TrapFrame - Supplies a pointer to a trap frame.
00232
00233 FirstChance - Supplies a
boolean value that specifies whether
this is
00234
the first (TRUE) or second (FALSE) chance for the exception.
00235
00236 Return Value:
00237
00238 STATUS_ACCESS_VIOLATION is returned if either the exception or the context
00239 record is not readable from user mode.
00240
00241 STATUS_DATATYPE_MISALIGNMENT is returned if the exception record or the
00242 context record are not properly aligned.
00243
00244 STATUS_INVALID_PARAMETER is returned if the number of exception parameters
00245 is greater than the maximum allowable number of exception parameters.
00246
00247 STATUS_SUCCESS is returned if the exception is dispatched and handled.
00248
00249 --*/
00250
00251 {
00252
00253 CONTEXT ContextRecord2;
00254 EXCEPTION_RECORD ExceptionRecord2;
00255 ULONG Length;
00256 ULONG Params;
00257
KPROCESSOR_MODE PreviousMode;
00258
00259
00260
00261
00262
00263
00264
00265
00266
try {
00267
00268
00269
00270
00271
00272
00273
00274 PreviousMode = KeGetPreviousMode();
00275
if (PreviousMode !=
KernelMode) {
00276
ProbeForRead(ContextRecord,
sizeof(CONTEXT), CONTEXT_ALIGN);
00277
ProbeForRead(ExceptionRecord,
00278 FIELD_OFFSET (EXCEPTION_RECORD, NumberParameters) +
00279
sizeof (ExceptionRecord->NumberParameters),
sizeof(ULONG));
00280 Params = ExceptionRecord->NumberParameters;
00281
if (Params > EXCEPTION_MAXIMUM_PARAMETERS) {
00282
return STATUS_INVALID_PARAMETER;
00283 }
00284
00285
00286
00287
00288
00289
00290 Length = (
sizeof(EXCEPTION_RECORD) -
00291 ((EXCEPTION_MAXIMUM_PARAMETERS - Params) *
00292
sizeof(ExceptionRecord->ExceptionInformation[0])));
00293
00294
00295
00296
00297
ProbeForRead(ExceptionRecord, Length,
sizeof(ULONG));
00298
00299
00300
00301
00302
00303
00304 RtlMoveMemory(&ContextRecord2, ContextRecord,
sizeof(CONTEXT));
00305 RtlMoveMemory(&ExceptionRecord2, ExceptionRecord, Length);
00306 ContextRecord = &ContextRecord2;
00307 ExceptionRecord = &ExceptionRecord2;
00308
00309
00310
00311
00312 ExceptionRecord->NumberParameters = Params;
00313 }
00314
00315
00316
00317
00318
00319
00320
00321 } except(EXCEPTION_EXECUTE_HANDLER) {
00322
return GetExceptionCode();
00323 }
00324
00325
00326
00327
00328
00329
00330
KeContextToKframes(TrapFrame,
00331 ExceptionFrame,
00332 ContextRecord,
00333 ContextRecord->ContextFlags,
00334 PreviousMode);
00335
00336
00337
00338
00339
00340
00341
00342
00343
00344 ExceptionRecord->ExceptionCode &= 0xefffffff;
00345
KiDispatchException(ExceptionRecord,
00346 ExceptionFrame,
00347 TrapFrame,
00348 PreviousMode,
00349 FirstChance);
00350
00351
return STATUS_SUCCESS;
00352 }
}