
カーネル ヘッダーについて、またそれがどこでどのように使用されるかについて明確な理解がないため、これは一貫性のない質問かもしれません。フラグが立てられると思います。私の質問は 3 つの部分から構成されています。
カーネル ヘッダーは、モジュールなどのカーネルの他の部分が使用できるようにインターフェイスを提供するものだと思います。これは私の知識です。カーネル ヘッダーを使用したコードは見たことも見つけたこともありません (どなたか教えていただければ幸いです)。ユーザー空間でも使用できますか? コード例があれば教えてください。
make headers_install
カーネル ヘッダーの使用はユーザー空間で公開されているが、同時にユーザー空間でカーネル ヘッダーを使用することは推奨されていないことがわかりました。推奨されていないのであれば、それをユーザー空間に公開することに何の意味があるのでしょうか?に従ってこれそしてこれカーネル ヘッダー ファイル (.h ファイル) は、次の 3 つの場所にある必要があります。a.
/usr/include/linux/kernel.h
ユーザー空間用 b./lib/modules/$(uname -r)/build/include/linux/sched.h
外部モジュール c./usr/src/...
カーネル モジュール用 異なるディレクトリのヘッダー ファイルは目的やインターフェイス、シグネチャが異なるということですか? つまり、#include <linux/xyz.h>
ユーザー空間のコードは#include <linux/xyz.h>
カーネル モジュールとは異なる意味を持つということですか? また、外部モジュールはカーネル モジュールと同じですか?
ありがとう。
答え1
Unix & Linux StackExchange へようこそ!
はい、カーネル ヘッダーはカーネルの他の部分へのインターフェイスを提供します。この点では完全に正しいです。また、カーネルとユーザー空間間のインターフェイスの定義も含まれていますが、通常、「生の」カーネル インターフェイスは直接使用されるのではなく、C ライブラリ (多くの場合glibc
) を介して使用されます。
ユーザー空間カーネル インターフェースには、下位互換性の理由から、特定のシステム コールの複数のバージョンが含まれる場合があります。C ライブラリを介してシステム コールを行うことで、すべてのアプリケーションが実際のシステム コールの同じバージョンを取得し、一貫した動作が保証されます。また、カーネル インターフェースの関連部分が更新された場合、新しい機能を利用するには C ライブラリを更新するだけで済みます。
(たとえば、Y2K38 問題を回避するために 32 ビット アーキテクチャで time_t が 64 ビットに拡張されると、C ライブラリはカーネル インターフェイスの 64 ビット バージョンを常に使用するように移行しますが、32 ビット バージョンをまだ使用するアプリケーション用にユーザー空間で構成可能なマッピングを持つようになります。その時点で、32 ビットの time_t を使用する関数は廃止され、カーネルから削除され、C ライブラリは、32 ビット タイプをまだ使用するレガシー アプリケーションに対してより適切な回避策を提供できます。)
したがって、C ライブラリの独自のバージョンもコンパイルしていない限り、通常はカーネル ヘッダーを直接使用するのではなく、C ライブラリの開発ヘッダーを使用することをお勧めします。
ヘッダーは/usr/include/linux/
通常、C ライブラリの開発ヘッダー パッケージに付属しており、C ライブラリがコンパイルされたカーネルのバージョンを記述します。これは、ユーザー空間アプリケーション開発者が通常必要とするものです。
/lib/modules/$(uname -r)/build
多くの場合、実際に実行されているカーネル バージョンのヘッダーまたは完全なソース コードが保存されている場所へのシンボリック リンクです/usr/src/...
。これは、外部 (つまりサードパーティ) カーネル モジュール、つまりメイン カーネル ソース コードに統合されていないソースからのカーネル モジュールをコンパイルするときに使用されます。これらのヘッダーには、モジュールがバージョン固有のカーネル内部 API を使用できるように、必要なカーネル API バージョン署名が含まれています。