1 /**
2  * \file
3  */
4 
5 #ifndef __MONO_MONO_SIGCONTEXT_H__
6 #define __MONO_MONO_SIGCONTEXT_H__
7 
8 #include <config.h>
9 #if defined(HOST_ANDROID)
10 #include <asm/sigcontext.h>
11 #endif
12 
13 #ifdef HAVE_UCONTEXT_H
14 #include <ucontext.h>
15 #endif
16 
17 #ifdef HAVE_UNISTD_H
18 #include <unistd.h>
19 #endif
20 
21 #ifdef HAVE_SIGNAL_H
22 #include <signal.h>
23 #endif
24 
25 #if defined(TARGET_X86)
26 
27 #if defined(__APPLE__)
28 #include <AvailabilityMacros.h>
29 #endif
30 
31 #if defined(__FreeBSD__) || defined(__FreeBSD_kernel__) || defined(__DragonFly__)
32 	#define UCONTEXT_REG_EAX(ctx) (((ucontext_t*)(ctx))->uc_mcontext.mc_eax)
33 	#define UCONTEXT_REG_EBX(ctx) (((ucontext_t*)(ctx))->uc_mcontext.mc_ebx)
34 	#define UCONTEXT_REG_ECX(ctx) (((ucontext_t*)(ctx))->uc_mcontext.mc_ecx)
35 	#define UCONTEXT_REG_EDX(ctx) (((ucontext_t*)(ctx))->uc_mcontext.mc_edx)
36 	#define UCONTEXT_REG_EBP(ctx) (((ucontext_t*)(ctx))->uc_mcontext.mc_ebp)
37 	#define UCONTEXT_REG_ESP(ctx) (((ucontext_t*)(ctx))->uc_mcontext.mc_esp)
38 	#define UCONTEXT_REG_ESI(ctx) (((ucontext_t*)(ctx))->uc_mcontext.mc_esi)
39 	#define UCONTEXT_REG_EDI(ctx) (((ucontext_t*)(ctx))->uc_mcontext.mc_edi)
40 	#define UCONTEXT_REG_EIP(ctx) (((ucontext_t*)(ctx))->uc_mcontext.mc_eip)
41 #elif defined(__APPLE__)
42 #  if defined (TARGET_IOS) || (MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_5)
43 	#define UCONTEXT_REG_EAX(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__eax)
44 	#define UCONTEXT_REG_EBX(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__ebx)
45 	#define UCONTEXT_REG_ECX(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__ecx)
46 	#define UCONTEXT_REG_EDX(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__edx)
47 	#define UCONTEXT_REG_EBP(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__ebp)
48 	#define UCONTEXT_REG_ESP(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__esp)
49 	#define UCONTEXT_REG_ESI(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__esi)
50 	#define UCONTEXT_REG_EDI(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__edi)
51 	#define UCONTEXT_REG_EIP(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__eip)
52 	#define UCONTEXT_HAS_XMM(_ctx) (TRUE)
53 	#define UCONTEXT_REG_XMM0(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__fs.__fpu_xmm0)
54 	#define UCONTEXT_REG_XMM1(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__fs.__fpu_xmm1)
55 	#define UCONTEXT_REG_XMM2(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__fs.__fpu_xmm2)
56 	#define UCONTEXT_REG_XMM3(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__fs.__fpu_xmm3)
57 	#define UCONTEXT_REG_XMM4(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__fs.__fpu_xmm4)
58 	#define UCONTEXT_REG_XMM5(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__fs.__fpu_xmm5)
59 	#define UCONTEXT_REG_XMM6(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__fs.__fpu_xmm6)
60 	#define UCONTEXT_REG_XMM7(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__fs.__fpu_xmm7)
61 #  else
62 	#define UCONTEXT_REG_EAX(ctx) (((ucontext_t*)(ctx))->uc_mcontext->ss.eax)
63 	#define UCONTEXT_REG_EBX(ctx) (((ucontext_t*)(ctx))->uc_mcontext->ss.ebx)
64 	#define UCONTEXT_REG_ECX(ctx) (((ucontext_t*)(ctx))->uc_mcontext->ss.ecx)
65 	#define UCONTEXT_REG_EDX(ctx) (((ucontext_t*)(ctx))->uc_mcontext->ss.edx)
66 	#define UCONTEXT_REG_EBP(ctx) (((ucontext_t*)(ctx))->uc_mcontext->ss.ebp)
67 	#define UCONTEXT_REG_ESP(ctx) (((ucontext_t*)(ctx))->uc_mcontext->ss.esp)
68 	#define UCONTEXT_REG_ESI(ctx) (((ucontext_t*)(ctx))->uc_mcontext->ss.esi)
69 	#define UCONTEXT_REG_EDI(ctx) (((ucontext_t*)(ctx))->uc_mcontext->ss.edi)
70 	#define UCONTEXT_REG_EIP(ctx) (((ucontext_t*)(ctx))->uc_mcontext->ss.eip)
71 #  endif
72 #elif defined(__NetBSD__)
73 	#define UCONTEXT_REG_EAX(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_EAX])
74 	#define UCONTEXT_REG_EBX(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_EBX])
75 	#define UCONTEXT_REG_ECX(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_ECX])
76 	#define UCONTEXT_REG_EDX(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_EDX])
77 	#define UCONTEXT_REG_EBP(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_EBP])
78 	#define UCONTEXT_REG_ESP(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_ESP])
79 	#define UCONTEXT_REG_ESI(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_ESI])
80 	#define UCONTEXT_REG_EDI(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_EDI])
81 	#define UCONTEXT_REG_EIP(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_EIP])
82 #elif defined(__OpenBSD__)
83     #define UCONTEXT_REG_EAX(ctx) (((ucontext_t*)(ctx))->sc_eax)
84 	#define UCONTEXT_REG_EBX(ctx) (((ucontext_t*)(ctx))->sc_ebx)
85 	#define UCONTEXT_REG_ECX(ctx) (((ucontext_t*)(ctx))->sc_ecx)
86 	#define UCONTEXT_REG_EDX(ctx) (((ucontext_t*)(ctx))->sc_edx)
87 	#define UCONTEXT_REG_EBP(ctx) (((ucontext_t*)(ctx))->sc_ebp)
88 	#define UCONTEXT_REG_ESP(ctx) (((ucontext_t*)(ctx))->sc_esp)
89 	#define UCONTEXT_REG_ESI(ctx) (((ucontext_t*)(ctx))->sc_esi)
90 	#define UCONTEXT_REG_EDI(ctx) (((ucontext_t*)(ctx))->sc_edi)
91 	#define UCONTEXT_REG_EIP(ctx) (((ucontext_t*)(ctx))->sc_eip)
92 #elif defined(HOST_SOLARIS)
93 	#define UCONTEXT_REG_EAX(ctx) (((ucontext_t*)(ctx))->uc_mcontext.gregs [EAX])
94 	#define UCONTEXT_REG_EBX(ctx) (((ucontext_t*)(ctx))->uc_mcontext.gregs [EBX])
95 	#define UCONTEXT_REG_ECX(ctx) (((ucontext_t*)(ctx))->uc_mcontext.gregs [ECX])
96 	#define UCONTEXT_REG_EDX(ctx) (((ucontext_t*)(ctx))->uc_mcontext.gregs [EDX])
97 	#define UCONTEXT_REG_EBP(ctx) (((ucontext_t*)(ctx))->uc_mcontext.gregs [EBP])
98 	#define UCONTEXT_REG_ESP(ctx) (((ucontext_t*)(ctx))->uc_mcontext.gregs [ESP])
99 	#define UCONTEXT_REG_ESI(ctx) (((ucontext_t*)(ctx))->uc_mcontext.gregs [ESI])
100 	#define UCONTEXT_REG_EDI(ctx) (((ucontext_t*)(ctx))->uc_mcontext.gregs [EDI])
101 	#define UCONTEXT_REG_EIP(ctx) (((ucontext_t*)(ctx))->uc_mcontext.gregs [EIP])
102 #else
103 
104 #if defined(HOST_ANDROID) && !defined(HAVE_UCONTEXT_H)
105 /* No ucontext.h as of NDK v6b */
106 typedef int greg_t;
107 #define NGREG 19
108 typedef greg_t gregset_t [NGREG];
109 enum
110 {
111   REG_GS = 0,
112 # define REG_GS         REG_GS
113   REG_FS,
114 # define REG_FS         REG_FS
115   REG_ES,
116 # define REG_ES         REG_ES
117   REG_DS,
118 # define REG_DS         REG_DS
119   REG_EDI,
120 # define REG_EDI        REG_EDI
121   REG_ESI,
122 # define REG_ESI        REG_ESI
123   REG_EBP,
124 # define REG_EBP        REG_EBP
125   REG_ESP,
126 # define REG_ESP        REG_ESP
127   REG_EBX,
128 # define REG_EBX        REG_EBX
129   REG_EDX,
130 # define REG_EDX        REG_EDX
131   REG_ECX,
132 # define REG_ECX        REG_ECX
133   REG_EAX,
134 # define REG_EAX        REG_EAX
135   REG_TRAPNO,
136 # define REG_TRAPNO     REG_TRAPNO
137   REG_ERR,
138 # define REG_ERR        REG_ERR
139   REG_EIP,
140 # define REG_EIP        REG_EIP
141 };
142 
143 typedef struct {
144     gregset_t gregs;
145 	/* Many missing fields */
146 } mcontext_t;
147 
148 typedef struct ucontext {
149     unsigned long int uc_flags;
150     struct ucontext *uc_link;
151     stack_t uc_stack;
152     mcontext_t uc_mcontext;
153 	/* Many missing fields */
154 } ucontext_t;
155 
156 #endif
157 
158 	#define UCONTEXT_REG_EAX(ctx) (((ucontext_t*)(ctx))->uc_mcontext.gregs [REG_EAX])
159 	#define UCONTEXT_REG_EBX(ctx) (((ucontext_t*)(ctx))->uc_mcontext.gregs [REG_EBX])
160 	#define UCONTEXT_REG_ECX(ctx) (((ucontext_t*)(ctx))->uc_mcontext.gregs [REG_ECX])
161 	#define UCONTEXT_REG_EDX(ctx) (((ucontext_t*)(ctx))->uc_mcontext.gregs [REG_EDX])
162 	#define UCONTEXT_REG_EBP(ctx) (((ucontext_t*)(ctx))->uc_mcontext.gregs [REG_EBP])
163 	#define UCONTEXT_REG_ESP(ctx) (((ucontext_t*)(ctx))->uc_mcontext.gregs [REG_ESP])
164 	#define UCONTEXT_REG_ESI(ctx) (((ucontext_t*)(ctx))->uc_mcontext.gregs [REG_ESI])
165 	#define UCONTEXT_REG_EDI(ctx) (((ucontext_t*)(ctx))->uc_mcontext.gregs [REG_EDI])
166 	#define UCONTEXT_REG_EIP(ctx) (((ucontext_t*)(ctx))->uc_mcontext.gregs [REG_EIP])
167 #endif
168 
169 #elif defined(TARGET_AMD64)
170 
171 #if defined(__APPLE__)
172 	#define UCONTEXT_REG_RAX(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__rax)
173 	#define UCONTEXT_REG_RBX(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__rbx)
174 	#define UCONTEXT_REG_RCX(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__rcx)
175 	#define UCONTEXT_REG_RDX(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__rdx)
176 	#define UCONTEXT_REG_RBP(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__rbp)
177 	#define UCONTEXT_REG_RSP(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__rsp)
178 	#define UCONTEXT_REG_RSI(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__rsi)
179 	#define UCONTEXT_REG_RDI(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__rdi)
180 	#define UCONTEXT_REG_RIP(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__rip)
181 	#define UCONTEXT_REG_R8(ctx)  (((ucontext_t*)(ctx))->uc_mcontext->__ss.__r8)
182 	#define UCONTEXT_REG_R9(ctx)  (((ucontext_t*)(ctx))->uc_mcontext->__ss.__r9)
183 	#define UCONTEXT_REG_R10(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__r10)
184 	#define UCONTEXT_REG_R11(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__r11)
185 	#define UCONTEXT_REG_R12(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__r12)
186 	#define UCONTEXT_REG_R13(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__r13)
187 	#define UCONTEXT_REG_R14(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__r14)
188 	#define UCONTEXT_REG_R15(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__r15)
189 	#define UCONTEXT_HAS_XMM(_ctx) (TRUE)
190 	#define UCONTEXT_REG_XMM0(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__fs.__fpu_xmm0)
191 	#define UCONTEXT_REG_XMM1(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__fs.__fpu_xmm1)
192 	#define UCONTEXT_REG_XMM2(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__fs.__fpu_xmm2)
193 	#define UCONTEXT_REG_XMM3(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__fs.__fpu_xmm3)
194 	#define UCONTEXT_REG_XMM4(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__fs.__fpu_xmm4)
195 	#define UCONTEXT_REG_XMM5(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__fs.__fpu_xmm5)
196 	#define UCONTEXT_REG_XMM6(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__fs.__fpu_xmm6)
197 	#define UCONTEXT_REG_XMM7(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__fs.__fpu_xmm7)
198 	#define UCONTEXT_REG_XMM8(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__fs.__fpu_xmm8)
199 	#define UCONTEXT_REG_XMM9(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__fs.__fpu_xmm9)
200 	#define UCONTEXT_REG_XMM10(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__fs.__fpu_xmm10)
201 	#define UCONTEXT_REG_XMM11(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__fs.__fpu_xmm11)
202 	#define UCONTEXT_REG_XMM12(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__fs.__fpu_xmm12)
203 	#define UCONTEXT_REG_XMM13(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__fs.__fpu_xmm13)
204 	#define UCONTEXT_REG_XMM14(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__fs.__fpu_xmm14)
205 	#define UCONTEXT_REG_XMM15(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__fs.__fpu_xmm15)
206 #elif defined(__FreeBSD__) || defined(__FreeBSD_kernel__)
207 	#define UCONTEXT_REG_RAX(ctx) (((ucontext_t*)(ctx))->uc_mcontext.mc_rax)
208 	#define UCONTEXT_REG_RBX(ctx) (((ucontext_t*)(ctx))->uc_mcontext.mc_rbx)
209 	#define UCONTEXT_REG_RCX(ctx) (((ucontext_t*)(ctx))->uc_mcontext.mc_rcx)
210 	#define UCONTEXT_REG_RDX(ctx) (((ucontext_t*)(ctx))->uc_mcontext.mc_rdx)
211 	#define UCONTEXT_REG_RBP(ctx) (((ucontext_t*)(ctx))->uc_mcontext.mc_rbp)
212 	#define UCONTEXT_REG_RSP(ctx) (((ucontext_t*)(ctx))->uc_mcontext.mc_rsp)
213 	#define UCONTEXT_REG_RSI(ctx) (((ucontext_t*)(ctx))->uc_mcontext.mc_rsi)
214 	#define UCONTEXT_REG_RDI(ctx) (((ucontext_t*)(ctx))->uc_mcontext.mc_rdi)
215 	#define UCONTEXT_REG_RIP(ctx) (((ucontext_t*)(ctx))->uc_mcontext.mc_rip)
216 	#define UCONTEXT_REG_R8(ctx)  (((ucontext_t*)(ctx))->uc_mcontext.mc_r8)
217 	#define UCONTEXT_REG_R9(ctx)  (((ucontext_t*)(ctx))->uc_mcontext.mc_r9)
218 	#define UCONTEXT_REG_R10(ctx) (((ucontext_t*)(ctx))->uc_mcontext.mc_r10)
219 	#define UCONTEXT_REG_R11(ctx) (((ucontext_t*)(ctx))->uc_mcontext.mc_r11)
220 	#define UCONTEXT_REG_R12(ctx) (((ucontext_t*)(ctx))->uc_mcontext.mc_r12)
221 	#define UCONTEXT_REG_R13(ctx) (((ucontext_t*)(ctx))->uc_mcontext.mc_r13)
222 	#define UCONTEXT_REG_R14(ctx) (((ucontext_t*)(ctx))->uc_mcontext.mc_r14)
223 	#define UCONTEXT_REG_R15(ctx) (((ucontext_t*)(ctx))->uc_mcontext.mc_r15)
224 #elif defined(__NetBSD__)
225 	#define UCONTEXT_REG_RAX(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_RAX])
226 	#define UCONTEXT_REG_RBX(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_RBX])
227 	#define UCONTEXT_REG_RCX(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_RCX])
228 	#define UCONTEXT_REG_RDX(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_RDX])
229 	#define UCONTEXT_REG_RBP(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_RBP])
230 	#define UCONTEXT_REG_RSP(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_RSP])
231 	#define UCONTEXT_REG_RSI(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_RSI])
232 	#define UCONTEXT_REG_RDI(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_RDI])
233 	#define UCONTEXT_REG_RIP(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_RIP])
234 	#define UCONTEXT_REG_R8(ctx)  (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_R8])
235 	#define UCONTEXT_REG_R9(ctx)  (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_R9])
236 	#define UCONTEXT_REG_R10(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_R10])
237 	#define UCONTEXT_REG_R11(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_R11])
238 	#define UCONTEXT_REG_R12(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_R12])
239 	#define UCONTEXT_REG_R13(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_R13])
240 	#define UCONTEXT_REG_R14(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_R14])
241 	#define UCONTEXT_REG_R15(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_R15])
242 #elif defined(__OpenBSD__)
243     /* OpenBSD/amd64 has no gregs array, ucontext_t == sigcontext */
244 	#define UCONTEXT_REG_RAX(ctx) (((ucontext_t*)(ctx))->sc_rax)
245 	#define UCONTEXT_REG_RBX(ctx) (((ucontext_t*)(ctx))->sc_rbx)
246 	#define UCONTEXT_REG_RCX(ctx) (((ucontext_t*)(ctx))->sc_rcx)
247 	#define UCONTEXT_REG_RDX(ctx) (((ucontext_t*)(ctx))->sc_rdx)
248 	#define UCONTEXT_REG_RBP(ctx) (((ucontext_t*)(ctx))->sc_rbp)
249 	#define UCONTEXT_REG_RSP(ctx) (((ucontext_t*)(ctx))->sc_rsp)
250 	#define UCONTEXT_REG_RSI(ctx) (((ucontext_t*)(ctx))->sc_rsi)
251 	#define UCONTEXT_REG_RDI(ctx) (((ucontext_t*)(ctx))->sc_rdi)
252 	#define UCONTEXT_REG_RIP(ctx) (((ucontext_t*)(ctx))->sc_rip)
253 	#define UCONTEXT_REG_R8(ctx) (((ucontext_t*)(ctx))->sc_r8)
254 	#define UCONTEXT_REG_R9(ctx) (((ucontext_t*)(ctx))->sc_r9)
255 	#define UCONTEXT_REG_R10(ctx) (((ucontext_t*)(ctx))->sc_r10)
256 	#define UCONTEXT_REG_R11(ctx) (((ucontext_t*)(ctx))->sc_r11)
257 	#define UCONTEXT_REG_R12(ctx) (((ucontext_t*)(ctx))->sc_r12)
258 	#define UCONTEXT_REG_R13(ctx) (((ucontext_t*)(ctx))->sc_r13)
259 	#define UCONTEXT_REG_R14(ctx) (((ucontext_t*)(ctx))->sc_r14)
260 	#define UCONTEXT_REG_R15(ctx) (((ucontext_t*)(ctx))->sc_r15)
261 #elif !defined(HOST_WIN32)
262 	#define UCONTEXT_GREGS(ctx)	((guint64*)&(((ucontext_t*)(ctx))->uc_mcontext.gregs))
263 #if defined(__GLIBC__)
264 	/*
265 	 * Ordinarily, ctx->uc_mcontext.fpregs is a pointer to somewhere in
266 	 * ctx->__fpregs_mem and is the preferred way to access the fpstate.
267 	 * However, some versions of Windows Subsystem for Linux have a bug where
268 	 * the fpregs field is a NULL pointer instead. Since accessing __fpregs_mem
269 	 * directly is quite complicated because its exact layout depends on CPU
270 	 * features and/or kernel configuration, we sinply won't make the fpstate
271 	 * available if the fpregs pointer is NULL.
272 	 *
273 	 * This is of course not correct (as we won't scan XMM registers on those
274 	 * broken WSL versions), but it'll at least prevent a crash when accessing
275 	 * the fpregs pointer.
276 	 */
277 	#define UCONTEXT_HAS_FREGS(ctx) (!!((ucontext_t *) (ctx))->uc_mcontext.fpregs)
278 	#define UCONTEXT_FREGS(ctx)	(((ucontext_t *) (ctx))->uc_mcontext.fpregs->_xmm)
279 #endif
280 #endif
281 
282 #ifdef UCONTEXT_GREGS
283 #define UCONTEXT_REG_RAX(ctx) (UCONTEXT_GREGS ((ctx)) [REG_RAX])
284 #define UCONTEXT_REG_RBX(ctx) (UCONTEXT_GREGS ((ctx)) [REG_RBX])
285 #define UCONTEXT_REG_RCX(ctx) (UCONTEXT_GREGS ((ctx)) [REG_RCX])
286 #define UCONTEXT_REG_RDX(ctx) (UCONTEXT_GREGS ((ctx)) [REG_RDX])
287 #define UCONTEXT_REG_RBP(ctx) (UCONTEXT_GREGS ((ctx)) [REG_RBP])
288 #define UCONTEXT_REG_RSP(ctx) (UCONTEXT_GREGS ((ctx)) [REG_RSP])
289 #define UCONTEXT_REG_RSI(ctx) (UCONTEXT_GREGS ((ctx)) [REG_RSI])
290 #define UCONTEXT_REG_RDI(ctx) (UCONTEXT_GREGS ((ctx)) [REG_RDI])
291 #define UCONTEXT_REG_RIP(ctx) (UCONTEXT_GREGS ((ctx)) [REG_RIP])
292 #define UCONTEXT_REG_R8(ctx)  (UCONTEXT_GREGS ((ctx)) [REG_R8])
293 #define UCONTEXT_REG_R9(ctx)  (UCONTEXT_GREGS ((ctx)) [REG_R9])
294 #define UCONTEXT_REG_R10(ctx) (UCONTEXT_GREGS ((ctx)) [REG_R10])
295 #define UCONTEXT_REG_R11(ctx) (UCONTEXT_GREGS ((ctx)) [REG_R11])
296 #define UCONTEXT_REG_R12(ctx) (UCONTEXT_GREGS ((ctx)) [REG_R12])
297 #define UCONTEXT_REG_R13(ctx) (UCONTEXT_GREGS ((ctx)) [REG_R13])
298 #define UCONTEXT_REG_R14(ctx) (UCONTEXT_GREGS ((ctx)) [REG_R14])
299 #define UCONTEXT_REG_R15(ctx) (UCONTEXT_GREGS ((ctx)) [REG_R15])
300 #endif
301 
302 #ifdef UCONTEXT_FREGS
303 #define UCONTEXT_HAS_XMM(ctx)   (UCONTEXT_HAS_FREGS (ctx))
304 #define UCONTEXT_REG_XMM0(ctx)  (UCONTEXT_FREGS ((ctx)) [AMD64_XMM0])
305 #define UCONTEXT_REG_XMM1(ctx)  (UCONTEXT_FREGS ((ctx)) [AMD64_XMM1])
306 #define UCONTEXT_REG_XMM2(ctx)  (UCONTEXT_FREGS ((ctx)) [AMD64_XMM2])
307 #define UCONTEXT_REG_XMM3(ctx)  (UCONTEXT_FREGS ((ctx)) [AMD64_XMM3])
308 #define UCONTEXT_REG_XMM4(ctx)  (UCONTEXT_FREGS ((ctx)) [AMD64_XMM4])
309 #define UCONTEXT_REG_XMM5(ctx)  (UCONTEXT_FREGS ((ctx)) [AMD64_XMM5])
310 #define UCONTEXT_REG_XMM6(ctx)  (UCONTEXT_FREGS ((ctx)) [AMD64_XMM6])
311 #define UCONTEXT_REG_XMM7(ctx)  (UCONTEXT_FREGS ((ctx)) [AMD64_XMM7])
312 #define UCONTEXT_REG_XMM8(ctx)  (UCONTEXT_FREGS ((ctx)) [AMD64_XMM8])
313 #define UCONTEXT_REG_XMM9(ctx)  (UCONTEXT_FREGS ((ctx)) [AMD64_XMM9])
314 #define UCONTEXT_REG_XMM10(ctx) (UCONTEXT_FREGS ((ctx)) [AMD64_XMM10])
315 #define UCONTEXT_REG_XMM11(ctx) (UCONTEXT_FREGS ((ctx)) [AMD64_XMM11])
316 #define UCONTEXT_REG_XMM12(ctx) (UCONTEXT_FREGS ((ctx)) [AMD64_XMM12])
317 #define UCONTEXT_REG_XMM13(ctx) (UCONTEXT_FREGS ((ctx)) [AMD64_XMM13])
318 #define UCONTEXT_REG_XMM14(ctx) (UCONTEXT_FREGS ((ctx)) [AMD64_XMM14])
319 #define UCONTEXT_REG_XMM15(ctx) (UCONTEXT_FREGS ((ctx)) [AMD64_XMM15])
320 #endif
321 
322 #elif defined(__mono_ppc__)
323 
324 #if HAVE_UCONTEXT_H
325 #include <ucontext.h>
326 #endif
327 
328 #if defined(__linux__)
329 	typedef ucontext_t os_ucontext;
330 
331 #ifdef __mono_ppc64__
332 	#define UCONTEXT_REG_Rn(ctx, n)   (((os_ucontext*)(ctx))->uc_mcontext.gp_regs [(n)])
333 	#define UCONTEXT_REG_FPRn(ctx, n) (((os_ucontext*)(ctx))->uc_mcontext.fp_regs [(n)])
334 	#define UCONTEXT_REG_NIP(ctx)     (((os_ucontext*)(ctx))->uc_mcontext.gp_regs [PT_NIP])
335 	#define UCONTEXT_REG_LNK(ctx)     (((os_ucontext*)(ctx))->uc_mcontext.gp_regs [PT_LNK])
336 #else
337 	#define UCONTEXT_REG_Rn(ctx, n)   (((os_ucontext*)(ctx))->uc_mcontext.uc_regs->gregs [(n)])
338 	#define UCONTEXT_REG_FPRn(ctx, n) (((os_ucontext*)(ctx))->uc_mcontext.uc_regs->fpregs.fpregs [(n)])
339 	#define UCONTEXT_REG_NIP(ctx)     (((os_ucontext*)(ctx))->uc_mcontext.uc_regs->gregs [PT_NIP])
340 	#define UCONTEXT_REG_LNK(ctx)     (((os_ucontext*)(ctx))->uc_mcontext.uc_regs->gregs [PT_LNK])
341 #endif
342 #elif defined (__APPLE__) && defined (_STRUCT_MCONTEXT)
343 	typedef struct __darwin_ucontext os_ucontext;
344 
345 	#define UCONTEXT_REG_Rn(ctx, n)   ((&((os_ucontext*)(ctx))->uc_mcontext->__ss.__r0) [(n)])
346 	#define UCONTEXT_REG_FPRn(ctx, n) (((os_ucontext*)(ctx))->uc_mcontext->__fs.__fpregs [(n)])
347 	#define UCONTEXT_REG_NIP(ctx)     (((os_ucontext*)(ctx))->uc_mcontext->__ss.__srr0)
348 	#define UCONTEXT_REG_LNK(ctx)     (((os_ucontext*)(ctx))->uc_mcontext->__ss.__lr)
349 #elif defined (__APPLE__) && !defined (_STRUCT_MCONTEXT)
350 	typedef struct ucontext os_ucontext;
351 
352 	#define UCONTEXT_REG_Rn(ctx, n)   ((&((os_ucontext*)(ctx))->uc_mcontext->ss.r0) [(n)])
353 	#define UCONTEXT_REG_FPRn(ctx, n) (((os_ucontext*)(ctx))->uc_mcontext->fs.fpregs [(n)])
354 	#define UCONTEXT_REG_NIP(ctx)     (((os_ucontext*)(ctx))->uc_mcontext->ss.srr0)
355 	#define UCONTEXT_REG_LNK(ctx)     (((os_ucontext*)(ctx))->uc_mcontext->ss.lr)
356 #elif defined(__NetBSD__)
357 	typedef ucontext_t os_ucontext;
358 
359 	#define UCONTEXT_REG_Rn(ctx, n)   (((os_ucontext*)(ctx))->uc_mcontext.__gregs [(n)])
360 	#define UCONTEXT_REG_FPRn(ctx, n) (((os_ucontext*)(ctx))->uc_mcontext.__fpregs.__fpu_regs [(n)])
361 	#define UCONTEXT_REG_NIP(ctx)     _UC_MACHINE_PC(ctx)
362 	#define UCONTEXT_REG_LNK(ctx)     (((os_ucontext*)(ctx))->uc_mcontext.__gregs [_REG_LR])
363 #elif defined(__FreeBSD__)
364 	typedef ucontext_t os_ucontext;
365 
366 	#define UCONTEXT_REG_Rn(ctx, n)   (((os_ucontext*)(ctx))->uc_mcontext.mc_gpr [(n)])
367 	#define UCONTEXT_REG_FPRn(ctx, n) (((os_ucontext*)(ctx))->uc_mcontext.mc_fpreg [(n)])
368 	#define UCONTEXT_REG_NIP(ctx)     (((os_ucontext*)(ctx))->uc_mcontext.mc_srr0)
369 	#define UCONTEXT_REG_LNK(ctx)     (((os_ucontext*)(ctx))->uc_mcontext.mc_lr)
370 #endif
371 
372 #elif defined(TARGET_ARM)
373 #if defined(__APPLE__)
374 	typedef ucontext_t arm_ucontext;
375 
376 	#define UCONTEXT_REG_PC(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__pc)
377 	#define UCONTEXT_REG_SP(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__sp)
378 	#define UCONTEXT_REG_LR(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__lr)
379 	#define UCONTEXT_REG_R0(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__r[0])
380 	#define UCONTEXT_REG_R1(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__r[1])
381 	#define UCONTEXT_REG_R2(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__r[2])
382 	#define UCONTEXT_REG_R3(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__r[3])
383 	#define UCONTEXT_REG_R4(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__r[4])
384 	#define UCONTEXT_REG_R5(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__r[5])
385 	#define UCONTEXT_REG_R6(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__r[6])
386 	#define UCONTEXT_REG_R7(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__r[7])
387 	#define UCONTEXT_REG_R8(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__r[8])
388 	#define UCONTEXT_REG_R9(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__r[9])
389 	#define UCONTEXT_REG_R10(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__r[10])
390 	#define UCONTEXT_REG_R11(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__r[11])
391 	#define UCONTEXT_REG_R12(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__r[12])
392 	#define UCONTEXT_REG_CPSR(ctx) (((ucontext_t*)(ctx))->uc_mcontext->__ss.__cpsr)
393 	#define UCONTEXT_REG_VFPREGS(ctx) (double*)(((ucontext_t*)(ctx))->uc_mcontext->__fs.__r)
394 #elif defined(__linux__)
395 	typedef struct arm_ucontext {
396 		unsigned long       uc_flags;
397 		struct arm_ucontext *uc_link;
398 		struct {
399 			void *p;
400 			int flags;
401 			size_t size;
402 		} sstack_data;
403 		struct sigcontext sig_ctx;
404 		/* some 2.6.x kernel has fp data here after a few other fields
405 		* we don't use them for now...
406 		*/
407 	} arm_ucontext;
408 	#define UCONTEXT_REG_PC(ctx) (((arm_ucontext*)(ctx))->sig_ctx.arm_pc)
409 	#define UCONTEXT_REG_SP(ctx) (((arm_ucontext*)(ctx))->sig_ctx.arm_sp)
410 	#define UCONTEXT_REG_LR(ctx) (((arm_ucontext*)(ctx))->sig_ctx.arm_lr)
411 	#define UCONTEXT_REG_R0(ctx) (((arm_ucontext*)(ctx))->sig_ctx.arm_r0)
412 	#define UCONTEXT_REG_R1(ctx) (((arm_ucontext*)(ctx))->sig_ctx.arm_r1)
413 	#define UCONTEXT_REG_R2(ctx) (((arm_ucontext*)(ctx))->sig_ctx.arm_r2)
414 	#define UCONTEXT_REG_R3(ctx) (((arm_ucontext*)(ctx))->sig_ctx.arm_r3)
415 	#define UCONTEXT_REG_R4(ctx) (((arm_ucontext*)(ctx))->sig_ctx.arm_r4)
416 	#define UCONTEXT_REG_R5(ctx) (((arm_ucontext*)(ctx))->sig_ctx.arm_r5)
417 	#define UCONTEXT_REG_R6(ctx) (((arm_ucontext*)(ctx))->sig_ctx.arm_r6)
418 	#define UCONTEXT_REG_R7(ctx) (((arm_ucontext*)(ctx))->sig_ctx.arm_r7)
419 	#define UCONTEXT_REG_R8(ctx) (((arm_ucontext*)(ctx))->sig_ctx.arm_r8)
420 	#define UCONTEXT_REG_R9(ctx) (((arm_ucontext*)(ctx))->sig_ctx.arm_r9)
421 	#define UCONTEXT_REG_R10(ctx) (((arm_ucontext*)(ctx))->sig_ctx.arm_r10)
422 	#define UCONTEXT_REG_R11(ctx) (((arm_ucontext*)(ctx))->sig_ctx.arm_fp)
423 	#define UCONTEXT_REG_R12(ctx) (((arm_ucontext*)(ctx))->sig_ctx.arm_ip)
424 	#define UCONTEXT_REG_CPSR(ctx) (((arm_ucontext*)(ctx))->sig_ctx.arm_cpsr)
425 #elif defined(__NetBSD__)
426 	typedef ucontext_t arm_ucontext;
427 
428 	#define UCONTEXT_REG_PC(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_PC])
429 	#define UCONTEXT_REG_SP(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_SP])
430 	#define UCONTEXT_REG_LR(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_LR])
431 	#define UCONTEXT_REG_R0(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_R0])
432 	#define UCONTEXT_REG_R1(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_R1])
433 	#define UCONTEXT_REG_R2(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_R2])
434 	#define UCONTEXT_REG_R3(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_R3])
435 	#define UCONTEXT_REG_R4(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_R4])
436 	#define UCONTEXT_REG_R5(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_R5])
437 	#define UCONTEXT_REG_R6(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_R6])
438 	#define UCONTEXT_REG_R7(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_R7])
439 	#define UCONTEXT_REG_R8(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_R8])
440 	#define UCONTEXT_REG_R9(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_R9])
441 	#define UCONTEXT_REG_R10(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_R10])
442 	#define UCONTEXT_REG_R11(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_R11])
443 	#define UCONTEXT_REG_R12(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_R12])
444 	#define UCONTEXT_REG_CPSR(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_CPSR])
445 	#define UCONTEXT_REG_VFPREGS(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_VFPREGS])
446 #endif
447 
448 #elif defined(TARGET_ARM64)
449 
450 #if defined(MONO_CROSS_COMPILE)
451 	#define UCONTEXT_REG_PC(ctx) NULL
452 	#define UCONTEXT_REG_SP(ctx) NULL
453 	#define UCONTEXT_REG_R0(ctx) NULL
454 	#define UCONTEXT_GREGS(ctx) NULL
455 #elif defined(__APPLE__)
456 #include <machine/_mcontext.h>
457 #include <sys/_types/_ucontext64.h>
458 	/* mach/arm/_structs.h */
459 	#define UCONTEXT_REG_PC(ctx) (((ucontext64_t*)(ctx))->uc_mcontext64->__ss.__pc)
460 	#define UCONTEXT_REG_SP(ctx) (((ucontext64_t*)(ctx))->uc_mcontext64->__ss.__sp)
461 	#define UCONTEXT_REG_R0(ctx) (((ucontext64_t*)(ctx))->uc_mcontext64->__ss.__x [ARMREG_R0])
462 	#define UCONTEXT_GREGS(ctx) (&(((ucontext64_t*)(ctx))->uc_mcontext64->__ss.__x))
463 #elif defined(__FreeBSD__)
464 #include <ucontext.h>
465 	/* https://lists.freebsd.org/pipermail/freebsd-arm/2017-February/015611.html */
466 	#define UCONTEXT_REG_PC(ctx) (((ucontext_t*)(ctx))->uc_mcontext.mc_gpregs.gp_elr)
467 	#define UCONTEXT_REG_SP(ctx) (((ucontext_t*)(ctx))->uc_mcontext.mc_gpregs.gp_sp)
468 	#define UCONTEXT_REG_R0(ctx) (((ucontext_t*)(ctx))->uc_mcontext.mc_gpregs.gp_x [ARMREG_R0])
469 	#define UCONTEXT_GREGS(ctx) (&(((ucontext_t*)(ctx))->uc_mcontext.mc_gpregs.gp_x))
470 #else
471 #include <ucontext.h>
472 	#define UCONTEXT_REG_PC(ctx) (((ucontext_t*)(ctx))->uc_mcontext.pc)
473 	#define UCONTEXT_REG_SP(ctx) (((ucontext_t*)(ctx))->uc_mcontext.sp)
474 	#define UCONTEXT_REG_R0(ctx) (((ucontext_t*)(ctx))->uc_mcontext.regs [ARMREG_R0])
475 	#define UCONTEXT_GREGS(ctx) (&(((ucontext_t*)(ctx))->uc_mcontext.regs))
476 #endif
477 
478 #elif defined(__mips__)
479 
480 # if HAVE_UCONTEXT_H
481 #  include <ucontext.h>
482 # endif
483 
484 /* No ucontext.h */
485 #if defined(TARGET_ANDROID)
486 
487 #define NGREG   32
488 #define NFPREG  32
489 
490 typedef unsigned long gregset_t[NGREG];
491 
492 typedef struct fpregset {
493 	union {
494 		double  fp_dregs[NFPREG];
495 		struct {
496 			float           _fp_fregs;
497 			unsigned int    _fp_pad;
498 		} fp_fregs[NFPREG];
499 	} fp_r;
500 } fpregset_t;
501 
502 typedef struct
503   {
504     unsigned int regmask;
505     unsigned int status;
506     unsigned long pc;
507     gregset_t gregs;
508     fpregset_t fpregs;
509 	  /* missing fields follow */
510 } mcontext_t;
511 
512 typedef struct ucontext
513   {
514     unsigned long int uc_flags;
515     struct ucontext *uc_link;
516     stack_t uc_stack;
517     mcontext_t uc_mcontext;
518 	  /* missing fields follow */
519   } ucontext_t;
520 
521 #endif
522 
523 # define UCONTEXT_GREGS(ctx)	(((ucontext_t *)(ctx))->uc_mcontext.gregs)
524 # define UCONTEXT_FPREGS(ctx)	(((ucontext_t *)(ctx))->uc_mcontext.fpregs.fp_r.fp_dregs)
525 # define UCONTEXT_REG_PC(ctx)	(((ucontext_t *)(ctx))->uc_mcontext.pc)
526 
527 #elif defined(__s390x__)
528 
529 # if HAVE_UCONTEXT_H
530 #  include <ucontext.h>
531 # endif
532 
533 # define UCONTEXT_GREGS(ctx)	(((ucontext_t *)(ctx))->uc_mcontext.gregs)
534 #endif
535 
536 #endif
537