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
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));
/* 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;
/* 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;
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,
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;
#elif defined(__linux__)
typedef struct _libc_xmmreg MonoContextSimdReg;
#endif
+#elif defined(TARGET_ARM64)
+typedef __uint128_t MonoContextSimdReg;
#endif
/*
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
"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" \