GDBRemoteCommunication.cpp revision a2f7423310044cf76d8d52aa9153b7fd8b226b49
1//===-- GDBRemoteCommunication.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 "GDBRemoteCommunication.h" 12 13// C Includes 14// C++ Includes 15// Other libraries and framework includes 16#include "llvm/ADT/Triple.h" 17#include "lldb/Interpreter/Args.h" 18#include "lldb/Core/ConnectionFileDescriptor.h" 19#include "lldb/Core/Log.h" 20#include "lldb/Core/State.h" 21#include "lldb/Core/StreamString.h" 22#include "lldb/Host/Host.h" 23#include "lldb/Host/TimeValue.h" 24 25// Project includes 26#include "Utility/StringExtractorGDBRemote.h" 27#include "ProcessGDBRemote.h" 28#include "ProcessGDBRemoteLog.h" 29 30using namespace lldb; 31using namespace lldb_private; 32 33//---------------------------------------------------------------------- 34// GDBRemoteCommunication constructor 35//---------------------------------------------------------------------- 36GDBRemoteCommunication::GDBRemoteCommunication() : 37 Communication("gdb-remote.packets"), 38 m_supports_not_sending_acks (eLazyBoolCalculate), 39 m_supports_thread_suffix (eLazyBoolCalculate), 40 m_supports_qHostInfo (eLazyBoolCalculate), 41 m_supports_vCont_all (eLazyBoolCalculate), 42 m_supports_vCont_any (eLazyBoolCalculate), 43 m_supports_vCont_c (eLazyBoolCalculate), 44 m_supports_vCont_C (eLazyBoolCalculate), 45 m_supports_vCont_s (eLazyBoolCalculate), 46 m_supports_vCont_S (eLazyBoolCalculate), 47 m_rx_packet_listener ("gdbremote.rx_packet"), 48 m_sequence_mutex (Mutex::eMutexTypeRecursive), 49 m_public_is_running (false), 50 m_private_is_running (false), 51 m_async_mutex (Mutex::eMutexTypeRecursive), 52 m_async_packet_predicate (false), 53 m_async_packet (), 54 m_async_response (), 55 m_async_timeout (UINT32_MAX), 56 m_async_signal (-1), 57 m_arch(), 58 m_os(), 59 m_vendor(), 60 m_byte_order(lldb::endian::InlHostByteOrder()), 61 m_pointer_byte_size(0) 62{ 63 m_rx_packet_listener.StartListeningForEvents(this, 64 Communication::eBroadcastBitPacketAvailable | 65 Communication::eBroadcastBitReadThreadDidExit); 66} 67 68//---------------------------------------------------------------------- 69// Destructor 70//---------------------------------------------------------------------- 71GDBRemoteCommunication::~GDBRemoteCommunication() 72{ 73 m_rx_packet_listener.StopListeningForEvents(this, 74 Communication::eBroadcastBitPacketAvailable | 75 Communication::eBroadcastBitReadThreadDidExit); 76 if (IsConnected()) 77 { 78 StopReadThread(); 79 Disconnect(); 80 } 81} 82 83 84char 85GDBRemoteCommunication::CalculcateChecksum (const char *payload, size_t payload_length) 86{ 87 int checksum = 0; 88 89 // We only need to compute the checksum if we are sending acks 90 if (GetSendAcks ()) 91 { 92 for (size_t i = 0; i < payload_length; ++i) 93 checksum += payload[i]; 94 } 95 return checksum & 255; 96} 97 98size_t 99GDBRemoteCommunication::SendAck () 100{ 101 LogSP log (ProcessGDBRemoteLog::GetLogIfAllCategoriesSet (GDBR_LOG_PACKETS)); 102 if (log) 103 log->Printf ("send packet: +"); 104 ConnectionStatus status = eConnectionStatusSuccess; 105 char ack_char = '+'; 106 return Write (&ack_char, 1, status, NULL) == 1; 107} 108 109size_t 110GDBRemoteCommunication::SendNack () 111{ 112 LogSP log (ProcessGDBRemoteLog::GetLogIfAllCategoriesSet (GDBR_LOG_PACKETS)); 113 if (log) 114 log->Printf ("send packet: -"); 115 ConnectionStatus status = eConnectionStatusSuccess; 116 char nack_char = '-'; 117 return Write (&nack_char, 1, status, NULL) == 1; 118} 119 120bool 121GDBRemoteCommunication::GetSendAcks () 122{ 123 if (m_supports_not_sending_acks == eLazyBoolCalculate) 124 { 125 StringExtractorGDBRemote response; 126 m_supports_not_sending_acks = eLazyBoolNo; 127 if (SendPacketAndWaitForResponse("QStartNoAckMode", response, 1, false)) 128 { 129 if (response.IsOKPacket()) 130 m_supports_not_sending_acks = eLazyBoolYes; 131 } 132 } 133 return m_supports_not_sending_acks != eLazyBoolYes; 134} 135 136void 137GDBRemoteCommunication::ResetDiscoverableSettings() 138{ 139 m_supports_not_sending_acks = eLazyBoolCalculate; 140 m_supports_thread_suffix = eLazyBoolCalculate; 141 m_supports_qHostInfo = eLazyBoolCalculate; 142 m_supports_vCont_c = eLazyBoolCalculate; 143 m_supports_vCont_C = eLazyBoolCalculate; 144 m_supports_vCont_s = eLazyBoolCalculate; 145 m_supports_vCont_S = eLazyBoolCalculate; 146 m_arch.Clear(); 147 m_os.Clear(); 148 m_vendor.Clear(); 149 m_byte_order = lldb::endian::InlHostByteOrder(); 150 m_pointer_byte_size = 0; 151} 152 153 154bool 155GDBRemoteCommunication::GetThreadSuffixSupported () 156{ 157 if (m_supports_thread_suffix == eLazyBoolCalculate) 158 { 159 StringExtractorGDBRemote response; 160 m_supports_thread_suffix = eLazyBoolNo; 161 if (SendPacketAndWaitForResponse("QThreadSuffixSupported", response, 1, false)) 162 { 163 if (response.IsOKPacket()) 164 m_supports_thread_suffix = eLazyBoolYes; 165 } 166 } 167 return m_supports_thread_suffix; 168} 169bool 170GDBRemoteCommunication::GetVContSupported (char flavor) 171{ 172 if (m_supports_vCont_c == eLazyBoolCalculate) 173 { 174 StringExtractorGDBRemote response; 175 m_supports_vCont_any = eLazyBoolNo; 176 m_supports_vCont_all = eLazyBoolNo; 177 m_supports_vCont_c = eLazyBoolNo; 178 m_supports_vCont_C = eLazyBoolNo; 179 m_supports_vCont_s = eLazyBoolNo; 180 m_supports_vCont_S = eLazyBoolNo; 181 if (SendPacketAndWaitForResponse("vCont?", response, 1, false)) 182 { 183 const char *response_cstr = response.GetStringRef().c_str(); 184 if (::strstr (response_cstr, ";c")) 185 m_supports_vCont_c = eLazyBoolYes; 186 187 if (::strstr (response_cstr, ";C")) 188 m_supports_vCont_C = eLazyBoolYes; 189 190 if (::strstr (response_cstr, ";s")) 191 m_supports_vCont_s = eLazyBoolYes; 192 193 if (::strstr (response_cstr, ";S")) 194 m_supports_vCont_S = eLazyBoolYes; 195 196 if (m_supports_vCont_c == eLazyBoolYes && 197 m_supports_vCont_C == eLazyBoolYes && 198 m_supports_vCont_s == eLazyBoolYes && 199 m_supports_vCont_S == eLazyBoolYes) 200 { 201 m_supports_vCont_all = eLazyBoolYes; 202 } 203 204 if (m_supports_vCont_c == eLazyBoolYes || 205 m_supports_vCont_C == eLazyBoolYes || 206 m_supports_vCont_s == eLazyBoolYes || 207 m_supports_vCont_S == eLazyBoolYes) 208 { 209 m_supports_vCont_any = eLazyBoolYes; 210 } 211 } 212 } 213 214 switch (flavor) 215 { 216 case 'a': return m_supports_vCont_any; 217 case 'A': return m_supports_vCont_all; 218 case 'c': return m_supports_vCont_c; 219 case 'C': return m_supports_vCont_C; 220 case 's': return m_supports_vCont_s; 221 case 'S': return m_supports_vCont_S; 222 default: break; 223 } 224 return false; 225} 226 227 228size_t 229GDBRemoteCommunication::SendPacketAndWaitForResponse 230( 231 const char *payload, 232 StringExtractorGDBRemote &response, 233 uint32_t timeout_seconds, 234 bool send_async 235) 236{ 237 return SendPacketAndWaitForResponse (payload, 238 ::strlen (payload), 239 response, 240 timeout_seconds, 241 send_async); 242} 243 244size_t 245GDBRemoteCommunication::SendPacketAndWaitForResponse 246( 247 const char *payload, 248 size_t payload_length, 249 StringExtractorGDBRemote &response, 250 uint32_t timeout_seconds, 251 bool send_async 252) 253{ 254 Mutex::Locker locker; 255 TimeValue timeout_time; 256 timeout_time = TimeValue::Now(); 257 timeout_time.OffsetWithSeconds (timeout_seconds); 258 LogSP log (ProcessGDBRemoteLog::GetLogIfAllCategoriesSet (GDBR_LOG_PROCESS)); 259 260 if (GetSequenceMutex (locker)) 261 { 262 if (SendPacketNoLock (payload, strlen(payload))) 263 return WaitForPacketNoLock (response, &timeout_time); 264 } 265 else 266 { 267 if (send_async) 268 { 269 Mutex::Locker async_locker (m_async_mutex); 270 m_async_packet.assign(payload, payload_length); 271 m_async_timeout = timeout_seconds; 272 m_async_packet_predicate.SetValue (true, eBroadcastNever); 273 274 if (log) 275 log->Printf ("async: async packet = %s", m_async_packet.c_str()); 276 277 bool timed_out = false; 278 bool sent_interrupt = false; 279 if (SendInterrupt(locker, 2, sent_interrupt, timed_out)) 280 { 281 if (sent_interrupt) 282 { 283 if (log) 284 log->Printf ("async: sent interrupt"); 285 if (m_async_packet_predicate.WaitForValueEqualTo (false, &timeout_time, &timed_out)) 286 { 287 if (log) 288 log->Printf ("async: got response"); 289 response = m_async_response; 290 return response.GetStringRef().size(); 291 } 292 else 293 { 294 if (log) 295 log->Printf ("async: timed out waiting for response"); 296 } 297 298 // Make sure we wait until the continue packet has been sent again... 299 if (m_private_is_running.WaitForValueEqualTo (true, &timeout_time, &timed_out)) 300 { 301 if (log) 302 log->Printf ("async: timed out waiting for process to resume"); 303 } 304 } 305 else 306 { 307 // We had a racy condition where we went to send the interrupt 308 // yet we were able to get the loc 309 } 310 } 311 else 312 { 313 if (log) 314 log->Printf ("async: failed to interrupt"); 315 } 316 } 317 else 318 { 319 if (log) 320 log->Printf ("mutex taken and send_async == false, aborting packet"); 321 } 322 } 323 return 0; 324} 325 326//template<typename _Tp> 327//class ScopedValueChanger 328//{ 329//public: 330// // Take a value reference and the value to assign it to when this class 331// // instance goes out of scope. 332// ScopedValueChanger (_Tp &value_ref, _Tp value) : 333// m_value_ref (value_ref), 334// m_value (value) 335// { 336// } 337// 338// // This object is going out of scope, change the value pointed to by 339// // m_value_ref to the value we got during construction which was stored in 340// // m_value; 341// ~ScopedValueChanger () 342// { 343// m_value_ref = m_value; 344// } 345//protected: 346// _Tp &m_value_ref; // A reference to the value we will change when this object destructs 347// _Tp m_value; // The value to assign to m_value_ref when this goes out of scope. 348//}; 349 350StateType 351GDBRemoteCommunication::SendContinuePacketAndWaitForResponse 352( 353 ProcessGDBRemote *process, 354 const char *payload, 355 size_t packet_length, 356 StringExtractorGDBRemote &response 357) 358{ 359 LogSP log (ProcessGDBRemoteLog::GetLogIfAllCategoriesSet (GDBR_LOG_PROCESS)); 360 if (log) 361 log->Printf ("GDBRemoteCommunication::%s ()", __FUNCTION__); 362 363 Mutex::Locker locker(m_sequence_mutex); 364 StateType state = eStateRunning; 365 366 BroadcastEvent(eBroadcastBitRunPacketSent, NULL); 367 m_public_is_running.SetValue (true, eBroadcastNever); 368 // Set the starting continue packet into "continue_packet". This packet 369 // make change if we are interrupted and we continue after an async packet... 370 std::string continue_packet(payload, packet_length); 371 372 while (state == eStateRunning) 373 { 374 if (log) 375 log->Printf ("GDBRemoteCommunication::%s () sending continue packet: %s", __FUNCTION__, continue_packet.c_str()); 376 if (SendPacket(continue_packet.c_str(), continue_packet.size()) == 0) 377 state = eStateInvalid; 378 379 m_private_is_running.SetValue (true, eBroadcastNever); 380 381 if (log) 382 log->Printf ("GDBRemoteCommunication::%s () WaitForPacket(%.*s)", __FUNCTION__); 383 384 if (WaitForPacket (response, (TimeValue*)NULL)) 385 { 386 if (response.Empty()) 387 state = eStateInvalid; 388 else 389 { 390 const char stop_type = response.GetChar(); 391 if (log) 392 log->Printf ("GDBRemoteCommunication::%s () got packet: %s", __FUNCTION__, response.GetStringRef().c_str()); 393 switch (stop_type) 394 { 395 case 'T': 396 case 'S': 397 if (process->GetStopID() == 0) 398 { 399 if (process->GetID() == LLDB_INVALID_PROCESS_ID) 400 { 401 lldb::pid_t pid = GetCurrentProcessID (1); 402 if (pid != LLDB_INVALID_PROCESS_ID) 403 process->SetID (pid); 404 } 405 process->BuildDynamicRegisterInfo (true); 406 } 407 408 // Privately notify any internal threads that we have stopped 409 // in case we wanted to interrupt our process, yet we might 410 // send a packet and continue without returning control to the 411 // user. 412 m_private_is_running.SetValue (false, eBroadcastAlways); 413 if (m_async_signal != -1) 414 { 415 if (log) 416 log->Printf ("async: send signo = %s", Host::GetSignalAsCString (m_async_signal)); 417 418 // Save off the async signal we are supposed to send 419 const int async_signal = m_async_signal; 420 // Clear the async signal member so we don't end up 421 // sending the signal multiple times... 422 m_async_signal = -1; 423 // Check which signal we stopped with 424 uint8_t signo = response.GetHexU8(255); 425 if (signo == async_signal) 426 { 427 if (log) 428 log->Printf ("async: stopped with signal %s, we are done running", Host::GetSignalAsCString (signo)); 429 430 // We already stopped with a signal that we wanted 431 // to stop with, so we are done 432 response.SetFilePos (0); 433 } 434 else 435 { 436 // We stopped with a different signal that the one 437 // we wanted to stop with, so now we must resume 438 // with the signal we want 439 char signal_packet[32]; 440 int signal_packet_len = 0; 441 signal_packet_len = ::snprintf (signal_packet, 442 sizeof (signal_packet), 443 "C%2.2x", 444 async_signal); 445 446 if (log) 447 log->Printf ("async: stopped with signal %s, resume with %s", 448 Host::GetSignalAsCString (signo), 449 Host::GetSignalAsCString (async_signal)); 450 451 // Set the continue packet to resume... 452 continue_packet.assign(signal_packet, signal_packet_len); 453 continue; 454 } 455 } 456 else if (m_async_packet_predicate.GetValue()) 457 { 458 // We are supposed to send an asynchronous packet while 459 // we are running. 460 m_async_response.Clear(); 461 if (m_async_packet.empty()) 462 { 463 if (log) 464 log->Printf ("async: error: empty async packet"); 465 466 } 467 else 468 { 469 if (log) 470 log->Printf ("async: sending packet: %s", 471 m_async_packet.c_str()); 472 473 SendPacketAndWaitForResponse (&m_async_packet[0], 474 m_async_packet.size(), 475 m_async_response, 476 m_async_timeout, 477 false); 478 } 479 // Let the other thread that was trying to send the async 480 // packet know that the packet has been sent and response is 481 // ready... 482 m_async_packet_predicate.SetValue(false, eBroadcastAlways); 483 484 // Set the continue packet to resume... 485 continue_packet.assign (1, 'c'); 486 continue; 487 } 488 // Stop with signal and thread info 489 state = eStateStopped; 490 break; 491 492 case 'W': 493 case 'X': 494 // process exited 495 state = eStateExited; 496 break; 497 498 case 'O': 499 // STDOUT 500 { 501 std::string inferior_stdout; 502 inferior_stdout.reserve(response.GetBytesLeft () / 2); 503 char ch; 504 while ((ch = response.GetHexU8()) != '\0') 505 inferior_stdout.append(1, ch); 506 process->AppendSTDOUT (inferior_stdout.c_str(), inferior_stdout.size()); 507 } 508 break; 509 510 case 'E': 511 // ERROR 512 state = eStateInvalid; 513 break; 514 515 default: 516 if (log) 517 log->Printf ("GDBRemoteCommunication::%s () unrecognized async packet", __FUNCTION__); 518 state = eStateInvalid; 519 break; 520 } 521 } 522 } 523 else 524 { 525 if (log) 526 log->Printf ("GDBRemoteCommunication::%s () WaitForPacket(...) => false", __FUNCTION__); 527 state = eStateInvalid; 528 } 529 } 530 if (log) 531 log->Printf ("GDBRemoteCommunication::%s () => %s", __FUNCTION__, StateAsCString(state)); 532 response.SetFilePos(0); 533 m_private_is_running.SetValue (false, eBroadcastAlways); 534 m_public_is_running.SetValue (false, eBroadcastAlways); 535 return state; 536} 537 538size_t 539GDBRemoteCommunication::SendPacket (const char *payload) 540{ 541 Mutex::Locker locker(m_sequence_mutex); 542 return SendPacketNoLock (payload, ::strlen (payload)); 543} 544 545size_t 546GDBRemoteCommunication::SendPacket (const char *payload, size_t payload_length) 547{ 548 Mutex::Locker locker(m_sequence_mutex); 549 return SendPacketNoLock (payload, payload_length); 550} 551 552size_t 553GDBRemoteCommunication::SendPacketNoLock (const char *payload, size_t payload_length) 554{ 555 if (IsConnected()) 556 { 557 StreamString packet(0, 4, eByteOrderBig); 558 559 packet.PutChar('$'); 560 packet.Write (payload, payload_length); 561 packet.PutChar('#'); 562 packet.PutHex8(CalculcateChecksum (payload, payload_length)); 563 564 LogSP log (ProcessGDBRemoteLog::GetLogIfAllCategoriesSet (GDBR_LOG_PACKETS)); 565 if (log) 566 log->Printf ("send packet: %s", packet.GetData()); 567 ConnectionStatus status = eConnectionStatusSuccess; 568 size_t bytes_written = Write (packet.GetData(), packet.GetSize(), status, NULL); 569 if (bytes_written == packet.GetSize()) 570 { 571 if (GetSendAcks ()) 572 { 573 if (GetAck (1) != '+') 574 return 0; 575 } 576 } 577 else 578 { 579 LogSP log (ProcessGDBRemoteLog::GetLogIfAllCategoriesSet (GDBR_LOG_PACKETS)); 580 if (log) 581 log->Printf ("error: failed to send packet: %s", packet.GetData()); 582 } 583 return bytes_written; 584 } 585 return 0; 586} 587 588char 589GDBRemoteCommunication::GetAck (uint32_t timeout_seconds) 590{ 591 StringExtractorGDBRemote response; 592 if (WaitForPacket (response, timeout_seconds) == 1) 593 return response.GetChar(); 594 return 0; 595} 596 597bool 598GDBRemoteCommunication::GetSequenceMutex (Mutex::Locker& locker) 599{ 600 return locker.TryLock (m_sequence_mutex.GetMutex()); 601} 602 603bool 604GDBRemoteCommunication::SendAsyncSignal (int signo) 605{ 606 m_async_signal = signo; 607 bool timed_out = false; 608 bool sent_interrupt = false; 609 Mutex::Locker locker; 610 if (SendInterrupt (locker, 1, sent_interrupt, timed_out)) 611 return true; 612 m_async_signal = -1; 613 return false; 614} 615 616// This function takes a mutex locker as a parameter in case the GetSequenceMutex 617// actually succeeds. If it doesn't succeed in acquiring the sequence mutex 618// (the expected result), then it will send the halt packet. If it does succeed 619// then the caller that requested the interrupt will want to keep the sequence 620// locked down so that no one else can send packets while the caller has control. 621// This function usually gets called when we are running and need to stop the 622// target. It can also be used when we are running and and we need to do something 623// else (like read/write memory), so we need to interrupt the running process 624// (gdb remote protocol requires this), and do what we need to do, then resume. 625 626bool 627GDBRemoteCommunication::SendInterrupt 628( 629 Mutex::Locker& locker, 630 uint32_t seconds_to_wait_for_stop, 631 bool &sent_interrupt, 632 bool &timed_out 633) 634{ 635 sent_interrupt = false; 636 timed_out = false; 637 LogSP log (ProcessGDBRemoteLog::GetLogIfAllCategoriesSet (GDBR_LOG_PROCESS)); 638 639 if (IsRunning()) 640 { 641 // Only send an interrupt if our debugserver is running... 642 if (GetSequenceMutex (locker) == false) 643 { 644 // Someone has the mutex locked waiting for a response or for the 645 // inferior to stop, so send the interrupt on the down low... 646 char ctrl_c = '\x03'; 647 ConnectionStatus status = eConnectionStatusSuccess; 648 TimeValue timeout; 649 if (seconds_to_wait_for_stop) 650 { 651 timeout = TimeValue::Now(); 652 timeout.OffsetWithSeconds (seconds_to_wait_for_stop); 653 } 654 size_t bytes_written = Write (&ctrl_c, 1, status, NULL); 655 ProcessGDBRemoteLog::LogIf (GDBR_LOG_PACKETS | GDBR_LOG_PROCESS, "send packet: \\x03"); 656 if (bytes_written > 0) 657 { 658 sent_interrupt = true; 659 if (seconds_to_wait_for_stop) 660 { 661 if (m_private_is_running.WaitForValueEqualTo (false, &timeout, &timed_out)) 662 { 663 if (log) 664 log->Printf ("GDBRemoteCommunication::%s () - sent interrupt, private state stopped", __FUNCTION__); 665 return true; 666 } 667 else 668 { 669 if (log) 670 log->Printf ("GDBRemoteCommunication::%s () - sent interrupt, timed out wating for async thread resume", __FUNCTION__); 671 } 672 } 673 else 674 { 675 if (log) 676 log->Printf ("GDBRemoteCommunication::%s () - sent interrupt, not waiting for stop...", __FUNCTION__); 677 return true; 678 } 679 } 680 else 681 { 682 if (log) 683 log->Printf ("GDBRemoteCommunication::%s () - failed to write interrupt", __FUNCTION__); 684 } 685 return false; 686 } 687 else 688 { 689 if (log) 690 log->Printf ("GDBRemoteCommunication::%s () - got sequence mutex without having to interrupt", __FUNCTION__); 691 } 692 } 693 return true; 694} 695 696bool 697GDBRemoteCommunication::WaitForNotRunning (const TimeValue *timeout_ptr) 698{ 699 return m_public_is_running.WaitForValueEqualTo (false, timeout_ptr, NULL); 700} 701 702bool 703GDBRemoteCommunication::WaitForNotRunningPrivate (const TimeValue *timeout_ptr) 704{ 705 return m_private_is_running.WaitForValueEqualTo (false, timeout_ptr, NULL); 706} 707 708size_t 709GDBRemoteCommunication::WaitForPacket (StringExtractorGDBRemote &response, uint32_t timeout_seconds) 710{ 711 Mutex::Locker locker(m_sequence_mutex); 712 TimeValue timeout_time; 713 timeout_time = TimeValue::Now(); 714 timeout_time.OffsetWithSeconds (timeout_seconds); 715 return WaitForPacketNoLock (response, &timeout_time); 716} 717 718size_t 719GDBRemoteCommunication::WaitForPacket (StringExtractorGDBRemote &response, const TimeValue* timeout_time_ptr) 720{ 721 Mutex::Locker locker(m_sequence_mutex); 722 return WaitForPacketNoLock (response, timeout_time_ptr); 723} 724 725size_t 726GDBRemoteCommunication::WaitForPacketNoLock (StringExtractorGDBRemote &response, const TimeValue* timeout_time_ptr) 727{ 728 bool checksum_error = false; 729 response.Clear (); 730 731 EventSP event_sp; 732 733 if (m_rx_packet_listener.WaitForEvent (timeout_time_ptr, event_sp)) 734 { 735 const uint32_t event_type = event_sp->GetType(); 736 if (event_type | Communication::eBroadcastBitPacketAvailable) 737 { 738 const EventDataBytes *event_bytes = EventDataBytes::GetEventDataFromEvent(event_sp.get()); 739 if (event_bytes) 740 { 741 const char * packet_data = (const char *)event_bytes->GetBytes(); 742 LogSP log (ProcessGDBRemoteLog::GetLogIfAllCategoriesSet (GDBR_LOG_PACKETS)); 743 if (log) 744 log->Printf ("read packet: %s", packet_data); 745 const size_t packet_size = event_bytes->GetByteSize(); 746 if (packet_data && packet_size > 0) 747 { 748 std::string &response_str = response.GetStringRef(); 749 if (packet_data[0] == '$') 750 { 751 bool success = false; 752 if (packet_size < 4) 753 ::fprintf (stderr, "Packet that starts with $ is too short: '%s'\n", packet_data); 754 else if (packet_data[packet_size-3] != '#' || 755 !::isxdigit (packet_data[packet_size-2]) || 756 !::isxdigit (packet_data[packet_size-1])) 757 ::fprintf (stderr, "Invalid checksum footer for packet: '%s'\n", packet_data); 758 else 759 success = true; 760 761 if (success) 762 response_str.assign (packet_data + 1, packet_size - 4); 763 if (GetSendAcks ()) 764 { 765 char packet_checksum = strtol (&packet_data[packet_size-2], NULL, 16); 766 char actual_checksum = CalculcateChecksum (&response_str[0], response_str.size()); 767 checksum_error = packet_checksum != actual_checksum; 768 // Send the ack or nack if needed 769 if (checksum_error || !success) 770 SendNack(); 771 else 772 SendAck(); 773 } 774 } 775 else 776 { 777 response_str.assign (packet_data, packet_size); 778 } 779 return response_str.size(); 780 } 781 } 782 } 783 else if (Communication::eBroadcastBitReadThreadDidExit) 784 { 785 // Our read thread exited on us so just fall through and return zero... 786 } 787 } 788 return 0; 789} 790 791void 792GDBRemoteCommunication::AppendBytesToCache (const uint8_t *src, size_t src_len, bool broadcast, 793 ConnectionStatus status) 794{ 795 // Put the packet data into the buffer in a thread safe fashion 796 Mutex::Locker locker(m_bytes_mutex); 797 m_bytes.append ((const char *)src, src_len); 798 799 // Parse up the packets into gdb remote packets 800 while (!m_bytes.empty()) 801 { 802 // end_idx must be one past the last valid packet byte. Start 803 // it off with an invalid value that is the same as the current 804 // index. 805 size_t end_idx = 0; 806 807 switch (m_bytes[0]) 808 { 809 case '+': // Look for ack 810 case '-': // Look for cancel 811 case '\x03': // ^C to halt target 812 end_idx = 1; // The command is one byte long... 813 break; 814 815 case '$': 816 // Look for a standard gdb packet? 817 end_idx = m_bytes.find('#'); 818 if (end_idx != std::string::npos) 819 { 820 if (end_idx + 2 < m_bytes.size()) 821 { 822 end_idx += 3; 823 } 824 else 825 { 826 // Checksum bytes aren't all here yet 827 end_idx = std::string::npos; 828 } 829 } 830 break; 831 832 default: 833 break; 834 } 835 836 if (end_idx == std::string::npos) 837 { 838 //ProcessGDBRemoteLog::LogIf (GDBR_LOG_PACKETS | GDBR_LOG_VERBOSE, "GDBRemoteCommunication::%s packet not yet complete: '%s'",__FUNCTION__, m_bytes.c_str()); 839 return; 840 } 841 else if (end_idx > 0) 842 { 843 // We have a valid packet... 844 assert (end_idx <= m_bytes.size()); 845 std::auto_ptr<EventDataBytes> event_bytes_ap (new EventDataBytes (&m_bytes[0], end_idx)); 846 ProcessGDBRemoteLog::LogIf (GDBR_LOG_COMM, "got full packet: %s", event_bytes_ap->GetBytes()); 847 BroadcastEvent (eBroadcastBitPacketAvailable, event_bytes_ap.release()); 848 m_bytes.erase(0, end_idx); 849 } 850 else 851 { 852 assert (1 <= m_bytes.size()); 853 ProcessGDBRemoteLog::LogIf (GDBR_LOG_COMM, "GDBRemoteCommunication::%s tossing junk byte at %c",__FUNCTION__, m_bytes[0]); 854 m_bytes.erase(0, 1); 855 } 856 } 857} 858 859lldb::pid_t 860GDBRemoteCommunication::GetCurrentProcessID (uint32_t timeout_seconds) 861{ 862 StringExtractorGDBRemote response; 863 if (SendPacketAndWaitForResponse("qC", strlen("qC"), response, timeout_seconds, false)) 864 { 865 if (response.GetChar() == 'Q') 866 if (response.GetChar() == 'C') 867 return response.GetHexMaxU32 (false, LLDB_INVALID_PROCESS_ID); 868 } 869 return LLDB_INVALID_PROCESS_ID; 870} 871 872bool 873GDBRemoteCommunication::GetLaunchSuccess (uint32_t timeout_seconds, std::string &error_str) 874{ 875 error_str.clear(); 876 StringExtractorGDBRemote response; 877 if (SendPacketAndWaitForResponse("qLaunchSuccess", strlen("qLaunchSuccess"), response, timeout_seconds, false)) 878 { 879 if (response.IsOKPacket()) 880 return true; 881 if (response.GetChar() == 'E') 882 { 883 // A string the describes what failed when launching... 884 error_str = response.GetStringRef().substr(1); 885 } 886 else 887 { 888 error_str.assign ("unknown error occurred launching process"); 889 } 890 } 891 else 892 { 893 error_str.assign ("failed to send the qLaunchSuccess packet"); 894 } 895 return false; 896} 897 898int 899GDBRemoteCommunication::SendArgumentsPacket (char const *argv[], uint32_t timeout_seconds) 900{ 901 if (argv && argv[0]) 902 { 903 StreamString packet; 904 packet.PutChar('A'); 905 const char *arg; 906 for (uint32_t i = 0; (arg = argv[i]) != NULL; ++i) 907 { 908 const int arg_len = strlen(arg); 909 if (i > 0) 910 packet.PutChar(','); 911 packet.Printf("%i,%i,", arg_len * 2, i); 912 packet.PutBytesAsRawHex8 (arg, arg_len); 913 } 914 915 StringExtractorGDBRemote response; 916 if (SendPacketAndWaitForResponse (packet.GetData(), packet.GetSize(), response, timeout_seconds, false)) 917 { 918 if (response.IsOKPacket()) 919 return 0; 920 uint8_t error = response.GetError(); 921 if (error) 922 return error; 923 } 924 } 925 return -1; 926} 927 928int 929GDBRemoteCommunication::SendEnvironmentPacket (char const *name_equal_value, uint32_t timeout_seconds) 930{ 931 if (name_equal_value && name_equal_value[0]) 932 { 933 StreamString packet; 934 packet.Printf("QEnvironment:%s", name_equal_value); 935 StringExtractorGDBRemote response; 936 if (SendPacketAndWaitForResponse (packet.GetData(), packet.GetSize(), response, timeout_seconds, false)) 937 { 938 if (response.IsOKPacket()) 939 return 0; 940 uint8_t error = response.GetError(); 941 if (error) 942 return error; 943 } 944 } 945 return -1; 946} 947 948bool 949GDBRemoteCommunication::GetHostInfo () 950{ 951 if (m_supports_qHostInfo == eLazyBoolCalculate) 952 { 953 m_supports_qHostInfo = eLazyBoolNo; 954 955 StringExtractorGDBRemote response; 956 if (SendPacketAndWaitForResponse ("qHostInfo", response, 1, false)) 957 { 958 if (response.IsUnsupportedPacket()) 959 return false; 960 961 m_supports_qHostInfo = eLazyBoolYes; 962 963 std::string name; 964 std::string value; 965 uint32_t cpu = LLDB_INVALID_CPUTYPE; 966 uint32_t sub = 0; 967 968 while (response.GetNameColonValue(name, value)) 969 { 970 if (name.compare("cputype") == 0) 971 { 972 // exception type in big endian hex 973 cpu = Args::StringToUInt32 (value.c_str(), LLDB_INVALID_CPUTYPE, 0); 974 } 975 else if (name.compare("cpusubtype") == 0) 976 { 977 // exception count in big endian hex 978 sub = Args::StringToUInt32 (value.c_str(), 0, 0); 979 } 980 else if (name.compare("ostype") == 0) 981 { 982 // exception data in big endian hex 983 m_os.SetCString(value.c_str()); 984 } 985 else if (name.compare("vendor") == 0) 986 { 987 m_vendor.SetCString(value.c_str()); 988 } 989 else if (name.compare("endian") == 0) 990 { 991 if (value.compare("little") == 0) 992 m_byte_order = eByteOrderLittle; 993 else if (value.compare("big") == 0) 994 m_byte_order = eByteOrderBig; 995 else if (value.compare("pdp") == 0) 996 m_byte_order = eByteOrderPDP; 997 } 998 else if (name.compare("ptrsize") == 0) 999 { 1000 m_pointer_byte_size = Args::StringToUInt32 (value.c_str(), 0, 0); 1001 } 1002 } 1003 1004 if (cpu != LLDB_INVALID_CPUTYPE) 1005 m_arch.SetArchitecture (lldb::eArchTypeMachO, cpu, sub); 1006 } 1007 } 1008 return m_supports_qHostInfo == eLazyBoolYes; 1009} 1010 1011int 1012GDBRemoteCommunication::SendAttach 1013( 1014 lldb::pid_t pid, 1015 uint32_t timeout_seconds, 1016 StringExtractorGDBRemote& response 1017) 1018{ 1019 if (pid != LLDB_INVALID_PROCESS_ID) 1020 { 1021 StreamString packet; 1022 packet.Printf("vAttach;%x", pid); 1023 1024 if (SendPacketAndWaitForResponse (packet.GetData(), packet.GetSize(), response, timeout_seconds, false)) 1025 { 1026 if (response.IsErrorPacket()) 1027 return response.GetError(); 1028 return 0; 1029 } 1030 } 1031 return -1; 1032} 1033 1034const lldb_private::ArchSpec & 1035GDBRemoteCommunication::GetHostArchitecture () 1036{ 1037 if (!HostInfoIsValid ()) 1038 GetHostInfo (); 1039 return m_arch; 1040} 1041 1042const lldb_private::ConstString & 1043GDBRemoteCommunication::GetOSString () 1044{ 1045 if (!HostInfoIsValid ()) 1046 GetHostInfo (); 1047 return m_os; 1048} 1049 1050const lldb_private::ConstString & 1051GDBRemoteCommunication::GetVendorString() 1052{ 1053 if (!HostInfoIsValid ()) 1054 GetHostInfo (); 1055 return m_vendor; 1056} 1057 1058lldb::ByteOrder 1059GDBRemoteCommunication::GetByteOrder () 1060{ 1061 if (!HostInfoIsValid ()) 1062 GetHostInfo (); 1063 return m_byte_order; 1064} 1065 1066uint32_t 1067GDBRemoteCommunication::GetAddressByteSize () 1068{ 1069 if (!HostInfoIsValid ()) 1070 GetHostInfo (); 1071 return m_pointer_byte_size; 1072} 1073 1074addr_t 1075GDBRemoteCommunication::AllocateMemory (size_t size, uint32_t permissions, uint32_t timeout_seconds) 1076{ 1077 char packet[64]; 1078 ::snprintf (packet, sizeof(packet), "_M%zx,%s%s%s", size, 1079 permissions & lldb::ePermissionsReadable ? "r" : "", 1080 permissions & lldb::ePermissionsWritable ? "w" : "", 1081 permissions & lldb::ePermissionsExecutable ? "x" : ""); 1082 StringExtractorGDBRemote response; 1083 if (SendPacketAndWaitForResponse (packet, response, timeout_seconds, false)) 1084 { 1085 if (!response.IsErrorPacket()) 1086 return response.GetHexMaxU64(false, LLDB_INVALID_ADDRESS); 1087 } 1088 return LLDB_INVALID_ADDRESS; 1089} 1090 1091bool 1092GDBRemoteCommunication::DeallocateMemory (addr_t addr, uint32_t timeout_seconds) 1093{ 1094 char packet[64]; 1095 snprintf(packet, sizeof(packet), "_m%llx", (uint64_t)addr); 1096 StringExtractorGDBRemote response; 1097 if (SendPacketAndWaitForResponse (packet, response, timeout_seconds, false)) 1098 { 1099 if (response.IsOKPacket()) 1100 return true; 1101 } 1102 return false; 1103} 1104 1105int 1106GDBRemoteCommunication::SetSTDIN (char const *path) 1107{ 1108 if (path && path[0]) 1109 { 1110 StreamString packet; 1111 packet.PutCString("QSetSTDIN:"); 1112 packet.PutBytesAsRawHex8(path, strlen(path)); 1113 1114 StringExtractorGDBRemote response; 1115 if (SendPacketAndWaitForResponse (packet.GetData(), packet.GetSize(), response, 1, false)) 1116 { 1117 if (response.IsOKPacket()) 1118 return 0; 1119 uint8_t error = response.GetError(); 1120 if (error) 1121 return error; 1122 } 1123 } 1124 return -1; 1125} 1126 1127int 1128GDBRemoteCommunication::SetSTDOUT (char const *path) 1129{ 1130 if (path && path[0]) 1131 { 1132 StreamString packet; 1133 packet.PutCString("QSetSTDOUT:"); 1134 packet.PutBytesAsRawHex8(path, strlen(path)); 1135 1136 StringExtractorGDBRemote response; 1137 if (SendPacketAndWaitForResponse (packet.GetData(), packet.GetSize(), response, 1, false)) 1138 { 1139 if (response.IsOKPacket()) 1140 return 0; 1141 uint8_t error = response.GetError(); 1142 if (error) 1143 return error; 1144 } 1145 } 1146 return -1; 1147} 1148 1149int 1150GDBRemoteCommunication::SetSTDERR (char const *path) 1151{ 1152 if (path && path[0]) 1153 { 1154 StreamString packet; 1155 packet.PutCString("QSetSTDERR:"); 1156 packet.PutBytesAsRawHex8(path, strlen(path)); 1157 1158 StringExtractorGDBRemote response; 1159 if (SendPacketAndWaitForResponse (packet.GetData(), packet.GetSize(), response, 1, false)) 1160 { 1161 if (response.IsOKPacket()) 1162 return 0; 1163 uint8_t error = response.GetError(); 1164 if (error) 1165 return error; 1166 } 1167 } 1168 return -1; 1169} 1170 1171int 1172GDBRemoteCommunication::SetWorkingDir (char const *path) 1173{ 1174 if (path && path[0]) 1175 { 1176 StreamString packet; 1177 packet.PutCString("QSetWorkingDir:"); 1178 packet.PutBytesAsRawHex8(path, strlen(path)); 1179 1180 StringExtractorGDBRemote response; 1181 if (SendPacketAndWaitForResponse (packet.GetData(), packet.GetSize(), response, 1, false)) 1182 { 1183 if (response.IsOKPacket()) 1184 return 0; 1185 uint8_t error = response.GetError(); 1186 if (error) 1187 return error; 1188 } 1189 } 1190 return -1; 1191} 1192 1193int 1194GDBRemoteCommunication::SetDisableASLR (bool enable) 1195{ 1196 StreamString packet; 1197 packet.Printf("QSetDisableASLR:%i", enable ? 1 : 0); 1198 1199 StringExtractorGDBRemote response; 1200 if (SendPacketAndWaitForResponse (packet.GetData(), packet.GetSize(), response, 1, false)) 1201 { 1202 if (response.IsOKPacket()) 1203 return 0; 1204 uint8_t error = response.GetError(); 1205 if (error) 1206 return error; 1207 } 1208 return -1; 1209} 1210