Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
PojavLauncherTeam
GitHub Repository: PojavLauncherTeam/mobile
Path: blob/master/src/hotspot/share/interpreter/templateInterpreter.cpp
40949 views
1
/*
2
* Copyright (c) 1997, 2020, Oracle and/or its affiliates. All rights reserved.
3
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4
*
5
* This code is free software; you can redistribute it and/or modify it
6
* under the terms of the GNU General Public License version 2 only, as
7
* published by the Free Software Foundation.
8
*
9
* This code is distributed in the hope that it will be useful, but WITHOUT
10
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
12
* version 2 for more details (a copy is included in the LICENSE file that
13
* accompanied this code).
14
*
15
* You should have received a copy of the GNU General Public License version
16
* 2 along with this work; if not, write to the Free Software Foundation,
17
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
18
*
19
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
20
* or visit www.oracle.com if you need additional information or have any
21
* questions.
22
*
23
*/
24
25
#include "precompiled.hpp"
26
#include "interpreter/interpreter.hpp"
27
#include "interpreter/interpreterRuntime.hpp"
28
#include "interpreter/interp_masm.hpp"
29
#include "interpreter/templateInterpreter.hpp"
30
#include "interpreter/templateInterpreterGenerator.hpp"
31
#include "interpreter/templateTable.hpp"
32
#include "logging/log.hpp"
33
#include "memory/resourceArea.hpp"
34
#include "prims/jvmtiExport.hpp"
35
#include "runtime/safepoint.hpp"
36
#include "runtime/timerTrace.hpp"
37
#include "utilities/copy.hpp"
38
39
# define __ _masm->
40
41
void TemplateInterpreter::initialize_stub() {
42
// assertions
43
assert(_code == NULL, "must only initialize once");
44
assert((int)Bytecodes::number_of_codes <= (int)DispatchTable::length,
45
"dispatch table too small");
46
47
// allocate interpreter
48
int code_size = InterpreterCodeSize;
49
NOT_PRODUCT(code_size *= 4;) // debug uses extra interpreter code space
50
_code = new StubQueue(new InterpreterCodeletInterface, code_size, NULL,
51
"Interpreter");
52
}
53
54
void TemplateInterpreter::initialize_code() {
55
AbstractInterpreter::initialize();
56
57
TemplateTable::initialize();
58
59
// generate interpreter
60
{ ResourceMark rm;
61
TraceTime timer("Interpreter generation", TRACETIME_LOG(Info, startuptime));
62
TemplateInterpreterGenerator g(_code);
63
// Free the unused memory not occupied by the interpreter and the stubs
64
_code->deallocate_unused_tail();
65
}
66
67
if (PrintInterpreter) {
68
ResourceMark rm;
69
print();
70
}
71
72
// initialize dispatch table
73
_active_table = _normal_table;
74
}
75
76
//------------------------------------------------------------------------------------------------------------------------
77
// Implementation of EntryPoint
78
79
EntryPoint::EntryPoint() {
80
assert(number_of_states == 10, "check the code below");
81
_entry[btos] = NULL;
82
_entry[ztos] = NULL;
83
_entry[ctos] = NULL;
84
_entry[stos] = NULL;
85
_entry[atos] = NULL;
86
_entry[itos] = NULL;
87
_entry[ltos] = NULL;
88
_entry[ftos] = NULL;
89
_entry[dtos] = NULL;
90
_entry[vtos] = NULL;
91
}
92
93
94
EntryPoint::EntryPoint(address bentry, address zentry, address centry, address sentry, address aentry, address ientry, address lentry, address fentry, address dentry, address ventry) {
95
assert(number_of_states == 10, "check the code below");
96
_entry[btos] = bentry;
97
_entry[ztos] = zentry;
98
_entry[ctos] = centry;
99
_entry[stos] = sentry;
100
_entry[atos] = aentry;
101
_entry[itos] = ientry;
102
_entry[ltos] = lentry;
103
_entry[ftos] = fentry;
104
_entry[dtos] = dentry;
105
_entry[vtos] = ventry;
106
}
107
108
EntryPoint::EntryPoint(address aentry, address ientry, address lentry, address fentry, address dentry, address ventry) {
109
assert(number_of_states == 10, "check the code below");
110
_entry[btos] = ientry;
111
_entry[ztos] = ientry;
112
_entry[ctos] = ientry;
113
_entry[stos] = ientry;
114
_entry[atos] = aentry;
115
_entry[itos] = ientry;
116
_entry[ltos] = lentry;
117
_entry[ftos] = fentry;
118
_entry[dtos] = dentry;
119
_entry[vtos] = ventry;
120
}
121
122
void EntryPoint::set_entry(TosState state, address entry) {
123
assert(0 <= state && state < number_of_states, "state out of bounds");
124
_entry[state] = entry;
125
}
126
127
128
address EntryPoint::entry(TosState state) const {
129
assert(0 <= state && state < number_of_states, "state out of bounds");
130
return _entry[state];
131
}
132
133
134
void EntryPoint::print() {
135
tty->print("[");
136
for (int i = 0; i < number_of_states; i++) {
137
if (i > 0) tty->print(", ");
138
tty->print(INTPTR_FORMAT, p2i(_entry[i]));
139
}
140
tty->print("]");
141
}
142
143
144
bool EntryPoint::operator == (const EntryPoint& y) {
145
int i = number_of_states;
146
while (i-- > 0) {
147
if (_entry[i] != y._entry[i]) return false;
148
}
149
return true;
150
}
151
152
153
//------------------------------------------------------------------------------------------------------------------------
154
// Implementation of DispatchTable
155
156
EntryPoint DispatchTable::entry(int i) const {
157
assert(0 <= i && i < length, "index out of bounds");
158
return
159
EntryPoint(
160
_table[btos][i],
161
_table[ztos][i],
162
_table[ctos][i],
163
_table[stos][i],
164
_table[atos][i],
165
_table[itos][i],
166
_table[ltos][i],
167
_table[ftos][i],
168
_table[dtos][i],
169
_table[vtos][i]
170
);
171
}
172
173
174
void DispatchTable::set_entry(int i, EntryPoint& entry) {
175
assert(0 <= i && i < length, "index out of bounds");
176
assert(number_of_states == 10, "check the code below");
177
_table[btos][i] = entry.entry(btos);
178
_table[ztos][i] = entry.entry(ztos);
179
_table[ctos][i] = entry.entry(ctos);
180
_table[stos][i] = entry.entry(stos);
181
_table[atos][i] = entry.entry(atos);
182
_table[itos][i] = entry.entry(itos);
183
_table[ltos][i] = entry.entry(ltos);
184
_table[ftos][i] = entry.entry(ftos);
185
_table[dtos][i] = entry.entry(dtos);
186
_table[vtos][i] = entry.entry(vtos);
187
}
188
189
190
bool DispatchTable::operator == (DispatchTable& y) {
191
int i = length;
192
while (i-- > 0) {
193
EntryPoint t = y.entry(i); // for compiler compatibility (BugId 4150096)
194
if (!(entry(i) == t)) return false;
195
}
196
return true;
197
}
198
199
address TemplateInterpreter::_remove_activation_entry = NULL;
200
address TemplateInterpreter::_remove_activation_preserving_args_entry = NULL;
201
202
203
address TemplateInterpreter::_throw_ArrayIndexOutOfBoundsException_entry = NULL;
204
address TemplateInterpreter::_throw_ArrayStoreException_entry = NULL;
205
address TemplateInterpreter::_throw_ArithmeticException_entry = NULL;
206
address TemplateInterpreter::_throw_ClassCastException_entry = NULL;
207
address TemplateInterpreter::_throw_NullPointerException_entry = NULL;
208
address TemplateInterpreter::_throw_StackOverflowError_entry = NULL;
209
address TemplateInterpreter::_throw_exception_entry = NULL;
210
211
#ifndef PRODUCT
212
EntryPoint TemplateInterpreter::_trace_code;
213
#endif // !PRODUCT
214
EntryPoint TemplateInterpreter::_return_entry[TemplateInterpreter::number_of_return_entries];
215
EntryPoint TemplateInterpreter::_earlyret_entry;
216
EntryPoint TemplateInterpreter::_deopt_entry [TemplateInterpreter::number_of_deopt_entries ];
217
address TemplateInterpreter::_deopt_reexecute_return_entry;
218
EntryPoint TemplateInterpreter::_safept_entry;
219
220
address TemplateInterpreter::_invoke_return_entry[TemplateInterpreter::number_of_return_addrs];
221
address TemplateInterpreter::_invokeinterface_return_entry[TemplateInterpreter::number_of_return_addrs];
222
address TemplateInterpreter::_invokedynamic_return_entry[TemplateInterpreter::number_of_return_addrs];
223
224
DispatchTable TemplateInterpreter::_active_table;
225
DispatchTable TemplateInterpreter::_normal_table;
226
DispatchTable TemplateInterpreter::_safept_table;
227
address TemplateInterpreter::_wentry_point[DispatchTable::length];
228
229
230
//------------------------------------------------------------------------------------------------------------------------
231
// Entry points
232
233
/**
234
* Returns the return entry table for the given invoke bytecode.
235
*/
236
address* TemplateInterpreter::invoke_return_entry_table_for(Bytecodes::Code code) {
237
switch (code) {
238
case Bytecodes::_invokestatic:
239
case Bytecodes::_invokespecial:
240
case Bytecodes::_invokevirtual:
241
case Bytecodes::_invokehandle:
242
return Interpreter::invoke_return_entry_table();
243
case Bytecodes::_invokeinterface:
244
return Interpreter::invokeinterface_return_entry_table();
245
case Bytecodes::_invokedynamic:
246
return Interpreter::invokedynamic_return_entry_table();
247
default:
248
fatal("invalid bytecode: %s", Bytecodes::name(code));
249
return NULL;
250
}
251
}
252
253
/**
254
* Returns the return entry address for the given top-of-stack state and bytecode.
255
*/
256
address TemplateInterpreter::return_entry(TosState state, int length, Bytecodes::Code code) {
257
guarantee(0 <= length && length < Interpreter::number_of_return_entries, "illegal length");
258
const int index = TosState_as_index(state);
259
switch (code) {
260
case Bytecodes::_invokestatic:
261
case Bytecodes::_invokespecial:
262
case Bytecodes::_invokevirtual:
263
case Bytecodes::_invokehandle:
264
return _invoke_return_entry[index];
265
case Bytecodes::_invokeinterface:
266
return _invokeinterface_return_entry[index];
267
case Bytecodes::_invokedynamic:
268
return _invokedynamic_return_entry[index];
269
default:
270
assert(!Bytecodes::is_invoke(code), "invoke instructions should be handled separately: %s", Bytecodes::name(code));
271
address entry = _return_entry[length].entry(state);
272
vmassert(entry != NULL, "unsupported return entry requested, length=%d state=%d", length, index);
273
return entry;
274
}
275
}
276
277
278
address TemplateInterpreter::deopt_entry(TosState state, int length) {
279
guarantee(0 <= length && length < Interpreter::number_of_deopt_entries, "illegal length");
280
address entry = _deopt_entry[length].entry(state);
281
vmassert(entry != NULL, "unsupported deopt entry requested, length=%d state=%d", length, TosState_as_index(state));
282
return entry;
283
}
284
285
//------------------------------------------------------------------------------------------------------------------------
286
// Suport for invokes
287
288
int TemplateInterpreter::TosState_as_index(TosState state) {
289
assert( state < number_of_states , "Invalid state in TosState_as_index");
290
assert(0 <= (int)state && (int)state < TemplateInterpreter::number_of_return_addrs, "index out of bounds");
291
return (int)state;
292
}
293
294
295
//------------------------------------------------------------------------------------------------------------------------
296
// Safepoint support
297
298
static inline void copy_table(address* from, address* to, int size) {
299
// Copy non-overlapping tables.
300
if (SafepointSynchronize::is_at_safepoint()) {
301
// Nothing is using the table at a safepoint so skip atomic word copy.
302
Copy::disjoint_words((HeapWord*)from, (HeapWord*)to, (size_t)size);
303
} else {
304
// Use atomic word copy when not at a safepoint for safety.
305
Copy::disjoint_words_atomic((HeapWord*)from, (HeapWord*)to, (size_t)size);
306
}
307
}
308
309
void TemplateInterpreter::notice_safepoints() {
310
if (!_notice_safepoints) {
311
log_debug(interpreter, safepoint)("switching active_table to safept_table.");
312
// switch to safepoint dispatch table
313
_notice_safepoints = true;
314
copy_table((address*)&_safept_table, (address*)&_active_table, sizeof(_active_table) / sizeof(address));
315
} else {
316
log_debug(interpreter, safepoint)("active_table is already safept_table; "
317
"notice_safepoints() call is no-op.");
318
}
319
}
320
321
// switch from the dispatch table which notices safepoints back to the
322
// normal dispatch table. So that we can notice single stepping points,
323
// keep the safepoint dispatch table if we are single stepping in JVMTI.
324
// Note that the should_post_single_step test is exactly as fast as the
325
// JvmtiExport::_enabled test and covers both cases.
326
void TemplateInterpreter::ignore_safepoints() {
327
if (_notice_safepoints) {
328
if (!JvmtiExport::should_post_single_step()) {
329
log_debug(interpreter, safepoint)("switching active_table to normal_table.");
330
// switch to normal dispatch table
331
_notice_safepoints = false;
332
copy_table((address*)&_normal_table, (address*)&_active_table, sizeof(_active_table) / sizeof(address));
333
} else {
334
log_debug(interpreter, safepoint)("single stepping is still active; "
335
"ignoring ignore_safepoints() call.");
336
}
337
} else {
338
log_debug(interpreter, safepoint)("active_table is already normal_table; "
339
"ignore_safepoints() call is no-op.");
340
}
341
}
342
343
//------------------------------------------------------------------------------------------------------------------------
344
// Deoptimization support
345
346
// If deoptimization happens, this function returns the point of next bytecode to continue execution
347
address TemplateInterpreter::deopt_continue_after_entry(Method* method, address bcp, int callee_parameters, bool is_top_frame) {
348
return AbstractInterpreter::deopt_continue_after_entry(method, bcp, callee_parameters, is_top_frame);
349
}
350
351
// If deoptimization happens, this function returns the point where the interpreter reexecutes
352
// the bytecode.
353
// Note: Bytecodes::_athrow (C1 only) and Bytecodes::_return are the special cases
354
// that do not return "Interpreter::deopt_entry(vtos, 0)"
355
address TemplateInterpreter::deopt_reexecute_entry(Method* method, address bcp) {
356
assert(method->contains(bcp), "just checkin'");
357
Bytecodes::Code code = Bytecodes::code_at(method, bcp);
358
if (code == Bytecodes::_return_register_finalizer) {
359
// This is used for deopt during registration of finalizers
360
// during Object.<init>. We simply need to resume execution at
361
// the standard return vtos bytecode to pop the frame normally.
362
// reexecuting the real bytecode would cause double registration
363
// of the finalizable object.
364
return Interpreter::deopt_reexecute_return_entry();
365
} else {
366
return AbstractInterpreter::deopt_reexecute_entry(method, bcp);
367
}
368
}
369
370
// If deoptimization happens, the interpreter should reexecute this bytecode.
371
// This function mainly helps the compilers to set up the reexecute bit.
372
bool TemplateInterpreter::bytecode_should_reexecute(Bytecodes::Code code) {
373
if (code == Bytecodes::_return) {
374
//Yes, we consider Bytecodes::_return as a special case of reexecution
375
return true;
376
} else {
377
return AbstractInterpreter::bytecode_should_reexecute(code);
378
}
379
}
380
381
InterpreterCodelet* TemplateInterpreter::codelet_containing(address pc) {
382
return (InterpreterCodelet*)_code->stub_containing(pc);
383
}
384
385