[tools] Add nuget-hash-extractor tool to help produce the runtime ignored assemblies...
[mono-project.git] / mono / utils / mono-context.c
blob7ab01d1481f174a6ce3320852faa1ad35367df1d
1 /*
2 * mono-context.c: plat independent machine state definitions
5 * Copyright (c) 2011 Novell, Inc (http://www.novell.com)
6 * Licensed under the MIT license. See LICENSE file in the project root for full license information.
7 */
9 #include <mono/utils/mono-sigcontext.h>
11 #ifdef HAVE_UCONTEXT_H
12 #include <ucontext.h>
13 #endif
15 #if (defined(__i386__) && !defined(MONO_CROSS_COMPILE)) || (defined(TARGET_X86))
17 #include <mono/utils/mono-context.h>
19 #ifdef HOST_WIN32
20 #include <windows.h>
21 #endif
23 #ifdef __sun
24 #define REG_EAX EAX
25 #define REG_EBX EBX
26 #define REG_ECX ECX
27 #define REG_EDX EDX
28 #define REG_EBP EBP
29 #define REG_ESP ESP
30 #define REG_ESI ESI
31 #define REG_EDI EDI
32 #define REG_EIP EIP
33 #endif
35 void
36 mono_sigctx_to_monoctx (void *sigctx, MonoContext *mctx)
38 #if defined (__native_client__) || defined (HOST_WATCHOS)
39 printf("WARNING: mono_arch_sigctx_to_monoctx() called!\n");
40 mctx->eax = 0xDEADBEEF;
41 mctx->ebx = 0xDEADBEEF;
42 mctx->ecx = 0xDEADBEEF;
43 mctx->edx = 0xDEADBEEF;
44 mctx->ebp = 0xDEADBEEF;
45 mctx->esp = 0xDEADBEEF;
46 mctx->esi = 0xDEADBEEF;
47 mctx->edi = 0xDEADBEEF;
48 mctx->eip = 0xDEADBEEF;
49 #elif MONO_CROSS_COMPILE
50 g_assert_not_reached ();
51 #elif defined(MONO_SIGNAL_USE_UCONTEXT_T)
52 ucontext_t *ctx = (ucontext_t*)sigctx;
54 mctx->eax = UCONTEXT_REG_EAX (ctx);
55 mctx->ebx = UCONTEXT_REG_EBX (ctx);
56 mctx->ecx = UCONTEXT_REG_ECX (ctx);
57 mctx->edx = UCONTEXT_REG_EDX (ctx);
58 mctx->ebp = UCONTEXT_REG_EBP (ctx);
59 mctx->esp = UCONTEXT_REG_ESP (ctx);
60 mctx->esi = UCONTEXT_REG_ESI (ctx);
61 mctx->edi = UCONTEXT_REG_EDI (ctx);
62 mctx->eip = UCONTEXT_REG_EIP (ctx);
63 #elif defined(HOST_WIN32)
64 CONTEXT *context = (CONTEXT*)sigctx;
66 mctx->eip = context->Eip;
67 mctx->edi = context->Edi;
68 mctx->esi = context->Esi;
69 mctx->ebx = context->Ebx;
70 mctx->edx = context->Edx;
71 mctx->ecx = context->Ecx;
72 mctx->eax = context->Eax;
73 mctx->ebp = context->Ebp;
74 mctx->esp = context->Esp;
75 #else
76 struct sigcontext *ctx = (struct sigcontext *)sigctx;
78 mctx->eax = ctx->SC_EAX;
79 mctx->ebx = ctx->SC_EBX;
80 mctx->ecx = ctx->SC_ECX;
81 mctx->edx = ctx->SC_EDX;
82 mctx->ebp = ctx->SC_EBP;
83 mctx->esp = ctx->SC_ESP;
84 mctx->esi = ctx->SC_ESI;
85 mctx->edi = ctx->SC_EDI;
86 mctx->eip = ctx->SC_EIP;
87 #endif /* if defined(__native_client__) */
90 void
91 mono_monoctx_to_sigctx (MonoContext *mctx, void *sigctx)
93 #if defined(__native_client__) || defined(HOST_WATCHOS)
94 printf("WARNING: mono_arch_monoctx_to_sigctx() called!\n");
95 #elif MONO_CROSS_COMPILE
96 g_assert_not_reached ();
97 #elif defined(MONO_SIGNAL_USE_UCONTEXT_T)
98 ucontext_t *ctx = (ucontext_t*)sigctx;
100 UCONTEXT_REG_EAX (ctx) = mctx->eax;
101 UCONTEXT_REG_EBX (ctx) = mctx->ebx;
102 UCONTEXT_REG_ECX (ctx) = mctx->ecx;
103 UCONTEXT_REG_EDX (ctx) = mctx->edx;
104 UCONTEXT_REG_EBP (ctx) = mctx->ebp;
105 UCONTEXT_REG_ESP (ctx) = mctx->esp;
106 UCONTEXT_REG_ESI (ctx) = mctx->esi;
107 UCONTEXT_REG_EDI (ctx) = mctx->edi;
108 UCONTEXT_REG_EIP (ctx) = mctx->eip;
109 #elif defined(HOST_WIN32)
110 CONTEXT *context = (CONTEXT*)sigctx;
112 context->Eip = mctx->eip;
113 context->Edi = mctx->edi;
114 context->Esi = mctx->esi;
115 context->Ebx = mctx->ebx;
116 context->Edx = mctx->edx;
117 context->Ecx = mctx->ecx;
118 context->Eax = mctx->eax;
119 context->Ebp = mctx->ebp;
120 context->Esp = mctx->esp;
121 #else
122 struct sigcontext *ctx = (struct sigcontext *)sigctx;
124 ctx->SC_EAX = mctx->eax;
125 ctx->SC_EBX = mctx->ebx;
126 ctx->SC_ECX = mctx->ecx;
127 ctx->SC_EDX = mctx->edx;
128 ctx->SC_EBP = mctx->ebp;
129 ctx->SC_ESP = mctx->esp;
130 ctx->SC_ESI = mctx->esi;
131 ctx->SC_EDI = mctx->edi;
132 ctx->SC_EIP = mctx->eip;
133 #endif /* __native_client__ */
136 #elif (defined(__x86_64__) && !defined(MONO_CROSS_COMPILE)) || (defined(TARGET_AMD64)) /* defined(__i386__) */
138 #include <mono/utils/mono-context.h>
140 #ifdef HOST_WIN32
141 #include <windows.h>
142 #endif
144 void
145 mono_sigctx_to_monoctx (void *sigctx, MonoContext *mctx)
147 #if defined(__native_client_codegen__) || defined(__native_client__)
148 printf("WARNING: mono_arch_sigctx_to_monoctx() called!\n");
149 #endif
151 #ifdef MONO_CROSS_COMPILE
152 g_assert_not_reached ();
153 #elif defined(MONO_SIGNAL_USE_UCONTEXT_T)
154 ucontext_t *ctx = (ucontext_t*)sigctx;
156 mctx->gregs [AMD64_RAX] = UCONTEXT_REG_RAX (ctx);
157 mctx->gregs [AMD64_RBX] = UCONTEXT_REG_RBX (ctx);
158 mctx->gregs [AMD64_RCX] = UCONTEXT_REG_RCX (ctx);
159 mctx->gregs [AMD64_RDX] = UCONTEXT_REG_RDX (ctx);
160 mctx->gregs [AMD64_RBP] = UCONTEXT_REG_RBP (ctx);
161 mctx->gregs [AMD64_RSP] = UCONTEXT_REG_RSP (ctx);
162 mctx->gregs [AMD64_RSI] = UCONTEXT_REG_RSI (ctx);
163 mctx->gregs [AMD64_RDI] = UCONTEXT_REG_RDI (ctx);
164 mctx->gregs [AMD64_R8] = UCONTEXT_REG_R8 (ctx);
165 mctx->gregs [AMD64_R9] = UCONTEXT_REG_R9 (ctx);
166 mctx->gregs [AMD64_R10] = UCONTEXT_REG_R10 (ctx);
167 mctx->gregs [AMD64_R11] = UCONTEXT_REG_R11 (ctx);
168 mctx->gregs [AMD64_R12] = UCONTEXT_REG_R12 (ctx);
169 mctx->gregs [AMD64_R13] = UCONTEXT_REG_R13 (ctx);
170 mctx->gregs [AMD64_R14] = UCONTEXT_REG_R14 (ctx);
171 mctx->gregs [AMD64_R15] = UCONTEXT_REG_R15 (ctx);
172 mctx->gregs [AMD64_RIP] = UCONTEXT_REG_RIP (ctx);
174 #ifdef UCONTEXT_REG_XMM
175 mctx->fregs [0] = UCONTEXT_REG_XMM0 (ctx);
176 mctx->fregs [1] = UCONTEXT_REG_XMM1 (ctx);
177 mctx->fregs [2] = UCONTEXT_REG_XMM2 (ctx);
178 mctx->fregs [3] = UCONTEXT_REG_XMM3 (ctx);
179 mctx->fregs [4] = UCONTEXT_REG_XMM4 (ctx);
180 mctx->fregs [5] = UCONTEXT_REG_XMM5 (ctx);
181 mctx->fregs [6] = UCONTEXT_REG_XMM6 (ctx);
182 mctx->fregs [7] = UCONTEXT_REG_XMM7 (ctx);
183 mctx->fregs [8] = UCONTEXT_REG_XMM8 (ctx);
184 mctx->fregs [9] = UCONTEXT_REG_XMM9 (ctx);
185 mctx->fregs [10] = UCONTEXT_REG_XMM10 (ctx);
186 mctx->fregs [11] = UCONTEXT_REG_XMM11 (ctx);
187 mctx->fregs [12] = UCONTEXT_REG_XMM12 (ctx);
188 mctx->fregs [13] = UCONTEXT_REG_XMM13 (ctx);
189 mctx->fregs [14] = UCONTEXT_REG_XMM14 (ctx);
190 mctx->fregs [15] = UCONTEXT_REG_XMM15 (ctx);
191 #endif
193 #elif defined(HOST_WIN32)
194 CONTEXT *context = (CONTEXT*)sigctx;
196 mctx->gregs [AMD64_RIP] = context->Rip;
197 mctx->gregs [AMD64_RAX] = context->Rax;
198 mctx->gregs [AMD64_RCX] = context->Rcx;
199 mctx->gregs [AMD64_RDX] = context->Rdx;
200 mctx->gregs [AMD64_RBX] = context->Rbx;
201 mctx->gregs [AMD64_RSP] = context->Rsp;
202 mctx->gregs [AMD64_RBP] = context->Rbp;
203 mctx->gregs [AMD64_RSI] = context->Rsi;
204 mctx->gregs [AMD64_RDI] = context->Rdi;
205 mctx->gregs [AMD64_R8] = context->R8;
206 mctx->gregs [AMD64_R9] = context->R9;
207 mctx->gregs [AMD64_R10] = context->R10;
208 mctx->gregs [AMD64_R11] = context->R11;
209 mctx->gregs [AMD64_R12] = context->R12;
210 mctx->gregs [AMD64_R13] = context->R13;
211 mctx->gregs [AMD64_R14] = context->R14;
212 mctx->gregs [AMD64_R15] = context->R15;
213 #else
214 g_assert_not_reached ();
215 #endif
218 void
219 mono_monoctx_to_sigctx (MonoContext *mctx, void *sigctx)
221 #if defined(__native_client__) || defined(__native_client_codegen__)
222 printf("WARNING: mono_arch_monoctx_to_sigctx() called!\n");
223 #endif
225 #ifdef MONO_CROSS_COMPILE
226 g_assert_not_reached ();
227 #elif defined(MONO_SIGNAL_USE_UCONTEXT_T)
228 ucontext_t *ctx = (ucontext_t*)sigctx;
230 UCONTEXT_REG_RAX (ctx) = mctx->gregs [AMD64_RAX];
231 UCONTEXT_REG_RBX (ctx) = mctx->gregs [AMD64_RBX];
232 UCONTEXT_REG_RCX (ctx) = mctx->gregs [AMD64_RCX];
233 UCONTEXT_REG_RDX (ctx) = mctx->gregs [AMD64_RDX];
234 UCONTEXT_REG_RBP (ctx) = mctx->gregs [AMD64_RBP];
235 UCONTEXT_REG_RSP (ctx) = mctx->gregs [AMD64_RSP];
236 UCONTEXT_REG_RSI (ctx) = mctx->gregs [AMD64_RSI];
237 UCONTEXT_REG_RDI (ctx) = mctx->gregs [AMD64_RDI];
238 UCONTEXT_REG_R8 (ctx) = mctx->gregs [AMD64_R8];
239 UCONTEXT_REG_R9 (ctx) = mctx->gregs [AMD64_R9];
240 UCONTEXT_REG_R10 (ctx) = mctx->gregs [AMD64_R10];
241 UCONTEXT_REG_R11 (ctx) = mctx->gregs [AMD64_R11];
242 UCONTEXT_REG_R12 (ctx) = mctx->gregs [AMD64_R12];
243 UCONTEXT_REG_R13 (ctx) = mctx->gregs [AMD64_R13];
244 UCONTEXT_REG_R14 (ctx) = mctx->gregs [AMD64_R14];
245 UCONTEXT_REG_R15 (ctx) = mctx->gregs [AMD64_R15];
246 UCONTEXT_REG_RIP (ctx) = mctx->gregs [AMD64_RIP];
248 #ifdef UCONTEXT_REG_XMM
249 UCONTEXT_REG_XMM0 (ctx) = mctx->fregs [0];
250 UCONTEXT_REG_XMM1 (ctx) = mctx->fregs [1];
251 UCONTEXT_REG_XMM2 (ctx) = mctx->fregs [2];
252 UCONTEXT_REG_XMM3 (ctx) = mctx->fregs [3];
253 UCONTEXT_REG_XMM4 (ctx) = mctx->fregs [4];
254 UCONTEXT_REG_XMM5 (ctx) = mctx->fregs [5];
255 UCONTEXT_REG_XMM6 (ctx) = mctx->fregs [6];
256 UCONTEXT_REG_XMM7 (ctx) = mctx->fregs [7];
257 UCONTEXT_REG_XMM8 (ctx) = mctx->fregs [8];
258 UCONTEXT_REG_XMM9 (ctx) = mctx->fregs [9];
259 UCONTEXT_REG_XMM10 (ctx) = mctx->fregs [10];
260 UCONTEXT_REG_XMM11 (ctx) = mctx->fregs [11];
261 UCONTEXT_REG_XMM12 (ctx) = mctx->fregs [12];
262 UCONTEXT_REG_XMM13 (ctx) = mctx->fregs [13];
263 UCONTEXT_REG_XMM14 (ctx) = mctx->fregs [14];
264 UCONTEXT_REG_XMM15 (ctx) = mctx->fregs [15];
265 #endif
267 #elif defined(HOST_WIN32)
268 CONTEXT *context = (CONTEXT*)sigctx;
270 context->Rip = mctx->gregs [AMD64_RIP];
271 context->Rax = mctx->gregs [AMD64_RAX];
272 context->Rcx = mctx->gregs [AMD64_RCX];
273 context->Rdx = mctx->gregs [AMD64_RDX];
274 context->Rbx = mctx->gregs [AMD64_RBX];
275 context->Rsp = mctx->gregs [AMD64_RSP];
276 context->Rbp = mctx->gregs [AMD64_RBP];
277 context->Rsi = mctx->gregs [AMD64_RSI];
278 context->Rdi = mctx->gregs [AMD64_RDI];
279 context->R8 = mctx->gregs [AMD64_R8];
280 context->R9 = mctx->gregs [AMD64_R9];
281 context->R10 = mctx->gregs [AMD64_R10];
282 context->R11 = mctx->gregs [AMD64_R11];
283 context->R12 = mctx->gregs [AMD64_R12];
284 context->R13 = mctx->gregs [AMD64_R13];
285 context->R14 = mctx->gregs [AMD64_R14];
286 context->R15 = mctx->gregs [AMD64_R15];
287 #else
288 g_assert_not_reached ();
289 #endif
292 #elif defined(__s390x__)
294 #include <mono/utils/mono-context.h>
296 /*------------------------------------------------------------------*/
297 /* */
298 /* Name - mono_arch_sigctx_to_monoctx. */
299 /* */
300 /* Function - Called from the signal handler to convert signal */
301 /* context to MonoContext. */
302 /* */
303 /*------------------------------------------------------------------*/
305 void
306 mono_sigctx_to_monoctx (void *ctx, MonoContext *mctx)
308 memcpy (mctx, ctx, sizeof(MonoContext));
311 /*========================= End of Function ========================*/
313 /*------------------------------------------------------------------*/
314 /* */
315 /* Name - mono_arch_monoctx_to_sigctx. */
316 /* */
317 /* Function - Convert MonoContext structure to signal context. */
318 /* */
319 /*------------------------------------------------------------------*/
321 void
322 mono_monoctx_to_sigctx (MonoContext *mctx, void *ctx)
324 memcpy (ctx, mctx, sizeof(MonoContext));
327 /*========================= End of Function ========================*/
329 #elif (defined(__arm__) && !defined(MONO_CROSS_COMPILE)) || (defined(TARGET_ARM))
331 #include <mono/utils/mono-context.h>
332 #include <mono/arch/arm/arm-codegen.h>
333 #include <mono/arch/arm/arm-vfp-codegen.h>
335 void
336 mono_sigctx_to_monoctx (void *sigctx, MonoContext *mctx)
338 #ifdef MONO_CROSS_COMPILE
339 g_assert_not_reached ();
340 #elif defined(__native_client__)
341 g_assert_not_reached ();
342 #else
343 arm_ucontext *my_uc = sigctx;
345 mctx->pc = UCONTEXT_REG_PC (my_uc);
346 mctx->regs [ARMREG_SP] = UCONTEXT_REG_SP (my_uc);
347 mctx->cpsr = UCONTEXT_REG_CPSR (my_uc);
348 memcpy (&mctx->regs, &UCONTEXT_REG_R0 (my_uc), sizeof (mgreg_t) * 16);
349 #ifdef UCONTEXT_REG_VFPREGS
350 memcpy (&mctx->fregs, UCONTEXT_REG_VFPREGS (my_uc), sizeof (double) * 16);
351 #endif
352 #endif
355 void
356 mono_monoctx_to_sigctx (MonoContext *mctx, void *ctx)
358 #ifdef MONO_CROSS_COMPILE
359 g_assert_not_reached ();
360 #elif defined(__native_client__)
361 g_assert_not_reached ();
362 #else
363 arm_ucontext *my_uc = ctx;
365 UCONTEXT_REG_PC (my_uc) = mctx->pc;
366 UCONTEXT_REG_SP (my_uc) = mctx->regs [ARMREG_SP];
367 UCONTEXT_REG_CPSR (my_uc) = mctx->cpsr;
368 /* The upper registers are not guaranteed to be valid */
369 memcpy (&UCONTEXT_REG_R0 (my_uc), &mctx->regs, sizeof (mgreg_t) * 12);
370 #ifdef UCONTEXT_REG_VFPREGS
371 memcpy (UCONTEXT_REG_VFPREGS (my_uc), &mctx->fregs, sizeof (double) * 16);
372 #endif
373 #endif
376 #elif (defined(__aarch64__) && !defined(MONO_CROSS_COMPILE)) || (defined(TARGET_ARM64))
378 #include <mono/utils/mono-context.h>
380 void
381 mono_sigctx_to_monoctx (void *sigctx, MonoContext *mctx)
383 #ifdef MONO_CROSS_COMPILE
384 g_assert_not_reached ();
385 #else
386 memcpy (mctx->regs, UCONTEXT_GREGS (sigctx), sizeof (mgreg_t) * 31);
387 mctx->pc = UCONTEXT_REG_PC (sigctx);
388 mctx->regs [ARMREG_SP] = UCONTEXT_REG_SP (sigctx);
389 #ifdef __linux__
390 struct fpsimd_context *fpctx = (struct fpsimd_context*)&((ucontext_t*)sigctx)->uc_mcontext.__reserved;
391 int i;
393 g_assert (fpctx->head.magic == FPSIMD_MAGIC);
394 for (i = 0; i < 32; ++i)
395 /* Only store the bottom 8 bytes for now */
396 *(guint64*)&(mctx->fregs [i]) = fpctx->vregs [i];
397 #endif
398 /* FIXME: apple */
399 #endif
402 void
403 mono_monoctx_to_sigctx (MonoContext *mctx, void *sigctx)
405 #ifdef MONO_CROSS_COMPILE
406 g_assert_not_reached ();
407 #else
408 memcpy (UCONTEXT_GREGS (sigctx), mctx->regs, sizeof (mgreg_t) * 31);
409 UCONTEXT_REG_PC (sigctx) = mctx->pc;
410 UCONTEXT_REG_SP (sigctx) = mctx->regs [ARMREG_SP];
411 #endif
414 #elif (defined(__mips__) && !defined(MONO_CROSS_COMPILE)) || (defined(TARGET_MIPS))
416 #include <mono/utils/mono-context.h>
417 #include <mono/arch/mips/mips-codegen.h>
419 void
420 mono_sigctx_to_monoctx (void *sigctx, MonoContext *mctx)
422 int i;
424 mctx->sc_pc = UCONTEXT_REG_PC (sigctx);
425 for (i = 0; i < 32; ++i) {
426 mctx->sc_regs[i] = UCONTEXT_GREGS (sigctx) [i];
427 mctx->sc_fpregs[i] = UCONTEXT_FPREGS (sigctx) [i];
431 void
432 mono_monoctx_to_sigctx (MonoContext *mctx, void *sigctx)
434 int i;
436 UCONTEXT_REG_PC (sigctx) = mctx->sc_pc;
437 for (i = 0; i < 32; ++i) {
438 UCONTEXT_GREGS (sigctx) [i] = mctx->sc_regs[i];
439 UCONTEXT_FPREGS (sigctx) [i] = mctx->sc_fpregs[i];
443 #elif (((defined(__ppc__) || defined(__powerpc__) || defined(__ppc64__)) && !defined(MONO_CROSS_COMPILE))) || (defined(TARGET_POWERPC))
445 #include <mono/utils/mono-context.h>
446 #include <mono/mini/mini-ppc.h>
448 void
449 mono_sigctx_to_monoctx (void *sigctx, MonoContext *mctx)
451 os_ucontext *uc = sigctx;
453 mctx->sc_ir = UCONTEXT_REG_NIP(uc);
454 mctx->sc_sp = UCONTEXT_REG_Rn(uc, 1);
455 memcpy (&mctx->regs, &UCONTEXT_REG_Rn(uc, 13), sizeof (mgreg_t) * MONO_SAVED_GREGS);
456 memcpy (&mctx->fregs, &UCONTEXT_REG_FPRn(uc, 14), sizeof (double) * MONO_SAVED_FREGS);
459 void
460 mono_monoctx_to_sigctx (MonoContext *mctx, void *sigctx)
462 os_ucontext *uc = sigctx;
464 UCONTEXT_REG_NIP(uc) = mctx->sc_ir;
465 UCONTEXT_REG_Rn(uc, 1) = mctx->sc_sp;
466 memcpy (&UCONTEXT_REG_Rn(uc, 13), &mctx->regs, sizeof (mgreg_t) * MONO_SAVED_GREGS);
467 memcpy (&UCONTEXT_REG_FPRn(uc, 14), &mctx->fregs, sizeof (double) * MONO_SAVED_FREGS);
470 #endif /* #if defined(__i386__) */