[NTOS:EX] Improve NtSystemDebugControl

- Add SEH probing for user buffer
- Mark some classes as i386 only
- Explicitly return STATUS_NOT_IMPLEMENTED on disabled classes (must use KdSystemDebugControl instead)
- Explicitly return STATUS_NOT_IMPLEMENTED on not implemented classes
- Return STATUS_INVALID_INFO_CLASS on all other classes
This commit is contained in:
Hervé Poussineau 2024-09-14 08:41:20 +02:00 committed by Hermès Bélusca-Maïto
parent 0f36ef3392
commit 9e7c3770e3
No known key found for this signature in database
GPG key ID: 3B2539C65E7B93D0

View file

@ -214,48 +214,87 @@ NtSystemDebugControl(
_In_ ULONG OutputBufferLength,
_Out_opt_ PULONG ReturnLength)
{
switch (Command)
{
case SysDbgQueryModuleInformation:
case SysDbgQueryTraceInformation:
case SysDbgSetTracepoint:
case SysDbgSetSpecialCall:
case SysDbgClearSpecialCalls:
case SysDbgQuerySpecialCalls:
case SysDbgQueryVersion:
case SysDbgReadVirtual:
case SysDbgWriteVirtual:
case SysDbgReadPhysical:
case SysDbgWritePhysical:
case SysDbgReadControlSpace:
case SysDbgWriteControlSpace:
case SysDbgReadIoSpace:
case SysDbgWriteIoSpace:
case SysDbgReadMsr:
case SysDbgWriteMsr:
case SysDbgReadBusData:
case SysDbgWriteBusData:
case SysDbgCheckLowMemory:
case SysDbgGetTriageDump:
return STATUS_NOT_IMPLEMENTED;
case SysDbgBreakPoint:
case SysDbgEnableKernelDebugger:
case SysDbgDisableKernelDebugger:
case SysDbgGetAutoKdEnable:
case SysDbgSetAutoKdEnable:
case SysDbgGetPrintBufferSize:
case SysDbgSetPrintBufferSize:
case SysDbgGetKdUmExceptionEnable:
case SysDbgSetKdUmExceptionEnable:
KPROCESSOR_MODE PreviousMode = KeGetPreviousMode();
ULONG Length = 0;
NTSTATUS Status;
case SysDbgGetKdBlockEnable:
case SysDbgSetKdBlockEnable:
return KdSystemDebugControl(
Command,
InputBuffer, InputBufferLength,
OutputBuffer, OutputBufferLength,
ReturnLength, KeGetPreviousMode());
default:
return STATUS_INVALID_INFO_CLASS;
_SEH2_TRY
{
if (PreviousMode != KernelMode)
{
if (InputBufferLength)
ProbeForRead(InputBuffer, InputBufferLength, sizeof(ULONG));
if (OutputBufferLength)
ProbeForWrite(OutputBuffer, OutputBufferLength, sizeof(ULONG));
if (ReturnLength)
ProbeForWriteUlong(ReturnLength);
}
switch (Command)
{
case SysDbgQueryModuleInformation:
/* Removed in WinNT4 */
Status = STATUS_INVALID_INFO_CLASS;
break;
#ifdef _M_IX86
case SysDbgQueryTraceInformation:
case SysDbgSetTracepoint:
case SysDbgSetSpecialCall:
case SysDbgClearSpecialCalls:
case SysDbgQuerySpecialCalls:
UNIMPLEMENTED;
Status = STATUS_NOT_IMPLEMENTED;
break;
#endif
case SysDbgQueryVersion:
case SysDbgReadVirtual:
case SysDbgWriteVirtual:
case SysDbgReadPhysical:
case SysDbgWritePhysical:
case SysDbgReadControlSpace:
case SysDbgWriteControlSpace:
case SysDbgReadIoSpace:
case SysDbgWriteIoSpace:
case SysDbgReadMsr:
case SysDbgWriteMsr:
case SysDbgReadBusData:
case SysDbgWriteBusData:
case SysDbgCheckLowMemory:
/* Those are implemented in KdSystemDebugControl */
Status = STATUS_NOT_IMPLEMENTED;
break;
case SysDbgBreakPoint:
case SysDbgEnableKernelDebugger:
case SysDbgDisableKernelDebugger:
case SysDbgGetAutoKdEnable:
case SysDbgSetAutoKdEnable:
case SysDbgGetPrintBufferSize:
case SysDbgSetPrintBufferSize:
case SysDbgGetKdUmExceptionEnable:
case SysDbgSetKdUmExceptionEnable:
case SysDbgGetTriageDump:
case SysDbgGetKdBlockEnable:
case SysDbgSetKdBlockEnable:
UNIMPLEMENTED;
Status = STATUS_NOT_IMPLEMENTED;
break;
default:
Status = STATUS_INVALID_INFO_CLASS;
break;
}
if (ReturnLength)
*ReturnLength = Length;
_SEH2_YIELD(return Status);
}
_SEH2_EXCEPT(EXCEPTION_EXECUTE_HANDLER)
{
_SEH2_YIELD(return _SEH2_GetExceptionCode());
}
_SEH2_END;
}