* src/vm/jit/powerpc64/emit.c (emit_trap): Use M_ILLEGAL.
* src/vm/jit/powerpc64/linux/md-os.c (md_signal_handler_sigill): New
function.
* src/vm/jit/powerpc64/md-trap.h: Use a lage number for TRAP_PATCHER.
* src/vm/signal.c (signal_init) [__POWERPC64__]: Register
md_signal_handler_sigill.
* src/vm/signallocal.h (md_signal_handler_sigill) [__POWERPC64__]:
Added defined.
/* instruction macros *********************************************************/
-#define M_IADD(a,b,c) M_LADD(a,b,c)
+#define M_ILLEGAL M_OP3(0, 0, 0, 0, 0, 0, 0)
+#define M_IADD(a,b,c) M_LADD(a,b,c)
#define M_LADD(a,b,c) M_OP3(31, 266, 0, 0, c, a, b)
#define M_IADD_IMM(a,b,c) M_OP2_IMM(14, c, a, b) /* XXX */
#define M_LADD_IMM(a,b,c) M_OP2_IMM(14, c, a, b)
uint32_t emit_trap(codegendata *cd)
{
- uint32_t mcode;
+ // Get machine code which is patched back in later. The trap is 1
+ // instruction word long.
+ uint32_t mcode = *((uint32_t*) cd->mcodeptr);
- /* Get machine code which is patched back in later. The
- trap is 1 instruction word long. */
-
- mcode = *((uint32_t *) cd->mcodeptr);
-
- /* ALD is 4 byte aligned, ILD 2, only LWZ is byte aligned */
- M_LWZ(REG_ZERO, REG_ZERO, TRAP_PATCHER);
+ M_ILLEGAL;
return mcode;
}
}
+/**
+ * Signal handler for patcher calls.
+ */
+void md_signal_handler_sigill(int sig, siginfo_t* siginfo, void* _p)
+{
+ ucontext_t* _uc = (ucontext_t*) _p;
+ mcontext_t* _mc = &(_uc->uc_mcontext);
+
+ /* get register values */
+
+ void* pv = (void*) _mc->gp_regs[REG_PV];
+ void* sp = (void*) _mc->gp_regs[REG_SP];
+ void* ra = (void*) _mc->gp_regs[PT_LNK]; // The RA is correct for leag methods.
+ void* xpc =(void*) _mc->gp_regs[PT_NIP];
+
+ // Get the illegal-instruction.
+ uint32_t mcode = *((uint32_t*) xpc);
+
+ // This signal is always a patcher.
+ int type = TRAP_PATCHER;
+ intptr_t val = 0;
+
+ // Handle the trap.
+ void* p = trap_handle(type, val, pv, sp, ra, xpc, _p);
+
+ // Set registers if we have an exception, continue execution
+ // otherwise.
+ if (p != NULL) {
+ _mc->gp_regs[REG_ITMP1_XPTR] = (uintptr_t) p;
+ _mc->gp_regs[REG_ITMP2_XPC] = (uintptr_t) xpc;
+ _mc->gp_regs[PT_NIP] = (uintptr_t) asm_handle_exception;
+ }
+}
+
+
/* md_signal_handler_sigusr2 ***************************************************
Signal handler for profiling sampling.
TRAP_ClassCastException = 5,
TRAP_CHECK_EXCEPTION = 6,
- TRAP_PATCHER = 7,
+ TRAP_COMPILER = 7,
/* Don't use 8 (could be a normal load offset). */
- TRAP_COMPILER = 9,
- TRAP_COUNTDOWN = 10,
- TRAP_END
+ TRAP_COUNTDOWN = 9,
+ TRAP_END,
+
+ // This handled via SIGILL.
+ TRAP_PATCHER = 99 // A large number.
};
#endif /* _MD_TRAP_H */
SA_NODEFER | SA_SIGINFO);
# endif
-# if defined(__ALPHA__) || defined(__ARM__) || defined(__I386__) || defined(__S390__) || defined(__X86_64__) || defined(__M68K__)
+# if defined(__ALPHA__) || defined(__ARM__) || defined(__I386__) || defined(__POWERPC64__) || defined(__S390__) || defined(__X86_64__) || defined(__M68K__)
/* XXX use better defines for that (in arch.h) */
/* SIGILL handler */
void md_signal_handler_sigfpe(int sig, siginfo_t *siginfo, void *_p);
#endif
-#if defined(__ALPHA__) || defined(__ARM__) || defined(__I386__) || defined(__S390__) || defined(__X86_64__) || defined(__M68K__)
+#if defined(__ALPHA__) || defined(__ARM__) || defined(__I386__) || defined(__POWERPC64__) || defined(__S390__) || defined(__X86_64__) || defined(__M68K__)
/* XXX use better defines for that (in arch.h) */
void md_signal_handler_sigill(int sig, siginfo_t *siginfo, void *_p);
#endif