• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
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 <stddef.h>
20 
21 #include <memory>
22 #include <mutex>
23 #include <string>
24 #include <unordered_map>
25 #include <utility>
26 
27 #include <unwindstack/Arch.h>
28 #include <unwindstack/ElfInterface.h>
29 #include <unwindstack/Memory.h>
30 #include <unwindstack/SharedString.h>
31 
32 #if !defined(EM_AARCH64)
33 #define EM_AARCH64 183
34 #endif
35 
36 namespace unwindstack {
37 
38 // Forward declaration.
39 class MapInfo;
40 class Regs;
41 
42 class Elf {
43  public:
Elf(Memory * memory)44   Elf(Memory* memory) : memory_(memory) {}
45   virtual ~Elf() = default;
46 
47   bool Init();
48 
49   void InitGnuDebugdata();
50 
51   void Invalidate();
52 
53   std::string GetSoname();
54 
55   bool GetFunctionName(uint64_t addr, SharedString* name, uint64_t* func_offset);
56 
57   bool GetGlobalVariableOffset(const std::string& name, uint64_t* memory_offset);
58 
59   uint64_t GetRelPc(uint64_t pc, MapInfo* map_info);
60 
61   bool StepIfSignalHandler(uint64_t rel_pc, Regs* regs, Memory* process_memory);
62 
63   bool Step(uint64_t rel_pc, Regs* regs, Memory* process_memory, bool* finished,
64             bool* is_signal_frame);
65 
66   ElfInterface* CreateInterfaceFromMemory(Memory* memory);
67 
68   std::string GetBuildID();
69 
70   std::string GetPrintableBuildID();
71 
GetLoadBias()72   int64_t GetLoadBias() { return load_bias_; }
73 
74   bool IsValidPc(uint64_t pc);
75 
76   bool GetTextRange(uint64_t* addr, uint64_t* size);
77 
78   void GetLastError(ErrorData* data);
79   ErrorCode GetLastErrorCode();
80   uint64_t GetLastErrorAddress();
81 
valid()82   bool valid() { return valid_; }
83 
machine_type()84   uint32_t machine_type() { return machine_type_; }
85 
class_type()86   uint8_t class_type() { return class_type_; }
87 
arch()88   ArchEnum arch() { return arch_; }
89 
memory()90   Memory* memory() { return memory_.get(); }
91 
interface()92   ElfInterface* interface() { return interface_.get(); }
93 
gnu_debugdata_interface()94   ElfInterface* gnu_debugdata_interface() { return gnu_debugdata_interface_.get(); }
95 
96   static bool IsValidElf(Memory* memory);
97 
98   static bool GetInfo(Memory* memory, uint64_t* size);
99 
100   static int64_t GetLoadBias(Memory* memory);
101 
102   static std::string GetBuildID(Memory* memory);
103 
104   // Caching cannot be enabled/disabled while unwinding. It is assumed
105   // that once enabled, it remains enabled while all unwinds are running.
106   // If the state of the caching changes while unwinding is occurring,
107   // it could cause crashes.
108   static void SetCachingEnabled(bool enable);
109 
CachingEnabled()110   static bool CachingEnabled() { return cache_enabled_; }
111 
112   static void CacheLock();
113   static void CacheUnlock();
114   static void CacheAdd(MapInfo* info);
115   static bool CacheGet(MapInfo* info);
116 
117   static std::string GetPrintableBuildID(std::string& build_id);
118 
119  protected:
120   bool valid_ = false;
121   int64_t load_bias_ = 0;
122   std::unique_ptr<ElfInterface> interface_;
123   std::unique_ptr<Memory> memory_;
124   uint32_t machine_type_;
125   uint8_t class_type_;
126   ArchEnum arch_;
127   // Protect calls that can modify internal state of the interface object.
128   std::mutex lock_;
129 
130   std::unique_ptr<Memory> gnu_debugdata_memory_;
131   std::unique_ptr<ElfInterface> gnu_debugdata_interface_;
132 
133   static bool cache_enabled_;
134   static std::unordered_map<std::string, std::unordered_map<uint64_t, std::shared_ptr<Elf>>>*
135       cache_;
136   static std::mutex* cache_lock_;
137 };
138 
139 }  // namespace unwindstack
140