diff options
-rw-r--r-- | lldb/include/lldb/Target/Process.h | 2 | ||||
-rw-r--r-- | lldb/source/Commands/CommandObjectImage.cpp | 2 | ||||
-rw-r--r-- | lldb/source/Commands/CommandObjectProcess.cpp | 30 | ||||
-rw-r--r-- | lldb/source/Core/Address.cpp | 2 | ||||
-rw-r--r-- | lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunication.cpp | 11 | ||||
-rw-r--r-- | lldb/source/Plugins/Process/gdb-remote/ProcessGDBRemote.cpp | 186 | ||||
-rw-r--r-- | lldb/source/Plugins/Process/gdb-remote/ProcessGDBRemote.h | 2 | ||||
-rw-r--r-- | lldb/source/Target/Process.cpp | 87 |
8 files changed, 132 insertions, 190 deletions
diff --git a/lldb/include/lldb/Target/Process.h b/lldb/include/lldb/Target/Process.h index a884e20c711..fcf48afef37 100644 --- a/lldb/include/lldb/Target/Process.h +++ b/lldb/include/lldb/Target/Process.h @@ -1918,7 +1918,7 @@ protected: typedef std::map<lldb::LanguageType, lldb::LanguageRuntimeSP> LanguageRuntimeCollection; LanguageRuntimeCollection m_language_runtimes; - std::auto_ptr<NextEventAction> *m_next_event_action_ap; + std::auto_ptr<NextEventAction> m_next_event_action_ap; size_t RemoveBreakpointOpcodesFromBuffer (lldb::addr_t addr, size_t size, uint8_t *buf) const; diff --git a/lldb/source/Commands/CommandObjectImage.cpp b/lldb/source/Commands/CommandObjectImage.cpp index 1f6cd50941d..5b56b6a0d7a 100644 --- a/lldb/source/Commands/CommandObjectImage.cpp +++ b/lldb/source/Commands/CommandObjectImage.cpp @@ -240,7 +240,7 @@ LookupAddressInModule // If an offset was given, print out the address we ended up looking up if (offset) - strm.Printf("0x%llx: ", addr); + strm.Printf("File Address: 0x%llx\n", addr); ExecutionContextScope *exe_scope = interpreter.GetDebugger().GetExecutionContext().GetBestExecutionContextScope(); strm.IndentMore(); diff --git a/lldb/source/Commands/CommandObjectProcess.cpp b/lldb/source/Commands/CommandObjectProcess.cpp index 42bc4af3bb2..3d863b7b83d 100644 --- a/lldb/source/Commands/CommandObjectProcess.cpp +++ b/lldb/source/Commands/CommandObjectProcess.cpp @@ -167,10 +167,14 @@ public: Process *process = m_interpreter.GetDebugger().GetExecutionContext().process; if (process && process->IsAlive()) { - if (!m_interpreter.Confirm ("There is a running process, kill it and restart?", true)) + char message[1024]; + if (process->GetState() == eStateAttaching) + ::strncpy (message, "There is a pending attach, abort it and launch a new process?", sizeof(message)); + else + ::strncpy (message, "There is a running process, kill it and restart?", sizeof(message)); + + if (!m_interpreter.Confirm (message, true)) { - result.AppendErrorWithFormat ("Process %u is currently being debugged, restart cancelled.\n", - process->GetID()); result.SetStatus (eReturnStatusFailed); return false; } @@ -623,7 +627,7 @@ public: return false; } - m_interpreter.GetDebugger().GetOutputStream().Printf("Waiting to attach to a process named \"%s\".\n", wait_name); + result.AppendMessageWithFormat("Waiting to attach to a process named \"%s\".\n", wait_name); error = process->Attach (wait_name, m_options.waitfor); if (error.Success()) { @@ -652,7 +656,6 @@ public: else { result.SetDidChangeProcessState (true); - result.AppendMessageWithFormat ("Starting to attach to process."); result.SetStatus (eReturnStatusSuccessFinishNoResult); } } @@ -712,7 +715,6 @@ public: else { result.SetDidChangeProcessState (true); - result.AppendMessageWithFormat ("Starting to attach to process."); result.SetStatus (eReturnStatusSuccessFinishNoResult); } } @@ -731,18 +733,20 @@ public: if (result.Succeeded()) { // Okay, we're done. Last step is to warn if the executable module has changed: + char new_path[PATH_MAX]; if (!old_exec_module_sp) { - char new_path[PATH_MAX + 1]; - target->GetExecutableModule()->GetFileSpec().GetPath(new_path, PATH_MAX); - - result.AppendMessageWithFormat("Executable module set to \"%s\".\n", - new_path); + // We might not have a module if we attached to a raw pid... + ModuleSP new_module_sp (target->GetExecutableModule()); + if (new_module_sp) + { + new_module_sp->GetFileSpec().GetPath(new_path, PATH_MAX); + result.AppendMessageWithFormat("Executable module set to \"%s\".\n", new_path); + } } else if (old_exec_module_sp->GetFileSpec() != target->GetExecutableModule()->GetFileSpec()) { - char old_path[PATH_MAX + 1]; - char new_path[PATH_MAX + 1]; + char old_path[PATH_MAX]; old_exec_module_sp->GetFileSpec().GetPath(old_path, PATH_MAX); target->GetExecutableModule()->GetFileSpec().GetPath (new_path, PATH_MAX); diff --git a/lldb/source/Core/Address.cpp b/lldb/source/Core/Address.cpp index fadbef25715..967ccd0d3c2 100644 --- a/lldb/source/Core/Address.cpp +++ b/lldb/source/Core/Address.cpp @@ -576,7 +576,7 @@ Address::Dump (Stream *s, ExecutionContextScope *exe_scope, DumpStyle style, Dum bool show_stop_context = true; const bool show_module = (style == DumpStyleResolvedDescription); const bool show_fullpaths = false; - const bool show_inlined_frames = false; + const bool show_inlined_frames = true; if (sc.function == NULL && sc.symbol != NULL) { // If we have just a symbol make sure it is in the right section diff --git a/lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunication.cpp b/lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunication.cpp index 20af4b44a1c..54382ff1240 100644 --- a/lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunication.cpp +++ b/lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunication.cpp @@ -273,6 +273,17 @@ GDBRemoteCommunication::SendContinuePacketAndWaitForResponse { case 'T': case 'S': + if (process->GetStopID() == 0) + { + if (process->GetID() == LLDB_INVALID_PROCESS_ID) + { + lldb::pid_t pid = GetCurrentProcessID (1); + if (pid != LLDB_INVALID_PROCESS_ID) + process->SetID (pid); + } + process->BuildDynamicRegisterInfo (true); + } + // Privately notify any internal threads that we have stopped // in case we wanted to interrupt our process, yet we might // send a packet and continue without returning control to the diff --git a/lldb/source/Plugins/Process/gdb-remote/ProcessGDBRemote.cpp b/lldb/source/Plugins/Process/gdb-remote/ProcessGDBRemote.cpp index afaf3744c0e..d50c57a3fd2 100644 --- a/lldb/source/Plugins/Process/gdb-remote/ProcessGDBRemote.cpp +++ b/lldb/source/Plugins/Process/gdb-remote/ProcessGDBRemote.cpp @@ -184,18 +184,22 @@ ProcessGDBRemote::EnablePluginLogging (Stream *strm, Args &command) } void -ProcessGDBRemote::BuildDynamicRegisterInfo () +ProcessGDBRemote::BuildDynamicRegisterInfo (bool force) { - char register_info_command[64]; + if (!force && m_register_info.GetNumRegisters() > 0) + return; + + char packet[128]; m_register_info.Clear(); StringExtractorGDBRemote::Type packet_type = StringExtractorGDBRemote::eResponse; uint32_t reg_offset = 0; uint32_t reg_num = 0; for (; packet_type == StringExtractorGDBRemote::eResponse; ++reg_num) { - ::snprintf (register_info_command, sizeof(register_info_command), "qRegisterInfo%x", reg_num); + const int packet_len = ::snprintf (packet, sizeof(packet), "qRegisterInfo%x", reg_num); + assert (packet_len < sizeof(packet)); StringExtractorGDBRemote response; - if (m_gdb_comm.SendPacketAndWaitForResponse(register_info_command, response, 2, false)) + if (m_gdb_comm.SendPacketAndWaitForResponse(packet, packet_len, response, 2, false)) { packet_type = response.GetType(); if (packet_type == StringExtractorGDBRemote::eResponse) @@ -586,7 +590,7 @@ ProcessGDBRemote::DidLaunchOrAttach () { m_dispatch_queue_offsets_addr = LLDB_INVALID_ADDRESS; - BuildDynamicRegisterInfo (); + BuildDynamicRegisterInfo (false); m_byte_order = m_gdb_comm.GetByteOrder(); @@ -677,43 +681,11 @@ ProcessGDBRemote::DoAttachToProcessWithID (lldb::pid_t attach_pid) { char packet[64]; const int packet_len = ::snprintf (packet, sizeof(packet), "vAttach;%x", attach_pid); - StringExtractorGDBRemote response; - StateType stop_state = m_gdb_comm.SendContinuePacketAndWaitForResponse (this, - packet, - packet_len, - response); - switch (stop_state) - { - case eStateStopped: - case eStateCrashed: - case eStateSuspended: - SetID (attach_pid); - m_last_stop_packet = response; - m_last_stop_packet.SetFilePos (0); - SetPrivateState (stop_state); - break; - - case eStateExited: - m_last_stop_packet = response; - m_last_stop_packet.SetFilePos (0); - response.SetFilePos(1); - SetExitStatus(response.GetHexU8(), NULL); - break; - - default: - SetExitStatus(-1, "unable to attach to process"); - break; - } - + + m_async_broadcaster.BroadcastEvent (eBroadcastBitAsyncContinue, new EventDataBytes (packet, packet_len)); } } } - - lldb::pid_t pid = GetID(); - if (pid == LLDB_INVALID_PROCESS_ID) - { - KillDebugserverProcess(); - } return error; } @@ -787,86 +759,15 @@ ProcessGDBRemote::DoAttachToProcessWithName (const char *process_name, bool wait packet.PutCString("vAttachName"); packet.PutChar(';'); packet.PutBytesAsRawHex8(process_name, strlen(process_name), eByteOrderHost, eByteOrderHost); - StringExtractorGDBRemote response; - StateType stop_state = m_gdb_comm.SendContinuePacketAndWaitForResponse (this, - packet.GetData(), - packet.GetSize(), - response); - switch (stop_state) - { - case eStateStopped: - case eStateCrashed: - case eStateSuspended: - SetID (m_gdb_comm.GetCurrentProcessID(m_packet_timeout)); - m_last_stop_packet = response; - m_last_stop_packet.SetFilePos (0); - SetPrivateState (stop_state); - break; - - case eStateExited: - m_last_stop_packet = response; - m_last_stop_packet.SetFilePos (0); - response.SetFilePos(1); - SetExitStatus(response.GetHexU8(), NULL); - break; + + m_async_broadcaster.BroadcastEvent (eBroadcastBitAsyncContinue, new EventDataBytes (packet.GetData(), packet.GetSize())); - default: - SetExitStatus(-1, "unable to attach to process"); - break; - } } } } - - lldb::pid_t pid = GetID(); - if (pid == LLDB_INVALID_PROCESS_ID) - { - KillDebugserverProcess(); - - if (error.Success()) - error.SetErrorStringWithFormat("unable to attach to process named '%s'", process_name); - } - return error; } -// -// if (wait_for_launch) -// { -// InputReaderSP reader_sp (new InputReader()); -// StreamString instructions; -// instructions.Printf("Hit any key to cancel waiting for '%s' to launch...", process_name); -// error = reader_sp->Initialize (AttachInputReaderCallback, // callback -// this, // baton -// eInputReaderGranularityByte, -// NULL, // End token -// false); -// -// StringExtractorGDBRemote response; -// m_waiting_for_attach = true; -// FILE *reader_out_fh = reader_sp->GetOutputFileHandle(); -// while (m_waiting_for_attach) -// { -// // Wait for one second for the stop reply packet -// if (m_gdb_comm.WaitForPacket(response, 1)) -// { -// // Got some sort of packet, see if it is the stop reply packet? -// char ch = response.GetChar(0); -// if (ch == 'T') -// { -// m_waiting_for_attach = false; -// } -// } -// else -// { -// // Put a period character every second -// fputc('.', reader_out_fh); -// } -// } -// } -// } -// return GetID(); -//} void ProcessGDBRemote::DidAttach () @@ -1158,15 +1059,23 @@ ProcessGDBRemote::DoHalt (bool &caused_stop) bool timed_out = false; Mutex::Locker locker; - - if (!m_gdb_comm.SendInterrupt (locker, 2, caused_stop, timed_out)) + + if (m_public_state.GetValue() == eStateAttaching) { - if (timed_out) - error.SetErrorString("timed out sending interrupt packet"); - else - error.SetErrorString("unknown error sending interrupt packet"); + // We are being asked to halt during an attach. We need to just close + // our file handle and debugserver will go away, and we can be done... + m_gdb_comm.Disconnect(); + } + else + { + if (!m_gdb_comm.SendInterrupt (locker, 2, caused_stop, timed_out)) + { + if (timed_out) + error.SetErrorString("timed out sending interrupt packet"); + else + error.SetErrorString("unknown error sending interrupt packet"); + } } - return error; } @@ -1305,22 +1214,32 @@ ProcessGDBRemote::DoDestroy () // Interrupt if our inferior is running... if (m_gdb_comm.IsConnected()) { - StringExtractorGDBRemote response; - bool send_async = true; - if (m_gdb_comm.SendPacketAndWaitForResponse("k", 1, response, 2, send_async)) + if (m_public_state.GetValue() == eStateAttaching) { - char packet_cmd = response.GetChar(0); - - if (packet_cmd == 'W' || packet_cmd == 'X') - { - m_last_stop_packet = response; - SetExitStatus(response.GetHexU8(), NULL); - } + // We are being asked to halt during an attach. We need to just close + // our file handle and debugserver will go away, and we can be done... + m_gdb_comm.Disconnect(); } else { - SetExitStatus(SIGABRT, NULL); - //error.SetErrorString("kill packet failed"); + + StringExtractorGDBRemote response; + bool send_async = true; + if (m_gdb_comm.SendPacketAndWaitForResponse("k", 1, response, 2, send_async)) + { + char packet_cmd = response.GetChar(0); + + if (packet_cmd == 'W' || packet_cmd == 'X') + { + m_last_stop_packet = response; + SetExitStatus(response.GetHexU8(), NULL); + } + } + else + { + SetExitStatus(SIGABRT, NULL); + //error.SetErrorString("kill packet failed"); + } } } StopAsyncThread (); @@ -1951,7 +1870,7 @@ ProcessGDBRemote::StartDebugserverProcess debugserver_args.AppendArgument(arg_cstr); } // debugserver_args.AppendArgument("--log-file=/tmp/debugserver.txt"); -// debugserver_args.AppendArgument("--log-flags=0x800e0e"); +// debugserver_args.AppendArgument("--log-flags=0x802e0e"); // Now append the program arguments if (launch_process) @@ -2268,7 +2187,8 @@ ProcessGDBRemote::AsyncThread (void *arg) if (log) log->Printf ("ProcessGDBRemote::%s (arg = %p, pid = %i) got eBroadcastBitAsyncContinue: %s", __FUNCTION__, arg, process->GetID(), continue_cstr); - process->SetPrivateState(eStateRunning); + if (::strstr (continue_cstr, "vAttach") == NULL) + process->SetPrivateState(eStateRunning); StringExtractorGDBRemote response; StateType stop_state = process->GetGDBRemote().SendContinuePacketAndWaitForResponse (process, continue_cstr, continue_cstr_len, response); diff --git a/lldb/source/Plugins/Process/gdb-remote/ProcessGDBRemote.h b/lldb/source/Plugins/Process/gdb-remote/ProcessGDBRemote.h index 6fa5ab7a752..af3084c6496 100644 --- a/lldb/source/Plugins/Process/gdb-remote/ProcessGDBRemote.h +++ b/lldb/source/Plugins/Process/gdb-remote/ProcessGDBRemote.h @@ -307,7 +307,7 @@ protected: KillDebugserverProcess (); void - BuildDynamicRegisterInfo (); + BuildDynamicRegisterInfo (bool force); GDBRemoteCommunication & GetGDBRemote() diff --git a/lldb/source/Target/Process.cpp b/lldb/source/Target/Process.cpp index 46f3a4721ba..e443ba66292 100644 --- a/lldb/source/Target/Process.cpp +++ b/lldb/source/Target/Process.cpp @@ -238,7 +238,7 @@ Process::Process(Target &target, Listener &listener) : m_stdio_communication_mutex (Mutex::eMutexTypeRecursive), m_stdout_data (), m_memory_cache (), - m_next_event_action_ap(NULL) + m_next_event_action_ap() { UpdateInstanceName(); @@ -1590,37 +1590,46 @@ Process::AttachCompletionHandler::PerformAction (lldb::EventSP &event_sp) StateType state = ProcessEventData::GetStateFromEvent (event_sp.get()); switch (state) { - case eStateStopped: - case eStateCrashed: - { - m_process->DidAttach (); - // Figure out which one is the executable, and set that in our target: - ModuleList &modules = m_process->GetTarget().GetImages(); - - size_t num_modules = modules.GetSize(); - for (int i = 0; i < num_modules; i++) + case eStateRunning: + return eEventActionRetry; + + case eStateStopped: + case eStateCrashed: { - ModuleSP module_sp = modules.GetModuleAtIndex(i); - if (module_sp->IsExecutable()) + // During attach, prior to sending the eStateStopped event, + // lldb_private::Process subclasses must set the process must set + // the new process ID. + assert (m_process->GetID() != LLDB_INVALID_PROCESS_ID); + m_process->DidAttach (); + // Figure out which one is the executable, and set that in our target: + ModuleList &modules = m_process->GetTarget().GetImages(); + + size_t num_modules = modules.GetSize(); + for (int i = 0; i < num_modules; i++) { - ModuleSP exec_module = m_process->GetTarget().GetExecutableModule(); - if (!exec_module || exec_module != module_sp) + ModuleSP module_sp = modules.GetModuleAtIndex(i); + if (module_sp->IsExecutable()) { - - m_process->GetTarget().SetExecutableModule (module_sp, false); + ModuleSP exec_module = m_process->GetTarget().GetExecutableModule(); + if (!exec_module || exec_module != module_sp) + { + + m_process->GetTarget().SetExecutableModule (module_sp, false); + } + break; } - break; } + return eEventActionSuccess; } - return eEventActionSuccess; - } - break; - default: - case eStateExited: - case eStateInvalid: - m_exit_string.assign ("No valid Process"); - return eEventActionExit; - break; + + + break; + default: + case eStateExited: + case eStateInvalid: + m_exit_string.assign ("No valid Process"); + return eEventActionExit; + break; } } @@ -1778,24 +1787,23 @@ Process::Halt () PausePrivateStateThread(); EventSP event_sp; - Error error; + Error error (WillHalt()); - if (m_public_state.GetValue() == eStateAttaching) - { - SetExitStatus(SIGKILL, "Cancelled async attach."); - } - else + if (error.Success()) { - error = WillHalt(); + bool caused_stop = false; + + // Ask the process subclass to actually halt our process + error = DoHalt(caused_stop); if (error.Success()) { - - bool caused_stop = false; - - // Ask the process subclass to actually halt our process - error = DoHalt(caused_stop); - if (error.Success()) + if (m_public_state.GetValue() == eStateAttaching) + { + SetExitStatus(SIGKILL, "Cancelled async attach."); + Destroy (); + } + else { // If "caused_stop" is true, then DoHalt stopped the process. If // "caused_stop" is false, the process was already stopped. @@ -1835,7 +1843,6 @@ Process::Halt () } } DidHalt(); - } } } |