1cb8977d726be451df9978a74088435667fa37da2Greg Clayton//===-- PlatformRemoteGDBServer.cpp -----------------------------*- C++ -*-===//
2cb8977d726be451df9978a74088435667fa37da2Greg Clayton//
3cb8977d726be451df9978a74088435667fa37da2Greg Clayton//                     The LLVM Compiler Infrastructure
4cb8977d726be451df9978a74088435667fa37da2Greg Clayton//
5cb8977d726be451df9978a74088435667fa37da2Greg Clayton// This file is distributed under the University of Illinois Open Source
6cb8977d726be451df9978a74088435667fa37da2Greg Clayton// License. See LICENSE.TXT for details.
7cb8977d726be451df9978a74088435667fa37da2Greg Clayton//
8cb8977d726be451df9978a74088435667fa37da2Greg Clayton//===----------------------------------------------------------------------===//
9cb8977d726be451df9978a74088435667fa37da2Greg Clayton
10d891f9b872103235cfd2ed452c6f14a4394d9b3aDaniel Malea#include "lldb/lldb-python.h"
11d891f9b872103235cfd2ed452c6f14a4394d9b3aDaniel Malea
12cb8977d726be451df9978a74088435667fa37da2Greg Clayton#include "PlatformRemoteGDBServer.h"
13cb8977d726be451df9978a74088435667fa37da2Greg Clayton
14cb8977d726be451df9978a74088435667fa37da2Greg Clayton// C Includes
15cb8977d726be451df9978a74088435667fa37da2Greg Clayton#include <sys/sysctl.h>
16cb8977d726be451df9978a74088435667fa37da2Greg Clayton
17cb8977d726be451df9978a74088435667fa37da2Greg Clayton// C++ Includes
18cb8977d726be451df9978a74088435667fa37da2Greg Clayton// Other libraries and framework includes
19cb8977d726be451df9978a74088435667fa37da2Greg Clayton// Project includes
20cb8977d726be451df9978a74088435667fa37da2Greg Clayton#include "lldb/Breakpoint/BreakpointLocation.h"
2158e26e0935138225477fd61283215ceff2068899Greg Clayton#include "lldb/Core/ConnectionFileDescriptor.h"
22b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton#include "lldb/Core/Debugger.h"
2358e26e0935138225477fd61283215ceff2068899Greg Clayton#include "lldb/Core/Error.h"
24cb8977d726be451df9978a74088435667fa37da2Greg Clayton#include "lldb/Core/Module.h"
25cb8977d726be451df9978a74088435667fa37da2Greg Clayton#include "lldb/Core/ModuleList.h"
26cb8977d726be451df9978a74088435667fa37da2Greg Clayton#include "lldb/Core/PluginManager.h"
27cb8977d726be451df9978a74088435667fa37da2Greg Clayton#include "lldb/Core/StreamString.h"
28cb8977d726be451df9978a74088435667fa37da2Greg Clayton#include "lldb/Host/FileSpec.h"
29cb8977d726be451df9978a74088435667fa37da2Greg Clayton#include "lldb/Host/Host.h"
30cb8977d726be451df9978a74088435667fa37da2Greg Clayton#include "lldb/Target/Process.h"
31cb8977d726be451df9978a74088435667fa37da2Greg Clayton#include "lldb/Target/Target.h"
32cb8977d726be451df9978a74088435667fa37da2Greg Clayton
33cb8977d726be451df9978a74088435667fa37da2Greg Claytonusing namespace lldb;
34cb8977d726be451df9978a74088435667fa37da2Greg Claytonusing namespace lldb_private;
35cb8977d726be451df9978a74088435667fa37da2Greg Clayton
36cb8977d726be451df9978a74088435667fa37da2Greg Claytonstatic bool g_initialized = false;
37cb8977d726be451df9978a74088435667fa37da2Greg Clayton
38cb8977d726be451df9978a74088435667fa37da2Greg Claytonvoid
39cb8977d726be451df9978a74088435667fa37da2Greg ClaytonPlatformRemoteGDBServer::Initialize ()
40cb8977d726be451df9978a74088435667fa37da2Greg Clayton{
41cb8977d726be451df9978a74088435667fa37da2Greg Clayton    if (g_initialized == false)
42cb8977d726be451df9978a74088435667fa37da2Greg Clayton    {
43cb8977d726be451df9978a74088435667fa37da2Greg Clayton        g_initialized = true;
440e191607adcb0ea8ebd06c278be648a7f5c0097fGreg Clayton        PluginManager::RegisterPlugin (PlatformRemoteGDBServer::GetPluginNameStatic(),
45cb8977d726be451df9978a74088435667fa37da2Greg Clayton                                       PlatformRemoteGDBServer::GetDescriptionStatic(),
46cb8977d726be451df9978a74088435667fa37da2Greg Clayton                                       PlatformRemoteGDBServer::CreateInstance);
47cb8977d726be451df9978a74088435667fa37da2Greg Clayton    }
48cb8977d726be451df9978a74088435667fa37da2Greg Clayton}
49cb8977d726be451df9978a74088435667fa37da2Greg Clayton
50cb8977d726be451df9978a74088435667fa37da2Greg Claytonvoid
51cb8977d726be451df9978a74088435667fa37da2Greg ClaytonPlatformRemoteGDBServer::Terminate ()
52cb8977d726be451df9978a74088435667fa37da2Greg Clayton{
53cb8977d726be451df9978a74088435667fa37da2Greg Clayton    if (g_initialized)
54cb8977d726be451df9978a74088435667fa37da2Greg Clayton    {
55cb8977d726be451df9978a74088435667fa37da2Greg Clayton        g_initialized = false;
56cb8977d726be451df9978a74088435667fa37da2Greg Clayton        PluginManager::UnregisterPlugin (PlatformRemoteGDBServer::CreateInstance);
57cb8977d726be451df9978a74088435667fa37da2Greg Clayton    }
58cb8977d726be451df9978a74088435667fa37da2Greg Clayton}
59cb8977d726be451df9978a74088435667fa37da2Greg Clayton
60cb8977d726be451df9978a74088435667fa37da2Greg ClaytonPlatform*
61b1db658333cdebca31a128be95e926d80c3c7796Greg ClaytonPlatformRemoteGDBServer::CreateInstance (bool force, const lldb_private::ArchSpec *arch)
62cb8977d726be451df9978a74088435667fa37da2Greg Clayton{
63b170aee2daacc83e3d71c3e3acc9d56c89893a7bGreg Clayton    bool create = force;
64b170aee2daacc83e3d71c3e3acc9d56c89893a7bGreg Clayton    if (!create)
65b170aee2daacc83e3d71c3e3acc9d56c89893a7bGreg Clayton    {
66b170aee2daacc83e3d71c3e3acc9d56c89893a7bGreg Clayton        create = !arch->TripleVendorWasSpecified() && !arch->TripleOSWasSpecified();
67b170aee2daacc83e3d71c3e3acc9d56c89893a7bGreg Clayton    }
68b170aee2daacc83e3d71c3e3acc9d56c89893a7bGreg Clayton    if (create)
69b170aee2daacc83e3d71c3e3acc9d56c89893a7bGreg Clayton        return new PlatformRemoteGDBServer ();
70b170aee2daacc83e3d71c3e3acc9d56c89893a7bGreg Clayton    return NULL;
71cb8977d726be451df9978a74088435667fa37da2Greg Clayton}
72cb8977d726be451df9978a74088435667fa37da2Greg Clayton
73b170aee2daacc83e3d71c3e3acc9d56c89893a7bGreg Clayton
740e191607adcb0ea8ebd06c278be648a7f5c0097fGreg Claytonlldb_private::ConstString
750e191607adcb0ea8ebd06c278be648a7f5c0097fGreg ClaytonPlatformRemoteGDBServer::GetPluginNameStatic()
76cb8977d726be451df9978a74088435667fa37da2Greg Clayton{
770e191607adcb0ea8ebd06c278be648a7f5c0097fGreg Clayton    static ConstString g_name("remote-gdb-server");
780e191607adcb0ea8ebd06c278be648a7f5c0097fGreg Clayton    return g_name;
79cb8977d726be451df9978a74088435667fa37da2Greg Clayton}
80cb8977d726be451df9978a74088435667fa37da2Greg Clayton
81cb8977d726be451df9978a74088435667fa37da2Greg Claytonconst char *
82cb8977d726be451df9978a74088435667fa37da2Greg ClaytonPlatformRemoteGDBServer::GetDescriptionStatic()
83cb8977d726be451df9978a74088435667fa37da2Greg Clayton{
84cb8977d726be451df9978a74088435667fa37da2Greg Clayton    return "A platform that uses the GDB remote protocol as the communication transport.";
85cb8977d726be451df9978a74088435667fa37da2Greg Clayton}
86cb8977d726be451df9978a74088435667fa37da2Greg Clayton
87cb8977d726be451df9978a74088435667fa37da2Greg Claytonconst char *
88cb8977d726be451df9978a74088435667fa37da2Greg ClaytonPlatformRemoteGDBServer::GetDescription ()
89cb8977d726be451df9978a74088435667fa37da2Greg Clayton{
90cb8977d726be451df9978a74088435667fa37da2Greg Clayton    if (m_platform_description.empty())
91cb8977d726be451df9978a74088435667fa37da2Greg Clayton    {
92cb8977d726be451df9978a74088435667fa37da2Greg Clayton        if (IsConnected())
93cb8977d726be451df9978a74088435667fa37da2Greg Clayton        {
94cb8977d726be451df9978a74088435667fa37da2Greg Clayton            // Send the get description packet
95cb8977d726be451df9978a74088435667fa37da2Greg Clayton        }
96cb8977d726be451df9978a74088435667fa37da2Greg Clayton    }
97cb8977d726be451df9978a74088435667fa37da2Greg Clayton
98cb8977d726be451df9978a74088435667fa37da2Greg Clayton    if (!m_platform_description.empty())
99cb8977d726be451df9978a74088435667fa37da2Greg Clayton        return m_platform_description.c_str();
100cb8977d726be451df9978a74088435667fa37da2Greg Clayton    return GetDescriptionStatic();
101cb8977d726be451df9978a74088435667fa37da2Greg Clayton}
102cb8977d726be451df9978a74088435667fa37da2Greg Clayton
103cb8977d726be451df9978a74088435667fa37da2Greg ClaytonError
104cb8977d726be451df9978a74088435667fa37da2Greg ClaytonPlatformRemoteGDBServer::ResolveExecutable (const FileSpec &exe_file,
105cb8977d726be451df9978a74088435667fa37da2Greg Clayton                                            const ArchSpec &exe_arch,
1069ce953807eb814a93b449dc243de4f7bf32c3115Greg Clayton                                            lldb::ModuleSP &exe_module_sp,
1079ce953807eb814a93b449dc243de4f7bf32c3115Greg Clayton                                            const FileSpecList *module_search_paths_ptr)
108cb8977d726be451df9978a74088435667fa37da2Greg Clayton{
109cb8977d726be451df9978a74088435667fa37da2Greg Clayton    Error error;
110cb8977d726be451df9978a74088435667fa37da2Greg Clayton    error.SetErrorString ("PlatformRemoteGDBServer::ResolveExecutable() is unimplemented");
111cb8977d726be451df9978a74088435667fa37da2Greg Clayton    return error;
112cb8977d726be451df9978a74088435667fa37da2Greg Clayton}
113cb8977d726be451df9978a74088435667fa37da2Greg Clayton
114cb8977d726be451df9978a74088435667fa37da2Greg ClaytonError
115cb8977d726be451df9978a74088435667fa37da2Greg ClaytonPlatformRemoteGDBServer::GetFile (const FileSpec &platform_file,
116cb8977d726be451df9978a74088435667fa37da2Greg Clayton                                  const UUID *uuid_ptr,
117cb8977d726be451df9978a74088435667fa37da2Greg Clayton                                  FileSpec &local_file)
118cb8977d726be451df9978a74088435667fa37da2Greg Clayton{
119cb8977d726be451df9978a74088435667fa37da2Greg Clayton    // Default to the local case
120cb8977d726be451df9978a74088435667fa37da2Greg Clayton    local_file = platform_file;
121cb8977d726be451df9978a74088435667fa37da2Greg Clayton    return Error();
122cb8977d726be451df9978a74088435667fa37da2Greg Clayton}
123cb8977d726be451df9978a74088435667fa37da2Greg Clayton
124cb8977d726be451df9978a74088435667fa37da2Greg Clayton//------------------------------------------------------------------
125cb8977d726be451df9978a74088435667fa37da2Greg Clayton/// Default Constructor
126cb8977d726be451df9978a74088435667fa37da2Greg Clayton//------------------------------------------------------------------
127cb8977d726be451df9978a74088435667fa37da2Greg ClaytonPlatformRemoteGDBServer::PlatformRemoteGDBServer () :
128b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton    Platform(false), // This is a remote platform
129b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton    m_gdb_client(true)
130cb8977d726be451df9978a74088435667fa37da2Greg Clayton{
131cb8977d726be451df9978a74088435667fa37da2Greg Clayton}
132cb8977d726be451df9978a74088435667fa37da2Greg Clayton
133cb8977d726be451df9978a74088435667fa37da2Greg Clayton//------------------------------------------------------------------
134cb8977d726be451df9978a74088435667fa37da2Greg Clayton/// Destructor.
135cb8977d726be451df9978a74088435667fa37da2Greg Clayton///
136cb8977d726be451df9978a74088435667fa37da2Greg Clayton/// The destructor is virtual since this class is designed to be
137cb8977d726be451df9978a74088435667fa37da2Greg Clayton/// inherited from by the plug-in instance.
138cb8977d726be451df9978a74088435667fa37da2Greg Clayton//------------------------------------------------------------------
139cb8977d726be451df9978a74088435667fa37da2Greg ClaytonPlatformRemoteGDBServer::~PlatformRemoteGDBServer()
140cb8977d726be451df9978a74088435667fa37da2Greg Clayton{
141cb8977d726be451df9978a74088435667fa37da2Greg Clayton}
142cb8977d726be451df9978a74088435667fa37da2Greg Clayton
143cb8977d726be451df9978a74088435667fa37da2Greg Claytonbool
144cb8977d726be451df9978a74088435667fa37da2Greg ClaytonPlatformRemoteGDBServer::GetSupportedArchitectureAtIndex (uint32_t idx, ArchSpec &arch)
145cb8977d726be451df9978a74088435667fa37da2Greg Clayton{
146cb8977d726be451df9978a74088435667fa37da2Greg Clayton    return false;
147cb8977d726be451df9978a74088435667fa37da2Greg Clayton}
148cb8977d726be451df9978a74088435667fa37da2Greg Clayton
149cb8977d726be451df9978a74088435667fa37da2Greg Claytonsize_t
150cb8977d726be451df9978a74088435667fa37da2Greg ClaytonPlatformRemoteGDBServer::GetSoftwareBreakpointTrapOpcode (Target &target, BreakpointSite *bp_site)
151cb8977d726be451df9978a74088435667fa37da2Greg Clayton{
152cb8977d726be451df9978a74088435667fa37da2Greg Clayton    // This isn't needed if the z/Z packets are supported in the GDB remote
153cb8977d726be451df9978a74088435667fa37da2Greg Clayton    // server. But we might need a packet to detect this.
154cb8977d726be451df9978a74088435667fa37da2Greg Clayton    return 0;
155cb8977d726be451df9978a74088435667fa37da2Greg Clayton}
156cb8977d726be451df9978a74088435667fa37da2Greg Clayton
157cb8977d726be451df9978a74088435667fa37da2Greg Claytonbool
15858e26e0935138225477fd61283215ceff2068899Greg ClaytonPlatformRemoteGDBServer::GetRemoteOSVersion ()
159cb8977d726be451df9978a74088435667fa37da2Greg Clayton{
16058e26e0935138225477fd61283215ceff2068899Greg Clayton    uint32_t major, minor, update;
16158e26e0935138225477fd61283215ceff2068899Greg Clayton    if (m_gdb_client.GetOSVersion (major, minor, update))
16258e26e0935138225477fd61283215ceff2068899Greg Clayton    {
16358e26e0935138225477fd61283215ceff2068899Greg Clayton        m_major_os_version = major;
16458e26e0935138225477fd61283215ceff2068899Greg Clayton        m_minor_os_version = minor;
16558e26e0935138225477fd61283215ceff2068899Greg Clayton        m_update_os_version = update;
16658e26e0935138225477fd61283215ceff2068899Greg Clayton        return true;
16758e26e0935138225477fd61283215ceff2068899Greg Clayton    }
168cb8977d726be451df9978a74088435667fa37da2Greg Clayton    return false;
169cb8977d726be451df9978a74088435667fa37da2Greg Clayton}
170cb8977d726be451df9978a74088435667fa37da2Greg Clayton
17158e26e0935138225477fd61283215ceff2068899Greg Claytonbool
17258e26e0935138225477fd61283215ceff2068899Greg ClaytonPlatformRemoteGDBServer::GetRemoteOSBuildString (std::string &s)
17358e26e0935138225477fd61283215ceff2068899Greg Clayton{
17458e26e0935138225477fd61283215ceff2068899Greg Clayton    return m_gdb_client.GetOSBuildString (s);
17558e26e0935138225477fd61283215ceff2068899Greg Clayton}
17658e26e0935138225477fd61283215ceff2068899Greg Clayton
17758e26e0935138225477fd61283215ceff2068899Greg Claytonbool
17858e26e0935138225477fd61283215ceff2068899Greg ClaytonPlatformRemoteGDBServer::GetRemoteOSKernelDescription (std::string &s)
17958e26e0935138225477fd61283215ceff2068899Greg Clayton{
18058e26e0935138225477fd61283215ceff2068899Greg Clayton    return m_gdb_client.GetOSKernelDescription (s);
18158e26e0935138225477fd61283215ceff2068899Greg Clayton}
18258e26e0935138225477fd61283215ceff2068899Greg Clayton
18358e26e0935138225477fd61283215ceff2068899Greg Clayton// Remote Platform subclasses need to override this function
18458e26e0935138225477fd61283215ceff2068899Greg ClaytonArchSpec
18558e26e0935138225477fd61283215ceff2068899Greg ClaytonPlatformRemoteGDBServer::GetRemoteSystemArchitecture ()
18658e26e0935138225477fd61283215ceff2068899Greg Clayton{
18758e26e0935138225477fd61283215ceff2068899Greg Clayton    return m_gdb_client.GetSystemArchitecture();
18858e26e0935138225477fd61283215ceff2068899Greg Clayton}
18958e26e0935138225477fd61283215ceff2068899Greg Clayton
19058e26e0935138225477fd61283215ceff2068899Greg Claytonbool
19158e26e0935138225477fd61283215ceff2068899Greg ClaytonPlatformRemoteGDBServer::IsConnected () const
19258e26e0935138225477fd61283215ceff2068899Greg Clayton{
19358e26e0935138225477fd61283215ceff2068899Greg Clayton    return m_gdb_client.IsConnected();
19458e26e0935138225477fd61283215ceff2068899Greg Clayton}
19558e26e0935138225477fd61283215ceff2068899Greg Clayton
196cb8977d726be451df9978a74088435667fa37da2Greg ClaytonError
197cb8977d726be451df9978a74088435667fa37da2Greg ClaytonPlatformRemoteGDBServer::ConnectRemote (Args& args)
198cb8977d726be451df9978a74088435667fa37da2Greg Clayton{
199cb8977d726be451df9978a74088435667fa37da2Greg Clayton    Error error;
20058e26e0935138225477fd61283215ceff2068899Greg Clayton    if (IsConnected())
201cb8977d726be451df9978a74088435667fa37da2Greg Clayton    {
20258e26e0935138225477fd61283215ceff2068899Greg Clayton        error.SetErrorStringWithFormat ("the platform is already connected to '%s', execute 'platform disconnect' to close the current connection",
20358e26e0935138225477fd61283215ceff2068899Greg Clayton                                        GetHostname());
204cb8977d726be451df9978a74088435667fa37da2Greg Clayton    }
205cb8977d726be451df9978a74088435667fa37da2Greg Clayton    else
206cb8977d726be451df9978a74088435667fa37da2Greg Clayton    {
20758e26e0935138225477fd61283215ceff2068899Greg Clayton        if (args.GetArgumentCount() == 1)
20858e26e0935138225477fd61283215ceff2068899Greg Clayton        {
20958e26e0935138225477fd61283215ceff2068899Greg Clayton            const char *url = args.GetArgumentAtIndex(0);
21058e26e0935138225477fd61283215ceff2068899Greg Clayton            m_gdb_client.SetConnection (new ConnectionFileDescriptor());
21158e26e0935138225477fd61283215ceff2068899Greg Clayton            const ConnectionStatus status = m_gdb_client.Connect(url, &error);
21258e26e0935138225477fd61283215ceff2068899Greg Clayton            if (status == eConnectionStatusSuccess)
21358e26e0935138225477fd61283215ceff2068899Greg Clayton            {
21458e26e0935138225477fd61283215ceff2068899Greg Clayton                if (m_gdb_client.HandshakeWithServer(&error))
21558e26e0935138225477fd61283215ceff2068899Greg Clayton                {
21658e26e0935138225477fd61283215ceff2068899Greg Clayton                    m_gdb_client.QueryNoAckModeSupported();
21758e26e0935138225477fd61283215ceff2068899Greg Clayton                    m_gdb_client.GetHostInfo();
21806d7cc86937caca0acf2b990a02a641dc9c7579aGreg Clayton#if 0
21906d7cc86937caca0acf2b990a02a641dc9c7579aGreg Clayton                    m_gdb_client.TestPacketSpeed(10000);
22006d7cc86937caca0acf2b990a02a641dc9c7579aGreg Clayton#endif
22158e26e0935138225477fd61283215ceff2068899Greg Clayton                }
22258e26e0935138225477fd61283215ceff2068899Greg Clayton                else
22358e26e0935138225477fd61283215ceff2068899Greg Clayton                {
22458e26e0935138225477fd61283215ceff2068899Greg Clayton                    m_gdb_client.Disconnect();
22558e26e0935138225477fd61283215ceff2068899Greg Clayton                }
22658e26e0935138225477fd61283215ceff2068899Greg Clayton            }
22758e26e0935138225477fd61283215ceff2068899Greg Clayton        }
22858e26e0935138225477fd61283215ceff2068899Greg Clayton        else
22958e26e0935138225477fd61283215ceff2068899Greg Clayton        {
23058e26e0935138225477fd61283215ceff2068899Greg Clayton            error.SetErrorString ("\"platform connect\" takes a single argument: <connect-url>");
23158e26e0935138225477fd61283215ceff2068899Greg Clayton        }
232cb8977d726be451df9978a74088435667fa37da2Greg Clayton    }
233cb8977d726be451df9978a74088435667fa37da2Greg Clayton
234cb8977d726be451df9978a74088435667fa37da2Greg Clayton    return error;
235cb8977d726be451df9978a74088435667fa37da2Greg Clayton}
236cb8977d726be451df9978a74088435667fa37da2Greg Clayton
237cb8977d726be451df9978a74088435667fa37da2Greg ClaytonError
238cb8977d726be451df9978a74088435667fa37da2Greg ClaytonPlatformRemoteGDBServer::DisconnectRemote ()
239cb8977d726be451df9978a74088435667fa37da2Greg Clayton{
240cb8977d726be451df9978a74088435667fa37da2Greg Clayton    Error error;
241cb8977d726be451df9978a74088435667fa37da2Greg Clayton    m_gdb_client.Disconnect(&error);
242cb8977d726be451df9978a74088435667fa37da2Greg Clayton    return error;
243cb8977d726be451df9978a74088435667fa37da2Greg Clayton}
244cb8977d726be451df9978a74088435667fa37da2Greg Clayton
245cb8977d726be451df9978a74088435667fa37da2Greg Claytonconst char *
24624bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg ClaytonPlatformRemoteGDBServer::GetHostname ()
247cb8977d726be451df9978a74088435667fa37da2Greg Clayton{
24858e26e0935138225477fd61283215ceff2068899Greg Clayton    m_gdb_client.GetHostname (m_name);
24958e26e0935138225477fd61283215ceff2068899Greg Clayton    if (m_name.empty())
25058e26e0935138225477fd61283215ceff2068899Greg Clayton        return NULL;
25158e26e0935138225477fd61283215ceff2068899Greg Clayton    return m_name.c_str();
252cb8977d726be451df9978a74088435667fa37da2Greg Clayton}
253cb8977d726be451df9978a74088435667fa37da2Greg Clayton
25424bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Claytonconst char *
25524bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg ClaytonPlatformRemoteGDBServer::GetUserName (uint32_t uid)
25624bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Clayton{
25724bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Clayton    // Try and get a cache user name first
25824bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Clayton    const char *cached_user_name = Platform::GetUserName(uid);
25924bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Clayton    if (cached_user_name)
26024bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Clayton        return cached_user_name;
26124bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Clayton    std::string name;
26224bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Clayton    if (m_gdb_client.GetUserName(uid, name))
26324bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Clayton        return SetCachedUserName(uid, name.c_str(), name.size());
26424bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Clayton
26524bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Clayton    SetUserNameNotFound(uid); // Negative cache so we don't keep sending packets
26624bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Clayton    return NULL;
26724bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Clayton}
26824bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Clayton
26924bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Claytonconst char *
27024bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg ClaytonPlatformRemoteGDBServer::GetGroupName (uint32_t gid)
27124bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Clayton{
27224bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Clayton    const char *cached_group_name = Platform::GetGroupName(gid);
27324bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Clayton    if (cached_group_name)
27424bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Clayton        return cached_group_name;
27524bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Clayton    std::string name;
27624bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Clayton    if (m_gdb_client.GetGroupName(gid, name))
27724bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Clayton        return SetCachedGroupName(gid, name.c_str(), name.size());
27824bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Clayton
27924bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Clayton    SetGroupNameNotFound(gid); // Negative cache so we don't keep sending packets
28024bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Clayton    return NULL;
28124bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Clayton}
28224bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Clayton
28324bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Claytonuint32_t
284b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg ClaytonPlatformRemoteGDBServer::FindProcesses (const ProcessInstanceInfoMatch &match_info,
285b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton                                        ProcessInstanceInfoList &process_infos)
28624bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Clayton{
28724bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Clayton    return m_gdb_client.FindProcesses (match_info, process_infos);
28824bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Clayton}
28924bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Clayton
29024bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Claytonbool
291b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg ClaytonPlatformRemoteGDBServer::GetProcessInfo (lldb::pid_t pid, ProcessInstanceInfo &process_info)
29224bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Clayton{
29324bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Clayton    return m_gdb_client.GetProcessInfo (pid, process_info);
29424bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Clayton}
29524bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Clayton
29624bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Clayton
297b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg ClaytonError
298b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg ClaytonPlatformRemoteGDBServer::LaunchProcess (ProcessLaunchInfo &launch_info)
299b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton{
300b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton    Error error;
301b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton    lldb::pid_t pid = LLDB_INVALID_PROCESS_ID;
302b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton
303b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton    m_gdb_client.SetSTDIN ("/dev/null");
304b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton    m_gdb_client.SetSTDOUT ("/dev/null");
305b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton    m_gdb_client.SetSTDERR ("/dev/null");
306b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton    m_gdb_client.SetDisableASLR (launch_info.GetFlags().Test (eLaunchFlagDisableASLR));
307b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton
308b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton    const char *working_dir = launch_info.GetWorkingDirectory();
309b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton    if (working_dir && working_dir[0])
310b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton    {
311b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton        m_gdb_client.SetWorkingDir (working_dir);
312b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton    }
313b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton
314b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton    // Send the environment and the program + arguments after we connect
315b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton    const char **argv = launch_info.GetArguments().GetConstArgumentVector();
316b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton    const char **envp = launch_info.GetEnvironmentEntries().GetConstArgumentVector();
317b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton
318b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton    if (envp)
319b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton    {
320b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton        const char *env_entry;
321b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton        for (int i=0; (env_entry = envp[i]); ++i)
322b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton        {
323b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton            if (m_gdb_client.SendEnvironmentPacket(env_entry) != 0)
324b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton                break;
325b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton        }
326b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton    }
3275e342f50b42b265d8568e1c926328858e74b2c0aGreg Clayton    const uint32_t old_packet_timeout = m_gdb_client.SetPacketTimeout (5);
328b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton    int arg_packet_err = m_gdb_client.SendArgumentsPacket (argv);
329b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton    m_gdb_client.SetPacketTimeout (old_packet_timeout);
330b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton    if (arg_packet_err == 0)
331b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton    {
332b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton        std::string error_str;
333b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton        if (m_gdb_client.GetLaunchSuccess (error_str))
334b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton        {
335b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton            pid = m_gdb_client.GetCurrentProcessID ();
336b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton            if (pid != LLDB_INVALID_PROCESS_ID)
337b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton                launch_info.SetProcessID (pid);
338b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton        }
339b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton        else
340b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton        {
341b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton            error.SetErrorString (error_str.c_str());
342b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton        }
343b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton    }
344b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton    else
345b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton    {
3469c236733d43e6250c8a5671a438f4a2afeb9c0b2Greg Clayton        error.SetErrorStringWithFormat("'A' packet returned an error: %i", arg_packet_err);
347b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton    }
348b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton    return error;
349b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton}
350b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton
351b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Claytonlldb::ProcessSP
352527154d8e532f27f25af226c9e1dac607c48b5d1Greg ClaytonPlatformRemoteGDBServer::Attach (lldb_private::ProcessAttachInfo &attach_info,
353b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton                                 Debugger &debugger,
354b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton                                 Target *target,       // Can be NULL, if NULL create a new target, else use existing one
355b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton                                 Listener &listener,
356b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton                                 Error &error)
357b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton{
358b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton    lldb::ProcessSP process_sp;
359b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton    if (IsRemote())
360b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton    {
361b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton        if (IsConnected())
362b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton        {
363b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton            uint16_t port = m_gdb_client.LaunchGDBserverAndGetPort();
364b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton
365b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton            if (port == 0)
366b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton            {
367b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton                error.SetErrorStringWithFormat ("unable to launch a GDB server on '%s'", GetHostname ());
368b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton            }
369b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton            else
370b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton            {
371b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton                if (target == NULL)
372b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton                {
373b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton                    TargetSP new_target_sp;
374b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton
375b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton                    error = debugger.GetTargetList().CreateTarget (debugger,
376ed0a0fbd021e44727469d6fa20cc337c58bd04c3Greg Clayton                                                                   NULL,
3773e8c25f62f92145b6fb699b379cbfe72b1245d4aGreg Clayton                                                                   NULL,
378b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton                                                                   false,
3793e8c25f62f92145b6fb699b379cbfe72b1245d4aGreg Clayton                                                                   NULL,
380b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton                                                                   new_target_sp);
381b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton                    target = new_target_sp.get();
382b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton                }
383b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton                else
384b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton                    error.Clear();
385b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton
386b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton                if (target && error.Success())
387b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton                {
388b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton                    debugger.GetTargetList().SetSelectedTarget(target);
389b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton
390b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton                    // The darwin always currently uses the GDB remote debugger plug-in
391b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton                    // so even when debugging locally we are debugging remotely!
39246c9a355af9b39db78c006b2a5cbf97d3c58d947Greg Clayton                    process_sp = target->CreateProcess (listener, "gdb-remote", NULL);
393b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton
394b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton                    if (process_sp)
395b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton                    {
396b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton                        char connect_url[256];
397b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton                        const int connect_url_len = ::snprintf (connect_url,
398b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton                                                                sizeof(connect_url),
399b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton                                                                "connect://%s:%u",
400b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton                                                                GetHostname (),
401b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton                                                                port);
4023e11c7ec050648ba865f1d451f8cb46fd39072a8Andy Gibbs                        assert (connect_url_len < (int)sizeof(connect_url));
403fac2e62f08719ba800a440b7ad0d5a55a26dc620Jason Molenda                        error = process_sp->ConnectRemote (NULL, connect_url);
404b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton                        if (error.Success())
405527154d8e532f27f25af226c9e1dac607c48b5d1Greg Clayton                            error = process_sp->Attach(attach_info);
406b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton                    }
407b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton                }
408b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton            }
409b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton        }
410b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton        else
411b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton        {
412b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton            error.SetErrorString("not connected to remote gdb server");
413b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton        }
414b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton    }
415b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton    return process_sp;
416b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton}
417b72d0f098e45936fa72e26b1a026c603e17e2d6cGreg Clayton
41824bc5d9bfad2a1c562c27e7cf37e1c56d85c45e7Greg Clayton
419