書式
fdisk [-u] [-b sectorsize] [-C cyls] [-H heads] [-S sects] devicefdisk -l [-u] [device ...]
fdisk -s partition ...
fdisk -v
説明
ハードディスクは、一つ以上の論理的なディスクに分割することができる。 これは パーティション (partition) と呼ばれる。この分割に関する情報は、ディスクのセクタ 0 に置かれる パーティションテーブル に保存される。BSD の世界では、それぞれ「ディスクスライス (disk slice)」、 「ディスクラベル (disklabel)」といった用語が用いられる。
Linux は少なくとも一つのパーティションを必要とする。 すなわちルートファイルシステムとするパーティションである。 また Linux ではスワップファルやスワップパーティションを 利用することができるが、後者の方が効率が良い。 したがって、通常は二つめのパーティションを スワップ用に利用したくなる場合が多いだろう。 Intel 互換のハードウェアでは、システムをブートさせる BIOS はディスクの 先頭 1024 シリンダにしかアクセスできない場合が多い。 したがって大きなディスクを使っているユーザーは、 数メガバイト程度の第三のパーティションを追加することになる。 これは典型的には /boot にマウントされ、カーネルイメージと、 ブートに必要ないくつかの外部ファイルを保存する。 このようにして、ブートに必要なファイルが BIOS によって アクセス可能であることを保証するのである。 またセキュリティ、保守の都合、バックアップ、テストなど、 より多くのパーティションを使う理由は他にも存在する。
(最初の形式で起動された場合には) fdisk はメニュー駆動型のプログラムであり、 パーティションテーブルの作成と操作を行う。 DOS 形式のパーティションや、BSD, SUN 形式のディスクラベルを扱うこともできる。
device
に指定するのは通常以下のうちのどれかである。
- /dev/hda /dev/hdb /dev/sda /dev/sdb
partition は device 名にパーティション番号を付加したものである。例えば /dev/hda1 はシステムの第一 IDE ハードディスクの第一パーティションを指す。 IDE ディスクは 63 個までのパーティションを保持することができる。 SCSI ディスクは 15 までである。 /usr/src/linux/Documentation/devices.txt も参考にすると良い。
BSD/SUN 形式のディスクラベルは 8 パーティションを扱うことができる。 そのうち 3 番目は「ディスク全体」を表すパーティションとなる。 先頭セクタを実際に利用するパーティション (スワップなど) を シリンダ 0 から割り当ててはならない。ディスクラベルを破壊してしまう。
IRIX/SGI 形式のディスクラベルは、16 パーティションを記述できる。 そのうちの第 11 番目は `volume' 全体に対応するパーティションであり、 第 9 番目は `volume header' とラベル付けされる。 volume header はパーティションテーブルの領域もカバーする。 つまり volume header はブロック 0 から始まり、デフォルトでは シリンダ 5 までの部分を占める。volume header の残りの部分は ヘッダディレクトリエントリに用いられる。 volume header は他のパーティションと重なってはならない。 またパーティションテーブルが含まれているので、形式を変更したり、 ファイルシステムを作ったりもできない。 このラベル形式は、IRIX/SGI マシンで動作している Linux か、 IRIX/SGI ディスクを Linux で使う場合に限って用いること。
DOS 形式のパーティションテーブルは、パーティションの数に制限がない。 セクタ 0 には、4 つのパーティション (「基本 (primary) パーティション」と呼ばれる) に関する情報が記述されている。 これら基本パーティションは、拡張 (extended) パーティションにすることもできる。 これは論理 (logical) パーティションの入れ物となる。 拡張パーティションにはディスクリプターが セクタのリンクリストの形式で置かれ、 それぞれ対応する論理パーティションの情報を保持する。 四つの基本パーティションには (存在していなくても) 番号 1-4 が割り当てられる。論理パーティションの番号は 5 から始まる。
DOS 形式のパーティションテーブルでは、それぞれのパーティションの スタートオフセットとサイズは、二種類の方法で保存される。 一つはセクタの絶対数 (32 ビット) であり、 もう一つは「シリンダ数/ヘッド数/セクタ数 (C/H/S)」の三つの組み合わせである (それぞれ 10, 8, 6 ビット)。 前者には問題は特になく、512 バイトのセクタで 2 TB を扱うことができる。 後者には二種類の問題がある。まず第一に、この C/H/S を与えるためには、 ヘッド数とトラックあたりのセクタ数を知っていなければならない。 第二に、これらの数値がわかったとしても、24 ビットでは足りないかもしれない。 DOS は C/H/S だけを用いる。Windows は両方を用いる。 Linux では C/H/S は使わない。
fdisk は、 可能な場合にはディスクのジオメトリを自動的に取得する。 これはディスクの物理的なジオメトリであるとは限らない (実際、最近のディスクでは、本当に物理的な - 単純な C/H/S 形式で記述できるような - ジオメトリを持っていないものもある)。 しかしいずれにせよ、 MS-DOS はこのジオメトリをパーティションテーブルで利用する。
Linux しか置かないディスクなら、通常はデフォルトで問題なくすべてうまくいく。 しかし他の OS とディスクを共有しなければならない場合には、 まず他の OS 上で、その OS 付属の fdisk を先に実行し、 少なくとも一つのパーティションを作っておくと良い場合が多い。 Linux は、他の OS とうまく付き合うために、 ブート時にパーティションテーブルを参照し、 どんなジオメトリが要求されているのかを判断・決定しようとする (要求されているジオメトリは、 物理的なものとは異なっているかもしれないから)。
パーティションテーブルが表示されるときには、パーティションテーブルの エントリに対して整合性チェックが行われる。このチェックは、パーティション の開始と終了に関する、物理的な情報と論理的なそれとが同一であるか、また パーティションの開始/終了点がシリンダ境界にあるかを調べる (ただし後者 のチェックでは、最初のパーティションは例外である)。
MS-DOS のバージョンによっては、最初のパーティションの開始点をシリンダ 境界ではなく先頭シリンダの第 2 セクタにするものがある。 シリンダ 1 から始まるパーティションの開始点はシリンダ境界にならないが、 これは問題になることはあまりないだろう。 ただし OS/2 を同じマシンで使っていなければ、であるが。
パーティションテーブルが更新されると、終了する前に sync() と BLKRRPART ioctl() (ディスクからパーティションテーブルを読み込みなおす) が 実行される。とても昔には、fdisk を利用した後にはリブートが 必須だったこともあった。 多分これは現在では直っていると思う - むしろ、あまりに急いで リブートすると、まだ書き込まれていないデータを失うかもしれない。 カーネルとディスクハードウェアの両方にバッファーデータが存在することに 注意すること。
DOS 6.x 向けの警告
DOS 6.x の FORMAT コマンドはパーティションのデータエリアの 第一セクタからある種の情報を検索し、 これをパーティションテーブルにある情報より信頼できるものとして扱う。 DOS の FORMAT は、容量が変更されたときには最初の 512 バイト分の データ領域が DOS 版 FDISK によってクリアされていることを仮定している。 DOS の FORMAT はこの拡張情報を /U フラグを指定した場合でも見ようとする - これは DOS FORMAT と DOS FDISK のバグであると我々は考える。
結局のところ、cfdisk や fdisk を用いて DOS パーティションの容量を 変更したときは、DOS FORMAT を使ってパーティションをフォーマットする前に dd を使って先頭の 512 バイトを 0 で埋めなければならない、というわけである。 例えば cfdisk を用いて /dev/hda1 の DOS パーティションの テーブルエントリを作成した場合には、(fdisk または cfdisk を終了し、 Linux をリブートしてパーティションテーブルの情報を有効にしたあとで) 先頭の 512 バイトをゼロにするために "dd if=/dev/zero of=/dev/hda1 bs=512 count=1" などと実行する必要がある。
dd コマンドを使う場合には特に注意すること。ちょっとしたタイプミスで、 ディスク上のすべてのデータがパーになる可能性もある。
できるだけ問題を起こしたくなければ、常に OS 固有のパーティション テーブル用プログラムを用いることである。 例えば DOS パーティションは DOS FDISK プログラムで作り、 Linux のパーティションは Linux の fdisk または cfdisk で作るべきなのである。
オプション
- -b sectorsize
- ディスクのセクタサイズを指定する。 指定できる値は 512, 1024, 2048 のいずれかである。 (最近のカーネルはセクタサイズをうまく扱える。 このオプションを用いるのは、カーネルが古い場合や、 カーネルの考えを上書きする場合だけにすること。)
- -C cyls
- ディスクのシリンダ数を指定する。 なぜこれを指定したいと思うのかは分からない。
- -H heads
- ディスクのヘッダ数を指定する (もちろん物理的なヘッダ数ではなく、 パーティションテーブルに使われるヘッダ数である)。 適切な値は 255 または 16 である。
- -S sects
- ディスクの 1 トラック当りのセクタ数を指定する (もちろん物理的なセクタ数ではなく、 パーティションテーブルに使われるセクタ数である)。 適切な値は 63 である。
- -l
- 指定したデバイスのパーティションテーブルをリストして終了する。 デバイスを何も指定しないと、 /proc/partitions があれば、そこにあるデバイスを対象にする。
- -u
- パーティションテーブルをリストするときに、サイズをシリンダ単位ではなく セクタ単位で表示する。
- -s partition
- パーティションのサイズを (ブロック単位で) 標準出力に表示する。
- -v
- fdisk プログラムのバージョン番号を表示して終了する。
バグ
この種の *fdisk プログラムには、同じ機能を持ったものが複数存在する。 それぞれ長所短所がある。 cfdisk, fdisk, sfdisk の順に試してみると良いだろう。 (実際のところ、 cfdisk は美しいプログラムであり、受付けるパーティションテーブルに 厳しい条件を課し、品質の高いパーティションテーブルを生成する。 可能な場合はこれを用いること。 fdisk はバグっぽいプログラムで、やることもややあやふやである - 通常は真っ当な結果を出力するけれど。一つ利点があるとすると、 fdisk は BSD のディスクラベルや、その他の非 DOS パーティションテーブルを 多少サポートしている点である。 sfdisk はハッカー専用である。ユーザーインターフェースはひどいが、 fdisk よりも正しく、また fdisk, cfdisk のどちらよりもパワフルだ。 それに、インタラクティブでない使い方もできる)最近は parted というツールもある。 cfdisk のインタフェースは優れているが、parted はより優れている。 parted はパーティションのサイズを変更するだけではなく、 パーティションにあるファイルシステムのサイズも変更する。
IRIX/SGI 形式のディスクラベルは、現時点ではカーネルでサポートされていない。 また IRIX/SGI ヘッダディレクトリはまだ完全にはサポートできていない。
「パーティションテーブルをファイルにダンプする」 オプションは存在しない。