1 /* 2 * Copyright (C) 2014 The Android Open Source Project 3 * All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions 7 * are met: 8 * * Redistributions of source code must retain the above copyright 9 * notice, this list of conditions and the following disclaimer. 10 * * Redistributions in binary form must reproduce the above copyright 11 * notice, this list of conditions and the following disclaimer in 12 * the documentation and/or other materials provided with the 13 * distribution. 14 * 15 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 16 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 17 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS 18 * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE 19 * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, 20 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, 21 * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS 22 * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED 23 * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, 24 * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT 25 * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 26 * SUCH DAMAGE. 27 */ 28 29 #ifndef _SYS_UCONTEXT_H_ 30 #define _SYS_UCONTEXT_H_ 31 32 #include <signal.h> 33 #include <sys/user.h> 34 35 __BEGIN_DECLS 36 37 #if defined(__arm__) 38 39 enum { 40 REG_R0 = 0, 41 REG_R1, 42 REG_R2, 43 REG_R3, 44 REG_R4, 45 REG_R5, 46 REG_R6, 47 REG_R7, 48 REG_R8, 49 REG_R9, 50 REG_R10, 51 REG_R11, 52 REG_R12, 53 REG_R13, 54 REG_R14, 55 REG_R15, 56 }; 57 58 #define NGREG 18 /* Like glibc. */ 59 60 typedef int greg_t; 61 typedef greg_t gregset_t[NGREG]; 62 typedef struct user_fpregs fpregset_t; 63 64 #include <asm/sigcontext.h> 65 typedef struct sigcontext mcontext_t; 66 67 typedef struct ucontext { 68 unsigned long uc_flags; 69 struct ucontext* uc_link; 70 stack_t uc_stack; 71 mcontext_t uc_mcontext; 72 sigset_t uc_sigmask; 73 // Android has a wrong (smaller) sigset_t on ARM. 74 uint32_t __padding_rt_sigset; 75 // The kernel adds extra padding after uc_sigmask to match glibc sigset_t on ARM. 76 char __padding[120]; 77 unsigned long uc_regspace[128] __attribute__((__aligned__(8))); 78 } ucontext_t; 79 80 #elif defined(__aarch64__) 81 82 #define NGREG 34 /* x0..x30 + sp + pc + pstate */ 83 typedef unsigned long greg_t; 84 typedef greg_t gregset_t[NGREG]; 85 typedef struct user_fpsimd_struct fpregset_t; 86 87 #include <asm/sigcontext.h> 88 typedef struct sigcontext mcontext_t; 89 90 typedef struct ucontext { 91 unsigned long uc_flags; 92 struct ucontext *uc_link; 93 stack_t uc_stack; 94 sigset_t uc_sigmask; 95 // The kernel adds extra padding after uc_sigmask to match glibc sigset_t on ARM64. 96 char __padding[128 - sizeof(sigset_t)]; 97 mcontext_t uc_mcontext; 98 } ucontext_t; 99 100 #elif defined(__i386__) 101 102 enum { 103 REG_GS = 0, 104 REG_FS, 105 REG_ES, 106 REG_DS, 107 REG_EDI, 108 REG_ESI, 109 REG_EBP, 110 REG_ESP, 111 REG_EBX, 112 REG_EDX, 113 REG_ECX, 114 REG_EAX, 115 REG_TRAPNO, 116 REG_ERR, 117 REG_EIP, 118 REG_CS, 119 REG_EFL, 120 REG_UESP, 121 REG_SS, 122 NGREG 123 }; 124 125 typedef int greg_t; 126 typedef greg_t gregset_t[NGREG]; 127 128 struct _libc_fpreg { 129 unsigned short significand[4]; 130 unsigned short exponent; 131 }; 132 133 struct _libc_fpstate { 134 unsigned long cw; 135 unsigned long sw; 136 unsigned long tag; 137 unsigned long ipoff; 138 unsigned long cssel; 139 unsigned long dataoff; 140 unsigned long datasel; 141 struct _libc_fpreg _st[8]; 142 unsigned long status; 143 }; 144 145 typedef struct _libc_fpstate* fpregset_t; 146 147 typedef struct { 148 gregset_t gregs; 149 fpregset_t fpregs; 150 unsigned long oldmask; 151 unsigned long cr2; 152 } mcontext_t; 153 154 typedef struct ucontext { 155 unsigned long uc_flags; 156 struct ucontext* uc_link; 157 stack_t uc_stack; 158 mcontext_t uc_mcontext; 159 sigset_t uc_sigmask; 160 // Android has a wrong (smaller) sigset_t on x86. 161 uint32_t __padding_rt_sigset; 162 struct _libc_fpstate __fpregs_mem; 163 } ucontext_t; 164 165 #elif defined(__mips__) 166 167 /* glibc doesn't have names for MIPS registers. */ 168 169 #define NGREG 32 170 #define NFPREG 32 171 172 typedef unsigned long long greg_t; 173 typedef greg_t gregset_t[NGREG]; 174 175 typedef struct fpregset { 176 union { 177 double fp_dregs[NFPREG]; 178 struct { 179 float _fp_fregs; 180 unsigned _fp_pad; 181 } fp_fregs[NFPREG]; 182 } fp_r; 183 } fpregset_t; 184 185 #ifdef __LP64__ 186 typedef struct { 187 gregset_t gregs; 188 fpregset_t fpregs; 189 greg_t mdhi; 190 greg_t hi1; 191 greg_t hi2; 192 greg_t hi3; 193 greg_t mdlo; 194 greg_t lo1; 195 greg_t lo2; 196 greg_t lo3; 197 greg_t pc; 198 uint32_t fpc_csr; 199 uint32_t used_math; 200 uint32_t dsp; 201 uint32_t reserved; 202 } mcontext_t; 203 #else 204 typedef struct { 205 unsigned regmask; 206 unsigned status; 207 greg_t pc; 208 gregset_t gregs; 209 fpregset_t fpregs; 210 unsigned fp_owned; 211 unsigned fpc_csr; 212 unsigned fpc_eir; 213 unsigned used_math; 214 unsigned dsp; 215 greg_t mdhi; 216 greg_t mdlo; 217 unsigned long hi1; 218 unsigned long lo1; 219 unsigned long hi2; 220 unsigned long lo2; 221 unsigned long hi3; 222 unsigned long lo3; 223 } mcontext_t; 224 #endif 225 226 typedef struct ucontext { 227 unsigned long uc_flags; 228 struct ucontext* uc_link; 229 stack_t uc_stack; 230 mcontext_t uc_mcontext; 231 sigset_t uc_sigmask; 232 } ucontext_t; 233 234 #elif defined(__x86_64__) 235 236 enum { 237 REG_R8 = 0, 238 REG_R9, 239 REG_R10, 240 REG_R11, 241 REG_R12, 242 REG_R13, 243 REG_R14, 244 REG_R15, 245 REG_RDI, 246 REG_RSI, 247 REG_RBP, 248 REG_RBX, 249 REG_RDX, 250 REG_RAX, 251 REG_RCX, 252 REG_RSP, 253 REG_RIP, 254 REG_EFL, 255 REG_CSGSFS, 256 REG_ERR, 257 REG_TRAPNO, 258 REG_OLDMASK, 259 REG_CR2, 260 NGREG 261 }; 262 263 typedef long greg_t; 264 typedef greg_t gregset_t[NGREG]; 265 266 struct _libc_fpxreg { 267 unsigned short significand[4]; 268 unsigned short exponent; 269 unsigned short padding[3]; 270 }; 271 272 struct _libc_xmmreg { 273 uint32_t element[4]; 274 }; 275 276 struct _libc_fpstate { 277 uint16_t cwd; 278 uint16_t swd; 279 uint16_t ftw; 280 uint16_t fop; 281 uint64_t rip; 282 uint64_t rdp; 283 uint32_t mxcsr; 284 uint32_t mxcr_mask; 285 struct _libc_fpxreg _st[8]; 286 struct _libc_xmmreg _xmm[16]; 287 uint32_t padding[24]; 288 }; 289 290 typedef struct _libc_fpstate* fpregset_t; 291 292 typedef struct { 293 gregset_t gregs; 294 fpregset_t fpregs; 295 unsigned long __reserved1[8]; 296 } mcontext_t; 297 298 typedef struct ucontext { 299 unsigned long uc_flags; 300 struct ucontext* uc_link; 301 stack_t uc_stack; 302 mcontext_t uc_mcontext; 303 sigset_t uc_sigmask; 304 struct _libc_fpstate __fpregs_mem; 305 } ucontext_t; 306 307 #endif 308 309 __END_DECLS 310 311 #endif /* _SYS_UCONTEXT_H_ */ 312