summaryrefslogtreecommitdiffstats
path: root/lldb/source/Target/Target.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'lldb/source/Target/Target.cpp')
-rw-r--r--lldb/source/Target/Target.cpp109
1 files changed, 109 insertions, 0 deletions
diff --git a/lldb/source/Target/Target.cpp b/lldb/source/Target/Target.cpp
index 0336f775859..7c850c6680a 100644
--- a/lldb/source/Target/Target.cpp
+++ b/lldb/source/Target/Target.cpp
@@ -28,6 +28,7 @@
#include "lldb/Core/ModuleSpec.h"
#include "lldb/Core/Section.h"
#include "lldb/Core/SourceManager.h"
+#include "lldb/Core/State.h"
#include "lldb/Core/StreamString.h"
#include "lldb/Core/Timer.h"
#include "lldb/Core/ValueObject.h"
@@ -2317,6 +2318,114 @@ Target::ClearAllLoadedSections ()
m_section_load_history.Clear();
}
+
+Error
+Target::Launch (Listener &listener, ProcessLaunchInfo &launch_info)
+{
+ Error error;
+ Error error2;
+
+ StateType state = eStateInvalid;
+
+ launch_info.GetFlags().Set (eLaunchFlagDebug);
+
+ // Get the value of synchronous execution here. If you wait till after you have started to
+ // run, then you could have hit a breakpoint, whose command might switch the value, and
+ // then you'll pick up that incorrect value.
+ Debugger &debugger = GetDebugger();
+ const bool synchronous_execution = debugger.GetCommandInterpreter().GetSynchronous ();
+
+ PlatformSP platform_sp (GetPlatform());
+
+ // Finalize the file actions, and if none were given, default to opening
+ // up a pseudo terminal
+ const bool default_to_use_pty = platform_sp ? platform_sp->IsHost() : false;
+ launch_info.FinalizeFileActions (this, default_to_use_pty);
+
+ if (state == eStateConnected)
+ {
+ if (launch_info.GetFlags().Test (eLaunchFlagLaunchInTTY))
+ {
+ error.SetErrorString("can't launch in tty when launching through a remote connection");
+ return error;
+ }
+ }
+
+ if (!launch_info.GetArchitecture().IsValid())
+ launch_info.GetArchitecture() = GetArchitecture();
+
+ if (state != eStateConnected && platform_sp && platform_sp->CanDebugProcess ())
+ {
+ m_process_sp = GetPlatform()->DebugProcess (launch_info,
+ debugger,
+ this,
+ listener,
+ error);
+ }
+ else
+ {
+ if (state == eStateConnected)
+ {
+ assert(m_process_sp);
+ }
+ else
+ {
+ const char *plugin_name = launch_info.GetProcessPluginName();
+ CreateProcess (listener, plugin_name, NULL);
+ }
+
+ if (m_process_sp)
+ error = m_process_sp->Launch (launch_info);
+ }
+
+ if (!m_process_sp)
+ {
+ if (error.Success())
+ error.SetErrorString("failed to launch or debug process");
+ return error;
+ }
+
+ if (error.Success())
+ {
+ if (launch_info.GetFlags().Test(eLaunchFlagStopAtEntry) == false)
+ {
+ StateType state = m_process_sp->WaitForProcessToStop (NULL, NULL, false);
+
+ if (state == eStateStopped)
+ {
+ error = m_process_sp->Resume();
+ if (error.Success())
+ {
+ if (synchronous_execution)
+ {
+ state = m_process_sp->WaitForProcessToStop (NULL);
+ const bool must_be_alive = false; // eStateExited is ok, so this must be false
+ if (!StateIsStoppedState(state, must_be_alive))
+ {
+ error2.SetErrorStringWithFormat("process isn't stopped: %s", StateAsCString(state));
+ return error2;
+ }
+ }
+ }
+ else
+ {
+ error2.SetErrorStringWithFormat("process resume at entry point failed: %s", error.AsCString());
+ return error2;
+ }
+ }
+ else
+ {
+ error.SetErrorStringWithFormat ("initial process state wasn't stopped: %s", StateAsCString(state));
+ }
+ }
+ }
+ else
+ {
+ error2.SetErrorStringWithFormat ("process launch failed: %s", error.AsCString());
+ return error2;
+ }
+ return error;
+}
//--------------------------------------------------------------
// Target::StopHook
//--------------------------------------------------------------
OpenPOWER on IntegriCloud