[Mono-dev] [PATCH]: Fix abort when generating sparc V9 code

David Miller davem at davemloft.net
Fri Nov 2 00:49:41 EDT 2007

In current SVN the testsuite gives an abort on sparc because the JIT
generates a branch whose relocation cannot fit.

It's a branch to an exception stub, so the branch is to the end of the
code generation area where the exception handler stubs are placed.

The V9 branch can only handle signed 19-bit offsets, and in this
case the code area is so big that the displacement to the exception
area is too large to fit into the relocation.

For these cases we only need the 32-bit icc condition codes.  So we
can expand the range of offsets that can be handled by using the
pre-v9 branches in this case.  This gives us a signed 22-bit offset to
work with.

This is not even sub-optimal for v9 chips because v9 chips use a
default prediction of not-taken for pre-v9 branches, and since
exceptions are "exceptional"...

While working on this patch I noticed a NULL pointer assertion in the
exception handler stub emitter that was after the first dereference of
that pointer, making it useless.

Please apply, thanks.

2007-11-01  David S. Miller  <davem at davemloft.net>

	sparcv9, use non-v9 branch if using sparc_icc_short.
	(mono_arch_emit_exceptions): Move NULL pointer assertion before
	first dereference.

Index: mono/mini/mini-sparc.c
--- mono/mini/mini-sparc.c	(revision 88629)
+++ mono/mini/mini-sparc.c	(working copy)
@@ -1387,7 +1387,7 @@ if (ins->flags & MONO_INST_BRLABEL) { \
 #define EMIT_COND_SYSTEM_EXCEPTION_GENERAL(ins,cond,sexc_name,filldelay,icc) do {     \
 		mono_add_patch_info (cfg, (guint8*)(code) - (cfg)->native_code,   \
 				    MONO_PATCH_INFO_EXC, sexc_name);  \
-        if (sparcv9) { \
+	if (sparcv9 && ((icc) != sparc_icc_short)) {	      \
            sparc_branchp (code, 0, (cond), (icc), 0, 0); \
         } \
         else { \
@@ -4207,8 +4207,8 @@ mono_arch_emit_exceptions (MonoCompile *
 			sparc_patch ((guint32*)(cfg->native_code + patch_info->ip.i), code);
 			exc_class = mono_class_from_name (mono_defaults.corlib, "System", patch_info->data.name);
-			type_idx = exc_class->type_token - MONO_TOKEN_TYPE_DEF;
 			g_assert (exc_class);
+			type_idx = exc_class->type_token - MONO_TOKEN_TYPE_DEF;
 			throw_ip = patch_info->ip.i;
 			/* Find a throw sequence for the same exception class */

More information about the Mono-devel-list mailing list