]> git.unchartedbackwaters.co.uk Git - francis/libjit.git/commitdiff
Improve the maintainability of the apply macros.
authorRhys Weatherley <rweather@southern-storm.com.au>
Sun, 2 May 2004 23:40:18 +0000 (23:40 +0000)
committerRhys Weatherley <rweather@southern-storm.com.au>
Sun, 2 May 2004 23:40:18 +0000 (23:40 +0000)
ChangeLog
tools/gen-apply.c

index d63be17b2b2621c168d4e8dff0a3757e436a477b..402abb99fc6df3678d8e2da4e5a3a0458abfddde 100644 (file)
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,4 +1,8 @@
 
+2004-05-03  Rhys Weatherley  <rweather@southern-storm.com.au>
+
+       * tools/gen-apply.c: improve the maintainability of the apply macros.
+
 2004-05-01  Rhys Weatherley  <rweather@southern-storm.com.au>
 
        * jit/jit-apply-x86.c, jit/jit-rules-x86.c, tools/gen-apply.c:
index 232565b53f17c380dc2bc089ee3ba06edc77ad8c..0bb1690fcc25a321f523eb88dfc4e336619b06ae 100644 (file)
@@ -76,6 +76,7 @@ int struct_reg_overlaps_word_reg = 0;
 int struct_return_in_reg[64];
 int align_long_regs = 0;
 int align_long_stack = 0;
+int can_split_long = 0;
 int max_apply_size = 0;
 int x86_fastcall = 0;
 int parent_frame_offset = 0;
@@ -848,6 +849,10 @@ void detect_struct_conventions(void)
        if(struct_return_special_reg || num_word_regs > 0)
        {
                args[1] = (jit_nint)buffer;
+               if(struct_reg_overlaps_word_reg)
+               {
+                       args[2] = (jit_nint)buffer;
+               }
        }
 
        /* Apply the structure return tests for all sizes from 1 to 64 */
@@ -917,6 +922,280 @@ void detect_struct_conventions(void)
        call_struct_test(64);
 }
 
+/*
+ * Detect alignment of "long" values in registers and on the stack.
+ */
+#ifdef JIT_NATIVE_INT32
+void detect_reg_alignment_one_word(jit_long y, jit_long z)
+{
+       jit_nint *args, *stack_args;
+       jit_builtin_apply_args(jit_nint *, args);
+       stack_args = (jit_nint *)(args[0]);
+       if(!mem_cmp(stack_args, &y, sizeof(y)))
+       {
+               /* The value of y was pushed out onto the stack, so we
+                  cannot split long values between registers and the stack */
+               can_split_long = 0;
+       }
+}
+void detect_reg_alignment_two_words(jit_int x, jit_long y, jit_long z)
+{
+       jit_nint *args, *stack_args;
+       jit_builtin_apply_args(jit_nint *, args);
+       stack_args = (jit_nint *)(args[0]);
+       if(!mem_cmp(stack_args, &y, sizeof(y)))
+       {
+               /* The value of y was pushed out, so alignment has occurred */
+               can_split_long = 0;
+               align_long_regs = 1;
+       }
+       else if(!mem_cmp(stack_args, ((jit_nint *)&y) + 1, sizeof(jit_nint)))
+       {
+               /* The long value was split between registers and the stack */
+               can_split_long = 1;
+       }
+}
+void detect_reg_alignment_three_words(jit_int x, jit_long y, jit_long z)
+{
+       jit_nint *args, *stack_args;
+       jit_builtin_apply_args(jit_nint *, args);
+       stack_args = (jit_nint *)(args[0]);
+       if(!mem_cmp(stack_args, &y, sizeof(y)))
+       {
+               /* The value of y was pushed out, so alignment has occurred */
+               can_split_long = 0;
+               align_long_regs = 1;
+       }
+       else if(!mem_cmp(stack_args, ((jit_nint *)&y) + 1, sizeof(jit_nint)))
+       {
+               /* The long value was split between registers and the stack,
+                  so alignment has occurred, together with a split */
+               can_split_long = 1;
+               align_long_regs = 1;
+       }
+}
+void detect_reg_alignment_more_words(jit_int x, jit_long y, jit_long z)
+{
+       jit_nint *args, *word_regs;
+       jit_builtin_apply_args(jit_nint *, args);
+       word_regs = args + struct_return_special_reg + 1;
+       if(!mem_cmp(word_regs + 2, &y, sizeof(y)))
+       {
+               /* The value of "y" was aligned within the word registers */
+               align_long_regs = 1;
+       }
+}
+void detect_reg_split_even_words(jit_int x, jit_long y1, jit_long y2,
+                                                                jit_long y3, jit_long y4, jit_long y5,
+                                                                jit_long y6, jit_long y7, jit_long y8,
+                                                                jit_long y9, jit_long y10, jit_long y11,
+                                                                jit_long y12, jit_long y13, jit_long y14,
+                                                                jit_long y15, jit_long y16, jit_long y17,
+                                                                jit_long y18, jit_long y19, jit_long y20)
+{
+       jit_nint *args, *stack_args;
+       int posn;
+       jit_long value;
+       jit_builtin_apply_args(jit_nint *, args);
+       stack_args = (jit_nint *)(args[0]);
+       for(posn = 1; posn <= 20; ++posn)
+       {
+               switch(posn)
+               {
+                       case 1:         value = y1; break;
+                       case 2:         value = y2; break;
+                       case 3:         value = y3; break;
+                       case 4:         value = y4; break;
+                       case 5:         value = y5; break;
+                       case 6:         value = y6; break;
+                       case 7:         value = y7; break;
+                       case 8:         value = y8; break;
+                       case 9:         value = y9; break;
+                       case 10:        value = y10; break;
+                       case 11:        value = y11; break;
+                       case 12:        value = y12; break;
+                       case 13:        value = y13; break;
+                       case 14:        value = y14; break;
+                       case 15:        value = y15; break;
+                       case 16:        value = y16; break;
+                       case 17:        value = y17; break;
+                       case 18:        value = y18; break;
+                       case 19:        value = y19; break;
+                       default:        value = y20; break;
+               }
+               if(!mem_cmp(stack_args, ((jit_nint *)&value) + 1, sizeof(jit_nint)))
+               {
+                       /* We've detected a register/stack split in this argument */
+                       can_split_long = 1;
+                       break;
+               }
+       }
+}
+void detect_reg_split_odd_words(jit_long y1, jit_long y2,
+                                                               jit_long y3, jit_long y4, jit_long y5,
+                                                               jit_long y6, jit_long y7, jit_long y8,
+                                                               jit_long y9, jit_long y10, jit_long y11,
+                                                               jit_long y12, jit_long y13, jit_long y14,
+                                                               jit_long y15, jit_long y16, jit_long y17,
+                                                               jit_long y18, jit_long y19, jit_long y20)
+{
+       jit_nint *args, *stack_args;
+       int posn;
+       jit_long value;
+       jit_builtin_apply_args(jit_nint *, args);
+       stack_args = (jit_nint *)(args[0]);
+       for(posn = 1; posn <= 20; ++posn)
+       {
+               switch(posn)
+               {
+                       case 1:         value = y1; break;
+                       case 2:         value = y2; break;
+                       case 3:         value = y3; break;
+                       case 4:         value = y4; break;
+                       case 5:         value = y5; break;
+                       case 6:         value = y6; break;
+                       case 7:         value = y7; break;
+                       case 8:         value = y8; break;
+                       case 9:         value = y9; break;
+                       case 10:        value = y10; break;
+                       case 11:        value = y11; break;
+                       case 12:        value = y12; break;
+                       case 13:        value = y13; break;
+                       case 14:        value = y14; break;
+                       case 15:        value = y15; break;
+                       case 16:        value = y16; break;
+                       case 17:        value = y17; break;
+                       case 18:        value = y18; break;
+                       case 19:        value = y19; break;
+                       default:        value = y20; break;
+               }
+               if(!mem_cmp(stack_args, ((jit_nint *)&value) + 1, sizeof(jit_nint)))
+               {
+                       /* We've detected a register/stack split in this argument */
+                       can_split_long = 1;
+                       break;
+               }
+       }
+}
+void detect_stack_align_even_words
+                                       (jit_nint arg1, jit_nint arg2, jit_nint arg3,
+                                        jit_nint arg4, jit_nint arg5, jit_nint arg6,
+                                        jit_nint arg7, jit_nint arg8, jit_nint arg9,
+                                        jit_nint arg10, jit_nint arg11, jit_nint arg12,
+                                        jit_nint arg13, jit_nint arg14, jit_nint arg15,
+                                        jit_nint arg16, jit_nint arg17, jit_nint arg18,
+                                        jit_nint arg19, jit_nint arg20, jit_nint arg21,
+                                        jit_nint arg22, jit_nint arg23, jit_nint arg24,
+                                        jit_nint arg25, jit_nint arg26, jit_nint arg27,
+                                        jit_nint arg28, jit_nint arg29, jit_nint arg30,
+                                        jit_nint arg31, jit_nint arg32, jit_nint arg33,
+                                        jit_long y, jit_long z)
+{
+       jit_nint *args, *stack_args;
+       int index;
+       jit_builtin_apply_args(jit_nint *, args);
+       stack_args = (jit_nint *)(args[0]);
+       index = 33 - num_word_regs;
+       if(!mem_cmp(stack_args + index + 1, &y, sizeof(y)))
+       {
+               align_long_stack = 1;
+       }
+}
+void detect_stack_align_odd_words
+                                       (jit_nint arg1, jit_nint arg2, jit_nint arg3,
+                                        jit_nint arg4, jit_nint arg5, jit_nint arg6,
+                                        jit_nint arg7, jit_nint arg8, jit_nint arg9,
+                                        jit_nint arg10, jit_nint arg11, jit_nint arg12,
+                                        jit_nint arg13, jit_nint arg14, jit_nint arg15,
+                                        jit_nint arg16, jit_nint arg17, jit_nint arg18,
+                                        jit_nint arg19, jit_nint arg20, jit_nint arg21,
+                                        jit_nint arg22, jit_nint arg23, jit_nint arg24,
+                                        jit_nint arg25, jit_nint arg26, jit_nint arg27,
+                                        jit_nint arg28, jit_nint arg29, jit_nint arg30,
+                                        jit_nint arg31, jit_nint arg32,
+                                        jit_long y, jit_long z)
+{
+       jit_nint *args, *stack_args;
+       int index;
+       jit_builtin_apply_args(jit_nint *, args);
+       stack_args = (jit_nint *)(args[0]);
+       index = 32 - num_word_regs;
+       if(!mem_cmp(stack_args + index + 1, &y, sizeof(y)))
+       {
+               align_long_stack = 1;
+       }
+}
+void detect_long_alignment()
+{
+       jit_long value1, value2;
+       jit_long align_values[20];
+       int posn;
+       value1 = (((jit_long)0x01020304) << 32) | ((jit_long)0x05060708);
+       value2 = (((jit_long)0x090A0B0C) << 32) | ((jit_long)0x0D0E0F00);
+       if(num_word_regs == 1)
+       {
+               detect_reg_alignment_one_word(value1, value2);
+       }
+       else if(num_word_regs == 2)
+       {
+               detect_reg_alignment_two_words((jit_int)(-1), value1, value2);
+       }
+       else if(num_word_regs == 3)
+       {
+               detect_reg_alignment_three_words((jit_int)(-1), value1, value2);
+       }
+       else if(num_word_regs > 0)
+       {
+               detect_reg_alignment_more_words((jit_int)(-1), value1, value2);
+       }
+       else if(x86_fastcall)
+       {
+               /* We can split long values using FASTCALL under Win32 */
+               can_split_long = 1;
+       }
+       for(posn = 0; posn < 20; ++posn)
+       {
+               align_values[posn] = ((jit_long)(posn + 4567)) +
+                                                    (((jit_long)((posn + 1) * 127)) << 32);
+       }
+       if((num_word_regs % 2) == 0)
+       {
+               detect_reg_split_even_words
+                       ((jit_int)(-1), align_values[0], align_values[1],
+                        align_values[2], align_values[3], align_values[4],
+                        align_values[5], align_values[6], align_values[7],
+                        align_values[8], align_values[9], align_values[10],
+                        align_values[11], align_values[12], align_values[13],
+                        align_values[14], align_values[15], align_values[16],
+                        align_values[17], align_values[18], align_values[19]);
+               detect_stack_align_even_words
+                       (0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+                        0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+                        value1, value2);
+       }
+       else
+       {
+               detect_reg_split_odd_words
+                       (align_values[0], align_values[1],
+                        align_values[2], align_values[3], align_values[4],
+                        align_values[5], align_values[6], align_values[7],
+                        align_values[8], align_values[9], align_values[10],
+                        align_values[11], align_values[12], align_values[13],
+                        align_values[14], align_values[15], align_values[16],
+                        align_values[17], align_values[18], align_values[19]);
+               detect_stack_align_odd_words
+                       (0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+                        0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+                        value1, value2);
+       }
+}
+#else  /* JIT_NATIVE_INT64 */
+void detect_long_alignment()
+{
+       /* Long values are always aligned on 64-bit architectures */
+}
+#endif /* JIT_NATIVE_INT64 */
+
 /*
  * Determine the maximum size for the apply structure.
  */
@@ -1325,31 +1604,95 @@ void dump_apply_macros(void)
        }
        printf("\t} while (0)\n\n");
 
+       /* Macro to align the word registers for a "long" value */
+       printf("#define jit_apply_builder_align_regs(builder,num_words,align) \\\n");
+       if((align_long_regs || !can_split_long) &&
+          (num_word_regs > 0 || x86_fastcall))
+       {
+               printf("\tdo { \\\n");
+               printf("\t\tif((align) > sizeof(jit_nint) && (num_words) > 1) \\\n");
+               printf("\t\t{ \\\n");
+               if(align_long_regs)
+               {
+                       printf("\t\t\tif(((builder)->word_used %% 2) == 1) \\\n");
+                       printf("\t\t\t{ \\n");
+                       printf("\t\t\t\t++((builder)->word_used); \\n");
+                       printf("\t\t\t} \\n");
+               }
+               if(!can_split_long)
+               {
+                       printf("\t\t\tif((%s - (builder)->word_used) < (num_words)) \\\n", word_reg_limit);
+                       printf("\t\t\t{ \\n");
+                       printf("\t\t\t\t(builder)->word_used = %s; \\n", word_reg_limit);
+                       printf("\t\t\t} \\n");
+               }
+               printf("\t\t} \\\n");
+               printf("\t} while (0)\n\n");
+       }
+       else
+       {
+               printf("\tdo { ; } while (0)\n\n");
+       }
+
+       /* Macro to align the stack for a "long" value */
+       printf("#define jit_apply_builder_align_stack(builder,num_words,align) \\\n");
+       if(align_long_stack)
+       {
+               printf("\tdo { \\\n");
+               printf("\t\tif((align) > sizeof(jit_nint) && (num_words) > 1) \\\n");
+               printf("\t\t{ \\\n");
+               printf("\t\t\tif(((builder)->stack_used %% 2) == 1) \\\n");
+               printf("\t\t\t{ \\n");
+               printf("\t\t\t\t++((builder)->stack_used); \\n");
+               printf("\t\t\t} \\n");
+               printf("\t\t} \\\n");
+               printf("\t} while (0)\n\n");
+       }
+       else
+       {
+               printf("\tdo { ; } while (0)\n\n");
+       }
+
        /* Macro to add a large (e.g. dword) argument to the apply parameters */
-       printf("#define jit_apply_builder_add_large(builder,type,value) \\\n");
+       printf("#define jit_apply_builder_add_large_inner(builder,ptr,size,align) \\\n");
        printf("\tdo { \\\n");
-       printf("\t\ttype __temp = (type)(value); \\\n");
-       printf("\t\tunsigned int __num_words = (sizeof(__temp) + sizeof(jit_nint) - 1) / sizeof(jit_nint); \\\n");
+       printf("\t\tunsigned int __num_words = ((size) + sizeof(jit_nint) - 1) / sizeof(jit_nint); \\\n");
        if(num_word_regs > 0 || x86_fastcall)
        {
+               printf("\t\tjit_apply_builder_align_regs((builder), __num_words, (align)); \\\n");
                printf("\t\tif((%s - (builder)->word_used) >= __num_words) \\\n", word_reg_limit);
                printf("\t\t{ \\\n");
-               printf("\t\t\tjit_memcpy((builder)->apply_args->word_regs + (builder)->word_used, &__temp, sizeof(__temp)); \\\n");
+               printf("\t\t\tjit_memcpy((builder)->apply_args->word_regs + (builder)->word_used, (ptr), (size)); \\\n");
                printf("\t\t\t(builder)->word_used += __num_words; \\\n");
                printf("\t\t} \\\n");
+               printf("\t\telse if((builder)->word_used) < %s) \\\n", word_reg_limit);
+               printf("\t\t{ \\\n");
+               printf("\t\t\tunsigned int __split = (%s - (builder)->word_used); \\\n", word_reg_limit);
+               printf("\t\t\tjit_memcpy((builder)->apply_args->word_regs + (builder)->word_used, (ptr), __split * sizeof(jit_nint)); \\\n");
+               printf("\t\t\tjit_memcpy((builder)->apply_args->stack_args, ((jit_nint *)(ptr)) + __split, (size) - __split * sizeof(jit_nint)); \\\n");
+               printf("\t\t\t(builder)->word_used = %s; \\\n", word_reg_limit);
+               printf("\t\t\t(builder)->stack_used = __num_words - __split; \\\n");
+               printf("\t\t} \\\n");
                printf("\t\telse \\\n");
                printf("\t\t{ \\\n");
-               printf("\t\t\tjit_memcpy((builder)->apply_args->stack_args + (builder)->stack_used, &__temp, sizeof(__temp)); \\\n");
+               printf("\t\t\tjit_apply_builder_align_stack((builder), __num_words, (align)); \\\n");
+               printf("\t\t\tjit_memcpy((builder)->apply_args->stack_args + (builder)->stack_used, (ptr), (size)); \\\n");
                printf("\t\t\t(builder)->stack_used += __num_words * sizeof(jit_nint); \\\n");
                printf("\t\t\t(builder)->word_used = %s; \\\n", word_reg_limit);
                printf("\t\t} \\\n");
        }
        else
        {
-               printf("\t\tjit_memcpy((builder)->apply_args->stack_args + (builder)->stack_used, &__temp, sizeof(__temp)); \\\n");
+               printf("\t\tjit_apply_builder_align_stack((builder), __num_words, (align)); \\\n");
+               printf("\t\tjit_memcpy((builder)->apply_args->stack_args + (builder)->stack_used, (ptr), (size)); \\\n");
                printf("\t\t(builder)->stack_used += __num_words * sizeof(jit_nint); \\\n");
        }
        printf("\t} while (0)\n\n");
+       printf("#define jit_apply_builder_add_large(builder,type,value) \\\n");
+       printf("\tdo { \\\n");
+       printf("\t\ttype __temp = (type)(value); \\\n");
+       printf("\t\tjit_apply_builder_add_large_inner((builder), &__temp, sizeof(__temp), sizeof(jit_nint)); \\\n");
+       printf("\t} while (0)\n\n");
 
        /* Macro to get a large (e.g. dword) argument from the apply parameters */
        printf("#define jit_apply_parser_get_large(builder,type,finaltype,value) \\\n");
@@ -1358,13 +1701,23 @@ void dump_apply_macros(void)
        printf("\t\tunsigned int __num_words = (sizeof(__temp) + sizeof(jit_nint) - 1) / sizeof(jit_nint); \\\n");
        if(num_word_regs > 0 || x86_fastcall)
        {
+               printf("\t\tjit_apply_builder_align_regs((builder), __num_words, sizeof(type)); \\\n");
                printf("\t\tif((%s - (builder)->word_used) >= __num_words) \\\n", word_reg_limit);
                printf("\t\t{ \\\n");
                printf("\t\t\tjit_memcpy(&__temp, (builder)->apply_args->word_regs + (builder)->word_used, sizeof(__temp)); \\\n");
                printf("\t\t\t(builder)->word_used += __num_words; \\\n");
                printf("\t\t} \\\n");
+               printf("\t\telse if((builder)->word_used) < %s) \\\n", word_reg_limit);
+               printf("\t\t{ \\\n");
+               printf("\t\t\tunsigned int __split = (%s - (builder)->word_used); \\\n", word_reg_limit);
+               printf("\t\t\tjit_memcpy(&__temp, (builder)->apply_args->word_regs + (builder)->word_used, __split * sizeof(jit_nint)); \\\n");
+               printf("\t\t\tjit_memcpy(((jit_nint *)&__temp) + __split, (builder)->apply_args->stack_args, (__num_words - __split) * sizeof(jit_nint)); \\\n");
+               printf("\t\t\t(builder)->word_used = %s; \\\n", word_reg_limit);
+               printf("\t\t\t(builder)->stack_used = __num_words - __split; \\\n");
+               printf("\t\t} \\\n");
                printf("\t\telse \\\n");
                printf("\t\t{ \\\n");
+               printf("\t\t\tjit_apply_builder_align_stack((builder), __num_words, sizeof(type)); \\\n");
                printf("\t\t\tjit_memcpy(&__temp, (builder)->apply_args->stack_args + (builder)->stack_used, sizeof(__temp)); \\\n");
                printf("\t\t\t(builder)->stack_used += __num_words * sizeof(jit_nint); \\\n");
                printf("\t\t\t(builder)->word_used = %s; \\\n", word_reg_limit);
@@ -1372,6 +1725,7 @@ void dump_apply_macros(void)
        }
        else
        {
+               printf("\t\tjit_apply_builder_align_stack((builder), __num_words, sizeof(type)); \\\n");
                printf("\t\tjit_memcpy(&__temp, (builder)->apply_args->stack_args + (builder)->stack_used, sizeof(__temp)); \\\n");
                printf("\t\t(builder)->stack_used += __num_words * sizeof(jit_nint); \\\n");
        }
@@ -1384,6 +1738,7 @@ void dump_apply_macros(void)
        printf("\tdo { \\\n");
        printf("\t\ttype __temp = (type)(value); \\\n");
        printf("\t\tunsigned int __num_words = (sizeof(__temp) + sizeof(jit_nint) - 1) / sizeof(jit_nint); \\\n");
+       printf("\t\tjit_apply_builder_align_stack((builder), __num_words, sizeof(type)); \\\n");
        printf("\t\tjit_memcpy((builder)->apply_args->stack_args + (builder)->stack_used, &__temp, sizeof(__temp)); \\\n");
        printf("\t\t(builder)->stack_used += __num_words * sizeof(jit_nint); \\\n");
        printf("\t} while (0)\n\n");
@@ -1394,6 +1749,7 @@ void dump_apply_macros(void)
        printf("\tdo { \\\n");
        printf("\t\ttype __temp; \\\n");
        printf("\t\tunsigned int __num_words = (sizeof(__temp) + sizeof(jit_nint) - 1) / sizeof(jit_nint); \\\n");
+       printf("\t\tjit_apply_builder_align_stack((builder), __num_words, sizeof(type)); \\\n");
        printf("\t\tjit_memcpy(&__temp, (builder)->apply_args->stack_args + (builder)->stack_used, sizeof(__temp)); \\\n");
        printf("\t\t(builder)->stack_used += __num_words * sizeof(jit_nint); \\\n");
        printf("\t\t(value) = (finaltype)(__temp); \\\n");
@@ -1616,30 +1972,8 @@ void dump_apply_macros(void)
        printf("#define jit_apply_builder_add_struct(builder,value,size,align) \\\n");
        printf("\tdo { \\\n");
        printf("\t\tunsigned int __size = (size); \\\n");
-       if(align_long_regs || align_long_stack)
-       {
-               printf("\t\tunsigned int __align = (align); \\\n");
-       }
-       printf("\t\tunsigned int __num_words = (__size + sizeof(jit_nint) - 1) / sizeof(jit_nint); \\\n");
-       if(num_word_regs > 0 || x86_fastcall)
-       {
-               printf("\t\tif((builder)->word_used < %s) \\\n", word_reg_limit);
-               printf("\t\t{ \\\n");
-               printf("\t\t\tjit_memcpy((builder)->apply_args->word_regs + (builder)->word_used, (value), __size); \\\n");
-               printf("\t\t\t(builder)->word_used += __num_words; \\\n");
-               printf("\t\t} \\\n");
-               printf("\t\telse \\\n");
-               printf("\t\t{ \\\n");
-               printf("\t\t\tjit_memcpy((builder)->apply_args->stack_args + (builder)->stack_used, (value), __size); \\\n");
-               printf("\t\t\t(builder)->stack_used += __num_words * sizeof(jit_nint); \\\n");
-               printf("\t\t\t(builder)->word_used = %s; \\\n", word_reg_limit);
-               printf("\t\t} \\\n");
-       }
-       else
-       {
-               printf("\t\tjit_memcpy((builder)->apply_args->stack_args + (builder)->stack_used, (value), __size); \\\n");
-               printf("\t\t(builder)->stack_used += __num_words * sizeof(jit_nint); \\\n");
-       }
+       printf("\t\tunsigned int __align; __align = (align); \\\n");
+       printf("\t\tjit_apply_builder_add_large_inner((builder), (value), __size, __align); \\\n");
        printf("\t} while (0)\n\n");
 
        printf("\n");
@@ -1899,18 +2233,6 @@ int main(int argc, char *argv[])
                                                17.0, 18.0, 19.0, 20.0, 21.0, 22.0, 23.0, 24.0,
                                                25.0, 26.0, 27.0, 28.0, 29.0, 30.0, 31.0);
 
-       /* Detect the alignment of "long" values in registers and on the stack */
-#ifdef JIT_NATIVE_INT32
-       if(num_word_regs > 1)
-       {
-               /* TODO */
-       }
-       else
-       {
-               /* TODO */
-       }
-#endif
-
        /* Determine if variable arguments are always passed on the stack */
        detect_varargs_on_stack(0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13,
                                14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26,
@@ -1933,6 +2255,9 @@ int main(int argc, char *argv[])
        /* TODO */
 #endif
 
+       /* Detect the alignment of "long" values */
+       detect_long_alignment();
+
        /* Determine the maximum sizes */
        detect_max_sizes();
 
@@ -1974,6 +2299,7 @@ int main(int argc, char *argv[])
                   struct_reg_overlaps_word_reg);
        printf("#define JIT_APPLY_ALIGN_LONG_REGS %d\n", align_long_regs);
        printf("#define JIT_APPLY_ALIGN_LONG_STACK %d\n", align_long_stack);
+       printf("#define JIT_APPLY_CAN_SPLIT_LONG %d\n", can_split_long);
        printf("#define JIT_APPLY_STRUCT_RETURN_IN_REG_INIT \\\n\t{");
        max_struct_in_reg = 0;
        for(size = 0; size < 64; size += 8)