方法tl; dr
あなたの図は本質的に正しいです。
/dev/<device>
ファイル
あなたの質問に答え始める最も基本的な方法は、/dev/<device>
ファイルとは何かだと思います。ハードディスクがあるとします。このハードディスクにはMBRベースのパーティションテーブルがあり、2つのパーティションがあります。1つはフォーマットされたext4にいくつかのファイルがあり、もう1つはLVM用に設定されています。この回答では、オンザフライのデバイスファイル作成について説明していることに注意してください。これは、Linuxカーネルを使用していることを意味します。他のユニックスでは状況が少し異なります。
このハードディスクを接続すると(またはシステムが起動時に検出した場合)、デバイスファイルが/dev
ディレクトリに作成されます-一般的にどちら/dev/sd*
かと呼ばれます/dev/hd*
(ドライブの接続に使用されるコントローラに応じて)-*は文字。デバイスファイルのバイトは、基本的に物理ディスクのバイトに線形にマッピングされます。ツールを使用してデバイスファイルの先頭に書き込むと、そのデータは物理ディスクの物理的な先頭にも書き込まれます。
現在、システムはMBRやGPTなどのパーティションテーブルも認識します。初期デバイスファイルが作成されると、パーティションテーブルがあるかどうかを判断するために読み取られます。存在する場合、これらのパーティションを表すデバイスファイルが作成されます。したがって、元のデバイスファイルが呼び出されたとする/dev/sda
と、デバイス/dev/sda1
(最初のext4フォーマットのパーティションを表す)と呼ばれるデバイスファイル/dev/sda2
(2番目のLVMパーティションを表す)が作成されます。これらはドライブ全体と同じ方法でそれぞれのパーティションに線形にマッピングされます-つまり、ツールを使用して(たとえば)の先頭に書き込むと、/dev/sda2
書き込まれたデータは物理的に2番目のパーティションの先頭に書き込まれます、実際には真ん中です そこから2番目のパーティションが開始されるためです。
ブロックとセクター
これは、ブロックとセクターについて話すのに便利な時間です。これらは物理ディスク上のスペースの単なる測定値であり、それ以上のものはありません(少なくとも正しく理解している場合)。セクターは、ハードドライブ上の物理領域です。通常、512バイト-新しいハードドライブでは4 KBです。ブロックも測定単位であり、ほぼ常に8 KBです。誰かがブロックの読み取りと書き込みについて話すとき、それは単に、データの各バイトを個別に読み取る代わりに、8 KBのチャンクでデータを読み書きすることを意味します。
ファイルシステムとiノード
次に、ファイルシステムとiノード。ファイルシステムはかなり単純な概念です。ファイルシステムが存在する領域の先頭(この領域は通常パーティションです)には、ファイルシステムに関する情報がたくさんあります。このヘッダー(スーパーブロックとも呼ばれます)は、最初にどのファイルシステムドライバーを使用してファイルシステムを読み取るかを決定するために使用され、次に選択したファイルシステムドライバーがファイルを読み取るために使用します。もちろんこれは単純化ですが、基本的に2つのもの(fsタイプに応じてディスク上の2つの異なるデータ構造として格納される場合とされない場合があります)を格納します:ディレクトリツリーとiノードのリスト。ディレクトリツリーは、ls
またはを実行したときに表示されるものですtree
。ディレクトリツリーには、どのファイルとディレクトリが他のどのディレクトリの子であるかが示されます。ファイル/ディレクトリの親子関係は、私たちが知っているUNIXディレクトリツリーを形成します。
ただし、ディレクトリツリーには名前のみが含まれます。これらの名前は、さらにiノード番号に関連付けられています。iノード番号には、ファイルの断片がディスク上の物理的に格納されている場所などの情報が含まれています。iノード自体は、名前のない単なる「ファイル」です。iノードは、ディレクトリツリーを介して名前に関連付けられます。「スーパーブロック、iノード、デントリ、およびファイルとは」も参照してください。
これまでのところ、/dev/sd*
ファイルはハードドライブに/dev/sd*#
マップされ、ファイルはのパーティション番号#
にマップされ/dev/sd*
ます。ファイルシステムは、ディレクトリツリーを追跡するディスク上のデータ構造です。通常、パーティション(/dev/sd*#
)に保持されます。ファイルシステムにはiノードが含まれています。iノードは、ファイルとそれらのファイルに関連付けられたデータ(ディレクトリツリーでの名前と位置を除く)を表す番号です。
ファイルシステムは通常、ブロック単位でデータを追跡していることに注意してください。通常、ディレクトリツリーとiノードリストはバイト単位ではなくブロック単位で保存され、iノードはバイト単位ではなくディスク上のブロックを指します。(これは、ファイルシステムがブロック全体を割り当てたが、ファイルの最後の部分にそのブロック全体を使用する必要がないため、ファイルが通常スペースの半分のブロックを浪費する問題を引き起こす可能性があります。)
デバイスマッパー
パズルの最後のピースは、デバイスマッパーと呼ばれるLinuxカーネルの非常に重要なモジュールです(ロードしますmodprobe dm
)。デバイスマッパーを使用すると、基本的に/dev/mapper
ディレクトリに別のデバイスファイルを作成できます。次に、そのデバイスファイルは別のデータソースにマップされ、そのプロセスで変換される可能性があります。最も単純な例は、ファイルの一部を読み取ることです。
パーティションテーブルを備えたフルディスクイメージがあるとします。イメージ内のパーティションの1つからデータを読み取る必要がありますが、単一パーティションイメージではなくフルディスクイメージであるため、そのパーティションだけに到達することはできません。解決策は、パーティションがイメージ内のどこにあるかを見つけ、ディスクイメージのその部分にマッピングする新しいデバイスファイルを作成することです。以下に図を示します。
.-------------------.
| /dev/mapper/foo | <- This is the device file created with the device mapper
.___________________.
\ /
\ /
\ / <- This is a small section of the image being mapped to
\ / the new device file
\ /
\ /
.------------------.
| diskimage.img | <- This is the full-disk image. It's a regular file.
.__________________. Notice how the mapping goes to _part_ of the file.
別の考え方は、変換パイプラインのようなものです(これは、カーネルの内部で起こっていることのより正確なメタファーです)。コンベアベルトを想像してください。要求-読み取り、書き込みなど-は、デバイスマッパーで作成されたデバイスファイルで、コンベアベルトの一端から始まります。その後、リクエストはデバイスマッパートランスフォーメーションを介してソースファイルに移動します。上記の例では、このソースファイルは通常のファイルですdiskimage.img
。以下に図を示します。
Read operation goes onto
device mapper conveyor belt
read() The device mapper transforms the read The modified read request finally
\ request by moving the requested region reaches the source file, and the data
\ Beginning of conveyor belt to read forward by some number of bytes. is retrieved from the filesystem.
\
\ .-------------------. .--------------------------. .------------------------.
\ | /dev/mapper/foo | | Transformation logic | | /path/to/diskimage.img |
\ .___________________. .___+_____+_____+_____+____. .________________________.
\-->
---------------------------------------------------------------------------------------------------------------
o o o o o o o o o o o
図では、デバイスマッパーに接続された変換ロジック+
には、コンベヤベルト上を移動する読み取り要求を操作するツールがほとんどありません。
今、私は特にその図をコピーしてLVM用に変更する気はありませんが、基本的に、変換部分は何でも構いません-バイト範囲を前方にシフトするだけではありません。これがLVMの仕組みです。LVM物理エクステントはLVMの一部であり、ディスク上にあり、データの場所を追跡します。LVMのファイルシステムのように考えてください。コンベヤベルトの比phorでは、物理エクステントはソースファイルの1つであり、変換はLVMがその処理を行い、論理ボリューム(コンベヤベルトの左端のアイテム)の要求をディスク上の物理データにマッピングします。そういえば...
私はLVMの概念に少しさびていますが、ボリュームグループであるIIRCは本質的にLVMのディスクのようなものです。繰り返しますが、IIRC、RAIDレベルなどはボリュームグループごとに管理されます。論理ボリュームはパーティションのようなものであり、論理ボリュームは実際にそれらを表すデバイスファイルを持っています。論理ボリュームにファイルシステムとスタッフを置きます。
デバイスマッパーの優れた点は、それを使用して構築されたロジックをデータスタックに任意に挿入できることです。読み取り中のデバイス名を変更するだけです。これは、暗号化されたパーティションの仕組みです(ファイルレベルで機能する暗号化スキームではなく、FUSEを使用します)。これがLVMの仕組みです。現時点では他の例は考えられませんが、私を信じてください。デバイスマッパーはかなり悪いです。
論理ブロックのアドレス指定
私はこれを聞いたことがないので、それに関する情報を提供することはできません。誰かが来て、この答えを編集することを願っています。