diff options
Diffstat (limited to 'lldb/source')
16 files changed, 736 insertions, 131 deletions
diff --git a/lldb/source/Commands/CommandObjectPlatform.cpp b/lldb/source/Commands/CommandObjectPlatform.cpp index 97eb0a4e5fc..dc6b4efb8dc 100644 --- a/lldb/source/Commands/CommandObjectPlatform.cpp +++ b/lldb/source/Commands/CommandObjectPlatform.cpp @@ -281,6 +281,137 @@ public: }; +//---------------------------------------------------------------------- +// "platform connect <connect-url>" +//---------------------------------------------------------------------- +class CommandObjectPlatformConnect : public CommandObject +{ +public: + CommandObjectPlatformConnect (CommandInterpreter &interpreter) : + CommandObject (interpreter, + "platform connect", + "Connect a platform by name to be the currently selected platform.", + "platform connect <connect-url>", + 0) + { + } + + virtual + ~CommandObjectPlatformConnect () + { + } + + virtual bool + Execute (Args& args, CommandReturnObject &result) + { + Stream &ostrm = result.GetOutputStream(); + + // Get rid of the "connect" from the args and leave the rest to the platform + args.Shift(); + PlatformSP selected_platform_sp (m_interpreter.GetDebugger().GetPlatformList().GetSelectedPlatform()); + if (selected_platform_sp) + { + Error error (selected_platform_sp->ConnectRemote (args)); + if (error.Success()) + { + ostrm.Printf ("Connected to \"%s\"\n", selected_platform_sp->GetInstanceName()); + selected_platform_sp->GetStatus (ostrm); + result.SetStatus (eReturnStatusSuccessFinishResult); + } + else + { + result.AppendErrorWithFormat ("connection failed: %s", error.AsCString()); + result.SetStatus (eReturnStatusFailed); + } + } + else + { + result.AppendError ("no platform us currently selected"); + result.SetStatus (eReturnStatusFailed); + } + return result.Succeeded(); + } +}; + +//---------------------------------------------------------------------- +// "platform disconnect" +//---------------------------------------------------------------------- +class CommandObjectPlatformDisconnect : public CommandObject +{ +public: + CommandObjectPlatformDisconnect (CommandInterpreter &interpreter) : + CommandObject (interpreter, + "platform disconnect", + "Disconnect a platform by name to be the currently selected platform.", + "platform disconnect", + 0) + { + } + + virtual + ~CommandObjectPlatformDisconnect () + { + } + + virtual bool + Execute (Args& args, CommandReturnObject &result) + { + PlatformSP selected_platform_sp (m_interpreter.GetDebugger().GetPlatformList().GetSelectedPlatform()); + if (selected_platform_sp) + { + if (args.GetArgumentCount() == 0) + { + Error error; + + if (selected_platform_sp->IsConnected()) + { + // Cache the instance name if there is one since we are + // about to disconnect and the name might go with it. + const char *instance_name_cstr = selected_platform_sp->GetInstanceName(); + std::string instance_name; + if (instance_name_cstr) + instance_name.assign (instance_name_cstr); + + error = selected_platform_sp->DisconnectRemote (); + if (error.Success()) + { + Stream &ostrm = result.GetOutputStream(); + if (instance_name.empty()) + ostrm.Printf ("Disconnected from \"%s\"\n", selected_platform_sp->GetShortPluginName()); + else + ostrm.Printf ("Disconnected from \"%s\"\n", instance_name.c_str()); + result.SetStatus (eReturnStatusSuccessFinishResult); + } + else + { + result.AppendErrorWithFormat ("disconnect failed: %s", error.AsCString()); + result.SetStatus (eReturnStatusFailed); + } + } + else + { + // Not connected... + result.AppendError ("not connected."); + result.SetStatus (eReturnStatusFailed); + } + } + else + { + // Bad args + result.AppendError ("\"platform disconnect\" doesn't take any arguments"); + result.SetStatus (eReturnStatusFailed); + } + } + else + { + result.AppendError ("no platform us currently selected"); + result.SetStatus (eReturnStatusFailed); + } + return result.Succeeded(); + } +}; + + //---------------------------------------------------------------------- // CommandObjectPlatform constructor @@ -289,12 +420,14 @@ CommandObjectPlatform::CommandObjectPlatform(CommandInterpreter &interpreter) : CommandObjectMultiword (interpreter, "platform", "A set of commands to manage and create platforms.", - "platform [create|list|status|select] ...") + "platform [connect|create|disconnect|list|status|select] ...") { LoadSubCommand ("create", CommandObjectSP (new CommandObjectPlatformCreate (interpreter))); LoadSubCommand ("list" , CommandObjectSP (new CommandObjectPlatformList (interpreter))); LoadSubCommand ("select", CommandObjectSP (new CommandObjectPlatformSelect (interpreter))); LoadSubCommand ("status", CommandObjectSP (new CommandObjectPlatformStatus (interpreter))); + LoadSubCommand ("connect", CommandObjectSP (new CommandObjectPlatformConnect (interpreter))); + LoadSubCommand ("disconnect", CommandObjectSP (new CommandObjectPlatformDisconnect (interpreter))); } diff --git a/lldb/source/Plugins/Platform/MacOSX/PlatformMacOSX.cpp b/lldb/source/Plugins/Platform/MacOSX/PlatformMacOSX.cpp index 8c1ef1d5c9d..ba7be39b1bd 100644 --- a/lldb/source/Plugins/Platform/MacOSX/PlatformMacOSX.cpp +++ b/lldb/source/Plugins/Platform/MacOSX/PlatformMacOSX.cpp @@ -1,4 +1,4 @@ -//===-- Platform.cpp --------------------------------------------*- C++ -*-===// +//===-- PlatformMacOSX.cpp --------------------------------------*- C++ -*-===// // // The LLVM Compiler Infrastructure // @@ -138,7 +138,9 @@ PlatformMacOSX::ResolveExecutable (const FileSpec &exe_file, } Error -PlatformMacOSX::GetFile (const FileSpec &platform_file, FileSpec &local_file) +PlatformMacOSX::GetFile (const FileSpec &platform_file, + const UUID *uuid_ptr, + FileSpec &local_file) { // Default to the local case local_file = platform_file; @@ -193,11 +195,7 @@ PlatformMacOSX::GetStatus (Stream &strm) /// Default Constructor //------------------------------------------------------------------ PlatformMacOSX::PlatformMacOSX () : -#if defined (__APPLE__) Platform(true) // This is the local host platform -#else - Platform(false) // This is a remote platform -#endif { } diff --git a/lldb/source/Plugins/Platform/MacOSX/PlatformMacOSX.h b/lldb/source/Plugins/Platform/MacOSX/PlatformMacOSX.h index 4b0db1584a4..b0e3d1ad987 100644 --- a/lldb/source/Plugins/Platform/MacOSX/PlatformMacOSX.h +++ b/lldb/source/Plugins/Platform/MacOSX/PlatformMacOSX.h @@ -73,7 +73,9 @@ namespace lldb_private { GetStatus (Stream &strm); virtual Error - GetFile (const FileSpec &platform_file, FileSpec &local_file); + GetFile (const FileSpec &platform_file, + const UUID *uuid_ptr, + FileSpec &local_file); virtual uint32_t FindProcessesByName (const char *name_match, @@ -96,4 +98,4 @@ namespace lldb_private { }; } // namespace lldb_private -#endif // liblldb_Platform_h_ +#endif // liblldb_PlatformMacOSX_h_ diff --git a/lldb/source/Plugins/Platform/MacOSX/PlatformRemoteiOS.cpp b/lldb/source/Plugins/Platform/MacOSX/PlatformRemoteiOS.cpp index c0bece1f207..fa6fcdc3d4a 100644 --- a/lldb/source/Plugins/Platform/MacOSX/PlatformRemoteiOS.cpp +++ b/lldb/source/Plugins/Platform/MacOSX/PlatformRemoteiOS.cpp @@ -1,4 +1,4 @@ -//===-- Platform.cpp --------------------------------------------*- C++ -*-===// +//===-- PlatformRemoteiOS.cpp -----------------------------------*- C++ -*-===// // // The LLVM Compiler Infrastructure // @@ -27,18 +27,28 @@ using namespace lldb; using namespace lldb_private; + +static bool g_initialized = false; void PlatformRemoteiOS::Initialize () { - static bool g_initialized = false; - if (g_initialized == false) { g_initialized = true; - PluginManager::RegisterPlugin (GetShortPluginNameStatic(), - GetDescriptionStatic(), - CreateInstance); + PluginManager::RegisterPlugin (PlatformRemoteiOS::GetShortPluginNameStatic(), + PlatformRemoteiOS::GetDescriptionStatic(), + PlatformRemoteiOS::CreateInstance); + } +} + +void +PlatformRemoteiOS::Terminate () +{ + if (g_initialized) + { + g_initialized = false; + PluginManager::UnregisterPlugin (PlatformRemoteiOS::CreateInstance); } } @@ -48,10 +58,6 @@ PlatformRemoteiOS::CreateInstance () return new PlatformRemoteiOS (); } -void -PlatformRemoteiOS::Terminate () -{ -} const char * PlatformRemoteiOS::GetPluginNameStatic () @@ -358,6 +364,7 @@ PlatformRemoteiOS::GetDeviceSupportDirectoryForOSVersion() Error PlatformRemoteiOS::GetFile (const FileSpec &platform_file, + const UUID *uuid_ptr, FileSpec &local_file) { Error error; @@ -442,6 +449,29 @@ PlatformRemoteiOS::GetProcessInfo (lldb::pid_t pid, ProcessInfo &process_info) return false; } +const char * +PlatformRemoteiOS::GetRemoteInstanceName () +{ + if (m_remote_instance_name.empty()) + { + const char *device_support_dir = GetDeviceSupportDirectory(); + if (device_support_dir) + { + std::string latest_device_support_dir; + latest_device_support_dir.assign (device_support_dir); + latest_device_support_dir.append ("/Platforms/iPhoneOS.platform/DeviceSupport/Latest"); + const bool resolve_path = true; + FileSpec file_spec (m_device_support_directory_for_os_version.c_str(), resolve_path); + // We are using the resolved basename of the "Latest" symlink (which + // is usually the latest and greatest SDK version and the update + // which is something like: "4.0 (8A123)" + if (file_spec.Exists()) + m_remote_instance_name.assign (file_spec.GetFilename().GetCString()); + } + } + return m_remote_instance_name.c_str(); +} + bool PlatformRemoteiOS::GetSupportedArchitectureAtIndex (uint32_t idx, ArchSpec &arch) { @@ -549,6 +579,13 @@ PlatformRemoteiOS::GetSupportedArchitectureAtIndex (uint32_t idx, ArchSpec &arch return false; } +bool +PlatformRemoteiOS::FetchRemoteOSVersion () +{ + return false; +} + + size_t PlatformRemoteiOS::GetSoftwareBreakpointTrapOpcode (Target &target, BreakpointSite *bp_site) { @@ -610,3 +647,35 @@ PlatformRemoteiOS::GetSoftwareBreakpointTrapOpcode (Target &target, BreakpointSi return 0; } + +Error +PlatformRemoteiOS::ConnectRemote (Args& args) +{ + Error error; + error.SetErrorStringWithFormat ("'platform connect' is not implemented yet for platform '%s'", GetShortPluginNameStatic()); + +// if (args.GetArgumentCount() == 1) +// { +// const char *remote_url = args.GetArgumentAtIndex(0); +// ConnectionStatus status = m_gdb_client.Connect(remote_url, &error); +// if (status == eConnectionStatusSuccess) +// { +// m_gdb_client.GetHostInfo(); +// } +// } +// else +// { +// error.SetErrorString ("\"platform connect\" takes a single argument: <connect-url>"); +// } + + return error; +} + +Error +PlatformRemoteiOS::DisconnectRemote () +{ + Error error; + error.SetErrorStringWithFormat ("'platform disconnect' is not implemented yet for platform '%s'", GetShortPluginNameStatic()); +// m_gdb_client.Disconnect(&error); + return error; +} diff --git a/lldb/source/Plugins/Platform/MacOSX/PlatformRemoteiOS.h b/lldb/source/Plugins/Platform/MacOSX/PlatformRemoteiOS.h index 5c0f075b41c..36f4c004597 100644 --- a/lldb/source/Plugins/Platform/MacOSX/PlatformRemoteiOS.h +++ b/lldb/source/Plugins/Platform/MacOSX/PlatformRemoteiOS.h @@ -85,7 +85,9 @@ namespace lldb_private { GetStatus (Stream &strm); virtual Error - GetFile (const FileSpec &platform_file, FileSpec &local_file); + GetFile (const FileSpec &platform_file, + const UUID *uuid_ptr, + FileSpec &local_file); virtual uint32_t FindProcessesByName (const char *name_match, @@ -102,6 +104,19 @@ namespace lldb_private { GetSoftwareBreakpointTrapOpcode (Target &target, BreakpointSite *bp_site); + virtual bool + FetchRemoteOSVersion (); + + virtual Error + ConnectRemote (Args& args); + + virtual Error + DisconnectRemote (); + + virtual const char * + GetRemoteInstanceName (); + + protected: std::string m_device_support_directory; std::string m_device_support_directory_for_os_version; @@ -120,4 +135,4 @@ namespace lldb_private { }; } // namespace lldb_private -#endif // liblldb_Platform_h_ +#endif // liblldb_PlatformRemoteiOS_h_ diff --git a/lldb/source/Plugins/Platform/gdb-server/PlatformRemoteGDBServer.cpp b/lldb/source/Plugins/Platform/gdb-server/PlatformRemoteGDBServer.cpp new file mode 100644 index 00000000000..f8a73a3826d --- /dev/null +++ b/lldb/source/Plugins/Platform/gdb-server/PlatformRemoteGDBServer.cpp @@ -0,0 +1,240 @@ +//===-- PlatformRemoteGDBServer.cpp -----------------------------*- C++ -*-===// +// +// The LLVM Compiler Infrastructure +// +// This file is distributed under the University of Illinois Open Source +// License. See LICENSE.TXT for details. +// +//===----------------------------------------------------------------------===// + +#include "PlatformRemoteGDBServer.h" + +// C Includes +#include <sys/sysctl.h> + +// C++ Includes +// Other libraries and framework includes +// Project includes +#include "lldb/Core/Error.h" +#include "lldb/Breakpoint/BreakpointLocation.h" +#include "lldb/Core/Module.h" +#include "lldb/Core/ModuleList.h" +#include "lldb/Core/PluginManager.h" +#include "lldb/Core/StreamString.h" +#include "lldb/Host/FileSpec.h" +#include "lldb/Host/Host.h" +#include "lldb/Target/Process.h" +#include "lldb/Target/Target.h" + +using namespace lldb; +using namespace lldb_private; + +static bool g_initialized = false; + +void +PlatformRemoteGDBServer::Initialize () +{ + if (g_initialized == false) + { + g_initialized = true; + PluginManager::RegisterPlugin (PlatformRemoteGDBServer::GetShortPluginNameStatic(), + PlatformRemoteGDBServer::GetDescriptionStatic(), + PlatformRemoteGDBServer::CreateInstance); + } +} + +void +PlatformRemoteGDBServer::Terminate () +{ + if (g_initialized) + { + g_initialized = false; + PluginManager::UnregisterPlugin (PlatformRemoteGDBServer::CreateInstance); + } +} + +Platform* +PlatformRemoteGDBServer::CreateInstance () +{ + return new PlatformRemoteGDBServer (); +} + +const char * +PlatformRemoteGDBServer::GetShortPluginNameStatic() +{ + return "remote-gdb-server"; +} + +const char * +PlatformRemoteGDBServer::GetDescriptionStatic() +{ + return "A platform that uses the GDB remote protocol as the communication transport."; +} + +const char * +PlatformRemoteGDBServer::GetDescription () +{ + if (m_platform_description.empty()) + { + if (IsConnected()) + { + // Send the get description packet + } + } + + if (!m_platform_description.empty()) + return m_platform_description.c_str(); + return GetDescriptionStatic(); +} + +Error +PlatformRemoteGDBServer::ResolveExecutable (const FileSpec &exe_file, + const ArchSpec &exe_arch, + lldb::ModuleSP &exe_module_sp) +{ + Error error; + error.SetErrorString ("PlatformRemoteGDBServer::ResolveExecutable() is unimplemented"); + return error; +} + +Error +PlatformRemoteGDBServer::GetFile (const FileSpec &platform_file, + const UUID *uuid_ptr, + FileSpec &local_file) +{ + // Default to the local case + local_file = platform_file; + return Error(); +} + + +void +PlatformRemoteGDBServer::GetStatus (Stream &strm) +{ + char sysctlstring[1024]; + size_t datalen; + int mib[CTL_MAXNAME]; + + uint32_t major = UINT32_MAX; + uint32_t minor = UINT32_MAX; + uint32_t update = UINT32_MAX; + strm.PutCString("Remote GDB server platform"); + if (GetOSVersion(major, minor, update)) + { + strm.Printf("OS version: %u", major); + if (minor != UINT32_MAX) + strm.Printf(".%u", minor); + if (update != UINT32_MAX) + strm.Printf(".%u", update); + + + mib[0] = CTL_KERN; + mib[1] = KERN_OSVERSION; + datalen = sizeof(sysctlstring); + if (::sysctl (mib, 2, sysctlstring, &datalen, NULL, 0) == 0) + { + sysctlstring[datalen] = '\0'; + strm.Printf(" (%s)", sysctlstring); + } + + strm.EOL(); + } + + mib[0] = CTL_KERN; + mib[1] = KERN_VERSION; + datalen = sizeof(sysctlstring); + if (::sysctl (mib, 2, sysctlstring, &datalen, NULL, 0) == 0) + { + sysctlstring[datalen] = '\0'; + strm.Printf("Kernel version: %s\n", sysctlstring); + } +} + + +//------------------------------------------------------------------ +/// Default Constructor +//------------------------------------------------------------------ +PlatformRemoteGDBServer::PlatformRemoteGDBServer () : + Platform(false) // This is a remote platform +{ +} + +//------------------------------------------------------------------ +/// Destructor. +/// +/// The destructor is virtual since this class is designed to be +/// inherited from by the plug-in instance. +//------------------------------------------------------------------ +PlatformRemoteGDBServer::~PlatformRemoteGDBServer() +{ +} + +uint32_t +PlatformRemoteGDBServer::FindProcessesByName (const char *name_match, + lldb::NameMatchType name_match_type, + ProcessInfoList &process_infos) +{ + return 0; +} + +bool +PlatformRemoteGDBServer::GetProcessInfo (lldb::pid_t pid, ProcessInfo &process_info) +{ + return false; +} + +bool +PlatformRemoteGDBServer::GetSupportedArchitectureAtIndex (uint32_t idx, ArchSpec &arch) +{ + return false; +} + +size_t +PlatformRemoteGDBServer::GetSoftwareBreakpointTrapOpcode (Target &target, BreakpointSite *bp_site) +{ + // This isn't needed if the z/Z packets are supported in the GDB remote + // server. But we might need a packet to detect this. + return 0; +} + +bool +PlatformRemoteGDBServer::FetchRemoteOSVersion () +{ + return false; +} + +Error +PlatformRemoteGDBServer::ConnectRemote (Args& args) +{ + Error error; + if (args.GetArgumentCount() == 1) + { + const char *remote_url = args.GetArgumentAtIndex(0); + ConnectionStatus status = m_gdb_client.Connect(remote_url, &error); + if (status == eConnectionStatusSuccess) + { + m_gdb_client.GetHostInfo(); + } + } + else + { + error.SetErrorString ("\"platform connect\" takes a single argument: <connect-url>"); + } + + return error; +} + +Error +PlatformRemoteGDBServer::DisconnectRemote () +{ + Error error; + m_gdb_client.Disconnect(&error); + return error; +} + +const char * +PlatformRemoteGDBServer::GetRemoteInstanceName () +{ + return NULL; +} + diff --git a/lldb/source/Plugins/Platform/gdb-server/PlatformRemoteGDBServer.h b/lldb/source/Plugins/Platform/gdb-server/PlatformRemoteGDBServer.h new file mode 100644 index 00000000000..6c322d38c9c --- /dev/null +++ b/lldb/source/Plugins/Platform/gdb-server/PlatformRemoteGDBServer.h @@ -0,0 +1,127 @@ +//===-- PlatformRemoteGDBServer.h ----------------------------------------*- C++ -*-===// +// +// The LLVM Compiler Infrastructure +// +// This file is distributed under the University of Illinois Open Source +// License. See LICENSE.TXT for details. +// +//===----------------------------------------------------------------------===// + +#ifndef liblldb_PlatformRemoteGDBServer_h_ +#define liblldb_PlatformRemoteGDBServer_h_ + +// C Includes +// C++ Includes +#include <string> + +// Other libraries and framework includes +// Project includes +#include "lldb/Target/Platform.h" +#include "../../Process/gdb-remote/GDBRemoteCommunicationClient.h" + +namespace lldb_private { + + class PlatformRemoteGDBServer : public Platform + { + public: + + static void + Initialize (); + + static void + Terminate (); + + static Platform* + CreateInstance (); + + static const char * + GetShortPluginNameStatic(); + + static const char * + GetDescriptionStatic(); + + + PlatformRemoteGDBServer (); + + virtual + ~PlatformRemoteGDBServer(); + + //------------------------------------------------------------ + // lldb_private::PluginInterface functions + //------------------------------------------------------------ + virtual const char * + GetPluginName() + { + return "PlatformRemoteGDBServer"; + } + + virtual const char * + GetShortPluginName() + { + return GetShortPluginNameStatic(); + } + + virtual uint32_t + GetPluginVersion() + { + return 1; + } + + + //------------------------------------------------------------ + // lldb_private::Platform functions + //------------------------------------------------------------ + virtual Error + ResolveExecutable (const FileSpec &exe_file, + const ArchSpec &arch, + lldb::ModuleSP &module_sp); + + virtual const char * + GetDescription (); + + virtual void + GetStatus (Stream &strm); + + virtual Error + GetFile (const FileSpec &platform_file, + const UUID *uuid_ptr, + FileSpec &local_file); + + virtual uint32_t + FindProcessesByName (const char *name_match, + lldb::NameMatchType name_match_type, + ProcessInfoList &process_infos); + + virtual bool + GetProcessInfo (lldb::pid_t pid, ProcessInfo &proc_info); + + virtual bool + GetSupportedArchitectureAtIndex (uint32_t idx, ArchSpec &arch); + + virtual size_t + GetSoftwareBreakpointTrapOpcode (Target &target, + BreakpointSite *bp_site); + + virtual bool + FetchRemoteOSVersion (); + + virtual Error + ConnectRemote (Args& args); + + virtual Error + DisconnectRemote (); + + virtual const char * + GetRemoteInstanceName (); + + protected: + GDBRemoteCommunicationClient m_gdb_client; + std::string m_platform_description; // After we connect we can get a more complete description of what we are connected to + + private: + DISALLOW_COPY_AND_ASSIGN (PlatformRemoteGDBServer); + + }; +} // namespace lldb_private + +#endif // liblldb_PlatformRemoteGDBServer_h_ diff --git a/lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationClient.cpp b/lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationClient.cpp index b4fb6f2ddfe..7700ab2b7f5 100644 --- a/lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationClient.cpp +++ b/lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationClient.cpp @@ -50,11 +50,7 @@ GDBRemoteCommunicationClient::GDBRemoteCommunicationClient() : m_async_packet (), m_async_response (), m_async_signal (-1), - m_arch(), - m_os(), - m_vendor(), - m_byte_order(lldb::endian::InlHostByteOrder()), - m_pointer_byte_size(0) + m_host_arch() { m_rx_packet_listener.StartListeningForEvents(this, Communication::eBroadcastBitPacketAvailable | @@ -102,11 +98,7 @@ GDBRemoteCommunicationClient::ResetDiscoverableSettings() m_supports_vCont_C = eLazyBoolCalculate; m_supports_vCont_s = eLazyBoolCalculate; m_supports_vCont_S = eLazyBoolCalculate; - m_arch.Clear(); - m_os.Clear(); - m_vendor.Clear(); - m_byte_order = lldb::endian::InlHostByteOrder(); - m_pointer_byte_size = 0; + m_host_arch.Clear(); } @@ -690,7 +682,11 @@ GDBRemoteCommunicationClient::GetHostInfo () std::string value; uint32_t cpu = LLDB_INVALID_CPUTYPE; uint32_t sub = 0; - + std::string arch_name; + std::string os_name; + std::string vendor_name; + uint32_t pointer_byte_size = 0; + ByteOrder byte_order = eByteOrderInvalid; while (response.GetNameColonValue(name, value)) { if (name.compare("cputype") == 0) @@ -703,32 +699,69 @@ GDBRemoteCommunicationClient::GetHostInfo () // exception count in big endian hex sub = Args::StringToUInt32 (value.c_str(), 0, 0); } + else if (name.compare("arch") == 0) + { + arch_name.swap (value); + } else if (name.compare("ostype") == 0) { - // exception data in big endian hex - m_os.SetCString(value.c_str()); + os_name.swap (value); } else if (name.compare("vendor") == 0) { - m_vendor.SetCString(value.c_str()); + vendor_name.swap(value); } else if (name.compare("endian") == 0) { if (value.compare("little") == 0) - m_byte_order = eByteOrderLittle; + byte_order = eByteOrderLittle; else if (value.compare("big") == 0) - m_byte_order = eByteOrderBig; + byte_order = eByteOrderBig; else if (value.compare("pdp") == 0) - m_byte_order = eByteOrderPDP; + byte_order = eByteOrderPDP; } else if (name.compare("ptrsize") == 0) { - m_pointer_byte_size = Args::StringToUInt32 (value.c_str(), 0, 0); + pointer_byte_size = Args::StringToUInt32 (value.c_str(), 0, 0); } } - if (cpu != LLDB_INVALID_CPUTYPE) - m_arch.SetArchitecture (lldb::eArchTypeMachO, cpu, sub); + if (arch_name.empty()) + { + if (cpu != LLDB_INVALID_CPUTYPE) + { + m_host_arch.SetArchitecture (lldb::eArchTypeMachO, cpu, sub); + if (pointer_byte_size) + { + assert (pointer_byte_size == m_host_arch.GetAddressByteSize()); + } + if (byte_order != eByteOrderInvalid) + { + assert (byte_order == m_host_arch.GetByteOrder()); + } + if (!vendor_name.empty()) + m_host_arch.GetTriple().setVendorName (llvm::StringRef (vendor_name)); + if (!os_name.empty()) + m_host_arch.GetTriple().setVendorName (llvm::StringRef (os_name)); + + } + } + else + { + std::string triple; + triple += arch_name; + triple += '-'; + if (vendor_name.empty()) + triple += "unknown"; + else + triple += vendor_name; + triple += '-'; + if (os_name.empty()) + triple += "unknown"; + else + triple += os_name; + m_host_arch.SetTriple (triple.c_str()); + } } } return m_supports_qHostInfo == eLazyBoolYes; @@ -759,41 +792,9 @@ GDBRemoteCommunicationClient::SendAttach const lldb_private::ArchSpec & GDBRemoteCommunicationClient::GetHostArchitecture () { - if (!HostInfoIsValid ()) - GetHostInfo (); - return m_arch; -} - -const lldb_private::ConstString & -GDBRemoteCommunicationClient::GetOSString () -{ - if (!HostInfoIsValid ()) - GetHostInfo (); - return m_os; -} - -const lldb_private::ConstString & -GDBRemoteCommunicationClient::GetVendorString() -{ - if (!HostInfoIsValid ()) - GetHostInfo (); - return m_vendor; -} - -lldb::ByteOrder -GDBRemoteCommunicationClient::GetByteOrder () -{ - if (!HostInfoIsValid ()) - GetHostInfo (); - return m_byte_order; -} - -uint32_t -GDBRemoteCommunicationClient::GetAddressByteSize () -{ - if (!HostInfoIsValid ()) + if (m_supports_qHostInfo == lldb::eLazyBoolCalculate) GetHostInfo (); - return m_pointer_byte_size; + return m_host_arch; } addr_t diff --git a/lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationClient.h b/lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationClient.h index 604e09a9491..bcf23f2c589 100644 --- a/lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationClient.h +++ b/lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationClient.h @@ -176,18 +176,6 @@ public: const lldb_private::ArchSpec & GetHostArchitecture (); - const lldb_private::ConstString & - GetOSString (); - - const lldb_private::ConstString & - GetVendorString(); - - lldb::ByteOrder - GetByteOrder (); - - uint32_t - GetAddressByteSize (); - bool GetVContSupported (char flavor); @@ -222,12 +210,6 @@ public: protected: - bool - HostInfoIsValid () const - { - return m_supports_qHostInfo != lldb::eLazyBoolCalculate; - } - //------------------------------------------------------------------ // Classes that inherit from GDBRemoteCommunicationClient can see and modify these //------------------------------------------------------------------ @@ -249,14 +231,8 @@ protected: StringExtractorGDBRemote m_async_response; int m_async_signal; // We were asked to deliver a signal to the inferior process. - lldb_private::ArchSpec m_arch; + lldb_private::ArchSpec m_host_arch; uint32_t m_cpusubtype; - lldb_private::ConstString m_os; - lldb_private::ConstString m_vendor; - lldb::ByteOrder m_byte_order; - uint32_t m_pointer_byte_size; - - private: //------------------------------------------------------------------ diff --git a/lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationServer.cpp b/lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationServer.cpp index 2e4ff70cf2d..18d6087e8b5 100644 --- a/lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationServer.cpp +++ b/lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationServer.cpp @@ -72,10 +72,12 @@ GDBRemoteCommunicationServer::~GDBRemoteCommunicationServer() //} // bool -GDBRemoteCommunicationServer::GetPacketAndSendResponse (const TimeValue* timeout_time_ptr) +GDBRemoteCommunicationServer::GetPacketAndSendResponse (const TimeValue* timeout_ptr, + bool &interrupt, + bool &quit) { StringExtractorGDBRemote packet; - if (WaitForPacketNoLock (packet, timeout_time_ptr)) + if (WaitForPacketNoLock (packet, timeout_ptr)) { const StringExtractorGDBRemote::ServerPacketType packet_type = packet.GetServerPacketType (); switch (packet_type) @@ -85,6 +87,13 @@ GDBRemoteCommunicationServer::GetPacketAndSendResponse (const TimeValue* timeout break; case StringExtractorGDBRemote::eServerPacketType_invalid: + quit = true; + break; + + case StringExtractorGDBRemote::eServerPacketType_interrupt: + interrupt = true; + break; + case StringExtractorGDBRemote::eServerPacketType_unimplemented: return SendUnimplementedResponse () > 0; diff --git a/lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationServer.h b/lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationServer.h index 8ccfca2ee1d..4e0b24ddea0 100644 --- a/lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationServer.h +++ b/lldb/source/Plugins/Process/gdb-remote/GDBRemoteCommunicationServer.h @@ -34,7 +34,9 @@ public: ~GDBRemoteCommunicationServer(); bool - GetPacketAndSendResponse (const lldb_private::TimeValue* timeout_time_ptr); + GetPacketAndSendResponse (const lldb_private::TimeValue* timeout_ptr, + bool &interrupt, + bool &quit); virtual bool GetThreadSuffixSupported () diff --git a/lldb/source/Plugins/Process/gdb-remote/ProcessGDBRemote.cpp b/lldb/source/Plugins/Process/gdb-remote/ProcessGDBRemote.cpp index 79949669e77..e5a1d7c0606 100644 --- a/lldb/source/Plugins/Process/gdb-remote/ProcessGDBRemote.cpp +++ b/lldb/source/Plugins/Process/gdb-remote/ProcessGDBRemote.cpp @@ -622,34 +622,52 @@ ProcessGDBRemote::DidLaunchOrAttach () BuildDynamicRegisterInfo (false); - m_target.GetArchitecture().SetByteOrder (m_gdb_comm.GetByteOrder()); StreamString strm; // See if the GDB server supports the qHostInfo information - const char *vendor = m_gdb_comm.GetVendorString().AsCString(); - const char *os_type = m_gdb_comm.GetOSString().AsCString(); - ArchSpec target_arch (GetTarget().GetArchitecture()); - ArchSpec gdb_remote_arch (m_gdb_comm.GetHostArchitecture()); - - // If the remote host is ARM and we have apple as the vendor, then - // ARM executables and shared libraries can have mixed ARM architectures. - // You can have an armv6 executable, and if the host is armv7, then the - // system will load the best possible architecture for all shared libraries - // it has, so we really need to take the remote host architecture as our - // defacto architecture in this case. - - if (gdb_remote_arch.GetMachine() == llvm::Triple::arm && - gdb_remote_arch.GetTriple().getVendor() == llvm::Triple::Apple) + + const ArchSpec &gdb_remote_arch = m_gdb_comm.GetHostArchitecture(); + if (gdb_remote_arch.IsValid()) { - GetTarget().SetArchitecture (gdb_remote_arch); - target_arch = gdb_remote_arch; + ArchSpec &target_arch = GetTarget().GetArchitecture(); + + if (target_arch.IsValid()) + { + // If the remote host is ARM and we have apple as the vendor, then + // ARM executables and shared libraries can have mixed ARM architectures. + // You can have an armv6 executable, and if the host is armv7, then the + // system will load the best possible architecture for all shared libraries + // it has, so we really need to take the remote host architecture as our + // defacto architecture in this case. + + if (gdb_remote_arch.GetMachine() == llvm::Triple::arm && + gdb_remote_arch.GetTriple().getVendor() == llvm::Triple::Apple) + { + target_arch = gdb_remote_arch; + } + else + { + // Fill in what is missing in the triple + const llvm::Triple &remote_triple = gdb_remote_arch.GetTriple(); + llvm::Triple &target_triple = target_arch.GetTriple(); + if (target_triple.getVendor() == llvm::Triple::UnknownVendor) + target_triple.setVendor (remote_triple.getVendor()); + + if (target_triple.getOS() == llvm::Triple::UnknownOS) + target_triple.setOS (remote_triple.getOS()); + + if (target_triple.getEnvironment() == llvm::Triple::UnknownEnvironment) + target_triple.setEnvironment (remote_triple.getEnvironment()); + } + } + else + { + // The target doesn't have a valid architecture yet, set it from + // the architecture we got from the remote GDB server + target_arch = gdb_remote_arch; + } } - - if (vendor) - m_target.GetArchitecture().GetTriple().setVendorName(vendor); - if (os_type) - m_target.GetArchitecture().GetTriple().setOSName(os_type); } } diff --git a/lldb/source/Target/Platform.cpp b/lldb/source/Target/Platform.cpp index 32ac194b66c..a6df50d9e70 100644 --- a/lldb/source/Target/Platform.cpp +++ b/lldb/source/Target/Platform.cpp @@ -69,7 +69,9 @@ Platform::SetDefaultPlatform (const lldb::PlatformSP &platform_sp) } Error -Platform::GetFile (const FileSpec &platform_file, FileSpec &local_file) +Platform::GetFile (const FileSpec &platform_file, + const UUID *uuid_ptr, + FileSpec &local_file) { // Default to the local case local_file = platform_file; @@ -123,6 +125,7 @@ Platform::Platform (bool is_host) : m_os_version_set_while_connected (false), m_system_arch_set_while_connected (false), m_remote_url (), + m_remote_instance_name (), m_major_os_version (UINT32_MAX), m_minor_os_version (UINT32_MAX), m_update_os_version (UINT32_MAX) @@ -330,17 +333,23 @@ Platform::GetSystemArchitecture() Error -Platform::ConnectRemote (const char *remote_url) +Platform::ConnectRemote (Args& args) { Error error; - error.SetErrorStringWithFormat ("Platform::ConnectRemote() is not supported by %s", GetShortPluginName()); + if (IsHost()) + error.SetErrorStringWithFormat ("The currently selected platform (%s) is the host platform and is always connected.", GetShortPluginName()); + else + error.SetErrorStringWithFormat ("Platform::ConnectRemote() is not supported by %s", GetShortPluginName()); return error; } Error -Platform::DisconnectRemote (const lldb::PlatformSP &platform_sp) +Platform::DisconnectRemote () { Error error; - error.SetErrorStringWithFormat ("Platform::DisconnectRemote() is not supported by %s", GetShortPluginName()); + if (IsHost()) + error.SetErrorStringWithFormat ("The currently selected platform (%s) is the host platform and is always connected.", GetShortPluginName()); + else + error.SetErrorStringWithFormat ("Platform::DisconnectRemote() is not supported by %s", GetShortPluginName()); return error; } diff --git a/lldb/source/Target/Target.cpp b/lldb/source/Target/Target.cpp index 46aa45042e4..8cc0a725125 100644 --- a/lldb/source/Target/Target.cpp +++ b/lldb/source/Target/Target.cpp @@ -428,7 +428,7 @@ Target::SetExecutableModule (ModuleSP& executable_sp, bool get_dependent_files) FileSpec dependent_file_spec (dependent_files.GetFileSpecPointerAtIndex(i)); FileSpec platform_dependent_file_spec; if (m_platform_sp) - m_platform_sp->GetFile (dependent_file_spec, platform_dependent_file_spec); + m_platform_sp->GetFile (dependent_file_spec, NULL, platform_dependent_file_spec); else platform_dependent_file_spec = dependent_file_spec; diff --git a/lldb/source/Utility/StringExtractorGDBRemote.cpp b/lldb/source/Utility/StringExtractorGDBRemote.cpp index fc64b275e55..372eaee501c 100644 --- a/lldb/source/Utility/StringExtractorGDBRemote.cpp +++ b/lldb/source/Utility/StringExtractorGDBRemote.cpp @@ -59,6 +59,11 @@ StringExtractorGDBRemote::GetServerPacketType () const const char *packet_cstr = m_packet.c_str(); switch (m_packet[0]) { + case '\x03': + if (m_packet.size() == 1) + return eServerPacketType_interrupt; + break; + case '-': if (m_packet.size() == 1) return eServerPacketType_nack; diff --git a/lldb/source/Utility/StringExtractorGDBRemote.h b/lldb/source/Utility/StringExtractorGDBRemote.h index e8c41778ec0..8c65e0c7a39 100644 --- a/lldb/source/Utility/StringExtractorGDBRemote.h +++ b/lldb/source/Utility/StringExtractorGDBRemote.h @@ -45,6 +45,7 @@ public: eServerPacketType_ack, eServerPacketType_invalid, eServerPacketType_unimplemented, + eServerPacketType_interrupt, // CTRL+c packet or "\x03" eServerPacketType_qHostInfo }; |