blob: cc8070d437c27b3cda1f0b8af6a17bfd30cf02c1 [file] [log] [blame]
Greg Claytone4b9c1f2011-03-08 22:40:15 +00001//===-- Platform.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
10#include "lldb/Target/Platform.h"
11
12// C Includes
13// C++ Includes
14// Other libraries and framework includes
15// Project includes
16#include "lldb/Core/Error.h"
Greg Claytonb72d0f02011-04-12 05:54:46 +000017#include "lldb/Core/Log.h"
Greg Claytone4b9c1f2011-03-08 22:40:15 +000018#include "lldb/Core/PluginManager.h"
19#include "lldb/Host/FileSpec.h"
Greg Claytonb1888f22011-03-19 01:12:21 +000020#include "lldb/Host/Host.h"
Greg Claytonb72d0f02011-04-12 05:54:46 +000021#include "lldb/Target/Process.h"
Greg Claytone4b9c1f2011-03-08 22:40:15 +000022#include "lldb/Target/Target.h"
23
24using namespace lldb;
25using namespace lldb_private;
26
27// Use a singleton function for g_local_platform_sp to avoid init
28// constructors since LLDB is often part of a shared library
29static PlatformSP&
30GetDefaultPlatformSP ()
31{
32 static PlatformSP g_default_platform_sp;
33 return g_default_platform_sp;
34}
35
Greg Claytone4b9c1f2011-03-08 22:40:15 +000036static Mutex &
37GetConnectedPlatformListMutex ()
38{
39 static Mutex g_remote_connected_platforms_mutex (Mutex::eMutexTypeRecursive);
40 return g_remote_connected_platforms_mutex;
41}
42static std::vector<PlatformSP> &
43GetConnectedPlatformList ()
44{
45 static std::vector<PlatformSP> g_remote_connected_platforms;
46 return g_remote_connected_platforms;
47}
48
Greg Clayton5e342f52011-04-13 22:47:15 +000049
50const char *
51Platform::GetHostPlatformName ()
52{
53 return "host";
54}
55
Greg Claytone4b9c1f2011-03-08 22:40:15 +000056//------------------------------------------------------------------
57/// Get the native host platform plug-in.
58///
59/// There should only be one of these for each host that LLDB runs
60/// upon that should be statically compiled in and registered using
61/// preprocessor macros or other similar build mechanisms.
62///
63/// This platform will be used as the default platform when launching
64/// or attaching to processes unless another platform is specified.
65//------------------------------------------------------------------
66PlatformSP
67Platform::GetDefaultPlatform ()
68{
69 return GetDefaultPlatformSP ();
70}
71
72void
73Platform::SetDefaultPlatform (const lldb::PlatformSP &platform_sp)
74{
75 // The native platform should use its static void Platform::Initialize()
76 // function to register itself as the native platform.
77 GetDefaultPlatformSP () = platform_sp;
78}
79
Greg Claytone4b9c1f2011-03-08 22:40:15 +000080Error
Greg Claytoncb8977d2011-03-23 00:09:55 +000081Platform::GetFile (const FileSpec &platform_file,
82 const UUID *uuid_ptr,
83 FileSpec &local_file)
Greg Claytone4b9c1f2011-03-08 22:40:15 +000084{
85 // Default to the local case
86 local_file = platform_file;
87 return Error();
88}
89
Greg Clayton24bc5d92011-03-30 18:16:51 +000090Error
Greg Clayton444fe992012-02-26 05:51:37 +000091Platform::GetSharedModule (const ModuleSpec &module_spec,
Greg Clayton24bc5d92011-03-30 18:16:51 +000092 ModuleSP &module_sp,
Greg Clayton9ce95382012-02-13 23:10:39 +000093 const FileSpecList *module_search_paths_ptr,
Greg Clayton24bc5d92011-03-30 18:16:51 +000094 ModuleSP *old_module_sp_ptr,
95 bool *did_create_ptr)
96{
97 // Don't do any path remapping for the default implementation
98 // of the platform GetSharedModule function, just call through
99 // to our static ModuleList function. Platform subclasses that
100 // implement remote debugging, might have a developer kits
101 // installed that have cached versions of the files for the
102 // remote target, or might implement a download and cache
103 // locally implementation.
104 const bool always_create = false;
Greg Clayton444fe992012-02-26 05:51:37 +0000105 return ModuleList::GetSharedModule (module_spec,
Greg Clayton24bc5d92011-03-30 18:16:51 +0000106 module_sp,
Greg Clayton9ce95382012-02-13 23:10:39 +0000107 module_search_paths_ptr,
Greg Clayton24bc5d92011-03-30 18:16:51 +0000108 old_module_sp_ptr,
109 did_create_ptr,
110 always_create);
111}
112
Greg Claytone4b9c1f2011-03-08 22:40:15 +0000113PlatformSP
Greg Claytonb1888f22011-03-19 01:12:21 +0000114Platform::Create (const char *platform_name, Error &error)
Greg Claytone4b9c1f2011-03-08 22:40:15 +0000115{
116 PlatformCreateInstance create_callback = NULL;
117 lldb::PlatformSP platform_sp;
Greg Claytonb1888f22011-03-19 01:12:21 +0000118 if (platform_name && platform_name[0])
Greg Claytone4b9c1f2011-03-08 22:40:15 +0000119 {
120 create_callback = PluginManager::GetPlatformCreateCallbackForPluginName (platform_name);
121 if (create_callback)
Greg Claytonb1db6582012-03-20 18:34:04 +0000122 platform_sp.reset(create_callback(true, NULL));
Greg Claytone4b9c1f2011-03-08 22:40:15 +0000123 else
Greg Claytonb1888f22011-03-19 01:12:21 +0000124 error.SetErrorStringWithFormat ("unable to find a plug-in for the platform named \"%s\"", platform_name);
Greg Claytone4b9c1f2011-03-08 22:40:15 +0000125 }
126 else
Greg Claytonb1888f22011-03-19 01:12:21 +0000127 error.SetErrorString ("invalid platform name");
Greg Claytone4b9c1f2011-03-08 22:40:15 +0000128 return platform_sp;
129}
130
Greg Claytonb1db6582012-03-20 18:34:04 +0000131
132PlatformSP
133Platform::Create (const ArchSpec &arch, Error &error)
134{
135 lldb::PlatformSP platform_sp;
136 if (arch.IsValid())
137 {
138 PlatformCreateInstance create_callback;
139 for (uint32_t idx = 0; (create_callback = PluginManager::GetPlatformCreateCallbackAtIndex (idx)); ++idx)
140 {
141 if (create_callback)
142 platform_sp.reset(create_callback(false, &arch));
143 if (platform_sp && platform_sp->IsCompatibleWithArchitecture(arch))
144 break;
145 }
146 }
147 else
148 error.SetErrorString ("invalid platform name");
149 return platform_sp;
150}
151
Greg Claytone4b9c1f2011-03-08 22:40:15 +0000152uint32_t
153Platform::GetNumConnectedRemotePlatforms ()
154{
155 Mutex::Locker locker (GetConnectedPlatformListMutex ());
156 return GetConnectedPlatformList().size();
157}
158
159PlatformSP
160Platform::GetConnectedRemotePlatformAtIndex (uint32_t idx)
161{
162 PlatformSP platform_sp;
163 {
164 Mutex::Locker locker (GetConnectedPlatformListMutex ());
165 if (idx < GetConnectedPlatformList().size())
166 platform_sp = GetConnectedPlatformList ()[idx];
167 }
168 return platform_sp;
169}
170
171//------------------------------------------------------------------
172/// Default Constructor
173//------------------------------------------------------------------
Greg Claytonb1888f22011-03-19 01:12:21 +0000174Platform::Platform (bool is_host) :
175 m_is_host (is_host),
Greg Claytonb1888f22011-03-19 01:12:21 +0000176 m_os_version_set_while_connected (false),
177 m_system_arch_set_while_connected (false),
Greg Clayton604f0d32011-06-17 03:31:01 +0000178 m_sdk_sysroot (),
179 m_sdk_build (),
Greg Claytonb1888f22011-03-19 01:12:21 +0000180 m_remote_url (),
Greg Clayton58e26e02011-03-24 04:28:38 +0000181 m_name (),
Greg Claytonb1888f22011-03-19 01:12:21 +0000182 m_major_os_version (UINT32_MAX),
183 m_minor_os_version (UINT32_MAX),
Greg Clayton24bc5d92011-03-30 18:16:51 +0000184 m_update_os_version (UINT32_MAX),
185 m_system_arch(),
186 m_uid_map_mutex (Mutex::eMutexTypeNormal),
187 m_gid_map_mutex (Mutex::eMutexTypeNormal),
188 m_uid_map(),
189 m_gid_map(),
190 m_max_uid_name_len (0),
191 m_max_gid_name_len (0)
Greg Claytone4b9c1f2011-03-08 22:40:15 +0000192{
Greg Claytonb72d0f02011-04-12 05:54:46 +0000193 LogSP log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_OBJECT));
194 if (log)
195 log->Printf ("%p Platform::Platform()", this);
Greg Claytone4b9c1f2011-03-08 22:40:15 +0000196}
197
198//------------------------------------------------------------------
199/// Destructor.
200///
201/// The destructor is virtual since this class is designed to be
202/// inherited from by the plug-in instance.
203//------------------------------------------------------------------
204Platform::~Platform()
205{
Greg Claytonb72d0f02011-04-12 05:54:46 +0000206 LogSP log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_OBJECT));
207 if (log)
208 log->Printf ("%p Platform::~Platform()", this);
Greg Claytone4b9c1f2011-03-08 22:40:15 +0000209}
210
Greg Clayton58e26e02011-03-24 04:28:38 +0000211void
212Platform::GetStatus (Stream &strm)
213{
214 uint32_t major = UINT32_MAX;
215 uint32_t minor = UINT32_MAX;
216 uint32_t update = UINT32_MAX;
217 std::string s;
Greg Clayton24bc5d92011-03-30 18:16:51 +0000218 strm.Printf (" Platform: %s\n", GetShortPluginName());
Greg Clayton58e26e02011-03-24 04:28:38 +0000219
220 ArchSpec arch (GetSystemArchitecture());
221 if (arch.IsValid())
222 {
223 if (!arch.GetTriple().str().empty())
Greg Clayton24bc5d92011-03-30 18:16:51 +0000224 strm.Printf(" Triple: %s\n", arch.GetTriple().str().c_str());
Greg Clayton58e26e02011-03-24 04:28:38 +0000225 }
226
227 if (GetOSVersion(major, minor, update))
228 {
Greg Clayton24bc5d92011-03-30 18:16:51 +0000229 strm.Printf("OS Version: %u", major);
Greg Clayton58e26e02011-03-24 04:28:38 +0000230 if (minor != UINT32_MAX)
231 strm.Printf(".%u", minor);
232 if (update != UINT32_MAX)
233 strm.Printf(".%u", update);
234
235 if (GetOSBuildString (s))
236 strm.Printf(" (%s)", s.c_str());
237
238 strm.EOL();
239 }
240
241 if (GetOSKernelDescription (s))
Greg Clayton24bc5d92011-03-30 18:16:51 +0000242 strm.Printf(" Kernel: %s\n", s.c_str());
Greg Clayton58e26e02011-03-24 04:28:38 +0000243
244 if (IsHost())
245 {
Greg Clayton24bc5d92011-03-30 18:16:51 +0000246 strm.Printf(" Hostname: %s\n", GetHostname());
Greg Clayton58e26e02011-03-24 04:28:38 +0000247 }
248 else
249 {
Greg Clayton24bc5d92011-03-30 18:16:51 +0000250 const bool is_connected = IsConnected();
251 if (is_connected)
252 strm.Printf(" Hostname: %s\n", GetHostname());
253 strm.Printf(" Connected: %s\n", is_connected ? "yes" : "no");
Greg Clayton58e26e02011-03-24 04:28:38 +0000254 }
255}
256
Greg Claytonb1888f22011-03-19 01:12:21 +0000257
258bool
259Platform::GetOSVersion (uint32_t &major,
260 uint32_t &minor,
261 uint32_t &update)
262{
263 bool success = m_major_os_version != UINT32_MAX;
264 if (IsHost())
265 {
266 if (!success)
267 {
268 // We have a local host platform
269 success = Host::GetOSVersion (m_major_os_version,
270 m_minor_os_version,
271 m_update_os_version);
272 m_os_version_set_while_connected = success;
273 }
274 }
275 else
276 {
277 // We have a remote platform. We can only fetch the remote
278 // OS version if we are connected, and we don't want to do it
279 // more than once.
280
281 const bool is_connected = IsConnected();
282
Greg Clayton58e26e02011-03-24 04:28:38 +0000283 bool fetch = false;
Greg Claytonb1888f22011-03-19 01:12:21 +0000284 if (success)
285 {
286 // We have valid OS version info, check to make sure it wasn't
287 // manually set prior to connecting. If it was manually set prior
288 // to connecting, then lets fetch the actual OS version info
289 // if we are now connected.
290 if (is_connected && !m_os_version_set_while_connected)
Greg Clayton58e26e02011-03-24 04:28:38 +0000291 fetch = true;
Greg Claytonb1888f22011-03-19 01:12:21 +0000292 }
293 else
294 {
295 // We don't have valid OS version info, fetch it if we are connected
Greg Clayton58e26e02011-03-24 04:28:38 +0000296 fetch = is_connected;
Greg Claytonb1888f22011-03-19 01:12:21 +0000297 }
298
Greg Clayton58e26e02011-03-24 04:28:38 +0000299 if (fetch)
Greg Claytonb1888f22011-03-19 01:12:21 +0000300 {
Greg Clayton58e26e02011-03-24 04:28:38 +0000301 success = GetRemoteOSVersion ();
Greg Claytonb1888f22011-03-19 01:12:21 +0000302 m_os_version_set_while_connected = success;
303 }
304 }
305
306 if (success)
307 {
308 major = m_major_os_version;
309 minor = m_minor_os_version;
310 update = m_update_os_version;
311 }
312 return success;
313}
Greg Clayton58e26e02011-03-24 04:28:38 +0000314
315bool
316Platform::GetOSBuildString (std::string &s)
317{
318 if (IsHost())
319 return Host::GetOSBuildString (s);
320 else
321 return GetRemoteOSBuildString (s);
322}
323
324bool
325Platform::GetOSKernelDescription (std::string &s)
326{
327 if (IsHost())
328 return Host::GetOSKernelDescription (s);
329 else
330 return GetRemoteOSKernelDescription (s);
331}
332
333const char *
Greg Claytonb72d0f02011-04-12 05:54:46 +0000334Platform::GetName ()
335{
336 const char *name = GetHostname();
337 if (name == NULL || name[0] == '\0')
338 name = GetShortPluginName();
339 return name;
340}
341
342const char *
Greg Clayton58e26e02011-03-24 04:28:38 +0000343Platform::GetHostname ()
344{
Greg Clayton5e342f52011-04-13 22:47:15 +0000345 if (IsHost())
346 return "localhost";
Greg Clayton24bc5d92011-03-30 18:16:51 +0000347
348 if (m_name.empty())
349 return NULL;
350 return m_name.c_str();
351}
352
353const char *
354Platform::GetUserName (uint32_t uid)
355{
356 const char *user_name = GetCachedUserName(uid);
357 if (user_name)
358 return user_name;
359 if (IsHost())
360 {
361 std::string name;
362 if (Host::GetUserName(uid, name))
363 return SetCachedUserName (uid, name.c_str(), name.size());
364 }
Greg Clayton58e26e02011-03-24 04:28:38 +0000365 return NULL;
366}
367
Greg Clayton24bc5d92011-03-30 18:16:51 +0000368const char *
369Platform::GetGroupName (uint32_t gid)
370{
371 const char *group_name = GetCachedGroupName(gid);
372 if (group_name)
373 return group_name;
374 if (IsHost())
375 {
376 std::string name;
377 if (Host::GetGroupName(gid, name))
378 return SetCachedGroupName (gid, name.c_str(), name.size());
379 }
380 return NULL;
381}
Greg Clayton58e26e02011-03-24 04:28:38 +0000382
Greg Claytonb1888f22011-03-19 01:12:21 +0000383bool
384Platform::SetOSVersion (uint32_t major,
385 uint32_t minor,
386 uint32_t update)
387{
388 if (IsHost())
389 {
390 // We don't need anyone setting the OS version for the host platform,
391 // we should be able to figure it out by calling Host::GetOSVersion(...).
392 return false;
393 }
394 else
395 {
396 // We have a remote platform, allow setting the target OS version if
397 // we aren't connected, since if we are connected, we should be able to
398 // request the remote OS version from the connected platform.
399 if (IsConnected())
400 return false;
401 else
402 {
403 // We aren't connected and we might want to set the OS version
404 // ahead of time before we connect so we can peruse files and
405 // use a local SDK or PDK cache of support files to disassemble
406 // or do other things.
407 m_major_os_version = major;
408 m_minor_os_version = minor;
409 m_update_os_version = update;
410 return true;
411 }
412 }
413 return false;
414}
415
416
Greg Claytone4b9c1f2011-03-08 22:40:15 +0000417Error
418Platform::ResolveExecutable (const FileSpec &exe_file,
419 const ArchSpec &exe_arch,
Greg Clayton9ce95382012-02-13 23:10:39 +0000420 lldb::ModuleSP &exe_module_sp,
421 const FileSpecList *module_search_paths_ptr)
Greg Claytone4b9c1f2011-03-08 22:40:15 +0000422{
423 Error error;
424 if (exe_file.Exists())
425 {
Greg Clayton444fe992012-02-26 05:51:37 +0000426 ModuleSpec module_spec (exe_file, exe_arch);
427 if (module_spec.GetArchitecture().IsValid())
Greg Claytone4b9c1f2011-03-08 22:40:15 +0000428 {
Greg Clayton444fe992012-02-26 05:51:37 +0000429 error = ModuleList::GetSharedModule (module_spec,
Greg Claytone4b9c1f2011-03-08 22:40:15 +0000430 exe_module_sp,
Greg Clayton9ce95382012-02-13 23:10:39 +0000431 module_search_paths_ptr,
Greg Claytone4b9c1f2011-03-08 22:40:15 +0000432 NULL,
433 NULL);
434 }
435 else
436 {
437 // No valid architecture was specified, ask the platform for
438 // the architectures that we should be using (in the correct order)
439 // and see if we can find a match that way
Greg Clayton444fe992012-02-26 05:51:37 +0000440 for (uint32_t idx = 0; GetSupportedArchitectureAtIndex (idx, module_spec.GetArchitecture()); ++idx)
Greg Claytone4b9c1f2011-03-08 22:40:15 +0000441 {
Greg Clayton444fe992012-02-26 05:51:37 +0000442 error = ModuleList::GetSharedModule (module_spec,
Greg Claytone4b9c1f2011-03-08 22:40:15 +0000443 exe_module_sp,
Greg Clayton9ce95382012-02-13 23:10:39 +0000444 module_search_paths_ptr,
Greg Claytone4b9c1f2011-03-08 22:40:15 +0000445 NULL,
446 NULL);
447 // Did we find an executable using one of the
448 if (error.Success() && exe_module_sp)
449 break;
450 }
451 }
452 }
453 else
454 {
455 error.SetErrorStringWithFormat ("'%s%s%s' does not exist",
456 exe_file.GetDirectory().AsCString(""),
457 exe_file.GetDirectory() ? "/" : "",
458 exe_file.GetFilename().AsCString(""));
459 }
460 return error;
461}
462
Greg Claytonf2bf8702011-08-11 16:25:18 +0000463bool
464Platform::ResolveRemotePath (const FileSpec &platform_path,
465 FileSpec &resolved_platform_path)
466{
467 resolved_platform_path = platform_path;
468 return resolved_platform_path.ResolvePath();
469}
470
Greg Claytonb1888f22011-03-19 01:12:21 +0000471
472const ArchSpec &
473Platform::GetSystemArchitecture()
474{
475 if (IsHost())
476 {
477 if (!m_system_arch.IsValid())
478 {
479 // We have a local host platform
480 m_system_arch = Host::GetArchitecture();
481 m_system_arch_set_while_connected = m_system_arch.IsValid();
482 }
483 }
484 else
485 {
486 // We have a remote platform. We can only fetch the remote
487 // system architecture if we are connected, and we don't want to do it
488 // more than once.
489
490 const bool is_connected = IsConnected();
491
492 bool fetch = false;
493 if (m_system_arch.IsValid())
494 {
495 // We have valid OS version info, check to make sure it wasn't
496 // manually set prior to connecting. If it was manually set prior
497 // to connecting, then lets fetch the actual OS version info
498 // if we are now connected.
499 if (is_connected && !m_system_arch_set_while_connected)
500 fetch = true;
501 }
502 else
503 {
504 // We don't have valid OS version info, fetch it if we are connected
505 fetch = is_connected;
506 }
507
508 if (fetch)
509 {
Greg Clayton58e26e02011-03-24 04:28:38 +0000510 m_system_arch = GetRemoteSystemArchitecture ();
Greg Claytonb1888f22011-03-19 01:12:21 +0000511 m_system_arch_set_while_connected = m_system_arch.IsValid();
512 }
513 }
514 return m_system_arch;
515}
516
517
Greg Claytone4b9c1f2011-03-08 22:40:15 +0000518Error
Greg Claytoncb8977d2011-03-23 00:09:55 +0000519Platform::ConnectRemote (Args& args)
Greg Claytone4b9c1f2011-03-08 22:40:15 +0000520{
521 Error error;
Greg Claytoncb8977d2011-03-23 00:09:55 +0000522 if (IsHost())
523 error.SetErrorStringWithFormat ("The currently selected platform (%s) is the host platform and is always connected.", GetShortPluginName());
524 else
525 error.SetErrorStringWithFormat ("Platform::ConnectRemote() is not supported by %s", GetShortPluginName());
Greg Claytone4b9c1f2011-03-08 22:40:15 +0000526 return error;
527}
528
529Error
Greg Claytoncb8977d2011-03-23 00:09:55 +0000530Platform::DisconnectRemote ()
Greg Claytone4b9c1f2011-03-08 22:40:15 +0000531{
532 Error error;
Greg Claytoncb8977d2011-03-23 00:09:55 +0000533 if (IsHost())
534 error.SetErrorStringWithFormat ("The currently selected platform (%s) is the host platform and is always connected.", GetShortPluginName());
535 else
536 error.SetErrorStringWithFormat ("Platform::DisconnectRemote() is not supported by %s", GetShortPluginName());
Greg Claytone4b9c1f2011-03-08 22:40:15 +0000537 return error;
538}
Greg Clayton24bc5d92011-03-30 18:16:51 +0000539
540bool
Greg Claytonb72d0f02011-04-12 05:54:46 +0000541Platform::GetProcessInfo (lldb::pid_t pid, ProcessInstanceInfo &process_info)
Greg Clayton24bc5d92011-03-30 18:16:51 +0000542{
543 // Take care of the host case so that each subclass can just
Greg Claytonb72d0f02011-04-12 05:54:46 +0000544 // call this function to get the host functionality.
Greg Clayton24bc5d92011-03-30 18:16:51 +0000545 if (IsHost())
546 return Host::GetProcessInfo (pid, process_info);
547 return false;
548}
549
550uint32_t
Greg Claytonb72d0f02011-04-12 05:54:46 +0000551Platform::FindProcesses (const ProcessInstanceInfoMatch &match_info,
552 ProcessInstanceInfoList &process_infos)
Greg Clayton24bc5d92011-03-30 18:16:51 +0000553{
Greg Claytonb72d0f02011-04-12 05:54:46 +0000554 // Take care of the host case so that each subclass can just
555 // call this function to get the host functionality.
Greg Clayton24bc5d92011-03-30 18:16:51 +0000556 uint32_t match_count = 0;
557 if (IsHost())
558 match_count = Host::FindProcesses (match_info, process_infos);
559 return match_count;
560}
Greg Claytonb72d0f02011-04-12 05:54:46 +0000561
562
563Error
564Platform::LaunchProcess (ProcessLaunchInfo &launch_info)
565{
566 Error error;
567 // Take care of the host case so that each subclass can just
568 // call this function to get the host functionality.
569 if (IsHost())
570 error = Host::LaunchProcess (launch_info);
571 else
572 error.SetErrorString ("base lldb_private::Platform class can't launch remote processes");
573 return error;
574}
575
576lldb::ProcessSP
577Platform::DebugProcess (ProcessLaunchInfo &launch_info,
578 Debugger &debugger,
579 Target *target, // Can be NULL, if NULL create a new target, else use existing one
580 Listener &listener,
581 Error &error)
582{
583 ProcessSP process_sp;
584 // Make sure we stop at the entry point
585 launch_info.GetFlags ().Set (eLaunchFlagDebug);
586 error = LaunchProcess (launch_info);
587 if (error.Success())
588 {
Greg Clayton527154d2011-11-15 03:53:30 +0000589 if (launch_info.GetProcessID() != LLDB_INVALID_PROCESS_ID)
Greg Claytonb72d0f02011-04-12 05:54:46 +0000590 {
Greg Clayton527154d2011-11-15 03:53:30 +0000591 ProcessAttachInfo attach_info (launch_info);
592 process_sp = Attach (attach_info, debugger, target, listener, error);
Greg Claytonffa43a62011-11-17 04:46:02 +0000593 if (process_sp)
594 {
595 // Since we attached to the process, it will think it needs to detach
596 // if the process object just goes away without an explicit call to
597 // Process::Kill() or Process::Detach(), so let it know to kill the
598 // process if this happens.
599 process_sp->SetShouldDetach (false);
Greg Clayton464c6162011-11-17 22:14:31 +0000600
601 // If we didn't have any file actions, the pseudo terminal might
602 // have been used where the slave side was given as the file to
603 // open for stdin/out/err after we have already opened the master
604 // so we can read/write stdin/out/err.
605 int pty_fd = launch_info.GetPTY().ReleaseMasterFileDescriptor();
606 if (pty_fd != lldb_utility::PseudoTerminal::invalid_fd)
607 {
608 process_sp->SetSTDIOFileDescriptor(pty_fd);
609 }
Greg Claytonffa43a62011-11-17 04:46:02 +0000610 }
Greg Claytonb72d0f02011-04-12 05:54:46 +0000611 }
612 }
613 return process_sp;
614}
Greg Claytonb1db6582012-03-20 18:34:04 +0000615
616
617lldb::PlatformSP
618Platform::GetPlatformForArchitecture (const ArchSpec &arch)
619{
620 lldb::PlatformSP platform_sp;
621 Error error;
622 if (arch.IsValid())
623 platform_sp = Platform::Create (arch, error);
624 return platform_sp;
625}
626
627
628//------------------------------------------------------------------
629/// Lets a platform answer if it is compatible with a given
630/// architecture and the target triple contained within.
631//------------------------------------------------------------------
632bool
633Platform::IsCompatibleWithArchitecture (const ArchSpec &arch)
634{
635 // If the architecture is invalid, we must answer true...
636 if (!arch.IsValid())
637 return true;
638
639 ArchSpec platform_arch;
640 for (uint32_t arch_idx=0; GetSupportedArchitectureAtIndex (arch_idx, platform_arch); ++arch_idx)
641 {
642 if (arch == platform_arch)
643 return true;
644 }
645 return false;
646
647}
648
649