* src/vm/jit/patcher-common.h: Added __X86_64__ ifdef.
authorChristian Thalinger <twisti@complang.tuwien.ac.at>
Fri, 7 Sep 2007 23:50:30 +0000 (01:50 +0200)
committerChristian Thalinger <twisti@complang.tuwien.ac.at>
Fri, 7 Sep 2007 23:50:30 +0000 (01:50 +0200)
* src/vm/signal.c (signal_init): Likewise.
* src/vm/signallocal.h: Likewise.

* src/vm/jit/x86_64/asmpart.S (asm_patcher_wrapper): Removed.

* src/vm/jit/x86_64/codegen.c (vm/jit/patcher.h): Removed.
(vm/jit/patcher-common.h): Added.
(codegen_emit): Implemented patchers-by-signal and load data from data
segment instead of moving inline.
(codegen_emit_stub_native): Likewise.
(codegen_emit_stub_compiler): Quick hack for ALD.

* src/vm/jit/x86_64/codegen.h (PATCHER_CALL_SIZE): Changed to 2.
(PATCHER_NOPS): Likewise.
(M_ALD): Handle RIP properly.

* src/vm/jit/x86_64/emit.c (vm/jit/patcher-common.h): Added.
(emit_patcher_stubs): Removed.
(emit_trap): Emit UD2.

* src/vm/jit/x86_64/linux/md-os.c (md_signal_handler_sigill): New
function.

* src/vm/jit/x86_64/patcher.c (vm/jit/patcher.h): Removed.
(vm/jit/patcher-common.h): Added.
(patcher_wrapper): Removed.
(PATCH_BACK_ORIGINAL_MCODE): New macro.
(patcher_patch_code): New function.
(patcher_resolve_classref_to_classinfo): Likewise.
(patcher_resolve_classref_to_vftbl): Likewise.
(patcher_resolve_classref_to_flags): Likewise.
(patcher_resolve_native_function): Likewise.
(patcher_aconst): Removed.
(patcher_builtin_multianewarray): Likewise.
(patcher_builtin_arraycheckcast): Likewise.
(patcher_checkcast_instanceof_flags): Likewise.
(patcher_checkcast_class): Likewise.
(patcher_instanceof_class): Likewise.
(patcher_clinit): Likewise.
(patcher_athrow_areturn): Likewise.
(patcher_resolve_native): Likewise.

src/vm/jit/patcher-common.h
src/vm/jit/x86_64/asmpart.S
src/vm/jit/x86_64/codegen.c
src/vm/jit/x86_64/codegen.h
src/vm/jit/x86_64/emit.c
src/vm/jit/x86_64/linux/md-os.c
src/vm/jit/x86_64/patcher.c
src/vm/signal.c
src/vm/signallocal.h

index 9b1414d4714c71cf066461c60d13ebcdf26c566d..63e607e3001a24152d9dd7965b4b55a3e5cfc56f 100644 (file)
@@ -81,7 +81,7 @@ void patcher_patch_code(patchref_t *pr);
 
 /* patcher prototypes and macros **********************************************/
 
-#if defined(__ALPHA__) || defined(__ARM__) || defined(__I386__) || defined(__MIPS__) || defined(__POWERPC__) || defined(__POWERPC64__) || defined (__S390__)
+#if defined(__ALPHA__) || defined(__ARM__) || defined(__I386__) || defined(__MIPS__) || defined(__POWERPC__) || defined(__POWERPC64__) || defined (__S390__) || defined(__X86_64__)
 
 /* new patcher functions */
 
@@ -142,7 +142,7 @@ bool patcher_invokevirtual(patchref_t *pr);
 bool patcher_invokeinterface(patchref_t *pr);
 #define PATCHER_invokeinterface (functionptr) patcher_invokeinterface
 
-#if defined(__ALPHA__) || defined(__I386__) || defined(__MIPS__) || defined(__POWERPC__) || defined(__POWERPC64__) || defined(__S390__) 
+#if defined(__ALPHA__) || defined(__I386__) || defined(__MIPS__) || defined(__POWERPC__) || defined(__POWERPC64__) || defined(__S390__) || defined(__X86_64__)
 
 bool patcher_checkcast_interface(patchref_t *pr);
 #define PATCHER_checkcast_interface (functionptr) patcher_checkcast_interface
@@ -150,7 +150,7 @@ bool patcher_checkcast_interface(patchref_t *pr);
 bool patcher_instanceof_interface(patchref_t *pr);
 #define PATCHER_instanceof_interface (functionptr) patcher_instanceof_interface
 
-#endif /* defined(__ALPHA__) || defined(__I386__) || defined(__MIPS__) || defined(__POWERPC__) || defined(__POWERPC64__) || defined(__S390__) */
+#endif /* defined(__ALPHA__) || defined(__I386__) || defined(__MIPS__) || defined(__POWERPC__) || defined(__POWERPC64__) || defined(__S390__) || defined(__X86_64__) */
 
 #if defined(__S390__)
 
index 58ab38124a894b21f02c4bb48d912dfc5a899660..1129d51936edd1cd0f7432d3cf907f92b353fbd1 100644 (file)
@@ -55,8 +55,6 @@
 
        .globl asm_abstractmethoderror
 
-       .globl asm_patcher_wrapper
-
 #if defined(ENABLE_REPLACEMENT)
        .globl asm_replacement_out
        .globl asm_replacement_in
@@ -405,61 +403,6 @@ asm_abstractmethoderror:
        jmp     L_asm_handle_exception
 
 
-/* asm_patcher_wrapper *********************************************************
-
-   XXX
-
-   Stack layout:
-     40   return address
-     32   pointer to virtual java_objectheader
-     24   machine code (which is patched back later)
-     16   unresolved class/method/field reference
-      8   data segment displacement from load instructions
-      0   pointer to patcher function
-     -8   bp
-
-*******************************************************************************/
-
-asm_patcher_wrapper:
-       push    bp                          /* save base pointer                  */
-       mov     sp,bp                       /* move actual sp to bp               */
-       sub     $(3+ARG_CNT+TMP_CNT)*8,sp
-       and     $0xfffffffffffffff0,sp      /* align sp to 16-byte (this is for   */
-                                           /* leaf functions)                    */
-
-       SAVE_ARGUMENT_REGISTERS(3)
-       SAVE_TEMPORARY_REGISTERS(3+ARG_CNT)
-
-       mov     itmp1,0*8(sp)               /* save itmp1 and itmp2               */
-       mov     itmp2,1*8(sp)               /* can be used by some instructions   */
-
-       mov     bp,a0                       /* pass SP of patcher stub            */
-       add     $(1*8),a0
-       mov     $0,a1                       /* pass PV (if NULL, use findmethod)  */
-       mov     $0,a2                       /* pass RA (it's on the stack)        */
-       call    patcher_wrapper@PLT
-       mov     v0,2*8(sp)                  /* save return value                  */
-
-       RESTORE_ARGUMENT_REGISTERS(3)
-       RESTORE_TEMPORARY_REGISTERS(3+ARG_CNT)
-
-       mov     0*8(sp),itmp1               /* restore itmp1 and itmp2            */
-       mov     1*8(sp),itmp2               /* can be used by some instructions   */
-       mov     2*8(sp),itmp3               /* restore return value               */
-
-       mov     bp,sp                       /* restore original sp                */
-       pop     bp                          /* restore bp                         */
-       add     $(5*8),sp                   /* remove patcher stackframe, keep RA */
-
-       test    itmp3,itmp3                 /* exception thrown?                  */
-       jne     L_asm_patcher_wrapper_exception
-       ret                                 /* call new patched code              */
-
-L_asm_patcher_wrapper_exception:
-       mov     itmp3,xptr                  /* get exception                      */
-       pop     xpc                         /* get and remove return address      */
-       jmp     L_asm_handle_exception
-
 #if defined(ENABLE_REPLACEMENT)
 
 /* asm_replacement_out *********************************************************
index dc2e2465f387acf0569ab219432d3a0b2f2b68a3..7a9b7755aba00659f1719895b625e588f76896b0 100644 (file)
@@ -60,7 +60,7 @@
 #include "vm/jit/jit.h"
 #include "vm/jit/methodheader.h"
 #include "vm/jit/parse.h"
-#include "vm/jit/patcher.h"
+#include "vm/jit/patcher-common.h"
 #include "vm/jit/reg.h"
 #include "vm/jit/replace.h"
 #include "vm/jit/stacktrace.h"
@@ -474,21 +474,26 @@ bool codegen_emit(jitdata *jd)
                        d = codegen_reg_of_dst(jd, iptr, REG_ITMP1);
 
                        if (INSTRUCTION_IS_UNRESOLVED(iptr)) {
-                               cr = iptr->sx.val.c.ref;
+                               cr   = iptr->sx.val.c.ref;
+                               disp = dseg_add_unique_address(cd, cr);
 
 /*                             PROFILE_CYCLE_STOP; */
 
-                               codegen_add_patch_ref(cd, PATCHER_aconst, cr, 0);
+                               patcher_add_patch_ref(jd, PATCHER_resolve_classref_to_classinfo,
+                                                                         cr, disp);
 
 /*                             PROFILE_CYCLE_START; */
 
-                               M_MOV_IMM(NULL, d);
-
-                       else {
-                               if (iptr->sx.val.anyptr == 0)
+                               M_ALD(d, RIP, disp);
+                       }
+                       else {
+                               if (iptr->sx.val.anyptr == 0) {
                                        M_CLR(d);
-                               else
-                                       M_MOV_IMM(iptr->sx.val.anyptr, d);
+                               }
+                               else {
+                                       disp = dseg_add_address(cd, iptr->sx.val.anyptr);
+                                       M_ALD(d, RIP, disp);
+                               }
                        }
                        emit_store_dst(jd, iptr, d);
                        break;
@@ -1750,17 +1755,11 @@ bool codegen_emit(jitdata *jd)
                        if (INSTRUCTION_IS_UNRESOLVED(iptr)) {
                                uf        = iptr->sx.s23.s3.uf;
                                fieldtype = uf->fieldref->parseddesc.fd->type;
-                               disp      = dseg_add_unique_address(cd, NULL);
-                               disp      = disp + -((cd->mcodeptr + 7) - cd->mcodebase);
-
-                               /* must be calculated before codegen_add_patch_ref */
-
-                               if (opt_shownops)
-                                       disp -= PATCHER_CALL_SIZE;
+                               disp      = dseg_add_unique_address(cd, uf);
 
 /*                             PROFILE_CYCLE_STOP; */
 
-                               codegen_add_patch_ref(cd, PATCHER_get_putstatic, uf, disp);
+                               patcher_add_patch_ref(jd, PATCHER_get_putstatic, uf, disp);
 
 /*                             PROFILE_CYCLE_START; */
                        }
@@ -1768,17 +1767,14 @@ bool codegen_emit(jitdata *jd)
                                fi        = iptr->sx.s23.s3.fmiref->p.field;
                                fieldtype = fi->type;
                                disp      = dseg_add_address(cd, fi->value);
-                               disp      = disp + -((cd->mcodeptr + 7) - cd->mcodebase);
 
                                if (!CLASS_IS_OR_ALMOST_INITIALIZED(fi->class)) {
                                        PROFILE_CYCLE_STOP;
 
-                                       codegen_add_patch_ref(cd, PATCHER_clinit, fi->class, 0);
+                                       patcher_add_patch_ref(jd, PATCHER_initialize_class,
+                                                                                 fi->class, 0);
 
                                        PROFILE_CYCLE_START;
-
-                                       if (opt_shownops)
-                                               disp -= PATCHER_CALL_SIZE;
                                }
                        }
 
@@ -1814,17 +1810,11 @@ bool codegen_emit(jitdata *jd)
                        if (INSTRUCTION_IS_UNRESOLVED(iptr)) {
                                uf        = iptr->sx.s23.s3.uf;
                                fieldtype = uf->fieldref->parseddesc.fd->type;
-                               disp      = dseg_add_unique_address(cd, NULL);
-                               disp      = disp + -((cd->mcodeptr + 7) - cd->mcodebase);
-
-                               /* must be calculated before codegen_add_patch_ref */
-
-                               if (opt_shownops)
-                                       disp -= PATCHER_CALL_SIZE;
+                               disp      = dseg_add_unique_address(cd, uf);
 
 /*                             PROFILE_CYCLE_STOP; */
 
-                               codegen_add_patch_ref(cd, PATCHER_get_putstatic, uf, disp);
+                               patcher_add_patch_ref(jd, PATCHER_get_putstatic, uf, disp);
 
 /*                             PROFILE_CYCLE_START; */
                        }
@@ -1832,17 +1822,14 @@ bool codegen_emit(jitdata *jd)
                                fi        = iptr->sx.s23.s3.fmiref->p.field;
                                fieldtype = fi->type;
                                disp      = dseg_add_address(cd, fi->value);
-                               disp      = disp + -((cd->mcodeptr + 7) - cd->mcodebase);
 
                                if (!CLASS_IS_OR_ALMOST_INITIALIZED(fi->class)) {
                                        PROFILE_CYCLE_STOP;
 
-                                       codegen_add_patch_ref(cd, PATCHER_clinit, fi->class, 0);
+                                       patcher_add_patch_ref(jd, PATCHER_initialize_class,
+                                                                                 fi->class, 0);
 
                                        PROFILE_CYCLE_START;
-
-                                       if (opt_shownops)
-                                               disp -= PATCHER_CALL_SIZE;
                                }
                        }
 
@@ -1879,17 +1866,11 @@ bool codegen_emit(jitdata *jd)
                        if (INSTRUCTION_IS_UNRESOLVED(iptr)) {
                                uf        = iptr->sx.s23.s3.uf;
                                fieldtype = uf->fieldref->parseddesc.fd->type;
-                               disp      = dseg_add_unique_address(cd, NULL);
-                               disp      = disp + -((cd->mcodeptr + 7) - cd->mcodebase);
-
-                               /* must be calculated before codegen_add_patch_ref */
-
-                               if (opt_shownops)
-                                       disp -= PATCHER_CALL_SIZE;
+                               disp      = dseg_add_unique_address(cd, uf);
 
 /*                             PROFILE_CYCLE_STOP; */
 
-                               codegen_add_patch_ref(cd, PATCHER_get_putstatic, uf, disp);
+                               patcher_add_patch_ref(jd, PATCHER_get_putstatic, uf, disp);
 
 /*                             PROFILE_CYCLE_START; */
                        }
@@ -1897,17 +1878,14 @@ bool codegen_emit(jitdata *jd)
                                fi        = iptr->sx.s23.s3.fmiref->p.field;
                                fieldtype = fi->type;
                                disp      = dseg_add_address(cd, fi->value);
-                               disp      = disp + -((cd->mcodeptr + 7) - cd->mcodebase);
 
                                if (!CLASS_IS_OR_ALMOST_INITIALIZED(fi->class)) {
                                        PROFILE_CYCLE_STOP;
 
-                                       codegen_add_patch_ref(cd, PATCHER_clinit, fi->class, 0);
+                                       patcher_add_patch_ref(jd, PATCHER_initialize_class,
+                                                                                 fi->class, 0);
 
                                        PROFILE_CYCLE_START;
-
-                                       if (opt_shownops)
-                                               disp -= PATCHER_CALL_SIZE;
                                }
                        }
 
@@ -1945,7 +1923,7 @@ bool codegen_emit(jitdata *jd)
 
 /*                             PROFILE_CYCLE_STOP; */
 
-                               codegen_add_patch_ref(cd, PATCHER_get_putfield, uf, 0);
+                               patcher_add_patch_ref(jd, PATCHER_get_putfield, uf, 0);
 
 /*                             PROFILE_CYCLE_START; */
                        }
@@ -1990,7 +1968,7 @@ bool codegen_emit(jitdata *jd)
 
 /*                             PROFILE_CYCLE_STOP; */
 
-                               codegen_add_patch_ref(cd, PATCHER_get_putfield, uf, 0);
+                               patcher_add_patch_ref(jd, PATCHER_get_putfield, uf, 0);
 
 /*                             PROFILE_CYCLE_START; */
                        } 
@@ -2031,7 +2009,7 @@ bool codegen_emit(jitdata *jd)
 
 /*                             PROFILE_CYCLE_STOP; */
 
-                               codegen_add_patch_ref(cd, PATCHER_putfieldconst, uf, 0);
+                               patcher_add_patch_ref(jd, PATCHER_putfieldconst, uf, 0);
 
 /*                             PROFILE_CYCLE_START; */
                        } 
@@ -2071,7 +2049,7 @@ bool codegen_emit(jitdata *jd)
                        if (INSTRUCTION_IS_UNRESOLVED(iptr)) {
                                uc = iptr->sx.s23.s2.uc;
 
-                               codegen_add_patch_ref(cd, PATCHER_athrow_areturn, uc, 0);
+                               patcher_add_patch_ref(jd, PATCHER_resolve_class, uc, 0);
                        }
 #endif /* ENABLE_VERIFIER */
 
@@ -2187,7 +2165,7 @@ bool codegen_emit(jitdata *jd)
 
                                PROFILE_CYCLE_STOP;
 
-                               codegen_add_patch_ref(cd, PATCHER_athrow_areturn, uc, 0);
+                               patcher_add_patch_ref(jd, PATCHER_resolve_class, uc, 0);
 
                                PROFILE_CYCLE_START;
                        }
@@ -2434,34 +2412,22 @@ gen_method:
 
                        case ICMD_INVOKESTATIC:
                                if (lm == NULL) {
-                                       disp = dseg_add_unique_address(cd, NULL);
-                                       disp = disp + -((cd->mcodeptr + 7) - cd->mcodebase);
-
-                                       /* must be calculated before codegen_add_patch_ref */
+                                       disp = dseg_add_unique_address(cd, um);
 
-                                       if (opt_shownops)
-                                               disp -= PATCHER_CALL_SIZE;
-
-                                       codegen_add_patch_ref(cd, PATCHER_invokestatic_special,
+                                       patcher_add_patch_ref(jd, PATCHER_invokestatic_special,
                                                                                  um, disp);
-
-/*                                     a = 0; */
                                }
                                else {
                                        disp = dseg_add_functionptr(cd, lm->stubroutine);
-                                       disp = disp + -((cd->mcodeptr + 7) - cd->mcodebase);
-
-/*                                     a = (ptrint) lm->stubroutine; */
                                }
 
-/*                             M_MOV_IMM(a, REG_ITMP2); */
                                M_ALD(REG_ITMP2, RIP, disp);
                                M_CALL(REG_ITMP2);
                                break;
 
                        case ICMD_INVOKEVIRTUAL:
                                if (lm == NULL) {
-                                       codegen_add_patch_ref(cd, PATCHER_invokevirtual, um, 0);
+                                       patcher_add_patch_ref(jd, PATCHER_invokevirtual, um, 0);
 
                                        s1 = 0;
                                }
@@ -2478,7 +2444,7 @@ gen_method:
 
                        case ICMD_INVOKEINTERFACE:
                                if (lm == NULL) {
-                                       codegen_add_patch_ref(cd, PATCHER_invokeinterface, um, 0);
+                                       patcher_add_patch_ref(jd, PATCHER_invokeinterface, um, 0);
 
                                        s1 = 0;
                                        s2 = 0;
@@ -2536,18 +2502,15 @@ gen_method:
                                /* object type cast-check */
 
                                classinfo *super;
-                               vftbl_t   *supervftbl;
                                s4         superindex;
 
                                if (INSTRUCTION_IS_UNRESOLVED(iptr)) {
                                        super      = NULL;
                                        superindex = 0;
-                                       supervftbl = NULL;
                                }
                                else {
                                        super      = iptr->sx.s23.s3.c.cls;
                                        superindex = super->index;
-                                       supervftbl = super->vftbl;
                                }
 
                                if ((super == NULL) || !(super->flags & ACC_INTERFACE))
@@ -2561,7 +2524,7 @@ gen_method:
                                        M_TEST(s1);
                                        emit_label_beq(cd, BRANCH_LABEL_1);
 
-                                       codegen_add_patch_ref(cd, PATCHER_checkcast_instanceof_flags,
+                                       patcher_add_patch_ref(jd, PATCHER_resolve_classref_to_flags,
                                                                                  iptr->sx.s23.s3.c.ref, 0);
 
                                        M_IMOV_IMM(0, REG_ITMP2);                 /* super->flags */
@@ -2580,7 +2543,7 @@ gen_method:
                                        M_ALD(REG_ITMP2, s1, OFFSET(java_object_t, vftbl));
 
                                        if (super == NULL) {
-                                               codegen_add_patch_ref(cd, PATCHER_checkcast_interface,
+                                               patcher_add_patch_ref(jd, PATCHER_checkcast_interface,
                                                                                          iptr->sx.s23.s3.c.ref,
                                                                                          0);
                                        }
@@ -2607,25 +2570,27 @@ gen_method:
                                if ((super == NULL) || !(super->flags & ACC_INTERFACE)) {
                                        if (super == NULL) {
                                                emit_label(cd, BRANCH_LABEL_2);
+
+                                               cr   = iptr->sx.s23.s3.c.ref;
+                                               disp = dseg_add_unique_address(cd, cr);
+
+                                               patcher_add_patch_ref(jd,
+                                                                                         PATCHER_resolve_classref_to_vftbl,
+                                                                                         cr, disp);
                                        }
                                        else {
                                                M_TEST(s1);
                                                emit_label_beq(cd, BRANCH_LABEL_5);
-                                       }
 
-                                       M_ALD(REG_ITMP2, s1, OFFSET(java_object_t, vftbl));
-
-                                       if (super == NULL) {
-                                               codegen_add_patch_ref(cd, PATCHER_checkcast_class,
-                                                                                         iptr->sx.s23.s3.c.ref,
-                                                                                         0);
+                                               disp = dseg_add_address(cd, super->vftbl);
                                        }
 
-                                       M_MOV_IMM(supervftbl, REG_ITMP3);
+                                       M_ALD(REG_ITMP2, s1, OFFSET(java_object_t, vftbl));
+                                       M_ALD(REG_ITMP3, RIP, disp);
 
                                        CODEGEN_CRITICAL_SECTION_START;
 
-                                       M_ILD32(REG_ITMP2, REG_ITMP2, OFFSET(vftbl_t, baseval));
+                                       M_ILD(REG_ITMP2, REG_ITMP2, OFFSET(vftbl_t, baseval));
 
                                        /*                                      if (s1 != REG_ITMP1) { */
                                        /*                                              emit_movl_membase_reg(cd, REG_ITMP3, */
@@ -2641,9 +2606,9 @@ gen_method:
 
                                        /*                                      } else { */
 
-                                       M_ILD32(REG_ITMP3, REG_ITMP3, OFFSET(vftbl_t, baseval));
+                                       M_ILD(REG_ITMP3, REG_ITMP3, OFFSET(vftbl_t, baseval));
                                        M_ISUB(REG_ITMP3, REG_ITMP2);
-                                       M_MOV_IMM(supervftbl, REG_ITMP3);
+                                       M_ALD(REG_ITMP3, RIP, disp);
                                        M_ILD(REG_ITMP3, REG_ITMP3, OFFSET(vftbl_t, diffval));
                                        /*                                      } */
 
@@ -2670,11 +2635,18 @@ gen_method:
                                M_INTMOVE(s1, REG_A0);
 
                                if (INSTRUCTION_IS_UNRESOLVED(iptr)) {
-                                       codegen_add_patch_ref(cd, PATCHER_builtin_arraycheckcast,
-                                                                                 iptr->sx.s23.s3.c.ref, 0);
+                                       cr   = iptr->sx.s23.s3.c.ref;
+                                       disp = dseg_add_unique_address(cd, cr);
+
+                                       patcher_add_patch_ref(jd,
+                                                                                 PATCHER_resolve_classref_to_classinfo,
+                                                                                 cr, disp);
+                               }
+                               else {
+                                       disp = dseg_add_address(cd, iptr->sx.s23.s3.c.cls);
                                }
 
-                               M_MOV_IMM(iptr->sx.s23.s3.c.cls, REG_A1);
+                               M_ALD(REG_A1, RIP, disp);
                                M_MOV_IMM(BUILTIN_arraycheckcast, REG_ITMP1);
                                M_CALL(REG_ITMP1);
 
@@ -2694,18 +2666,15 @@ gen_method:
 
                        {
                        classinfo *super;
-                       vftbl_t   *supervftbl;
                        s4         superindex;
 
                        if (INSTRUCTION_IS_UNRESOLVED(iptr)) {
                                super      = NULL;
                                superindex = 0;
-                               supervftbl = NULL;
                        }
                        else {
                                super      = iptr->sx.s23.s3.c.cls;
                                superindex = super->index;
-                               supervftbl = super->vftbl;
                        }
 
                        if ((super == NULL) || !(super->flags & ACC_INTERFACE))
@@ -2727,7 +2696,7 @@ gen_method:
                                M_TEST(s1);
                                emit_label_beq(cd, BRANCH_LABEL_1);
 
-                               codegen_add_patch_ref(cd, PATCHER_checkcast_instanceof_flags,
+                               patcher_add_patch_ref(jd, PATCHER_resolve_classref_to_flags,
                                                                          iptr->sx.s23.s3.c.ref, 0);
 
                                M_IMOV_IMM(0, REG_ITMP3);                     /* super->flags */
@@ -2746,7 +2715,7 @@ gen_method:
                                M_ALD(REG_ITMP1, s1, OFFSET(java_object_t, vftbl));
 
                                if (super == NULL) {
-                                       codegen_add_patch_ref(cd, PATCHER_instanceof_interface,
+                                       patcher_add_patch_ref(jd, PATCHER_instanceof_interface,
                                                                                  iptr->sx.s23.s3.c.ref, 0);
                                }
 
@@ -2774,20 +2743,23 @@ gen_method:
                        if ((super == NULL) || !(super->flags & ACC_INTERFACE)) {
                                if (super == NULL) {
                                        emit_label(cd, BRANCH_LABEL_2);
+
+                                       cr   = iptr->sx.s23.s3.c.ref;
+                                       disp = dseg_add_unique_address(cd, cr);
+
+                                       patcher_add_patch_ref(jd,
+                                                                                 PATCHER_resolve_classref_to_vftbl,
+                                                                                 cr, disp);
                                }
                                else {
                                        M_TEST(s1);
                                        emit_label_beq(cd, BRANCH_LABEL_5);
-                               }
-
-                               M_ALD(REG_ITMP1, s1, OFFSET(java_object_t, vftbl));
 
-                               if (super == NULL) {
-                                       codegen_add_patch_ref(cd, PATCHER_instanceof_class,
-                                                                                 iptr->sx.s23.s3.c.ref, 0);
+                                       disp = dseg_add_address(cd, super->vftbl);
                                }
 
-                               M_MOV_IMM(supervftbl, REG_ITMP2);
+                               M_ALD(REG_ITMP1, s1, OFFSET(java_object_t, vftbl));
+                               M_ALD(REG_ITMP2, RIP, disp);
 
                                CODEGEN_CRITICAL_SECTION_START;
 
@@ -2833,20 +2805,26 @@ gen_method:
                                }
                        }
 
+                       /* a0 = dimension count */
+
+                       M_MOV_IMM(iptr->s1.argcount, REG_A0);
+
                        /* is a patcher function set? */
 
                        if (INSTRUCTION_IS_UNRESOLVED(iptr)) {
-                               codegen_add_patch_ref(cd, PATCHER_builtin_multianewarray,
-                                                                         iptr->sx.s23.s3.c.ref, 0);
-                       }
-
-                       /* a0 = dimension count */
+                               cr   = iptr->sx.s23.s3.c.ref;
+                               disp = dseg_add_unique_address(cd, cr);
 
-                       M_MOV_IMM(iptr->s1.argcount, REG_A0);
+                               patcher_add_patch_ref(jd, PATCHER_resolve_classref_to_classinfo,
+                                                                         cr, disp);
+                       }
+                       else {
+                               disp = dseg_add_address(cd, iptr->sx.s23.s3.c.cls);
+                       }
 
                        /* a1 = classinfo */
 
-                       M_MOV_IMM(iptr->sx.s23.s3.c.cls, REG_A1);
+                       M_ALD(REG_A1, RIP, disp);
 
                        /* a2 = pointer to dimensions = stack pointer */
 
@@ -2890,9 +2868,9 @@ gen_method:
 
        dseg_createlinenumbertable(cd);
 
-       /* generate stubs */
+       /* Generate patcher traps. */
 
-       emit_patcher_stubs(jd);
+       emit_patcher_traps(jd);
 
        /* everything's ok */
 
@@ -2918,8 +2896,10 @@ void codegen_emit_stub_compiler(jitdata *jd)
 
        /* code for the stub */
 
-       M_ALD(REG_ITMP1, RIP, -(7 * 1 + 2 * SIZEOF_VOID_P));       /* methodinfo  */
-       M_ALD(REG_ITMP3, RIP, -(7 * 2 + 3 * SIZEOF_VOID_P));  /* compiler pointer */
+       M_LLD(REG_ITMP1, RIP, -(7 * 1 + 2 * SIZEOF_VOID_P));               /* methodinfo  */
+/*     M_ALD(REG_ITMP1, RIP, -(2 * SIZEOF_VOID_P));               /\* methodinfo  *\/ */
+       M_LLD(REG_ITMP3, RIP, -(7 * 2 + 3 * SIZEOF_VOID_P));          /* compiler pointer */
+/*     M_ALD(REG_ITMP3, RIP, -(3 * SIZEOF_VOID_P));          /\* compiler pointer *\/ */
        M_JMP(REG_ITMP3);
 }
 
@@ -3109,7 +3089,11 @@ void codegen_emit_stub_native(jitdata *jd, methoddesc *nmd, functionptr f)
        s4           nativeparams;
        s4           i, j;
        s4           t;
-       s4           s1, s2, disp;
+       s4           s1, s2;
+       int          funcdisp;
+#if defined(ENABLE_GC_CACAO)
+       int          disp;
+#endif
 
        /* get required compiler data */
 
@@ -3161,10 +3145,10 @@ void codegen_emit_stub_native(jitdata *jd, methoddesc *nmd, functionptr f)
 
        /* get function address (this must happen before the stackframeinfo) */
 
-       if (f == NULL)
-               codegen_add_patch_ref(cd, PATCHER_resolve_native, m, 0);
+       funcdisp = dseg_add_functionptr(cd, f);
 
-       M_MOV_IMM(f, REG_ITMP3);
+       if (f == NULL)
+               patcher_add_patch_ref(jd, PATCHER_resolve_native_function, m, funcdisp);
 
 #if defined(ENABLE_GC_CACAO)
        /* Save callee saved integer registers in stackframeinfo (GC may
@@ -3197,8 +3181,6 @@ void codegen_emit_stub_native(jitdata *jd, methoddesc *nmd, functionptr f)
                }
        }
 
-       M_AST(REG_ITMP3, REG_SP, md->paramcount * 8);
-
        /* create dynamic stack info */
 
        M_MOV(REG_SP, REG_A0);
@@ -3231,8 +3213,6 @@ void codegen_emit_stub_native(jitdata *jd, methoddesc *nmd, functionptr f)
                }
        }
 
-       M_ALD(REG_ITMP3, REG_SP, md->paramcount * 8);
-
        /* copy or spill arguments to new locations */
 
        for (i = md->paramcount - 1, j = i + nativeparams; i >= 0; i--, j--) {
@@ -3284,7 +3264,8 @@ void codegen_emit_stub_native(jitdata *jd, methoddesc *nmd, functionptr f)
 
        /* do the native function call */
 
-       M_CALL(REG_ITMP3);
+       M_ALD(REG_ITMP1, RIP, funcdisp);
+       M_CALL(REG_ITMP1);
 
        /* save return value */
 
@@ -3356,9 +3337,9 @@ void codegen_emit_stub_native(jitdata *jd, methoddesc *nmd, functionptr f)
        M_MOV_IMM(asm_handle_nat_exception, REG_ITMP3);
        M_JMP(REG_ITMP3);
 
-       /* generate patcher stubs */
+       /* Generate patcher traps. */
 
-       emit_patcher_stubs(jd);
+       emit_patcher_traps(jd);
 }
 
 
index 4eb7e8b8ebfaa8f4f1617cc168dd2fd2799f6c63..6b0fb88fc2ef3be100810093efa96b06eb255621 100644 (file)
 
 /* patcher defines ************************************************************/
 
-#define PATCHER_CALL_SIZE    5          /* size in bytes of a patcher call    */
+#define PATCHER_CALL_SIZE    2          /* size in bytes of a patcher call    */
 
 #define PATCHER_NOPS \
     do { \
         M_NOP; \
         M_NOP; \
-        M_NOP; \
-        M_NOP; \
-        M_NOP; \
     } while (0)
 
 
 #define M_IINC(a)               emit_incl_reg(cd, (a))
 #define M_IDEC(a)               emit_decl_reg(cd, (a))
 
-#define M_ALD(a,b,disp)         M_LLD(a,b,disp)
+#define M_ALD(a,b,disp) \
+    do { \
+        if (b == RIP) \
+            M_LLD(a, b, disp + -((cd->mcodeptr + 7) - cd->mcodebase)); \
+        else \
+            M_LLD(a, b, disp); \
+    } while (0)
+
 #define M_ALD32(a,b,disp)       M_LLD32(a,b,disp)
 
 #define M_ALD_MEM(a,disp)       emit_mov_mem_reg(cd, (disp), (a))
index fd7df3364f14a8a2e45789b1640443b6ef764033..4693e218c26a2513bd57db0936c8c9376b4abed2 100644 (file)
@@ -48,6 +48,7 @@
 #include "vm/jit/codegen-common.h"
 #include "vm/jit/emit-common.h"
 #include "vm/jit/jit.h"
+#include "vm/jit/patcher-common.h"
 #include "vm/jit/replace.h"
 
 #include "vmcore/options.h"
@@ -434,93 +435,6 @@ void emit_exception_check(codegendata *cd, instruction *iptr)
 }
 
 
-/* emit_patcher_stubs **********************************************************
-
-   Generates the code for the patcher stubs.
-
-*******************************************************************************/
-
-void emit_patcher_stubs(jitdata *jd)
-{
-       codegendata *cd;
-       patchref    *pref;
-       u8           mcode;
-       u1          *savedmcodeptr;
-       u1          *tmpmcodeptr;
-       s4           targetdisp;
-       s4           disp;
-
-       /* get required compiler data */
-
-       cd = jd->cd;
-
-       /* generate code patching stub call code */
-
-       targetdisp = 0;
-
-       for (pref = cd->patchrefs; pref != NULL; pref = pref->next) {
-               /* check size of code segment */
-
-               MCODECHECK(512);
-
-               /* Get machine code which is patched back in later. A
-                  `call rel32' is 5 bytes long (but read 8 bytes). */
-
-               savedmcodeptr = cd->mcodebase + pref->branchpos;
-               mcode = *((u8 *) savedmcodeptr);
-
-               /* patch in `call rel32' to call the following code */
-
-               tmpmcodeptr  = cd->mcodeptr;    /* save current mcodeptr              */
-               cd->mcodeptr = savedmcodeptr;   /* set mcodeptr to patch position     */
-
-               M_CALL_IMM(tmpmcodeptr - (savedmcodeptr + PATCHER_CALL_SIZE));
-
-               cd->mcodeptr = tmpmcodeptr;     /* restore the current mcodeptr       */
-
-               /* move pointer to java_objectheader onto stack */
-
-#if defined(ENABLE_THREADS)
-               /* create a virtual java_objectheader */
-
-               (void) dseg_add_unique_address(cd, NULL);                  /* flcword */
-               (void) dseg_add_unique_address(cd, lock_get_initial_lock_word());
-               disp = dseg_add_unique_address(cd, NULL);                  /* vftbl   */
-
-               emit_lea_membase_reg(cd, RIP, -((cd->mcodeptr + 7) - cd->mcodebase) + disp, REG_ITMP3);
-               M_PUSH(REG_ITMP3);
-#else
-               M_PUSH_IMM(0);
-#endif
-
-               /* move machine code bytes and classinfo pointer into registers */
-
-               M_MOV_IMM(mcode, REG_ITMP3);
-               M_PUSH(REG_ITMP3);
-
-               M_MOV_IMM(pref->ref, REG_ITMP3);
-               M_PUSH(REG_ITMP3);
-
-               M_MOV_IMM(pref->disp, REG_ITMP3);
-               M_PUSH(REG_ITMP3);
-
-               M_MOV_IMM(pref->patcher, REG_ITMP3);
-               M_PUSH(REG_ITMP3);
-
-               if (targetdisp == 0) {
-                       targetdisp = cd->mcodeptr - cd->mcodebase;
-
-                       M_MOV_IMM(asm_patcher_wrapper, REG_ITMP3);
-                       M_JMP(REG_ITMP3);
-               }
-               else {
-                       M_JMP_IMM((cd->mcodebase + targetdisp) -
-                                         (cd->mcodeptr + PATCHER_CALL_SIZE));
-               }
-       }
-}
-
-
 /* emit_trap *******************************************************************
 
    Emit a trap instruction and return the original machine code.
@@ -529,14 +443,17 @@ void emit_patcher_stubs(jitdata *jd)
 
 uint32_t emit_trap(codegendata *cd)
 {
-       uint32_t mcode;
+       uint16_t mcode;
 
-       /* Get machine code which is patched back in later. The
-          trap is 1 instruction word long. */
+       /* Get machine code which is patched back in later. The trap is 2
+          bytes long. */
 
-       mcode = *((uint32_t *) cd->mcodeptr);
+       mcode = *((uint16_t *) cd->mcodeptr);
 
-       M_NOP;
+       /* XXX This needs to be change to INT3 when the debugging problems
+          with gdb are resolved. */
+
+       M_UD2;
 
        return mcode;
 }
index 69a9b2b47baace592d7ca116aa06eb9b4e77b1b5..a81d13f1d8934f5f7f6b973060976db4bae8826d 100644 (file)
@@ -234,6 +234,63 @@ void md_signal_handler_sigfpe(int sig, siginfo_t *siginfo, void *_p)
 }
 
 
+/* md_signal_handler_sigill ****************************************************
+
+   Signal handler for patchers.
+
+*******************************************************************************/
+
+void md_signal_handler_sigill(int sig, siginfo_t *siginfo, void *_p)
+{
+       stackframeinfo  sfi;
+       ucontext_t     *_uc;
+       mcontext_t     *_mc;
+       u1             *pv;
+       u1             *sp;
+       u1             *ra;
+       u1             *xpc;
+       int             type;
+       intptr_t        val;
+       void           *p;
+
+       _uc = (ucontext_t *) _p;
+       _mc = &_uc->uc_mcontext;
+
+       /* ATTENTION: Don't use CACAO's internal REG_* defines as they are
+          different to the ones in <ucontext.h>. */
+
+       pv  = NULL;
+       sp  = (u1 *) _mc->gregs[REG_RSP];
+       xpc = (u1 *) _mc->gregs[REG_RIP];
+       ra  = xpc;                          /* return address is equal to xpc     */
+
+       /* This is a patcher. */
+
+       type = EXCEPTION_HARDWARE_PATCHER;
+       val  = 0;
+
+       /* create stackframeinfo */
+
+       stacktrace_create_extern_stackframeinfo(&sfi, pv, sp, ra, xpc);
+
+       /* Handle the type. */
+
+       p = signal_handle(xpc, type, val);
+
+       /* remove stackframeinfo */
+
+       stacktrace_remove_stackframeinfo(&sfi);
+
+       /* set registers */
+
+       if (p != NULL) {
+               _mc->gregs[REG_RAX] = (intptr_t) p;
+               _mc->gregs[REG_R10] = (intptr_t) xpc;                /* REG_ITMP2_XPC */
+               _mc->gregs[REG_RIP] = (intptr_t) asm_handle_exception;
+       }
+}
+
+
 /* md_signal_handler_sigusr1 ***************************************************
 
    Signal handler for suspending threads.
index 037d9e61787cba749d53727ab2102981cec19fe5..6df31c6d80d5b053af4086bf0025e3e4a3928c52 100644 (file)
@@ -41,7 +41,7 @@
 #include "vm/exceptions.h"
 #include "vm/initialize.h"
 
-#include "vm/jit/patcher.h"
+#include "vm/jit/patcher-common.h"
 #include "vm/jit/stacktrace.h"
 
 #include "vmcore/class.h"
 #include "vm/resolve.h"
 
 
-/* patcher_wrapper *************************************************************
+#define PATCH_BACK_ORIGINAL_MCODE \
+    do { \
+        *((uint16_t *) pr->mpc) = (uint16_t) pr->mcode; \
+    } while (0)
 
-   Wrapper for all patchers.  It also creates the stackframe info
-   structure.
 
-   If the return value of the patcher function is false, it gets the
-   exception object, clears the exception pointer and returns the
-   exception.
+/* patcher_patch_code **********************************************************
+
+   Just patches back the original machine code.
 
 *******************************************************************************/
 
-java_object_t *patcher_wrapper(u1 *sp, u1 *pv, u1 *ra)
+void patcher_patch_code(patchref_t *pr)
 {
-       stackframeinfo     sfi;
-       u1                *xpc;
-       java_object_t     *o;
-       functionptr        f;
-       bool               result;
-       java_handle_t     *e;
+       PATCH_BACK_ORIGINAL_MCODE;
+}
+
+
+/* patcher_resolve_classref_to_classinfo ***************************************
+
+   ACONST:
+
+   <patched call position>
+   48 bf a0 f0 92 00 00 00 00 00    mov    $0x92f0a0,%rdi
+
+   MULTIANEWARRAY:
+
+   <patched call position>
+   48 be 30 40 b2 00 00 00 00 00    mov    $0xb24030,%rsi
+   48 89 e2                         mov    %rsp,%rdx
+   48 b8 7c 96 4b 00 00 00 00 00    mov    $0x4b967c,%rax
+   48 ff d0                         callq  *%rax
 
-       /* define the patcher function */
+   ARRAYCHECKCAST:
+
+   <patched call position>
+   48 be b8 3f b2 00 00 00 00 00    mov    $0xb23fb8,%rsi
+   48 b8 00 00 00 00 00 00 00 00    mov    $0x0,%rax
+   48 ff d0                         callq  *%rax
+
+*******************************************************************************/
+
+bool patcher_resolve_classref_to_classinfo(patchref_t *pr)
+{
+       constant_classref *cr;
+       intptr_t          *datap;
+       classinfo         *c;
 
-       bool (*patcher_function)(u1 *);
+       cr    = (constant_classref *) pr->ref;
+       datap = (intptr_t *)          pr->datap;
+
+       /* get the classinfo */
+
+       if (!(c = resolve_classref_eager(cr)))
+               return false;
+
+       PATCH_BACK_ORIGINAL_MCODE;
+
+       /* patch the classinfo pointer */
+
+       *datap = (intptr_t) c;
+
+       return true;
+}
+
+
+/* patcher_resolve_classref_to_vftbl *******************************************
+
+   CHECKCAST (class):
+   INSTANCEOF (class):
+
+   <patched call position>
+
+*******************************************************************************/
+
+bool patcher_resolve_classref_to_vftbl(patchref_t *pr)
+{
+       constant_classref *cr;
+       intptr_t          *datap;
+       classinfo         *c;
 
        /* get stuff from the stack */
 
-       xpc = (u1 *)                *((ptrint *) (sp + 5 * 8));
-       o   = (java_object_t *)     *((ptrint *) (sp + 4 * 8));
-       f   = (functionptr)         *((ptrint *) (sp + 0 * 8));
+       cr    = (constant_classref *) pr->ref;
+       datap = (intptr_t *)          pr->datap;
+
+       /* get the fieldinfo */
+
+       if (!(c = resolve_classref_eager(cr)))
+               return false;
 
-       /* calculate and set the new return address */
+       PATCH_BACK_ORIGINAL_MCODE;
 
-       xpc = xpc - PATCHER_CALL_SIZE;
+       /* patch super class' vftbl */
 
-       *((ptrint *) (sp + 5 * 8)) = (ptrint) xpc;
+       *datap = (intptr_t) c->vftbl;
+
+       return true;
+}
 
-       /* cast the passed function to a patcher function */
 
-       patcher_function = (bool (*)(u1 *)) (ptrint) f;
+/* patcher_resolve_classref_to_flags *******************************************
 
-       /* enter a monitor on the patching position */
+   CHECKCAST/INSTANCEOF:
+
+   <patched call position>
+
+*******************************************************************************/
+
+bool patcher_resolve_classref_to_flags(patchref_t *pr)
+{
+       constant_classref *cr;
+       int32_t           *datap;
+       classinfo         *c;
+       uint8_t           *ra;
 
-       PATCHER_MONITORENTER;
+       cr    = (constant_classref *) pr->ref;
+       datap = (int32_t *)           pr->datap;
+       ra    = (uint8_t *)           pr->mpc;
 
-       /* create the stackframeinfo */
+       /* get the fieldinfo */
 
-       /* RA is passed as NULL, but the XPC is correct and can be used in
-          stacktrace_create_extern_stackframeinfo for
-          md_codegen_get_pv_from_pc. */
+       if (!(c = resolve_classref_eager(cr)))
+               return false;
 
-       stacktrace_create_extern_stackframeinfo(&sfi, pv, sp + 6 * 8, xpc, xpc);
+       PATCH_BACK_ORIGINAL_MCODE;
 
-       /* call the proper patcher function */
+       /* if we show disassembly, we have to skip the nop's */
 
-       result = (patcher_function)(sp);
+       if (opt_shownops)
+               ra = ra + PATCHER_CALL_SIZE;
 
-       /* remove the stackframeinfo */
+       /* patch class flags */
 
-       stacktrace_remove_stackframeinfo(&sfi);
+/*     *datap = c->flags; */
+       *((int32_t *) (ra + 2)) = c->flags;
 
-       /* check for return value and exit accordingly */
+       return true;
+}
 
-       if (result == false) {
-               e = exceptions_get_and_clear_exception();
 
-               PATCHER_MONITOREXIT;
+/* patcher_resolve_native_function *********************************************
 
-               return e;
-       }
+   XXX
 
-       PATCHER_MARK_PATCHED_MONITOREXIT;
+*******************************************************************************/
 
-       return NULL;
+bool patcher_resolve_native_function(patchref_t *pr)
+{
+       methodinfo  *m;
+       intptr_t    *datap;
+       functionptr  f;
+
+       m     = (methodinfo *) pr->ref;
+       datap = (intptr_t *)   pr->datap;
+
+       /* resolve native function */
+
+       if (!(f = native_resolve_function(m)))
+               return false;
+
+       PATCH_BACK_ORIGINAL_MCODE;
+
+       /* patch native function pointer */
+
+       *datap = (intptr_t) f;
+
+       return true;
 }
 
 
@@ -137,20 +232,14 @@ java_object_t *patcher_wrapper(u1 *sp, u1 *pv, u1 *ra)
 
 *******************************************************************************/
 
-bool patcher_get_putstatic(u1 *sp)
+bool patcher_get_putstatic(patchref_t *pr)
 {
-       u1               *ra;
-       u8                mcode;
        unresolved_field *uf;
-       s4                disp;
+       intptr_t         *datap;
        fieldinfo        *fi;
 
-       /* get stuff from the stack */
-
-       ra    = (u1 *)               *((ptrint *) (sp + 5 * 8));
-       mcode =                      *((u8 *)     (sp + 3 * 8));
-       uf    = (unresolved_field *) *((ptrint *) (sp + 2 * 8));
-       disp  =                      *((s4 *)     (sp + 1 * 8));
+       uf    = (unresolved_field *) pr->ref;
+       datap = (intptr_t *)         pr->datap;
 
        /* get the fieldinfo */
 
@@ -163,18 +252,11 @@ bool patcher_get_putstatic(u1 *sp)
                if (!initialize_class(fi->class))
                        return false;
 
-       /* patch back original code */
-
-       *((u8 *) ra) = mcode;
-
-       /* if we show disassembly, we have to skip the nop's */
-
-       if (opt_shownops)
-               ra = ra + 5;
+       PATCH_BACK_ORIGINAL_MCODE;
 
        /* patch the field value's address */
 
-       *((intptr_t *) (ra + 7 + disp)) = (intptr_t) fi->value;
+       *datap = (intptr_t) fi->value;
 
        return true;
 }
@@ -189,40 +271,33 @@ bool patcher_get_putstatic(u1 *sp)
 
 *******************************************************************************/
 
-bool patcher_get_putfield(u1 *sp)
+bool patcher_get_putfield(patchref_t *pr)
 {
-       u1               *ra;
-       u8                mcode;
+       uint8_t          *ra;
        unresolved_field *uf;
        fieldinfo        *fi;
-       u1                byte;
+       uint8_t           byte;
 
-       /* get stuff from the stack */
-
-       ra    = (u1 *)               *((ptrint *) (sp + 5 * 8));
-       mcode =                      *((u8 *)     (sp + 3 * 8));
-       uf    = (unresolved_field *) *((ptrint *) (sp + 2 * 8));
+       ra = (uint8_t *)          pr->mpc;
+       uf = (unresolved_field *) pr->ref;
 
        /* get the fieldinfo */
 
        if (!(fi = resolve_field_eager(uf)))
                return false;
 
-       /* patch back original code (instruction code is smaller than 8 bytes) */
-
-       *((u4 *) (ra + 0)) = (u4) mcode;
-       *((u1 *) (ra + 4)) = (u1) (mcode >> 32);
+       PATCH_BACK_ORIGINAL_MCODE;
 
        /* if we show disassembly, we have to skip the nop's */
 
        if (opt_shownops)
-               ra = ra + 5;
+               ra = ra + PATCHER_CALL_SIZE;
 
-       /* patch the field's offset: we check for the field type, because the     */
-       /* instructions have different lengths                                    */
+       /* Patch the field's offset: we check for the field type, because
+          the instructions have different lengths. */
 
        if (IS_INT_LNG_TYPE(fi->type)) {
-               /* check for special case: %rsp or %r12 as base register */
+               /* Check for special case: %rsp or %r12 as base register. */
 
                byte = *(ra + 3);
 
@@ -232,7 +307,7 @@ bool patcher_get_putfield(u1 *sp)
                        *((int32_t *) (ra + 3)) = fi->offset;
        }
        else {
-               /* check for special case: %rsp or %r12 as base register */
+               /* Check for special case: %rsp or %r12 as base register. */
 
                byte = *(ra + 5);
 
@@ -255,39 +330,36 @@ bool patcher_get_putfield(u1 *sp)
 
 *******************************************************************************/
 
-bool patcher_putfieldconst(u1 *sp)
+bool patcher_putfieldconst(patchref_t *pr)
 {
-       u1               *ra;
-       u8                mcode;
+       uint8_t          *ra;
        unresolved_field *uf;
        fieldinfo        *fi;
+       uint8_t           byte;
 
-       /* get stuff from the stack */
-
-       ra    = (u1 *)               *((ptrint *) (sp + 5 * 8));
-       mcode =                      *((u8 *)     (sp + 3 * 8));
-       uf    = (unresolved_field *) *((ptrint *) (sp + 2 * 8));
+       ra = (uint8_t *)          pr->mpc;
+       uf = (unresolved_field *) pr->ref;
 
        /* get the fieldinfo */
 
        if (!(fi = resolve_field_eager(uf)))
                return false;
 
-       /* patch back original code */
-
-       *((u8 *) ra) = mcode;
+       PATCH_BACK_ORIGINAL_MCODE;
 
        /* if we show disassembly, we have to skip the nop's */
 
        if (opt_shownops)
-               ra = ra + 5;
+               ra = ra + PATCHER_CALL_SIZE;
 
        /* patch the field's offset */
 
        if (IS_2_WORD_TYPE(fi->type) || IS_ADR_TYPE(fi->type)) {
                /* handle special case when the base register is %r12 */
 
-               if (*(ra + 2) == 0x84) {
+               byte = *(ra + 2);
+
+               if (byte == 0x84) {
                        *((uint32_t *) (ra + 4))      = fi->offset;
                        *((uint32_t *) (ra + 12 + 4)) = fi->offset + 4;
                }
@@ -299,7 +371,9 @@ bool patcher_putfieldconst(u1 *sp)
        else {
                /* handle special case when the base register is %r12 */
 
-               if (*(ra + 2) == 0x84)
+               byte = *(ra + 2);
+
+               if (byte == 0x84)
                        *((uint32_t *) (ra + 4)) = fi->offset;
                else
                        *((uint32_t *) (ra + 3)) = fi->offset;
@@ -309,144 +383,6 @@ bool patcher_putfieldconst(u1 *sp)
 }
 
 
-/* patcher_aconst **************************************************************
-
-   Machine code:
-
-   <patched call position>
-   48 bf a0 f0 92 00 00 00 00 00    mov    $0x92f0a0,%rdi
-
-*******************************************************************************/
-
-bool patcher_aconst(u1 *sp)
-{
-       u1                *ra;
-       u8                 mcode;
-       constant_classref *cr;
-       classinfo         *c;
-
-       /* get stuff from the stack */
-
-       ra    = (u1 *)                *((ptrint *) (sp + 5 * 8));
-       mcode =                       *((u8 *)     (sp + 3 * 8));
-       cr    = (constant_classref *) *((ptrint *) (sp + 2 * 8));
-
-       /* get the classinfo */
-
-       if (!(c = resolve_classref_eager(cr)))
-               return false;
-
-       /* patch back original code */
-
-       *((u8 *) ra) = mcode;
-
-       /* if we show disassembly, we have to skip the nop's */
-
-       if (opt_shownops)
-               ra = ra + 5;
-
-       /* patch the classinfo pointer */
-
-       *((ptrint *) (ra + 2)) = (ptrint) c;
-
-       return true;
-}
-
-
-/* patcher_builtin_multianewarray **********************************************
-
-   Machine code:
-
-   <patched call position>
-   48 bf 02 00 00 00 00 00 00 00    mov    $0x2,%rdi
-   48 be 30 40 b2 00 00 00 00 00    mov    $0xb24030,%rsi
-   48 89 e2                         mov    %rsp,%rdx
-   48 b8 7c 96 4b 00 00 00 00 00    mov    $0x4b967c,%rax
-   48 ff d0                         callq  *%rax
-
-*******************************************************************************/
-
-bool patcher_builtin_multianewarray(u1 *sp)
-{
-       u1                *ra;
-       u8                 mcode;
-       constant_classref *cr;
-       classinfo         *c;
-
-       /* get stuff from the stack */
-
-       ra    = (u1 *)                *((ptrint *) (sp + 5 * 8));
-       mcode =                       *((u8 *)     (sp + 3 * 8));
-       cr    = (constant_classref *) *((ptrint *) (sp + 2 * 8));
-
-       /* get the classinfo */
-
-       if (!(c = resolve_classref_eager(cr)))
-               return false;
-
-       /* patch back original code */
-
-       *((u8 *) ra) = mcode;
-
-       /* if we show disassembly, we have to skip the nop's */
-
-       if (opt_shownops)
-               ra = ra + 5;
-
-       /* patch the classinfo pointer */
-
-       *((ptrint *) (ra + 10 + 2)) = (ptrint) c;
-
-       return true;
-}
-
-
-/* patcher_builtin_arraycheckcast **********************************************
-
-   Machine code:
-
-   <patched call position>
-   48 be b8 3f b2 00 00 00 00 00    mov    $0xb23fb8,%rsi
-   48 b8 00 00 00 00 00 00 00 00    mov    $0x0,%rax
-   48 ff d0                         callq  *%rax
-
-*******************************************************************************/
-
-bool patcher_builtin_arraycheckcast(u1 *sp)
-{
-       u1                *ra;
-       u8                 mcode;
-       constant_classref *cr;
-       classinfo         *c;
-
-       /* get stuff from the stack */
-
-       ra    = (u1 *)                *((ptrint *) (sp + 5 * 8));
-       mcode =                       *((u8 *)     (sp + 3 * 8));
-       cr    = (constant_classref *) *((ptrint *) (sp + 2 * 8));
-
-       /* get the classinfo */
-
-       if (!(c = resolve_classref_eager(cr)))
-               return false;
-
-       /* patch back original code */
-
-       *((u8 *) ra) = mcode;
-
-       /* if we show disassembly, we have to skip the nop's */
-
-       if (opt_shownops)
-               ra = ra + 5;
-
-       /* patch the classinfo pointer */
-
-       *((ptrint *) (ra + 2)) = (ptrint) c;
-
-       return true;
-}
-
-
 /* patcher_invokestatic_special ************************************************
 
    Machine code:
@@ -457,39 +393,27 @@ bool patcher_builtin_arraycheckcast(u1 *sp)
 
 *******************************************************************************/
 
-bool patcher_invokestatic_special(u1 *sp)
+bool patcher_invokestatic_special(patchref_t *pr)
 {
-       u1                *ra;
-       u8                 mcode;
        unresolved_method *um;
-       s4                 disp;
+       intptr_t          *datap;
        methodinfo        *m;
 
        /* get stuff from the stack */
 
-       ra    = (u1 *)                *((ptrint *) (sp + 5 * 8));
-       mcode =                       *((u8 *)     (sp + 3 * 8));
-       um    = (unresolved_method *) *((ptrint *) (sp + 2 * 8));
-       disp  =                       *((s4 *)     (sp + 1 * 8));
+       um    = (unresolved_method *) pr->ref;
+       datap = (intptr_t *)          pr->datap;
 
        /* get the fieldinfo */
 
        if (!(m = resolve_method_eager(um)))
                return false;
 
-       /* patch back original code */
-
-       *((u8 *) ra) = mcode;
-
-       /* if we show disassembly, we have to skip the nop's */
-
-       if (opt_shownops)
-               ra = ra + PATCHER_CALL_SIZE;
+       PATCH_BACK_ORIGINAL_MCODE;
 
        /* patch stubroutine */
 
-/*     *((ptrint *) (ra + 2)) = (ptrint) m->stubroutine; */
-       *((ptrint *) (ra + 7 + disp)) = (ptrint) m->stubroutine;
+       *datap = (intptr_t) m->stubroutine;
 
        return true;
 }
@@ -506,37 +430,32 @@ bool patcher_invokestatic_special(u1 *sp)
 
 *******************************************************************************/
 
-bool patcher_invokevirtual(u1 *sp)
+bool patcher_invokevirtual(patchref_t *pr)
 {
-       u1                *ra;
-       u8                 mcode;
+       uint8_t           *ra;
        unresolved_method *um;
        methodinfo        *m;
 
-       /* get stuff from the stack */
+       ra = (uint8_t *)           pr->mpc;
+       um = (unresolved_method *) pr->ref;
 
-       ra    = (u1 *)                *((ptrint *) (sp + 5 * 8));
-       mcode =                       *((u8 *)     (sp + 3 * 8));
-       um    = (unresolved_method *) *((ptrint *) (sp + 2 * 8));
-
-       /* get the fieldinfo */
+       /* get the methodinfo */
 
        if (!(m = resolve_method_eager(um)))
                return false;
 
-       /* patch back original code */
-
-       *((u8 *) ra) = mcode;
+       PATCH_BACK_ORIGINAL_MCODE;
 
        /* if we show disassembly, we have to skip the nop's */
 
        if (opt_shownops)
-               ra = ra + 5;
+               ra = ra + PATCHER_CALL_SIZE;
 
        /* patch vftbl index */
 
-       *((s4 *) (ra + 3 + 3)) = (s4) (OFFSET(vftbl_t, table[0]) +
-                                                                  sizeof(methodptr) * m->vftblindex);
+       *((int32_t *) (ra + 3 + 3)) =
+               (int32_t) (OFFSET(vftbl_t, table[0]) +
+                                  sizeof(methodptr) * m->vftblindex);
 
        return true;
 }
@@ -554,88 +473,39 @@ bool patcher_invokevirtual(u1 *sp)
 
 *******************************************************************************/
 
-bool patcher_invokeinterface(u1 *sp)
+bool patcher_invokeinterface(patchref_t *pr)
 {
-       u1                *ra;
-       u8                 mcode;
+       uint8_t           *ra;
        unresolved_method *um;
        methodinfo        *m;
 
        /* get stuff from the stack */
 
-       ra    = (u1 *)                *((ptrint *) (sp + 5 * 8));
-       mcode =                       *((u8 *)     (sp + 3 * 8));
-       um    = (unresolved_method *) *((ptrint *) (sp + 2 * 8));
+       ra = (uint8_t *)           pr->mpc;
+       um = (unresolved_method *) pr->ref;
 
        /* get the fieldinfo */
 
        if (!(m = resolve_method_eager(um)))
                return false;
 
-       /* patch back original code */
-
-       *((u8 *) ra) = mcode;
+       PATCH_BACK_ORIGINAL_MCODE;
 
        /* if we show disassembly, we have to skip the nop's */
 
        if (opt_shownops)
-               ra = ra + 5;
+               ra = ra + PATCHER_CALL_SIZE;
 
        /* patch interfacetable index */
 
-       *((s4 *) (ra + 3 + 3)) = (s4) (OFFSET(vftbl_t, interfacetable[0]) -
-                                                                  sizeof(methodptr) * m->class->index);
+       *((int32_t *) (ra + 3 + 3)) =
+               (int32_t) (OFFSET(vftbl_t, interfacetable[0]) -
+                                  sizeof(methodptr) * m->class->index);
 
        /* patch method offset */
 
-       *((s4 *) (ra + 3 + 7 + 3)) =
-               (s4) (sizeof(methodptr) * (m - m->class->methods));
-
-       return true;
-}
-
-
-/* patcher_checkcast_instanceof_flags ******************************************
-
-   Machine code:
-
-   <patched call position>
-   41 ba 00 00 00 00                mov    $0x0,%r10d
-   41 81 e2 00 02 00 00             and    $0x200,%r10d
-   0f 84 35 00 00 00                je     0x00002aaaaab01479
-
-*******************************************************************************/
-
-bool patcher_checkcast_instanceof_flags(u1 *sp)
-{
-       u1                *ra;
-       u8                 mcode;
-       constant_classref *cr;
-       classinfo         *c;
-
-       /* get stuff from the stack */
-
-       ra    = (u1 *)                *((ptrint *) (sp + 5 * 8));
-       mcode =                       *((u8 *)     (sp + 3 * 8));
-       cr    = (constant_classref *) *((ptrint *) (sp + 2 * 8));
-
-       /* get the fieldinfo */
-
-       if (!(c = resolve_classref_eager(cr)))
-               return false;
-
-       /* patch back original code */
-
-       *((u8 *) ra) = mcode;
-
-       /* if we show disassembly, we have to skip the nop's */
-
-       if (opt_shownops)
-               ra = ra + 5;
-
-       /* patch class flags */
-
-       *((s4 *) (ra + 2)) = (s4) c->flags;
+       *((int32_t *) (ra + 3 + 7 + 3)) =
+               (int32_t) (sizeof(methodptr) * (m - m->class->methods));
 
        return true;
 }
@@ -654,27 +524,21 @@ bool patcher_checkcast_instanceof_flags(u1 *sp)
 
 *******************************************************************************/
 
-bool patcher_checkcast_interface(u1 *sp)
+bool patcher_checkcast_interface(patchref_t *pr)
 {
-       u1                *ra;
-       u8                 mcode;
+       uint8_t           *ra;
        constant_classref *cr;
        classinfo         *c;
 
-       /* get stuff from the stack */
-
-       ra    = (u1 *)                *((ptrint *) (sp + 5 * 8));
-       mcode =                       *((u8 *)     (sp + 3 * 8));
-       cr    = (constant_classref *) *((ptrint *) (sp + 2 * 8));
+       ra = (uint8_t *)           pr->mpc;
+       cr = (constant_classref *) pr->ref;
 
        /* get the fieldinfo */
 
        if (!(c = resolve_classref_eager(cr)))
                return false;
 
-       /* patch back original code */
-
-       *((u8 *) ra) = mcode;
+       PATCH_BACK_ORIGINAL_MCODE;
 
        /* if we show disassembly, we have to skip the nop's */
 
@@ -683,60 +547,11 @@ bool patcher_checkcast_interface(u1 *sp)
 
        /* patch super class index */
 
-       *((s4 *) (ra + 7 + 3)) = (s4) c->index;
+       *((int32_t *) (ra + 7 + 3)) = c->index;
 
-       *((s4 *) (ra + 7 + 7 + 6 + 8 + 3)) =
-               (s4) (OFFSET(vftbl_t, interfacetable[0]) -
-                         c->index * sizeof(methodptr*));
-
-       return true;
-}
-
-
-/* patcher_checkcast_class *****************************************************
-
-   Machine code:
-
-   <patched call position>
-   49 bb 00 00 00 00 00 00 00 00    mov    $0x0,%r11
-   45 8b 92 20 00 00 00             mov    0x20(%r10),%r10d
-   45 8b 9b 20 00 00 00             mov    0x20(%r11),%r11d
-   4d 29 da                         sub    %r11,%r10
-   49 bb 00 00 00 00 00 00 00 00    mov    $0x0,%r11
-
-*******************************************************************************/
-
-bool patcher_checkcast_class(u1 *sp)
-{
-       u1                *ra;
-       u8                 mcode;
-       constant_classref *cr;
-       classinfo         *c;
-
-       /* get stuff from the stack */
-
-       ra    = (u1 *)                *((ptrint *) (sp + 5 * 8));
-       mcode =                       *((u8 *)     (sp + 3 * 8));
-       cr    = (constant_classref *) *((ptrint *) (sp + 2 * 8));
-
-       /* get the fieldinfo */
-
-       if (!(c = resolve_classref_eager(cr)))
-               return false;
-
-       /* patch back original code */
-
-       *((u8 *) ra) = mcode;
-
-       /* if we show disassembly, we have to skip the nop's */
-
-       if (opt_shownops)
-               ra = ra + 5;
-
-       /* patch super class' vftbl */
-
-       *((ptrint *) (ra + 2)) = (ptrint) c->vftbl;
-       *((ptrint *) (ra + 10 + 7 + 7 + 3 + 2)) = (ptrint) c->vftbl;
+       *((int32_t *) (ra + 7 + 7 + 6 + 8 + 3)) =
+               (int32_t) (OFFSET(vftbl_t, interfacetable[0]) -
+                                  c->index * sizeof(methodptr*));
 
        return true;
 }
@@ -754,27 +569,21 @@ bool patcher_checkcast_class(u1 *sp)
 
 *******************************************************************************/
 
-bool patcher_instanceof_interface(u1 *sp)
+bool patcher_instanceof_interface(patchref_t *pr)
 {
-       u1                *ra;
-       u8                 mcode;
+       uint8_t           *ra;
        constant_classref *cr;
        classinfo         *c;
 
-       /* get stuff from the stack */
-
-       ra    = (u1 *)                *((ptrint *) (sp + 5 * 8));
-       mcode =                       *((u8 *)     (sp + 3 * 8));
-       cr    = (constant_classref *) *((ptrint *) (sp + 2 * 8));
+       ra = (uint8_t *)           pr->mpc;
+       cr = (constant_classref *) pr->ref;
 
        /* get the fieldinfo */
 
        if (!(c = resolve_classref_eager(cr)))
                return false;
 
-       /* patch back original code */
-
-       *((u8 *) ra) = mcode;
+       PATCH_BACK_ORIGINAL_MCODE;
 
        /* if we show disassembly, we have to skip the nop's */
 
@@ -783,173 +592,11 @@ bool patcher_instanceof_interface(u1 *sp)
 
        /* patch super class index */
 
-       *((s4 *) (ra + 7 + 3)) = (s4) c->index;
-
-       *((s4 *) (ra + 7 + 7 + 6 + 3)) =
-               (s4) (OFFSET(vftbl_t, interfacetable[0]) -
-                         c->index * sizeof(methodptr*));
-
-       return true;
-}
-
-
-/* patcher_instanceof_class ****************************************************
-
-   Machine code:
-
-   <patched call position>
-   49 ba 00 00 00 00 00 00 00 00    mov    $0x0,%r10
-
-*******************************************************************************/
-
-bool patcher_instanceof_class(u1 *sp)
-{
-       u1                *ra;
-       u8                 mcode;
-       constant_classref *cr;
-       classinfo         *c;
-
-       /* get stuff from the stack */
-
-       ra    = (u1 *)                *((ptrint *) (sp + 5 * 8));
-       mcode =                       *((u8 *)     (sp + 3 * 8));
-       cr    = (constant_classref *) *((ptrint *) (sp + 2 * 8));
-
-       /* get the fieldinfo */
-
-       if (!(c = resolve_classref_eager(cr)))
-               return false;
-
-       /* patch back original code */
-
-       *((u8 *) ra) = mcode;
-
-       /* if we show disassembly, we have to skip the nop's */
-
-       if (opt_shownops)
-               ra = ra + 5;
-
-       /* patch super class' vftbl */
-
-       *((ptrint *) (ra + 2)) = (ptrint) c->vftbl;
-
-       return true;
-}
-
-
-/* patcher_clinit **************************************************************
-
-   May be used for GET/PUTSTATIC and in native stub.
-
-   Machine code:
-
-   <patched call position>
-   4d 8b 15 92 ff ff ff             mov    -110(%rip),%r10
-   49 89 1a                         mov    %rbx,(%r10)
-
-*******************************************************************************/
-
-bool patcher_clinit(u1 *sp)
-{
-       u1        *ra;
-       u8         mcode;
-       classinfo *c;
-
-       /* get stuff from the stack */
-
-       ra    = (u1 *)        *((ptrint *) (sp + 5 * 8));
-       mcode =               *((u8 *)     (sp + 3 * 8));
-       c     = (classinfo *) *((ptrint *) (sp + 2 * 8));
-
-       /* check if the class is initialized */
-
-       if (!(c->state & CLASS_INITIALIZED))
-               if (!initialize_class(c))
-                       return false;
-
-       /* patch back original code */
-
-       *((u8 *) ra) = mcode;
-
-       return true;
-}
-
-
-/* patcher_athrow_areturn ******************************************************
-
-   Machine code:
-
-   <patched call position>
-
-*******************************************************************************/
-
-#ifdef ENABLE_VERIFIER
-bool patcher_athrow_areturn(u1 *sp)
-{
-       u1               *ra;
-       u8                mcode;
-       unresolved_class *uc;
-
-       /* get stuff from the stack */
-
-       ra    = (u1 *)               *((ptrint *) (sp + 5 * 8));
-       mcode =                      *((u8 *)     (sp + 3 * 8));
-       uc    = (unresolved_class *) *((ptrint *) (sp + 2 * 8));
-
-       /* resolve the class and check subtype constraints */
-
-       if (!resolve_class_eager_no_access_check(uc))
-               return false;
-
-       /* patch back original code */
-
-       *((u8 *) ra) = mcode;
-
-       return true;
-}
-#endif /* ENABLE_VERIFIER */
-
-
-/* patcher_resolve_native ******************************************************
-
-   Machine code:
-
-   <patched call position>
-   48 b8 00 00 00 00 00 00 00 00    mov    $0x0,%rax
-   48 ff d0                         callq  *%rax
-
-*******************************************************************************/
-
-bool patcher_resolve_native(u1 *sp)
-{
-       u1          *ra;
-       u8           mcode;
-       methodinfo  *m;
-       functionptr  f;
-
-       /* get stuff from the stack */
-
-       ra    = (u1 *)         *((ptrint *) (sp + 5 * 8));
-       mcode =                *((u8 *)     (sp + 3 * 8));
-       m     = (methodinfo *) *((ptrint *) (sp + 2 * 8));
-
-       /* resolve native function */
-
-       if (!(f = native_resolve_function(m)))
-               return false;
-
-       /* patch back original code */
-
-       *((u8 *) ra) = mcode;
-
-       /* if we show disassembly, we have to skip the nop's */
-
-       if (opt_shownops)
-               ra = ra + 5;
-
-       /* patch native function pointer */
+       *((int32_t *) (ra + 7 + 3)) = c->index;
 
-       *((ptrint *) (ra + 2)) = (ptrint) f;
+       *((int32_t *) (ra + 7 + 7 + 6 + 3)) =
+               (int32_t) (OFFSET(vftbl_t, interfacetable[0]) -
+                                  c->index * sizeof(methodptr*));
 
        return true;
 }
index eaee45f286e0ed5f24db22186aea90cf828fb3e7..55010dbf2544d8f765e83172739c634cead28918 100644 (file)
@@ -145,7 +145,7 @@ bool signal_init(void)
                                                           SA_NODEFER | SA_SIGINFO);
 #  endif
 
-#  if defined(__ARM__) || defined(__I386__) || defined(__S390__)
+#  if defined(__ARM__) || defined(__I386__) || defined(__S390__) || defined(__X86_64__)
                /* XXX use better defines for that (in arch.h) */
                /* SIGILL handler */
 
index 6ddcde0eddef52786af8f868ee07d1fcdaf260c1..0edca83552b160189d76dad2838f9b862a094e44 100644 (file)
@@ -51,7 +51,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__) || defined(__I386__) || defined(__S390__)
+#if defined(__ARM__) || defined(__I386__) || defined(__S390__) || defined(__X86_64__)
 /* XXX use better defines for that (in arch.h) */
 void md_signal_handler_sigill(int sig, siginfo_t *siginfo, void *_p);
 #endif