Example #1
0
void
mono_arm_throw_exception (MonoObject *exc, mgreg_t pc, mgreg_t sp, mgreg_t *int_regs, gdouble *fp_regs)
{
	MonoError error;
	MonoContext ctx;
	gboolean rethrow = sp & 1;

	sp &= ~1; /* clear the optional rethrow bit */
	pc &= ~1; /* clear the thumb bit */
	/* adjust eip so that it point into the call instruction */
	pc -= 4;

	/*printf ("stack in throw: %p\n", esp);*/
	MONO_CONTEXT_SET_BP (&ctx, int_regs [ARMREG_FP - 4]);
	MONO_CONTEXT_SET_SP (&ctx, sp);
	MONO_CONTEXT_SET_IP (&ctx, pc);
	memcpy (((guint8*)&ctx.regs) + (ARMREG_R4 * sizeof (mgreg_t)), int_regs, 8 * sizeof (mgreg_t));
	memcpy (&ctx.fregs, fp_regs, sizeof (double) * 16);

	if (mono_object_isinst_checked (exc, mono_defaults.exception_class, &error)) {
		MonoException *mono_ex = (MonoException*)exc;
		if (!rethrow) {
			mono_ex->stack_trace = NULL;
			mono_ex->trace_ips = NULL;
		}
	}
	mono_error_assert_ok (&error);
	mono_handle_exception (&ctx, exc);
	mono_restore_context (&ctx);
	g_assert_not_reached ();
}
Example #2
0
void
mono_ppc_throw_exception (MonoObject *exc, unsigned long eip, unsigned long esp, mgreg_t *int_regs, gdouble *fp_regs, gboolean rethrow)
{
	MonoError error;
	MonoContext ctx;

	/* adjust eip so that it point into the call instruction */
	eip -= 4;

	setup_context (&ctx);

	/*printf ("stack in throw: %p\n", esp);*/
	MONO_CONTEXT_SET_BP (&ctx, esp);
	MONO_CONTEXT_SET_IP (&ctx, eip);
	memcpy (&ctx.regs, int_regs, sizeof (mgreg_t) * MONO_MAX_IREGS);
	memcpy (&ctx.fregs, fp_regs, sizeof (double) * MONO_MAX_FREGS);

	if (mono_object_isinst_checked (exc, mono_defaults.exception_class, &error)) {
		MonoException *mono_ex = (MonoException*)exc;
		if (!rethrow) {
			mono_ex->stack_trace = NULL;
			mono_ex->trace_ips = NULL;
		}
	}
	mono_error_assert_ok (&error);
	mono_handle_exception (&ctx, exc);
	mono_restore_context (&ctx);

	g_assert_not_reached ();
}
Example #3
0
static void
throw_exception (MonoObject *exc, gpointer sp, gpointer ip, gboolean rethrow, gboolean preserve_ips)
{
	ERROR_DECL (error);
	MonoContext ctx;
	static void (*restore_context) (MonoContext *);
	gpointer *window;
	
	if (!restore_context)
		restore_context = mono_get_restore_context ();

	window = MONO_SPARC_WINDOW_ADDR (sp);
	ctx.sp = (gpointer*)sp;
	ctx.ip = ip;
	ctx.fp = (gpointer*)(MONO_SPARC_WINDOW_ADDR (sp) [sparc_i6 - 16]);

	if (mono_object_isinst_checked (exc, mono_defaults.exception_class, error)) {
		MonoException *mono_ex = (MonoException*)exc;
		if (!rethrow) {
			mono_ex->stack_trace = NULL;
			mono_ex->trace_ips = NULL;
		} else (preserve_ips) {
			mono_ex->caught_in_unmanaged = NULL;
		}
	}
Example #4
0
/* 
 * The first few arguments are dummy, to force the other arguments to be passed on
 * the stack, this avoids overwriting the argument registers in the throw trampoline.
 */
void
mono_amd64_throw_exception (guint64 dummy1, guint64 dummy2, guint64 dummy3, guint64 dummy4,
							guint64 dummy5, guint64 dummy6,
							MonoContext *mctx, MonoObject *exc, gboolean rethrow)
{
	MonoError error;
	MonoContext ctx;

	/* mctx is on the caller's stack */
	memcpy (&ctx, mctx, sizeof (MonoContext));

	if (mono_object_isinst_checked (exc, mono_defaults.exception_class, &error)) {
		MonoException *mono_ex = (MonoException*)exc;
		if (!rethrow) {
			mono_ex->stack_trace = NULL;
			mono_ex->trace_ips = NULL;
		}
	}
	mono_error_assert_ok (&error);

	/* adjust eip so that it point into the call instruction */
	ctx.gregs [AMD64_RIP] --;

	mono_handle_exception (&ctx, exc);
	mono_restore_context (&ctx);
	g_assert_not_reached ();
}
Example #5
0
static void
throw_exception (MonoObject *exc, unsigned long eip, unsigned long esp, gboolean rethrow, gboolean preserve_ips)
{
	ERROR_DECL (error);
	MonoContext ctx;

#ifdef DEBUG_EXCEPTIONS
	g_print ("throw_exception: exc=%p eip=%p esp=%p rethrow=%d\n",
		 exc, (void *)eip, (void *) esp, rethrow);
#endif

	/* adjust eip so that it point into the call instruction */
	eip -= 8;

	memset (&ctx, 0, sizeof (MonoContext));

	/*g_print  ("stack in throw: %p\n", esp);*/
	memcpy (&ctx.sc_regs, (void *)(esp + MIPS_STACK_PARAM_OFFSET),
		sizeof (gulong) * MONO_SAVED_GREGS);
	memset (&ctx.sc_fpregs, 0, sizeof (mips_freg) * MONO_SAVED_FREGS);
	MONO_CONTEXT_SET_IP (&ctx, eip);

	if (mono_object_isinst_checked (exc, mono_defaults.exception_class, error)) {
		MonoException *mono_ex = (MonoException*)exc;
		if (!rethrow) {
			mono_ex->stack_trace = NULL;
			mono_ex->trace_ips = NULL;
		} if (preserve_ips) {
			mono_ex->caught_in_unmanaged = TRUE;
		}
	}
	mono_error_assert_ok (error);
	mono_handle_exception (&ctx, exc);
#ifdef DEBUG_EXCEPTIONS
	g_print ("throw_exception: restore to pc=%p sp=%p fp=%p ctx=%p\n",
		 (void *) ctx.sc_pc, (void *) ctx.sc_regs[mips_sp],
		 (void *) ctx.sc_regs[mips_fp], &ctx);
#endif
	mono_restore_context (&ctx);

	g_assert_not_reached ();
}
Example #6
0
/*
 * mono_x86_throw_exception:
 *
 *   C function called from the throw trampolines.
 */
void
mono_x86_throw_exception (mgreg_t *regs, MonoObject *exc, 
						  mgreg_t eip, gboolean rethrow)
{
	MonoError error;
	MonoContext ctx;

	ctx.esp = regs [X86_ESP];
	ctx.eip = eip;
	ctx.ebp = regs [X86_EBP];
	ctx.edi = regs [X86_EDI];
	ctx.esi = regs [X86_ESI];
	ctx.ebx = regs [X86_EBX];
	ctx.edx = regs [X86_EDX];
	ctx.ecx = regs [X86_ECX];
	ctx.eax = regs [X86_EAX];

#ifdef __APPLE__
	/* The OSX ABI specifies 16 byte alignment at call sites */
	g_assert ((ctx.esp % MONO_ARCH_FRAME_ALIGNMENT) == 0);
#endif

	if (mono_object_isinst_checked (exc, mono_defaults.exception_class, &error)) {
		MonoException *mono_ex = (MonoException*)exc;
		if (!rethrow) {
			mono_ex->stack_trace = NULL;
			mono_ex->trace_ips = NULL;
		}
	}
	mono_error_assert_ok (&error);

	/* adjust eip so that it point into the call instruction */
	ctx.eip -= 1;

	mono_handle_exception (&ctx, exc);

	mono_restore_context (&ctx);

	g_assert_not_reached ();
}
Example #7
0
/*
 * mono_arm_throw_exception:
 *
 *   This function is called by the exception trampolines.
 * FP_REGS points to the 8 callee saved fp regs.
 */
void
mono_arm_throw_exception (gpointer arg, mgreg_t pc, mgreg_t *int_regs, gdouble *fp_regs, gboolean corlib, gboolean rethrow)
{
    MonoError error;
    MonoContext ctx;
    MonoObject *exc = NULL;
    guint32 ex_token_index, ex_token;

    if (!corlib)
        exc = arg;
    else {
        ex_token_index = (guint64)arg;
        ex_token = MONO_TOKEN_TYPE_DEF | ex_token_index;
        exc = (MonoObject*)mono_exception_from_token (mono_defaults.corlib, ex_token);
    }

    /* Adjust pc so it points into the call instruction */
    pc -= 4;

    /* Initialize a ctx based on the arguments */
    memset (&ctx, 0, sizeof (MonoContext));
    memcpy (&(ctx.regs [0]), int_regs, sizeof (mgreg_t) * 32);
    memcpy (&(ctx.fregs [ARMREG_D8]), fp_regs, sizeof (double) * 8);
    ctx.has_fregs = 1;
    ctx.pc = pc;

    if (mono_object_isinst_checked (exc, mono_defaults.exception_class, &error)) {
        MonoException *mono_ex = (MonoException*)exc;
        if (!rethrow) {
            mono_ex->stack_trace = NULL;
            mono_ex->trace_ips = NULL;
        }
    }
    mono_error_assert_ok (&error);

    mono_handle_exception (&ctx, exc);

    mono_restore_context (&ctx);
}