00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
#include "kdp.h"
00022
00023
00024
00025
00026
00027 #define BAUD_OPTION "BAUDRATE"
00028 #define PORT_OPTION "DEBUGPORT"
00029
00030
00031
#ifdef ALLOC_PRAGMA
00032
#pragma alloc_text(PAGEKD, KdInitSystem)
00033
#pragma alloc_text(PAGEKD, KdUpdateDataBlock)
00034
#endif
00035
00036
00037
VOID
00038 KdUpdateDataBlock(
00039 VOID
00040 )
00041
00042
00043
00044
00045
00046
00047
00048
00049 {
00050
KdDebuggerDataBlock.KeUserCallbackDispatcher = (ULONG_PTR)
KeUserCallbackDispatcher;
00051 }
00052
00053
00054 ULONG_PTR
00055 KdGetDataBlock(
00056 VOID
00057 )
00058
00059
00060
00061
00062
00063
00064
00065
00066 {
00067
return (ULONG_PTR)(&
KdDebuggerDataBlock);
00068 }
00069
00070
00071 BOOLEAN
00072 KdInitSystem(
00073 IN
PLOADER_PARAMETER_BLOCK LoaderBlock OPTIONAL,
00074 BOOLEAN StopInDebugger
00075 )
00076
00077
00078
00079
00080
00081
00082
00083
00084
00085
00086
00087
00088
00089
00090
00091
00092
00093
00094
00095
00096
00097 {
00098
00099 ULONG
Index;
00100 BOOLEAN Initialize;
00101 PCHAR Options;
00102 PCHAR BaudOption;
00103 PCHAR PortOption;
00104
00105
00106
00107
00108
00109
if (
KdDebuggerEnabled !=
FALSE) {
00110
return TRUE;
00111 }
00112
00113
KiDebugRoutine =
KdpStub;
00114
00115
00116
00117
00118
00119
00120
00121
00122
00123
if (LoaderBlock !=
NULL) {
00124
00125
KdpNtosImageBase = CONTAINING_RECORD(
00126 (LoaderBlock->LoadOrderListHead.Flink),
00127 LDR_DATA_TABLE_ENTRY,
00128 InLoadOrderLinks)->DllBase;
00129
00130
00131
00132
00133
00134 InitializeListHead(&
KdpDebuggerDataListHead);
00135
00136
00137
00138
00139
00140
00141
00142
KdDebuggerDataBlock.KernBase = (ULONG_PTR)
KdpNtosImageBase;
00143
00144
KdRegisterDebuggerDataBlock(KDBG_TAG,
00145 &
KdDebuggerDataBlock.Header,
00146
sizeof(
KdDebuggerDataBlock));
00147
00148
if (LoaderBlock->LoadOptions !=
NULL) {
00149 Options = LoaderBlock->LoadOptions;
00150 _strupr(Options);
00151
00152
00153
00154
00155
00156
00157 Initialize =
TRUE;
00158 PortOption = strstr(Options,
PORT_OPTION);
00159 BaudOption = strstr(Options,
BAUD_OPTION);
00160
if ((PortOption ==
NULL) && (BaudOption ==
NULL)) {
00161
if (strstr(Options,
"DEBUG") ==
NULL) {
00162 Initialize =
FALSE;
00163 }
00164
00165 }
else {
00166
if (PortOption) {
00167 PortOption = strstr(PortOption,
"COM");
00168
if (PortOption) {
00169
KdDebugParameters.
CommunicationPort =
00170 atol(PortOption + 3);
00171 }
00172 }
00173
00174
if (BaudOption) {
00175 BaudOption +=
strlen(
BAUD_OPTION);
00176
while (*BaudOption ==
' ') {
00177 BaudOption++;
00178 }
00179
00180
if (*BaudOption !=
'\0') {
00181
KdDebugParameters.
BaudRate = atol(BaudOption + 1);
00182 }
00183 }
00184 }
00185
00186
00187
00188
00189
00190
if (strstr(Options,
"NODEBUG")) {
00191 Initialize =
FALSE;
00192
KdPitchDebugger =
TRUE;
00193 }
00194
00195
if (strstr(Options,
"CRASHDEBUG")) {
00196 Initialize =
FALSE;
00197
KdPitchDebugger =
FALSE;
00198 }
00199
00200 }
else {
00201
00202
00203
00204
00205
00206
KdPitchDebugger =
TRUE;
00207 Initialize =
FALSE;
00208 }
00209
00210 }
else {
00211 Initialize =
TRUE;
00212 }
00213
00214
if ((
KdPortInitialize(&
KdDebugParameters, LoaderBlock, Initialize) ==
FALSE) ||
00215 (Initialize ==
FALSE)) {
00216
return(
TRUE);
00217 }
00218
00219
00220
00221
00222
00223
KiDebugRoutine =
KdpTrap;
00224
00225
if (!
KdpDebuggerStructuresInitialized) {
00226
00227
KiDebugSwitchRoutine =
KdpSwitchProcessor;
00228
KdpBreakpointInstruction =
KDP_BREAKPOINT_VALUE;
00229
KdpOweBreakpoint =
FALSE;
00230
00231
00232
00233
00234
00235
for (
Index = 0;
Index < BREAKPOINT_TABLE_SIZE;
Index += 1) {
00236
KdpBreakpointTable[
Index].
Flags = 0;
00237
KdpBreakpointTable[
Index].
Address =
NULL;
00238
KdpBreakpointTable[
Index].
DirectoryTableBase = 0
L;
00239 }
00240
00241
00242
00243
00244
KeInitializeDpc(&
KdpTimeSlipDpc,
KdpTimeSlipDpcRoutine,
NULL);
00245
KeInitializeTimer(&
KdpTimeSlipTimer);
00246
ExInitializeWorkItem(&
KdpTimeSlipWorkItem,
KdpTimeSlipWork,
NULL);
00247
00248
KdpDebuggerStructuresInitialized =
TRUE ;
00249 }
00250
00251
00252
00253
00254
00255
KeQueryPerformanceCounter(&
KdPerformanceCounterRate);
00256
KdTimerStart.HighPart = 0
L;
00257
KdTimerStart.LowPart = 0
L;
00258
00259
00260
00261
00262
00263
00264
KdpNextPacketIdToSend = INITIAL_PACKET_ID | SYNC_PACKET_ID;
00265
KdpPacketIdExpected = INITIAL_PACKET_ID;
00266
00267
00268
00269
00270
KdPitchDebugger =
FALSE;
00271
KdDebuggerEnabled =
TRUE;
00272 SharedUserData->KdDebuggerEnabled = 0x00000001;
00273
00274
00275
00276
00277
00278
if (StopInDebugger) {
00279 DbgBreakPoint();
00280 }
00281
00282
return TRUE;
00283 }
00284
00285
00286 BOOLEAN
00287 KdRegisterDebuggerDataBlock(
00288 IN ULONG Tag,
00289 IN PDBGKD_DEBUG_DATA_HEADER64 DataHeader,
00290 IN ULONG Size
00291 )
00292
00293
00294
00295
00296
00297
00298
00299
00300
00301
00302
00303
00304
00305
00306
00307
00308
00309
00310
00311
00312
00313
00314
00315
00316
00317
00318
00319
00320
00321
00322 {
00323 KIRQL OldIrql;
00324 PLIST_ENTRY
List;
00325
PDBGKD_DEBUG_DATA_HEADER64 Header;
00326
00327
KeAcquireSpinLock(&
KdpDataSpinLock, &OldIrql);
00328
00329
00330
00331
00332
00333
List =
KdpDebuggerDataListHead.Flink;
00334
00335
while (
List != &
KdpDebuggerDataListHead) {
00336
00337
Header = CONTAINING_RECORD(
List, DBGKD_DEBUG_DATA_HEADER64,
List);
00338
00339
List =
List->Flink;
00340
00341
if ((
Header == DataHeader) || (
Header->OwnerTag == Tag)) {
00342
KeReleaseSpinLock(&
KdpDataSpinLock, OldIrql);
00343
return FALSE;
00344 }
00345 }
00346
00347
00348
00349
00350
00351 DataHeader->OwnerTag = Tag;
00352 DataHeader->Size =
Size;
00353
00354 InsertTailList(&
KdpDebuggerDataListHead, (PLIST_ENTRY)(&DataHeader->List));
00355
00356
KeReleaseSpinLock(&
KdpDataSpinLock, OldIrql);
00357
00358
return TRUE;
00359 }
00360
00361
00362
VOID
00363 KdDeregisterDebuggerDataBlock(
00364 IN PDBGKD_DEBUG_DATA_HEADER64 DataHeader
00365 )
00366
00367
00368
00369
00370
00371
00372
00373
00374
00375
00376
00377
00378
00379
00380
00381
00382
00383
00384
00385 {
00386 KIRQL OldIrql;
00387 PLIST_ENTRY
List;
00388
PDBGKD_DEBUG_DATA_HEADER64 Header;
00389
00390
KeAcquireSpinLock(&
KdpDataSpinLock, &OldIrql);
00391
00392
00393
00394
00395
00396
List =
KdpDebuggerDataListHead.Flink;
00397
00398
while (
List != &
KdpDebuggerDataListHead) {
00399
00400
Header = CONTAINING_RECORD(
List, DBGKD_DEBUG_DATA_HEADER64,
List);
00401
List =
List->Flink;
00402
00403
if (DataHeader ==
Header) {
00404 RemoveEntryList((PLIST_ENTRY)(&DataHeader->List));
00405
break;
00406 }
00407 }
00408
00409
KeReleaseSpinLock(&
KdpDataSpinLock, OldIrql);
00410 }
00411
00412
00413
VOID
00414 KdLogDbgPrint(
00415 IN PSTRING String
00416 )
00417 {
00418 KIRQL OldIrql;
00419 ULONG Length;
00420 ULONG LengthCopied;
00421
00422
for (; ;) {
00423
if (KeTestSpinLock (&
KdpPrintSpinLock)) {
00424
KeRaiseIrql (
HIGH_LEVEL, &OldIrql);
00425
if (
KiTryToAcquireSpinLock(&
KdpPrintSpinLock)) {
00426
break;
00427 }
00428
KeLowerIrql(OldIrql);
00429 }
00430 }
00431
00432
if (
KdPrintCircularBuffer) {
00433 Length =
String->Length;
00434
00435
00436
00437
if (Length >
KDPRINTBUFFERSIZE) {
00438 Length =
KDPRINTBUFFERSIZE;
00439 }
00440
00441
if (
KdPrintWritePointer + Length <=
KdPrintCircularBuffer+
KDPRINTBUFFERSIZE) {
00442 LengthCopied =
KdpMoveMemory(
KdPrintWritePointer,
String->Buffer, Length);
00443
KdPrintWritePointer += LengthCopied;
00444
if (
KdPrintWritePointer >=
KdPrintCircularBuffer+
KDPRINTBUFFERSIZE) {
00445
KdPrintWritePointer =
KdPrintCircularBuffer;
00446
KdPrintRolloverCount++;
00447 }
00448 }
else {
00449 ULONG First = (ULONG)(
KdPrintCircularBuffer +
KDPRINTBUFFERSIZE -
KdPrintWritePointer);
00450 LengthCopied =
KdpMoveMemory(
KdPrintWritePointer,
00451
String->Buffer,
00452 First);
00453
if (LengthCopied == First) {
00454 LengthCopied +=
KdpMoveMemory(
KdPrintCircularBuffer,
00455
String->Buffer + First,
00456 Length - First);
00457 }
00458
if (LengthCopied > First) {
00459
KdPrintWritePointer =
KdPrintCircularBuffer + LengthCopied - First;
00460
KdPrintRolloverCount++;
00461 }
else {
00462
KdPrintWritePointer += LengthCopied;
00463
if (
KdPrintWritePointer >=
KdPrintCircularBuffer+
KDPRINTBUFFERSIZE) {
00464
KdPrintWritePointer =
KdPrintCircularBuffer;
00465
KdPrintRolloverCount++;
00466 }
00467 }
00468 }
00469 }
00470
00471 KiReleaseSpinLock(&
KdpPrintSpinLock);
00472
KeLowerIrql(OldIrql);
00473 }