solve the build break due to the lack of this method. It also propose a solution to the API changes in RegisterContext. I upgraded also the the python version in the makefile. My linux installation has python2.7 and AFAIK also the latest ubuntu has this version of python so maybe is worth upgrading. Patch by Marco Minutoli <mminutoli@gmail.com> [Note: I had to hand merge in the diffs since patch thinks it is a corrupt patch.] llvm-svn: 131313
262 lines
7.9 KiB
C++
262 lines
7.9 KiB
C++
//===-- PlatformLinux.cpp ---------------------------------------*- C++ -*-===//
|
|
//
|
|
// The LLVM Compiler Infrastructure
|
|
//
|
|
// This file is distributed under the University of Illinois Open Source
|
|
// License. See LICENSE.TXT for details.
|
|
//
|
|
//===----------------------------------------------------------------------===//
|
|
|
|
#include "PlatformLinux.h"
|
|
|
|
// C Includes
|
|
#include <stdio.h>
|
|
#include <sys/utsname.h>
|
|
|
|
// C++ Includes
|
|
// Other libraries and framework includes
|
|
// Project includes
|
|
#include "lldb/Core/Error.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/Target.h"
|
|
#include "lldb/Target/Process.h"
|
|
|
|
using namespace lldb;
|
|
using namespace lldb_private;
|
|
|
|
Platform *
|
|
PlatformLinux::CreateInstance ()
|
|
{
|
|
return new PlatformLinux();
|
|
}
|
|
|
|
const char *
|
|
PlatformLinux::GetPluginNameStatic()
|
|
{
|
|
return "plugin.platform.linux";
|
|
}
|
|
|
|
const char *
|
|
PlatformLinux::GetPluginDescriptionStatic()
|
|
{
|
|
return "Default platform plugin for Linux";
|
|
}
|
|
|
|
void
|
|
PlatformLinux::Initialize ()
|
|
{
|
|
static bool g_initialized = false;
|
|
|
|
if (!g_initialized)
|
|
{
|
|
PlatformSP default_platform_sp (CreateInstance());
|
|
Platform::SetDefaultPlatform (default_platform_sp);
|
|
PluginManager::RegisterPlugin(GetPluginNameStatic(),
|
|
GetPluginDescriptionStatic(),
|
|
CreateInstance);
|
|
g_initialized = true;
|
|
}
|
|
}
|
|
|
|
void
|
|
PlatformLinux::Terminate ()
|
|
{
|
|
}
|
|
|
|
|
|
Error
|
|
PlatformLinux::ResolveExecutable (const FileSpec &exe_file,
|
|
const ArchSpec &exe_arch,
|
|
lldb::ModuleSP &exe_module_sp)
|
|
{
|
|
Error error;
|
|
// Nothing special to do here, just use the actual file and architecture
|
|
|
|
FileSpec resolved_exe_file (exe_file);
|
|
|
|
// If we have "ls" as the exe_file, resolve the executable loation based on
|
|
// the current path variables
|
|
if (!resolved_exe_file.Exists())
|
|
resolved_exe_file.ResolveExecutableLocation ();
|
|
|
|
// Resolve any executable within a bundle on MacOSX
|
|
Host::ResolveExecutableInBundle (resolved_exe_file);
|
|
|
|
if (resolved_exe_file.Exists())
|
|
{
|
|
if (exe_arch.IsValid())
|
|
{
|
|
error = ModuleList::GetSharedModule (resolved_exe_file,
|
|
exe_arch,
|
|
NULL,
|
|
NULL,
|
|
0,
|
|
exe_module_sp,
|
|
NULL,
|
|
NULL);
|
|
|
|
if (exe_module_sp->GetObjectFile() == NULL)
|
|
{
|
|
exe_module_sp.reset();
|
|
error.SetErrorStringWithFormat ("'%s%s%s' doesn't contain the architecture %s",
|
|
exe_file.GetDirectory().AsCString(""),
|
|
exe_file.GetDirectory() ? "/" : "",
|
|
exe_file.GetFilename().AsCString(""),
|
|
exe_arch.GetArchitectureName());
|
|
}
|
|
}
|
|
else
|
|
{
|
|
// No valid architecture was specified, ask the platform for
|
|
// the architectures that we should be using (in the correct order)
|
|
// and see if we can find a match that way
|
|
StreamString arch_names;
|
|
ArchSpec platform_arch;
|
|
for (uint32_t idx = 0; GetSupportedArchitectureAtIndex (idx, platform_arch); ++idx)
|
|
{
|
|
error = ModuleList::GetSharedModule (resolved_exe_file,
|
|
platform_arch,
|
|
NULL,
|
|
NULL,
|
|
0,
|
|
exe_module_sp,
|
|
NULL,
|
|
NULL);
|
|
// Did we find an executable using one of the
|
|
if (error.Success())
|
|
{
|
|
if (exe_module_sp && exe_module_sp->GetObjectFile())
|
|
break;
|
|
else
|
|
error.SetErrorToGenericError();
|
|
}
|
|
|
|
if (idx > 0)
|
|
arch_names.PutCString (", ");
|
|
arch_names.PutCString (platform_arch.GetArchitectureName());
|
|
}
|
|
|
|
if (error.Fail() || !exe_module_sp)
|
|
{
|
|
error.SetErrorStringWithFormat ("'%s%s%s' doesn't contain any '%s' platform architectures: %s",
|
|
exe_file.GetDirectory().AsCString(""),
|
|
exe_file.GetDirectory() ? "/" : "",
|
|
exe_file.GetFilename().AsCString(""),
|
|
GetShortPluginName(),
|
|
arch_names.GetString().c_str());
|
|
}
|
|
}
|
|
}
|
|
else
|
|
{
|
|
error.SetErrorStringWithFormat ("'%s%s%s' does not exist",
|
|
exe_file.GetDirectory().AsCString(""),
|
|
exe_file.GetDirectory() ? "/" : "",
|
|
exe_file.GetFilename().AsCString(""));
|
|
}
|
|
|
|
return error;
|
|
}
|
|
|
|
Error
|
|
PlatformLinux::GetFile (const FileSpec &platform_file,
|
|
const UUID *uuid, FileSpec &local_file)
|
|
{
|
|
// Default to the local case
|
|
local_file = platform_file;
|
|
return Error();
|
|
}
|
|
|
|
|
|
//------------------------------------------------------------------
|
|
/// Default Constructor
|
|
//------------------------------------------------------------------
|
|
PlatformLinux::PlatformLinux () :
|
|
Platform(true)
|
|
{
|
|
}
|
|
|
|
//------------------------------------------------------------------
|
|
/// Destructor.
|
|
///
|
|
/// The destructor is virtual since this class is designed to be
|
|
/// inherited from by the plug-in instance.
|
|
//------------------------------------------------------------------
|
|
PlatformLinux::~PlatformLinux()
|
|
{
|
|
}
|
|
|
|
bool
|
|
PlatformLinux::GetProcessInfo (lldb::pid_t pid, ProcessInstanceInfo &process_info)
|
|
{
|
|
return Host::GetProcessInfo (pid, process_info);
|
|
}
|
|
|
|
bool
|
|
PlatformLinux::GetSupportedArchitectureAtIndex (uint32_t idx, ArchSpec &arch)
|
|
{
|
|
if (idx == 0)
|
|
{
|
|
arch = Host::GetArchitecture (Host::eSystemDefaultArchitecture);
|
|
return arch.IsValid();
|
|
}
|
|
return false;
|
|
}
|
|
|
|
void
|
|
PlatformLinux::GetStatus (Stream &strm)
|
|
{
|
|
struct utsname un;
|
|
|
|
if (uname(&un)) {
|
|
strm << "Linux";
|
|
return;
|
|
}
|
|
|
|
strm << un.sysname << ' ' << un.release << ' ' << un.version << '\n';
|
|
}
|
|
|
|
size_t
|
|
PlatformLinux::GetSoftwareBreakpointTrapOpcode (Target &target,
|
|
BreakpointSite *bp_site)
|
|
{
|
|
static const uint8_t g_i386_opcode[] = { 0xCC };
|
|
|
|
ArchSpec arch = target.GetArchitecture();
|
|
const uint8_t *opcode = NULL;
|
|
size_t opcode_size = 0;
|
|
|
|
switch (arch.GetCore())
|
|
{
|
|
default:
|
|
assert(false && "CPU type not supported!");
|
|
break;
|
|
|
|
case ArchSpec::eCore_x86_32_i386:
|
|
case ArchSpec::eCore_x86_64_x86_64:
|
|
opcode = g_i386_opcode;
|
|
opcode_size = sizeof(g_i386_opcode);
|
|
break;
|
|
}
|
|
|
|
bp_site->SetTrapOpcode(opcode, opcode_size);
|
|
return opcode_size;
|
|
}
|
|
|
|
lldb::ProcessSP
|
|
PlatformLinux::Attach(lldb::pid_t pid,
|
|
Debugger &debugger,
|
|
Target *target,
|
|
Listener &listener,
|
|
Error &error)
|
|
{
|
|
ProcessSP processSP;
|
|
assert(!"Not implemented yet!");
|
|
return processSP;
|
|
}
|