A _syscall macro
これらのマクロは、指定した引き数を持つ name という名前の関数を生成する。 一度ソースファイル中でこの _syscall() マクロを呼んでおくと、 name でこのシステムコールを呼ぶことができる。
_syscall() マクロはプロトタイプを「生成しない」。ユーザーは自分で プロトタイプを書かなければならないかもしれない。
システムコールは正のエラーコードのみまたは負のエラーコードのみを 返すことが定められているわけではない。 そのシステムコールがどのようなエラーコードを返すかについて確認する ためにはそのソースコードを読む必要がある。 たいていの場合、標準のエラーコードの負の値 (例えば -EPERM のような) を返す。 _syscall() マクロは、そのシステムコールの返り値 r が負でない場合、 その値をそのまま返す。負の場合には変数 errno に -r を設定して -1 を返す。 各エラーコードに関しては errno(3) を参照。
(mmap(2) などの) いくつかのシステムコールは 5個より多くの引き数を要求する。 こういったシステムコールはスタックに引き数をプッシュし、 その引き数のかたまりへのポインタを渡して処理される。 システムコールを定義する場合、その引き数の型は値渡し (by-value) か、 (構造体のような集合的なデータの場合は) ポインタ渡し (by-pointer) でなければならない。
#include <stdio.h> #include <stdlib.h> #include <errno.h> #include <linux/unistd.h> /* for _syscallX macros/related stuff */ #include <linux/kernel.h> /* for struct sysinfo */ _syscall1(int, sysinfo, struct sysinfo *, info); /* 注意: nroff のソースファイルから直接コピーするときは printf 文に含まれている余分なバックスラッシュを除去する ことを忘れないように */ int main(void) { struct sysinfo s_info; int error; error = sysinfo(&s_info); printf("code error = %d\n", error); printf("Uptime = %lds\nLoad: 1 min %lu / 5 min %lu / 15 min %lu\n" "RAM: total %lu / free %lu / shared %lu\n" "Memory in buffers = %lu\nSwap: total %lu / free %lu\n" "Number of processes = %d\n", s_info.uptime, s_info.loads[0], s_info.loads[1], s_info.loads[2], s_info.totalram, s_info.freeram, s_info.sharedram, s_info.bufferram, s_info.totalswap, s_info.freeswap, s_info.procs); exit(EXIT_SUCCESS); }
code error = 0 uptime = 502034s Load: 1 min 13376 / 5 min 5504 / 15 min 1152 RAM: total 15343616 / free 827392 / shared 8237056 Memory in buffers = 5066752 Swap: total 27881472 / free 24698880 Number of processes = 40