From: Vlad Brezae Date: Fri, 22 Sep 2017 22:42:43 +0000 (+0300) Subject: [arm64] Add the full neon regs to the context X-Git-Url: http://wien.tomnetworks.com/gitweb/?p=mono.git;a=commitdiff_plain;h=c889057d6474dd7e077a4622bce8afe182f4164d [arm64] Add the full neon regs to the context The full regs are still not handled in the trampolines. Only the lower half is saved. --- diff --git a/mono/mini/exceptions-arm64.c b/mono/mini/exceptions-arm64.c index fb8d1736c10..9e19a8d25e7 100644 --- a/mono/mini/exceptions-arm64.c +++ b/mono/mini/exceptions-arm64.c @@ -43,7 +43,7 @@ mono_arch_get_restore_context (MonoTrampInfo **info, gboolean aot) labels [0] = code; arm_cbzx (code, ARMREG_IP1, 0); for (i = 0; i < 32; ++i) - arm_ldrfpx (code, i, ctx_reg, MONO_STRUCT_OFFSET (MonoContext, fregs) + (i * 8)); + arm_ldrfpx (code, i, ctx_reg, MONO_STRUCT_OFFSET (MonoContext, fregs) + (i * sizeof (MonoContextSimdReg))); mono_arm_patch (labels [0], code, MONO_R_ARM64_CBZ); /* Restore gregs */ // FIXME: Restore less registers @@ -124,7 +124,7 @@ mono_arch_get_call_filter (MonoTrampInfo **info, gboolean aot) labels [0] = code; arm_cbzx (code, ARMREG_IP0, 0); for (i = 0; i < num_fregs; ++i) - arm_ldrfpx (code, ARMREG_D8 + i, ARMREG_R0, MONO_STRUCT_OFFSET (MonoContext, fregs) + ((i + 8) * 8)); + arm_ldrfpx (code, ARMREG_D8 + i, ARMREG_R0, MONO_STRUCT_OFFSET (MonoContext, fregs) + ((i + 8) * sizeof (MonoContextSimdReg))); mono_arm_patch (labels [0], code, MONO_R_ARM64_CBZ); /* Load fp */ arm_ldrx (code, ARMREG_FP, ARMREG_R0, MONO_STRUCT_OFFSET (MonoContext, regs) + (ARMREG_FP * 8)); @@ -393,7 +393,8 @@ mono_arm_throw_exception (gpointer arg, mgreg_t pc, mgreg_t *int_regs, gdouble * /* 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); + for (int i = 0; i < 8; i++) + *((gdouble*)&ctx.fregs [ARMREG_D8 + i]) = fp_regs [i]; ctx.has_fregs = 1; ctx.pc = pc; @@ -422,7 +423,8 @@ mono_arm_resume_unwind (gpointer arg, mgreg_t pc, mgreg_t *int_regs, gdouble *fp /* 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); + for (int i = 0; i < 8; i++) + *((gdouble*)&ctx.fregs [ARMREG_D8 + i]) = fp_regs [i]; ctx.has_fregs = 1; ctx.pc = pc; @@ -460,7 +462,8 @@ mono_arch_unwind_frame (MonoDomain *domain, MonoJitTlsData *jit_tls, memcpy (regs, &new_ctx->regs, sizeof (mgreg_t) * 32); /* v8..v15 are callee saved */ - memcpy (regs + MONO_MAX_IREGS, &(new_ctx->fregs [8]), sizeof (mgreg_t) * 8); + for (int i = 0; i < 8; i++) + (regs + MONO_MAX_IREGS) [i] = *((mgreg_t*)&new_ctx->fregs [8 + i]); mono_unwind_frame (unwind_info, unwind_info_len, ji->code_start, (guint8*)ji->code_start + ji->code_size, @@ -468,7 +471,8 @@ mono_arch_unwind_frame (MonoDomain *domain, MonoJitTlsData *jit_tls, save_locations, MONO_MAX_IREGS, &cfa); memcpy (&new_ctx->regs, regs, sizeof (mgreg_t) * 32); - memcpy (&(new_ctx->fregs [8]), regs + MONO_MAX_IREGS, sizeof (mgreg_t) * 8); + for (int i = 0; i < 8; i++) + *((mgreg_t*)&new_ctx->fregs [8 + i]) = (regs + MONO_MAX_IREGS) [i]; new_ctx->pc = regs [ARMREG_LR]; new_ctx->regs [ARMREG_SP] = (mgreg_t)cfa; diff --git a/mono/utils/mono-context.c b/mono/utils/mono-context.c index 3861e54f5e6..59ef74b215c 100644 --- a/mono/utils/mono-context.c +++ b/mono/utils/mono-context.c @@ -401,8 +401,7 @@ mono_sigctx_to_monoctx (void *sigctx, MonoContext *mctx) g_assert (fpctx->head.magic == FPSIMD_MAGIC); for (i = 0; i < 32; ++i) - /* Only store the bottom 8 bytes for now */ - *(guint64*)&(mctx->fregs [i]) = fpctx->vregs [i]; + mctx->fregs [i] = fpctx->vregs [i]; #endif /* FIXME: apple */ #endif diff --git a/mono/utils/mono-context.h b/mono/utils/mono-context.h index bac2fb331a1..290f24f115c 100644 --- a/mono/utils/mono-context.h +++ b/mono/utils/mono-context.h @@ -32,6 +32,8 @@ typedef struct __darwin_xmm_reg MonoContextSimdReg; #elif defined(__linux__) typedef struct _libc_xmmreg MonoContextSimdReg; #endif +#elif defined(TARGET_ARM64) +typedef __uint128_t MonoContextSimdReg; #endif /* @@ -425,7 +427,8 @@ typedef struct { typedef struct { mgreg_t regs [32]; - double fregs [32]; + /* FIXME not fully saved in trampolines */ + MonoContextSimdReg fregs [32]; mgreg_t pc; /* * fregs might not be initialized if this context was created from a @@ -478,22 +481,22 @@ typedef struct { "stp x30, xzr, [x16], #8\n" \ "mov x30, sp\n" \ "str x30, [x16], #8\n" \ - "stp d0, d1, [x16], #16\n" \ - "stp d2, d3, [x16], #16\n" \ - "stp d4, d5, [x16], #16\n" \ - "stp d6, d7, [x16], #16\n" \ - "stp d8, d9, [x16], #16\n" \ - "stp d10, d11, [x16], #16\n" \ - "stp d12, d13, [x16], #16\n" \ - "stp d14, d15, [x16], #16\n" \ - "stp d16, d17, [x16], #16\n" \ - "stp d18, d19, [x16], #16\n" \ - "stp d20, d21, [x16], #16\n" \ - "stp d22, d23, [x16], #16\n" \ - "stp d24, d25, [x16], #16\n" \ - "stp d26, d27, [x16], #16\n" \ - "stp d28, d29, [x16], #16\n" \ - "stp d30, d31, [x16], #16\n" \ + "stp q0, q1, [x16], #32\n" \ + "stp q2, q3, [x16], #32\n" \ + "stp q4, q5, [x16], #32\n" \ + "stp q6, q7, [x16], #32\n" \ + "stp q8, q9, [x16], #32\n" \ + "stp q10, q11, [x16], #32\n" \ + "stp q12, q13, [x16], #32\n" \ + "stp q14, q15, [x16], #32\n" \ + "stp q16, q17, [x16], #32\n" \ + "stp q18, q19, [x16], #32\n" \ + "stp q20, q21, [x16], #32\n" \ + "stp q22, q23, [x16], #32\n" \ + "stp q24, q25, [x16], #32\n" \ + "stp q26, q27, [x16], #32\n" \ + "stp q28, q29, [x16], #32\n" \ + "stp q30, q31, [x16], #32\n" \ : \ : "r" (&ctx.regs) \ : "x16", "x30", "memory" \