Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
PojavLauncherTeam
GitHub Repository: PojavLauncherTeam/openjdk-multiarch-jdk8u
Path: blob/aarch64-shenandoah-jdk8u272-b10/jdk/src/share/demo/jvmti/compiledMethodLoad/compiledMethodLoad.c
38829 views
1
/*
2
* Copyright (c) 2010, 2011, Oracle and/or its affiliates. All rights reserved.
3
*
4
* Redistribution and use in source and binary forms, with or without
5
* modification, are permitted provided that the following conditions
6
* are met:
7
*
8
* - Redistributions of source code must retain the above copyright
9
* notice, this list of conditions and the following disclaimer.
10
*
11
* - Redistributions in binary form must reproduce the above copyright
12
* notice, this list of conditions and the following disclaimer in the
13
* documentation and/or other materials provided with the distribution.
14
*
15
* - Neither the name of Oracle nor the names of its
16
* contributors may be used to endorse or promote products derived
17
* from this software without specific prior written permission.
18
*
19
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
20
* IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
21
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
22
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
23
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
24
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
25
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
26
* PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
27
* LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
28
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
29
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
30
*/
31
32
/*
33
* This source code is provided to illustrate the usage of a given feature
34
* or technique and has been deliberately simplified. Additional steps
35
* required for a production-quality application, such as security checks,
36
* input validation and proper error handling, might not be present in
37
* this sample code.
38
*/
39
40
41
#include <stdio.h>
42
#include <stdlib.h>
43
#include <string.h>
44
45
#include "jni.h"
46
#include "jvmti.h"
47
#include "jvmticmlr.h"
48
49
#include "agent_util.h"
50
51
/* Global static data */
52
static char OUTPUT_FILE[] = "compiledMethodLoad.txt";
53
static FILE *fp;
54
static jvmtiEnv *jvmti;
55
static jrawMonitorID lock;
56
57
/* print a jvmtiCompiledMethodLoadDummyRecord */
58
void
59
print_dummy_record(jvmtiCompiledMethodLoadDummyRecord* record,
60
jvmtiEnv* jvmti, FILE* fp) {
61
62
if (record != NULL) {
63
fprintf(fp, "Dummy record detected containing message: %s\n",
64
(char *)record->message);
65
}
66
}
67
68
/* print the specified stack frames */
69
void
70
print_stack_frames(PCStackInfo* record, jvmtiEnv *jvmti, FILE* fp) {
71
if (record != NULL && record->methods != NULL) {
72
int i;
73
74
for (i = 0; i < record->numstackframes; i++) {
75
jvmtiError err;
76
char* method_name = NULL;
77
char* class_name = NULL;
78
char* method_signature = NULL;
79
char* class_signature = NULL;
80
char* generic_ptr_method = NULL;
81
char* generic_ptr_class = NULL;
82
jmethodID id;
83
jclass declaringclassptr;
84
id = record->methods[i];
85
86
err = (*jvmti)->GetMethodDeclaringClass(jvmti, id,
87
&declaringclassptr);
88
check_jvmti_error(jvmti, err, "get method declaring class");
89
90
err = (*jvmti)->GetClassSignature(jvmti, declaringclassptr,
91
&class_signature, &generic_ptr_class);
92
check_jvmti_error(jvmti, err, "get class signature");
93
94
err = (*jvmti)->GetMethodName(jvmti, id, &method_name,
95
&method_signature, &generic_ptr_method);
96
check_jvmti_error(jvmti, err, "get method name");
97
98
fprintf(fp, "%s::%s %s %s @%d\n", class_signature, method_name,
99
method_signature,
100
generic_ptr_method == NULL ? "" : generic_ptr_method,
101
record->bcis[i]);
102
103
if (method_name != NULL) {
104
err = (*jvmti)->Deallocate(jvmti, (unsigned char*)method_name);
105
check_jvmti_error(jvmti, err, "deallocate method_name");
106
}
107
if (method_signature != NULL) {
108
err = (*jvmti)->Deallocate(jvmti,
109
(unsigned char*)method_signature);
110
check_jvmti_error(jvmti, err, "deallocate method_signature");
111
}
112
if (generic_ptr_method != NULL) {
113
err = (*jvmti)->Deallocate(jvmti,
114
(unsigned char*)generic_ptr_method);
115
check_jvmti_error(jvmti, err, "deallocate generic_ptr_method");
116
}
117
if (class_name != NULL) {
118
err = (*jvmti)->Deallocate(jvmti, (unsigned char*)class_name);
119
check_jvmti_error(jvmti, err, "deallocate class_name");
120
}
121
if (class_signature != NULL) {
122
err = (*jvmti)->Deallocate(jvmti,
123
(unsigned char*)class_signature);
124
check_jvmti_error(jvmti, err, "deallocate class_signature");
125
}
126
if (generic_ptr_class != NULL) {
127
err = (*jvmti)->Deallocate(jvmti,
128
(unsigned char*)generic_ptr_class);
129
check_jvmti_error(jvmti, err, "deallocate generic_ptr_class");
130
}
131
}
132
}
133
}
134
135
/* print a jvmtiCompiledMethodLoadInlineRecord */
136
void
137
print_inline_info_record(jvmtiCompiledMethodLoadInlineRecord* record,
138
jvmtiEnv *jvmti, FILE* fp) {
139
140
if (record != NULL && record->pcinfo != NULL) {
141
int numpcs = record->numpcs;
142
int i;
143
144
for (i = 0; i < numpcs; i++) {
145
PCStackInfo pcrecord = (record->pcinfo[i]);
146
fprintf(fp, "PcDescriptor(pc=0x%lx):\n", (jint)(pcrecord.pc));
147
print_stack_frames(&pcrecord, jvmti, fp);
148
}
149
}
150
}
151
152
/* decode kind of CompiledMethodLoadRecord and print */
153
void
154
print_records(jvmtiCompiledMethodLoadRecordHeader* list, jvmtiEnv *jvmti,
155
FILE* fp)
156
{
157
jvmtiCompiledMethodLoadRecordHeader* curr = list;
158
fprintf(fp, "\nPrinting PC Descriptors\n\n");
159
while (curr != NULL) {
160
switch (curr->kind) {
161
case JVMTI_CMLR_DUMMY:
162
print_dummy_record((jvmtiCompiledMethodLoadDummyRecord *)curr,
163
jvmti, fp);
164
break;
165
166
case JVMTI_CMLR_INLINE_INFO:
167
print_inline_info_record(
168
(jvmtiCompiledMethodLoadInlineRecord *)curr, jvmti, fp);
169
break;
170
171
default:
172
fprintf(fp, "Warning: unrecognized record: kind=%d\n", curr->kind);
173
break;
174
}
175
176
curr = (jvmtiCompiledMethodLoadRecordHeader *)curr->next;
177
}
178
}
179
180
/* Callback for JVMTI_EVENT_COMPILED_METHOD_LOAD */
181
void JNICALL
182
compiled_method_load(jvmtiEnv *jvmti, jmethodID method, jint code_size,
183
const void* code_addr, jint map_length, const jvmtiAddrLocationMap* map,
184
const void* compile_info)
185
{
186
jvmtiError err;
187
char* name = NULL;
188
char* signature = NULL;
189
char* generic_ptr = NULL;
190
jvmtiCompiledMethodLoadRecordHeader* pcs;
191
192
err = (*jvmti)->RawMonitorEnter(jvmti, lock);
193
check_jvmti_error(jvmti, err, "raw monitor enter");
194
195
err = (*jvmti)->GetMethodName(jvmti, method, &name, &signature,
196
&generic_ptr);
197
check_jvmti_error(jvmti, err, "get method name");
198
199
fprintf(fp, "\nCompiled method load event\n");
200
fprintf(fp, "Method name %s %s %s\n\n", name, signature,
201
generic_ptr == NULL ? "" : generic_ptr);
202
pcs = (jvmtiCompiledMethodLoadRecordHeader *)compile_info;
203
if (pcs != NULL) {
204
print_records(pcs, jvmti, fp);
205
}
206
207
if (name != NULL) {
208
err = (*jvmti)->Deallocate(jvmti, (unsigned char*)name);
209
check_jvmti_error(jvmti, err, "deallocate name");
210
}
211
if (signature != NULL) {
212
err = (*jvmti)->Deallocate(jvmti, (unsigned char*)signature);
213
check_jvmti_error(jvmti, err, "deallocate signature");
214
}
215
if (generic_ptr != NULL) {
216
err = (*jvmti)->Deallocate(jvmti, (unsigned char*)generic_ptr);
217
check_jvmti_error(jvmti, err, "deallocate generic_ptr");
218
}
219
220
err = (*jvmti)->RawMonitorExit(jvmti, lock);
221
check_jvmti_error(jvmti, err, "raw monitor exit");
222
}
223
224
/* Agent_OnLoad() is called first, we prepare for a COMPILED_METHOD_LOAD
225
* event here.
226
*/
227
JNIEXPORT jint JNICALL
228
Agent_OnLoad(JavaVM *vm, char *options, void *reserved)
229
{
230
jint rc;
231
jvmtiError err;
232
jvmtiCapabilities capabilities;
233
jvmtiEventCallbacks callbacks;
234
235
fp = fopen(OUTPUT_FILE, "w");
236
if (fp == NULL) {
237
fatal_error("ERROR: %s: Unable to create output file\n", OUTPUT_FILE);
238
return -1;
239
}
240
241
/* Get JVMTI environment */
242
rc = (*vm)->GetEnv(vm, (void **)&jvmti, JVMTI_VERSION);
243
if (rc != JNI_OK) {
244
fatal_error(
245
"ERROR: Unable to create jvmtiEnv, GetEnv failed, error=%d\n", rc);
246
return -1;
247
}
248
249
/* add JVMTI capabilities */
250
memset(&capabilities,0, sizeof(capabilities));
251
capabilities.can_generate_compiled_method_load_events = 1;
252
err = (*jvmti)->AddCapabilities(jvmti, &capabilities);
253
check_jvmti_error(jvmti, err, "add capabilities");
254
255
/* set JVMTI callbacks for events */
256
memset(&callbacks, 0, sizeof(callbacks));
257
callbacks.CompiledMethodLoad = &compiled_method_load;
258
err = (*jvmti)->SetEventCallbacks(jvmti, &callbacks, sizeof(callbacks));
259
check_jvmti_error(jvmti, err, "set event callbacks");
260
261
/* enable JVMTI events */
262
err = (*jvmti)->SetEventNotificationMode(jvmti, JVMTI_ENABLE,
263
JVMTI_EVENT_COMPILED_METHOD_LOAD, NULL);
264
check_jvmti_error(jvmti, err, "set event notify");
265
266
/* create coordination monitor */
267
err = (*jvmti)->CreateRawMonitor(jvmti, "agent lock", &lock);
268
check_jvmti_error(jvmti, err, "create raw monitor");
269
270
return 0;
271
}
272
273
/* Agent_OnUnload() is called last */
274
JNIEXPORT void JNICALL
275
Agent_OnUnload(JavaVM *vm)
276
{
277
}
278
279