1 //===-- GDBRemoteCommunicationClient.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 "GDBRemoteCommunicationClient.h"
12
13 // C Includes
14 #include <sys/stat.h>
15
16 // C++ Includes
17 #include <sstream>
18
19 // Other libraries and framework includes
20 #include "llvm/ADT/Triple.h"
21 #include "lldb/Interpreter/Args.h"
22 #include "lldb/Core/ConnectionFileDescriptor.h"
23 #include "lldb/Core/Log.h"
24 #include "lldb/Core/State.h"
25 #include "lldb/Core/StreamGDBRemote.h"
26 #include "lldb/Core/StreamString.h"
27 #include "lldb/Host/Endian.h"
28 #include "lldb/Host/Host.h"
29 #include "lldb/Host/TimeValue.h"
30
31 // Project includes
32 #include "Utility/StringExtractorGDBRemote.h"
33 #include "ProcessGDBRemote.h"
34 #include "ProcessGDBRemoteLog.h"
35 #include "lldb/Host/Config.h"
36
37 using namespace lldb;
38 using namespace lldb_private;
39
40 #ifdef LLDB_DISABLE_POSIX
41 #define SIGSTOP 17
42 #endif
43
44 //----------------------------------------------------------------------
45 // GDBRemoteCommunicationClient constructor
46 //----------------------------------------------------------------------
GDBRemoteCommunicationClient(bool is_platform)47 GDBRemoteCommunicationClient::GDBRemoteCommunicationClient(bool is_platform) :
48 GDBRemoteCommunication("gdb-remote.client", "gdb-remote.client.rx_packet", is_platform),
49 m_supports_not_sending_acks (eLazyBoolCalculate),
50 m_supports_thread_suffix (eLazyBoolCalculate),
51 m_supports_threads_in_stop_reply (eLazyBoolCalculate),
52 m_supports_vCont_all (eLazyBoolCalculate),
53 m_supports_vCont_any (eLazyBoolCalculate),
54 m_supports_vCont_c (eLazyBoolCalculate),
55 m_supports_vCont_C (eLazyBoolCalculate),
56 m_supports_vCont_s (eLazyBoolCalculate),
57 m_supports_vCont_S (eLazyBoolCalculate),
58 m_qHostInfo_is_valid (eLazyBoolCalculate),
59 m_qProcessInfo_is_valid (eLazyBoolCalculate),
60 m_supports_alloc_dealloc_memory (eLazyBoolCalculate),
61 m_supports_memory_region_info (eLazyBoolCalculate),
62 m_supports_watchpoint_support_info (eLazyBoolCalculate),
63 m_supports_detach_stay_stopped (eLazyBoolCalculate),
64 m_watchpoints_trigger_after_instruction(eLazyBoolCalculate),
65 m_attach_or_wait_reply(eLazyBoolCalculate),
66 m_prepare_for_reg_writing_reply (eLazyBoolCalculate),
67 m_supports_p (eLazyBoolCalculate),
68 m_supports_QSaveRegisterState (eLazyBoolCalculate),
69 m_supports_qXfer_libraries_read (eLazyBoolCalculate),
70 m_supports_qXfer_libraries_svr4_read (eLazyBoolCalculate),
71 m_supports_augmented_libraries_svr4_read (eLazyBoolCalculate),
72 m_supports_qProcessInfoPID (true),
73 m_supports_qfProcessInfo (true),
74 m_supports_qUserName (true),
75 m_supports_qGroupName (true),
76 m_supports_qThreadStopInfo (true),
77 m_supports_z0 (true),
78 m_supports_z1 (true),
79 m_supports_z2 (true),
80 m_supports_z3 (true),
81 m_supports_z4 (true),
82 m_supports_QEnvironment (true),
83 m_supports_QEnvironmentHexEncoded (true),
84 m_curr_tid (LLDB_INVALID_THREAD_ID),
85 m_curr_tid_run (LLDB_INVALID_THREAD_ID),
86 m_num_supported_hardware_watchpoints (0),
87 m_async_mutex (Mutex::eMutexTypeRecursive),
88 m_async_packet_predicate (false),
89 m_async_packet (),
90 m_async_result (PacketResult::Success),
91 m_async_response (),
92 m_async_signal (-1),
93 m_thread_id_to_used_usec_map (),
94 m_host_arch(),
95 m_process_arch(),
96 m_os_version_major (UINT32_MAX),
97 m_os_version_minor (UINT32_MAX),
98 m_os_version_update (UINT32_MAX),
99 m_os_build (),
100 m_os_kernel (),
101 m_hostname (),
102 m_default_packet_timeout (0),
103 m_max_packet_size (0)
104 {
105 }
106
107 //----------------------------------------------------------------------
108 // Destructor
109 //----------------------------------------------------------------------
~GDBRemoteCommunicationClient()110 GDBRemoteCommunicationClient::~GDBRemoteCommunicationClient()
111 {
112 if (IsConnected())
113 Disconnect();
114 }
115
116 bool
HandshakeWithServer(Error * error_ptr)117 GDBRemoteCommunicationClient::HandshakeWithServer (Error *error_ptr)
118 {
119 ResetDiscoverableSettings();
120
121 // Start the read thread after we send the handshake ack since if we
122 // fail to send the handshake ack, there is no reason to continue...
123 if (SendAck())
124 {
125 // Wait for any responses that might have been queued up in the remote
126 // GDB server and flush them all
127 StringExtractorGDBRemote response;
128 PacketResult packet_result = PacketResult::Success;
129 const uint32_t timeout_usec = 10 * 1000; // Wait for 10 ms for a response
130 while (packet_result == PacketResult::Success)
131 packet_result = WaitForPacketWithTimeoutMicroSecondsNoLock (response, timeout_usec);
132
133 // The return value from QueryNoAckModeSupported() is true if the packet
134 // was sent and _any_ response (including UNIMPLEMENTED) was received),
135 // or false if no response was received. This quickly tells us if we have
136 // a live connection to a remote GDB server...
137 if (QueryNoAckModeSupported())
138 {
139 #if 0
140 // Set above line to "#if 1" to test packet speed if remote GDB server
141 // supports the qSpeedTest packet...
142 TestPacketSpeed(10000);
143 #endif
144 return true;
145 }
146 else
147 {
148 if (error_ptr)
149 error_ptr->SetErrorString("failed to get reply to handshake packet");
150 }
151 }
152 else
153 {
154 if (error_ptr)
155 error_ptr->SetErrorString("failed to send the handshake ack");
156 }
157 return false;
158 }
159
160 bool
GetAugmentedLibrariesSVR4ReadSupported()161 GDBRemoteCommunicationClient::GetAugmentedLibrariesSVR4ReadSupported ()
162 {
163 if (m_supports_augmented_libraries_svr4_read == eLazyBoolCalculate)
164 {
165 GetRemoteQSupported();
166 }
167 return (m_supports_augmented_libraries_svr4_read == eLazyBoolYes);
168 }
169
170 bool
GetQXferLibrariesSVR4ReadSupported()171 GDBRemoteCommunicationClient::GetQXferLibrariesSVR4ReadSupported ()
172 {
173 if (m_supports_qXfer_libraries_svr4_read == eLazyBoolCalculate)
174 {
175 GetRemoteQSupported();
176 }
177 return (m_supports_qXfer_libraries_svr4_read == eLazyBoolYes);
178 }
179
180 bool
GetQXferLibrariesReadSupported()181 GDBRemoteCommunicationClient::GetQXferLibrariesReadSupported ()
182 {
183 if (m_supports_qXfer_libraries_read == eLazyBoolCalculate)
184 {
185 GetRemoteQSupported();
186 }
187 return (m_supports_qXfer_libraries_read == eLazyBoolYes);
188 }
189
190 uint64_t
GetRemoteMaxPacketSize()191 GDBRemoteCommunicationClient::GetRemoteMaxPacketSize()
192 {
193 if (m_max_packet_size == 0)
194 {
195 GetRemoteQSupported();
196 }
197 return m_max_packet_size;
198 }
199
200 bool
QueryNoAckModeSupported()201 GDBRemoteCommunicationClient::QueryNoAckModeSupported ()
202 {
203 if (m_supports_not_sending_acks == eLazyBoolCalculate)
204 {
205 m_send_acks = true;
206 m_supports_not_sending_acks = eLazyBoolNo;
207
208 StringExtractorGDBRemote response;
209 if (SendPacketAndWaitForResponse("QStartNoAckMode", response, false) == PacketResult::Success)
210 {
211 if (response.IsOKResponse())
212 {
213 m_send_acks = false;
214 m_supports_not_sending_acks = eLazyBoolYes;
215 }
216 return true;
217 }
218 }
219 return false;
220 }
221
222 void
GetListThreadsInStopReplySupported()223 GDBRemoteCommunicationClient::GetListThreadsInStopReplySupported ()
224 {
225 if (m_supports_threads_in_stop_reply == eLazyBoolCalculate)
226 {
227 m_supports_threads_in_stop_reply = eLazyBoolNo;
228
229 StringExtractorGDBRemote response;
230 if (SendPacketAndWaitForResponse("QListThreadsInStopReply", response, false) == PacketResult::Success)
231 {
232 if (response.IsOKResponse())
233 m_supports_threads_in_stop_reply = eLazyBoolYes;
234 }
235 }
236 }
237
238 bool
GetVAttachOrWaitSupported()239 GDBRemoteCommunicationClient::GetVAttachOrWaitSupported ()
240 {
241 if (m_attach_or_wait_reply == eLazyBoolCalculate)
242 {
243 m_attach_or_wait_reply = eLazyBoolNo;
244
245 StringExtractorGDBRemote response;
246 if (SendPacketAndWaitForResponse("qVAttachOrWaitSupported", response, false) == PacketResult::Success)
247 {
248 if (response.IsOKResponse())
249 m_attach_or_wait_reply = eLazyBoolYes;
250 }
251 }
252 if (m_attach_or_wait_reply == eLazyBoolYes)
253 return true;
254 else
255 return false;
256 }
257
258 bool
GetSyncThreadStateSupported()259 GDBRemoteCommunicationClient::GetSyncThreadStateSupported ()
260 {
261 if (m_prepare_for_reg_writing_reply == eLazyBoolCalculate)
262 {
263 m_prepare_for_reg_writing_reply = eLazyBoolNo;
264
265 StringExtractorGDBRemote response;
266 if (SendPacketAndWaitForResponse("qSyncThreadStateSupported", response, false) == PacketResult::Success)
267 {
268 if (response.IsOKResponse())
269 m_prepare_for_reg_writing_reply = eLazyBoolYes;
270 }
271 }
272 if (m_prepare_for_reg_writing_reply == eLazyBoolYes)
273 return true;
274 else
275 return false;
276 }
277
278
279 void
ResetDiscoverableSettings()280 GDBRemoteCommunicationClient::ResetDiscoverableSettings()
281 {
282 m_supports_not_sending_acks = eLazyBoolCalculate;
283 m_supports_thread_suffix = eLazyBoolCalculate;
284 m_supports_threads_in_stop_reply = eLazyBoolCalculate;
285 m_supports_vCont_c = eLazyBoolCalculate;
286 m_supports_vCont_C = eLazyBoolCalculate;
287 m_supports_vCont_s = eLazyBoolCalculate;
288 m_supports_vCont_S = eLazyBoolCalculate;
289 m_supports_p = eLazyBoolCalculate;
290 m_supports_QSaveRegisterState = eLazyBoolCalculate;
291 m_qHostInfo_is_valid = eLazyBoolCalculate;
292 m_qProcessInfo_is_valid = eLazyBoolCalculate;
293 m_supports_alloc_dealloc_memory = eLazyBoolCalculate;
294 m_supports_memory_region_info = eLazyBoolCalculate;
295 m_prepare_for_reg_writing_reply = eLazyBoolCalculate;
296 m_attach_or_wait_reply = eLazyBoolCalculate;
297 m_supports_qXfer_libraries_read = eLazyBoolCalculate;
298 m_supports_qXfer_libraries_svr4_read = eLazyBoolCalculate;
299 m_supports_augmented_libraries_svr4_read = eLazyBoolCalculate;
300
301 m_supports_qProcessInfoPID = true;
302 m_supports_qfProcessInfo = true;
303 m_supports_qUserName = true;
304 m_supports_qGroupName = true;
305 m_supports_qThreadStopInfo = true;
306 m_supports_z0 = true;
307 m_supports_z1 = true;
308 m_supports_z2 = true;
309 m_supports_z3 = true;
310 m_supports_z4 = true;
311 m_supports_QEnvironment = true;
312 m_supports_QEnvironmentHexEncoded = true;
313 m_host_arch.Clear();
314 m_process_arch.Clear();
315
316 m_max_packet_size = 0;
317 }
318
319 void
GetRemoteQSupported()320 GDBRemoteCommunicationClient::GetRemoteQSupported ()
321 {
322 // Clear out any capabilities we expect to see in the qSupported response
323 m_supports_qXfer_libraries_svr4_read = eLazyBoolNo;
324 m_supports_qXfer_libraries_read = eLazyBoolNo;
325 m_supports_augmented_libraries_svr4_read = eLazyBoolNo;
326 m_max_packet_size = UINT64_MAX; // It's supposed to always be there, but if not, we assume no limit
327
328 StringExtractorGDBRemote response;
329 if (SendPacketAndWaitForResponse("qSupported",
330 response,
331 /*send_async=*/false) == PacketResult::Success)
332 {
333 const char *response_cstr = response.GetStringRef().c_str();
334 if (::strstr (response_cstr, "qXfer:libraries-svr4:read+"))
335 m_supports_qXfer_libraries_svr4_read = eLazyBoolYes;
336 if (::strstr (response_cstr, "augmented-libraries-svr4-read"))
337 {
338 m_supports_qXfer_libraries_svr4_read = eLazyBoolYes; // implied
339 m_supports_augmented_libraries_svr4_read = eLazyBoolYes;
340 }
341 if (::strstr (response_cstr, "qXfer:libraries:read+"))
342 m_supports_qXfer_libraries_read = eLazyBoolYes;
343
344 const char *packet_size_str = ::strstr (response_cstr, "PacketSize=");
345 if (packet_size_str)
346 {
347 StringExtractorGDBRemote packet_response(packet_size_str + strlen("PacketSize="));
348 m_max_packet_size = packet_response.GetHexMaxU64(/*little_endian=*/false, UINT64_MAX);
349 if (m_max_packet_size == 0)
350 {
351 m_max_packet_size = UINT64_MAX; // Must have been a garbled response
352 Log *log (ProcessGDBRemoteLog::GetLogIfAllCategoriesSet (GDBR_LOG_PROCESS));
353 if (log)
354 log->Printf ("Garbled PacketSize spec in qSupported response");
355 }
356 }
357 }
358 }
359
360 bool
GetThreadSuffixSupported()361 GDBRemoteCommunicationClient::GetThreadSuffixSupported ()
362 {
363 if (m_supports_thread_suffix == eLazyBoolCalculate)
364 {
365 StringExtractorGDBRemote response;
366 m_supports_thread_suffix = eLazyBoolNo;
367 if (SendPacketAndWaitForResponse("QThreadSuffixSupported", response, false) == PacketResult::Success)
368 {
369 if (response.IsOKResponse())
370 m_supports_thread_suffix = eLazyBoolYes;
371 }
372 }
373 return m_supports_thread_suffix;
374 }
375 bool
GetVContSupported(char flavor)376 GDBRemoteCommunicationClient::GetVContSupported (char flavor)
377 {
378 if (m_supports_vCont_c == eLazyBoolCalculate)
379 {
380 StringExtractorGDBRemote response;
381 m_supports_vCont_any = eLazyBoolNo;
382 m_supports_vCont_all = eLazyBoolNo;
383 m_supports_vCont_c = eLazyBoolNo;
384 m_supports_vCont_C = eLazyBoolNo;
385 m_supports_vCont_s = eLazyBoolNo;
386 m_supports_vCont_S = eLazyBoolNo;
387 if (SendPacketAndWaitForResponse("vCont?", response, false) == PacketResult::Success)
388 {
389 const char *response_cstr = response.GetStringRef().c_str();
390 if (::strstr (response_cstr, ";c"))
391 m_supports_vCont_c = eLazyBoolYes;
392
393 if (::strstr (response_cstr, ";C"))
394 m_supports_vCont_C = eLazyBoolYes;
395
396 if (::strstr (response_cstr, ";s"))
397 m_supports_vCont_s = eLazyBoolYes;
398
399 if (::strstr (response_cstr, ";S"))
400 m_supports_vCont_S = eLazyBoolYes;
401
402 if (m_supports_vCont_c == eLazyBoolYes &&
403 m_supports_vCont_C == eLazyBoolYes &&
404 m_supports_vCont_s == eLazyBoolYes &&
405 m_supports_vCont_S == eLazyBoolYes)
406 {
407 m_supports_vCont_all = eLazyBoolYes;
408 }
409
410 if (m_supports_vCont_c == eLazyBoolYes ||
411 m_supports_vCont_C == eLazyBoolYes ||
412 m_supports_vCont_s == eLazyBoolYes ||
413 m_supports_vCont_S == eLazyBoolYes)
414 {
415 m_supports_vCont_any = eLazyBoolYes;
416 }
417 }
418 }
419
420 switch (flavor)
421 {
422 case 'a': return m_supports_vCont_any;
423 case 'A': return m_supports_vCont_all;
424 case 'c': return m_supports_vCont_c;
425 case 'C': return m_supports_vCont_C;
426 case 's': return m_supports_vCont_s;
427 case 'S': return m_supports_vCont_S;
428 default: break;
429 }
430 return false;
431 }
432
433 // Check if the target supports 'p' packet. It sends out a 'p'
434 // packet and checks the response. A normal packet will tell us
435 // that support is available.
436 //
437 // Takes a valid thread ID because p needs to apply to a thread.
438 bool
GetpPacketSupported(lldb::tid_t tid)439 GDBRemoteCommunicationClient::GetpPacketSupported (lldb::tid_t tid)
440 {
441 if (m_supports_p == eLazyBoolCalculate)
442 {
443 StringExtractorGDBRemote response;
444 m_supports_p = eLazyBoolNo;
445 char packet[256];
446 if (GetThreadSuffixSupported())
447 snprintf(packet, sizeof(packet), "p0;thread:%" PRIx64 ";", tid);
448 else
449 snprintf(packet, sizeof(packet), "p0");
450
451 if (SendPacketAndWaitForResponse(packet, response, false) == PacketResult::Success)
452 {
453 if (response.IsNormalResponse())
454 m_supports_p = eLazyBoolYes;
455 }
456 }
457 return m_supports_p;
458 }
459
460 GDBRemoteCommunicationClient::PacketResult
SendPacketsAndConcatenateResponses(const char * payload_prefix,std::string & response_string)461 GDBRemoteCommunicationClient::SendPacketsAndConcatenateResponses
462 (
463 const char *payload_prefix,
464 std::string &response_string
465 )
466 {
467 Mutex::Locker locker;
468 if (!GetSequenceMutex(locker,
469 "ProcessGDBRemote::SendPacketsAndConcatenateResponses() failed due to not getting the sequence mutex"))
470 {
471 Log *log (ProcessGDBRemoteLog::GetLogIfAnyCategoryIsSet (GDBR_LOG_PROCESS | GDBR_LOG_PACKETS));
472 if (log)
473 log->Printf("error: failed to get packet sequence mutex, not sending packets with prefix '%s'",
474 payload_prefix);
475 return PacketResult::ErrorNoSequenceLock;
476 }
477
478 response_string = "";
479 std::string payload_prefix_str(payload_prefix);
480 unsigned int response_size = 0x1000;
481 if (response_size > GetRemoteMaxPacketSize()) { // May send qSupported packet
482 response_size = GetRemoteMaxPacketSize();
483 }
484
485 for (unsigned int offset = 0; true; offset += response_size)
486 {
487 StringExtractorGDBRemote this_response;
488 // Construct payload
489 char sizeDescriptor[128];
490 snprintf(sizeDescriptor, sizeof(sizeDescriptor), "%x,%x", offset, response_size);
491 PacketResult result = SendPacketAndWaitForResponse((payload_prefix_str + sizeDescriptor).c_str(),
492 this_response,
493 /*send_async=*/false);
494 if (result != PacketResult::Success)
495 return result;
496
497 const std::string &this_string = this_response.GetStringRef();
498
499 // Check for m or l as first character; l seems to mean this is the last chunk
500 char first_char = *this_string.c_str();
501 if (first_char != 'm' && first_char != 'l')
502 {
503 return PacketResult::ErrorReplyInvalid;
504 }
505 // Skip past m or l
506 const char *s = this_string.c_str() + 1;
507
508 // Concatenate the result so far
509 response_string += s;
510 if (first_char == 'l')
511 // We're done
512 return PacketResult::Success;
513 }
514 }
515
516 GDBRemoteCommunicationClient::PacketResult
SendPacketAndWaitForResponse(const char * payload,StringExtractorGDBRemote & response,bool send_async)517 GDBRemoteCommunicationClient::SendPacketAndWaitForResponse
518 (
519 const char *payload,
520 StringExtractorGDBRemote &response,
521 bool send_async
522 )
523 {
524 return SendPacketAndWaitForResponse (payload,
525 ::strlen (payload),
526 response,
527 send_async);
528 }
529
530 GDBRemoteCommunicationClient::PacketResult
SendPacketAndWaitForResponseNoLock(const char * payload,size_t payload_length,StringExtractorGDBRemote & response)531 GDBRemoteCommunicationClient::SendPacketAndWaitForResponseNoLock (const char *payload,
532 size_t payload_length,
533 StringExtractorGDBRemote &response)
534 {
535 PacketResult packet_result = SendPacketNoLock (payload, payload_length);
536 if (packet_result == PacketResult::Success)
537 packet_result = WaitForPacketWithTimeoutMicroSecondsNoLock (response, GetPacketTimeoutInMicroSeconds ());
538 return packet_result;
539 }
540
541 GDBRemoteCommunicationClient::PacketResult
SendPacketAndWaitForResponse(const char * payload,size_t payload_length,StringExtractorGDBRemote & response,bool send_async)542 GDBRemoteCommunicationClient::SendPacketAndWaitForResponse
543 (
544 const char *payload,
545 size_t payload_length,
546 StringExtractorGDBRemote &response,
547 bool send_async
548 )
549 {
550 PacketResult packet_result = PacketResult::ErrorSendFailed;
551 Mutex::Locker locker;
552 Log *log (ProcessGDBRemoteLog::GetLogIfAllCategoriesSet (GDBR_LOG_PROCESS));
553 size_t response_len = 0;
554 if (GetSequenceMutex (locker))
555 {
556 packet_result = SendPacketAndWaitForResponseNoLock (payload, payload_length, response);
557 }
558 else
559 {
560 if (send_async)
561 {
562 if (IsRunning())
563 {
564 Mutex::Locker async_locker (m_async_mutex);
565 m_async_packet.assign(payload, payload_length);
566 m_async_packet_predicate.SetValue (true, eBroadcastNever);
567
568 if (log)
569 log->Printf ("async: async packet = %s", m_async_packet.c_str());
570
571 bool timed_out = false;
572 if (SendInterrupt(locker, 2, timed_out))
573 {
574 if (m_interrupt_sent)
575 {
576 m_interrupt_sent = false;
577 TimeValue timeout_time;
578 timeout_time = TimeValue::Now();
579 timeout_time.OffsetWithSeconds (m_packet_timeout);
580
581 if (log)
582 log->Printf ("async: sent interrupt");
583
584 if (m_async_packet_predicate.WaitForValueEqualTo (false, &timeout_time, &timed_out))
585 {
586 if (log)
587 log->Printf ("async: got response");
588
589 // Swap the response buffer to avoid malloc and string copy
590 response.GetStringRef().swap (m_async_response.GetStringRef());
591 response_len = response.GetStringRef().size();
592 packet_result = m_async_result;
593 }
594 else
595 {
596 if (log)
597 log->Printf ("async: timed out waiting for response");
598 }
599
600 // Make sure we wait until the continue packet has been sent again...
601 if (m_private_is_running.WaitForValueEqualTo (true, &timeout_time, &timed_out))
602 {
603 if (log)
604 {
605 if (timed_out)
606 log->Printf ("async: timed out waiting for process to resume, but process was resumed");
607 else
608 log->Printf ("async: async packet sent");
609 }
610 }
611 else
612 {
613 if (log)
614 log->Printf ("async: timed out waiting for process to resume");
615 }
616 }
617 else
618 {
619 // We had a racy condition where we went to send the interrupt
620 // yet we were able to get the lock, so the process must have
621 // just stopped?
622 if (log)
623 log->Printf ("async: got lock without sending interrupt");
624 // Send the packet normally since we got the lock
625 packet_result = SendPacketAndWaitForResponseNoLock (payload, payload_length, response);
626 }
627 }
628 else
629 {
630 if (log)
631 log->Printf ("async: failed to interrupt");
632 }
633 }
634 else
635 {
636 if (log)
637 log->Printf ("async: not running, async is ignored");
638 }
639 }
640 else
641 {
642 if (log)
643 log->Printf("error: failed to get packet sequence mutex, not sending packet '%*s'", (int) payload_length, payload);
644 }
645 }
646 return packet_result;
647 }
648
649 static const char *end_delimiter = "--end--;";
650 static const int end_delimiter_len = 8;
651
652 std::string
HarmonizeThreadIdsForProfileData(ProcessGDBRemote * process,StringExtractorGDBRemote & profileDataExtractor)653 GDBRemoteCommunicationClient::HarmonizeThreadIdsForProfileData
654 ( ProcessGDBRemote *process,
655 StringExtractorGDBRemote& profileDataExtractor
656 )
657 {
658 std::map<uint64_t, uint32_t> new_thread_id_to_used_usec_map;
659 std::stringstream final_output;
660 std::string name, value;
661
662 // Going to assuming thread_used_usec comes first, else bail out.
663 while (profileDataExtractor.GetNameColonValue(name, value))
664 {
665 if (name.compare("thread_used_id") == 0)
666 {
667 StringExtractor threadIDHexExtractor(value.c_str());
668 uint64_t thread_id = threadIDHexExtractor.GetHexMaxU64(false, 0);
669
670 bool has_used_usec = false;
671 uint32_t curr_used_usec = 0;
672 std::string usec_name, usec_value;
673 uint32_t input_file_pos = profileDataExtractor.GetFilePos();
674 if (profileDataExtractor.GetNameColonValue(usec_name, usec_value))
675 {
676 if (usec_name.compare("thread_used_usec") == 0)
677 {
678 has_used_usec = true;
679 curr_used_usec = strtoull(usec_value.c_str(), NULL, 0);
680 }
681 else
682 {
683 // We didn't find what we want, it is probably
684 // an older version. Bail out.
685 profileDataExtractor.SetFilePos(input_file_pos);
686 }
687 }
688
689 if (has_used_usec)
690 {
691 uint32_t prev_used_usec = 0;
692 std::map<uint64_t, uint32_t>::iterator iterator = m_thread_id_to_used_usec_map.find(thread_id);
693 if (iterator != m_thread_id_to_used_usec_map.end())
694 {
695 prev_used_usec = m_thread_id_to_used_usec_map[thread_id];
696 }
697
698 uint32_t real_used_usec = curr_used_usec - prev_used_usec;
699 // A good first time record is one that runs for at least 0.25 sec
700 bool good_first_time = (prev_used_usec == 0) && (real_used_usec > 250000);
701 bool good_subsequent_time = (prev_used_usec > 0) &&
702 ((real_used_usec > 0) || (process->HasAssignedIndexIDToThread(thread_id)));
703
704 if (good_first_time || good_subsequent_time)
705 {
706 // We try to avoid doing too many index id reservation,
707 // resulting in fast increase of index ids.
708
709 final_output << name << ":";
710 int32_t index_id = process->AssignIndexIDToThread(thread_id);
711 final_output << index_id << ";";
712
713 final_output << usec_name << ":" << usec_value << ";";
714 }
715 else
716 {
717 // Skip past 'thread_used_name'.
718 std::string local_name, local_value;
719 profileDataExtractor.GetNameColonValue(local_name, local_value);
720 }
721
722 // Store current time as previous time so that they can be compared later.
723 new_thread_id_to_used_usec_map[thread_id] = curr_used_usec;
724 }
725 else
726 {
727 // Bail out and use old string.
728 final_output << name << ":" << value << ";";
729 }
730 }
731 else
732 {
733 final_output << name << ":" << value << ";";
734 }
735 }
736 final_output << end_delimiter;
737 m_thread_id_to_used_usec_map = new_thread_id_to_used_usec_map;
738
739 return final_output.str();
740 }
741
742 StateType
SendContinuePacketAndWaitForResponse(ProcessGDBRemote * process,const char * payload,size_t packet_length,StringExtractorGDBRemote & response)743 GDBRemoteCommunicationClient::SendContinuePacketAndWaitForResponse
744 (
745 ProcessGDBRemote *process,
746 const char *payload,
747 size_t packet_length,
748 StringExtractorGDBRemote &response
749 )
750 {
751 m_curr_tid = LLDB_INVALID_THREAD_ID;
752 Log *log (ProcessGDBRemoteLog::GetLogIfAllCategoriesSet (GDBR_LOG_PROCESS));
753 if (log)
754 log->Printf ("GDBRemoteCommunicationClient::%s ()", __FUNCTION__);
755
756 Mutex::Locker locker(m_sequence_mutex);
757 StateType state = eStateRunning;
758
759 BroadcastEvent(eBroadcastBitRunPacketSent, NULL);
760 m_public_is_running.SetValue (true, eBroadcastNever);
761 // Set the starting continue packet into "continue_packet". This packet
762 // may change if we are interrupted and we continue after an async packet...
763 std::string continue_packet(payload, packet_length);
764
765 bool got_async_packet = false;
766
767 while (state == eStateRunning)
768 {
769 if (!got_async_packet)
770 {
771 if (log)
772 log->Printf ("GDBRemoteCommunicationClient::%s () sending continue packet: %s", __FUNCTION__, continue_packet.c_str());
773 if (SendPacketNoLock(continue_packet.c_str(), continue_packet.size()) != PacketResult::Success)
774 state = eStateInvalid;
775
776 m_private_is_running.SetValue (true, eBroadcastAlways);
777 }
778
779 got_async_packet = false;
780
781 if (log)
782 log->Printf ("GDBRemoteCommunicationClient::%s () WaitForPacket(%s)", __FUNCTION__, continue_packet.c_str());
783
784 if (WaitForPacketWithTimeoutMicroSecondsNoLock(response, UINT32_MAX) == PacketResult::Success)
785 {
786 if (response.Empty())
787 state = eStateInvalid;
788 else
789 {
790 const char stop_type = response.GetChar();
791 if (log)
792 log->Printf ("GDBRemoteCommunicationClient::%s () got packet: %s", __FUNCTION__, response.GetStringRef().c_str());
793 switch (stop_type)
794 {
795 case 'T':
796 case 'S':
797 {
798 if (process->GetStopID() == 0)
799 {
800 if (process->GetID() == LLDB_INVALID_PROCESS_ID)
801 {
802 lldb::pid_t pid = GetCurrentProcessID ();
803 if (pid != LLDB_INVALID_PROCESS_ID)
804 process->SetID (pid);
805 }
806 process->BuildDynamicRegisterInfo (true);
807 }
808
809 // Privately notify any internal threads that we have stopped
810 // in case we wanted to interrupt our process, yet we might
811 // send a packet and continue without returning control to the
812 // user.
813 m_private_is_running.SetValue (false, eBroadcastAlways);
814
815 const uint8_t signo = response.GetHexU8 (UINT8_MAX);
816
817 bool continue_after_async = m_async_signal != -1 || m_async_packet_predicate.GetValue();
818 if (continue_after_async || m_interrupt_sent)
819 {
820 // We sent an interrupt packet to stop the inferior process
821 // for an async signal or to send an async packet while running
822 // but we might have been single stepping and received the
823 // stop packet for the step instead of for the interrupt packet.
824 // Typically when an interrupt is sent a SIGINT or SIGSTOP
825 // is used, so if we get anything else, we need to try and
826 // get another stop reply packet that may have been sent
827 // due to sending the interrupt when the target is stopped
828 // which will just re-send a copy of the last stop reply
829 // packet. If we don't do this, then the reply for our
830 // async packet will be the repeat stop reply packet and cause
831 // a lot of trouble for us!
832 if (signo != SIGINT && signo != SIGSTOP)
833 {
834 continue_after_async = false;
835
836 // We didn't get a a SIGINT or SIGSTOP, so try for a
837 // very brief time (1 ms) to get another stop reply
838 // packet to make sure it doesn't get in the way
839 StringExtractorGDBRemote extra_stop_reply_packet;
840 uint32_t timeout_usec = 1000;
841 if (WaitForPacketWithTimeoutMicroSecondsNoLock (extra_stop_reply_packet, timeout_usec) == PacketResult::Success)
842 {
843 switch (extra_stop_reply_packet.GetChar())
844 {
845 case 'T':
846 case 'S':
847 // We did get an extra stop reply, which means
848 // our interrupt didn't stop the target so we
849 // shouldn't continue after the async signal
850 // or packet is sent...
851 continue_after_async = false;
852 break;
853 }
854 }
855 }
856 }
857
858 if (m_async_signal != -1)
859 {
860 if (log)
861 log->Printf ("async: send signo = %s", Host::GetSignalAsCString (m_async_signal));
862
863 // Save off the async signal we are supposed to send
864 const int async_signal = m_async_signal;
865 // Clear the async signal member so we don't end up
866 // sending the signal multiple times...
867 m_async_signal = -1;
868 // Check which signal we stopped with
869 if (signo == async_signal)
870 {
871 if (log)
872 log->Printf ("async: stopped with signal %s, we are done running", Host::GetSignalAsCString (signo));
873
874 // We already stopped with a signal that we wanted
875 // to stop with, so we are done
876 }
877 else
878 {
879 // We stopped with a different signal that the one
880 // we wanted to stop with, so now we must resume
881 // with the signal we want
882 char signal_packet[32];
883 int signal_packet_len = 0;
884 signal_packet_len = ::snprintf (signal_packet,
885 sizeof (signal_packet),
886 "C%2.2x",
887 async_signal);
888
889 if (log)
890 log->Printf ("async: stopped with signal %s, resume with %s",
891 Host::GetSignalAsCString (signo),
892 Host::GetSignalAsCString (async_signal));
893
894 // Set the continue packet to resume even if the
895 // interrupt didn't cause our stop (ignore continue_after_async)
896 continue_packet.assign(signal_packet, signal_packet_len);
897 continue;
898 }
899 }
900 else if (m_async_packet_predicate.GetValue())
901 {
902 Log * packet_log (ProcessGDBRemoteLog::GetLogIfAllCategoriesSet (GDBR_LOG_PACKETS));
903
904 // We are supposed to send an asynchronous packet while
905 // we are running.
906 m_async_response.Clear();
907 if (m_async_packet.empty())
908 {
909 m_async_result = PacketResult::ErrorSendFailed;
910 if (packet_log)
911 packet_log->Printf ("async: error: empty async packet");
912
913 }
914 else
915 {
916 if (packet_log)
917 packet_log->Printf ("async: sending packet");
918
919 m_async_result = SendPacketAndWaitForResponse (&m_async_packet[0],
920 m_async_packet.size(),
921 m_async_response,
922 false);
923 }
924 // Let the other thread that was trying to send the async
925 // packet know that the packet has been sent and response is
926 // ready...
927 m_async_packet_predicate.SetValue(false, eBroadcastAlways);
928
929 if (packet_log)
930 packet_log->Printf ("async: sent packet, continue_after_async = %i", continue_after_async);
931
932 // Set the continue packet to resume if our interrupt
933 // for the async packet did cause the stop
934 if (continue_after_async)
935 {
936 // Reverting this for now as it is causing deadlocks
937 // in programs (<rdar://problem/11529853>). In the future
938 // we should check our thread list and "do the right thing"
939 // for new threads that show up while we stop and run async
940 // packets. Setting the packet to 'c' to continue all threads
941 // is the right thing to do 99.99% of the time because if a
942 // thread was single stepping, and we sent an interrupt, we
943 // will notice above that we didn't stop due to an interrupt
944 // but stopped due to stepping and we would _not_ continue.
945 continue_packet.assign (1, 'c');
946 continue;
947 }
948 }
949 // Stop with signal and thread info
950 state = eStateStopped;
951 }
952 break;
953
954 case 'W':
955 case 'X':
956 // process exited
957 state = eStateExited;
958 break;
959
960 case 'O':
961 // STDOUT
962 {
963 got_async_packet = true;
964 std::string inferior_stdout;
965 inferior_stdout.reserve(response.GetBytesLeft () / 2);
966 char ch;
967 while ((ch = response.GetHexU8()) != '\0')
968 inferior_stdout.append(1, ch);
969 process->AppendSTDOUT (inferior_stdout.c_str(), inferior_stdout.size());
970 }
971 break;
972
973 case 'A':
974 // Async miscellaneous reply. Right now, only profile data is coming through this channel.
975 {
976 got_async_packet = true;
977 std::string input = response.GetStringRef().substr(1); // '1' to move beyond 'A'
978 if (m_partial_profile_data.length() > 0)
979 {
980 m_partial_profile_data.append(input);
981 input = m_partial_profile_data;
982 m_partial_profile_data.clear();
983 }
984
985 size_t found, pos = 0, len = input.length();
986 while ((found = input.find(end_delimiter, pos)) != std::string::npos)
987 {
988 StringExtractorGDBRemote profileDataExtractor(input.substr(pos, found).c_str());
989 std::string profile_data = HarmonizeThreadIdsForProfileData(process, profileDataExtractor);
990 process->BroadcastAsyncProfileData (profile_data);
991
992 pos = found + end_delimiter_len;
993 }
994
995 if (pos < len)
996 {
997 // Last incomplete chunk.
998 m_partial_profile_data = input.substr(pos);
999 }
1000 }
1001 break;
1002
1003 case 'E':
1004 // ERROR
1005 state = eStateInvalid;
1006 break;
1007
1008 default:
1009 if (log)
1010 log->Printf ("GDBRemoteCommunicationClient::%s () unrecognized async packet", __FUNCTION__);
1011 state = eStateInvalid;
1012 break;
1013 }
1014 }
1015 }
1016 else
1017 {
1018 if (log)
1019 log->Printf ("GDBRemoteCommunicationClient::%s () WaitForPacket(...) => false", __FUNCTION__);
1020 state = eStateInvalid;
1021 }
1022 }
1023 if (log)
1024 log->Printf ("GDBRemoteCommunicationClient::%s () => %s", __FUNCTION__, StateAsCString(state));
1025 response.SetFilePos(0);
1026 m_private_is_running.SetValue (false, eBroadcastAlways);
1027 m_public_is_running.SetValue (false, eBroadcastAlways);
1028 return state;
1029 }
1030
1031 bool
SendAsyncSignal(int signo)1032 GDBRemoteCommunicationClient::SendAsyncSignal (int signo)
1033 {
1034 Mutex::Locker async_locker (m_async_mutex);
1035 m_async_signal = signo;
1036 bool timed_out = false;
1037 Mutex::Locker locker;
1038 if (SendInterrupt (locker, 1, timed_out))
1039 return true;
1040 m_async_signal = -1;
1041 return false;
1042 }
1043
1044 // This function takes a mutex locker as a parameter in case the GetSequenceMutex
1045 // actually succeeds. If it doesn't succeed in acquiring the sequence mutex
1046 // (the expected result), then it will send the halt packet. If it does succeed
1047 // then the caller that requested the interrupt will want to keep the sequence
1048 // locked down so that no one else can send packets while the caller has control.
1049 // This function usually gets called when we are running and need to stop the
1050 // target. It can also be used when we are running and and we need to do something
1051 // else (like read/write memory), so we need to interrupt the running process
1052 // (gdb remote protocol requires this), and do what we need to do, then resume.
1053
1054 bool
SendInterrupt(Mutex::Locker & locker,uint32_t seconds_to_wait_for_stop,bool & timed_out)1055 GDBRemoteCommunicationClient::SendInterrupt
1056 (
1057 Mutex::Locker& locker,
1058 uint32_t seconds_to_wait_for_stop,
1059 bool &timed_out
1060 )
1061 {
1062 timed_out = false;
1063 Log *log (ProcessGDBRemoteLog::GetLogIfAnyCategoryIsSet (GDBR_LOG_PROCESS | GDBR_LOG_PACKETS));
1064
1065 if (IsRunning())
1066 {
1067 // Only send an interrupt if our debugserver is running...
1068 if (GetSequenceMutex (locker))
1069 {
1070 if (log)
1071 log->Printf ("SendInterrupt () - got sequence mutex without having to interrupt");
1072 }
1073 else
1074 {
1075 // Someone has the mutex locked waiting for a response or for the
1076 // inferior to stop, so send the interrupt on the down low...
1077 char ctrl_c = '\x03';
1078 ConnectionStatus status = eConnectionStatusSuccess;
1079 size_t bytes_written = Write (&ctrl_c, 1, status, NULL);
1080 if (log)
1081 log->PutCString("send packet: \\x03");
1082 if (bytes_written > 0)
1083 {
1084 m_interrupt_sent = true;
1085 if (seconds_to_wait_for_stop)
1086 {
1087 TimeValue timeout;
1088 if (seconds_to_wait_for_stop)
1089 {
1090 timeout = TimeValue::Now();
1091 timeout.OffsetWithSeconds (seconds_to_wait_for_stop);
1092 }
1093 if (m_private_is_running.WaitForValueEqualTo (false, &timeout, &timed_out))
1094 {
1095 if (log)
1096 log->PutCString ("SendInterrupt () - sent interrupt, private state stopped");
1097 return true;
1098 }
1099 else
1100 {
1101 if (log)
1102 log->Printf ("SendInterrupt () - sent interrupt, timed out wating for async thread resume");
1103 }
1104 }
1105 else
1106 {
1107 if (log)
1108 log->Printf ("SendInterrupt () - sent interrupt, not waiting for stop...");
1109 return true;
1110 }
1111 }
1112 else
1113 {
1114 if (log)
1115 log->Printf ("SendInterrupt () - failed to write interrupt");
1116 }
1117 return false;
1118 }
1119 }
1120 else
1121 {
1122 if (log)
1123 log->Printf ("SendInterrupt () - not running");
1124 }
1125 return true;
1126 }
1127
1128 lldb::pid_t
GetCurrentProcessID()1129 GDBRemoteCommunicationClient::GetCurrentProcessID ()
1130 {
1131 StringExtractorGDBRemote response;
1132 if (SendPacketAndWaitForResponse("qC", strlen("qC"), response, false) == PacketResult::Success)
1133 {
1134 if (response.GetChar() == 'Q')
1135 if (response.GetChar() == 'C')
1136 return response.GetHexMaxU32 (false, LLDB_INVALID_PROCESS_ID);
1137 }
1138 return LLDB_INVALID_PROCESS_ID;
1139 }
1140
1141 bool
GetLaunchSuccess(std::string & error_str)1142 GDBRemoteCommunicationClient::GetLaunchSuccess (std::string &error_str)
1143 {
1144 error_str.clear();
1145 StringExtractorGDBRemote response;
1146 if (SendPacketAndWaitForResponse("qLaunchSuccess", strlen("qLaunchSuccess"), response, false) == PacketResult::Success)
1147 {
1148 if (response.IsOKResponse())
1149 return true;
1150 if (response.GetChar() == 'E')
1151 {
1152 // A string the describes what failed when launching...
1153 error_str = response.GetStringRef().substr(1);
1154 }
1155 else
1156 {
1157 error_str.assign ("unknown error occurred launching process");
1158 }
1159 }
1160 else
1161 {
1162 error_str.assign ("timed out waiting for app to launch");
1163 }
1164 return false;
1165 }
1166
1167 int
SendArgumentsPacket(const ProcessLaunchInfo & launch_info)1168 GDBRemoteCommunicationClient::SendArgumentsPacket (const ProcessLaunchInfo &launch_info)
1169 {
1170 // Since we don't get the send argv0 separate from the executable path, we need to
1171 // make sure to use the actual exectuable path found in the launch_info...
1172 std::vector<const char *> argv;
1173 FileSpec exe_file = launch_info.GetExecutableFile();
1174 std::string exe_path;
1175 const char *arg = NULL;
1176 const Args &launch_args = launch_info.GetArguments();
1177 if (exe_file)
1178 exe_path = exe_file.GetPath();
1179 else
1180 {
1181 arg = launch_args.GetArgumentAtIndex(0);
1182 if (arg)
1183 exe_path = arg;
1184 }
1185 if (!exe_path.empty())
1186 {
1187 argv.push_back(exe_path.c_str());
1188 for (uint32_t i=1; (arg = launch_args.GetArgumentAtIndex(i)) != NULL; ++i)
1189 {
1190 if (arg)
1191 argv.push_back(arg);
1192 }
1193 }
1194 if (!argv.empty())
1195 {
1196 StreamString packet;
1197 packet.PutChar('A');
1198 for (size_t i = 0, n = argv.size(); i < n; ++i)
1199 {
1200 arg = argv[i];
1201 const int arg_len = strlen(arg);
1202 if (i > 0)
1203 packet.PutChar(',');
1204 packet.Printf("%i,%i,", arg_len * 2, (int)i);
1205 packet.PutBytesAsRawHex8 (arg, arg_len);
1206 }
1207
1208 StringExtractorGDBRemote response;
1209 if (SendPacketAndWaitForResponse (packet.GetData(), packet.GetSize(), response, false) == PacketResult::Success)
1210 {
1211 if (response.IsOKResponse())
1212 return 0;
1213 uint8_t error = response.GetError();
1214 if (error)
1215 return error;
1216 }
1217 }
1218 return -1;
1219 }
1220
1221 int
SendEnvironmentPacket(char const * name_equal_value)1222 GDBRemoteCommunicationClient::SendEnvironmentPacket (char const *name_equal_value)
1223 {
1224 if (name_equal_value && name_equal_value[0])
1225 {
1226 StreamString packet;
1227 bool send_hex_encoding = false;
1228 for (const char *p = name_equal_value; *p != '\0' && send_hex_encoding == false; ++p)
1229 {
1230 if (isprint(*p))
1231 {
1232 switch (*p)
1233 {
1234 case '$':
1235 case '#':
1236 send_hex_encoding = true;
1237 break;
1238 default:
1239 break;
1240 }
1241 }
1242 else
1243 {
1244 // We have non printable characters, lets hex encode this...
1245 send_hex_encoding = true;
1246 }
1247 }
1248
1249 StringExtractorGDBRemote response;
1250 if (send_hex_encoding)
1251 {
1252 if (m_supports_QEnvironmentHexEncoded)
1253 {
1254 packet.PutCString("QEnvironmentHexEncoded:");
1255 packet.PutBytesAsRawHex8 (name_equal_value, strlen(name_equal_value));
1256 if (SendPacketAndWaitForResponse (packet.GetData(), packet.GetSize(), response, false) == PacketResult::Success)
1257 {
1258 if (response.IsOKResponse())
1259 return 0;
1260 uint8_t error = response.GetError();
1261 if (error)
1262 return error;
1263 if (response.IsUnsupportedResponse())
1264 m_supports_QEnvironmentHexEncoded = false;
1265 }
1266 }
1267
1268 }
1269 else if (m_supports_QEnvironment)
1270 {
1271 packet.Printf("QEnvironment:%s", name_equal_value);
1272 if (SendPacketAndWaitForResponse (packet.GetData(), packet.GetSize(), response, false) == PacketResult::Success)
1273 {
1274 if (response.IsOKResponse())
1275 return 0;
1276 uint8_t error = response.GetError();
1277 if (error)
1278 return error;
1279 if (response.IsUnsupportedResponse())
1280 m_supports_QEnvironment = false;
1281 }
1282 }
1283 }
1284 return -1;
1285 }
1286
1287 int
SendLaunchArchPacket(char const * arch)1288 GDBRemoteCommunicationClient::SendLaunchArchPacket (char const *arch)
1289 {
1290 if (arch && arch[0])
1291 {
1292 StreamString packet;
1293 packet.Printf("QLaunchArch:%s", arch);
1294 StringExtractorGDBRemote response;
1295 if (SendPacketAndWaitForResponse (packet.GetData(), packet.GetSize(), response, false) == PacketResult::Success)
1296 {
1297 if (response.IsOKResponse())
1298 return 0;
1299 uint8_t error = response.GetError();
1300 if (error)
1301 return error;
1302 }
1303 }
1304 return -1;
1305 }
1306
1307 bool
GetOSVersion(uint32_t & major,uint32_t & minor,uint32_t & update)1308 GDBRemoteCommunicationClient::GetOSVersion (uint32_t &major,
1309 uint32_t &minor,
1310 uint32_t &update)
1311 {
1312 if (GetHostInfo ())
1313 {
1314 if (m_os_version_major != UINT32_MAX)
1315 {
1316 major = m_os_version_major;
1317 minor = m_os_version_minor;
1318 update = m_os_version_update;
1319 return true;
1320 }
1321 }
1322 return false;
1323 }
1324
1325 bool
GetOSBuildString(std::string & s)1326 GDBRemoteCommunicationClient::GetOSBuildString (std::string &s)
1327 {
1328 if (GetHostInfo ())
1329 {
1330 if (!m_os_build.empty())
1331 {
1332 s = m_os_build;
1333 return true;
1334 }
1335 }
1336 s.clear();
1337 return false;
1338 }
1339
1340
1341 bool
GetOSKernelDescription(std::string & s)1342 GDBRemoteCommunicationClient::GetOSKernelDescription (std::string &s)
1343 {
1344 if (GetHostInfo ())
1345 {
1346 if (!m_os_kernel.empty())
1347 {
1348 s = m_os_kernel;
1349 return true;
1350 }
1351 }
1352 s.clear();
1353 return false;
1354 }
1355
1356 bool
GetHostname(std::string & s)1357 GDBRemoteCommunicationClient::GetHostname (std::string &s)
1358 {
1359 if (GetHostInfo ())
1360 {
1361 if (!m_hostname.empty())
1362 {
1363 s = m_hostname;
1364 return true;
1365 }
1366 }
1367 s.clear();
1368 return false;
1369 }
1370
1371 ArchSpec
GetSystemArchitecture()1372 GDBRemoteCommunicationClient::GetSystemArchitecture ()
1373 {
1374 if (GetHostInfo ())
1375 return m_host_arch;
1376 return ArchSpec();
1377 }
1378
1379 const lldb_private::ArchSpec &
GetProcessArchitecture()1380 GDBRemoteCommunicationClient::GetProcessArchitecture ()
1381 {
1382 if (m_qProcessInfo_is_valid == eLazyBoolCalculate)
1383 GetCurrentProcessInfo ();
1384 return m_process_arch;
1385 }
1386
1387
1388 bool
GetHostInfo(bool force)1389 GDBRemoteCommunicationClient::GetHostInfo (bool force)
1390 {
1391 if (force || m_qHostInfo_is_valid == eLazyBoolCalculate)
1392 {
1393 m_qHostInfo_is_valid = eLazyBoolNo;
1394 StringExtractorGDBRemote response;
1395 if (SendPacketAndWaitForResponse ("qHostInfo", response, false) == PacketResult::Success)
1396 {
1397 if (response.IsNormalResponse())
1398 {
1399 std::string name;
1400 std::string value;
1401 uint32_t cpu = LLDB_INVALID_CPUTYPE;
1402 uint32_t sub = 0;
1403 std::string arch_name;
1404 std::string os_name;
1405 std::string vendor_name;
1406 std::string triple;
1407 std::string distribution_id;
1408 uint32_t pointer_byte_size = 0;
1409 StringExtractor extractor;
1410 ByteOrder byte_order = eByteOrderInvalid;
1411 uint32_t num_keys_decoded = 0;
1412 while (response.GetNameColonValue(name, value))
1413 {
1414 if (name.compare("cputype") == 0)
1415 {
1416 // exception type in big endian hex
1417 cpu = Args::StringToUInt32 (value.c_str(), LLDB_INVALID_CPUTYPE, 0);
1418 if (cpu != LLDB_INVALID_CPUTYPE)
1419 ++num_keys_decoded;
1420 }
1421 else if (name.compare("cpusubtype") == 0)
1422 {
1423 // exception count in big endian hex
1424 sub = Args::StringToUInt32 (value.c_str(), 0, 0);
1425 if (sub != 0)
1426 ++num_keys_decoded;
1427 }
1428 else if (name.compare("arch") == 0)
1429 {
1430 arch_name.swap (value);
1431 ++num_keys_decoded;
1432 }
1433 else if (name.compare("triple") == 0)
1434 {
1435 // The triple comes as ASCII hex bytes since it contains '-' chars
1436 extractor.GetStringRef().swap(value);
1437 extractor.SetFilePos(0);
1438 extractor.GetHexByteString (triple);
1439 ++num_keys_decoded;
1440 }
1441 else if (name.compare ("distribution_id") == 0)
1442 {
1443 extractor.GetStringRef ().swap (value);
1444 extractor.SetFilePos (0);
1445 extractor.GetHexByteString (distribution_id);
1446 ++num_keys_decoded;
1447 }
1448 else if (name.compare("os_build") == 0)
1449 {
1450 extractor.GetStringRef().swap(value);
1451 extractor.SetFilePos(0);
1452 extractor.GetHexByteString (m_os_build);
1453 ++num_keys_decoded;
1454 }
1455 else if (name.compare("hostname") == 0)
1456 {
1457 extractor.GetStringRef().swap(value);
1458 extractor.SetFilePos(0);
1459 extractor.GetHexByteString (m_hostname);
1460 ++num_keys_decoded;
1461 }
1462 else if (name.compare("os_kernel") == 0)
1463 {
1464 extractor.GetStringRef().swap(value);
1465 extractor.SetFilePos(0);
1466 extractor.GetHexByteString (m_os_kernel);
1467 ++num_keys_decoded;
1468 }
1469 else if (name.compare("ostype") == 0)
1470 {
1471 os_name.swap (value);
1472 ++num_keys_decoded;
1473 }
1474 else if (name.compare("vendor") == 0)
1475 {
1476 vendor_name.swap(value);
1477 ++num_keys_decoded;
1478 }
1479 else if (name.compare("endian") == 0)
1480 {
1481 ++num_keys_decoded;
1482 if (value.compare("little") == 0)
1483 byte_order = eByteOrderLittle;
1484 else if (value.compare("big") == 0)
1485 byte_order = eByteOrderBig;
1486 else if (value.compare("pdp") == 0)
1487 byte_order = eByteOrderPDP;
1488 else
1489 --num_keys_decoded;
1490 }
1491 else if (name.compare("ptrsize") == 0)
1492 {
1493 pointer_byte_size = Args::StringToUInt32 (value.c_str(), 0, 0);
1494 if (pointer_byte_size != 0)
1495 ++num_keys_decoded;
1496 }
1497 else if (name.compare("os_version") == 0)
1498 {
1499 Args::StringToVersion (value.c_str(),
1500 m_os_version_major,
1501 m_os_version_minor,
1502 m_os_version_update);
1503 if (m_os_version_major != UINT32_MAX)
1504 ++num_keys_decoded;
1505 }
1506 else if (name.compare("watchpoint_exceptions_received") == 0)
1507 {
1508 ++num_keys_decoded;
1509 if (strcmp(value.c_str(),"before") == 0)
1510 m_watchpoints_trigger_after_instruction = eLazyBoolNo;
1511 else if (strcmp(value.c_str(),"after") == 0)
1512 m_watchpoints_trigger_after_instruction = eLazyBoolYes;
1513 else
1514 --num_keys_decoded;
1515 }
1516 else if (name.compare("default_packet_timeout") == 0)
1517 {
1518 m_default_packet_timeout = Args::StringToUInt32(value.c_str(), 0);
1519 if (m_default_packet_timeout > 0)
1520 {
1521 SetPacketTimeout(m_default_packet_timeout);
1522 ++num_keys_decoded;
1523 }
1524 }
1525
1526 }
1527
1528 if (num_keys_decoded > 0)
1529 m_qHostInfo_is_valid = eLazyBoolYes;
1530
1531 if (triple.empty())
1532 {
1533 if (arch_name.empty())
1534 {
1535 if (cpu != LLDB_INVALID_CPUTYPE)
1536 {
1537 m_host_arch.SetArchitecture (eArchTypeMachO, cpu, sub);
1538 if (pointer_byte_size)
1539 {
1540 assert (pointer_byte_size == m_host_arch.GetAddressByteSize());
1541 }
1542 if (byte_order != eByteOrderInvalid)
1543 {
1544 assert (byte_order == m_host_arch.GetByteOrder());
1545 }
1546
1547 if (!os_name.empty() && vendor_name.compare("apple") == 0 && os_name.find("darwin") == 0)
1548 {
1549 switch (m_host_arch.GetMachine())
1550 {
1551 case llvm::Triple::arm:
1552 case llvm::Triple::thumb:
1553 os_name = "ios";
1554 break;
1555 default:
1556 os_name = "macosx";
1557 break;
1558 }
1559 }
1560 if (!vendor_name.empty())
1561 m_host_arch.GetTriple().setVendorName (llvm::StringRef (vendor_name));
1562 if (!os_name.empty())
1563 m_host_arch.GetTriple().setOSName (llvm::StringRef (os_name));
1564
1565 }
1566 }
1567 else
1568 {
1569 std::string triple;
1570 triple += arch_name;
1571 if (!vendor_name.empty() || !os_name.empty())
1572 {
1573 triple += '-';
1574 if (vendor_name.empty())
1575 triple += "unknown";
1576 else
1577 triple += vendor_name;
1578 triple += '-';
1579 if (os_name.empty())
1580 triple += "unknown";
1581 else
1582 triple += os_name;
1583 }
1584 m_host_arch.SetTriple (triple.c_str());
1585
1586 llvm::Triple &host_triple = m_host_arch.GetTriple();
1587 if (host_triple.getVendor() == llvm::Triple::Apple && host_triple.getOS() == llvm::Triple::Darwin)
1588 {
1589 switch (m_host_arch.GetMachine())
1590 {
1591 case llvm::Triple::arm:
1592 case llvm::Triple::thumb:
1593 host_triple.setOS(llvm::Triple::IOS);
1594 break;
1595 default:
1596 host_triple.setOS(llvm::Triple::MacOSX);
1597 break;
1598 }
1599 }
1600 if (pointer_byte_size)
1601 {
1602 assert (pointer_byte_size == m_host_arch.GetAddressByteSize());
1603 }
1604 if (byte_order != eByteOrderInvalid)
1605 {
1606 assert (byte_order == m_host_arch.GetByteOrder());
1607 }
1608
1609 }
1610 }
1611 else
1612 {
1613 m_host_arch.SetTriple (triple.c_str());
1614 if (pointer_byte_size)
1615 {
1616 assert (pointer_byte_size == m_host_arch.GetAddressByteSize());
1617 }
1618 if (byte_order != eByteOrderInvalid)
1619 {
1620 assert (byte_order == m_host_arch.GetByteOrder());
1621 }
1622 }
1623 if (!distribution_id.empty ())
1624 m_host_arch.SetDistributionId (distribution_id.c_str ());
1625 }
1626 }
1627 }
1628 return m_qHostInfo_is_valid == eLazyBoolYes;
1629 }
1630
1631 int
SendAttach(lldb::pid_t pid,StringExtractorGDBRemote & response)1632 GDBRemoteCommunicationClient::SendAttach
1633 (
1634 lldb::pid_t pid,
1635 StringExtractorGDBRemote& response
1636 )
1637 {
1638 if (pid != LLDB_INVALID_PROCESS_ID)
1639 {
1640 char packet[64];
1641 const int packet_len = ::snprintf (packet, sizeof(packet), "vAttach;%" PRIx64, pid);
1642 assert (packet_len < (int)sizeof(packet));
1643 if (SendPacketAndWaitForResponse (packet, packet_len, response, false) == PacketResult::Success)
1644 {
1645 if (response.IsErrorResponse())
1646 return response.GetError();
1647 return 0;
1648 }
1649 }
1650 return -1;
1651 }
1652
1653 const lldb_private::ArchSpec &
GetHostArchitecture()1654 GDBRemoteCommunicationClient::GetHostArchitecture ()
1655 {
1656 if (m_qHostInfo_is_valid == eLazyBoolCalculate)
1657 GetHostInfo ();
1658 return m_host_arch;
1659 }
1660
1661 uint32_t
GetHostDefaultPacketTimeout()1662 GDBRemoteCommunicationClient::GetHostDefaultPacketTimeout ()
1663 {
1664 if (m_qHostInfo_is_valid == eLazyBoolCalculate)
1665 GetHostInfo ();
1666 return m_default_packet_timeout;
1667 }
1668
1669 addr_t
AllocateMemory(size_t size,uint32_t permissions)1670 GDBRemoteCommunicationClient::AllocateMemory (size_t size, uint32_t permissions)
1671 {
1672 if (m_supports_alloc_dealloc_memory != eLazyBoolNo)
1673 {
1674 m_supports_alloc_dealloc_memory = eLazyBoolYes;
1675 char packet[64];
1676 const int packet_len = ::snprintf (packet, sizeof(packet), "_M%" PRIx64 ",%s%s%s",
1677 (uint64_t)size,
1678 permissions & lldb::ePermissionsReadable ? "r" : "",
1679 permissions & lldb::ePermissionsWritable ? "w" : "",
1680 permissions & lldb::ePermissionsExecutable ? "x" : "");
1681 assert (packet_len < (int)sizeof(packet));
1682 StringExtractorGDBRemote response;
1683 if (SendPacketAndWaitForResponse (packet, packet_len, response, false) == PacketResult::Success)
1684 {
1685 if (!response.IsErrorResponse())
1686 return response.GetHexMaxU64(false, LLDB_INVALID_ADDRESS);
1687 }
1688 else
1689 {
1690 m_supports_alloc_dealloc_memory = eLazyBoolNo;
1691 }
1692 }
1693 return LLDB_INVALID_ADDRESS;
1694 }
1695
1696 bool
DeallocateMemory(addr_t addr)1697 GDBRemoteCommunicationClient::DeallocateMemory (addr_t addr)
1698 {
1699 if (m_supports_alloc_dealloc_memory != eLazyBoolNo)
1700 {
1701 m_supports_alloc_dealloc_memory = eLazyBoolYes;
1702 char packet[64];
1703 const int packet_len = ::snprintf(packet, sizeof(packet), "_m%" PRIx64, (uint64_t)addr);
1704 assert (packet_len < (int)sizeof(packet));
1705 StringExtractorGDBRemote response;
1706 if (SendPacketAndWaitForResponse (packet, packet_len, response, false) == PacketResult::Success)
1707 {
1708 if (response.IsOKResponse())
1709 return true;
1710 }
1711 else
1712 {
1713 m_supports_alloc_dealloc_memory = eLazyBoolNo;
1714 }
1715 }
1716 return false;
1717 }
1718
1719 Error
Detach(bool keep_stopped)1720 GDBRemoteCommunicationClient::Detach (bool keep_stopped)
1721 {
1722 Error error;
1723
1724 if (keep_stopped)
1725 {
1726 if (m_supports_detach_stay_stopped == eLazyBoolCalculate)
1727 {
1728 char packet[64];
1729 const int packet_len = ::snprintf(packet, sizeof(packet), "qSupportsDetachAndStayStopped:");
1730 assert (packet_len < (int)sizeof(packet));
1731 StringExtractorGDBRemote response;
1732 if (SendPacketAndWaitForResponse (packet, packet_len, response, false) == PacketResult::Success)
1733 {
1734 m_supports_detach_stay_stopped = eLazyBoolYes;
1735 }
1736 else
1737 {
1738 m_supports_detach_stay_stopped = eLazyBoolNo;
1739 }
1740 }
1741
1742 if (m_supports_detach_stay_stopped == eLazyBoolNo)
1743 {
1744 error.SetErrorString("Stays stopped not supported by this target.");
1745 return error;
1746 }
1747 else
1748 {
1749 PacketResult packet_result = SendPacket ("D1", 2);
1750 if (packet_result != PacketResult::Success)
1751 error.SetErrorString ("Sending extended disconnect packet failed.");
1752 }
1753 }
1754 else
1755 {
1756 PacketResult packet_result = SendPacket ("D", 1);
1757 if (packet_result != PacketResult::Success)
1758 error.SetErrorString ("Sending disconnect packet failed.");
1759 }
1760 return error;
1761 }
1762
1763 Error
GetMemoryRegionInfo(lldb::addr_t addr,lldb_private::MemoryRegionInfo & region_info)1764 GDBRemoteCommunicationClient::GetMemoryRegionInfo (lldb::addr_t addr,
1765 lldb_private::MemoryRegionInfo ®ion_info)
1766 {
1767 Error error;
1768 region_info.Clear();
1769
1770 if (m_supports_memory_region_info != eLazyBoolNo)
1771 {
1772 m_supports_memory_region_info = eLazyBoolYes;
1773 char packet[64];
1774 const int packet_len = ::snprintf(packet, sizeof(packet), "qMemoryRegionInfo:%" PRIx64, (uint64_t)addr);
1775 assert (packet_len < (int)sizeof(packet));
1776 StringExtractorGDBRemote response;
1777 if (SendPacketAndWaitForResponse (packet, packet_len, response, false) == PacketResult::Success)
1778 {
1779 std::string name;
1780 std::string value;
1781 addr_t addr_value;
1782 bool success = true;
1783 bool saw_permissions = false;
1784 while (success && response.GetNameColonValue(name, value))
1785 {
1786 if (name.compare ("start") == 0)
1787 {
1788 addr_value = Args::StringToUInt64(value.c_str(), LLDB_INVALID_ADDRESS, 16, &success);
1789 if (success)
1790 region_info.GetRange().SetRangeBase(addr_value);
1791 }
1792 else if (name.compare ("size") == 0)
1793 {
1794 addr_value = Args::StringToUInt64(value.c_str(), 0, 16, &success);
1795 if (success)
1796 region_info.GetRange().SetByteSize (addr_value);
1797 }
1798 else if (name.compare ("permissions") == 0 && region_info.GetRange().IsValid())
1799 {
1800 saw_permissions = true;
1801 if (region_info.GetRange().Contains (addr))
1802 {
1803 if (value.find('r') != std::string::npos)
1804 region_info.SetReadable (MemoryRegionInfo::eYes);
1805 else
1806 region_info.SetReadable (MemoryRegionInfo::eNo);
1807
1808 if (value.find('w') != std::string::npos)
1809 region_info.SetWritable (MemoryRegionInfo::eYes);
1810 else
1811 region_info.SetWritable (MemoryRegionInfo::eNo);
1812
1813 if (value.find('x') != std::string::npos)
1814 region_info.SetExecutable (MemoryRegionInfo::eYes);
1815 else
1816 region_info.SetExecutable (MemoryRegionInfo::eNo);
1817 }
1818 else
1819 {
1820 // The reported region does not contain this address -- we're looking at an unmapped page
1821 region_info.SetReadable (MemoryRegionInfo::eNo);
1822 region_info.SetWritable (MemoryRegionInfo::eNo);
1823 region_info.SetExecutable (MemoryRegionInfo::eNo);
1824 }
1825 }
1826 else if (name.compare ("error") == 0)
1827 {
1828 StringExtractorGDBRemote name_extractor;
1829 // Swap "value" over into "name_extractor"
1830 name_extractor.GetStringRef().swap(value);
1831 // Now convert the HEX bytes into a string value
1832 name_extractor.GetHexByteString (value);
1833 error.SetErrorString(value.c_str());
1834 }
1835 }
1836
1837 // We got a valid address range back but no permissions -- which means this is an unmapped page
1838 if (region_info.GetRange().IsValid() && saw_permissions == false)
1839 {
1840 region_info.SetReadable (MemoryRegionInfo::eNo);
1841 region_info.SetWritable (MemoryRegionInfo::eNo);
1842 region_info.SetExecutable (MemoryRegionInfo::eNo);
1843 }
1844 }
1845 else
1846 {
1847 m_supports_memory_region_info = eLazyBoolNo;
1848 }
1849 }
1850
1851 if (m_supports_memory_region_info == eLazyBoolNo)
1852 {
1853 error.SetErrorString("qMemoryRegionInfo is not supported");
1854 }
1855 if (error.Fail())
1856 region_info.Clear();
1857 return error;
1858
1859 }
1860
1861 Error
GetWatchpointSupportInfo(uint32_t & num)1862 GDBRemoteCommunicationClient::GetWatchpointSupportInfo (uint32_t &num)
1863 {
1864 Error error;
1865
1866 if (m_supports_watchpoint_support_info == eLazyBoolYes)
1867 {
1868 num = m_num_supported_hardware_watchpoints;
1869 return error;
1870 }
1871
1872 // Set num to 0 first.
1873 num = 0;
1874 if (m_supports_watchpoint_support_info != eLazyBoolNo)
1875 {
1876 char packet[64];
1877 const int packet_len = ::snprintf(packet, sizeof(packet), "qWatchpointSupportInfo:");
1878 assert (packet_len < (int)sizeof(packet));
1879 StringExtractorGDBRemote response;
1880 if (SendPacketAndWaitForResponse (packet, packet_len, response, false) == PacketResult::Success)
1881 {
1882 m_supports_watchpoint_support_info = eLazyBoolYes;
1883 std::string name;
1884 std::string value;
1885 while (response.GetNameColonValue(name, value))
1886 {
1887 if (name.compare ("num") == 0)
1888 {
1889 num = Args::StringToUInt32(value.c_str(), 0, 0);
1890 m_num_supported_hardware_watchpoints = num;
1891 }
1892 }
1893 }
1894 else
1895 {
1896 m_supports_watchpoint_support_info = eLazyBoolNo;
1897 }
1898 }
1899
1900 if (m_supports_watchpoint_support_info == eLazyBoolNo)
1901 {
1902 error.SetErrorString("qWatchpointSupportInfo is not supported");
1903 }
1904 return error;
1905
1906 }
1907
1908 lldb_private::Error
GetWatchpointSupportInfo(uint32_t & num,bool & after)1909 GDBRemoteCommunicationClient::GetWatchpointSupportInfo (uint32_t &num, bool& after)
1910 {
1911 Error error(GetWatchpointSupportInfo(num));
1912 if (error.Success())
1913 error = GetWatchpointsTriggerAfterInstruction(after);
1914 return error;
1915 }
1916
1917 lldb_private::Error
GetWatchpointsTriggerAfterInstruction(bool & after)1918 GDBRemoteCommunicationClient::GetWatchpointsTriggerAfterInstruction (bool &after)
1919 {
1920 Error error;
1921
1922 // we assume watchpoints will happen after running the relevant opcode
1923 // and we only want to override this behavior if we have explicitly
1924 // received a qHostInfo telling us otherwise
1925 if (m_qHostInfo_is_valid != eLazyBoolYes)
1926 after = true;
1927 else
1928 after = (m_watchpoints_trigger_after_instruction != eLazyBoolNo);
1929 return error;
1930 }
1931
1932 int
SetSTDIN(char const * path)1933 GDBRemoteCommunicationClient::SetSTDIN (char const *path)
1934 {
1935 if (path && path[0])
1936 {
1937 StreamString packet;
1938 packet.PutCString("QSetSTDIN:");
1939 packet.PutBytesAsRawHex8(path, strlen(path));
1940
1941 StringExtractorGDBRemote response;
1942 if (SendPacketAndWaitForResponse (packet.GetData(), packet.GetSize(), response, false) == PacketResult::Success)
1943 {
1944 if (response.IsOKResponse())
1945 return 0;
1946 uint8_t error = response.GetError();
1947 if (error)
1948 return error;
1949 }
1950 }
1951 return -1;
1952 }
1953
1954 int
SetSTDOUT(char const * path)1955 GDBRemoteCommunicationClient::SetSTDOUT (char const *path)
1956 {
1957 if (path && path[0])
1958 {
1959 StreamString packet;
1960 packet.PutCString("QSetSTDOUT:");
1961 packet.PutBytesAsRawHex8(path, strlen(path));
1962
1963 StringExtractorGDBRemote response;
1964 if (SendPacketAndWaitForResponse (packet.GetData(), packet.GetSize(), response, false) == PacketResult::Success)
1965 {
1966 if (response.IsOKResponse())
1967 return 0;
1968 uint8_t error = response.GetError();
1969 if (error)
1970 return error;
1971 }
1972 }
1973 return -1;
1974 }
1975
1976 int
SetSTDERR(char const * path)1977 GDBRemoteCommunicationClient::SetSTDERR (char const *path)
1978 {
1979 if (path && path[0])
1980 {
1981 StreamString packet;
1982 packet.PutCString("QSetSTDERR:");
1983 packet.PutBytesAsRawHex8(path, strlen(path));
1984
1985 StringExtractorGDBRemote response;
1986 if (SendPacketAndWaitForResponse (packet.GetData(), packet.GetSize(), response, false) == PacketResult::Success)
1987 {
1988 if (response.IsOKResponse())
1989 return 0;
1990 uint8_t error = response.GetError();
1991 if (error)
1992 return error;
1993 }
1994 }
1995 return -1;
1996 }
1997
1998 bool
GetWorkingDir(std::string & cwd)1999 GDBRemoteCommunicationClient::GetWorkingDir (std::string &cwd)
2000 {
2001 StringExtractorGDBRemote response;
2002 if (SendPacketAndWaitForResponse ("qGetWorkingDir", response, false) == PacketResult::Success)
2003 {
2004 if (response.IsUnsupportedResponse())
2005 return false;
2006 if (response.IsErrorResponse())
2007 return false;
2008 response.GetHexByteString (cwd);
2009 return !cwd.empty();
2010 }
2011 return false;
2012 }
2013
2014 int
SetWorkingDir(char const * path)2015 GDBRemoteCommunicationClient::SetWorkingDir (char const *path)
2016 {
2017 if (path && path[0])
2018 {
2019 StreamString packet;
2020 packet.PutCString("QSetWorkingDir:");
2021 packet.PutBytesAsRawHex8(path, strlen(path));
2022
2023 StringExtractorGDBRemote response;
2024 if (SendPacketAndWaitForResponse (packet.GetData(), packet.GetSize(), response, false) == PacketResult::Success)
2025 {
2026 if (response.IsOKResponse())
2027 return 0;
2028 uint8_t error = response.GetError();
2029 if (error)
2030 return error;
2031 }
2032 }
2033 return -1;
2034 }
2035
2036 int
SetDisableASLR(bool enable)2037 GDBRemoteCommunicationClient::SetDisableASLR (bool enable)
2038 {
2039 char packet[32];
2040 const int packet_len = ::snprintf (packet, sizeof (packet), "QSetDisableASLR:%i", enable ? 1 : 0);
2041 assert (packet_len < (int)sizeof(packet));
2042 StringExtractorGDBRemote response;
2043 if (SendPacketAndWaitForResponse (packet, packet_len, response, false) == PacketResult::Success)
2044 {
2045 if (response.IsOKResponse())
2046 return 0;
2047 uint8_t error = response.GetError();
2048 if (error)
2049 return error;
2050 }
2051 return -1;
2052 }
2053
2054 bool
DecodeProcessInfoResponse(StringExtractorGDBRemote & response,ProcessInstanceInfo & process_info)2055 GDBRemoteCommunicationClient::DecodeProcessInfoResponse (StringExtractorGDBRemote &response, ProcessInstanceInfo &process_info)
2056 {
2057 if (response.IsNormalResponse())
2058 {
2059 std::string name;
2060 std::string value;
2061 StringExtractor extractor;
2062
2063 uint32_t cpu = LLDB_INVALID_CPUTYPE;
2064 uint32_t sub = 0;
2065 std::string vendor;
2066 std::string os_type;
2067
2068 while (response.GetNameColonValue(name, value))
2069 {
2070 if (name.compare("pid") == 0)
2071 {
2072 process_info.SetProcessID (Args::StringToUInt32 (value.c_str(), LLDB_INVALID_PROCESS_ID, 0));
2073 }
2074 else if (name.compare("ppid") == 0)
2075 {
2076 process_info.SetParentProcessID (Args::StringToUInt32 (value.c_str(), LLDB_INVALID_PROCESS_ID, 0));
2077 }
2078 else if (name.compare("uid") == 0)
2079 {
2080 process_info.SetUserID (Args::StringToUInt32 (value.c_str(), UINT32_MAX, 0));
2081 }
2082 else if (name.compare("euid") == 0)
2083 {
2084 process_info.SetEffectiveUserID (Args::StringToUInt32 (value.c_str(), UINT32_MAX, 0));
2085 }
2086 else if (name.compare("gid") == 0)
2087 {
2088 process_info.SetGroupID (Args::StringToUInt32 (value.c_str(), UINT32_MAX, 0));
2089 }
2090 else if (name.compare("egid") == 0)
2091 {
2092 process_info.SetEffectiveGroupID (Args::StringToUInt32 (value.c_str(), UINT32_MAX, 0));
2093 }
2094 else if (name.compare("triple") == 0)
2095 {
2096 // The triple comes as ASCII hex bytes since it contains '-' chars
2097 extractor.GetStringRef().swap(value);
2098 extractor.SetFilePos(0);
2099 extractor.GetHexByteString (value);
2100 process_info.GetArchitecture ().SetTriple (value.c_str());
2101 }
2102 else if (name.compare("name") == 0)
2103 {
2104 StringExtractor extractor;
2105 // The process name from ASCII hex bytes since we can't
2106 // control the characters in a process name
2107 extractor.GetStringRef().swap(value);
2108 extractor.SetFilePos(0);
2109 extractor.GetHexByteString (value);
2110 process_info.GetExecutableFile().SetFile (value.c_str(), false);
2111 }
2112 else if (name.compare("cputype") == 0)
2113 {
2114 cpu = Args::StringToUInt32 (value.c_str(), LLDB_INVALID_CPUTYPE, 16);
2115 }
2116 else if (name.compare("cpusubtype") == 0)
2117 {
2118 sub = Args::StringToUInt32 (value.c_str(), 0, 16);
2119 }
2120 else if (name.compare("vendor") == 0)
2121 {
2122 vendor = value;
2123 }
2124 else if (name.compare("ostype") == 0)
2125 {
2126 os_type = value;
2127 }
2128 }
2129
2130 if (cpu != LLDB_INVALID_CPUTYPE && !vendor.empty() && !os_type.empty())
2131 {
2132 if (vendor == "apple")
2133 {
2134 process_info.GetArchitecture().SetArchitecture (eArchTypeMachO, cpu, sub);
2135 process_info.GetArchitecture().GetTriple().setVendorName (llvm::StringRef (vendor));
2136 process_info.GetArchitecture().GetTriple().setOSName (llvm::StringRef (os_type));
2137 }
2138 }
2139
2140 if (process_info.GetProcessID() != LLDB_INVALID_PROCESS_ID)
2141 return true;
2142 }
2143 return false;
2144 }
2145
2146 bool
GetProcessInfo(lldb::pid_t pid,ProcessInstanceInfo & process_info)2147 GDBRemoteCommunicationClient::GetProcessInfo (lldb::pid_t pid, ProcessInstanceInfo &process_info)
2148 {
2149 process_info.Clear();
2150
2151 if (m_supports_qProcessInfoPID)
2152 {
2153 char packet[32];
2154 const int packet_len = ::snprintf (packet, sizeof (packet), "qProcessInfoPID:%" PRIu64, pid);
2155 assert (packet_len < (int)sizeof(packet));
2156 StringExtractorGDBRemote response;
2157 if (SendPacketAndWaitForResponse (packet, packet_len, response, false) == PacketResult::Success)
2158 {
2159 return DecodeProcessInfoResponse (response, process_info);
2160 }
2161 else
2162 {
2163 m_supports_qProcessInfoPID = false;
2164 return false;
2165 }
2166 }
2167 return false;
2168 }
2169
2170 bool
GetCurrentProcessInfo()2171 GDBRemoteCommunicationClient::GetCurrentProcessInfo ()
2172 {
2173 if (m_qProcessInfo_is_valid == eLazyBoolYes)
2174 return true;
2175 if (m_qProcessInfo_is_valid == eLazyBoolNo)
2176 return false;
2177
2178 GetHostInfo ();
2179
2180 StringExtractorGDBRemote response;
2181 if (SendPacketAndWaitForResponse ("qProcessInfo", response, false) == PacketResult::Success)
2182 {
2183 if (response.IsNormalResponse())
2184 {
2185 std::string name;
2186 std::string value;
2187 uint32_t cpu = LLDB_INVALID_CPUTYPE;
2188 uint32_t sub = 0;
2189 std::string arch_name;
2190 std::string os_name;
2191 std::string vendor_name;
2192 std::string triple;
2193 uint32_t pointer_byte_size = 0;
2194 StringExtractor extractor;
2195 ByteOrder byte_order = eByteOrderInvalid;
2196 uint32_t num_keys_decoded = 0;
2197 while (response.GetNameColonValue(name, value))
2198 {
2199 if (name.compare("cputype") == 0)
2200 {
2201 cpu = Args::StringToUInt32 (value.c_str(), LLDB_INVALID_CPUTYPE, 16);
2202 if (cpu != LLDB_INVALID_CPUTYPE)
2203 ++num_keys_decoded;
2204 }
2205 else if (name.compare("cpusubtype") == 0)
2206 {
2207 sub = Args::StringToUInt32 (value.c_str(), 0, 16);
2208 if (sub != 0)
2209 ++num_keys_decoded;
2210 }
2211 else if (name.compare("ostype") == 0)
2212 {
2213 os_name.swap (value);
2214 ++num_keys_decoded;
2215 }
2216 else if (name.compare("vendor") == 0)
2217 {
2218 vendor_name.swap(value);
2219 ++num_keys_decoded;
2220 }
2221 else if (name.compare("endian") == 0)
2222 {
2223 ++num_keys_decoded;
2224 if (value.compare("little") == 0)
2225 byte_order = eByteOrderLittle;
2226 else if (value.compare("big") == 0)
2227 byte_order = eByteOrderBig;
2228 else if (value.compare("pdp") == 0)
2229 byte_order = eByteOrderPDP;
2230 else
2231 --num_keys_decoded;
2232 }
2233 else if (name.compare("ptrsize") == 0)
2234 {
2235 pointer_byte_size = Args::StringToUInt32 (value.c_str(), 0, 16);
2236 if (pointer_byte_size != 0)
2237 ++num_keys_decoded;
2238 }
2239 }
2240 if (num_keys_decoded > 0)
2241 m_qProcessInfo_is_valid = eLazyBoolYes;
2242 if (cpu != LLDB_INVALID_CPUTYPE && !os_name.empty() && !vendor_name.empty())
2243 {
2244 m_process_arch.SetArchitecture (eArchTypeMachO, cpu, sub);
2245 if (pointer_byte_size)
2246 {
2247 assert (pointer_byte_size == m_process_arch.GetAddressByteSize());
2248 }
2249 m_host_arch.GetTriple().setVendorName (llvm::StringRef (vendor_name));
2250 m_host_arch.GetTriple().setOSName (llvm::StringRef (os_name));
2251 return true;
2252 }
2253 }
2254 }
2255 else
2256 {
2257 m_qProcessInfo_is_valid = eLazyBoolNo;
2258 }
2259
2260 return false;
2261 }
2262
2263
2264 uint32_t
FindProcesses(const ProcessInstanceInfoMatch & match_info,ProcessInstanceInfoList & process_infos)2265 GDBRemoteCommunicationClient::FindProcesses (const ProcessInstanceInfoMatch &match_info,
2266 ProcessInstanceInfoList &process_infos)
2267 {
2268 process_infos.Clear();
2269
2270 if (m_supports_qfProcessInfo)
2271 {
2272 StreamString packet;
2273 packet.PutCString ("qfProcessInfo");
2274 if (!match_info.MatchAllProcesses())
2275 {
2276 packet.PutChar (':');
2277 const char *name = match_info.GetProcessInfo().GetName();
2278 bool has_name_match = false;
2279 if (name && name[0])
2280 {
2281 has_name_match = true;
2282 NameMatchType name_match_type = match_info.GetNameMatchType();
2283 switch (name_match_type)
2284 {
2285 case eNameMatchIgnore:
2286 has_name_match = false;
2287 break;
2288
2289 case eNameMatchEquals:
2290 packet.PutCString ("name_match:equals;");
2291 break;
2292
2293 case eNameMatchContains:
2294 packet.PutCString ("name_match:contains;");
2295 break;
2296
2297 case eNameMatchStartsWith:
2298 packet.PutCString ("name_match:starts_with;");
2299 break;
2300
2301 case eNameMatchEndsWith:
2302 packet.PutCString ("name_match:ends_with;");
2303 break;
2304
2305 case eNameMatchRegularExpression:
2306 packet.PutCString ("name_match:regex;");
2307 break;
2308 }
2309 if (has_name_match)
2310 {
2311 packet.PutCString ("name:");
2312 packet.PutBytesAsRawHex8(name, ::strlen(name));
2313 packet.PutChar (';');
2314 }
2315 }
2316
2317 if (match_info.GetProcessInfo().ProcessIDIsValid())
2318 packet.Printf("pid:%" PRIu64 ";",match_info.GetProcessInfo().GetProcessID());
2319 if (match_info.GetProcessInfo().ParentProcessIDIsValid())
2320 packet.Printf("parent_pid:%" PRIu64 ";",match_info.GetProcessInfo().GetParentProcessID());
2321 if (match_info.GetProcessInfo().UserIDIsValid())
2322 packet.Printf("uid:%u;",match_info.GetProcessInfo().GetUserID());
2323 if (match_info.GetProcessInfo().GroupIDIsValid())
2324 packet.Printf("gid:%u;",match_info.GetProcessInfo().GetGroupID());
2325 if (match_info.GetProcessInfo().EffectiveUserIDIsValid())
2326 packet.Printf("euid:%u;",match_info.GetProcessInfo().GetEffectiveUserID());
2327 if (match_info.GetProcessInfo().EffectiveGroupIDIsValid())
2328 packet.Printf("egid:%u;",match_info.GetProcessInfo().GetEffectiveGroupID());
2329 if (match_info.GetProcessInfo().EffectiveGroupIDIsValid())
2330 packet.Printf("all_users:%u;",match_info.GetMatchAllUsers() ? 1 : 0);
2331 if (match_info.GetProcessInfo().GetArchitecture().IsValid())
2332 {
2333 const ArchSpec &match_arch = match_info.GetProcessInfo().GetArchitecture();
2334 const llvm::Triple &triple = match_arch.GetTriple();
2335 packet.PutCString("triple:");
2336 packet.PutCStringAsRawHex8(triple.getTriple().c_str());
2337 packet.PutChar (';');
2338 }
2339 }
2340 StringExtractorGDBRemote response;
2341 if (SendPacketAndWaitForResponse (packet.GetData(), packet.GetSize(), response, false) == PacketResult::Success)
2342 {
2343 do
2344 {
2345 ProcessInstanceInfo process_info;
2346 if (!DecodeProcessInfoResponse (response, process_info))
2347 break;
2348 process_infos.Append(process_info);
2349 response.GetStringRef().clear();
2350 response.SetFilePos(0);
2351 } while (SendPacketAndWaitForResponse ("qsProcessInfo", strlen ("qsProcessInfo"), response, false) == PacketResult::Success);
2352 }
2353 else
2354 {
2355 m_supports_qfProcessInfo = false;
2356 return 0;
2357 }
2358 }
2359 return process_infos.GetSize();
2360
2361 }
2362
2363 bool
GetUserName(uint32_t uid,std::string & name)2364 GDBRemoteCommunicationClient::GetUserName (uint32_t uid, std::string &name)
2365 {
2366 if (m_supports_qUserName)
2367 {
2368 char packet[32];
2369 const int packet_len = ::snprintf (packet, sizeof (packet), "qUserName:%i", uid);
2370 assert (packet_len < (int)sizeof(packet));
2371 StringExtractorGDBRemote response;
2372 if (SendPacketAndWaitForResponse (packet, packet_len, response, false) == PacketResult::Success)
2373 {
2374 if (response.IsNormalResponse())
2375 {
2376 // Make sure we parsed the right number of characters. The response is
2377 // the hex encoded user name and should make up the entire packet.
2378 // If there are any non-hex ASCII bytes, the length won't match below..
2379 if (response.GetHexByteString (name) * 2 == response.GetStringRef().size())
2380 return true;
2381 }
2382 }
2383 else
2384 {
2385 m_supports_qUserName = false;
2386 return false;
2387 }
2388 }
2389 return false;
2390
2391 }
2392
2393 bool
GetGroupName(uint32_t gid,std::string & name)2394 GDBRemoteCommunicationClient::GetGroupName (uint32_t gid, std::string &name)
2395 {
2396 if (m_supports_qGroupName)
2397 {
2398 char packet[32];
2399 const int packet_len = ::snprintf (packet, sizeof (packet), "qGroupName:%i", gid);
2400 assert (packet_len < (int)sizeof(packet));
2401 StringExtractorGDBRemote response;
2402 if (SendPacketAndWaitForResponse (packet, packet_len, response, false) == PacketResult::Success)
2403 {
2404 if (response.IsNormalResponse())
2405 {
2406 // Make sure we parsed the right number of characters. The response is
2407 // the hex encoded group name and should make up the entire packet.
2408 // If there are any non-hex ASCII bytes, the length won't match below..
2409 if (response.GetHexByteString (name) * 2 == response.GetStringRef().size())
2410 return true;
2411 }
2412 }
2413 else
2414 {
2415 m_supports_qGroupName = false;
2416 return false;
2417 }
2418 }
2419 return false;
2420 }
2421
2422 void
TestPacketSpeed(const uint32_t num_packets)2423 GDBRemoteCommunicationClient::TestPacketSpeed (const uint32_t num_packets)
2424 {
2425 uint32_t i;
2426 TimeValue start_time, end_time;
2427 uint64_t total_time_nsec;
2428 if (SendSpeedTestPacket (0, 0))
2429 {
2430 static uint32_t g_send_sizes[] = { 0, 64, 128, 512, 1024 };
2431 static uint32_t g_recv_sizes[] = { 0, 64, 128, 512, 1024 }; //, 4*1024, 8*1024, 16*1024, 32*1024, 48*1024, 64*1024, 96*1024, 128*1024 };
2432 const size_t k_num_send_sizes = sizeof(g_send_sizes)/sizeof(uint32_t);
2433 const size_t k_num_recv_sizes = sizeof(g_recv_sizes)/sizeof(uint32_t);
2434 const uint64_t k_recv_amount = 4*1024*1024; // Receive 4MB
2435 for (uint32_t send_idx = 0; send_idx < k_num_send_sizes; ++send_idx)
2436 {
2437 const uint32_t send_size = g_send_sizes[send_idx];
2438 for (uint32_t recv_idx = 0; recv_idx < k_num_recv_sizes; ++recv_idx)
2439 {
2440 const uint32_t recv_size = g_recv_sizes[recv_idx];
2441 StreamString packet;
2442 packet.Printf ("qSpeedTest:response_size:%i;data:", recv_size);
2443 uint32_t bytes_left = send_size;
2444 while (bytes_left > 0)
2445 {
2446 if (bytes_left >= 26)
2447 {
2448 packet.PutCString("abcdefghijklmnopqrstuvwxyz");
2449 bytes_left -= 26;
2450 }
2451 else
2452 {
2453 packet.Printf ("%*.*s;", bytes_left, bytes_left, "abcdefghijklmnopqrstuvwxyz");
2454 bytes_left = 0;
2455 }
2456 }
2457
2458 start_time = TimeValue::Now();
2459 if (recv_size == 0)
2460 {
2461 for (i=0; i<num_packets; ++i)
2462 {
2463 StringExtractorGDBRemote response;
2464 SendPacketAndWaitForResponse (packet.GetData(), packet.GetSize(), response, false);
2465 }
2466 }
2467 else
2468 {
2469 uint32_t bytes_read = 0;
2470 while (bytes_read < k_recv_amount)
2471 {
2472 StringExtractorGDBRemote response;
2473 SendPacketAndWaitForResponse (packet.GetData(), packet.GetSize(), response, false);
2474 bytes_read += recv_size;
2475 }
2476 }
2477 end_time = TimeValue::Now();
2478 total_time_nsec = end_time.GetAsNanoSecondsSinceJan1_1970() - start_time.GetAsNanoSecondsSinceJan1_1970();
2479 if (recv_size == 0)
2480 {
2481 float packets_per_second = (((float)num_packets)/(float)total_time_nsec) * (float)TimeValue::NanoSecPerSec;
2482 printf ("%u qSpeedTest(send=%-7u, recv=%-7u) in %" PRIu64 ".%9.9" PRIu64 " sec for %f packets/sec.\n",
2483 num_packets,
2484 send_size,
2485 recv_size,
2486 total_time_nsec / TimeValue::NanoSecPerSec,
2487 total_time_nsec % TimeValue::NanoSecPerSec,
2488 packets_per_second);
2489 }
2490 else
2491 {
2492 float mb_second = ((((float)k_recv_amount)/(float)total_time_nsec) * (float)TimeValue::NanoSecPerSec) / (1024.0*1024.0);
2493 printf ("%u qSpeedTest(send=%-7u, recv=%-7u) sent 4MB in %" PRIu64 ".%9.9" PRIu64 " sec for %f MB/sec.\n",
2494 num_packets,
2495 send_size,
2496 recv_size,
2497 total_time_nsec / TimeValue::NanoSecPerSec,
2498 total_time_nsec % TimeValue::NanoSecPerSec,
2499 mb_second);
2500 }
2501 }
2502 }
2503 }
2504 }
2505
2506 bool
SendSpeedTestPacket(uint32_t send_size,uint32_t recv_size)2507 GDBRemoteCommunicationClient::SendSpeedTestPacket (uint32_t send_size, uint32_t recv_size)
2508 {
2509 StreamString packet;
2510 packet.Printf ("qSpeedTest:response_size:%i;data:", recv_size);
2511 uint32_t bytes_left = send_size;
2512 while (bytes_left > 0)
2513 {
2514 if (bytes_left >= 26)
2515 {
2516 packet.PutCString("abcdefghijklmnopqrstuvwxyz");
2517 bytes_left -= 26;
2518 }
2519 else
2520 {
2521 packet.Printf ("%*.*s;", bytes_left, bytes_left, "abcdefghijklmnopqrstuvwxyz");
2522 bytes_left = 0;
2523 }
2524 }
2525
2526 StringExtractorGDBRemote response;
2527 return SendPacketAndWaitForResponse (packet.GetData(), packet.GetSize(), response, false) == PacketResult::Success;
2528 }
2529
2530 uint16_t
LaunchGDBserverAndGetPort(lldb::pid_t & pid,const char * remote_accept_hostname)2531 GDBRemoteCommunicationClient::LaunchGDBserverAndGetPort (lldb::pid_t &pid, const char *remote_accept_hostname)
2532 {
2533 pid = LLDB_INVALID_PROCESS_ID;
2534 StringExtractorGDBRemote response;
2535 StreamString stream;
2536 stream.PutCString("qLaunchGDBServer;");
2537 std::string hostname;
2538 if (remote_accept_hostname && remote_accept_hostname[0])
2539 hostname = remote_accept_hostname;
2540 else
2541 {
2542 if (Host::GetHostname (hostname))
2543 {
2544 // Make the GDB server we launch only accept connections from this host
2545 stream.Printf("host:%s;", hostname.c_str());
2546 }
2547 else
2548 {
2549 // Make the GDB server we launch accept connections from any host since we can't figure out the hostname
2550 stream.Printf("host:*;");
2551 }
2552 }
2553 const char *packet = stream.GetData();
2554 int packet_len = stream.GetSize();
2555
2556 if (SendPacketAndWaitForResponse(packet, packet_len, response, false) == PacketResult::Success)
2557 {
2558 std::string name;
2559 std::string value;
2560 uint16_t port = 0;
2561 while (response.GetNameColonValue(name, value))
2562 {
2563 if (name.compare("port") == 0)
2564 port = Args::StringToUInt32(value.c_str(), 0, 0);
2565 else if (name.compare("pid") == 0)
2566 pid = Args::StringToUInt64(value.c_str(), LLDB_INVALID_PROCESS_ID, 0);
2567 }
2568 return port;
2569 }
2570 return 0;
2571 }
2572
2573 bool
KillSpawnedProcess(lldb::pid_t pid)2574 GDBRemoteCommunicationClient::KillSpawnedProcess (lldb::pid_t pid)
2575 {
2576 StreamString stream;
2577 stream.Printf ("qKillSpawnedProcess:%" PRId64 , pid);
2578 const char *packet = stream.GetData();
2579 int packet_len = stream.GetSize();
2580
2581 StringExtractorGDBRemote response;
2582 if (SendPacketAndWaitForResponse(packet, packet_len, response, false) == PacketResult::Success)
2583 {
2584 if (response.IsOKResponse())
2585 return true;
2586 }
2587 return false;
2588 }
2589
2590 bool
SetCurrentThread(uint64_t tid)2591 GDBRemoteCommunicationClient::SetCurrentThread (uint64_t tid)
2592 {
2593 if (m_curr_tid == tid)
2594 return true;
2595
2596 char packet[32];
2597 int packet_len;
2598 if (tid == UINT64_MAX)
2599 packet_len = ::snprintf (packet, sizeof(packet), "Hg-1");
2600 else
2601 packet_len = ::snprintf (packet, sizeof(packet), "Hg%" PRIx64, tid);
2602 assert (packet_len + 1 < (int)sizeof(packet));
2603 StringExtractorGDBRemote response;
2604 if (SendPacketAndWaitForResponse(packet, packet_len, response, false) == PacketResult::Success)
2605 {
2606 if (response.IsOKResponse())
2607 {
2608 m_curr_tid = tid;
2609 return true;
2610 }
2611 }
2612 return false;
2613 }
2614
2615 bool
SetCurrentThreadForRun(uint64_t tid)2616 GDBRemoteCommunicationClient::SetCurrentThreadForRun (uint64_t tid)
2617 {
2618 if (m_curr_tid_run == tid)
2619 return true;
2620
2621 char packet[32];
2622 int packet_len;
2623 if (tid == UINT64_MAX)
2624 packet_len = ::snprintf (packet, sizeof(packet), "Hc-1");
2625 else
2626 packet_len = ::snprintf (packet, sizeof(packet), "Hc%" PRIx64, tid);
2627
2628 assert (packet_len + 1 < (int)sizeof(packet));
2629 StringExtractorGDBRemote response;
2630 if (SendPacketAndWaitForResponse(packet, packet_len, response, false) == PacketResult::Success)
2631 {
2632 if (response.IsOKResponse())
2633 {
2634 m_curr_tid_run = tid;
2635 return true;
2636 }
2637 }
2638 return false;
2639 }
2640
2641 bool
GetStopReply(StringExtractorGDBRemote & response)2642 GDBRemoteCommunicationClient::GetStopReply (StringExtractorGDBRemote &response)
2643 {
2644 if (SendPacketAndWaitForResponse("?", 1, response, false) == PacketResult::Success)
2645 return response.IsNormalResponse();
2646 return false;
2647 }
2648
2649 bool
GetThreadStopInfo(lldb::tid_t tid,StringExtractorGDBRemote & response)2650 GDBRemoteCommunicationClient::GetThreadStopInfo (lldb::tid_t tid, StringExtractorGDBRemote &response)
2651 {
2652 if (m_supports_qThreadStopInfo)
2653 {
2654 char packet[256];
2655 int packet_len = ::snprintf(packet, sizeof(packet), "qThreadStopInfo%" PRIx64, tid);
2656 assert (packet_len < (int)sizeof(packet));
2657 if (SendPacketAndWaitForResponse(packet, packet_len, response, false) == PacketResult::Success)
2658 {
2659 if (response.IsUnsupportedResponse())
2660 m_supports_qThreadStopInfo = false;
2661 else if (response.IsNormalResponse())
2662 return true;
2663 else
2664 return false;
2665 }
2666 else
2667 {
2668 m_supports_qThreadStopInfo = false;
2669 }
2670 }
2671 return false;
2672 }
2673
2674
2675 uint8_t
SendGDBStoppointTypePacket(GDBStoppointType type,bool insert,addr_t addr,uint32_t length)2676 GDBRemoteCommunicationClient::SendGDBStoppointTypePacket (GDBStoppointType type, bool insert, addr_t addr, uint32_t length)
2677 {
2678 // Check if the stub is known not to support this breakpoint type
2679 if (!SupportsGDBStoppointPacket(type))
2680 return UINT8_MAX;
2681 // Construct the breakpoint packet
2682 char packet[64];
2683 const int packet_len = ::snprintf (packet,
2684 sizeof(packet),
2685 "%c%i,%" PRIx64 ",%x",
2686 insert ? 'Z' : 'z',
2687 type,
2688 addr,
2689 length);
2690 // Check we havent overwritten the end of the packet buffer
2691 assert (packet_len + 1 < (int)sizeof(packet));
2692 StringExtractorGDBRemote response;
2693 // Try to send the breakpoint packet, and check that it was correctly sent
2694 if (SendPacketAndWaitForResponse(packet, packet_len, response, true) == PacketResult::Success)
2695 {
2696 // Receive and OK packet when the breakpoint successfully placed
2697 if (response.IsOKResponse())
2698 return 0;
2699
2700 // Error while setting breakpoint, send back specific error
2701 if (response.IsErrorResponse())
2702 return response.GetError();
2703
2704 // Empty packet informs us that breakpoint is not supported
2705 if (response.IsUnsupportedResponse())
2706 {
2707 // Disable this breakpoint type since it is unsupported
2708 switch (type)
2709 {
2710 case eBreakpointSoftware: m_supports_z0 = false; break;
2711 case eBreakpointHardware: m_supports_z1 = false; break;
2712 case eWatchpointWrite: m_supports_z2 = false; break;
2713 case eWatchpointRead: m_supports_z3 = false; break;
2714 case eWatchpointReadWrite: m_supports_z4 = false; break;
2715 }
2716 }
2717 }
2718 // Signal generic faliure
2719 return UINT8_MAX;
2720 }
2721
2722 size_t
GetCurrentThreadIDs(std::vector<lldb::tid_t> & thread_ids,bool & sequence_mutex_unavailable)2723 GDBRemoteCommunicationClient::GetCurrentThreadIDs (std::vector<lldb::tid_t> &thread_ids,
2724 bool &sequence_mutex_unavailable)
2725 {
2726 Mutex::Locker locker;
2727 thread_ids.clear();
2728
2729 if (GetSequenceMutex (locker, "ProcessGDBRemote::UpdateThreadList() failed due to not getting the sequence mutex"))
2730 {
2731 sequence_mutex_unavailable = false;
2732 StringExtractorGDBRemote response;
2733
2734 PacketResult packet_result;
2735 for (packet_result = SendPacketAndWaitForResponseNoLock ("qfThreadInfo", strlen("qfThreadInfo"), response);
2736 packet_result == PacketResult::Success && response.IsNormalResponse();
2737 packet_result = SendPacketAndWaitForResponseNoLock ("qsThreadInfo", strlen("qsThreadInfo"), response))
2738 {
2739 char ch = response.GetChar();
2740 if (ch == 'l')
2741 break;
2742 if (ch == 'm')
2743 {
2744 do
2745 {
2746 tid_t tid = response.GetHexMaxU64(false, LLDB_INVALID_THREAD_ID);
2747
2748 if (tid != LLDB_INVALID_THREAD_ID)
2749 {
2750 thread_ids.push_back (tid);
2751 }
2752 ch = response.GetChar(); // Skip the command separator
2753 } while (ch == ','); // Make sure we got a comma separator
2754 }
2755 }
2756 }
2757 else
2758 {
2759 #if defined (LLDB_CONFIGURATION_DEBUG)
2760 // assert(!"ProcessGDBRemote::UpdateThreadList() failed due to not getting the sequence mutex");
2761 #else
2762 Log *log (ProcessGDBRemoteLog::GetLogIfAnyCategoryIsSet (GDBR_LOG_PROCESS | GDBR_LOG_PACKETS));
2763 if (log)
2764 log->Printf("error: failed to get packet sequence mutex, not sending packet 'qfThreadInfo'");
2765 #endif
2766 sequence_mutex_unavailable = true;
2767 }
2768 return thread_ids.size();
2769 }
2770
2771 lldb::addr_t
GetShlibInfoAddr()2772 GDBRemoteCommunicationClient::GetShlibInfoAddr()
2773 {
2774 if (!IsRunning())
2775 {
2776 StringExtractorGDBRemote response;
2777 if (SendPacketAndWaitForResponse("qShlibInfoAddr", ::strlen ("qShlibInfoAddr"), response, false) == PacketResult::Success)
2778 {
2779 if (response.IsNormalResponse())
2780 return response.GetHexMaxU64(false, LLDB_INVALID_ADDRESS);
2781 }
2782 }
2783 return LLDB_INVALID_ADDRESS;
2784 }
2785
2786 lldb_private::Error
RunShellCommand(const char * command,const char * working_dir,int * status_ptr,int * signo_ptr,std::string * command_output,uint32_t timeout_sec)2787 GDBRemoteCommunicationClient::RunShellCommand (const char *command, // Shouldn't be NULL
2788 const char *working_dir, // Pass NULL to use the current working directory
2789 int *status_ptr, // Pass NULL if you don't want the process exit status
2790 int *signo_ptr, // Pass NULL if you don't want the signal that caused the process to exit
2791 std::string *command_output, // Pass NULL if you don't want the command output
2792 uint32_t timeout_sec) // Timeout in seconds to wait for shell program to finish
2793 {
2794 lldb_private::StreamString stream;
2795 stream.PutCString("qPlatform_shell:");
2796 stream.PutBytesAsRawHex8(command, strlen(command));
2797 stream.PutChar(',');
2798 stream.PutHex32(timeout_sec);
2799 if (working_dir && *working_dir)
2800 {
2801 stream.PutChar(',');
2802 stream.PutBytesAsRawHex8(working_dir, strlen(working_dir));
2803 }
2804 const char *packet = stream.GetData();
2805 int packet_len = stream.GetSize();
2806 StringExtractorGDBRemote response;
2807 if (SendPacketAndWaitForResponse(packet, packet_len, response, false) == PacketResult::Success)
2808 {
2809 if (response.GetChar() != 'F')
2810 return Error("malformed reply");
2811 if (response.GetChar() != ',')
2812 return Error("malformed reply");
2813 uint32_t exitcode = response.GetHexMaxU32(false, UINT32_MAX);
2814 if (exitcode == UINT32_MAX)
2815 return Error("unable to run remote process");
2816 else if (status_ptr)
2817 *status_ptr = exitcode;
2818 if (response.GetChar() != ',')
2819 return Error("malformed reply");
2820 uint32_t signo = response.GetHexMaxU32(false, UINT32_MAX);
2821 if (signo_ptr)
2822 *signo_ptr = signo;
2823 if (response.GetChar() != ',')
2824 return Error("malformed reply");
2825 std::string output;
2826 response.GetEscapedBinaryData(output);
2827 if (command_output)
2828 command_output->assign(output);
2829 return Error();
2830 }
2831 return Error("unable to send packet");
2832 }
2833
2834 Error
MakeDirectory(const char * path,uint32_t file_permissions)2835 GDBRemoteCommunicationClient::MakeDirectory (const char *path,
2836 uint32_t file_permissions)
2837 {
2838 lldb_private::StreamString stream;
2839 stream.PutCString("qPlatform_mkdir:");
2840 stream.PutHex32(file_permissions);
2841 stream.PutChar(',');
2842 stream.PutBytesAsRawHex8(path, strlen(path));
2843 const char *packet = stream.GetData();
2844 int packet_len = stream.GetSize();
2845 StringExtractorGDBRemote response;
2846 if (SendPacketAndWaitForResponse(packet, packet_len, response, false) == PacketResult::Success)
2847 {
2848 return Error(response.GetHexMaxU32(false, UINT32_MAX), eErrorTypePOSIX);
2849 }
2850 return Error();
2851
2852 }
2853
2854 Error
SetFilePermissions(const char * path,uint32_t file_permissions)2855 GDBRemoteCommunicationClient::SetFilePermissions (const char *path,
2856 uint32_t file_permissions)
2857 {
2858 lldb_private::StreamString stream;
2859 stream.PutCString("qPlatform_chmod:");
2860 stream.PutHex32(file_permissions);
2861 stream.PutChar(',');
2862 stream.PutBytesAsRawHex8(path, strlen(path));
2863 const char *packet = stream.GetData();
2864 int packet_len = stream.GetSize();
2865 StringExtractorGDBRemote response;
2866 if (SendPacketAndWaitForResponse(packet, packet_len, response, false) == PacketResult::Success)
2867 {
2868 return Error(response.GetHexMaxU32(false, UINT32_MAX), eErrorTypePOSIX);
2869 }
2870 return Error();
2871
2872 }
2873
2874 static uint64_t
ParseHostIOPacketResponse(StringExtractorGDBRemote & response,uint64_t fail_result,Error & error)2875 ParseHostIOPacketResponse (StringExtractorGDBRemote &response,
2876 uint64_t fail_result,
2877 Error &error)
2878 {
2879 response.SetFilePos(0);
2880 if (response.GetChar() != 'F')
2881 return fail_result;
2882 int32_t result = response.GetS32 (-2);
2883 if (result == -2)
2884 return fail_result;
2885 if (response.GetChar() == ',')
2886 {
2887 int result_errno = response.GetS32 (-2);
2888 if (result_errno != -2)
2889 error.SetError(result_errno, eErrorTypePOSIX);
2890 else
2891 error.SetError(-1, eErrorTypeGeneric);
2892 }
2893 else
2894 error.Clear();
2895 return result;
2896 }
2897 lldb::user_id_t
OpenFile(const lldb_private::FileSpec & file_spec,uint32_t flags,mode_t mode,Error & error)2898 GDBRemoteCommunicationClient::OpenFile (const lldb_private::FileSpec& file_spec,
2899 uint32_t flags,
2900 mode_t mode,
2901 Error &error)
2902 {
2903 lldb_private::StreamString stream;
2904 stream.PutCString("vFile:open:");
2905 std::string path (file_spec.GetPath());
2906 if (path.empty())
2907 return UINT64_MAX;
2908 stream.PutCStringAsRawHex8(path.c_str());
2909 stream.PutChar(',');
2910 const uint32_t posix_open_flags = File::ConvertOpenOptionsForPOSIXOpen(flags);
2911 stream.PutHex32(posix_open_flags);
2912 stream.PutChar(',');
2913 stream.PutHex32(mode);
2914 const char* packet = stream.GetData();
2915 int packet_len = stream.GetSize();
2916 StringExtractorGDBRemote response;
2917 if (SendPacketAndWaitForResponse(packet, packet_len, response, false) == PacketResult::Success)
2918 {
2919 return ParseHostIOPacketResponse (response, UINT64_MAX, error);
2920 }
2921 return UINT64_MAX;
2922 }
2923
2924 bool
CloseFile(lldb::user_id_t fd,Error & error)2925 GDBRemoteCommunicationClient::CloseFile (lldb::user_id_t fd,
2926 Error &error)
2927 {
2928 lldb_private::StreamString stream;
2929 stream.Printf("vFile:close:%i", (int)fd);
2930 const char* packet = stream.GetData();
2931 int packet_len = stream.GetSize();
2932 StringExtractorGDBRemote response;
2933 if (SendPacketAndWaitForResponse(packet, packet_len, response, false) == PacketResult::Success)
2934 {
2935 return ParseHostIOPacketResponse (response, -1, error) == 0;
2936 }
2937 return false;
2938 }
2939
2940 // Extension of host I/O packets to get the file size.
2941 lldb::user_id_t
GetFileSize(const lldb_private::FileSpec & file_spec)2942 GDBRemoteCommunicationClient::GetFileSize (const lldb_private::FileSpec& file_spec)
2943 {
2944 lldb_private::StreamString stream;
2945 stream.PutCString("vFile:size:");
2946 std::string path (file_spec.GetPath());
2947 stream.PutCStringAsRawHex8(path.c_str());
2948 const char* packet = stream.GetData();
2949 int packet_len = stream.GetSize();
2950 StringExtractorGDBRemote response;
2951 if (SendPacketAndWaitForResponse(packet, packet_len, response, false) == PacketResult::Success)
2952 {
2953 if (response.GetChar() != 'F')
2954 return UINT64_MAX;
2955 uint32_t retcode = response.GetHexMaxU64(false, UINT64_MAX);
2956 return retcode;
2957 }
2958 return UINT64_MAX;
2959 }
2960
2961 Error
GetFilePermissions(const char * path,uint32_t & file_permissions)2962 GDBRemoteCommunicationClient::GetFilePermissions(const char *path, uint32_t &file_permissions)
2963 {
2964 Error error;
2965 lldb_private::StreamString stream;
2966 stream.PutCString("vFile:mode:");
2967 stream.PutCStringAsRawHex8(path);
2968 const char* packet = stream.GetData();
2969 int packet_len = stream.GetSize();
2970 StringExtractorGDBRemote response;
2971 if (SendPacketAndWaitForResponse(packet, packet_len, response, false) == PacketResult::Success)
2972 {
2973 if (response.GetChar() != 'F')
2974 {
2975 error.SetErrorStringWithFormat ("invalid response to '%s' packet", packet);
2976 }
2977 else
2978 {
2979 const uint32_t mode = response.GetS32(-1);
2980 if (mode == -1)
2981 {
2982 if (response.GetChar() == ',')
2983 {
2984 int response_errno = response.GetS32(-1);
2985 if (response_errno > 0)
2986 error.SetError(response_errno, lldb::eErrorTypePOSIX);
2987 else
2988 error.SetErrorToGenericError();
2989 }
2990 else
2991 error.SetErrorToGenericError();
2992 }
2993 else
2994 {
2995 file_permissions = mode & (S_IRWXU|S_IRWXG|S_IRWXO);
2996 }
2997 }
2998 }
2999 else
3000 {
3001 error.SetErrorStringWithFormat ("failed to send '%s' packet", packet);
3002 }
3003 return error;
3004 }
3005
3006 uint64_t
ReadFile(lldb::user_id_t fd,uint64_t offset,void * dst,uint64_t dst_len,Error & error)3007 GDBRemoteCommunicationClient::ReadFile (lldb::user_id_t fd,
3008 uint64_t offset,
3009 void *dst,
3010 uint64_t dst_len,
3011 Error &error)
3012 {
3013 lldb_private::StreamString stream;
3014 stream.Printf("vFile:pread:%i,%" PRId64 ",%" PRId64, (int)fd, dst_len, offset);
3015 const char* packet = stream.GetData();
3016 int packet_len = stream.GetSize();
3017 StringExtractorGDBRemote response;
3018 if (SendPacketAndWaitForResponse(packet, packet_len, response, false) == PacketResult::Success)
3019 {
3020 if (response.GetChar() != 'F')
3021 return 0;
3022 uint32_t retcode = response.GetHexMaxU32(false, UINT32_MAX);
3023 if (retcode == UINT32_MAX)
3024 return retcode;
3025 const char next = (response.Peek() ? *response.Peek() : 0);
3026 if (next == ',')
3027 return 0;
3028 if (next == ';')
3029 {
3030 response.GetChar(); // skip the semicolon
3031 std::string buffer;
3032 if (response.GetEscapedBinaryData(buffer))
3033 {
3034 const uint64_t data_to_write = std::min<uint64_t>(dst_len, buffer.size());
3035 if (data_to_write > 0)
3036 memcpy(dst, &buffer[0], data_to_write);
3037 return data_to_write;
3038 }
3039 }
3040 }
3041 return 0;
3042 }
3043
3044 uint64_t
WriteFile(lldb::user_id_t fd,uint64_t offset,const void * src,uint64_t src_len,Error & error)3045 GDBRemoteCommunicationClient::WriteFile (lldb::user_id_t fd,
3046 uint64_t offset,
3047 const void* src,
3048 uint64_t src_len,
3049 Error &error)
3050 {
3051 lldb_private::StreamGDBRemote stream;
3052 stream.Printf("vFile:pwrite:%i,%" PRId64 ",", (int)fd, offset);
3053 stream.PutEscapedBytes(src, src_len);
3054 const char* packet = stream.GetData();
3055 int packet_len = stream.GetSize();
3056 StringExtractorGDBRemote response;
3057 if (SendPacketAndWaitForResponse(packet, packet_len, response, false) == PacketResult::Success)
3058 {
3059 if (response.GetChar() != 'F')
3060 {
3061 error.SetErrorStringWithFormat("write file failed");
3062 return 0;
3063 }
3064 uint64_t bytes_written = response.GetU64(UINT64_MAX);
3065 if (bytes_written == UINT64_MAX)
3066 {
3067 error.SetErrorToGenericError();
3068 if (response.GetChar() == ',')
3069 {
3070 int response_errno = response.GetS32(-1);
3071 if (response_errno > 0)
3072 error.SetError(response_errno, lldb::eErrorTypePOSIX);
3073 }
3074 return 0;
3075 }
3076 return bytes_written;
3077 }
3078 else
3079 {
3080 error.SetErrorString ("failed to send vFile:pwrite packet");
3081 }
3082 return 0;
3083 }
3084
3085 Error
CreateSymlink(const char * src,const char * dst)3086 GDBRemoteCommunicationClient::CreateSymlink (const char *src, const char *dst)
3087 {
3088 Error error;
3089 lldb_private::StreamGDBRemote stream;
3090 stream.PutCString("vFile:symlink:");
3091 // the unix symlink() command reverses its parameters where the dst if first,
3092 // so we follow suit here
3093 stream.PutCStringAsRawHex8(dst);
3094 stream.PutChar(',');
3095 stream.PutCStringAsRawHex8(src);
3096 const char* packet = stream.GetData();
3097 int packet_len = stream.GetSize();
3098 StringExtractorGDBRemote response;
3099 if (SendPacketAndWaitForResponse(packet, packet_len, response, false) == PacketResult::Success)
3100 {
3101 if (response.GetChar() == 'F')
3102 {
3103 uint32_t result = response.GetU32(UINT32_MAX);
3104 if (result != 0)
3105 {
3106 error.SetErrorToGenericError();
3107 if (response.GetChar() == ',')
3108 {
3109 int response_errno = response.GetS32(-1);
3110 if (response_errno > 0)
3111 error.SetError(response_errno, lldb::eErrorTypePOSIX);
3112 }
3113 }
3114 }
3115 else
3116 {
3117 // Should have returned with 'F<result>[,<errno>]'
3118 error.SetErrorStringWithFormat("symlink failed");
3119 }
3120 }
3121 else
3122 {
3123 error.SetErrorString ("failed to send vFile:symlink packet");
3124 }
3125 return error;
3126 }
3127
3128 Error
Unlink(const char * path)3129 GDBRemoteCommunicationClient::Unlink (const char *path)
3130 {
3131 Error error;
3132 lldb_private::StreamGDBRemote stream;
3133 stream.PutCString("vFile:unlink:");
3134 // the unix symlink() command reverses its parameters where the dst if first,
3135 // so we follow suit here
3136 stream.PutCStringAsRawHex8(path);
3137 const char* packet = stream.GetData();
3138 int packet_len = stream.GetSize();
3139 StringExtractorGDBRemote response;
3140 if (SendPacketAndWaitForResponse(packet, packet_len, response, false) == PacketResult::Success)
3141 {
3142 if (response.GetChar() == 'F')
3143 {
3144 uint32_t result = response.GetU32(UINT32_MAX);
3145 if (result != 0)
3146 {
3147 error.SetErrorToGenericError();
3148 if (response.GetChar() == ',')
3149 {
3150 int response_errno = response.GetS32(-1);
3151 if (response_errno > 0)
3152 error.SetError(response_errno, lldb::eErrorTypePOSIX);
3153 }
3154 }
3155 }
3156 else
3157 {
3158 // Should have returned with 'F<result>[,<errno>]'
3159 error.SetErrorStringWithFormat("unlink failed");
3160 }
3161 }
3162 else
3163 {
3164 error.SetErrorString ("failed to send vFile:unlink packet");
3165 }
3166 return error;
3167 }
3168
3169 // Extension of host I/O packets to get whether a file exists.
3170 bool
GetFileExists(const lldb_private::FileSpec & file_spec)3171 GDBRemoteCommunicationClient::GetFileExists (const lldb_private::FileSpec& file_spec)
3172 {
3173 lldb_private::StreamString stream;
3174 stream.PutCString("vFile:exists:");
3175 std::string path (file_spec.GetPath());
3176 stream.PutCStringAsRawHex8(path.c_str());
3177 const char* packet = stream.GetData();
3178 int packet_len = stream.GetSize();
3179 StringExtractorGDBRemote response;
3180 if (SendPacketAndWaitForResponse(packet, packet_len, response, false) == PacketResult::Success)
3181 {
3182 if (response.GetChar() != 'F')
3183 return false;
3184 if (response.GetChar() != ',')
3185 return false;
3186 bool retcode = (response.GetChar() != '0');
3187 return retcode;
3188 }
3189 return false;
3190 }
3191
3192 bool
CalculateMD5(const lldb_private::FileSpec & file_spec,uint64_t & high,uint64_t & low)3193 GDBRemoteCommunicationClient::CalculateMD5 (const lldb_private::FileSpec& file_spec,
3194 uint64_t &high,
3195 uint64_t &low)
3196 {
3197 lldb_private::StreamString stream;
3198 stream.PutCString("vFile:MD5:");
3199 std::string path (file_spec.GetPath());
3200 stream.PutCStringAsRawHex8(path.c_str());
3201 const char* packet = stream.GetData();
3202 int packet_len = stream.GetSize();
3203 StringExtractorGDBRemote response;
3204 if (SendPacketAndWaitForResponse(packet, packet_len, response, false) == PacketResult::Success)
3205 {
3206 if (response.GetChar() != 'F')
3207 return false;
3208 if (response.GetChar() != ',')
3209 return false;
3210 if (response.Peek() && *response.Peek() == 'x')
3211 return false;
3212 low = response.GetHexMaxU64(false, UINT64_MAX);
3213 high = response.GetHexMaxU64(false, UINT64_MAX);
3214 return true;
3215 }
3216 return false;
3217 }
3218
3219 bool
ReadRegister(lldb::tid_t tid,uint32_t reg,StringExtractorGDBRemote & response)3220 GDBRemoteCommunicationClient::ReadRegister(lldb::tid_t tid, uint32_t reg, StringExtractorGDBRemote &response)
3221 {
3222 Mutex::Locker locker;
3223 if (GetSequenceMutex (locker, "Didn't get sequence mutex for p packet."))
3224 {
3225 const bool thread_suffix_supported = GetThreadSuffixSupported();
3226
3227 if (thread_suffix_supported || SetCurrentThread(tid))
3228 {
3229 char packet[64];
3230 int packet_len = 0;
3231 if (thread_suffix_supported)
3232 packet_len = ::snprintf (packet, sizeof(packet), "p%x;thread:%4.4" PRIx64 ";", reg, tid);
3233 else
3234 packet_len = ::snprintf (packet, sizeof(packet), "p%x", reg);
3235 assert (packet_len < ((int)sizeof(packet) - 1));
3236 return SendPacketAndWaitForResponse(packet, response, false) == PacketResult::Success;
3237 }
3238 }
3239 return false;
3240
3241 }
3242
3243
3244 bool
ReadAllRegisters(lldb::tid_t tid,StringExtractorGDBRemote & response)3245 GDBRemoteCommunicationClient::ReadAllRegisters (lldb::tid_t tid, StringExtractorGDBRemote &response)
3246 {
3247 Mutex::Locker locker;
3248 if (GetSequenceMutex (locker, "Didn't get sequence mutex for g packet."))
3249 {
3250 const bool thread_suffix_supported = GetThreadSuffixSupported();
3251
3252 if (thread_suffix_supported || SetCurrentThread(tid))
3253 {
3254 char packet[64];
3255 int packet_len = 0;
3256 // Get all registers in one packet
3257 if (thread_suffix_supported)
3258 packet_len = ::snprintf (packet, sizeof(packet), "g;thread:%4.4" PRIx64 ";", tid);
3259 else
3260 packet_len = ::snprintf (packet, sizeof(packet), "g");
3261 assert (packet_len < ((int)sizeof(packet) - 1));
3262 return SendPacketAndWaitForResponse(packet, response, false) == PacketResult::Success;
3263 }
3264 }
3265 return false;
3266 }
3267 bool
SaveRegisterState(lldb::tid_t tid,uint32_t & save_id)3268 GDBRemoteCommunicationClient::SaveRegisterState (lldb::tid_t tid, uint32_t &save_id)
3269 {
3270 save_id = 0; // Set to invalid save ID
3271 if (m_supports_QSaveRegisterState == eLazyBoolNo)
3272 return false;
3273
3274 m_supports_QSaveRegisterState = eLazyBoolYes;
3275 Mutex::Locker locker;
3276 if (GetSequenceMutex (locker, "Didn't get sequence mutex for QSaveRegisterState."))
3277 {
3278 const bool thread_suffix_supported = GetThreadSuffixSupported();
3279 if (thread_suffix_supported || SetCurrentThread(tid))
3280 {
3281 char packet[256];
3282 if (thread_suffix_supported)
3283 ::snprintf (packet, sizeof(packet), "QSaveRegisterState;thread:%4.4" PRIx64 ";", tid);
3284 else
3285 ::strncpy (packet, "QSaveRegisterState", sizeof(packet));
3286
3287 StringExtractorGDBRemote response;
3288
3289 if (SendPacketAndWaitForResponse(packet, response, false) == PacketResult::Success)
3290 {
3291 if (response.IsUnsupportedResponse())
3292 {
3293 // This packet isn't supported, don't try calling it again
3294 m_supports_QSaveRegisterState = eLazyBoolNo;
3295 }
3296
3297 const uint32_t response_save_id = response.GetU32(0);
3298 if (response_save_id != 0)
3299 {
3300 save_id = response_save_id;
3301 return true;
3302 }
3303 }
3304 }
3305 }
3306 return false;
3307 }
3308
3309 bool
RestoreRegisterState(lldb::tid_t tid,uint32_t save_id)3310 GDBRemoteCommunicationClient::RestoreRegisterState (lldb::tid_t tid, uint32_t save_id)
3311 {
3312 // We use the "m_supports_QSaveRegisterState" variable here becuase the
3313 // QSaveRegisterState and QRestoreRegisterState packets must both be supported in
3314 // order to be useful
3315 if (m_supports_QSaveRegisterState == eLazyBoolNo)
3316 return false;
3317
3318 Mutex::Locker locker;
3319 if (GetSequenceMutex (locker, "Didn't get sequence mutex for QRestoreRegisterState."))
3320 {
3321 const bool thread_suffix_supported = GetThreadSuffixSupported();
3322 if (thread_suffix_supported || SetCurrentThread(tid))
3323 {
3324 char packet[256];
3325 if (thread_suffix_supported)
3326 ::snprintf (packet, sizeof(packet), "QRestoreRegisterState:%u;thread:%4.4" PRIx64 ";", save_id, tid);
3327 else
3328 ::snprintf (packet, sizeof(packet), "QRestoreRegisterState:%u" PRIx64 ";", save_id);
3329
3330 StringExtractorGDBRemote response;
3331
3332 if (SendPacketAndWaitForResponse(packet, response, false) == PacketResult::Success)
3333 {
3334 if (response.IsOKResponse())
3335 {
3336 return true;
3337 }
3338 else if (response.IsUnsupportedResponse())
3339 {
3340 // This packet isn't supported, don't try calling this packet or
3341 // QSaveRegisterState again...
3342 m_supports_QSaveRegisterState = eLazyBoolNo;
3343 }
3344 }
3345 }
3346 }
3347 return false;
3348 }
3349