github.com/google/syzkaller@v0.0.0-20240517125934-c0f1611a36d6/executor/android/android_seccomp.h (about) 1 // Copyright 2020 syzkaller project authors. All rights reserved. 2 // Use of this source code is governed by Apache 2 LICENSE that can be found in the LICENSE file. 3 4 // These headers are generated by the Android build system and need to be updated periodically. 5 6 // Header files are generated by `genseccomp.py` 7 // (https://android.googlesource.com/platform/bionic/+/refs/heads/main/libc/tools/genseccomp.py). 8 // Arguments are taken from the android build file 9 // (https://android.googlesource.com/platform/bionic/+/refs/heads/main/libc/Android.bp). 10 #if GOARCH_arm64 11 #define PRIMARY_ARCH AUDIT_ARCH_AARCH64 12 #include "arm64_app_policy.h" 13 static const struct sock_filter* primary_app_filter = arm64_app_filter; 14 static const size_t primary_app_filter_size = arm64_app_filter_size; 15 #include "arm64_system_policy.h" 16 static const struct sock_filter* system_filter = arm64_system_filter; 17 static const size_t system_filter_size = arm64_system_filter_size; 18 // We need 3 for ValidateArchitecture and 1 for ExamineSyscall and 4 for ValidateArchitectureAndJumpIfNeeded + 2 extra Disallow 19 #define kFilterMaxSize (arm64_app_filter_size + 3 + 1 + 4 + 2) 20 21 #elif GOARCH_arm 22 #define PRIMARY_ARCH AUDIT_ARCH_ARM 23 #include "arm_app_policy.h" 24 static const struct sock_filter* primary_app_filter = arm_app_filter; 25 static const size_t primary_app_filter_size = arm_app_filter_size; 26 #include "arm_system_policy.h" 27 static const struct sock_filter* system_filter = arm_system_filter; 28 static const size_t system_filter_size = arm_system_filter_size; 29 #define kFilterMaxSize (arm_app_filter_size + 3 + 1 + 4 + 2) 30 31 // Note: clone3() and set/get_robust_list() are added as they are used 32 // by pthread_create(). 33 #elif GOARCH_amd64 34 #define PRIMARY_ARCH AUDIT_ARCH_X86_64 35 #include "x86_64_app_policy.h" 36 static const struct sock_filter* primary_app_filter = x86_64_app_filter; 37 static const size_t primary_app_filter_size = x86_64_app_filter_size; 38 #include "x86_64_system_policy.h" 39 static const struct sock_filter* system_filter = x86_64_system_filter; 40 static const size_t system_filter_size = x86_64_system_filter_size; 41 #define kFilterMaxSize (x86_64_app_filter_size + 3 + 1 + 4 + 2) 42 43 #elif GOARCH_386 44 #define PRIMARY_ARCH AUDIT_ARCH_I386 45 #include "x86_app_policy.h" 46 static const struct sock_filter* primary_app_filter = x86_app_filter; 47 static const size_t primary_app_filter_size = x86_app_filter_size; 48 #include "x86_system_policy.h" 49 static const struct sock_filter* system_filter = x86_system_filter; 50 static const size_t system_filter_size = x86_system_filter_size; 51 #define kFilterMaxSize (x86_app_filter_size + 3 + 1 + 4 + 2) 52 53 #else 54 #error No architecture was defined! 55 #endif 56 57 #define syscall_nr (offsetof(struct seccomp_data, nr)) 58 #define arch_nr (offsetof(struct seccomp_data, arch)) 59 60 typedef struct Filter_t { 61 struct sock_filter data[kFilterMaxSize]; 62 size_t count; 63 } Filter; 64 65 static void push_back(Filter* filter_array, struct sock_filter filter) 66 { 67 if (filter_array->count == kFilterMaxSize) 68 failmsg("can't add another syscall to seccomp filter", "count=%zu", filter_array->count); 69 filter_array->data[filter_array->count++] = filter; 70 } 71 72 static void Disallow(Filter* f) 73 { 74 struct sock_filter filter = BPF_STMT(BPF_RET | BPF_K, SECCOMP_RET_TRAP); 75 push_back(f, filter); 76 } 77 78 static void ExamineSyscall(Filter* f) 79 { 80 struct sock_filter filter = BPF_STMT(BPF_LD | BPF_W | BPF_ABS, syscall_nr); 81 push_back(f, filter); 82 } 83 84 static void ValidateArchitecture(Filter* f) 85 { 86 struct sock_filter filter1 = BPF_STMT(BPF_LD | BPF_W | BPF_ABS, arch_nr); 87 struct sock_filter filter2 = BPF_JUMP(BPF_JMP | BPF_JEQ | BPF_K, PRIMARY_ARCH, 1, 0); 88 push_back(f, filter1); 89 push_back(f, filter2); 90 Disallow(f); 91 } 92 93 // Modified from the orignal Android code to fail instead of return. 94 static void install_filter(const Filter* f) 95 { 96 struct sock_fprog prog = { 97 (unsigned short)f->count, 98 (struct sock_filter*)&f->data[0], 99 }; 100 // This assumes either the current process has CAP_SYS_ADMIN, or PR_SET_NO_NEW_PRIVS bit is set. 101 if (prctl(PR_SET_SECCOMP, SECCOMP_MODE_FILTER, &prog) < 0) 102 failmsg("could not set seccomp filter", "size=%zu", f->count); 103 } 104 105 // Modified from the original Android code as we don't need dual arch support 106 static void set_seccomp_filter(const struct sock_filter* filter, size_t size) 107 { 108 Filter f; 109 f.count = 0; 110 ValidateArchitecture(&f); 111 ExamineSyscall(&f); 112 113 for (size_t i = 0; i < size; ++i) 114 push_back(&f, filter[i]); 115 Disallow(&f); 116 117 // Will fail() if anything fails. 118 install_filter(&f); 119 } 120 121 enum { 122 SCFS_RestrictedApp, 123 SCFS_SystemAccount 124 }; 125 126 static void set_app_seccomp_filter(int account) 127 { 128 if (account == SCFS_SystemAccount) { 129 set_seccomp_filter(system_filter, system_filter_size); 130 } else { 131 set_seccomp_filter(primary_app_filter, primary_app_filter_size); 132 } 133 }