2008-10-17 Mark Probst <mark.probst@gmail.com>
authorMark Probst <mark.probst@gmail.com>
Fri, 17 Oct 2008 20:15:10 +0000 (20:15 -0000)
committerMark Probst <mark.probst@gmail.com>
Fri, 17 Oct 2008 20:15:10 +0000 (20:15 -0000)
* mini-x86.h, mini-x86.c, exceptions-x86.c: Align stack on all
platforms, with definable stack alignment value.  Set to 16 now
for all platforms.

* mini.c, mini.h, driver.c: Command line option for disabling
stack alignment.

svn path=/trunk/mono/; revision=116313

mono/mini/ChangeLog
mono/mini/driver.c
mono/mini/exceptions-x86.c
mono/mini/mini-x86.c
mono/mini/mini-x86.h
mono/mini/mini.c
mono/mini/mini.h

index 8b50f2e339af432b8a39fa337050892c3387088e..d684199ae9a6875e60d9bbae9af4371acfc38b83 100644 (file)
@@ -1,3 +1,12 @@
+2008-10-17  Mark Probst  <mark.probst@gmail.com>
+
+       * mini-x86.h, mini-x86.c, exceptions-x86.c: Align stack on all
+       platforms, with definable stack alignment value.  Set to 16 now
+       for all platforms.
+
+       * mini.c, mini.h, driver.c: Command line option for disabling
+       stack alignment.
+
 2008-10-17  Rodrigo Kumpera  <rkumpera@novell.com>
 
        * basic-simd.cs: Tests for new methods in Vector4ui.
index 4dcad38f637d557a88d0f04f2b4a33402f087f2c..40c7c8cd77cae5caf13815eb463971b367152b90 100644 (file)
@@ -1059,6 +1059,7 @@ mini_usage_jitdeveloper (void)
                 "    --verify-all           Run the verifier on all methods\n"
                 "    --full-aot             Avoid JITting any code\n"
                 "    --agent=ASSEMBLY[:ARG] Loads the specific agent assembly and executes its Main method with the given argument before loading the main assembly.\n"
+                "    --no-x86-stack-align   Don't align stack on x86\n"
                 "\n"
                 "Other options:\n" 
                 "    --graph[=TYPE] METHOD  Draws a graph of the specified method:\n");
@@ -1465,6 +1466,8 @@ mono_main (int argc, char* argv[])
                                fprintf (stderr, "Invalid --wapi suboption: '%s'\n", argv [i]);
                                return 1;
                        }
+               } else if (strcmp (argv [i], "--no-x86-stack-align") == 0) {
+                       mono_do_x86_stack_align = FALSE;
 #ifdef MONO_JIT_INFO_TABLE_TEST
                } else if (strcmp (argv [i], "--test-jit-info-table") == 0) {
                        test_jit_info_table = TRUE;
index 0384d6d97c11365ddf77ca30a800467df89c5dfd..527aa176714a8ced4d905e7fccb17d97ab62dc01 100644 (file)
@@ -334,9 +334,19 @@ mono_arch_get_call_filter (void)
        x86_mov_reg_membase (code, X86_ESI, X86_EAX,  G_STRUCT_OFFSET (MonoContext, esi), 4);
        x86_mov_reg_membase (code, X86_EDI, X86_EAX,  G_STRUCT_OFFSET (MonoContext, edi), 4);
 
+       /* align stack and save ESP */
+       x86_mov_reg_reg (code, X86_EDX, X86_ESP, 4);
+       x86_alu_reg_imm (code, X86_AND, X86_ESP, -MONO_ARCH_FRAME_ALIGNMENT);
+       g_assert (MONO_ARCH_FRAME_ALIGNMENT >= 8);
+       x86_alu_reg_imm (code, X86_SUB, X86_ESP, MONO_ARCH_FRAME_ALIGNMENT - 8);
+       x86_push_reg (code, X86_EDX);
+
        /* call the handler */
        x86_call_reg (code, X86_ECX);
 
+       /* restore ESP */
+       x86_pop_reg (code, X86_ESP);
+
        /* restore EBP */
        x86_pop_reg (code, X86_EBP);
 
index a66edc517ac8e5b979f499095b5d7abbcf00f9ef..bb4c60d8ac54f78dc6b9a9bcbd15b25169911fb2 100644 (file)
@@ -464,12 +464,11 @@ get_call_info (MonoGenericSharingContext *gsctx, MonoMemPool *mp, MonoMethodSign
                add_general (&gr, &stack_size, &cinfo->sig_cookie);
        }
 
-#if defined(__APPLE__)
-       if ((stack_size % 16) != 0) { 
+       if (mono_do_x86_stack_align && (stack_size % MONO_ARCH_FRAME_ALIGNMENT) != 0) {
                cinfo->need_stack_align = TRUE;
-               stack_size += cinfo->stack_align_amount = 16-(stack_size % 16);
+               cinfo->stack_align_amount = MONO_ARCH_FRAME_ALIGNMENT - (stack_size % MONO_ARCH_FRAME_ALIGNMENT);
+               stack_size += cinfo->stack_align_amount;
        }
-#endif
 
        cinfo->stack_usage = stack_size;
        cinfo->reg_usage = gr;
@@ -529,7 +528,10 @@ mono_arch_get_argument_info (MonoMethodSignature *csig, int param_count, MonoJit
                offset += size;
        }
 
-       align = 4;
+       if (mono_do_x86_stack_align)
+               align = MONO_ARCH_FRAME_ALIGNMENT;
+       else
+               align = 4;
        args_size += pad = (align - (args_size & (align - 1))) & (align - 1);
        arg_info [k].pad = pad;
 
@@ -1182,14 +1184,12 @@ mono_arch_call_opcode (MonoCompile *cfg, MonoBasicBlock* bb, MonoCallInst *call,
 
        call->stack_usage = cinfo->stack_usage;
 
-#if defined(__APPLE__)
        if (cinfo->need_stack_align) {
                MONO_INST_NEW (cfg, arg, OP_X86_OUTARG_ALIGN_STACK);
                arg->inst_c0 = cinfo->stack_align_amount;
                arg->next = call->out_args;
                call->out_args = arg;
         }
-#endif 
 
        return call;
 }
@@ -1233,7 +1233,6 @@ mono_arch_emit_call (MonoCompile *cfg, MonoCallInst *call)
        if (!sig->pinvoke && (sig->call_convention == MONO_CALL_VARARG))
                sentinelpos = sig->sentinelpos + (sig->hasthis ? 1 : 0);
 
-#if defined(__APPLE__)
        if (cinfo->need_stack_align) {
                MONO_INST_NEW (cfg, arg, OP_SUB_IMM);
                arg->dreg = X86_ESP;
@@ -1241,7 +1240,6 @@ mono_arch_emit_call (MonoCompile *cfg, MonoCallInst *call)
                arg->inst_imm = cinfo->stack_align_amount;
                MONO_ADD_INS (cfg->cbb, arg);
        }
-#endif 
 
        if (sig->ret && MONO_TYPE_ISSTRUCT (sig->ret)) {
                MonoInst *vtarg;
@@ -1433,9 +1431,8 @@ mono_arch_instrument_prolog (MonoCompile *cfg, void *func, void *p, gboolean ena
 {
        guchar *code = p;
 
-#if __APPLE__
-       x86_alu_reg_imm (code, X86_SUB, X86_ESP, 8);
-#endif
+       g_assert (MONO_ARCH_FRAME_ALIGNMENT >= 8);
+       x86_alu_reg_imm (code, X86_SUB, X86_ESP, MONO_ARCH_FRAME_ALIGNMENT - 8);
 
        /* if some args are passed in registers, we need to save them here */
        x86_push_reg (code, X86_EBP);
@@ -1450,11 +1447,7 @@ mono_arch_instrument_prolog (MonoCompile *cfg, void *func, void *p, gboolean ena
                mono_add_patch_info (cfg, code-cfg->native_code, MONO_PATCH_INFO_ABS, func);
                x86_call_code (code, 0);
        }
-#if __APPLE__
-       x86_alu_reg_imm (code, X86_ADD, X86_ESP, 16);
-#else
-       x86_alu_reg_imm (code, X86_ADD, X86_ESP, 8);
-#endif
+       x86_alu_reg_imm (code, X86_ADD, X86_ESP, MONO_ARCH_FRAME_ALIGNMENT);
 
        return code;
 }
@@ -2953,14 +2946,10 @@ mono_arch_output_basic_block (MonoCompile *cfg, MonoBasicBlock *bb)
                        break;
                }
                case OP_CALL_HANDLER:
-#if __APPLE__
-                       x86_alu_reg_imm (code, X86_SUB, X86_ESP, 12);
-#endif
+                       x86_alu_reg_imm (code, X86_SUB, X86_ESP, MONO_ARCH_FRAME_ALIGNMENT - 4);
                        mono_add_patch_info (cfg, code - cfg->native_code, MONO_PATCH_INFO_BB, ins->inst_target_bb);
                        x86_call_imm (code, 0);
-#ifdef __APPLE__
-                       x86_alu_reg_imm (code, X86_ADD, X86_ESP, 12);
-#endif
+                       x86_alu_reg_imm (code, X86_ADD, X86_ESP, MONO_ARCH_FRAME_ALIGNMENT - 4);
                        break;
                case OP_START_HANDLER: {
                        MonoInst *spvar = mono_find_spvar_for_region (cfg, bb->region);
@@ -4332,19 +4321,12 @@ mono_arch_emit_prolog (MonoCompile *cfg)
 
        alloc_size -= pos;
 
-#if __APPLE__
        /* the original alloc_size is already aligned: there is %ebp and retip pushed, so realign */
-       {
+       if (mono_do_x86_stack_align) {
                int tot = alloc_size + pos + 4 + 4; /* ret ip + ebp */
-               if (tot & 4) {
-                       tot += 4;
-                       alloc_size += 4;
-               }
-               if (tot & 8) {
-                       alloc_size += 8;
-               }
+               tot &= MONO_ARCH_FRAME_ALIGNMENT - 1;
+               alloc_size += MONO_ARCH_FRAME_ALIGNMENT - tot;
        }
-#endif
 
        if (alloc_size) {
                /* See mono_emit_stack_alloc */
@@ -4362,13 +4344,20 @@ mono_arch_emit_prolog (MonoCompile *cfg)
 #endif
        }
 
-#if __APPLE__ && DEBUG_APPLE_ALIGNMENT
+       if (cfg->method->wrapper_type == MONO_WRAPPER_NATIVE_TO_MANAGED ||
+                       cfg->method->wrapper_type == MONO_WRAPPER_RUNTIME_INVOKE) {
+               x86_alu_reg_imm (code, X86_AND, X86_ESP, -MONO_ARCH_FRAME_ALIGNMENT);
+       }
+
+#if DEBUG_STACK_ALIGNMENT
        /* check the stack is aligned */
-       x86_mov_reg_reg (code, X86_EDX, X86_ESP, 4);
-       x86_alu_reg_imm (code, X86_AND, X86_EDX, 15);
-       x86_alu_reg_imm (code, X86_CMP, X86_EDX, 0);
-       x86_branch_disp (code, X86_CC_EQ, 3, FALSE);
-       x86_breakpoint (code);
+       if (method->wrapper_type == MONO_WRAPPER_NONE) {
+               x86_mov_reg_reg (code, X86_ECX, X86_ESP, 4);
+               x86_alu_reg_imm (code, X86_AND, X86_ECX, MONO_ARCH_FRAME_ALIGNMENT - 1);
+               x86_alu_reg_imm (code, X86_CMP, X86_ECX, 0);
+               x86_branch_disp (code, X86_CC_EQ, 3, FALSE);
+               x86_breakpoint (code);
+       }
 #endif
 
         /* compute max_offset in order to use short forward jumps */
index e714eb7b58b0171c2764b714aef3102f1eaf55bd..12c447967092af29cd95dbbd7f662959cb614538 100644 (file)
@@ -111,12 +111,8 @@ LONG CALLBACK seh_handler(EXCEPTION_POINTERS* ep);
 #define MONO_ARCH_INST_IS_REGPAIR(desc) (desc == 'l' || desc == 'L')
 #define MONO_ARCH_INST_REGPAIR_REG2(desc,hreg1) (desc == 'l' ? X86_EDX : -1)
 
-#if __APPLE__
+/* must be at a power of 2 and >= 8 */
 #define MONO_ARCH_FRAME_ALIGNMENT 16
-#else
-/* For storing doubles on the stack */
-#define MONO_ARCH_FRAME_ALIGNMENT 8
-#endif
 
 /* fixme: align to 16byte instead of 32byte (we align to 32byte to get 
  * reproduceable results for benchmarks */
index 6583f2cdbf177f6d517295b5229ea300702d0e99..361ae292fe06a14bf7af5721129517efcf09d3f2 100644 (file)
@@ -183,6 +183,7 @@ MonoMethodDesc *mono_inject_async_exc_method = NULL;
 int mono_inject_async_exc_pos;
 MonoMethodDesc *mono_break_at_bb_method = NULL;
 int mono_break_at_bb_bb_num;
+gboolean mono_do_x86_stack_align = TRUE;
 
 static int mini_verbose = 0;
 
index 68ef312856b9b668106a31416669e96d4863cd73..66790397a0528bec9a1ddd2c1ea36b673391bf4f 100644 (file)
@@ -255,6 +255,7 @@ extern gboolean check_for_pending_exc;
 extern gboolean disable_vtypes_in_regs;
 extern gboolean mono_verify_all;
 extern gboolean mono_dont_free_global_codeman;
+extern gboolean mono_do_x86_stack_align;
 
 #define INS_INFO(opcode) (&ins_info [((opcode) - OP_START - 1) * 3])