Home | History | Annotate | Download | only in bpf_dsl
      1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
      2 // Use of this source code is governed by a BSD-style license that can be
      3 // found in the LICENSE file.
      4 
      5 #ifndef SANDBOX_LINUX_BPF_DSL_SECCOMP_MACROS_H_
      6 #define SANDBOX_LINUX_BPF_DSL_SECCOMP_MACROS_H_
      7 
      8 #include <sys/types.h>  // For __BIONIC__.
      9 // Old Bionic versions do not have sys/user.h.  The if can be removed once we no
     10 // longer need to support these old Bionic versions.
     11 // All x86_64 builds use a new enough bionic to have sys/user.h.
     12 #if !defined(__BIONIC__) || defined(__x86_64__)
     13 #if !defined(__native_client_nonsfi__)
     14 #include <sys/user.h>
     15 #endif
     16 #if defined(__mips__)
     17 // sys/user.h in eglibc misses size_t definition
     18 #include <stddef.h>
     19 #endif
     20 #endif
     21 
     22 #include "sandbox/linux/system_headers/linux_seccomp.h"  // For AUDIT_ARCH_*
     23 
     24 // Impose some reasonable maximum BPF program size. Realistically, the
     25 // kernel probably has much lower limits. But by limiting to less than
     26 // 30 bits, we can ease requirements on some of our data types.
     27 #define SECCOMP_MAX_PROGRAM_SIZE (1<<30)
     28 
     29 #if defined(__i386__)
     30 #define SECCOMP_ARCH        AUDIT_ARCH_I386
     31 
     32 #define SECCOMP_REG(_ctx, _reg) ((_ctx)->uc_mcontext.gregs[(_reg)])
     33 #define SECCOMP_RESULT(_ctx)    SECCOMP_REG(_ctx, REG_EAX)
     34 #define SECCOMP_SYSCALL(_ctx)   SECCOMP_REG(_ctx, REG_EAX)
     35 #define SECCOMP_IP(_ctx)        SECCOMP_REG(_ctx, REG_EIP)
     36 #define SECCOMP_PARM1(_ctx)     SECCOMP_REG(_ctx, REG_EBX)
     37 #define SECCOMP_PARM2(_ctx)     SECCOMP_REG(_ctx, REG_ECX)
     38 #define SECCOMP_PARM3(_ctx)     SECCOMP_REG(_ctx, REG_EDX)
     39 #define SECCOMP_PARM4(_ctx)     SECCOMP_REG(_ctx, REG_ESI)
     40 #define SECCOMP_PARM5(_ctx)     SECCOMP_REG(_ctx, REG_EDI)
     41 #define SECCOMP_PARM6(_ctx)     SECCOMP_REG(_ctx, REG_EBP)
     42 #define SECCOMP_NR_IDX          (offsetof(struct arch_seccomp_data, nr))
     43 #define SECCOMP_ARCH_IDX        (offsetof(struct arch_seccomp_data, arch))
     44 #define SECCOMP_IP_MSB_IDX      (offsetof(struct arch_seccomp_data,           \
     45                                           instruction_pointer) + 4)
     46 #define SECCOMP_IP_LSB_IDX      (offsetof(struct arch_seccomp_data,           \
     47                                           instruction_pointer) + 0)
     48 #define SECCOMP_ARG_MSB_IDX(nr) (offsetof(struct arch_seccomp_data, args) +   \
     49                                  8*(nr) + 4)
     50 #define SECCOMP_ARG_LSB_IDX(nr) (offsetof(struct arch_seccomp_data, args) +   \
     51                                  8*(nr) + 0)
     52 
     53 
     54 #if defined(__BIONIC__) || defined(__native_client_nonsfi__)
     55 // Old Bionic versions and PNaCl toolchain don't have sys/user.h, so we just
     56 // define regs_struct directly.  This can be removed once we no longer need to
     57 // support these old Bionic versions and PNaCl toolchain.
     58 struct regs_struct {
     59   long int ebx;
     60   long int ecx;
     61   long int edx;
     62   long int esi;
     63   long int edi;
     64   long int ebp;
     65   long int eax;
     66   long int xds;
     67   long int xes;
     68   long int xfs;
     69   long int xgs;
     70   long int orig_eax;
     71   long int eip;
     72   long int xcs;
     73   long int eflags;
     74   long int esp;
     75   long int xss;
     76 };
     77 #else
     78 typedef user_regs_struct regs_struct;
     79 #endif
     80 
     81 #define SECCOMP_PT_RESULT(_regs)  (_regs).eax
     82 #define SECCOMP_PT_SYSCALL(_regs) (_regs).orig_eax
     83 #define SECCOMP_PT_IP(_regs)      (_regs).eip
     84 #define SECCOMP_PT_PARM1(_regs)   (_regs).ebx
     85 #define SECCOMP_PT_PARM2(_regs)   (_regs).ecx
     86 #define SECCOMP_PT_PARM3(_regs)   (_regs).edx
     87 #define SECCOMP_PT_PARM4(_regs)   (_regs).esi
     88 #define SECCOMP_PT_PARM5(_regs)   (_regs).edi
     89 #define SECCOMP_PT_PARM6(_regs)   (_regs).ebp
     90 
     91 #elif defined(__x86_64__)
     92 #define SECCOMP_ARCH        AUDIT_ARCH_X86_64
     93 
     94 #define SECCOMP_REG(_ctx, _reg) ((_ctx)->uc_mcontext.gregs[(_reg)])
     95 #define SECCOMP_RESULT(_ctx)    SECCOMP_REG(_ctx, REG_RAX)
     96 #define SECCOMP_SYSCALL(_ctx)   SECCOMP_REG(_ctx, REG_RAX)
     97 #define SECCOMP_IP(_ctx)        SECCOMP_REG(_ctx, REG_RIP)
     98 #define SECCOMP_PARM1(_ctx)     SECCOMP_REG(_ctx, REG_RDI)
     99 #define SECCOMP_PARM2(_ctx)     SECCOMP_REG(_ctx, REG_RSI)
    100 #define SECCOMP_PARM3(_ctx)     SECCOMP_REG(_ctx, REG_RDX)
    101 #define SECCOMP_PARM4(_ctx)     SECCOMP_REG(_ctx, REG_R10)
    102 #define SECCOMP_PARM5(_ctx)     SECCOMP_REG(_ctx, REG_R8)
    103 #define SECCOMP_PARM6(_ctx)     SECCOMP_REG(_ctx, REG_R9)
    104 #define SECCOMP_NR_IDX          (offsetof(struct arch_seccomp_data, nr))
    105 #define SECCOMP_ARCH_IDX        (offsetof(struct arch_seccomp_data, arch))
    106 #define SECCOMP_IP_MSB_IDX      (offsetof(struct arch_seccomp_data,           \
    107                                           instruction_pointer) + 4)
    108 #define SECCOMP_IP_LSB_IDX      (offsetof(struct arch_seccomp_data,           \
    109                                           instruction_pointer) + 0)
    110 #define SECCOMP_ARG_MSB_IDX(nr) (offsetof(struct arch_seccomp_data, args) +   \
    111                                  8*(nr) + 4)
    112 #define SECCOMP_ARG_LSB_IDX(nr) (offsetof(struct arch_seccomp_data, args) +   \
    113                                  8*(nr) + 0)
    114 
    115 typedef user_regs_struct regs_struct;
    116 #define SECCOMP_PT_RESULT(_regs)  (_regs).rax
    117 #define SECCOMP_PT_SYSCALL(_regs) (_regs).orig_rax
    118 #define SECCOMP_PT_IP(_regs)      (_regs).rip
    119 #define SECCOMP_PT_PARM1(_regs)   (_regs).rdi
    120 #define SECCOMP_PT_PARM2(_regs)   (_regs).rsi
    121 #define SECCOMP_PT_PARM3(_regs)   (_regs).rdx
    122 #define SECCOMP_PT_PARM4(_regs)   (_regs).r10
    123 #define SECCOMP_PT_PARM5(_regs)   (_regs).r8
    124 #define SECCOMP_PT_PARM6(_regs)   (_regs).r9
    125 
    126 #elif defined(__arm__) && (defined(__thumb__) || defined(__ARM_EABI__))
    127 #define SECCOMP_ARCH AUDIT_ARCH_ARM
    128 
    129 // ARM sigcontext_t is different from i386/x86_64.
    130 // See </arch/arm/include/asm/sigcontext.h> in the Linux kernel.
    131 #define SECCOMP_REG(_ctx, _reg) ((_ctx)->uc_mcontext.arm_##_reg)
    132 // ARM EABI syscall convention.
    133 #define SECCOMP_RESULT(_ctx)    SECCOMP_REG(_ctx, r0)
    134 #define SECCOMP_SYSCALL(_ctx)   SECCOMP_REG(_ctx, r7)
    135 #define SECCOMP_IP(_ctx)        SECCOMP_REG(_ctx, pc)
    136 #define SECCOMP_PARM1(_ctx)     SECCOMP_REG(_ctx, r0)
    137 #define SECCOMP_PARM2(_ctx)     SECCOMP_REG(_ctx, r1)
    138 #define SECCOMP_PARM3(_ctx)     SECCOMP_REG(_ctx, r2)
    139 #define SECCOMP_PARM4(_ctx)     SECCOMP_REG(_ctx, r3)
    140 #define SECCOMP_PARM5(_ctx)     SECCOMP_REG(_ctx, r4)
    141 #define SECCOMP_PARM6(_ctx)     SECCOMP_REG(_ctx, r5)
    142 #define SECCOMP_NR_IDX          (offsetof(struct arch_seccomp_data, nr))
    143 #define SECCOMP_ARCH_IDX        (offsetof(struct arch_seccomp_data, arch))
    144 #define SECCOMP_IP_MSB_IDX      (offsetof(struct arch_seccomp_data,           \
    145                                           instruction_pointer) + 4)
    146 #define SECCOMP_IP_LSB_IDX      (offsetof(struct arch_seccomp_data,           \
    147                                           instruction_pointer) + 0)
    148 #define SECCOMP_ARG_MSB_IDX(nr) (offsetof(struct arch_seccomp_data, args) +   \
    149                                  8*(nr) + 4)
    150 #define SECCOMP_ARG_LSB_IDX(nr) (offsetof(struct arch_seccomp_data, args) +   \
    151                                  8*(nr) + 0)
    152 
    153 #if defined(__BIONIC__) || defined(__native_client_nonsfi__)
    154 // Old Bionic versions and PNaCl toolchain don't have sys/user.h, so we just
    155 // define regs_struct directly.  This can be removed once we no longer need to
    156 // support these old Bionic versions and PNaCl toolchain.
    157 struct regs_struct {
    158   unsigned long uregs[18];
    159 };
    160 #else
    161 typedef user_regs regs_struct;
    162 #endif
    163 
    164 #define REG_cpsr    uregs[16]
    165 #define REG_pc      uregs[15]
    166 #define REG_lr      uregs[14]
    167 #define REG_sp      uregs[13]
    168 #define REG_ip      uregs[12]
    169 #define REG_fp      uregs[11]
    170 #define REG_r10     uregs[10]
    171 #define REG_r9      uregs[9]
    172 #define REG_r8      uregs[8]
    173 #define REG_r7      uregs[7]
    174 #define REG_r6      uregs[6]
    175 #define REG_r5      uregs[5]
    176 #define REG_r4      uregs[4]
    177 #define REG_r3      uregs[3]
    178 #define REG_r2      uregs[2]
    179 #define REG_r1      uregs[1]
    180 #define REG_r0      uregs[0]
    181 #define REG_ORIG_r0 uregs[17]
    182 
    183 #define SECCOMP_PT_RESULT(_regs)  (_regs).REG_r0
    184 #define SECCOMP_PT_SYSCALL(_regs) (_regs).REG_r7
    185 #define SECCOMP_PT_IP(_regs)      (_regs).REG_pc
    186 #define SECCOMP_PT_PARM1(_regs)   (_regs).REG_r0
    187 #define SECCOMP_PT_PARM2(_regs)   (_regs).REG_r1
    188 #define SECCOMP_PT_PARM3(_regs)   (_regs).REG_r2
    189 #define SECCOMP_PT_PARM4(_regs)   (_regs).REG_r3
    190 #define SECCOMP_PT_PARM5(_regs)   (_regs).REG_r4
    191 #define SECCOMP_PT_PARM6(_regs)   (_regs).REG_r5
    192 
    193 #elif defined(__mips__) && (_MIPS_SIM == _MIPS_SIM_ABI32)
    194 #define SECCOMP_ARCH        AUDIT_ARCH_MIPSEL
    195 #define SYSCALL_EIGHT_ARGS
    196 // MIPS sigcontext_t is different from i386/x86_64 and ARM.
    197 // See </arch/mips/include/uapi/asm/sigcontext.h> in the Linux kernel.
    198 #define SECCOMP_REG(_ctx, _reg) ((_ctx)->uc_mcontext.gregs[_reg])
    199 // Based on MIPS o32 ABI syscall convention.
    200 // On MIPS, when indirect syscall is being made (syscall(__NR_foo)),
    201 // real identificator (__NR_foo) is not in v0, but in a0
    202 #define SECCOMP_RESULT(_ctx)    SECCOMP_REG(_ctx, 2)
    203 #define SECCOMP_SYSCALL(_ctx)   SECCOMP_REG(_ctx, 2)
    204 #define SECCOMP_IP(_ctx)        (_ctx)->uc_mcontext.pc
    205 #define SECCOMP_PARM1(_ctx)     SECCOMP_REG(_ctx, 4)
    206 #define SECCOMP_PARM2(_ctx)     SECCOMP_REG(_ctx, 5)
    207 #define SECCOMP_PARM3(_ctx)     SECCOMP_REG(_ctx, 6)
    208 #define SECCOMP_PARM4(_ctx)     SECCOMP_REG(_ctx, 7)
    209 // Only the first 4 arguments of syscall are in registers.
    210 // The rest are on the stack.
    211 #define SECCOMP_STACKPARM(_ctx, n)  (((long *)SECCOMP_REG(_ctx, 29))[(n)])
    212 #define SECCOMP_PARM5(_ctx)         SECCOMP_STACKPARM(_ctx, 4)
    213 #define SECCOMP_PARM6(_ctx)         SECCOMP_STACKPARM(_ctx, 5)
    214 #define SECCOMP_PARM7(_ctx)         SECCOMP_STACKPARM(_ctx, 6)
    215 #define SECCOMP_PARM8(_ctx)         SECCOMP_STACKPARM(_ctx, 7)
    216 #define SECCOMP_NR_IDX          (offsetof(struct arch_seccomp_data, nr))
    217 #define SECCOMP_ARCH_IDX        (offsetof(struct arch_seccomp_data, arch))
    218 #define SECCOMP_IP_MSB_IDX      (offsetof(struct arch_seccomp_data,           \
    219                                           instruction_pointer) + 4)
    220 #define SECCOMP_IP_LSB_IDX      (offsetof(struct arch_seccomp_data,           \
    221                                           instruction_pointer) + 0)
    222 #define SECCOMP_ARG_MSB_IDX(nr) (offsetof(struct arch_seccomp_data, args) +   \
    223                                  8*(nr) + 4)
    224 #define SECCOMP_ARG_LSB_IDX(nr) (offsetof(struct arch_seccomp_data, args) +   \
    225                                  8*(nr) + 0)
    226 
    227 // On Mips we don't have structures like user_regs or user_regs_struct in
    228 // sys/user.h that we could use, so we just define regs_struct directly.
    229 struct regs_struct {
    230   unsigned long long regs[32];
    231 };
    232 
    233 #define REG_a3 regs[7]
    234 #define REG_a2 regs[6]
    235 #define REG_a1 regs[5]
    236 #define REG_a0 regs[4]
    237 #define REG_v1 regs[3]
    238 #define REG_v0 regs[2]
    239 
    240 #define SECCOMP_PT_RESULT(_regs)  (_regs).REG_v0
    241 #define SECCOMP_PT_SYSCALL(_regs) (_regs).REG_v0
    242 #define SECCOMP_PT_PARM1(_regs)   (_regs).REG_a0
    243 #define SECCOMP_PT_PARM2(_regs)   (_regs).REG_a1
    244 #define SECCOMP_PT_PARM3(_regs)   (_regs).REG_a2
    245 #define SECCOMP_PT_PARM4(_regs)   (_regs).REG_a3
    246 
    247 #elif defined(__aarch64__)
    248 struct regs_struct {
    249   unsigned long long regs[31];
    250   unsigned long long sp;
    251   unsigned long long pc;
    252   unsigned long long pstate;
    253 };
    254 
    255 #define SECCOMP_ARCH AUDIT_ARCH_AARCH64
    256 
    257 #define SECCOMP_REG(_ctx, _reg) ((_ctx)->uc_mcontext.regs[_reg])
    258 
    259 #define SECCOMP_RESULT(_ctx) SECCOMP_REG(_ctx, 0)
    260 #define SECCOMP_SYSCALL(_ctx) SECCOMP_REG(_ctx, 8)
    261 #define SECCOMP_IP(_ctx) (_ctx)->uc_mcontext.pc
    262 #define SECCOMP_PARM1(_ctx) SECCOMP_REG(_ctx, 0)
    263 #define SECCOMP_PARM2(_ctx) SECCOMP_REG(_ctx, 1)
    264 #define SECCOMP_PARM3(_ctx) SECCOMP_REG(_ctx, 2)
    265 #define SECCOMP_PARM4(_ctx) SECCOMP_REG(_ctx, 3)
    266 #define SECCOMP_PARM5(_ctx) SECCOMP_REG(_ctx, 4)
    267 #define SECCOMP_PARM6(_ctx) SECCOMP_REG(_ctx, 5)
    268 
    269 #define SECCOMP_NR_IDX (offsetof(struct arch_seccomp_data, nr))
    270 #define SECCOMP_ARCH_IDX (offsetof(struct arch_seccomp_data, arch))
    271 #define SECCOMP_IP_MSB_IDX \
    272   (offsetof(struct arch_seccomp_data, instruction_pointer) + 4)
    273 #define SECCOMP_IP_LSB_IDX \
    274   (offsetof(struct arch_seccomp_data, instruction_pointer) + 0)
    275 #define SECCOMP_ARG_MSB_IDX(nr) \
    276   (offsetof(struct arch_seccomp_data, args) + 8 * (nr) + 4)
    277 #define SECCOMP_ARG_LSB_IDX(nr) \
    278   (offsetof(struct arch_seccomp_data, args) + 8 * (nr) + 0)
    279 
    280 #define SECCOMP_PT_RESULT(_regs) (_regs).regs[0]
    281 #define SECCOMP_PT_SYSCALL(_regs) (_regs).regs[8]
    282 #define SECCOMP_PT_IP(_regs) (_regs).pc
    283 #define SECCOMP_PT_PARM1(_regs) (_regs).regs[0]
    284 #define SECCOMP_PT_PARM2(_regs) (_regs).regs[1]
    285 #define SECCOMP_PT_PARM3(_regs) (_regs).regs[2]
    286 #define SECCOMP_PT_PARM4(_regs) (_regs).regs[3]
    287 #define SECCOMP_PT_PARM5(_regs) (_regs).regs[4]
    288 #define SECCOMP_PT_PARM6(_regs) (_regs).regs[5]
    289 #else
    290 #error Unsupported target platform
    291 
    292 #endif
    293 
    294 #endif  // SANDBOX_LINUX_BPF_DSL_SECCOMP_MACROS_H_
    295