• 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_DEX_FILE_H_
18 #define ART_RUNTIME_DEX_FILE_H_
19 
20 #include <memory>
21 #include <string>
22 #include <unordered_map>
23 #include <vector>
24 
25 #include "base/logging.h"
26 #include "base/mutex.h"  // For Locks::mutator_lock_.
27 #include "globals.h"
28 #include "invoke_type.h"
29 #include "jni.h"
30 #include "modifiers.h"
31 #include "utf.h"
32 
33 namespace art {
34 
35 // TODO: remove dependencies on mirror classes, primarily by moving
36 // EncodedStaticFieldValueIterator to its own file.
37 namespace mirror {
38   class ArtField;
39   class ArtMethod;
40   class ClassLoader;
41   class DexCache;
42 }  // namespace mirror
43 class ClassLinker;
44 class MemMap;
45 class Signature;
46 template<class T> class Handle;
47 class StringPiece;
48 class ZipArchive;
49 
50 // TODO: move all of the macro functionality into the DexCache class.
51 class DexFile {
52  public:
53   static const byte kDexMagic[];
54   static const byte kDexMagicVersion[];
55   static const size_t kSha1DigestSize = 20;
56   static const uint32_t kDexEndianConstant = 0x12345678;
57 
58   // name of the DexFile entry within a zip archive
59   static const char* kClassesDex;
60 
61   // The value of an invalid index.
62   static const uint32_t kDexNoIndex = 0xFFFFFFFF;
63 
64   // The value of an invalid index.
65   static const uint16_t kDexNoIndex16 = 0xFFFF;
66 
67   // The separator charactor in MultiDex locations.
68   static constexpr char kMultiDexSeparator = ':';
69 
70   // A string version of the previous. This is a define so that we can merge string literals in the
71   // preprocessor.
72   #define kMultiDexSeparatorString ":"
73 
74   // Raw header_item.
75   struct Header {
76     uint8_t magic_[8];
77     uint32_t checksum_;  // See also location_checksum_
78     uint8_t signature_[kSha1DigestSize];
79     uint32_t file_size_;  // size of entire file
80     uint32_t header_size_;  // offset to start of next section
81     uint32_t endian_tag_;
82     uint32_t link_size_;  // unused
83     uint32_t link_off_;  // unused
84     uint32_t map_off_;  // unused
85     uint32_t string_ids_size_;  // number of StringIds
86     uint32_t string_ids_off_;  // file offset of StringIds array
87     uint32_t type_ids_size_;  // number of TypeIds, we don't support more than 65535
88     uint32_t type_ids_off_;  // file offset of TypeIds array
89     uint32_t proto_ids_size_;  // number of ProtoIds, we don't support more than 65535
90     uint32_t proto_ids_off_;  // file offset of ProtoIds array
91     uint32_t field_ids_size_;  // number of FieldIds
92     uint32_t field_ids_off_;  // file offset of FieldIds array
93     uint32_t method_ids_size_;  // number of MethodIds
94     uint32_t method_ids_off_;  // file offset of MethodIds array
95     uint32_t class_defs_size_;  // number of ClassDefs
96     uint32_t class_defs_off_;  // file offset of ClassDef array
97     uint32_t data_size_;  // unused
98     uint32_t data_off_;  // unused
99 
100    private:
101     DISALLOW_COPY_AND_ASSIGN(Header);
102   };
103 
104   // Map item type codes.
105   enum {
106     kDexTypeHeaderItem               = 0x0000,
107     kDexTypeStringIdItem             = 0x0001,
108     kDexTypeTypeIdItem               = 0x0002,
109     kDexTypeProtoIdItem              = 0x0003,
110     kDexTypeFieldIdItem              = 0x0004,
111     kDexTypeMethodIdItem             = 0x0005,
112     kDexTypeClassDefItem             = 0x0006,
113     kDexTypeMapList                  = 0x1000,
114     kDexTypeTypeList                 = 0x1001,
115     kDexTypeAnnotationSetRefList     = 0x1002,
116     kDexTypeAnnotationSetItem        = 0x1003,
117     kDexTypeClassDataItem            = 0x2000,
118     kDexTypeCodeItem                 = 0x2001,
119     kDexTypeStringDataItem           = 0x2002,
120     kDexTypeDebugInfoItem            = 0x2003,
121     kDexTypeAnnotationItem           = 0x2004,
122     kDexTypeEncodedArrayItem         = 0x2005,
123     kDexTypeAnnotationsDirectoryItem = 0x2006,
124   };
125 
126   struct MapItem {
127     uint16_t type_;
128     uint16_t unused_;
129     uint32_t size_;
130     uint32_t offset_;
131 
132    private:
133     DISALLOW_COPY_AND_ASSIGN(MapItem);
134   };
135 
136   struct MapList {
137     uint32_t size_;
138     MapItem list_[1];
139 
140    private:
141     DISALLOW_COPY_AND_ASSIGN(MapList);
142   };
143 
144   // Raw string_id_item.
145   struct StringId {
146     uint32_t string_data_off_;  // offset in bytes from the base address
147 
148    private:
149     DISALLOW_COPY_AND_ASSIGN(StringId);
150   };
151 
152   // Raw type_id_item.
153   struct TypeId {
154     uint32_t descriptor_idx_;  // index into string_ids
155 
156    private:
157     DISALLOW_COPY_AND_ASSIGN(TypeId);
158   };
159 
160   // Raw field_id_item.
161   struct FieldId {
162     uint16_t class_idx_;  // index into type_ids_ array for defining class
163     uint16_t type_idx_;  // index into type_ids_ array for field type
164     uint32_t name_idx_;  // index into string_ids_ array for field name
165 
166    private:
167     DISALLOW_COPY_AND_ASSIGN(FieldId);
168   };
169 
170   // Raw method_id_item.
171   struct MethodId {
172     uint16_t class_idx_;  // index into type_ids_ array for defining class
173     uint16_t proto_idx_;  // index into proto_ids_ array for method prototype
174     uint32_t name_idx_;  // index into string_ids_ array for method name
175 
176    private:
177     DISALLOW_COPY_AND_ASSIGN(MethodId);
178   };
179 
180   // Raw proto_id_item.
181   struct ProtoId {
182     uint32_t shorty_idx_;  // index into string_ids array for shorty descriptor
183     uint16_t return_type_idx_;  // index into type_ids array for return type
184     uint16_t pad_;             // padding = 0
185     uint32_t parameters_off_;  // file offset to type_list for parameter types
186 
187    private:
188     DISALLOW_COPY_AND_ASSIGN(ProtoId);
189   };
190 
191   // Raw class_def_item.
192   struct ClassDef {
193     uint16_t class_idx_;  // index into type_ids_ array for this class
194     uint16_t pad1_;  // padding = 0
195     uint32_t access_flags_;
196     uint16_t superclass_idx_;  // index into type_ids_ array for superclass
197     uint16_t pad2_;  // padding = 0
198     uint32_t interfaces_off_;  // file offset to TypeList
199     uint32_t source_file_idx_;  // index into string_ids_ for source file name
200     uint32_t annotations_off_;  // file offset to annotations_directory_item
201     uint32_t class_data_off_;  // file offset to class_data_item
202     uint32_t static_values_off_;  // file offset to EncodedArray
203 
204     // Returns the valid access flags, that is, Java modifier bits relevant to the ClassDef type
205     // (class or interface). These are all in the lower 16b and do not contain runtime flags.
GetJavaAccessFlagsClassDef206     uint32_t GetJavaAccessFlags() const {
207       // Make sure that none of our runtime-only flags are set.
208       COMPILE_ASSERT((kAccValidClassFlags & kAccJavaFlagsMask) == kAccValidClassFlags,
209                      valid_class_flags_not_subset_of_java_flags);
210       COMPILE_ASSERT((kAccValidInterfaceFlags & kAccJavaFlagsMask) == kAccValidInterfaceFlags,
211                      valid_interface_flags_not_subset_of_java_flags);
212 
213       if ((access_flags_ & kAccInterface) != 0) {
214         // Interface.
215         return access_flags_ & kAccValidInterfaceFlags;
216       } else {
217         // Class.
218         return access_flags_ & kAccValidClassFlags;
219       }
220     }
221 
222    private:
223     DISALLOW_COPY_AND_ASSIGN(ClassDef);
224   };
225 
226   // Raw type_item.
227   struct TypeItem {
228     uint16_t type_idx_;  // index into type_ids section
229 
230    private:
231     DISALLOW_COPY_AND_ASSIGN(TypeItem);
232   };
233 
234   // Raw type_list.
235   class TypeList {
236    public:
Size()237     uint32_t Size() const {
238       return size_;
239     }
240 
GetTypeItem(uint32_t idx)241     const TypeItem& GetTypeItem(uint32_t idx) const {
242       DCHECK_LT(idx, this->size_);
243       return this->list_[idx];
244     }
245 
246     // Size in bytes of the part of the list that is common.
GetHeaderSize()247     static constexpr size_t GetHeaderSize() {
248       return 4U;
249     }
250 
251     // Size in bytes of the whole type list including all the stored elements.
GetListSize(size_t count)252     static constexpr size_t GetListSize(size_t count) {
253       return GetHeaderSize() + sizeof(TypeItem) * count;
254     }
255 
256    private:
257     uint32_t size_;  // size of the list, in entries
258     TypeItem list_[1];  // elements of the list
259     DISALLOW_COPY_AND_ASSIGN(TypeList);
260   };
261 
262   // Raw code_item.
263   struct CodeItem {
264     uint16_t registers_size_;
265     uint16_t ins_size_;
266     uint16_t outs_size_;
267     uint16_t tries_size_;
268     uint32_t debug_info_off_;  // file offset to debug info stream
269     uint32_t insns_size_in_code_units_;  // size of the insns array, in 2 byte code units
270     uint16_t insns_[1];
271 
272    private:
273     DISALLOW_COPY_AND_ASSIGN(CodeItem);
274   };
275 
276   // Raw try_item.
277   struct TryItem {
278     uint32_t start_addr_;
279     uint16_t insn_count_;
280     uint16_t handler_off_;
281 
282    private:
283     DISALLOW_COPY_AND_ASSIGN(TryItem);
284   };
285 
286   // Annotation constants.
287   enum {
288     kDexVisibilityBuild         = 0x00,     /* annotation visibility */
289     kDexVisibilityRuntime       = 0x01,
290     kDexVisibilitySystem        = 0x02,
291 
292     kDexAnnotationByte          = 0x00,
293     kDexAnnotationShort         = 0x02,
294     kDexAnnotationChar          = 0x03,
295     kDexAnnotationInt           = 0x04,
296     kDexAnnotationLong          = 0x06,
297     kDexAnnotationFloat         = 0x10,
298     kDexAnnotationDouble        = 0x11,
299     kDexAnnotationString        = 0x17,
300     kDexAnnotationType          = 0x18,
301     kDexAnnotationField         = 0x19,
302     kDexAnnotationMethod        = 0x1a,
303     kDexAnnotationEnum          = 0x1b,
304     kDexAnnotationArray         = 0x1c,
305     kDexAnnotationAnnotation    = 0x1d,
306     kDexAnnotationNull          = 0x1e,
307     kDexAnnotationBoolean       = 0x1f,
308 
309     kDexAnnotationValueTypeMask = 0x1f,     /* low 5 bits */
310     kDexAnnotationValueArgShift = 5,
311   };
312 
313   struct AnnotationsDirectoryItem {
314     uint32_t class_annotations_off_;
315     uint32_t fields_size_;
316     uint32_t methods_size_;
317     uint32_t parameters_size_;
318 
319    private:
320     DISALLOW_COPY_AND_ASSIGN(AnnotationsDirectoryItem);
321   };
322 
323   struct FieldAnnotationsItem {
324     uint32_t field_idx_;
325     uint32_t annotations_off_;
326 
327    private:
328     DISALLOW_COPY_AND_ASSIGN(FieldAnnotationsItem);
329   };
330 
331   struct MethodAnnotationsItem {
332     uint32_t method_idx_;
333     uint32_t annotations_off_;
334 
335    private:
336     DISALLOW_COPY_AND_ASSIGN(MethodAnnotationsItem);
337   };
338 
339   struct ParameterAnnotationsItem {
340     uint32_t method_idx_;
341     uint32_t annotations_off_;
342 
343    private:
344     DISALLOW_COPY_AND_ASSIGN(ParameterAnnotationsItem);
345   };
346 
347   struct AnnotationSetRefItem {
348     uint32_t annotations_off_;
349 
350    private:
351     DISALLOW_COPY_AND_ASSIGN(AnnotationSetRefItem);
352   };
353 
354   struct AnnotationSetRefList {
355     uint32_t size_;
356     AnnotationSetRefItem list_[1];
357 
358    private:
359     DISALLOW_COPY_AND_ASSIGN(AnnotationSetRefList);
360   };
361 
362   struct AnnotationSetItem {
363     uint32_t size_;
364     uint32_t entries_[1];
365 
366    private:
367     DISALLOW_COPY_AND_ASSIGN(AnnotationSetItem);
368   };
369 
370   struct AnnotationItem {
371     uint8_t visibility_;
372     uint8_t annotation_[1];
373 
374    private:
375     DISALLOW_COPY_AND_ASSIGN(AnnotationItem);
376   };
377 
378   // Returns the checksum of a file for comparison with GetLocationChecksum().
379   // For .dex files, this is the header checksum.
380   // For zip files, this is the classes.dex zip entry CRC32 checksum.
381   // Return true if the checksum could be found, false otherwise.
382   static bool GetChecksum(const char* filename, uint32_t* checksum, std::string* error_msg);
383 
384   // Opens .dex files found in the container, guessing the container format based on file extension.
385   static bool Open(const char* filename, const char* location, std::string* error_msg,
386                    std::vector<const DexFile*>* dex_files);
387 
388   // Opens .dex file, backed by existing memory
Open(const uint8_t * base,size_t size,const std::string & location,uint32_t location_checksum,std::string * error_msg)389   static const DexFile* Open(const uint8_t* base, size_t size,
390                              const std::string& location,
391                              uint32_t location_checksum,
392                              std::string* error_msg) {
393     return OpenMemory(base, size, location, location_checksum, NULL, error_msg);
394   }
395 
396   // Open all classesXXX.dex files from a zip archive.
397   static bool OpenFromZip(const ZipArchive& zip_archive, const std::string& location,
398                           std::string* error_msg, std::vector<const DexFile*>* dex_files);
399 
400   // Closes a .dex file.
401   virtual ~DexFile();
402 
GetLocation()403   const std::string& GetLocation() const {
404     return location_;
405   }
406 
407   // For normal dex files, location and base location coincide. If a dex file is part of a multidex
408   // archive, the base location is the name of the originating jar/apk, stripped of any internal
409   // classes*.dex path.
GetBaseLocation(const char * location)410   static std::string GetBaseLocation(const char* location) {
411     const char* pos = strrchr(location, kMultiDexSeparator);
412     if (pos == nullptr) {
413       return location;
414     } else {
415       return std::string(location, pos - location);
416     }
417   }
418 
GetBaseLocation()419   std::string GetBaseLocation() const {
420     size_t pos = location_.rfind(kMultiDexSeparator);
421     if (pos == std::string::npos) {
422       return location_;
423     } else {
424       return location_.substr(0, pos);
425     }
426   }
427 
428   // For DexFiles directly from .dex files, this is the checksum from the DexFile::Header.
429   // For DexFiles opened from a zip files, this will be the ZipEntry CRC32 of classes.dex.
GetLocationChecksum()430   uint32_t GetLocationChecksum() const {
431     return location_checksum_;
432   }
433 
GetHeader()434   const Header& GetHeader() const {
435     DCHECK(header_ != NULL) << GetLocation();
436     return *header_;
437   }
438 
439   // Decode the dex magic version
440   uint32_t GetVersion() const;
441 
442   // Returns true if the byte string points to the magic value.
443   static bool IsMagicValid(const byte* magic);
444 
445   // Returns true if the byte string after the magic is the correct value.
446   static bool IsVersionValid(const byte* magic);
447 
448   // Returns the number of string identifiers in the .dex file.
NumStringIds()449   size_t NumStringIds() const {
450     DCHECK(header_ != NULL) << GetLocation();
451     return header_->string_ids_size_;
452   }
453 
454   // Returns the StringId at the specified index.
GetStringId(uint32_t idx)455   const StringId& GetStringId(uint32_t idx) const {
456     DCHECK_LT(idx, NumStringIds()) << GetLocation();
457     return string_ids_[idx];
458   }
459 
GetIndexForStringId(const StringId & string_id)460   uint32_t GetIndexForStringId(const StringId& string_id) const {
461     CHECK_GE(&string_id, string_ids_) << GetLocation();
462     CHECK_LT(&string_id, string_ids_ + header_->string_ids_size_) << GetLocation();
463     return &string_id - string_ids_;
464   }
465 
466   int32_t GetStringLength(const StringId& string_id) const;
467 
468   // Returns a pointer to the UTF-8 string data referred to by the given string_id as well as the
469   // length of the string when decoded as a UTF-16 string. Note the UTF-16 length is not the same
470   // as the string length of the string data.
471   const char* GetStringDataAndUtf16Length(const StringId& string_id, uint32_t* utf16_length) const;
472 
GetStringData(const StringId & string_id)473   const char* GetStringData(const StringId& string_id) const {
474     uint32_t ignored;
475     return GetStringDataAndUtf16Length(string_id, &ignored);
476   }
477 
478   // Index version of GetStringDataAndUtf16Length.
StringDataAndUtf16LengthByIdx(uint32_t idx,uint32_t * utf16_length)479   const char* StringDataAndUtf16LengthByIdx(uint32_t idx, uint32_t* utf16_length) const {
480     if (idx == kDexNoIndex) {
481       *utf16_length = 0;
482       return NULL;
483     }
484     const StringId& string_id = GetStringId(idx);
485     return GetStringDataAndUtf16Length(string_id, utf16_length);
486   }
487 
StringDataByIdx(uint32_t idx)488   const char* StringDataByIdx(uint32_t idx) const {
489     uint32_t unicode_length;
490     return StringDataAndUtf16LengthByIdx(idx, &unicode_length);
491   }
492 
493   // Looks up a string id for a given modified utf8 string.
494   const StringId* FindStringId(const char* string) const;
495 
496   // Looks up a string id for a given utf16 string.
497   const StringId* FindStringId(const uint16_t* string) const;
498 
499   // Returns the number of type identifiers in the .dex file.
NumTypeIds()500   uint32_t NumTypeIds() const {
501     DCHECK(header_ != NULL) << GetLocation();
502     return header_->type_ids_size_;
503   }
504 
505   // Returns the TypeId at the specified index.
GetTypeId(uint32_t idx)506   const TypeId& GetTypeId(uint32_t idx) const {
507     DCHECK_LT(idx, NumTypeIds()) << GetLocation();
508     return type_ids_[idx];
509   }
510 
GetIndexForTypeId(const TypeId & type_id)511   uint16_t GetIndexForTypeId(const TypeId& type_id) const {
512     CHECK_GE(&type_id, type_ids_) << GetLocation();
513     CHECK_LT(&type_id, type_ids_ + header_->type_ids_size_) << GetLocation();
514     size_t result = &type_id - type_ids_;
515     DCHECK_LT(result, 65536U) << GetLocation();
516     return static_cast<uint16_t>(result);
517   }
518 
519   // Get the descriptor string associated with a given type index.
StringByTypeIdx(uint32_t idx,uint32_t * unicode_length)520   const char* StringByTypeIdx(uint32_t idx, uint32_t* unicode_length) const {
521     const TypeId& type_id = GetTypeId(idx);
522     return StringDataAndUtf16LengthByIdx(type_id.descriptor_idx_, unicode_length);
523   }
524 
StringByTypeIdx(uint32_t idx)525   const char* StringByTypeIdx(uint32_t idx) const {
526     const TypeId& type_id = GetTypeId(idx);
527     return StringDataByIdx(type_id.descriptor_idx_);
528   }
529 
530   // Returns the type descriptor string of a type id.
GetTypeDescriptor(const TypeId & type_id)531   const char* GetTypeDescriptor(const TypeId& type_id) const {
532     return StringDataByIdx(type_id.descriptor_idx_);
533   }
534 
535   // Looks up a type for the given string index
536   const TypeId* FindTypeId(uint32_t string_idx) const;
537 
538   // Returns the number of field identifiers in the .dex file.
NumFieldIds()539   size_t NumFieldIds() const {
540     DCHECK(header_ != NULL) << GetLocation();
541     return header_->field_ids_size_;
542   }
543 
544   // Returns the FieldId at the specified index.
GetFieldId(uint32_t idx)545   const FieldId& GetFieldId(uint32_t idx) const {
546     DCHECK_LT(idx, NumFieldIds()) << GetLocation();
547     return field_ids_[idx];
548   }
549 
GetIndexForFieldId(const FieldId & field_id)550   uint32_t GetIndexForFieldId(const FieldId& field_id) const {
551     CHECK_GE(&field_id, field_ids_) << GetLocation();
552     CHECK_LT(&field_id, field_ids_ + header_->field_ids_size_) << GetLocation();
553     return &field_id - field_ids_;
554   }
555 
556   // Looks up a field by its declaring class, name and type
557   const FieldId* FindFieldId(const DexFile::TypeId& declaring_klass,
558                              const DexFile::StringId& name,
559                              const DexFile::TypeId& type) const;
560 
561   // Returns the declaring class descriptor string of a field id.
GetFieldDeclaringClassDescriptor(const FieldId & field_id)562   const char* GetFieldDeclaringClassDescriptor(const FieldId& field_id) const {
563     const DexFile::TypeId& type_id = GetTypeId(field_id.class_idx_);
564     return GetTypeDescriptor(type_id);
565   }
566 
567   // Returns the class descriptor string of a field id.
GetFieldTypeDescriptor(const FieldId & field_id)568   const char* GetFieldTypeDescriptor(const FieldId& field_id) const {
569     const DexFile::TypeId& type_id = GetTypeId(field_id.type_idx_);
570     return GetTypeDescriptor(type_id);
571   }
572 
573   // Returns the name of a field id.
GetFieldName(const FieldId & field_id)574   const char* GetFieldName(const FieldId& field_id) const {
575     return StringDataByIdx(field_id.name_idx_);
576   }
577 
578   // Returns the number of method identifiers in the .dex file.
NumMethodIds()579   size_t NumMethodIds() const {
580     DCHECK(header_ != NULL) << GetLocation();
581     return header_->method_ids_size_;
582   }
583 
584   // Returns the MethodId at the specified index.
GetMethodId(uint32_t idx)585   const MethodId& GetMethodId(uint32_t idx) const {
586     DCHECK_LT(idx, NumMethodIds()) << GetLocation();
587     return method_ids_[idx];
588   }
589 
GetIndexForMethodId(const MethodId & method_id)590   uint32_t GetIndexForMethodId(const MethodId& method_id) const {
591     CHECK_GE(&method_id, method_ids_) << GetLocation();
592     CHECK_LT(&method_id, method_ids_ + header_->method_ids_size_) << GetLocation();
593     return &method_id - method_ids_;
594   }
595 
596   // Looks up a method by its declaring class, name and proto_id
597   const MethodId* FindMethodId(const DexFile::TypeId& declaring_klass,
598                                const DexFile::StringId& name,
599                                const DexFile::ProtoId& signature) const;
600 
601   // Returns the declaring class descriptor string of a method id.
GetMethodDeclaringClassDescriptor(const MethodId & method_id)602   const char* GetMethodDeclaringClassDescriptor(const MethodId& method_id) const {
603     const DexFile::TypeId& type_id = GetTypeId(method_id.class_idx_);
604     return GetTypeDescriptor(type_id);
605   }
606 
607   // Returns the prototype of a method id.
GetMethodPrototype(const MethodId & method_id)608   const ProtoId& GetMethodPrototype(const MethodId& method_id) const {
609     return GetProtoId(method_id.proto_idx_);
610   }
611 
612   // Returns a representation of the signature of a method id.
613   const Signature GetMethodSignature(const MethodId& method_id) const;
614 
615   // Returns the name of a method id.
GetMethodName(const MethodId & method_id)616   const char* GetMethodName(const MethodId& method_id) const {
617     return StringDataByIdx(method_id.name_idx_);
618   }
619 
620   // Returns the shorty of a method id.
GetMethodShorty(const MethodId & method_id)621   const char* GetMethodShorty(const MethodId& method_id) const {
622     return StringDataByIdx(GetProtoId(method_id.proto_idx_).shorty_idx_);
623   }
GetMethodShorty(const MethodId & method_id,uint32_t * length)624   const char* GetMethodShorty(const MethodId& method_id, uint32_t* length) const {
625     // Using the UTF16 length is safe here as shorties are guaranteed to be ASCII characters.
626     return StringDataAndUtf16LengthByIdx(GetProtoId(method_id.proto_idx_).shorty_idx_, length);
627   }
628   // Returns the number of class definitions in the .dex file.
NumClassDefs()629   uint32_t NumClassDefs() const {
630     DCHECK(header_ != NULL) << GetLocation();
631     return header_->class_defs_size_;
632   }
633 
634   // Returns the ClassDef at the specified index.
GetClassDef(uint16_t idx)635   const ClassDef& GetClassDef(uint16_t idx) const {
636     DCHECK_LT(idx, NumClassDefs()) << GetLocation();
637     return class_defs_[idx];
638   }
639 
GetIndexForClassDef(const ClassDef & class_def)640   uint16_t GetIndexForClassDef(const ClassDef& class_def) const {
641     CHECK_GE(&class_def, class_defs_) << GetLocation();
642     CHECK_LT(&class_def, class_defs_ + header_->class_defs_size_) << GetLocation();
643     return &class_def - class_defs_;
644   }
645 
646   // Returns the class descriptor string of a class definition.
GetClassDescriptor(const ClassDef & class_def)647   const char* GetClassDescriptor(const ClassDef& class_def) const {
648     return StringByTypeIdx(class_def.class_idx_);
649   }
650 
651   // Looks up a class definition by its class descriptor.
652   const ClassDef* FindClassDef(const char* descriptor) const;
653 
654   // Looks up a class definition by its type index.
655   const ClassDef* FindClassDef(uint16_t type_idx) const;
656 
GetInterfacesList(const ClassDef & class_def)657   const TypeList* GetInterfacesList(const ClassDef& class_def) const {
658     if (class_def.interfaces_off_ == 0) {
659         return NULL;
660     } else {
661       const byte* addr = begin_ + class_def.interfaces_off_;
662       return reinterpret_cast<const TypeList*>(addr);
663     }
664   }
665 
666   // Returns a pointer to the raw memory mapped class_data_item
GetClassData(const ClassDef & class_def)667   const byte* GetClassData(const ClassDef& class_def) const {
668     if (class_def.class_data_off_ == 0) {
669       return NULL;
670     } else {
671       return begin_ + class_def.class_data_off_;
672     }
673   }
674 
675   //
GetCodeItem(const uint32_t code_off)676   const CodeItem* GetCodeItem(const uint32_t code_off) const {
677     if (code_off == 0) {
678       return NULL;  // native or abstract method
679     } else {
680       const byte* addr = begin_ + code_off;
681       return reinterpret_cast<const CodeItem*>(addr);
682     }
683   }
684 
GetReturnTypeDescriptor(const ProtoId & proto_id)685   const char* GetReturnTypeDescriptor(const ProtoId& proto_id) const {
686     return StringByTypeIdx(proto_id.return_type_idx_);
687   }
688 
689   // Returns the number of prototype identifiers in the .dex file.
NumProtoIds()690   size_t NumProtoIds() const {
691     DCHECK(header_ != NULL) << GetLocation();
692     return header_->proto_ids_size_;
693   }
694 
695   // Returns the ProtoId at the specified index.
GetProtoId(uint32_t idx)696   const ProtoId& GetProtoId(uint32_t idx) const {
697     DCHECK_LT(idx, NumProtoIds()) << GetLocation();
698     return proto_ids_[idx];
699   }
700 
GetIndexForProtoId(const ProtoId & proto_id)701   uint16_t GetIndexForProtoId(const ProtoId& proto_id) const {
702     CHECK_GE(&proto_id, proto_ids_) << GetLocation();
703     CHECK_LT(&proto_id, proto_ids_ + header_->proto_ids_size_) << GetLocation();
704     return &proto_id - proto_ids_;
705   }
706 
707   // Looks up a proto id for a given return type and signature type list
708   const ProtoId* FindProtoId(uint16_t return_type_idx,
709                              const uint16_t* signature_type_idxs, uint32_t signature_length) const;
FindProtoId(uint16_t return_type_idx,const std::vector<uint16_t> & signature_type_idxs)710   const ProtoId* FindProtoId(uint16_t return_type_idx,
711                              const std::vector<uint16_t>& signature_type_idxs) const {
712     return FindProtoId(return_type_idx, &signature_type_idxs[0], signature_type_idxs.size());
713   }
714 
715   // Given a signature place the type ids into the given vector, returns true on success
716   bool CreateTypeList(const StringPiece& signature, uint16_t* return_type_idx,
717                       std::vector<uint16_t>* param_type_idxs) const;
718 
719   // Create a Signature from the given string signature or return Signature::NoSignature if not
720   // possible.
721   const Signature CreateSignature(const StringPiece& signature) const;
722 
723   // Returns the short form method descriptor for the given prototype.
GetShorty(uint32_t proto_idx)724   const char* GetShorty(uint32_t proto_idx) const {
725     const ProtoId& proto_id = GetProtoId(proto_idx);
726     return StringDataByIdx(proto_id.shorty_idx_);
727   }
728 
GetProtoParameters(const ProtoId & proto_id)729   const TypeList* GetProtoParameters(const ProtoId& proto_id) const {
730     if (proto_id.parameters_off_ == 0) {
731       return NULL;
732     } else {
733       const byte* addr = begin_ + proto_id.parameters_off_;
734       return reinterpret_cast<const TypeList*>(addr);
735     }
736   }
737 
GetEncodedStaticFieldValuesArray(const ClassDef & class_def)738   const byte* GetEncodedStaticFieldValuesArray(const ClassDef& class_def) const {
739     if (class_def.static_values_off_ == 0) {
740       return 0;
741     } else {
742       return begin_ + class_def.static_values_off_;
743     }
744   }
745 
746   static const TryItem* GetTryItems(const CodeItem& code_item, uint32_t offset);
747 
748   // Get the base of the encoded data for the given DexCode.
GetCatchHandlerData(const CodeItem & code_item,uint32_t offset)749   static const byte* GetCatchHandlerData(const CodeItem& code_item, uint32_t offset) {
750     const byte* handler_data =
751         reinterpret_cast<const byte*>(GetTryItems(code_item, code_item.tries_size_));
752     return handler_data + offset;
753   }
754 
755   // Find which try region is associated with the given address (ie dex pc). Returns -1 if none.
756   static int32_t FindTryItem(const CodeItem &code_item, uint32_t address);
757 
758   // Find the handler offset associated with the given address (ie dex pc). Returns -1 if none.
759   static int32_t FindCatchHandlerOffset(const CodeItem &code_item, uint32_t address);
760 
761   // Get the pointer to the start of the debugging data
GetDebugInfoStream(const CodeItem * code_item)762   const byte* GetDebugInfoStream(const CodeItem* code_item) const {
763     if (code_item->debug_info_off_ == 0) {
764       return NULL;
765     } else {
766       return begin_ + code_item->debug_info_off_;
767     }
768   }
769 
770   // Callback for "new position table entry".
771   // Returning true causes the decoder to stop early.
772   typedef bool (*DexDebugNewPositionCb)(void* context, uint32_t address, uint32_t line_num);
773 
774   // Callback for "new locals table entry". "signature" is an empty string
775   // if no signature is available for an entry.
776   typedef void (*DexDebugNewLocalCb)(void* context, uint16_t reg,
777                                      uint32_t start_address,
778                                      uint32_t end_address,
779                                      const char* name,
780                                      const char* descriptor,
781                                      const char* signature);
782 
783   static bool LineNumForPcCb(void* context, uint32_t address, uint32_t line_num);
784 
785   // Debug info opcodes and constants
786   enum {
787     DBG_END_SEQUENCE         = 0x00,
788     DBG_ADVANCE_PC           = 0x01,
789     DBG_ADVANCE_LINE         = 0x02,
790     DBG_START_LOCAL          = 0x03,
791     DBG_START_LOCAL_EXTENDED = 0x04,
792     DBG_END_LOCAL            = 0x05,
793     DBG_RESTART_LOCAL        = 0x06,
794     DBG_SET_PROLOGUE_END     = 0x07,
795     DBG_SET_EPILOGUE_BEGIN   = 0x08,
796     DBG_SET_FILE             = 0x09,
797     DBG_FIRST_SPECIAL        = 0x0a,
798     DBG_LINE_BASE            = -4,
799     DBG_LINE_RANGE           = 15,
800   };
801 
802   struct LocalInfo {
LocalInfoLocalInfo803     LocalInfo()
804         : name_(NULL), descriptor_(NULL), signature_(NULL), start_address_(0), is_live_(false) {}
805 
806     const char* name_;  // E.g., list
807     const char* descriptor_;  // E.g., Ljava/util/LinkedList;
808     const char* signature_;  // E.g., java.util.LinkedList<java.lang.Integer>
809     uint16_t start_address_;  // PC location where the local is first defined.
810     bool is_live_;  // Is the local defined and live.
811 
812    private:
813     DISALLOW_COPY_AND_ASSIGN(LocalInfo);
814   };
815 
816   struct LineNumFromPcContext {
LineNumFromPcContextLineNumFromPcContext817     LineNumFromPcContext(uint32_t address, uint32_t line_num)
818         : address_(address), line_num_(line_num) {}
819     uint32_t address_;
820     uint32_t line_num_;
821    private:
822     DISALLOW_COPY_AND_ASSIGN(LineNumFromPcContext);
823   };
824 
InvokeLocalCbIfLive(void * context,int reg,uint32_t end_address,LocalInfo * local_in_reg,DexDebugNewLocalCb local_cb)825   void InvokeLocalCbIfLive(void* context, int reg, uint32_t end_address,
826                            LocalInfo* local_in_reg, DexDebugNewLocalCb local_cb) const {
827     if (local_cb != NULL && local_in_reg[reg].is_live_) {
828       local_cb(context, reg, local_in_reg[reg].start_address_, end_address,
829           local_in_reg[reg].name_, local_in_reg[reg].descriptor_,
830           local_in_reg[reg].signature_ != NULL ? local_in_reg[reg].signature_ : "");
831     }
832   }
833 
834   // Determine the source file line number based on the program counter.
835   // "pc" is an offset, in 16-bit units, from the start of the method's code.
836   //
837   // Returns -1 if no match was found (possibly because the source files were
838   // compiled without "-g", so no line number information is present).
839   // Returns -2 for native methods (as expected in exception traces).
840   //
841   // This is used by runtime; therefore use art::Method not art::DexFile::Method.
842   int32_t GetLineNumFromPC(mirror::ArtMethod* method, uint32_t rel_pc) const
843       SHARED_LOCKS_REQUIRED(Locks::mutator_lock_);
844 
845   void DecodeDebugInfo(const CodeItem* code_item, bool is_static, uint32_t method_idx,
846                        DexDebugNewPositionCb position_cb, DexDebugNewLocalCb local_cb,
847                        void* context) const;
848 
GetSourceFile(const ClassDef & class_def)849   const char* GetSourceFile(const ClassDef& class_def) const {
850     if (class_def.source_file_idx_ == 0xffffffff) {
851       return NULL;
852     } else {
853       return StringDataByIdx(class_def.source_file_idx_);
854     }
855   }
856 
857   int GetPermissions() const;
858 
859   bool IsReadOnly() const;
860 
861   bool EnableWrite() const;
862 
863   bool DisableWrite() const;
864 
Begin()865   const byte* Begin() const {
866     return begin_;
867   }
868 
Size()869   size_t Size() const {
870     return size_;
871   }
872 
873   static std::string GetMultiDexClassesDexName(size_t number, const char* dex_location);
874 
875   // Returns the canonical form of the given dex location.
876   //
877   // There are different flavors of "dex locations" as follows:
878   // the file name of a dex file:
879   //     The actual file path that the dex file has on disk.
880   // dex_location:
881   //     This acts as a key for the class linker to know which dex file to load.
882   //     It may correspond to either an old odex file or a particular dex file
883   //     inside an oat file. In the first case it will also match the file name
884   //     of the dex file. In the second case (oat) it will include the file name
885   //     and possibly some multidex annotation to uniquely identify it.
886   // canonical_dex_location:
887   //     the dex_location where it's file name part has been made canonical.
888   static std::string GetDexCanonicalLocation(const char* dex_location);
889 
890  private:
891   // Opens a .dex file
892   static const DexFile* OpenFile(int fd, const char* location, bool verify, std::string* error_msg);
893 
894   // Opens dex files from within a .jar, .zip, or .apk file
895   static bool OpenZip(int fd, const std::string& location, std::string* error_msg,
896                       std::vector<const DexFile*>* dex_files);
897 
898   enum class ZipOpenErrorCode {  // private
899     kNoError,
900     kEntryNotFound,
901     kExtractToMemoryError,
902     kDexFileError,
903     kMakeReadOnlyError,
904     kVerifyError
905   };
906 
907   // Opens .dex file from the entry_name in a zip archive. error_code is undefined when non-nullptr
908   // return.
909   static const DexFile* Open(const ZipArchive& zip_archive, const char* entry_name,
910                              const std::string& location, std::string* error_msg,
911                              ZipOpenErrorCode* error_code);
912 
913   // Opens a .dex file at the given address backed by a MemMap
914   static const DexFile* OpenMemory(const std::string& location,
915                                    uint32_t location_checksum,
916                                    MemMap* mem_map,
917                                    std::string* error_msg);
918 
919   // Opens a .dex file at the given address, optionally backed by a MemMap
920   static const DexFile* OpenMemory(const byte* dex_file,
921                                    size_t size,
922                                    const std::string& location,
923                                    uint32_t location_checksum,
924                                    MemMap* mem_map,
925                                    std::string* error_msg);
926 
927   DexFile(const byte* base, size_t size,
928           const std::string& location,
929           uint32_t location_checksum,
930           MemMap* mem_map);
931 
932   // Top-level initializer that calls other Init methods.
933   bool Init(std::string* error_msg);
934 
935   // Returns true if the header magic and version numbers are of the expected values.
936   bool CheckMagicAndVersion(std::string* error_msg) const;
937 
938   void DecodeDebugInfo0(const CodeItem* code_item, bool is_static, uint32_t method_idx,
939       DexDebugNewPositionCb position_cb, DexDebugNewLocalCb local_cb,
940       void* context, const byte* stream, LocalInfo* local_in_reg) const;
941 
942   // Check whether a location denotes a multidex dex file. This is a very simple check: returns
943   // whether the string contains the separator character.
944   static bool IsMultiDexLocation(const char* location);
945 
946 
947   // The base address of the memory mapping.
948   const byte* const begin_;
949 
950   // The size of the underlying memory allocation in bytes.
951   const size_t size_;
952 
953   // Typically the dex file name when available, alternatively some identifying string.
954   //
955   // The ClassLinker will use this to match DexFiles the boot class
956   // path to DexCache::GetLocation when loading from an image.
957   const std::string location_;
958 
959   const uint32_t location_checksum_;
960 
961   // Manages the underlying memory allocation.
962   std::unique_ptr<MemMap> mem_map_;
963 
964   // Points to the header section.
965   const Header* const header_;
966 
967   // Points to the base of the string identifier list.
968   const StringId* const string_ids_;
969 
970   // Points to the base of the type identifier list.
971   const TypeId* const type_ids_;
972 
973   // Points to the base of the field identifier list.
974   const FieldId* const field_ids_;
975 
976   // Points to the base of the method identifier list.
977   const MethodId* const method_ids_;
978 
979   // Points to the base of the prototype identifier list.
980   const ProtoId* const proto_ids_;
981 
982   // Points to the base of the class definition list.
983   const ClassDef* const class_defs_;
984 
985   // Number of misses finding a class def from a descriptor.
986   mutable Atomic<uint32_t> find_class_def_misses_;
987 
988   struct UTF16HashCmp {
989     // Hash function.
operatorUTF16HashCmp990     size_t operator()(const char* key) const {
991       return ComputeUtf8Hash(key);
992     }
993     // std::equal function.
operatorUTF16HashCmp994     bool operator()(const char* a, const char* b) const {
995       return CompareModifiedUtf8ToModifiedUtf8AsUtf16CodePointValues(a, b) == 0;
996     }
997   };
998   typedef std::unordered_map<const char*, const ClassDef*, UTF16HashCmp, UTF16HashCmp> Index;
999   mutable Atomic<Index*> class_def_index_;
1000   mutable Mutex build_class_def_index_mutex_ DEFAULT_MUTEX_ACQUIRED_AFTER;
1001 };
1002 std::ostream& operator<<(std::ostream& os, const DexFile& dex_file);
1003 
1004 // Iterate over a dex file's ProtoId's paramters
1005 class DexFileParameterIterator {
1006  public:
DexFileParameterIterator(const DexFile & dex_file,const DexFile::ProtoId & proto_id)1007   DexFileParameterIterator(const DexFile& dex_file, const DexFile::ProtoId& proto_id)
1008       : dex_file_(dex_file), size_(0), pos_(0) {
1009     type_list_ = dex_file_.GetProtoParameters(proto_id);
1010     if (type_list_ != NULL) {
1011       size_ = type_list_->Size();
1012     }
1013   }
HasNext()1014   bool HasNext() const { return pos_ < size_; }
Next()1015   void Next() { ++pos_; }
GetTypeIdx()1016   uint16_t GetTypeIdx() {
1017     return type_list_->GetTypeItem(pos_).type_idx_;
1018   }
GetDescriptor()1019   const char* GetDescriptor() {
1020     return dex_file_.StringByTypeIdx(GetTypeIdx());
1021   }
1022  private:
1023   const DexFile& dex_file_;
1024   const DexFile::TypeList* type_list_;
1025   uint32_t size_;
1026   uint32_t pos_;
1027   DISALLOW_IMPLICIT_CONSTRUCTORS(DexFileParameterIterator);
1028 };
1029 
1030 // Abstract the signature of a method.
1031 class Signature {
1032  public:
1033   std::string ToString() const;
1034 
NoSignature()1035   static Signature NoSignature() {
1036     return Signature();
1037   }
1038 
1039   bool operator==(const Signature& rhs) const;
1040   bool operator!=(const Signature& rhs) const {
1041     return !(*this == rhs);
1042   }
1043 
1044   bool operator==(const StringPiece& rhs) const;
1045 
1046  private:
Signature(const DexFile * dex,const DexFile::ProtoId & proto)1047   Signature(const DexFile* dex, const DexFile::ProtoId& proto) : dex_file_(dex), proto_id_(&proto) {
1048   }
1049 
Signature()1050   Signature() : dex_file_(nullptr), proto_id_(nullptr) {
1051   }
1052 
1053   friend class DexFile;
1054 
1055   const DexFile* const dex_file_;
1056   const DexFile::ProtoId* const proto_id_;
1057 };
1058 std::ostream& operator<<(std::ostream& os, const Signature& sig);
1059 
1060 // Iterate and decode class_data_item
1061 class ClassDataItemIterator {
1062  public:
ClassDataItemIterator(const DexFile & dex_file,const byte * raw_class_data_item)1063   ClassDataItemIterator(const DexFile& dex_file, const byte* raw_class_data_item)
1064       : dex_file_(dex_file), pos_(0), ptr_pos_(raw_class_data_item), last_idx_(0) {
1065     ReadClassDataHeader();
1066     if (EndOfInstanceFieldsPos() > 0) {
1067       ReadClassDataField();
1068     } else if (EndOfVirtualMethodsPos() > 0) {
1069       ReadClassDataMethod();
1070     }
1071   }
NumStaticFields()1072   uint32_t NumStaticFields() const {
1073     return header_.static_fields_size_;
1074   }
NumInstanceFields()1075   uint32_t NumInstanceFields() const {
1076     return header_.instance_fields_size_;
1077   }
NumDirectMethods()1078   uint32_t NumDirectMethods() const {
1079     return header_.direct_methods_size_;
1080   }
NumVirtualMethods()1081   uint32_t NumVirtualMethods() const {
1082     return header_.virtual_methods_size_;
1083   }
HasNextStaticField()1084   bool HasNextStaticField() const {
1085     return pos_ < EndOfStaticFieldsPos();
1086   }
HasNextInstanceField()1087   bool HasNextInstanceField() const {
1088     return pos_ >= EndOfStaticFieldsPos() && pos_ < EndOfInstanceFieldsPos();
1089   }
HasNextDirectMethod()1090   bool HasNextDirectMethod() const {
1091     return pos_ >= EndOfInstanceFieldsPos() && pos_ < EndOfDirectMethodsPos();
1092   }
HasNextVirtualMethod()1093   bool HasNextVirtualMethod() const {
1094     return pos_ >= EndOfDirectMethodsPos() && pos_ < EndOfVirtualMethodsPos();
1095   }
HasNext()1096   bool HasNext() const {
1097     return pos_ < EndOfVirtualMethodsPos();
1098   }
Next()1099   inline void Next() {
1100     pos_++;
1101     if (pos_ < EndOfStaticFieldsPos()) {
1102       last_idx_ = GetMemberIndex();
1103       ReadClassDataField();
1104     } else if (pos_ == EndOfStaticFieldsPos() && NumInstanceFields() > 0) {
1105       last_idx_ = 0;  // transition to next array, reset last index
1106       ReadClassDataField();
1107     } else if (pos_ < EndOfInstanceFieldsPos()) {
1108       last_idx_ = GetMemberIndex();
1109       ReadClassDataField();
1110     } else if (pos_ == EndOfInstanceFieldsPos() && NumDirectMethods() > 0) {
1111       last_idx_ = 0;  // transition to next array, reset last index
1112       ReadClassDataMethod();
1113     } else if (pos_ < EndOfDirectMethodsPos()) {
1114       last_idx_ = GetMemberIndex();
1115       ReadClassDataMethod();
1116     } else if (pos_ == EndOfDirectMethodsPos() && NumVirtualMethods() > 0) {
1117       last_idx_ = 0;  // transition to next array, reset last index
1118       ReadClassDataMethod();
1119     } else if (pos_ < EndOfVirtualMethodsPos()) {
1120       last_idx_ = GetMemberIndex();
1121       ReadClassDataMethod();
1122     } else {
1123       DCHECK(!HasNext());
1124     }
1125   }
GetMemberIndex()1126   uint32_t GetMemberIndex() const {
1127     if (pos_ < EndOfInstanceFieldsPos()) {
1128       return last_idx_ + field_.field_idx_delta_;
1129     } else {
1130       DCHECK_LT(pos_, EndOfVirtualMethodsPos());
1131       return last_idx_ + method_.method_idx_delta_;
1132     }
1133   }
GetRawMemberAccessFlags()1134   uint32_t GetRawMemberAccessFlags() const {
1135     if (pos_ < EndOfInstanceFieldsPos()) {
1136       return field_.access_flags_;
1137     } else {
1138       DCHECK_LT(pos_, EndOfVirtualMethodsPos());
1139       return method_.access_flags_;
1140     }
1141   }
GetFieldAccessFlags()1142   uint32_t GetFieldAccessFlags() const {
1143     return GetRawMemberAccessFlags() & kAccValidFieldFlags;
1144   }
GetMethodAccessFlags()1145   uint32_t GetMethodAccessFlags() const {
1146     return GetRawMemberAccessFlags() & kAccValidMethodFlags;
1147   }
MemberIsNative()1148   bool MemberIsNative() const {
1149     return GetRawMemberAccessFlags() & kAccNative;
1150   }
MemberIsFinal()1151   bool MemberIsFinal() const {
1152     return GetRawMemberAccessFlags() & kAccFinal;
1153   }
GetMethodInvokeType(const DexFile::ClassDef & class_def)1154   InvokeType GetMethodInvokeType(const DexFile::ClassDef& class_def) const {
1155     if (HasNextDirectMethod()) {
1156       if ((GetRawMemberAccessFlags() & kAccStatic) != 0) {
1157         return kStatic;
1158       } else {
1159         return kDirect;
1160       }
1161     } else {
1162       DCHECK_EQ(GetRawMemberAccessFlags() & kAccStatic, 0U);
1163       if ((class_def.access_flags_ & kAccInterface) != 0) {
1164         return kInterface;
1165       } else if ((GetRawMemberAccessFlags() & kAccConstructor) != 0) {
1166         return kSuper;
1167       } else {
1168         return kVirtual;
1169       }
1170     }
1171   }
GetMethodCodeItem()1172   const DexFile::CodeItem* GetMethodCodeItem() const {
1173     return dex_file_.GetCodeItem(method_.code_off_);
1174   }
GetMethodCodeItemOffset()1175   uint32_t GetMethodCodeItemOffset() const {
1176     return method_.code_off_;
1177   }
EndDataPointer()1178   const byte* EndDataPointer() const {
1179     CHECK(!HasNext());
1180     return ptr_pos_;
1181   }
1182 
1183  private:
1184   // A dex file's class_data_item is leb128 encoded, this structure holds a decoded form of the
1185   // header for a class_data_item
1186   struct ClassDataHeader {
1187     uint32_t static_fields_size_;  // the number of static fields
1188     uint32_t instance_fields_size_;  // the number of instance fields
1189     uint32_t direct_methods_size_;  // the number of direct methods
1190     uint32_t virtual_methods_size_;  // the number of virtual methods
1191   } header_;
1192 
1193   // Read and decode header from a class_data_item stream into header
1194   void ReadClassDataHeader();
1195 
EndOfStaticFieldsPos()1196   uint32_t EndOfStaticFieldsPos() const {
1197     return header_.static_fields_size_;
1198   }
EndOfInstanceFieldsPos()1199   uint32_t EndOfInstanceFieldsPos() const {
1200     return EndOfStaticFieldsPos() + header_.instance_fields_size_;
1201   }
EndOfDirectMethodsPos()1202   uint32_t EndOfDirectMethodsPos() const {
1203     return EndOfInstanceFieldsPos() + header_.direct_methods_size_;
1204   }
EndOfVirtualMethodsPos()1205   uint32_t EndOfVirtualMethodsPos() const {
1206     return EndOfDirectMethodsPos() + header_.virtual_methods_size_;
1207   }
1208 
1209   // A decoded version of the field of a class_data_item
1210   struct ClassDataField {
1211     uint32_t field_idx_delta_;  // delta of index into the field_ids array for FieldId
1212     uint32_t access_flags_;  // access flags for the field
ClassDataFieldClassDataField1213     ClassDataField() :  field_idx_delta_(0), access_flags_(0) {}
1214 
1215    private:
1216     DISALLOW_COPY_AND_ASSIGN(ClassDataField);
1217   };
1218   ClassDataField field_;
1219 
1220   // Read and decode a field from a class_data_item stream into field
1221   void ReadClassDataField();
1222 
1223   // A decoded version of the method of a class_data_item
1224   struct ClassDataMethod {
1225     uint32_t method_idx_delta_;  // delta of index into the method_ids array for MethodId
1226     uint32_t access_flags_;
1227     uint32_t code_off_;
ClassDataMethodClassDataMethod1228     ClassDataMethod() : method_idx_delta_(0), access_flags_(0), code_off_(0) {}
1229 
1230    private:
1231     DISALLOW_COPY_AND_ASSIGN(ClassDataMethod);
1232   };
1233   ClassDataMethod method_;
1234 
1235   // Read and decode a method from a class_data_item stream into method
1236   void ReadClassDataMethod();
1237 
1238   const DexFile& dex_file_;
1239   size_t pos_;  // integral number of items passed
1240   const byte* ptr_pos_;  // pointer into stream of class_data_item
1241   uint32_t last_idx_;  // last read field or method index to apply delta to
1242   DISALLOW_IMPLICIT_CONSTRUCTORS(ClassDataItemIterator);
1243 };
1244 
1245 class EncodedStaticFieldValueIterator {
1246  public:
1247   EncodedStaticFieldValueIterator(const DexFile& dex_file, Handle<mirror::DexCache>* dex_cache,
1248                                   Handle<mirror::ClassLoader>* class_loader,
1249                                   ClassLinker* linker, const DexFile::ClassDef& class_def)
1250       SHARED_LOCKS_REQUIRED(Locks::mutator_lock_);
1251 
1252   template<bool kTransactionActive>
1253   void ReadValueToField(mirror::ArtField* field) const SHARED_LOCKS_REQUIRED(Locks::mutator_lock_);
1254 
HasNext()1255   bool HasNext() { return pos_ < array_size_; }
1256 
1257   void Next();
1258 
1259   enum ValueType {
1260     kByte = 0x00,
1261     kShort = 0x02,
1262     kChar = 0x03,
1263     kInt = 0x04,
1264     kLong = 0x06,
1265     kFloat = 0x10,
1266     kDouble = 0x11,
1267     kString = 0x17,
1268     kType = 0x18,
1269     kField = 0x19,
1270     kMethod = 0x1a,
1271     kEnum = 0x1b,
1272     kArray = 0x1c,
1273     kAnnotation = 0x1d,
1274     kNull = 0x1e,
1275     kBoolean = 0x1f
1276   };
1277 
1278  private:
1279   static const byte kEncodedValueTypeMask = 0x1f;  // 0b11111
1280   static const byte kEncodedValueArgShift = 5;
1281 
1282   const DexFile& dex_file_;
1283   Handle<mirror::DexCache>* const dex_cache_;  // Dex cache to resolve literal objects.
1284   Handle<mirror::ClassLoader>* const class_loader_;  // ClassLoader to resolve types.
1285   ClassLinker* linker_;  // Linker to resolve literal objects.
1286   size_t array_size_;  // Size of array.
1287   size_t pos_;  // Current position.
1288   const byte* ptr_;  // Pointer into encoded data array.
1289   ValueType type_;  // Type of current encoded value.
1290   jvalue jval_;  // Value of current encoded value.
1291   DISALLOW_IMPLICIT_CONSTRUCTORS(EncodedStaticFieldValueIterator);
1292 };
1293 std::ostream& operator<<(std::ostream& os, const EncodedStaticFieldValueIterator::ValueType& code);
1294 
1295 class CatchHandlerIterator {
1296   public:
1297     CatchHandlerIterator(const DexFile::CodeItem& code_item, uint32_t address);
1298 
1299     CatchHandlerIterator(const DexFile::CodeItem& code_item,
1300                          const DexFile::TryItem& try_item);
1301 
CatchHandlerIterator(const byte * handler_data)1302     explicit CatchHandlerIterator(const byte* handler_data) {
1303       Init(handler_data);
1304     }
1305 
GetHandlerTypeIndex()1306     uint16_t GetHandlerTypeIndex() const {
1307       return handler_.type_idx_;
1308     }
GetHandlerAddress()1309     uint32_t GetHandlerAddress() const {
1310       return handler_.address_;
1311     }
1312     void Next();
HasNext()1313     bool HasNext() const {
1314       return remaining_count_ != -1 || catch_all_;
1315     }
1316     // End of this set of catch blocks, convenience method to locate next set of catch blocks
EndDataPointer()1317     const byte* EndDataPointer() const {
1318       CHECK(!HasNext());
1319       return current_data_;
1320     }
1321 
1322   private:
1323     void Init(const DexFile::CodeItem& code_item, int32_t offset);
1324     void Init(const byte* handler_data);
1325 
1326     struct CatchHandlerItem {
1327       uint16_t type_idx_;  // type index of the caught exception type
1328       uint32_t address_;  // handler address
1329     } handler_;
1330     const byte *current_data_;  // the current handler in dex file.
1331     int32_t remaining_count_;   // number of handlers not read.
1332     bool catch_all_;            // is there a handler that will catch all exceptions in case
1333                                 // that all typed handler does not match.
1334 };
1335 
1336 }  // namespace art
1337 
1338 #endif  // ART_RUNTIME_DEX_FILE_H_
1339