1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127
|
//===-- LLDBMemoryReader.h --------------------------------------*- C++ -*-===//
//
// This source file is part of the Swift.org open source project
//
// Copyright (c) 2014 - 2020 Apple Inc. and the Swift project authors
// Licensed under Apache License v2.0 with Runtime Library Exception
//
// See https://swift.org/LICENSE.txt for license information
// See https://swift.org/CONTRIBUTORS.txt for the list of Swift project authors
//
//===----------------------------------------------------------------------===//
#ifndef liblldb_LLDBMemoryReader_h_
#define liblldb_LLDBMemoryReader_h_
#include "SwiftLanguageRuntime.h"
// We need to include ReflectionContext.h before TypeLowering.h to avoid
// conflicts between mach/machine.h and llvm/BinaryFormat/MachO.h.
#include "swift/RemoteInspection/ReflectionContext.h"
#include "swift/RemoteInspection/TypeLowering.h"
#include "llvm/ADT/SmallSet.h"
#include "llvm/Support/Memory.h"
namespace lldb_private {
class LLDBMemoryReader : public swift::remote::MemoryReader {
public:
LLDBMemoryReader(Process &p,
std::function<swift::remote::RemoteAbsolutePointer(
swift::remote::RemoteAbsolutePointer)>
stripper,
size_t max_read_amount = INT32_MAX)
: m_process(p), signedPointerStripper(stripper), m_range_module_map() {
m_max_read_amount = max_read_amount;
}
virtual ~LLDBMemoryReader() = default;
bool queryDataLayout(DataLayoutQueryType type, void *inBuffer,
void *outBuffer) override;
swift::remote::RemoteAddress
getSymbolAddress(const std::string &name) override;
std::optional<swift::remote::RemoteAbsolutePointer>
resolvePointerAsSymbol(swift::remote::RemoteAddress address) override;
swift::remote::RemoteAbsolutePointer
resolvePointer(swift::remote::RemoteAddress address,
uint64_t readValue) override;
bool readBytes(swift::remote::RemoteAddress address, uint8_t *dest,
uint64_t size) override;
bool readString(swift::remote::RemoteAddress address,
std::string &dest) override;
void pushLocalBuffer(uint64_t local_buffer, uint64_t local_buffer_size);
void popLocalBuffer();
/// Adds the module to the list of modules we're tracking using tagged
/// addresses, so we can read memory from the file cache whenever possible.
/// \return a pair of addresses indicating the start and end of this image in
/// the tagged address space. None on failure.
std::optional<std::pair<uint64_t, uint64_t>>
addModuleToAddressMap(lldb::ModuleSP module, bool register_symbol_obj_file);
/// Returns whether the filecache optimization is enabled or not.
bool readMetadataFromFileCacheEnabled() const;
private:
/// Gets the file address and module that were mapped to a given tagged
/// address.
std::optional<std::pair<uint64_t, lldb::ModuleSP>>
getFileAddressAndModuleForTaggedAddress(uint64_t tagged_address) const;
/// Resolves the address by either mapping a tagged address back to an LLDB
/// Address with section + offset, or, in case the address is not tagged,
/// constructing an LLDB address with just the offset.
/// \return an Address with Section + offset if we succesfully converted a
/// tagged address back, an Address with just an offset if the address was not
/// tagged, and None if the address was tagged but we couldn't convert it back
/// to an Address.
std::optional<Address> resolveRemoteAddress(uint64_t address) const;
/// Reads memory from the symbol rich binary from the address into dest.
/// \return true if it was able to successfully read memory.
std::optional<Address>
resolveRemoteAddressFromSymbolObjectFile(uint64_t address) const;
private:
Process &m_process;
size_t m_max_read_amount;
std::optional<uint64_t> m_local_buffer;
uint64_t m_local_buffer_size = 0;
std::function<swift::remote::RemoteAbsolutePointer(
swift::remote::RemoteAbsolutePointer)>
signedPointerStripper;
/// LLDBMemoryReader prefers to read reflection metadata from the
/// binary on disk, which is faster than reading it out of process
/// memory, especially when debugging remotely. To achieve this LLDB
/// registers virtual addresses starting at (0x0 &
/// LLDB_VIRTUAL_ADDRESS_BIT) with ReflectionContext. Sorted by
/// virtual address, m_lldb_virtual_address_map stores each
/// lldb::Module and the first virtual address after the end of that
/// module's virtual address space.
std::vector<std::pair<uint64_t, lldb::ModuleSP>> m_range_module_map;
/// The set of modules where we should read memory from the symbol file's
/// object file instead of the main object file.
llvm::SmallSet<lldb::ModuleSP, 8> m_modules_with_metadata_in_symbol_obj_file;
/// The bit used to tag LLDB's virtual addresses as such. See \c
/// m_range_module_map.
const static uint64_t LLDB_FILE_ADDRESS_BIT = 0x2000000000000000;
static_assert(LLDB_FILE_ADDRESS_BIT & SWIFT_ABI_X86_64_SWIFT_SPARE_BITS_MASK,
"LLDB file address bit not in spare bits mask!");
static_assert(LLDB_FILE_ADDRESS_BIT & SWIFT_ABI_ARM64_SWIFT_SPARE_BITS_MASK,
"LLDB file address bit not in spare bits mask!");
};
} // namespace lldb_private
#endif
|