1 /* 2 * Copyright (C) 2011 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 #ifndef ART_RUNTIME_OAT_FILE_H_ 18 #define ART_RUNTIME_OAT_FILE_H_ 19 20 #include <list> 21 #include <string> 22 #include <vector> 23 24 #include "base/array_ref.h" 25 #include "base/mutex.h" 26 #include "base/stringpiece.h" 27 #include "compiler_filter.h" 28 #include "dex_file.h" 29 #include "dex_file_layout.h" 30 #include "method_bss_mapping.h" 31 #include "mirror/class.h" 32 #include "oat.h" 33 #include "os.h" 34 #include "type_lookup_table.h" 35 #include "utf.h" 36 #include "utils.h" 37 38 namespace art { 39 40 class BitVector; 41 class ElfFile; 42 class DexLayoutSections; 43 template <class MirrorType> class GcRoot; 44 class MemMap; 45 class OatDexFile; 46 class OatHeader; 47 class OatMethodOffsets; 48 class OatQuickMethodHeader; 49 class VdexFile; 50 51 namespace gc { 52 namespace collector { 53 class DummyOatFile; 54 } // namespace collector 55 } // namespace gc 56 57 // Runtime representation of the OAT file format which holds compiler output. 58 // The class opens an OAT file from storage and maps it to memory, typically with 59 // dlopen and provides access to its internal data structures (see OatWriter for 60 // for more details about the OAT format). 61 // In the process of loading OAT, the class also loads the associated VDEX file 62 // with the input DEX files (see VdexFile for details about the VDEX format). 63 // The raw DEX data are accessible transparently through the OatDexFile objects. 64 65 class OatFile { 66 public: 67 // Special classpath that skips shared library check. 68 static constexpr const char* kSpecialSharedLibrary = "&"; 69 70 typedef art::OatDexFile OatDexFile; 71 72 // Opens an oat file contained within the given elf file. This is always opened as 73 // non-executable at the moment. 74 static OatFile* OpenWithElfFile(ElfFile* elf_file, 75 VdexFile* vdex_file, 76 const std::string& location, 77 const char* abs_dex_location, 78 std::string* error_msg); 79 // Open an oat file. Returns null on failure. Requested base can 80 // optionally be used to request where the file should be loaded. 81 // See the ResolveRelativeEncodedDexLocation for a description of how the 82 // abs_dex_location argument is used. 83 static OatFile* Open(const std::string& filename, 84 const std::string& location, 85 uint8_t* requested_base, 86 uint8_t* oat_file_begin, 87 bool executable, 88 bool low_4gb, 89 const char* abs_dex_location, 90 std::string* error_msg); 91 92 // Open an oat file from an already opened File. 93 // Does not use dlopen underneath so cannot be used for runtime use 94 // where relocations may be required. Currently used from 95 // ImageWriter which wants to open a writable version from an existing 96 // file descriptor for patching. 97 static OatFile* OpenWritable(File* file, const std::string& location, 98 const char* abs_dex_location, 99 std::string* error_msg); 100 // Opens an oat file from an already opened File. Maps it PROT_READ, MAP_PRIVATE. 101 static OatFile* OpenReadable(File* file, const std::string& location, 102 const char* abs_dex_location, 103 std::string* error_msg); 104 105 virtual ~OatFile(); 106 IsExecutable()107 bool IsExecutable() const { 108 return is_executable_; 109 } 110 111 bool IsPic() const; 112 113 // Indicates whether the oat file was compiled with full debugging capability. 114 bool IsDebuggable() const; 115 116 CompilerFilter::Filter GetCompilerFilter() const; 117 118 std::string GetClassLoaderContext() const; 119 GetLocation()120 const std::string& GetLocation() const { 121 return location_; 122 } 123 124 const OatHeader& GetOatHeader() const; 125 126 class OatMethod FINAL { 127 public: 128 void LinkMethod(ArtMethod* method) const; 129 130 uint32_t GetCodeOffset() const; 131 132 const void* GetQuickCode() const; 133 134 // Returns size of quick code. 135 uint32_t GetQuickCodeSize() const; 136 uint32_t GetQuickCodeSizeOffset() const; 137 138 // Returns OatQuickMethodHeader for debugging. Most callers should 139 // use more specific methods such as GetQuickCodeSize. 140 const OatQuickMethodHeader* GetOatQuickMethodHeader() const; 141 uint32_t GetOatQuickMethodHeaderOffset() const; 142 143 size_t GetFrameSizeInBytes() const; 144 uint32_t GetCoreSpillMask() const; 145 uint32_t GetFpSpillMask() const; 146 147 const uint8_t* GetVmapTable() const; 148 uint32_t GetVmapTableOffset() const; 149 uint32_t GetVmapTableOffsetOffset() const; 150 151 // Create an OatMethod with offsets relative to the given base address OatMethod(const uint8_t * base,const uint32_t code_offset)152 OatMethod(const uint8_t* base, const uint32_t code_offset) 153 : begin_(base), code_offset_(code_offset) { 154 } 155 OatMethod(const OatMethod&) = default; ~OatMethod()156 ~OatMethod() {} 157 158 OatMethod& operator=(const OatMethod&) = default; 159 160 // A representation of an invalid OatMethod, used when an OatMethod or OatClass can't be found. 161 // See ClassLinker::FindOatMethodFor. Invalid()162 static const OatMethod Invalid() { 163 return OatMethod(nullptr, -1); 164 } 165 166 private: 167 template<class T> GetOatPointer(uint32_t offset)168 T GetOatPointer(uint32_t offset) const { 169 if (offset == 0) { 170 return nullptr; 171 } 172 return reinterpret_cast<T>(begin_ + offset); 173 } 174 175 const uint8_t* begin_; 176 uint32_t code_offset_; 177 178 friend class OatClass; 179 }; 180 181 class OatClass FINAL { 182 public: GetStatus()183 mirror::Class::Status GetStatus() const { 184 return status_; 185 } 186 GetType()187 OatClassType GetType() const { 188 return type_; 189 } 190 191 // Get the OatMethod entry based on its index into the class 192 // defintion. Direct methods come first, followed by virtual 193 // methods. Note that runtime created methods such as miranda 194 // methods are not included. 195 const OatMethod GetOatMethod(uint32_t method_index) const; 196 197 // Return a pointer to the OatMethodOffsets for the requested 198 // method_index, or null if none is present. Note that most 199 // callers should use GetOatMethod. 200 const OatMethodOffsets* GetOatMethodOffsets(uint32_t method_index) const; 201 202 // Return the offset from the start of the OatFile to the 203 // OatMethodOffsets for the requested method_index, or 0 if none 204 // is present. Note that most callers should use GetOatMethod. 205 uint32_t GetOatMethodOffsetsOffset(uint32_t method_index) const; 206 207 // A representation of an invalid OatClass, used when an OatClass can't be found. 208 // See FindOatClass(). Invalid()209 static OatClass Invalid() { 210 return OatClass(/* oat_file */ nullptr, 211 mirror::Class::kStatusErrorUnresolved, 212 kOatClassNoneCompiled, 213 /* bitmap_size */ 0, 214 /* bitmap_pointer */ nullptr, 215 /* methods_pointer */ nullptr); 216 } 217 218 private: 219 OatClass(const OatFile* oat_file, 220 mirror::Class::Status status, 221 OatClassType type, 222 uint32_t bitmap_size, 223 const uint32_t* bitmap_pointer, 224 const OatMethodOffsets* methods_pointer); 225 226 const OatFile* const oat_file_; 227 228 const mirror::Class::Status status_; 229 230 const OatClassType type_; 231 232 const uint32_t* const bitmap_; 233 234 const OatMethodOffsets* const methods_pointer_; 235 236 friend class art::OatDexFile; 237 }; 238 239 // Get the OatDexFile for the given dex_location within this oat file. 240 // If dex_location_checksum is non-null, the OatDexFile will only be 241 // returned if it has a matching checksum. 242 // If error_msg is non-null and no OatDexFile is returned, error_msg will 243 // be updated with a description of why no OatDexFile was returned. 244 const OatDexFile* GetOatDexFile(const char* dex_location, 245 const uint32_t* const dex_location_checksum, 246 /*out*/std::string* error_msg = nullptr) const 247 REQUIRES(!secondary_lookup_lock_); 248 GetOatDexFiles()249 const std::vector<const OatDexFile*>& GetOatDexFiles() const { 250 return oat_dex_files_storage_; 251 } 252 Size()253 size_t Size() const { 254 return End() - Begin(); 255 } 256 Contains(const void * p)257 bool Contains(const void* p) const { 258 return p >= Begin() && p < End(); 259 } 260 BssSize()261 size_t BssSize() const { 262 return BssEnd() - BssBegin(); 263 } 264 BssMethodsOffset()265 size_t BssMethodsOffset() const { 266 // Note: This is used only for symbolizer and needs to return a valid .bss offset. 267 return (bss_methods_ != nullptr) ? bss_methods_ - BssBegin() : BssRootsOffset(); 268 } 269 BssRootsOffset()270 size_t BssRootsOffset() const { 271 // Note: This is used only for symbolizer and needs to return a valid .bss offset. 272 return (bss_roots_ != nullptr) ? bss_roots_ - BssBegin() : BssSize(); 273 } 274 DexSize()275 size_t DexSize() const { 276 return DexEnd() - DexBegin(); 277 } 278 279 const uint8_t* Begin() const; 280 const uint8_t* End() const; 281 282 const uint8_t* BssBegin() const; 283 const uint8_t* BssEnd() const; 284 285 const uint8_t* DexBegin() const; 286 const uint8_t* DexEnd() const; 287 288 ArrayRef<ArtMethod*> GetBssMethods() const; 289 ArrayRef<GcRoot<mirror::Object>> GetBssGcRoots() const; 290 291 // Returns the absolute dex location for the encoded relative dex location. 292 // 293 // If not null, abs_dex_location is used to resolve the absolute dex 294 // location of relative dex locations encoded in the oat file. 295 // For example, given absolute location "/data/app/foo/base.apk", encoded 296 // dex locations "base.apk", "base.apk!classes2.dex", etc. would be resolved 297 // to "/data/app/foo/base.apk", "/data/app/foo/base.apk!classes2.dex", etc. 298 // Relative encoded dex locations that don't match the given abs_dex_location 299 // are left unchanged. 300 static std::string ResolveRelativeEncodedDexLocation( 301 const char* abs_dex_location, const std::string& rel_dex_location); 302 303 // Finds the associated oat class for a dex_file and descriptor. Returns an invalid OatClass on 304 // error and sets found to false. 305 static OatClass FindOatClass(const DexFile& dex_file, uint16_t class_def_idx, bool* found); 306 GetVdexFile()307 VdexFile* GetVdexFile() const { 308 return vdex_.get(); 309 } 310 311 protected: 312 OatFile(const std::string& filename, bool executable); 313 314 private: 315 // The oat file name. 316 // 317 // The image will embed this to link its associated oat file. 318 const std::string location_; 319 320 // Pointer to the Vdex file with the Dex files for this Oat file. 321 std::unique_ptr<VdexFile> vdex_; 322 323 // Pointer to OatHeader. 324 const uint8_t* begin_; 325 326 // Pointer to end of oat region for bounds checking. 327 const uint8_t* end_; 328 329 // Pointer to the .bss section, if present, otherwise null. 330 uint8_t* bss_begin_; 331 332 // Pointer to the end of the .bss section, if present, otherwise null. 333 uint8_t* bss_end_; 334 335 // Pointer to the beginning of the ArtMethod*s in .bss section, if present, otherwise null. 336 uint8_t* bss_methods_; 337 338 // Pointer to the beginning of the GC roots in .bss section, if present, otherwise null. 339 uint8_t* bss_roots_; 340 341 // Was this oat_file loaded executable? 342 const bool is_executable_; 343 344 // Owning storage for the OatDexFile objects. 345 std::vector<const OatDexFile*> oat_dex_files_storage_; 346 347 // NOTE: We use a StringPiece as the key type to avoid a memory allocation on every 348 // lookup with a const char* key. The StringPiece doesn't own its backing storage, 349 // therefore we're using the OatDexFile::dex_file_location_ as the backing storage 350 // for keys in oat_dex_files_ and the string_cache_ entries for the backing storage 351 // of keys in secondary_oat_dex_files_ and oat_dex_files_by_canonical_location_. 352 typedef AllocationTrackingSafeMap<StringPiece, const OatDexFile*, kAllocatorTagOatFile> Table; 353 354 // Map each location and canonical location (if different) retrieved from the 355 // oat file to its OatDexFile. This map doesn't change after it's constructed in Setup() 356 // and therefore doesn't need any locking and provides the cheapest dex file lookup 357 // for GetOatDexFile() for a very frequent use case. Never contains a null value. 358 Table oat_dex_files_; 359 360 // Lock guarding all members needed for secondary lookup in GetOatDexFile(). 361 mutable Mutex secondary_lookup_lock_ DEFAULT_MUTEX_ACQUIRED_AFTER; 362 363 // If the primary oat_dex_files_ lookup fails, use a secondary map. This map stores 364 // the results of all previous secondary lookups, whether successful (non-null) or 365 // failed (null). If it doesn't contain an entry we need to calculate the canonical 366 // location and use oat_dex_files_by_canonical_location_. 367 mutable Table secondary_oat_dex_files_ GUARDED_BY(secondary_lookup_lock_); 368 369 // Cache of strings. Contains the backing storage for keys in the secondary_oat_dex_files_ 370 // and the lazily initialized oat_dex_files_by_canonical_location_. 371 // NOTE: We're keeping references to contained strings in form of StringPiece and adding 372 // new strings to the end. The adding of a new element must not touch any previously stored 373 // elements. std::list<> and std::deque<> satisfy this requirement, std::vector<> doesn't. 374 mutable std::list<std::string> string_cache_ GUARDED_BY(secondary_lookup_lock_); 375 376 friend class gc::collector::DummyOatFile; // For modifying begin_ and end_. 377 friend class OatClass; 378 friend class art::OatDexFile; 379 friend class OatDumper; // For GetBase and GetLimit 380 friend class OatFileBase; 381 DISALLOW_COPY_AND_ASSIGN(OatFile); 382 }; 383 384 // OatDexFile should be an inner class of OatFile. Unfortunately, C++ doesn't 385 // support forward declarations of inner classes, and we want to 386 // forward-declare OatDexFile so that we can store an opaque pointer to an 387 // OatDexFile in DexFile. 388 class OatDexFile FINAL { 389 public: 390 // Opens the DexFile referred to by this OatDexFile from within the containing OatFile. 391 std::unique_ptr<const DexFile> OpenDexFile(std::string* error_msg) const; 392 393 // May return null if the OatDexFile only contains a type lookup table. This case only happens 394 // for the compiler to speed up compilation. GetOatFile()395 const OatFile* GetOatFile() const { 396 // Avoid pulling in runtime.h in the header file. 397 if (kIsDebugBuild && oat_file_ == nullptr) { 398 AssertAotCompiler(); 399 } 400 return oat_file_; 401 } 402 403 // Returns the size of the DexFile refered to by this OatDexFile. 404 size_t FileSize() const; 405 406 // Returns original path of DexFile that was the source of this OatDexFile. GetDexFileLocation()407 const std::string& GetDexFileLocation() const { 408 return dex_file_location_; 409 } 410 411 // Returns the canonical location of DexFile that was the source of this OatDexFile. GetCanonicalDexFileLocation()412 const std::string& GetCanonicalDexFileLocation() const { 413 return canonical_dex_file_location_; 414 } 415 416 // Returns checksum of original DexFile that was the source of this OatDexFile; GetDexFileLocationChecksum()417 uint32_t GetDexFileLocationChecksum() const { 418 return dex_file_location_checksum_; 419 } 420 421 // Returns the OatClass for the class specified by the given DexFile class_def_index. 422 OatFile::OatClass GetOatClass(uint16_t class_def_index) const; 423 424 // Returns the offset to the OatClass information. Most callers should use GetOatClass. 425 uint32_t GetOatClassOffset(uint16_t class_def_index) const; 426 GetDexCacheArrays()427 uint8_t* GetDexCacheArrays() const { 428 return dex_cache_arrays_; 429 } 430 GetLookupTableData()431 const uint8_t* GetLookupTableData() const { 432 return lookup_table_data_; 433 } 434 GetMethodBssMapping()435 const MethodBssMapping* GetMethodBssMapping() const { 436 return method_bss_mapping_; 437 } 438 GetDexFilePointer()439 const uint8_t* GetDexFilePointer() const { 440 return dex_file_pointer_; 441 } 442 443 // Looks up a class definition by its class descriptor. Hash must be 444 // ComputeModifiedUtf8Hash(descriptor). 445 static const DexFile::ClassDef* FindClassDef(const DexFile& dex_file, 446 const char* descriptor, 447 size_t hash); 448 449 // Madvise the dex file based on the state we are moving to. 450 static void MadviseDexFile(const DexFile& dex_file, MadviseState state); 451 GetTypeLookupTable()452 TypeLookupTable* GetTypeLookupTable() const { 453 return lookup_table_.get(); 454 } 455 456 ~OatDexFile(); 457 458 // Create only with a type lookup table, used by the compiler to speed up compilation. 459 explicit OatDexFile(std::unique_ptr<TypeLookupTable>&& lookup_table); 460 461 // Return the dex layout sections. GetDexLayoutSections()462 const DexLayoutSections* GetDexLayoutSections() const { 463 return dex_layout_sections_; 464 } 465 466 private: 467 OatDexFile(const OatFile* oat_file, 468 const std::string& dex_file_location, 469 const std::string& canonical_dex_file_location, 470 uint32_t dex_file_checksum, 471 const uint8_t* dex_file_pointer, 472 const uint8_t* lookup_table_data, 473 const MethodBssMapping* method_bss_mapping, 474 const uint32_t* oat_class_offsets_pointer, 475 uint8_t* dex_cache_arrays, 476 const DexLayoutSections* dex_layout_sections); 477 478 static void AssertAotCompiler(); 479 480 const OatFile* const oat_file_ = nullptr; 481 const std::string dex_file_location_; 482 const std::string canonical_dex_file_location_; 483 const uint32_t dex_file_location_checksum_ = 0u; 484 const uint8_t* const dex_file_pointer_ = nullptr; 485 const uint8_t* const lookup_table_data_ = nullptr; 486 const MethodBssMapping* const method_bss_mapping_ = nullptr; 487 const uint32_t* const oat_class_offsets_pointer_ = 0u; 488 uint8_t* const dex_cache_arrays_ = nullptr; 489 mutable std::unique_ptr<TypeLookupTable> lookup_table_; 490 const DexLayoutSections* const dex_layout_sections_ = nullptr; 491 492 friend class OatFile; 493 friend class OatFileBase; 494 DISALLOW_COPY_AND_ASSIGN(OatDexFile); 495 }; 496 497 } // namespace art 498 499 #endif // ART_RUNTIME_OAT_FILE_H_ 500