1//===-- MemoryTagMap.h ------------------------------------------*- C++ -*-===// 2// 3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4// See https://llvm.org/LICENSE.txt for license information. 5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6// 7//===----------------------------------------------------------------------===// 8 9#ifndef LLDB_TARGET_MEMORYTAGMAP_H 10#define LLDB_TARGET_MEMORYTAGMAP_H 11 12#include "lldb/Target/MemoryTagManager.h" 13#include "lldb/lldb-private.h" 14#include <map> 15#include <optional> 16 17namespace lldb_private { 18 19/// MemoryTagMap provides a way to give a sparse read result 20/// when reading memory tags for a range. This is useful when 21/// you want to annotate some large memory dump that might include 22/// tagged memory but you don't know that it is all tagged. 23class MemoryTagMap { 24public: 25 /// Init an empty tag map 26 /// 27 /// \param [in] manager 28 /// Non-null pointer to a memory tag manager. 29 MemoryTagMap(const MemoryTagManager *manager); 30 31 /// Insert tags into the map starting from addr. 32 /// 33 /// \param [in] addr 34 /// Start address of the range to insert tags for. 35 /// This address should be granule aligned and have had 36 /// any non address bits removed. 37 /// (ideally you would use the base of the range you used 38 /// to read the tags in the first place) 39 /// 40 /// \param [in] tags 41 /// Vector of tags to insert. The first tag will be inserted 42 /// at addr, the next at addr+granule size and so on until 43 /// all tags have been inserted. 44 void InsertTags(lldb::addr_t addr, const std::vector<lldb::addr_t> tags); 45 46 bool Empty() const; 47 48 /// Lookup memory tags for a range of memory from addr to addr+len. 49 /// 50 /// \param [in] addr 51 /// The start of the range. This may include non address bits and 52 /// does not have to be granule aligned. 53 /// 54 /// \param [in] len 55 /// The length in bytes of the range to read tags for. This does 56 /// not need to be multiple of the granule size. 57 /// 58 /// \return 59 /// A vector containing the tags found for the granules in the 60 /// range. (which is the result of granule aligning the given range) 61 /// 62 /// Each item in the vector is an optional tag. Meaning that if 63 /// it is valid then the granule had a tag and if not, it didn't. 64 /// 65 /// If the range had no tags at all, the vector will be empty. 66 /// If some of the range was tagged it will have items and some 67 /// of them may be std::nullopt. 68 /// (this saves the caller checking whether all items are std::nullopt) 69 std::vector<std::optional<lldb::addr_t>> GetTags(lldb::addr_t addr, 70 size_t len) const; 71 72private: 73 /// Lookup the tag for address 74 /// 75 /// \param [in] address 76 /// The address to lookup a tag for. This should be aligned 77 /// to a granule boundary. 78 /// 79 /// \return 80 /// The tag for the granule that address refers to, or std::nullopt 81 /// if it has no memory tag. 82 std::optional<lldb::addr_t> GetTag(lldb::addr_t addr) const; 83 84 // A map of granule aligned addresses to their memory tag 85 std::map<lldb::addr_t, lldb::addr_t> m_addr_to_tag; 86 87 // Memory tag manager used to align addresses and get granule size. 88 // Ideally this would be a const& but only certain architectures will 89 // have a memory tag manager class to provide here. So for a method 90 // returning a MemoryTagMap, std::optional<MemoryTagMap> allows it to handle 91 // architectures without memory tagging. Optionals cannot hold references 92 // so we go with a pointer that we assume will be not be null. 93 const MemoryTagManager *m_manager; 94}; 95 96} // namespace lldb_private 97 98#endif // LLDB_TARGET_MEMORYTAGMAP_H 99