// check whether it is an old version of lldb-server.
return GetThreadSuffixSupported();
}
+
+llvm::Expected<int> GDBRemoteCommunicationClient::KillProcess(lldb::pid_t pid) {
+ StringExtractorGDBRemote response;
+ GDBRemoteCommunication::ScopedTimeout(*this, seconds(3));
+
+ if (SendPacketAndWaitForResponse("k", response, GetPacketTimeout()) !=
+ PacketResult::Success)
+ return llvm::createStringError(llvm::inconvertibleErrorCode(),
+ "failed to send k packet");
+
+ char packet_cmd = response.GetChar(0);
+ if (packet_cmd == 'W' || packet_cmd == 'X')
+ return response.GetHexU8();
+
+ return llvm::createStringError(llvm::inconvertibleErrorCode(),
+ "unexpected response to k packet: %s",
+ response.GetStringRef().str().c_str());
+}
}
Status ProcessGDBRemote::DoDestroy() {
- Status error;
Log *log = GetLog(GDBRLog::Process);
LLDB_LOGF(log, "ProcessGDBRemote::DoDestroy()");
if (m_gdb_comm.IsConnected()) {
if (m_public_state.GetValue() != eStateAttaching) {
- StringExtractorGDBRemote response;
- GDBRemoteCommunication::ScopedTimeout(m_gdb_comm,
- std::chrono::seconds(3));
-
- if (m_gdb_comm.SendPacketAndWaitForResponse("k", response,
- GetInterruptTimeout()) ==
- GDBRemoteCommunication::PacketResult::Success) {
- char packet_cmd = response.GetChar(0);
+ llvm::Expected<int> kill_res = m_gdb_comm.KillProcess(GetID());
- if (packet_cmd == 'W' || packet_cmd == 'X') {
+ if (kill_res) {
+ exit_status = kill_res.get();
#if defined(__APPLE__)
- // For Native processes on Mac OS X, we launch through the Host
- // Platform, then hand the process off to debugserver, which becomes
- // the parent process through "PT_ATTACH". Then when we go to kill
- // the process on Mac OS X we call ptrace(PT_KILL) to kill it, then
- // we call waitpid which returns with no error and the correct
- // status. But amusingly enough that doesn't seem to actually reap
- // the process, but instead it is left around as a Zombie. Probably
- // the kernel is in the process of switching ownership back to lldb
- // which was the original parent, and gets confused in the handoff.
- // Anyway, so call waitpid here to finally reap it.
- PlatformSP platform_sp(GetTarget().GetPlatform());
- if (platform_sp && platform_sp->IsHost()) {
- int status;
- ::pid_t reap_pid;
- reap_pid = waitpid(GetID(), &status, WNOHANG);
- LLDB_LOGF(log, "Reaped pid: %d, status: %d.\n", reap_pid, status);
- }
-#endif
- SetLastStopPacket(response);
- ClearThreadIDList();
- exit_status = response.GetHexU8();
- } else {
- LLDB_LOGF(log,
- "ProcessGDBRemote::DoDestroy - got unexpected response "
- "to k packet: %s",
- response.GetStringRef().data());
- exit_string.assign("got unexpected response to k packet: ");
- exit_string.append(std::string(response.GetStringRef()));
+ // For Native processes on Mac OS X, we launch through the Host
+ // Platform, then hand the process off to debugserver, which becomes
+ // the parent process through "PT_ATTACH". Then when we go to kill
+ // the process on Mac OS X we call ptrace(PT_KILL) to kill it, then
+ // we call waitpid which returns with no error and the correct
+ // status. But amusingly enough that doesn't seem to actually reap
+ // the process, but instead it is left around as a Zombie. Probably
+ // the kernel is in the process of switching ownership back to lldb
+ // which was the original parent, and gets confused in the handoff.
+ // Anyway, so call waitpid here to finally reap it.
+ PlatformSP platform_sp(GetTarget().GetPlatform());
+ if (platform_sp && platform_sp->IsHost()) {
+ int status;
+ ::pid_t reap_pid;
+ reap_pid = waitpid(GetID(), &status, WNOHANG);
+ LLDB_LOGF(log, "Reaped pid: %d, status: %d.\n", reap_pid, status);
}
+#endif
+ ClearThreadIDList();
+ exit_string.assign("killed");
} else {
- LLDB_LOGF(log, "ProcessGDBRemote::DoDestroy - failed to send k packet");
- exit_string.assign("failed to send the k packet");
+ exit_string.assign(llvm::toString(kill_res.takeError()));
}
} else {
- LLDB_LOGF(log,
- "ProcessGDBRemote::DoDestroy - killed or interrupted while "
- "attaching");
exit_string.assign("killed or interrupted while attaching.");
}
} else {
StopAsyncThread();
KillDebugserverProcess();
- return error;
+ return Status();
}
void ProcessGDBRemote::SetLastStopPacket(