forked from OSchip/llvm-project
Allow debugserver to detach from the target if the connection is
unexpectedly closed. llvm-svn: 202110
This commit is contained in:
parent
47ff9ab1be
commit
5881318c88
|
@ -650,6 +650,10 @@ DNBProcessDetach (nub_process_t pid)
|
|||
MachProcessSP procSP;
|
||||
if (GetProcessSP (pid, procSP))
|
||||
{
|
||||
const bool remove = true;
|
||||
DNBLogThreaded("Disabling breakpoints and watchpoints, and detaching from %d.", pid);
|
||||
procSP->DisableAllBreakpoints(remove);
|
||||
procSP->DisableAllWatchpoints (remove);
|
||||
return procSP->Detach();
|
||||
}
|
||||
return false;
|
||||
|
|
|
@ -307,14 +307,16 @@ MachProcess::SetState(nub_state_t new_state)
|
|||
}
|
||||
|
||||
void
|
||||
MachProcess::Clear()
|
||||
MachProcess::Clear(bool detaching)
|
||||
{
|
||||
// Clear any cached thread list while the pid and task are still valid
|
||||
|
||||
m_task.Clear();
|
||||
// Now clear out all member variables
|
||||
m_pid = INVALID_NUB_PROCESS;
|
||||
CloseChildFileDescriptors();
|
||||
if (!detaching)
|
||||
CloseChildFileDescriptors();
|
||||
|
||||
m_path.clear();
|
||||
m_args.clear();
|
||||
SetState(eStateUnloaded);
|
||||
|
@ -554,7 +556,8 @@ MachProcess::Detach()
|
|||
m_task.Clear();
|
||||
|
||||
// Clear out any notion of the process we once were
|
||||
Clear();
|
||||
const bool detaching = true;
|
||||
Clear(detaching);
|
||||
|
||||
SetState(eStateDetached);
|
||||
|
||||
|
|
|
@ -258,7 +258,7 @@ private:
|
|||
eMachProcessFlagsAttached = (1 << 0),
|
||||
eMachProcessFlagsUsingSBS = (1 << 1)
|
||||
};
|
||||
void Clear ();
|
||||
void Clear (bool detaching = false);
|
||||
void ReplyToAllExceptions ();
|
||||
void PrivateResume ();
|
||||
|
||||
|
|
|
@ -57,7 +57,8 @@ public:
|
|||
m_pid_pthread(),
|
||||
m_launch_status(),
|
||||
m_arg_vec (),
|
||||
m_env_vec ()
|
||||
m_env_vec (),
|
||||
m_detach_on_error(false)
|
||||
{
|
||||
}
|
||||
|
||||
|
@ -116,6 +117,10 @@ public:
|
|||
const char * GetSTDOUTPath() { return m_stdout.empty() ? NULL : m_stdout.c_str(); }
|
||||
const char * GetSTDERRPath() { return m_stderr.empty() ? NULL : m_stderr.c_str(); }
|
||||
const char * GetWorkingDirPath() { return m_working_dir.empty() ? NULL : m_working_dir.c_str(); }
|
||||
|
||||
void SetDetachOnError(bool detach) { m_detach_on_error = detach; }
|
||||
bool GetDetachOnError () { return m_detach_on_error; }
|
||||
|
||||
protected:
|
||||
//------------------------------------------------------------------
|
||||
// Classes that inherit from RNBContext can see and modify these
|
||||
|
@ -133,6 +138,7 @@ protected:
|
|||
std::vector<std::string> m_arg_vec;
|
||||
std::vector<std::string> m_env_vec; // This will be unparsed - entries FOO=value
|
||||
std::string m_working_directory;
|
||||
bool m_detach_on_error;
|
||||
|
||||
void StartProcessStatusThread();
|
||||
void StopProcessStatusThread();
|
||||
|
|
|
@ -63,6 +63,7 @@ static nub_launch_flavor_t g_launch_flavor = eLaunchFlavorDefault;
|
|||
int g_disable_aslr = 0;
|
||||
|
||||
int g_isatty = 0;
|
||||
bool g_detach_on_error = false;
|
||||
|
||||
#define RNBLogSTDOUT(fmt, ...) do { if (g_isatty) { fprintf(stdout, fmt, ## __VA_ARGS__); } else { _DNBLog(0, fmt, ## __VA_ARGS__); } } while (0)
|
||||
#define RNBLogSTDERR(fmt, ...) do { if (g_isatty) { fprintf(stderr, fmt, ## __VA_ARGS__); } else { _DNBLog(0, fmt, ## __VA_ARGS__); } } while (0)
|
||||
|
@ -571,8 +572,24 @@ RNBRunLoopInferiorExecuting (RNBRemote *remote)
|
|||
// in its current state and listen for another connection...
|
||||
if (ctx.ProcessStateRunning())
|
||||
{
|
||||
DNBLog ("debugserver's event read thread is exiting, killing the inferior process.");
|
||||
DNBProcessKill (ctx.ProcessID());
|
||||
if (ctx.GetDetachOnError())
|
||||
{
|
||||
DNBLog ("debugserver's event read thread is exiting, detaching from the inferior process.");
|
||||
DNBProcessDetach (ctx.ProcessID());
|
||||
}
|
||||
else
|
||||
{
|
||||
DNBLog ("debugserver's event read thread is exiting, killing the inferior process.");
|
||||
DNBProcessKill (ctx.ProcessID());
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if (ctx.GetDetachOnError())
|
||||
{
|
||||
DNBLog ("debugserver's event read thread is exiting, detaching from the inferior process.");
|
||||
DNBProcessDetach (ctx.ProcessID());
|
||||
}
|
||||
}
|
||||
}
|
||||
mode = eRNBRunLoopModeExit;
|
||||
|
@ -814,6 +831,7 @@ static struct option g_long_options[] =
|
|||
{ "attach", required_argument, NULL, 'a' },
|
||||
{ "arch", required_argument, NULL, 'A' },
|
||||
{ "debug", no_argument, NULL, 'g' },
|
||||
{ "detach-on-error", no_argument, NULL, 'e' },
|
||||
{ "verbose", no_argument, NULL, 'v' },
|
||||
{ "lockdown", no_argument, &g_lockdown_opt, 1 }, // short option "-k"
|
||||
{ "applist", no_argument, &g_applist_opt, 1 }, // short option "-t"
|
||||
|
@ -1011,6 +1029,9 @@ main (int argc, char *argv[])
|
|||
}
|
||||
}
|
||||
break;
|
||||
|
||||
case 'e':
|
||||
g_detach_on_error = true;
|
||||
|
||||
case 'W':
|
||||
if (optarg && optarg[0])
|
||||
|
@ -1181,6 +1202,8 @@ main (int argc, char *argv[])
|
|||
}
|
||||
}
|
||||
|
||||
remote->Context().SetDetachOnError(g_detach_on_error);
|
||||
|
||||
remote->Initialize();
|
||||
|
||||
// It is ok for us to set NULL as the logfile (this will disable any logging)
|
||||
|
|
Loading…
Reference in New Issue