sanitizer_procmaps.h revision 9ae2883d88dd28b9c5dc862107e6e6d12a35926e
1//===-- sanitizer_procmaps.h ------------------------------------*- C++ -*-===// 2// 3// The LLVM Compiler Infrastructure 4// 5// This file is distributed under the University of Illinois Open Source 6// License. See LICENSE.TXT for details. 7// 8//===----------------------------------------------------------------------===// 9// 10// This file is shared between AddressSanitizer and ThreadSanitizer. 11// 12// Information about the process mappings. 13//===----------------------------------------------------------------------===// 14#ifndef SANITIZER_PROCMAPS_H 15#define SANITIZER_PROCMAPS_H 16 17#include "sanitizer_internal_defs.h" 18#include "sanitizer_mutex.h" 19 20namespace __sanitizer { 21 22#if SANITIZER_WINDOWS 23class MemoryMappingLayout { 24 public: 25 MemoryMappingLayout() {} 26 bool GetObjectNameAndOffset(uptr addr, uptr *offset, 27 char filename[], uptr filename_size, 28 uptr *protection) { 29 UNIMPLEMENTED(); 30 } 31}; 32 33#else // _WIN32 34#if SANITIZER_LINUX 35struct ProcSelfMapsBuff { 36 char *data; 37 uptr mmaped_size; 38 uptr len; 39}; 40#endif // SANITIZER_LINUX 41 42class MemoryMappingLayout { 43 public: 44 explicit MemoryMappingLayout(bool cache_enabled); 45 bool Next(uptr *start, uptr *end, uptr *offset, 46 char filename[], uptr filename_size, uptr *protection); 47 void Reset(); 48 // Gets the object file name and the offset in that object for a given 49 // address 'addr'. Returns true on success. 50 bool GetObjectNameAndOffset(uptr addr, uptr *offset, 51 char filename[], uptr filename_size, 52 uptr *protection); 53 // In some cases, e.g. when running under a sandbox on Linux, ASan is unable 54 // to obtain the memory mappings. It should fall back to pre-cached data 55 // instead of aborting. 56 static void CacheMemoryMappings(); 57 ~MemoryMappingLayout(); 58 59 // Memory protection masks. 60 static const uptr kProtectionRead = 1; 61 static const uptr kProtectionWrite = 2; 62 static const uptr kProtectionExecute = 4; 63 static const uptr kProtectionShared = 8; 64 65 private: 66 void LoadFromCache(); 67 // Default implementation of GetObjectNameAndOffset. 68 // Quite slow, because it iterates through the whole process map for each 69 // lookup. 70 bool IterateForObjectNameAndOffset(uptr addr, uptr *offset, 71 char filename[], uptr filename_size, 72 uptr *protection) { 73 Reset(); 74 uptr start, end, file_offset; 75 for (int i = 0; Next(&start, &end, &file_offset, filename, filename_size, 76 protection); 77 i++) { 78 if (addr >= start && addr < end) { 79 // Don't subtract 'start' for the first entry: 80 // * If a binary is compiled w/o -pie, then the first entry in 81 // process maps is likely the binary itself (all dynamic libs 82 // are mapped higher in address space). For such a binary, 83 // instruction offset in binary coincides with the actual 84 // instruction address in virtual memory (as code section 85 // is mapped to a fixed memory range). 86 // * If a binary is compiled with -pie, all the modules are 87 // mapped high at address space (in particular, higher than 88 // shadow memory of the tool), so the module can't be the 89 // first entry. 90 *offset = (addr - (i ? start : 0)) + file_offset; 91 return true; 92 } 93 } 94 if (filename_size) 95 filename[0] = '\0'; 96 return false; 97 } 98 99# if defined __linux__ 100 ProcSelfMapsBuff proc_self_maps_; 101 char *current_; 102 103 // Static mappings cache. 104 static ProcSelfMapsBuff cached_proc_self_maps_; 105 static StaticSpinMutex cache_lock_; // protects cached_proc_self_maps_. 106# elif defined __APPLE__ 107 template<u32 kLCSegment, typename SegmentCommand> 108 bool NextSegmentLoad(uptr *start, uptr *end, uptr *offset, 109 char filename[], uptr filename_size, 110 uptr *protection); 111 int current_image_; 112 u32 current_magic_; 113 u32 current_filetype_; 114 int current_load_cmd_count_; 115 char *current_load_cmd_addr_; 116# endif 117}; 118 119#endif // _WIN32 120 121} // namespace __sanitizer 122 123#endif // SANITIZER_PROCMAPS_H 124