Answers:
该文件/proc/kallsyms
列出了正在运行的内核的所有符号。按照惯例,系统调用的名称以开头sys_
。在64位系统上,对32位程序的系统调用的名称以开头sys32_
。严格来说,它列出了内部内核函数,而不是系统调用,但是我认为通信确实有效(每个系统调用都会调用内部内核函数来完成这项工作,而且我认为名称始终是带有sys_
前缀的系统调用的名称。)。
</proc/kallsyms sed -n 's/.* sys_//p'
这通常不是有用的信息,因为系统调用的变化非常缓慢。可选组件使用设备(使用ioctl何时read
和write
不剪切时使用ioctl),文件系统,套接字等常规功能来提供现有系统调用的功能。确定受支持的syscall列表不会告诉您有关这些功能的任何信息系统支持的功能。其他内部函数名称也无济于事,因为它们的变化非常快:在一个内核版本上实现某些功能的函数的名称可能在下一版本上更改。
在写这个答案时,我一直在寻找新的选择,所以我只写了一些关于每个选择的详细信息,并做了一些统计。基本上,您可以:
/proc
)。/sys
目录。完成数学运算后,我建议(在其他选择中)使用/sys
文件系统,因为就系统调用次数而言,它似乎能提供最佳结果。如果您不想阅读其他技巧,可以直接跳到该部分。
尽管您可能会错过其中的一些apropos
手册,但是您可以使用它列出属于第2节(系统调用)的所有联机帮助页:
$ apropos -s2 . | awk '{print $1}' | column
column
如果您不希望使用花式列输出,请删除。
我刚刚发现了它,但是有一个关于系统调用的Linux手册页,您将能够在其中找到大多数。
$ man syscalls
我还遇到了这两个有趣的网站:
编辑:现在,当以编程方式(或至少不依赖于已记录的功能)确定可用的系统调用时,恐怕内核不会保留其系统调用表,至少不会以字符串列表(您可能希望操纵它们)。在此级别上,我们将更多地讨论函数地址和指针,而不是函数名称。
我只是浏览了/usr/include
目录并添加grep
了一些内容:您可能会发现以下目录很有趣。其中有些可能在您的计算机上有所不同,具体取决于您的体系结构和分布,但是我相信您将能够对其进行调整。
通过在此文件中查找函数定义,您将遇到许多系统调用,即使它们中没有完整定义它们。我grep
在这些目录中运行了几个,并且能够找到一些系统调用的提及。这是一个例子:
$ grep 'sys_exit' /usr/include -R
asm-generic/unistd.h:__SYSCALL(__NR_exit, sys_exit)
因此,我猜测找到其中一些的另一种方法是:
$ egrep '^__SYSCALL' /usr/include -Rh | awk '{print $2}' | tr -d ')'
另一种解决方案是使用内核源代码本身(而不只是标头!),并找到一种有效搜索它的方法。由于内核提交303395ac3bf3e2cb488435537d416bc840438fcb,您可能会发现它比以前容易一些。这是3.13(这是我的内核)的示例:
$ wget https://git.kernel.org/cgit/linux/kernel/git/stable/linux-stable.git/plain/arch/x86/syscalls/syscall_64.tbl?id=refs/tags/v3.13 -O syscall_64.tbl
现在您已经获得了实际的syscalls表,只需浏览即可:
$ while read line; do awk '! /#/ {print $3}'; done < syscall_64.tbl
您可以找到一种方法,使用uname
和,根据运行的内核版本和体系结构直接从git.kernel.orgarch
下载tbl
文件。
/sys
文件系统Gilles的回答给了我一些启发,您可能会在其中找到这些系统调用/sys/kernel/debug/tracing/events/syscalls
。该目录用于监视系统上每个系统调用的使用。每个系统调用中都有两个目录:
因此,使用ls
,grep
并cut
...
$ ls /sys/kernel/debug/tracing/events/syscalls | grep 'sys_enter' | cut -d'_' -f3
在我的系统上:
grep
__SYSCALL
头文件中的-ing 显示212个系统调用。/sys
显示的290个系统调用。现在,如果我把所有东西都放在一起...
$ apropos -s2 . | awk '{print $1}' > system_calls.txt
$ egrep '^__SYSCALL' /usr/include -Rh | awk '{print $2}' | tr -d ')' >> system_calls.txt
$ while read line; do awk '! /#/ {print $3}'; done < syscall_64.tbl >> system_calls.txt
$ ls /sys/kernel/debug/tracing/events/syscalls | grep 'sys_enter' | cut -d'_' -f3 >> system_calls.txt
$ sort < system_calls.txt | uniq | wc -l
707
我们去了,有707个系统调用!当然,该数字反映了“系统调用”的非常灵活的定义,因为3.13应该只提供274个系统调用(阅读/sys
似乎是最接近的解决方案)。
所有答案都很好。
如果您要查找特定的系统调用名称:
$ cat /proc/kallsyms | grep <sys_call_name>
如果要查找所有系统调用的列表:
$ cat /proc/kallsyms
/proc/kallsyms
可以像其他文件一样进行操作,因此在程序中使用它变得非常容易。