blob: 72b4c030f81e30c98a45c313870aca2137d31864 [file] [log] [blame]
Elliott Hughes0f3c5532012-03-30 14:51:51 -07001/*
2 * Copyright (C) 2012 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
buzbee54330722011-08-23 16:46:55 -070016
Ian Rogers7655f292013-07-29 11:07:13 -070017#ifndef ART_RUNTIME_ENTRYPOINTS_ENTRYPOINT_UTILS_H_
18#define ART_RUNTIME_ENTRYPOINTS_ENTRYPOINT_UTILS_H_
Ian Rogers450dcb52013-09-20 17:36:02 -070019
Mingyao Yang98d1cc82014-05-15 17:02:16 -070020#include <jni.h>
21#include <stdint.h>
22
Andreas Gampe8228cdf2017-05-30 15:03:54 -070023#include "base/callee_save_type.h"
Andreas Gampe7fbc4a52018-11-28 08:26:47 -080024#include "base/locks.h"
Ian Rogers450dcb52013-09-20 17:36:02 -070025#include "base/macros.h"
David Sehr9e734c72018-01-04 17:56:19 -080026#include "dex/dex_file_types.h"
27#include "dex/dex_instruction.h"
Mingyao Yang98d1cc82014-05-15 17:02:16 -070028#include "gc/allocator_type.h"
Mathieu Chartierbe08cf52016-09-13 13:41:24 -070029#include "handle.h"
Mingyao Yang98d1cc82014-05-15 17:02:16 -070030#include "jvalue.h"
Ian Rogers57b86d42012-03-27 16:05:41 -070031
Shih-wei Liao2d831012011-09-28 22:06:53 -070032namespace art {
Ian Rogers848871b2013-08-05 10:56:33 -070033
Ian Rogers2dd0e2c2013-01-24 12:42:14 -080034namespace mirror {
Igor Murashkin2ffb7032017-11-08 13:35:21 -080035class Array;
36class Class;
Orion Hodsondbaa5c72018-05-10 08:22:46 +010037class MethodHandle;
Orion Hodson18259d72018-04-12 11:18:23 +010038class MethodType;
Igor Murashkin2ffb7032017-11-08 13:35:21 -080039class Object;
40class String;
Ian Rogers848871b2013-08-05 10:56:33 -070041} // namespace mirror
Ian Rogers57b86d42012-03-27 16:05:41 -070042
Mathieu Chartierc7853442015-03-27 14:35:38 -070043class ArtField;
Mathieu Chartiere401d142015-04-22 13:56:20 -070044class ArtMethod;
Vladimir Marko6e043bb2020-02-10 16:56:54 +000045class HandleScope;
Andreas Gampe04c6ab92017-06-08 21:49:14 -070046enum InvokeType : uint32_t;
Vladimir Marko86c87522020-05-11 16:55:55 +010047class MethodReference;
Nicolas Geoffray524e7ea2015-10-16 17:13:34 +010048class OatQuickMethodHeader;
Mingyao Yang98d1cc82014-05-15 17:02:16 -070049class ScopedObjectAccessAlreadyRunnable;
50class Thread;
51
Ian Rogers57b86d42012-03-27 16:05:41 -070052// Given the context of a calling Method, use its DexCache to resolve a type to a Class. If it
53// cannot be resolved, throw an error. If it can, use it to create an instance.
Vladimir Marko9b81ac32019-05-16 16:47:08 +010054template <bool kInstrumented = true>
Vladimir Marko4bb2af52019-03-22 11:09:19 +000055ALWAYS_INLINE inline ObjPtr<mirror::Object> AllocObjectFromCode(ObjPtr<mirror::Class> klass,
56 Thread* self,
57 gc::AllocatorType allocator_type)
Mathieu Chartierbe08cf52016-09-13 13:41:24 -070058 REQUIRES_SHARED(Locks::mutator_lock_)
59 REQUIRES(!Roles::uninterruptible_);
Hiroshi Yamauchi3b4c1892013-09-12 21:33:12 -070060
Hiroshi Yamauchibe1ca552014-01-15 11:46:48 -080061// Given the context of a calling Method and a resolved class, create an instance.
Hiroshi Yamauchibe1ca552014-01-15 11:46:48 -080062template <bool kInstrumented>
Vladimir Marko4bb2af52019-03-22 11:09:19 +000063ALWAYS_INLINE
64inline ObjPtr<mirror::Object> AllocObjectFromCodeResolved(ObjPtr<mirror::Class> klass,
65 Thread* self,
66 gc::AllocatorType allocator_type)
Mathieu Chartierbe08cf52016-09-13 13:41:24 -070067 REQUIRES_SHARED(Locks::mutator_lock_)
68 REQUIRES(!Roles::uninterruptible_);
Hiroshi Yamauchibe1ca552014-01-15 11:46:48 -080069
70// Given the context of a calling Method and an initialized class, create an instance.
Hiroshi Yamauchibe1ca552014-01-15 11:46:48 -080071template <bool kInstrumented>
Vladimir Marko4bb2af52019-03-22 11:09:19 +000072ALWAYS_INLINE
73inline ObjPtr<mirror::Object> AllocObjectFromCodeInitialized(ObjPtr<mirror::Class> klass,
74 Thread* self,
75 gc::AllocatorType allocator_type)
Mathieu Chartierbe08cf52016-09-13 13:41:24 -070076 REQUIRES_SHARED(Locks::mutator_lock_)
77 REQUIRES(!Roles::uninterruptible_);
Hiroshi Yamauchibe1ca552014-01-15 11:46:48 -080078
79
Mathieu Chartiercbb2d202013-11-14 17:45:16 -080080template <bool kAccessCheck>
Vladimir Marko4bb2af52019-03-22 11:09:19 +000081ALWAYS_INLINE inline ObjPtr<mirror::Class> CheckArrayAlloc(dex::TypeIndex type_idx,
82 int32_t component_count,
83 ArtMethod* method,
84 bool* slow_path)
Mathieu Chartierbe08cf52016-09-13 13:41:24 -070085 REQUIRES_SHARED(Locks::mutator_lock_)
86 REQUIRES(!Roles::uninterruptible_);
Ian Rogers57b86d42012-03-27 16:05:41 -070087
88// Given the context of a calling Method, use its DexCache to resolve a type to an array Class. If
89// it cannot be resolved, throw an error. If it can, use it to create an array.
90// When verification/compiler hasn't been able to verify access, optionally perform an access
91// check.
Vladimir Marko9b81ac32019-05-16 16:47:08 +010092template <bool kAccessCheck, bool kInstrumented = true>
Vladimir Markobcf17522018-06-01 13:14:32 +010093ALWAYS_INLINE inline ObjPtr<mirror::Array> AllocArrayFromCode(dex::TypeIndex type_idx,
94 int32_t component_count,
95 ArtMethod* method,
96 Thread* self,
97 gc::AllocatorType allocator_type)
Mathieu Chartierbe08cf52016-09-13 13:41:24 -070098 REQUIRES_SHARED(Locks::mutator_lock_)
99 REQUIRES(!Roles::uninterruptible_);
Ian Rogers57b86d42012-03-27 16:05:41 -0700100
Nicolas Geoffraye761bcc2017-01-19 08:59:37 +0000101template <bool kInstrumented>
Vladimir Marko4bb2af52019-03-22 11:09:19 +0000102ALWAYS_INLINE
103inline ObjPtr<mirror::Array> AllocArrayFromCodeResolved(ObjPtr<mirror::Class> klass,
104 int32_t component_count,
105 Thread* self,
106 gc::AllocatorType allocator_type)
Mathieu Chartierbe08cf52016-09-13 13:41:24 -0700107 REQUIRES_SHARED(Locks::mutator_lock_)
108 REQUIRES(!Roles::uninterruptible_);
Hiroshi Yamauchibb8f0ab2014-01-27 16:50:29 -0800109
David Srbeckyce32c102018-08-31 07:21:07 +0100110enum FindFieldFlags {
111 InstanceBit = 1 << 0,
112 StaticBit = 1 << 1,
113 ObjectBit = 1 << 2,
114 PrimitiveBit = 1 << 3,
115 ReadBit = 1 << 4,
116 WriteBit = 1 << 5,
117};
118
Ian Rogers08f753d2012-08-24 14:35:25 -0700119// Type of find field operation for fast and slow case.
120enum FindFieldType {
David Srbeckyce32c102018-08-31 07:21:07 +0100121 InstanceObjectRead = InstanceBit | ObjectBit | ReadBit,
122 InstanceObjectWrite = InstanceBit | ObjectBit | WriteBit,
123 InstancePrimitiveRead = InstanceBit | PrimitiveBit | ReadBit,
124 InstancePrimitiveWrite = InstanceBit | PrimitiveBit | WriteBit,
125 StaticObjectRead = StaticBit | ObjectBit | ReadBit,
126 StaticObjectWrite = StaticBit | ObjectBit | WriteBit,
127 StaticPrimitiveRead = StaticBit | PrimitiveBit | ReadBit,
128 StaticPrimitiveWrite = StaticBit | PrimitiveBit | WriteBit,
Ian Rogers08f753d2012-08-24 14:35:25 -0700129};
130
Sebastien Hertzd4beb6b2013-10-02 17:07:20 +0200131template<FindFieldType type, bool access_check>
Mathieu Chartierbe08cf52016-09-13 13:41:24 -0700132inline ArtField* FindFieldFromCode(uint32_t field_idx,
133 ArtMethod* referrer,
134 Thread* self,
135 size_t expected_size)
136 REQUIRES_SHARED(Locks::mutator_lock_)
137 REQUIRES(!Roles::uninterruptible_);
Sebastien Hertzd4beb6b2013-10-02 17:07:20 +0200138
139template<InvokeType type, bool access_check>
Mathieu Chartierbe08cf52016-09-13 13:41:24 -0700140inline ArtMethod* FindMethodFromCode(uint32_t method_idx,
Mathieu Chartieref41db72016-10-25 15:08:01 -0700141 ObjPtr<mirror::Object>* this_object,
Mathieu Chartierbe08cf52016-09-13 13:41:24 -0700142 ArtMethod* referrer,
143 Thread* self)
144 REQUIRES_SHARED(Locks::mutator_lock_)
145 REQUIRES(!Roles::uninterruptible_);
Ian Rogers57b86d42012-03-27 16:05:41 -0700146
Ian Rogers08f753d2012-08-24 14:35:25 -0700147// Fast path field resolution that can't initialize classes or throw exceptions.
Mathieu Chartierbe08cf52016-09-13 13:41:24 -0700148inline ArtField* FindFieldFast(uint32_t field_idx,
149 ArtMethod* referrer,
150 FindFieldType type,
151 size_t expected_size)
Andreas Gampebdf7f1c2016-08-30 16:38:47 -0700152 REQUIRES_SHARED(Locks::mutator_lock_);
Ian Rogers57b86d42012-03-27 16:05:41 -0700153
Ian Rogers08f753d2012-08-24 14:35:25 -0700154// Fast path method resolution that can't throw exceptions.
Vladimir Markof79aa7f2017-07-04 16:58:55 +0100155template <InvokeType type, bool access_check>
Mathieu Chartierbe08cf52016-09-13 13:41:24 -0700156inline ArtMethod* FindMethodFast(uint32_t method_idx,
Mathieu Chartieref41db72016-10-25 15:08:01 -0700157 ObjPtr<mirror::Object> this_object,
Vladimir Markof79aa7f2017-07-04 16:58:55 +0100158 ArtMethod* referrer)
Andreas Gampebdf7f1c2016-08-30 16:38:47 -0700159 REQUIRES_SHARED(Locks::mutator_lock_);
Ian Rogers57b86d42012-03-27 16:05:41 -0700160
Vladimir Marko28e012a2017-12-07 11:22:59 +0000161inline ObjPtr<mirror::Class> ResolveVerifyAndClinit(dex::TypeIndex type_idx,
162 ArtMethod* referrer,
163 Thread* self,
164 bool can_run_clinit,
165 bool verify_access)
Mathieu Chartierbe08cf52016-09-13 13:41:24 -0700166 REQUIRES_SHARED(Locks::mutator_lock_)
167 REQUIRES(!Roles::uninterruptible_);
Ian Rogers57b86d42012-03-27 16:05:41 -0700168
Orion Hodsondbaa5c72018-05-10 08:22:46 +0100169ObjPtr<mirror::MethodHandle> ResolveMethodHandleFromCode(ArtMethod* referrer,
170 uint32_t method_handle_idx)
171 REQUIRES_SHARED(Locks::mutator_lock_)
172 REQUIRES(!Roles::uninterruptible_);
173
Orion Hodson06d10a72018-05-14 08:53:38 +0100174ObjPtr<mirror::MethodType> ResolveMethodTypeFromCode(ArtMethod* referrer, dex::ProtoIndex proto_idx)
Orion Hodson18259d72018-04-12 11:18:23 +0100175 REQUIRES_SHARED(Locks::mutator_lock_)
176 REQUIRES(!Roles::uninterruptible_);
177
Mathieu Chartierbe08cf52016-09-13 13:41:24 -0700178void CheckReferenceResult(Handle<mirror::Object> o, Thread* self)
179 REQUIRES_SHARED(Locks::mutator_lock_)
180 REQUIRES(!Roles::uninterruptible_);
TDYa1273d71d802012-08-15 03:47:03 -0700181
Vladimir Marko4bb2af52019-03-22 11:09:19 +0000182JValue InvokeProxyInvocationHandler(ScopedObjectAccessAlreadyRunnable& soa,
183 const char* shorty,
184 jobject rcvr_jobj,
185 jobject interface_art_method_jobj,
Ian Rogersaf6e67a2013-01-16 08:38:37 -0800186 std::vector<jvalue>& args)
Mathieu Chartierbe08cf52016-09-13 13:41:24 -0700187 REQUIRES_SHARED(Locks::mutator_lock_)
188 REQUIRES(!Roles::uninterruptible_);
Ian Rogersaf6e67a2013-01-16 08:38:37 -0800189
Mathieu Chartieref41db72016-10-25 15:08:01 -0700190bool FillArrayData(ObjPtr<mirror::Object> obj, const Instruction::ArrayDataPayload* payload)
Mathieu Chartierbe08cf52016-09-13 13:41:24 -0700191 REQUIRES_SHARED(Locks::mutator_lock_)
192 REQUIRES(!Roles::uninterruptible_);
Ian Rogers832336b2014-10-08 15:35:22 -0700193
Ian Rogers450dcb52013-09-20 17:36:02 -0700194template <typename INT_TYPE, typename FLOAT_TYPE>
Andreas Gampe9f612ff2014-11-24 13:42:22 -0800195inline INT_TYPE art_float_to_integral(FLOAT_TYPE f);
Ian Rogers450dcb52013-09-20 17:36:02 -0700196
Nicolas Geoffray1920c102015-09-29 18:00:03 +0000197ArtMethod* GetCalleeSaveMethodCaller(ArtMethod** sp,
Andreas Gampe8228cdf2017-05-30 15:03:54 -0700198 CalleeSaveType type,
Mathieu Chartierbe08cf52016-09-13 13:41:24 -0700199 bool do_caller_check = false)
200 REQUIRES_SHARED(Locks::mutator_lock_);
201
Vladimir Marko6bec91c2017-01-09 15:03:12 +0000202struct CallerAndOuterMethod {
203 ArtMethod* caller;
204 ArtMethod* outer_method;
205};
206
Andreas Gampe8228cdf2017-05-30 15:03:54 -0700207CallerAndOuterMethod GetCalleeSaveMethodCallerAndOuterMethod(Thread* self, CalleeSaveType type)
Mathieu Chartierbe08cf52016-09-13 13:41:24 -0700208 REQUIRES_SHARED(Locks::mutator_lock_);
Nicolas Geoffray1920c102015-09-29 18:00:03 +0000209
Andreas Gampe8228cdf2017-05-30 15:03:54 -0700210ArtMethod* GetCalleeSaveOuterMethod(Thread* self, CalleeSaveType type)
Nicolas Geoffray5b3c6c02017-01-19 14:22:26 +0000211 REQUIRES_SHARED(Locks::mutator_lock_);
212
Vladimir Marko5115a4d2019-10-17 14:56:47 +0100213// Returns whether we need to do class initialization check before invoking the method.
214// The caller is responsible for performing that check.
215bool NeedsClinitCheckBeforeCall(ArtMethod* method) REQUIRES_SHARED(Locks::mutator_lock_);
216
Vladimir Markocedec9d2021-02-08 16:16:13 +0000217// Returns the synchronization object for a native method for a GenericJni frame
218// we have just created or are about to exit. The synchronization object is
219// the class object for static methods and the `this` object otherwise.
220jobject GetGenericJniSynchronizationObject(Thread* self, ArtMethod* called)
221 REQUIRES_SHARED(Locks::mutator_lock_);
Vladimir Marko6e043bb2020-02-10 16:56:54 +0000222
Vladimir Marko86c87522020-05-11 16:55:55 +0100223// Update .bss method entrypoint if the `callee_reference` has an associated oat file
224// and that oat file has a .bss entry for the `callee_reference`.
225void MaybeUpdateBssMethodEntry(ArtMethod* callee, MethodReference callee_reference);
226
Shih-wei Liao2d831012011-09-28 22:06:53 -0700227} // namespace art
Ian Rogersad42e132011-09-17 20:23:33 -0700228
Ian Rogers7655f292013-07-29 11:07:13 -0700229#endif // ART_RUNTIME_ENTRYPOINTS_ENTRYPOINT_UTILS_H_