ReactOS 0.4.16-dev-306-g647d351
kddll.c File Reference
#include "kddll.h"
Include dependency graph for kddll.c:

Go to the source code of this file.

Functions

ULONG NTAPI KdpCalculateChecksum (IN PVOID Buffer, IN ULONG Length)
 
VOID NTAPI KdpSendControlPacket (IN USHORT PacketType, IN ULONG PacketId OPTIONAL)
 
KDP_STATUS NTAPI KdReceivePacket (IN ULONG PacketType, OUT PSTRING MessageHeader, OUT PSTRING MessageData, OUT PULONG DataLength, IN OUT PKD_CONTEXT KdContext)
 
VOID NTAPI KdSendPacket (IN ULONG PacketType, IN PSTRING MessageHeader, IN PSTRING MessageData, IN OUT PKD_CONTEXT KdContext)
 

Variables

ULONG CurrentPacketId = INITIAL_PACKET_ID | SYNC_PACKET_ID
 
ULONG RemotePacketId = INITIAL_PACKET_ID
 

Function Documentation

◆ KdpCalculateChecksum()

ULONG NTAPI KdpCalculateChecksum ( IN PVOID  Buffer,
IN ULONG  Length 
)

Definition at line 29 of file kddll.c.

32{
33 PUCHAR ByteBuffer = Buffer;
34 ULONG Checksum = 0;
35
36 while (Length-- > 0)
37 {
38 Checksum += (ULONG)*ByteBuffer++;
39 }
40 return Checksum;
41}
Definition: bufpool.h:45
_In_ ULONG _In_ ULONG _In_ ULONG Length
Definition: ntddpcm.h:102
unsigned char * PUCHAR
Definition: typedefs.h:53
uint32_t ULONG
Definition: typedefs.h:59

Referenced by KdReceivePacket(), and KdSendPacket().

◆ KdpSendControlPacket()

VOID NTAPI KdpSendControlPacket ( IN USHORT  PacketType,
IN ULONG PacketId  OPTIONAL 
)

Definition at line 45 of file kddll.c.

48{
50
51 Packet.PacketLeader = CONTROL_PACKET_LEADER;
52 Packet.PacketId = PacketId;
53 Packet.ByteCount = 0;
54 Packet.Checksum = 0;
55 Packet.PacketType = PacketType;
56
58}
VOID NTAPI KdpSendBuffer(IN PVOID Buffer, IN ULONG Size)
Definition: kdserial.c:21
_In_ NDIS_HANDLE _In_ PNDIS_PACKET Packet
Definition: ndis.h:1549
#define CONTROL_PACKET_LEADER
Definition: windbgkd.h:34

Referenced by KdReceivePacket().

◆ KdReceivePacket()

KDP_STATUS NTAPI KdReceivePacket ( IN ULONG  PacketType,
OUT PSTRING  MessageHeader,
OUT PSTRING  MessageData,
OUT PULONG  DataLength,
IN OUT PKD_CONTEXT  KdContext 
)

Definition at line 80 of file kddll.c.

86{
87 UCHAR Byte = 0;
88 KDP_STATUS KdStatus;
90 ULONG Checksum;
91
92 /* Special handling for breakin packet */
93 if (PacketType == PACKET_TYPE_KD_POLL_BREAKIN)
94 {
95 return KdpPollBreakIn();
96 }
97
98 for (;;)
99 {
100 /* Step 1 - Read PacketLeader */
101 KdStatus = KdpReceivePacketLeader(&Packet.PacketLeader);
102 if (KdStatus != KDP_PACKET_RECEIVED)
103 {
104 /* Check if we got a breakin */
105 if (KdStatus == KDP_PACKET_RESEND)
106 {
107 KdContext->KdpControlCPending = TRUE;
108 }
109 return KdStatus;
110 }
111
112 /* Step 2 - Read PacketType */
113 KdStatus = KdpReceiveBuffer(&Packet.PacketType, sizeof(USHORT));
114 if (KdStatus != KDP_PACKET_RECEIVED)
115 {
116 /* Didn't receive a PacketType. */
117 return KdStatus;
118 }
119
120 /* Check if we got a resend packet */
121 if (Packet.PacketLeader == CONTROL_PACKET_LEADER &&
122 Packet.PacketType == PACKET_TYPE_KD_RESEND)
123 {
124 return KDP_PACKET_RESEND;
125 }
126
127 /* Step 3 - Read ByteCount */
128 KdStatus = KdpReceiveBuffer(&Packet.ByteCount, sizeof(USHORT));
129 if (KdStatus != KDP_PACKET_RECEIVED)
130 {
131 /* Didn't receive ByteCount. */
132 return KdStatus;
133 }
134
135 /* Step 4 - Read PacketId */
136 KdStatus = KdpReceiveBuffer(&Packet.PacketId, sizeof(ULONG));
137 if (KdStatus != KDP_PACKET_RECEIVED)
138 {
139 /* Didn't receive PacketId. */
140 return KdStatus;
141 }
142
143/*
144 if (Packet.PacketId != ExpectedPacketId)
145 {
146 // Ask for a resend!
147 continue;
148 }
149*/
150
151 /* Step 5 - Read Checksum */
152 KdStatus = KdpReceiveBuffer(&Packet.Checksum, sizeof(ULONG));
153 if (KdStatus != KDP_PACKET_RECEIVED)
154 {
155 /* Didn't receive Checksum. */
156 return KdStatus;
157 }
158
159 /* Step 6 - Handle control packets */
160 if (Packet.PacketLeader == CONTROL_PACKET_LEADER)
161 {
162 switch (Packet.PacketType)
163 {
165 /* Are we waiting for an ACK packet? */
166 if (PacketType == PACKET_TYPE_KD_ACKNOWLEDGE &&
167 Packet.PacketId == (CurrentPacketId & ~SYNC_PACKET_ID))
168 {
169 /* Remote acknowledges the last packet */
170 CurrentPacketId ^= 1;
171 return KDP_PACKET_RECEIVED;
172 }
173 /* That's not what we were waiting for, start over */
174 continue;
175
177 KDDBGPRINT("KdReceivePacket - got PACKET_TYPE_KD_RESET\n");
181 /* Fall through */
182
184 KDDBGPRINT("KdReceivePacket - got PACKET_TYPE_KD_RESEND\n");
185 /* Remote wants us to resend the last packet */
186 return KDP_PACKET_RESEND;
187
188 default:
189 KDDBGPRINT("KdReceivePacket - got unknown control packet\n");
190 /* We got an invalid packet, ignore it and start over */
191 continue;
192 }
193 }
194
195 /* Did we wait for an ack packet? */
196 if (PacketType == PACKET_TYPE_KD_ACKNOWLEDGE)
197 {
198 /* We received something different */
200 CurrentPacketId ^= 1;
201 return KDP_PACKET_RECEIVED;
202 }
203
204 /* Get size of the message header */
205 MessageHeader->Length = MessageHeader->MaximumLength;
206
207 /* Packet smaller than expected or too big? */
208 if (Packet.ByteCount < MessageHeader->Length ||
209 Packet.ByteCount > PACKET_MAX_SIZE)
210 {
211 KDDBGPRINT("KdReceivePacket - too few data (%d) for type %d\n",
212 Packet.ByteCount, MessageHeader->Length);
213 MessageHeader->Length = Packet.ByteCount;
215 continue;
216 }
217
218 //KDDBGPRINT("KdReceivePacket - got normal PacketType, Buffer = %p\n", MessageHeader->Buffer);
219
220 /* Receive the message header data */
221 KdStatus = KdpReceiveBuffer(MessageHeader->Buffer,
222 MessageHeader->Length);
223 if (KdStatus != KDP_PACKET_RECEIVED)
224 {
225 /* Didn't receive data. Packet needs to be resent. */
226 KDDBGPRINT("KdReceivePacket - Didn't receive message header data.\n");
228 continue;
229 }
230
231 //KDDBGPRINT("KdReceivePacket - got normal PacketType 3\n");
232
233 /* Calculate checksum for the header data */
234 Checksum = KdpCalculateChecksum(MessageHeader->Buffer,
235 MessageHeader->Length);
236
237 /* Calculate the length of the message data */
238 *DataLength = Packet.ByteCount - MessageHeader->Length;
239
240 /* Shall we receive message data? */
241 if (MessageData)
242 {
243 /* Set the length of the message data */
244 MessageData->Length = (USHORT)*DataLength;
245
246 /* Do we have data? */
247 if (MessageData->Length)
248 {
249 KDDBGPRINT("KdReceivePacket - got data\n");
250
251 /* Receive the message data */
252 KdStatus = KdpReceiveBuffer(MessageData->Buffer,
253 MessageData->Length);
254 if (KdStatus != KDP_PACKET_RECEIVED)
255 {
256 /* Didn't receive data. Start over. */
257 KDDBGPRINT("KdReceivePacket - Didn't receive message data.\n");
259 continue;
260 }
261
262 /* Add cheksum for message data */
263 Checksum += KdpCalculateChecksum(MessageData->Buffer,
264 MessageData->Length);
265 }
266 }
267
268 /* We must receive a PACKET_TRAILING_BYTE now */
269 KdStatus = KdpReceiveBuffer(&Byte, sizeof(UCHAR));
270 if (KdStatus != KDP_PACKET_RECEIVED || Byte != PACKET_TRAILING_BYTE)
271 {
272 KDDBGPRINT("KdReceivePacket - wrong trailing byte (0x%x), status 0x%x\n", Byte, KdStatus);
274 continue;
275 }
276
277 /* Compare checksum */
278 if (Packet.Checksum != Checksum)
279 {
280 KDDBGPRINT("KdReceivePacket - wrong cheksum, got %x, calculated %x\n",
281 Packet.Checksum, Checksum);
283 continue;
284 }
285
286 /* Acknowledge the received packet */
288
289 /* Check if the received PacketId is ok */
290 if (Packet.PacketId != RemotePacketId)
291 {
292 /* Continue with next packet */
293 continue;
294 }
295
296 /* Did we get the right packet type? */
297 if (PacketType == Packet.PacketType)
298 {
299 /* Yes, return success */
300 //KDDBGPRINT("KdReceivePacket - all ok\n");
301 RemotePacketId ^= 1;
302 return KDP_PACKET_RECEIVED;
303 }
304
305 /* We received something different, ignore it. */
306 KDDBGPRINT("KdReceivePacket - wrong PacketType\n");
307 }
308
309 return KDP_PACKET_RECEIVED;
310}
_In_ ULONG _In_opt_ WDFREQUEST _In_opt_ PVOID _In_ size_t _In_ PVOID _In_ size_t _Out_ size_t * DataLength
Definition: cdrom.h:1444
#define TRUE
Definition: types.h:120
unsigned char Byte
Definition: zlib.h:37
#define KDDBGPRINT(...)
Definition: kddll.h:19
KDP_STATUS NTAPI KdpReceiveBuffer(OUT PVOID Buffer, IN ULONG Size)
Definition: kdserial.c:43
KDP_STATUS
Definition: kddll.h:26
@ KDP_PACKET_RESEND
Definition: kddll.h:29
@ KDP_PACKET_RECEIVED
Definition: kddll.h:27
KDP_STATUS NTAPI KdpReceivePacketLeader(OUT PULONG PacketLeader)
Definition: kdserial.c:75
KDP_STATUS NTAPI KdpPollBreakIn(VOID)
Definition: kdcom.c:343
ULONG CurrentPacketId
Definition: kddll.c:13
ULONG NTAPI KdpCalculateChecksum(IN PVOID Buffer, IN ULONG Length)
Definition: kddll.c:29
ULONG RemotePacketId
Definition: kddll.c:14
VOID NTAPI KdpSendControlPacket(IN USHORT PacketType, IN ULONG PacketId OPTIONAL)
Definition: kddll.c:45
unsigned short USHORT
Definition: pedump.c:61
#define PACKET_MAX_SIZE
Definition: windbgkd.h:18
#define PACKET_TYPE_KD_ACKNOWLEDGE
Definition: windbgkd.h:45
#define PACKET_TRAILING_BYTE
Definition: windbgkd.h:36
#define PACKET_TYPE_KD_POLL_BREAKIN
Definition: windbgkd.h:49
#define INITIAL_PACKET_ID
Definition: windbgkd.h:24
#define PACKET_TYPE_KD_RESET
Definition: windbgkd.h:47
#define SYNC_PACKET_ID
Definition: windbgkd.h:25
#define PACKET_TYPE_KD_RESEND
Definition: windbgkd.h:46
unsigned char UCHAR
Definition: xmlstorage.h:181

Referenced by KdPollBreakIn(), KdpPollBreakInWithPortLock(), KdpPromptString(), KdpSendWaitContinue(), and KdSendPacket().

◆ KdSendPacket()

VOID NTAPI KdSendPacket ( IN ULONG  PacketType,
IN PSTRING  MessageHeader,
IN PSTRING  MessageData,
IN OUT PKD_CONTEXT  KdContext 
)

Definition at line 314 of file kddll.c.

319{
321 KDP_STATUS KdStatus;
322 ULONG Retries;
323
324 /* Initialize a KD_PACKET */
325 Packet.PacketLeader = PACKET_LEADER;
326 Packet.PacketType = (USHORT)PacketType;
327 Packet.ByteCount = MessageHeader->Length;
328 Packet.Checksum = KdpCalculateChecksum(MessageHeader->Buffer,
329 MessageHeader->Length);
330
331 /* If we have message data, add it to the packet */
332 if (MessageData)
333 {
334 Packet.ByteCount += MessageData->Length;
335 Packet.Checksum += KdpCalculateChecksum(MessageData->Buffer,
336 MessageData->Length);
337 }
338
339 Retries = KdContext->KdpDefaultRetries;
340
341 for (;;)
342 {
343 /* Set the packet id */
344 Packet.PacketId = CurrentPacketId;
345
346 /* Send the packet header to the KD port */
347 KdpSendBuffer(&Packet, sizeof(KD_PACKET));
348
349 /* Send the message header */
350 KdpSendBuffer(MessageHeader->Buffer, MessageHeader->Length);
351
352 /* If we have message data, also send it */
353 if (MessageData)
354 {
355 KdpSendBuffer(MessageData->Buffer, MessageData->Length);
356 }
357
358 /* Finalize with a trailing byte */
360
361 /* Wait for acknowledge */
363 NULL,
364 NULL,
365 NULL,
366 KdContext);
367
368 /* Did we succeed? */
369 if (KdStatus == KDP_PACKET_RECEIVED)
370 {
371 /* Packet received, we can quit the loop */
372 CurrentPacketId &= ~SYNC_PACKET_ID;
373 Retries = KdContext->KdpDefaultRetries;
374 break;
375 }
376 else if (KdStatus == KDP_PACKET_TIMEOUT)
377 {
378 /* Timeout, decrement the retry count */
379 if (Retries > 0)
380 Retries--;
381
382 /*
383 * If the retry count reaches zero, bail out
384 * for packet types allowed to timeout.
385 */
386 if (Retries == 0)
387 {
388 ULONG MessageId = *(PULONG)MessageHeader->Buffer;
389 switch (PacketType)
390 {
392 {
393 if (MessageId != DbgKdPrintStringApi) continue;
394 break;
395 }
396
399 {
400 if (MessageId != DbgKdLoadSymbolsStateChange) continue;
401 break;
402 }
403
405 {
406 if (MessageId != DbgKdCreateFileApi) continue;
407 break;
408 }
409 }
410
411 /* Reset debugger state */
413 SharedUserData->KdDebuggerEnabled &= ~0x00000002;
416
417 return;
418 }
419 }
420 // else (KdStatus == KDP_PACKET_RESEND) /* Resend the packet */
421
422 /* Packet timed out, send it again */
423 KDDBGPRINT("KdSendPacket got KdStatus 0x%x\n", KdStatus);
424 }
425}
#define NULL
Definition: types.h:112
@ KDP_PACKET_TIMEOUT
Definition: kddll.h:28
switch(r->id)
Definition: btrfs.c:3046
VOID NTAPI KdpSendByte(IN UCHAR Byte)
Definition: kdcom.c:291
KDP_STATUS NTAPI KdReceivePacket(IN ULONG PacketType, OUT PSTRING MessageHeader, OUT PSTRING MessageData, OUT PULONG DataLength, IN OUT PKD_CONTEXT KdContext)
Definition: kddll.c:80
#define SharedUserData
uint32_t * PULONG
Definition: typedefs.h:59
#define DbgKdLoadSymbolsStateChange
Definition: windbgkd.h:60
#define DbgKdPrintStringApi
Definition: windbgkd.h:122
#define PACKET_TYPE_KD_FILE_IO
Definition: windbgkd.h:52
#define PACKET_TYPE_KD_STATE_CHANGE32
Definition: windbgkd.h:42
#define PACKET_TYPE_KD_STATE_CHANGE64
Definition: windbgkd.h:48
#define DbgKdCreateFileApi
Definition: windbgkd.h:139
#define PACKET_LEADER
Definition: windbgkd.h:32
#define PACKET_TYPE_KD_DEBUG_IO
Definition: windbgkd.h:44
#define KD_DEBUGGER_NOT_PRESENT
Definition: kdfuncs.h:133

Referenced by KdpCheckLowMemory(), KdpFillMemory(), KdpGetBusData(), KdpGetContext(), KdpGetContextEx(), KdpGetVersion(), KdpNotSupported(), KdpPrintString(), KdpPromptString(), KdpQueryMemory(), KdpReadControlSpace(), KdpReadIoSpace(), KdpReadIoSpaceExtended(), KdpReadMachineSpecificRegister(), KdpReadPhysicalMemory(), KdpReadVirtualMemory(), KdpRestoreBreakpoint(), KdpRestoreBreakPointEx(), KdpSearchMemory(), KdpSendWaitContinue(), KdpSetBusData(), KdpSetContext(), KdpSetContextEx(), KdpWriteBreakpoint(), KdpWriteBreakPointEx(), KdpWriteControlSpace(), KdpWriteCustomBreakpoint(), KdpWriteIoSpace(), KdpWriteIoSpaceExtended(), KdpWriteMachineSpecificRegister(), KdpWritePhysicalMemory(), and KdpWriteVirtualMemory().

Variable Documentation

◆ CurrentPacketId

ULONG CurrentPacketId = INITIAL_PACKET_ID | SYNC_PACKET_ID

Definition at line 13 of file kddll.c.

Referenced by KdReceivePacket(), and KdSendPacket().

◆ RemotePacketId

ULONG RemotePacketId = INITIAL_PACKET_ID

Definition at line 14 of file kddll.c.

Referenced by KdReceivePacket(), and KdSendPacket().