brintos

brintos / llvm-project-archived public Read only

0
0
Text · 5.7 KiB · 1a01712 Raw
157 lines · c
1//===-- NativeProcessTestUtils.cpp ------------------------------*- 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-exception6//7//===----------------------------------------------------------------------===//8 9#ifndef LLDB_UNITTESTS_TESTINGSUPPORT_HOST_NATIVEPROCESSTESTUTILS_H10#define LLDB_UNITTESTS_TESTINGSUPPORT_HOST_NATIVEPROCESSTESTUTILS_H11 12#include "lldb/Host/common/NativeProcessProtocol.h"13#include "llvm/Testing/Support/Error.h"14#include "gmock/gmock.h"15 16using namespace lldb_private;17using namespace lldb;18using namespace testing;19 20namespace lldb_private {21 22class MockDelegate : public NativeProcessProtocol::NativeDelegate {23public:24  MOCK_METHOD1(InitializeDelegate, void(NativeProcessProtocol *Process));25  MOCK_METHOD2(ProcessStateChanged,26               void(NativeProcessProtocol *Process, StateType State));27  MOCK_METHOD1(DidExec, void(NativeProcessProtocol *Process));28  MOCK_METHOD2(NewSubprocessImpl,29               void(NativeProcessProtocol *parent_process,30                    std::unique_ptr<NativeProcessProtocol> &child_process));31  // This is a hack to avoid MOCK_METHOD2 incompatibility with std::unique_ptr32  // passed as value.33  void NewSubprocess(NativeProcessProtocol *parent_process,34                     std::unique_ptr<NativeProcessProtocol> child_process) {35    NewSubprocessImpl(parent_process, child_process);36  }37};38 39// NB: This class doesn't use the override keyword to avoid40// -Winconsistent-missing-override warnings from the compiler. The41// inconsistency comes from the overriding definitions in the MOCK_*** macros.42template <typename T> class MockProcess : public T {43public:44  MockProcess(NativeProcessProtocol::NativeDelegate &Delegate,45              const ArchSpec &Arch, lldb::pid_t Pid = 1)46      : T(Pid, -1, Delegate), Arch(Arch) {}47 48  MOCK_METHOD1(Resume, Status(const ResumeActionList &ResumeActions));49  MOCK_METHOD0(Halt, Status());50  MOCK_METHOD0(Detach, Status());51  MOCK_METHOD1(Signal, Status(int Signo));52  MOCK_METHOD0(Kill, Status());53  MOCK_METHOD0(GetSharedLibraryInfoAddress, addr_t());54  MOCK_METHOD0(UpdateThreads, size_t());55  MOCK_CONST_METHOD0(GetAuxvData,56                     llvm::ErrorOr<std::unique_ptr<llvm::MemoryBuffer>>());57  MOCK_METHOD2(GetLoadedModuleFileSpec,58               Status(const char *ModulePath, FileSpec &Spec));59  MOCK_METHOD2(GetFileLoadAddress,60               Status(const llvm::StringRef &FileName, addr_t &Addr));61 62  const ArchSpec &GetArchitecture() const /*override*/ { return Arch; }63  Status SetBreakpoint(lldb::addr_t Addr, uint32_t Size,64                       bool Hardware) /*override*/ {65    if (Hardware)66      return this->SetHardwareBreakpoint(Addr, Size);67    else68      return this->SetSoftwareBreakpoint(Addr, Size);69  }70 71  // Redirect base class Read/Write Memory methods to functions whose signatures72  // are more mock-friendly.73  Status ReadMemory(addr_t Addr, void *Buf, size_t Size,74                    size_t &BytesRead) /*override*/ {75    auto ExpectedMemory = this->ReadMemory(Addr, Size);76    if (!ExpectedMemory) {77      BytesRead = 0;78      return Status::FromError(ExpectedMemory.takeError());79    }80    BytesRead = ExpectedMemory->size();81    assert(BytesRead <= Size);82    std::memcpy(Buf, ExpectedMemory->data(), BytesRead);83    return Status();84  }85 86  Status WriteMemory(addr_t Addr, const void *Buf, size_t Size,87                     size_t &BytesWritten) /*override*/ {88    auto ExpectedBytes = this->WriteMemory(89        Addr, llvm::ArrayRef(static_cast<const uint8_t *>(Buf), Size));90    if (!ExpectedBytes) {91      BytesWritten = 0;92      return Status::FromError(ExpectedBytes.takeError());93    }94    BytesWritten = *ExpectedBytes;95    return Status();96  }97 98  MOCK_METHOD2(ReadMemory,99               llvm::Expected<std::vector<uint8_t>>(addr_t Addr, size_t Size));100  MOCK_METHOD2(WriteMemory,101               llvm::Expected<size_t>(addr_t Addr,102                                      llvm::ArrayRef<uint8_t> Data));103 104  using T::GetSoftwareBreakpointTrapOpcode;105  llvm::Expected<std::vector<uint8_t>> ReadMemoryWithoutTrap(addr_t Addr,106                                                             size_t Size) {107    std::vector<uint8_t> Data(Size, 0);108    size_t BytesRead;109    Status ST =110        T::ReadMemoryWithoutTrap(Addr, Data.data(), Data.size(), BytesRead);111    if (ST.Fail())112      return ST.ToError();113    Data.resize(BytesRead);114    return std::move(Data);115  }116 117private:118  ArchSpec Arch;119};120 121class FakeMemory {122public:123  FakeMemory(llvm::ArrayRef<uint8_t> Data, addr_t start_addr = 0)124      : Data(Data), m_start_addr(start_addr) {}125 126  FakeMemory(const void *Data, size_t data_size, addr_t start_addr = 0)127      : Data((const uint8_t *)Data, ((const uint8_t *)Data) + data_size),128        m_start_addr(start_addr) {}129 130  llvm::Expected<std::vector<uint8_t>> Read(addr_t Addr, size_t Size) {131    Addr -= m_start_addr;132    if (Addr >= Data.size())133      return llvm::createStringError(llvm::inconvertibleErrorCode(),134                                     "Address out of range.");135    Size = std::min(Size, Data.size() - (size_t)Addr);136    auto Begin = std::next(Data.begin(), Addr);137    return std::vector<uint8_t>(Begin, std::next(Begin, Size));138  }139 140  llvm::Expected<size_t> Write(addr_t Addr, llvm::ArrayRef<uint8_t> Chunk) {141    Addr -= m_start_addr;142    if (Addr >= Data.size())143      return llvm::createStringError(llvm::inconvertibleErrorCode(),144                                     "Address out of range.");145    size_t Size = std::min(Chunk.size(), Data.size() - (size_t)Addr);146    std::copy_n(Chunk.begin(), Size, &Data[Addr]);147    return Size;148  }149 150private:151  std::vector<uint8_t> Data;152  addr_t m_start_addr;153};154} // namespace lldb_private155 156#endif157