• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
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_IMAGE_H_
18 #define ART_RUNTIME_IMAGE_H_
19 
20 #include <string.h>
21 
22 #include "globals.h"
23 #include "mirror/object.h"
24 
25 namespace art {
26 
27 class ArtField;
28 class ArtMethod;
29 
30 class ArtMethodVisitor {
31  public:
~ArtMethodVisitor()32   virtual ~ArtMethodVisitor() {}
33 
34   virtual void Visit(ArtMethod* method) = 0;
35 };
36 
37 class ArtFieldVisitor {
38  public:
~ArtFieldVisitor()39   virtual ~ArtFieldVisitor() {}
40 
41   virtual void Visit(ArtField* method) = 0;
42 };
43 
44 class PACKED(4) ImageSection {
45  public:
ImageSection()46   ImageSection() : offset_(0), size_(0) { }
ImageSection(uint32_t offset,uint32_t size)47   ImageSection(uint32_t offset, uint32_t size) : offset_(offset), size_(size) { }
48   ImageSection(const ImageSection& section) = default;
49   ImageSection& operator=(const ImageSection& section) = default;
50 
Offset()51   uint32_t Offset() const {
52     return offset_;
53   }
54 
Size()55   uint32_t Size() const {
56     return size_;
57   }
58 
End()59   uint32_t End() const {
60     return Offset() + Size();
61   }
62 
Contains(uint64_t offset)63   bool Contains(uint64_t offset) const {
64     return offset - offset_ < size_;
65   }
66 
67  private:
68   uint32_t offset_;
69   uint32_t size_;
70 };
71 
72 // header of image files written by ImageWriter, read and validated by Space.
73 class PACKED(4) ImageHeader {
74  public:
75   enum StorageMode : uint32_t {
76     kStorageModeUncompressed,
77     kStorageModeLZ4,
78     kStorageModeLZ4HC,
79     kStorageModeCount,  // Number of elements in enum.
80   };
81   static constexpr StorageMode kDefaultStorageMode = kStorageModeUncompressed;
82 
ImageHeader()83   ImageHeader()
84       : image_begin_(0U),
85         image_size_(0U),
86         oat_checksum_(0U),
87         oat_file_begin_(0U),
88         oat_data_begin_(0U),
89         oat_data_end_(0U),
90         oat_file_end_(0U),
91         boot_image_begin_(0U),
92         boot_image_size_(0U),
93         boot_oat_begin_(0U),
94         boot_oat_size_(0U),
95         patch_delta_(0),
96         image_roots_(0U),
97         pointer_size_(0U),
98         compile_pic_(0),
99         is_pic_(0),
100         storage_mode_(kDefaultStorageMode),
101         data_size_(0) {}
102 
103   ImageHeader(uint32_t image_begin,
104               uint32_t image_size,
105               ImageSection* sections,
106               uint32_t image_roots,
107               uint32_t oat_checksum,
108               uint32_t oat_file_begin,
109               uint32_t oat_data_begin,
110               uint32_t oat_data_end,
111               uint32_t oat_file_end,
112               uint32_t boot_image_begin,
113               uint32_t boot_image_size,
114               uint32_t boot_oat_begin,
115               uint32_t boot_oat_size,
116               uint32_t pointer_size,
117               bool compile_pic,
118               bool is_pic,
119               StorageMode storage_mode,
120               size_t data_size);
121 
122   bool IsValid() const;
123   const char* GetMagic() const;
124 
GetImageBegin()125   uint8_t* GetImageBegin() const {
126     return reinterpret_cast<uint8_t*>(image_begin_);
127   }
128 
GetImageSize()129   size_t GetImageSize() const {
130     return static_cast<uint32_t>(image_size_);
131   }
132 
GetOatChecksum()133   uint32_t GetOatChecksum() const {
134     return oat_checksum_;
135   }
136 
SetOatChecksum(uint32_t oat_checksum)137   void SetOatChecksum(uint32_t oat_checksum) {
138     oat_checksum_ = oat_checksum;
139   }
140 
141   // The location that the oat file was expected to be when the image was created. The actual
142   // oat file may be at a different location for application images.
GetOatFileBegin()143   uint8_t* GetOatFileBegin() const {
144     return reinterpret_cast<uint8_t*>(oat_file_begin_);
145   }
146 
GetOatDataBegin()147   uint8_t* GetOatDataBegin() const {
148     return reinterpret_cast<uint8_t*>(oat_data_begin_);
149   }
150 
GetOatDataEnd()151   uint8_t* GetOatDataEnd() const {
152     return reinterpret_cast<uint8_t*>(oat_data_end_);
153   }
154 
GetOatFileEnd()155   uint8_t* GetOatFileEnd() const {
156     return reinterpret_cast<uint8_t*>(oat_file_end_);
157   }
158 
GetPointerSize()159   uint32_t GetPointerSize() const {
160     return pointer_size_;
161   }
162 
GetPatchDelta()163   off_t GetPatchDelta() const {
164     return patch_delta_;
165   }
166 
GetOatLocationFromImageLocation(const std::string & image)167   static std::string GetOatLocationFromImageLocation(const std::string& image) {
168     std::string oat_filename = image;
169     if (oat_filename.length() <= 3) {
170       oat_filename += ".oat";
171     } else {
172       oat_filename.replace(oat_filename.length() - 3, 3, "oat");
173     }
174     return oat_filename;
175   }
176 
177   enum ImageMethod {
178     kResolutionMethod,
179     kImtConflictMethod,
180     kImtUnimplementedMethod,
181     kCalleeSaveMethod,
182     kRefsOnlySaveMethod,
183     kRefsAndArgsSaveMethod,
184     kImageMethodsCount,  // Number of elements in enum.
185   };
186 
187   enum ImageRoot {
188     kDexCaches,
189     kClassRoots,
190     kImageRootsMax,
191   };
192 
193   enum ImageSections {
194     kSectionObjects,
195     kSectionArtFields,
196     kSectionArtMethods,
197     kSectionRuntimeMethods,
198     kSectionImTables,
199     kSectionIMTConflictTables,
200     kSectionDexCacheArrays,
201     kSectionInternedStrings,
202     kSectionClassTable,
203     kSectionImageBitmap,
204     kSectionCount,  // Number of elements in enum.
205   };
206 
207   ArtMethod* GetImageMethod(ImageMethod index) const;
208   void SetImageMethod(ImageMethod index, ArtMethod* method);
209 
210   const ImageSection& GetImageSection(ImageSections index) const;
211 
GetMethodsSection()212   const ImageSection& GetMethodsSection() const {
213     return GetImageSection(kSectionArtMethods);
214   }
215 
GetRuntimeMethodsSection()216   const ImageSection& GetRuntimeMethodsSection() const {
217     return GetImageSection(kSectionRuntimeMethods);
218   }
219 
GetFieldsSection()220   const ImageSection& GetFieldsSection() const {
221     return GetImageSection(ImageHeader::kSectionArtFields);
222   }
223 
224   template <ReadBarrierOption kReadBarrierOption = kWithReadBarrier>
225   mirror::Object* GetImageRoot(ImageRoot image_root) const
226       SHARED_REQUIRES(Locks::mutator_lock_);
227 
228   template <ReadBarrierOption kReadBarrierOption = kWithReadBarrier>
229   mirror::ObjectArray<mirror::Object>* GetImageRoots() const
230       SHARED_REQUIRES(Locks::mutator_lock_);
231 
232   void RelocateImage(off_t delta);
233   void RelocateImageMethods(off_t delta);
234   void RelocateImageObjects(off_t delta);
235 
CompilePic()236   bool CompilePic() const {
237     return compile_pic_ != 0;
238   }
239 
IsPic()240   bool IsPic() const {
241     return is_pic_ != 0;
242   }
243 
GetBootImageBegin()244   uint32_t GetBootImageBegin() const {
245     return boot_image_begin_;
246   }
247 
GetBootImageSize()248   uint32_t GetBootImageSize() const {
249     return boot_image_size_;
250   }
251 
GetBootOatBegin()252   uint32_t GetBootOatBegin() const {
253     return boot_oat_begin_;
254   }
255 
GetBootOatSize()256   uint32_t GetBootOatSize() const {
257     return boot_oat_size_;
258   }
259 
GetStorageMode()260   StorageMode GetStorageMode() const {
261     return storage_mode_;
262   }
263 
GetDataSize()264   uint64_t GetDataSize() const {
265     return data_size_;
266   }
267 
IsAppImage()268   bool IsAppImage() const {
269     // App images currently require a boot image, if the size is non zero then it is an app image
270     // header.
271     return boot_image_size_ != 0u;
272   }
273 
274   // Visit ArtMethods in the section starting at base. Includes runtime methods.
275   // TODO: Delete base parameter if it is always equal to GetImageBegin.
276   void VisitPackedArtMethods(ArtMethodVisitor* visitor, uint8_t* base, size_t pointer_size) const;
277 
278   // Visit ArtMethods in the section starting at base.
279   // TODO: Delete base parameter if it is always equal to GetImageBegin.
280   void VisitPackedArtFields(ArtFieldVisitor* visitor, uint8_t* base) const;
281 
282   template <typename Visitor>
283   void VisitPackedImTables(const Visitor& visitor,
284                            uint8_t* base,
285                            size_t pointer_size) const;
286 
287   template <typename Visitor>
288   void VisitPackedImtConflictTables(const Visitor& visitor,
289                                     uint8_t* base,
290                                     size_t pointer_size) const;
291 
292  private:
293   static const uint8_t kImageMagic[4];
294   static const uint8_t kImageVersion[4];
295 
296   uint8_t magic_[4];
297   uint8_t version_[4];
298 
299   // Required base address for mapping the image.
300   uint32_t image_begin_;
301 
302   // Image size, not page aligned.
303   uint32_t image_size_;
304 
305   // Checksum of the oat file we link to for load time sanity check.
306   uint32_t oat_checksum_;
307 
308   // Start address for oat file. Will be before oat_data_begin_ for .so files.
309   uint32_t oat_file_begin_;
310 
311   // Required oat address expected by image Method::GetCode() pointers.
312   uint32_t oat_data_begin_;
313 
314   // End of oat data address range for this image file.
315   uint32_t oat_data_end_;
316 
317   // End of oat file address range. will be after oat_data_end_ for
318   // .so files. Used for positioning a following alloc spaces.
319   uint32_t oat_file_end_;
320 
321   // Boot image begin and end (app image headers only).
322   uint32_t boot_image_begin_;
323   uint32_t boot_image_size_;
324 
325   // Boot oat begin and end (app image headers only).
326   uint32_t boot_oat_begin_;
327   uint32_t boot_oat_size_;
328 
329   // TODO: We should probably insert a boot image checksum for app images.
330 
331   // The total delta that this image has been patched.
332   int32_t patch_delta_;
333 
334   // Absolute address of an Object[] of objects needed to reinitialize from an image.
335   uint32_t image_roots_;
336 
337   // Pointer size, this affects the size of the ArtMethods.
338   uint32_t pointer_size_;
339 
340   // Boolean (0 or 1) to denote if the image was compiled with --compile-pic option
341   const uint32_t compile_pic_;
342 
343   // Boolean (0 or 1) to denote if the image can be mapped at a random address, this only refers to
344   // the .art file. Currently, app oat files do not depend on their app image. There are no pointers
345   // from the app oat code to the app image.
346   const uint32_t is_pic_;
347 
348   // Image section sizes/offsets correspond to the uncompressed form.
349   ImageSection sections_[kSectionCount];
350 
351   // Image methods, may be inside of the boot image for app images.
352   uint64_t image_methods_[kImageMethodsCount];
353 
354   // Storage method for the image, the image may be compressed.
355   StorageMode storage_mode_;
356 
357   // Data size for the image data excluding the bitmap and the header. For compressed images, this
358   // is the compressed size in the file.
359   uint32_t data_size_;
360 
361   friend class ImageWriter;
362 };
363 
364 std::ostream& operator<<(std::ostream& os, const ImageHeader::ImageMethod& policy);
365 std::ostream& operator<<(std::ostream& os, const ImageHeader::ImageRoot& policy);
366 std::ostream& operator<<(std::ostream& os, const ImageHeader::ImageSections& section);
367 std::ostream& operator<<(std::ostream& os, const ImageSection& section);
368 std::ostream& operator<<(std::ostream& os, const ImageHeader::StorageMode& mode);
369 
370 }  // namespace art
371 
372 #endif  // ART_RUNTIME_IMAGE_H_
373