22 */
23
24 /*
25 This test case to test the following:
26
27 GetCurrentThreadCpuTime
28 GetThreadCpuTime
29 GetTime
30 */
31
32 #define VARIANCE (0.10)
33 #define VARIANCE_PERCENT (VARIANCE * 100.0)
34
35 #include <stdio.h>
36 #include <string.h>
37 #include "jvmti.h"
38 #include "agent_common.h"
39
40 #include "jni_tools.h"
41
42 #ifdef __cplusplus
43 extern "C" {
44 #endif
45
46 #ifndef JNI_ENV_ARG
47
48 #ifdef __cplusplus
49 #define JNI_ENV_PTR(x) x
50 #define JNI_ENV_ARG(x, y) y
51 #else
52 #define JNI_ENV_PTR(x) (*x)
53 #define JNI_ENV_ARG(x, y) x, y
54 #endif
55
56 #endif
57
58 #define JVMTI_ENV_PTR JNI_ENV_PTR
59 #define JVMTI_ENV_ARG JNI_ENV_ARG
60
61 #define JVMTI_ERROR_CHECK_DURING_ONLOAD(str,res) if ( res != JVMTI_ERROR_NONE) { printf("Fatal error: %s - %d\n", str, res); return JNI_ERR; }
62
63 #define JVMTI_ERROR_CHECK_RETURN(str,res) if ( res != JVMTI_ERROR_NONE) { printf("Error: %s - %d\n", str, res); return; }
64
65 #define JVMTI_ERROR_CHECK(str,res) if ( res != JVMTI_ERROR_NONE) { printf("Error: %s - %d\n", str, res); }
66
67 #define THREADS_LIMIT 200
68
69
70 jvmtiEnv *jvmti;
71 jint iGlobalStatus = 0;
72 jthread susp_thrd[THREADS_LIMIT];
73 static jvmtiEventCallbacks callbacks;
74 static jvmtiCapabilities capabilities;
75 jrawMonitorID jraw_monitor[20];
76 jlong initial_time;
77
78 struct ThreadInfo {
79 jint iterationCount;
85 int printdump = 1;
86
87
88 void debug_printf(const char *fmt, ...) {
89 va_list args;
90
91 va_start(args, fmt);
92 if (printdump) {
93 vprintf(fmt, args);
94 }
95 va_end(args);
96 }
97
98 void JNICALL vmInit(jvmtiEnv *jvmti_env, JNIEnv *env, jthread thread) {
99 jvmtiError err;
100 char buffer[32];
101
102 debug_printf("VMInit event\n");
103
104 debug_printf("jvmti GetTime \n");
105 err = JVMTI_ENV_PTR(jvmti_env)->GetTime(JVMTI_ENV_ARG(jvmti_env, &initial_time));
106 JVMTI_ERROR_CHECK("GetTime", err);
107 debug_printf(" Initial time: %s ns\n",
108 jlong_to_string(initial_time, buffer));
109 }
110
111 void JNICALL vmExit(jvmtiEnv *jvmti_env, JNIEnv *env) {
112 debug_printf("VMDeath event\n");
113 }
114
115
116 void init_callbacks() {
117 memset((void *)&callbacks, 0, sizeof(jvmtiEventCallbacks));
118 callbacks.VMInit = vmInit;
119 callbacks.VMDeath = vmExit;
120 }
121
122
123 #ifdef STATIC_BUILD
124 JNIEXPORT jint JNICALL Agent_OnLoad_JvmtiTest(JavaVM *jvm, char *options, void *reserved) {
125 return Agent_Initialize(jvm, options, reserved);
140 printdump = 1;
141 }
142 }
143
144 res = jvm->GetEnv((void **) &jvmti, JVMTI_VERSION_1_1);
145 if (res < 0) {
146 printf("Wrong result of a valid call to GetEnv!\n");
147 return JNI_ERR;
148 }
149
150
151 /* Add capabilities */
152 memset(&capabilities, 0, sizeof(jvmtiCapabilities));
153 capabilities.can_get_current_thread_cpu_time = 1;
154 capabilities.can_get_thread_cpu_time = 1;
155 err = jvmti->AddCapabilities(&capabilities);
156 JVMTI_ERROR_CHECK_DURING_ONLOAD("(AddCapabilities)", err);
157
158 /* Enable events */
159 init_callbacks();
160 res = JVMTI_ENV_PTR(jvmti)->SetEventCallbacks(JVMTI_ENV_ARG(jvmti_env, &callbacks), sizeof(callbacks));
161 JVMTI_ERROR_CHECK_DURING_ONLOAD("SetEventCallbacks returned error", res);
162
163 res = JVMTI_ENV_PTR(jvmti)->SetEventNotificationMode(JVMTI_ENV_ARG(jvmti_env, JVMTI_ENABLE), JVMTI_EVENT_VM_INIT, NULL);
164 JVMTI_ERROR_CHECK_DURING_ONLOAD("SetEventNotificationMode for VM_INIT returned error", res);
165
166 res = JVMTI_ENV_PTR(jvmti)->SetEventNotificationMode(JVMTI_ENV_ARG(jvmti_env, JVMTI_ENABLE), JVMTI_EVENT_VM_DEATH, NULL);
167 JVMTI_ERROR_CHECK_DURING_ONLOAD("SetEventNotificationMode for vm death event returned error", res);
168
169 return JNI_OK;
170 }
171
172
173 JNIEXPORT jint JNICALL
174 Java_nsk_jvmti_unit_timers_JvmtiTest_GetResult(JNIEnv * env, jclass cls) {
175 return iGlobalStatus;
176 }
177
178 #define milli(x) ((x)/(1000L * 1000L))
179
180 JNIEXPORT void JNICALL
181 Java_nsk_jvmti_unit_timers_JvmtiTest_RegisterCompletedThread(JNIEnv * env,
182 jclass cls, jthread thread, jint threadNumber, jint iterationCount) {
183 jvmtiError ret;
184 jlong curr;
185
186 debug_printf("jvmti GetCurrentThreadCpuTime \n");
187 ret = JVMTI_ENV_PTR(jvmti)->GetCurrentThreadCpuTime(JVMTI_ENV_ARG(jvmti_env, &curr));
188 JVMTI_ERROR_CHECK_RETURN("GetCurrentThreadCpuTime", ret);
189
190 thread_info[threadNumber].iterationCount = iterationCount;
191 thread_info[threadNumber].currThreadTime = curr;
192 thread_info[threadNumber].ref = JNI_ENV_PTR(env)->NewWeakGlobalRef(JNI_ENV_ARG(env, thread));
193 }
194
195 static void print_timerinfo(jvmtiTimerInfo* timerInfo) {
196 char buffer[32];
197 const char* timerKind;
198 switch(timerInfo->kind) {
199 case JVMTI_TIMER_USER_CPU:
200 timerKind = "JVMTI_TIMER_USER_CPU";
201 break;
202 case JVMTI_TIMER_TOTAL_CPU:
203 timerKind = "JVMTI_TIMER_TOTAL_CPU";
204 break;
205 case JVMTI_TIMER_ELAPSED:
206 timerKind = "JVMTI_TIMER_ELAPSED_CPU";
207 break;
208 default:
209 timerKind = "<unknown>";
210 break;
211 }
212 debug_printf(" Max = %s [%s %s] kind = %s\n",
220 Java_nsk_jvmti_unit_timers_JvmtiTest_Analyze(JNIEnv * env, jclass cls) {
221 jvmtiError ret;
222 jlong now;
223 jlong etime;
224 jint thrCnt;
225 jvmtiTimerInfo timerInfoCurr;
226 jvmtiTimerInfo timerInfoOther;
227 jvmtiTimerInfo timerInfoTime;
228 jint processor_count;
229 jint totalIter = 0;
230 jlong totalTimeCurr = 0;
231 jlong totalTime = 0;
232 jlong possibleTime;
233 double one_iter_cost;
234 jthread *thrArray;
235 int k;
236 int i;
237 char buffer[32];
238
239 debug_printf("jvmti GetTime \n");
240 ret = JVMTI_ENV_PTR(jvmti)->GetTime(JVMTI_ENV_ARG(jvmti_env, &now));
241 JVMTI_ERROR_CHECK_RETURN("GetTime", ret);
242 etime = now - initial_time;
243 debug_printf(" Elapsed time: %s ms\n",
244 jlong_to_string(milli(etime), buffer));
245
246 debug_printf("jvmti GetCurrentThreadCpuTimerInfo \n");
247 ret = JVMTI_ENV_PTR(jvmti)->GetCurrentThreadCpuTimerInfo(JVMTI_ENV_ARG(jvmti_env, &timerInfoCurr));
248 JVMTI_ERROR_CHECK_RETURN("GetCurrentThreadCpuTimerInfo", ret);
249 print_timerinfo(&timerInfoCurr);
250
251 debug_printf("jvmti GetThreadCpuTimerInfo \n");
252 ret = JVMTI_ENV_PTR(jvmti)->GetThreadCpuTimerInfo(JVMTI_ENV_ARG(jvmti_env, &timerInfoOther));
253 JVMTI_ERROR_CHECK_RETURN("GetThreadCpuTimerInfo", ret);
254 print_timerinfo(&timerInfoOther);
255
256 debug_printf("jvmti GetTimerInfo \n");
257 ret = JVMTI_ENV_PTR(jvmti)->GetTimerInfo(JVMTI_ENV_ARG(jvmti_env, &timerInfoTime));
258 JVMTI_ERROR_CHECK_RETURN("GetTimerInfo", ret);
259 print_timerinfo(&timerInfoTime);
260
261 debug_printf("jvmti GetAvailableProcessors \n");
262 ret = JVMTI_ENV_PTR(jvmti)->GetAvailableProcessors(JVMTI_ENV_ARG(jvmti_env, &processor_count));
263 JVMTI_ERROR_CHECK_RETURN("GetAvailableProcessors", ret);
264 debug_printf(" processor_count = %d\n", processor_count);
265
266 debug_printf("jvmti GetAllThreads \n");
267 ret = JVMTI_ENV_PTR(jvmti)->GetAllThreads(JVMTI_ENV_ARG(jvmti_env, &thrCnt), &thrArray);
268 JVMTI_ERROR_CHECK_RETURN("GetAllThreads", ret);
269
270 for (k = 0; k < thrCnt; ++k) {
271 jlong oth;
272 jthread thread;
273
274 thread = thrArray[k];
275 ret = JVMTI_ENV_PTR(jvmti)->GetThreadCpuTime(JVMTI_ENV_ARG(jvmti_env, thread), &oth);
276 JVMTI_ERROR_CHECK_RETURN("GetThreadCpuTime", ret);
277
278 for (i = 1; i < THREADS_LIMIT; ++i) {
279 jweak tref = thread_info[i].ref;
280 if (tref != 0) {
281 if (JNI_ENV_PTR(env)->IsSameObject(JNI_ENV_ARG(env, thread), tref)) {
282 thread_info[i].threadTime = oth;
283 break;
284 }
285 }
286 }
287 if (i == THREADS_LIMIT) {
288 jvmtiThreadInfo info;
289 info.name = (char*) "*retrieval error*";
290 ret = JVMTI_ENV_PTR(jvmti)->GetThreadInfo(JVMTI_ENV_ARG(jvmti_env, thread), &info);
291 JVMTI_ERROR_CHECK("GetThreadInfo %d \n", ret);
292
293 debug_printf("non-test thread: %s - %s ms\n", info.name,
294 jlong_to_string(milli(oth), buffer));
295 }
296 }
297 for (i = 1; i < THREADS_LIMIT; ++i) {
298 jweak tref = thread_info[i].ref;
299 if (tref != 0) {
300 totalIter += thread_info[i].iterationCount;
301 totalTimeCurr += thread_info[i].currThreadTime;
302 totalTime += thread_info[i].threadTime;
303 }
304 }
305 possibleTime = etime * processor_count;
306 debug_printf("Totals -- \n");
307 debug_printf(" Iter = %d\n", totalIter);
308 debug_printf(" Total GetThreadCpuTime = %s ns", jlong_to_string(totalTime, buffer));
309 debug_printf(" %s ms\n", jlong_to_string(milli(totalTime), buffer));
310 debug_printf(" Total GetCurrentThreadCpuTimerInfo = %s ns", jlong_to_string(totalTimeCurr, buffer));
363 // fail in this case.
364 if (!passed && milli(tt - ctt) <= 15) {
365 printf("Passing due to special consideration on Windows for 15ms timer accuracy\n");
366 passed = 1;
367 }
368 #endif
369 if (passed) {
370 debug_printf("Pass: currThreadTime(" JLONG_FORMAT ") >= %2.0f%% of threadTime(" JLONG_FORMAT ")\n",
371 ctt, 100.0 - VARIANCE_PERCENT, tt);
372 } else {
373 printf("FAIL: currThreadTime(" JLONG_FORMAT ") < %2.0f%% of threadTime(" JLONG_FORMAT ")\n",
374 ctt, 100.0 - VARIANCE_PERCENT, tt);
375 iGlobalStatus = 2;
376 }
377 }
378 }
379 }
380 }
381
382
383 #ifdef __cplusplus
384 }
385 #endif
|
22 */
23
24 /*
25 This test case to test the following:
26
27 GetCurrentThreadCpuTime
28 GetThreadCpuTime
29 GetTime
30 */
31
32 #define VARIANCE (0.10)
33 #define VARIANCE_PERCENT (VARIANCE * 100.0)
34
35 #include <stdio.h>
36 #include <string.h>
37 #include "jvmti.h"
38 #include "agent_common.h"
39
40 #include "jni_tools.h"
41
42 extern "C" {
43
44 #define JVMTI_ERROR_CHECK_DURING_ONLOAD(str,res) if ( res != JVMTI_ERROR_NONE) { printf("Fatal error: %s - %d\n", str, res); return JNI_ERR; }
45
46 #define JVMTI_ERROR_CHECK_RETURN(str,res) if ( res != JVMTI_ERROR_NONE) { printf("Error: %s - %d\n", str, res); return; }
47
48 #define JVMTI_ERROR_CHECK(str,res) if ( res != JVMTI_ERROR_NONE) { printf("Error: %s - %d\n", str, res); }
49
50 #define THREADS_LIMIT 200
51
52
53 jvmtiEnv *jvmti;
54 jint iGlobalStatus = 0;
55 jthread susp_thrd[THREADS_LIMIT];
56 static jvmtiEventCallbacks callbacks;
57 static jvmtiCapabilities capabilities;
58 jrawMonitorID jraw_monitor[20];
59 jlong initial_time;
60
61 struct ThreadInfo {
62 jint iterationCount;
68 int printdump = 1;
69
70
71 void debug_printf(const char *fmt, ...) {
72 va_list args;
73
74 va_start(args, fmt);
75 if (printdump) {
76 vprintf(fmt, args);
77 }
78 va_end(args);
79 }
80
81 void JNICALL vmInit(jvmtiEnv *jvmti_env, JNIEnv *env, jthread thread) {
82 jvmtiError err;
83 char buffer[32];
84
85 debug_printf("VMInit event\n");
86
87 debug_printf("jvmti GetTime \n");
88 err = jvmti_env->GetTime(&initial_time);
89 JVMTI_ERROR_CHECK("GetTime", err);
90 debug_printf(" Initial time: %s ns\n",
91 jlong_to_string(initial_time, buffer));
92 }
93
94 void JNICALL vmExit(jvmtiEnv *jvmti_env, JNIEnv *env) {
95 debug_printf("VMDeath event\n");
96 }
97
98
99 void init_callbacks() {
100 memset((void *)&callbacks, 0, sizeof(jvmtiEventCallbacks));
101 callbacks.VMInit = vmInit;
102 callbacks.VMDeath = vmExit;
103 }
104
105
106 #ifdef STATIC_BUILD
107 JNIEXPORT jint JNICALL Agent_OnLoad_JvmtiTest(JavaVM *jvm, char *options, void *reserved) {
108 return Agent_Initialize(jvm, options, reserved);
123 printdump = 1;
124 }
125 }
126
127 res = jvm->GetEnv((void **) &jvmti, JVMTI_VERSION_1_1);
128 if (res < 0) {
129 printf("Wrong result of a valid call to GetEnv!\n");
130 return JNI_ERR;
131 }
132
133
134 /* Add capabilities */
135 memset(&capabilities, 0, sizeof(jvmtiCapabilities));
136 capabilities.can_get_current_thread_cpu_time = 1;
137 capabilities.can_get_thread_cpu_time = 1;
138 err = jvmti->AddCapabilities(&capabilities);
139 JVMTI_ERROR_CHECK_DURING_ONLOAD("(AddCapabilities)", err);
140
141 /* Enable events */
142 init_callbacks();
143 res = jvmti->SetEventCallbacks(&callbacks, sizeof(callbacks));
144 JVMTI_ERROR_CHECK_DURING_ONLOAD("SetEventCallbacks returned error", res);
145
146 res = jvmti->SetEventNotificationMode(JVMTI_ENABLE, JVMTI_EVENT_VM_INIT, NULL);
147 JVMTI_ERROR_CHECK_DURING_ONLOAD("SetEventNotificationMode for VM_INIT returned error", res);
148
149 res = jvmti->SetEventNotificationMode(JVMTI_ENABLE, JVMTI_EVENT_VM_DEATH, NULL);
150 JVMTI_ERROR_CHECK_DURING_ONLOAD("SetEventNotificationMode for vm death event returned error", res);
151
152 return JNI_OK;
153 }
154
155
156 JNIEXPORT jint JNICALL
157 Java_nsk_jvmti_unit_timers_JvmtiTest_GetResult(JNIEnv * env, jclass cls) {
158 return iGlobalStatus;
159 }
160
161 #define milli(x) ((x)/(1000L * 1000L))
162
163 JNIEXPORT void JNICALL
164 Java_nsk_jvmti_unit_timers_JvmtiTest_RegisterCompletedThread(JNIEnv * env,
165 jclass cls, jthread thread, jint threadNumber, jint iterationCount) {
166 jvmtiError ret;
167 jlong curr;
168
169 debug_printf("jvmti GetCurrentThreadCpuTime \n");
170 ret = jvmti->GetCurrentThreadCpuTime(&curr);
171 JVMTI_ERROR_CHECK_RETURN("GetCurrentThreadCpuTime", ret);
172
173 thread_info[threadNumber].iterationCount = iterationCount;
174 thread_info[threadNumber].currThreadTime = curr;
175 thread_info[threadNumber].ref = env->NewWeakGlobalRef(thread);
176 }
177
178 static void print_timerinfo(jvmtiTimerInfo* timerInfo) {
179 char buffer[32];
180 const char* timerKind;
181 switch(timerInfo->kind) {
182 case JVMTI_TIMER_USER_CPU:
183 timerKind = "JVMTI_TIMER_USER_CPU";
184 break;
185 case JVMTI_TIMER_TOTAL_CPU:
186 timerKind = "JVMTI_TIMER_TOTAL_CPU";
187 break;
188 case JVMTI_TIMER_ELAPSED:
189 timerKind = "JVMTI_TIMER_ELAPSED_CPU";
190 break;
191 default:
192 timerKind = "<unknown>";
193 break;
194 }
195 debug_printf(" Max = %s [%s %s] kind = %s\n",
203 Java_nsk_jvmti_unit_timers_JvmtiTest_Analyze(JNIEnv * env, jclass cls) {
204 jvmtiError ret;
205 jlong now;
206 jlong etime;
207 jint thrCnt;
208 jvmtiTimerInfo timerInfoCurr;
209 jvmtiTimerInfo timerInfoOther;
210 jvmtiTimerInfo timerInfoTime;
211 jint processor_count;
212 jint totalIter = 0;
213 jlong totalTimeCurr = 0;
214 jlong totalTime = 0;
215 jlong possibleTime;
216 double one_iter_cost;
217 jthread *thrArray;
218 int k;
219 int i;
220 char buffer[32];
221
222 debug_printf("jvmti GetTime \n");
223 ret = jvmti->GetTime(&now);
224 JVMTI_ERROR_CHECK_RETURN("GetTime", ret);
225 etime = now - initial_time;
226 debug_printf(" Elapsed time: %s ms\n",
227 jlong_to_string(milli(etime), buffer));
228
229 debug_printf("jvmti GetCurrentThreadCpuTimerInfo \n");
230 ret = jvmti->GetCurrentThreadCpuTimerInfo(&timerInfoCurr);
231 JVMTI_ERROR_CHECK_RETURN("GetCurrentThreadCpuTimerInfo", ret);
232 print_timerinfo(&timerInfoCurr);
233
234 debug_printf("jvmti GetThreadCpuTimerInfo \n");
235 ret = jvmti->GetThreadCpuTimerInfo(&timerInfoOther);
236 JVMTI_ERROR_CHECK_RETURN("GetThreadCpuTimerInfo", ret);
237 print_timerinfo(&timerInfoOther);
238
239 debug_printf("jvmti GetTimerInfo \n");
240 ret = jvmti->GetTimerInfo(&timerInfoTime);
241 JVMTI_ERROR_CHECK_RETURN("GetTimerInfo", ret);
242 print_timerinfo(&timerInfoTime);
243
244 debug_printf("jvmti GetAvailableProcessors \n");
245 ret = jvmti->GetAvailableProcessors(&processor_count);
246 JVMTI_ERROR_CHECK_RETURN("GetAvailableProcessors", ret);
247 debug_printf(" processor_count = %d\n", processor_count);
248
249 debug_printf("jvmti GetAllThreads \n");
250 ret = jvmti->GetAllThreads(&thrCnt, &thrArray);
251 JVMTI_ERROR_CHECK_RETURN("GetAllThreads", ret);
252
253 for (k = 0; k < thrCnt; ++k) {
254 jlong oth;
255 jthread thread;
256
257 thread = thrArray[k];
258 ret = jvmti->GetThreadCpuTime(thread, &oth);
259 JVMTI_ERROR_CHECK_RETURN("GetThreadCpuTime", ret);
260
261 for (i = 1; i < THREADS_LIMIT; ++i) {
262 jweak tref = thread_info[i].ref;
263 if (tref != 0) {
264 if (env->IsSameObject(thread, tref)) {
265 thread_info[i].threadTime = oth;
266 break;
267 }
268 }
269 }
270 if (i == THREADS_LIMIT) {
271 jvmtiThreadInfo info;
272 info.name = (char*) "*retrieval error*";
273 ret = jvmti->GetThreadInfo(thread, &info);
274 JVMTI_ERROR_CHECK("GetThreadInfo %d \n", ret);
275
276 debug_printf("non-test thread: %s - %s ms\n", info.name,
277 jlong_to_string(milli(oth), buffer));
278 }
279 }
280 for (i = 1; i < THREADS_LIMIT; ++i) {
281 jweak tref = thread_info[i].ref;
282 if (tref != 0) {
283 totalIter += thread_info[i].iterationCount;
284 totalTimeCurr += thread_info[i].currThreadTime;
285 totalTime += thread_info[i].threadTime;
286 }
287 }
288 possibleTime = etime * processor_count;
289 debug_printf("Totals -- \n");
290 debug_printf(" Iter = %d\n", totalIter);
291 debug_printf(" Total GetThreadCpuTime = %s ns", jlong_to_string(totalTime, buffer));
292 debug_printf(" %s ms\n", jlong_to_string(milli(totalTime), buffer));
293 debug_printf(" Total GetCurrentThreadCpuTimerInfo = %s ns", jlong_to_string(totalTimeCurr, buffer));
346 // fail in this case.
347 if (!passed && milli(tt - ctt) <= 15) {
348 printf("Passing due to special consideration on Windows for 15ms timer accuracy\n");
349 passed = 1;
350 }
351 #endif
352 if (passed) {
353 debug_printf("Pass: currThreadTime(" JLONG_FORMAT ") >= %2.0f%% of threadTime(" JLONG_FORMAT ")\n",
354 ctt, 100.0 - VARIANCE_PERCENT, tt);
355 } else {
356 printf("FAIL: currThreadTime(" JLONG_FORMAT ") < %2.0f%% of threadTime(" JLONG_FORMAT ")\n",
357 ctt, 100.0 - VARIANCE_PERCENT, tt);
358 iGlobalStatus = 2;
359 }
360 }
361 }
362 }
363 }
364
365
366 }
|