2 * COPYRIGHT: See COPYING in the top level directory
3 * PROJECT: ReactOS Kernel
4 * FILE: ntoskrnl/kd/kdinit.c
5 * PURPOSE: Kernel Debugger Initializtion
7 * PROGRAMMERS: Alex Ionescu (alex@relsoft.net)
14 /* Make bochs debug output in the very early boot phase available */
15 //#define AUTO_ENABLE_BOCHS
17 /* VARIABLES ***************************************************************/
19 KD_PORT_INFORMATION PortInfo
= {DEFAULT_DEBUG_PORT
, DEFAULT_DEBUG_BAUD_RATE
, 0};
21 #ifdef AUTO_ENABLE_BOCHS
22 KDP_DEBUG_MODE KdpDebugMode
= {{{.Bochs
=TRUE
}}};
24 KDP_DEBUG_MODE KdpDebugMode
;
26 PKDP_INIT_ROUTINE WrapperInitRoutine
;
27 KD_DISPATCH_TABLE WrapperTable
;
28 BOOLEAN KdpEarlyBreak
= FALSE
;
29 LIST_ENTRY KdProviders
= {&KdProviders
, &KdProviders
};
30 KD_DISPATCH_TABLE DispatchTable
[KdMax
];
32 PKDP_INIT_ROUTINE InitRoutines
[KdMax
] = {KdpScreenInit
,
38 extern ANSI_STRING KdpLogFileName
;
40 /* PRIVATE FUNCTIONS *********************************************************/
45 KdpGetDebugMode(PCHAR Currentp2
)
47 PCHAR p1
, p2
= Currentp2
;
50 /* Check for Screen Debugging */
51 if (!_strnicmp(p2
, "SCREEN", 6))
55 KdpDebugMode
.Screen
= TRUE
;
57 /* Check for Serial Debugging */
58 else if (!_strnicmp(p2
, "COM", 3))
60 /* Gheck for a valid Serial Port */
64 Value
= (ULONG
)atol(p2
);
65 if (Value
> 0 && Value
< 5)
67 /* Valid port found, enable Serial Debugging */
68 KdpDebugMode
.Serial
= TRUE
;
70 /* Set the port to use */
71 SerialPortInfo
.ComPort
= Value
;
77 Value
= strtoul(p2
+ 1, NULL
, 0);
80 KdpDebugMode
.Serial
= TRUE
;
81 SerialPortInfo
.BaseAddress
= Value
;
82 SerialPortInfo
.ComPort
= 0;
88 /* Check for Debug Log Debugging */
89 else if (!_strnicmp(p2
, "FILE", 4))
93 KdpDebugMode
.File
= TRUE
;
98 while (*p2
!= '\0' && *p2
!= ' ') p2
++;
99 KdpLogFileName
.MaximumLength
= KdpLogFileName
.Length
= p2
- p1
;
100 KdpLogFileName
.Buffer
= p1
;
104 /* Check for BOCHS Debugging */
105 else if (!_strnicmp(p2
, "BOCHS", 5))
109 KdpDebugMode
.Bochs
= TRUE
;
112 /* Check for GDB Debugging */
113 else if (!_strnicmp(p2
, "GDB", 3))
117 KdpDebugMode
.Gdb
= TRUE
;
119 /* Enable Debugging */
120 KdDebuggerEnabled
= TRUE
;
121 KdDebuggerNotPresent
= FALSE
;
122 WrapperInitRoutine
= KdpGdbStubInit
;
125 /* Check for PICE Debugging */
126 else if (!_strnicmp(p2
, "PICE", 4))
130 KdpDebugMode
.Pice
= TRUE
;
132 /* Enable Debugging */
133 KdDebuggerEnabled
= TRUE
;
134 KdDebuggerNotPresent
= FALSE
;
143 KdpCallInitRoutine(ULONG BootPhase
)
145 PLIST_ENTRY CurrentEntry
;
146 PKD_DISPATCH_TABLE CurrentTable
;
148 /* Call the registered handlers */
149 CurrentEntry
= KdProviders
.Flink
;
150 while (CurrentEntry
!= &KdProviders
)
152 /* Get the current table */
153 CurrentTable
= CONTAINING_RECORD(CurrentEntry
,
158 CurrentTable
->KdpInitRoutine(CurrentTable
, BootPhase
);
161 CurrentEntry
= CurrentEntry
->Flink
;
164 /* Call the Wrapper Init Routine */
165 if (WrapperInitRoutine
)
166 WrapperTable
.KdpInitRoutine(&WrapperTable
, BootPhase
);
171 KdInitSystem(ULONG BootPhase
,
172 PLOADER_PARAMETER_BLOCK LoaderBlock
)
176 PCHAR CommandLine
, Port
, BaudRate
, Irq
;
178 /* Set Default Port Options */
181 /* Get the Command Line */
182 CommandLine
= LoaderBlock
->LoadOptions
;
185 _strupr(CommandLine
);
187 /* XXX Check for settings that we support */
188 if (strstr(CommandLine
, "BREAK")) KdpEarlyBreak
= TRUE
;
189 if (strstr(CommandLine
, "NODEBUG")) KdDebuggerEnabled
= FALSE
;
190 else if (strstr(CommandLine
, "CRASHDEBUG")) KdDebuggerEnabled
= FALSE
;
191 else if (strstr(CommandLine
, "DEBUG"))
193 /* Enable the kernel debugger */
194 KdDebuggerEnabled
= TRUE
;
195 KdDebuggerNotPresent
= FALSE
;
197 /* Get the KDBG Settings */
198 KdbpGetCommandLineSettings(LoaderBlock
->LoadOptions
);
202 /* Get the port and baud rate */
203 Port
= strstr(CommandLine
, "DEBUGPORT");
204 BaudRate
= strstr(CommandLine
, "BAUDRATE");
205 Irq
= strstr(CommandLine
, "IRQ");
207 /* Check if we got the /DEBUGPORT parameter(s) */
210 /* Move past the actual string, to reach the port*/
211 Port
+= sizeof("DEBUGPORT") - 1;
213 /* Now get past any spaces and skip the equal sign */
214 while (*Port
== ' ') Port
++;
217 /* Get the debug mode and wrapper */
218 Port
= KdpGetDebugMode(Port
);
219 Port
= strstr(Port
, "DEBUGPORT");
222 /* Use serial port then */
223 if (KdDebuggerEnabled
&& KdpDebugMode
.Value
== 0)
224 KdpDebugMode
.Serial
= TRUE
;
226 /* Check if we got a baud rate */
229 /* Move past the actual string, to reach the rate */
230 BaudRate
+= sizeof("BAUDRATE") - 1;
232 /* Now get past any spaces */
233 while (*BaudRate
== ' ') BaudRate
++;
235 /* And make sure we have a rate */
238 /* Read and set it */
239 Value
= atol(BaudRate
+ 1);
240 if (Value
) PortInfo
.BaudRate
= SerialPortInfo
.BaudRate
= Value
;
244 /* Check Serial Port Settings [IRQ] */
247 /* Move past the actual string, to reach the rate */
248 Irq
+= sizeof("IRQ") - 1;
250 /* Now get past any spaces */
251 while (*Irq
== ' ') Irq
++;
253 /* And make sure we have an IRQ */
256 /* Read and set it */
257 Value
= atol(Irq
+ 1);
258 if (Value
) KdpPortIrq
= Value
;
262 /* Call Providers at Phase 0 */
263 for (i
= 0; i
< KdMax
; i
++)
265 InitRoutines
[i
](&DispatchTable
[i
], 0);
268 /* Call Wrapper at Phase 0 */
269 if (WrapperInitRoutine
) WrapperInitRoutine(&WrapperTable
, 0);
272 else /* BootPhase > 0 */
279 /* Call the Initialization Routines of the Registered Providers */
280 KdpCallInitRoutine(BootPhase
);