ファイルシステム

目次

ファイルシステムとは

簡単に言うと ディスク のことですが、Linux では単にディスクだけではなく、ソケット、デバイスなどもファイルシステムにマッピングして利用しています。

用語

フォルダとディレクトリ

Windows では「フォルダ」、Linux では「ディレクトリ」と呼びますが、ほぼ同義です。細かなことを除けば、「フォルダ=ディレクトリ」と考えて差し支えありません。

ファイルとディレクトリ

「ファイル」という用語は狭義には「ディレクトリ」以外のファイルを意味します。広義には「ディレクトリ」も含めて「ファイル」と表現することがあります。

パス名

Windows であれば C:\Windows\System32 など、Linux では /usr/local/bin など、ディレクトリ名やファイル名を階層的に表現したものを パス名 と呼びます。Windows ではバックスラッシュ(\)を区切り文字に使用しますが、Linuxではスラッシュ(/)を区切り文字とします。

ドライブ名

Windows では C:D: などのドライブ名を使用しますが、Linux にはドライブの概念はありません。ディスクを増設した時も /dev/sdb1 などのパス名にマッピングして参照されます。

ルートディレクトリ

一番最上位のディレクトリを ルートディレクトリ と呼びます。ルートディレクトリは / で表します。

$ cd /         # ルートディレクトリに移動する

カレントディレクトリ

現在自分が居るディレクトリを カレントディレクトリ と呼びます。カレントディレクトリは . で表します。

$ ls -l .      # カレントディレクトリのファイル一覧を表示する(省略時も同じ動作)

カレントディレクトリの実行ファイルを指定する際、単にファイル名を指定するのではなく、./ をつけることがあります。これは、環境変数 PATH に依存せず、確実にカレントディレクトリのコマンドを実行する際に有効です。例えば環境変数 PATH に . が含まれていない場合、コマンド名だけを指定してもコマンドが実行できなかったり、PATH の最初の方に設定されたパスの中の同名コマンドが実行されてしまうのを防ぎます。

$ ./test       # カレントディレクトリの test コマンドを実行する
$ test         # ./test を実行したつもりが /usr/bin/test を実行してしまう

親ディレクトリ

現在自分が居るディレクトリのひとつ上の階層のディレクトリを 親ディレクトリ と呼びます。親ディレクトリは .. で表します。

$ cd ..        # ひとつ親のディレクトリに移動する

絶対パス

ルートディレクトリ(/)から始まるパス名を 絶対パス と呼びます。

$ cd /usr/local/bin

相対パス

ルートディレクトリ(/)以外の文字から始まるパス名を 相対パス と呼びます。相対パスはカレントディレクトリを起点としたパス名となります。

$ cd tmp      # カレントディレクトリ配下の tmp ディレクトリに移動
$ cd ..       # ひとつ上のディレクトリに移動
$ cd ../tmp   # ひとつ上のディレクトリの中の tmp ディレクトリに移動

ファイルの種類

Linux では下記の種類のファイルがあります。

通常ファイル
テキストファイルや実行ファイルなどのファイルです。ls -l コマンドでは先頭文字が - となります。
ディレクトリ
ディレクトリ(Windows 用語だとフォルダ)です。ls -l コマンドでは先頭文字が d となります。
シンボリックリンクファイル
ln -s コマンドで作成するシンボリックリンクです。Windows のショートカットファイルに相当します。ls -l コマンドでは先頭文字が l となります。
ソケットファイル
プロセス間通信の一種であるUNIXドメインソケットで利用されるファイルです。ls -l コマンドでは先頭文字が s となります。
FIFOパイプファイル
プロセス間通信の一種であるFIFOパイプで利用されるファイルです。ls -l コマンドでは先頭文字が p となります。
ブロックデバイスファイル
ディスクを示す /dev/sda などブロック単位で読み書きする特殊デバイスファイルです。ls -l コマンドでは先頭文字が b となります。
キャラクタデバイスファイル
コンソールを示す /dev/console などキャラクタ単位で読み書きする特殊デバイスファイルです。ls -l コマンドでは先頭文字が c となります。

ファイルシステム階層構造(FHS)

Linux のファイルシステムの階層構造は FHS(Filesystem Hierarchy Standard) という仕様に従っています。主なディレクトリの利用用途を下記に示します。

/bin   シングルユーザモードでも必要となる重要な実行ファイル(BINary)
/boot  ブートローダー関連ファイル(BOOT loader)
/dev   デバイス(DEVice)
/etc   各種設定ファイル(ETCetera)
/home  ユーザーのホームディレクトリ(HOME)
/lib   ライブラリ(LIBrary)
/mnt   マウントポイント(MouNT)
/opt   オプションツール(OPTion)
/proc  プロセス情報(PROCess)
/root  rootユーザーのホームディレクトリ(ROOT)
/run   実行中プロセスに関する情報(RUNning)
/sbin  システム管理系の実行ファイル(System BINary)
/srv   システム提供ファイル(SeRVed)
/sys   システムファイル(SYStem)
/tmp   テンポラリファイル(TeMPorary)
/usr   マルチユーザモードで必要となるファイル群(USeR)
/var   ログなどの可変ファイル(VARiable)

パーミッション

読込・書込・実行権

ディレクトリやファイルは パーミッション と呼ばれるアクセス権情報を持っています。基本的なパーミッションは 9 ビットで構成され、最初の3ビットがファイルの所有者(user)、次の3ビットがファイルのグループ(group)、次の3ビットがその他ユーザ(other)に対するアクセス権を保持します。それぞれの3ビットは、最初が読み取り権(Read)、次が書き込み権(Write)、次が実行権(eXecute)を意味します。実行権はディレクトリの場合はそのディレクトリに移動できることを意味します。

usergroupother
rwxrwxrwx
421421421

パーミッションの変更は chmod コマンドで行います。

chmod u+w file          # userの書き込み権を追加する
chmod u-w file          # userの書き込み権を削除する
chmod g+r file          # groupの読み取り権を追加する
chmod g-r file          # groupの読み取り権を削除する
chmod o+x file          # otherの実行権を追加する
chmod o-x file          # otherの実行権を削除する

また、rwx の3ビットを8進数(0~7)で指定することもできます。6 は read(4)+write(2)、7 は read(4)+write(2)+execute(1) を意味します。

chmod 644 file          自分は読み書き、他は読み込みのみ可能。(rw-r--r--)
chmod 755 file          自分は読み書き実行、他は読込と実行可能。(rwxr-xr-x)

拡張パーミッション

拡張パーミッションを加えると、パーミッションは下記の12ビットとなります。setuid, setgid, sticky ビットの3ビットが加わります。

extendedownergroupother
susgstrwxrwxrwx
421421421421

setuid ビット

実行ファイルに付与します。このフラグが立った実行ファイルを実行すると、プロセスの実行権限がプロセスを起動したユーザーではなく、実行ファイルの所有者となります。ディレクトリに指定しても効果はありません。

setuid ビットを有効にするには chmodu+s を指定します。

chmod u+s file

または8進数で 4755 などを指定します。

chmod 4755 file

setuid ビットが立っているファイルは、ユーザーの実行権が x から s に変わります。

$ ls -l
-rwsr-xr-x 1 yamada yamada execute_command

例えば、/usr/bin/passwd コマンドは /etc/passwd ファイルを書き換える必要があるため、一般ユーザーが実行しても root 権限で実行できるように setuid ビットが立てられています。

# ls -l /usr/bin/passwd
-rwsr-xr-x 1 root root 91416 Nov  4  2024 /usr/bin/passwd

setgid ビット

実行ファイルに指定した場合、このフラグが立った実行ファイルを実行すると、プロセスの実行グループがプロセスを起動したユーザーのグループではなく、実行ファイルのグループとなります。

setuid ビットを有効にするには chmodg+s を指定します。

chmod g+s file

または8進数で 2755 などを指定します。

chmod 2755 file

setgid ビットが立っているファイルは、ユーザーの実行権が x から s に変わります。

$ ls -l
-rwxr-sr-x 1 yamada yamada execute_command

実行ファイルに setgid ビットを立てるケースはあまり多くありませんが、setgid はディレクトリに対して設定すると効果を発揮します。setgid が設定されたディレクトリ配下にファイルを作成した場合、そのファイルのグループはディレクトリの所有者になります。これにより、グループで作業を行う際にグループでファイルを共有することが楽になります。

# groupadd groupA               # gruopAを作成
# mkdir /home/groupA            # /home/groupA を作成
# chgrp groupA /home/groupA     # グループを変更
# chmod g+s /home/groupA        # setgidビットを立てる
# touch /home/groupA/file1.txt  # ファイルを作成する
# ls -l /home/groupA            # 作成されたファイルのグループを確認する
-rw-r--r-- 1 root groupA 0 Jul 12 15:42 file1.txt

sticky ビット

sticky は「粘着性のある」を意味します。sticky ビットは元々実行ファイルに指定して、高速化のためにその実行ファイルのバイナリ情報をメモリに保持するのに使用されていました。しかし、現在ではメモリキャッシュの技術が進化したため、この目的では使用されていません。現在では、ディレクトリに指定して、そのディレクトリ配下のファイルのファイルの削除や名前変更を、ファイルの所有者のみに制限する目的で使用されています。

sticky bit を立てるには chmodo+t を指定します。

chmod o+t file

または8進数で 1755 などを指定します。

chmod 1755 file

sticky ビットが立っているファイルは、他者の実行権が x から t に変わります。

$ ls -ld /tmp
drwxrwxrwt 1 root root 4096 Jul 12 15:55 /tmp

使用例を下記に示します。/tmp は誰でも書き込みできるはずですが、sticky ビットが立っているため、yamada ユーザーが作成したファイルを suzuki ユーザーが削除や名前変更しようとするとエラーとなります。

# su - yamada                             # ユーザーyamadaになる
yamada$ touch /tmp/file1.txt              # /tmp/file1.txt を作成する
yamada$ exit                              # yamadaを抜ける
# su - suzuki                             # ユーザーsuzukiになる
suzuki$ rm -f /tmp/file1.txt              # /tmp/file1.txt を削除しようとする
rm: cannot remove '/tmp/file1.txt': Operation not permitted
suzuki$ mv /tmp/file1.txt /tmp/file2.txt  # 名前変更しようとする
mv: cannot move '/tmp/file1.txt' to '/tmp/file2.txt': Operation not permitted