blob: 9e23b4f849555b771aef7b6f499045da558f400b [file] [log] [blame]
Todd Fiala6d6b55d2014-06-30 00:30:53 +00001//===-- ProcessLaunchInfo.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
Eugene Zelenko9394d7722016-02-18 00:10:17 +000010// C Includes
11// C++ Includes
12#include <climits>
Todd Fiala2850b1b2014-06-30 23:51:35 +000013
Eugene Zelenko9394d7722016-02-18 00:10:17 +000014// Other libraries and framework includes
15// Project includes
Greg Clayton8012cad2014-11-17 19:39:20 +000016#include "lldb/Core/Debugger.h"
Zachary Turner190fadc2016-03-22 17:58:09 +000017#include "lldb/Host/Config.h"
Zachary Turner4eff2d32015-10-14 21:37:36 +000018#include "lldb/Host/FileSystem.h"
Zachary Turner190fadc2016-03-22 17:58:09 +000019#include "lldb/Host/HostInfo.h"
Zachary Turner696b5282014-08-14 16:01:25 +000020#include "lldb/Target/FileAction.h"
Zachary Turner190fadc2016-03-22 17:58:09 +000021#include "lldb/Target/ProcessLaunchInfo.h"
Todd Fiala6d6b55d2014-06-30 00:30:53 +000022#include "lldb/Target/Target.h"
Zachary Turner6f9e6902017-03-03 20:56:28 +000023#include "lldb/Utility/Log.h"
Zachary Turner2f3df612017-04-06 21:28:29 +000024#include "lldb/Utility/StreamString.h"
Todd Fiala6d6b55d2014-06-30 00:30:53 +000025
Zachary Turner190fadc2016-03-22 17:58:09 +000026#include "llvm/Support/ConvertUTF.h"
Pavel Labath1d5855b2017-01-23 15:56:45 +000027#include "llvm/Support/FileSystem.h"
Zachary Turner190fadc2016-03-22 17:58:09 +000028
29#if !defined(_WIN32)
30#include <limits.h>
31#endif
32
Todd Fiala6d6b55d2014-06-30 00:30:53 +000033using namespace lldb;
34using namespace lldb_private;
35
36//----------------------------------------------------------------------------
Todd Fiala6d6b55d2014-06-30 00:30:53 +000037// ProcessLaunchInfo member functions
38//----------------------------------------------------------------------------
39
Kate Stoneb9c1b512016-09-06 20:57:50 +000040ProcessLaunchInfo::ProcessLaunchInfo()
41 : ProcessInfo(), m_working_dir(), m_plugin_name(), m_flags(0),
Pavel Labath07d6f882017-12-11 10:09:14 +000042 m_file_actions(), m_pty(new PseudoTerminal), m_resume_count(0),
43 m_monitor_callback(nullptr), m_monitor_callback_baton(nullptr),
44 m_monitor_signals(false), m_listener_sp(), m_hijack_listener_sp() {}
Todd Fiala6d6b55d2014-06-30 00:30:53 +000045
Chaoren Lind3173f32015-05-29 19:52:29 +000046ProcessLaunchInfo::ProcessLaunchInfo(const FileSpec &stdin_file_spec,
47 const FileSpec &stdout_file_spec,
48 const FileSpec &stderr_file_spec,
49 const FileSpec &working_directory,
Kate Stoneb9c1b512016-09-06 20:57:50 +000050 uint32_t launch_flags)
51 : ProcessInfo(), m_working_dir(), m_plugin_name(), m_flags(launch_flags),
Pavel Labath07d6f882017-12-11 10:09:14 +000052 m_file_actions(), m_pty(new PseudoTerminal), m_resume_count(0),
53 m_monitor_callback(nullptr), m_monitor_callback_baton(nullptr),
54 m_monitor_signals(false), m_listener_sp(), m_hijack_listener_sp() {
Kate Stoneb9c1b512016-09-06 20:57:50 +000055 if (stdin_file_spec) {
Todd Fiala6d6b55d2014-06-30 00:30:53 +000056 FileAction file_action;
Kate Stoneb9c1b512016-09-06 20:57:50 +000057 const bool read = true;
58 const bool write = false;
59 if (file_action.Open(STDIN_FILENO, stdin_file_spec, read, write))
60 AppendFileAction(file_action);
61 }
62 if (stdout_file_spec) {
Todd Fiala6d6b55d2014-06-30 00:30:53 +000063 FileAction file_action;
Kate Stoneb9c1b512016-09-06 20:57:50 +000064 const bool read = false;
65 const bool write = true;
66 if (file_action.Open(STDOUT_FILENO, stdout_file_spec, read, write))
67 AppendFileAction(file_action);
68 }
69 if (stderr_file_spec) {
Todd Fiala6d6b55d2014-06-30 00:30:53 +000070 FileAction file_action;
Kate Stoneb9c1b512016-09-06 20:57:50 +000071 const bool read = false;
72 const bool write = true;
73 if (file_action.Open(STDERR_FILENO, stderr_file_spec, read, write))
74 AppendFileAction(file_action);
75 }
76 if (working_directory)
77 SetWorkingDirectory(working_directory);
Todd Fiala6d6b55d2014-06-30 00:30:53 +000078}
79
Kate Stoneb9c1b512016-09-06 20:57:50 +000080bool ProcessLaunchInfo::AppendCloseFileAction(int fd) {
81 FileAction file_action;
82 if (file_action.Close(fd)) {
83 AppendFileAction(file_action);
84 return true;
85 }
86 return false;
Todd Fiala6d6b55d2014-06-30 00:30:53 +000087}
88
Kate Stoneb9c1b512016-09-06 20:57:50 +000089bool ProcessLaunchInfo::AppendDuplicateFileAction(int fd, int dup_fd) {
90 FileAction file_action;
91 if (file_action.Duplicate(fd, dup_fd)) {
92 AppendFileAction(file_action);
93 return true;
94 }
95 return false;
Todd Fiala6d6b55d2014-06-30 00:30:53 +000096}
97
Kate Stoneb9c1b512016-09-06 20:57:50 +000098bool ProcessLaunchInfo::AppendOpenFileAction(int fd, const FileSpec &file_spec,
99 bool read, bool write) {
100 FileAction file_action;
101 if (file_action.Open(fd, file_spec, read, write)) {
102 AppendFileAction(file_action);
103 return true;
104 }
105 return false;
Todd Fiala6d6b55d2014-06-30 00:30:53 +0000106}
107
Kate Stoneb9c1b512016-09-06 20:57:50 +0000108bool ProcessLaunchInfo::AppendSuppressFileAction(int fd, bool read,
109 bool write) {
110 FileAction file_action;
Jonas Devlieghere8f3be7a2018-11-01 21:05:36 +0000111 if (file_action.Open(fd, FileSpec(FileSystem::DEV_NULL), read, write)) {
Kate Stoneb9c1b512016-09-06 20:57:50 +0000112 AppendFileAction(file_action);
113 return true;
114 }
115 return false;
Todd Fiala6d6b55d2014-06-30 00:30:53 +0000116}
117
Kate Stoneb9c1b512016-09-06 20:57:50 +0000118const FileAction *ProcessLaunchInfo::GetFileActionAtIndex(size_t idx) const {
119 if (idx < m_file_actions.size())
120 return &m_file_actions[idx];
121 return nullptr;
Todd Fiala6d6b55d2014-06-30 00:30:53 +0000122}
123
Kate Stoneb9c1b512016-09-06 20:57:50 +0000124const FileAction *ProcessLaunchInfo::GetFileActionForFD(int fd) const {
125 for (size_t idx = 0, count = m_file_actions.size(); idx < count; ++idx) {
126 if (m_file_actions[idx].GetFD() == fd)
127 return &m_file_actions[idx];
128 }
129 return nullptr;
Todd Fiala6d6b55d2014-06-30 00:30:53 +0000130}
131
Kate Stoneb9c1b512016-09-06 20:57:50 +0000132const FileSpec &ProcessLaunchInfo::GetWorkingDirectory() const {
133 return m_working_dir;
Todd Fiala6d6b55d2014-06-30 00:30:53 +0000134}
135
Kate Stoneb9c1b512016-09-06 20:57:50 +0000136void ProcessLaunchInfo::SetWorkingDirectory(const FileSpec &working_dir) {
137 m_working_dir = working_dir;
Todd Fiala6d6b55d2014-06-30 00:30:53 +0000138}
139
Kate Stoneb9c1b512016-09-06 20:57:50 +0000140const char *ProcessLaunchInfo::GetProcessPluginName() const {
141 return (m_plugin_name.empty() ? nullptr : m_plugin_name.c_str());
Todd Fiala6d6b55d2014-06-30 00:30:53 +0000142}
143
Zachary Turnerfe114832016-11-12 16:56:47 +0000144void ProcessLaunchInfo::SetProcessPluginName(llvm::StringRef plugin) {
145 m_plugin_name = plugin;
Todd Fiala6d6b55d2014-06-30 00:30:53 +0000146}
147
Kate Stoneb9c1b512016-09-06 20:57:50 +0000148const FileSpec &ProcessLaunchInfo::GetShell() const { return m_shell; }
149
150void ProcessLaunchInfo::SetShell(const FileSpec &shell) {
151 m_shell = shell;
152 if (m_shell) {
Jonas Devlieghere2c22c802018-11-01 17:09:22 +0000153 FileSystem::Instance().ResolveExecutableLocation(m_shell);
Kate Stoneb9c1b512016-09-06 20:57:50 +0000154 m_flags.Set(lldb::eLaunchFlagLaunchInShell);
155 } else
156 m_flags.Clear(lldb::eLaunchFlagLaunchInShell);
Todd Fiala6d6b55d2014-06-30 00:30:53 +0000157}
158
Kate Stoneb9c1b512016-09-06 20:57:50 +0000159void ProcessLaunchInfo::SetLaunchInSeparateProcessGroup(bool separate) {
160 if (separate)
161 m_flags.Set(lldb::eLaunchFlagLaunchInSeparateProcessGroup);
162 else
163 m_flags.Clear(lldb::eLaunchFlagLaunchInSeparateProcessGroup);
164}
165
166void ProcessLaunchInfo::SetShellExpandArguments(bool expand) {
167 if (expand)
168 m_flags.Set(lldb::eLaunchFlagShellExpandArguments);
169 else
170 m_flags.Clear(lldb::eLaunchFlagShellExpandArguments);
171}
172
173void ProcessLaunchInfo::Clear() {
174 ProcessInfo::Clear();
175 m_working_dir.Clear();
176 m_plugin_name.clear();
177 m_shell.Clear();
178 m_flags.Clear();
179 m_file_actions.clear();
180 m_resume_count = 0;
181 m_listener_sp.reset();
182 m_hijack_listener_sp.reset();
183}
184
185void ProcessLaunchInfo::SetMonitorProcessCallback(
186 const Host::MonitorChildProcessCallback &callback, bool monitor_signals) {
187 m_monitor_callback = callback;
188 m_monitor_signals = monitor_signals;
189}
190
Pavel Labath245dd2e2018-05-15 13:42:26 +0000191bool ProcessLaunchInfo::NoOpMonitorCallback(lldb::pid_t pid, bool exited, int signal, int status) {
192 Log *log = lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_PROCESS);
193 LLDB_LOG(log, "pid = {0}, exited = {1}, signal = {2}, status = {3}", pid,
194 exited, signal, status);
195 return true;
196}
197
Kate Stoneb9c1b512016-09-06 20:57:50 +0000198bool ProcessLaunchInfo::MonitorProcess() const {
199 if (m_monitor_callback && ProcessIDIsValid()) {
200 Host::StartMonitoringChildProcess(m_monitor_callback, GetProcessID(),
201 m_monitor_signals);
202 return true;
203 }
204 return false;
205}
206
207void ProcessLaunchInfo::SetDetachOnError(bool enable) {
208 if (enable)
209 m_flags.Set(lldb::eLaunchFlagDetachOnError);
210 else
211 m_flags.Clear(lldb::eLaunchFlagDetachOnError);
212}
213
214void ProcessLaunchInfo::FinalizeFileActions(Target *target,
215 bool default_to_use_pty) {
216 Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_PROCESS));
217
218 // If nothing for stdin or stdout or stderr was specified, then check the
Adrian Prantl05097242018-04-30 16:49:04 +0000219 // process for any default settings that were set with "settings set"
Kate Stoneb9c1b512016-09-06 20:57:50 +0000220 if (GetFileActionForFD(STDIN_FILENO) == nullptr ||
221 GetFileActionForFD(STDOUT_FILENO) == nullptr ||
222 GetFileActionForFD(STDERR_FILENO) == nullptr) {
223 if (log)
224 log->Printf("ProcessLaunchInfo::%s at least one of stdin/stdout/stderr "
225 "was not set, evaluating default handling",
226 __FUNCTION__);
227
228 if (m_flags.Test(eLaunchFlagLaunchInTTY)) {
Adrian Prantl05097242018-04-30 16:49:04 +0000229 // Do nothing, if we are launching in a remote terminal no file actions
230 // should be done at all.
Kate Stoneb9c1b512016-09-06 20:57:50 +0000231 return;
Todd Fiala6d6b55d2014-06-30 00:30:53 +0000232 }
Todd Fiala6d6b55d2014-06-30 00:30:53 +0000233
Kate Stoneb9c1b512016-09-06 20:57:50 +0000234 if (m_flags.Test(eLaunchFlagDisableSTDIO)) {
235 if (log)
236 log->Printf("ProcessLaunchInfo::%s eLaunchFlagDisableSTDIO set, adding "
237 "suppression action for stdin, stdout and stderr",
238 __FUNCTION__);
239 AppendSuppressFileAction(STDIN_FILENO, true, false);
240 AppendSuppressFileAction(STDOUT_FILENO, false, true);
241 AppendSuppressFileAction(STDERR_FILENO, false, true);
242 } else {
Adrian Prantl05097242018-04-30 16:49:04 +0000243 // Check for any values that might have gotten set with any of: (lldb)
244 // settings set target.input-path (lldb) settings set target.output-path
Kate Stoneb9c1b512016-09-06 20:57:50 +0000245 // (lldb) settings set target.error-path
246 FileSpec in_file_spec;
247 FileSpec out_file_spec;
248 FileSpec err_file_spec;
249 if (target) {
Adrian Prantl05097242018-04-30 16:49:04 +0000250 // Only override with the target settings if we don't already have an
251 // action for in, out or error
Kate Stoneb9c1b512016-09-06 20:57:50 +0000252 if (GetFileActionForFD(STDIN_FILENO) == nullptr)
253 in_file_spec = target->GetStandardInputPath();
254 if (GetFileActionForFD(STDOUT_FILENO) == nullptr)
255 out_file_spec = target->GetStandardOutputPath();
256 if (GetFileActionForFD(STDERR_FILENO) == nullptr)
257 err_file_spec = target->GetStandardErrorPath();
258 }
Todd Fiala6d6b55d2014-06-30 00:30:53 +0000259
Kate Stoneb9c1b512016-09-06 20:57:50 +0000260 if (log)
261 log->Printf("ProcessLaunchInfo::%s target stdin='%s', target "
262 "stdout='%s', stderr='%s'",
263 __FUNCTION__,
264 in_file_spec ? in_file_spec.GetCString() : "<null>",
265 out_file_spec ? out_file_spec.GetCString() : "<null>",
266 err_file_spec ? err_file_spec.GetCString() : "<null>");
Todd Fiala75f47c32014-10-11 21:42:09 +0000267
Kate Stoneb9c1b512016-09-06 20:57:50 +0000268 if (in_file_spec) {
269 AppendOpenFileAction(STDIN_FILENO, in_file_spec, true, false);
Todd Fiala75f47c32014-10-11 21:42:09 +0000270 if (log)
Kate Stoneb9c1b512016-09-06 20:57:50 +0000271 log->Printf(
272 "ProcessLaunchInfo::%s appended stdin open file action for %s",
273 __FUNCTION__, in_file_spec.GetCString());
274 }
Todd Fiala75f47c32014-10-11 21:42:09 +0000275
Kate Stoneb9c1b512016-09-06 20:57:50 +0000276 if (out_file_spec) {
277 AppendOpenFileAction(STDOUT_FILENO, out_file_spec, false, true);
278 if (log)
279 log->Printf(
280 "ProcessLaunchInfo::%s appended stdout open file action for %s",
281 __FUNCTION__, out_file_spec.GetCString());
282 }
Greg Claytonbf91f712015-07-10 18:04:46 +0000283
Kate Stoneb9c1b512016-09-06 20:57:50 +0000284 if (err_file_spec) {
285 AppendOpenFileAction(STDERR_FILENO, err_file_spec, false, true);
286 if (log)
287 log->Printf(
288 "ProcessLaunchInfo::%s appended stderr open file action for %s",
289 __FUNCTION__, err_file_spec.GetCString());
290 }
Todd Fiala6d6b55d2014-06-30 00:30:53 +0000291
Kate Stoneb9c1b512016-09-06 20:57:50 +0000292 if (default_to_use_pty &&
293 (!in_file_spec || !out_file_spec || !err_file_spec)) {
294 if (log)
295 log->Printf("ProcessLaunchInfo::%s default_to_use_pty is set, and at "
296 "least one stdin/stderr/stdout is unset, so generating a "
297 "pty to use for it",
298 __FUNCTION__);
Todd Fiala75f47c32014-10-11 21:42:09 +0000299
Kate Stoneb9c1b512016-09-06 20:57:50 +0000300 int open_flags = O_RDWR | O_NOCTTY;
Hafiz Abid Qadeerf6ee79c2016-12-15 15:00:41 +0000301#if !defined(_WIN32)
Adrian Prantl05097242018-04-30 16:49:04 +0000302 // We really shouldn't be specifying platform specific flags that are
303 // intended for a system call in generic code. But this will have to
304 // do for now.
Kate Stoneb9c1b512016-09-06 20:57:50 +0000305 open_flags |= O_CLOEXEC;
Zachary Turner362a8132015-02-04 19:11:48 +0000306#endif
Kate Stoneb9c1b512016-09-06 20:57:50 +0000307 if (m_pty->OpenFirstAvailableMaster(open_flags, nullptr, 0)) {
Jonas Devlieghere8f3be7a2018-11-01 21:05:36 +0000308 const FileSpec slave_file_spec(m_pty->GetSlaveName(nullptr, 0));
Todd Fiala6d6b55d2014-06-30 00:30:53 +0000309
Kate Stoneb9c1b512016-09-06 20:57:50 +0000310 // Only use the slave tty if we don't have anything specified for
311 // input and don't have an action for stdin
312 if (!in_file_spec && GetFileActionForFD(STDIN_FILENO) == nullptr) {
313 AppendOpenFileAction(STDIN_FILENO, slave_file_spec, true, false);
314 }
Todd Fiala6d6b55d2014-06-30 00:30:53 +0000315
Kate Stoneb9c1b512016-09-06 20:57:50 +0000316 // Only use the slave tty if we don't have anything specified for
317 // output and don't have an action for stdout
318 if (!out_file_spec && GetFileActionForFD(STDOUT_FILENO) == nullptr) {
319 AppendOpenFileAction(STDOUT_FILENO, slave_file_spec, false, true);
320 }
Todd Fiala6d6b55d2014-06-30 00:30:53 +0000321
Kate Stoneb9c1b512016-09-06 20:57:50 +0000322 // Only use the slave tty if we don't have anything specified for
323 // error and don't have an action for stderr
324 if (!err_file_spec && GetFileActionForFD(STDERR_FILENO) == nullptr) {
325 AppendOpenFileAction(STDERR_FILENO, slave_file_spec, false, true);
326 }
Todd Fiala6d6b55d2014-06-30 00:30:53 +0000327 }
Kate Stoneb9c1b512016-09-06 20:57:50 +0000328 }
Todd Fiala6d6b55d2014-06-30 00:30:53 +0000329 }
Kate Stoneb9c1b512016-09-06 20:57:50 +0000330 }
Todd Fiala6d6b55d2014-06-30 00:30:53 +0000331}
332
Kate Stoneb9c1b512016-09-06 20:57:50 +0000333bool ProcessLaunchInfo::ConvertArgumentsForLaunchingInShell(
Zachary Turner97206d52017-05-12 04:51:55 +0000334 Status &error, bool localhost, bool will_debug,
Kate Stoneb9c1b512016-09-06 20:57:50 +0000335 bool first_arg_is_full_shell_command, int32_t num_resumes) {
336 error.Clear();
Todd Fiala6d6b55d2014-06-30 00:30:53 +0000337
Kate Stoneb9c1b512016-09-06 20:57:50 +0000338 if (GetFlags().Test(eLaunchFlagLaunchInShell)) {
339 if (m_shell) {
340 std::string shell_executable = m_shell.GetPath();
Todd Fiala6d6b55d2014-06-30 00:30:53 +0000341
Kate Stoneb9c1b512016-09-06 20:57:50 +0000342 const char **argv = GetArguments().GetConstArgumentVector();
343 if (argv == nullptr || argv[0] == nullptr)
344 return false;
345 Args shell_arguments;
346 std::string safe_arg;
Zachary Turnerecbb0bb2016-09-19 17:54:06 +0000347 shell_arguments.AppendArgument(shell_executable);
Kate Stoneb9c1b512016-09-06 20:57:50 +0000348 const llvm::Triple &triple = GetArchitecture().GetTriple();
349 if (triple.getOS() == llvm::Triple::Win32 &&
350 !triple.isWindowsCygwinEnvironment())
Zachary Turnerecbb0bb2016-09-19 17:54:06 +0000351 shell_arguments.AppendArgument(llvm::StringRef("/C"));
Kate Stoneb9c1b512016-09-06 20:57:50 +0000352 else
Zachary Turnerecbb0bb2016-09-19 17:54:06 +0000353 shell_arguments.AppendArgument(llvm::StringRef("-c"));
Zachary Turner270e99a2014-12-08 21:36:42 +0000354
Kate Stoneb9c1b512016-09-06 20:57:50 +0000355 StreamString shell_command;
356 if (will_debug) {
Adrian Prantl05097242018-04-30 16:49:04 +0000357 // Add a modified PATH environment variable in case argv[0] is a
358 // relative path.
Kate Stoneb9c1b512016-09-06 20:57:50 +0000359 const char *argv0 = argv[0];
Jonas Devlieghere8f3be7a2018-11-01 21:05:36 +0000360 FileSpec arg_spec(argv0);
Kate Stoneb9c1b512016-09-06 20:57:50 +0000361 if (arg_spec.IsRelative()) {
Adrian Prantl05097242018-04-30 16:49:04 +0000362 // We have a relative path to our executable which may not work if we
363 // just try to run "a.out" (without it being converted to "./a.out")
Kate Stoneb9c1b512016-09-06 20:57:50 +0000364 FileSpec working_dir = GetWorkingDirectory();
365 // Be sure to put quotes around PATH's value in case any paths have
366 // spaces...
367 std::string new_path("PATH=\"");
368 const size_t empty_path_len = new_path.size();
Todd Fiala6d6b55d2014-06-30 00:30:53 +0000369
Kate Stoneb9c1b512016-09-06 20:57:50 +0000370 if (working_dir) {
371 new_path += working_dir.GetPath();
372 } else {
Pavel Labath1d5855b2017-01-23 15:56:45 +0000373 llvm::SmallString<64> cwd;
374 if (! llvm::sys::fs::current_path(cwd))
Kate Stoneb9c1b512016-09-06 20:57:50 +0000375 new_path += cwd;
376 }
377 std::string curr_path;
378 if (HostInfo::GetEnvironmentVar("PATH", curr_path)) {
379 if (new_path.size() > empty_path_len)
380 new_path += ':';
381 new_path += curr_path;
382 }
383 new_path += "\" ";
Malcolm Parsons771ef6d2016-11-02 20:34:10 +0000384 shell_command.PutCString(new_path);
Todd Fiala6d6b55d2014-06-30 00:30:53 +0000385 }
Kate Stoneb9c1b512016-09-06 20:57:50 +0000386
387 if (triple.getOS() != llvm::Triple::Win32 ||
388 triple.isWindowsCygwinEnvironment())
389 shell_command.PutCString("exec");
390
391 // Only Apple supports /usr/bin/arch being able to specify the
392 // architecture
393 if (GetArchitecture().IsValid() && // Valid architecture
394 GetArchitecture().GetTriple().getVendor() ==
395 llvm::Triple::Apple && // Apple only
396 GetArchitecture().GetCore() !=
397 ArchSpec::eCore_x86_64_x86_64h) // Don't do this for x86_64h
398 {
399 shell_command.Printf(" /usr/bin/arch -arch %s",
400 GetArchitecture().GetArchitectureName());
401 // Set the resume count to 2:
402 // 1 - stop in shell
403 // 2 - stop in /usr/bin/arch
404 // 3 - then we will stop in our program
405 SetResumeCount(num_resumes + 1);
406 } else {
407 // Set the resume count to 1:
408 // 1 - stop in shell
409 // 2 - then we will stop in our program
410 SetResumeCount(num_resumes);
411 }
412 }
413
414 if (first_arg_is_full_shell_command) {
Adrian Prantl05097242018-04-30 16:49:04 +0000415 // There should only be one argument that is the shell command itself
416 // to be used as is
Kate Stoneb9c1b512016-09-06 20:57:50 +0000417 if (argv[0] && !argv[1])
418 shell_command.Printf("%s", argv[0]);
Todd Fiala6d6b55d2014-06-30 00:30:53 +0000419 else
Kate Stoneb9c1b512016-09-06 20:57:50 +0000420 return false;
421 } else {
422 for (size_t i = 0; argv[i] != nullptr; ++i) {
423 const char *arg =
424 Args::GetShellSafeArgument(m_shell, argv[i], safe_arg);
425 shell_command.Printf(" %s", arg);
Todd Fiala6d6b55d2014-06-30 00:30:53 +0000426 }
Kate Stoneb9c1b512016-09-06 20:57:50 +0000427 }
Zachary Turnerecbb0bb2016-09-19 17:54:06 +0000428 shell_arguments.AppendArgument(shell_command.GetString());
Kate Stoneb9c1b512016-09-06 20:57:50 +0000429 m_executable = m_shell;
430 m_arguments = shell_arguments;
431 return true;
432 } else {
433 error.SetErrorString("invalid shell path");
Todd Fiala6d6b55d2014-06-30 00:30:53 +0000434 }
Kate Stoneb9c1b512016-09-06 20:57:50 +0000435 } else {
436 error.SetErrorString("not launching in shell");
437 }
438 return false;
Todd Fiala6d6b55d2014-06-30 00:30:53 +0000439}
Greg Clayton8012cad2014-11-17 19:39:20 +0000440
Kate Stoneb9c1b512016-09-06 20:57:50 +0000441ListenerSP ProcessLaunchInfo::GetListenerForProcess(Debugger &debugger) {
442 if (m_listener_sp)
443 return m_listener_sp;
444 else
445 return debugger.GetListener();
Greg Clayton8012cad2014-11-17 19:39:20 +0000446}