1 /*
2  * Copyright (C) 2008 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 #include "java_lang_reflect_Field.h"
18 
19 #include "android-base/stringprintf.h"
20 #include "nativehelper/jni_macros.h"
21 
22 #include "art_field-inl.h"
23 #include "base/utils.h"
24 #include "class_linker-inl.h"
25 #include "class_linker.h"
26 #include "common_throws.h"
27 #include "dex/dex_file-inl.h"
28 #include "dex/dex_file_annotations.h"
29 #include "jni/jni_internal.h"
30 #include "jvalue-inl.h"
31 #include "mirror/class-inl.h"
32 #include "mirror/field-inl.h"
33 #include "mirror/object_array-alloc-inl.h"
34 #include "native_util.h"
35 #include "reflection-inl.h"
36 #include "scoped_fast_native_object_access-inl.h"
37 #include "well_known_classes.h"
38 
39 namespace art {
40 
41 using android::base::StringPrintf;
42 
43 template<bool kIsSet>
VerifyFieldAccess(Thread * self,ObjPtr<mirror::Field> field,ObjPtr<mirror::Object> obj)44 ALWAYS_INLINE inline static bool VerifyFieldAccess(Thread* self,
45                                                    ObjPtr<mirror::Field> field,
46                                                    ObjPtr<mirror::Object> obj)
47     REQUIRES_SHARED(Locks::mutator_lock_) {
48   if (kIsSet && field->IsFinal()) {
49     ThrowIllegalAccessException(
50             StringPrintf("Cannot set %s field %s of class %s",
51                 PrettyJavaAccessFlags(field->GetAccessFlags()).c_str(),
52                 ArtField::PrettyField(field->GetArtField()).c_str(),
53                 field->GetDeclaringClass() == nullptr ? "null" :
54                     field->GetDeclaringClass()->PrettyClass().c_str()).c_str());
55     return false;
56   }
57   ObjPtr<mirror::Class> calling_class;
58   if (!VerifyAccess(self,
59                     obj,
60                     field->GetDeclaringClass(),
61                     field->GetAccessFlags(),
62                     &calling_class,
63                     1)) {
64     ThrowIllegalAccessException(
65             StringPrintf("Class %s cannot access %s field %s of class %s",
66                 calling_class == nullptr ? "null" : calling_class->PrettyClass().c_str(),
67                 PrettyJavaAccessFlags(field->GetAccessFlags()).c_str(),
68                 ArtField::PrettyField(field->GetArtField()).c_str(),
69                 field->GetDeclaringClass() == nullptr ? "null" :
70                     field->GetDeclaringClass()->PrettyClass().c_str()).c_str());
71     return false;
72   }
73   return true;
74 }
75 
76 template<bool kAllowReferences>
GetFieldValue(ObjPtr<mirror::Object> o,ObjPtr<mirror::Field> f,Primitive::Type field_type,JValue * value)77 ALWAYS_INLINE inline static bool GetFieldValue(ObjPtr<mirror::Object> o,
78                                                ObjPtr<mirror::Field> f,
79                                                Primitive::Type field_type,
80                                                JValue* value)
81     REQUIRES_SHARED(Locks::mutator_lock_) {
82   DCHECK_EQ(value->GetJ(), INT64_C(0));
83   MemberOffset offset(f->GetOffset());
84   const bool is_volatile = f->IsVolatile();
85   switch (field_type) {
86     case Primitive::kPrimBoolean:
87       value->SetZ(is_volatile ? o->GetFieldBooleanVolatile(offset) : o->GetFieldBoolean(offset));
88       return true;
89     case Primitive::kPrimByte:
90       value->SetB(is_volatile ? o->GetFieldByteVolatile(offset) : o->GetFieldByte(offset));
91       return true;
92     case Primitive::kPrimChar:
93       value->SetC(is_volatile ? o->GetFieldCharVolatile(offset) : o->GetFieldChar(offset));
94       return true;
95     case Primitive::kPrimInt:
96     case Primitive::kPrimFloat:
97       value->SetI(is_volatile ? o->GetField32Volatile(offset) : o->GetField32(offset));
98       return true;
99     case Primitive::kPrimLong:
100     case Primitive::kPrimDouble:
101       value->SetJ(is_volatile ? o->GetField64Volatile(offset) : o->GetField64(offset));
102       return true;
103     case Primitive::kPrimShort:
104       value->SetS(is_volatile ? o->GetFieldShortVolatile(offset) : o->GetFieldShort(offset));
105       return true;
106     case Primitive::kPrimNot:
107       if (kAllowReferences) {
108         value->SetL(is_volatile ? o->GetFieldObjectVolatile<mirror::Object>(offset) :
109             o->GetFieldObject<mirror::Object>(offset));
110         return true;
111       }
112       // Else break to report an error.
113       break;
114     case Primitive::kPrimVoid:
115       // Never okay.
116       break;
117   }
118   ThrowIllegalArgumentException(
119       StringPrintf("Not a primitive field: %s",
120                    ArtField::PrettyField(f->GetArtField()).c_str()).c_str());
121   return false;
122 }
123 
CheckReceiver(const ScopedFastNativeObjectAccess & soa,jobject j_rcvr,ObjPtr<mirror::Field> * f,ObjPtr<mirror::Object> * class_or_rcvr)124 ALWAYS_INLINE inline static bool CheckReceiver(const ScopedFastNativeObjectAccess& soa,
125                                                jobject j_rcvr,
126                                                ObjPtr<mirror::Field>* f,
127                                                ObjPtr<mirror::Object>* class_or_rcvr)
128     REQUIRES_SHARED(Locks::mutator_lock_) {
129   soa.Self()->AssertThreadSuspensionIsAllowable();
130   ObjPtr<mirror::Class> declaring_class = (*f)->GetDeclaringClass();
131   if ((*f)->IsStatic()) {
132     if (UNLIKELY(!declaring_class->IsVisiblyInitialized())) {
133       Thread* self = soa.Self();
134       StackHandleScope<2> hs(self);
135       HandleWrapperObjPtr<mirror::Field> h_f(hs.NewHandleWrapper(f));
136       HandleWrapperObjPtr<mirror::Class> h_klass(hs.NewHandleWrapper(&declaring_class));
137       if (UNLIKELY(!Runtime::Current()->GetClassLinker()->EnsureInitialized(
138                         self, h_klass, /*can_init_fields=*/ true, /*can_init_parents=*/ true))) {
139         DCHECK(self->IsExceptionPending());
140         return false;
141       }
142       DCHECK(h_klass->IsInitializing());
143     }
144     *class_or_rcvr = declaring_class;
145     return true;
146   }
147   *class_or_rcvr = soa.Decode<mirror::Object>(j_rcvr);
148   if (!VerifyObjectIsClass(*class_or_rcvr, declaring_class)) {
149     DCHECK(soa.Self()->IsExceptionPending());
150     return false;
151   }
152   return true;
153 }
154 
Field_get(JNIEnv * env,jobject javaField,jobject javaObj)155 static jobject Field_get(JNIEnv* env, jobject javaField, jobject javaObj) {
156   ScopedFastNativeObjectAccess soa(env);
157   ObjPtr<mirror::Field> f = soa.Decode<mirror::Field>(javaField);
158   ObjPtr<mirror::Object> o;
159   if (!CheckReceiver(soa, javaObj, &f, &o)) {
160     DCHECK(soa.Self()->IsExceptionPending());
161     return nullptr;
162   }
163   // If field is not set to be accessible, verify it can be accessed by the caller.
164   if (!f->IsAccessible() && !VerifyFieldAccess<false>(soa.Self(), f, o)) {
165     DCHECK(soa.Self()->IsExceptionPending());
166     return nullptr;
167   }
168   // We now don't expect suspension unless an exception is thrown.
169   // Get the field's value, boxing if necessary.
170   Primitive::Type field_type = f->GetTypeAsPrimitiveType();
171   JValue value;
172   if (!GetFieldValue<true>(o, f, field_type, &value)) {
173     DCHECK(soa.Self()->IsExceptionPending());
174     return nullptr;
175   }
176   return soa.AddLocalReference<jobject>(BoxPrimitive(field_type, value));
177 }
178 
179 template<Primitive::Type kPrimitiveType>
GetPrimitiveField(JNIEnv * env,jobject javaField,jobject javaObj)180 ALWAYS_INLINE inline static JValue GetPrimitiveField(JNIEnv* env,
181                                                      jobject javaField,
182                                                      jobject javaObj) {
183   ScopedFastNativeObjectAccess soa(env);
184   ObjPtr<mirror::Field> f = soa.Decode<mirror::Field>(javaField);
185   ObjPtr<mirror::Object> o;
186   if (!CheckReceiver(soa, javaObj, &f, &o)) {
187     DCHECK(soa.Self()->IsExceptionPending());
188     return JValue();
189   }
190 
191   // If field is not set to be accessible, verify it can be accessed by the caller.
192   if (!f->IsAccessible() && !VerifyFieldAccess<false>(soa.Self(), f, o)) {
193     DCHECK(soa.Self()->IsExceptionPending());
194     return JValue();
195   }
196 
197   // We now don't expect suspension unless an exception is thrown.
198   // Read the value.
199   Primitive::Type field_type = f->GetTypeAsPrimitiveType();
200   JValue field_value;
201   if (field_type == kPrimitiveType) {
202     // This if statement should get optimized out since we only pass in valid primitive types.
203     if (UNLIKELY(!GetFieldValue<false>(o, f, kPrimitiveType, &field_value))) {
204       DCHECK(soa.Self()->IsExceptionPending());
205       return JValue();
206     }
207     return field_value;
208   }
209   if (!GetFieldValue<false>(o, f, field_type, &field_value)) {
210     DCHECK(soa.Self()->IsExceptionPending());
211     return JValue();
212   }
213   // Widen it if necessary (and possible).
214   JValue wide_value;
215   if (!ConvertPrimitiveValue(false, field_type, kPrimitiveType, field_value,
216                              &wide_value)) {
217     DCHECK(soa.Self()->IsExceptionPending());
218     return JValue();
219   }
220   return wide_value;
221 }
222 
Field_getBoolean(JNIEnv * env,jobject javaField,jobject javaObj)223 static jboolean Field_getBoolean(JNIEnv* env, jobject javaField, jobject javaObj) {
224   return GetPrimitiveField<Primitive::kPrimBoolean>(env, javaField, javaObj).GetZ();
225 }
226 
Field_getByte(JNIEnv * env,jobject javaField,jobject javaObj)227 static jbyte Field_getByte(JNIEnv* env, jobject javaField, jobject javaObj) {
228   return GetPrimitiveField<Primitive::kPrimByte>(env, javaField, javaObj).GetB();
229 }
230 
Field_getChar(JNIEnv * env,jobject javaField,jobject javaObj)231 static jchar Field_getChar(JNIEnv* env, jobject javaField, jobject javaObj) {
232   return GetPrimitiveField<Primitive::kPrimChar>(env, javaField, javaObj).GetC();
233 }
234 
Field_getDouble(JNIEnv * env,jobject javaField,jobject javaObj)235 static jdouble Field_getDouble(JNIEnv* env, jobject javaField, jobject javaObj) {
236   return GetPrimitiveField<Primitive::kPrimDouble>(env, javaField, javaObj).GetD();
237 }
238 
Field_getFloat(JNIEnv * env,jobject javaField,jobject javaObj)239 static jfloat Field_getFloat(JNIEnv* env, jobject javaField, jobject javaObj) {
240   return GetPrimitiveField<Primitive::kPrimFloat>(env, javaField, javaObj).GetF();
241 }
242 
Field_getInt(JNIEnv * env,jobject javaField,jobject javaObj)243 static jint Field_getInt(JNIEnv* env, jobject javaField, jobject javaObj) {
244   return GetPrimitiveField<Primitive::kPrimInt>(env, javaField, javaObj).GetI();
245 }
246 
Field_getLong(JNIEnv * env,jobject javaField,jobject javaObj)247 static jlong Field_getLong(JNIEnv* env, jobject javaField, jobject javaObj) {
248   return GetPrimitiveField<Primitive::kPrimLong>(env, javaField, javaObj).GetJ();
249 }
250 
Field_getShort(JNIEnv * env,jobject javaField,jobject javaObj)251 static jshort Field_getShort(JNIEnv* env, jobject javaField, jobject javaObj) {
252   return GetPrimitiveField<Primitive::kPrimShort>(env, javaField, javaObj).GetS();
253 }
254 
SetFieldValue(ObjPtr<mirror::Object> o,ObjPtr<mirror::Field> f,Primitive::Type field_type,bool allow_references,const JValue & new_value)255 ALWAYS_INLINE inline static void SetFieldValue(ObjPtr<mirror::Object> o,
256                                                ObjPtr<mirror::Field> f,
257                                                Primitive::Type field_type,
258                                                bool allow_references,
259                                                const JValue& new_value)
260     REQUIRES_SHARED(Locks::mutator_lock_) {
261   DCHECK(f->GetDeclaringClass()->IsInitializing());
262   MemberOffset offset(f->GetOffset());
263   const bool is_volatile = f->IsVolatile();
264   switch (field_type) {
265   case Primitive::kPrimBoolean:
266     if (is_volatile) {
267       o->SetFieldBooleanVolatile<false>(offset, new_value.GetZ());
268     } else {
269       o->SetFieldBoolean<false>(offset, new_value.GetZ());
270     }
271     break;
272   case Primitive::kPrimByte:
273     if (is_volatile) {
274       o->SetFieldBooleanVolatile<false>(offset, new_value.GetB());
275     } else {
276       o->SetFieldBoolean<false>(offset, new_value.GetB());
277     }
278     break;
279   case Primitive::kPrimChar:
280     if (is_volatile) {
281       o->SetFieldCharVolatile<false>(offset, new_value.GetC());
282     } else {
283       o->SetFieldChar<false>(offset, new_value.GetC());
284     }
285     break;
286   case Primitive::kPrimInt:
287   case Primitive::kPrimFloat:
288     if (is_volatile) {
289       o->SetField32Volatile<false>(offset, new_value.GetI());
290     } else {
291       o->SetField32<false>(offset, new_value.GetI());
292     }
293     break;
294   case Primitive::kPrimLong:
295   case Primitive::kPrimDouble:
296     if (is_volatile) {
297       o->SetField64Volatile<false>(offset, new_value.GetJ());
298     } else {
299       o->SetField64<false>(offset, new_value.GetJ());
300     }
301     break;
302   case Primitive::kPrimShort:
303     if (is_volatile) {
304       o->SetFieldShortVolatile<false>(offset, new_value.GetS());
305     } else {
306       o->SetFieldShort<false>(offset, new_value.GetS());
307     }
308     break;
309   case Primitive::kPrimNot:
310     if (allow_references) {
311       if (is_volatile) {
312         o->SetFieldObjectVolatile<false>(offset, new_value.GetL());
313       } else {
314         o->SetFieldObject<false>(offset, new_value.GetL());
315       }
316       break;
317     }
318     // Else fall through to report an error.
319     FALLTHROUGH_INTENDED;
320   case Primitive::kPrimVoid:
321     // Never okay.
322     ThrowIllegalArgumentException(
323         StringPrintf("Not a primitive field: %s",
324                      ArtField::PrettyField(f->GetArtField()).c_str()).c_str());
325     return;
326   }
327 }
328 
Field_set(JNIEnv * env,jobject javaField,jobject javaObj,jobject javaValue)329 static void Field_set(JNIEnv* env, jobject javaField, jobject javaObj, jobject javaValue) {
330   ScopedFastNativeObjectAccess soa(env);
331   ObjPtr<mirror::Field> f = soa.Decode<mirror::Field>(javaField);
332   // Check that the receiver is non-null and an instance of the field's declaring class.
333   ObjPtr<mirror::Object> o;
334   if (!CheckReceiver(soa, javaObj, &f, &o)) {
335     DCHECK(soa.Self()->IsExceptionPending());
336     return;
337   }
338   ObjPtr<mirror::Class> field_type;
339   const char* field_type_descriptor = f->GetArtField()->GetTypeDescriptor();
340   Primitive::Type field_prim_type = Primitive::GetType(field_type_descriptor[0]);
341   if (field_prim_type == Primitive::kPrimNot) {
342     field_type = f->GetType();
343   } else {
344     field_type =
345         Runtime::Current()->GetClassLinker()->LookupPrimitiveClass(field_type_descriptor[0]);
346   }
347   DCHECK(field_type != nullptr) << field_type_descriptor;
348   // We now don't expect suspension unless an exception is thrown.
349   // Unbox the value, if necessary.
350   ObjPtr<mirror::Object> boxed_value = soa.Decode<mirror::Object>(javaValue);
351   JValue unboxed_value;
352   if (!UnboxPrimitiveForField(boxed_value,
353                               field_type,
354                               f->GetArtField(),
355                               &unboxed_value)) {
356     DCHECK(soa.Self()->IsExceptionPending());
357     return;
358   }
359   // If field is not set to be accessible, verify it can be accessed by the caller.
360   if (!f->IsAccessible() && !VerifyFieldAccess<true>(soa.Self(), f, o)) {
361     DCHECK(soa.Self()->IsExceptionPending());
362     return;
363   }
364   SetFieldValue(o, f, field_prim_type, true, unboxed_value);
365 }
366 
367 template<Primitive::Type kPrimitiveType>
SetPrimitiveField(JNIEnv * env,jobject javaField,jobject javaObj,const JValue & new_value)368 static void SetPrimitiveField(JNIEnv* env,
369                               jobject javaField,
370                               jobject javaObj,
371                               const JValue& new_value) {
372   ScopedFastNativeObjectAccess soa(env);
373   ObjPtr<mirror::Field> f = soa.Decode<mirror::Field>(javaField);
374   ObjPtr<mirror::Object> o;
375   if (!CheckReceiver(soa, javaObj, &f, &o)) {
376     return;
377   }
378   Primitive::Type field_type = f->GetTypeAsPrimitiveType();
379   if (UNLIKELY(field_type == Primitive::kPrimNot)) {
380     ThrowIllegalArgumentException(
381         StringPrintf("Not a primitive field: %s",
382                      ArtField::PrettyField(f->GetArtField()).c_str()).c_str());
383     return;
384   }
385 
386   // Widen the value if necessary (and possible).
387   JValue wide_value;
388   if (!ConvertPrimitiveValue(false, kPrimitiveType, field_type, new_value, &wide_value)) {
389     DCHECK(soa.Self()->IsExceptionPending());
390     return;
391   }
392 
393   // If field is not set to be accessible, verify it can be accessed by the caller.
394   if (!f->IsAccessible() && !VerifyFieldAccess<true>(soa.Self(), f, o)) {
395     DCHECK(soa.Self()->IsExceptionPending());
396     return;
397   }
398 
399   // Write the value.
400   SetFieldValue(o, f, field_type, false, wide_value);
401 }
402 
Field_setBoolean(JNIEnv * env,jobject javaField,jobject javaObj,jboolean z)403 static void Field_setBoolean(JNIEnv* env, jobject javaField, jobject javaObj, jboolean z) {
404   JValue value;
405   value.SetZ(z);
406   SetPrimitiveField<Primitive::kPrimBoolean>(env, javaField, javaObj, value);
407 }
408 
Field_setByte(JNIEnv * env,jobject javaField,jobject javaObj,jbyte b)409 static void Field_setByte(JNIEnv* env, jobject javaField, jobject javaObj, jbyte b) {
410   JValue value;
411   value.SetB(b);
412   SetPrimitiveField<Primitive::kPrimByte>(env, javaField, javaObj, value);
413 }
414 
Field_setChar(JNIEnv * env,jobject javaField,jobject javaObj,jchar c)415 static void Field_setChar(JNIEnv* env, jobject javaField, jobject javaObj, jchar c) {
416   JValue value;
417   value.SetC(c);
418   SetPrimitiveField<Primitive::kPrimChar>(env, javaField, javaObj, value);
419 }
420 
Field_setDouble(JNIEnv * env,jobject javaField,jobject javaObj,jdouble d)421 static void Field_setDouble(JNIEnv* env, jobject javaField, jobject javaObj, jdouble d) {
422   JValue value;
423   value.SetD(d);
424   SetPrimitiveField<Primitive::kPrimDouble>(env, javaField, javaObj, value);
425 }
426 
Field_setFloat(JNIEnv * env,jobject javaField,jobject javaObj,jfloat f)427 static void Field_setFloat(JNIEnv* env, jobject javaField, jobject javaObj, jfloat f) {
428   JValue value;
429   value.SetF(f);
430   SetPrimitiveField<Primitive::kPrimFloat>(env, javaField, javaObj, value);
431 }
432 
Field_setInt(JNIEnv * env,jobject javaField,jobject javaObj,jint i)433 static void Field_setInt(JNIEnv* env, jobject javaField, jobject javaObj, jint i) {
434   JValue value;
435   value.SetI(i);
436   SetPrimitiveField<Primitive::kPrimInt>(env, javaField, javaObj, value);
437 }
438 
Field_setLong(JNIEnv * env,jobject javaField,jobject javaObj,jlong j)439 static void Field_setLong(JNIEnv* env, jobject javaField, jobject javaObj, jlong j) {
440   JValue value;
441   value.SetJ(j);
442   SetPrimitiveField<Primitive::kPrimLong>(env, javaField, javaObj, value);
443 }
444 
Field_setShort(JNIEnv * env,jobject javaField,jobject javaObj,jshort s)445 static void Field_setShort(JNIEnv* env, jobject javaField, jobject javaObj, jshort s) {
446   JValue value;
447   value.SetS(s);
448   SetPrimitiveField<Primitive::kPrimShort>(env, javaField, javaObj, value);
449 }
450 
Field_getAnnotationNative(JNIEnv * env,jobject javaField,jclass annotationType)451 static jobject Field_getAnnotationNative(JNIEnv* env, jobject javaField, jclass annotationType) {
452   ScopedFastNativeObjectAccess soa(env);
453   StackHandleScope<1> hs(soa.Self());
454   ArtField* field = soa.Decode<mirror::Field>(javaField)->GetArtField();
455   if (field->GetDeclaringClass()->IsProxyClass()) {
456     return nullptr;
457   }
458   Handle<mirror::Class> klass(hs.NewHandle(soa.Decode<mirror::Class>(annotationType)));
459   return soa.AddLocalReference<jobject>(annotations::GetAnnotationForField(field, klass));
460 }
461 
Field_getArtField(JNIEnv * env,jobject javaField)462 static jlong Field_getArtField(JNIEnv* env, jobject javaField) {
463   ScopedFastNativeObjectAccess soa(env);
464   ArtField* field = soa.Decode<mirror::Field>(javaField)->GetArtField();
465   return reinterpret_cast<jlong>(field);
466 }
467 
Field_getNameInternal(JNIEnv * env,jobject javaField)468 static jstring Field_getNameInternal(JNIEnv* env, jobject javaField) {
469   ScopedFastNativeObjectAccess soa(env);
470   ArtField* field = soa.Decode<mirror::Field>(javaField)->GetArtField();
471   return soa.AddLocalReference<jstring>(field->ResolveNameString());
472 }
473 
Field_getDeclaredAnnotations(JNIEnv * env,jobject javaField)474 static jobjectArray Field_getDeclaredAnnotations(JNIEnv* env, jobject javaField) {
475   ScopedFastNativeObjectAccess soa(env);
476   ArtField* field = soa.Decode<mirror::Field>(javaField)->GetArtField();
477   if (field->GetDeclaringClass()->IsProxyClass()) {
478     // Return an empty array instead of a null pointer.
479     ObjPtr<mirror::Class> annotation_array_class =
480         soa.Decode<mirror::Class>(WellKnownClasses::java_lang_annotation_Annotation__array);
481     ObjPtr<mirror::ObjectArray<mirror::Object>> empty_array =
482         mirror::ObjectArray<mirror::Object>::Alloc(soa.Self(), annotation_array_class, 0);
483     return soa.AddLocalReference<jobjectArray>(empty_array);
484   }
485   return soa.AddLocalReference<jobjectArray>(annotations::GetAnnotationsForField(field));
486 }
487 
Field_getSignatureAnnotation(JNIEnv * env,jobject javaField)488 static jobjectArray Field_getSignatureAnnotation(JNIEnv* env, jobject javaField) {
489   ScopedFastNativeObjectAccess soa(env);
490   ArtField* field = soa.Decode<mirror::Field>(javaField)->GetArtField();
491   if (field->GetDeclaringClass()->IsProxyClass()) {
492     return nullptr;
493   }
494   return soa.AddLocalReference<jobjectArray>(annotations::GetSignatureAnnotationForField(field));
495 }
496 
Field_isAnnotationPresentNative(JNIEnv * env,jobject javaField,jclass annotationType)497 static jboolean Field_isAnnotationPresentNative(JNIEnv* env,
498                                                 jobject javaField,
499                                                 jclass annotationType) {
500   ScopedFastNativeObjectAccess soa(env);
501   StackHandleScope<1> hs(soa.Self());
502   ArtField* field = soa.Decode<mirror::Field>(javaField)->GetArtField();
503   if (field->GetDeclaringClass()->IsProxyClass()) {
504     return false;
505   }
506   Handle<mirror::Class> klass(hs.NewHandle(soa.Decode<mirror::Class>(annotationType)));
507   return annotations::IsFieldAnnotationPresent(field, klass);
508 }
509 
510 static JNINativeMethod gMethods[] = {
511   FAST_NATIVE_METHOD(Field, get,        "(Ljava/lang/Object;)Ljava/lang/Object;"),
512   FAST_NATIVE_METHOD(Field, getBoolean, "(Ljava/lang/Object;)Z"),
513   FAST_NATIVE_METHOD(Field, getByte,    "(Ljava/lang/Object;)B"),
514   FAST_NATIVE_METHOD(Field, getChar,    "(Ljava/lang/Object;)C"),
515   FAST_NATIVE_METHOD(Field, getAnnotationNative,
516                 "(Ljava/lang/Class;)Ljava/lang/annotation/Annotation;"),
517   FAST_NATIVE_METHOD(Field, getArtField, "()J"),
518   FAST_NATIVE_METHOD(Field, getDeclaredAnnotations, "()[Ljava/lang/annotation/Annotation;"),
519   FAST_NATIVE_METHOD(Field, getSignatureAnnotation, "()[Ljava/lang/String;"),
520   FAST_NATIVE_METHOD(Field, getDouble,  "(Ljava/lang/Object;)D"),
521   FAST_NATIVE_METHOD(Field, getFloat,   "(Ljava/lang/Object;)F"),
522   FAST_NATIVE_METHOD(Field, getInt,     "(Ljava/lang/Object;)I"),
523   FAST_NATIVE_METHOD(Field, getLong,    "(Ljava/lang/Object;)J"),
524   FAST_NATIVE_METHOD(Field, getNameInternal, "()Ljava/lang/String;"),
525   FAST_NATIVE_METHOD(Field, getShort,   "(Ljava/lang/Object;)S"),
526   FAST_NATIVE_METHOD(Field, isAnnotationPresentNative, "(Ljava/lang/Class;)Z"),
527   FAST_NATIVE_METHOD(Field, set,        "(Ljava/lang/Object;Ljava/lang/Object;)V"),
528   FAST_NATIVE_METHOD(Field, setBoolean, "(Ljava/lang/Object;Z)V"),
529   FAST_NATIVE_METHOD(Field, setByte,    "(Ljava/lang/Object;B)V"),
530   FAST_NATIVE_METHOD(Field, setChar,    "(Ljava/lang/Object;C)V"),
531   FAST_NATIVE_METHOD(Field, setDouble,  "(Ljava/lang/Object;D)V"),
532   FAST_NATIVE_METHOD(Field, setFloat,   "(Ljava/lang/Object;F)V"),
533   FAST_NATIVE_METHOD(Field, setInt,     "(Ljava/lang/Object;I)V"),
534   FAST_NATIVE_METHOD(Field, setLong,    "(Ljava/lang/Object;J)V"),
535   FAST_NATIVE_METHOD(Field, setShort,   "(Ljava/lang/Object;S)V"),
536 };
537 
register_java_lang_reflect_Field(JNIEnv * env)538 void register_java_lang_reflect_Field(JNIEnv* env) {
539   REGISTER_NATIVE_METHODS("java/lang/reflect/Field");
540 }
541 
542 }  // namespace art
543