* src/vm/jit/show.h (show_filters_init, show_filters_apply, show_filters_test_verbose...
authorpm <none@none>
Fri, 25 May 2007 12:41:03 +0000 (12:41 +0000)
committerpm <none@none>
Fri, 25 May 2007 12:41:03 +0000 (12:41 +0000)
* src/vm/jit/show.c: Likewise.
* src/vm/jit/jit.c (jit_compile_intern): Honour filters.
* src/vm/jit/codegen-common.c (codegen_add_patch_ref, codegen_generate_stub_native): Honour PATCHER_LONGBRANCHES_NOPS if defined, honour filters.
* src/vm/builtin.c (builtin_trace_exception, builtin_verbosecall_enter, builtin_verbosecall_exit): Honour filters.
* src/vm/signal.c (signal_init): Register SIGILL handler on s390.
* src/vm/vm.c: Handle -XXfi, -XXfe, -XXfm commandline options.
* src/vm/signallocal.h (md_signal_handler_sigill): Forward declare on s390.
* src/threads/none/threads.h (_no_threads_filterverbosecallctr, FILTERVERBOSECALLCTR): Added.
* src/threads/native/threads.h (struct threadobject): Added filterverbosecallctr.
* src/threads/native/threads.c (threads_impl_thread_new): Initialize filterverbosecallctr.
* src/threads/critical.c (critical_comparator): On s390, clear bit 32 of pointer when comparing.
* src/vmcore/options.h (opt_filter_verbosecall_include, opt_filter_verbosecall_exclude, opt_filter_show_method): Added.
* src/vmcore/options.c: Likewise.
* src/vmcore/method.h (struct methodinfo): Added filtermatches.
* configure.ac: If no NDEBUG and regex.h header is present, define ENABLE_DEBUG_FILTER.
* src/vm/jit/s390/emit.c,
src/vm/jit/s390/md.c,
src/vm/jit/s390/codegen.c,
src/vm/jit/s390/codegen.h,
src/vm/jit/s390/tests/dacapo.status,
src/vm/jit/s390/patcher.c: Changed a lot.

22 files changed:
configure.ac
src/threads/critical.c
src/threads/native/threads.c
src/threads/native/threads.h
src/threads/none/threads.h
src/vm/builtin.c
src/vm/jit/codegen-common.c
src/vm/jit/jit.c
src/vm/jit/s390/codegen.c
src/vm/jit/s390/codegen.h
src/vm/jit/s390/emit.c
src/vm/jit/s390/md.c
src/vm/jit/s390/patcher.c
src/vm/jit/s390/tests/dacapo.status
src/vm/jit/show.c
src/vm/jit/show.h
src/vm/signal.c
src/vm/signallocal.h
src/vm/vm.c
src/vmcore/method.h
src/vmcore/options.c
src/vmcore/options.h

index 11672d3969e8b0acb09d44c04024427f352df64e..139aff4e00ae8e8a09eb83beee15512f7210f949 100644 (file)
@@ -22,7 +22,7 @@ dnl along with this program; if not, write to the Free Software
 dnl Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
 dnl 02110-1301, USA.
 dnl 
-dnl $Id: configure.ac 7960 2007-05-23 22:04:49Z twisti $
+dnl $Id: configure.ac 7966 2007-05-25 12:41:03Z pm $
 
 dnl Process this file with autoconf to produce a configure script.
 
@@ -890,6 +890,10 @@ dnl check for some programs we need
 AC_PROG_JAVAC
 AC_PROG_JAR
 
+dnl If debug build, check for regex.h. If found enable debug filter
+if test x"${NDEBUG}" = "xno"; then
+       AC_CHECK_HEADERS([regex.h], [AC_DEFINE(ENABLE_DEBUG_FILTER, 1, [debug filter])])
+fi
 
 dnl finally pass CFLAGS to Makefiles via AM_CFLAGS
 CFLAGS=$OPT_CFLAGS
index a0d459561cd3dfb34687ac45b48e2fa63bc33567..5dda6b4c1c4303e3e8adbf3928dd43aaf8593e42 100644 (file)
@@ -86,17 +86,28 @@ static s4 critical_comparator(const void *treenode, const void *node)
        treecsn = treenode;
        csn     = node;
 
+#ifdef __S390__
+#      define ADDR_MASK(x) ((u1 *)((s4)(x) & 0x7FFFFFFF))
+#else
+#      define ADDR_MASK(x) (x)
+#endif
+
        /* compare for avl_find if we have found an entry */
 
-       if ((treecsn->start <= csn->start) && (csn->start < treecsn->end))
+       if (
+               (ADDR_MASK(treecsn->start) <= ADDR_MASK(csn->start)) && 
+               (ADDR_MASK(csn->start) < ADDR_MASK(treecsn->end))
+       )
                return 0;
 
        /* these are for walking the tree */
 
-       if (treecsn->start < csn->start)
+       if (ADDR_MASK(treecsn->start) < ADDR_MASK(csn->start))
                return -1;
        else
                return 1;
+
+#undef ADDR_MASK
 }
 
 
index 39e15de9c2b73a6ef7a12b717982b59be47299eb..d9df48ed01b475b72d0a1f7aacefd00155d8b4cd 100644 (file)
@@ -22,7 +22,7 @@
    Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
    02110-1301, USA.
 
-   $Id: threads.c 7963 2007-05-24 10:21:16Z twisti $
+   $Id: threads.c 7966 2007-05-25 12:41:03Z pm $
 
 */
 
@@ -620,6 +620,12 @@ void threads_impl_thread_new(threadobject *t)
 
        pthread_mutex_init(&(t->waitmutex), NULL);
        pthread_cond_init(&(t->waitcond), NULL);
+
+#if defined(ENABLE_DEBUG_FILTER)
+       /* Initialize filter counters */
+       t->filterverbosecallctr[0] = 0;
+       t->filterverbosecallctr[1] = 0;
+#endif
 }
 
 
index 343fb11756d867571a4a9dd7680011bd5c21d0ba..4f5193ddbbe5aa9b1b69a819a044b8381f08c362 100644 (file)
@@ -22,7 +22,7 @@
    Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
    02110-1301, USA.
 
-   $Id: threads.h 7963 2007-05-24 10:21:16Z twisti $
+   $Id: threads.h 7966 2007-05-25 12:41:03Z pm $
 
 */
 
@@ -135,6 +135,11 @@ struct threadobject {
 #endif
 
        dumpinfo_t            dumpinfo;     /* dump memory info structure         */
+
+#if defined(ENABLE_DEBUG_FILTER)
+       u2                    filterverbosecallctr[2]; /* counters for verbose call filter */
+#endif
+
        listnode_t            linkage;      /* threads-list                       */
 };
 
@@ -148,6 +153,11 @@ struct threadobject {
 
 #define STACKFRAMEINFO    (THREADOBJECT->_stackframeinfo)
 
+/* counter for verbose call filter ********************************************/
+
+#if defined(ENABLE_DEBUG_FILTER)
+#      define FILTERVERBOSECALLCTR (THREADOBJECT->filterverbosecallctr)
+#endif
 
 /* functions ******************************************************************/
 
index 4216d8582d8225f052535a6b2b96e1d7d960ba88..19146040aa79a98ac66401802f48744c0909da5d 100644 (file)
@@ -59,6 +59,11 @@ extern struct stackframeinfo       *_no_threads_stackframeinfo;
 
 #define STACKFRAMEINFO      (_no_threads_stackframeinfo)
 
+#if defined(ENABLE_DEBUG_FILTER)
+extern u2 _no_threads_filterverbosecallctr[2];
+#define FILTERVERBOSECALLCTR (_no_threads_filterverbosecallctr)
+#endif
+
 #endif /* _THREADS_H */
 
 
index 08f8645c1e64cc998b34cf07bfc6f9303e5edf06..1bbfd242eb7809f6c955b3aee3735ab34e3182b5 100644 (file)
@@ -28,7 +28,7 @@
    calls instead of machine instructions, using the C calling
    convention.
 
-   $Id: builtin.c 7907 2007-05-15 09:25:27Z tbfg $
+   $Id: builtin.c 7966 2007-05-25 12:41:03Z pm $
 
 */
 
@@ -83,6 +83,9 @@
 #include <vmlog_cacao.h>
 #endif
 
+#if defined(ENABLE_DEBUG_FILTER)
+#      include "vm/jit/show.h"
+#endif
 
 /* include builtin tables *****************************************************/
 
@@ -1151,6 +1154,10 @@ java_objectheader *builtin_trace_exception(java_objectheader *xptr,
        s4    dumpsize;
        codeinfo *code;
 
+#if defined(ENABLE_DEBUG_FILTER)
+       if (! show_filters_test_verbosecall_exit(m)) return xptr;
+#endif
+
 #if defined(ENABLE_VMLOG)
        return xptr;
 #endif
@@ -1394,7 +1401,6 @@ static char *builtin_print_argument(char *logtext, s4 *logtextlen,
 }
 #endif /* !defined(NDEBUG) */
 
-
 /* builtin_verbosecall_enter ***************************************************
 
    Print method call with arguments for -verbose:call.
@@ -1423,6 +1429,10 @@ void builtin_verbosecall_enter(s8 a0, s8 a1,
        s4          i;
        s4          pos;
 
+#if defined(ENABLE_DEBUG_FILTER)
+       if (! show_filters_test_verbosecall_enter(m)) return;
+#endif
+
 #if defined(ENABLE_VMLOG)
        vmlog_cacao_enter_method(m);
        return;
@@ -1577,6 +1587,7 @@ void builtin_verbosecall_enter(s8 a0, s8 a1,
        dump_release(dumpsize);
 
        methodindent++;
+
 }
 #endif
 #endif /* !defined(NDEBUG) */
@@ -1599,6 +1610,10 @@ void builtin_verbosecall_exit(s8 l, double d, float f, methodinfo *m)
        s4          pos;
        imm_union   val;
 
+#if defined(ENABLE_DEBUG_FILTER)
+       if (! show_filters_test_verbosecall_exit(m)) return;
+#endif
+
 #if defined(ENABLE_VMLOG)
        vmlog_cacao_leave_method(m);
        return;
@@ -1680,6 +1695,7 @@ void builtin_verbosecall_exit(s8 l, double d, float f, methodinfo *m)
        /* release memory */
 
        dump_release(dumpsize);
+
 }
 #endif /* !defined(NDEBUG) */
 
index 6719b63e8f2e73bc40b6a6fa1dcd1a4dbfd27a9e..0f5c62253839fe13b3c21a30d622ceb498d6a6b4 100644 (file)
@@ -39,7 +39,7 @@
    memory. All functions writing values into the data area return the offset
    relative the begin of the code area (start of procedure).   
 
-   $Id: codegen-common.c 7939 2007-05-23 09:40:05Z tbfg $
+   $Id: codegen-common.c 7966 2007-05-25 12:41:03Z pm $
 
 */
 
 #include <vmlog_cacao.h>
 #endif
 
+#include "show.h"
 
 /* in this tree we store all method addresses *********************************/
 
@@ -141,7 +142,9 @@ void codegen_init(void)
 
                avl_insert(methodtree, mte);
 #endif /* defined(ENABLE_JIT) */
+
        }
+
 }
 
 
@@ -546,7 +549,16 @@ void codegen_add_patch_ref(codegendata *cd, functionptr patcher, voidptr ref,
        if (opt_shownops)
                PATCHER_NOPS;
 
+       /* If the codegen provides a PACHER_LONGBRANCHES_NOPS macro, honour it. */
+
+#if defined(PATCHER_LONGBRANCHES_NOPS)
+       if (CODEGENDATA_HAS_FLAG_LONGBRANCHES(cd)) {
+               PATCHER_LONGBRANCHES_NOPS;
+       }
+#endif
+
 #if defined(ENABLE_JIT) && (defined(__I386__) || defined(__MIPS__) || defined(__X86_64__) || defined(__M68K__))
+
        /* On some architectures the patcher stub call instruction might
           be longer than the actual instruction generated.  On this
           architectures we store the last patcher call position and after
@@ -1283,16 +1295,21 @@ codeinfo *codegen_generate_stub_native(methodinfo *m, functionptr f)
        /* disassemble native stub */
 
        if (opt_shownativestub) {
+#if defined(ENABLE_DEBUG_FILTER)
+               if (m->filtermatches & SHOW_FILTER_FLAG_SHOW_METHOD)
+#endif
+               {
 #if defined(ENABLE_DISASSEMBLER)
-               codegen_disassemble_nativestub(m,
-                                                                          (u1 *) (ptrint) code->entrypoint,
-                                                                          (u1 *) (ptrint) code->entrypoint + (code->mcodelength - jd->cd->dseglen));
+                       codegen_disassemble_nativestub(m,
+                                                                                  (u1 *) (ptrint) code->entrypoint,
+                                                                                  (u1 *) (ptrint) code->entrypoint + (code->mcodelength - jd->cd->dseglen));
 #endif
 
-               /* show data segment */
+                       /* show data segment */
 
-               if (opt_showddatasegment)
-                       dseg_display(jd);
+                       if (opt_showddatasegment)
+                               dseg_display(jd);
+               }
        }
 #endif /* !defined(NDEBUG) */
 
@@ -1552,7 +1569,6 @@ s4 codegen_reg_of_dst(jitdata *jd, instruction *iptr, s4 tempregnum)
        return codegen_reg_of_var(iptr->opc, VAROP(iptr->dst), tempregnum);
 }
 
-
 /* codegen_emit_phi_moves ****************************************************
 
    Emits phi moves at the end of the basicblock.
index 9db6ce98d5cbf046712b60f85a7aa68ee7b94e07..9061bd8c779b0111e4d3c8e854193c3aa8908c16 100644 (file)
@@ -22,7 +22,7 @@
    Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
    02110-1301, USA.
 
-   $Id: jit.c 7949 2007-05-23 17:46:27Z twisti $
+   $Id: jit.c 7966 2007-05-25 12:41:03Z pm $
 
 */
 
@@ -1283,6 +1283,10 @@ static u1 *jit_compile_intern(jitdata *jd)
 
        DEBUG_JIT_COMPILEVERBOSE("Compiling: ");
 
+#if defined(ENABLE_DEBUG_FILTER)
+       show_filters_apply(jd->m);
+#endif
+
        /* handle native methods and create a native stub */
 
        if (m->flags & ACC_NATIVE) {
@@ -1509,20 +1513,25 @@ static u1 *jit_compile_intern(jitdata *jd)
        DEBUG_JIT_COMPILEVERBOSE("Generating code done: ");
 
 #if !defined(NDEBUG)
-       /* intermediate and assembly code listings */
+#if defined(ENABLE_DEBUG_FILTER)
+       if (jd->m->filtermatches & SHOW_FILTER_FLAG_SHOW_METHOD)
+#endif
+       {
+               /* intermediate and assembly code listings */
                
-       if (JITDATA_HAS_FLAG_SHOWINTERMEDIATE(jd)) {
-               show_method(jd, SHOW_CODE);
-       }
-       else if (JITDATA_HAS_FLAG_SHOWDISASSEMBLE(jd)) {
+               if (JITDATA_HAS_FLAG_SHOWINTERMEDIATE(jd)) {
+                       show_method(jd, SHOW_CODE);
+               }
+               else if (JITDATA_HAS_FLAG_SHOWDISASSEMBLE(jd)) {
 # if defined(ENABLE_DISASSEMBLER)
-               DISASSEMBLE(code->entrypoint,
-                                       code->entrypoint + (code->mcodelength - cd->dseglen));
+                       DISASSEMBLE(code->entrypoint,
+                                               code->entrypoint + (code->mcodelength - cd->dseglen));
 # endif
-       }
+               }
 
-       if (opt_showddatasegment)
-               dseg_display(jd);
+               if (opt_showddatasegment)
+                       dseg_display(jd);
+       }
 #endif
 
        DEBUG_JIT_COMPILEVERBOSE("Compiling done: ");
index bf0b938813b8e60723e0c45f3aff4ffab4ecda81..cef1c16333023338cb6fdc6206cf5aeffc634281 100644 (file)
@@ -22,7 +22,7 @@
    Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
    02110-1301, USA.
 
-   $Id: codegen.c 7848 2007-05-01 21:40:26Z pm $
+   $Id: codegen.c 7966 2007-05-25 12:41:03Z pm $
 
 */
 
@@ -1902,7 +1902,7 @@ bool codegen_emit(jitdata *jd)
                                M_ILD(d, REG_ITMP1, 0);
                                break;
                        case TYPE_LNG:
-                               d = codegen_reg_of_dst(jd, iptr, REG_ITMP12_PACKED);
+                               d = codegen_reg_of_dst(jd, iptr, REG_ITMP23_PACKED);
                                M_LLD(d, REG_ITMP1, 0);
                                break;
                        case TYPE_ADR:
@@ -1991,7 +1991,7 @@ bool codegen_emit(jitdata *jd)
                                M_ILD(d, s1, disp);
                                break;
                        case TYPE_LNG:
-                               d = codegen_reg_of_dst(jd, iptr, REG_ITMP12_PACKED);
+                               d = codegen_reg_of_dst(jd, iptr, REG_ITMP23_PACKED);
                                if (GET_HIGH_REG(d) == s1) {
                                        M_ILD(GET_LOW_REG(d), s1, disp + 4);
                                        M_ILD(GET_HIGH_REG(d), s1, disp);
@@ -2018,6 +2018,8 @@ bool codegen_emit(jitdata *jd)
                        break;
 
                case ICMD_PUTFIELD:   /* ..., objectref, value  ==> ...               */
+                       {
+                       u1 *ref;
 
                        s1 = emit_load_s1_notzero(jd, iptr, REG_ITMP1);
                        emit_nullpointer_check(cd, iptr, s1);
@@ -2033,36 +2035,53 @@ bool codegen_emit(jitdata *jd)
                                disp      = fi->offset;
                        }
 
+                       /* We can't add a patcher ref behind this load,
+                        * because the patcher would destroy REG_ITMP3.
+                        *
+                        * We pass in the disp parameter, how many bytes
+                        * to skip to the to the actual store.
+                        *
+                        * XXX this relies on codegen_add_patch_ref internals
+                        */
+
+                       if (INSTRUCTION_IS_UNRESOLVED(iptr)) {
+                               codegen_addpatchref(cd, PATCHER_get_putfield, uf, 0);
+                               ref = cd->mcodeptr;
+                       }
+
+
                        if (IS_INT_LNG_TYPE(fieldtype)) {
                                if (IS_2_WORD_TYPE(fieldtype))
                                        s2 = emit_load_s2(jd, iptr, REG_ITMP23_PACKED);
                                else
                                        s2 = emit_load_s2(jd, iptr, REG_ITMP2);
-                       }
-                       else
+                       } else {
                                s2 = emit_load_s2(jd, iptr, REG_FTMP2);
+                       }
 
-                       if (INSTRUCTION_IS_UNRESOLVED(iptr))
-                               codegen_addpatchref(cd, PATCHER_get_putfield, uf, 0);
+                       if (INSTRUCTION_IS_UNRESOLVED(iptr)) {
+                               cd->patchrefs->disp = (cd->mcodeptr - ref);
+                       }
 
                        switch (fieldtype) {
-                       case TYPE_INT:
-                               M_IST(s2, s1, disp);
-                               break;
-                       case TYPE_LNG:
-                               /* TODO really order */
-                               M_IST(GET_LOW_REG(s2), s1, disp + 4);      /* keep this order */
-                               M_IST(GET_HIGH_REG(s2), s1, disp);         /* keep this order */
-                               break;
-                       case TYPE_ADR:
-                               M_AST(s2, s1, disp);
-                               break;
-                       case TYPE_FLT:
-                               M_FST(s2, s1, disp);
-                               break;
-                       case TYPE_DBL:
-                               M_DST(s2, s1, disp);
-                               break;
+                               case TYPE_INT:
+                                       M_IST(s2, s1, disp);
+                                       break;
+                               case TYPE_LNG:
+                                       M_IST(GET_LOW_REG(s2), s1, disp + 4);      /* keep this order */
+                                       M_IST(GET_HIGH_REG(s2), s1, disp);         /* keep this order */
+                                       break;
+                               case TYPE_ADR:
+                                       M_AST(s2, s1, disp);
+                                       break;
+                               case TYPE_FLT:
+                                       M_FST(s2, s1, disp);
+                                       break;
+                               case TYPE_DBL:
+                                       M_DST(s2, s1, disp);
+                                       break;
+                       }
+
                        }
                        break;
 
@@ -2826,9 +2845,9 @@ gen_method:
                                        supervftbl = super->vftbl;
                                }
 
-#if defined(ENABLE_THREADS)
-                               codegen_threadcritrestart(cd, cd->mcodeptr - cd->mcodebase);
-#endif
+                               if ((super == NULL) || !(super->flags & ACC_INTERFACE))
+                                       CODEGEN_CRITICAL_SECTION_NEW;
+
                                s1 = emit_load_s1_notzero(jd, iptr, REG_ITMP1);
 
                                /* if class is not resolved, check which code to call */
@@ -2902,17 +2921,17 @@ gen_method:
 
                                        M_ALD(REG_ITMP2, s1, OFFSET(java_objectheader, vftbl));
                                        M_ALD(REG_ITMP3, REG_PV, disp);
-#if defined(ENABLE_THREADS)
-                                       codegen_threadcritstart(cd, cd->mcodeptr - cd->mcodebase);
-#endif
+
+                                       CODEGEN_CRITICAL_SECTION_START;
+
                                        M_ILD(REG_ITMP2, REG_ITMP2, OFFSET(vftbl_t, baseval));
                                        M_ILD(REG_ITMP3, REG_ITMP3, OFFSET(vftbl_t, baseval));
                                        M_ISUB(REG_ITMP3, REG_ITMP2);
                                        M_ALD(REG_ITMP3, REG_PV, disp);
                                        M_ILD(REG_ITMP3, REG_ITMP3, OFFSET(vftbl_t, diffval));
-#if defined(ENABLE_THREADS)
-                                       codegen_threadcritstop(cd, cd->mcodeptr - cd->mcodebase);
-#endif
+
+                                       CODEGEN_CRITICAL_SECTION_END;
+                                       
                                        M_CMPU(REG_ITMP2, REG_ITMP3); /* Unsigned compare */
                                        /* M_CMPULE(REG_ITMP2, REG_ITMP3, REG_ITMP3); itmp3 = (itmp2 <= itmp3) */
                                        /* M_BEQZ(REG_ITMP3, 0); branch if (! itmp) -> branch if > */
@@ -3014,9 +3033,9 @@ gen_method:
 #                      define LABEL_EXIT_INTERFACE_DONE BRANCH_LABEL_5
 #                      define LABEL_EXIT_CLASS_NULL BRANCH_LABEL_6
 
-#if defined(ENABLE_THREADS)
-                       codegen_threadcritrestart(cd, cd->mcodeptr - cd->mcodebase);
-#endif
+                       if ((super == NULL) || !(super->flags & ACC_INTERFACE))
+                               CODEGEN_CRITICAL_SECTION_NEW;
+
                        s1 = emit_load_s1_notzero(jd, iptr, REG_ITMP1);
                        d = codegen_reg_of_dst(jd, iptr, REG_ITMP2);
                        if (s1 == d) {
@@ -3111,15 +3130,15 @@ gen_method:
 
                                M_ALD(REG_ITMP1, s1, OFFSET(java_objectheader, vftbl));
                                M_ALD(REG_ITMP2, REG_PV, disp);
-#if defined(ENABLE_THREADS)
-                               codegen_threadcritstart(cd, cd->mcodeptr - cd->mcodebase);
-#endif
+
+                               CODEGEN_CRITICAL_SECTION_START;
+
                                M_ILD(REG_ITMP1, REG_ITMP1, OFFSET(vftbl_t, baseval));
                                M_ILD(REG_ITMP3, REG_ITMP2, OFFSET(vftbl_t, baseval));
                                M_ILD(REG_ITMP2, REG_ITMP2, OFFSET(vftbl_t, diffval));
-#if defined(ENABLE_THREADS)
-                               codegen_threadcritstop(cd, cd->mcodeptr - cd->mcodebase);
-#endif
+
+                               CODEGEN_CRITICAL_SECTION_END;
+
                                M_ISUB(REG_ITMP3, REG_ITMP1); /* itmp1 :=  itmp1 (sub.baseval) - itmp3 (super.baseval) */
 
                                M_CMPU(REG_ITMP1, REG_ITMP2); /* d := (uint)REG_ITMP1 <= (uint)REG_ITMP2 */
index 5d01e252eb97a281bc0ede0a10f0b610c239fbfb..832da7879cb622ed944466d34b09f30dc6ebf444 100644 (file)
@@ -22,7 +22,7 @@
    Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
    02110-1301, USA.
 
-   $Id: codegen.h 7848 2007-05-01 21:40:26Z pm $
+   $Id: codegen.h 7966 2007-05-25 12:41:03Z pm $
 
 */
 
 
 #define PATCHER_NOPS \
     do { \
-        M_NOP; \
-               M_NOP; \
-               M_NOP; \
+               /* do not generate additonal nops for long patcher branches */ \
+               if (! CODEGENDATA_HAS_FLAG_LONGBRANCHES(cd)) { \
+               M_NOP; \
+                       M_NOP; \
+                       M_NOP; \
+               } \
     } while (0)
 
+#define PATCHER_LONGBRANCHES_NOPS \
+       do { \
+               M_BR(SZ_BRC + (10 * 2)); \
+               M_NOP2; M_NOP2; M_NOP2; M_NOP2; M_NOP2; M_NOP2; M_NOP2; M_NOP2; /* ild */ \
+               M_NOP2; /* aadd */ \
+               M_NOP2; /* jmp */ \
+       } while (0)
+
 #define PATCHER_NOPS_SKIP   12 
+#define PATCHER_LONGBRANCHES_NOPS_SKIP 24
 
 /* branch defines ************************************************************/
 
-#define BRANCH_NOPS M_NOP /* Size of at least M_BRC */
+#define BRANCH_NOPS \
+       do { \
+               if (CODEGENDATA_HAS_FLAG_LONGBRANCHES(cd)) { \
+                       M_NOP2; M_NOP2; /* brc */ \
+                       M_NOP2; M_NOP2; M_NOP2; M_NOP2; M_NOP2; M_NOP2; M_NOP2; M_NOP2; /* ild */ \
+                       M_NOP2; /* ar, bcr */ \
+               } else { \
+                       M_NOP; /* brc */ \
+               } \
+       } while (0) 
 
 /* stub defines **************************************************************/
 
        do { \
                if (N_VALID_DISP(d)) { \
                        N_L(r, d, RN, b); \
-               } else if (r == R0) { \
+               } else if ((r == R0) && N_VALID_IMM(d)) { \
                        N_LR(R0, R1); \
                        N_LHI(R1, d); \
                        N_L(R1, 0, R1, b); \
                        N_XR(R1, R0); \
                        N_XR(R0, R1); \
                        N_XR(R1, R0); \
-               } else { \
+               } else if ((r != R0) && N_VALID_IMM(d)) { \
                        N_LHI(r, d); N_L(r, 0, r, b); \
+               } else { \
+                       N_BRAS(r, SZ_BRAS + SZ_LONG); \
+                       N_LONG(d); \
+                       N_L(r, 0, RN, r); \
+                       N_L(r, 0, r, b); \
                } \
        } while (0)
 
 #define M_ALD(r, b, d) M_ILD(r, b, d)
 
-#define M_LDA(r, b, d) _IFNEG( \
-       d, \
-       N_LHI(r, d); N_LA(r, 0, r, b), \
-       N_LA(r, d, RN, b) \
-)
+#define M_LDA(r, b, d) \
+       do { \
+               if (N_VALID_DISP(d)) { \
+                       N_LA(r, d, RN, b); \
+               } else if (N_VALID_IMM(d)) { \
+                       N_LHI(r, d); \
+                       N_LA(r, 0, r, b); \
+               } else { \
+                       N_BRAS(r, SZ_BRAS + SZ_LONG); \
+                       N_LONG(d); \
+                       N_L(r, 0, RN, r); \
+                       N_LA(r, 0, r, b); \
+               } \
+       } while (0)
 
 #define M_FLD(r, b, d) N_LE(r, d, RN, b)
 
 #define M_BR(disp) N_BRC(DD_ANY, disp)
 #define M_JMP(rs, rd) _IF(rs == RN, N_BCR(DD_ANY, rd), N_BASR(rs, rd))
 #define M_NOP N_BC(0, 0, RN, RN)
+#define M_NOP2 N_BCR(0, RN)
 #define M_JSR(reg_ret, reg_addr) N_BASR(reg_ret, reg_addr)
 #define M_ICMP(a, b) N_CR(a, b)
 #define M_ICMPU(a, b) N_CLR(a, b)
 #define M_CVTFI(src, dst) N_CFEBR(dst, 5, src)
 #define M_CVTDI(src, dst) N_CFDBR(dst, 5, src)
 #define M_IADD(a, dest) N_AR(dest, a)
+#define M_AADD(a, dest) N_AR(dest, a)
 #define M_ISUB(a, dest) N_SR(dest, a)
 #define M_ASUB(a, dest) N_SR(dest, a)
 #define M_IAND(a, dest) N_NR(dest, a)
 
 #define M_AST_IMM32(a,b,c) _DEPR( M_AST_IMM32(a,b,c) )
 
-#define M_AADD(a,b) _DEPR( M_AADD(a,b) )
-
 #define M_LADD_IMM32(a,b) _DEPR( M_LADD_IMM32(a,b) )
 #define M_AADD_IMM32(a,b) _DEPR( M_AADD_IMM32(a,b) )
 #define M_LSUB_IMM32(a,b) _DEPR( M_LSUB_IMM32(a,b) )
index ff0b786a875a2ea52eb293cba7a7e8540685a3b7..4ea81f56c3a85e88a02b75480093563d627664fd 100644 (file)
@@ -22,7 +22,7 @@
    Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
    02110-1301, USA.
 
-   $Id: emit.c 7848 2007-05-01 21:40:26Z pm $
+   $Id: emit.c 7966 2007-05-25 12:41:03Z pm $
 
 */
 
@@ -227,6 +227,7 @@ __PORTED__ void emit_patcher_stubs(jitdata *jd)
        u1          *tmpmcodeptr;
        s4           targetdisp;
        s4           disp;
+       u1          *ref;
 
        /* get required compiler data */
 
@@ -255,7 +256,46 @@ __PORTED__ void emit_patcher_stubs(jitdata *jd)
                cd->mcodeptr  = tmpmcodeptr;    /* set mcodeptr to patch position     */
 
                disp = (savedmcodeptr) - (tmpmcodeptr);
-               M_BSR(REG_ITMP3, disp);
+
+               if (! N_VALID_BRANCH(disp)) {
+                       /* Displacement overflow */
+
+                       /* If LONGBRANCHES is not set, the flag and the error flag */
+                       
+                       if (! CODEGENDATA_HAS_FLAG_LONGBRANCHES(cd)) {
+                               cd->flags |= (CODEGENDATA_FLAG_ERROR |
+                                       CODEGENDATA_FLAG_LONGBRANCHES);
+                       }
+
+                       /* If error flag is set, do nothing. The method has to be recompiled. */
+
+                       if (CODEGENDATA_HAS_FLAG_LONGBRANCHES(cd) && CODEGENDATA_HAS_FLAG_ERROR(cd)) {
+                               return;
+                       }
+               }
+
+               if (CODEGENDATA_HAS_FLAG_LONGBRANCHES(cd)) {    
+
+                       /* Generating long branches */
+
+                       disp = dseg_add_s4(cd, savedmcodeptr - cd->mcodebase);
+       
+                       M_ILD(REG_ITMP3, REG_PV, disp);
+                       M_AADD(REG_PV, REG_ITMP3);
+
+                       /* Do the branch at the end of NOP sequence.
+                        * This way the patch position is at a *fixed* offset 
+                        * (PATCHER_LONGBRANCHES_NOPS_SKIP) of the return address.
+                        */
+
+                       cd->mcodeptr = tmpmcodeptr + PATCHER_LONGBRANCHES_NOPS_SKIP - SZ_BASR;
+                       M_JMP(REG_ITMP3, REG_ITMP3);
+               } else {
+
+                       /* Generating short branches */
+
+                       M_BSR(REG_ITMP3, disp);
+               }
 
                cd->mcodeptr = savedmcodeptr;   /* restore the current mcodeptr       */
 
@@ -317,7 +357,7 @@ __PORTED__ void emit_patcher_stubs(jitdata *jd)
                        disp = ((cd->mcodebase) + targetdisp) -
                                (( cd->mcodeptr) );
 
-                       M_BR(disp);
+                       emit_branch(cd, disp, BRANCH_UNCONDITIONAL, RN, 0);
                }
        }
 }
@@ -840,31 +880,99 @@ void emit_copy_dst(jitdata *jd, instruction *iptr, s4 dtmpreg) {
 void emit_branch(codegendata *cd, s4 disp, s4 condition, s4 reg, u4 opt) {
 
        s4 branchdisp = disp;
+       s4 branchmpc;
+       u1 *ref;
+
+       if (N_VALID_BRANCH(branchdisp)) {
+
+               /* valid displacement */
 
-       switch (condition) {
-               case BRANCH_EQ:
-                       M_BEQ(branchdisp);
-                       break;
-               case BRANCH_NE:
-                       M_BNE(branchdisp);
-                       break;
-               case BRANCH_LT:
-                       M_BLT(branchdisp);
-                       break;
-               case BRANCH_GE:
-                       M_BGE(branchdisp);
-                       break;
-               case BRANCH_GT:
-                       M_BGT(branchdisp);
-                       break;
-               case BRANCH_LE:
-                       M_BLE(branchdisp);
-                       break;
-               case BRANCH_UNCONDITIONAL:
-                       M_BR(branchdisp);
-                       break;
-               default:
-                       vm_abort("emit_branch: unknown condition %d", condition);
+               switch (condition) {
+                       case BRANCH_EQ:
+                               M_BEQ(branchdisp);
+                               break;
+                       case BRANCH_NE:
+                               M_BNE(branchdisp);
+                               break;
+                       case BRANCH_LT:
+                               M_BLT(branchdisp);
+                               break;
+                       case BRANCH_GE:
+                               M_BGE(branchdisp);
+                               break;
+                       case BRANCH_GT:
+                               M_BGT(branchdisp);
+                               break;
+                       case BRANCH_LE:
+                               M_BLE(branchdisp);
+                               break;
+                       case BRANCH_UNCONDITIONAL:
+                               M_BR(branchdisp);
+                               break;
+                       default:
+                               vm_abort("emit_branch: unknown condition %d", condition);
+               }
+       } else {
+
+               /* If LONGBRANCHES is not set, the flag and the error flag */
+
+               if (!CODEGENDATA_HAS_FLAG_LONGBRANCHES(cd)) {
+                       cd->flags |= (CODEGENDATA_FLAG_ERROR |
+                               CODEGENDATA_FLAG_LONGBRANCHES);
+               }
+
+               /* If error flag is set, do nothing. The method has to be recompiled. */
+
+               if (CODEGENDATA_HAS_FLAG_LONGBRANCHES(cd) && CODEGENDATA_HAS_FLAG_ERROR(cd)) {
+                       return;
+               }
+
+               /* Patch the displacement to branch over the actual branch manually
+                * to not get yet more nops.
+                */
+
+               branchmpc = cd->mcodeptr - cd->mcodebase;
+               ref = cd->mcodeptr;
+
+               switch (condition) {
+                       case BRANCH_EQ:
+                               M_BNE(0);
+                               break;
+                       case BRANCH_NE:
+                               M_BEQ(0);
+                               break;
+                       case BRANCH_LT:
+                               M_BGE(0);
+                               break;
+                       case BRANCH_GE:
+                               M_BLT(0);
+                               break;
+                       case BRANCH_GT:
+                               M_BLE(0);
+                               break;
+                       case BRANCH_LE:
+                               M_BGT(0);
+                               break;
+                       case BRANCH_UNCONDITIONAL:
+                               /* fall through, no displacement to patch */
+                               ref = NULL;
+                               break;
+                       default:
+                               vm_abort("emit_branch: unknown condition %d", condition);
+               }
+
+               /* The actual long branch */
+
+               disp = dseg_add_s4(cd, branchmpc + disp);
+               M_ILD(REG_ITMP3, REG_PV, disp);
+               M_AADD(REG_PV, REG_ITMP3);
+               M_JMP(RN, REG_ITMP3);
+
+               /* Patch back the displacement */
+
+               if (ref != NULL) {
+                       *(u4 *)ref |= (u4)((cd->mcodeptr - ref) / 2);
+               }
        }
 }
 
index 6129ff20a1db309d808130c084cb6b6cd47a9d6b..fd1485583b5d9df4dd8c14ca17af783a67d70297 100644 (file)
@@ -28,7 +28,7 @@
 
    Changes: Edwin Steiner
 
-   $Id: md.c 7848 2007-05-01 21:40:26Z pm $
+   $Id: md.c 7966 2007-05-25 12:41:03Z pm $
 
 */
 
@@ -77,14 +77,6 @@ void md_dump_context(u1 *pc, mcontext_t *mc);
 
 void md_init(void)
 {
-       struct sigaction act;
-       
-       act.sa_sigaction = md_signal_handler_sigill;
-       act.sa_flags     = SA_NODEFER | SA_SIGINFO;
-
-       if (sigaction(SIGILL, &act, NULL) == -1)        {
-               vm_abort("%s: error registering SIGILL signal handler.", __FUNCTION__);
-       }
 }
 
 /* md_dump_context ************************************************************
@@ -345,17 +337,22 @@ void md_signal_handler_sigusr2(int sig, siginfo_t *siginfo, void *_p)
 
 
 #if defined(ENABLE_THREADS)
-void thread_restartcriticalsection(ucontext_t *_uc)
+void md_critical_section_restart(ucontext_t *_uc)
 {
        mcontext_t *_mc;
-       void       *pc;
+       u1         *pc;
+       void       *npc;
 
        _mc = &_uc->uc_mcontext;
 
-       pc = critical_find_restart_point((void *) _mc->psw.addr);
+       pc = (u1 *)_mc->psw.addr;
 
-       if (pc != NULL)
-               _mc->psw.addr = (ptrint) pc;
+       npc = critical_find_restart_point(pc);
+
+       if (npc != NULL) {
+               log_println("%s: pc=%p, npc=%p", __FUNCTION__, pc, npc);
+               _mc->psw.addr = (ptrint) npc;
+       }
 }
 #endif
 
index 7b06b708e8a0cd3112b899402cf21adeed068fa6..47ad89989591627746ddac7df946536879dc448e 100644 (file)
 
    Changes:
 
-   $Id: patcher.c 7839 2007-04-29 22:46:56Z pm $
+   $Id: patcher.c 7966 2007-05-25 12:41:03Z pm $
+
+     GENERATED      PATCHER BRANCH           AFTER PATCH
+
+   Short patcher call:
+
+     foo            bras %r14, OFFSET        foo
+     bar     ===>   bar                ===>  bar
+     baz            baz                      baz
+
+   Short patcher call with nops:
+                                             PATCHER_NOPS_SKIP <-+
+                                                                 |
+     nop            bras %r14, OFFSET        nop               --+
+     nop     ===>   nop                ===>  nop                 |
+     nop            nop                      nop               --+
+     foo            foo                      foo
+
+   Long pacher call:
+                                PATCHER_LONGBRANCHES_NOPS_SKIP <-+
+                                                                 |
+     br exit:       ild itmp3, disp(pv)      br exit            -+
+        nop            aadd pv, itmp3           aadd pv, itmp3      | 
+        nop     ===>   nop                ===>  nop                 |
+        .....          ....                     ....                |
+        nop            basr itmp3, itmp3        basr itmp3, itmp3  -+
+   exit:                                   exit:
 
 */
 
@@ -56,6 +82,9 @@
 #define OOPS() assert(0);
 #define __PORTED__
 
+/* A normal patcher branch done using BRAS */
+#define PATCHER_IS_SHORTBRANCH(brcode) ((brcode & 0xFF0F0000) == 0xA7050000)
+
 /* patcher_wrapper *************************************************************
 
    Wrapper for all patchers.  It also creates the stackframe info
@@ -69,7 +98,6 @@
 
 java_objectheader *patcher_wrapper(u1 *sp, u1 *pv, u1 *ra)
 {
-#if 1
        stackframeinfo     sfi;
        u1                *xpc;
        java_objectheader *o;
@@ -87,7 +115,15 @@ java_objectheader *patcher_wrapper(u1 *sp, u1 *pv, u1 *ra)
        o   = (java_objectheader *) *((ptrint *) (sp + 4 * 4));
        f   = (functionptr)         *((ptrint *) (sp + 0 * 4));
        
-       xpc = xpc - 4; /* the patch position is 4 bytes before the RA */
+       /* For a normal branch, the patch position is SZ_BRAS bytes before the RA.
+        * For long branches it is PATCHER_LONGBRANCHES_NOPS_SKIP before the RA.
+        */
+
+       if (PATCHER_IS_SHORTBRANCH(*(u4 *)(xpc - SZ_BRAS))) {
+               xpc = xpc - SZ_BRAS;
+       } else {
+               xpc = xpc - PATCHER_LONGBRANCHES_NOPS_SKIP;
+       }
 
        *((ptrint *) (sp + 5 * 4)) = (ptrint) xpc;
 
@@ -132,69 +168,6 @@ java_objectheader *patcher_wrapper(u1 *sp, u1 *pv, u1 *ra)
        PATCHER_MARK_PATCHED_MONITOREXIT;
 
        return NULL;
-#else
-
-       stackframeinfo     sfi;
-       u1                *xpc;
-       java_objectheader *o;
-       u4                 mcode;
-       functionptr        f;
-       bool               result;
-       java_objectheader *e;
-
-       /* define the patcher function */
-
-       bool (*patcher_function)(u1 *);
-
-       assert(pv != NULL);
-
-       /* get stuff from the stack */
-
-       xpc = (u1 *)                *((ptrint *) (sp + 5 * 4));
-       o   = (java_objectheader *) *((ptrint *) (sp + 4 * 4));
-       f   = (functionptr)         *((ptrint *) (sp + 0 * 4));
-
-       /* Correct RA is calculated in codegen.c and stored in the patcher
-          stub stack.  There's no need to adjust xpc. */
-
-       /* store PV into the patcher function position */
-
-       *((ptrint *) (sp + 0 * 4)) = (ptrint) pv;
-
-       /* cast the passed function to a patcher function */
-
-       patcher_function = (bool (*)(u1 *)) (ptrint) f;
-
-       /* enter a monitor on the patching position */
-
-       PATCHER_MONITORENTER;
-
-       /* create the stackframeinfo */
-
-       stacktrace_create_extern_stackframeinfo(&sfi, pv, sp + 8 * 4, ra, xpc);
-
-       /* call the proper patcher function */
-
-       result = (patcher_function)(sp);
-
-       /* remove the stackframeinfo */
-
-       stacktrace_remove_stackframeinfo(&sfi);
-
-       /* check for return value and exit accordingly */
-
-       if (result == false) {
-               e = exceptions_get_and_clear_exception();
-
-               PATCHER_MONITOREXIT;
-
-               return e;
-       }
-
-       PATCHER_MARK_PATCHED_MONITOREXIT;
-
-       return NULL;
-#endif
 }
 
 
@@ -251,16 +224,18 @@ bool patcher_get_putstatic(u1 *sp)
 bool patcher_get_putfield(u1 *sp)
 {
        u1               *ra;
-       u4                mcode;
+       u4                mcode, brcode;
        unresolved_field *uf;
        fieldinfo        *fi;
        u1                byte;
+       s4                disp;
 
        /* get stuff from the stack */
 
        ra    = (u1 *)               *((ptrint *) (sp + 5 * 4));
        mcode =                      *((u4 *)     (sp + 3 * 4));
        uf    = (unresolved_field *) *((ptrint *) (sp + 2 * 4));
+       disp  =                      *((s4 *)     (sp + 1 * 4));
 
        /* get the fieldinfo */
 
@@ -269,13 +244,20 @@ bool patcher_get_putfield(u1 *sp)
 
        /* patch back original code */
 
+       brcode = *((u4 *) ra);
        *((u4 *) ra) = mcode;
 
        /* If NOPs are generated, skip them */
 
-       if (opt_shownops)
+       if (! PATCHER_IS_SHORTBRANCH(brcode))
+               ra += PATCHER_LONGBRANCHES_NOPS_SKIP;
+       else if (opt_shownops)
                ra += PATCHER_NOPS_SKIP;
 
+       /* If there is an operand load before, skip the load size passed in disp (see ICMD_PUTFIELD) */
+
+       ra += disp;
+
        /* patch correct offset */
 
        if (fi->type == TYPE_LNG) {
@@ -548,7 +530,7 @@ __PORTED__ bool patcher_invokestatic_special(u1 *sp)
 bool patcher_invokevirtual(u1 *sp)
 {
        u1                *ra;
-       u4                 mcode;
+       u4                 mcode, brcode;
        unresolved_method *um;
        methodinfo        *m;
        s4                off;
@@ -566,11 +548,14 @@ bool patcher_invokevirtual(u1 *sp)
 
        /* patch back original code */
 
+       brcode = *((u4 *) ra);
        *((u4 *) ra) = mcode;
 
        /* If NOPs are generated, skip them */
 
-       if (opt_shownops)
+       if (! PATCHER_IS_SHORTBRANCH(brcode))
+               ra += PATCHER_LONGBRANCHES_NOPS_SKIP;
+       else if (opt_shownops)
                ra += PATCHER_NOPS_SKIP;
 
        /* patch vftbl index */
@@ -596,7 +581,7 @@ bool patcher_invokevirtual(u1 *sp)
 bool patcher_invokeinterface(u1 *sp)
 {
        u1                *ra;
-       u4                 mcode;
+       u4                 mcode, brcode;
        unresolved_method *um;
        methodinfo        *m;
        s4                 idx, off;
@@ -614,11 +599,14 @@ bool patcher_invokeinterface(u1 *sp)
 
        /* patch back original code */
 
+       brcode = *((u4 *) ra);
        *((u4 *) ra) = mcode;
 
        /* If NOPs are generated, skip them */
 
-       if (opt_shownops)
+       if (! PATCHER_IS_SHORTBRANCH(brcode))
+               ra += PATCHER_LONGBRANCHES_NOPS_SKIP;
+       else if (opt_shownops)
                ra += PATCHER_NOPS_SKIP;
 
        /* get interfacetable index */
@@ -775,7 +763,7 @@ bool patcher_resolve_classref_to_vftbl(u1 *sp)
 bool patcher_checkcast_instanceof_interface(u1 *sp)
 {
        u1                *ra;
-       u4                 mcode;
+       u4                 mcode, brcode;
        constant_classref *cr;
        classinfo         *c;
 
@@ -792,11 +780,14 @@ bool patcher_checkcast_instanceof_interface(u1 *sp)
 
        /* patch back original code */
 
+       brcode = *((u4 *) ra);
        *((u4 *) ra) = mcode;
 
        /* If NOPs are generated, skip them */
 
-       if (opt_shownops)
+       if (! PATCHER_IS_SHORTBRANCH(brcode))
+               ra += PATCHER_LONGBRANCHES_NOPS_SKIP;
+       else if (opt_shownops)
                ra += PATCHER_NOPS_SKIP;
 
        /* patch super class index */
index 49767ae8eae2ec1f4a79bb723bb17b622dda7f43..1f423d6f19589fee43d472b03138ccac234379bf 100644 (file)
@@ -2,6 +2,10 @@ antlr
 
        * parses one or more grammar files and generates a parser and lexical analyzer for each.
        * Tue May  1 18:49:29 CEST 2007: ===== DaCapo antlr PASSED in 37095 msec =====
+       * Wed May  9 23:58:51 CEST 2007: (ibm java) ===== DaCapo antlr PASSED in 269244 msec =====
+       * Thu May 10 00:05:50 CEST 2007: ===== DaCapo antlr PASSED in 70164 msec =====
+       * Thu May 10 08:54:54 CEST 2007: (ibm java intrp) ===== DaCapo antlr PASSED in 686373 msec =====
+
 
 bloat
 
@@ -11,6 +15,7 @@ bloat
 chart
 
        * uses JFreeChart to plot a number of complex line graphs and renders them as PDF
+       * Fri May 18 02:08:25 CEST 2007: ===== DaCapo chart PASSED in 549048 msec =====
 
 eclipse
 
@@ -34,6 +39,7 @@ jython
 luindex
 
        * Uses lucene to indexes a set of documents; the works of Shakespeare and the King James Bible
+       * Sat May 12 20:27:43 CEST 2007: ===== DaCapo luindex PASSED in 92671 msec =====
 
 lusearch
 
@@ -51,3 +57,5 @@ xalan
                LOG: [0x77dc66c0] Generating code: org.apache.xalan.processor.XSLTSchema.build()V
                32834 (0x8042) is not an signed 16 bit integer at /home/peter/cacao-dev/build-s390/../svn/src/vm/jit/s390/emit.c:258.
                => branch to patcher overflow
+
+       * HANGUP !
index 12f28753f328db6c1be1f0cfd0d7de24a7f08841..449288e4f10e398334eaff39fc945ff01e32c3d5 100644 (file)
 
 #include "vmcore/options.h"
 
+#if defined(ENABLE_DEBUG_FILTER)
+#      include <sys/types.h>
+#      include <regex.h>
+#      if defined(ENABLE_THREADS)
+#              include "threads/native/threads.h"
+#      else
+#              include "threads/none/threads.h"
+#      endif
+#endif
 
 /* global variables ***********************************************************/
 
@@ -82,6 +91,10 @@ bool show_init(void)
        LOCK_INIT_OBJECT_LOCK(show_global_lock);
 #endif
 
+#if defined(ENABLE_DEBUG_FILTER)
+       show_filters_init();
+#endif
+
        /* everything's ok */
 
        return true;
@@ -1431,6 +1444,222 @@ void show_icmd(jitdata *jd, instruction *iptr, bool deadcode, int stage)
 }
 #endif /* !defined(NDEBUG) */
 
+/* Debug output filtering */
+
+#if defined(ENABLE_DEBUG_FILTER)
+
+#if !defined(ENABLE_THREADS)
+u4 _no_threads_filterverbosecallctr[2] = { 0, 0 };
+#endif
+
+struct show_filter {
+       /* Boolean indicating if filter is enabled. */
+       u1 enabled;
+       /* Regular expression the method name is matched against */
+       regex_t regex;
+       /* Flag set on m->filtermatches if regex matches */
+       u1 flag;
+};
+
+typedef struct show_filter show_filter_t;
+
+#define SHOW_FILTERS_SIZE 3
+
+/* Array of filters applyed on a method */
+static struct show_filter show_filters[SHOW_FILTERS_SIZE];
+
+static void show_filter_init(show_filter_t *cf, const char *str, u1 flag, u1 default_flag, const char *description) {
+       int err;
+       char err_buf[128];
+
+       if (str) {
+               err = regcomp(&cf->regex, str, REG_EXTENDED | REG_NOSUB);
+               if (err != 0) {
+                       regerror(err, &cf->regex, err_buf, sizeof(err_buf));
+                       vm_abort(
+                               "Invalid value given for %s: `%s' (%s).", 
+                               description, str, err_buf
+                       );
+               }
+               cf->flag = flag;
+               cf->enabled = 1;
+       } else {
+               cf->flag = default_flag;
+               cf->enabled = 0;
+       }
+}
+
+void show_filters_init(void) {
+
+       show_filter_init(
+               show_filters + 0,
+               opt_filter_verbosecall_include,
+               SHOW_FILTER_FLAG_VERBOSECALL_INCLUDE,
+               SHOW_FILTER_FLAG_VERBOSECALL_INCLUDE,
+               "verbose call include filter"
+       );
+
+       show_filter_init(
+               show_filters + 1,
+               opt_filter_verbosecall_exclude,
+               SHOW_FILTER_FLAG_VERBOSECALL_EXCLUDE,
+               0,
+               "verbose call exclude filter"
+       );
+
+       show_filter_init(
+               show_filters + 2,
+               opt_filter_show_method,
+               SHOW_FILTER_FLAG_SHOW_METHOD,
+               SHOW_FILTER_FLAG_SHOW_METHOD,
+               "show method filter"
+       );
+}
+
+/*
+ (Pseudo)State machine:
+
+ States are INITIAL, INCLUDE1, INCLUDE2, ..., EXCLUDE1, ..., EXCLUDE2, ...
+
+                                                        Enter              Enter
+ Enter                                                  Include            Include
+ Exclude                                                  | |                | |
+  | |    Enter              Enter              Enter      | |     Enter      | |
+  | |    Include            Include            Exclude    | |     Exclude    | |
+  | v   --------->        ---------->        ---------->  | v   ---------->  | v
+INITIAL           INCLUDE1           INCLUDE2           EXCLUDE1           EXCLUDE2
+  | ^   <---------        <----------        <----------  | ^   <----------  | ^
+  | |    Exit               Exit               Exit       | |     Exit       | |
+  | |    Include            Include            Exclude    | |     Exclude    | |
+  | |                                                     | |                | |
+ Exit                                                    Exit               Exit
+ Exclude                                                 Include            Include
+
+  Verbose call scope is active if we are in a INCLUDE state.
+
+  State encoding:
+
+  INITIAL: ctr[0] == 0, ctr[1] == 0
+  INCLUDEN: ctr[1] == N, ctr[1] == 0
+  EXCLUDEN: ctr[1] == N
+*/
+
+void show_filters_apply(methodinfo *m) {
+       int i;
+       int res;
+       char *method_name;
+       s4 len;
+       s4 dumpsize;
+
+       /* compose full name of method */
+
+       len = 
+               utf_bytes(m->class->name) +
+               1 +
+               utf_bytes(m->name) +
+               utf_bytes(m->descriptor) +
+               1;
+
+       dumpsize = dump_size(); /* allocate memory */
+
+       method_name = DMNEW(char, len);
+
+       utf_cat_classname(method_name, m->class->name);
+       strcat(method_name, ".");
+       utf_cat(method_name, m->name);
+       utf_cat(method_name, m->descriptor);
+
+       /* reset all flags */
+
+       m->filtermatches = 0;
+
+       for (i = 0; i < SHOW_FILTERS_SIZE; ++i) {
+               if (show_filters[i].enabled) {
+
+                       res = regexec(&show_filters[i].regex, method_name, 0, NULL, 0);
+
+                       if (res == 0) {
+                               m->filtermatches |= show_filters[i].flag;
+                       }
+               } else {
+                       /* Default is to show all */
+                       m->filtermatches |= show_filters[i].flag;
+               }
+       }
+
+       /* release memory */
+
+       dump_release(dumpsize); 
+
+}
+
+#define STATE_IS_INITIAL() ((FILTERVERBOSECALLCTR[0] == 0) && (FILTERVERBOSECALLCTR[1] == 0))
+#define STATE_IS_INCLUDE() ((FILTERVERBOSECALLCTR[0] > 0) && (FILTERVERBOSECALLCTR[1] == 0))
+#define STATE_IS_EXCLUDE() (FILTERVERBOSECALLCTR[1] > 0)
+#define EVENT_INCLUDE() (m->filtermatches & SHOW_FILTER_FLAG_VERBOSECALL_INCLUDE)
+#define EVENT_EXCLUDE() (m->filtermatches & SHOW_FILTER_FLAG_VERBOSECALL_EXCLUDE)
+#define TRANSITION_NEXT_INCLUDE() ++FILTERVERBOSECALLCTR[0]
+#define TRANSITION_PREV_INCLUDE() --FILTERVERBOSECALLCTR[0]
+#define TRANSITION_NEXT_EXCLUDE() ++FILTERVERBOSECALLCTR[1]
+#define TRANSITION_PREV_EXCLUDE() --FILTERVERBOSECALLCTR[1]
+
+#if 0
+void dump_state() {
+       if (STATE_IS_INITIAL()) printf("<INITIAL>\n");
+       else if (STATE_IS_INCLUDE()) printf("<INCLUDE %hd>\n", FILTERVERBOSECALLCTR[0]);
+       else if (STATE_IS_EXCLUDE()) printf("<EXCLUDE %hd>\n", FILTERVERBOSECALLCTR[1]);
+}
+#endif
+
+int show_filters_test_verbosecall_enter(methodinfo *m) {
+
+       int force_show = 0;
+
+       if (STATE_IS_INITIAL()) {
+               if (EVENT_INCLUDE()) {
+                       TRANSITION_NEXT_INCLUDE();
+               }
+       } else if (STATE_IS_INCLUDE()) {
+               if (EVENT_EXCLUDE()) {
+                       TRANSITION_NEXT_EXCLUDE();
+                       /* just entered exclude, show this method */
+                       force_show = 1;
+               } else if (EVENT_INCLUDE()) {
+                       TRANSITION_NEXT_INCLUDE();
+               }
+       } else if (STATE_IS_EXCLUDE()) {
+               if (EVENT_EXCLUDE()) {
+                       TRANSITION_NEXT_EXCLUDE();
+               }
+       }
+
+       return STATE_IS_INCLUDE() || force_show;
+}
+
+int show_filters_test_verbosecall_exit(methodinfo *m) {
+
+       int force_show = 0;
+
+       if (m) {
+               if (STATE_IS_INCLUDE()) {
+                       if (EVENT_INCLUDE()) {
+                               TRANSITION_PREV_INCLUDE();
+                               /* just entered initial, show this method */
+                               if (STATE_IS_INITIAL()) force_show = 1;
+                       }
+           } else if (STATE_IS_EXCLUDE()) {
+                       if (EVENT_EXCLUDE()) {
+                               TRANSITION_PREV_EXCLUDE();
+                       }
+               }
+       }
+
+       return STATE_IS_INCLUDE() || force_show;
+}
+
+#endif
+
 
 /*
  * These are local overrides for various environment variables in Emacs.
index 79dae83cd8871429702a6f86b5704ba8dae21c6d..4690513c6a84d42bded80612c4588909c8283cdf 100644 (file)
@@ -71,6 +71,19 @@ void show_javalocals_array(jitdata *jd, s4 *vars, int n, int stage);
 void show_allocation(s4 type, s4 flags, s4 regoff);
 #endif /* !defined(NDEBUG) */
 
+/* Debug output filtering */
+
+#if defined(ENABLE_DEBUG_FILTER)
+void show_filters_init(void);
+#define SHOW_FILTER_FLAG_VERBOSECALL_INCLUDE 0x01
+#define SHOW_FILTER_FLAG_VERBOSECALL_EXCLUDE 0x02
+#define SHOW_FILTER_FLAG_SHOW_METHOD 0x04
+void show_filters_apply(methodinfo *m);
+int show_filters_test_verbosecall_enter(methodinfo *m);
+int show_filters_test_verbosecall_exit(methodinfo *m);
+#endif
+
+
 #endif /* _SHOW_H */
 
 /*
index f1f1b462b970606fc4ecfecbfb54ea29c6f4a9db..270765bf1cc11a78f91475f734b3cba464fed72c 100644 (file)
@@ -22,7 +22,7 @@
    Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
    02110-1301, USA.
 
-   $Id: signal.c 7831 2007-04-26 12:48:16Z twisti $
+   $Id: signal.c 7966 2007-05-25 12:41:03Z pm $
 
 */
 
@@ -147,7 +147,7 @@ void signal_init(void)
                sigaction(SIGFPE, &act, NULL);
 #  endif
 
-#  if defined(__ARM__)
+#  if defined(__ARM__) || defined(__S390__)
                /* XXX use better defines for that (in arch.h) */
                /* SIGILL handler */
 
index 6667d69e96d161671320c94da41441add2e7fd0d..58cae57ae021151d9bc05b2ea1751eea07d5d6e1 100644 (file)
@@ -22,7 +22,7 @@
    Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
    02110-1301, USA.
 
-   $Id: signallocal.h 7596 2007-03-28 21:05:53Z twisti $
+   $Id: signallocal.h 7966 2007-05-25 12:41:03Z pm $
 
 */
 
@@ -52,7 +52,7 @@ void md_signal_handler_sigsegv(int sig, siginfo_t *siginfo, void *_p);
 void md_signal_handler_sigfpe(int sig, siginfo_t *siginfo, void *_p);
 #endif
 
-#if defined(__ARM__)
+#if defined(__ARM__) || defined(__S390__)
 /* XXX use better defines for that (in arch.h) */
 void md_signal_handler_sigill(int sig, siginfo_t *siginfo, void *_p);
 #endif
index 1ca71528e094363832e9eda1a9eb116285384dbf..43a710cabcc72e2764ff6ef617411482c1200f25 100644 (file)
@@ -252,6 +252,12 @@ enum {
        OPT_AGENTPATH,
 #endif
 
+#if defined(ENABLE_DEBUG_FILTER)
+       OPT_FILTER_VERBOSECALL_INCLUDE,
+       OPT_FILTER_VERBOSECALL_EXCLUDE,
+       OPT_FILTER_SHOW_METHOD,
+#endif
+
        DUMMY
 };
 
@@ -392,6 +398,12 @@ opt_struct opts[] = {
        { "s",                 true,  OPT_SHOW },
        { "debug-color",      false,  OPT_DEBUGCOLOR },
 
+#if defined(ENABLE_DEBUG_FILTER)
+       { "XXfi",              true,  OPT_FILTER_VERBOSECALL_INCLUDE },
+       { "XXfx",              true,  OPT_FILTER_VERBOSECALL_EXCLUDE },
+       { "XXfm",              true,  OPT_FILTER_SHOW_METHOD },
+#endif
+
        { NULL,                false, 0 }
 };
 
@@ -555,7 +567,11 @@ static void XXusage(void)
 #if defined(ENABLE_SSA)
        puts("    -lsra                    use linear scan register allocation (with SSA)");
 #endif
-
+#if defined(ENABLE_DEBUG_FILTER)
+       puts("    -XXfi <regex>            begin of dynamic scope for verbosecall filter");
+       puts("    -XXfx <regex>            end of dynamic scope for verbosecall filter");
+       puts("    -XXfm <regex>            filter for show options");
+#endif
        /* exit with error code */
 
        exit(1);
@@ -1408,6 +1424,20 @@ bool vm_create(JavaVMInitArgs *vm_args)
                        break;
 #endif
 
+#if defined(ENABLE_DEBUG_FILTER)
+               case OPT_FILTER_VERBOSECALL_INCLUDE:
+                       opt_filter_verbosecall_include = opt_arg;
+                       break;
+
+               case OPT_FILTER_VERBOSECALL_EXCLUDE:
+                       opt_filter_verbosecall_exclude = opt_arg;
+                       break;
+
+               case OPT_FILTER_SHOW_METHOD:
+                       opt_filter_show_method = opt_arg;
+                       break;
+
+#endif
                default:
                        printf("Unknown option: %s\n",
                                   vm_args->options[opt_index].optionString);
index ea02e1a3959bea4ad4dc70f68cc90779d9aa5285..71ce13c366328e763b92fa10a99eff7a8cdb4b86 100644 (file)
@@ -22,7 +22,7 @@
    Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
    02110-1301, USA.
 
-   $Id: method.h 7575 2007-03-25 20:30:50Z twisti $
+   $Id: method.h 7966 2007-05-25 12:41:03Z pm $
 */
 
 
@@ -104,6 +104,10 @@ struct methodinfo {                 /* method structure                       */
 #if defined(ENABLE_REPLACEMENT)
        s4            hitcountdown;     /* decreased for each hit                 */
 #endif
+
+#if defined(ENABLE_DEBUG_FILTER)
+       u1            filtermatches;    /* flags indicating which filters the method matches */
+#endif
 };
 
 
index 4f31ef465bcf360293f20c1b99243b9bbe4dd920..a7087529aba72268316a12ddfbe0fa0bd0c74242 100644 (file)
@@ -22,7 +22,7 @@
    Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
    02110-1301, USA.
 
-   $Id: options.c 7894 2007-05-10 14:04:05Z twisti $
+   $Id: options.c 7966 2007-05-25 12:41:03Z pm $
 
 */
 
@@ -163,6 +163,11 @@ s4   opt_static_supers = 0x7fffffff;
 bool vm_debug = false;          /* XXX this should be called `opt_trace'      */
 #endif
 
+#if defined(ENABLE_DEBUG_FILTER)
+const char *opt_filter_verbosecall_include = 0;
+const char *opt_filter_verbosecall_exclude = 0;
+const char *opt_filter_show_method = 0;
+#endif
 
 /* options_get *****************************************************************
 
index 92ecd07bb5f8fc6bd15710667cf565c8fb67d42c..3abb564e88334a5a4fd0f288cd052ed0fa50fc81 100644 (file)
@@ -22,7 +22,7 @@
    Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
    02110-1301, USA.
 
-   $Id: options.h 7894 2007-05-10 14:04:05Z twisti $
+   $Id: options.h 7966 2007-05-25 12:41:03Z pm $
 
 */
 
@@ -170,6 +170,13 @@ extern s4   opt_static_supers;
 extern bool vm_debug;
 #endif
 
+/* debug output filtering options *********************************************/
+
+#if defined(ENABLE_DEBUG_FILTER)
+extern const char *opt_filter_verbosecall_include;
+extern const char *opt_filter_verbosecall_exclude;
+extern const char *opt_filter_show_method;
+#endif
 
 /* function prototypes ********************************************************/