xref: /freebsd-src/contrib/llvm-project/lldb/source/Plugins/Process/gdb-remote/ProcessGDBRemote.h (revision 0fca6ea1d4eea4c934cfff25ac9ee8ad6fe95583)
10b57cec5SDimitry Andric //===-- ProcessGDBRemote.h --------------------------------------*- C++ -*-===//
20b57cec5SDimitry Andric //
30b57cec5SDimitry Andric // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
40b57cec5SDimitry Andric // See https://llvm.org/LICENSE.txt for license information.
50b57cec5SDimitry Andric // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
60b57cec5SDimitry Andric //
70b57cec5SDimitry Andric //===----------------------------------------------------------------------===//
80b57cec5SDimitry Andric 
95ffd83dbSDimitry Andric #ifndef LLDB_SOURCE_PLUGINS_PROCESS_GDB_REMOTE_PROCESSGDBREMOTE_H
105ffd83dbSDimitry Andric #define LLDB_SOURCE_PLUGINS_PROCESS_GDB_REMOTE_PROCESSGDBREMOTE_H
110b57cec5SDimitry Andric 
120b57cec5SDimitry Andric #include <atomic>
130b57cec5SDimitry Andric #include <map>
140b57cec5SDimitry Andric #include <mutex>
15bdd1243dSDimitry Andric #include <optional>
160b57cec5SDimitry Andric #include <string>
170b57cec5SDimitry Andric #include <vector>
180b57cec5SDimitry Andric 
190b57cec5SDimitry Andric #include "lldb/Core/LoadedModuleInfoList.h"
200b57cec5SDimitry Andric #include "lldb/Core/ModuleSpec.h"
210b57cec5SDimitry Andric #include "lldb/Core/ThreadSafeValue.h"
220b57cec5SDimitry Andric #include "lldb/Host/HostThread.h"
23349cc55cSDimitry Andric #include "lldb/Target/DynamicRegisterInfo.h"
240b57cec5SDimitry Andric #include "lldb/Target/Process.h"
250b57cec5SDimitry Andric #include "lldb/Target/Thread.h"
260b57cec5SDimitry Andric #include "lldb/Utility/ArchSpec.h"
270b57cec5SDimitry Andric #include "lldb/Utility/Broadcaster.h"
280b57cec5SDimitry Andric #include "lldb/Utility/ConstString.h"
299dba64beSDimitry Andric #include "lldb/Utility/GDBRemote.h"
300b57cec5SDimitry Andric #include "lldb/Utility/Status.h"
310b57cec5SDimitry Andric #include "lldb/Utility/StreamString.h"
320b57cec5SDimitry Andric #include "lldb/Utility/StringExtractor.h"
330b57cec5SDimitry Andric #include "lldb/Utility/StringList.h"
340b57cec5SDimitry Andric #include "lldb/Utility/StructuredData.h"
350b57cec5SDimitry Andric #include "lldb/lldb-private-forward.h"
360b57cec5SDimitry Andric 
370b57cec5SDimitry Andric #include "GDBRemoteCommunicationClient.h"
380b57cec5SDimitry Andric #include "GDBRemoteRegisterContext.h"
390b57cec5SDimitry Andric 
400b57cec5SDimitry Andric #include "llvm/ADT/DenseMap.h"
4106c3fb27SDimitry Andric #include "llvm/ADT/StringMap.h"
420b57cec5SDimitry Andric 
430b57cec5SDimitry Andric namespace lldb_private {
440b57cec5SDimitry Andric namespace repro {
450b57cec5SDimitry Andric class Loader;
460b57cec5SDimitry Andric }
470b57cec5SDimitry Andric namespace process_gdb_remote {
480b57cec5SDimitry Andric 
490b57cec5SDimitry Andric class ThreadGDBRemote;
500b57cec5SDimitry Andric 
510b57cec5SDimitry Andric class ProcessGDBRemote : public Process,
520b57cec5SDimitry Andric                          private GDBRemoteClientBase::ContinueDelegate {
530b57cec5SDimitry Andric public:
540b57cec5SDimitry Andric   ~ProcessGDBRemote() override;
550b57cec5SDimitry Andric 
560b57cec5SDimitry Andric   static lldb::ProcessSP CreateInstance(lldb::TargetSP target_sp,
570b57cec5SDimitry Andric                                         lldb::ListenerSP listener_sp,
58e8d8bef9SDimitry Andric                                         const FileSpec *crash_file_path,
59e8d8bef9SDimitry Andric                                         bool can_connect);
600b57cec5SDimitry Andric 
610b57cec5SDimitry Andric   static void Initialize();
620b57cec5SDimitry Andric 
630b57cec5SDimitry Andric   static void DebuggerInitialize(Debugger &debugger);
640b57cec5SDimitry Andric 
650b57cec5SDimitry Andric   static void Terminate();
660b57cec5SDimitry Andric 
67349cc55cSDimitry Andric   static llvm::StringRef GetPluginNameStatic() { return "gdb-remote"; }
680b57cec5SDimitry Andric 
69349cc55cSDimitry Andric   static llvm::StringRef GetPluginDescriptionStatic();
700b57cec5SDimitry Andric 
71fe6060f1SDimitry Andric   static std::chrono::seconds GetPacketTimeout();
72fe6060f1SDimitry Andric 
7381ad6265SDimitry Andric   ArchSpec GetSystemArchitecture() override;
7481ad6265SDimitry Andric 
750b57cec5SDimitry Andric   // Check if a given Process
760b57cec5SDimitry Andric   bool CanDebug(lldb::TargetSP target_sp,
770b57cec5SDimitry Andric                 bool plugin_specified_by_name) override;
780b57cec5SDimitry Andric 
790b57cec5SDimitry Andric   CommandObject *GetPluginCommandObject() override;
800b57cec5SDimitry Andric 
8106c3fb27SDimitry Andric   void DumpPluginHistory(Stream &s) override;
8206c3fb27SDimitry Andric 
830b57cec5SDimitry Andric   // Creating a new process, or attaching to an existing one
84bdd1243dSDimitry Andric   Status DoWillLaunch(Module *module) override;
850b57cec5SDimitry Andric 
860b57cec5SDimitry Andric   Status DoLaunch(Module *exe_module, ProcessLaunchInfo &launch_info) override;
870b57cec5SDimitry Andric 
880b57cec5SDimitry Andric   void DidLaunch() override;
890b57cec5SDimitry Andric 
90bdd1243dSDimitry Andric   Status DoWillAttachToProcessWithID(lldb::pid_t pid) override;
910b57cec5SDimitry Andric 
92bdd1243dSDimitry Andric   Status DoWillAttachToProcessWithName(const char *process_name,
930b57cec5SDimitry Andric                                        bool wait_for_launch) override;
940b57cec5SDimitry Andric 
955ffd83dbSDimitry Andric   Status DoConnectRemote(llvm::StringRef remote_url) override;
960b57cec5SDimitry Andric 
970b57cec5SDimitry Andric   Status WillLaunchOrAttach();
980b57cec5SDimitry Andric 
990b57cec5SDimitry Andric   Status DoAttachToProcessWithID(lldb::pid_t pid,
1000b57cec5SDimitry Andric                                  const ProcessAttachInfo &attach_info) override;
1010b57cec5SDimitry Andric 
1020b57cec5SDimitry Andric   Status
1030b57cec5SDimitry Andric   DoAttachToProcessWithName(const char *process_name,
1040b57cec5SDimitry Andric                             const ProcessAttachInfo &attach_info) override;
1050b57cec5SDimitry Andric 
1060b57cec5SDimitry Andric   void DidAttach(ArchSpec &process_arch) override;
1070b57cec5SDimitry Andric 
1080b57cec5SDimitry Andric   // PluginInterface protocol
109349cc55cSDimitry Andric   llvm::StringRef GetPluginName() override { return GetPluginNameStatic(); }
1100b57cec5SDimitry Andric 
1110b57cec5SDimitry Andric   // Process Control
1120b57cec5SDimitry Andric   Status WillResume() override;
1130b57cec5SDimitry Andric 
1140b57cec5SDimitry Andric   Status DoResume() override;
1150b57cec5SDimitry Andric 
1160b57cec5SDimitry Andric   Status DoHalt(bool &caused_stop) override;
1170b57cec5SDimitry Andric 
1180b57cec5SDimitry Andric   Status DoDetach(bool keep_stopped) override;
1190b57cec5SDimitry Andric 
1200b57cec5SDimitry Andric   bool DetachRequiresHalt() override { return true; }
1210b57cec5SDimitry Andric 
1220b57cec5SDimitry Andric   Status DoSignal(int signal) override;
1230b57cec5SDimitry Andric 
1240b57cec5SDimitry Andric   Status DoDestroy() override;
1250b57cec5SDimitry Andric 
1260b57cec5SDimitry Andric   void RefreshStateAfterStop() override;
1270b57cec5SDimitry Andric 
1280b57cec5SDimitry Andric   void SetUnixSignals(const lldb::UnixSignalsSP &signals_sp);
1290b57cec5SDimitry Andric 
1300b57cec5SDimitry Andric   // Process Queries
1310b57cec5SDimitry Andric   bool IsAlive() override;
1320b57cec5SDimitry Andric 
1330b57cec5SDimitry Andric   lldb::addr_t GetImageInfoAddress() override;
1340b57cec5SDimitry Andric 
1350b57cec5SDimitry Andric   void WillPublicStop() override;
1360b57cec5SDimitry Andric 
1370b57cec5SDimitry Andric   // Process Memory
1380b57cec5SDimitry Andric   size_t DoReadMemory(lldb::addr_t addr, void *buf, size_t size,
1390b57cec5SDimitry Andric                       Status &error) override;
1400b57cec5SDimitry Andric 
1410b57cec5SDimitry Andric   Status
1420b57cec5SDimitry Andric   WriteObjectFile(std::vector<ObjectFile::LoadableData> entries) override;
1430b57cec5SDimitry Andric 
1440b57cec5SDimitry Andric   size_t DoWriteMemory(lldb::addr_t addr, const void *buf, size_t size,
1450b57cec5SDimitry Andric                        Status &error) override;
1460b57cec5SDimitry Andric 
1470b57cec5SDimitry Andric   lldb::addr_t DoAllocateMemory(size_t size, uint32_t permissions,
1480b57cec5SDimitry Andric                                 Status &error) override;
1490b57cec5SDimitry Andric 
1500b57cec5SDimitry Andric   Status DoDeallocateMemory(lldb::addr_t ptr) override;
1510b57cec5SDimitry Andric 
1520b57cec5SDimitry Andric   // Process STDIO
1530b57cec5SDimitry Andric   size_t PutSTDIN(const char *buf, size_t buf_size, Status &error) override;
1540b57cec5SDimitry Andric 
1550b57cec5SDimitry Andric   // Process Breakpoints
1560b57cec5SDimitry Andric   Status EnableBreakpointSite(BreakpointSite *bp_site) override;
1570b57cec5SDimitry Andric 
1580b57cec5SDimitry Andric   Status DisableBreakpointSite(BreakpointSite *bp_site) override;
1590b57cec5SDimitry Andric 
1600b57cec5SDimitry Andric   // Process Watchpoints
1615f757f3fSDimitry Andric   Status EnableWatchpoint(lldb::WatchpointSP wp_sp,
1625f757f3fSDimitry Andric                           bool notify = true) override;
1630b57cec5SDimitry Andric 
1645f757f3fSDimitry Andric   Status DisableWatchpoint(lldb::WatchpointSP wp_sp,
1655f757f3fSDimitry Andric                            bool notify = true) override;
1660b57cec5SDimitry Andric 
16706c3fb27SDimitry Andric   std::optional<uint32_t> GetWatchpointSlotCount() override;
1680b57cec5SDimitry Andric 
169fe6060f1SDimitry Andric   llvm::Expected<TraceSupportedResponse> TraceSupported() override;
1700b57cec5SDimitry Andric 
171fe6060f1SDimitry Andric   llvm::Error TraceStop(const TraceStopRequest &request) override;
1720b57cec5SDimitry Andric 
173fe6060f1SDimitry Andric   llvm::Error TraceStart(const llvm::json::Value &request) override;
1740b57cec5SDimitry Andric 
175fe6060f1SDimitry Andric   llvm::Expected<std::string> TraceGetState(llvm::StringRef type) override;
1760b57cec5SDimitry Andric 
177fe6060f1SDimitry Andric   llvm::Expected<std::vector<uint8_t>>
178fe6060f1SDimitry Andric   TraceGetBinaryData(const TraceGetBinaryDataRequest &request) override;
1790b57cec5SDimitry Andric 
18006c3fb27SDimitry Andric   std::optional<bool> DoGetWatchpointReportedAfter() override;
1810b57cec5SDimitry Andric 
1820b57cec5SDimitry Andric   bool StartNoticingNewThreads() override;
1830b57cec5SDimitry Andric 
1840b57cec5SDimitry Andric   bool StopNoticingNewThreads() override;
1850b57cec5SDimitry Andric 
1860b57cec5SDimitry Andric   GDBRemoteCommunicationClient &GetGDBRemote() { return m_gdb_comm; }
1870b57cec5SDimitry Andric 
1880b57cec5SDimitry Andric   Status SendEventData(const char *data) override;
1890b57cec5SDimitry Andric 
1900b57cec5SDimitry Andric   // Override DidExit so we can disconnect from the remote GDB server
1910b57cec5SDimitry Andric   void DidExit() override;
1920b57cec5SDimitry Andric 
1930b57cec5SDimitry Andric   void SetUserSpecifiedMaxMemoryTransferSize(uint64_t user_specified_max);
1940b57cec5SDimitry Andric 
1950b57cec5SDimitry Andric   bool GetModuleSpec(const FileSpec &module_file_spec, const ArchSpec &arch,
1960b57cec5SDimitry Andric                      ModuleSpec &module_spec) override;
1970b57cec5SDimitry Andric 
1980b57cec5SDimitry Andric   void PrefetchModuleSpecs(llvm::ArrayRef<FileSpec> module_file_specs,
1990b57cec5SDimitry Andric                            const llvm::Triple &triple) override;
2000b57cec5SDimitry Andric 
2010b57cec5SDimitry Andric   llvm::VersionTuple GetHostOSVersion() override;
2029dba64beSDimitry Andric   llvm::VersionTuple GetHostMacCatalystVersion() override;
2030b57cec5SDimitry Andric 
2049dba64beSDimitry Andric   llvm::Error LoadModules() override;
2050b57cec5SDimitry Andric 
2069dba64beSDimitry Andric   llvm::Expected<LoadedModuleInfoList> GetLoadedModuleList() override;
2070b57cec5SDimitry Andric 
2080b57cec5SDimitry Andric   Status GetFileLoadAddress(const FileSpec &file, bool &is_loaded,
2090b57cec5SDimitry Andric                             lldb::addr_t &load_addr) override;
2100b57cec5SDimitry Andric 
2110b57cec5SDimitry Andric   void ModulesDidLoad(ModuleList &module_list) override;
2120b57cec5SDimitry Andric 
2130b57cec5SDimitry Andric   StructuredData::ObjectSP
2140b57cec5SDimitry Andric   GetLoadedDynamicLibrariesInfos(lldb::addr_t image_list_address,
2150b57cec5SDimitry Andric                                  lldb::addr_t image_count) override;
2160b57cec5SDimitry Andric 
2170b57cec5SDimitry Andric   Status
21806c3fb27SDimitry Andric   ConfigureStructuredData(llvm::StringRef type_name,
2190b57cec5SDimitry Andric                           const StructuredData::ObjectSP &config_sp) override;
2200b57cec5SDimitry Andric 
2210b57cec5SDimitry Andric   StructuredData::ObjectSP GetLoadedDynamicLibrariesInfos() override;
2220b57cec5SDimitry Andric 
2230b57cec5SDimitry Andric   StructuredData::ObjectSP GetLoadedDynamicLibrariesInfos(
2240b57cec5SDimitry Andric       const std::vector<lldb::addr_t> &load_addresses) override;
2250b57cec5SDimitry Andric 
2260b57cec5SDimitry Andric   StructuredData::ObjectSP
2270b57cec5SDimitry Andric   GetLoadedDynamicLibrariesInfos_sender(StructuredData::ObjectSP args);
2280b57cec5SDimitry Andric 
2290b57cec5SDimitry Andric   StructuredData::ObjectSP GetSharedCacheInfo() override;
2300b57cec5SDimitry Andric 
231bdd1243dSDimitry Andric   StructuredData::ObjectSP GetDynamicLoaderProcessState() override;
232bdd1243dSDimitry Andric 
2330b57cec5SDimitry Andric   std::string HarmonizeThreadIdsForProfileData(
2340b57cec5SDimitry Andric       StringExtractorGDBRemote &inputStringExtractor);
2350b57cec5SDimitry Andric 
236349cc55cSDimitry Andric   void DidFork(lldb::pid_t child_pid, lldb::tid_t child_tid) override;
237349cc55cSDimitry Andric   void DidVFork(lldb::pid_t child_pid, lldb::tid_t child_tid) override;
238349cc55cSDimitry Andric   void DidVForkDone() override;
239349cc55cSDimitry Andric   void DidExec() override;
240349cc55cSDimitry Andric 
241349cc55cSDimitry Andric   llvm::Expected<bool> SaveCore(llvm::StringRef outfile) override;
242349cc55cSDimitry Andric 
2430b57cec5SDimitry Andric protected:
2440b57cec5SDimitry Andric   friend class ThreadGDBRemote;
2450b57cec5SDimitry Andric   friend class GDBRemoteCommunicationClient;
2460b57cec5SDimitry Andric   friend class GDBRemoteRegisterContext;
2470b57cec5SDimitry Andric 
248bdd1243dSDimitry Andric   ProcessGDBRemote(lldb::TargetSP target_sp, lldb::ListenerSP listener_sp);
249bdd1243dSDimitry Andric 
250fe6060f1SDimitry Andric   bool SupportsMemoryTagging() override;
251fe6060f1SDimitry Andric 
2520b57cec5SDimitry Andric   /// Broadcaster event bits definitions.
2530b57cec5SDimitry Andric   enum {
2540b57cec5SDimitry Andric     eBroadcastBitAsyncContinue = (1 << 0),
2550b57cec5SDimitry Andric     eBroadcastBitAsyncThreadShouldExit = (1 << 1),
2560b57cec5SDimitry Andric     eBroadcastBitAsyncThreadDidExit = (1 << 2)
2570b57cec5SDimitry Andric   };
2580b57cec5SDimitry Andric 
2590b57cec5SDimitry Andric   GDBRemoteCommunicationClient m_gdb_comm;
2600b57cec5SDimitry Andric   std::atomic<lldb::pid_t> m_debugserver_pid;
261349cc55cSDimitry Andric 
262bdd1243dSDimitry Andric   std::optional<StringExtractorGDBRemote> m_last_stop_packet;
2630b57cec5SDimitry Andric   std::recursive_mutex m_last_stop_packet_mutex;
264349cc55cSDimitry Andric 
265e8d8bef9SDimitry Andric   GDBRemoteDynamicRegisterInfoSP m_register_info_sp;
2660b57cec5SDimitry Andric   Broadcaster m_async_broadcaster;
2670b57cec5SDimitry Andric   lldb::ListenerSP m_async_listener_sp;
2680b57cec5SDimitry Andric   HostThread m_async_thread;
2690b57cec5SDimitry Andric   std::recursive_mutex m_async_thread_state_mutex;
2700b57cec5SDimitry Andric   typedef std::vector<lldb::tid_t> tid_collection;
2710b57cec5SDimitry Andric   typedef std::vector<std::pair<lldb::tid_t, int>> tid_sig_collection;
2720b57cec5SDimitry Andric   typedef std::map<lldb::addr_t, lldb::addr_t> MMapMap;
2730b57cec5SDimitry Andric   typedef std::map<uint32_t, std::string> ExpeditedRegisterMap;
2740b57cec5SDimitry Andric   tid_collection m_thread_ids; // Thread IDs for all threads. This list gets
2750b57cec5SDimitry Andric                                // updated after stopping
2760b57cec5SDimitry Andric   std::vector<lldb::addr_t> m_thread_pcs;     // PC values for all the threads.
2770b57cec5SDimitry Andric   StructuredData::ObjectSP m_jstopinfo_sp;    // Stop info only for any threads
2780b57cec5SDimitry Andric                                               // that have valid stop infos
2790b57cec5SDimitry Andric   StructuredData::ObjectSP m_jthreadsinfo_sp; // Full stop info, expedited
2800b57cec5SDimitry Andric                                               // registers and memory for all
2810b57cec5SDimitry Andric                                               // threads if "jThreadsInfo"
2820b57cec5SDimitry Andric                                               // packet is supported
2830b57cec5SDimitry Andric   tid_collection m_continue_c_tids;           // 'c' for continue
2840b57cec5SDimitry Andric   tid_sig_collection m_continue_C_tids;       // 'C' for continue with signal
2850b57cec5SDimitry Andric   tid_collection m_continue_s_tids;           // 's' for step
2860b57cec5SDimitry Andric   tid_sig_collection m_continue_S_tids;       // 'S' for step with signal
2870b57cec5SDimitry Andric   uint64_t m_max_memory_size; // The maximum number of bytes to read/write when
2880b57cec5SDimitry Andric                               // reading and writing memory
2890b57cec5SDimitry Andric   uint64_t m_remote_stub_max_memory_size; // The maximum memory size the remote
2900b57cec5SDimitry Andric                                           // gdb stub can handle
2910b57cec5SDimitry Andric   MMapMap m_addr_to_mmap_size;
2920b57cec5SDimitry Andric   lldb::BreakpointSP m_thread_create_bp_sp;
2930b57cec5SDimitry Andric   bool m_waiting_for_attach;
2940b57cec5SDimitry Andric   lldb::CommandObjectSP m_command_sp;
2950b57cec5SDimitry Andric   int64_t m_breakpoint_pc_offset;
2960b57cec5SDimitry Andric   lldb::tid_t m_initial_tid; // The initial thread ID, given by stub on attach
297480093f4SDimitry Andric   bool m_use_g_packet_for_reading;
2980b57cec5SDimitry Andric 
2990b57cec5SDimitry Andric   bool m_allow_flash_writes;
3000b57cec5SDimitry Andric   using FlashRangeVector = lldb_private::RangeVector<lldb::addr_t, size_t>;
3010b57cec5SDimitry Andric   using FlashRange = FlashRangeVector::Entry;
3020b57cec5SDimitry Andric   FlashRangeVector m_erased_flash_ranges;
3030b57cec5SDimitry Andric 
304*0fca6ea1SDimitry Andric   // Number of vfork() operations being handled.
305*0fca6ea1SDimitry Andric   uint32_t m_vfork_in_progress_count;
306349cc55cSDimitry Andric 
3070b57cec5SDimitry Andric   // Accessors
3080b57cec5SDimitry Andric   bool IsRunning(lldb::StateType state) {
3090b57cec5SDimitry Andric     return state == lldb::eStateRunning || IsStepping(state);
3100b57cec5SDimitry Andric   }
3110b57cec5SDimitry Andric 
3120b57cec5SDimitry Andric   bool IsStepping(lldb::StateType state) {
3130b57cec5SDimitry Andric     return state == lldb::eStateStepping;
3140b57cec5SDimitry Andric   }
3150b57cec5SDimitry Andric 
3160b57cec5SDimitry Andric   bool CanResume(lldb::StateType state) { return state == lldb::eStateStopped; }
3170b57cec5SDimitry Andric 
3180b57cec5SDimitry Andric   bool HasExited(lldb::StateType state) { return state == lldb::eStateExited; }
3190b57cec5SDimitry Andric 
3200b57cec5SDimitry Andric   void Clear();
3210b57cec5SDimitry Andric 
322e8d8bef9SDimitry Andric   bool DoUpdateThreadList(ThreadList &old_thread_list,
3230b57cec5SDimitry Andric                           ThreadList &new_thread_list) override;
3240b57cec5SDimitry Andric 
3250b57cec5SDimitry Andric   Status EstablishConnectionIfNeeded(const ProcessInfo &process_info);
3260b57cec5SDimitry Andric 
3270b57cec5SDimitry Andric   Status LaunchAndConnectToDebugserver(const ProcessInfo &process_info);
3280b57cec5SDimitry Andric 
3290b57cec5SDimitry Andric   void KillDebugserverProcess();
3300b57cec5SDimitry Andric 
3310b57cec5SDimitry Andric   void BuildDynamicRegisterInfo(bool force);
3320b57cec5SDimitry Andric 
3330b57cec5SDimitry Andric   void SetLastStopPacket(const StringExtractorGDBRemote &response);
3340b57cec5SDimitry Andric 
3350b57cec5SDimitry Andric   bool ParsePythonTargetDefinition(const FileSpec &target_definition_fspec);
3360b57cec5SDimitry Andric 
3370b57cec5SDimitry Andric   DataExtractor GetAuxvData() override;
3380b57cec5SDimitry Andric 
3390b57cec5SDimitry Andric   StructuredData::ObjectSP GetExtendedInfoForThread(lldb::tid_t tid);
3400b57cec5SDimitry Andric 
3410b57cec5SDimitry Andric   void GetMaxMemorySize();
3420b57cec5SDimitry Andric 
3430b57cec5SDimitry Andric   bool CalculateThreadStopInfo(ThreadGDBRemote *thread);
3440b57cec5SDimitry Andric 
345349cc55cSDimitry Andric   size_t UpdateThreadPCsFromStopReplyThreadsValue(llvm::StringRef value);
3460b57cec5SDimitry Andric 
347fe6060f1SDimitry Andric   size_t UpdateThreadIDsFromStopReplyThreadsValue(llvm::StringRef value);
3480b57cec5SDimitry Andric 
3490b57cec5SDimitry Andric   bool StartAsyncThread();
3500b57cec5SDimitry Andric 
3510b57cec5SDimitry Andric   void StopAsyncThread();
3520b57cec5SDimitry Andric 
35381ad6265SDimitry Andric   lldb::thread_result_t AsyncThread();
3540b57cec5SDimitry Andric 
35581ad6265SDimitry Andric   static void
3560b57cec5SDimitry Andric   MonitorDebugserverProcess(std::weak_ptr<ProcessGDBRemote> process_wp,
35781ad6265SDimitry Andric                             lldb::pid_t pid, int signo, int exit_status);
3580b57cec5SDimitry Andric 
3590b57cec5SDimitry Andric   lldb::StateType SetThreadStopInfo(StringExtractor &stop_packet);
3600b57cec5SDimitry Andric 
3610b57cec5SDimitry Andric   bool
3620b57cec5SDimitry Andric   GetThreadStopInfoFromJSON(ThreadGDBRemote *thread,
3630b57cec5SDimitry Andric                             const StructuredData::ObjectSP &thread_infos_sp);
3640b57cec5SDimitry Andric 
3650b57cec5SDimitry Andric   lldb::ThreadSP SetThreadStopInfo(StructuredData::Dictionary *thread_dict);
3660b57cec5SDimitry Andric 
3670b57cec5SDimitry Andric   lldb::ThreadSP
3680b57cec5SDimitry Andric   SetThreadStopInfo(lldb::tid_t tid,
3690b57cec5SDimitry Andric                     ExpeditedRegisterMap &expedited_register_map, uint8_t signo,
3700b57cec5SDimitry Andric                     const std::string &thread_name, const std::string &reason,
3710b57cec5SDimitry Andric                     const std::string &description, uint32_t exc_type,
3720b57cec5SDimitry Andric                     const std::vector<lldb::addr_t> &exc_data,
3730b57cec5SDimitry Andric                     lldb::addr_t thread_dispatch_qaddr, bool queue_vars_valid,
3740b57cec5SDimitry Andric                     lldb_private::LazyBool associated_with_libdispatch_queue,
3750b57cec5SDimitry Andric                     lldb::addr_t dispatch_queue_t, std::string &queue_name,
3760b57cec5SDimitry Andric                     lldb::QueueKind queue_kind, uint64_t queue_serial);
3770b57cec5SDimitry Andric 
3780b57cec5SDimitry Andric   void ClearThreadIDList();
3790b57cec5SDimitry Andric 
3800b57cec5SDimitry Andric   bool UpdateThreadIDList();
3810b57cec5SDimitry Andric 
3820b57cec5SDimitry Andric   void DidLaunchOrAttach(ArchSpec &process_arch);
383bdd1243dSDimitry Andric   void LoadStubBinaries();
3845ffd83dbSDimitry Andric   void MaybeLoadExecutableModule();
3850b57cec5SDimitry Andric 
3860b57cec5SDimitry Andric   Status ConnectToDebugserver(llvm::StringRef host_port);
3870b57cec5SDimitry Andric 
3880b57cec5SDimitry Andric   const char *GetDispatchQueueNameForThread(lldb::addr_t thread_dispatch_qaddr,
3890b57cec5SDimitry Andric                                             std::string &dispatch_queue_name);
3900b57cec5SDimitry Andric 
3910b57cec5SDimitry Andric   DynamicLoader *GetDynamicLoader() override;
3920b57cec5SDimitry Andric 
393349cc55cSDimitry Andric   bool GetGDBServerRegisterInfoXMLAndProcess(
394349cc55cSDimitry Andric     ArchSpec &arch_to_use, std::string xml_filename,
395349cc55cSDimitry Andric     std::vector<DynamicRegisterInfo::Register> &registers);
3960b57cec5SDimitry Andric 
397349cc55cSDimitry Andric   // Convert DynamicRegisterInfo::Registers into RegisterInfos and add
398349cc55cSDimitry Andric   // to the dynamic register list.
399349cc55cSDimitry Andric   void AddRemoteRegisters(std::vector<DynamicRegisterInfo::Register> &registers,
400349cc55cSDimitry Andric                           const ArchSpec &arch_to_use);
4010b57cec5SDimitry Andric   // Query remote GDBServer for register information
4020b57cec5SDimitry Andric   bool GetGDBServerRegisterInfo(ArchSpec &arch);
4030b57cec5SDimitry Andric 
4040b57cec5SDimitry Andric   lldb::ModuleSP LoadModuleAtAddress(const FileSpec &file,
4050b57cec5SDimitry Andric                                      lldb::addr_t link_map,
4060b57cec5SDimitry Andric                                      lldb::addr_t base_addr,
4070b57cec5SDimitry Andric                                      bool value_is_offset);
4080b57cec5SDimitry Andric 
4090b57cec5SDimitry Andric   Status UpdateAutomaticSignalFiltering() override;
4100b57cec5SDimitry Andric 
4110b57cec5SDimitry Andric   Status FlashErase(lldb::addr_t addr, size_t size);
4120b57cec5SDimitry Andric 
4130b57cec5SDimitry Andric   Status FlashDone();
4140b57cec5SDimitry Andric 
4150b57cec5SDimitry Andric   bool HasErased(FlashRange range);
4160b57cec5SDimitry Andric 
417fe6060f1SDimitry Andric   llvm::Expected<std::vector<uint8_t>>
418fe6060f1SDimitry Andric   DoReadMemoryTags(lldb::addr_t addr, size_t len, int32_t type) override;
419fe6060f1SDimitry Andric 
420fe6060f1SDimitry Andric   Status DoWriteMemoryTags(lldb::addr_t addr, size_t len, int32_t type,
421fe6060f1SDimitry Andric                            const std::vector<uint8_t> &tags) override;
422fe6060f1SDimitry Andric 
423d56accc7SDimitry Andric   Status DoGetMemoryRegionInfo(lldb::addr_t load_addr,
424d56accc7SDimitry Andric                                MemoryRegionInfo &region_info) override;
425d56accc7SDimitry Andric 
4260b57cec5SDimitry Andric private:
4270b57cec5SDimitry Andric   // For ProcessGDBRemote only
4280b57cec5SDimitry Andric   std::string m_partial_profile_data;
4290b57cec5SDimitry Andric   std::map<uint64_t, uint32_t> m_thread_id_to_used_usec_map;
4300b57cec5SDimitry Andric   uint64_t m_last_signals_version = 0;
4310b57cec5SDimitry Andric 
4320b57cec5SDimitry Andric   static bool NewThreadNotifyBreakpointHit(void *baton,
4330b57cec5SDimitry Andric                                            StoppointCallbackContext *context,
4340b57cec5SDimitry Andric                                            lldb::user_id_t break_id,
4350b57cec5SDimitry Andric                                            lldb::user_id_t break_loc_id);
4360b57cec5SDimitry Andric 
4370b57cec5SDimitry Andric   // ContinueDelegate interface
4380b57cec5SDimitry Andric   void HandleAsyncStdout(llvm::StringRef out) override;
4390b57cec5SDimitry Andric   void HandleAsyncMisc(llvm::StringRef data) override;
4400b57cec5SDimitry Andric   void HandleStopReply() override;
4410b57cec5SDimitry Andric   void HandleAsyncStructuredDataPacket(llvm::StringRef data) override;
4420b57cec5SDimitry Andric 
4430b57cec5SDimitry Andric   void SetThreadPc(const lldb::ThreadSP &thread_sp, uint64_t index);
4440b57cec5SDimitry Andric   using ModuleCacheKey = std::pair<std::string, std::string>;
4450b57cec5SDimitry Andric   // KeyInfo for the cached module spec DenseMap.
4460b57cec5SDimitry Andric   // The invariant is that all real keys will have the file and architecture
4470b57cec5SDimitry Andric   // set.
4480b57cec5SDimitry Andric   // The empty key has an empty file and an empty arch.
4490b57cec5SDimitry Andric   // The tombstone key has an invalid arch and an empty file.
4500b57cec5SDimitry Andric   // The comparison and hash functions take the file name and architecture
4510b57cec5SDimitry Andric   // triple into account.
4520b57cec5SDimitry Andric   struct ModuleCacheInfo {
4530b57cec5SDimitry Andric     static ModuleCacheKey getEmptyKey() { return ModuleCacheKey(); }
4540b57cec5SDimitry Andric 
4550b57cec5SDimitry Andric     static ModuleCacheKey getTombstoneKey() { return ModuleCacheKey("", "T"); }
4560b57cec5SDimitry Andric 
4570b57cec5SDimitry Andric     static unsigned getHashValue(const ModuleCacheKey &key) {
4580b57cec5SDimitry Andric       return llvm::hash_combine(key.first, key.second);
4590b57cec5SDimitry Andric     }
4600b57cec5SDimitry Andric 
4610b57cec5SDimitry Andric     static bool isEqual(const ModuleCacheKey &LHS, const ModuleCacheKey &RHS) {
4620b57cec5SDimitry Andric       return LHS == RHS;
4630b57cec5SDimitry Andric     }
4640b57cec5SDimitry Andric   };
4650b57cec5SDimitry Andric 
4660b57cec5SDimitry Andric   llvm::DenseMap<ModuleCacheKey, ModuleSpec, ModuleCacheInfo>
4670b57cec5SDimitry Andric       m_cached_module_specs;
4680b57cec5SDimitry Andric 
4695ffd83dbSDimitry Andric   ProcessGDBRemote(const ProcessGDBRemote &) = delete;
4705ffd83dbSDimitry Andric   const ProcessGDBRemote &operator=(const ProcessGDBRemote &) = delete;
471349cc55cSDimitry Andric 
472349cc55cSDimitry Andric   // fork helpers
473349cc55cSDimitry Andric   void DidForkSwitchSoftwareBreakpoints(bool enable);
474349cc55cSDimitry Andric   void DidForkSwitchHardwareTraps(bool enable);
47506c3fb27SDimitry Andric 
4765f757f3fSDimitry Andric   void ParseExpeditedRegisters(ExpeditedRegisterMap &expedited_register_map,
4775f757f3fSDimitry Andric                                lldb::ThreadSP thread_sp);
4785f757f3fSDimitry Andric 
47906c3fb27SDimitry Andric   // Lists of register fields generated from the remote's target XML.
48006c3fb27SDimitry Andric   // Pointers to these RegisterFlags will be set in the register info passed
48106c3fb27SDimitry Andric   // back to the upper levels of lldb. Doing so is safe because this class will
48206c3fb27SDimitry Andric   // live at least as long as the debug session. We therefore do not store the
48306c3fb27SDimitry Andric   // data directly in the map because the map may reallocate it's storage as new
48406c3fb27SDimitry Andric   // entries are added. Which would invalidate any pointers set in the register
48506c3fb27SDimitry Andric   // info up to that point.
48606c3fb27SDimitry Andric   llvm::StringMap<std::unique_ptr<RegisterFlags>> m_registers_flags_types;
487*0fca6ea1SDimitry Andric 
488*0fca6ea1SDimitry Andric   // Enum types are referenced by register fields. This does not store the data
489*0fca6ea1SDimitry Andric   // directly because the map may reallocate. Pointers to these are contained
490*0fca6ea1SDimitry Andric   // within instances of RegisterFlags.
491*0fca6ea1SDimitry Andric   llvm::StringMap<std::unique_ptr<FieldEnum>> m_registers_enum_types;
4920b57cec5SDimitry Andric };
4930b57cec5SDimitry Andric 
4940b57cec5SDimitry Andric } // namespace process_gdb_remote
4950b57cec5SDimitry Andric } // namespace lldb_private
4960b57cec5SDimitry Andric 
4975ffd83dbSDimitry Andric #endif // LLDB_SOURCE_PLUGINS_PROCESS_GDB_REMOTE_PROCESSGDBREMOTE_H
498