Home | History | Annotate | Download | only in seccomp-bpf-helpers
      1 // Copyright (c) 2013 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 #include "sandbox/linux/seccomp-bpf-helpers/syscall_sets.h"
      6 
      7 #include "build/build_config.h"
      8 #include "sandbox/linux/services/linux_syscalls.h"
      9 
     10 namespace sandbox {
     11 
     12 // The functions below cover all existing i386, x86_64, and ARM system calls;
     13 // excluding syscalls made obsolete in ARM EABI.
     14 // The implicitly defined sets form a partition of the sets of
     15 // system calls.
     16 
     17 bool SyscallSets::IsKill(int sysno) {
     18   switch (sysno) {
     19     case __NR_kill:
     20     case __NR_tgkill:
     21     case __NR_tkill:  // Deprecated.
     22       return true;
     23     default:
     24       return false;
     25   }
     26 }
     27 
     28 bool SyscallSets::IsAllowedGettime(int sysno) {
     29   switch (sysno) {
     30     case __NR_clock_gettime:
     31     case __NR_gettimeofday:
     32 #if defined(__i386__) || defined(__x86_64__)
     33     case __NR_time:
     34 #endif
     35       return true;
     36     case __NR_adjtimex:         // Privileged.
     37     case __NR_clock_adjtime:    // Privileged.
     38     case __NR_clock_getres:     // Could be allowed.
     39     case __NR_clock_nanosleep:  // Could be allowed.
     40     case __NR_clock_settime:    // Privileged.
     41 #if defined(__i386__)
     42     case __NR_ftime:  // Obsolete.
     43 #endif
     44     case __NR_settimeofday:  // Privileged.
     45 #if defined(__i386__)
     46     case __NR_stime:
     47 #endif
     48     default:
     49       return false;
     50   }
     51 }
     52 
     53 bool SyscallSets::IsCurrentDirectory(int sysno) {
     54   switch (sysno) {
     55     case __NR_getcwd:
     56     case __NR_chdir:
     57     case __NR_fchdir:
     58       return true;
     59     default:
     60       return false;
     61   }
     62 }
     63 
     64 bool SyscallSets::IsUmask(int sysno) {
     65   switch (sysno) {
     66     case __NR_umask:
     67       return true;
     68     default:
     69       return false;
     70   }
     71 }
     72 
     73 // System calls that directly access the file system. They might acquire
     74 // a new file descriptor or otherwise perform an operation directly
     75 // via a path.
     76 // Both EPERM and ENOENT are valid errno unless otherwise noted in comment.
     77 bool SyscallSets::IsFileSystem(int sysno) {
     78   switch (sysno) {
     79     case __NR_access:  // EPERM not a valid errno.
     80     case __NR_chmod:
     81     case __NR_chown:
     82 #if defined(__i386__) || defined(__arm__)
     83     case __NR_chown32:
     84 #endif
     85     case __NR_creat:
     86     case __NR_execve:
     87     case __NR_faccessat:  // EPERM not a valid errno.
     88     case __NR_fchmodat:
     89     case __NR_fchownat:  // Should be called chownat ?
     90 #if defined(__x86_64__)
     91     case __NR_newfstatat:  // fstatat(). EPERM not a valid errno.
     92 #elif defined(__i386__) || defined(__arm__)
     93     case __NR_fstatat64:
     94 #endif
     95     case __NR_futimesat:  // Should be called utimesat ?
     96     case __NR_lchown:
     97 #if defined(__i386__) || defined(__arm__)
     98     case __NR_lchown32:
     99 #endif
    100     case __NR_link:
    101     case __NR_linkat:
    102     case __NR_lookup_dcookie:  // ENOENT not a valid errno.
    103     case __NR_lstat:           // EPERM not a valid errno.
    104 #if defined(__i386__)
    105     case __NR_oldlstat:
    106 #endif
    107 #if defined(__i386__) || defined(__arm__)
    108     case __NR_lstat64:
    109 #endif
    110     case __NR_mkdir:
    111     case __NR_mkdirat:
    112     case __NR_mknod:
    113     case __NR_mknodat:
    114     case __NR_open:
    115     case __NR_openat:
    116     case __NR_readlink:  // EPERM not a valid errno.
    117     case __NR_readlinkat:
    118     case __NR_rename:
    119     case __NR_renameat:
    120     case __NR_rmdir:
    121     case __NR_stat:  // EPERM not a valid errno.
    122 #if defined(__i386__)
    123     case __NR_oldstat:
    124 #endif
    125 #if defined(__i386__) || defined(__arm__)
    126     case __NR_stat64:
    127 #endif
    128     case __NR_statfs:  // EPERM not a valid errno.
    129 #if defined(__i386__) || defined(__arm__)
    130     case __NR_statfs64:
    131 #endif
    132     case __NR_symlink:
    133     case __NR_symlinkat:
    134     case __NR_truncate:
    135 #if defined(__i386__) || defined(__arm__)
    136     case __NR_truncate64:
    137 #endif
    138     case __NR_unlink:
    139     case __NR_unlinkat:
    140     case __NR_uselib:  // Neither EPERM, nor ENOENT are valid errno.
    141     case __NR_ustat:   // Same as above. Deprecated.
    142 #if defined(__i386__) || defined(__x86_64__)
    143     case __NR_utime:
    144 #endif
    145     case __NR_utimensat:  // New.
    146     case __NR_utimes:
    147       return true;
    148     default:
    149       return false;
    150   }
    151 }
    152 
    153 bool SyscallSets::IsAllowedFileSystemAccessViaFd(int sysno) {
    154   switch (sysno) {
    155     case __NR_fstat:
    156 #if defined(__i386__) || defined(__arm__)
    157     case __NR_fstat64:
    158 #endif
    159       return true;
    160 // TODO(jln): these should be denied gracefully as well (moved below).
    161 #if defined(__i386__) || defined(__x86_64__)
    162     case __NR_fadvise64:  // EPERM not a valid errno.
    163 #endif
    164 #if defined(__i386__)
    165     case __NR_fadvise64_64:
    166 #endif
    167 #if defined(__arm__)
    168     case __NR_arm_fadvise64_64:
    169 #endif
    170     case __NR_fdatasync:  // EPERM not a valid errno.
    171     case __NR_flock:      // EPERM not a valid errno.
    172     case __NR_fstatfs:    // Give information about the whole filesystem.
    173 #if defined(__i386__) || defined(__arm__)
    174     case __NR_fstatfs64:
    175 #endif
    176     case __NR_fsync:  // EPERM not a valid errno.
    177 #if defined(__i386__)
    178     case __NR_oldfstat:
    179 #endif
    180 #if defined(__i386__) || defined(__x86_64__)
    181     case __NR_sync_file_range:  // EPERM not a valid errno.
    182 #elif defined(__arm__)
    183     case __NR_arm_sync_file_range:  // EPERM not a valid errno.
    184 #endif
    185     default:
    186       return false;
    187   }
    188 }
    189 
    190 // EPERM is a good errno for any of these.
    191 bool SyscallSets::IsDeniedFileSystemAccessViaFd(int sysno) {
    192   switch (sysno) {
    193     case __NR_fallocate:
    194     case __NR_fchmod:
    195     case __NR_fchown:
    196     case __NR_ftruncate:
    197 #if defined(__i386__) || defined(__arm__)
    198     case __NR_fchown32:
    199     case __NR_ftruncate64:
    200 #endif
    201     case __NR_getdents:    // EPERM not a valid errno.
    202     case __NR_getdents64:  // EPERM not a valid errno.
    203 #if defined(__i386__)
    204     case __NR_readdir:
    205 #endif
    206       return true;
    207     default:
    208       return false;
    209   }
    210 }
    211 
    212 bool SyscallSets::IsGetSimpleId(int sysno) {
    213   switch (sysno) {
    214     case __NR_capget:
    215     case __NR_getegid:
    216     case __NR_geteuid:
    217     case __NR_getgid:
    218     case __NR_getgroups:
    219     case __NR_getpid:
    220     case __NR_getppid:
    221     case __NR_getresgid:
    222     case __NR_getsid:
    223     case __NR_gettid:
    224     case __NR_getuid:
    225     case __NR_getresuid:
    226 #if defined(__i386__) || defined(__arm__)
    227     case __NR_getegid32:
    228     case __NR_geteuid32:
    229     case __NR_getgid32:
    230     case __NR_getgroups32:
    231     case __NR_getresgid32:
    232     case __NR_getresuid32:
    233     case __NR_getuid32:
    234 #endif
    235       return true;
    236     default:
    237       return false;
    238   }
    239 }
    240 
    241 bool SyscallSets::IsProcessPrivilegeChange(int sysno) {
    242   switch (sysno) {
    243     case __NR_capset:
    244 #if defined(__i386__) || defined(__x86_64__)
    245     case __NR_ioperm:  // Intel privilege.
    246     case __NR_iopl:    // Intel privilege.
    247 #endif
    248     case __NR_setfsgid:
    249     case __NR_setfsuid:
    250     case __NR_setgid:
    251     case __NR_setgroups:
    252     case __NR_setregid:
    253     case __NR_setresgid:
    254     case __NR_setresuid:
    255     case __NR_setreuid:
    256     case __NR_setuid:
    257 #if defined(__i386__) || defined(__arm__)
    258     case __NR_setfsgid32:
    259     case __NR_setfsuid32:
    260     case __NR_setgid32:
    261     case __NR_setgroups32:
    262     case __NR_setregid32:
    263     case __NR_setresgid32:
    264     case __NR_setresuid32:
    265     case __NR_setreuid32:
    266     case __NR_setuid32:
    267 #endif
    268       return true;
    269     default:
    270       return false;
    271   }
    272 }
    273 
    274 bool SyscallSets::IsProcessGroupOrSession(int sysno) {
    275   switch (sysno) {
    276     case __NR_setpgid:
    277     case __NR_getpgrp:
    278     case __NR_setsid:
    279     case __NR_getpgid:
    280       return true;
    281     default:
    282       return false;
    283   }
    284 }
    285 
    286 bool SyscallSets::IsAllowedSignalHandling(int sysno) {
    287   switch (sysno) {
    288     case __NR_rt_sigaction:
    289     case __NR_rt_sigprocmask:
    290     case __NR_rt_sigreturn:
    291 #if defined(__i386__) || defined(__arm__)
    292     case __NR_sigaction:
    293     case __NR_sigprocmask:
    294     case __NR_sigreturn:
    295 #endif
    296       return true;
    297     case __NR_rt_sigpending:
    298     case __NR_rt_sigqueueinfo:
    299     case __NR_rt_sigsuspend:
    300     case __NR_rt_sigtimedwait:
    301     case __NR_rt_tgsigqueueinfo:
    302     case __NR_sigaltstack:
    303     case __NR_signalfd:
    304     case __NR_signalfd4:
    305 #if defined(__i386__) || defined(__arm__)
    306     case __NR_sigpending:
    307     case __NR_sigsuspend:
    308 #endif
    309 #if defined(__i386__)
    310     case __NR_signal:
    311     case __NR_sgetmask:  // Obsolete.
    312     case __NR_ssetmask:
    313 #endif
    314     default:
    315       return false;
    316   }
    317 }
    318 
    319 bool SyscallSets::IsAllowedOperationOnFd(int sysno) {
    320   switch (sysno) {
    321     case __NR_close:
    322     case __NR_dup:
    323     case __NR_dup2:
    324     case __NR_dup3:
    325 #if defined(__x86_64__) || defined(__arm__)
    326     case __NR_shutdown:
    327 #endif
    328       return true;
    329     case __NR_fcntl:
    330 #if defined(__i386__) || defined(__arm__)
    331     case __NR_fcntl64:
    332 #endif
    333     default:
    334       return false;
    335   }
    336 }
    337 
    338 bool SyscallSets::IsKernelInternalApi(int sysno) {
    339   switch (sysno) {
    340     case __NR_restart_syscall:
    341 #if defined(__arm__)
    342     case __ARM_NR_cmpxchg:
    343 #endif
    344       return true;
    345     default:
    346       return false;
    347   }
    348 }
    349 
    350 // This should be thought through in conjunction with IsFutex().
    351 bool SyscallSets::IsAllowedProcessStartOrDeath(int sysno) {
    352   switch (sysno) {
    353     case __NR_exit:
    354     case __NR_exit_group:
    355     case __NR_wait4:
    356     case __NR_waitid:
    357 #if defined(__i386__)
    358     case __NR_waitpid:
    359 #endif
    360       return true;
    361     case __NR_clone:  // Should be parameter-restricted.
    362     case __NR_setns:  // Privileged.
    363     case __NR_fork:
    364 #if defined(__i386__) || defined(__x86_64__)
    365     case __NR_get_thread_area:
    366     case __NR_set_thread_area:
    367 #endif
    368     case __NR_set_tid_address:
    369     case __NR_unshare:
    370     case __NR_vfork:
    371     default:
    372       return false;
    373   }
    374 }
    375 
    376 // It's difficult to restrict those, but there is attack surface here.
    377 bool SyscallSets::IsAllowedFutex(int sysno) {
    378   switch (sysno) {
    379     case __NR_get_robust_list:
    380     case __NR_set_robust_list:
    381       return true;
    382     case __NR_futex:
    383     default:
    384       return false;
    385   }
    386 }
    387 
    388 bool SyscallSets::IsAllowedEpoll(int sysno) {
    389   switch (sysno) {
    390     case __NR_epoll_create:
    391     case __NR_epoll_create1:
    392     case __NR_epoll_ctl:
    393     case __NR_epoll_wait:
    394       return true;
    395     default:
    396 #if defined(__x86_64__)
    397     case __NR_epoll_ctl_old:
    398 #endif
    399     case __NR_epoll_pwait:
    400 #if defined(__x86_64__)
    401     case __NR_epoll_wait_old:
    402 #endif
    403       return false;
    404   }
    405 }
    406 
    407 bool SyscallSets::IsAllowedGetOrModifySocket(int sysno) {
    408   switch (sysno) {
    409     case __NR_pipe:
    410     case __NR_pipe2:
    411       return true;
    412     default:
    413 #if defined(__x86_64__) || defined(__arm__)
    414     case __NR_socketpair:  // We will want to inspect its argument.
    415 #endif
    416       return false;
    417   }
    418 }
    419 
    420 bool SyscallSets::IsDeniedGetOrModifySocket(int sysno) {
    421   switch (sysno) {
    422 #if defined(__x86_64__) || defined(__arm__)
    423     case __NR_accept:
    424     case __NR_accept4:
    425     case __NR_bind:
    426     case __NR_connect:
    427     case __NR_socket:
    428     case __NR_listen:
    429       return true;
    430 #endif
    431     default:
    432       return false;
    433   }
    434 }
    435 
    436 #if defined(__i386__)
    437 // Big multiplexing system call for sockets.
    438 bool SyscallSets::IsSocketCall(int sysno) {
    439   switch (sysno) {
    440     case __NR_socketcall:
    441       return true;
    442     default:
    443       return false;
    444   }
    445 }
    446 #endif
    447 
    448 #if defined(__x86_64__) || defined(__arm__)
    449 bool SyscallSets::IsNetworkSocketInformation(int sysno) {
    450   switch (sysno) {
    451     case __NR_getpeername:
    452     case __NR_getsockname:
    453     case __NR_getsockopt:
    454     case __NR_setsockopt:
    455       return true;
    456     default:
    457       return false;
    458   }
    459 }
    460 #endif
    461 
    462 bool SyscallSets::IsAllowedAddressSpaceAccess(int sysno) {
    463   switch (sysno) {
    464     case __NR_brk:
    465     case __NR_mlock:
    466     case __NR_munlock:
    467     case __NR_munmap:
    468       return true;
    469     case __NR_madvise:
    470     case __NR_mincore:
    471     case __NR_mlockall:
    472 #if defined(__i386__) || defined(__x86_64__)
    473     case __NR_mmap:
    474 #endif
    475 #if defined(__i386__) || defined(__arm__)
    476     case __NR_mmap2:
    477 #endif
    478 #if defined(__i386__) || defined(__x86_64__)
    479     case __NR_modify_ldt:
    480 #endif
    481     case __NR_mprotect:
    482     case __NR_mremap:
    483     case __NR_msync:
    484     case __NR_munlockall:
    485     case __NR_readahead:
    486     case __NR_remap_file_pages:
    487 #if defined(__i386__)
    488     case __NR_vm86:
    489     case __NR_vm86old:
    490 #endif
    491     default:
    492       return false;
    493   }
    494 }
    495 
    496 bool SyscallSets::IsAllowedGeneralIo(int sysno) {
    497   switch (sysno) {
    498     case __NR_lseek:
    499 #if defined(__i386__) || defined(__arm__)
    500     case __NR__llseek:
    501 #endif
    502     case __NR_poll:
    503     case __NR_ppoll:
    504     case __NR_pselect6:
    505     case __NR_read:
    506     case __NR_readv:
    507 #if defined(__arm__)
    508     case __NR_recv:
    509 #endif
    510 #if defined(__x86_64__) || defined(__arm__)
    511     case __NR_recvfrom:  // Could specify source.
    512     case __NR_recvmsg:   // Could specify source.
    513 #endif
    514 #if defined(__i386__) || defined(__x86_64__)
    515     case __NR_select:
    516 #endif
    517 #if defined(__i386__) || defined(__arm__)
    518     case __NR__newselect:
    519 #endif
    520 #if defined(__arm__)
    521     case __NR_send:
    522 #endif
    523 #if defined(__x86_64__) || defined(__arm__)
    524     case __NR_sendmsg:  // Could specify destination.
    525     case __NR_sendto:   // Could specify destination.
    526 #endif
    527     case __NR_write:
    528     case __NR_writev:
    529       return true;
    530     case __NR_ioctl:  // Can be very powerful.
    531     case __NR_pread64:
    532     case __NR_preadv:
    533     case __NR_pwrite64:
    534     case __NR_pwritev:
    535     case __NR_recvmmsg:  // Could specify source.
    536     case __NR_sendfile:
    537 #if defined(__i386__) || defined(__arm__)
    538     case __NR_sendfile64:
    539 #endif
    540     case __NR_sendmmsg:  // Could specify destination.
    541     case __NR_splice:
    542     case __NR_tee:
    543     case __NR_vmsplice:
    544     default:
    545       return false;
    546   }
    547 }
    548 
    549 bool SyscallSets::IsPrctl(int sysno) {
    550   switch (sysno) {
    551 #if defined(__x86_64__)
    552     case __NR_arch_prctl:
    553 #endif
    554     case __NR_prctl:
    555       return true;
    556     default:
    557       return false;
    558   }
    559 }
    560 
    561 bool SyscallSets::IsAllowedBasicScheduler(int sysno) {
    562   switch (sysno) {
    563     case __NR_sched_yield:
    564     case __NR_pause:
    565     case __NR_nanosleep:
    566       return true;
    567     case __NR_getpriority:
    568 #if defined(__i386__) || defined(__arm__)
    569     case __NR_nice:
    570 #endif
    571     case __NR_setpriority:
    572     default:
    573       return false;
    574   }
    575 }
    576 
    577 bool SyscallSets::IsAdminOperation(int sysno) {
    578   switch (sysno) {
    579 #if defined(__i386__) || defined(__arm__)
    580     case __NR_bdflush:
    581 #endif
    582     case __NR_kexec_load:
    583     case __NR_reboot:
    584     case __NR_setdomainname:
    585     case __NR_sethostname:
    586     case __NR_syslog:
    587       return true;
    588     default:
    589       return false;
    590   }
    591 }
    592 
    593 bool SyscallSets::IsKernelModule(int sysno) {
    594   switch (sysno) {
    595 #if defined(__i386__) || defined(__x86_64__)
    596     case __NR_create_module:
    597     case __NR_get_kernel_syms:  // Should ENOSYS.
    598     case __NR_query_module:
    599 #endif
    600     case __NR_delete_module:
    601     case __NR_init_module:
    602       return true;
    603     default:
    604       return false;
    605   }
    606 }
    607 
    608 bool SyscallSets::IsGlobalFSViewChange(int sysno) {
    609   switch (sysno) {
    610     case __NR_pivot_root:
    611     case __NR_chroot:
    612     case __NR_sync:
    613       return true;
    614     default:
    615       return false;
    616   }
    617 }
    618 
    619 bool SyscallSets::IsFsControl(int sysno) {
    620   switch (sysno) {
    621     case __NR_mount:
    622     case __NR_nfsservctl:
    623     case __NR_quotactl:
    624     case __NR_swapoff:
    625     case __NR_swapon:
    626 #if defined(__i386__)
    627     case __NR_umount:
    628 #endif
    629     case __NR_umount2:
    630       return true;
    631     default:
    632       return false;
    633   }
    634 }
    635 
    636 bool SyscallSets::IsNuma(int sysno) {
    637   switch (sysno) {
    638     case __NR_get_mempolicy:
    639     case __NR_getcpu:
    640     case __NR_mbind:
    641 #if defined(__i386__) || defined(__x86_64__)
    642     case __NR_migrate_pages:
    643 #endif
    644     case __NR_move_pages:
    645     case __NR_set_mempolicy:
    646       return true;
    647     default:
    648       return false;
    649   }
    650 }
    651 
    652 bool SyscallSets::IsMessageQueue(int sysno) {
    653   switch (sysno) {
    654     case __NR_mq_getsetattr:
    655     case __NR_mq_notify:
    656     case __NR_mq_open:
    657     case __NR_mq_timedreceive:
    658     case __NR_mq_timedsend:
    659     case __NR_mq_unlink:
    660       return true;
    661     default:
    662       return false;
    663   }
    664 }
    665 
    666 bool SyscallSets::IsGlobalProcessEnvironment(int sysno) {
    667   switch (sysno) {
    668     case __NR_acct:  // Privileged.
    669 #if defined(__i386__) || defined(__x86_64__)
    670     case __NR_getrlimit:
    671 #endif
    672 #if defined(__i386__) || defined(__arm__)
    673     case __NR_ugetrlimit:
    674 #endif
    675 #if defined(__i386__)
    676     case __NR_ulimit:
    677 #endif
    678     case __NR_getrusage:
    679     case __NR_personality:  // Can change its personality as well.
    680     case __NR_prlimit64:    // Like setrlimit / getrlimit.
    681     case __NR_setrlimit:
    682     case __NR_times:
    683       return true;
    684     default:
    685       return false;
    686   }
    687 }
    688 
    689 bool SyscallSets::IsDebug(int sysno) {
    690   switch (sysno) {
    691     case __NR_ptrace:
    692     case __NR_process_vm_readv:
    693     case __NR_process_vm_writev:
    694 #if defined(__i386__) || defined(__x86_64__)
    695     case __NR_kcmp:
    696 #endif
    697       return true;
    698     default:
    699       return false;
    700   }
    701 }
    702 
    703 bool SyscallSets::IsGlobalSystemStatus(int sysno) {
    704   switch (sysno) {
    705     case __NR__sysctl:
    706     case __NR_sysfs:
    707     case __NR_sysinfo:
    708     case __NR_uname:
    709 #if defined(__i386__)
    710     case __NR_olduname:
    711     case __NR_oldolduname:
    712 #endif
    713       return true;
    714     default:
    715       return false;
    716   }
    717 }
    718 
    719 bool SyscallSets::IsEventFd(int sysno) {
    720   switch (sysno) {
    721     case __NR_eventfd:
    722     case __NR_eventfd2:
    723       return true;
    724     default:
    725       return false;
    726   }
    727 }
    728 
    729 // Asynchronous I/O API.
    730 bool SyscallSets::IsAsyncIo(int sysno) {
    731   switch (sysno) {
    732     case __NR_io_cancel:
    733     case __NR_io_destroy:
    734     case __NR_io_getevents:
    735     case __NR_io_setup:
    736     case __NR_io_submit:
    737       return true;
    738     default:
    739       return false;
    740   }
    741 }
    742 
    743 bool SyscallSets::IsKeyManagement(int sysno) {
    744   switch (sysno) {
    745     case __NR_add_key:
    746     case __NR_keyctl:
    747     case __NR_request_key:
    748       return true;
    749     default:
    750       return false;
    751   }
    752 }
    753 
    754 #if defined(__x86_64__) || defined(__arm__)
    755 bool SyscallSets::IsSystemVSemaphores(int sysno) {
    756   switch (sysno) {
    757     case __NR_semctl:
    758     case __NR_semget:
    759     case __NR_semop:
    760     case __NR_semtimedop:
    761       return true;
    762     default:
    763       return false;
    764   }
    765 }
    766 #endif
    767 
    768 #if defined(__x86_64__) || defined(__arm__)
    769 // These give a lot of ambient authority and bypass the setuid sandbox.
    770 bool SyscallSets::IsSystemVSharedMemory(int sysno) {
    771   switch (sysno) {
    772     case __NR_shmat:
    773     case __NR_shmctl:
    774     case __NR_shmdt:
    775     case __NR_shmget:
    776       return true;
    777     default:
    778       return false;
    779   }
    780 }
    781 #endif
    782 
    783 #if defined(__x86_64__) || defined(__arm__)
    784 bool SyscallSets::IsSystemVMessageQueue(int sysno) {
    785   switch (sysno) {
    786     case __NR_msgctl:
    787     case __NR_msgget:
    788     case __NR_msgrcv:
    789     case __NR_msgsnd:
    790       return true;
    791     default:
    792       return false;
    793   }
    794 }
    795 #endif
    796 
    797 #if defined(__i386__)
    798 // Big system V multiplexing system call.
    799 bool SyscallSets::IsSystemVIpc(int sysno) {
    800   switch (sysno) {
    801     case __NR_ipc:
    802       return true;
    803     default:
    804       return false;
    805   }
    806 }
    807 #endif
    808 
    809 bool SyscallSets::IsAnySystemV(int sysno) {
    810 #if defined(__x86_64__) || defined(__arm__)
    811   return IsSystemVMessageQueue(sysno) || IsSystemVSemaphores(sysno) ||
    812          IsSystemVSharedMemory(sysno);
    813 #elif defined(__i386__)
    814   return IsSystemVIpc(sysno);
    815 #endif
    816 }
    817 
    818 bool SyscallSets::IsAdvancedScheduler(int sysno) {
    819   switch (sysno) {
    820     case __NR_ioprio_get:  // IO scheduler.
    821     case __NR_ioprio_set:
    822     case __NR_sched_get_priority_max:
    823     case __NR_sched_get_priority_min:
    824     case __NR_sched_getaffinity:
    825     case __NR_sched_getparam:
    826     case __NR_sched_getscheduler:
    827     case __NR_sched_rr_get_interval:
    828     case __NR_sched_setaffinity:
    829     case __NR_sched_setparam:
    830     case __NR_sched_setscheduler:
    831       return true;
    832     default:
    833       return false;
    834   }
    835 }
    836 
    837 bool SyscallSets::IsInotify(int sysno) {
    838   switch (sysno) {
    839     case __NR_inotify_add_watch:
    840     case __NR_inotify_init:
    841     case __NR_inotify_init1:
    842     case __NR_inotify_rm_watch:
    843       return true;
    844     default:
    845       return false;
    846   }
    847 }
    848 
    849 bool SyscallSets::IsFaNotify(int sysno) {
    850   switch (sysno) {
    851     case __NR_fanotify_init:
    852     case __NR_fanotify_mark:
    853       return true;
    854     default:
    855       return false;
    856   }
    857 }
    858 
    859 bool SyscallSets::IsTimer(int sysno) {
    860   switch (sysno) {
    861     case __NR_getitimer:
    862 #if defined(__i386__) || defined(__x86_64__)
    863     case __NR_alarm:
    864 #endif
    865     case __NR_setitimer:
    866       return true;
    867     default:
    868       return false;
    869   }
    870 }
    871 
    872 bool SyscallSets::IsAdvancedTimer(int sysno) {
    873   switch (sysno) {
    874     case __NR_timer_create:
    875     case __NR_timer_delete:
    876     case __NR_timer_getoverrun:
    877     case __NR_timer_gettime:
    878     case __NR_timer_settime:
    879     case __NR_timerfd_create:
    880     case __NR_timerfd_gettime:
    881     case __NR_timerfd_settime:
    882       return true;
    883     default:
    884       return false;
    885   }
    886 }
    887 
    888 bool SyscallSets::IsExtendedAttributes(int sysno) {
    889   switch (sysno) {
    890     case __NR_fgetxattr:
    891     case __NR_flistxattr:
    892     case __NR_fremovexattr:
    893     case __NR_fsetxattr:
    894     case __NR_getxattr:
    895     case __NR_lgetxattr:
    896     case __NR_listxattr:
    897     case __NR_llistxattr:
    898     case __NR_lremovexattr:
    899     case __NR_lsetxattr:
    900     case __NR_removexattr:
    901     case __NR_setxattr:
    902       return true;
    903     default:
    904       return false;
    905   }
    906 }
    907 
    908 // Various system calls that need to be researched.
    909 // TODO(jln): classify this better.
    910 bool SyscallSets::IsMisc(int sysno) {
    911   switch (sysno) {
    912     case __NR_name_to_handle_at:
    913     case __NR_open_by_handle_at:
    914     case __NR_perf_event_open:
    915     case __NR_syncfs:
    916     case __NR_vhangup:
    917 // The system calls below are not implemented.
    918 #if defined(__i386__) || defined(__x86_64__)
    919     case __NR_afs_syscall:
    920 #endif
    921 #if defined(__i386__)
    922     case __NR_break:
    923 #endif
    924 #if defined(__i386__) || defined(__x86_64__)
    925     case __NR_getpmsg:
    926 #endif
    927 #if defined(__i386__)
    928     case __NR_gtty:
    929     case __NR_idle:
    930     case __NR_lock:
    931     case __NR_mpx:
    932     case __NR_prof:
    933     case __NR_profil:
    934 #endif
    935 #if defined(__i386__) || defined(__x86_64__)
    936     case __NR_putpmsg:
    937 #endif
    938 #if defined(__x86_64__)
    939     case __NR_security:
    940 #endif
    941 #if defined(__i386__)
    942     case __NR_stty:
    943 #endif
    944 #if defined(__x86_64__)
    945     case __NR_tuxcall:
    946 #endif
    947     case __NR_vserver:
    948       return true;
    949     default:
    950       return false;
    951   }
    952 }
    953 
    954 #if defined(__arm__)
    955 bool SyscallSets::IsArmPciConfig(int sysno) {
    956   switch (sysno) {
    957     case __NR_pciconfig_iobase:
    958     case __NR_pciconfig_read:
    959     case __NR_pciconfig_write:
    960       return true;
    961     default:
    962       return false;
    963   }
    964 }
    965 
    966 bool SyscallSets::IsArmPrivate(int sysno) {
    967   switch (sysno) {
    968     case __ARM_NR_breakpoint:
    969     case __ARM_NR_cacheflush:
    970     case __ARM_NR_set_tls:
    971     case __ARM_NR_usr26:
    972     case __ARM_NR_usr32:
    973       return true;
    974     default:
    975       return false;
    976   }
    977 }
    978 #endif  // defined(__arm__)
    979 
    980 }  // namespace sandbox.
    981