[Lldb-commits] [lldb] r110624 - in /lldb/trunk: include/lldb/Core/ include/lldb/Host/ include/lldb/Symbol/ include/lldb/Target/ source/Commands/ source/Core/ source/Host/macosx/ source/Plugins/DynamicLoader/MacOSX-DYLD/ source/Plugins/ObjectContainer/Universal-Mach-O/ source/Plugins/ObjectFile/ELF/ source/Plugins/ObjectFile/Mach-O/ source/Plugins/Process/MacOSX-User/source/ source/Plugins/Process/gdb-remote/ source/Symbol/ source/Target/
Jim Ingham
jingham at apple.com
Mon Aug 9 16:31:02 PDT 2010
Author: jingham
Date: Mon Aug 9 18:31:02 2010
New Revision: 110624
URL: http://llvm.org/viewvc/llvm-project?rev=110624&view=rev
Log:
Change Target & Process so they can really be initialized with an invalid architecture.
Arrange that this then gets properly set on attach, or when a "file" is set.
Add a completer for "process attach -n".
Caveats: there isn't currently a way to handle multiple processes with the same name. That
will have to wait on a way to pass annotations along with the completion strings.
Modified:
lldb/trunk/include/lldb/Core/Module.h
lldb/trunk/include/lldb/Host/Host.h
lldb/trunk/include/lldb/Symbol/ObjectFile.h
lldb/trunk/include/lldb/Target/Process.h
lldb/trunk/include/lldb/Target/Target.h
lldb/trunk/source/Commands/CommandObjectFile.cpp
lldb/trunk/source/Commands/CommandObjectProcess.cpp
lldb/trunk/source/Core/Module.cpp
lldb/trunk/source/Host/macosx/Host.mm
lldb/trunk/source/Plugins/DynamicLoader/MacOSX-DYLD/DynamicLoaderMacOSXDYLD.cpp
lldb/trunk/source/Plugins/ObjectContainer/Universal-Mach-O/ObjectContainerUniversalMachO.cpp
lldb/trunk/source/Plugins/ObjectFile/ELF/ObjectFileELF.cpp
lldb/trunk/source/Plugins/ObjectFile/ELF/ObjectFileELF.h
lldb/trunk/source/Plugins/ObjectFile/Mach-O/ObjectFileMachO.cpp
lldb/trunk/source/Plugins/ObjectFile/Mach-O/ObjectFileMachO.h
lldb/trunk/source/Plugins/Process/MacOSX-User/source/ProcessMacOSX.cpp
lldb/trunk/source/Plugins/Process/MacOSX-User/source/ProcessMacOSX.h
lldb/trunk/source/Plugins/Process/gdb-remote/ProcessGDBRemote.cpp
lldb/trunk/source/Plugins/Process/gdb-remote/ProcessGDBRemote.h
lldb/trunk/source/Symbol/ObjectFile.cpp
lldb/trunk/source/Target/Process.cpp
lldb/trunk/source/Target/StopInfo.cpp
lldb/trunk/source/Target/Target.cpp
lldb/trunk/source/Target/TargetList.cpp
Modified: lldb/trunk/include/lldb/Core/Module.h
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/include/lldb/Core/Module.h?rev=110624&r1=110623&r2=110624&view=diff
==============================================================================
--- lldb/trunk/include/lldb/Core/Module.h (original)
+++ lldb/trunk/include/lldb/Core/Module.h Mon Aug 9 18:31:02 2010
@@ -13,6 +13,7 @@
#include "lldb/Core/ArchSpec.h"
#include "lldb/Core/Section.h"
#include "lldb/Core/UUID.h"
+#include "lldb/Symbol/ObjectFile.h"
#include "lldb/Host/Mutex.h"
#include "lldb/Host/TimeValue.h"
#include "lldb/Symbol/CompileUnit.h"
@@ -46,6 +47,7 @@
{
public:
friend class ModuleList;
+ friend bool ObjectFile::SetModulesArchitecture (const ArchSpec &new_arch);
enum
{
@@ -343,6 +345,16 @@
const TimeValue &
GetModificationTime () const;
+
+ //------------------------------------------------------------------
+ /// Tells whether this module is capable of being the main executable
+ /// for a process.
+ ///
+ /// @return
+ /// \b true if it is, \b false otherwise.
+ //------------------------------------------------------------------
+ bool
+ IsExecutable ();
//------------------------------------------------------------------
/// Get the number of compile units for this module.
@@ -547,7 +559,7 @@
//------------------------------------------------------------------
mutable Mutex m_mutex; ///< A mutex to keep this object happy in multi-threaded environments.
TimeValue m_mod_time; ///< The modification time for this module when it was created.
- const ArchSpec m_arch; ///< The architecture for this module.
+ ArchSpec m_arch; ///< The architecture for this module.
UUID m_uuid; ///< Each module is assumed to have a unique identifier to help match it up to debug symbols.
FileSpec m_file; ///< The file representation on disk for this module (if there is one).
Flags m_flags; ///< Flags for this module to track what has been parsed already.
@@ -592,7 +604,9 @@
ResolveSymbolContextForAddress (lldb::addr_t vm_addr, bool vm_addr_is_file_addr, uint32_t resolve_scope, Address& so_addr, SymbolContext& sc);
void SymbolIndicesToSymbolContextList (Symtab *symtab, std::vector<uint32_t> &symbol_indexes, SymbolContextList &sc_list);
-
+
+ bool SetArchitecture (const ArchSpec &new_arch);
+
private:
DISALLOW_COPY_AND_ASSIGN (Module);
Modified: lldb/trunk/include/lldb/Host/Host.h
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/include/lldb/Host/Host.h?rev=110624&r1=110623&r2=110624&view=diff
==============================================================================
--- lldb/trunk/include/lldb/Host/Host.h (original)
+++ lldb/trunk/include/lldb/Host/Host.h Mon Aug 9 18:31:02 2010
@@ -13,6 +13,7 @@
#include "lldb/lldb-private.h"
+#include "lldb/Core/StringList.h"
namespace lldb_private {
@@ -273,6 +274,16 @@
static bool
ResolveExecutableInBundle (FileSpec *file);
+
+ static uint32_t
+ ListProcessesMatchingName (const char *name, StringList &matches, std::vector<lldb::pid_t> &pids);
+
+ static ArchSpec
+ GetArchSpecForExistingProcess (lldb::pid_t pid);
+
+ static ArchSpec
+ GetArchSpecForExistingProcess (const char *process_name);
+
};
} // namespace lldb_private
Modified: lldb/trunk/include/lldb/Symbol/ObjectFile.h
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/include/lldb/Symbol/ObjectFile.h?rev=110624&r1=110623&r2=110624&view=diff
==============================================================================
--- lldb/trunk/include/lldb/Symbol/ObjectFile.h (original)
+++ lldb/trunk/include/lldb/Symbol/ObjectFile.h Mon Aug 9 18:31:02 2010
@@ -51,6 +51,8 @@
public PluginInterface,
public ModuleChild
{
+friend class lldb_private::Module;
+
public:
//------------------------------------------------------------------
/// Construct with a parent module, offset, and header data.
@@ -159,7 +161,17 @@
//------------------------------------------------------------------
virtual uint32_t
GetDependentModules (FileSpecList& file_list) = 0;
-
+
+ //------------------------------------------------------------------
+ /// Tells whether this object file is capable of being the main executable
+ /// for a process.
+ ///
+ /// @return
+ /// \b true if it is, \b false otherwise.
+ //------------------------------------------------------------------
+ virtual bool
+ IsExecutable () const = 0;
+
//------------------------------------------------------------------
/// Returns the offset into a file at which this object resides.
///
@@ -290,6 +302,20 @@
lldb::addr_t m_offset; ///< The offset in bytes into the file, or the address in memory
lldb::addr_t m_length; ///< The length of this object file if it is known (can be zero if length is unknown or can't be determined).
DataExtractor m_data; ///< The data for this object file so things can be parsed lazily.
+
+ //------------------------------------------------------------------
+ /// Sets the architecture for a module. At present the architecture
+ /// can only be set if it is invalid. It is not allowed to switch from
+ /// one concrete architecture to another.
+ ///
+ /// @param[in] new_arch
+ /// The architecture this module will be set to.
+ ///
+ /// @return
+ /// Returns \b true if the architecture was changed, \b
+ /// false otherwise.
+ //------------------------------------------------------------------
+ bool SetModulesArchitecture (const ArchSpec &new_arch);
private:
DISALLOW_COPY_AND_ASSIGN (ObjectFile);
Modified: lldb/trunk/include/lldb/Target/Process.h
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/include/lldb/Target/Process.h?rev=110624&r1=110623&r2=110624&view=diff
==============================================================================
--- lldb/trunk/include/lldb/Target/Process.h (original)
+++ lldb/trunk/include/lldb/Target/Process.h Mon Aug 9 18:31:02 2010
@@ -20,6 +20,7 @@
#include "lldb/Core/Broadcaster.h"
#include "lldb/Core/Error.h"
#include "lldb/Core/Event.h"
+#include "lldb/Core/StringList.h"
#include "lldb/Core/ThreadSafeValue.h"
#include "lldb/Core/ThreadSafeSTLMap.h"
#include "lldb/Core/PluginInterface.h"
@@ -313,6 +314,58 @@
//------------------------------------------------------------------
virtual Error
Attach (const char *process_name, bool wait_for_launch);
+
+ //------------------------------------------------------------------
+ /// List the processes matching the given partial name.
+ ///
+ /// FIXME: Is it too heavyweight to create an entire process object to do this?
+ /// The problem is for remote processes we're going to have to set up the same transport
+ /// to get this data as to actually attach. So we need to factor out transport
+ /// and process before we can do this separately from the process.
+ ///
+ /// @param[in] name
+ /// A partial name to match against the current process list.
+ ///
+ /// @param[out] matches
+ /// The list of process names matching \a name.
+ ///
+ /// @param[in] pids
+ /// A vector filled with the pids that correspond to the names in \a matches.
+ ///
+ /// @return
+ /// Returns the number of matching processes.
+ //------------------------------------------------------------------
+
+ virtual uint32_t
+ ListProcessesMatchingName (const char *name, StringList &matches, std::vector<lldb::pid_t> &pids);
+
+ //------------------------------------------------------------------
+ /// Find the architecture of a process by pid.
+ ///
+ /// FIXME: See comment for ListProcessesMatchingName.
+ ///
+ /// @param[in] pid
+ /// A pid to inspect.
+ ///
+ /// @return
+ /// Returns the architecture of the process or an invalid architecture if the process can't be found.
+ //------------------------------------------------------------------
+ virtual ArchSpec
+ GetArchSpecForExistingProcess (lldb::pid_t pid);
+
+ //------------------------------------------------------------------
+ /// Find the architecture of a process by name.
+ ///
+ /// FIXME: See comment for ListProcessesMatchingName.
+ ///
+ /// @param[in] process_name
+ /// The process name to inspect.
+ ///
+ /// @return
+ /// Returns the architecture of the process or an invalid architecture if the process can't be found.
+ //------------------------------------------------------------------
+ virtual ArchSpec
+ GetArchSpecForExistingProcess (const char *process_name);
uint32_t
GetAddressByteSize();
Modified: lldb/trunk/include/lldb/Target/Target.h
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/include/lldb/Target/Target.h?rev=110624&r1=110623&r2=110624&view=diff
==============================================================================
--- lldb/trunk/include/lldb/Target/Target.h (original)
+++ lldb/trunk/include/lldb/Target/Target.h Mon Aug 9 18:31:02 2010
@@ -253,6 +253,27 @@
ArchSpec
GetArchitecture () const;
+
+ //------------------------------------------------------------------
+ /// Set the architecture for this target.
+ ///
+ /// If the current target has no Images read in, then this just sets the architecture, which will
+ /// be used to select the architecture of the ExecutableModule when that is set.
+ /// If the current target has an ExecutableModule, then calling SetArchitecture with a different
+ /// architecture from the currently selected one will reset the ExecutableModule to that slice
+ /// of the file backing the ExecutableModule. If the file backing the ExecutableModule does not
+ /// contain a fork of this architecture, then this code will return false, and the architecture
+ /// won't be changed.
+ /// If the input arch_spec is the same as the already set architecture, this is a no-op.
+ ///
+ /// @param[in] arch_spec
+ /// The new architecture.
+ ///
+ /// @return
+ /// \b true if the architecture was successfully set, \bfalse otherwise.
+ //------------------------------------------------------------------
+ bool
+ SetArchitecture (const ArchSpec &arch_spec);
Debugger &
GetDebugger ()
@@ -300,6 +321,7 @@
// Member variables.
//------------------------------------------------------------------
Debugger & m_debugger;
+ ArchSpec m_arch_spec;
ModuleList m_images; ///< The list of images for this process (shared libraries and anything dynamically loaded).
BreakpointList m_breakpoint_list;
BreakpointList m_internal_breakpoint_list;
Modified: lldb/trunk/source/Commands/CommandObjectFile.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Commands/CommandObjectFile.cpp?rev=110624&r1=110623&r2=110624&view=diff
==============================================================================
--- lldb/trunk/source/Commands/CommandObjectFile.cpp (original)
+++ lldb/trunk/source/Commands/CommandObjectFile.cpp Mon Aug 9 18:31:02 2010
@@ -126,31 +126,14 @@
TargetSP target_sp;
- ArchSpec arch;
- if (m_options.m_arch.IsValid())
- arch = m_options.m_arch;
- else
- {
- arch = lldb_private::GetDefaultArchitecture ();
- if (!arch.IsValid())
- arch = LLDB_ARCH_DEFAULT;
- }
+ ArchSpec arch = m_options.m_arch;
Debugger &debugger = interpreter.GetDebugger();
- Error error = debugger.GetTargetList().CreateTarget (debugger, file_spec, arch, NULL, true, target_sp);
-
- if (error.Fail() && !m_options.m_arch.IsValid())
- {
- if (arch == LLDB_ARCH_DEFAULT_32BIT)
- arch = LLDB_ARCH_DEFAULT_64BIT;
- else
- arch = LLDB_ARCH_DEFAULT_32BIT;
- error = debugger.GetTargetList().CreateTarget (debugger, file_spec, arch, NULL, true, target_sp);
- }
+ Error error = debugger.GetTargetList().CreateTarget (debugger, file_spec, m_options.m_arch, NULL, true, target_sp);
if (target_sp)
{
debugger.GetTargetList().SetCurrentTarget(target_sp.get());
- result.AppendMessageWithFormat ("Current executable set to '%s' (%s).\n", file_path, arch.AsCString());
+ result.AppendMessageWithFormat ("Current executable set to '%s' (%s).\n", file_path, target_sp->GetArchitecture().AsCString());
result.SetStatus (eReturnStatusSuccessFinishNoResult);
}
else
Modified: lldb/trunk/source/Commands/CommandObjectProcess.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Commands/CommandObjectProcess.cpp?rev=110624&r1=110623&r2=110624&view=diff
==============================================================================
--- lldb/trunk/source/Commands/CommandObjectProcess.cpp (original)
+++ lldb/trunk/source/Commands/CommandObjectProcess.cpp Mon Aug 9 18:31:02 2010
@@ -279,110 +279,6 @@
{
public:
- CommandObjectProcessAttach () :
- CommandObject ("process attach",
- "Attaches to a process.",
- "process attach <cmd-options>")
- {
- SetHelpLong("Currently, you must set the executable file before you can attach "
- "to a process.\n");
- }
-
- ~CommandObjectProcessAttach ()
- {
- }
-
- bool
- Execute (CommandInterpreter &interpreter,
- Args& command,
- CommandReturnObject &result)
- {
- Target *target = interpreter.GetDebugger().GetCurrentTarget().get();
- if (target == NULL)
- {
- result.AppendError ("invalid target, set executable file using 'file' command");
- result.SetStatus (eReturnStatusFailed);
- return false;
- }
-
- // If our listener is NULL, users aren't allows to launch
-
- Process *process = interpreter.GetDebugger().GetExecutionContext().process;
- if (process)
- {
- if (process->IsAlive())
- {
- result.AppendErrorWithFormat ("Process %u is currently being debugged, kill the process before attaching.\n", process->GetID());
- result.SetStatus (eReturnStatusFailed);
- return false;
- }
- }
-
- if (command.GetArgumentCount())
- {
- result.AppendErrorWithFormat("Invalid arguments for '%s'.\nUsage: \n", m_cmd_name.c_str(), m_cmd_syntax.c_str());
- result.SetStatus (eReturnStatusFailed);
- }
- else
- {
- const char *plugin_name = NULL;
-
- if (!m_options.plugin_name.empty())
- plugin_name = m_options.plugin_name.c_str();
-
- process = target->CreateProcess (interpreter.GetDebugger().GetListener(), plugin_name).get();
-
- if (process)
- {
- Error error;
- int attach_pid = m_options.pid;
-
- if (attach_pid != LLDB_INVALID_PROCESS_ID)
- {
- error = process->Attach (attach_pid);
- if (error.Success())
- {
- result.SetStatus (eReturnStatusSuccessContinuingNoResult);
- }
- else
- {
- result.AppendErrorWithFormat ("Attaching to process %i failed: %s.\n",
- attach_pid,
- error.AsCString());
- result.SetStatus (eReturnStatusFailed);
- }
- }
- else if (!m_options.name.empty())
- {
- error = process->Attach (m_options.name.c_str(), m_options.waitfor);
- if (error.Success())
- {
- result.SetStatus (eReturnStatusSuccessContinuingNoResult);
- }
- else
- {
- if (m_options.waitfor)
- result.AppendErrorWithFormat ("Waiting for a process to launch named '%s': %s\n",
- m_options.name.c_str(),
- error.AsCString());
- else
- result.AppendErrorWithFormat ("Failed to a process named '%s': %s\n",
- m_options.name.c_str(),
- error.AsCString());
- result.SetStatus (eReturnStatusFailed);
- }
- }
- }
- }
- return result.Succeeded();
- }
-
- Options *
- GetOptions ()
- {
- return &m_options;
- }
-
class CommandOptions : public Options
{
public:
@@ -448,6 +344,68 @@
return g_option_table;
}
+ virtual bool
+ HandleOptionArgumentCompletion (CommandInterpreter &interpreter,
+ Args &input,
+ int cursor_index,
+ int char_pos,
+ OptionElementVector &opt_element_vector,
+ int opt_element_index,
+ int match_start_point,
+ int max_return_elements,
+ bool &word_complete,
+ StringList &matches)
+ {
+ int opt_arg_pos = opt_element_vector[opt_element_index].opt_arg_pos;
+ int opt_defs_index = opt_element_vector[opt_element_index].opt_defs_index;
+
+ // We are only completing the name option for now...
+
+ const lldb::OptionDefinition *opt_defs = GetDefinitions();
+ if (opt_defs[opt_defs_index].short_option == 'n')
+ {
+ // Are we in the name?
+
+ // Look to see if there is a -P argument provided, and if so use that plugin, otherwise
+ // use the default plugin.
+ Process *process = interpreter.GetDebugger().GetExecutionContext().process;
+ bool need_to_delete_process = false;
+
+ const char *partial_name = NULL;
+ partial_name = input.GetArgumentAtIndex(opt_arg_pos);
+
+ if (process && process->IsAlive())
+ return true;
+
+ Target *target = interpreter.GetDebugger().GetCurrentTarget().get();
+ if (target == NULL)
+ {
+ // No target has been set yet, for now do host completion. Otherwise I don't know how we would
+ // figure out what the right target to use is...
+ std::vector<lldb::pid_t> pids;
+ Host::ListProcessesMatchingName (partial_name, matches, pids);
+ return true;
+ }
+ if (!process)
+ {
+ process = target->CreateProcess (interpreter.GetDebugger().GetListener(), partial_name).get();
+ need_to_delete_process = true;
+ }
+
+ if (process)
+ {
+ matches.Clear();
+ std::vector<lldb::pid_t> pids;
+ process->ListProcessesMatchingName (NULL, matches, pids);
+ if (need_to_delete_process)
+ target->DeleteCurrentProcess();
+ return true;
+ }
+ }
+
+ return false;
+ }
+
// Options table: Required for subclasses of Options.
static lldb::OptionDefinition g_option_table[];
@@ -460,6 +418,211 @@
bool waitfor;
};
+ CommandObjectProcessAttach () :
+ CommandObject ("process attach",
+ "Attaches to a process.",
+ "process attach <cmd-options>")
+ {
+ SetHelpLong("Currently, you must set the executable file before you can attach "
+ "to a process.\n");
+ }
+
+ ~CommandObjectProcessAttach ()
+ {
+ }
+
+ bool
+ Execute (CommandInterpreter &interpreter,
+ Args& command,
+ CommandReturnObject &result)
+ {
+ Target *target = interpreter.GetDebugger().GetCurrentTarget().get();
+
+ Process *process = interpreter.GetDebugger().GetExecutionContext().process;
+ if (process)
+ {
+ if (process->IsAlive())
+ {
+ result.AppendErrorWithFormat ("Process %u is currently being debugged, kill the process before attaching.\n",
+ process->GetID());
+ result.SetStatus (eReturnStatusFailed);
+ return false;
+ }
+ }
+
+ if (target == NULL)
+ {
+ // If there isn't a current target create one.
+ TargetSP new_target_sp;
+ FileSpec emptyFileSpec;
+ ArchSpec emptyArchSpec;
+ Error error;
+
+ error = interpreter.GetDebugger().GetTargetList().CreateTarget(interpreter.GetDebugger(),
+ emptyFileSpec,
+ emptyArchSpec,
+ NULL,
+ false,
+ new_target_sp);
+ target = new_target_sp.get();
+ if (target == NULL || error.Fail())
+ {
+ result.AppendError(error.AsCString("Error creating empty target"));
+ return false;
+ }
+ interpreter.GetDebugger().GetTargetList().SetCurrentTarget(target);
+ }
+
+ // Record the old executable module, we want to issue a warning if the process of attaching changed the
+ // current executable (like somebody said "file foo" then attached to a PID whose executable was bar.)
+
+ ModuleSP old_exec_module_sp = target->GetExecutableModule();
+ ArchSpec old_arch_spec = target->GetArchitecture();
+
+ if (command.GetArgumentCount())
+ {
+ result.AppendErrorWithFormat("Invalid arguments for '%s'.\nUsage: \n", m_cmd_name.c_str(), m_cmd_syntax.c_str());
+ result.SetStatus (eReturnStatusFailed);
+ }
+ else
+ {
+ const char *plugin_name = NULL;
+
+ if (!m_options.plugin_name.empty())
+ plugin_name = m_options.plugin_name.c_str();
+
+ process = target->CreateProcess (interpreter.GetDebugger().GetListener(), plugin_name).get();
+
+ if (process)
+ {
+ Error error;
+ int attach_pid = m_options.pid;
+
+ // If we are waiting for a process with this name to show up, do that first.
+ if (m_options.waitfor)
+ {
+ if (m_options.name.empty())
+ {
+ result.AppendError("Invalid arguments: must supply a process name with the waitfor option.\n");
+ result.SetStatus (eReturnStatusFailed);
+ return false;
+ }
+ else
+ {
+ error = process->Attach (m_options.name.c_str(), m_options.waitfor);
+ if (error.Success())
+ {
+ result.SetStatus (eReturnStatusSuccessContinuingNoResult);
+ }
+ else
+ {
+ result.AppendErrorWithFormat ("Waiting for a process to launch named '%s': %s\n",
+ m_options.name.c_str(),
+ error.AsCString());
+ result.SetStatus (eReturnStatusFailed);
+ return false;
+ }
+ }
+ }
+ else
+ {
+ // If the process was specified by name look it up, so we can warn if there are multiple
+ // processes with this pid.
+
+ if (attach_pid == LLDB_INVALID_PROCESS_ID && !m_options.name.empty())
+ {
+ std::vector<lldb::pid_t> pids;
+ StringList matches;
+
+ process->ListProcessesMatchingName(m_options.name.c_str(), matches, pids);
+ if (matches.GetSize() > 1)
+ {
+ result.AppendErrorWithFormat("More than one process named %s\n", m_options.name.c_str());
+ result.SetStatus (eReturnStatusFailed);
+ return false;
+ }
+ else if (matches.GetSize() == 0)
+ {
+ result.AppendErrorWithFormat("Could not find a process named %s\n", m_options.name.c_str());
+ result.SetStatus (eReturnStatusFailed);
+ return false;
+ }
+ else
+ {
+ attach_pid = pids[0];
+ }
+
+ }
+
+ if (attach_pid != LLDB_INVALID_PROCESS_ID)
+ {
+ error = process->Attach (attach_pid);
+ if (error.Success())
+ {
+ result.SetStatus (eReturnStatusSuccessContinuingNoResult);
+ }
+ else
+ {
+ result.AppendErrorWithFormat ("Attaching to process %i failed: %s.\n",
+ attach_pid,
+ error.AsCString());
+ result.SetStatus (eReturnStatusFailed);
+ }
+ }
+ else
+ {
+ result.AppendErrorWithFormat ("No PID specified for attach\n",
+ attach_pid,
+ error.AsCString());
+ result.SetStatus (eReturnStatusFailed);
+
+ }
+ }
+ }
+ }
+
+ if (result.Succeeded())
+ {
+ // Okay, we're done. Last step is to warn if the executable module has changed:
+ if (!old_exec_module_sp)
+ {
+ char new_path[PATH_MAX + 1];
+ target->GetExecutableModule()->GetFileSpec().GetPath(new_path, PATH_MAX);
+
+ result.AppendMessageWithFormat("Executable module set to \"%s\".\n",
+ new_path);
+ }
+ else if (old_exec_module_sp->GetFileSpec() != target->GetExecutableModule()->GetFileSpec())
+ {
+ char old_path[PATH_MAX + 1];
+ char new_path[PATH_MAX + 1];
+
+ old_exec_module_sp->GetFileSpec().GetPath(old_path, PATH_MAX);
+ target->GetExecutableModule()->GetFileSpec().GetPath (new_path, PATH_MAX);
+
+ result.AppendWarningWithFormat("Executable module changed from \"%s\" to \"%s\".\n",
+ old_path, new_path);
+ }
+
+ if (!old_arch_spec.IsValid())
+ {
+ result.AppendMessageWithFormat ("Architecture set to: %s.\n", target->GetArchitecture().AsCString());
+ }
+ else if (old_arch_spec != target->GetArchitecture())
+ {
+ result.AppendWarningWithFormat("Architecture changed from %s to %s.\n",
+ old_arch_spec.AsCString(), target->GetArchitecture().AsCString());
+ }
+ }
+ return result.Succeeded();
+ }
+
+ Options *
+ GetOptions ()
+ {
+ return &m_options;
+ }
+
protected:
CommandOptions m_options;
Modified: lldb/trunk/source/Core/Module.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Core/Module.cpp?rev=110624&r1=110623&r2=110624&view=diff
==============================================================================
--- lldb/trunk/source/Core/Module.cpp (original)
+++ lldb/trunk/source/Core/Module.cpp Mon Aug 9 18:31:02 2010
@@ -43,7 +43,6 @@
m_object_name.IsEmpty() ? "" : "(",
m_object_name.IsEmpty() ? "" : m_object_name.AsCString(""),
m_object_name.IsEmpty() ? "" : ")");
-
}
Module::~Module()
@@ -516,3 +515,30 @@
{
return m_mod_time;
}
+
+bool
+Module::IsExecutable ()
+{
+ if (GetObjectFile() == NULL)
+ return false;
+ else
+ return GetObjectFile()->IsExecutable();
+}
+
+bool
+Module::SetArchitecture (const ArchSpec &new_arch)
+{
+ if (m_arch == new_arch)
+ return true;
+ else if (!m_arch.IsValid())
+ {
+ m_arch = new_arch;
+ return true;
+ }
+ else
+ {
+ return false;
+ }
+
+}
+
Modified: lldb/trunk/source/Host/macosx/Host.mm
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Host/macosx/Host.mm?rev=110624&r1=110623&r2=110624&view=diff
==============================================================================
--- lldb/trunk/source/Host/macosx/Host.mm (original)
+++ lldb/trunk/source/Host/macosx/Host.mm Mon Aug 9 18:31:02 2010
@@ -15,6 +15,8 @@
#include <stddef.h>
#include <sys/sysctl.h>
#include <unistd.h>
+#include <libproc.h>
+#include <sys/proc_info.h>
#include <map>
#include <string>
@@ -802,3 +804,86 @@
}
}
+uint32_t
+Host::ListProcessesMatchingName (const char *name, StringList &matches, std::vector<lldb::pid_t> &pids)
+{
+
+ int num_pids;
+ int size_of_pids;
+ int *pid_list;
+ uint32_t num_matches = 0;
+
+ size_of_pids = proc_listpids(PROC_ALL_PIDS, 0, NULL, 0);
+ if (size_of_pids == -1)
+ return 0;
+
+ num_pids = size_of_pids/sizeof(int);
+ pid_list = (int *) malloc(size_of_pids);
+ size_of_pids = proc_listpids(PROC_ALL_PIDS, 0, pid_list, size_of_pids);
+ if (size_of_pids == -1)
+ return 0;
+
+ pid_t our_pid = getpid();
+
+ for (int i = 0; i < num_pids; i++)
+ {
+ struct proc_bsdinfo bsd_info;
+ int error = proc_pidinfo (pid_list[i], PROC_PIDTBSDINFO, (uint64_t) 0, &bsd_info, PROC_PIDTBSDINFO_SIZE);
+ if (error == 0)
+ continue;
+
+ // Don't offer to attach to zombie processes, already traced or exiting
+ // processes, and of course, ourselves... It looks like passing the second arg of
+ // 0 to proc_listpids will exclude zombies anyway, but that's not documented so...
+ if ((bsd_info.pbi_flags & (PROC_FLAG_TRACED | PROC_FLAG_INEXIT) != 0)
+ || (bsd_info.pbi_status == SZOMB)
+ || (bsd_info.pbi_pid == our_pid))
+ continue;
+ char pid_name[MAXCOMLEN * 2 + 1];
+ int name_len;
+ name_len = proc_name(bsd_info.pbi_pid, pid_name, MAXCOMLEN * 2);
+ if (name_len == 0)
+ continue;
+
+ if (strstr(pid_name, name) != pid_name)
+ continue;
+ matches.AppendString (pid_name);
+ pids.push_back (bsd_info.pbi_pid);
+ num_matches++;
+ }
+
+ return num_matches;
+}
+
+ArchSpec
+Host::GetArchSpecForExistingProcess (lldb::pid_t pid)
+{
+ ArchSpec return_spec;
+
+ struct proc_bsdinfo bsd_info;
+ int error = proc_pidinfo (pid, PROC_PIDTBSDINFO, (uint64_t) 0, &bsd_info, PROC_PIDTBSDINFO_SIZE);
+ if (error == 0)
+ return return_spec;
+ if (bsd_info.pbi_flags & PROC_FLAG_LP64)
+ return_spec.SetArch(LLDB_ARCH_DEFAULT_64BIT);
+ else
+ return_spec.SetArch(LLDB_ARCH_DEFAULT_32BIT);
+
+ return return_spec;
+}
+
+ArchSpec
+Host::GetArchSpecForExistingProcess (const char *process_name)
+{
+ ArchSpec returnSpec;
+ StringList matches;
+ std::vector<lldb::pid_t> pids;
+ if (ListProcessesMatchingName(process_name, matches, pids))
+ {
+ if (matches.GetSize() == 1)
+ {
+ return GetArchSpecForExistingProcess(pids[0]);
+ }
+ }
+ return returnSpec;
+}
Modified: lldb/trunk/source/Plugins/DynamicLoader/MacOSX-DYLD/DynamicLoaderMacOSXDYLD.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Plugins/DynamicLoader/MacOSX-DYLD/DynamicLoaderMacOSXDYLD.cpp?rev=110624&r1=110623&r2=110624&view=diff
==============================================================================
--- lldb/trunk/source/Plugins/DynamicLoader/MacOSX-DYLD/DynamicLoaderMacOSXDYLD.cpp (original)
+++ lldb/trunk/source/Plugins/DynamicLoader/MacOSX-DYLD/DynamicLoaderMacOSXDYLD.cpp Mon Aug 9 18:31:02 2010
@@ -1016,8 +1016,7 @@
return m_break_id != LLDB_INVALID_BREAK_ID;
}
-//----------------------------------------------------------------------Target.h
-
+//----------------------------------------------------------------------
// Member function that gets called when the process state changes.
//----------------------------------------------------------------------
void
Modified: lldb/trunk/source/Plugins/ObjectContainer/Universal-Mach-O/ObjectContainerUniversalMachO.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Plugins/ObjectContainer/Universal-Mach-O/ObjectContainerUniversalMachO.cpp?rev=110624&r1=110623&r2=110624&view=diff
==============================================================================
--- lldb/trunk/source/Plugins/ObjectContainer/Universal-Mach-O/ObjectContainerUniversalMachO.cpp (original)
+++ lldb/trunk/source/Plugins/ObjectContainer/Universal-Mach-O/ObjectContainerUniversalMachO.cpp Mon Aug 9 18:31:02 2010
@@ -199,7 +199,18 @@
ObjectContainerUniversalMachO::GetObjectFile (const FileSpec *file)
{
uint32_t arch_idx = 0;
- const ArchSpec arch = m_module->GetArchitecture();
+ ArchSpec arch;
+ // If the module hasn't specified an architecture yet, set it to the default
+ // architecture:
+ if (!m_module->GetArchitecture().IsValid())
+ {
+ arch = lldb_private::GetDefaultArchitecture ();
+ if (!arch.IsValid())
+ arch = LLDB_ARCH_DEFAULT;
+ }
+ else
+ arch = m_module->GetArchitecture();
+
ArchSpec curr_arch;
for (arch_idx = 0; arch_idx < m_header.nfat_arch; ++arch_idx)
{
Modified: lldb/trunk/source/Plugins/ObjectFile/ELF/ObjectFileELF.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Plugins/ObjectFile/ELF/ObjectFileELF.cpp?rev=110624&r1=110623&r2=110624&view=diff
==============================================================================
--- lldb/trunk/source/Plugins/ObjectFile/ELF/ObjectFileELF.cpp (original)
+++ lldb/trunk/source/Plugins/ObjectFile/ELF/ObjectFileELF.cpp Mon Aug 9 18:31:02 2010
@@ -145,6 +145,13 @@
{
}
+bool
+ObjectFileELF::IsExecutable() const
+{
+ // FIXME: How is this marked in ELF?
+ return false;
+}
+
ByteOrder
ObjectFileELF::GetByteOrder() const
{
Modified: lldb/trunk/source/Plugins/ObjectFile/ELF/ObjectFileELF.h
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Plugins/ObjectFile/ELF/ObjectFileELF.h?rev=110624&r1=110623&r2=110624&view=diff
==============================================================================
--- lldb/trunk/source/Plugins/ObjectFile/ELF/ObjectFileELF.h (original)
+++ lldb/trunk/source/Plugins/ObjectFile/ELF/ObjectFileELF.h Mon Aug 9 18:31:02 2010
@@ -86,6 +86,9 @@
virtual lldb::ByteOrder
GetByteOrder() const;
+ virtual bool
+ IsExecutable () const;
+
virtual size_t
GetAddressByteSize() const;
Modified: lldb/trunk/source/Plugins/ObjectFile/Mach-O/ObjectFileMachO.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Plugins/ObjectFile/Mach-O/ObjectFileMachO.cpp?rev=110624&r1=110623&r2=110624&view=diff
==============================================================================
--- lldb/trunk/source/Plugins/ObjectFile/Mach-O/ObjectFileMachO.cpp (original)
+++ lldb/trunk/source/Plugins/ObjectFile/Mach-O/ObjectFileMachO.cpp Mon Aug 9 18:31:02 2010
@@ -161,7 +161,8 @@
m_data.GetU32(&offset, &m_header.cputype, 6);
ArchSpec mach_arch(eArchTypeMachO, m_header.cputype, m_header.cpusubtype);
- if (mach_arch == m_module->GetArchitecture())
+
+ if (SetModulesArchitecture (mach_arch))
{
// Read in all only the load command data
DataBufferSP data_sp(m_file.ReadFileContents(m_offset, m_header.sizeofcmds + MachHeaderSizeFromMagic(m_header.magic)));
@@ -184,6 +185,11 @@
return m_data.GetByteOrder ();
}
+bool
+ObjectFileMachO::IsExecutable() const
+{
+ return m_header.filetype == HeaderFileTypeExecutable;
+}
size_t
ObjectFileMachO::GetAddressByteSize () const
Modified: lldb/trunk/source/Plugins/ObjectFile/Mach-O/ObjectFileMachO.h
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Plugins/ObjectFile/Mach-O/ObjectFileMachO.h?rev=110624&r1=110623&r2=110624&view=diff
==============================================================================
--- lldb/trunk/source/Plugins/ObjectFile/Mach-O/ObjectFileMachO.h (original)
+++ lldb/trunk/source/Plugins/ObjectFile/Mach-O/ObjectFileMachO.h Mon Aug 9 18:31:02 2010
@@ -66,6 +66,9 @@
virtual lldb::ByteOrder
GetByteOrder () const;
+
+ virtual bool
+ IsExecutable () const;
virtual size_t
GetAddressByteSize () const;
Modified: lldb/trunk/source/Plugins/Process/MacOSX-User/source/ProcessMacOSX.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Plugins/Process/MacOSX-User/source/ProcessMacOSX.cpp?rev=110624&r1=110623&r2=110624&view=diff
==============================================================================
--- lldb/trunk/source/Plugins/Process/MacOSX-User/source/ProcessMacOSX.cpp (original)
+++ lldb/trunk/source/Plugins/Process/MacOSX-User/source/ProcessMacOSX.cpp Mon Aug 9 18:31:02 2010
@@ -2208,5 +2208,10 @@
}
}
+uint32_t
+ProcessMacOSX::ListProcessesMatchingName (const char *name, lldb_private::StringList &matches, std::vector<lldb::pid_t> &pids)
+{
+ return Host::ListProcessesMatchingName (name, matches, pids);
+}
Modified: lldb/trunk/source/Plugins/Process/MacOSX-User/source/ProcessMacOSX.h
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Plugins/Process/MacOSX-User/source/ProcessMacOSX.h?rev=110624&r1=110623&r2=110624&view=diff
==============================================================================
--- lldb/trunk/source/Plugins/Process/MacOSX-User/source/ProcessMacOSX.h (original)
+++ lldb/trunk/source/Plugins/Process/MacOSX-User/source/ProcessMacOSX.h Mon Aug 9 18:31:02 2010
@@ -18,6 +18,7 @@
// Other libraries and framework includes
#include "lldb/Core/ArchSpec.h"
#include "lldb/Core/ThreadSafeValue.h"
+#include "lldb/Core/StringList.h"
#include "lldb/Target/Process.h"
#include "lldb/Target/Thread.h"
@@ -110,6 +111,9 @@
virtual void
DidAttach ();
+
+ virtual uint32_t
+ ListProcessesMatchingName (const char *name, lldb_private::StringList &matches, std::vector<lldb::pid_t> &pids);
//------------------------------------------------------------------
// PluginInterface protocol
Modified: lldb/trunk/source/Plugins/Process/gdb-remote/ProcessGDBRemote.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Plugins/Process/gdb-remote/ProcessGDBRemote.cpp?rev=110624&r1=110623&r2=110624&view=diff
==============================================================================
--- lldb/trunk/source/Plugins/Process/gdb-remote/ProcessGDBRemote.cpp (original)
+++ lldb/trunk/source/Plugins/Process/gdb-remote/ProcessGDBRemote.cpp Mon Aug 9 18:31:02 2010
@@ -93,7 +93,8 @@
ModuleSP exe_module_sp(target.GetExecutableModule());
if (exe_module_sp.get())
return exe_module_sp->GetFileSpec().Exists();
- return false;
+ // However, if there is no executable module, we return true since we might be preparing to attach.
+ return true;
}
//----------------------------------------------------------------------
@@ -106,7 +107,6 @@
m_stdio_communication ("gdb-remote.stdio"),
m_stdio_mutex (Mutex::eMutexTypeRecursive),
m_stdout_data (),
- m_arch_spec (),
m_byte_order (eByteOrderHost),
m_gdb_comm(),
m_debugserver_pid (LLDB_INVALID_PROCESS_ID),
@@ -124,7 +124,8 @@
m_max_memory_size (512),
m_libunwind_target_type (UNW_TARGET_UNSPECIFIED),
m_libunwind_addr_space (NULL),
- m_waiting_for_attach (false)
+ m_waiting_for_attach (false),
+ m_local_debugserver (true)
{
}
@@ -563,11 +564,9 @@
{
m_dispatch_queue_offsets_addr = LLDB_INVALID_ADDRESS;
- Module * exe_module = GetTarget().GetExecutableModule ().get();
+ Module * exe_module = GetTarget().GetExecutableModule ().get();
assert(exe_module);
- m_arch_spec = exe_module->GetArchitecture();
-
ObjectFile *exe_objfile = exe_module->GetObjectFile();
assert(exe_objfile);
@@ -580,8 +579,9 @@
// 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 arch_spec = GetTarget().GetArchitecture();
- if (m_arch_spec.IsValid() && m_arch_spec == ArchSpec ("arm"))
+ if (arch_spec.IsValid() && arch_spec == ArchSpec ("arm"))
{
// For ARM we can't trust the arch of the process as it could
// have an armv6 object file, but be running on armv7 kernel.
@@ -589,7 +589,7 @@
}
if (!inferior_arch.IsValid())
- inferior_arch = m_arch_spec;
+ inferior_arch = arch_spec;
if (vendor == NULL)
vendor = Host::GetVendorString().AsCString("apple");
@@ -622,11 +622,11 @@
Error error;
// Clear out and clean up from any current state
Clear();
- // HACK: require arch be set correctly at the target level until we can
- // figure out a good way to determine the arch of what we are attaching to
- m_arch_spec = m_target.GetArchitecture();
-
+ ArchSpec arch_spec = GetTarget().GetArchitecture();
+
//Log *log = ProcessGDBRemoteLog::GetLogIfAllCategoriesSet (GDBR_LOG_PROCESS);
+
+
if (attach_pid != LLDB_INVALID_PROCESS_ID)
{
SetPrivateState (eStateAttaching);
@@ -638,7 +638,7 @@
NULL,
LLDB_INVALID_PROCESS_ID,
NULL, false,
- m_arch_spec);
+ arch_spec);
if (error.Fail())
{
@@ -724,7 +724,6 @@
Clear();
// HACK: require arch be set correctly at the target level until we can
// figure out a good way to determine the arch of what we are attaching to
- m_arch_spec = m_target.GetArchitecture();
//Log *log = ProcessGDBRemoteLog::GetLogIfAllCategoriesSet (GDBR_LOG_PROCESS);
if (process_name && process_name[0])
@@ -732,6 +731,7 @@
SetPrivateState (eStateAttaching);
char host_port[128];
+ ArchSpec arch_spec = GetTarget().GetArchitecture();
snprintf (host_port, sizeof(host_port), "localhost:%u", get_random_port ());
error = StartDebugserverProcess (host_port,
NULL,
@@ -739,7 +739,7 @@
NULL,
LLDB_INVALID_PROCESS_ID,
NULL, false,
- m_arch_spec);
+ arch_spec);
if (error.Fail())
{
const char *error_string = error.AsCString();
@@ -840,9 +840,26 @@
void
ProcessGDBRemote::DidAttach ()
{
- DidLaunchOrAttach ();
+ // If we haven't got an executable module yet, then we should make a dynamic loader, and
+ // see if it can find the executable module for us. If we do have an executable module,
+ // make sure it matches the process we've just attached to.
+
+ ModuleSP exe_module_sp = GetTarget().GetExecutableModule();
+ if (!m_dynamic_loader_ap.get())
+ {
+ m_dynamic_loader_ap.reset(DynamicLoader::FindPlugin(this, "dynamic-loader.macosx-dyld"));
+ }
+
if (m_dynamic_loader_ap.get())
m_dynamic_loader_ap->DidAttach();
+
+ Module * new_exe_module = GetTarget().GetExecutableModule().get();
+ if (new_exe_module == NULL)
+ {
+
+ }
+
+ DidLaunchOrAttach ();
}
Error
@@ -876,7 +893,7 @@
static const uint8_t g_ppc_breakpoint_opcode[] = { 0x7F, 0xC0, 0x00, 0x08 };
static const uint8_t g_i386_breakpoint_opcode[] = { 0xCC };
- ArchSpec::CPU arch_cpu = m_arch_spec.GetGenericCPUType();
+ ArchSpec::CPU arch_cpu = GetTarget().GetArchitecture().GetGenericCPUType();
switch (arch_cpu)
{
case ArchSpec::eCPU_i386:
@@ -1060,13 +1077,16 @@
void
ProcessGDBRemote::RefreshStateAfterStop ()
{
+ // FIXME - add a variable to tell that we're in the middle of attaching if we
+ // need to know that.
// We must be attaching if we don't already have a valid architecture
- if (!m_arch_spec.IsValid())
- {
- Module *exe_module = GetTarget().GetExecutableModule().get();
- if (exe_module)
- m_arch_spec = exe_module->GetArchitecture();
- }
+// if (!GetTarget().GetArchitecture().IsValid())
+// {
+// Module *exe_module = GetTarget().GetExecutableModule().get();
+// if (exe_module)
+// m_arch_spec = exe_module->GetArchitecture();
+// }
+
// Let all threads recover from stopping and do any clean up based
// on the previous thread state (if any).
m_thread_list.RefreshStateAfterStop();
@@ -2251,3 +2271,19 @@
return dispatch_queue_name.c_str();
}
+uint32_t
+ProcessGDBRemote::ListProcessesMatchingName (const char *name, StringList &matches, std::vector<lldb::pid_t> &pids)
+{
+ // If we are planning to launch the debugserver remotely, then we need to fire up a debugserver
+ // process and ask it for the list of processes. But if we are local, we can let the Host do it.
+ if (m_local_debugserver)
+ {
+ return Host::ListProcessesMatchingName (name, matches, pids);
+ }
+ else
+ {
+ // FIXME: Implement talking to the remote debugserver.
+ return 0;
+ }
+
+}
Modified: lldb/trunk/source/Plugins/Process/gdb-remote/ProcessGDBRemote.h
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Plugins/Process/gdb-remote/ProcessGDBRemote.h?rev=110624&r1=110623&r2=110624&view=diff
==============================================================================
--- lldb/trunk/source/Plugins/Process/gdb-remote/ProcessGDBRemote.h (original)
+++ lldb/trunk/source/Plugins/Process/gdb-remote/ProcessGDBRemote.h Mon Aug 9 18:31:02 2010
@@ -21,6 +21,7 @@
#include "lldb/Core/Error.h"
#include "lldb/Core/InputReader.h"
#include "lldb/Core/StreamString.h"
+#include "lldb/Core/StringList.h"
#include "lldb/Core/ThreadSafeValue.h"
#include "lldb/Target/Process.h"
#include "lldb/Target/Thread.h"
@@ -67,6 +68,9 @@
virtual bool
CanDebug (lldb_private::Target &target);
+ virtual uint32_t
+ ListProcessesMatchingName (const char *name, lldb_private::StringList &matches, std::vector<lldb::pid_t> &pids);
+
//------------------------------------------------------------------
// Creating a new process, or attaching to an existing one
//------------------------------------------------------------------
@@ -262,17 +266,6 @@
void
AppendSTDOUT (const char* s, size_t len);
- lldb_private::ArchSpec&
- GetArchSpec()
- {
- return m_arch_spec;
- }
- const lldb_private::ArchSpec&
- GetArchSpec() const
- {
- return m_arch_spec;
- }
-
void
Clear ( );
@@ -328,7 +321,6 @@
lldb_private::Communication m_stdio_communication;
lldb_private::Mutex m_stdio_mutex; // Multithreaded protection for stdio
std::string m_stdout_data;
- lldb_private::ArchSpec m_arch_spec;
lldb::ByteOrder m_byte_order;
GDBRemoteCommunication m_gdb_comm;
lldb::pid_t m_debugserver_pid;
@@ -349,6 +341,7 @@
lldb_private::unw_targettype_t m_libunwind_target_type;
lldb_private::unw_addr_space_t m_libunwind_addr_space; // libunwind address space object for this process.
bool m_waiting_for_attach;
+ bool m_local_debugserver; // Is the debugserver process we are talking to local or on another machine.
void
ResetGDBRemoteState ();
Modified: lldb/trunk/source/Symbol/ObjectFile.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Symbol/ObjectFile.cpp?rev=110624&r1=110623&r2=110624&view=diff
==============================================================================
--- lldb/trunk/source/Symbol/ObjectFile.cpp (original)
+++ lldb/trunk/source/Symbol/ObjectFile.cpp Mon Aug 9 18:31:02 2010
@@ -90,3 +90,10 @@
}
return NULL;
}
+
+bool
+ObjectFile::SetModulesArchitecture (const ArchSpec &new_arch)
+{
+ return m_module->SetArchitecture (new_arch);
+}
+
Modified: lldb/trunk/source/Target/Process.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Target/Process.cpp?rev=110624&r1=110623&r2=110624&view=diff
==============================================================================
--- lldb/trunk/source/Target/Process.cpp (original)
+++ lldb/trunk/source/Target/Process.cpp Mon Aug 9 18:31:02 2010
@@ -1048,6 +1048,24 @@
if (state == eStateStopped || state == eStateCrashed)
{
DidAttach ();
+ // Figure out which one is the executable, and set that in our target:
+ ModuleList &modules = GetTarget().GetImages();
+
+ size_t num_modules = modules.GetSize();
+ for (int i = 0; i < num_modules; i++)
+ {
+ ModuleSP module_sp = modules.GetModuleAtIndex(i);
+ if (module_sp->IsExecutable())
+ {
+ ModuleSP exec_module = GetTarget().GetExecutableModule();
+ if (!exec_module || exec_module != module_sp)
+ {
+
+ GetTarget().SetExecutableModule (module_sp, false);
+ }
+ break;
+ }
+ }
// This delays passing the stopped event to listeners till DidLaunch gets
// a chance to complete...
@@ -1073,6 +1091,16 @@
m_target_triple.Clear();
m_abi_sp.reset();
+ // Find the process and its architecture. Make sure it matches the architecture
+ // of the current Target, and if not adjust it.
+
+ ArchSpec attach_spec = GetArchSpecForExistingProcess (attach_pid);
+ if (attach_spec != GetTarget().GetArchitecture())
+ {
+ // Set the architecture on the target.
+ GetTarget().SetArchitecture(attach_spec);
+ }
+
Error error (WillAttachToProcessWithID(attach_pid));
if (error.Success())
{
@@ -1102,6 +1130,16 @@
{
m_target_triple.Clear();
m_abi_sp.reset();
+
+ // Find the process and its architecture. Make sure it matches the architecture
+ // of the current Target, and if not adjust it.
+
+ ArchSpec attach_spec = GetArchSpecForExistingProcess (process_name);
+ if (attach_spec != GetTarget().GetArchitecture())
+ {
+ // Set the architecture on the target.
+ GetTarget().SetArchitecture(attach_spec);
+ }
Error error (WillAttachToProcessWithName(process_name, wait_for_launch));
if (error.Success())
@@ -1863,3 +1901,22 @@
return m_objc_object_printer;
}
+uint32_t
+Process::ListProcessesMatchingName (const char *name, StringList &matches, std::vector<lldb::pid_t> &pids)
+{
+ return 0;
+}
+
+ArchSpec
+Process::GetArchSpecForExistingProcess (lldb::pid_t pid)
+{
+ return Host::GetArchSpecForExistingProcess (pid);
+}
+
+ArchSpec
+Process::GetArchSpecForExistingProcess (const char *process_name)
+{
+ return Host::GetArchSpecForExistingProcess (process_name);
+}
+
+
Modified: lldb/trunk/source/Target/StopInfo.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Target/StopInfo.cpp?rev=110624&r1=110623&r2=110624&view=diff
==============================================================================
--- lldb/trunk/source/Target/StopInfo.cpp (original)
+++ lldb/trunk/source/Target/StopInfo.cpp Mon Aug 9 18:31:02 2010
@@ -79,7 +79,7 @@
&m_thread.GetProcess(),
&m_thread,
m_thread.GetStackFrameAtIndex(0).get(),
- false);
+ true);
m_should_stop = bp_site_sp->ShouldStop (&context);
}
Modified: lldb/trunk/source/Target/Target.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Target/Target.cpp?rev=110624&r1=110623&r2=110624&view=diff
==============================================================================
--- lldb/trunk/source/Target/Target.cpp (original)
+++ lldb/trunk/source/Target/Target.cpp Mon Aug 9 18:31:02 2010
@@ -373,6 +373,10 @@
m_images.Append(executable_sp); // The first image is our exectuable file
ArchSpec exe_arch = executable_sp->GetArchitecture();
+ // If we haven't set an architecture yet, reset our architecture based on what we found in the executable module.
+ if (!m_arch_spec.IsValid())
+ m_arch_spec = exe_arch;
+
FileSpecList dependent_files;
ObjectFile * executable_objfile = executable_sp->GetObjectFile();
if (executable_objfile == NULL)
@@ -426,18 +430,63 @@
ArchSpec
Target::GetArchitecture () const
{
- ArchSpec arch;
- if (m_images.GetSize() > 0)
+ return m_arch_spec;
+}
+
+bool
+Target::SetArchitecture (const ArchSpec &arch_spec)
+{
+ if (m_arch_spec == arch_spec)
{
- Module *exe_module = m_images.GetModulePointerAtIndex(0);
- if (exe_module)
- arch = exe_module->GetArchitecture();
+ // If we're setting the architecture to our current architecture, we
+ // don't need to do anything.
+ return true;
+ }
+ else if (!m_arch_spec.IsValid())
+ {
+ // If we haven't got a valid arch spec, then we just need to set it.
+ m_arch_spec = arch_spec;
+ return true;
+ }
+ else
+ {
+ // If we have an executable file, try to reset the executable to the desired architecture
+ m_arch_spec = arch_spec;
+ ModuleSP executable_sp = GetExecutableModule ();
+ m_images.Clear();
+ m_scratch_ast_context_ap.reset();
+ m_triple.Clear();
+ // Need to do something about unsetting breakpoints.
+
+ if (executable_sp)
+ {
+ FileSpec exec_file_spec = executable_sp->GetFileSpec();
+ Error error = ModuleList::GetSharedModule(exec_file_spec,
+ arch_spec,
+ NULL,
+ NULL,
+ 0,
+ executable_sp,
+ NULL,
+ NULL);
+
+ if (!error.Fail() && executable_sp)
+ {
+ SetExecutableModule (executable_sp, true);
+ return true;
+ }
+ else
+ {
+ return false;
+ }
+ }
+ else
+ {
+ return false;
+ }
}
- return arch;
}
-
-
bool
Target::GetTargetTriple(ConstString &triple)
{
Modified: lldb/trunk/source/Target/TargetList.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Target/TargetList.cpp?rev=110624&r1=110623&r2=110624&view=diff
==============================================================================
--- lldb/trunk/source/Target/TargetList.cpp (original)
+++ lldb/trunk/source/Target/TargetList.cpp Mon Aug 9 18:31:02 2010
@@ -60,30 +60,50 @@
file.GetFilename().AsCString(),
arch.AsCString(),
uuid_ptr);
- ModuleSP exe_module_sp;
- FileSpec resolved_file(file);
- if (!Host::ResolveExecutableInBundle (&resolved_file))
- resolved_file = file;
-
- Error error = ModuleList::GetSharedModule(resolved_file,
- arch,
- uuid_ptr,
- NULL,
- 0,
- exe_module_sp,
- NULL,
- NULL);
- if (exe_module_sp)
+ Error error;
+
+ if (!file)
{
target_sp.reset(new Target(debugger));
- target_sp->SetExecutableModule (exe_module_sp, get_dependent_files);
-
- if (target_sp.get())
+ target_sp->SetArchitecture(arch);
+ }
+ else
+ {
+ ModuleSP exe_module_sp;
+ FileSpec resolved_file(file);
+ if (!Host::ResolveExecutableInBundle (&resolved_file))
+ resolved_file = file;
+
+ error = ModuleList::GetSharedModule(resolved_file,
+ arch,
+ uuid_ptr,
+ NULL,
+ 0,
+ exe_module_sp,
+ NULL,
+ NULL);
+ if (exe_module_sp)
{
- Mutex::Locker locker(m_target_list_mutex);
- m_current_target_idx = m_target_list.size();
- m_target_list.push_back(target_sp);
+ if (exe_module_sp->GetObjectFile() == NULL)
+ {
+ error.SetErrorStringWithFormat("%s%s%s: doesn't contain architecture %s",
+ file.GetDirectory().AsCString(),
+ file.GetDirectory() ? "/" : "",
+ file.GetFilename().AsCString(),
+ arch.AsCString());
+ return error;
+ }
+ target_sp.reset(new Target(debugger));
+ target_sp->SetExecutableModule (exe_module_sp, get_dependent_files);
}
+ }
+
+ if (target_sp.get())
+ {
+ Mutex::Locker locker(m_target_list_mutex);
+ m_current_target_idx = m_target_list.size();
+ m_target_list.push_back(target_sp);
+ }
// target_sp.reset(new Target);
// // Let the target resolve any funky bundle paths before we try and get
@@ -107,7 +127,6 @@
// m_target_list.push_back(target_sp);
// }
// }
- }
else
{
target_sp.reset();
More information about the lldb-commits
mailing list