harmony-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From ge...@apache.org
Subject svn commit: r448639 - in /incubator/harmony/enhanced/drlvm/trunk/vm/vmcore: include/jvmti_internal.h src/exception/exceptions_jit.cpp src/jvmti/jvmti_break.cpp src/jvmti/jvmti_dasm.cpp src/jvmti/jvmti_step.cpp
Date Thu, 21 Sep 2006 19:17:22 GMT
Author: geirm
Date: Thu Sep 21 12:17:22 2006
New Revision: 448639

URL: http://svn.apache.org/viewvc?view=rev&rev=448639
Log:
HARMONY-1507

This patch fixes the following SingleStep bugs:

- Breakpoint was set for a wrong frame for regular bytecodes. The previous frame should be
used only for return type 
bytecodes
- Bug with uninitialized disassembler field in breakpoints when no other breakpoint is set
in the place where 
SingleStep breakpoint is going to be created
- Fixed exception RAISE state in breakpoints handler and exception event callback
- Fixed race condition when instrumenting compiled method
- Fixed function get_other_breakpoint_same_location
- Fixed SingleStep location prediction

The patch also adds a lot of tracing useful for debugging SingleStep code. 


Tested on Ubuntu 6.  smoke and c-unit pass.  kernel seemd to be usual mix of success and failure



Modified:
    incubator/harmony/enhanced/drlvm/trunk/vm/vmcore/include/jvmti_internal.h
    incubator/harmony/enhanced/drlvm/trunk/vm/vmcore/src/exception/exceptions_jit.cpp
    incubator/harmony/enhanced/drlvm/trunk/vm/vmcore/src/jvmti/jvmti_break.cpp
    incubator/harmony/enhanced/drlvm/trunk/vm/vmcore/src/jvmti/jvmti_dasm.cpp
    incubator/harmony/enhanced/drlvm/trunk/vm/vmcore/src/jvmti/jvmti_step.cpp

Modified: incubator/harmony/enhanced/drlvm/trunk/vm/vmcore/include/jvmti_internal.h
URL: http://svn.apache.org/viewvc/incubator/harmony/enhanced/drlvm/trunk/vm/vmcore/include/jvmti_internal.h?view=diff&rev=448639&r1=448638&r2=448639
==============================================================================
--- incubator/harmony/enhanced/drlvm/trunk/vm/vmcore/include/jvmti_internal.h (original)
+++ incubator/harmony/enhanced/drlvm/trunk/vm/vmcore/include/jvmti_internal.h Thu Sep 21 12:17:22
2006
@@ -316,12 +316,33 @@
             return NULL;
         }
 
-        BreakPoint *get_other_breakpoint_same_location(jmethodID m, jlocation l)
+        BreakPoint *get_other_breakpoint_same_location(BreakPoint *this_bp)
         {
             // assert(brkpntlst_lock._lock_or_null());
 
             for (BreakPoint *bp = brkpntlst; NULL != bp; bp = bp->next)
-                if (bp->method == m && bp->location == l)
+                if (bp != this_bp &&
+                    bp->method == this_bp->method && bp->location == this_bp->location)
+                    return bp;
+
+            return NULL;
+        }
+
+        BreakPoint *get_other_breakpoint_same_native_location(BreakPoint *this_bp)
+        {
+            // assert(brkpntlst_lock._lock_or_null());
+
+            for (BreakPoint *bp = brkpntlst; NULL != bp; bp = bp->next)
+                if (bp != this_bp && bp->native_location == this_bp->native_location)
+                    return bp;
+
+            return NULL;
+        }
+
+        BreakPoint *get_breakpoint_from_location(jmethodID method, jlocation location)
+        {
+            for (BreakPoint *bp = brkpntlst; NULL != bp; bp = bp->next)
+                if (bp->method == method && bp->location == location)
                     return bp;
 
             return NULL;
@@ -503,8 +524,8 @@
 jint load_agentpath(Agent *agent, const char *str, JavaVM_Internal *vm);
 
 // Breakpoints internal functions
-jvmtiError jvmti_get_next_bytecodes_up_stack_from_native(VM_thread *thread,
-    jvmti_StepLocation **next_step, unsigned *count);
+jvmtiError jvmti_get_next_bytecodes_stack_from_native(VM_thread *thread,
+    jvmti_StepLocation **next_step, unsigned *count, bool step_up);
 jvmtiError jvmti_set_breakpoint_for_jit(DebugUtilsTI *ti, BreakPoint *bp);
 void jvmti_remove_breakpoint_for_jit(DebugUtilsTI *ti, BreakPoint *bp);
 jvmtiError jvmti_set_single_step_breakpoints(DebugUtilsTI *ti,

Modified: incubator/harmony/enhanced/drlvm/trunk/vm/vmcore/src/exception/exceptions_jit.cpp
URL: http://svn.apache.org/viewvc/incubator/harmony/enhanced/drlvm/trunk/vm/vmcore/src/exception/exceptions_jit.cpp?view=diff&rev=448639&r1=448638&r2=448639
==============================================================================
--- incubator/harmony/enhanced/drlvm/trunk/vm/vmcore/src/exception/exceptions_jit.cpp (original)
+++ incubator/harmony/enhanced/drlvm/trunk/vm/vmcore/src/exception/exceptions_jit.cpp Thu
Sep 21 12:17:22 2006
@@ -299,12 +299,14 @@
                     }
                 }
 
+                BEGIN_RAISE_AREA;
                 // Reload exception object pointer because it could have
                 // moved while calling JVMTI callback
                 *exn_obj = jvmti_jit_exception_event_callback_call(*exn_obj,
                     interrupted_method_jit, interrupted_method,
                     interrupted_method_location,
                     jit, method, handler->get_handler_ip());
+                END_RAISE_AREA;
 
                 TRACE2("exn", ("setting return pointer to %d", exn_obj));
 

Modified: incubator/harmony/enhanced/drlvm/trunk/vm/vmcore/src/jvmti/jvmti_break.cpp
URL: http://svn.apache.org/viewvc/incubator/harmony/enhanced/drlvm/trunk/vm/vmcore/src/jvmti/jvmti_break.cpp?view=diff&rev=448639&r1=448638&r2=448639
==============================================================================
--- incubator/harmony/enhanced/drlvm/trunk/vm/vmcore/src/jvmti/jvmti_break.cpp (original)
+++ incubator/harmony/enhanced/drlvm/trunk/vm/vmcore/src/jvmti/jvmti_break.cpp Thu Sep 21
12:17:22 2006
@@ -34,6 +34,7 @@
 #include "jit_intf_cpp.h"
 #include "encoder.h"
 #include "m2n.h"
+#include "exceptions.h"
 
 
 #define INSTRUMENTATION_BYTE_HLT 0xf4 // HLT instruction
@@ -51,7 +52,10 @@
 VMEXPORT void*
 jvmti_process_interpreter_breakpoint_event(jmethodID method, jlocation location)
 {
-    TRACE2("jvmti.break", "BREAKPOINT occured, location = " << location);
+    TRACE2("jvmti.break", "BREAKPOINT occured: "
+        << class_get_name(method_get_class((Method*)method)) << "."
+        << method_get_name((Method*)method) << method_get_descriptor((Method*)method)
+        << " :" << location);
     ObjectHandle hThread = oh_allocate_local_handle();
     hThread->object = (Java_java_lang_Thread *)jthread_get_java_thread(hythread_self())->object;
     tmn_suspend_enable();
@@ -76,15 +80,21 @@
             if (NULL != func)
             {
                 JNIEnv *jni_env = (JNIEnv *)jni_native_intf;
-                TRACE2("jvmti.break", "Calling interpreter global breakpoint callback method
= " <<
-                    ((Method*)method)->get_name() << " location = " << location);
+                TRACE2("jvmti.break", "Calling interpreter global breakpoint callback: "
+                    << class_get_name(method_get_class((Method*)method)) << "."
+                    << method_get_name((Method*)method)
+                    << method_get_descriptor((Method*)method)
+                    << " :" << location);
 
                 ti->brkpntlst_lock._unlock();
                 func((jvmtiEnv*)env, jni_env, (jthread)hThread, method, location);
                 ti->brkpntlst_lock._lock();
 
-                TRACE2("jvmti.break", "Finished interpreter global breakpoint callback method
= " <<
-                    ((Method*)method)->get_name() << " location = " << location);
+                TRACE2("jvmti.break", "Finished interpreter global breakpoint callback: "
+                    << class_get_name(method_get_class((Method*)method)) << "."
+                    << method_get_name((Method*)method)
+                    << method_get_descriptor((Method*)method)
+                    << " :" << location);
             }
             bp = next_bp;
             continue; // Don't send local events
@@ -101,15 +111,21 @@
                 if (NULL != func)
                 {
                     JNIEnv *jni_env = (JNIEnv *)jni_native_intf;
-                    TRACE2("jvmti.break", "Calling interpreter local breakpoint callback
method = " <<
-                        ((Method*)method)->get_name() << " location = " <<
location);
+                    TRACE2("jvmti.break", "Calling interpreter local breakpoint callback:
"
+                        << class_get_name(method_get_class((Method*)method)) <<
"."
+                        << method_get_name((Method*)method)
+                        << method_get_descriptor((Method*)method)
+                        << " :" << location);
 
                     ti->brkpntlst_lock._unlock();
                     func((jvmtiEnv*)env, jni_env, (jthread)hThread, method, location);
                     ti->brkpntlst_lock._lock();
 
-                    TRACE2("jvmti.break", "Finished interpreter local breakpoint callback
method = " <<
-                        ((Method*)method)->get_name() << " location = " <<
location);
+                    TRACE2("jvmti.break", "Finished interpreter local breakpoint callback:
"
+                        << class_get_name(method_get_class((Method*)method)) <<
"."
+                        << method_get_name((Method*)method)
+                        << method_get_descriptor((Method*)method)
+                        << " :" << location);
                 }
             }
 
@@ -133,6 +149,32 @@
     return (ConditionCode)jump_type;
 }
 
+static BreakPoint *
+jvmti_check_and_get_single_step_breakpoint( DebugUtilsTI *ti,
+                                            VM_thread *vm_thread,
+                                            NativeCodePtr native_location)
+{
+    BreakPoint *ss_breakpoint = NULL;
+
+    if (ti->is_single_step_enabled())
+    {
+        if (NULL != vm_thread->ss_state)
+        {
+            for(unsigned iii = 0; iii < vm_thread->ss_state->predicted_bp_count;
iii++)
+            {
+                if (vm_thread->ss_state->predicted_breakpoints[iii]->native_location
==
+                    native_location)
+                {
+                    assert(!ss_breakpoint);
+                    ss_breakpoint =
+                        vm_thread->ss_state->predicted_breakpoints[iii];
+                }
+            }
+        }
+    }
+    return ss_breakpoint;
+} // jvmti_check_and_get_single_step_breakpoint
+
 bool jvmti_send_jit_breakpoint_event(Registers *regs)
 {
 #if PLATFORM_POSIX && INSTRUMENTATION_BYTE == INSTRUMENTATION_BYTE_INT3
@@ -142,7 +184,7 @@
     NativeCodePtr native_location = (NativeCodePtr)regs->get_ip();
 #endif
 
-    TRACE2("jvmti.break", "BREAKPOINT occured, location = " << native_location);
+    TRACE2("jvmti.break", "BREAKPOINT occured: " << native_location);
 
     DebugUtilsTI *ti = VM_Global_State::loader_env->TI;
     if (!ti->isEnabled() || ti->getPhase() != JVMTI_PHASE_LIVE)
@@ -160,6 +202,7 @@
     assert(!interpreter_enabled());
 
     M2nFrame *m2nf = m2n_push_suspended_frame(regs);
+    BEGIN_RAISE_AREA;
 
     hythread_t h_thread = hythread_self();
     jthread j_thread = jthread_get_java_thread(h_thread);
@@ -174,76 +217,80 @@
     InstructionDisassembler idisasm(*bp->disasm);
     JNIEnv *jni_env = (JNIEnv *)jni_native_intf;
 
-    BreakPoint *ss_breakpoint = NULL;
+    VM_thread *vm_thread = p_TLS_vmthread;
+    BreakPoint *ss_breakpoint = jvmti_check_and_get_single_step_breakpoint( ti,
+        vm_thread, native_location );
     // Check if there are Single Step type breakpoints in TLS
-    if (ti->is_single_step_enabled())
+    if (ss_breakpoint)
     {
-        VM_thread *vm_thread = p_TLS_vmthread;
-        if (NULL != vm_thread->ss_state)
+        TIEnv *ti_env = ti->getEnvironments();
+        TIEnv *next_env;
+        jlocation location = ss_breakpoint->location;
+        jmethodID method = ss_breakpoint->method;
+
+        while (NULL != ti_env)
         {
-            for(unsigned iii = 0; NULL != vm_thread->ss_state &&
-                    iii < vm_thread->ss_state->predicted_bp_count; iii++)
+            next_env = ti_env->next;
+            jvmtiEventSingleStep func =
+                (jvmtiEventSingleStep)ti_env->get_event_callback(JVMTI_EVENT_SINGLE_STEP);
+            if (NULL != func)
             {
-                if (vm_thread->ss_state->predicted_breakpoints[iii]->native_location
==
-                    native_location)
+                if (ti_env->global_events[JVMTI_EVENT_SINGLE_STEP - JVMTI_MIN_EVENT_TYPE_VAL])
                 {
-                    ss_breakpoint =
-                        vm_thread->ss_state->predicted_breakpoints[iii];
-
-                    TIEnv *ti_env = ti->getEnvironments();
-                    TIEnv *next_env;
-                    jlocation location = ss_breakpoint->location;
-                    jmethodID method = ss_breakpoint->method;
+                    TRACE2("jvmti.break.ss",
+                        "Calling JIT global SingleStep breakpoint callback: "
+                        << class_get_name(method_get_class((Method*)method)) <<
"."
+                        << method_get_name((Method*)method)
+                        << method_get_descriptor((Method*)method)
+                        << " :" << location << " :" << native_location);
+                    // fire global event
+                    ti->brkpntlst_lock._unlock();
+                    func((jvmtiEnv*)ti_env, jni_env, (jthread)hThread, method, location);
+                    ti->brkpntlst_lock._lock();
+                    TRACE2("jvmti.break.ss",
+                        "Finished JIT global SingleStep breakpoint callback: "
+                        << class_get_name(method_get_class((Method*)method)) <<
"."
+                        << method_get_name((Method*)method)
+                        << method_get_descriptor((Method*)method)
+                        << " :" << location << " :" << native_location);
+                    ti_env = next_env;
+                    continue;
+                }
 
-                    while (NULL != ti_env)
+                TIEventThread* next_ti_et;
+                // fire local events
+                for(TIEventThread* ti_et = ti_env->event_threads[JVMTI_EVENT_SINGLE_STEP
- JVMTI_MIN_EVENT_TYPE_VAL];
+                    ti_et != NULL; ti_et = next_ti_et)
+                {
+                    next_ti_et = ti_et->next;
+                    if (ti_et->thread == hythread_self())
                     {
-                        next_env = ti_env->next;
-                        jvmtiEventSingleStep func =
-                            (jvmtiEventSingleStep)ti_env->get_event_callback(JVMTI_EVENT_SINGLE_STEP);
-                        if (NULL != func)
-                        {
-                            if (ti_env->global_events[JVMTI_EVENT_SINGLE_STEP - JVMTI_MIN_EVENT_TYPE_VAL])
-                            {
-                                TRACE2("jvmti.break.ss",
-                                    "Calling JIT global SingleStep breakpoint callback method
= " <<
-                                    ((Method*)method)->get_name() << " location
= " << location);
-                                // fire global event
-                                ti->brkpntlst_lock._unlock();
-                                func((jvmtiEnv*)ti_env, jni_env, (jthread)hThread, method,
location);
-                                ti->brkpntlst_lock._lock();
-                                TRACE2("jvmti.break.ss",
-                                    "Finished JIT global SingleStep breakpoint callback method
= " <<
-                                    ((Method*)method)->get_name() << " location
= " << location);
-                                ti_env = next_env;
-                                continue;
-                            }
-
-                            // fire local events
-                            for(TIEventThread* ti_et = ti_env->event_threads[JVMTI_EVENT_SINGLE_STEP
- JVMTI_MIN_EVENT_TYPE_VAL];
-                                ti_et != NULL; ti_et = ti_et->next)
-                                if (ti_et->thread == hythread_self())
-                                {
-                                    TRACE2("jvmti.break.ss",
-                                        "Calling JIT local SingleStep breakpoint callback
method = " <<
-                                    ((Method*)method)->get_name() << " location
= " << location);
-                                    ti->brkpntlst_lock._unlock();
-                                    func((jvmtiEnv*)ti_env, jni_env,
-                                        (jthread)hThread, method, location);
-                                    ti->brkpntlst_lock._lock();
-                                    TRACE2("jvmti.break.ss",
-                                        "Finished JIT local SingleStep breakpoint callback
method = " <<
-                                    ((Method*)method)->get_name() << " location
= " << location);
-                                }
-                        }
-                        ti_env = next_env;
+                        TRACE2("jvmti.break.ss",
+                            "Calling JIT local SingleStep breakpoint callback: "
+                            << class_get_name(method_get_class((Method*)method)) <<
"."
+                            << method_get_name((Method*)method)
+                            << method_get_descriptor((Method*)method)
+                            << " :" << location << " :" << native_location);
+                        ti->brkpntlst_lock._unlock();
+                        func((jvmtiEnv*)ti_env, jni_env,
+                            (jthread)hThread, method, location);
+                        ti->brkpntlst_lock._lock();
+                        TRACE2("jvmti.break.ss",
+                            "Finished JIT local SingleStep breakpoint callback: "
+                            << class_get_name(method_get_class((Method*)method)) <<
"."
+                            << method_get_name((Method*)method)
+                            << method_get_descriptor((Method*)method)
+                            << " :" << location << " :" << native_location);
                     }
                 }
             }
-            // Reinitialize breakpoint after SingleStep because this
-            // breakpoint could have been deleted inside of callback
-            // if agent terminated single step
-            bp = ti->find_first_bpt(native_location);
+            ti_env = next_env;
         }
+
+        // Reinitialize breakpoint after SingleStep because this
+        // breakpoint could have been deleted inside of callback
+        // if agent terminated single step
+        bp = ti->find_first_bpt(native_location);
     }
 
 
@@ -256,7 +303,8 @@
         jmethodID method = bp->method;
         BreakPoint *next_bp = ti->find_next_bpt(bp, native_location);
 
-        if (bp == ss_breakpoint)
+        // check if this is a single step breakpoint
+        if (!bp->env)
         {
             // Don't send breakpoint event for breakpoint which was
             // actually SingleStep breakpoint
@@ -269,15 +317,21 @@
             jvmtiEventBreakpoint func = (jvmtiEventBreakpoint)env->get_event_callback(JVMTI_EVENT_BREAKPOINT);
             if (NULL != func)
             {
-                TRACE2("jvmti.break", "Calling JIT global breakpoint callback method = "
<<
-                    ((Method*)method)->get_name() << " location = " << location);
+                TRACE2("jvmti.break", "Calling JIT global breakpoint callback: "
+                    << class_get_name(method_get_class((Method*)method)) << "."
+                    << method_get_name((Method*)method)
+                    << method_get_descriptor((Method*)method)
+                    << " :" << location << " :" << native_location);
 
                 ti->brkpntlst_lock._unlock();
                 func((jvmtiEnv*)env, jni_env, (jthread)hThread, method, location);
                 ti->brkpntlst_lock._lock();
 
-                TRACE2("jvmti.break", "Finished JIT global breakpoint callback method = "
<<
-                    ((Method*)method)->get_name() << " location = " << location);
+                TRACE2("jvmti.break", "Finished JIT global breakpoint callback: "
+                    << class_get_name(method_get_class((Method*)method)) << "."
+                    << method_get_name((Method*)method)
+                    << method_get_descriptor((Method*)method)
+                    << " :" << location << " :" << native_location);
             }
             bp = next_bp;
             continue; // Don't send local events
@@ -294,15 +348,21 @@
                 if (NULL != func)
                 {
                     JNIEnv *jni_env = (JNIEnv *)jni_native_intf;
-                    TRACE2("jvmti.break", "Calling JIT local breakpoint callback method =
" <<
-                        ((Method*)method)->get_name() << " location = " <<
location);
+                    TRACE2("jvmti.break", "Calling JIT local breakpoint callback: "
+                        << class_get_name(method_get_class((Method*)method)) <<
"."
+                        << method_get_name((Method*)method)
+                        << method_get_descriptor((Method*)method)
+                        << " :" << location << " :" << native_location);
 
                     ti->brkpntlst_lock._unlock();
                     func((jvmtiEnv*)env, jni_env, (jthread)hThread, method, location);
                     ti->brkpntlst_lock._lock();
 
-                    TRACE2("jvmti.break", "Finished JIT local breakpoint callback method
= " <<
-                        ((Method*)method)->get_name() << " location = " <<
location);
+                    TRACE2("jvmti.break", "Finished JIT local breakpoint callback: "
+                        << class_get_name(method_get_class((Method*)method)) <<
"."
+                        << method_get_name((Method*)method)
+                        << method_get_descriptor((Method*)method)
+                        << " :" << location << " :" << native_location);
                 }
             }
 
@@ -320,7 +380,6 @@
     // special handling.
     InstructionDisassembler::Type type = idisasm.get_type();
 
-    VM_thread *vm_thread = p_TLS_vmthread;
     jbyte *instruction_buffer = vm_thread->jvmti_jit_breakpoints_handling_buffer;
     jbyte *interrupted_instruction = (jbyte *)native_location;
     jint instruction_length = idisasm.get_length_with_prefix();
@@ -398,23 +457,21 @@
 #endif
 
     // Set breakpoints on bytecodes after the current one
-    if (ti->is_single_step_enabled())
+    ss_breakpoint = jvmti_check_and_get_single_step_breakpoint( ti,
+        vm_thread, native_location );
+    if (ss_breakpoint)
     {
-        VM_thread *vm_thread = p_TLS_vmthread;
-        if (NULL != vm_thread->ss_state)
-        {
-            jvmti_StepLocation *locations;
-            unsigned locations_count;
+        jvmti_StepLocation *locations;
+        unsigned locations_count;
 
-            jvmti_SingleStepLocation(vm_thread, (Method *)ss_breakpoint->method,
-                (unsigned)ss_breakpoint->location, &locations, &locations_count);
+        jvmti_SingleStepLocation(vm_thread, (Method *)ss_breakpoint->method,
+           (unsigned)ss_breakpoint->location, &locations, &locations_count);
 
-            jvmti_remove_single_step_breakpoints(ti, vm_thread);
+        jvmti_remove_single_step_breakpoints(ti, vm_thread);
 
-            jvmtiError UNREF errorCode = jvmti_set_single_step_breakpoints(
-                ti, vm_thread, locations, locations_count);
-            assert(JVMTI_ERROR_NONE == errorCode);
-        }
+        jvmtiError UNREF errorCode = jvmti_set_single_step_breakpoints(
+            ti, vm_thread, locations, locations_count);
+        assert(JVMTI_ERROR_NONE == errorCode);
     }
 
     ti->brkpntlst_lock._unlock();
@@ -422,40 +479,55 @@
     tmn_suspend_disable();
     oh_discard_local_handle(hThread);
 
+    END_RAISE_AREA;
     m2n_set_last_frame(m2n_get_previous_frame(m2nf));
     STD_FREE(m2nf);
 
     return true;
 }
 
-jvmtiError jvmti_set_jit_mode_breakpoint(BreakPoint *bp)
+jvmtiError jvmti_set_jit_mode_breakpoint(DebugUtilsTI *ti, BreakPoint *bp)
 {
     // Function is always executed under global TI breakpoints lock
-
     // Find native location in the method code
     NativeCodePtr np = NULL;
     Method *m = (Method *)bp->method;
+    assert( m->get_state() == Method::ST_Compiled );
 
+    OpenExeJpdaError res = EXE_ERROR_NONE;
     for (CodeChunkInfo* cci = m->get_first_JIT_specific_info(); cci; cci = cci->_next)
     {
         JIT *jit = cci->get_jit();
-        OpenExeJpdaError res = jit->get_native_location_for_bc(m,
-            (uint16)bp->location, &np);
+        res = jit->get_native_location_for_bc(m, (uint16)bp->location, &np);
         if (res == EXE_ERROR_NONE)
             break;
     }
+    assert(res == EXE_ERROR_NONE);
 
     if (NULL == np)
         return JVMTI_ERROR_INTERNAL;
 
-    TRACE2("jvmti.break", "SetBreakpoint instrumenting native location " << np);
+    TRACE2("jvmti.break", "Set breakpoint: "
+        << class_get_name(method_get_class((Method *)bp->method)) << "."
+        << method_get_name((Method *)bp->method)
+        << method_get_descriptor((Method *)bp->method)
+        << " :" << bp->location << " :" << np);
 
     bp->native_location = np;
-    bp->disasm = new InstructionDisassembler(np);
 
-    jbyte *target_instruction = (jbyte *)np;
-    bp->id = (void *)(POINTER_SIZE_INT)*target_instruction;
-    *target_instruction = (jbyte)INSTRUMENTATION_BYTE;
+    BreakPoint *other_bp = ti->get_other_breakpoint_same_native_location(bp);
+    if (other_bp) // No other breakpoints were set in this place
+    {
+        assert(NULL == bp->disasm);
+        bp->id = other_bp->id;
+        bp->disasm = new InstructionDisassembler(*other_bp->disasm);
+    } else {
+        bp->disasm = new InstructionDisassembler(np);
+
+        jbyte *target_instruction = (jbyte *)np;
+        bp->id = (void *)(POINTER_SIZE_INT)*target_instruction;
+        *target_instruction = (jbyte)INSTRUMENTATION_BYTE;
+    }
 
     return JVMTI_ERROR_NONE;
 }
@@ -487,7 +559,7 @@
             if (bp->location == locations[iii])
                 continue;
 
-        jvmti_set_jit_mode_breakpoint(bp);
+        jvmti_set_jit_mode_breakpoint(ti, bp);
         locations[location_count++] = bp->location;
 
         method->remove_pending_breakpoint();
@@ -503,8 +575,7 @@
 {
     // Function is always executed under global TI breakpoints lock
 
-    BreakPoint *other_bp = ti->get_other_breakpoint_same_location(bp->method,
-        bp->location);
+    BreakPoint *other_bp = ti->get_other_breakpoint_same_location(bp);
 
     if (NULL == other_bp) // No other breakpoints were set in this place
     {
@@ -512,25 +583,27 @@
 
         if (m->get_state() == Method::ST_Compiled)
         {
-            jvmtiError errorCode = jvmti_set_jit_mode_breakpoint(bp);
+            jvmtiError errorCode = jvmti_set_jit_mode_breakpoint(ti, bp);
 
             if (JVMTI_ERROR_NONE != errorCode)
                 return JVMTI_ERROR_INTERNAL;
         }
         else
         {
-            TRACE2("jvmti.break", "Skipping setting breakpoing in method " <<
-                m->get_class()->name->bytes << "." <<
-                m->get_name()->bytes << " " << m->get_descriptor()->bytes
<<
-                " because it is not compiled yet");
+            TRACE2("jvmti.break", "Skipping setting breakpoint: "
+                << class_get_name(method_get_class((Method *)bp->method)) <<
"."
+                << method_get_name((Method *)bp->method)
+                << method_get_descriptor((Method *)bp->method)
+                << " :" << bp->location << ", because it is not compiled
yet");
             m->insert_pending_breakpoint();
         }
     }
     else
     {
         bp->id = other_bp->id;
-        if (NULL != bp->disasm)
-            bp->disasm = new InstructionDisassembler(*bp->disasm);
+        bp->native_location = other_bp->native_location;
+        assert(NULL == bp->disasm);
+        bp->disasm = new InstructionDisassembler(*other_bp->disasm);
     }
 
     ti->add_breakpoint(bp);
@@ -550,7 +623,12 @@
                    jmethodID method,
                    jlocation location)
 {
-    TRACE2("jvmti.break", "SetBreakpoint called, method = " << method << " ,
location = " << location);
+    TRACE2("jvmti.break", "SetBreakpoint called: "
+        << class_get_name(method_get_class((Method *)method)) << "."
+        << method_get_name((Method *)method)
+        << method_get_descriptor((Method *)method)
+        << " :" << location);
+
     SuspendEnabledChecker sec;
 
     jvmtiError errorCode;
@@ -566,8 +644,11 @@
         return JVMTI_ERROR_INVALID_METHODID;
 
     Method *m = (Method*) method;
-    TRACE2("jvmti.break", "SetBreakpoint method = " << m->get_class()->name->bytes
<< "." <<
-        m->get_name()->bytes << " " << m->get_descriptor()->bytes);
+    TRACE2("jvmti.break", "SetBreakpoint: "
+        << class_get_name(method_get_class((Method *)method)) << "."
+        << method_get_name((Method *)method)
+        << method_get_descriptor((Method *)method)
+        << " :" << location);
 
 #if defined (__INTEL_COMPILER) 
 #pragma warning( push )
@@ -604,14 +685,14 @@
     if (JVMTI_ERROR_NONE != errorCode)
         return errorCode;
 
+    memset( bp, 0, sizeof(BreakPoint));
     bp->method = method;
     bp->location = location;
     bp->env = p_env;
-    bp->disasm = NULL;
 
     if (interpreter_enabled())
     {
-        BreakPoint *other_bp = ti->get_other_breakpoint_same_location(method, location);
+        BreakPoint *other_bp = ti->get_other_breakpoint_same_location(bp);
 
         if (NULL == other_bp) // No other breakpoints were set in this place
             bp->id = interpreter.interpreter_ti_set_breakpoint(method, location);
@@ -634,19 +715,28 @@
 {
     // Function is always executed under global TI breakpoints lock
 
-    if (NULL == ti->get_other_breakpoint_same_location(bp->method, bp->location))
+    if (NULL == ti->get_other_breakpoint_same_location(bp))
     {
         Method *m = (Method *)bp->method;
 
         if (m->get_state() == Method::ST_Compiled)
         {
-            jbyte *target_instruction = (jbyte *)bp->native_location;
-            *target_instruction = (POINTER_SIZE_INT)bp->id;
+            if (NULL == ti->get_other_breakpoint_same_native_location(bp))
+            {
+                jbyte *target_instruction = (jbyte *)bp->native_location;
+                *target_instruction = (POINTER_SIZE_INT)bp->id;
+            }
         }
         else
             m->remove_pending_breakpoint();
     }
 
+    TRACE2("jvmti.break", "Remove breakpoint: "
+        << class_get_name(method_get_class((Method *)bp->method)) << "."
+        << method_get_name((Method *)bp->method)
+        << method_get_descriptor((Method *)bp->method)
+        << " :" << bp->location << " :" << bp->native_location);
+
     ti->remove_breakpoint(bp);
 }
 
@@ -663,7 +753,11 @@
                      jmethodID method,
                      jlocation location)
 {
-    TRACE2("jvmti.break", "ClearBreakpoint called, method = " << method << "
, location = " << location);
+    TRACE2("jvmti.break", "ClearBreakpoint called: "
+        << class_get_name(method_get_class((Method*)method)) << "."
+        << method_get_name((Method*)method)
+        << method_get_descriptor((Method*)method)
+        << " :" << location);
     SuspendEnabledChecker sec;
     jvmtiError errorCode;
 
@@ -678,8 +772,11 @@
         return JVMTI_ERROR_INVALID_METHODID;
 
     Method *m = (Method*) method;
-    TRACE2("jvmti.break", "ClearBreakpoint method = " << m->get_class()->name->bytes
<< "." <<
-        m->get_name()->bytes << " " << m->get_descriptor()->bytes);
+    TRACE2("jvmti.break", "ClearBreakpoint: "
+        << class_get_name(method_get_class((Method*)method)) << "."
+        << method_get_name((Method*)method)
+        << method_get_descriptor((Method*)method)
+        << " :" << location);
 
 #if defined (__INTEL_COMPILER) 
 #pragma warning( push )
@@ -715,7 +812,7 @@
 
     if (interpreter_enabled())
     {
-        if (NULL == ti->get_other_breakpoint_same_location(method, location))
+        if (NULL == ti->get_other_breakpoint_same_location(bp))
             // No other breakpoints were set in this place
             interpreter.interpreter_ti_clear_breakpoint(method, location, bp->id);
 

Modified: incubator/harmony/enhanced/drlvm/trunk/vm/vmcore/src/jvmti/jvmti_dasm.cpp
URL: http://svn.apache.org/viewvc/incubator/harmony/enhanced/drlvm/trunk/vm/vmcore/src/jvmti/jvmti_dasm.cpp?view=diff&rev=448639&r1=448638&r2=448639
==============================================================================
--- incubator/harmony/enhanced/drlvm/trunk/vm/vmcore/src/jvmti/jvmti_dasm.cpp (original)
+++ incubator/harmony/enhanced/drlvm/trunk/vm/vmcore/src/jvmti/jvmti_dasm.cpp Thu Sep 21 12:17:22
2006
@@ -27,6 +27,7 @@
 void InstructionDisassembler::disasm(const NativeCodePtr addr, 
                                      InstructionDisassembler * pidi)
 {
+    assert(addr);
     assert(pidi != NULL);
     Inst inst;
     pidi->len = DecoderBase::decode(addr, &inst);

Modified: incubator/harmony/enhanced/drlvm/trunk/vm/vmcore/src/jvmti/jvmti_step.cpp
URL: http://svn.apache.org/viewvc/incubator/harmony/enhanced/drlvm/trunk/vm/vmcore/src/jvmti/jvmti_step.cpp?view=diff&rev=448639&r1=448638&r2=448639
==============================================================================
--- incubator/harmony/enhanced/drlvm/trunk/vm/vmcore/src/jvmti/jvmti_step.cpp (original)
+++ incubator/harmony/enhanced/drlvm/trunk/vm/vmcore/src/jvmti/jvmti_step.cpp Thu Sep 21 12:17:22
2006
@@ -248,8 +248,8 @@
         case OPCODE_RETURN:         /* 0xb1 */
             assert( !is_wide );
             {
-                error = jvmti_get_next_bytecodes_up_stack_from_native( 
-                    thread, next_step, count );
+                error = jvmti_get_next_bytecodes_stack_from_native( 
+                    thread, next_step, count, true );
                 assert( error == JVMTI_ERROR_NONE );
             }
             break;
@@ -354,6 +354,16 @@
         break;
     } while( true );
 
+    for( unsigned index = 0; index < *count; index++ ) {
+        TRACE2( "jvmti.step", "Step: " << class_get_name(method_get_class(method))
+            << "." << method_get_name(method) << method_get_descriptor(method)
+            << " :" << bytecode_index << "\n      -> "
+            << class_get_name(method_get_class((*next_step)[index].method))
+            << "." << method_get_name((*next_step)[index].method)
+            << method_get_descriptor((*next_step)[index].method)
+            << " :" << (*next_step)[index].location )
+    }
+
     return;
 } // jvmti_SingleStepLocation
 
@@ -362,7 +372,7 @@
 {
     // Function is always executed under global TI breakpoints lock
     BreakPoint **thread_breakpoints;
-    jvmtiError errorCode = _allocate(sizeof(BreakPoint),
+    jvmtiError errorCode = _allocate(sizeof(BreakPoint*) * locations_number,
         (unsigned char **)&thread_breakpoints);
     if (JVMTI_ERROR_NONE != errorCode)
         return errorCode;
@@ -374,10 +384,15 @@
         if (JVMTI_ERROR_NONE != errorCode)
             return errorCode;
 
+        memset( bp, 0, sizeof(BreakPoint));
         bp->method = (jmethodID)locations[iii].method;
         bp->location = locations[iii].location;
-        bp->env = NULL;
-        bp->disasm = NULL;
+
+        TRACE2("jvmti.break.ss", "Set single step breakpoint: "
+            << class_get_name(method_get_class((Method *)bp->method)) << "."
+            << method_get_name((Method *)bp->method)
+            << method_get_descriptor((Method *)bp->method)
+            << " :" << bp->location);
 
         errorCode = jvmti_set_breakpoint_for_jit(ti, bp);
         if (JVMTI_ERROR_NONE != errorCode)
@@ -408,9 +423,10 @@
     ss_state->predicted_bp_count = 0;
 }
 
-jvmtiError jvmti_get_next_bytecodes_up_stack_from_native(VM_thread *thread,
+jvmtiError jvmti_get_next_bytecodes_stack_from_native(VM_thread *thread,
     jvmti_StepLocation **next_step,
-    unsigned *count)
+    unsigned *count,
+    bool step_up)
 {
     ASSERT_NO_INTERPRETER;
 
@@ -429,8 +445,10 @@
     }
 
     assert(!si_is_native(si));
-    // get previous stack frame
-    si_goto_previous(si);
+    if( step_up ) {
+        // get previous stack frame
+        si_goto_previous(si);
+    }
     if (!si_is_native(si)) {
         // stack frame is java frame, get frame method and location
         uint16 bc = 0;
@@ -441,11 +459,12 @@
         OpenExeJpdaError UNREF result =
                     jit->get_bc_location_for_native(func, ip, &bc);
         assert(result == EXE_ERROR_NONE);
+        TRACE2( "jvmti.break.ss", "SingleStep method IP: " << ip );
 
         // set step location structure
         *count = 1;
         jvmtiError error = _allocate( sizeof(jvmti_StepLocation), (unsigned char**)next_step
);
-        if( error == JVMTI_ERROR_NONE ) {
+        if( error != JVMTI_ERROR_NONE ) {
             si_free(si);
             return error;
         }
@@ -457,7 +476,7 @@
     }
     si_free(si);
     return JVMTI_ERROR_NONE;
-} // jvmti_get_next_bytecodes_up_stack_from_native
+} // jvmti_get_next_bytecodes_stack_from_native
 
 jvmtiError DebugUtilsTI::jvmti_single_step_start(void)
 {
@@ -477,6 +496,10 @@
     while ((ht = hythread_iterator_next(&threads_iterator)) != NULL)
     {
         VM_thread *vm_thread = get_vm_thread(ht);
+        if( !vm_thread ) {
+            assert(!hythread_is_alive(ht));
+            continue;
+        }
 
         // Init single step state for the thread
         jvmtiError errorCode = _allocate(sizeof(JVMTISingleStepState),
@@ -494,8 +517,8 @@
         jvmti_StepLocation *locations;
         unsigned locations_number;
 
-        errorCode = jvmti_get_next_bytecodes_up_stack_from_native(
-            vm_thread, &locations, &locations_number);
+        errorCode = jvmti_get_next_bytecodes_stack_from_native(
+            vm_thread, &locations, &locations_number, false);
 
         if (JVMTI_ERROR_NONE != errorCode)
         {
@@ -540,6 +563,10 @@
     while ((ht = hythread_iterator_next(&threads_iterator)) != NULL)
     {
         VM_thread *vm_thread = get_vm_thread(ht);
+        if( !vm_thread ) {
+            assert(!hythread_is_alive(ht));
+            continue;
+        }
         jvmti_remove_single_step_breakpoints(this, vm_thread);
         _deallocate((unsigned char *)vm_thread->ss_state);
         vm_thread->ss_state = NULL;



Mime
View raw message