Chromium Code Reviews| Index: sandbox/linux/seccomp-bpf/linux_seccomp.h |
| diff --git a/sandbox/linux/seccomp-bpf/linux_seccomp.h b/sandbox/linux/seccomp-bpf/linux_seccomp.h |
| index 270e11c1f8f79b88bbaee65004b222a8ab336cae..9b175e8ac4a291ebb9f1e8a4199cc0c4165f6e71 100644 |
| --- a/sandbox/linux/seccomp-bpf/linux_seccomp.h |
| +++ b/sandbox/linux/seccomp-bpf/linux_seccomp.h |
| @@ -15,12 +15,15 @@ |
| #include <asm/unistd.h> |
| #include <linux/filter.h> |
| - |
| #include <sys/cdefs.h> |
| // Old Bionic versions do not have sys/user.h. The if can be removed once we no |
| // longer need to support these old Bionic versions. |
| // All x86_64 builds use a new enough bionic to have sys/user.h. |
| #if !defined(__BIONIC__) || defined(__x86_64__) |
| +#if defined(__mips__) |
| +// sys/user.h in eglibc misses size_t definition |
| +#include <unistd.h> |
| +#endif |
| #include <sys/user.h> |
| #endif |
| @@ -34,6 +37,9 @@ |
| #ifndef EM_X86_64 |
| #define EM_X86_64 62 |
| #endif |
| +#ifndef EM_MIPS |
| +#define EM_MIPS 8 |
| +#endif |
| #ifndef __AUDIT_ARCH_64BIT |
| #define __AUDIT_ARCH_64BIT 0x80000000 |
| @@ -50,6 +56,9 @@ |
| #ifndef AUDIT_ARCH_X86_64 |
| #define AUDIT_ARCH_X86_64 (EM_X86_64|__AUDIT_ARCH_64BIT|__AUDIT_ARCH_LE) |
| #endif |
| +#ifndef AUDIT_ARCH_MIPSEL |
| +#define AUDIT_ARCH_MIPSEL (EM_MIPS|__AUDIT_ARCH_LE) |
| +#endif |
| // For prctl.h |
| #ifndef PR_SET_SECCOMP |
| @@ -286,6 +295,62 @@ typedef user_regs regs_struct; |
| #define SECCOMP_PT_PARM5(_regs) (_regs).REG_r4 |
| #define SECCOMP_PT_PARM6(_regs) (_regs).REG_r5 |
| +#elif defined(__mips__) && (_MIPS_SIM == _MIPS_SIM_ABI32) |
| +#define MIN_SYSCALL __NR_O32_Linux |
| +#define MAX_PUBLIC_SYSCALL (MIN_SYSCALL + __NR_Linux_syscalls) |
| +#define MAX_SYSCALL MAX_PUBLIC_SYSCALL |
| +#define SECCOMP_ARCH AUDIT_ARCH_MIPSEL |
| + |
| +// MIPS sigcontext_t is different from i386/x86_64 and ARM. |
| +// See </arch/mips/include/uapi/asm/sigcontext.h> in the Linux kernel. |
| +#define SECCOMP_REG(_ctx, _reg) ((_ctx)->uc_mcontext.gregs[_reg]) |
| +// Based on MIPS o32 ABI syscall convention. |
| +// On MIPS, when indirect syscall is being made (syscall(__NR_foo)), |
| +// real identificator (__NR_foo) is not in v0, but in a0 |
| +#define SECCOMP_RESULT(_ctx) SECCOMP_REG(_ctx, 2) |
| +#define SECCOMP_SYSCALL(_ctx) SECCOMP_REG(_ctx, 2) |
| +#define SECCOMP_IP(_ctx) (_ctx)->uc_mcontext.pc |
| +#define SECCOMP_PARM1(_ctx) SECCOMP_REG(_ctx, 4) |
| +#define SECCOMP_PARM2(_ctx) SECCOMP_REG(_ctx, 5) |
| +#define SECCOMP_PARM3(_ctx) SECCOMP_REG(_ctx, 6) |
| +#define SECCOMP_PARM4(_ctx) SECCOMP_REG(_ctx, 7) |
| +// Only the first 4 arguments of syscall are in registers. |
| +// The rest are on the stack. |
|
jln (very slow on Chromium)
2014/06/20 00:37:06
By the way, how does the kernel handle that?
The
nedeljko
2014/06/20 14:09:51
Yes, you are correct. Kernel copies arguments befo
|
| +#define SECCOMP_PARM5(_ctx) (long int)(*((intptr_t*)SECCOMP_REG(_ctx, \ |
| + 29) + 4)) |
| +#define SECCOMP_PARM6(_ctx) (long int)(*((intptr_t*)SECCOMP_REG(_ctx, \ |
| + 29) + 5)) |
| +#define SECCOMP_NR_IDX (offsetof(struct arch_seccomp_data, nr)) |
| +#define SECCOMP_ARCH_IDX (offsetof(struct arch_seccomp_data, arch)) |
| +#define SECCOMP_IP_MSB_IDX (offsetof(struct arch_seccomp_data, \ |
| + instruction_pointer) + 4) |
| +#define SECCOMP_IP_LSB_IDX (offsetof(struct arch_seccomp_data, \ |
| + instruction_pointer) + 0) |
| +#define SECCOMP_ARG_MSB_IDX(nr) (offsetof(struct arch_seccomp_data, args) + \ |
| + 8*(nr) + 4) |
| +#define SECCOMP_ARG_LSB_IDX(nr) (offsetof(struct arch_seccomp_data, args) + \ |
| + 8*(nr) + 0) |
| + |
| +// On Mips we don't have structures like user_regs or user_regs_struct in |
| +// sys/user.h that we could use, so we just define regs_struct directly. |
| +struct regs_struct { |
| + unsigned long long regs[32]; |
| +}; |
| + |
| +#define REG_a3 regs[7] |
| +#define REG_a2 regs[6] |
| +#define REG_a1 regs[5] |
| +#define REG_a0 regs[4] |
| +#define REG_v1 regs[3] |
| +#define REG_v0 regs[2] |
| + |
| +#define SECCOMP_PT_RESULT(_regs) (_regs).REG_v0 |
| +#define SECCOMP_PT_SYSCALL(_regs) (_regs).REG_v0 |
| +#define SECCOMP_PT_PARM1(_regs) (_regs).REG_a0 |
| +#define SECCOMP_PT_PARM2(_regs) (_regs).REG_a1 |
| +#define SECCOMP_PT_PARM3(_regs) (_regs).REG_a2 |
| +#define SECCOMP_PT_PARM4(_regs) (_regs).REG_a3 |
| + |
| #else |
| #error Unsupported target platform |