Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
PojavLauncherTeam
GitHub Repository: PojavLauncherTeam/openj9
Path: blob/master/runtime/compiler/p/codegen/CallSnippet.hpp
6004 views
1
/*******************************************************************************
2
* Copyright (c) 2000, 2019 IBM Corp. and others
3
*
4
* This program and the accompanying materials are made available under
5
* the terms of the Eclipse Public License 2.0 which accompanies this
6
* distribution and is available at https://www.eclipse.org/legal/epl-2.0/
7
* or the Apache License, Version 2.0 which accompanies this distribution and
8
* is available at https://www.apache.org/licenses/LICENSE-2.0.
9
*
10
* This Source Code may also be made available under the following
11
* Secondary Licenses when the conditions for such availability set
12
* forth in the Eclipse Public License, v. 2.0 are satisfied: GNU
13
* General Public License, version 2 with the GNU Classpath
14
* Exception [1] and GNU General Public License, version 2 with the
15
* OpenJDK Assembly Exception [2].
16
*
17
* [1] https://www.gnu.org/software/classpath/license.html
18
* [2] http://openjdk.java.net/legal/assembly-exception.html
19
*
20
* SPDX-License-Identifier: EPL-2.0 OR Apache-2.0 OR GPL-2.0 WITH Classpath-exception-2.0 OR LicenseRef-GPL-2.0 WITH Assembly-exception
21
*******************************************************************************/
22
23
#ifndef PPCCALLSNIPPET_INCL
24
#define PPCCALLSNIPPET_INCL
25
26
#include "codegen/Snippet.hpp"
27
#include "env/VMJ9.h"
28
#include "infra/Annotations.hpp"
29
#include "p/codegen/PPCInstruction.hpp"
30
31
namespace TR { class CodeGenerator; }
32
class TR_J2IThunk;
33
34
extern void ppcCodeSync(uint8_t *codePointer, uint32_t codeSize);
35
36
namespace TR {
37
38
class PPCCallSnippet : public TR::Snippet
39
{
40
uint8_t *callRA;
41
int32_t sizeOfArguments;
42
43
bool needsGCMap(TR::CodeGenerator *cg, TR::SymbolReference *methodSymRef)
44
{
45
TR_J9VMBase *fej9 = (TR_J9VMBase *)(cg->fe());
46
if (OMR_UNLIKELY(cg->comp()->compileRelocatableCode() && !cg->comp()->getOption(TR_UseSymbolValidationManager)))
47
return false;
48
TR::MethodSymbol *methodSymbol = methodSymRef->getSymbol()->castToMethodSymbol();
49
return !methodSymRef->isUnresolved() &&
50
(methodSymbol->isVMInternalNative() || methodSymbol->isJITInternalNative());
51
}
52
53
protected:
54
TR_RuntimeHelper getInterpretedDispatchHelper(TR::SymbolReference *methodSymRef,
55
TR::DataType type, bool isSynchronized,
56
bool& isNativeStatic, TR::CodeGenerator* cg);
57
TR::SymbolReference * _realMethodSymbolReference;
58
59
public:
60
61
PPCCallSnippet(TR::CodeGenerator *cg, TR::Node *c, TR::LabelSymbol *lab, int32_t s)
62
: TR::Snippet(cg, c, lab, needsGCMap(cg, c->getSymbolReference())), sizeOfArguments(s), callRA(0)
63
{
64
_realMethodSymbolReference = NULL;
65
}
66
67
PPCCallSnippet(TR::CodeGenerator *cg, TR::Node *c, TR::LabelSymbol *lab, TR::SymbolReference *symRef, int32_t s)
68
: TR::Snippet(cg, c, lab, needsGCMap(cg, symRef ? symRef : c->getSymbolReference())), sizeOfArguments(s), callRA(0)
69
{
70
_realMethodSymbolReference = symRef;
71
}
72
73
virtual Kind getKind() { return IsCall; }
74
75
virtual uint8_t *emitSnippetBody();
76
77
virtual uint32_t getLength(int32_t estimatedSnippetStart);
78
79
int32_t getSizeOfArguments() {return sizeOfArguments;}
80
int32_t setSizeOfArguments(int32_t s) {return (sizeOfArguments = s);}
81
82
uint8_t *getCallRA() {return callRA;}
83
uint8_t *setCallRA(uint8_t *ra) {return (callRA=ra);}
84
85
TR::SymbolReference *getRealMethodSymbolReference() {return _realMethodSymbolReference;}
86
void setRealMethodSymbolReference(TR::SymbolReference *sf) {_realMethodSymbolReference = sf;}
87
88
uint8_t *setUpArgumentsInRegister(uint8_t *buffer, TR::Node *callNode, int32_t argSize, TR::CodeGenerator *cg);
89
90
static uint8_t *generateVIThunk(TR::Node *callNode, int32_t argSize, TR::CodeGenerator *cg);
91
static TR_J2IThunk *generateInvokeExactJ2IThunk(TR::Node *callNode, int32_t argSize, TR::CodeGenerator *cg, char *signature);
92
static int32_t instructionCountForArguments(TR::Node *callNode, TR::CodeGenerator *cg);
93
};
94
95
class PPCUnresolvedCallSnippet : public TR::PPCCallSnippet
96
{
97
98
public:
99
100
PPCUnresolvedCallSnippet(TR::CodeGenerator *cg, TR::Node *c, TR::LabelSymbol *lab, int32_t s)
101
: TR::PPCCallSnippet(cg, c, lab, s)
102
{
103
}
104
105
virtual Kind getKind() { return IsUnresolvedCall; }
106
107
virtual uint8_t *emitSnippetBody();
108
109
virtual uint32_t getLength(int32_t estimatedSnippetStart);
110
};
111
112
class PPCVirtualSnippet : public TR::Snippet
113
{
114
TR::LabelSymbol *returnLabel;
115
int32_t sizeOfArguments;
116
117
public:
118
119
PPCVirtualSnippet(TR::CodeGenerator *cg, TR::Node *c, TR::LabelSymbol *lab, int32_t s, TR::LabelSymbol *retl, bool isGCSafePoint = false)
120
: TR::Snippet(cg, c, lab, isGCSafePoint), sizeOfArguments(s), returnLabel(retl) {}
121
122
virtual Kind getKind() { return IsVirtual; }
123
124
virtual uint8_t *emitSnippetBody();
125
126
virtual uint32_t getLength(int32_t estimatedSnippetStart);
127
128
int32_t getSizeOfArguments() {return sizeOfArguments;}
129
int32_t setSizeOfArguments(int32_t s) {return (sizeOfArguments = s);}
130
131
TR::LabelSymbol *getReturnLabel() {return returnLabel;}
132
TR::LabelSymbol *setReturnLabel(TR::LabelSymbol *rl) {return (returnLabel=rl);}
133
};
134
135
class PPCVirtualUnresolvedSnippet : public TR::PPCVirtualSnippet
136
{
137
uint8_t *thunkAddress;
138
public:
139
140
PPCVirtualUnresolvedSnippet(TR::CodeGenerator *cg, TR::Node *c, TR::LabelSymbol *lab, int32_t s, TR::LabelSymbol *retl)
141
: TR::PPCVirtualSnippet(cg, c, lab, s, retl, true), thunkAddress(NULL)
142
{
143
}
144
145
PPCVirtualUnresolvedSnippet(TR::CodeGenerator *cg, TR::Node *c, TR::LabelSymbol *lab, int32_t s, TR::LabelSymbol *retl, uint8_t *thunkPtr)
146
: TR::PPCVirtualSnippet(cg, c, lab, s, retl, true), thunkAddress(thunkPtr)
147
{
148
}
149
150
virtual Kind getKind() { return IsVirtualUnresolved; }
151
152
virtual uint8_t *emitSnippetBody();
153
154
virtual uint32_t getLength(int32_t estimatedSnippetStart);
155
};
156
157
class PPCInterfaceCallSnippet : public TR::PPCVirtualSnippet
158
{
159
TR::Instruction *_upperInstruction, *_lowerInstruction;
160
int32_t _tocOffset;
161
uint8_t *thunkAddress;
162
163
public:
164
165
PPCInterfaceCallSnippet(TR::CodeGenerator *cg, TR::Node *c, TR::LabelSymbol *lab, int32_t s, TR::LabelSymbol *retl)
166
: TR::PPCVirtualSnippet(cg, c, lab, s, retl, true),
167
_upperInstruction(NULL), _lowerInstruction(NULL), _tocOffset(0), thunkAddress(NULL)
168
{
169
}
170
171
PPCInterfaceCallSnippet(TR::CodeGenerator *cg, TR::Node *c, TR::LabelSymbol *lab, int32_t s, TR::LabelSymbol *retl, uint8_t *thunkPtr)
172
: TR::PPCVirtualSnippet(cg, c, lab, s, retl, true),
173
_upperInstruction(NULL), _lowerInstruction(NULL), _tocOffset(0), thunkAddress(thunkPtr)
174
{
175
}
176
177
virtual Kind getKind() { return IsInterfaceCall; }
178
179
TR::Instruction *getUpperInstruction() {return _upperInstruction;}
180
TR::Instruction *setUpperInstruction(TR::Instruction *pi)
181
{
182
return (_upperInstruction = pi);
183
}
184
185
TR::Instruction *getLowerInstruction() {return _lowerInstruction;}
186
TR::Instruction *setLowerInstruction(TR::Instruction *pi)
187
{
188
return (_lowerInstruction = pi);
189
}
190
191
int32_t getTOCOffset() {return _tocOffset;}
192
void setTOCOffset(int32_t v) {_tocOffset = v;}
193
194
virtual uint8_t *emitSnippetBody();
195
196
virtual uint32_t getLength(int32_t estimatedSnippetStart);
197
};
198
199
}
200
201
#endif
202
203