aboutsummaryrefslogtreecommitdiff
path: root/include/lldb/Host
diff options
context:
space:
mode:
Diffstat (limited to 'include/lldb/Host')
-rw-r--r--include/lldb/Host/Host.h4
-rw-r--r--include/lldb/Host/MainLoop.h27
-rw-r--r--include/lldb/Host/MainLoopBase.h94
-rw-r--r--include/lldb/Host/StringConvert.h2
-rw-r--r--include/lldb/Host/common/NativeProcessProtocol.h59
-rw-r--r--include/lldb/Host/posix/ConnectionFileDescriptorPosix.h7
-rw-r--r--include/lldb/Host/posix/MainLoopPosix.h100
7 files changed, 282 insertions, 11 deletions
diff --git a/include/lldb/Host/Host.h b/include/lldb/Host/Host.h
index caf33634057d..235367a7cc5c 100644
--- a/include/lldb/Host/Host.h
+++ b/include/lldb/Host/Host.h
@@ -244,8 +244,8 @@ public:
#endif // !defined(__ANDROID__) && !defined(__ANDROID_NDK__)
#endif // defined (__APPLE__) || defined (__linux__) || defined (__FreeBSD__) || defined (__GLIBC__) || defined(__NetBSD__)
- static const lldb_private::UnixSignalsSP&
- GetUnixSignals ();
+ static const lldb::UnixSignalsSP &
+ GetUnixSignals();
static Error
LaunchProcess (ProcessLaunchInfo &launch_info);
diff --git a/include/lldb/Host/MainLoop.h b/include/lldb/Host/MainLoop.h
new file mode 100644
index 000000000000..276538a336b6
--- /dev/null
+++ b/include/lldb/Host/MainLoop.h
@@ -0,0 +1,27 @@
+//===-- MainLoop.h ----------------------------------------------*- C++ -*-===//
+//
+// The LLVM Compiler Infrastructure
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef lldb_Host_MainLoop_h_
+#define lldb_Host_MainLoop_h_
+
+#ifdef _WIN32
+#include "lldb/Host/MainLoopBase.h"
+namespace lldb_private
+{
+typedef MainLoopBase MainLoop;
+}
+#else
+#include "lldb/Host/posix/MainLoopPosix.h"
+namespace lldb_private
+{
+typedef MainLoopPosix MainLoop;
+}
+#endif
+
+#endif // lldb_Host_MainLoop_h_
diff --git a/include/lldb/Host/MainLoopBase.h b/include/lldb/Host/MainLoopBase.h
new file mode 100644
index 000000000000..bff2ce78110d
--- /dev/null
+++ b/include/lldb/Host/MainLoopBase.h
@@ -0,0 +1,94 @@
+//===-- MainLoopBase.h ------------------------------------------*- C++ -*-===//
+//
+// The LLVM Compiler Infrastructure
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef lldb_Host_posix_MainLoopBase_h_
+#define lldb_Host_posix_MainLoopBase_h_
+
+#include <functional>
+
+#include "llvm/Support/ErrorHandling.h"
+
+#include "lldb/Core/Error.h"
+#include "lldb/Host/IOObject.h"
+
+namespace lldb_private {
+
+// The purpose of this class is to enable multiplexed processing of data from different sources
+// without resorting to multi-threading. Clients can register IOObjects, which will be monitored
+// for readability, and when they become ready, the specified callback will be invoked.
+// Monitoring for writability is not supported, but can be easily added if needed.
+//
+// The RegisterReadObject function return a handle, which controls the duration of the monitoring. When
+// this handle is destroyed, the callback is deregistered.
+//
+// This class simply defines the interface common for all platforms, actual implementations are
+// platform-specific.
+class MainLoopBase
+{
+private:
+ class ReadHandle;
+
+public:
+ MainLoopBase() { }
+ virtual ~MainLoopBase() { }
+
+ typedef std::unique_ptr<ReadHandle> ReadHandleUP;
+
+ typedef std::function<void(MainLoopBase &)> Callback;
+
+ virtual ReadHandleUP
+ RegisterReadObject(const lldb::IOObjectSP &object_sp, const Callback &callback, Error &error)
+ { llvm_unreachable("Not implemented"); }
+
+ // Waits for registered events and invoke the proper callbacks. Returns when all callbacks
+ // deregister themselves or when someone requests termination.
+ virtual Error
+ Run()
+ { llvm_unreachable("Not implemented"); }
+
+ // Requests the exit of the Run() function.
+ virtual void
+ RequestTermination()
+ { llvm_unreachable("Not implemented"); }
+
+protected:
+ ReadHandleUP
+ CreateReadHandle(const lldb::IOObjectSP &object_sp)
+ { return ReadHandleUP(new ReadHandle(*this, object_sp)); }
+
+ virtual void
+ UnregisterReadObject(const lldb::IOObjectSP &object_sp)
+ { llvm_unreachable("Not implemented"); }
+
+private:
+ class ReadHandle
+ {
+ public:
+ ~ReadHandle() { m_mainloop.UnregisterReadObject(m_object_sp); }
+
+ private:
+ ReadHandle(MainLoopBase &mainloop, const lldb::IOObjectSP &object_sp)
+ : m_mainloop(mainloop), m_object_sp(object_sp)
+ { }
+
+ MainLoopBase &m_mainloop;
+ lldb::IOObjectSP m_object_sp;
+
+ friend class MainLoopBase;
+ DISALLOW_COPY_AND_ASSIGN(ReadHandle);
+ };
+
+private:
+ DISALLOW_COPY_AND_ASSIGN(MainLoopBase);
+};
+
+} // namespace lldb_private
+
+
+#endif // lldb_Host_posix_MainLoopBase_h_
diff --git a/include/lldb/Host/StringConvert.h b/include/lldb/Host/StringConvert.h
index 3cc260cf2be1..af5c2a08db87 100644
--- a/include/lldb/Host/StringConvert.h
+++ b/include/lldb/Host/StringConvert.h
@@ -39,6 +39,8 @@ ToSInt64 (const char *s, int64_t fail_value = 0, int base = 0, bool *success_ptr
uint64_t
ToUInt64 (const char *s, uint64_t fail_value = 0, int base = 0, bool *success_ptr = nullptr);
+double
+ToDouble (const char *s, double fail_value = 0.0, bool *success_ptr = nullptr);
} // namespace StringConvert
} // namespace lldb_private
diff --git a/include/lldb/Host/common/NativeProcessProtocol.h b/include/lldb/Host/common/NativeProcessProtocol.h
index f6a685aae147..4f0f3a962d32 100644
--- a/include/lldb/Host/common/NativeProcessProtocol.h
+++ b/include/lldb/Host/common/NativeProcessProtocol.h
@@ -35,8 +35,6 @@ namespace lldb_private
friend class SoftwareBreakpoint;
public:
- static NativeProcessProtocol *
- CreateInstance (lldb::pid_t pid);
// lldb_private::Host calls should be used to launch a process for debugging, and
// then the process should be attached to. When attaching to a process
@@ -44,7 +42,6 @@ namespace lldb_private
// and then this function should be called.
NativeProcessProtocol (lldb::pid_t pid);
- public:
virtual ~NativeProcessProtocol ()
{
}
@@ -297,6 +294,62 @@ namespace lldb_private
virtual Error
GetFileLoadAddress(const llvm::StringRef& file_name, lldb::addr_t& load_addr) = 0;
+ //------------------------------------------------------------------
+ /// Launch a process for debugging. This method will create an concrete
+ /// instance of NativeProcessProtocol, based on the host platform.
+ /// (e.g. NativeProcessLinux on linux, etc.)
+ ///
+ /// @param[in] launch_info
+ /// Information required to launch the process.
+ ///
+ /// @param[in] native_delegate
+ /// The delegate that will receive messages regarding the
+ /// inferior. Must outlive the NativeProcessProtocol
+ /// instance.
+ ///
+ /// @param[out] process_sp
+ /// On successful return from the method, this parameter
+ /// contains the shared pointer to the
+ /// NativeProcessProtocol that can be used to manipulate
+ /// the native process.
+ ///
+ /// @return
+ /// An error object indicating if the operation succeeded,
+ /// and if not, what error occurred.
+ //------------------------------------------------------------------
+ static Error
+ Launch (ProcessLaunchInfo &launch_info,
+ NativeDelegate &native_delegate,
+ NativeProcessProtocolSP &process_sp);
+
+ //------------------------------------------------------------------
+ /// Attach to an existing process. This method will create an concrete
+ /// instance of NativeProcessProtocol, based on the host platform.
+ /// (e.g. NativeProcessLinux on linux, etc.)
+ ///
+ /// @param[in] pid
+ /// pid of the process locatable
+ ///
+ /// @param[in] native_delegate
+ /// The delegate that will receive messages regarding the
+ /// inferior. Must outlive the NativeProcessProtocol
+ /// instance.
+ ///
+ /// @param[out] process_sp
+ /// On successful return from the method, this parameter
+ /// contains the shared pointer to the
+ /// NativeProcessProtocol that can be used to manipulate
+ /// the native process.
+ ///
+ /// @return
+ /// An error object indicating if the operation succeeded,
+ /// and if not, what error occurred.
+ //------------------------------------------------------------------
+ static Error
+ Attach (lldb::pid_t pid,
+ NativeDelegate &native_delegate,
+ NativeProcessProtocolSP &process_sp);
+
protected:
lldb::pid_t m_pid;
diff --git a/include/lldb/Host/posix/ConnectionFileDescriptorPosix.h b/include/lldb/Host/posix/ConnectionFileDescriptorPosix.h
index bcbb6014b116..2e0fd705b2a8 100644
--- a/include/lldb/Host/posix/ConnectionFileDescriptorPosix.h
+++ b/include/lldb/Host/posix/ConnectionFileDescriptorPosix.h
@@ -59,12 +59,7 @@ class ConnectionFileDescriptor : public Connection
bool InterruptRead() override;
lldb::IOObjectSP
- GetReadObject()
- {
- return m_read_sp;
- }
- const lldb::IOObjectSP
- GetReadObject() const
+ GetReadObject() override
{
return m_read_sp;
}
diff --git a/include/lldb/Host/posix/MainLoopPosix.h b/include/lldb/Host/posix/MainLoopPosix.h
new file mode 100644
index 000000000000..9a665ded295e
--- /dev/null
+++ b/include/lldb/Host/posix/MainLoopPosix.h
@@ -0,0 +1,100 @@
+//===-- MainLoopPosix.h -----------------------------------------*- C++ -*-===//
+//
+// The LLVM Compiler Infrastructure
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef lldb_Host_posix_MainLoopPosix_h_
+#define lldb_Host_posix_MainLoopPosix_h_
+
+#include "lldb/Host/MainLoopBase.h"
+
+#include "llvm/ADT/DenseMap.h"
+
+namespace lldb_private {
+
+// Posix implementation of the MainLoopBase class. It can monitor file descriptors for
+// readability using pselect. In addition to the common base, this class provides the ability to
+// invoke a given handler when a signal is received.
+//
+// Since this class is primarily intended to be used for single-threaded processing, it does not
+// attempt to perform any internal synchronisation and any concurrent accesses must be protected
+// externally. However, it is perfectly legitimate to have more than one instance of this class
+// running on separate threads, or even a single thread (with some limitations on signal
+// monitoring).
+// TODO: Add locking if this class is to be used in a multi-threaded context.
+class MainLoopPosix: public MainLoopBase
+{
+private:
+ class SignalHandle;
+
+public:
+ typedef std::unique_ptr<SignalHandle> SignalHandleUP;
+
+ ~MainLoopPosix() override;
+
+ ReadHandleUP
+ RegisterReadObject(const lldb::IOObjectSP &object_sp, const Callback &callback, Error &error) override;
+
+ // Listening for signals from multiple MainLoopPosix instances is perfectly safe as long as they
+ // don't try to listen for the same signal. The callback function is invoked when the control
+ // returns to the Run() function, not when the hander is executed. This means that you can
+ // treat the callback as a normal function and perform things which would not be safe in a
+ // signal handler. However, since the callback is not invoked synchronously, you cannot use
+ // this mechanism to handle SIGSEGV and the like.
+ SignalHandleUP
+ RegisterSignal(int signo, const Callback &callback, Error &error);
+
+ Error
+ Run() override;
+
+ // This should only be performed from a callback. Do not attempt to terminate the processing
+ // from another thread.
+ // TODO: Add synchronization if we want to be terminated from another thread.
+ void
+ RequestTermination() override
+ { m_terminate_request = true; }
+
+protected:
+ void
+ UnregisterReadObject(const lldb::IOObjectSP &object_sp) override;
+
+ void
+ UnregisterSignal(int signo);
+
+private:
+ class SignalHandle
+ {
+ public:
+ ~SignalHandle() { m_mainloop.UnregisterSignal(m_signo); }
+
+ private:
+ SignalHandle(MainLoopPosix &mainloop, int signo) : m_mainloop(mainloop), m_signo(signo) { }
+
+ MainLoopPosix &m_mainloop;
+ int m_signo;
+
+ friend class MainLoopPosix;
+ DISALLOW_COPY_AND_ASSIGN(SignalHandle);
+ };
+
+ struct SignalInfo
+ {
+ Callback callback;
+ struct sigaction old_action;
+ bool was_blocked : 1;
+ };
+
+ llvm::DenseMap<IOObject::WaitableHandle, Callback> m_read_fds;
+ llvm::DenseMap<int, SignalInfo> m_signals;
+ bool m_terminate_request : 1;
+};
+
+} // namespace lldb_private
+
+
+#endif // lldb_Host_posix_MainLoopPosix_h_
+