Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2026-05-10 08:42:45

0001 //===-- ModuleList.h --------------------------------------------*- C++ -*-===//
0002 //
0003 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
0004 // See https://llvm.org/LICENSE.txt for license information.
0005 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
0006 //
0007 //===----------------------------------------------------------------------===//
0008 
0009 #ifndef LLDB_CORE_MODULELIST_H
0010 #define LLDB_CORE_MODULELIST_H
0011 
0012 #include "lldb/Core/Address.h"
0013 #include "lldb/Core/ModuleSpec.h"
0014 #include "lldb/Core/UserSettingsController.h"
0015 #include "lldb/Utility/FileSpec.h"
0016 #include "lldb/Utility/Iterable.h"
0017 #include "lldb/Utility/Status.h"
0018 #include "lldb/lldb-enumerations.h"
0019 #include "lldb/lldb-forward.h"
0020 #include "lldb/lldb-types.h"
0021 
0022 #include "llvm/ADT/DenseSet.h"
0023 #include "llvm/Support/RWMutex.h"
0024 
0025 #include <functional>
0026 #include <list>
0027 #include <mutex>
0028 #include <vector>
0029 
0030 #include <cstddef>
0031 #include <cstdint>
0032 
0033 namespace lldb_private {
0034 class ConstString;
0035 class FileSpecList;
0036 class Function;
0037 class Log;
0038 class Module;
0039 class RegularExpression;
0040 class Stream;
0041 class SymbolContext;
0042 class SymbolContextList;
0043 class SymbolFile;
0044 class Target;
0045 class TypeList;
0046 class UUID;
0047 class VariableList;
0048 struct ModuleFunctionSearchOptions;
0049 
0050 static constexpr OptionEnumValueElement g_auto_download_enum_values[] = {
0051     {
0052         lldb::eSymbolDownloadOff,
0053         "off",
0054         "Disable automatically downloading symbols.",
0055     },
0056     {
0057         lldb::eSymbolDownloadBackground,
0058         "background",
0059         "Download symbols in the background for images as they appear in the "
0060         "backtrace.",
0061     },
0062     {
0063         lldb::eSymbolDownloadForeground,
0064         "foreground",
0065         "Download symbols in the foreground for images as they appear in the "
0066         "backtrace.",
0067     },
0068 };
0069 
0070 class ModuleListProperties : public Properties {
0071   mutable llvm::sys::RWMutex m_symlink_paths_mutex;
0072   PathMappingList m_symlink_paths;
0073 
0074   void UpdateSymlinkMappings();
0075 
0076 public:
0077   ModuleListProperties();
0078 
0079   FileSpec GetClangModulesCachePath() const;
0080   bool SetClangModulesCachePath(const FileSpec &path);
0081   bool GetEnableExternalLookup() const;
0082   bool SetEnableExternalLookup(bool new_value);
0083   bool GetEnableLLDBIndexCache() const;
0084   bool SetEnableLLDBIndexCache(bool new_value);
0085   uint64_t GetLLDBIndexCacheMaxByteSize();
0086   uint64_t GetLLDBIndexCacheMaxPercent();
0087   uint64_t GetLLDBIndexCacheExpirationDays();
0088   FileSpec GetLLDBIndexCachePath() const;
0089   bool SetLLDBIndexCachePath(const FileSpec &path);
0090 
0091   bool GetLoadSymbolOnDemand();
0092 
0093   lldb::SymbolDownload GetSymbolAutoDownload() const;
0094 
0095   PathMappingList GetSymlinkMappings() const;
0096 };
0097 
0098 /// \class ModuleList ModuleList.h "lldb/Core/ModuleList.h"
0099 /// A collection class for Module objects.
0100 ///
0101 /// Modules in the module collection class are stored as reference counted
0102 /// shared pointers to Module objects.
0103 class ModuleList {
0104 public:
0105   class Notifier {
0106   public:
0107     virtual ~Notifier() = default;
0108 
0109     virtual void NotifyModuleAdded(const ModuleList &module_list,
0110                                    const lldb::ModuleSP &module_sp) = 0;
0111     virtual void NotifyModuleRemoved(const ModuleList &module_list,
0112                                      const lldb::ModuleSP &module_sp) = 0;
0113     virtual void NotifyModuleUpdated(const ModuleList &module_list,
0114                                      const lldb::ModuleSP &old_module_sp,
0115                                      const lldb::ModuleSP &new_module_sp) = 0;
0116     virtual void NotifyWillClearList(const ModuleList &module_list) = 0;
0117 
0118     virtual void NotifyModulesRemoved(lldb_private::ModuleList &module_list) = 0;
0119   };
0120 
0121   /// Default constructor.
0122   ///
0123   /// Creates an empty list of Module objects.
0124   ModuleList();
0125 
0126   /// Copy Constructor.
0127   ///
0128   /// Creates a new module list object with a copy of the modules from \a rhs.
0129   ///
0130   /// \param[in] rhs
0131   ///     Another module list object.
0132   ModuleList(const ModuleList &rhs);
0133 
0134   ModuleList(ModuleList::Notifier *notifier);
0135 
0136   /// Destructor.
0137   ~ModuleList();
0138 
0139   /// Assignment operator.
0140   ///
0141   /// Copies the module list from \a rhs into this list.
0142   ///
0143   /// \param[in] rhs
0144   ///     Another module list object.
0145   ///
0146   /// \return
0147   ///     A const reference to this object.
0148   const ModuleList &operator=(const ModuleList &rhs);
0149 
0150   /// Append a module to the module list.
0151   ///
0152   /// \param[in] module_sp
0153   ///     A shared pointer to a module to add to this collection.
0154   ///
0155   /// \param[in] notify
0156   ///     If true, and a notifier function is set, the notifier function
0157   ///     will be called.  Defaults to true.
0158   ///
0159   ///     When this ModuleList is the Target's ModuleList, the notifier
0160   ///     function is Target::ModulesDidLoad -- the call to
0161   ///     ModulesDidLoad may be deferred when adding multiple Modules
0162   ///     to the Target, but it must be called at the end,
0163   ///     before resuming execution.
0164   void Append(const lldb::ModuleSP &module_sp, bool notify = true);
0165 
0166   /// Append a module to the module list and remove any equivalent modules.
0167   /// Equivalent modules are ones whose file, platform file and architecture
0168   /// matches.
0169   ///
0170   /// Replaces the module to the collection.
0171   ///
0172   /// \param[in] module_sp
0173   ///     A shared pointer to a module to replace in this collection.
0174   ///
0175   /// \param[in] old_modules
0176   ///     Optional pointer to a vector which, if provided, will have shared
0177   ///     pointers to the replaced module(s) appended to it.
0178   void ReplaceEquivalent(
0179       const lldb::ModuleSP &module_sp,
0180       llvm::SmallVectorImpl<lldb::ModuleSP> *old_modules = nullptr);
0181 
0182   /// Append a module to the module list, if it is not already there.
0183   ///
0184   /// \param[in] notify
0185   ///     If true, and a notifier function is set, the notifier function
0186   ///     will be called.  Defaults to true.
0187   ///
0188   ///     When this ModuleList is the Target's ModuleList, the notifier
0189   ///     function is Target::ModulesDidLoad -- the call to
0190   ///     ModulesDidLoad may be deferred when adding multiple Modules
0191   ///     to the Target, but it must be called at the end,
0192   ///     before resuming execution.
0193   bool AppendIfNeeded(const lldb::ModuleSP &new_module, bool notify = true);
0194 
0195   void Append(const ModuleList &module_list);
0196 
0197   bool AppendIfNeeded(const ModuleList &module_list);
0198 
0199   bool ReplaceModule(const lldb::ModuleSP &old_module_sp,
0200                      const lldb::ModuleSP &new_module_sp);
0201 
0202   /// Clear the object's state.
0203   ///
0204   /// Clears the list of modules and releases a reference to each module
0205   /// object and if the reference count goes to zero, the module will be
0206   /// deleted.
0207   void Clear();
0208 
0209   /// Clear the object's state.
0210   ///
0211   /// Clears the list of modules and releases a reference to each module
0212   /// object and if the reference count goes to zero, the module will be
0213   /// deleted. Also release all memory that might be held by any collection
0214   /// classes (like std::vector)
0215   void Destroy();
0216 
0217   /// Dump the description of each module contained in this list.
0218   ///
0219   /// Dump the description of each module contained in this list to the
0220   /// supplied stream \a s.
0221   ///
0222   /// \param[in] s
0223   ///     The stream to which to dump the object description.
0224   ///
0225   /// \see Module::Dump(Stream *) const
0226   void Dump(Stream *s) const;
0227 
0228   void LogUUIDAndPaths(Log *log, const char *prefix_cstr);
0229 
0230   std::recursive_mutex &GetMutex() const { return m_modules_mutex; }
0231 
0232   size_t GetIndexForModule(const Module *module) const;
0233 
0234   /// Get the module shared pointer for the module at index \a idx.
0235   ///
0236   /// \param[in] idx
0237   ///     An index into this module collection.
0238   ///
0239   /// \return
0240   ///     A shared pointer to a Module which can contain NULL if
0241   ///     \a idx is out of range.
0242   ///
0243   /// \see ModuleList::GetSize()
0244   lldb::ModuleSP GetModuleAtIndex(size_t idx) const;
0245 
0246   /// Get the module shared pointer for the module at index \a idx without
0247   /// acquiring the ModuleList mutex.  This MUST already have been acquired
0248   /// with ModuleList::GetMutex and locked for this call to be safe.
0249   ///
0250   /// \param[in] idx
0251   ///     An index into this module collection.
0252   ///
0253   /// \return
0254   ///     A shared pointer to a Module which can contain NULL if
0255   ///     \a idx is out of range.
0256   ///
0257   /// \see ModuleList::GetSize()
0258   lldb::ModuleSP GetModuleAtIndexUnlocked(size_t idx) const;
0259 
0260   /// Get the module pointer for the module at index \a idx.
0261   ///
0262   /// \param[in] idx
0263   ///     An index into this module collection.
0264   ///
0265   /// \return
0266   ///     A pointer to a Module which can by nullptr if \a idx is out
0267   ///     of range.
0268   ///
0269   /// \see ModuleList::GetSize()
0270   Module *GetModulePointerAtIndex(size_t idx) const;
0271 
0272   /// Find compile units by partial or full path.
0273   ///
0274   /// Finds all compile units that match \a path in all of the modules and
0275   /// returns the results in \a sc_list.
0276   ///
0277   /// \param[in] path
0278   ///     The name of the compile unit we are looking for.
0279   ///
0280   /// \param[out] sc_list
0281   ///     A symbol context list that gets filled in with all of the
0282   ///     matches.
0283   void FindCompileUnits(const FileSpec &path, SymbolContextList &sc_list) const;
0284 
0285   /// \see Module::FindFunctions ()
0286   void FindFunctions(ConstString name, lldb::FunctionNameType name_type_mask,
0287                      const ModuleFunctionSearchOptions &options,
0288                      SymbolContextList &sc_list) const;
0289 
0290   /// \see Module::FindFunctionSymbols ()
0291   void FindFunctionSymbols(ConstString name,
0292                            lldb::FunctionNameType name_type_mask,
0293                            SymbolContextList &sc_list);
0294 
0295   /// \see Module::FindFunctions ()
0296   void FindFunctions(const RegularExpression &name,
0297                      const ModuleFunctionSearchOptions &options,
0298                      SymbolContextList &sc_list);
0299 
0300   /// Find global and static variables by name.
0301   ///
0302   /// \param[in] name
0303   ///     The name of the global or static variable we are looking
0304   ///     for.
0305   ///
0306   /// \param[in] max_matches
0307   ///     Allow the number of matches to be limited to \a
0308   ///     max_matches. Specify UINT32_MAX to get all possible matches.
0309   ///
0310   /// \param[in] variable_list
0311   ///     A list of variables that gets the matches appended to.
0312   void FindGlobalVariables(ConstString name, size_t max_matches,
0313                            VariableList &variable_list) const;
0314 
0315   /// Find global and static variables by regular expression.
0316   ///
0317   /// \param[in] regex
0318   ///     A regular expression to use when matching the name.
0319   ///
0320   /// \param[in] max_matches
0321   ///     Allow the number of matches to be limited to \a
0322   ///     max_matches. Specify UINT32_MAX to get all possible matches.
0323   ///
0324   /// \param[in] variable_list
0325   ///     A list of variables that gets the matches appended to.
0326   void FindGlobalVariables(const RegularExpression &regex, size_t max_matches,
0327                            VariableList &variable_list) const;
0328 
0329   /// Finds the first module whose file specification matches \a file_spec.
0330   ///
0331   /// \param[in] module_spec
0332   ///     A file specification object to match against the Module's
0333   ///     file specifications. If \a file_spec does not have
0334   ///     directory information, matches will occur by matching only
0335   ///     the basename of any modules in this list. If this value is
0336   ///     NULL, then file specifications won't be compared when
0337   ///     searching for matching modules.
0338   ///
0339   /// \param[out] matching_module_list
0340   ///     A module list that gets filled in with any modules that
0341   ///     match the search criteria.
0342   void FindModules(const ModuleSpec &module_spec,
0343                    ModuleList &matching_module_list) const;
0344 
0345   lldb::ModuleSP FindModule(const Module *module_ptr) const;
0346 
0347   // Find a module by UUID
0348   //
0349   // The UUID value for a module is extracted from the ObjectFile and is the
0350   // MD5 checksum, or a smarter object file equivalent, so finding modules by
0351   // UUID values is very efficient and accurate.
0352   lldb::ModuleSP FindModule(const UUID &uuid) const;
0353 
0354   lldb::ModuleSP FindFirstModule(const ModuleSpec &module_spec) const;
0355 
0356   void FindSymbolsWithNameAndType(ConstString name,
0357                                   lldb::SymbolType symbol_type,
0358                                   SymbolContextList &sc_list) const;
0359 
0360   void FindSymbolsMatchingRegExAndType(const RegularExpression &regex,
0361                                        lldb::SymbolType symbol_type,
0362                                        SymbolContextList &sc_list) const;
0363 
0364   /// Find types using a type-matching object that contains all search
0365   /// parameters.
0366   ///
0367   /// \param[in] search_first
0368   ///     If non-null, this module will be searched before any other
0369   ///     modules.
0370   ///
0371   /// \param[in] query
0372   ///     A type matching object that contains all of the details of the type
0373   ///     search.
0374   ///
0375   /// \param[in] results
0376   ///     Any matching types will be populated into the \a results object using
0377   ///     TypeMap::InsertUnique(...).
0378   void FindTypes(Module *search_first, const TypeQuery &query,
0379                  lldb_private::TypeResults &results) const;
0380 
0381   bool FindSourceFile(const FileSpec &orig_spec, FileSpec &new_spec) const;
0382 
0383   /// Find addresses by file/line
0384   ///
0385   /// \param[in] target_sp
0386   ///     The target the addresses are desired for.
0387   ///
0388   /// \param[in] file
0389   ///     Source file to locate.
0390   ///
0391   /// \param[in] line
0392   ///     Source line to locate.
0393   ///
0394   /// \param[in] function
0395   ///     Optional filter function. Addresses within this function will be
0396   ///     added to the 'local' list. All others will be added to the 'extern'
0397   ///     list.
0398   ///
0399   /// \param[out] output_local
0400   ///     All matching addresses within 'function'
0401   ///
0402   /// \param[out] output_extern
0403   ///     All matching addresses not within 'function'
0404   void FindAddressesForLine(const lldb::TargetSP target_sp,
0405                             const FileSpec &file, uint32_t line,
0406                             Function *function,
0407                             std::vector<Address> &output_local,
0408                             std::vector<Address> &output_extern);
0409 
0410   /// Remove a module from the module list.
0411   ///
0412   /// \param[in] module_sp
0413   ///     A shared pointer to a module to remove from this collection.
0414   ///
0415   /// \param[in] notify
0416   ///     If true, and a notifier function is set, the notifier function
0417   ///     will be called.  Defaults to true.
0418   ///
0419   ///     When this ModuleList is the Target's ModuleList, the notifier
0420   ///     function is Target::ModulesDidUnload -- the call to
0421   ///     ModulesDidUnload may be deferred when removing multiple Modules
0422   ///     from the Target, but it must be called at the end,
0423   ///     before resuming execution.
0424   bool Remove(const lldb::ModuleSP &module_sp, bool notify = true);
0425 
0426   size_t Remove(ModuleList &module_list);
0427 
0428   bool RemoveIfOrphaned(const Module *module_ptr);
0429 
0430   size_t RemoveOrphans(bool mandatory);
0431 
0432   bool ResolveFileAddress(lldb::addr_t vm_addr, Address &so_addr) const;
0433 
0434   /// \copydoc Module::ResolveSymbolContextForAddress (const Address
0435   /// &,uint32_t,SymbolContext&)
0436   uint32_t ResolveSymbolContextForAddress(const Address &so_addr,
0437                                           lldb::SymbolContextItem resolve_scope,
0438                                           SymbolContext &sc) const;
0439 
0440   /// \copydoc Module::ResolveSymbolContextForFilePath (const char
0441   /// *,uint32_t,bool,uint32_t,SymbolContextList&)
0442   uint32_t ResolveSymbolContextForFilePath(
0443       const char *file_path, uint32_t line, bool check_inlines,
0444       lldb::SymbolContextItem resolve_scope, SymbolContextList &sc_list) const;
0445 
0446   /// \copydoc Module::ResolveSymbolContextsForFileSpec (const FileSpec
0447   /// &,uint32_t,bool,uint32_t,SymbolContextList&)
0448   uint32_t ResolveSymbolContextsForFileSpec(
0449       const FileSpec &file_spec, uint32_t line, bool check_inlines,
0450       lldb::SymbolContextItem resolve_scope, SymbolContextList &sc_list) const;
0451 
0452   /// Gets the size of the module list.
0453   ///
0454   /// \return
0455   ///     The number of modules in the module list.
0456   size_t GetSize() const;
0457   bool IsEmpty() const { return !GetSize(); }
0458 
0459   bool LoadScriptingResourcesInTarget(Target *target, std::list<Status> &errors,
0460                                       Stream &feedback_stream,
0461                                       bool continue_on_error = true);
0462 
0463   static ModuleListProperties &GetGlobalModuleListProperties();
0464 
0465   static bool ModuleIsInCache(const Module *module_ptr);
0466 
0467   static Status
0468   GetSharedModule(const ModuleSpec &module_spec, lldb::ModuleSP &module_sp,
0469                   const FileSpecList *module_search_paths_ptr,
0470                   llvm::SmallVectorImpl<lldb::ModuleSP> *old_modules,
0471                   bool *did_create_ptr, bool always_create = false);
0472 
0473   static bool RemoveSharedModule(lldb::ModuleSP &module_sp);
0474 
0475   static void FindSharedModules(const ModuleSpec &module_spec,
0476                                 ModuleList &matching_module_list);
0477 
0478   static lldb::ModuleSP FindSharedModule(const UUID &uuid);
0479 
0480   static size_t RemoveOrphanSharedModules(bool mandatory);
0481 
0482   static bool RemoveSharedModuleIfOrphaned(const Module *module_ptr);
0483 
0484   /// Applies 'callback' to each module in this ModuleList.
0485   /// If 'callback' returns false, iteration terminates.
0486   /// The 'module_sp' passed to 'callback' is guaranteed to
0487   /// be non-null.
0488   ///
0489   /// This function is thread-safe.
0490   void ForEach(std::function<bool(const lldb::ModuleSP &module_sp)> const
0491                    &callback) const;
0492 
0493   /// Returns true if 'callback' returns true for one of the modules
0494   /// in this ModuleList.
0495   ///
0496   /// This function is thread-safe.
0497   bool AnyOf(
0498       std::function<bool(lldb_private::Module &module)> const &callback) const;
0499 
0500   /// Atomically swaps the contents of this module list with \a other.
0501   void Swap(ModuleList &other);
0502 
0503 protected:
0504   // Class typedefs.
0505   typedef std::vector<lldb::ModuleSP>
0506       collection; ///< The module collection type.
0507 
0508   void AppendImpl(const lldb::ModuleSP &module_sp, bool use_notifier = true);
0509 
0510   bool RemoveImpl(const lldb::ModuleSP &module_sp, bool use_notifier = true);
0511 
0512   collection::iterator RemoveImpl(collection::iterator pos,
0513                                   bool use_notifier = true);
0514 
0515   void ClearImpl(bool use_notifier = true);
0516 
0517   // Member variables.
0518   collection m_modules; ///< The collection of modules.
0519   mutable std::recursive_mutex m_modules_mutex;
0520 
0521   Notifier *m_notifier = nullptr;
0522 
0523 public:
0524   typedef LockingAdaptedIterable<collection, lldb::ModuleSP, vector_adapter,
0525                                  std::recursive_mutex>
0526       ModuleIterable;
0527   ModuleIterable Modules() const {
0528     return ModuleIterable(m_modules, GetMutex());
0529   }
0530 
0531   typedef AdaptedIterable<collection, lldb::ModuleSP, vector_adapter>
0532       ModuleIterableNoLocking;
0533   ModuleIterableNoLocking ModulesNoLocking() const {
0534     return ModuleIterableNoLocking(m_modules);
0535   }
0536 };
0537 
0538 } // namespace lldb_private
0539 
0540 #endif // LLDB_CORE_MODULELIST_H