class-inl.h revision 8261d02f9523b95013108f271b82bb157ef6f71d
12dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers/* 22dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers * Copyright (C) 2011 The Android Open Source Project 32dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers * 42dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers * Licensed under the Apache License, Version 2.0 (the "License"); 52dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers * you may not use this file except in compliance with the License. 62dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers * You may obtain a copy of the License at 72dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers * 82dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers * http://www.apache.org/licenses/LICENSE-2.0 92dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers * 102dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers * Unless required by applicable law or agreed to in writing, software 112dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers * distributed under the License is distributed on an "AS IS" BASIS, 122dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 132dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers * See the License for the specific language governing permissions and 142dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers * limitations under the License. 152dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers */ 162dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 17fc0e3219edc9a5bf81b166e82fd5db2796eb6a0dBrian Carlstrom#ifndef ART_RUNTIME_MIRROR_CLASS_INL_H_ 18fc0e3219edc9a5bf81b166e82fd5db2796eb6a0dBrian Carlstrom#define ART_RUNTIME_MIRROR_CLASS_INL_H_ 192dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 202dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers#include "class.h" 212dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 2298d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang#include "art_field-inl.h" 23e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier#include "art_method.h" 2498d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang#include "art_method-inl.h" 25e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light#include "base/array_slice.h" 26e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light#include "base/length_prefixed_array.h" 274f6ad8ab428038129b2d0d6c40b7fd625cca15e1Ian Rogers#include "class_loader.h" 2823a282146042a0d171aec2a415176f5d0621a90cVladimir Marko#include "common_throws.h" 294f6ad8ab428038129b2d0d6c40b7fd625cca15e1Ian Rogers#include "dex_cache.h" 30f832284dd847ff077577bb5712225430bbbb3b67Mathieu Chartier#include "dex_file.h" 313b4c18933c24b8a33f38573c2ebcdb9aa16efeb5Hiroshi Yamauchi#include "gc/heap-inl.h" 322dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers#include "iftable.h" 3362d6c772205b8859f0ebf7ad105402ec4c3e2e01Ian Rogers#include "object_array-inl.h" 3498d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang#include "read_barrier-inl.h" 354ee7a665e7f9cd2c5ace2d6304e33f64067b209fFred Shih#include "reference-inl.h" 362dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers#include "runtime.h" 372dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers#include "string.h" 3880afd02024d20e60b197d3adfbb43cc303cf29e0Vladimir Marko#include "utils.h" 392dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 402dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogersnamespace art { 412dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogersnamespace mirror { 422dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 4325023c744c4388a6459b21cc3babf8c602b024a2Hiroshi Yamauchitemplate<VerifyObjectFlags kVerifyFlags, ReadBarrierOption kReadBarrierOption> 44ef7d42fca18c16fbaf103822ad16f23246e2905dIan Rogersinline uint32_t Class::GetObjectSize() { 453481ba2c4e4f3aa80d8c6d50a9f85dacb56b508bVladimir Marko // Note: Extra parentheses to avoid the comma being interpreted as macro parameter separator. 463481ba2c4e4f3aa80d8c6d50a9f85dacb56b508bVladimir Marko DCHECK((!IsVariableSize<kVerifyFlags, kReadBarrierOption>())) << " class=" << PrettyTypeOf(this); 47e01a520fe0010f8abd344b5ed7120787d7ed1d71Hiroshi Yamauchi return GetField32(ObjectSizeOffset()); 482dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers} 492dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 50fbc31087932a65e036a153afab3049dc5298656aMathieu Chartiertemplate<VerifyObjectFlags kVerifyFlags, ReadBarrierOption kReadBarrierOption> 51ef7d42fca18c16fbaf103822ad16f23246e2905dIan Rogersinline Class* Class::GetSuperClass() { 522dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers // Can only get super class for loaded classes (hack for when runtime is 532dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers // initializing) 54fbc31087932a65e036a153afab3049dc5298656aMathieu Chartier DCHECK(IsLoaded<kVerifyFlags>() || 55fbc31087932a65e036a153afab3049dc5298656aMathieu Chartier IsErroneous<kVerifyFlags>() || 56fbc31087932a65e036a153afab3049dc5298656aMathieu Chartier !Runtime::Current()->IsStarted()) << IsLoaded(); 57fbc31087932a65e036a153afab3049dc5298656aMathieu Chartier return GetFieldObject<Class, kVerifyFlags, kReadBarrierOption>( 58fbc31087932a65e036a153afab3049dc5298656aMathieu Chartier OFFSET_OF_OBJECT_MEMBER(Class, super_class_)); 592dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers} 602dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 61ef7d42fca18c16fbaf103822ad16f23246e2905dIan Rogersinline ClassLoader* Class::GetClassLoader() { 62b0fa5dc7769c1e054032f39de0a3f6d6dd06f8cfIan Rogers return GetFieldObject<ClassLoader>(OFFSET_OF_OBJECT_MEMBER(Class, class_loader_)); 634f6ad8ab428038129b2d0d6c40b7fd625cca15e1Ian Rogers} 644f6ad8ab428038129b2d0d6c40b7fd625cca15e1Ian Rogers 65c2f4d0240b3a9b905dff5b546924865f15241481Mathieu Chartiertemplate<VerifyObjectFlags kVerifyFlags> 66ef7d42fca18c16fbaf103822ad16f23246e2905dIan Rogersinline DexCache* Class::GetDexCache() { 67b0fa5dc7769c1e054032f39de0a3f6d6dd06f8cfIan Rogers return GetFieldObject<DexCache, kVerifyFlags>(OFFSET_OF_OBJECT_MEMBER(Class, dex_cache_)); 684f6ad8ab428038129b2d0d6c40b7fd625cca15e1Ian Rogers} 694f6ad8ab428038129b2d0d6c40b7fd625cca15e1Ian Rogers 70e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Lightinline uint32_t Class::GetCopiedMethodsStartOffset() { 71e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light return GetFieldShort(OFFSET_OF_OBJECT_MEMBER(Class, copied_methods_offset_)); 72e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light} 73e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light 74e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Lightinline uint32_t Class::GetDirectMethodsStartOffset() { 75e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light return 0; 76e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light} 77e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light 78e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Lightinline uint32_t Class::GetVirtualMethodsStartOffset() { 79e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light return GetFieldShort(OFFSET_OF_OBJECT_MEMBER(Class, virtual_methods_offset_)); 80e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light} 81e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light 82e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Lighttemplate<VerifyObjectFlags kVerifyFlags> 83542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampeinline ArraySlice<ArtMethod> Class::GetDirectMethodsSlice(PointerSize pointer_size) { 842dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers DCHECK(IsLoaded() || IsErroneous()); 85e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light return GetDirectMethodsSliceUnchecked(pointer_size); 862dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers} 872dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 88542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampeinline ArraySlice<ArtMethod> Class::GetDirectMethodsSliceUnchecked(PointerSize pointer_size) { 89e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light return ArraySlice<ArtMethod>(GetMethodsPtr(), 90e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light GetDirectMethodsStartOffset(), 91e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light GetVirtualMethodsStartOffset(), 92e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light ArtMethod::Size(pointer_size), 93e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light ArtMethod::Alignment(pointer_size)); 946286a97bea0f584342803a215550038852b24776Alex Light} 956286a97bea0f584342803a215550038852b24776Alex Light 96e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Lighttemplate<VerifyObjectFlags kVerifyFlags> 97542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampeinline ArraySlice<ArtMethod> Class::GetDeclaredMethodsSlice(PointerSize pointer_size) { 98e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light DCHECK(IsLoaded() || IsErroneous()); 99e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light return GetDeclaredMethodsSliceUnchecked(pointer_size); 100e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light} 101e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light 102542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampeinline ArraySlice<ArtMethod> Class::GetDeclaredMethodsSliceUnchecked(PointerSize pointer_size) { 103e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light return ArraySlice<ArtMethod>(GetMethodsPtr(), 104e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light GetDirectMethodsStartOffset(), 105e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light GetCopiedMethodsStartOffset(), 106e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light ArtMethod::Size(pointer_size), 107e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light ArtMethod::Alignment(pointer_size)); 108e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light} 109e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Lighttemplate<VerifyObjectFlags kVerifyFlags> 110542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampeinline ArraySlice<ArtMethod> Class::GetDeclaredVirtualMethodsSlice(PointerSize pointer_size) { 111e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light DCHECK(IsLoaded() || IsErroneous()); 112e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light return GetDeclaredVirtualMethodsSliceUnchecked(pointer_size); 113e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light} 114e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light 115542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampeinline ArraySlice<ArtMethod> Class::GetDeclaredVirtualMethodsSliceUnchecked( 116542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampe PointerSize pointer_size) { 117e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light return ArraySlice<ArtMethod>(GetMethodsPtr(), 118e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light GetVirtualMethodsStartOffset(), 119e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light GetCopiedMethodsStartOffset(), 120e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light ArtMethod::Size(pointer_size), 121e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light ArtMethod::Alignment(pointer_size)); 122e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light} 123e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light 124e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Lighttemplate<VerifyObjectFlags kVerifyFlags> 125542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampeinline ArraySlice<ArtMethod> Class::GetVirtualMethodsSlice(PointerSize pointer_size) { 126e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light DCHECK(IsLoaded() || IsErroneous()); 127e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light return GetVirtualMethodsSliceUnchecked(pointer_size); 128e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light} 129e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light 130542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampeinline ArraySlice<ArtMethod> Class::GetVirtualMethodsSliceUnchecked(PointerSize pointer_size) { 131e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light LengthPrefixedArray<ArtMethod>* methods = GetMethodsPtr(); 132e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light return ArraySlice<ArtMethod>(methods, 133e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light GetVirtualMethodsStartOffset(), 134e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light NumMethods(), 135e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light ArtMethod::Size(pointer_size), 136e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light ArtMethod::Alignment(pointer_size)); 137e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light} 138e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light 139e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Lighttemplate<VerifyObjectFlags kVerifyFlags> 140542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampeinline ArraySlice<ArtMethod> Class::GetCopiedMethodsSlice(PointerSize pointer_size) { 141e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light DCHECK(IsLoaded() || IsErroneous()); 142e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light return GetCopiedMethodsSliceUnchecked(pointer_size); 143e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light} 144e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light 145542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampeinline ArraySlice<ArtMethod> Class::GetCopiedMethodsSliceUnchecked(PointerSize pointer_size) { 146e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light LengthPrefixedArray<ArtMethod>* methods = GetMethodsPtr(); 147e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light return ArraySlice<ArtMethod>(methods, 148e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light GetCopiedMethodsStartOffset(), 149e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light NumMethods(), 150e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light ArtMethod::Size(pointer_size), 151e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light ArtMethod::Alignment(pointer_size)); 152e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light} 153e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light 154e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Lightinline LengthPrefixedArray<ArtMethod>* Class::GetMethodsPtr() { 15554d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartier return reinterpret_cast<LengthPrefixedArray<ArtMethod>*>( 156f4b3dbad413023795b92a842aad1c3f2fe4a57e9Mathieu Chartier static_cast<uintptr_t>(GetField64(OFFSET_OF_OBJECT_MEMBER(Class, methods_)))); 1572dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers} 1582dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 159e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Lighttemplate<VerifyObjectFlags kVerifyFlags> 160542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampeinline ArraySlice<ArtMethod> Class::GetMethodsSlice(PointerSize pointer_size) { 161e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light DCHECK(IsLoaded() || IsErroneous()); 162e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light LengthPrefixedArray<ArtMethod>* methods = GetMethodsPtr(); 163e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light return ArraySlice<ArtMethod>(methods, 164e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light 0, 165e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light NumMethods(), 166e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light ArtMethod::Size(pointer_size), 167e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light ArtMethod::Alignment(pointer_size)); 1682dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers} 1692dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 170e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light 171e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Lightinline uint32_t Class::NumMethods() { 172e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light LengthPrefixedArray<ArtMethod>* methods = GetMethodsPtr(); 173e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light return (methods == nullptr) ? 0 : methods->size(); 174e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier} 175e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier 176542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampeinline ArtMethod* Class::GetDirectMethodUnchecked(size_t i, PointerSize pointer_size) { 177e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier CheckPointerSize(pointer_size); 178e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light return &GetDirectMethodsSliceUnchecked(pointer_size).At(i); 179e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier} 180e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier 181542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampeinline ArtMethod* Class::GetDirectMethod(size_t i, PointerSize pointer_size) { 182e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier CheckPointerSize(pointer_size); 183e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light return &GetDirectMethodsSlice(pointer_size).At(i); 1846286a97bea0f584342803a215550038852b24776Alex Light} 1856286a97bea0f584342803a215550038852b24776Alex Light 186e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Lightinline void Class::SetMethodsPtr(LengthPrefixedArray<ArtMethod>* new_methods, 187e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light uint32_t num_direct, 188e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light uint32_t num_virtual) { 189e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light DCHECK(GetMethodsPtr() == nullptr); 190e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light SetMethodsPtrUnchecked(new_methods, num_direct, num_virtual); 191e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light} 192e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light 193e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light 194e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Lightinline void Class::SetMethodsPtrUnchecked(LengthPrefixedArray<ArtMethod>* new_methods, 195e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light uint32_t num_direct, 196e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light uint32_t num_virtual) { 197e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light DCHECK_LE(num_direct + num_virtual, (new_methods == nullptr) ? 0 : new_methods->size()); 198e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light SetMethodsPtrInternal(new_methods); 199e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light SetFieldShort<false>(OFFSET_OF_OBJECT_MEMBER(Class, copied_methods_offset_), 200e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light dchecked_integral_cast<uint16_t>(num_direct + num_virtual)); 201e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light SetFieldShort<false>(OFFSET_OF_OBJECT_MEMBER(Class, virtual_methods_offset_), 202e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light dchecked_integral_cast<uint16_t>(num_direct)); 2032dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers} 2042dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 205e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Lightinline void Class::SetMethodsPtrInternal(LengthPrefixedArray<ArtMethod>* new_methods) { 206e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light SetField64<false>(OFFSET_OF_OBJECT_MEMBER(Class, methods_), 207f4b3dbad413023795b92a842aad1c3f2fe4a57e9Mathieu Chartier static_cast<uint64_t>(reinterpret_cast<uintptr_t>(new_methods))); 2082dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers} 2092dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 2104e30541a92381fb280cd0be9a1763b713ee4d64cMathieu Chartiertemplate<VerifyObjectFlags kVerifyFlags> 211542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampeinline ArtMethod* Class::GetVirtualMethod(size_t i, PointerSize pointer_size) { 212e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier CheckPointerSize(pointer_size); 213f4c15a18eb055735857a280856be5b142e0c1113Hiroshi Yamauchi DCHECK(IsResolved<kVerifyFlags>() || IsErroneous<kVerifyFlags>()) 214f4c15a18eb055735857a280856be5b142e0c1113Hiroshi Yamauchi << PrettyClass(this) << " status=" << GetStatus(); 215e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier return GetVirtualMethodUnchecked(i, pointer_size); 2162dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers} 2172dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 218542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampeinline ArtMethod* Class::GetVirtualMethodDuringLinking(size_t i, PointerSize pointer_size) { 219e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier CheckPointerSize(pointer_size); 2202dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers DCHECK(IsLoaded() || IsErroneous()); 221e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier return GetVirtualMethodUnchecked(i, pointer_size); 2222dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers} 2232dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 224542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampeinline ArtMethod* Class::GetVirtualMethodUnchecked(size_t i, PointerSize pointer_size) { 225e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier CheckPointerSize(pointer_size); 226e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light return &GetVirtualMethodsSliceUnchecked(pointer_size).At(i); 2272dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers} 2282dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 229fbc31087932a65e036a153afab3049dc5298656aMathieu Chartiertemplate<VerifyObjectFlags kVerifyFlags, 230fbc31087932a65e036a153afab3049dc5298656aMathieu Chartier ReadBarrierOption kReadBarrierOption> 231e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartierinline PointerArray* Class::GetVTable() { 232fbc31087932a65e036a153afab3049dc5298656aMathieu Chartier DCHECK(IsResolved<kVerifyFlags>() || IsErroneous<kVerifyFlags>()); 233fbc31087932a65e036a153afab3049dc5298656aMathieu Chartier return GetFieldObject<PointerArray, kVerifyFlags, kReadBarrierOption>( 234fbc31087932a65e036a153afab3049dc5298656aMathieu Chartier OFFSET_OF_OBJECT_MEMBER(Class, vtable_)); 2352dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers} 2362dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 237e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartierinline PointerArray* Class::GetVTableDuringLinking() { 2382dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers DCHECK(IsLoaded() || IsErroneous()); 239e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier return GetFieldObject<PointerArray>(OFFSET_OF_OBJECT_MEMBER(Class, vtable_)); 2402dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers} 2412dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 242e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartierinline void Class::SetVTable(PointerArray* new_vtable) { 243b0fa5dc7769c1e054032f39de0a3f6d6dd06f8cfIan Rogers SetFieldObject<false>(OFFSET_OF_OBJECT_MEMBER(Class, vtable_), new_vtable); 2442dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers} 2452dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 2462cdbad7c62f126581ec5177104de961c4d71adaaMingyao Yanginline bool Class::HasVTable() { 247a62cb9bb6cb2278cb41ab0664191623e178c6a4fArtem Udovichenko return GetVTable() != nullptr || ShouldHaveEmbeddedVTable(); 2482cdbad7c62f126581ec5177104de961c4d71adaaMingyao Yang} 2492cdbad7c62f126581ec5177104de961c4d71adaaMingyao Yang 2502cdbad7c62f126581ec5177104de961c4d71adaaMingyao Yanginline int32_t Class::GetVTableLength() { 251a62cb9bb6cb2278cb41ab0664191623e178c6a4fArtem Udovichenko if (ShouldHaveEmbeddedVTable()) { 2522cdbad7c62f126581ec5177104de961c4d71adaaMingyao Yang return GetEmbeddedVTableLength(); 2532cdbad7c62f126581ec5177104de961c4d71adaaMingyao Yang } 254e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier return GetVTable() != nullptr ? GetVTable()->GetLength() : 0; 2552cdbad7c62f126581ec5177104de961c4d71adaaMingyao Yang} 2562cdbad7c62f126581ec5177104de961c4d71adaaMingyao Yang 257542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampeinline ArtMethod* Class::GetVTableEntry(uint32_t i, PointerSize pointer_size) { 258a62cb9bb6cb2278cb41ab0664191623e178c6a4fArtem Udovichenko if (ShouldHaveEmbeddedVTable()) { 259e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier return GetEmbeddedVTableEntry(i, pointer_size); 2602cdbad7c62f126581ec5177104de961c4d71adaaMingyao Yang } 261e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier auto* vtable = GetVTable(); 262e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier DCHECK(vtable != nullptr); 263e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier return vtable->GetElementPtrSize<ArtMethod*>(i, pointer_size); 2642cdbad7c62f126581ec5177104de961c4d71adaaMingyao Yang} 2652cdbad7c62f126581ec5177104de961c4d71adaaMingyao Yang 2662cdbad7c62f126581ec5177104de961c4d71adaaMingyao Yanginline int32_t Class::GetEmbeddedVTableLength() { 267e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier return GetField32(MemberOffset(EmbeddedVTableLengthOffset())); 2682cdbad7c62f126581ec5177104de961c4d71adaaMingyao Yang} 2692cdbad7c62f126581ec5177104de961c4d71adaaMingyao Yang 2702cdbad7c62f126581ec5177104de961c4d71adaaMingyao Yanginline void Class::SetEmbeddedVTableLength(int32_t len) { 271e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier SetField32<false>(MemberOffset(EmbeddedVTableLengthOffset()), len); 2722cdbad7c62f126581ec5177104de961c4d71adaaMingyao Yang} 2732cdbad7c62f126581ec5177104de961c4d71adaaMingyao Yang 274542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampeinline ImTable* Class::GetImt(PointerSize pointer_size) { 275a62cb9bb6cb2278cb41ab0664191623e178c6a4fArtem Udovichenko return GetFieldPtrWithSize<ImTable*>(MemberOffset(ImtPtrOffset(pointer_size)), pointer_size); 276a62cb9bb6cb2278cb41ab0664191623e178c6a4fArtem Udovichenko} 277a62cb9bb6cb2278cb41ab0664191623e178c6a4fArtem Udovichenko 278542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampeinline void Class::SetImt(ImTable* imt, PointerSize pointer_size) { 279a62cb9bb6cb2278cb41ab0664191623e178c6a4fArtem Udovichenko return SetFieldPtrWithSize<false>(MemberOffset(ImtPtrOffset(pointer_size)), imt, pointer_size); 280a62cb9bb6cb2278cb41ab0664191623e178c6a4fArtem Udovichenko} 281a62cb9bb6cb2278cb41ab0664191623e178c6a4fArtem Udovichenko 282542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampeinline MemberOffset Class::EmbeddedVTableEntryOffset(uint32_t i, PointerSize pointer_size) { 283e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier return MemberOffset( 284e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier EmbeddedVTableOffset(pointer_size).Uint32Value() + i * VTableEntrySize(pointer_size)); 2852cdbad7c62f126581ec5177104de961c4d71adaaMingyao Yang} 2862cdbad7c62f126581ec5177104de961c4d71adaaMingyao Yang 287542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampeinline ArtMethod* Class::GetEmbeddedVTableEntry(uint32_t i, PointerSize pointer_size) { 288e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier return GetFieldPtrWithSize<ArtMethod*>(EmbeddedVTableEntryOffset(i, pointer_size), pointer_size); 289e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier} 290e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier 291e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartierinline void Class::SetEmbeddedVTableEntryUnchecked( 292542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampe uint32_t i, ArtMethod* method, PointerSize pointer_size) { 293e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier SetFieldPtrWithSize<false>(EmbeddedVTableEntryOffset(i, pointer_size), method, pointer_size); 294e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier} 295e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier 296542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampeinline void Class::SetEmbeddedVTableEntry(uint32_t i, ArtMethod* method, PointerSize pointer_size) { 297e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier auto* vtable = GetVTableDuringLinking(); 298e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier CHECK_EQ(method, vtable->GetElementPtrSize<ArtMethod*>(i, pointer_size)); 299e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier SetEmbeddedVTableEntryUnchecked(i, method, pointer_size); 30098d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang} 30198d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang 302ef7d42fca18c16fbaf103822ad16f23246e2905dIan Rogersinline bool Class::Implements(Class* klass) { 3032cebb24bfc3247d3e9be138a3350106737455918Mathieu Chartier DCHECK(klass != nullptr); 304693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers DCHECK(klass->IsInterface()) << PrettyClass(this); 305693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers // All interfaces implemented directly and by our superclass, and 306693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers // recursively all super-interfaces of those interfaces, are listed 307693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers // in iftable_, so we can just do a linear scan through that. 308693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers int32_t iftable_count = GetIfTableCount(); 309693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers IfTable* iftable = GetIfTable(); 310693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers for (int32_t i = 0; i < iftable_count; i++) { 311693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers if (iftable->GetInterface(i) == klass) { 312693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers return true; 313693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers } 314693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers } 315693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers return false; 316693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers} 317693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers 318693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers// Determine whether "this" is assignable from "src", where both of these 319693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers// are array classes. 320693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers// 321693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers// Consider an array class, e.g. Y[][], where Y is a subclass of X. 322693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers// Y[][] = Y[][] --> true (identity) 323693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers// X[][] = Y[][] --> true (element superclass) 324693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers// Y = Y[][] --> false 325693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers// Y[] = Y[][] --> false 326693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers// Object = Y[][] --> true (everything is an object) 327693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers// Object[] = Y[][] --> true 328693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers// Object[][] = Y[][] --> true 329693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers// Object[][][] = Y[][] --> false (too many []s) 330693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers// Serializable = Y[][] --> true (all arrays are Serializable) 331693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers// Serializable[] = Y[][] --> true 332693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers// Serializable[][] = Y[][] --> false (unless Y is Serializable) 333693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers// 334693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers// Don't forget about primitive types. 335693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers// Object[] = int[] --> false 336693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers// 337ef7d42fca18c16fbaf103822ad16f23246e2905dIan Rogersinline bool Class::IsArrayAssignableFromArray(Class* src) { 338693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers DCHECK(IsArrayClass()) << PrettyClass(this); 339693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers DCHECK(src->IsArrayClass()) << PrettyClass(src); 340693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers return GetComponentType()->IsAssignableFrom(src->GetComponentType()); 341693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers} 342693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers 343ef7d42fca18c16fbaf103822ad16f23246e2905dIan Rogersinline bool Class::IsAssignableFromArray(Class* src) { 344693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers DCHECK(!IsInterface()) << PrettyClass(this); // handled first in IsAssignableFrom 345693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers DCHECK(src->IsArrayClass()) << PrettyClass(src); 346693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers if (!IsArrayClass()) { 347693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers // If "this" is not also an array, it must be Object. 348693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers // src's super should be java_lang_Object, since it is an array. 349693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers Class* java_lang_Object = src->GetSuperClass(); 3502cebb24bfc3247d3e9be138a3350106737455918Mathieu Chartier DCHECK(java_lang_Object != nullptr) << PrettyClass(src); 3512cebb24bfc3247d3e9be138a3350106737455918Mathieu Chartier DCHECK(java_lang_Object->GetSuperClass() == nullptr) << PrettyClass(src); 352693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers return this == java_lang_Object; 353693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers } 354693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers return IsArrayAssignableFromArray(src); 355693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers} 356693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers 35789786437f4c0176b35ca0376153dd18ab7df4924Vladimir Markotemplate <bool throw_on_failure, bool use_referrers_cache> 35889786437f4c0176b35ca0376153dd18ab7df4924Vladimir Markoinline bool Class::ResolvedFieldAccessTest(Class* access_to, ArtField* field, 359ef7d42fca18c16fbaf103822ad16f23246e2905dIan Rogers uint32_t field_idx, DexCache* dex_cache) { 36089786437f4c0176b35ca0376153dd18ab7df4924Vladimir Marko DCHECK_EQ(use_referrers_cache, dex_cache == nullptr); 36123a282146042a0d171aec2a415176f5d0621a90cVladimir Marko if (UNLIKELY(!this->CanAccess(access_to))) { 36223a282146042a0d171aec2a415176f5d0621a90cVladimir Marko // The referrer class can't access the field's declaring class but may still be able 36323a282146042a0d171aec2a415176f5d0621a90cVladimir Marko // to access the field if the FieldId specifies an accessible subclass of the declaring 36423a282146042a0d171aec2a415176f5d0621a90cVladimir Marko // class rather than the declaring class itself. 365ef7d42fca18c16fbaf103822ad16f23246e2905dIan Rogers DexCache* referrer_dex_cache = use_referrers_cache ? this->GetDexCache() : dex_cache; 36623a282146042a0d171aec2a415176f5d0621a90cVladimir Marko uint32_t class_idx = referrer_dex_cache->GetDexFile()->GetFieldId(field_idx).class_idx_; 36723a282146042a0d171aec2a415176f5d0621a90cVladimir Marko // The referenced class has already been resolved with the field, get it from the dex cache. 36823a282146042a0d171aec2a415176f5d0621a90cVladimir Marko Class* dex_access_to = referrer_dex_cache->GetResolvedType(class_idx); 36923a282146042a0d171aec2a415176f5d0621a90cVladimir Marko DCHECK(dex_access_to != nullptr); 37023a282146042a0d171aec2a415176f5d0621a90cVladimir Marko if (UNLIKELY(!this->CanAccess(dex_access_to))) { 37123a282146042a0d171aec2a415176f5d0621a90cVladimir Marko if (throw_on_failure) { 37223a282146042a0d171aec2a415176f5d0621a90cVladimir Marko ThrowIllegalAccessErrorClass(this, dex_access_to); 37323a282146042a0d171aec2a415176f5d0621a90cVladimir Marko } 37423a282146042a0d171aec2a415176f5d0621a90cVladimir Marko return false; 37523a282146042a0d171aec2a415176f5d0621a90cVladimir Marko } 37623a282146042a0d171aec2a415176f5d0621a90cVladimir Marko } 37723a282146042a0d171aec2a415176f5d0621a90cVladimir Marko if (LIKELY(this->CanAccessMember(access_to, field->GetAccessFlags()))) { 37823a282146042a0d171aec2a415176f5d0621a90cVladimir Marko return true; 37923a282146042a0d171aec2a415176f5d0621a90cVladimir Marko } 38023a282146042a0d171aec2a415176f5d0621a90cVladimir Marko if (throw_on_failure) { 38123a282146042a0d171aec2a415176f5d0621a90cVladimir Marko ThrowIllegalAccessErrorField(this, field); 38223a282146042a0d171aec2a415176f5d0621a90cVladimir Marko } 38323a282146042a0d171aec2a415176f5d0621a90cVladimir Marko return false; 38423a282146042a0d171aec2a415176f5d0621a90cVladimir Marko} 38523a282146042a0d171aec2a415176f5d0621a90cVladimir Marko 38689786437f4c0176b35ca0376153dd18ab7df4924Vladimir Markotemplate <bool throw_on_failure, bool use_referrers_cache, InvokeType throw_invoke_type> 38789786437f4c0176b35ca0376153dd18ab7df4924Vladimir Markoinline bool Class::ResolvedMethodAccessTest(Class* access_to, ArtMethod* method, 388ef7d42fca18c16fbaf103822ad16f23246e2905dIan Rogers uint32_t method_idx, DexCache* dex_cache) { 389575e78c41ece0dec969d31f46be563d4eb7ae43bAndreas Gampe static_assert(throw_on_failure || throw_invoke_type == kStatic, "Non-default throw invoke type"); 39089786437f4c0176b35ca0376153dd18ab7df4924Vladimir Marko DCHECK_EQ(use_referrers_cache, dex_cache == nullptr); 39123a282146042a0d171aec2a415176f5d0621a90cVladimir Marko if (UNLIKELY(!this->CanAccess(access_to))) { 39223a282146042a0d171aec2a415176f5d0621a90cVladimir Marko // The referrer class can't access the method's declaring class but may still be able 39323a282146042a0d171aec2a415176f5d0621a90cVladimir Marko // to access the method if the MethodId specifies an accessible subclass of the declaring 39423a282146042a0d171aec2a415176f5d0621a90cVladimir Marko // class rather than the declaring class itself. 395ef7d42fca18c16fbaf103822ad16f23246e2905dIan Rogers DexCache* referrer_dex_cache = use_referrers_cache ? this->GetDexCache() : dex_cache; 39623a282146042a0d171aec2a415176f5d0621a90cVladimir Marko uint32_t class_idx = referrer_dex_cache->GetDexFile()->GetMethodId(method_idx).class_idx_; 39723a282146042a0d171aec2a415176f5d0621a90cVladimir Marko // The referenced class has already been resolved with the method, get it from the dex cache. 39823a282146042a0d171aec2a415176f5d0621a90cVladimir Marko Class* dex_access_to = referrer_dex_cache->GetResolvedType(class_idx); 39923a282146042a0d171aec2a415176f5d0621a90cVladimir Marko DCHECK(dex_access_to != nullptr); 40023a282146042a0d171aec2a415176f5d0621a90cVladimir Marko if (UNLIKELY(!this->CanAccess(dex_access_to))) { 40123a282146042a0d171aec2a415176f5d0621a90cVladimir Marko if (throw_on_failure) { 40223a282146042a0d171aec2a415176f5d0621a90cVladimir Marko ThrowIllegalAccessErrorClassForMethodDispatch(this, dex_access_to, 40323a282146042a0d171aec2a415176f5d0621a90cVladimir Marko method, throw_invoke_type); 40423a282146042a0d171aec2a415176f5d0621a90cVladimir Marko } 40523a282146042a0d171aec2a415176f5d0621a90cVladimir Marko return false; 40623a282146042a0d171aec2a415176f5d0621a90cVladimir Marko } 40723a282146042a0d171aec2a415176f5d0621a90cVladimir Marko } 40823a282146042a0d171aec2a415176f5d0621a90cVladimir Marko if (LIKELY(this->CanAccessMember(access_to, method->GetAccessFlags()))) { 40923a282146042a0d171aec2a415176f5d0621a90cVladimir Marko return true; 41023a282146042a0d171aec2a415176f5d0621a90cVladimir Marko } 41123a282146042a0d171aec2a415176f5d0621a90cVladimir Marko if (throw_on_failure) { 41223a282146042a0d171aec2a415176f5d0621a90cVladimir Marko ThrowIllegalAccessErrorMethod(this, method); 41323a282146042a0d171aec2a415176f5d0621a90cVladimir Marko } 41423a282146042a0d171aec2a415176f5d0621a90cVladimir Marko return false; 41523a282146042a0d171aec2a415176f5d0621a90cVladimir Marko} 41623a282146042a0d171aec2a415176f5d0621a90cVladimir Marko 41789786437f4c0176b35ca0376153dd18ab7df4924Vladimir Markoinline bool Class::CanAccessResolvedField(Class* access_to, ArtField* field, 418ef7d42fca18c16fbaf103822ad16f23246e2905dIan Rogers DexCache* dex_cache, uint32_t field_idx) { 419ef7d42fca18c16fbaf103822ad16f23246e2905dIan Rogers return ResolvedFieldAccessTest<false, false>(access_to, field, field_idx, dex_cache); 42089786437f4c0176b35ca0376153dd18ab7df4924Vladimir Marko} 42189786437f4c0176b35ca0376153dd18ab7df4924Vladimir Marko 42289786437f4c0176b35ca0376153dd18ab7df4924Vladimir Markoinline bool Class::CheckResolvedFieldAccess(Class* access_to, ArtField* field, 42389786437f4c0176b35ca0376153dd18ab7df4924Vladimir Marko uint32_t field_idx) { 42489786437f4c0176b35ca0376153dd18ab7df4924Vladimir Marko return ResolvedFieldAccessTest<true, true>(access_to, field, field_idx, nullptr); 42589786437f4c0176b35ca0376153dd18ab7df4924Vladimir Marko} 42689786437f4c0176b35ca0376153dd18ab7df4924Vladimir Marko 42789786437f4c0176b35ca0376153dd18ab7df4924Vladimir Markoinline bool Class::CanAccessResolvedMethod(Class* access_to, ArtMethod* method, 428ef7d42fca18c16fbaf103822ad16f23246e2905dIan Rogers DexCache* dex_cache, uint32_t method_idx) { 429ef7d42fca18c16fbaf103822ad16f23246e2905dIan Rogers return ResolvedMethodAccessTest<false, false, kStatic>(access_to, method, method_idx, dex_cache); 43089786437f4c0176b35ca0376153dd18ab7df4924Vladimir Marko} 43189786437f4c0176b35ca0376153dd18ab7df4924Vladimir Marko 43289786437f4c0176b35ca0376153dd18ab7df4924Vladimir Markotemplate <InvokeType throw_invoke_type> 43389786437f4c0176b35ca0376153dd18ab7df4924Vladimir Markoinline bool Class::CheckResolvedMethodAccess(Class* access_to, ArtMethod* method, 43489786437f4c0176b35ca0376153dd18ab7df4924Vladimir Marko uint32_t method_idx) { 43589786437f4c0176b35ca0376153dd18ab7df4924Vladimir Marko return ResolvedMethodAccessTest<true, true, throw_invoke_type>(access_to, method, method_idx, 43689786437f4c0176b35ca0376153dd18ab7df4924Vladimir Marko nullptr); 43789786437f4c0176b35ca0376153dd18ab7df4924Vladimir Marko} 43889786437f4c0176b35ca0376153dd18ab7df4924Vladimir Marko 439ef7d42fca18c16fbaf103822ad16f23246e2905dIan Rogersinline bool Class::IsSubClass(Class* klass) { 440693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers DCHECK(!IsInterface()) << PrettyClass(this); 441693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers DCHECK(!IsArrayClass()) << PrettyClass(this); 442ef7d42fca18c16fbaf103822ad16f23246e2905dIan Rogers Class* current = this; 443693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers do { 444693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers if (current == klass) { 445693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers return true; 446693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers } 447693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers current = current->GetSuperClass(); 4482cebb24bfc3247d3e9be138a3350106737455918Mathieu Chartier } while (current != nullptr); 449693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers return false; 450693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers} 451693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers 452542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampeinline ArtMethod* Class::FindVirtualMethodForInterface(ArtMethod* method, 453542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampe PointerSize pointer_size) { 454693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers Class* declaring_class = method->GetDeclaringClass(); 4552cebb24bfc3247d3e9be138a3350106737455918Mathieu Chartier DCHECK(declaring_class != nullptr) << PrettyClass(this); 456693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers DCHECK(declaring_class->IsInterface()) << PrettyMethod(method); 4570f7e8f59698265d416d40844233bb09d02e7fc33Alex Light DCHECK(!method->IsCopied()); 458693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers // TODO cache to improve lookup speed 459e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier const int32_t iftable_count = GetIfTableCount(); 460693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers IfTable* iftable = GetIfTable(); 461693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers for (int32_t i = 0; i < iftable_count; i++) { 462693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers if (iftable->GetInterface(i) == declaring_class) { 463e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier return iftable->GetMethodArray(i)->GetElementPtrSize<ArtMethod*>( 464e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier method->GetMethodIndex(), pointer_size); 465693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers } 466693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers } 4672cebb24bfc3247d3e9be138a3350106737455918Mathieu Chartier return nullptr; 468693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers} 469693ff61274cd2c9b8eb7e68c370f84a911b8ca52Ian Rogers 470542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampeinline ArtMethod* Class::FindVirtualMethodForVirtual(ArtMethod* method, PointerSize pointer_size) { 471eb7c144a6aff7da673ba53d501c46f00311d4d7fAlex Light // Only miranda or default methods may come from interfaces and be used as a virtual. 472eb7c144a6aff7da673ba53d501c46f00311d4d7fAlex Light DCHECK(!method->GetDeclaringClass()->IsInterface() || method->IsDefault() || method->IsMiranda()); 4732dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers // The argument method may from a super class. 4742dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers // Use the index to a potentially overridden one for this instance's class. 475e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier return GetVTableEntry(method->GetMethodIndex(), pointer_size); 4762dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers} 4772dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 478542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampeinline ArtMethod* Class::FindVirtualMethodForSuper(ArtMethod* method, PointerSize pointer_size) { 4792dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers DCHECK(!method->GetDeclaringClass()->IsInterface()); 480e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier return GetSuperClass()->GetVTableEntry(method->GetMethodIndex(), pointer_size); 4812dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers} 4822dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 483e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartierinline ArtMethod* Class::FindVirtualMethodForVirtualOrInterface(ArtMethod* method, 484542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampe PointerSize pointer_size) { 4852dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers if (method->IsDirect()) { 4862dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers return method; 4872dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers } 4883612149aee482ab7a17da68b0ef5fef3879729a2Alex Light if (method->GetDeclaringClass()->IsInterface() && !method->IsCopied()) { 489e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier return FindVirtualMethodForInterface(method, pointer_size); 4902dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers } 491e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier return FindVirtualMethodForVirtual(method, pointer_size); 4922dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers} 4932dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 494fbc31087932a65e036a153afab3049dc5298656aMathieu Chartiertemplate<VerifyObjectFlags kVerifyFlags, 495fbc31087932a65e036a153afab3049dc5298656aMathieu Chartier ReadBarrierOption kReadBarrierOption> 496ef7d42fca18c16fbaf103822ad16f23246e2905dIan Rogersinline IfTable* Class::GetIfTable() { 497fbc31087932a65e036a153afab3049dc5298656aMathieu Chartier return GetFieldObject<IfTable, kVerifyFlags, kReadBarrierOption>( 498fbc31087932a65e036a153afab3049dc5298656aMathieu Chartier OFFSET_OF_OBJECT_MEMBER(Class, iftable_)); 4992dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers} 5002dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 501ef7d42fca18c16fbaf103822ad16f23246e2905dIan Rogersinline int32_t Class::GetIfTableCount() { 5022dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers IfTable* iftable = GetIfTable(); 5032cebb24bfc3247d3e9be138a3350106737455918Mathieu Chartier if (iftable == nullptr) { 5042dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers return 0; 5052dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers } 5062dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers return iftable->Count(); 5072dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers} 5082dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 5092dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogersinline void Class::SetIfTable(IfTable* new_iftable) { 510b0fa5dc7769c1e054032f39de0a3f6d6dd06f8cfIan Rogers SetFieldObject<false>(OFFSET_OF_OBJECT_MEMBER(Class, iftable_), new_iftable); 5112dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers} 5122dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 51354d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartierinline LengthPrefixedArray<ArtField>* Class::GetIFieldsPtr() { 514fbc31087932a65e036a153afab3049dc5298656aMathieu Chartier DCHECK(IsLoaded() || IsErroneous()) << GetStatus(); 51554d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartier return GetFieldPtr<LengthPrefixedArray<ArtField>*>(OFFSET_OF_OBJECT_MEMBER(Class, ifields_)); 5162dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers} 5172dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 5185496f69c0a4c2cc357a065f57b7f4ff5d9ad2fa9Hiroshi Yamauchitemplate<VerifyObjectFlags kVerifyFlags, ReadBarrierOption kReadBarrierOption> 51976649e8d775519fe19f2b14d18ac488c13296054Vladimir Markoinline MemberOffset Class::GetFirstReferenceInstanceFieldOffset() { 5205496f69c0a4c2cc357a065f57b7f4ff5d9ad2fa9Hiroshi Yamauchi Class* super_class = GetSuperClass<kVerifyFlags, kReadBarrierOption>(); 52176649e8d775519fe19f2b14d18ac488c13296054Vladimir Marko return (super_class != nullptr) 5227a62e6728463237684d3d9834d81bd7bba7ab197Hiroshi Yamauchi ? MemberOffset(RoundUp(super_class->GetObjectSize<kVerifyFlags, kReadBarrierOption>(), 52376649e8d775519fe19f2b14d18ac488c13296054Vladimir Marko sizeof(mirror::HeapReference<mirror::Object>))) 52476649e8d775519fe19f2b14d18ac488c13296054Vladimir Marko : ClassOffset(); 52576649e8d775519fe19f2b14d18ac488c13296054Vladimir Marko} 52676649e8d775519fe19f2b14d18ac488c13296054Vladimir Marko 527dfe02f6aafee264478d510b9742ee266ea52e8a8Mathieu Chartiertemplate <VerifyObjectFlags kVerifyFlags, ReadBarrierOption kReadBarrierOption> 528542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampeinline MemberOffset Class::GetFirstReferenceStaticFieldOffset(PointerSize pointer_size) { 52976649e8d775519fe19f2b14d18ac488c13296054Vladimir Marko DCHECK(IsResolved()); 53076649e8d775519fe19f2b14d18ac488c13296054Vladimir Marko uint32_t base = sizeof(mirror::Class); // Static fields come after the class. 531a62cb9bb6cb2278cb41ab0664191623e178c6a4fArtem Udovichenko if (ShouldHaveEmbeddedVTable<kVerifyFlags, kReadBarrierOption>()) { 53276649e8d775519fe19f2b14d18ac488c13296054Vladimir Marko // Static fields come after the embedded tables. 533e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier base = mirror::Class::ComputeClassSize( 534e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier true, GetEmbeddedVTableLength(), 0, 0, 0, 0, 0, pointer_size); 53576649e8d775519fe19f2b14d18ac488c13296054Vladimir Marko } 53676649e8d775519fe19f2b14d18ac488c13296054Vladimir Marko return MemberOffset(base); 53776649e8d775519fe19f2b14d18ac488c13296054Vladimir Marko} 53876649e8d775519fe19f2b14d18ac488c13296054Vladimir Marko 539542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampeinline MemberOffset Class::GetFirstReferenceStaticFieldOffsetDuringLinking( 540542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampe PointerSize pointer_size) { 54176649e8d775519fe19f2b14d18ac488c13296054Vladimir Marko DCHECK(IsLoaded()); 54276649e8d775519fe19f2b14d18ac488c13296054Vladimir Marko uint32_t base = sizeof(mirror::Class); // Static fields come after the class. 543a62cb9bb6cb2278cb41ab0664191623e178c6a4fArtem Udovichenko if (ShouldHaveEmbeddedVTable()) { 54476649e8d775519fe19f2b14d18ac488c13296054Vladimir Marko // Static fields come after the embedded tables. 54576649e8d775519fe19f2b14d18ac488c13296054Vladimir Marko base = mirror::Class::ComputeClassSize(true, GetVTableDuringLinking()->GetLength(), 546e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier 0, 0, 0, 0, 0, pointer_size); 54776649e8d775519fe19f2b14d18ac488c13296054Vladimir Marko } 54876649e8d775519fe19f2b14d18ac488c13296054Vladimir Marko return MemberOffset(base); 54976649e8d775519fe19f2b14d18ac488c13296054Vladimir Marko} 55076649e8d775519fe19f2b14d18ac488c13296054Vladimir Marko 55154d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartierinline void Class::SetIFieldsPtr(LengthPrefixedArray<ArtField>* new_ifields) { 55254d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartier DCHECK(GetIFieldsPtrUnchecked() == nullptr); 553c785344b87221f5e4e6473e5b762e4e61fe65dcfMathieu Chartier return SetFieldPtr<false>(OFFSET_OF_OBJECT_MEMBER(Class, ifields_), new_ifields); 5542dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers} 5552dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 55654d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartierinline void Class::SetIFieldsPtrUnchecked(LengthPrefixedArray<ArtField>* new_ifields) { 557c785344b87221f5e4e6473e5b762e4e61fe65dcfMathieu Chartier SetFieldPtr<false, true, kVerifyNone>(OFFSET_OF_OBJECT_MEMBER(Class, ifields_), new_ifields); 5582dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers} 5592dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 56054d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartierinline LengthPrefixedArray<ArtField>* Class::GetSFieldsPtrUnchecked() { 56154d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartier return GetFieldPtr<LengthPrefixedArray<ArtField>*>(OFFSET_OF_OBJECT_MEMBER(Class, sfields_)); 5622dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers} 5632dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 56454d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartierinline LengthPrefixedArray<ArtField>* Class::GetIFieldsPtrUnchecked() { 56554d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartier return GetFieldPtr<LengthPrefixedArray<ArtField>*>(OFFSET_OF_OBJECT_MEMBER(Class, ifields_)); 5662dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers} 5672dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 56854d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartierinline LengthPrefixedArray<ArtField>* Class::GetSFieldsPtr() { 569c785344b87221f5e4e6473e5b762e4e61fe65dcfMathieu Chartier DCHECK(IsLoaded() || IsErroneous()) << GetStatus(); 57054d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartier return GetSFieldsPtrUnchecked(); 5712dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers} 5722dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 57354d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartierinline void Class::SetSFieldsPtr(LengthPrefixedArray<ArtField>* new_sfields) { 574c785344b87221f5e4e6473e5b762e4e61fe65dcfMathieu Chartier DCHECK((IsRetired() && new_sfields == nullptr) || 575c785344b87221f5e4e6473e5b762e4e61fe65dcfMathieu Chartier GetFieldPtr<ArtField*>(OFFSET_OF_OBJECT_MEMBER(Class, sfields_)) == nullptr); 576c785344b87221f5e4e6473e5b762e4e61fe65dcfMathieu Chartier SetFieldPtr<false>(OFFSET_OF_OBJECT_MEMBER(Class, sfields_), new_sfields); 5772dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers} 5782dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 57954d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartierinline void Class::SetSFieldsPtrUnchecked(LengthPrefixedArray<ArtField>* new_sfields) { 580c785344b87221f5e4e6473e5b762e4e61fe65dcfMathieu Chartier SetFieldPtr<false, true, kVerifyNone>(OFFSET_OF_OBJECT_MEMBER(Class, sfields_), new_sfields); 5812dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers} 5822dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 583c785344b87221f5e4e6473e5b762e4e61fe65dcfMathieu Chartierinline ArtField* Class::GetStaticField(uint32_t i) { 58454d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartier return &GetSFieldsPtr()->At(i); 5852dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers} 5862dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 587c785344b87221f5e4e6473e5b762e4e61fe65dcfMathieu Chartierinline ArtField* Class::GetInstanceField(uint32_t i) { 58854d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartier return &GetIFieldsPtr()->At(i); 5892dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers} 5902dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 591b0fa5dc7769c1e054032f39de0a3f6d6dd06f8cfIan Rogerstemplate<VerifyObjectFlags kVerifyFlags> 592b0fa5dc7769c1e054032f39de0a3f6d6dd06f8cfIan Rogersinline uint32_t Class::GetReferenceInstanceOffsets() { 593b0fa5dc7769c1e054032f39de0a3f6d6dd06f8cfIan Rogers DCHECK(IsResolved<kVerifyFlags>() || IsErroneous<kVerifyFlags>()); 594b0fa5dc7769c1e054032f39de0a3f6d6dd06f8cfIan Rogers return GetField32<kVerifyFlags>(OFFSET_OF_OBJECT_MEMBER(Class, reference_instance_offsets_)); 595b0fa5dc7769c1e054032f39de0a3f6d6dd06f8cfIan Rogers} 596b0fa5dc7769c1e054032f39de0a3f6d6dd06f8cfIan Rogers 597b0fa5dc7769c1e054032f39de0a3f6d6dd06f8cfIan Rogersinline void Class::SetClinitThreadId(pid_t new_clinit_thread_id) { 598b0fa5dc7769c1e054032f39de0a3f6d6dd06f8cfIan Rogers if (Runtime::Current()->IsActiveTransaction()) { 599b0fa5dc7769c1e054032f39de0a3f6d6dd06f8cfIan Rogers SetField32<true>(OFFSET_OF_OBJECT_MEMBER(Class, clinit_thread_id_), new_clinit_thread_id); 600b0fa5dc7769c1e054032f39de0a3f6d6dd06f8cfIan Rogers } else { 601b0fa5dc7769c1e054032f39de0a3f6d6dd06f8cfIan Rogers SetField32<false>(OFFSET_OF_OBJECT_MEMBER(Class, clinit_thread_id_), new_clinit_thread_id); 602b0fa5dc7769c1e054032f39de0a3f6d6dd06f8cfIan Rogers } 603b0fa5dc7769c1e054032f39de0a3f6d6dd06f8cfIan Rogers} 604b0fa5dc7769c1e054032f39de0a3f6d6dd06f8cfIan Rogers 6054e30541a92381fb280cd0be9a1763b713ee4d64cMathieu Chartiertemplate<VerifyObjectFlags kVerifyFlags> 606ef7d42fca18c16fbaf103822ad16f23246e2905dIan Rogersinline uint32_t Class::GetAccessFlags() { 60798d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang // Check class is loaded/retired or this is java.lang.String that has a 6082dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers // circularity issue during loading the names of its members 60998d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang DCHECK(IsIdxLoaded<kVerifyFlags>() || IsRetired<kVerifyFlags>() || 6104e30541a92381fb280cd0be9a1763b713ee4d64cMathieu Chartier IsErroneous<static_cast<VerifyObjectFlags>(kVerifyFlags & ~kVerifyThis)>() || 611e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier this == String::GetJavaLangString()) 612a6928661ad617880c99e3d8199b95871736564dbAndreas Gampe << "IsIdxLoaded=" << IsIdxLoaded<kVerifyFlags>() 613a6928661ad617880c99e3d8199b95871736564dbAndreas Gampe << " IsRetired=" << IsRetired<kVerifyFlags>() 614a6928661ad617880c99e3d8199b95871736564dbAndreas Gampe << " IsErroneous=" << 615a6928661ad617880c99e3d8199b95871736564dbAndreas Gampe IsErroneous<static_cast<VerifyObjectFlags>(kVerifyFlags & ~kVerifyThis)>() 616a6928661ad617880c99e3d8199b95871736564dbAndreas Gampe << " IsString=" << (this == String::GetJavaLangString()) 617705ad49f353d3f90d8b63625aca2c2035bacdbefAlex Light << " status= " << GetStatus<kVerifyFlags>() 618a6928661ad617880c99e3d8199b95871736564dbAndreas Gampe << " descriptor=" << PrettyDescriptor(this); 619e01a520fe0010f8abd344b5ed7120787d7ed1d71Hiroshi Yamauchi return GetField32<kVerifyFlags>(AccessFlagsOffset()); 6202dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers} 6212dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 622ef7d42fca18c16fbaf103822ad16f23246e2905dIan Rogersinline String* Class::GetName() { 623b0fa5dc7769c1e054032f39de0a3f6d6dd06f8cfIan Rogers return GetFieldObject<String>(OFFSET_OF_OBJECT_MEMBER(Class, name_)); 6242dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers} 62552a7f5caebdf359ab877f1928aad59f1e9ad29faMathieu Chartier 6262dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogersinline void Class::SetName(String* name) { 627d2fe10a3a34af171bf1631219cd2d6ff6b7778b5Sebastien Hertz if (Runtime::Current()->IsActiveTransaction()) { 628b0fa5dc7769c1e054032f39de0a3f6d6dd06f8cfIan Rogers SetFieldObject<true>(OFFSET_OF_OBJECT_MEMBER(Class, name_), name); 629d2fe10a3a34af171bf1631219cd2d6ff6b7778b5Sebastien Hertz } else { 630b0fa5dc7769c1e054032f39de0a3f6d6dd06f8cfIan Rogers SetFieldObject<false>(OFFSET_OF_OBJECT_MEMBER(Class, name_), name); 631d2fe10a3a34af171bf1631219cd2d6ff6b7778b5Sebastien Hertz } 6322dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers} 6332dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 634b0fa5dc7769c1e054032f39de0a3f6d6dd06f8cfIan Rogerstemplate<VerifyObjectFlags kVerifyFlags> 635b0fa5dc7769c1e054032f39de0a3f6d6dd06f8cfIan Rogersinline Primitive::Type Class::GetPrimitiveType() { 63633d6903e570daf8f3cf7c1f6ebd9a6dd22c7c23cRoland Levillain static_assert(sizeof(Primitive::Type) == sizeof(int32_t), 63733d6903e570daf8f3cf7c1f6ebd9a6dd22c7c23cRoland Levillain "art::Primitive::Type and int32_t have different sizes."); 638f0edfc355893d53d1104b05501c99ad5ccf305c4Hiroshi Yamauchi int32_t v32 = GetField32<kVerifyFlags>(OFFSET_OF_OBJECT_MEMBER(Class, primitive_type_)); 6398261d02f9523b95013108f271b82bb157ef6f71dMathieu Chartier Primitive::Type type = static_cast<Primitive::Type>(v32 & kPrimitiveTypeMask); 6408261d02f9523b95013108f271b82bb157ef6f71dMathieu Chartier DCHECK_EQ(static_cast<size_t>(v32 >> kPrimitiveTypeSizeShiftShift), 6418261d02f9523b95013108f271b82bb157ef6f71dMathieu Chartier Primitive::ComponentSizeShift(type)); 642f0edfc355893d53d1104b05501c99ad5ccf305c4Hiroshi Yamauchi return type; 643f0edfc355893d53d1104b05501c99ad5ccf305c4Hiroshi Yamauchi} 644f0edfc355893d53d1104b05501c99ad5ccf305c4Hiroshi Yamauchi 645f0edfc355893d53d1104b05501c99ad5ccf305c4Hiroshi Yamauchitemplate<VerifyObjectFlags kVerifyFlags> 646f0edfc355893d53d1104b05501c99ad5ccf305c4Hiroshi Yamauchiinline size_t Class::GetPrimitiveTypeSizeShift() { 64733d6903e570daf8f3cf7c1f6ebd9a6dd22c7c23cRoland Levillain static_assert(sizeof(Primitive::Type) == sizeof(int32_t), 64833d6903e570daf8f3cf7c1f6ebd9a6dd22c7c23cRoland Levillain "art::Primitive::Type and int32_t have different sizes."); 649f0edfc355893d53d1104b05501c99ad5ccf305c4Hiroshi Yamauchi int32_t v32 = GetField32<kVerifyFlags>(OFFSET_OF_OBJECT_MEMBER(Class, primitive_type_)); 6508261d02f9523b95013108f271b82bb157ef6f71dMathieu Chartier size_t size_shift = static_cast<Primitive::Type>(v32 >> kPrimitiveTypeSizeShiftShift); 6518261d02f9523b95013108f271b82bb157ef6f71dMathieu Chartier DCHECK_EQ(size_shift, 6528261d02f9523b95013108f271b82bb157ef6f71dMathieu Chartier Primitive::ComponentSizeShift(static_cast<Primitive::Type>(v32 & kPrimitiveTypeMask))); 653f0edfc355893d53d1104b05501c99ad5ccf305c4Hiroshi Yamauchi return size_shift; 654b0fa5dc7769c1e054032f39de0a3f6d6dd06f8cfIan Rogers} 655b0fa5dc7769c1e054032f39de0a3f6d6dd06f8cfIan Rogers 6563b4c18933c24b8a33f38573c2ebcdb9aa16efeb5Hiroshi Yamauchiinline void Class::CheckObjectAlloc() { 6574cd662e54440f76fc920cb2c67acab3bba8b33ddHiroshi Yamauchi DCHECK(!IsArrayClass()) 6584cd662e54440f76fc920cb2c67acab3bba8b33ddHiroshi Yamauchi << PrettyClass(this) 6594cd662e54440f76fc920cb2c67acab3bba8b33ddHiroshi Yamauchi << "A array shouldn't be allocated through this " 6604cd662e54440f76fc920cb2c67acab3bba8b33ddHiroshi Yamauchi << "as it requires a pre-fence visitor that sets the class size."; 6614cd662e54440f76fc920cb2c67acab3bba8b33ddHiroshi Yamauchi DCHECK(!IsClassClass()) 6624cd662e54440f76fc920cb2c67acab3bba8b33ddHiroshi Yamauchi << PrettyClass(this) 6634cd662e54440f76fc920cb2c67acab3bba8b33ddHiroshi Yamauchi << "A class object shouldn't be allocated through this " 6644cd662e54440f76fc920cb2c67acab3bba8b33ddHiroshi Yamauchi << "as it requires a pre-fence visitor that sets the class size."; 665848f70a3d73833fc1bf3032a9ff6812e429661d9Jeff Hao DCHECK(!IsStringClass()) 666848f70a3d73833fc1bf3032a9ff6812e429661d9Jeff Hao << PrettyClass(this) 667848f70a3d73833fc1bf3032a9ff6812e429661d9Jeff Hao << "A string shouldn't be allocated through this " 668848f70a3d73833fc1bf3032a9ff6812e429661d9Jeff Hao << "as it requires a pre-fence visitor that sets the class size."; 669967a0adf8b93a23d2a8fef82e06bd913db94ac19Hiroshi Yamauchi DCHECK(IsInstantiable()) << PrettyClass(this); 670967a0adf8b93a23d2a8fef82e06bd913db94ac19Hiroshi Yamauchi // TODO: decide whether we want this check. It currently fails during bootstrap. 671967a0adf8b93a23d2a8fef82e06bd913db94ac19Hiroshi Yamauchi // DCHECK(!Runtime::Current()->IsStarted() || IsInitializing()) << PrettyClass(this); 672967a0adf8b93a23d2a8fef82e06bd913db94ac19Hiroshi Yamauchi DCHECK_GE(this->object_size_, sizeof(Object)); 6733b4c18933c24b8a33f38573c2ebcdb9aa16efeb5Hiroshi Yamauchi} 6743b4c18933c24b8a33f38573c2ebcdb9aa16efeb5Hiroshi Yamauchi 6758668c3cbdcf9471bd97e0da68a240051f2973074Mathieu Chartiertemplate<bool kIsInstrumented, bool kCheckAddFinalizer> 676cbb2d20bea2861f244da2e2318d8c088300a3710Mathieu Chartierinline Object* Class::Alloc(Thread* self, gc::AllocatorType allocator_type) { 6773b4c18933c24b8a33f38573c2ebcdb9aa16efeb5Hiroshi Yamauchi CheckObjectAlloc(); 678590fee9e8972f872301c2d16a575d579ee564beeMathieu Chartier gc::Heap* heap = Runtime::Current()->GetHeap(); 6798668c3cbdcf9471bd97e0da68a240051f2973074Mathieu Chartier const bool add_finalizer = kCheckAddFinalizer && IsFinalizable(); 6808668c3cbdcf9471bd97e0da68a240051f2973074Mathieu Chartier if (!kCheckAddFinalizer) { 6818668c3cbdcf9471bd97e0da68a240051f2973074Mathieu Chartier DCHECK(!IsFinalizable()); 6828668c3cbdcf9471bd97e0da68a240051f2973074Mathieu Chartier } 6838668c3cbdcf9471bd97e0da68a240051f2973074Mathieu Chartier mirror::Object* obj = 6848668c3cbdcf9471bd97e0da68a240051f2973074Mathieu Chartier heap->AllocObjectWithAllocator<kIsInstrumented, false>(self, this, this->object_size_, 6858668c3cbdcf9471bd97e0da68a240051f2973074Mathieu Chartier allocator_type, VoidFunctor()); 6868668c3cbdcf9471bd97e0da68a240051f2973074Mathieu Chartier if (add_finalizer && LIKELY(obj != nullptr)) { 6878668c3cbdcf9471bd97e0da68a240051f2973074Mathieu Chartier heap->AddFinalizerReference(self, &obj); 6883ac90da48e9cd56eb4b392c7f176e9267d146500Pavel Vyssotski if (UNLIKELY(self->IsExceptionPending())) { 6893ac90da48e9cd56eb4b392c7f176e9267d146500Pavel Vyssotski // Failed to allocate finalizer reference, it means that the whole allocation failed. 6903ac90da48e9cd56eb4b392c7f176e9267d146500Pavel Vyssotski obj = nullptr; 6913ac90da48e9cd56eb4b392c7f176e9267d146500Pavel Vyssotski } 6928668c3cbdcf9471bd97e0da68a240051f2973074Mathieu Chartier } 6938668c3cbdcf9471bd97e0da68a240051f2973074Mathieu Chartier return obj; 694cbb2d20bea2861f244da2e2318d8c088300a3710Mathieu Chartier} 695cbb2d20bea2861f244da2e2318d8c088300a3710Mathieu Chartier 696cbb2d20bea2861f244da2e2318d8c088300a3710Mathieu Chartierinline Object* Class::AllocObject(Thread* self) { 697cbb2d20bea2861f244da2e2318d8c088300a3710Mathieu Chartier return Alloc<true>(self, Runtime::Current()->GetHeap()->GetCurrentAllocator()); 698cbb2d20bea2861f244da2e2318d8c088300a3710Mathieu Chartier} 699cbb2d20bea2861f244da2e2318d8c088300a3710Mathieu Chartier 700cbb2d20bea2861f244da2e2318d8c088300a3710Mathieu Chartierinline Object* Class::AllocNonMovableObject(Thread* self) { 701cbb2d20bea2861f244da2e2318d8c088300a3710Mathieu Chartier return Alloc<true>(self, Runtime::Current()->GetHeap()->GetCurrentNonMovingAllocator()); 702967a0adf8b93a23d2a8fef82e06bd913db94ac19Hiroshi Yamauchi} 703967a0adf8b93a23d2a8fef82e06bd913db94ac19Hiroshi Yamauchi 704a62cb9bb6cb2278cb41ab0664191623e178c6a4fArtem Udovichenkoinline uint32_t Class::ComputeClassSize(bool has_embedded_vtable, 70598d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang uint32_t num_vtable_entries, 70637f05ef45e0393de812d51261dc293240c17294dFred Shih uint32_t num_8bit_static_fields, 70737f05ef45e0393de812d51261dc293240c17294dFred Shih uint32_t num_16bit_static_fields, 70898d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang uint32_t num_32bit_static_fields, 70998d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang uint32_t num_64bit_static_fields, 710e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier uint32_t num_ref_static_fields, 711542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampe PointerSize pointer_size) { 71298d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang // Space used by java.lang.Class and its instance fields. 71398d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang uint32_t size = sizeof(Class); 71498d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang // Space used by embedded tables. 715a62cb9bb6cb2278cb41ab0664191623e178c6a4fArtem Udovichenko if (has_embedded_vtable) { 716542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampe size = RoundUp(size + sizeof(uint32_t), static_cast<size_t>(pointer_size)); 717542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampe size += static_cast<size_t>(pointer_size); // size of pointer to IMT 718a62cb9bb6cb2278cb41ab0664191623e178c6a4fArtem Udovichenko size += num_vtable_entries * VTableEntrySize(pointer_size); 71998d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang } 72037f05ef45e0393de812d51261dc293240c17294dFred Shih 72198d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang // Space used by reference statics. 722e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier size += num_ref_static_fields * sizeof(HeapReference<Object>); 72337f05ef45e0393de812d51261dc293240c17294dFred Shih if (!IsAligned<8>(size) && num_64bit_static_fields > 0) { 72437f05ef45e0393de812d51261dc293240c17294dFred Shih uint32_t gap = 8 - (size & 0x7); 72537f05ef45e0393de812d51261dc293240c17294dFred Shih size += gap; // will be padded 72637f05ef45e0393de812d51261dc293240c17294dFred Shih // Shuffle 4-byte fields forward. 72737f05ef45e0393de812d51261dc293240c17294dFred Shih while (gap >= sizeof(uint32_t) && num_32bit_static_fields != 0) { 72837f05ef45e0393de812d51261dc293240c17294dFred Shih --num_32bit_static_fields; 72937f05ef45e0393de812d51261dc293240c17294dFred Shih gap -= sizeof(uint32_t); 73037f05ef45e0393de812d51261dc293240c17294dFred Shih } 73137f05ef45e0393de812d51261dc293240c17294dFred Shih // Shuffle 2-byte fields forward. 73237f05ef45e0393de812d51261dc293240c17294dFred Shih while (gap >= sizeof(uint16_t) && num_16bit_static_fields != 0) { 73337f05ef45e0393de812d51261dc293240c17294dFred Shih --num_16bit_static_fields; 73437f05ef45e0393de812d51261dc293240c17294dFred Shih gap -= sizeof(uint16_t); 73537f05ef45e0393de812d51261dc293240c17294dFred Shih } 73637f05ef45e0393de812d51261dc293240c17294dFred Shih // Shuffle byte fields forward. 73737f05ef45e0393de812d51261dc293240c17294dFred Shih while (gap >= sizeof(uint8_t) && num_8bit_static_fields != 0) { 73837f05ef45e0393de812d51261dc293240c17294dFred Shih --num_8bit_static_fields; 73937f05ef45e0393de812d51261dc293240c17294dFred Shih gap -= sizeof(uint8_t); 7402cdbad7c62f126581ec5177104de961c4d71adaaMingyao Yang } 74198d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang } 74237f05ef45e0393de812d51261dc293240c17294dFred Shih // Guaranteed to be at least 4 byte aligned. No need for further alignments. 74398d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang // Space used for primitive static fields. 744e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier size += num_8bit_static_fields * sizeof(uint8_t) + num_16bit_static_fields * sizeof(uint16_t) + 745e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier num_32bit_static_fields * sizeof(uint32_t) + num_64bit_static_fields * sizeof(uint64_t); 74698d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang return size; 74798d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang} 74898d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang 749fbc31087932a65e036a153afab3049dc5298656aMathieu Chartiertemplate <bool kVisitNativeRoots, 750fbc31087932a65e036a153afab3049dc5298656aMathieu Chartier VerifyObjectFlags kVerifyFlags, 751fbc31087932a65e036a153afab3049dc5298656aMathieu Chartier ReadBarrierOption kReadBarrierOption, 752fbc31087932a65e036a153afab3049dc5298656aMathieu Chartier typename Visitor> 753407f702da4f867c074fc3c8c688b8f8c32279effMathieu Chartierinline void Class::VisitReferences(mirror::Class* klass, const Visitor& visitor) { 754fbc31087932a65e036a153afab3049dc5298656aMathieu Chartier VisitInstanceFieldsReferences<kVerifyFlags, kReadBarrierOption>(klass, visitor); 7552cd334ae2d4287216523882f0d298cf3901b7ab1Hiroshi Yamauchi // Right after a class is allocated, but not yet loaded 756c449e8b79aaaf156ce055524c41474cc1200ed5aIgor Murashkin // (kStatusNotReady, see ClassLinker::LoadClass()), GC may find it 7572cd334ae2d4287216523882f0d298cf3901b7ab1Hiroshi Yamauchi // and scan it. IsTemp() may call Class::GetAccessFlags() but may 7582cd334ae2d4287216523882f0d298cf3901b7ab1Hiroshi Yamauchi // fail in the DCHECK in Class::GetAccessFlags() because the class 7592cd334ae2d4287216523882f0d298cf3901b7ab1Hiroshi Yamauchi // status is kStatusNotReady. To avoid it, rely on IsResolved() 7602cd334ae2d4287216523882f0d298cf3901b7ab1Hiroshi Yamauchi // only. This is fine because a temp class never goes into the 7612cd334ae2d4287216523882f0d298cf3901b7ab1Hiroshi Yamauchi // kStatusResolved state. 762fbc31087932a65e036a153afab3049dc5298656aMathieu Chartier if (IsResolved<kVerifyFlags>()) { 76398d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang // Temp classes don't ever populate imt/vtable or static fields and they are not even 764f4c15a18eb055735857a280856be5b142e0c1113Hiroshi Yamauchi // allocated with the right size for those. Also, unresolved classes don't have fields 765f4c15a18eb055735857a280856be5b142e0c1113Hiroshi Yamauchi // linked yet. 766fbc31087932a65e036a153afab3049dc5298656aMathieu Chartier VisitStaticFieldsReferences<kVerifyFlags, kReadBarrierOption>(this, visitor); 767fbc31087932a65e036a153afab3049dc5298656aMathieu Chartier } 768fbc31087932a65e036a153afab3049dc5298656aMathieu Chartier if (kVisitNativeRoots) { 769fbc31087932a65e036a153afab3049dc5298656aMathieu Chartier // Since this class is reachable, we must also visit the associated roots when we scan it. 7707a62e6728463237684d3d9834d81bd7bba7ab197Hiroshi Yamauchi VisitNativeRoots<kReadBarrierOption>( 7717a62e6728463237684d3d9834d81bd7bba7ab197Hiroshi Yamauchi visitor, Runtime::Current()->GetClassLinker()->GetImagePointerSize()); 77298d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang } 773407f702da4f867c074fc3c8c688b8f8c32279effMathieu Chartier} 774407f702da4f867c074fc3c8c688b8f8c32279effMathieu Chartier 7754f1ebc2b86c8467d1ecb3ec655316e6d7ee8b8b5Hiroshi Yamauchitemplate<ReadBarrierOption kReadBarrierOption> 7764ee7a665e7f9cd2c5ace2d6304e33f64067b209fFred Shihinline bool Class::IsReferenceClass() const { 7774ee7a665e7f9cd2c5ace2d6304e33f64067b209fFred Shih return this == Reference::GetJavaLangRefReference<kReadBarrierOption>(); 7784ee7a665e7f9cd2c5ace2d6304e33f64067b209fFred Shih} 7794ee7a665e7f9cd2c5ace2d6304e33f64067b209fFred Shih 78025023c744c4388a6459b21cc3babf8c602b024a2Hiroshi Yamauchitemplate<VerifyObjectFlags kVerifyFlags, ReadBarrierOption kReadBarrierOption> 78125023c744c4388a6459b21cc3babf8c602b024a2Hiroshi Yamauchiinline bool Class::IsClassClass() { 78225023c744c4388a6459b21cc3babf8c602b024a2Hiroshi Yamauchi Class* java_lang_Class = GetClass<kVerifyFlags, kReadBarrierOption>()-> 78325023c744c4388a6459b21cc3babf8c602b024a2Hiroshi Yamauchi template GetClass<kVerifyFlags, kReadBarrierOption>(); 78425023c744c4388a6459b21cc3babf8c602b024a2Hiroshi Yamauchi return this == java_lang_Class; 78525023c744c4388a6459b21cc3babf8c602b024a2Hiroshi Yamauchi} 78625023c744c4388a6459b21cc3babf8c602b024a2Hiroshi Yamauchi 787f832284dd847ff077577bb5712225430bbbb3b67Mathieu Chartierinline const DexFile& Class::GetDexFile() { 7883a0909248e04b22c3981cbf617bc2502ed5b6380Nicolas Geoffray return *GetDexCache()->GetDexFile(); 789f832284dd847ff077577bb5712225430bbbb3b67Mathieu Chartier} 790f832284dd847ff077577bb5712225430bbbb3b67Mathieu Chartier 791f832284dd847ff077577bb5712225430bbbb3b67Mathieu Chartierinline bool Class::DescriptorEquals(const char* match) { 7921ff3c98775a4577cf053dba9a0c2d5c21c07b298Ian Rogers if (IsArrayClass()) { 793f832284dd847ff077577bb5712225430bbbb3b67Mathieu Chartier return match[0] == '[' && GetComponentType()->DescriptorEquals(match + 1); 7941ff3c98775a4577cf053dba9a0c2d5c21c07b298Ian Rogers } else if (IsPrimitive()) { 795f832284dd847ff077577bb5712225430bbbb3b67Mathieu Chartier return strcmp(Primitive::Descriptor(GetPrimitiveType()), match) == 0; 7963a0909248e04b22c3981cbf617bc2502ed5b6380Nicolas Geoffray } else if (IsProxyClass()) { 7973a0909248e04b22c3981cbf617bc2502ed5b6380Nicolas Geoffray return ProxyDescriptorEquals(match); 798f832284dd847ff077577bb5712225430bbbb3b67Mathieu Chartier } else { 799f832284dd847ff077577bb5712225430bbbb3b67Mathieu Chartier const DexFile& dex_file = GetDexFile(); 800f832284dd847ff077577bb5712225430bbbb3b67Mathieu Chartier const DexFile::TypeId& type_id = dex_file.GetTypeId(GetClassDef()->class_idx_); 801f832284dd847ff077577bb5712225430bbbb3b67Mathieu Chartier return strcmp(dex_file.GetTypeDescriptor(type_id), match) == 0; 802f832284dd847ff077577bb5712225430bbbb3b67Mathieu Chartier } 803f832284dd847ff077577bb5712225430bbbb3b67Mathieu Chartier} 804f832284dd847ff077577bb5712225430bbbb3b67Mathieu Chartier 8054e99b3d8955131f3fc71aa113f0fa71f0092cb6fSebastien Hertzinline void Class::AssertInitializedOrInitializingInThread(Thread* self) { 8064e99b3d8955131f3fc71aa113f0fa71f0092cb6fSebastien Hertz if (kIsDebugBuild && !IsInitialized()) { 8074e99b3d8955131f3fc71aa113f0fa71f0092cb6fSebastien Hertz CHECK(IsInitializing()) << PrettyClass(this) << " is not initializing: " << GetStatus(); 8084e99b3d8955131f3fc71aa113f0fa71f0092cb6fSebastien Hertz CHECK_EQ(GetClinitThreadId(), self->GetTid()) << PrettyClass(this) 8094e99b3d8955131f3fc71aa113f0fa71f0092cb6fSebastien Hertz << " is initializing in a different thread"; 8104e99b3d8955131f3fc71aa113f0fa71f0092cb6fSebastien Hertz } 8114e99b3d8955131f3fc71aa113f0fa71f0092cb6fSebastien Hertz} 8124e99b3d8955131f3fc71aa113f0fa71f0092cb6fSebastien Hertz 8133a0909248e04b22c3981cbf617bc2502ed5b6380Nicolas Geoffrayinline ObjectArray<Class>* Class::GetInterfaces() { 8143a0909248e04b22c3981cbf617bc2502ed5b6380Nicolas Geoffray CHECK(IsProxyClass()); 81598d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang // First static field. 816c785344b87221f5e4e6473e5b762e4e61fe65dcfMathieu Chartier auto* field = GetStaticField(0); 817c785344b87221f5e4e6473e5b762e4e61fe65dcfMathieu Chartier DCHECK_STREQ(field->GetName(), "interfaces"); 818c785344b87221f5e4e6473e5b762e4e61fe65dcfMathieu Chartier MemberOffset field_offset = field->GetOffset(); 8193a0909248e04b22c3981cbf617bc2502ed5b6380Nicolas Geoffray return GetFieldObject<ObjectArray<Class>>(field_offset); 82098d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang} 82198d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang 8223a0909248e04b22c3981cbf617bc2502ed5b6380Nicolas Geoffrayinline ObjectArray<ObjectArray<Class>>* Class::GetThrows() { 8233a0909248e04b22c3981cbf617bc2502ed5b6380Nicolas Geoffray CHECK(IsProxyClass()); 82498d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang // Second static field. 825c785344b87221f5e4e6473e5b762e4e61fe65dcfMathieu Chartier auto* field = GetStaticField(1); 826c785344b87221f5e4e6473e5b762e4e61fe65dcfMathieu Chartier DCHECK_STREQ(field->GetName(), "throws"); 827c785344b87221f5e4e6473e5b762e4e61fe65dcfMathieu Chartier MemberOffset field_offset = field->GetOffset(); 8283a0909248e04b22c3981cbf617bc2502ed5b6380Nicolas Geoffray return GetFieldObject<ObjectArray<ObjectArray<Class>>>(field_offset); 82998d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang} 83098d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang 8314ee7a665e7f9cd2c5ace2d6304e33f64067b209fFred Shihinline MemberOffset Class::GetDisableIntrinsicFlagOffset() { 8324ee7a665e7f9cd2c5ace2d6304e33f64067b209fFred Shih CHECK(IsReferenceClass()); 8334ee7a665e7f9cd2c5ace2d6304e33f64067b209fFred Shih // First static field 834c785344b87221f5e4e6473e5b762e4e61fe65dcfMathieu Chartier auto* field = GetStaticField(0); 835c785344b87221f5e4e6473e5b762e4e61fe65dcfMathieu Chartier DCHECK_STREQ(field->GetName(), "disableIntrinsic"); 836c785344b87221f5e4e6473e5b762e4e61fe65dcfMathieu Chartier return field->GetOffset(); 8374ee7a665e7f9cd2c5ace2d6304e33f64067b209fFred Shih} 8384ee7a665e7f9cd2c5ace2d6304e33f64067b209fFred Shih 8394ee7a665e7f9cd2c5ace2d6304e33f64067b209fFred Shihinline MemberOffset Class::GetSlowPathFlagOffset() { 8404ee7a665e7f9cd2c5ace2d6304e33f64067b209fFred Shih CHECK(IsReferenceClass()); 8414ee7a665e7f9cd2c5ace2d6304e33f64067b209fFred Shih // Second static field 842c785344b87221f5e4e6473e5b762e4e61fe65dcfMathieu Chartier auto* field = GetStaticField(1); 843c785344b87221f5e4e6473e5b762e4e61fe65dcfMathieu Chartier DCHECK_STREQ(field->GetName(), "slowPathEnabled"); 844c785344b87221f5e4e6473e5b762e4e61fe65dcfMathieu Chartier return field->GetOffset(); 8454ee7a665e7f9cd2c5ace2d6304e33f64067b209fFred Shih} 8464ee7a665e7f9cd2c5ace2d6304e33f64067b209fFred Shih 8474ee7a665e7f9cd2c5ace2d6304e33f64067b209fFred Shihinline bool Class::GetSlowPathEnabled() { 84837f05ef45e0393de812d51261dc293240c17294dFred Shih return GetFieldBoolean(GetSlowPathFlagOffset()); 8494ee7a665e7f9cd2c5ace2d6304e33f64067b209fFred Shih} 8504ee7a665e7f9cd2c5ace2d6304e33f64067b209fFred Shih 8514ee7a665e7f9cd2c5ace2d6304e33f64067b209fFred Shihinline void Class::SetSlowPath(bool enabled) { 852310008008c90fea246efd00cb99ee7ded97c5209Mathieu Chartier SetFieldBoolean<false, false>(GetSlowPathFlagOffset(), enabled); 8534ee7a665e7f9cd2c5ace2d6304e33f64067b209fFred Shih} 8544ee7a665e7f9cd2c5ace2d6304e33f64067b209fFred Shih 85598d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yanginline void Class::InitializeClassVisitor::operator()( 85698d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang mirror::Object* obj, size_t usable_size) const { 85798d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang DCHECK_LE(class_size_, usable_size); 85898d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang // Avoid AsClass as object is not yet in live bitmap or allocation stack. 85998d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang mirror::Class* klass = down_cast<mirror::Class*>(obj); 86098d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang // DCHECK(klass->IsClass()); 86198d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang klass->SetClassSize(class_size_); 86298d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang klass->SetPrimitiveType(Primitive::kPrimNot); // Default to not being primitive. 86398d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang klass->SetDexClassDefIndex(DexFile::kDexNoIndex16); // Default to no valid class def index. 86498d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang klass->SetDexTypeIndex(DexFile::kDexNoIndex16); // Default to no valid type index. 86598d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang} 86698d1cc8033251c93786e2fa8c59a2e555a9493beMingyao Yang 86748498591b90a8ff7b24b1ce05c220e3bc42013dfAndreas Gampeinline void Class::SetAccessFlags(uint32_t new_access_flags) { 86848498591b90a8ff7b24b1ce05c220e3bc42013dfAndreas Gampe // Called inside a transaction when setting pre-verified flag during boot image compilation. 86948498591b90a8ff7b24b1ce05c220e3bc42013dfAndreas Gampe if (Runtime::Current()->IsActiveTransaction()) { 87052a7f5caebdf359ab877f1928aad59f1e9ad29faMathieu Chartier SetField32<true>(AccessFlagsOffset(), new_access_flags); 87152a7f5caebdf359ab877f1928aad59f1e9ad29faMathieu Chartier } else { 87252a7f5caebdf359ab877f1928aad59f1e9ad29faMathieu Chartier SetField32<false>(AccessFlagsOffset(), new_access_flags); 87352a7f5caebdf359ab877f1928aad59f1e9ad29faMathieu Chartier } 87452a7f5caebdf359ab877f1928aad59f1e9ad29faMathieu Chartier} 87552a7f5caebdf359ab877f1928aad59f1e9ad29faMathieu Chartier 87652a7f5caebdf359ab877f1928aad59f1e9ad29faMathieu Chartierinline void Class::SetClassFlags(uint32_t new_flags) { 87752a7f5caebdf359ab877f1928aad59f1e9ad29faMathieu Chartier if (Runtime::Current()->IsActiveTransaction()) { 87852a7f5caebdf359ab877f1928aad59f1e9ad29faMathieu Chartier SetField32<true>(OFFSET_OF_OBJECT_MEMBER(Class, class_flags_), new_flags); 87948498591b90a8ff7b24b1ce05c220e3bc42013dfAndreas Gampe } else { 88052a7f5caebdf359ab877f1928aad59f1e9ad29faMathieu Chartier SetField32<false>(OFFSET_OF_OBJECT_MEMBER(Class, class_flags_), new_flags); 88148498591b90a8ff7b24b1ce05c220e3bc42013dfAndreas Gampe } 88248498591b90a8ff7b24b1ce05c220e3bc42013dfAndreas Gampe} 88348498591b90a8ff7b24b1ce05c220e3bc42013dfAndreas Gampe 8842d2621a1463d2f3f03fa73503fa42e43657cdcfcMathieu Chartierinline uint32_t Class::NumDirectInterfaces() { 8852d2621a1463d2f3f03fa73503fa42e43657cdcfcMathieu Chartier if (IsPrimitive()) { 8862d2621a1463d2f3f03fa73503fa42e43657cdcfcMathieu Chartier return 0; 8872d2621a1463d2f3f03fa73503fa42e43657cdcfcMathieu Chartier } else if (IsArrayClass()) { 8882d2621a1463d2f3f03fa73503fa42e43657cdcfcMathieu Chartier return 2; 8893a0909248e04b22c3981cbf617bc2502ed5b6380Nicolas Geoffray } else if (IsProxyClass()) { 8903a0909248e04b22c3981cbf617bc2502ed5b6380Nicolas Geoffray mirror::ObjectArray<mirror::Class>* interfaces = GetInterfaces(); 8912d2621a1463d2f3f03fa73503fa42e43657cdcfcMathieu Chartier return interfaces != nullptr ? interfaces->GetLength() : 0; 8922d2621a1463d2f3f03fa73503fa42e43657cdcfcMathieu Chartier } else { 8932d2621a1463d2f3f03fa73503fa42e43657cdcfcMathieu Chartier const DexFile::TypeList* interfaces = GetInterfaceTypeList(); 8942d2621a1463d2f3f03fa73503fa42e43657cdcfcMathieu Chartier if (interfaces == nullptr) { 8952d2621a1463d2f3f03fa73503fa42e43657cdcfcMathieu Chartier return 0; 8962d2621a1463d2f3f03fa73503fa42e43657cdcfcMathieu Chartier } else { 8972d2621a1463d2f3f03fa73503fa42e43657cdcfcMathieu Chartier return interfaces->Size(); 8982d2621a1463d2f3f03fa73503fa42e43657cdcfcMathieu Chartier } 8992d2621a1463d2f3f03fa73503fa42e43657cdcfcMathieu Chartier } 9002d2621a1463d2f3f03fa73503fa42e43657cdcfcMathieu Chartier} 9012d2621a1463d2f3f03fa73503fa42e43657cdcfcMathieu Chartier 90205792b98980741111b4d0a24d68cff2a8e070a3aVladimir Markoinline void Class::SetDexCacheStrings(GcRoot<String>* new_dex_cache_strings) { 90305792b98980741111b4d0a24d68cff2a8e070a3aVladimir Marko SetFieldPtr<false>(DexCacheStringsOffset(), new_dex_cache_strings); 904eace45873190a27302b3644c32ec82854b59d299Mathieu Chartier} 905eace45873190a27302b3644c32ec82854b59d299Mathieu Chartier 90605792b98980741111b4d0a24d68cff2a8e070a3aVladimir Markoinline GcRoot<String>* Class::GetDexCacheStrings() { 90705792b98980741111b4d0a24d68cff2a8e070a3aVladimir Marko return GetFieldPtr<GcRoot<String>*>(DexCacheStringsOffset()); 908eace45873190a27302b3644c32ec82854b59d299Mathieu Chartier} 909eace45873190a27302b3644c32ec82854b59d299Mathieu Chartier 9107a62e6728463237684d3d9834d81bd7bba7ab197Hiroshi Yamauchitemplate<ReadBarrierOption kReadBarrierOption, class Visitor> 911542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampevoid mirror::Class::VisitNativeRoots(Visitor& visitor, PointerSize pointer_size) { 91254d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartier for (ArtField& field : GetSFieldsUnchecked()) { 91354d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartier // Visit roots first in case the declaring class gets moved. 91454d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartier field.VisitRoots(visitor); 91554d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartier if (kIsDebugBuild && IsResolved()) { 9167a62e6728463237684d3d9834d81bd7bba7ab197Hiroshi Yamauchi CHECK_EQ(field.GetDeclaringClass<kReadBarrierOption>(), this) << GetStatus(); 917c785344b87221f5e4e6473e5b762e4e61fe65dcfMathieu Chartier } 918c785344b87221f5e4e6473e5b762e4e61fe65dcfMathieu Chartier } 91954d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartier for (ArtField& field : GetIFieldsUnchecked()) { 92054d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartier // Visit roots first in case the declaring class gets moved. 92154d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartier field.VisitRoots(visitor); 92254d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartier if (kIsDebugBuild && IsResolved()) { 9237a62e6728463237684d3d9834d81bd7bba7ab197Hiroshi Yamauchi CHECK_EQ(field.GetDeclaringClass<kReadBarrierOption>(), this) << GetStatus(); 924c785344b87221f5e4e6473e5b762e4e61fe65dcfMathieu Chartier } 925c785344b87221f5e4e6473e5b762e4e61fe65dcfMathieu Chartier } 926e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light for (ArtMethod& method : GetMethods(pointer_size)) { 9277a62e6728463237684d3d9834d81bd7bba7ab197Hiroshi Yamauchi method.VisitRoots<kReadBarrierOption>(visitor, pointer_size); 928e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier } 929e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier} 930e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier 931542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampeinline IterationRange<StrideIterator<ArtMethod>> Class::GetDirectMethods(PointerSize pointer_size) { 932e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier CheckPointerSize(pointer_size); 933e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light return GetDirectMethodsSliceUnchecked(pointer_size).AsRange(); 934e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light} 935e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light 936e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Lightinline IterationRange<StrideIterator<ArtMethod>> Class::GetDeclaredMethods( 937542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampe PointerSize pointer_size) { 938e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light return GetDeclaredMethodsSliceUnchecked(pointer_size).AsRange(); 939e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light} 940e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light 941e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Lightinline IterationRange<StrideIterator<ArtMethod>> Class::GetDeclaredVirtualMethods( 942542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampe PointerSize pointer_size) { 943e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light return GetDeclaredVirtualMethodsSliceUnchecked(pointer_size).AsRange(); 944e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier} 945e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier 946542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampeinline IterationRange<StrideIterator<ArtMethod>> Class::GetVirtualMethods( 947542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampe PointerSize pointer_size) { 948e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier CheckPointerSize(pointer_size); 949e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light return GetVirtualMethodsSliceUnchecked(pointer_size).AsRange(); 950e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light} 951e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light 952542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampeinline IterationRange<StrideIterator<ArtMethod>> Class::GetCopiedMethods(PointerSize pointer_size) { 953e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light CheckPointerSize(pointer_size); 954e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light return GetCopiedMethodsSliceUnchecked(pointer_size).AsRange(); 955e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light} 956e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light 957e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light 958542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampeinline IterationRange<StrideIterator<ArtMethod>> Class::GetMethods(PointerSize pointer_size) { 959e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light CheckPointerSize(pointer_size); 960e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light return MakeIterationRangeFromLengthPrefixedArray(GetMethodsPtr(), 96114632857428b7e37761e6e811c19021715a400f8Vladimir Marko ArtMethod::Size(pointer_size), 96214632857428b7e37761e6e811c19021715a400f8Vladimir Marko ArtMethod::Alignment(pointer_size)); 963e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier} 964e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier 96554d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartierinline IterationRange<StrideIterator<ArtField>> Class::GetIFields() { 966cf36d493124d8048efa0bd6f67d817ce3cd6b725Vladimir Marko return MakeIterationRangeFromLengthPrefixedArray(GetIFieldsPtr()); 967e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier} 968e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier 96954d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartierinline IterationRange<StrideIterator<ArtField>> Class::GetSFields() { 970cf36d493124d8048efa0bd6f67d817ce3cd6b725Vladimir Marko return MakeIterationRangeFromLengthPrefixedArray(GetSFieldsPtr()); 971e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier} 972e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier 97354d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartierinline IterationRange<StrideIterator<ArtField>> Class::GetIFieldsUnchecked() { 974cf36d493124d8048efa0bd6f67d817ce3cd6b725Vladimir Marko return MakeIterationRangeFromLengthPrefixedArray(GetIFieldsPtrUnchecked()); 975e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier} 976e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier 97754d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartierinline IterationRange<StrideIterator<ArtField>> Class::GetSFieldsUnchecked() { 978cf36d493124d8048efa0bd6f67d817ce3cd6b725Vladimir Marko return MakeIterationRangeFromLengthPrefixedArray(GetSFieldsPtrUnchecked()); 979e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier} 980e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier 981542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampeinline MemberOffset Class::EmbeddedVTableOffset(PointerSize pointer_size) { 982e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier CheckPointerSize(pointer_size); 983542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampe return MemberOffset(ImtPtrOffset(pointer_size).Uint32Value() + static_cast<size_t>(pointer_size)); 984e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier} 985e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier 986542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampeinline void Class::CheckPointerSize(PointerSize pointer_size) { 987e401d146407d61eeb99f8d6176b2ac13c4df1e33Mathieu Chartier DCHECK_EQ(pointer_size, Runtime::Current()->GetClassLinker()->GetImagePointerSize()); 988c785344b87221f5e4e6473e5b762e4e61fe65dcfMathieu Chartier} 989c785344b87221f5e4e6473e5b762e4e61fe65dcfMathieu Chartier 9902e76830f0b3f23825677436c0633714402715099Calin Juravletemplate<VerifyObjectFlags kVerifyFlags, ReadBarrierOption kReadBarrierOption> 9912e76830f0b3f23825677436c0633714402715099Calin Juravleinline Class* Class::GetComponentType() { 9922e76830f0b3f23825677436c0633714402715099Calin Juravle return GetFieldObject<Class, kVerifyFlags, kReadBarrierOption>(ComponentTypeOffset()); 9932e76830f0b3f23825677436c0633714402715099Calin Juravle} 9942e76830f0b3f23825677436c0633714402715099Calin Juravle 9952e76830f0b3f23825677436c0633714402715099Calin Juravletemplate<VerifyObjectFlags kVerifyFlags, ReadBarrierOption kReadBarrierOption> 9962e76830f0b3f23825677436c0633714402715099Calin Juravleinline bool Class::IsArrayClass() { 9972e76830f0b3f23825677436c0633714402715099Calin Juravle return GetComponentType<kVerifyFlags, kReadBarrierOption>() != nullptr; 9982e76830f0b3f23825677436c0633714402715099Calin Juravle} 9992e76830f0b3f23825677436c0633714402715099Calin Juravle 10002e76830f0b3f23825677436c0633714402715099Calin Juravleinline bool Class::IsAssignableFrom(Class* src) { 10012e76830f0b3f23825677436c0633714402715099Calin Juravle DCHECK(src != nullptr); 10022e76830f0b3f23825677436c0633714402715099Calin Juravle if (this == src) { 10032e76830f0b3f23825677436c0633714402715099Calin Juravle // Can always assign to things of the same type. 10042e76830f0b3f23825677436c0633714402715099Calin Juravle return true; 10052e76830f0b3f23825677436c0633714402715099Calin Juravle } else if (IsObjectClass()) { 10062e76830f0b3f23825677436c0633714402715099Calin Juravle // Can assign any reference to java.lang.Object. 10072e76830f0b3f23825677436c0633714402715099Calin Juravle return !src->IsPrimitive(); 10082e76830f0b3f23825677436c0633714402715099Calin Juravle } else if (IsInterface()) { 10092e76830f0b3f23825677436c0633714402715099Calin Juravle return src->Implements(this); 10102e76830f0b3f23825677436c0633714402715099Calin Juravle } else if (src->IsArrayClass()) { 10112e76830f0b3f23825677436c0633714402715099Calin Juravle return IsAssignableFromArray(src); 10122e76830f0b3f23825677436c0633714402715099Calin Juravle } else { 10132e76830f0b3f23825677436c0633714402715099Calin Juravle return !src->IsInterface() && src->IsSubClass(this); 10142e76830f0b3f23825677436c0633714402715099Calin Juravle } 10152e76830f0b3f23825677436c0633714402715099Calin Juravle} 10162e76830f0b3f23825677436c0633714402715099Calin Juravle 101754d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartierinline uint32_t Class::NumDirectMethods() { 1018e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light return GetVirtualMethodsStartOffset(); 1019e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light} 1020e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light 1021e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Lightinline uint32_t Class::NumDeclaredVirtualMethods() { 1022e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light return GetCopiedMethodsStartOffset() - GetVirtualMethodsStartOffset(); 102354d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartier} 102454d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartier 102554d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartierinline uint32_t Class::NumVirtualMethods() { 1026e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light return NumMethods() - GetVirtualMethodsStartOffset(); 102754d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartier} 102854d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartier 102954d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartierinline uint32_t Class::NumInstanceFields() { 103054d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartier LengthPrefixedArray<ArtField>* arr = GetIFieldsPtrUnchecked(); 103135831e8bfa1c0944d4c978d99c4c5b9577945170Vladimir Marko return arr != nullptr ? arr->size() : 0u; 103254d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartier} 103354d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartier 103454d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartierinline uint32_t Class::NumStaticFields() { 103554d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartier LengthPrefixedArray<ArtField>* arr = GetSFieldsPtrUnchecked(); 103635831e8bfa1c0944d4c978d99c4c5b9577945170Vladimir Marko return arr != nullptr ? arr->size() : 0u; 103754d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartier} 103854d220eb9cc51215d75b9e0fe921b94bebbb3fd6Mathieu Chartier 1039dfe02f6aafee264478d510b9742ee266ea52e8a8Mathieu Chartiertemplate <VerifyObjectFlags kVerifyFlags, ReadBarrierOption kReadBarrierOption, typename Visitor> 10404b00d3415beb7a816a3b5948f43f3b2e4b856ea8Mathieu Chartierinline void Class::FixupNativePointers(mirror::Class* dest, 1041542451cc546779f5c67840e105c51205a1b0a8fdAndreas Gampe PointerSize pointer_size, 10424b00d3415beb7a816a3b5948f43f3b2e4b856ea8Mathieu Chartier const Visitor& visitor) { 10434b00d3415beb7a816a3b5948f43f3b2e4b856ea8Mathieu Chartier // Update the field arrays. 10444b00d3415beb7a816a3b5948f43f3b2e4b856ea8Mathieu Chartier LengthPrefixedArray<ArtField>* const sfields = GetSFieldsPtr(); 10454b00d3415beb7a816a3b5948f43f3b2e4b856ea8Mathieu Chartier LengthPrefixedArray<ArtField>* const new_sfields = visitor(sfields); 10464b00d3415beb7a816a3b5948f43f3b2e4b856ea8Mathieu Chartier if (sfields != new_sfields) { 10474b00d3415beb7a816a3b5948f43f3b2e4b856ea8Mathieu Chartier dest->SetSFieldsPtrUnchecked(new_sfields); 10484b00d3415beb7a816a3b5948f43f3b2e4b856ea8Mathieu Chartier } 10494b00d3415beb7a816a3b5948f43f3b2e4b856ea8Mathieu Chartier LengthPrefixedArray<ArtField>* const ifields = GetIFieldsPtr(); 10504b00d3415beb7a816a3b5948f43f3b2e4b856ea8Mathieu Chartier LengthPrefixedArray<ArtField>* const new_ifields = visitor(ifields); 10514b00d3415beb7a816a3b5948f43f3b2e4b856ea8Mathieu Chartier if (ifields != new_ifields) { 10524b00d3415beb7a816a3b5948f43f3b2e4b856ea8Mathieu Chartier dest->SetIFieldsPtrUnchecked(new_ifields); 10534b00d3415beb7a816a3b5948f43f3b2e4b856ea8Mathieu Chartier } 1054e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light // Update method array. 1055e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light LengthPrefixedArray<ArtMethod>* methods = GetMethodsPtr(); 1056e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light LengthPrefixedArray<ArtMethod>* new_methods = visitor(methods); 1057e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light if (methods != new_methods) { 1058e64300b8488716056775ecbfa2915dd1b4ce7e08Alex Light dest->SetMethodsPtrInternal(new_methods); 10594b00d3415beb7a816a3b5948f43f3b2e4b856ea8Mathieu Chartier } 10604b00d3415beb7a816a3b5948f43f3b2e4b856ea8Mathieu Chartier // Update dex cache strings. 10614b00d3415beb7a816a3b5948f43f3b2e4b856ea8Mathieu Chartier GcRoot<mirror::String>* strings = GetDexCacheStrings(); 10624b00d3415beb7a816a3b5948f43f3b2e4b856ea8Mathieu Chartier GcRoot<mirror::String>* new_strings = visitor(strings); 10634b00d3415beb7a816a3b5948f43f3b2e4b856ea8Mathieu Chartier if (strings != new_strings) { 10644b00d3415beb7a816a3b5948f43f3b2e4b856ea8Mathieu Chartier dest->SetDexCacheStrings(new_strings); 10654b00d3415beb7a816a3b5948f43f3b2e4b856ea8Mathieu Chartier } 10664b00d3415beb7a816a3b5948f43f3b2e4b856ea8Mathieu Chartier // Fix up embedded tables. 1067a62cb9bb6cb2278cb41ab0664191623e178c6a4fArtem Udovichenko if (!IsTemp() && ShouldHaveEmbeddedVTable<kVerifyNone, kReadBarrierOption>()) { 10684b00d3415beb7a816a3b5948f43f3b2e4b856ea8Mathieu Chartier for (int32_t i = 0, count = GetEmbeddedVTableLength(); i < count; ++i) { 10694b00d3415beb7a816a3b5948f43f3b2e4b856ea8Mathieu Chartier ArtMethod* method = GetEmbeddedVTableEntry(i, pointer_size); 10704b00d3415beb7a816a3b5948f43f3b2e4b856ea8Mathieu Chartier ArtMethod* new_method = visitor(method); 10714b00d3415beb7a816a3b5948f43f3b2e4b856ea8Mathieu Chartier if (method != new_method) { 10724b00d3415beb7a816a3b5948f43f3b2e4b856ea8Mathieu Chartier dest->SetEmbeddedVTableEntryUnchecked(i, new_method, pointer_size); 10734b00d3415beb7a816a3b5948f43f3b2e4b856ea8Mathieu Chartier } 10744b00d3415beb7a816a3b5948f43f3b2e4b856ea8Mathieu Chartier } 1075a62cb9bb6cb2278cb41ab0664191623e178c6a4fArtem Udovichenko } 1076a62cb9bb6cb2278cb41ab0664191623e178c6a4fArtem Udovichenko if (!IsTemp() && ShouldHaveImt<kVerifyNone, kReadBarrierOption>()) { 1077a62cb9bb6cb2278cb41ab0664191623e178c6a4fArtem Udovichenko dest->SetImt(visitor(GetImt(pointer_size)), pointer_size); 10784b00d3415beb7a816a3b5948f43f3b2e4b856ea8Mathieu Chartier } 10794b00d3415beb7a816a3b5948f43f3b2e4b856ea8Mathieu Chartier} 10804b00d3415beb7a816a3b5948f43f3b2e4b856ea8Mathieu Chartier 10812dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers} // namespace mirror 10822dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers} // namespace art 10832dd0e2cea360bc9206eb88ecc40d259e796c239dIan Rogers 1084fc0e3219edc9a5bf81b166e82fd5db2796eb6a0dBrian Carlstrom#endif // ART_RUNTIME_MIRROR_CLASS_INL_H_ 1085