• 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_ART_FIELD_H_
18 #define ART_RUNTIME_ART_FIELD_H_
19 
20 #include "base/macros.h"
21 #include "dex/modifiers.h"
22 #include "dex/primitive.h"
23 #include "gc_root.h"
24 #include "obj_ptr.h"
25 #include "offsets.h"
26 #include "read_barrier_option.h"
27 #include "verify_object.h"
28 
29 namespace art HIDDEN {
30 
31 class DexFile;
32 template<typename T> class LengthPrefixedArray;
33 class ScopedObjectAccessAlreadyRunnable;
34 
35 namespace mirror {
36 class Class;
37 class ClassLoader;
38 class DexCache;
39 class Object;
40 class String;
41 }  // namespace mirror
42 
43 class EXPORT ArtField final {
44  public:
45   // Visit declaring classes of all the art-fields in 'array' that reside
46   // in [start_boundary, end_boundary).
47   template<typename RootVisitorType>
48   static void VisitArrayRoots(RootVisitorType& visitor,
49                               uint8_t* start_boundary,
50                               uint8_t* end_boundary,
51                               LengthPrefixedArray<ArtField>* array)
52       REQUIRES_SHARED(Locks::mutator_lock_);
53 
54   template<ReadBarrierOption kReadBarrierOption = kWithReadBarrier>
55   ObjPtr<mirror::Class> GetDeclaringClass() REQUIRES_SHARED(Locks::mutator_lock_);
56 
57   ObjPtr<mirror::ClassLoader> GetClassLoader() REQUIRES_SHARED(Locks::mutator_lock_);
58 
59   void SetDeclaringClass(ObjPtr<mirror::Class> new_declaring_class)
60       REQUIRES_SHARED(Locks::mutator_lock_);
61 
GetDeclaringClassAddressWithoutBarrier()62   mirror::CompressedReference<mirror::Object>* GetDeclaringClassAddressWithoutBarrier() {
63     return declaring_class_.AddressWithoutBarrier();
64   }
65 
GetAccessFlags()66   uint32_t GetAccessFlags() {
67     return access_flags_;
68   }
69 
SetAccessFlags(uint32_t new_access_flags)70   void SetAccessFlags(uint32_t new_access_flags) {
71     // Not called within a transaction.
72     access_flags_ = new_access_flags;
73   }
74 
IsPublic()75   bool IsPublic() {
76     return (GetAccessFlags() & kAccPublic) != 0;
77   }
78 
IsStatic()79   bool IsStatic() {
80     return (GetAccessFlags() & kAccStatic) != 0;
81   }
82 
IsFinal()83   bool IsFinal() {
84     return (GetAccessFlags() & kAccFinal) != 0;
85   }
86 
IsPrivate()87   bool IsPrivate() {
88     return (GetAccessFlags() & kAccPrivate) != 0;
89   }
90 
GetDexFieldIndex()91   uint32_t GetDexFieldIndex() {
92     return field_dex_idx_;
93   }
94 
SetDexFieldIndex(uint32_t new_idx)95   void SetDexFieldIndex(uint32_t new_idx) {
96     // Not called within a transaction.
97     field_dex_idx_ = new_idx;
98   }
99 
100   // Offset to field within an Object.
GetOffset()101   MemberOffset GetOffset() {
102     return MemberOffset(offset_);
103   }
104 
OffsetOffset()105   static constexpr MemberOffset OffsetOffset() {
106     return MemberOffset(OFFSETOF_MEMBER(ArtField, offset_));
107   }
108 
DeclaringClassOffset()109   static constexpr MemberOffset DeclaringClassOffset() {
110     return MemberOffset(OFFSETOF_MEMBER(ArtField, declaring_class_));
111   }
112 
113   MemberOffset GetOffsetDuringLinking() REQUIRES_SHARED(Locks::mutator_lock_);
114 
115   void SetOffset(MemberOffset num_bytes) REQUIRES_SHARED(Locks::mutator_lock_);
116 
117   // field access, null object for static fields
118   uint8_t GetBoolean(ObjPtr<mirror::Object> object) REQUIRES_SHARED(Locks::mutator_lock_);
119 
120   template<bool kTransactionActive>
121   void SetBoolean(ObjPtr<mirror::Object> object, uint8_t z) REQUIRES_SHARED(Locks::mutator_lock_);
122 
123   int8_t GetByte(ObjPtr<mirror::Object> object) REQUIRES_SHARED(Locks::mutator_lock_);
124 
125   template<bool kTransactionActive>
126   void SetByte(ObjPtr<mirror::Object> object, int8_t b) REQUIRES_SHARED(Locks::mutator_lock_);
127 
128   uint16_t GetChar(ObjPtr<mirror::Object> object) REQUIRES_SHARED(Locks::mutator_lock_);
129   uint16_t GetCharacter(ObjPtr<mirror::Object> object) REQUIRES_SHARED(Locks::mutator_lock_);
130 
131   template<bool kTransactionActive>
132   void SetChar(ObjPtr<mirror::Object> object, uint16_t c) REQUIRES_SHARED(Locks::mutator_lock_);
133 
134   int16_t GetShort(ObjPtr<mirror::Object> object) REQUIRES_SHARED(Locks::mutator_lock_);
135 
136   template<bool kTransactionActive>
137   void SetShort(ObjPtr<mirror::Object> object, int16_t s) REQUIRES_SHARED(Locks::mutator_lock_);
138 
139   int32_t GetInt(ObjPtr<mirror::Object> object) REQUIRES_SHARED(Locks::mutator_lock_);
140   int32_t GetInteger(ObjPtr<mirror::Object> object) REQUIRES_SHARED(Locks::mutator_lock_);
141 
142   template<bool kTransactionActive>
143   void SetInt(ObjPtr<mirror::Object> object, int32_t i) REQUIRES_SHARED(Locks::mutator_lock_);
144 
145   int64_t GetLong(ObjPtr<mirror::Object> object) REQUIRES_SHARED(Locks::mutator_lock_);
146 
147   template<bool kTransactionActive>
148   void SetLong(ObjPtr<mirror::Object> object, int64_t j) REQUIRES_SHARED(Locks::mutator_lock_);
149 
150   float GetFloat(ObjPtr<mirror::Object> object) REQUIRES_SHARED(Locks::mutator_lock_);
151 
152   template<bool kTransactionActive>
153   void SetFloat(ObjPtr<mirror::Object> object, float f) REQUIRES_SHARED(Locks::mutator_lock_);
154 
155   double GetDouble(ObjPtr<mirror::Object> object) REQUIRES_SHARED(Locks::mutator_lock_);
156 
157   template<bool kTransactionActive>
158   void SetDouble(ObjPtr<mirror::Object> object, double d) REQUIRES_SHARED(Locks::mutator_lock_);
159 
160   template<ReadBarrierOption kReadBarrierOption = kWithReadBarrier>
161   ObjPtr<mirror::Object> GetObject(ObjPtr<mirror::Object> object)
162       REQUIRES_SHARED(Locks::mutator_lock_);
163 
164   template<bool kTransactionActive>
165   void SetObject(ObjPtr<mirror::Object> object, ObjPtr<mirror::Object> l)
166       REQUIRES_SHARED(Locks::mutator_lock_);
167 
168   // Raw field accesses.
169   uint32_t Get32(ObjPtr<mirror::Object> object) REQUIRES_SHARED(Locks::mutator_lock_);
170 
171   template<bool kTransactionActive>
172   void Set32(ObjPtr<mirror::Object> object, uint32_t new_value)
173       REQUIRES_SHARED(Locks::mutator_lock_);
174 
175   uint64_t Get64(ObjPtr<mirror::Object> object) REQUIRES_SHARED(Locks::mutator_lock_);
176 
177   template<bool kTransactionActive>
178   void Set64(ObjPtr<mirror::Object> object, uint64_t new_value)
179       REQUIRES_SHARED(Locks::mutator_lock_);
180 
181   template<class MirrorType = mirror::Object,
182            ReadBarrierOption kReadBarrierOption = kWithReadBarrier>
183   ObjPtr<MirrorType> GetObj(ObjPtr<mirror::Object> object)
184       REQUIRES_SHARED(Locks::mutator_lock_);
185 
186   template<bool kTransactionActive>
187   void SetObj(ObjPtr<mirror::Object> object, ObjPtr<mirror::Object> new_value)
188       REQUIRES_SHARED(Locks::mutator_lock_);
189 
190   // NO_THREAD_SAFETY_ANALYSIS since we don't know what the callback requires.
191   template<typename RootVisitorType>
VisitRoots(RootVisitorType & visitor)192   ALWAYS_INLINE inline void VisitRoots(RootVisitorType& visitor) NO_THREAD_SAFETY_ANALYSIS {
193     visitor.VisitRoot(declaring_class_.AddressWithoutBarrier());
194   }
195 
IsVolatile()196   bool IsVolatile() {
197     return (GetAccessFlags() & kAccVolatile) != 0;
198   }
199 
200   // Returns an instance field with this offset in the given class or null if not found.
201   // If kExactOffset is true then we only find the matching offset, not the field containing the
202   // offset.
203   template <bool kExactOffset = true,
204             VerifyObjectFlags kVerifyFlags = kDefaultVerifyFlags,
205             ReadBarrierOption kReadBarrierOption = kWithReadBarrier>
206   static ArtField* FindInstanceFieldWithOffset(ObjPtr<mirror::Class> klass, uint32_t field_offset)
207       REQUIRES_SHARED(Locks::mutator_lock_);
208 
209   // Returns a static field with this offset in the given class or null if not found.
210   // If kExactOffset is true then we only find the matching offset, not the field containing the
211   // offset.
212   template <bool kExactOffset = true>
213   static ArtField* FindStaticFieldWithOffset(ObjPtr<mirror::Class> klass, uint32_t field_offset)
214       REQUIRES_SHARED(Locks::mutator_lock_);
215 
216   const char* GetName() REQUIRES_SHARED(Locks::mutator_lock_);
217   std::string_view GetNameView() REQUIRES_SHARED(Locks::mutator_lock_);
218 
219   // Resolves / returns the name from the dex cache.
220   ObjPtr<mirror::String> ResolveNameString() REQUIRES_SHARED(Locks::mutator_lock_);
221 
222   const char* GetTypeDescriptor() REQUIRES_SHARED(Locks::mutator_lock_);
223   std::string_view GetTypeDescriptorView() REQUIRES_SHARED(Locks::mutator_lock_);
224 
225   Primitive::Type GetTypeAsPrimitiveType() REQUIRES_SHARED(Locks::mutator_lock_);
226 
227   bool IsPrimitiveType() REQUIRES_SHARED(Locks::mutator_lock_);
228 
229   ObjPtr<mirror::Class> LookupResolvedType() REQUIRES_SHARED(Locks::mutator_lock_);
230   ObjPtr<mirror::Class> ResolveType() REQUIRES_SHARED(Locks::mutator_lock_);
231 
232   size_t FieldSize() REQUIRES_SHARED(Locks::mutator_lock_);
233 
234   template <ReadBarrierOption kReadBarrierOption = kWithReadBarrier>
235   ObjPtr<mirror::DexCache> GetDexCache() REQUIRES_SHARED(Locks::mutator_lock_);
236 
237   const DexFile* GetDexFile() REQUIRES_SHARED(Locks::mutator_lock_);
238 
239   const char* GetDeclaringClassDescriptor() REQUIRES_SHARED(Locks::mutator_lock_);
240   std::string_view GetDeclaringClassDescriptorView() REQUIRES_SHARED(Locks::mutator_lock_);
241 
DeclaringClassRoot()242   GcRoot<mirror::Class>& DeclaringClassRoot() {
243     return declaring_class_;
244   }
245 
246   // Returns a human-readable signature. Something like "a.b.C.f" or
247   // "int a.b.C.f" (depending on the value of 'with_type').
248   static std::string PrettyField(ArtField* f, bool with_type = true)
249       REQUIRES_SHARED(Locks::mutator_lock_);
250   std::string PrettyField(bool with_type = true)
251       REQUIRES_SHARED(Locks::mutator_lock_);
252 
253   // Returns true if a set-* instruction in the given method is allowable.
254   ALWAYS_INLINE inline bool CanBeChangedBy(ArtMethod* method) REQUIRES_SHARED(Locks::mutator_lock_);
255 
256  private:
257   bool IsProxyField() REQUIRES_SHARED(Locks::mutator_lock_);
258 
259   ObjPtr<mirror::Class> ProxyFindSystemClass(const char* descriptor)
260       REQUIRES_SHARED(Locks::mutator_lock_);
261 
262   GcRoot<mirror::Class> declaring_class_;
263 
264   uint32_t access_flags_ = 0;
265 
266   // Dex cache index of field id
267   uint32_t field_dex_idx_ = 0;
268 
269   // Offset of field within an instance or in the Class' static fields
270   uint32_t offset_ = 0;
271 };
272 
273 }  // namespace art
274 
275 #endif  // ART_RUNTIME_ART_FIELD_H_
276