1 /* 2 * Copyright (c) 2003, 2018, 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 #include <string.h> 25 #include "jvmti.h" 26 #include "agent_common.h" 27 #include "jni_tools.h" 28 #include "jvmti_tools.h" 29 30 extern "C" { 31 32 /* ============================================================================= */ 33 34 /* scaffold objects */ 35 static jlong timeout = 0; 36 37 /* constants */ 38 #define EVENTS_COUNT 3 39 40 /* tested events */ 41 static jvmtiEvent eventsList[EVENTS_COUNT] = { 42 JVMTI_EVENT_VM_INIT, 43 JVMTI_EVENT_THREAD_START, 44 JVMTI_EVENT_THREAD_END 45 }; 46 47 static const char* eventsNameList[EVENTS_COUNT] = { 48 "JVMTI_EVENT_VM_INIT", 49 "JVMTI_EVENT_THREAD_START", 50 "JVMTI_EVENT_THREAD_END" 51 }; 52 53 static int eventsCountList[EVENTS_COUNT]; 54 55 /* ============================================================================= */ 56 57 /** Clear events counters. */ 58 static void cleanEventCounts() { 59 int i; 60 61 for (i = 0; i < EVENTS_COUNT; i++) { 62 eventsCountList[i] = 0; 63 } 64 } 65 66 /** Check if all expected events received. */ 67 static int checkEventCounts() { 68 int success = NSK_TRUE; 69 int i; 70 71 NSK_DISPLAY0("Callbacks invoked:\n"); 72 for (i = 0; i < EVENTS_COUNT; i++) { 73 NSK_DISPLAY2(" %s: %d times\n", 74 eventsNameList[i], eventsCountList[i]); 75 } 76 77 if (eventsCountList[0] <= 0) { 78 NSK_COMPLAIN2("# No %s event callback invoked:\n" 79 "# invoked: %d times\n", 80 eventsNameList[0], eventsCountList[0]); 81 success = NSK_FALSE; 82 } 83 84 for (i = 1; i < EVENTS_COUNT; i++) { 85 if (eventsCountList[i] > 0) { 86 NSK_COMPLAIN2("# %s event callback was invoked after SetEventsCallback() for zero sized struct:\n" 87 "# invoked: %d times\n", 88 eventsNameList[i], eventsCountList[i]); 89 success = NSK_FALSE; 90 } 91 } 92 93 return success; 94 } 95 96 /* ============================================================================= */ 97 98 /** Agent algorithm. */ 99 static void JNICALL 100 agentProc(jvmtiEnv* jvmti, JNIEnv* jni, void* arg) { 101 NSK_DISPLAY0("Wait for debugee to generate events\n"); 102 if (!nsk_jvmti_waitForSync(timeout)) 103 return; 104 105 NSK_DISPLAY0(">>> Testcase #3: Check if no unexpected events callbacks were invoked\n"); 106 if (!checkEventCounts()) { 107 nsk_jvmti_setFailStatus(); 108 } 109 110 NSK_DISPLAY0("Disable events\n"); 111 nsk_jvmti_enableEvents(JVMTI_DISABLE, EVENTS_COUNT, eventsList, NULL); 112 113 NSK_DISPLAY0("Let debugee to finish\n"); 114 if (!nsk_jvmti_resumeSync()) 115 return; 116 } 117 118 /* ============================================================================= */ 119 120 /** 121 * Callback for THREAD_START event. 122 */ 123 JNIEXPORT void JNICALL 124 callbackThreadStart(jvmtiEnv* jvmti, JNIEnv* jni, jthread thread) { 125 NSK_DISPLAY1(" <THREAD_START>: thread: 0x%p\n", (void*)thread); 126 eventsCountList[1]++; 127 } 128 129 /** 130 * Callback for THREAD_END event. 131 */ 132 JNIEXPORT void JNICALL 133 callbackThreadEnd(jvmtiEnv* jvmti, JNIEnv* jni, jthread thread) { 134 NSK_DISPLAY1(" <THREAD_END>: thread: 0x%p\n", (void*)thread); 135 eventsCountList[2]++; 136 } 137 138 /** 139 * Callback for VM_INIT event. 140 */ 141 JNIEXPORT void JNICALL 142 callbackVMInit(jvmtiEnv* jvmti, JNIEnv* jni, jthread thread) { 143 NSK_DISPLAY1(" <VM_INIT>: thread: 0x%p\n", (void*)thread); 144 eventsCountList[0]++; 145 146 NSK_DISPLAY0(">>> Testcase #2: Invoke SetEventsCallback() for zero sized callbacks struct\n"); 147 { 148 jvmtiEventCallbacks eventCallbacks; 149 jint size = 0; 150 151 memset(&eventCallbacks, 0, sizeof(eventCallbacks)); 152 eventCallbacks.ThreadStart = callbackThreadStart; 153 eventCallbacks.ThreadEnd = callbackThreadEnd; 154 if (!NSK_JVMTI_VERIFY( 155 NSK_CPP_STUB3(SetEventCallbacks, jvmti, 156 &eventCallbacks, size))) { 157 nsk_jvmti_setFailStatus(); 158 } 159 160 nsk_jvmti_enableEvents(JVMTI_ENABLE, EVENTS_COUNT - 1, eventsList + 1, NULL); 161 } 162 } 163 164 /* ============================================================================= */ 165 166 /** Agent library initialization. */ 167 #ifdef STATIC_BUILD 168 JNIEXPORT jint JNICALL Agent_OnLoad_setevntcallb003(JavaVM *jvm, char *options, void *reserved) { 169 return Agent_Initialize(jvm, options, reserved); 170 } 171 JNIEXPORT jint JNICALL Agent_OnAttach_setevntcallb003(JavaVM *jvm, char *options, void *reserved) { 172 return Agent_Initialize(jvm, options, reserved); 173 } 174 JNIEXPORT jint JNI_OnLoad_setevntcallb003(JavaVM *jvm, char *options, void *reserved) { 175 return JNI_VERSION_1_8; 176 } 177 #endif 178 jint Agent_Initialize(JavaVM *jvm, char *options, void *reserved) { 179 jvmtiEnv* jvmti = NULL; 180 181 if (!NSK_VERIFY(nsk_jvmti_parseOptions(options))) 182 return JNI_ERR; 183 184 timeout = nsk_jvmti_getWaitTime() * 60 * 1000; 185 186 if (!NSK_VERIFY((jvmti = 187 nsk_jvmti_createJVMTIEnv(jvm, reserved)) != NULL)) 188 return JNI_ERR; 189 190 if (!NSK_VERIFY(nsk_jvmti_setAgentProc(agentProc, NULL))) 191 return JNI_ERR; 192 193 NSK_DISPLAY0(">>> Testcase #1: Set callbacks for all tested events\n"); 194 { 195 jvmtiEventCallbacks eventCallbacks; 196 197 cleanEventCounts(); 198 199 memset(&eventCallbacks, 0, sizeof(eventCallbacks)); 200 eventCallbacks.VMInit = callbackVMInit; 201 if (!NSK_JVMTI_VERIFY( 202 NSK_CPP_STUB3(SetEventCallbacks, jvmti, 203 &eventCallbacks, sizeof(eventCallbacks)))) { 204 nsk_jvmti_setFailStatus(); 205 } else { 206 nsk_jvmti_enableEvents(JVMTI_ENABLE, 1, eventsList, NULL); 207 } 208 } 209 return JNI_OK; 210 } 211 212 /* ============================================================================= */ 213 214 }