1 /* 2 * Copyright (c) 2004, 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 <stdlib.h> 25 #include <string.h> 26 #include "jni_tools.h" 27 #include "agent_common.h" 28 #include "jvmti_tools.h" 29 30 #define PASSED 0 31 #define STATUS_FAILED 2 32 #define SAMPLE_TAG ((jlong) 222222) 33 34 extern "C" { 35 36 /* ========================================================================== */ 37 38 /* scaffold objects */ 39 static jlong timeout = 0; 40 41 /* test objects */ 42 static jobject testedObject = NULL; 43 static jobject testedInstance = NULL; 44 static jclass testedClass = NULL; 45 static int ObjectsCount = 0; 46 47 /* ========================================================================== */ 48 49 /** callback functions **/ 50 51 static jvmtiIterationControl JNICALL heap_object_callback 52 (jlong class_tag, jlong size, jlong* tag_ptr, void* user_data) 53 { 54 char buffer[32]; 55 56 if (*tag_ptr != 0) { 57 NSK_DISPLAY1("tag = %s\n", jlong_to_string(*tag_ptr, buffer)); 58 if (*tag_ptr == SAMPLE_TAG) { 59 ObjectsCount++; 60 } else { 61 NSK_COMPLAIN1("testedObject tagged incorrectly, expected=%s,", 62 jlong_to_string(SAMPLE_TAG, buffer)); 63 NSK_COMPLAIN1(" got=%s\n", jlong_to_string(*tag_ptr, buffer)); 64 nsk_jvmti_setFailStatus(); 65 } 66 } 67 68 return JVMTI_ITERATION_CONTINUE; 69 } 70 71 /* ========================================================================== */ 72 73 static int prepare(JNIEnv* jni) { 74 const char* CLASS_NAME = "nsk/jvmti/scenarios/multienv/MA04/ma04t002"; 75 const char* FIELD_NAME = "testedObject2"; 76 const char* FIELD_SIGNATURE = "Ljava/lang/Object;"; 77 const char* INSTANCE_NAME = "testedInstance2"; 78 const char* INSTANCE_SIGNATURE = "Lnsk/jvmti/scenarios/multienv/MA04/ma04t002;"; 79 jfieldID fid = NULL; 80 81 NSK_DISPLAY0("Obtain tested object from a static field of debugee class\n"); 82 83 NSK_DISPLAY1("Find class: %s\n", CLASS_NAME); 84 if (!NSK_JNI_VERIFY(jni, (testedClass = 85 NSK_CPP_STUB2(FindClass, jni, CLASS_NAME)) != NULL)) 86 return NSK_FALSE; 87 88 if (!NSK_JNI_VERIFY(jni, (testedClass = (jclass) 89 NSK_CPP_STUB2(NewGlobalRef, jni, testedClass)) != NULL)) 90 return NSK_FALSE; 91 92 NSK_DISPLAY2("Find field: %s:%s\n", FIELD_NAME, FIELD_SIGNATURE); 93 if (!NSK_JNI_VERIFY(jni, (fid = 94 NSK_CPP_STUB4(GetStaticFieldID, jni, testedClass, 95 FIELD_NAME, FIELD_SIGNATURE)) != NULL)) 96 return NSK_FALSE; 97 98 if (!NSK_JNI_VERIFY(jni, (testedObject = 99 NSK_CPP_STUB3(GetStaticObjectField, jni, testedClass, fid)) != NULL)) 100 return NSK_FALSE; 101 102 NSK_DISPLAY2("Find class instance: %s:%s\n", 103 INSTANCE_NAME, INSTANCE_SIGNATURE); 104 if (!NSK_JNI_VERIFY(jni, (fid = 105 NSK_CPP_STUB4(GetStaticFieldID, jni, testedClass, 106 INSTANCE_NAME, INSTANCE_SIGNATURE)) != NULL)) 107 return NSK_FALSE; 108 109 if (!NSK_JNI_VERIFY(jni, (testedInstance = 110 NSK_CPP_STUB3(GetStaticObjectField, jni, testedClass, fid)) != NULL)) 111 return NSK_FALSE; 112 113 return NSK_TRUE; 114 } 115 116 /* ========================================================================== */ 117 118 /** Agent algorithm. */ 119 static void JNICALL 120 agentProc(jvmtiEnv* jvmti, JNIEnv* jni, void* arg) { 121 jint dummy; 122 123 if (!nsk_jvmti_waitForSync(timeout)) 124 return; 125 126 if (!prepare(jni)) { 127 nsk_jvmti_setFailStatus(); 128 return; 129 } 130 131 NSK_DISPLAY0("Testcase #1: check that there are no tagged objects\n"); 132 133 ObjectsCount = 0; 134 if (!NSK_JVMTI_VERIFY(NSK_CPP_STUB4(IterateOverHeap, jvmti, 135 JVMTI_HEAP_OBJECT_EITHER, heap_object_callback, &dummy))) { 136 nsk_jvmti_setFailStatus(); 137 return; 138 } 139 NSK_DISPLAY1("ObjectsCount = %d\n", ObjectsCount); 140 if (ObjectsCount != 0) { 141 NSK_COMPLAIN1("Some objects were unexpectedly tagged: %d\n", 142 ObjectsCount); 143 nsk_jvmti_setFailStatus(); 144 } 145 146 ObjectsCount = 0; 147 if (!NSK_JVMTI_VERIFY(NSK_CPP_STUB4(IterateOverHeap, jvmti, 148 JVMTI_HEAP_OBJECT_TAGGED, heap_object_callback, &dummy))) { 149 nsk_jvmti_setFailStatus(); 150 return; 151 } 152 NSK_DISPLAY1("ObjectsCount = %d\n", ObjectsCount); 153 if (ObjectsCount != 0) { 154 NSK_COMPLAIN1("Some objects were unexpectedly tagged: %d\n", 155 ObjectsCount); 156 nsk_jvmti_setFailStatus(); 157 } 158 159 ObjectsCount = 0; 160 if (!NSK_JVMTI_VERIFY(NSK_CPP_STUB5(IterateOverInstancesOfClass, jvmti, 161 testedClass, JVMTI_HEAP_OBJECT_EITHER, heap_object_callback, &dummy))) { 162 nsk_jvmti_setFailStatus(); 163 return; 164 } 165 NSK_DISPLAY1("ObjectsCount = %d\n", ObjectsCount); 166 if (ObjectsCount != 0) { 167 NSK_COMPLAIN1("Some class instances were unexpectedly tagged: %d\n", 168 ObjectsCount); 169 nsk_jvmti_setFailStatus(); 170 } 171 172 ObjectsCount = 0; 173 if (!NSK_JVMTI_VERIFY(NSK_CPP_STUB5(IterateOverInstancesOfClass, jvmti, 174 testedClass, JVMTI_HEAP_OBJECT_EITHER, heap_object_callback, &dummy))) { 175 nsk_jvmti_setFailStatus(); 176 return; 177 } 178 NSK_DISPLAY1("ObjectsCount = %d\n", ObjectsCount); 179 if (ObjectsCount != 0) { 180 NSK_COMPLAIN1("Some class instances were unexpectedly tagged: %d\n", 181 ObjectsCount); 182 nsk_jvmti_setFailStatus(); 183 } 184 185 if (!NSK_JVMTI_VERIFY(NSK_CPP_STUB3(SetTag, jvmti, testedObject, 186 SAMPLE_TAG))) { 187 nsk_jvmti_setFailStatus(); 188 return; 189 } 190 191 if (!NSK_VERIFY(nsk_jvmti_resumeSync())) 192 return; 193 if (!NSK_VERIFY(nsk_jvmti_waitForSync(timeout))) 194 return; 195 196 197 NSK_DISPLAY0("Testcase #2: check that there is only one object tagged\n"); 198 199 ObjectsCount = 0; 200 if (!NSK_JVMTI_VERIFY(NSK_CPP_STUB4(IterateOverHeap, jvmti, 201 JVMTI_HEAP_OBJECT_EITHER, heap_object_callback, &dummy))) { 202 nsk_jvmti_setFailStatus(); 203 return; 204 } 205 NSK_DISPLAY1("ObjectsCount = %d\n", ObjectsCount); 206 if (ObjectsCount != 1) { 207 NSK_COMPLAIN1("Expected 1 object to be tagged: %d\n", ObjectsCount); 208 nsk_jvmti_setFailStatus(); 209 } 210 211 ObjectsCount = 0; 212 if (!NSK_JVMTI_VERIFY(NSK_CPP_STUB4(IterateOverHeap, jvmti, 213 JVMTI_HEAP_OBJECT_TAGGED, heap_object_callback, &dummy))) { 214 nsk_jvmti_setFailStatus(); 215 return; 216 } 217 NSK_DISPLAY1("ObjectsCount = %d\n", ObjectsCount); 218 if (ObjectsCount != 1) { 219 NSK_COMPLAIN1("Expected 1 object to be tagged: %d\n", ObjectsCount); 220 nsk_jvmti_setFailStatus(); 221 } 222 223 ObjectsCount = 0; 224 if (!NSK_JVMTI_VERIFY(NSK_CPP_STUB4(IterateOverHeap, jvmti, 225 JVMTI_HEAP_OBJECT_UNTAGGED, heap_object_callback, &dummy))) { 226 nsk_jvmti_setFailStatus(); 227 return; 228 } 229 NSK_DISPLAY1("ObjectsCount = %d\n", ObjectsCount); 230 if (ObjectsCount != 0) { 231 NSK_COMPLAIN1("Some tagged objects were unexpectedly shown as untagged: %d\n", 232 ObjectsCount); 233 nsk_jvmti_setFailStatus(); 234 } 235 236 if (!NSK_JVMTI_VERIFY(NSK_CPP_STUB3(SetTag, jvmti, testedInstance, 237 SAMPLE_TAG))) { 238 nsk_jvmti_setFailStatus(); 239 return; 240 } 241 242 if (!NSK_VERIFY(nsk_jvmti_resumeSync())) 243 return; 244 if (!NSK_VERIFY(nsk_jvmti_waitForSync(timeout))) 245 return; 246 247 248 NSK_DISPLAY0("Testcase #3: check that there is only one class object tagged\n"); 249 250 ObjectsCount = 0; 251 if (!NSK_JVMTI_VERIFY(NSK_CPP_STUB5(IterateOverInstancesOfClass, jvmti, 252 testedClass, JVMTI_HEAP_OBJECT_EITHER, heap_object_callback, &dummy))) { 253 nsk_jvmti_setFailStatus(); 254 return; 255 } 256 NSK_DISPLAY1("ObjectsCount = %d\n", ObjectsCount); 257 if (ObjectsCount != 1) { 258 NSK_COMPLAIN1("Expected 1 class instance to be tagged: %d\n", 259 ObjectsCount); 260 nsk_jvmti_setFailStatus(); 261 } 262 263 ObjectsCount = 0; 264 if (!NSK_JVMTI_VERIFY(NSK_CPP_STUB5(IterateOverInstancesOfClass, jvmti, 265 testedClass, JVMTI_HEAP_OBJECT_EITHER, heap_object_callback, &dummy))) { 266 nsk_jvmti_setFailStatus(); 267 return; 268 } 269 NSK_DISPLAY1("ObjectsCount = %d\n", ObjectsCount); 270 if (ObjectsCount != 1) { 271 NSK_COMPLAIN1("Expected 1 class instance to be tagged: %d\n", 272 ObjectsCount); 273 nsk_jvmti_setFailStatus(); 274 } 275 276 ObjectsCount = 0; 277 if (!NSK_JVMTI_VERIFY(NSK_CPP_STUB4(IterateOverHeap, jvmti, 278 JVMTI_HEAP_OBJECT_UNTAGGED, heap_object_callback, &dummy))) { 279 nsk_jvmti_setFailStatus(); 280 return; 281 } 282 NSK_DISPLAY1("ObjectsCount = %d\n", ObjectsCount); 283 if (ObjectsCount != 0) { 284 NSK_COMPLAIN1("Some tagged class instances were unexpectedly shown as untagged: %d\n", 285 ObjectsCount); 286 nsk_jvmti_setFailStatus(); 287 } 288 289 290 NSK_TRACE(NSK_CPP_STUB2(DeleteGlobalRef, jni, testedClass)); 291 292 if (!nsk_jvmti_resumeSync()) 293 return; 294 } 295 296 /* ========================================================================== */ 297 298 /** Agent library initialization. */ 299 #ifdef STATIC_BUILD 300 JNIEXPORT jint JNICALL Agent_OnLoad_ma04t002a(JavaVM *jvm, char *options, void *reserved) { 301 return Agent_Initialize(jvm, options, reserved); 302 } 303 JNIEXPORT jint JNICALL Agent_OnAttach_ma04t002a(JavaVM *jvm, char *options, void *reserved) { 304 return Agent_Initialize(jvm, options, reserved); 305 } 306 JNIEXPORT jint JNI_OnLoad_ma04t002a(JavaVM *jvm, char *options, void *reserved) { 307 return JNI_VERSION_1_8; 308 } 309 #endif 310 jint Agent_Initialize(JavaVM *jvm, char *options, void *reserved) { 311 jvmtiEnv* jvmti = NULL; 312 jvmtiEventCallbacks callbacks; 313 jvmtiCapabilities caps; 314 315 NSK_DISPLAY0("Agent_OnLoad\n"); 316 317 if (!NSK_VERIFY(nsk_jvmti_parseOptions(options))) 318 return JNI_ERR; 319 320 timeout = nsk_jvmti_getWaitTime() * 60 * 1000; 321 322 if (!NSK_VERIFY((jvmti = 323 nsk_jvmti_createJVMTIEnv(jvm, reserved)) != NULL)) 324 return JNI_ERR; 325 326 memset(&caps, 0, sizeof(caps)); 327 caps.can_tag_objects = 1; 328 caps.can_generate_object_free_events = 1; 329 if (!NSK_JVMTI_VERIFY(NSK_CPP_STUB2(AddCapabilities, jvmti, &caps))) { 330 return JNI_ERR; 331 } 332 333 if (!NSK_VERIFY(nsk_jvmti_setAgentProc(agentProc, NULL))) 334 return JNI_ERR; 335 336 memset(&callbacks, 0, sizeof(callbacks)); 337 if (!NSK_VERIFY(nsk_jvmti_init_MA(&callbacks))) 338 return JNI_ERR; 339 340 if (!NSK_JVMTI_VERIFY(NSK_CPP_STUB4(SetEventNotificationMode, 341 jvmti, JVMTI_ENABLE, JVMTI_EVENT_OBJECT_FREE, NULL))) 342 return JNI_ERR; 343 344 return JNI_OK; 345 } 346 347 /* ========================================================================== */ 348 349 }