1 Reply Latest reply: Oct 27, 2012 2:16 AM by 971002 RSS

    Agent_OnLoad, VMInit / Death never called.

      Hello all,

      First of all, my environment details:-

      OS: Windows 7 64 bit
      JDK: 1.7

      Now, I have a very simple JVMTI agent which prints messages on screen in the OnLoad, OnUnload, VMInit, VMDeath events. My agent runs fine with the following Java program:-
      public class Main {
           public static void main(String[] args) {
      The above when executed prints the following:-

      Agent Onload+
      VM INIT+
      VM DEATH+
      Agent OnUnload+

      However, it prints nothing at all if I run the following Java code:-
      public class Main {
           public static void main(String[] args) {
                new Thread(new Worker()).start();     
           private static class Worker implements Runnable {
                public void run() {
                     while(true) {
                          try {
                          } catch(Exception e) {
      It only prints out the string Executed*

      Notice that in the second case, I have a perpetually running Java program. However, shouldn't the Agent_OnLoad and the vmInit methods not be called at the very least here as well? Am I missing something here? Please find the agent code below:-
      #include <jni.h>
      #include <jni_md.h>
      #include <jvmti.h>
      #include <stdio.h>
      #include <stdlib.h>
      #include <stddef.h>
      #include <string.h>
      jvmtiEnv *env = NULL;
      jrawMonitorID lock;
      void enterAgentMonitor() {
      void exitAgentMonitor() {
      static void JNICALL vmInit(jvmtiEnv *jvmti, JNIEnv *env, jthread thread) {
                fprintf(stdout, "VM INIT\n");    
      static void JNICALL vmDeath(jvmtiEnv *jvmti, JNIEnv *env) {
           jvmtiError err;
           err = jvmti->ForceGarbageCollection();
                fprintf(stdout, "VM DEATH\n");
      JNIEXPORT jint JNICALL Agent_OnLoad(JavaVM *jvm, char *options, void *reserved) {
           fprintf(stdout, "Agent Onload\n");
           jvm->GetEnv((void **)&env, JVMTI_VERSION);
           //Create the lock used for critical sections within the agent.
           env->CreateRawMonitor("Lock", &lock);
           jvmtiCapabilities jvmCaps;
           jvmtiEventCallbacks callbacks;
           memset(&jvmCaps, 0, sizeof(jvmtiCapabilities));
           memset(&callbacks, 0, sizeof(jvmtiEventCallbacks));
           //Add the capabilities that we will need for method callbacks.
           jvmCaps.can_signal_thread = 1;
           jvmCaps.can_get_owned_monitor_info = 1;
           jvmCaps.can_generate_method_entry_events = 1;
           jvmCaps.can_generate_exception_events = 1;
           jvmCaps.can_generate_vm_object_alloc_events = 1;
           jvmCaps.can_tag_objects = 1;
           callbacks.VMInit = &vmInit;
           callbacks.VMDeath = &vmDeath;
           env->SetEventNotificationMode(JVMTI_ENABLE, JVMTI_EVENT_VM_INIT, 0);
           env->SetEventNotificationMode(JVMTI_ENABLE, JVMTI_EVENT_VM_DEATH, 0);
           env->SetEventCallbacks(&callbacks, sizeof(jvmtiEventCallbacks));
           return JNI_OK;
      JNIEXPORT void JNICALL Agent_OnUnload(JavaVM *vm) {
           fprintf(stdout, "Agent OnUnload\n");
      The VM correctly points to the DLL using the agentpath VM argument in both the cases. Any help will be appreciated!

      Edited by: 967999 on Oct 27, 2012 12:08 AM

      Edited by: 967999 on Oct 27, 2012 12:11 AM