1 //===-- CommunicationKDP.cpp ------------------------------------*- C++ -*-===//
2 //
3 //                     The LLVM Compiler Infrastructure
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 
10 
11 #include "CommunicationKDP.h"
12 
13 // C Includes
14 #include <errno.h>
15 #include <limits.h>
16 #include <string.h>
17 
18 // C++ Includes
19 
20 // Other libraries and framework includes
21 #include "lldb/Core/DataBufferHeap.h"
22 #include "lldb/Core/DataExtractor.h"
23 #include "lldb/Core/Log.h"
24 #include "lldb/Core/State.h"
25 #include "lldb/Core/UUID.h"
26 #include "lldb/Host/FileSpec.h"
27 #include "lldb/Host/Host.h"
28 #include "lldb/Host/TimeValue.h"
29 #include "lldb/Target/Process.h"
30 
31 // Project includes
32 #include "ProcessKDPLog.h"
33 
34 using namespace lldb;
35 using namespace lldb_private;
36 
37 //----------------------------------------------------------------------
38 // CommunicationKDP constructor
39 //----------------------------------------------------------------------
40 CommunicationKDP::CommunicationKDP (const char *comm_name) :
41     Communication(comm_name),
42     m_addr_byte_size (4),
43     m_byte_order (eByteOrderLittle),
44     m_packet_timeout (5),
45     m_sequence_mutex (Mutex::eMutexTypeRecursive),
46     m_is_running (false),
47     m_session_key (0u),
48     m_request_sequence_id (0u),
49     m_exception_sequence_id (0u),
50     m_kdp_version_version (0u),
51     m_kdp_version_feature (0u),
52     m_kdp_hostinfo_cpu_mask (0u),
53     m_kdp_hostinfo_cpu_type (0u),
54     m_kdp_hostinfo_cpu_subtype (0u)
55 {
56 }
57 
58 //----------------------------------------------------------------------
59 // Destructor
60 //----------------------------------------------------------------------
61 CommunicationKDP::~CommunicationKDP()
62 {
63     if (IsConnected())
64     {
65         Disconnect();
66     }
67 }
68 
69 bool
70 CommunicationKDP::SendRequestPacket (const PacketStreamType &request_packet)
71 {
72     Mutex::Locker locker(m_sequence_mutex);
73     return SendRequestPacketNoLock (request_packet);
74 }
75 
76 #if 0
77 typedef struct {
78 	uint8_t     request;	// Either: CommandType | ePacketTypeRequest, or CommandType | ePacketTypeReply
79 	uint8_t     sequence;
80 	uint16_t    length;		// Length of entire packet including this header
81 	uint32_t	key;		// Session key
82 } kdp_hdr_t;
83 #endif
84 
85 void
86 CommunicationKDP::MakeRequestPacketHeader (CommandType request_type,
87                                            PacketStreamType &request_packet,
88                                            uint16_t request_length)
89 {
90     request_packet.Clear();
91     request_packet.PutHex8 (request_type | ePacketTypeRequest); // Set the request type
92     request_packet.PutHex8 (m_request_sequence_id++);           // Sequence number
93     request_packet.PutHex16 (request_length);                   // Length of the packet including this header
94     request_packet.PutHex32 (m_session_key);                    // Session key
95 }
96 
97 bool
98 CommunicationKDP::SendRequestAndGetReply (const CommandType command,
99                                           const PacketStreamType &request_packet,
100                                           DataExtractor &reply_packet)
101 {
102     if (IsRunning())
103     {
104         Log *log (ProcessKDPLog::GetLogIfAllCategoriesSet (KDP_LOG_PACKETS));
105         if (log)
106         {
107             PacketStreamType log_strm;
108             DumpPacket (log_strm, request_packet.GetData(), request_packet.GetSize());
109             log->Printf("error: kdp running, not sending packet: %.*s", (uint32_t)log_strm.GetSize(), log_strm.GetData());
110         }
111         return false;
112     }
113 
114     Mutex::Locker locker(m_sequence_mutex);
115 #ifdef LLDB_CONFIGURATION_DEBUG
116     // NOTE: this only works for packets that are in native endian byte order
117     assert (request_packet.GetSize() == *((uint16_t *)(request_packet.GetData() + 2)));
118 #endif
119     lldb::offset_t offset = 1;
120     const uint32_t num_retries = 3;
121     for (uint32_t i=0; i<num_retries; ++i)
122     {
123         if (SendRequestPacketNoLock(request_packet))
124         {
125             const uint8_t request_sequence_id = (uint8_t)request_packet.GetData()[1];
126             while (1)
127             {
128                 if (WaitForPacketWithTimeoutMicroSecondsNoLock (reply_packet, GetPacketTimeoutInMicroSeconds ()))
129                 {
130                     offset = 0;
131                     const uint8_t reply_command = reply_packet.GetU8 (&offset);
132                     const uint8_t reply_sequence_id = reply_packet.GetU8 (&offset);
133                     if (request_sequence_id == reply_sequence_id)
134                     {
135                         // The sequent ID was correct, now verify we got the response we were looking for
136                         if ((reply_command & eCommandTypeMask) == command)
137                         {
138                             // Success
139                             if (command == KDP_RESUMECPUS)
140                                 m_is_running.SetValue(true, eBroadcastAlways);
141                             return true;
142                         }
143                         else
144                         {
145                             // Failed to get the correct response, bail
146                             reply_packet.Clear();
147                             return false;
148                         }
149                     }
150                     else if (reply_sequence_id > request_sequence_id)
151                     {
152                         // Sequence ID was greater than the sequence ID of the packet we sent, something
153                         // is really wrong...
154                         reply_packet.Clear();
155                         return false;
156                     }
157                     else
158                     {
159                         // The reply sequence ID was less than our current packet's sequence ID
160                         // so we should keep trying to get a response because this was a response
161                         // for a previous packet that we must have retried.
162                     }
163                 }
164                 else
165                 {
166                     // Break and retry sending the packet as we didn't get a response due to timeout
167                     break;
168                 }
169             }
170         }
171     }
172     reply_packet.Clear();
173     return false;
174 }
175 
176 bool
177 CommunicationKDP::SendRequestPacketNoLock (const PacketStreamType &request_packet)
178 {
179     if (IsConnected())
180     {
181         const char *packet_data = request_packet.GetData();
182         const size_t packet_size = request_packet.GetSize();
183 
184         Log *log (ProcessKDPLog::GetLogIfAllCategoriesSet (KDP_LOG_PACKETS));
185         if (log)
186         {
187             PacketStreamType log_strm;
188             DumpPacket (log_strm, packet_data, packet_size);
189             log->Printf("%.*s", (uint32_t)log_strm.GetSize(), log_strm.GetData());
190         }
191         ConnectionStatus status = eConnectionStatusSuccess;
192 
193         size_t bytes_written = Write (packet_data,
194                                       packet_size,
195                                       status,
196                                       NULL);
197 
198         if (bytes_written == packet_size)
199             return true;
200 
201         if (log)
202             log->Printf ("error: failed to send packet entire packet %" PRIu64 " of %" PRIu64 " bytes sent", (uint64_t)bytes_written, (uint64_t)packet_size);
203     }
204     return false;
205 }
206 
207 bool
208 CommunicationKDP::GetSequenceMutex (Mutex::Locker& locker)
209 {
210     return locker.TryLock (m_sequence_mutex);
211 }
212 
213 
214 bool
215 CommunicationKDP::WaitForNotRunningPrivate (const TimeValue *timeout_ptr)
216 {
217     return m_is_running.WaitForValueEqualTo (false, timeout_ptr, NULL);
218 }
219 
220 size_t
221 CommunicationKDP::WaitForPacketWithTimeoutMicroSeconds (DataExtractor &packet, uint32_t timeout_usec)
222 {
223     Mutex::Locker locker(m_sequence_mutex);
224     return WaitForPacketWithTimeoutMicroSecondsNoLock (packet, timeout_usec);
225 }
226 
227 size_t
228 CommunicationKDP::WaitForPacketWithTimeoutMicroSecondsNoLock (DataExtractor &packet, uint32_t timeout_usec)
229 {
230     uint8_t buffer[8192];
231     Error error;
232 
233     Log *log (ProcessKDPLog::GetLogIfAllCategoriesSet (KDP_LOG_PACKETS | KDP_LOG_VERBOSE));
234 
235     // Check for a packet from our cache first without trying any reading...
236     if (CheckForPacket (NULL, 0, packet))
237         return packet.GetByteSize();
238 
239     bool timed_out = false;
240     while (IsConnected() && !timed_out)
241     {
242         lldb::ConnectionStatus status = eConnectionStatusNoConnection;
243         size_t bytes_read = Read (buffer, sizeof(buffer), timeout_usec, status, &error);
244 
245         if (log)
246             log->Printf ("%s: Read (buffer, (sizeof(buffer), timeout_usec = 0x%x, status = %s, error = %s) => bytes_read = %" PRIu64,
247                          __PRETTY_FUNCTION__,
248                          timeout_usec,
249                          Communication::ConnectionStatusAsCString (status),
250                          error.AsCString(),
251                          (uint64_t)bytes_read);
252 
253         if (bytes_read > 0)
254         {
255             if (CheckForPacket (buffer, bytes_read, packet))
256                 return packet.GetByteSize();
257         }
258         else
259         {
260             switch (status)
261             {
262             case eConnectionStatusTimedOut:
263                 timed_out = true;
264                 break;
265             case eConnectionStatusSuccess:
266                 //printf ("status = success but error = %s\n", error.AsCString("<invalid>"));
267                 break;
268 
269             case eConnectionStatusEndOfFile:
270             case eConnectionStatusNoConnection:
271             case eConnectionStatusLostConnection:
272             case eConnectionStatusError:
273                 Disconnect();
274                 break;
275             }
276         }
277     }
278     packet.Clear ();
279     return 0;
280 }
281 
282 bool
283 CommunicationKDP::CheckForPacket (const uint8_t *src, size_t src_len, DataExtractor &packet)
284 {
285     // Put the packet data into the buffer in a thread safe fashion
286     Mutex::Locker locker(m_bytes_mutex);
287 
288     Log *log (ProcessKDPLog::GetLogIfAllCategoriesSet (KDP_LOG_PACKETS));
289 
290     if (src && src_len > 0)
291     {
292         if (log && log->GetVerbose())
293         {
294             PacketStreamType log_strm;
295             DataExtractor::DumpHexBytes (&log_strm, src, src_len, UINT32_MAX, LLDB_INVALID_ADDRESS);
296             log->Printf ("CommunicationKDP::%s adding %u bytes: %s",
297                          __FUNCTION__,
298                          (uint32_t)src_len,
299                          log_strm.GetData());
300         }
301         m_bytes.append ((const char *)src, src_len);
302     }
303 
304     // Make sure we at least have enough bytes for a packet header
305     const size_t bytes_available = m_bytes.size();
306     if (bytes_available >= 8)
307     {
308         packet.SetData (&m_bytes[0], bytes_available, m_byte_order);
309         lldb::offset_t offset = 0;
310         uint8_t reply_command = packet.GetU8(&offset);
311         switch (reply_command)
312         {
313         case ePacketTypeRequest | KDP_EXCEPTION:
314         case ePacketTypeRequest | KDP_TERMINATION:
315             // We got an exception request, so be sure to send an ACK
316             {
317                 PacketStreamType request_ack_packet (Stream::eBinary, m_addr_byte_size, m_byte_order);
318                 // Set the reply but and make the ACK packet
319                 request_ack_packet.PutHex8 (reply_command | ePacketTypeReply);
320                 request_ack_packet.PutHex8 (packet.GetU8(&offset));
321                 request_ack_packet.PutHex16 (packet.GetU16(&offset));
322                 request_ack_packet.PutHex32 (packet.GetU32(&offset));
323                 m_is_running.SetValue(false, eBroadcastAlways);
324                 // Ack to the exception or termination
325                 SendRequestPacketNoLock (request_ack_packet);
326             }
327             // Fall through to case below to get packet contents
328         case ePacketTypeReply | KDP_CONNECT:
329         case ePacketTypeReply | KDP_DISCONNECT:
330         case ePacketTypeReply | KDP_HOSTINFO:
331         case ePacketTypeReply | KDP_VERSION:
332         case ePacketTypeReply | KDP_MAXBYTES:
333         case ePacketTypeReply | KDP_READMEM:
334         case ePacketTypeReply | KDP_WRITEMEM:
335         case ePacketTypeReply | KDP_READREGS:
336         case ePacketTypeReply | KDP_WRITEREGS:
337         case ePacketTypeReply | KDP_LOAD:
338         case ePacketTypeReply | KDP_IMAGEPATH:
339         case ePacketTypeReply | KDP_SUSPEND:
340         case ePacketTypeReply | KDP_RESUMECPUS:
341         case ePacketTypeReply | KDP_BREAKPOINT_SET:
342         case ePacketTypeReply | KDP_BREAKPOINT_REMOVE:
343         case ePacketTypeReply | KDP_REGIONS:
344         case ePacketTypeReply | KDP_REATTACH:
345         case ePacketTypeReply | KDP_HOSTREBOOT:
346         case ePacketTypeReply | KDP_READMEM64:
347         case ePacketTypeReply | KDP_WRITEMEM64:
348         case ePacketTypeReply | KDP_BREAKPOINT_SET64:
349         case ePacketTypeReply | KDP_BREAKPOINT_REMOVE64:
350         case ePacketTypeReply | KDP_KERNELVERSION:
351         case ePacketTypeReply | KDP_READPHYSMEM64:
352         case ePacketTypeReply | KDP_WRITEPHYSMEM64:
353         case ePacketTypeReply | KDP_READIOPORT:
354         case ePacketTypeReply | KDP_WRITEIOPORT:
355         case ePacketTypeReply | KDP_READMSR64:
356         case ePacketTypeReply | KDP_WRITEMSR64:
357         case ePacketTypeReply | KDP_DUMPINFO:
358             {
359                 offset = 2;
360                 const uint16_t length = packet.GetU16 (&offset);
361                 if (length <= bytes_available)
362                 {
363                     // We have an entire packet ready, we need to copy the data
364                     // bytes into a buffer that will be owned by the packet and
365                     // erase the bytes from our communcation buffer "m_bytes"
366                     packet.SetData (DataBufferSP (new DataBufferHeap (&m_bytes[0], length)));
367                     m_bytes.erase (0, length);
368 
369                     if (log)
370                     {
371                         PacketStreamType log_strm;
372                         DumpPacket (log_strm, packet);
373 
374                         log->Printf("%.*s", (uint32_t)log_strm.GetSize(), log_strm.GetData());
375                     }
376                     return true;
377                 }
378             }
379             break;
380 
381         default:
382             // Unrecognized reply command byte, erase this byte and try to get back on track
383             if (log)
384                 log->Printf ("CommunicationKDP::%s: tossing junk byte: 0x%2.2x",
385                              __FUNCTION__,
386                              (uint8_t)m_bytes[0]);
387             m_bytes.erase(0, 1);
388             break;
389         }
390     }
391     packet.Clear();
392     return false;
393 }
394 
395 
396 bool
397 CommunicationKDP::SendRequestConnect (uint16_t reply_port,
398                                       uint16_t exc_port,
399                                       const char *greeting)
400 {
401     PacketStreamType request_packet (Stream::eBinary, m_addr_byte_size, m_byte_order);
402     if (greeting == NULL)
403         greeting = "";
404 
405     const CommandType command = KDP_CONNECT;
406     // Length is 82 uint16_t and the length of the greeting C string with the terminating NULL
407     const uint32_t command_length = 8 + 2 + 2 + ::strlen(greeting) + 1;
408     MakeRequestPacketHeader (command, request_packet, command_length);
409     // Always send connect ports as little endian
410     request_packet.SetByteOrder (eByteOrderLittle);
411     request_packet.PutHex16 (htons(reply_port));
412     request_packet.PutHex16 (htons(exc_port));
413     request_packet.SetByteOrder (m_byte_order);
414     request_packet.PutCString (greeting);
415     DataExtractor reply_packet;
416     return SendRequestAndGetReply (command, request_packet, reply_packet);
417 }
418 
419 void
420 CommunicationKDP::ClearKDPSettings ()
421 {
422     m_request_sequence_id = 0;
423     m_kdp_version_version = 0;
424     m_kdp_version_feature = 0;
425     m_kdp_hostinfo_cpu_mask = 0;
426     m_kdp_hostinfo_cpu_type = 0;
427     m_kdp_hostinfo_cpu_subtype = 0;
428 }
429 
430 bool
431 CommunicationKDP::SendRequestReattach (uint16_t reply_port)
432 {
433     PacketStreamType request_packet (Stream::eBinary, m_addr_byte_size, m_byte_order);
434     const CommandType command = KDP_REATTACH;
435     // Length is 8 bytes for the header plus 2 bytes for the reply UDP port
436     const uint32_t command_length = 8 + 2;
437     MakeRequestPacketHeader (command, request_packet, command_length);
438     // Always send connect ports as little endian
439     request_packet.SetByteOrder (eByteOrderLittle);
440     request_packet.PutHex16(htons(reply_port));
441     request_packet.SetByteOrder (m_byte_order);
442     DataExtractor reply_packet;
443     if (SendRequestAndGetReply (command, request_packet, reply_packet))
444     {
445         // Reset the sequence ID to zero for reattach
446         ClearKDPSettings ();
447         lldb::offset_t offset = 4;
448         m_session_key = reply_packet.GetU32 (&offset);
449         return true;
450     }
451     return false;
452 }
453 
454 uint32_t
455 CommunicationKDP::GetVersion ()
456 {
457     if (!VersionIsValid())
458         SendRequestVersion();
459     return m_kdp_version_version;
460 }
461 
462 uint32_t
463 CommunicationKDP::GetFeatureFlags ()
464 {
465     if (!VersionIsValid())
466         SendRequestVersion();
467     return m_kdp_version_feature;
468 }
469 
470 bool
471 CommunicationKDP::SendRequestVersion ()
472 {
473     PacketStreamType request_packet (Stream::eBinary, m_addr_byte_size, m_byte_order);
474     const CommandType command = KDP_VERSION;
475     const uint32_t command_length = 8;
476     MakeRequestPacketHeader (command, request_packet, command_length);
477     DataExtractor reply_packet;
478     if (SendRequestAndGetReply (command, request_packet, reply_packet))
479     {
480         lldb::offset_t offset = 8;
481         m_kdp_version_version = reply_packet.GetU32 (&offset);
482         m_kdp_version_feature = reply_packet.GetU32 (&offset);
483         return true;
484     }
485     return false;
486 }
487 
488 #if 0 // Disable KDP_IMAGEPATH for now, it seems to hang the KDP connection...
489 const char *
490 CommunicationKDP::GetImagePath ()
491 {
492     if (m_image_path.empty())
493         SendRequestImagePath();
494     return m_image_path.c_str();
495 }
496 
497 bool
498 CommunicationKDP::SendRequestImagePath ()
499 {
500     PacketStreamType request_packet (Stream::eBinary, m_addr_byte_size, m_byte_order);
501     const CommandType command = KDP_IMAGEPATH;
502     const uint32_t command_length = 8;
503     MakeRequestPacketHeader (command, request_packet, command_length);
504     DataExtractor reply_packet;
505     if (SendRequestAndGetReply (command, request_packet, reply_packet))
506     {
507         const char *path = reply_packet.PeekCStr(8);
508         if (path && path[0])
509             m_kernel_version.assign (path);
510         return true;
511     }
512     return false;
513 }
514 #endif
515 
516 uint32_t
517 CommunicationKDP::GetCPUMask ()
518 {
519     if (!HostInfoIsValid())
520         SendRequestHostInfo();
521     return m_kdp_hostinfo_cpu_mask;
522 }
523 
524 uint32_t
525 CommunicationKDP::GetCPUType ()
526 {
527     if (!HostInfoIsValid())
528         SendRequestHostInfo();
529     return m_kdp_hostinfo_cpu_type;
530 }
531 
532 uint32_t
533 CommunicationKDP::GetCPUSubtype ()
534 {
535     if (!HostInfoIsValid())
536         SendRequestHostInfo();
537     return m_kdp_hostinfo_cpu_subtype;
538 }
539 
540 lldb_private::UUID
541 CommunicationKDP::GetUUID ()
542 {
543     UUID uuid;
544     if (GetKernelVersion() == NULL)
545         return uuid;
546 
547     if (m_kernel_version.find("UUID=") == std::string::npos)
548         return uuid;
549 
550     size_t p = m_kernel_version.find("UUID=") + strlen ("UUID=");
551     std::string uuid_str = m_kernel_version.substr(p, 36);
552     if (uuid_str.size() < 32)
553         return uuid;
554 
555     if (uuid.SetFromCString (uuid_str.c_str()) == 0)
556     {
557         UUID invalid_uuid;
558         return invalid_uuid;
559     }
560 
561     return uuid;
562 }
563 
564 bool
565 CommunicationKDP::RemoteIsEFI ()
566 {
567     if (GetKernelVersion() == NULL)
568         return false;
569     if (strncmp (m_kernel_version.c_str(), "EFI", 3) == 0)
570         return true;
571     else
572         return false;
573 }
574 
575 bool
576 CommunicationKDP::RemoteIsDarwinKernel ()
577 {
578     if (GetKernelVersion() == NULL)
579         return false;
580     if (m_kernel_version.find("Darwin Kernel") != std::string::npos)
581         return true;
582     else
583         return false;
584 }
585 
586 lldb::addr_t
587 CommunicationKDP::GetLoadAddress ()
588 {
589     if (GetKernelVersion() == NULL)
590         return LLDB_INVALID_ADDRESS;
591 
592     if (m_kernel_version.find("stext=") == std::string::npos)
593         return LLDB_INVALID_ADDRESS;
594     size_t p = m_kernel_version.find("stext=") + strlen ("stext=");
595     if (m_kernel_version[p] != '0' || m_kernel_version[p + 1] != 'x')
596         return LLDB_INVALID_ADDRESS;
597 
598     addr_t kernel_load_address;
599     errno = 0;
600     kernel_load_address = ::strtoul (m_kernel_version.c_str() + p, NULL, 16);
601     if (errno != 0 || kernel_load_address == 0)
602         return LLDB_INVALID_ADDRESS;
603 
604     return kernel_load_address;
605 }
606 
607 bool
608 CommunicationKDP::SendRequestHostInfo ()
609 {
610     PacketStreamType request_packet (Stream::eBinary, m_addr_byte_size, m_byte_order);
611     const CommandType command = KDP_HOSTINFO;
612     const uint32_t command_length = 8;
613     MakeRequestPacketHeader (command, request_packet, command_length);
614     DataExtractor reply_packet;
615     if (SendRequestAndGetReply (command, request_packet, reply_packet))
616     {
617         lldb::offset_t offset = 8;
618         m_kdp_hostinfo_cpu_mask     = reply_packet.GetU32 (&offset);
619         m_kdp_hostinfo_cpu_type     = reply_packet.GetU32 (&offset);
620         m_kdp_hostinfo_cpu_subtype  = reply_packet.GetU32 (&offset);
621 
622         ArchSpec kernel_arch;
623         kernel_arch.SetArchitecture (eArchTypeMachO,
624                                      m_kdp_hostinfo_cpu_type,
625                                      m_kdp_hostinfo_cpu_subtype);
626 
627         m_addr_byte_size = kernel_arch.GetAddressByteSize();
628         m_byte_order = kernel_arch.GetByteOrder();
629         return true;
630     }
631     return false;
632 }
633 
634 const char *
635 CommunicationKDP::GetKernelVersion ()
636 {
637     if (m_kernel_version.empty())
638         SendRequestKernelVersion ();
639     return m_kernel_version.c_str();
640 }
641 
642 bool
643 CommunicationKDP::SendRequestKernelVersion ()
644 {
645     PacketStreamType request_packet (Stream::eBinary, m_addr_byte_size, m_byte_order);
646     const CommandType command = KDP_KERNELVERSION;
647     const uint32_t command_length = 8;
648     MakeRequestPacketHeader (command, request_packet, command_length);
649     DataExtractor reply_packet;
650     if (SendRequestAndGetReply (command, request_packet, reply_packet))
651     {
652         const char *kernel_version_cstr = reply_packet.PeekCStr(8);
653         if (kernel_version_cstr && kernel_version_cstr[0])
654             m_kernel_version.assign (kernel_version_cstr);
655         return true;
656     }
657     return false;
658 }
659 
660 bool
661 CommunicationKDP::SendRequestDisconnect ()
662 {
663     PacketStreamType request_packet (Stream::eBinary, m_addr_byte_size, m_byte_order);
664     const CommandType command = KDP_DISCONNECT;
665     const uint32_t command_length = 8;
666     MakeRequestPacketHeader (command, request_packet, command_length);
667     DataExtractor reply_packet;
668     if (SendRequestAndGetReply (command, request_packet, reply_packet))
669     {
670         // Are we supposed to get a reply for disconnect?
671     }
672     ClearKDPSettings ();
673     return true;
674 }
675 
676 uint32_t
677 CommunicationKDP::SendRequestReadMemory (lldb::addr_t addr,
678                                          void *dst,
679                                          uint32_t dst_len,
680                                          Error &error)
681 {
682     PacketStreamType request_packet (Stream::eBinary, m_addr_byte_size, m_byte_order);
683     bool use_64 = (GetVersion() >= 11);
684     uint32_t command_addr_byte_size = use_64 ? 8 : 4;
685     const CommandType command = use_64 ? KDP_READMEM64 : KDP_READMEM;
686     // Size is header + address size + uint32_t length
687     const uint32_t command_length = 8 + command_addr_byte_size + 4;
688     MakeRequestPacketHeader (command, request_packet, command_length);
689     request_packet.PutMaxHex64 (addr, command_addr_byte_size);
690     request_packet.PutHex32 (dst_len);
691     DataExtractor reply_packet;
692     if (SendRequestAndGetReply (command, request_packet, reply_packet))
693     {
694         lldb::offset_t offset = 8;
695         uint32_t kdp_error = reply_packet.GetU32 (&offset);
696         uint32_t src_len = reply_packet.GetByteSize() - 12;
697 
698         if (src_len > 0)
699         {
700             const void *src = reply_packet.GetData(&offset, src_len);
701             if (src)
702             {
703                 ::memcpy (dst, src, src_len);
704                 error.Clear();
705                 return src_len;
706             }
707         }
708         if (kdp_error)
709             error.SetErrorStringWithFormat ("kdp read memory failed (error %u)", kdp_error);
710         else
711             error.SetErrorString ("kdp read memory failed");
712     }
713     else
714     {
715         error.SetErrorString ("failed to send packet");
716     }
717     return 0;
718 }
719 
720 
721 uint32_t
722 CommunicationKDP::SendRequestWriteMemory (lldb::addr_t addr,
723                                           const void *src,
724                                           uint32_t src_len,
725                                           Error &error)
726 {
727     PacketStreamType request_packet (Stream::eBinary, m_addr_byte_size, m_byte_order);
728     bool use_64 = (GetVersion() >= 11);
729     uint32_t command_addr_byte_size = use_64 ? 8 : 4;
730     const CommandType command = use_64 ? KDP_WRITEMEM64 : KDP_WRITEMEM;
731     // Size is header + address size + uint32_t length
732     const uint32_t command_length = 8 + command_addr_byte_size + 4 + src_len;
733     MakeRequestPacketHeader (command, request_packet, command_length);
734     request_packet.PutMaxHex64 (addr, command_addr_byte_size);
735     request_packet.PutHex32 (src_len);
736     request_packet.PutRawBytes(src, src_len);
737 
738     DataExtractor reply_packet;
739     if (SendRequestAndGetReply (command, request_packet, reply_packet))
740     {
741         lldb::offset_t offset = 8;
742         uint32_t kdp_error = reply_packet.GetU32 (&offset);
743         if (kdp_error)
744             error.SetErrorStringWithFormat ("kdp write memory failed (error %u)", kdp_error);
745         else
746         {
747             error.Clear();
748             return src_len;
749         }
750     }
751     else
752     {
753         error.SetErrorString ("failed to send packet");
754     }
755     return 0;
756 }
757 
758 bool
759 CommunicationKDP::SendRawRequest (uint8_t command_byte,
760                                   const void *src,  // Raw packet payload bytes
761                                   uint32_t src_len, // Raw packet payload length
762                                   DataExtractor &reply_packet,
763                                   Error &error)
764 {
765     PacketStreamType request_packet (Stream::eBinary, m_addr_byte_size, m_byte_order);
766     // Size is header + address size + uint32_t length
767     const uint32_t command_length = 8 + src_len;
768     const CommandType command = (CommandType)command_byte;
769     MakeRequestPacketHeader (command, request_packet, command_length);
770     request_packet.PutRawBytes(src, src_len);
771 
772     if (SendRequestAndGetReply (command, request_packet, reply_packet))
773     {
774         lldb::offset_t offset = 8;
775         uint32_t kdp_error = reply_packet.GetU32 (&offset);
776         if (kdp_error  && (command_byte != KDP_DUMPINFO))
777             error.SetErrorStringWithFormat ("request packet 0x%8.8x failed (error %u)", command_byte, kdp_error);
778         else
779         {
780             error.Clear();
781             return true;
782         }
783     }
784     else
785     {
786         error.SetErrorString ("failed to send packet");
787     }
788     return false;
789 }
790 
791 
792 const char *
793 CommunicationKDP::GetCommandAsCString (uint8_t command)
794 {
795     switch (command)
796     {
797     case KDP_CONNECT:               return "KDP_CONNECT";
798     case KDP_DISCONNECT:            return "KDP_DISCONNECT";
799     case KDP_HOSTINFO:              return "KDP_HOSTINFO";
800     case KDP_VERSION:               return "KDP_VERSION";
801     case KDP_MAXBYTES:              return "KDP_MAXBYTES";
802     case KDP_READMEM:               return "KDP_READMEM";
803     case KDP_WRITEMEM:              return "KDP_WRITEMEM";
804     case KDP_READREGS:              return "KDP_READREGS";
805     case KDP_WRITEREGS:             return "KDP_WRITEREGS";
806     case KDP_LOAD:                  return "KDP_LOAD";
807     case KDP_IMAGEPATH:             return "KDP_IMAGEPATH";
808     case KDP_SUSPEND:               return "KDP_SUSPEND";
809     case KDP_RESUMECPUS:            return "KDP_RESUMECPUS";
810     case KDP_EXCEPTION:             return "KDP_EXCEPTION";
811     case KDP_TERMINATION:           return "KDP_TERMINATION";
812     case KDP_BREAKPOINT_SET:        return "KDP_BREAKPOINT_SET";
813     case KDP_BREAKPOINT_REMOVE:     return "KDP_BREAKPOINT_REMOVE";
814     case KDP_REGIONS:               return "KDP_REGIONS";
815     case KDP_REATTACH:              return "KDP_REATTACH";
816     case KDP_HOSTREBOOT:            return "KDP_HOSTREBOOT";
817     case KDP_READMEM64:             return "KDP_READMEM64";
818     case KDP_WRITEMEM64:            return "KDP_WRITEMEM64";
819     case KDP_BREAKPOINT_SET64:      return "KDP_BREAKPOINT64_SET";
820     case KDP_BREAKPOINT_REMOVE64:   return "KDP_BREAKPOINT64_REMOVE";
821     case KDP_KERNELVERSION:         return "KDP_KERNELVERSION";
822     case KDP_READPHYSMEM64:         return "KDP_READPHYSMEM64";
823     case KDP_WRITEPHYSMEM64:        return "KDP_WRITEPHYSMEM64";
824     case KDP_READIOPORT:            return "KDP_READIOPORT";
825     case KDP_WRITEIOPORT:           return "KDP_WRITEIOPORT";
826     case KDP_READMSR64:             return "KDP_READMSR64";
827     case KDP_WRITEMSR64:            return "KDP_WRITEMSR64";
828     case KDP_DUMPINFO:              return "KDP_DUMPINFO";
829     }
830     return NULL;
831 }
832 
833 void
834 CommunicationKDP::DumpPacket (Stream &s, const void *data, uint32_t data_len)
835 {
836     DataExtractor extractor (data, data_len, m_byte_order, m_addr_byte_size);
837     DumpPacket (s, extractor);
838 }
839 
840 void
841 CommunicationKDP::DumpPacket (Stream &s, const DataExtractor& packet)
842 {
843     const char *error_desc = NULL;
844     if (packet.GetByteSize() < 8)
845     {
846         error_desc = "error: invalid packet (too short): ";
847     }
848     else
849     {
850         lldb::offset_t offset = 0;
851         const uint8_t first_packet_byte = packet.GetU8 (&offset);
852         const uint8_t sequence_id = packet.GetU8 (&offset);
853         const uint16_t length = packet.GetU16 (&offset);
854         const uint32_t key = packet.GetU32 (&offset);
855         const CommandType command = ExtractCommand (first_packet_byte);
856         const char *command_name = GetCommandAsCString (command);
857         if (command_name)
858         {
859             const bool is_reply = ExtractIsReply(first_packet_byte);
860             s.Printf ("(running=%i) %s %24s: 0x%2.2x 0x%2.2x 0x%4.4x 0x%8.8x ",
861                       IsRunning(),
862                       is_reply ? "<--" : "-->",
863                       command_name,
864                       first_packet_byte,
865                       sequence_id,
866                       length,
867                       key);
868 
869             if (is_reply)
870             {
871                 // Dump request reply packets
872                 switch (command)
873                 {
874                     // Commands that return a single 32 bit error
875                     case KDP_CONNECT:
876                     case KDP_WRITEMEM:
877                     case KDP_WRITEMEM64:
878                     case KDP_BREAKPOINT_SET:
879                     case KDP_BREAKPOINT_REMOVE:
880                     case KDP_BREAKPOINT_SET64:
881                     case KDP_BREAKPOINT_REMOVE64:
882                     case KDP_WRITEREGS:
883                     case KDP_LOAD:
884                     case KDP_WRITEIOPORT:
885                     case KDP_WRITEMSR64:
886                         {
887                             const uint32_t error = packet.GetU32 (&offset);
888                             s.Printf(" (error=0x%8.8x)", error);
889                         }
890                         break;
891 
892                     case KDP_DISCONNECT:
893                     case KDP_REATTACH:
894                     case KDP_HOSTREBOOT:
895                     case KDP_SUSPEND:
896                     case KDP_RESUMECPUS:
897                     case KDP_EXCEPTION:
898                     case KDP_TERMINATION:
899                         // No return value for the reply, just the header to ack
900                         s.PutCString(" ()");
901                         break;
902 
903                     case KDP_HOSTINFO:
904                         {
905                             const uint32_t cpu_mask = packet.GetU32 (&offset);
906                             const uint32_t cpu_type = packet.GetU32 (&offset);
907                             const uint32_t cpu_subtype = packet.GetU32 (&offset);
908                             s.Printf(" (cpu_mask=0x%8.8x, cpu_type=0x%8.8x, cpu_subtype=0x%8.8x)", cpu_mask, cpu_type, cpu_subtype);
909                         }
910                         break;
911 
912                     case KDP_VERSION:
913                         {
914                             const uint32_t version = packet.GetU32 (&offset);
915                             const uint32_t feature = packet.GetU32 (&offset);
916                             s.Printf(" (version=0x%8.8x, feature=0x%8.8x)", version, feature);
917                         }
918                         break;
919 
920                     case KDP_REGIONS:
921                         {
922                             const uint32_t region_count = packet.GetU32 (&offset);
923                             s.Printf(" (count = %u", region_count);
924                             for (uint32_t i=0; i<region_count; ++i)
925                             {
926                                 const addr_t region_addr = packet.GetPointer (&offset);
927                                 const uint32_t region_size = packet.GetU32 (&offset);
928                                 const uint32_t region_prot = packet.GetU32 (&offset);
929                                 s.Printf("\n\tregion[%" PRIu64 "] = { range = [0x%16.16" PRIx64 " - 0x%16.16" PRIx64 "), size = 0x%8.8x, prot = %s }", region_addr, region_addr, region_addr + region_size, region_size, GetPermissionsAsCString (region_prot));
930                             }
931                         }
932                         break;
933 
934                     case KDP_READMEM:
935                     case KDP_READMEM64:
936                     case KDP_READPHYSMEM64:
937                         {
938                             const uint32_t error = packet.GetU32 (&offset);
939                             const uint32_t count = packet.GetByteSize() - offset;
940                             s.Printf(" (error = 0x%8.8x:\n", error);
941                             if (count > 0)
942                                 packet.Dump (&s,                        // Stream to dump to
943                                              offset,                    // Offset within "packet"
944                                              eFormatBytesWithASCII,     // Format to use
945                                              1,                         // Size of each item in bytes
946                                              count,                     // Number of items
947                                              16,                        // Number per line
948                                              m_last_read_memory_addr,   // Don't show addresses before each line
949                                              0, 0);                     // No bitfields
950                         }
951                         break;
952 
953                     case KDP_READREGS:
954                         {
955                             const uint32_t error = packet.GetU32 (&offset);
956                             const uint32_t count = packet.GetByteSize() - offset;
957                             s.Printf(" (error = 0x%8.8x regs:\n", error);
958                             if (count > 0)
959                                 packet.Dump (&s,                        // Stream to dump to
960                                              offset,                    // Offset within "packet"
961                                              eFormatHex,                // Format to use
962                                              m_addr_byte_size,          // Size of each item in bytes
963                                              count / m_addr_byte_size,  // Number of items
964                                              16 / m_addr_byte_size,     // Number per line
965                                              LLDB_INVALID_ADDRESS,      // Don't show addresses before each line
966                                              0, 0);                     // No bitfields
967                         }
968                         break;
969 
970                     case KDP_KERNELVERSION:
971                         {
972                             const char *kernel_version = packet.PeekCStr(8);
973                             s.Printf(" (version = \"%s\")", kernel_version);
974                         }
975                         break;
976 
977                     case KDP_MAXBYTES:
978                         {
979                             const uint32_t max_bytes = packet.GetU32 (&offset);
980                             s.Printf(" (max_bytes = 0x%8.8x (%u))", max_bytes, max_bytes);
981                         }
982                         break;
983                     case KDP_IMAGEPATH:
984                         {
985                             const char *path = packet.GetCStr(&offset);
986                             s.Printf(" (path = \"%s\")", path);
987                         }
988                         break;
989 
990                     case KDP_READIOPORT:
991                     case KDP_READMSR64:
992                         {
993                             const uint32_t error = packet.GetU32 (&offset);
994                             const uint32_t count = packet.GetByteSize() - offset;
995                             s.Printf(" (error = 0x%8.8x io:\n", error);
996                             if (count > 0)
997                                 packet.Dump (&s,                        // Stream to dump to
998                                              offset,                    // Offset within "packet"
999                                              eFormatHex,                // Format to use
1000                                              1,                         // Size of each item in bytes
1001                                              count,                     // Number of items
1002                                              16,                        // Number per line
1003                                              LLDB_INVALID_ADDRESS,      // Don't show addresses before each line
1004                                              0, 0);                     // No bitfields
1005                         }
1006                         break;
1007                     case KDP_DUMPINFO:
1008                         {
1009                             const uint32_t count = packet.GetByteSize() - offset;
1010                             s.Printf(" (count = %u, bytes = \n", count);
1011                             if (count > 0)
1012                                 packet.Dump (&s,                        // Stream to dump to
1013                                              offset,                    // Offset within "packet"
1014                                              eFormatHex,                // Format to use
1015                                              1,                         // Size of each item in bytes
1016                                              count,                     // Number of items
1017                                              16,                        // Number per line
1018                                              LLDB_INVALID_ADDRESS,      // Don't show addresses before each line
1019                                              0, 0);                     // No bitfields
1020 
1021                         }
1022                         break;
1023 
1024                     default:
1025                         s.Printf(" (add support for dumping this packet reply!!!");
1026                         break;
1027 
1028                 }
1029             }
1030             else
1031             {
1032                 // Dump request packets
1033                 switch (command)
1034                 {
1035                     case KDP_CONNECT:
1036                         {
1037                             const uint16_t reply_port = ntohs(packet.GetU16 (&offset));
1038                             const uint16_t exc_port = ntohs(packet.GetU16 (&offset));
1039                             s.Printf(" (reply_port = %u, exc_port = %u, greeting = \"%s\")", reply_port, exc_port, packet.GetCStr(&offset));
1040                         }
1041                         break;
1042 
1043                     case KDP_DISCONNECT:
1044                     case KDP_HOSTREBOOT:
1045                     case KDP_HOSTINFO:
1046                     case KDP_VERSION:
1047                     case KDP_REGIONS:
1048                     case KDP_KERNELVERSION:
1049                     case KDP_MAXBYTES:
1050                     case KDP_IMAGEPATH:
1051                     case KDP_SUSPEND:
1052                         // No args, just the header in the request...
1053                         s.PutCString(" ()");
1054                         break;
1055 
1056                     case KDP_RESUMECPUS:
1057                         {
1058                             const uint32_t cpu_mask = packet.GetU32 (&offset);
1059                             s.Printf(" (cpu_mask = 0x%8.8x)", cpu_mask);
1060                         }
1061                         break;
1062 
1063                     case KDP_READMEM:
1064                         {
1065                             const uint32_t addr = packet.GetU32 (&offset);
1066                             const uint32_t size = packet.GetU32 (&offset);
1067                             s.Printf(" (addr = 0x%8.8x, size = %u)", addr, size);
1068                             m_last_read_memory_addr = addr;
1069                         }
1070                         break;
1071 
1072                     case KDP_WRITEMEM:
1073                         {
1074                             const uint32_t addr = packet.GetU32 (&offset);
1075                             const uint32_t size = packet.GetU32 (&offset);
1076                             s.Printf(" (addr = 0x%8.8x, size = %u, bytes = \n", addr, size);
1077                             if (size > 0)
1078                                 DataExtractor::DumpHexBytes(&s, packet.GetData(&offset, size), size, 32, addr);
1079                         }
1080                         break;
1081 
1082                     case KDP_READMEM64:
1083                         {
1084                             const uint64_t addr = packet.GetU64 (&offset);
1085                             const uint32_t size = packet.GetU32 (&offset);
1086                             s.Printf(" (addr = 0x%16.16" PRIx64 ", size = %u)", addr, size);
1087                             m_last_read_memory_addr = addr;
1088                         }
1089                         break;
1090 
1091                     case KDP_READPHYSMEM64:
1092                         {
1093                             const uint64_t addr = packet.GetU64 (&offset);
1094                             const uint32_t size = packet.GetU32 (&offset);
1095                             const uint32_t lcpu = packet.GetU16 (&offset);
1096                             s.Printf(" (addr = 0x%16.16llx, size = %u, lcpu = %u)", addr, size, lcpu);
1097                             m_last_read_memory_addr = addr;
1098                         }
1099                         break;
1100 
1101                     case KDP_WRITEMEM64:
1102                         {
1103                             const uint64_t addr = packet.GetU64 (&offset);
1104                             const uint32_t size = packet.GetU32 (&offset);
1105                             s.Printf(" (addr = 0x%16.16" PRIx64 ", size = %u, bytes = \n", addr, size);
1106                             if (size > 0)
1107                                 DataExtractor::DumpHexBytes(&s, packet.GetData(&offset, size), size, 32, addr);
1108                         }
1109                         break;
1110 
1111                     case KDP_WRITEPHYSMEM64:
1112                         {
1113                             const uint64_t addr = packet.GetU64 (&offset);
1114                             const uint32_t size = packet.GetU32 (&offset);
1115                             const uint32_t lcpu = packet.GetU16 (&offset);
1116                             s.Printf(" (addr = 0x%16.16llx, size = %u, lcpu = %u, bytes = \n", addr, size, lcpu);
1117                             if (size > 0)
1118                                 DataExtractor::DumpHexBytes(&s, packet.GetData(&offset, size), size, 32, addr);
1119                         }
1120                         break;
1121 
1122                     case KDP_READREGS:
1123                         {
1124                             const uint32_t cpu = packet.GetU32 (&offset);
1125                             const uint32_t flavor = packet.GetU32 (&offset);
1126                             s.Printf(" (cpu = %u, flavor = %u)", cpu, flavor);
1127                         }
1128                         break;
1129 
1130                     case KDP_WRITEREGS:
1131                         {
1132                             const uint32_t cpu = packet.GetU32 (&offset);
1133                             const uint32_t flavor = packet.GetU32 (&offset);
1134                             const uint32_t nbytes = packet.GetByteSize() - offset;
1135                             s.Printf(" (cpu = %u, flavor = %u, regs = \n", cpu, flavor);
1136                             if (nbytes > 0)
1137                                 packet.Dump (&s,                        // Stream to dump to
1138                                              offset,                    // Offset within "packet"
1139                                              eFormatHex,                // Format to use
1140                                              m_addr_byte_size,          // Size of each item in bytes
1141                                              nbytes / m_addr_byte_size, // Number of items
1142                                              16 / m_addr_byte_size,     // Number per line
1143                                              LLDB_INVALID_ADDRESS,      // Don't show addresses before each line
1144                                              0, 0);                     // No bitfields
1145                         }
1146                         break;
1147 
1148 
1149                     case KDP_BREAKPOINT_SET:
1150                     case KDP_BREAKPOINT_REMOVE:
1151                         {
1152                             const uint32_t addr = packet.GetU32 (&offset);
1153                             s.Printf(" (addr = 0x%8.8x)", addr);
1154                         }
1155                         break;
1156 
1157                     case KDP_BREAKPOINT_SET64:
1158                     case KDP_BREAKPOINT_REMOVE64:
1159                         {
1160                             const uint64_t addr = packet.GetU64 (&offset);
1161                             s.Printf(" (addr = 0x%16.16" PRIx64 ")", addr);
1162                         }
1163                         break;
1164 
1165 
1166                     case KDP_LOAD:
1167                         {
1168                             const char *path = packet.GetCStr(&offset);
1169                             s.Printf(" (path = \"%s\")", path);
1170                         }
1171                         break;
1172 
1173                     case KDP_EXCEPTION:
1174                         {
1175                             const uint32_t count = packet.GetU32 (&offset);
1176 
1177                             for (uint32_t i=0; i<count; ++i)
1178                             {
1179                                 const uint32_t cpu = packet.GetU32 (&offset);
1180                                 const uint32_t exc = packet.GetU32 (&offset);
1181                                 const uint32_t code = packet.GetU32 (&offset);
1182                                 const uint32_t subcode = packet.GetU32 (&offset);
1183                                 const char *exc_cstr = NULL;
1184                                 switch (exc)
1185                                 {
1186                                     case 1:  exc_cstr = "EXC_BAD_ACCESS"; break;
1187                                     case 2:  exc_cstr = "EXC_BAD_INSTRUCTION"; break;
1188                                     case 3:  exc_cstr = "EXC_ARITHMETIC"; break;
1189                                     case 4:  exc_cstr = "EXC_EMULATION"; break;
1190                                     case 5:  exc_cstr = "EXC_SOFTWARE"; break;
1191                                     case 6:  exc_cstr = "EXC_BREAKPOINT"; break;
1192                                     case 7:  exc_cstr = "EXC_SYSCALL"; break;
1193                                     case 8:  exc_cstr = "EXC_MACH_SYSCALL"; break;
1194                                     case 9:  exc_cstr = "EXC_RPC_ALERT"; break;
1195                                     case 10: exc_cstr = "EXC_CRASH"; break;
1196                                     default:
1197                                         break;
1198                                 }
1199 
1200                                 s.Printf ("{ cpu = 0x%8.8x, exc = %s (%u), code = %u (0x%8.8x), subcode = %u (0x%8.8x)} ",
1201                                           cpu, exc_cstr, exc, code, code, subcode, subcode);
1202                             }
1203                         }
1204                         break;
1205 
1206                     case KDP_TERMINATION:
1207                         {
1208                             const uint32_t term_code = packet.GetU32 (&offset);
1209                             const uint32_t exit_code = packet.GetU32 (&offset);
1210                             s.Printf(" (term_code = 0x%8.8x (%u), exit_code = 0x%8.8x (%u))", term_code, term_code, exit_code, exit_code);
1211                         }
1212                         break;
1213 
1214                     case KDP_REATTACH:
1215                         {
1216                             const uint16_t reply_port = ntohs(packet.GetU16 (&offset));
1217                             s.Printf(" (reply_port = %u)", reply_port);
1218                         }
1219                         break;
1220 
1221                     case KDP_READMSR64:
1222                         {
1223                             const uint32_t address = packet.GetU32 (&offset);
1224                             const uint16_t lcpu = packet.GetU16 (&offset);
1225                             s.Printf(" (address=0x%8.8x, lcpu=0x%4.4x)", address, lcpu);
1226                         }
1227                         break;
1228 
1229                     case KDP_WRITEMSR64:
1230                         {
1231                             const uint32_t address = packet.GetU32 (&offset);
1232                             const uint16_t lcpu = packet.GetU16 (&offset);
1233                             const uint32_t nbytes = packet.GetByteSize() - offset;
1234                             s.Printf(" (address=0x%8.8x, lcpu=0x%4.4x, nbytes=0x%8.8x)", lcpu, address, nbytes);
1235                             if (nbytes > 0)
1236                                 packet.Dump (&s,                        // Stream to dump to
1237                                              offset,                    // Offset within "packet"
1238                                              eFormatHex,                // Format to use
1239                                              1,                         // Size of each item in bytes
1240                                              nbytes,                    // Number of items
1241                                              16,                        // Number per line
1242                                              LLDB_INVALID_ADDRESS,      // Don't show addresses before each line
1243                                              0, 0);                     // No bitfields
1244                         }
1245                         break;
1246 
1247                     case KDP_READIOPORT:
1248                         {
1249                             const uint16_t lcpu = packet.GetU16 (&offset);
1250                             const uint16_t address = packet.GetU16 (&offset);
1251                             const uint16_t nbytes = packet.GetU16 (&offset);
1252                             s.Printf(" (lcpu=0x%4.4x, address=0x%4.4x, nbytes=%u)", lcpu, address, nbytes);
1253                         }
1254                         break;
1255 
1256                     case KDP_WRITEIOPORT:
1257                          {
1258                             const uint16_t lcpu = packet.GetU16 (&offset);
1259                             const uint16_t address = packet.GetU16 (&offset);
1260                             const uint16_t nbytes = packet.GetU16 (&offset);
1261                             s.Printf(" (lcpu = %u, addr = 0x%4.4x, nbytes = %u, bytes = \n", lcpu, address, nbytes);
1262                             if (nbytes > 0)
1263                                 packet.Dump (&s,                        // Stream to dump to
1264                                              offset,                    // Offset within "packet"
1265                                              eFormatHex,                // Format to use
1266                                              1,                         // Size of each item in bytes
1267                                              nbytes,                    // Number of items
1268                                              16,                        // Number per line
1269                                              LLDB_INVALID_ADDRESS,      // Don't show addresses before each line
1270                                              0, 0);                     // No bitfields
1271                         }
1272                         break;
1273 
1274                     case KDP_DUMPINFO:
1275                         {
1276                             const uint32_t count = packet.GetByteSize() - offset;
1277                             s.Printf(" (count = %u, bytes = \n", count);
1278                             if (count > 0)
1279                                 packet.Dump (&s,                        // Stream to dump to
1280                                              offset,                    // Offset within "packet"
1281                                              eFormatHex,                // Format to use
1282                                              1,                         // Size of each item in bytes
1283                                              count,                     // Number of items
1284                                              16,                        // Number per line
1285                                              LLDB_INVALID_ADDRESS,      // Don't show addresses before each line
1286                                              0, 0);                     // No bitfields
1287 
1288                         }
1289                         break;
1290 
1291                }
1292             }
1293         }
1294         else
1295         {
1296             error_desc = "error: invalid packet command: ";
1297         }
1298     }
1299 
1300     if (error_desc)
1301     {
1302         s.PutCString (error_desc);
1303 
1304         packet.Dump (&s,                    // Stream to dump to
1305                      0,                     // Offset into "packet"
1306                      eFormatBytes,          // Dump as hex bytes
1307                      1,                     // Size of each item is 1 for single bytes
1308                      packet.GetByteSize(),  // Number of bytes
1309                      UINT32_MAX,            // Num bytes per line
1310                      LLDB_INVALID_ADDRESS,  // Base address
1311                      0, 0);                 // Bitfield info set to not do anything bitfield related
1312     }
1313 }
1314 
1315 uint32_t
1316 CommunicationKDP::SendRequestReadRegisters (uint32_t cpu,
1317                                             uint32_t flavor,
1318                                             void *dst,
1319                                             uint32_t dst_len,
1320                                             Error &error)
1321 {
1322     PacketStreamType request_packet (Stream::eBinary, m_addr_byte_size, m_byte_order);
1323     const CommandType command = KDP_READREGS;
1324     // Size is header + 4 byte cpu and 4 byte flavor
1325     const uint32_t command_length = 8 + 4 + 4;
1326     MakeRequestPacketHeader (command, request_packet, command_length);
1327     request_packet.PutHex32 (cpu);
1328     request_packet.PutHex32 (flavor);
1329     DataExtractor reply_packet;
1330     if (SendRequestAndGetReply (command, request_packet, reply_packet))
1331     {
1332         lldb::offset_t offset = 8;
1333         uint32_t kdp_error = reply_packet.GetU32 (&offset);
1334         uint32_t src_len = reply_packet.GetByteSize() - 12;
1335 
1336         if (src_len > 0)
1337         {
1338             const uint32_t bytes_to_copy = std::min<uint32_t>(src_len, dst_len);
1339             const void *src = reply_packet.GetData(&offset, bytes_to_copy);
1340             if (src)
1341             {
1342                 ::memcpy (dst, src, bytes_to_copy);
1343                 error.Clear();
1344                 // Return the number of bytes we could have returned regardless if
1345                 // we copied them or not, just so we know when things don't match up
1346                 return src_len;
1347             }
1348         }
1349         if (kdp_error)
1350             error.SetErrorStringWithFormat("failed to read kdp registers for cpu %u flavor %u (error %u)", cpu, flavor, kdp_error);
1351         else
1352             error.SetErrorStringWithFormat("failed to read kdp registers for cpu %u flavor %u", cpu, flavor);
1353     }
1354     else
1355     {
1356         error.SetErrorString ("failed to send packet");
1357     }
1358     return 0;
1359 }
1360 
1361 uint32_t
1362 CommunicationKDP::SendRequestWriteRegisters (uint32_t cpu,
1363                                              uint32_t flavor,
1364                                              const void *src,
1365                                              uint32_t src_len,
1366                                              Error &error)
1367 {
1368     PacketStreamType request_packet (Stream::eBinary, m_addr_byte_size, m_byte_order);
1369     const CommandType command = KDP_WRITEREGS;
1370     // Size is header + 4 byte cpu and 4 byte flavor
1371     const uint32_t command_length = 8 + 4 + 4 + src_len;
1372     MakeRequestPacketHeader (command, request_packet, command_length);
1373     request_packet.PutHex32 (cpu);
1374     request_packet.PutHex32 (flavor);
1375     request_packet.Write(src, src_len);
1376     DataExtractor reply_packet;
1377     if (SendRequestAndGetReply (command, request_packet, reply_packet))
1378     {
1379         lldb::offset_t offset = 8;
1380         uint32_t kdp_error = reply_packet.GetU32 (&offset);
1381         if (kdp_error == 0)
1382             return src_len;
1383         error.SetErrorStringWithFormat("failed to read kdp registers for cpu %u flavor %u (error %u)", cpu, flavor, kdp_error);
1384     }
1385     else
1386     {
1387         error.SetErrorString ("failed to send packet");
1388     }
1389     return 0;
1390 }
1391 
1392 
1393 bool
1394 CommunicationKDP::SendRequestResume ()
1395 {
1396     PacketStreamType request_packet (Stream::eBinary, m_addr_byte_size, m_byte_order);
1397     const CommandType command = KDP_RESUMECPUS;
1398     const uint32_t command_length = 12;
1399     MakeRequestPacketHeader (command, request_packet, command_length);
1400     request_packet.PutHex32(GetCPUMask());
1401 
1402     DataExtractor reply_packet;
1403     if (SendRequestAndGetReply (command, request_packet, reply_packet))
1404         return true;
1405     return false;
1406 }
1407 
1408 bool
1409 CommunicationKDP::SendRequestBreakpoint (bool set, addr_t addr)
1410 {
1411     PacketStreamType request_packet (Stream::eBinary, m_addr_byte_size, m_byte_order);
1412     bool use_64 = (GetVersion() >= 11);
1413     uint32_t command_addr_byte_size = use_64 ? 8 : 4;
1414     const CommandType command = set ? (use_64 ? KDP_BREAKPOINT_SET64    : KDP_BREAKPOINT_SET   ):
1415                                       (use_64 ? KDP_BREAKPOINT_REMOVE64 : KDP_BREAKPOINT_REMOVE);
1416 
1417     const uint32_t command_length = 8 + command_addr_byte_size;
1418     MakeRequestPacketHeader (command, request_packet, command_length);
1419     request_packet.PutMaxHex64 (addr, command_addr_byte_size);
1420 
1421     DataExtractor reply_packet;
1422     if (SendRequestAndGetReply (command, request_packet, reply_packet))
1423     {
1424         lldb::offset_t offset = 8;
1425         uint32_t kdp_error = reply_packet.GetU32 (&offset);
1426         if (kdp_error == 0)
1427             return true;
1428     }
1429     return false;
1430 }
1431 
1432 bool
1433 CommunicationKDP::SendRequestSuspend ()
1434 {
1435     PacketStreamType request_packet (Stream::eBinary, m_addr_byte_size, m_byte_order);
1436     const CommandType command = KDP_SUSPEND;
1437     const uint32_t command_length = 8;
1438     MakeRequestPacketHeader (command, request_packet, command_length);
1439     DataExtractor reply_packet;
1440     if (SendRequestAndGetReply (command, request_packet, reply_packet))
1441         return true;
1442     return false;
1443 }
1444 
1445