Linuxのカーネルに関する世界観です。
パソコンはOSが無ければただの箱と言うが、言ってしまえば、Linuxをインストールしたパソコンでは、常にLinuxカーネルが動いている。
常に動きながら、たくさんのプログラムを「自身の上で実行する」、それがLinuxカーネルだ。
GNOMEはX11を使い、X11はカーネルを使い、カーネルはハードウェアを使う。そして、最終的にはCPUとメモリが動いている。
それを階層構造で示した時に、メインとなるのは、Linuxカーネルだ。
Androidのスマホを実行する場合でも、Linuxのサーバーを利用する場合でも、その環境で常に動いているのは、Linuxカーネルだ。
そう考えると、このLinuxと言うカーネルがオープンソースで技術的に公開されていて、自由に参加出来て、改良やコピー・再配布も自由である、と言うことは、この上なく良いことのように感じられる。それをやりたかったのが、GNU Projectのストールマンだと思う。
カーネルとは、ハードウェアとソフトウェアの橋渡しをするものであり、システムの中で常に実行されながら、特定のプログラムを適切に実行し、それぞれのプログラムにリソース(利用出来るコンピュータ資源)を割り当てると同時に、ソフトウェアからの要求に応じてハードウェアへのアクセス手段を与え、サーバーやアプリケーションのようなプログラムがプログラムとして実行が可能になるための環境を与えるものだ。
OSの中で、カーネルとはある意味下層部分と上層部分を繋げるノリのようなものであると同時に、ソフトウェアの仕掛け全体の中核に位置しながら、全てをきちんと成り立たせる、オーケストラで言えばコンダクター(指揮者)のようなものである。だが、主役は基本的にアプリケーションであり、それらが楽器である。
OSの中でカーネルは一部分にすぎず、コマンドを入力するシェルや、それぞれの仕事を、UNIXにおいてはそれぞれが単機能に行う、各種のコマンドプログラム、システムに常駐するデーモン、X11のようなハードウェアをグラフィカルな操作インターフェースに変える特殊なアプリケーション、そしてコンパイラやパッケージ管理システムがなければならない。GNU/LinuxにおいてはカーネルはLinuxだが、OSとしてはGNUのさまざまなツールを使うため、GNU/Linuxと言う呼び名が適切であると(少なくともFSFからは)言われている。
だが、技術的に見ると、デバイスドライバやメモリマネージメントやCPUの並列処理といったハードウェアの操作と、C言語ライブラリとの関係性、そしてプロセスの作成とリソースの割り当てやタイムスケジューリング、OSの下層システムとして必要なファイルシステムの実現やネットワーク接続(パケットやソケットなどの実現)が多い。ハードウェアをソフトウェアから適切に使うことが主目的であり、ネットワークやグラフィックスで専門的な用途を行うためには、カーネルを用いてハードウェアに接続する「ユーザーランド」が必要となる。これは、Apache HTTPDやX11 Serverのようなシステムに必須の専門プログラムから、専門的アプリケーションに至る広汎なソフトウェア集団となる。
カーネルの特殊な用途はネットワークであり、カーネル以外での特殊の用途はグラフィックスであると言える。両者はカーネルとユーザーランドのどちらにも区分されにくい領域であり、WindowsのようなOSではグラフィックスはOSに統合されている。特に、X11はとても巨大であり、X11からKDE/GNOMEに至るGUIデスクトップ環境の領域は、「GUI時代の第二のカーネル(サブカーネル)」と呼んでも良いかもしれない。(サブカーネルは、僕の作った造語にすぎません。)
Linuxカーネルも参照のこと。
Linuxの大きな特徴として、低水準レイヤーと高水準レイヤーがある。
UNIXでは、カーネルの上でユーザーランドのプログラムが動く、という比較的単純なレイヤー分けがなされているが、それが大きく様々なプログラムが発達したLinuxでは、もっと複雑になる。
たとえば、X11では、X Window Systemがまず最下部にあり、その上でGTKやQtなどのツールキットがあって、その上にGNOMEやKDEのデスクトップ環境がある。
また、プログラミング言語では、Javaの仮想マシンやPerlやPythonやRubyのインタープリタがあって、その上にDjangoやRailsなどのフレームワークがある。
ほかにも、ApacheなどのWebサーバや、TomcatやJBossなどのミドルウェア、MySQLやPostgreSQLなどのデータベース管理システムが、低水準レイヤーとして存在する。
こうした「高水準・低水準」という考え方がLinuxには多く見られる。自分でプログラムを開発する場合には、自分のプログラムよりも低水準のレイヤーがどういう技術仕様で実装されているかやAPIなどに習熟しておく必要がある。
システムレイヤーも参照のこと。
OSには二つの側面、すなわち「ハードウェアシステムの利用の簡素化」と「リソースの管理」があります。
OSがもしなかったら、ハードウェアデバイスを自分で管理して操作しなければならない。多くのデバイスはとても詳細で難しい仕様をしており、プログラマが扱うのは困難を極める。OSは、このようなデバイスに対して抽象化を行い、「抽象化レイヤー」を提供する。
また、OSがもしなかったら、ハードウェアリソースを自分で管理しなければならない。これはすなわち、プリンタやストレージを扱うのであっても、きちんと正しい順番でプリンタやストレージに情報を書き込むことができなくなる、ということを意味する。OSは、こうしたリソースを裏側で管理し、「リソースマネージャ」として機能する。
詳しくは以下の書籍を参照のこと。
OSも参照のこと。
Linuxカーネルは、システムコールによる、関数呼び出しとよく似たモデルで、サービスをプロセスやユーザーに提供する。
Linuxカーネルは、自分から何かをすることは一切なく、全てがサービスの要求であるシステムコールを通じて行われる。
このことを「イベント駆動」と呼ぶこともある。
しかしながら、僕はここに、コンピュータの原理や仕組みそのものの制限と可能性が見えてくると思う。
すなわち、Linuxはイベントによって「通知」し、普段何もしないで「待機」している中で「これをしろ」と言われた時だけそれをするようにできている。
実際のハードウェアと違って、「待機と通知」をコンピュータ上で実現するのは、意外と難しい。待機している状態にも、常にイベントが発生してこないかを「監視」し、もしイベントが通知されたら「対応」しなければならないからである。
Windows APIやX11では、これをイベントループ(メッセージループ)によって実現する。すなわち、常にイベントを監視するループ処理を行い、次のイベントが通知されたらそれに対して対処し、イベントハンドラに結びつけられたコールバック関数を実行する。
このように、LinuxであってもWindowsであってもX11であっても、意外と「待機しておけ」というだけの状態を作り出すのがパソコンでは難しい。逆に、自分から「印刷してほしい」とか、「このWebサイトの情報をダウンロードしてほしい」とお願いをするのは簡単である。そのため、待機をするだけであってもイベント駆動でプロセスからの要求に応答するように作る。
このような時に、イベント駆動だけではなく、「ポーリング」という仕組みを取ることもある。これは「一定時間ごとに問い合わせて確認する」というもので、イベント通知とは異なる仕組みである。また、キューとして発生したメッセージをひとつひとつ順番に処理する仕組みもある。これらはメールの確認やプリンターのジョブキューなどに使われている。
システムコール・APIも参照のこと。
OSを参照のこと。
UNIXを参照のこと。
Linuxカーネルを参照のこと。