1 /* 2 * Copyright (C) 2016 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 #pragma once 18 19 #include <stdint.h> 20 #include <unistd.h> 21 22 #include <functional> 23 #include <string> 24 #include <vector> 25 26 #include <unwindstack/Arch.h> 27 #include <unwindstack/Error.h> 28 29 namespace unwindstack { 30 31 // Forward declarations. 32 class Elf; 33 class Memory; 34 35 class Regs { 36 public: 37 enum LocationEnum : uint8_t { 38 LOCATION_UNKNOWN = 0, 39 LOCATION_REGISTER, 40 LOCATION_SP_OFFSET, 41 }; 42 43 struct Location { LocationLocation44 Location(LocationEnum type, int16_t value) : type(type), value(value) {} 45 46 LocationEnum type; 47 int16_t value; 48 }; 49 Regs(uint16_t total_regs,const Location & return_loc)50 Regs(uint16_t total_regs, const Location& return_loc) 51 : total_regs_(total_regs), return_loc_(return_loc) {} 52 virtual ~Regs() = default; 53 54 virtual ArchEnum Arch() = 0; 55 Is32Bit()56 bool Is32Bit() { return ArchIs32Bit(Arch()); } 57 58 virtual void* RawData() = 0; 59 virtual uint64_t pc() = 0; 60 virtual uint64_t sp() = 0; 61 62 virtual void set_pc(uint64_t pc) = 0; 63 virtual void set_sp(uint64_t sp) = 0; 64 dex_pc()65 uint64_t dex_pc() { return dex_pc_; } set_dex_pc(uint64_t dex_pc)66 void set_dex_pc(uint64_t dex_pc) { dex_pc_ = dex_pc; } 67 fallback_pc()68 virtual void fallback_pc() {} 69 ResetPseudoRegisters()70 virtual void ResetPseudoRegisters() {} SetPseudoRegister(uint16_t,uint64_t)71 virtual bool SetPseudoRegister(uint16_t, uint64_t) { return false; } GetPseudoRegister(uint16_t,uint64_t *)72 virtual bool GetPseudoRegister(uint16_t, uint64_t*) { return false; } 73 74 virtual bool StepIfSignalHandler(uint64_t elf_offset, Elf* elf, Memory* process_memory) = 0; 75 76 virtual bool SetPcFromReturnAddress(Memory* process_memory) = 0; 77 78 virtual void IterateRegisters(std::function<void(const char*, uint64_t)>) = 0; 79 total_regs()80 uint16_t total_regs() { return total_regs_; } 81 82 virtual Regs* Clone() = 0; 83 Convert(uint16_t reg)84 virtual uint16_t Convert(uint16_t reg) { return reg; } 85 86 static ArchEnum CurrentArch(); 87 static ArchEnum RemoteGetArch(pid_t pid, ErrorCode* error_code = nullptr); 88 static Regs* RemoteGet(pid_t pid, ErrorCode* error_code = nullptr); 89 static Regs* CreateFromUcontext(ArchEnum arch, void* ucontext); 90 static Regs* CreateFromLocal(); 91 92 protected: 93 uint16_t total_regs_; 94 Location return_loc_; 95 uint64_t dex_pc_ = 0; 96 }; 97 98 template <typename AddressType> 99 class RegsImpl : public Regs { 100 public: RegsImpl(uint16_t total_regs,Location return_loc)101 RegsImpl(uint16_t total_regs, Location return_loc) 102 : Regs(total_regs, return_loc), regs_(total_regs) {} 103 virtual ~RegsImpl() = default; 104 105 inline AddressType& operator[](size_t reg) { return regs_[reg]; } 106 RawData()107 void* RawData() override { return regs_.data(); } 108 IterateRegisters(std::function<void (const char *,uint64_t)> fn)109 virtual void IterateRegisters(std::function<void(const char*, uint64_t)> fn) override { 110 for (size_t i = 0; i < regs_.size(); ++i) { 111 fn(std::to_string(i).c_str(), regs_[i]); 112 } 113 } 114 115 protected: 116 std::vector<AddressType> regs_; 117 }; 118 119 uint64_t GetPcAdjustment(uint64_t rel_pc, Elf* elf, ArchEnum arch); 120 121 } // namespace unwindstack 122