diff options
author | Ed Maste <emaste@FreeBSD.org> | 2015-02-06 21:38:51 +0000 |
---|---|---|
committer | Ed Maste <emaste@FreeBSD.org> | 2015-02-06 21:38:51 +0000 |
commit | 205afe679855a4ce8149cdaa94d3f0868ce796dc (patch) | |
tree | 09bc83f73246ee3c7a779605cd0122093d2a8a19 /include/lldb/Target | |
parent | 0cac4ca3916ac24ab6139d03cbfd18db9e715bfe (diff) |
Notes
Diffstat (limited to 'include/lldb/Target')
22 files changed, 625 insertions, 105 deletions
diff --git a/include/lldb/Target/ABI.h b/include/lldb/Target/ABI.h index 8809c0047fa0..cfd214d28874 100644 --- a/include/lldb/Target/ABI.h +++ b/include/lldb/Target/ABI.h @@ -112,12 +112,6 @@ public: virtual bool RegisterIsVolatile (const RegisterInfo *reg_info) = 0; - // Should return true if your ABI uses frames when doing stack backtraces. This - // means a frame pointer is used that points to the previous stack frame in some - // way or another. - virtual bool - StackUsesFrames () = 0; - // Should take a look at a call frame address (CFA) which is just the stack // pointer value upon entry to a function. ABIs usually impose alignment // restrictions (4, 8 or 16 byte aligned), and zero is usually not allowed. @@ -143,15 +137,6 @@ public: virtual const RegisterInfo * GetRegisterInfoArray (uint32_t &count) = 0; - // Some architectures (e.g. x86) will push the return address on the stack and decrement - // the stack pointer when making a function call. This means that every stack frame will - // have a unique CFA. - // Other architectures (e.g. arm) pass the return address in a register so it is possible - // to have a frame on a backtrace that does not push anything on the stack or change the - // CFA. - virtual bool - FunctionCallsChangeCFA () = 0; - bool GetRegisterInfoByName (const ConstString &name, RegisterInfo &info); diff --git a/include/lldb/Target/CPPLanguageRuntime.h b/include/lldb/Target/CPPLanguageRuntime.h index daf8a67d2a9d..43df9e67add0 100644 --- a/include/lldb/Target/CPPLanguageRuntime.h +++ b/include/lldb/Target/CPPLanguageRuntime.h @@ -65,8 +65,10 @@ public: Clear(); bool - IsValid () const + IsValid () { + if (!m_parsed) + Parse(); if (m_parse_error) return false; if (m_type == eTypeInvalid) @@ -132,9 +134,16 @@ public: static bool IsCPPMangledName(const char *name); - + + // Extract C++ context and identifier from a string using heuristic matching (as opposed to + // CPPLanguageRuntime::MethodName which has to have a fully qualified C++ name with parens and arguments. + // If the name is a lone C identifier (e.g. C) or a qualified C identifier (e.g. A::B::C) it will return true, + // and identifier will be the identifier (C and C respectively) and the context will be "" and "A::B::" respectively. + // If the name fails the heuristic matching for a qualified or unqualified C/C++ identifier, then it will return false + // and identifier and context will be unchanged. + static bool - StripNamespacesFromVariableName (const char *name, const char *&base_name_start, const char *&base_name_end); + ExtractContextAndIdentifier (const char *name, llvm::StringRef &context, llvm::StringRef &identifier); // in some cases, compilers will output different names for one same type. when that happens, it might be impossible // to construct SBType objects for a valid type, because the name that is available is not the same as the name that diff --git a/include/lldb/Target/FileAction.h b/include/lldb/Target/FileAction.h index db84c0ef468c..228a9e6098c1 100644 --- a/include/lldb/Target/FileAction.h +++ b/include/lldb/Target/FileAction.h @@ -56,6 +56,9 @@ class FileAction const char *GetPath() const; + void + Dump (Stream &stream) const; + protected: Action m_action; // The action for this file int m_fd; // An existing file descriptor diff --git a/include/lldb/Target/InstrumentationRuntime.h b/include/lldb/Target/InstrumentationRuntime.h new file mode 100644 index 000000000000..70aa62908406 --- /dev/null +++ b/include/lldb/Target/InstrumentationRuntime.h @@ -0,0 +1,47 @@ +//===-- InstrumentationRuntime.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_InstrumentationRuntime_h_ +#define liblldb_InstrumentationRuntime_h_ + +// C Includes +// C++ Includes +#include <vector> +#include <map> + +// Other libraries and framework includes +// Project includes +#include "lldb/lldb-private.h" +#include "lldb/lldb-types.h" +#include "lldb/Core/PluginInterface.h" + +namespace lldb_private { + +typedef std::map<lldb::InstrumentationRuntimeType, lldb::InstrumentationRuntimeSP> InstrumentationRuntimeCollection; + +class InstrumentationRuntime : + public std::enable_shared_from_this<InstrumentationRuntime>, + public PluginInterface +{ +public: + + static void + ModulesDidLoad(lldb_private::ModuleList &module_list, Process *process, InstrumentationRuntimeCollection &runtimes); + + virtual void + ModulesDidLoad(lldb_private::ModuleList &module_list); + + virtual bool + IsActive(); + +}; + +} // namespace lldb_private + +#endif // liblldb_InstrumentationRuntime_h_ diff --git a/include/lldb/Target/InstrumentationRuntimeStopInfo.h b/include/lldb/Target/InstrumentationRuntimeStopInfo.h new file mode 100644 index 000000000000..624267ce8221 --- /dev/null +++ b/include/lldb/Target/InstrumentationRuntimeStopInfo.h @@ -0,0 +1,52 @@ +//===-- InstrumentationRuntimeStopInfo.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_InstrumentationRuntimeStopInfo_h_ +#define liblldb_InstrumentationRuntimeStopInfo_h_ + +// C Includes +// C++ Includes +#include <string> + +// Other libraries and framework includes +// Project includes +#include "lldb/Target/StopInfo.h" +#include "lldb/Core/StructuredData.h" + +namespace lldb_private { + +class InstrumentationRuntimeStopInfo : public StopInfo +{ +public: + + virtual ~InstrumentationRuntimeStopInfo() + { + } + + virtual lldb::StopReason + GetStopReason () const + { + return lldb::eStopReasonInstrumentation; + } + + virtual const char * + GetDescription (); + + static lldb::StopInfoSP + CreateStopReasonWithInstrumentationData (Thread &thread, std::string description, StructuredData::ObjectSP additional_data); + +private: + + InstrumentationRuntimeStopInfo(Thread &thread, std::string description, StructuredData::ObjectSP additional_data); + +}; + +} // namespace lldb_private + +#endif // liblldb_InstrumentationRuntimeStopInfo_h_ diff --git a/include/lldb/Target/MemoryHistory.h b/include/lldb/Target/MemoryHistory.h new file mode 100644 index 000000000000..b3bd62d6547c --- /dev/null +++ b/include/lldb/Target/MemoryHistory.h @@ -0,0 +1,42 @@ +//===-- MemoryHistory.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_MemoryHistory_h_ +#define liblldb_MemoryHistory_h_ + +// C Includes +// C++ Includes +#include <vector> + +// Other libraries and framework includes +// Project includes +#include "lldb/lldb-private.h" +#include "lldb/lldb-types.h" +#include "lldb/Core/PluginInterface.h" + +namespace lldb_private { + +typedef std::vector<lldb::ThreadSP> HistoryThreads; + +class MemoryHistory : + public std::enable_shared_from_this<MemoryHistory>, + public PluginInterface +{ +public: + + static lldb::MemoryHistorySP + FindPlugin (const lldb::ProcessSP process); + + virtual HistoryThreads + GetHistoryThreads(lldb::addr_t address) = 0; +}; + +} // namespace lldb_private + +#endif // liblldb_MemoryHistory_h_ diff --git a/include/lldb/Target/ObjCLanguageRuntime.h b/include/lldb/Target/ObjCLanguageRuntime.h index 12254f942e42..a3fee91428fa 100644 --- a/include/lldb/Target/ObjCLanguageRuntime.h +++ b/include/lldb/Target/ObjCLanguageRuntime.h @@ -21,8 +21,8 @@ #include "lldb/lldb-private.h" #include "lldb/Core/PluginInterface.h" #include "lldb/Symbol/ClangASTType.h" +#include "lldb/Symbol/DeclVendor.h" #include "lldb/Symbol/Type.h" -#include "lldb/Symbol/TypeVendor.h" #include "lldb/Target/LanguageRuntime.h" namespace lldb_private { @@ -166,6 +166,9 @@ public: virtual ClassDescriptorSP GetSuperclass () = 0; + virtual ClassDescriptorSP + GetMetaclass () const = 0; + // virtual if any implementation has some other version-specific rules // but for the known v1/v2 this is all that needs to be done virtual bool @@ -275,10 +278,10 @@ public: class EncodingToType { public: - virtual ClangASTType RealizeType (ClangASTContext& ast_ctx, const char* name, bool allow_unknownanytype); - virtual ClangASTType RealizeType (const char* name, bool allow_unknownanytype); + virtual ClangASTType RealizeType (ClangASTContext& ast_ctx, const char* name, bool for_expression); + virtual ClangASTType RealizeType (const char* name, bool for_expression); - virtual ClangASTType RealizeType (clang::ASTContext& ast_ctx, const char* name, bool allow_unknownanytype) = 0; + virtual ClangASTType RealizeType (clang::ASTContext& ast_ctx, const char* name, bool for_expression) = 0; virtual ~EncodingToType(); @@ -382,8 +385,8 @@ public: virtual ObjCISA GetParentClass(ObjCISA isa); - virtual TypeVendor * - GetTypeVendor() + virtual DeclVendor * + GetDeclVendor() { return NULL; } diff --git a/include/lldb/Target/Platform.h b/include/lldb/Target/Platform.h index e3d6abe3f398..8b14cc2a0ece 100644 --- a/include/lldb/Target/Platform.h +++ b/include/lldb/Target/Platform.h @@ -62,7 +62,7 @@ namespace lldb_private { /// or attaching to processes unless another platform is specified. //------------------------------------------------------------------ static lldb::PlatformSP - GetDefaultPlatform (); + GetHostPlatform (); static lldb::PlatformSP GetPlatformForArchitecture (const ArchSpec &arch, @@ -72,10 +72,14 @@ namespace lldb_private { GetHostPlatformName (); static void - SetDefaultPlatform (const lldb::PlatformSP &platform_sp); + SetHostPlatform (const lldb::PlatformSP &platform_sp); + // Find an existing platform plug-in by name static lldb::PlatformSP - Create (const char *platform_name, Error &error); + Find (const ConstString &name); + + static lldb::PlatformSP + Create (const ConstString &name, Error &error); static lldb::PlatformSP Create (const ArchSpec &arch, ArchSpec *platform_arch_ptr, Error &error); @@ -114,8 +118,8 @@ namespace lldb_private { /// An optional name of a specific platform plug-in that /// should be used. If NULL, pick the best plug-in. //------------------------------------------------------------------ - static Platform* - FindPlugin (Process *process, const ConstString &plugin_name); +// static lldb::PlatformSP +// FindPlugin (Process *process, const ConstString &plugin_name); //------------------------------------------------------------------ /// Set the target's executable based off of the existing @@ -137,8 +141,7 @@ namespace lldb_private { /// a suitable executable, \b false otherwise. //------------------------------------------------------------------ virtual Error - ResolveExecutable (const FileSpec &exe_file, - const ArchSpec &arch, + ResolveExecutable (const ModuleSpec &module_spec, lldb::ModuleSP &module_sp, const FileSpecList *module_search_paths_ptr); @@ -409,7 +412,6 @@ namespace lldb_private { DebugProcess (ProcessLaunchInfo &launch_info, Debugger &debugger, Target *target, // Can be NULL, if NULL create a new target, else use existing one - Listener &listener, Error &error); //------------------------------------------------------------------ @@ -434,7 +436,6 @@ namespace lldb_private { Attach (ProcessAttachInfo &attach_info, Debugger &debugger, Target *target, // Can be NULL, if NULL create a new target, else use existing one - Listener &listener, Error &error) = 0; //------------------------------------------------------------------ @@ -559,7 +560,16 @@ namespace lldb_private { SetSDKBuild (const ConstString &sdk_build) { m_sdk_build = sdk_build; - } + } + + // Override this to return true if your platform supports Clang modules. + // You may also need to override AddClangModuleCompilationOptions to pass the right Clang flags for your platform. + virtual bool + SupportsModules () { return false; } + + // Appends the platform-specific options required to find the modules for the current platform. + virtual void + AddClangModuleCompilationOptions (std::vector<std::string> &options); ConstString GetWorkingDirectory (); @@ -571,7 +581,7 @@ namespace lldb_private { // The platform will return "true" from this call if the passed in module happens to be one of these. virtual bool - ModuleIsExcludedForNonModuleSpecificSearches (Target &target, const lldb::ModuleSP &module_sp) + ModuleIsExcludedForUnconstrainedSearches (Target &target, const lldb::ModuleSP &module_sp) { return false; } diff --git a/include/lldb/Target/Process.h b/include/lldb/Target/Process.h index 641707c58deb..e04de511c797 100644 --- a/include/lldb/Target/Process.h +++ b/include/lldb/Target/Process.h @@ -38,6 +38,7 @@ #include "lldb/Expression/IRDynamicChecks.h" #include "lldb/Host/FileSpec.h" #include "lldb/Host/Host.h" +#include "lldb/Host/HostThread.h" #include "lldb/Host/ProcessRunLock.h" #include "lldb/Interpreter/Args.h" #include "lldb/Interpreter/Options.h" @@ -51,6 +52,7 @@ #include "lldb/Target/ThreadList.h" #include "lldb/Target/UnixSignals.h" #include "lldb/Utility/PseudoTerminal.h" +#include "lldb/Target/InstrumentationRuntime.h" namespace lldb_private { @@ -60,7 +62,8 @@ namespace lldb_private { class ProcessProperties : public Properties { public: - ProcessProperties(bool is_global); + // Pass NULL for "process" if the ProcessProperties are to be the global copy + ProcessProperties (lldb_private::Process *process); virtual ~ProcessProperties(); @@ -68,6 +71,9 @@ public: bool GetDisableMemoryCache() const; + uint64_t + GetMemoryCacheLineSize () const; + Args GetExtraStartupCommands () const; @@ -103,6 +109,13 @@ public: void SetDetachKeepsStopped (bool keep_stopped); + +protected: + + static void + OptionValueChangedCallback (void *baton, OptionValue *option_value); + + Process * m_process; // Can be NULL for global ProcessProperties }; typedef std::shared_ptr<ProcessProperties> ProcessPropertiesSP; @@ -223,6 +236,8 @@ class ProcessAttachInfo : public ProcessInstanceInfo public: ProcessAttachInfo() : ProcessInstanceInfo(), + m_listener_sp(), + m_hijack_listener_sp(), m_plugin_name (), m_resume_count (0), m_wait_for_launch (false), @@ -234,6 +249,8 @@ public: ProcessAttachInfo (const ProcessLaunchInfo &launch_info) : ProcessInstanceInfo(), + m_listener_sp(), + m_hijack_listener_sp(), m_plugin_name (), m_resume_count (0), m_wait_for_launch (false), @@ -244,6 +261,7 @@ public: ProcessInfo::operator= (launch_info); SetProcessPluginName (launch_info.GetProcessPluginName()); SetResumeCount (launch_info.GetResumeCount()); + SetListener(launch_info.GetListener()); SetHijackListener(launch_info.GetHijackListener()); m_detach_on_error = launch_info.GetDetachOnError(); } @@ -359,8 +377,26 @@ public: { m_detach_on_error = enable; } - + + // Get and set the actual listener that will be used for the process events + lldb::ListenerSP + GetListener () const + { + return m_listener_sp; + } + + void + SetListener (const lldb::ListenerSP &listener_sp) + { + m_listener_sp = listener_sp; + } + + + Listener & + GetListenerForProcess (Debugger &debugger); + protected: + lldb::ListenerSP m_listener_sp; lldb::ListenerSP m_hijack_listener_sp; std::string m_plugin_name; uint32_t m_resume_count; // How many times do we resume after launching @@ -1268,7 +1304,9 @@ public: //------------------------------------------------------------------ Error Resume(); - + + Error + ResumeSynchronous (Stream *stream); //------------------------------------------------------------------ /// Halts a running process. /// @@ -2447,17 +2485,26 @@ public: //------------------------------------------------------------------ /// Get any available STDOUT. /// - /// If the process was launched without supplying valid file paths - /// for stdin, stdout, and stderr, then the Process class might - /// try to cache the STDOUT for the process if it is able. Events - /// will be queued indicating that there is STDOUT available that - /// can be retrieved using this function. + /// Calling this method is a valid operation only if all of the + /// following conditions are true: + /// 1) The process was launched, and not attached to. + /// 2) The process was not launched with eLaunchFlagDisableSTDIO. + /// 3) The process was launched without supplying a valid file path + /// for STDOUT. + /// + /// Note that the implementation will probably need to start a read + /// thread in the background to make sure that the pipe is drained + /// and the STDOUT buffered appropriately, to prevent the process + /// from deadlocking trying to write to a full buffer. + /// + /// Events will be queued indicating that there is STDOUT available + /// that can be retrieved using this function. /// /// @param[out] buf /// A buffer that will receive any STDOUT bytes that are /// currently available. /// - /// @param[out] buf_size + /// @param[in] buf_size /// The size in bytes for the buffer \a buf. /// /// @return @@ -2471,13 +2518,22 @@ public: //------------------------------------------------------------------ /// Get any available STDERR. /// - /// If the process was launched without supplying valid file paths - /// for stdin, stdout, and stderr, then the Process class might - /// try to cache the STDERR for the process if it is able. Events - /// will be queued indicating that there is STDERR available that - /// can be retrieved using this function. + /// Calling this method is a valid operation only if all of the + /// following conditions are true: + /// 1) The process was launched, and not attached to. + /// 2) The process was not launched with eLaunchFlagDisableSTDIO. + /// 3) The process was launched without supplying a valid file path + /// for STDERR. /// - /// @param[out] buf + /// Note that the implementation will probably need to start a read + /// thread in the background to make sure that the pipe is drained + /// and the STDERR buffered appropriately, to prevent the process + /// from deadlocking trying to write to a full buffer. + /// + /// Events will be queued indicating that there is STDERR available + /// that can be retrieved using this function. + /// + /// @param[in] buf /// A buffer that will receive any STDERR bytes that are /// currently available. /// @@ -2492,6 +2548,27 @@ public: virtual size_t GetSTDERR (char *buf, size_t buf_size, Error &error); + //------------------------------------------------------------------ + /// Puts data into this process's STDIN. + /// + /// Calling this method is a valid operation only if all of the + /// following conditions are true: + /// 1) The process was launched, and not attached to. + /// 2) The process was not launched with eLaunchFlagDisableSTDIO. + /// 3) The process was launched without supplying a valid file path + /// for STDIN. + /// + /// @param[in] buf + /// A buffer that contains the data to write to the process's STDIN. + /// + /// @param[in] buf_size + /// The size in bytes for the buffer \a buf. + /// + /// @return + /// The number of bytes written into \a buf. If this value is + /// less than \a buf_size, another call to this function should + /// be made to write the rest of the data. + //------------------------------------------------------------------ virtual size_t PutSTDIN (const char *buf, size_t buf_size, Error &error) { @@ -2675,7 +2752,8 @@ public: WaitForProcessToStop (const TimeValue *timeout, lldb::EventSP *event_sp_ptr = NULL, bool wait_always = true, - Listener *hijack_listener = NULL); + Listener *hijack_listener = NULL, + Stream *stream = NULL); //-------------------------------------------------------------------------------------- @@ -2700,7 +2778,28 @@ public: WaitForStateChangedEvents (const TimeValue *timeout, lldb::EventSP &event_sp, Listener *hijack_listener); // Pass NULL to use builtin listener - + + //-------------------------------------------------------------------------------------- + /// Centralize the code that handles and prints descriptions for process state changes. + /// + /// @param[in] event_sp + /// The process state changed event + /// + /// @param[in] stream + /// The output stream to get the state change description + /// + /// @param[inout] pop_process_io_handler + /// If this value comes in set to \b true, then pop the Process IOHandler if needed. + /// Else this variable will be set to \b true or \b false to indicate if the process + /// needs to have its process IOHandler popped. + /// + /// @return + /// \b true if the event describes a process state changed event, \b false otherwise. + //-------------------------------------------------------------------------------------- + static bool + HandleProcessStateChangedEvent (const lldb::EventSP &event_sp, + Stream *stream, + bool &pop_process_io_handler); Event * PeekAtStateChangedEvents (); @@ -2723,6 +2822,7 @@ public: Process &m_process; }; friend class ProcessEventHijacker; + friend class ProcessProperties; //------------------------------------------------------------------ /// If you need to ensure that you and only you will hear about some public /// event, then make a new listener, set to listen to process events, and @@ -2776,7 +2876,12 @@ public: { return m_os_ap.get(); } - + + ArchSpec::StopInfoOverrideCallbackType + GetStopInfoOverrideCallback () const + { + return m_stop_info_override_callback; + } virtual LanguageRuntime * GetLanguageRuntime (lldb::LanguageType language, bool retry_if_null = true); @@ -2906,7 +3011,7 @@ public: ProcessRunLock & GetRunLock () { - if (Host::GetCurrentThread() == m_private_state_thread) + if (m_private_state_thread.EqualsThread(Host::GetCurrentThread())) return m_private_run_lock; else return m_public_run_lock; @@ -2919,6 +3024,12 @@ public: Error return_error ("Sending an event is not supported for this process."); return return_error; } + + lldb::ThreadCollectionSP + GetHistoryThreads(lldb::addr_t addr); + + lldb::InstrumentationRuntimeSP + GetInstrumentationRuntime(lldb::InstrumentationRuntimeType type); protected: @@ -3001,7 +3112,7 @@ protected: bool PrivateStateThreadIsValid () const { - return IS_VALID_LLDB_HOST_THREAD(m_private_state_thread); + return m_private_state_thread.IsJoinable(); } void @@ -3036,13 +3147,14 @@ protected: Broadcaster m_private_state_control_broadcaster; // This is the control broadcaster, used to pause, resume & stop the private state thread. Listener m_private_state_listener; // This is the listener for the private state thread. Predicate<bool> m_private_state_control_wait; /// This Predicate is used to signal that a control operation is complete. - lldb::thread_t m_private_state_thread; // Thread ID for the thread that watches internal state events + HostThread m_private_state_thread; // Thread ID for the thread that watches internal state events ProcessModID m_mod_id; ///< Tracks the state of the process over stops and other alterations. uint32_t m_process_unique_id; ///< Each lldb_private::Process class that is created gets a unique integer ID that increments with each new instance uint32_t m_thread_index_id; ///< Each thread is created with a 1 based index that won't get re-used. std::map<uint64_t, uint32_t> m_thread_id_to_index_id_map; int m_exit_status; ///< The exit status of the process, or -1 if not set. std::string m_exit_string; ///< A textual description of why a process exited. + Mutex m_exit_status_mutex; ///< Mutex so m_exit_status m_exit_string can be safely accessed from multiple threads Mutex m_thread_mutex; ThreadList m_thread_list_real; ///< The threads for this process as are known to the protocol we are debugging with ThreadList m_thread_list; ///< The threads for this process as the user will see them. This is usually the same as @@ -3074,11 +3186,13 @@ protected: AllocatedMemoryCache m_allocated_memory_cache; bool m_should_detach; /// Should we detach if the process object goes away with an explicit call to Kill or Detach? LanguageRuntimeCollection m_language_runtimes; + InstrumentationRuntimeCollection m_instrumentation_runtimes; std::unique_ptr<NextEventAction> m_next_event_action_ap; std::vector<PreResumeCallbackAndBaton> m_pre_resume_actions; ProcessRunLock m_public_run_lock; ProcessRunLock m_private_run_lock; Predicate<bool> m_currently_handling_event; // This predicate is set in HandlePrivateEvent while all its business is being done. + ArchSpec::StopInfoOverrideCallbackType m_stop_info_override_callback; bool m_currently_handling_do_on_removals; bool m_resume_requested; // If m_currently_handling_event or m_currently_handling_do_on_removals are true, Resume will only request a resume, using this flag to check. bool m_finalize_called; @@ -3170,7 +3284,12 @@ protected: Error HaltForDestroyOrDetach(lldb::EventSP &exit_event_sp); - + + bool + StateChangedIsExternallyHijacked(); + + void + LoadOperatingSystemPlugin(bool flush); private: //------------------------------------------------------------------ // For Process only diff --git a/include/lldb/Target/ProcessLaunchInfo.h b/include/lldb/Target/ProcessLaunchInfo.h index 77d829a7e476..897704488e5f 100644 --- a/include/lldb/Target/ProcessLaunchInfo.h +++ b/include/lldb/Target/ProcessLaunchInfo.h @@ -15,6 +15,7 @@ // LLDB Headers #include "lldb/Core/Flags.h" +#include "lldb/Host/FileSpec.h" #include "lldb/Host/Host.h" #include "lldb/Target/FileAction.h" #include "lldb/Target/ProcessInfo.h" @@ -105,11 +106,11 @@ namespace lldb_private void SetProcessPluginName (const char *plugin); - const char * + const FileSpec & GetShell () const; void - SetShell (const char * path); + SetShell (const FileSpec &shell); uint32_t GetResumeCount () const @@ -124,7 +125,7 @@ namespace lldb_private } bool - GetLaunchInSeparateProcessGroup () + GetLaunchInSeparateProcessGroup() const { return m_flags.Test(lldb::eLaunchFlagLaunchInSeparateProcessGroup); } @@ -148,17 +149,23 @@ namespace lldb_private bool monitor_signals); Host::MonitorChildProcessCallback - GetMonitorProcessCallback () + GetMonitorProcessCallback() const { return m_monitor_callback; } - const void* - GetMonitorProcessBaton () const + void * + GetMonitorProcessBaton() const { return m_monitor_callback_baton; } + bool + GetMonitorSignals() const + { + return m_monitor_signals; + } + // If the LaunchInfo has a monitor callback, then arrange to monitor the process. // Return true if the LaunchInfo has taken care of monitoring the process, and false if the // caller might want to monitor the process themselves. @@ -169,9 +176,25 @@ namespace lldb_private lldb_utility::PseudoTerminal & GetPTY () { - return m_pty; + return *m_pty; } + // Get and set the actual listener that will be used for the process events + lldb::ListenerSP + GetListener () const + { + return m_listener_sp; + } + + void + SetListener (const lldb::ListenerSP &listener_sp) + { + m_listener_sp = listener_sp; + } + + Listener & + GetListenerForProcess (Debugger &debugger); + lldb::ListenerSP GetHijackListener () const { @@ -184,7 +207,6 @@ namespace lldb_private m_hijack_listener_sp = listener_sp; } - void SetLaunchEventData (const char *data) { @@ -209,15 +231,16 @@ namespace lldb_private protected: std::string m_working_dir; std::string m_plugin_name; - std::string m_shell; + FileSpec m_shell; Flags m_flags; // Bitwise OR of bits from lldb::LaunchFlags std::vector<FileAction> m_file_actions; // File actions for any other files - lldb_utility::PseudoTerminal m_pty; + std::shared_ptr<lldb_utility::PseudoTerminal> m_pty; uint32_t m_resume_count; // How many times do we resume after launching Host::MonitorChildProcessCallback m_monitor_callback; void *m_monitor_callback_baton; bool m_monitor_signals; std::string m_event_data; // A string passed to the plugin launch, having no meaning to the upper levels of lldb. + lldb::ListenerSP m_listener_sp; lldb::ListenerSP m_hijack_listener_sp; }; } diff --git a/include/lldb/Target/StackFrame.h b/include/lldb/Target/StackFrame.h index 1274dcc64bd3..95e21445be04 100644 --- a/include/lldb/Target/StackFrame.h +++ b/include/lldb/Target/StackFrame.h @@ -519,6 +519,7 @@ private: lldb::VariableListSP m_variable_list_sp; ValueObjectList m_variable_list_value_objects; // Value objects for each variable in m_variable_list_sp StreamString m_disassembly; + Mutex m_mutex; DISALLOW_COPY_AND_ASSIGN (StackFrame); }; diff --git a/include/lldb/Target/StopInfo.h b/include/lldb/Target/StopInfo.h index 8de40e852f4c..e0d029bcc956 100644 --- a/include/lldb/Target/StopInfo.h +++ b/include/lldb/Target/StopInfo.h @@ -18,6 +18,7 @@ // Project includes #include "lldb/lldb-public.h" #include "lldb/Target/Process.h" +#include "lldb/Core/StructuredData.h" namespace lldb_private { @@ -140,6 +141,12 @@ public: return m_override_should_stop == eLazyBoolYes; } + StructuredData::ObjectSP + GetExtendedInfo () + { + return m_extended_info; + } + static lldb::StopInfoSP CreateStopReasonWithBreakpointSiteID (Thread &thread, lldb::break_id_t break_id); @@ -211,6 +218,8 @@ protected: LazyBool m_override_should_notify; LazyBool m_override_should_stop; + StructuredData::ObjectSP m_extended_info; // The extended info for this stop info + // This determines whether the target has run since this stop info. // N.B. running to evaluate a user expression does not count. bool HasTargetRunSinceMe (); diff --git a/include/lldb/Target/Target.h b/include/lldb/Target/Target.h index 64f3edf0fc4f..a33734fd5b63 100644 --- a/include/lldb/Target/Target.h +++ b/include/lldb/Target/Target.h @@ -26,6 +26,7 @@ #include "lldb/Core/Event.h" #include "lldb/Core/ModuleList.h" #include "lldb/Core/UserSettingsController.h" +#include "lldb/Expression/ClangModulesDeclVendor.h" #include "lldb/Expression/ClangPersistentVariables.h" #include "lldb/Interpreter/Args.h" #include "lldb/Interpreter/OptionValueBoolean.h" @@ -554,12 +555,20 @@ private: //------------------------------------------------------------------ Target (Debugger &debugger, const ArchSpec &target_arch, - const lldb::PlatformSP &platform_sp); + const lldb::PlatformSP &platform_sp, + bool is_dummy_target); // Helper function. bool ProcessIsValid (); + // Copy breakpoints, stop hooks and so forth from the dummy target: + void + PrimeFromDummyTarget(Target *dummy_target); + + void + AddBreakpoint(lldb::BreakpointSP breakpoint_sp, bool internal); + public: ~Target(); @@ -607,8 +616,8 @@ public: Destroy(); Error - Launch (Listener &listener, - ProcessLaunchInfo &launch_info); + Launch (ProcessLaunchInfo &launch_info, + Stream *stream); // Optional stream to receive first stop info //------------------------------------------------------------------ // This part handles the breakpoints. @@ -954,9 +963,9 @@ public: //------------------------------------------------------------------ /// Return whether this FileSpec corresponds to a module that should be considered for general searches. /// - /// This API will be consulted by the SearchFilterForNonModuleSpecificSearches + /// This API will be consulted by the SearchFilterForUnconstrainedSearches /// and any module that returns \b true will not be searched. Note the - /// SearchFilterForNonModuleSpecificSearches is the search filter that + /// SearchFilterForUnconstrainedSearches is the search filter that /// gets used in the CreateBreakpoint calls when no modules is provided. /// /// The target call at present just consults the Platform's call of the @@ -968,14 +977,14 @@ public: /// @return \b true if the module should be excluded, \b false otherwise. //------------------------------------------------------------------ bool - ModuleIsExcludedForNonModuleSpecificSearches (const FileSpec &module_spec); + ModuleIsExcludedForUnconstrainedSearches (const FileSpec &module_spec); //------------------------------------------------------------------ /// Return whether this module should be considered for general searches. /// - /// This API will be consulted by the SearchFilterForNonModuleSpecificSearches + /// This API will be consulted by the SearchFilterForUnconstrainedSearches /// and any module that returns \b true will not be searched. Note the - /// SearchFilterForNonModuleSpecificSearches is the search filter that + /// SearchFilterForUnconstrainedSearches is the search filter that /// gets used in the CreateBreakpoint calls when no modules is provided. /// /// The target call at present just consults the Platform's call of the @@ -990,7 +999,7 @@ public: /// @return \b true if the module should be excluded, \b false otherwise. //------------------------------------------------------------------ bool - ModuleIsExcludedForNonModuleSpecificSearches (const lldb::ModuleSP &module_sp); + ModuleIsExcludedForUnconstrainedSearches (const lldb::ModuleSP &module_sp); ArchSpec & GetArchitecture () @@ -1132,6 +1141,9 @@ public: Error Install(ProcessLaunchInfo *launch_info); + bool + ResolveFileAddress (lldb::addr_t load_addr, + Address &so_addr); bool ResolveLoadAddress (lldb::addr_t load_addr, @@ -1143,6 +1155,12 @@ public: lldb::addr_t load_addr, bool warn_multiple = false); + size_t + UnloadModuleSections (const lldb::ModuleSP &module_sp); + + size_t + UnloadModuleSections (const ModuleList &module_list); + bool SetSectionUnloaded (const lldb::SectionSP §ion_sp); @@ -1332,6 +1350,9 @@ public: SourceManager & GetSourceManager (); + + ClangModulesDeclVendor * + GetClangModulesDeclVendor (); //------------------------------------------------------------------ // Methods. @@ -1369,6 +1390,7 @@ protected: std::unique_ptr<ClangASTContext> m_scratch_ast_context_ap; std::unique_ptr<ClangASTSource> m_scratch_ast_source_ap; std::unique_ptr<ClangASTImporter> m_ast_importer_ap; + std::unique_ptr<ClangModulesDeclVendor> m_clang_modules_decl_vendor_ap; ClangPersistentVariables m_persistent_variables; ///< These are the persistent variables associated with this process for the expression parser. std::unique_ptr<SourceManager> m_source_manager_ap; @@ -1378,6 +1400,7 @@ protected: lldb::user_id_t m_stop_hook_next_id; bool m_valid; bool m_suppress_stop_hooks; + bool m_is_dummy_target; static void ImageSearchPathsChanged (const PathMappingList &path_list, diff --git a/include/lldb/Target/TargetList.h b/include/lldb/Target/TargetList.h index 6abf13e8704c..27e46ba81a70 100644 --- a/include/lldb/Target/TargetList.h +++ b/include/lldb/Target/TargetList.h @@ -221,16 +221,42 @@ public: lldb::TargetSP GetSelectedTarget (); - protected: typedef std::vector<lldb::TargetSP> collection; //------------------------------------------------------------------ // Member variables. //------------------------------------------------------------------ collection m_target_list; + lldb::TargetSP m_dummy_target_sp; mutable Mutex m_target_list_mutex; uint32_t m_selected_target_idx; private: + lldb::TargetSP + GetDummyTarget (lldb_private::Debugger &debugger); + + Error + CreateDummyTarget (Debugger &debugger, + const char *specified_arch_name, + lldb::TargetSP &target_sp); + + Error + CreateTargetInternal (Debugger &debugger, + const char *user_exe_path, + const char *triple_cstr, + bool get_dependent_files, + const OptionGroupPlatform *platform_options, + lldb::TargetSP &target_sp, + bool is_dummy_target); + + Error + CreateTargetInternal (Debugger &debugger, + const char *user_exe_path, + const ArchSpec& arch, + bool get_dependent_modules, + lldb::PlatformSP &platform_sp, + lldb::TargetSP &target_sp, + bool is_dummy_target); + DISALLOW_COPY_AND_ASSIGN (TargetList); }; diff --git a/include/lldb/Target/Thread.h b/include/lldb/Target/Thread.h index cba09e164105..25c0c0e92bec 100644 --- a/include/lldb/Target/Thread.h +++ b/include/lldb/Target/Thread.h @@ -535,7 +535,7 @@ public: DumpUsingSettingsFormat (Stream &strm, uint32_t frame_idx); bool - GetDescription (Stream &s, lldb::DescriptionLevel level, bool json_output); + GetDescription (Stream &s, lldb::DescriptionLevel level, bool print_json_thread, bool print_json_stopinfo); //------------------------------------------------------------------ /// Default implementation for stepping into. @@ -912,6 +912,11 @@ public: bool stop_others, uint32_t frame_idx); + virtual lldb::ThreadPlanSP + QueueThreadPlanForStepScripted (bool abort_other_plans, + const char *class_name, + bool stop_other_threads); + //------------------------------------------------------------------ // Thread Plan accessors: //------------------------------------------------------------------ @@ -1041,6 +1046,20 @@ public: void DiscardThreadPlansUpToPlan (ThreadPlan *up_to_plan_ptr); + + //------------------------------------------------------------------ + /// Discards the plans queued on the plan stack of the current thread up to and + /// including the plan in that matches \a thread_index counting only + /// the non-Private plans. + /// + /// @param[in] up_to_plan_sp + /// Discard all plans up to and including this user plan given by this index. + /// + /// @return + /// \b true if there was a thread plan with that user index, \b false otherwise. + //------------------------------------------------------------------ + bool + DiscardUserThreadPlansUpToIndex (uint32_t thread_index); //------------------------------------------------------------------ /// Prints the current plan stack. @@ -1050,7 +1069,10 @@ public: /// //------------------------------------------------------------------ void - DumpThreadPlans (Stream *s) const; + DumpThreadPlans (Stream *s, + lldb::DescriptionLevel desc_level = lldb::eDescriptionLevelVerbose, + bool include_internal = true, + bool ignore_boring = false) const; virtual bool CheckpointThreadState (ThreadStateCheckpoint &saved_state); @@ -1293,6 +1315,7 @@ protected: lldb::ProcessWP m_process_wp; ///< The process that owns this thread. lldb::StopInfoSP m_stop_info_sp; ///< The private stop reason for this thread uint32_t m_stop_info_stop_id; // This is the stop id for which the StopInfo is valid. Can use this so you know that + uint32_t m_stop_info_override_stop_id; // The stop ID containing the last time the stop info was checked against the stop info override // the thread's m_stop_info_sp is current and you don't have to fetch it again const uint32_t m_index_id; ///< A unique 1 based index assigned to each thread for easy UI/command line access. lldb::RegisterContextSP m_reg_context_sp; ///< The register context for this thread's current register state. diff --git a/include/lldb/Target/ThreadCollection.h b/include/lldb/Target/ThreadCollection.h new file mode 100644 index 000000000000..0c2b41cc0ca4 --- /dev/null +++ b/include/lldb/Target/ThreadCollection.h @@ -0,0 +1,70 @@ +//===-- ThreadCollection.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_ThreadCollection_h_ +#define liblldb_ThreadCollection_h_ + +#include <vector> + +#include "lldb/lldb-private.h" +#include "lldb/Host/Mutex.h" +#include "lldb/Utility/Iterable.h" + +namespace lldb_private { + +class ThreadCollection +{ +public: + typedef std::vector<lldb::ThreadSP> collection; + typedef LockingAdaptedIterable<collection, lldb::ThreadSP, vector_adapter> ThreadIterable; + + ThreadCollection(); + + ThreadCollection(collection threads); + + virtual + ~ThreadCollection() + { + } + + uint32_t + GetSize(); + + void + AddThread (const lldb::ThreadSP &thread_sp); + + void + InsertThread (const lldb::ThreadSP &thread_sp, uint32_t idx); + + // Note that "idx" is not the same as the "thread_index". It is a zero + // based index to accessing the current threads, whereas "thread_index" + // is a unique index assigned + lldb::ThreadSP + GetThreadAtIndex (uint32_t idx); + + virtual ThreadIterable + Threads () + { + return ThreadIterable(m_threads, GetMutex()); + } + + virtual Mutex & + GetMutex() + { + return m_mutex; + } + +protected: + collection m_threads; + Mutex m_mutex; +}; + +} // namespace lldb_private + +#endif // liblldb_ThreadCollection_h_ diff --git a/include/lldb/Target/ThreadList.h b/include/lldb/Target/ThreadList.h index 65d9b74098a6..12c430c9c8d8 100644 --- a/include/lldb/Target/ThreadList.h +++ b/include/lldb/Target/ThreadList.h @@ -15,16 +15,14 @@ #include "lldb/lldb-private.h" #include "lldb/Core/UserID.h" #include "lldb/Utility/Iterable.h" +#include "lldb/Target/ThreadCollection.h" - -// FIXME: Currently this is a thread list with lots of functionality for use only by -// the process for which this is the thread list. If we ever want a container class -// to hand out that is just a random subset of threads, with iterator functionality, -// then we should make that part a base class, and make a ProcessThreadList for the -// process. namespace lldb_private { -class ThreadList +// This is a thread list with lots of functionality for use only by the process +// for which this is the thread list. A generic container class with iterator +// functionality is ThreadCollection. +class ThreadList : public ThreadCollection { friend class Process; @@ -34,6 +32,7 @@ public: ThreadList (const ThreadList &rhs); + virtual ~ThreadList (); const ThreadList& @@ -42,11 +41,6 @@ public: uint32_t GetSize(bool can_update = true); - void - AddThread (const lldb::ThreadSP &thread_sp); - - void - InsertThread (const lldb::ThreadSP &thread_sp, uint32_t idx); // Return the selected thread if there is one. Otherwise, return the thread // selected at index 0. lldb::ThreadSP @@ -72,15 +66,6 @@ public: // is a unique index assigned lldb::ThreadSP GetThreadAtIndex (uint32_t idx, bool can_update = true); - - typedef std::vector<lldb::ThreadSP> collection; - typedef LockingAdaptedIterable<collection, lldb::ThreadSP, vector_adapter> ThreadIterable; - - ThreadIterable - Threads () - { - return ThreadIterable(m_threads, GetMutex()); - } lldb::ThreadSP FindThreadByID (lldb::tid_t tid, bool can_update = true); @@ -143,7 +128,7 @@ public: void SetStopID (uint32_t stop_id); - Mutex & + virtual Mutex & GetMutex (); void @@ -162,7 +147,6 @@ protected: //------------------------------------------------------------------ Process *m_process; ///< The process that manages this thread list. uint32_t m_stop_id; ///< The process stop ID that this thread list is valid for. - collection m_threads; ///< The threads for this process. lldb::tid_t m_selected_tid; ///< For targets that need the notion of a current thread. private: diff --git a/include/lldb/Target/ThreadPlan.h b/include/lldb/Target/ThreadPlan.h index 1f20841906d3..db2e79894057 100644 --- a/include/lldb/Target/ThreadPlan.h +++ b/include/lldb/Target/ThreadPlan.h @@ -223,6 +223,7 @@ namespace lldb_private { //------------------------------------------------------------------ class ThreadPlan : + public std::enable_shared_from_this<ThreadPlan>, public UserID { public: @@ -241,6 +242,7 @@ public: eKindNull, eKindBase, eKindCallFunction, + eKindPython, eKindStepInstruction, eKindStepOut, eKindStepOverBreakpoint, @@ -687,7 +689,8 @@ protected: virtual lldb::StateType GetPlanRunState (); - + + DISALLOW_COPY_AND_ASSIGN(ThreadPlanNull); }; diff --git a/include/lldb/Target/ThreadPlanPython.h b/include/lldb/Target/ThreadPlanPython.h new file mode 100644 index 000000000000..fa41af1915cd --- /dev/null +++ b/include/lldb/Target/ThreadPlanPython.h @@ -0,0 +1,80 @@ +//===-- ThreadPlanPython.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_ThreadPlan_Python_h_ +#define liblldb_ThreadPlan_Python_h_ + +// C Includes +// C++ Includes +#include <string> +// Other libraries and framework includes +// Project includes +#include "lldb/lldb-private.h" +#include "lldb/Core/UserID.h" +#include "lldb/Host/Mutex.h" +#include "lldb/Target/Process.h" +#include "lldb/Target/Target.h" +#include "lldb/Target/Thread.h" +#include "lldb/Target/ThreadPlan.h" +#include "lldb/Target/ThreadPlanTracer.h" +#include "lldb/Target/StopInfo.h" + +namespace lldb_private { + +//------------------------------------------------------------------ +// ThreadPlanPython: +// +//------------------------------------------------------------------ + +class ThreadPlanPython : public ThreadPlan +{ +public: + ThreadPlanPython (Thread &thread, const char *class_name); + virtual ~ThreadPlanPython (); + + virtual void + GetDescription (Stream *s, + lldb::DescriptionLevel level); + + virtual bool + ValidatePlan (Stream *error); + + virtual bool + ShouldStop (Event *event_ptr); + + virtual bool + MischiefManaged (); + + virtual bool + WillStop (); + + virtual bool + StopOthers (); + + virtual void + DidPush (); + +protected: + virtual bool + DoPlanExplainsStop (Event *event_ptr); + + virtual lldb::StateType + GetPlanRunState (); + +private: + std::string m_class_name; + lldb::ScriptInterpreterObjectSP m_implementation_sp; + + DISALLOW_COPY_AND_ASSIGN(ThreadPlanPython); +}; + + +} // namespace lldb_private + +#endif // liblldb_ThreadPlan_Python_h_ diff --git a/include/lldb/Target/ThreadPlanStepOverBreakpoint.h b/include/lldb/Target/ThreadPlanStepOverBreakpoint.h index 41cac5c9b0b4..a4806056afb9 100644 --- a/include/lldb/Target/ThreadPlanStepOverBreakpoint.h +++ b/include/lldb/Target/ThreadPlanStepOverBreakpoint.h @@ -35,7 +35,13 @@ public: virtual void ThreadDestroyed (); void SetAutoContinue (bool do_it); virtual bool ShouldAutoContinue(Event *event_ptr); + virtual bool IsPlanStale(); + lldb::addr_t + GetBreakpointLoadAddress() const + { + return m_breakpoint_addr; + } protected: virtual bool DoPlanExplainsStop (Event *event_ptr); virtual bool DoWillResume (lldb::StateType resume_state, bool current_plan); diff --git a/include/lldb/Target/ThreadPlanStepRange.h b/include/lldb/Target/ThreadPlanStepRange.h index 3487e9ad66cb..43c55c2aa411 100644 --- a/include/lldb/Target/ThreadPlanStepRange.h +++ b/include/lldb/Target/ThreadPlanStepRange.h @@ -30,7 +30,8 @@ public: Thread &thread, const AddressRange &range, const SymbolContext &addr_context, - lldb::RunMode stop_others); + lldb::RunMode stop_others, + bool given_ranges_only = false); virtual ~ThreadPlanStepRange (); @@ -83,6 +84,7 @@ protected: bool m_first_run_event; // We want to broadcast only one running event, our first. lldb::BreakpointSP m_next_branch_bp_sp; bool m_use_fast_step; + bool m_given_ranges_only; private: std::vector<lldb::DisassemblerSP> m_instruction_ranges; diff --git a/include/lldb/Target/Unwind.h b/include/lldb/Target/Unwind.h index 7cda4aeb2e18..17c6c0df8207 100644 --- a/include/lldb/Target/Unwind.h +++ b/include/lldb/Target/Unwind.h @@ -27,7 +27,7 @@ protected: //------------------------------------------------------------------ Unwind(Thread &thread) : m_thread (thread), - m_unwind_mutex() + m_unwind_mutex(Mutex::eMutexTypeRecursive) { } |