システム コールの仕組みと、システム コール全般の必要性については、ほぼ理解しています。ただし、create() file、read() file、close() などの一部のシステム コールがカーネル モードでのみ実行される必要がある理由がわかりません。
たとえば、create() および read() ファイルの場合、ユーザー空間またはユーザーモードではなぜ発生しないのでしょうか? ユーザーがファイルを作成および読み取ることで、システムに損害を与える可能性はあるのでしょうか? close() システム コールの場合にも同じ疑問があります。
答え1
create() ファイル、read() ファイル、close() などの一部のシステム コールがカーネル モードでのみ実行される必要がある理由がわかりません。
そうですね、システム コールは定義上、カーネル モードで実行されます。ユーザー空間では、これらは通常、同じ名前を持つライブラリ ラッパー関数を介して利用できます。出典man 2 intro
:
システム コールは、Linux カーネルへのエントリ ポイントです。通常、システム コールは直接呼び出されません。代わりに、ほとんどのシステム コールには、システム コールを呼び出すために必要な手順 (カーネル モードへのトラップなど) を実行する対応する C ライブラリ ラッパー関数があります。したがって、システム コールを行うことは、通常のライブラリ関数を呼び出すことと同じように見えます。
(参照man 2 syscall
)
コメントで @dirkt と @StephenKitt が述べているように、あなたが言及したシステム コールは、ファイル記述子テーブルに書き込み、ファイル I/O のドライバーにアクセスし、アクセス権を確認する必要があるため、カーネル空間で実行する必要があります。
答え2
たとえば、ファイルでは
create()
、read()
なぜユーザー空間では発生しないのでしょうか?
いくつかのプラットフォーム(Linuxベースのものを含む)では、ファイルシステムIOをユーザー空間から実行することが可能だ。これはFUSEと呼ばれ、以下で読むことができる。ユーザー空間のファイルシステムトピックの紹介の 1 つです。
FUSEベースのファイルシステムは数多く存在し、その中にはSSHFS(ファイルシステム以上ssh
)およびS3QL(クラウド ストレージ上のファイルシステム)。
カーネルは、ユーザー空間クライアント (アプリケーション プログラム) と FUSE 実装の間のレイヤーを仲介し、ファイルシステムのセマンティクスが検証され、一貫性が保たれるようにしますが、、、、、、などの実際の IO コードはすべてユーザーcreat()
空間サービスopen()
から実行されます。read()
write()
fcntl()
close()