Linuxの主なコマンド

複数のコマンドを結びつけるパイプはGUIワープロと良く似ている

UNIXのコマンドで多用される仕組みとして、パイプがある。これは、「あるコマンドの出力を、別のコマンドの入力として、出力した内容をさらに加工する」ということができる。
僕は、これがGUIワープロと良く似ていると思う。GUIワープロでは、ひとつのドキュメントをさまざまな機能で加工し、目的の出力を得るが、これはパイプでストリームデータを加工し続け、磨きをかけていくのと同じだからである。
そう、僕はUNIXGUIは共存できると思う。特にUNIXはプレーンテキストデータを好むが、viなどでUNIXコマンドを使うこともできる。

rootユーザー

UNIXシステムの管理者ユーザー。システムを変え、破壊する権限を持つ。rootになるためには、su -を実行する。

ホームディレクトリ(~/)

ユーザーに与えられた、自由なディレクトリ。

端末とシェル

コマンドを入力し、実行するための、端末とシェルについて。
$や%は一般ユーザーでの操作、#はrootユーザーでの操作。

初期化ファイル

bashは、初期化設定ファイルを読み込みます。
~/.bashrcはユーザーの設定で、シェルの起動時に毎回読み込まれる。
~/.bash_profileはユーザーの設定で、ログイン時のシェル(ログインシェル)で一回だけ読み込まれる。
/etc/profileは、システムの標準設定で、ログインシェルで読み込まれる。
/etc/bashrcは、システムの標準設定で、シェルの起動時に毎回読み込まれる。

コマンド補完

途中まで打ち込んで、タブキーを押すと、コマンド補完が出来ます。

ワイルドカード

シェルでコマンドを実行する際、ファイル名などに*や?などのワイルドカードが使える。
*は任意の文字列(複数文字)、?は任意の文字(1文字)を表す。
たとえば、

ls /etc/*.conf

などとできる。

シェル芸の例

以下はシステムにある100MB以上のファイルやフォルダをソートして一覧表示する。

$ sudo du -x -m -d 5 / | awk '$1 >= 100{print}' | sort -n -r | less

man

マニュアルページを表示する。

man man

主なオプションは-C(manの設定ファイルを指定して実行)、-P(manで使用するページャを指定して実行)。

less/more

ファイルの中身を表示する。lessではスクロールでファイルの全体を観覧出来る。

find / | less

lv

lessと同様にファイルの内容を表示するページャだが、EUC-JP、UTF-8、Shift-JISなどの文字コードに対応している。

ls

ディレクトリの中身のリスト(ファイル一覧)を表示する。

ls -Al

主なオプションは-a(隠しファイルの表示)、-l(詳細表示)、-t(更新時間でソート)、-x(拡張子でソート)、-F(ディレクトリや実行ファイルをマーキング)。

cd

現在のディレクトリを変更(移動)する。

cd ..

主なオプションは-L(シンボリックリンクの場合にリンク先に移動)、-P(シンボリックリンクの場合に移動しない)。

pwd

作業中のディレクトリのパスを表示する。

pwd

mkdir

ディレクトリを新しく作成する。

mkdir -m 0755 test

主なオプションは-p(上位ディレクトリも含めて作成する)。

cp

ファイルやディレクトリをコピーする。

cp -r hoge1 hoge2

主なオプションは-i(移動先に同じファイル・ディレクトリがあった場合に確認する)。

mv

ファイルやディレクトリを移動・名前変更する。

mv hoge1 hoge2

主なオプションは-i(移動先に同じファイル・ディレクトリがあった場合に確認する)。

rm

ファイルやディレクトリを削除する。

rm hoge

主なオプションは-i(削除の確認を表示)。

cat

ファイルの中身を表示する。ファイルの全体をコマンドラインに出力する。

cat a.txt b.txt > c.txt

ln

ファイルのリンク(ハードリンク・シンボリックリンク)を作る。

ln -s /usr/local/bin bin

shred

ファイルを復元不可能にする。
主なオプションは-v(作業状況を表示)、-z(作業後にnullデータで上書きし、痕跡を残さない)。

chmod/chown

ファイルのパーミッション・オーナーを変更する。

ps

実行中のプロセス一覧を表示する。

$ ps
 PID TTY          TIME CMD
 404 pts/1    00:00:00 bash
 460 pts/1    00:00:00 ps

主なオプションはa(全てのプロセスを表示)、r(実行中のプロセスを表示)、-u ユーザ名(ユーザ名やユーザIDで抽出したプロセスを表示)、T(プロセスの状態を含めて表示)。
また、状態はSがスリープ、Dがスリープ(割り込み可能)、Rが実行可能、Tがトレース・停止中、Zがゾンビ。

kill/killall

プロセスを強制終了する。Ctrl+Cも使います。

$ cp /home/hoge/test1 /home/hoge/test2 &
$ ps
 PID TTY          TIME CMD
 404 pts/1    00:00:00 bash
 460 pts/1    00:00:00 ps
 480 pts/1    00:00:00 cp
$ kill 480

killのオプションは-s シグナル名(送信するシグナルを指定)、-l(シグナル一覧を表示)。

find

ファイルを検索して一覧表示する。

find /

grep

特定の文字列を含む行を抽出する。

find . | grep keyword

tar

アーカイブファイルを作成・展開する。

tar -zcvf xxxx.tar.gz directory
tar -zxvf xxxx.tar.gz

xは展開、cは作成、tは表示、rは追加。

date/cal

dateは日付を表示・設定する。calはカレンダーを表示する。

adduser

ユーザを追加する。
主なオプションは--conf ファイル名(設定ファイルを指定してユーザを作成)--shell シェル名(使用するログインシェルを指定してユーザを作成)。

passwd

パスワードを変更する。
主なオプションは-l(アカウントを停止)-u(アカウントの停止を解除)、-S(アカウントの状態を表示)。

halt/shutdown

システムを停止させるコマンド。
haltのオプションは-w(再起動・停止をせずにwtmpに記録を行う)、-d(wtmpに記録を行わない)、-f(強制的に再起動や停止を行う)。
shutdownのオプションは-h(システムを終了する)、-r(システムを再起動する)、-F(再起動時にfsckを行う)、hh : mm(指定した時間にシャットダウンを行う)、+数字(指定した分後にシャットダウンを行う)、now(コマンド入力直後にシステムを終了する)。

ユーザープログラム

cat, echo

catは、ファイルやストリームを表示する。
echoは、文字列や変数の値を表示する。

tr, cut, paste

trは、テキストファイル内の特定の文字を置換する。trコマンドは、複数の置換をまとめて記述できるのが特徴で、たとえばa-zをA-Zにすることができる(全ての小文字が大文字に置換される)。これに対して、sedのようなストリームエディタでは、正規表現を用いたパターンマッチングの置換ができる。
cutは、各行から指定した範囲を切り出すコマンド。テキストファイル内で特定の列を取り出す。空白によって分けられた文章を分割したりすることもできる。
pasteは、複数ファイルの行をマージする。テキストファイルを列方向に結合する。

sort

テキストをソート(並べ替え)してくれる。
sortはパイプで使われることが多く、またviなどで使うととても強力である。headコマンドで先頭の行だけを取り出すこともできる。

uniq

重複した行をひとつにまとめてくれる。
sortやwcと同様に、パイプで使うことが多い。

join

2つの入力ファイルから共通するフィールド(項目)を結合する。
たとえば、

$ cat test1.txt
1 Zaw
2 Shcwarz
$ cat test2.txt
1 150
2 250
$ join test1.txt test2.txt
1 Zaw 150
2 Schwarz 250

となる。SQLにおけるJOINと同様のものであると考えればいいかも。

wc

文字数や行数を数えてくれる。特に行数を数えてスクリプト処理を通して出力したりするのに使える。

head, tail

headはテキストファイルの先頭部分、tailはテキストファイルの末尾の部分を表示する。パイプを使って、ストリームの最初の方や最後の方だけを表示する時に使うことが多い(たとえば、ソートして上から10行表示する)。

splitとcsplit

splitはバイト単位・行単位で、csplitは任意の文字列でファイルを分割することの出来るコマンド。

diffとpatch

ファイルを内容の詳細まで比較したり、その変更(パッチ)を適用できるコマンド。

rev

各行の文字を逆に並べ替える。そのままtacに送ればファイルの行末から表示できる。

$ cat hoge.txt | rev | tac

less

コマンドが大量の出力を吐く場合など、ストリームをスクロールして表示させたい時は、パイプでless(ページャ)に送るのが有用だ。

$ find /usr/src/linux | less

vi/nano

viは無駄に使える。もっと簡単なテキストエディタが欲しい時は、nanoを使うと良い。
viでは、:!commandでUNIXコマンドを実行できる。:1,10!sortなどとすれば、1~10行目をソートすることもできる。
viでは、先に書いたようにsortコマンドをコードブロックの中で実行できるが、このように、viでUNIXコマンドを実行することで、UNIXコマンドははじめて真価を発揮する。

lpr/lp

lprはBSD系、lpはSystemV系の印刷コマンド。CUPSを設定した上で、どちらかのコマンドを使って印刷が行える。

source-highlight

シンタックスハイライトをしてくれるツール。

ctags

ctagsは、vimなどと一緒に使うことで、C言語の関数定義情報が入ったtagsファイルを作成し、tagsに基づいて関数定義がどこのファイルに入っているかを検出し、指定の関数定義を探し出すことができる。

make

コンパイルやインストールを一括で実行する。

scriptとtee

scriptコマンドは、scriptを実行してからexitを実行するまでの端末の操作(全てのキータイプと出力)を記録する。
ファイル名を指定した場合はそのファイルに、指定しなかった場合はデフォルトではtypescriptというファイルに記録される。
teeコマンドは、パイプでコマンド出力の「写しを取る」。
DNF/Yum/Aptなどで、「どんなパッケージを(依存関係などを含めて)インストールしたかメモしたい」などといった状況で使える。

watch

コマンドを繰り返し実行して結果を再描画する。
以下のようにすると効果を発揮する。

$ wget --background https://www.kernel.org/pub/linux/kernel/v3.x/linux-3.9.tar.xz
$ watch -n 1 ls -l linux*.xz
(ダウンロードしているファイルの増加具合を1秒ごとに表示する。)

pv

パイプを使った処理の進歩状況を表示する。
特に、以下のようにすると効果を発揮する。

$ pv linux-3.9.tar.bz2 | tar xfj -
(進歩状況がプログレスバーで表示される)

tar

tarは複数のファイルを圧縮して1つのファイルにアーカイブすることができる。

rsync

ディレクトリ間のファイルの同期を行う。

git

gitは使える。
最近、僕もgitを使うようになりました。ローカルだけで使うのであっても、差分を見事に管理してくれます。また、GitHubを使うことで、別の場所で変更・編集したファイルを同期することも簡単です。僕はホームページのファイルの同期に使っています。詳細はGitの世界観にあります。

shred

ファイルを復元できないように削除する。重要な情報が書かれたファイルを削除するために使う。作業状況を表示するためには-vオプション。

$ shred -v daiji.txt

-zオプションを使うと、shred処理を隠すため、最後にゼロクリアする(nullデータで上書きする)。

file

fileコマンドを使うと、ファイルのファイル形式を確認できる。

$ file test.txt
test.txt: ASCII text

システム

su -

rootユーザーになってシェルを実行する。

$ su -
Password: (root のパスワードを入力)
# (rootのシェルになった)

終了する時はexitを実行する。

# exit
$ (ユーザーに戻る)

sudo

そのコマンドだけをroot権限で実行出来る。僕はあまり好きではないが、使いやすさを考えてUbuntuでは標準である。

chroot

ルートディレクトリを変更してシェルを実行する。
特に、ディストリビューションの手動によるインストールなどの際、マウントしたディレクトリに入る時などに使われる。
Gentoo Linuxではハンドブックによるインストールの時の必須ツールである。

df

ディスクの使用容量を確認する。

du

ファイルやディレクトリの使用容量を確認する。

lftp

FTPクライアント。コマンドでFTP操作が可能。

wget

コマンドからURLを直接渡してファイルをダウンロードするためには、wgetを使うのが良い。

links/lynx/w3m

CUI環境でインターネットのWebページを見たい時には、linksやlynxw3mのようなテキストブラウザが使える。
特に、Gentoo Linuxのインストール時などにハンドブックを確認するのに有用だ。だが、英語でしか文字が表示出来ないCUI環境もあるので注意が必要だ。

curl

コマンドからHTTPリクエストができる。

lspci

PCIバイス情報を確認するコマンド。

lsusb

USBデバイスを表示する。

lsscsi

SCSIバイスを表示する。

lscpu

CPU情報を表示する。

lsblk

ブロックデバイス一覧を表示する。

/proc/cpuinfo, /proc/meminfo

cat /proc/cpuinfoでCPUの情報、cat /proc/meminfoでメモリの情報を確認できる。

プロセス

ps

プロセス状況を表示する。

pstree

プロセスの親子関係を分かりやすくツリー表示してくれる。

pgrep/pkill

プロセスIDを表示し、プロセスにシグナルを送信する。

pidof

実行しているコマンドのプロセスIDを表示する。

kill

プロセスを終了する。

killall

killallを使うと、プロセスを殺す時に、killのようなプロセスIDではなく、プロセスの名前で指定できる。同じ名前のプロセスは全部死ぬ。
killを使うよりも使いやすいが、別のプロセスまで一緒に殺さないように注意しよう。

free/vmstat/dstat

freeは、空きメモリや利用中メモリを表示する。vmstatは、仮想メモリの統計情報を表示する。
vmstatはサーバーのリソースをリアルタイムでモニタリングするのに使える。だが、vmstatはメモリやブロックの状況、iostatはI/Oの状況を見ることができるが、他の状況は見ることができない。mpstat、ifstatも同様。1つのターミナルでたくさんのさまざまな状況を見たいときは、dstatを使う。

ドキュメント

man

manは、マニュアルドキュメントを表示する。以下はlsコマンドのマニュアルを表示する例。

$ man ls

英語のmanページを表示したい時は、以下のようにする。

$ LANG=en_US man ls

コマンドの概要や詳細なコマンドラインオプションなどが表示される。また、manのマニュアルは設定ファイルやシステムコール・ライブラリ関数などのドキュメントも表示することができる。これが分かっていないと、Linuxをそもそも使うことができない。だが、manのマニュアルは詳しい反面、とても理解するのが難しい。

とりあえずmanコマンド

Linuxのコマンドで困った時は、まずmanコマンド。とりあえずmanコマンドをすることで、何でもすぐに分かる。
catコマンドについて知りたい時は、端末にman catと入力してエンター。そうすると、troffで書かれたcatについてのmanページがすぐに出てくる。ここに詳細なcatの使い方が全部書いてある。端末で読むのが見づらいのであれば、Mozilla FirefoxなどでブラウザからJMプロジェクトなどの検索欄にcatと叩けば良い。
GNUのツールであれば、infoコマンドの方が文書が整備されていることもある。info catと入力してエンター。文書内のリンクなどが整備されており、特定の機能だけにアクセスしやすくなっている。

apropos

manの不便な点は、コマンド名が分からないと検索できないこと。aproposコマンドを使えば、概要欄を検索して関連するコマンドを調査できる。

groff (troff)

groffはUNIXの文書整形コマンドroffのGNUによる実装で、manページの整形に使われている。

info/Texinfo

GNU系のアプリでは「info」コマンドでinfoページを表示することもできる。リンクなどがそろっていて利用しやすい。
infoでは、manとは違い章ごとにページが分かれており、リンクを辿ってテキストブラウザのように各ページを表示できる。ただ、「manと何が違うのか良く分からない」というユーザも多く、良く嫌われている。
TexinfoはGNU infoで使われているドキュメント形式。

情報の探し方

Linuxに関する情報を探す際に、良く言われることは既知の情報があるかどうかを探すことです。たとえば、以下のような方法があります。
・コマンドに類することであれば、manコマンド・infoコマンドの実行。
・ソフトウェア個別のことであれば、tarballの中にあるREADME(インストール方法であればINSTALL)や、システムのdocディレクトリ(/usr/share/doc/や/usr/docや/usr/share/[アプリケーション名]などのディレクトリ)を参照する。
・TLDPやJFなどでLinux関連のマニュアルを読む。
Webブラウザを起動し、アプリケーションを開発しているプロジェクトのサイトに行って、公式のドキュメントやリファレンスを探す。特にチュートリアルAPIリファレンスなど。
ディストリビューション付属のマニュアルを読む。
GNOMEKDEのヘルプなどのヘルプ機能から使い方を探す。
Googleで検索する。ブログや個人サイトを検索できるほか、エラーメッセージや設定ファイル名などを検索するとピンポイントでダイレクトに分かる場合が多い。
・フォーラムやメーリングリストIRCで教えてもらう。過去のアーカイブなどから同じ質問がないか調べてみる。

grep, find, sed, awk

grep

テキストの中でマッチする行だけを取り出す。grep, sed, awkとして検索・置換の三人衆と知られている。

grepの例

grepはパイプを使ってストリームの中のパターンにマッチする行を抽出するために使うことができます。データベースで言えばフィルターのようなものです。

find /usr/src/linux | grep fs

こんなこともできる。

grep -rn "Linus" /usr/src/linux

あるいは、

find /usr/src/linux -name "*.c" | xargs grep -l "Linus"

-rオプションはディレクトリ内の再帰的な検索、-nは行番号を表示、-lはファイル名のみを表示。
ちなみに、正規表現を使用しない場合はfgrepで高速検索ができる。

findとlocate

findはファイルを検索する際、色んなオプションが使える。locateはオプションは貧弱だが、事前に作られたデータベースから検索するために、検索速度が速い。
データベースはcronで自動で作られるが、手動で作る場合はrootユーザーになってupdatedbを実行する。

更新日が最近の10日以内のファイルを探す

findの便利な使い方。更新日が最近の10日以内のファイルを見つける。場所はカレントディレクトリ「.」以下から。詳細に(-ls)

$ find . -mtime -10 -ls

xargs

xargsを上手く使うことで、一覧されたテキストから全てに対するコマンドを実行できる。findとともに使うことで、手作業でうんざりする作業をしなくても済む。
xargsコマンドを上手く使うことで、findやgrepなどの結果から、「全ての行に対するコマンド」を実行出来る。

全てのファイルの内容を正規表現で置換

xargsは、たとえば、findで一覧した全てのファイルに対して、sedのようなコマンドで正規表現をかけ、保存したい場合などに使える。
xargsで全てのファイルを正規表現で置換する。

find ./ -name *.html | xargs sed -i 's/検索文字列/置換文字列/g'

同様のことをWindowsで行うためには、フリーソフトサクラエディタGrepGrep検索機能を使う。あるいはxyzzyなどでも同じ機能がある。

xargs & parallel

GNU parallelはコマンドを並列実行するツール。簡単な並列実行ならxargsに-Pオプションでもいける。

sed

正規表現で検索や置換を行ったり、パターンにマッチする行だけを抜き出したい・削除したいなど、ストリームの編集を行いたい時は、sedを使う。
コマンド行に変換してbashに送る、などといった荒業も可能だ。

viとsed

viは入力されたデータをそのまま出力するためビジュアルエディタと呼ばれる。sedは入力されたデータを行単位で処理するためストリームエディタと呼ばれる。

sedと一緒にviも使おう

sedはコマンドで使うと強力だが、テキストを編集する際にはviを使おう。とても便利で簡単にテキスト処理ができる。sedとviを制するものはLinuxを制す。

awk

awkは昔からあるUNIXスクリプト言語で、空白やタブで区切られたテキストに対してスクリプト処理をかけることができる。
特に、特定のカラムを表示させたい時は、awkを使うと便利です。

diff, patch, テキスト処理

split, csplit

splitはバイト単位・行単位で、csplitは任意の文字列でファイルを分割することの出来るコマンド。
csplitを使うことで、こんな風に出来る。

$ cat sample.doc
第1章

...

第2章

...

第3章

...

第4章

...

第5章

...

$ csplit sample.doc /^第[1-9]章/ {*}

上を実行すると、「xx00」から「xx05」というファイルが作成される。

sort

テキストを並び替えられる便利なコマンド。シェルから実行できるほか、viなどで:1,10!sortとすれば、1~10行目をソートできる。

diff

diffは:

diff -u test_before.txt test_after.txt > test.patch

ディレクトリを再帰的に比較する場合は-rオプション。
-uはunified diff形式でパッチを出力する。-cの場合、context diff形式での出力になる。基本的に-uを使おう。
diffは使えます。僕はWindowsでもcygwinをインストールしてdiffを使っています。
Windowsで使う場合は、オプション--strip-trailing-crをつけて改行コードCRを削除しましょう。

$ diff -ru --strip-trailing-cr dir1/ dir2/

ちなみに、Windowsで使えるサクラエディタにもDiffの機能があります。

patch

patchは:

patch -u < test.patch

-uはunified diff形式のパッチを適用する。-cの場合、context diff形式での適用になる。
patchの書式:

$ patch [-u(または -c)] -p数 -d 適用するディレクトリ名 < パッチファイル名

「-p数」はパッチファイルで見つかったファイルパスから数で指定された分のパス(プレフィックス)を取り除く。
例えば、「test_before/dirA/test_A.txt」で「-p1」と指定した場合は、「dirA/test_A.txt」というパスでパッチが適用される。
「-d」はパッチを適用するディレクトリ名を指定するオプション。

comm/cmp

diffのほかにも、comm(行単位で比較)やcmp(1バイトごとに比較)などのツールがある。

md5sum/sha1sum

MD5/SHA1メッセージダイジェスト(そのファイルが変更されていないことを示すためのファイル内容の整合性を確認するハッシュ値)を表示する。
MD5/SHA1ハッシュはLinuxディストリビューションのISOファイルのダウンロードの際などに使われており、ファイルが壊れていないか(あるいは改竄されていないか)のチェックに使うことができる。
ファイル内容が完全に同じであれば、同じハッシュ値となる。もし少しでも壊れていれば、ハッシュ値は同じにならない。

uuencode/uudecode

バイナリファイルをテキストファイルに変換・復元する。

base64

入力をBase64エンコード・デコードする。
Base64は、文字の種類が64文字の印刷可能な英数文字しか使えない通信環境で、マルチバイト文字やバイナリデータなどを扱うための技術。7ビットのデータしか使えない電子メールで広く使われている。

アーカイブ、同期、デバイス

圧縮アルゴリズム

ZIPのdeflate圧縮やLHAのlhXシリーズ圧縮は、ハフマン法と辞書式という二つのアルゴリズムで構成されている。
辞書式は、同じフレーズがでてきたら「何文字前から何文字」に書きかえる。
ハフマン法は、多く出現する記号は短い符号で、少なく出現する記号は長い符号で、と符号化する。

deflate圧縮

deflate圧縮は、zipやgzipなどで使われている可逆データ圧縮アルゴリズム
可逆圧縮で、インターネットで広く使われている。圧縮は比較的高速で、伸長は非常に高速。
日本人により考案されたLHAは、ほぼ同じアルゴリズムを使う。

tar

tarを使うことで、ファイルをまとめて圧縮し、圧縮ファイルを作ることが出来る。また、圧縮ファイルから元のファイルを展開(解凍)することもできる。
tarは複数のファイルをひとつのファイルにアーカイブするプログラム。gzipやbzip2を使用しており、それらのアルゴリズムに基づいてアーカイブを圧縮・解凍できる。
圧縮する場合:

$ tar cvfz archive20180721.tar.gz dir/

解凍する場合:

$ tar xvfz archive20180721.tar.gz

rsync

ディレクトリ間のファイルの同期を行う。
rsyncを使うことで、データをディレクトリ間で同期することが出来ます。
rsyncを使うと、ディレクトリの中で変更があったファイルだけを探し出し、新しいファイルだけをコピーできる。オプションでアーカイブモードを選択することで、サブディレクトリを再帰的に実行したり、ファイルの属性(パーミッション、タイムスタンプ、シンボリックリンク)をそのまま保持することができる。

$ rsync -av 同期元/ 同期先/

-vは動作内容を表示するオプション。-aはアーカイブモード(「-rlptgoD -no-H -no-A -no-X」相当)で、サブディレクトリが存在した場合は、「そのディレクトリも処理する(再帰処理)」「パーミッションやファイルのタイムスタンプを保持する」「シンボリックリンクシンボリックリンクのままコピーする」などの動作となる。
rsyncシェルスクリプトにしてcronに指定することで、毎日夜に定期的に同期してくれるように設定することもできる。tarとの併用で、たまに全体のバックアップをとっても良いだろう。

dumpとrestore

イメージ単位でファイルシステム全体をバックアップ・復旧できる。
UNIXのバックアップツールとして最も一般的で最適だが、ファイルシステムの一部だけをバックアップしたり、複数のファイルシステムにまたがるディレクトリツリーをバックアップすることはできない。
そのような場合にはtarやrsync, cpioを用いる。
dumpとrestoreを使うのは、システム全体をバックアップ・復旧したい場合で、他にddコマンドなどがあり、ddコマンドは環境をまるごと複製する際に便利。システム管理者としては覚えておかなければならないコマンドである。
以下はdumpの例:

# dump -0uf /mnt/backupUSB/dump-sda1.dumpbackup /dev/sda1

0~9でバックアップレベルを指定する。0とした場合はフルバックアップとなり、それよりも大きなレベルが指定された場合は、その設定したレベルよりも低い部分から変更された部分のみがバックアップされる。1、2、3としていけば順に増分バックアップされていく。-uは/etc/dumpdatesファイルを記録・更新する。-fはダンプ出力先のファイルまたはデバイスを指定する。
以下はrestoreの例:

# restore -rf /path/dump-sda1.dumpbackup

フルバックアップをレストアしてから、1、2、3と作成したダンプファイルをレストアする。-rは対話せず一括で復元する。-fはバックアップファイルを指定する。

gzip/gunzip

gzipアーカイブに圧縮・展開する。
そもそもUNIXではcompressという圧縮コマンドを使っていたが、それで使われていたLZWは特許侵害の恐れがあり、GNUが安全・安心な代替として開発した。
Lempel-Zivアルゴリズム(LZ77)とハフマン符号を用いて、compressよりも圧縮率が高い。ファイルアーカイバとしての機能はないためtarと組み合わせて使う。

bzip2/bunzip2

bzip2アーカイブに圧縮・展開する。
bzip2ではブロックソート法(バロウズ-ホイラー変換)とMTF (Move-To-Front) 法、ハフマン符号化法を使うことでgzipよりも高い圧縮率を持つが、処理速度の点でgzipよりも劣っている。

cpio

cpio形式に圧縮・展開する。アーカイブへのコピーやアーカイブからのコピーができる。
cpioよりもtarの方が良く知られている。RPMパッケージに採用されていることで有名。RPMパッケージはrpm2cpioコマンドでcpio形式に変換することができる。

unzip/lhasa/unrar

ZIP/LHA/RAR形式のアーカイブを展開する。
たとえば、Windowsで圧縮したzip形式の圧縮ファイルを解凍したりするのに使う。
暗号化されたzipを解凍したい場合は、zipcloakコマンドを使用する。
あるいは、zipの-eオプションやunzipの-Pオプションを使う。

mktemp

一時ファイル・一時ディレクトリを作成する。

df

ディスクの使用容量を確認する。

$ df -h

du

ファイルやディレクトリの使用容量を確認する。

$ du -h

dd

ブロックファイルや変換形式を指定して、ファイルを変換してコピーする。
ddコマンドでは、入力(if=/dev/sdb1など)と出力(of=/dev/sdb2など)を指定する。ここでデバイスを指定できるため、デバイスの内容をそのままコピーできる。
たとえば、CD-ROMからisoイメージを作成するためには以下のようにする。

dd if=/dev/cdrom of=install.iso

ほかにも、「bs=バイト数 count=個数」でバイト数×個数分のサイズのファイルを出力したりできる。また、「conv=block cbs=サイズ」のようにconv=に変換方式を指定することで、ファイルを変換してコピーできる。iflag、oflagにはさまざまなフラグが設定できる。
用途としては、簡単なファイルの複製や、デバイスファイル(HDDやCD-ROM)からファイルへのコピー、ディスクイメージをデバイスに出力する際に利用できる。またKVMXenの仮想イメージ作成にも利用できる。作成したイメージはファイルシステムの作成後に、mount(8)に「-o loop」をつけてマウントできる。
以下はディスクイメージを作成してマウントする例:

dd if=/dev/zero of=/xen/disk01.img bs=1MB count=1024
mkfs.ext4 -j -F /xen/disk01.img
mount -o loop /xen/disk01.img /mnt/xen

バイスをそのままイメージに出力したり、イメージからデバイスに出力したり、といった用途に使うことが多い。

lsattr/chattr

ext2/3/4のファイル属性を表示・変更する。追記専用、変更不可、安全な削除、復旧可能など、さまざまな機能が使える。

zchunk/zsync & jigdo

zchunkは差分圧縮フォーマットで、zsyncは差分同期システム。
ひとつのファイルを複数の「チャンク」に分割し、コピーする時は必要なチャンクだけを差分コピーすれば良い。
Fedora 30でDNFがzchunkに対応した。zsyncはUbuntuなどの毎日更新されるテスト版(日本のミラーサーバーにミラーリングされない)を高率的にダウンロードするために、isoファイルの差分同期を行うために使える。
ちなみに、Debianには昔からjigdoと呼ばれるパッケージのダウンロードシステムがある。パッケージを個別にダウンロードし、最後にCD形式にまとめる。

ファイル名が文字化けした時はconvmv

特に、Windowsからzip圧縮ファイルを持ってきて展開した場合などに、ファイル名が文字化けすることがあります。
この場合、convmvコマンドを使って、ファイル名を変換できます。

Bashのジョブ制御

ジョブ制御

フォアグラウンドで実行
コマンドをフォアグラウンドで実行する時は、単にコマンドを実行します。

バックグラウンドで実行(&)

コマンドの最後に&を付けると、バックグランドで並列的にコマンドを実行出来ます。

$ cp /home/hoge/test1 /home/hoge/test2 &

&をつけたバックグラウンド実行はとても良く使うので覚えておきましょう。特に、GUIアプリケーションをコマンドラインから実行したりする時に良く使います。サーバーデーモンも&と同じ仕組みで動いています。
基本的に、コマンドをマルチタスクで実行したい時は、なんでもコマンド行の最後に&をつければ並列で実行される。特にXのターミナルからGUIアプリケーションを実行する時、&をつけずに実行すると、ターミナルエミュレータのウィンドウを閉じた時にGUIアプリケーションも一緒に終了してしまう。必ず「firefox &」のように最後に&をつけて並列で実行させるようにしよう。

ジョブ制御のコマンド一覧

  • Ctrl+z
    • コマンドの一時停止。
  • Ctrl+c
    • フォアグランドで実行中のプロセスを強制終了する。
  • jobs
    • 一時停止中・バックグラウンドで実行中のコマンドの一覧。
  • bg
    • 一時停止中のコマンドをバックグラウンドに移す。
  • fg
    • 一時停止中・バックグラウンドで実行中のコマンドをフォアグラウンドに持ってくる。
  • ps
    • 実行中のプロセス一覧。
  • kill
    • バックグラウンドで実行中のプロセスを強制終了する。
  • Ctrl+z
    • 一時停止

コマンドを間違ってフォアグラウンドで実行した場合、Ctrl+zで一時停止が出来ます。

jobs: 裏で実行中のコマンド一覧

jobsコマンドを使うことで、一時停止中・バックグラウンドで実行中のコマンドの一覧を見ることが出来ます。

$ jobs
[1]+  Stopped                 cp /home/hoge/test1 /home/hoge/test2

bg: バックグラウンドに移す

一時停止中のコマンドをバックグラウンドで実行するためには、bgコマンドを使います。jobsコマンドで表示される番号で指定します。

$ bg 1
[1]+  cp /home/hoge/test1 /home/hoge/test2

fg: フォアグラウンドに持ってくる

コマンドをフォアグラウンドに持ってくる場合は、fgコマンドを使います。

$ fg 1
cp /home/hoge/test1 /home/hoge/test2

ps: プロセス一覧

psコマンドを使うことで、今実行されているプロセスの一覧を見ることが出来ます。

$ ps
 PID TTY          TIME CMD
 404 pts/1    00:00:00 bash
 460 pts/1    00:00:00 ps

Ctrl+c: 強制終了

フォアグラウンドで実行中のプロセスは、Ctrl+cで強制終了出来ます。

kill: 裏のプロセスの強制終了

バックグラウンドで実行中のプロセスは、killで強制終了出来ます。

$ cp /home/hoge/test1 /home/hoge/test2 &
$ ps
 PID TTY          TIME CMD
 404 pts/1    00:00:00 bash
 460 pts/1    00:00:00 ps
 480 pts/1    00:00:00 cp
$ kill 480

シェルの記法

複数行に渡るコマンド(\)

行末に\を付けることで、コマンドを複数行にわたって記述出来ます。

パイプとリダイレクト(| < > >>)

パイプは、プログラムが出力した内容を別のプログラムに入力として再度渡す機能。上手く使うことで、たくさんの処理をひとつのテキストデータ(ストリーム)に対して複数行うことができる。また、リダイレクトはストリームとファイル入出力を変換する機能。読み込み、書き込み、追記が存在する。
言ってしまえば、オブジェクト指向の「.」と同じような考え方である。UNIXのコマンドは、多くがこのパイプによって使われることを意図して設計されている。

リダイレクト

リダイレクトは、<は読み込み、>は書き込み、>>は追記です。
リダイレクトの例1:

$ echo hello > test_hello.txt
$ echo hello2 >> test_hello.txt
$ cat test_hello.txt
hello
hello2

リダイレクトの例2:

$ patch -u < test.patch

その他にも、既にファイルが存在しても書く場合、エラー出力も取る場合などがあり、またCシェルとBシェルでも違う。以下のようなページを参照のこと。
普通のリダイレクトでは、標準出力しかリダイレクトされず、標準エラー出力は無視される。標準エラー出力もリダイレクトしたい場合は「&> all.txt」などとする。また、標準出力を1>、標準エラー出力を2>と分けて使うこともできる。(Windowsコマンドプロンプトも同様に1>と2>で標準出力と標準エラー出力を区別できる。)

標準エラー出力を除外

標準エラー出力を除外したい場合は、「2> /dev/null」のようにリダイレクトする。このようにした場合、標準エラー出力はどこにも表示されず、保存もされない。

$ ls * | cpio -ov > /tmp/work.cpio 2> /dev/null
$ cpio -it < /tmp/work.cpio

パイプ

パイプを使うことで、あるコマンドの結果を別のコマンドに渡すことができる。

$ find / | grep 2018

標準エラー出力も合わせてパイプに渡したい場合は、「|& more」などとする。

コマンドの同時実行(; && ||)

;を使うことで、複数のコマンドを同時に実行出来ます。また、&&や||を使うことで、コマンドが正常に終了した場合、異常に終了した場合に次のコマンドを実行出来ます。
たとえばこんな感じ:

# ./configure && make && make install
(Linuxコマンドを連続して使うには - Qiitaより引用。)

グロブとワイルドカード(* ? [])

ファイル名展開(グロブ)は以下のようになる。

  • *
    • 0文字以上の任意の文字列にマッチ。
  • ?
    • 1文字の任意の文字列にマッチ。
  • [...]
    • ブラケットで挟まれている文字のうち任意の1文字にマッチ。正規表現におけるブラケットの解釈とほぼ同じです。

ブレース展開 ({})

ブレース展開はまとめてファイルやディレクトリを作成する時などによく使われる。

$ mkdir -p a/b{0,1}/c{0,1}

チルダ展開 (~)

チルダ(~)はホームディレクトリを指す。

cd ~

「cd ~」とすることでホームディレクトリに移動できるほか、ホームディレクトリ内のディレクトリやファイルを「vi ~/.emacs」などと表すことができる。

変数展開 ($)

変数を使うことで、シェルスクリプトなどが綺麗に書けることがある。

$変数名

または

${変数名}

のように使う。

コマンド置換 (``)

コマンド名をそのコマンドを実行した出力で置き換えられる。

$(コマンド)

または

`コマンド`

のように使う。

シェル変数と環境変数

シェル変数とset

シェル変数の一覧を見るためには、setコマンドを使う。

$ set
BASH=/bin/bash
~略~

シェル変数の設定は以下のように行う。

$ HOGE=hoge

環境変数とenv/export

環境変数の一覧を見るためには、envコマンドを使う。

$ env
PWD=/home
~略~

環境変数を設定するためには、一度シェル変数を設定して、exportする。

$ env | grep HOGE
$ HOGE=hoge
$ export HOGE
$ env | grep HOGE
HOGE=hoge

シェル変数は、シェルから起動したプロセスに値が引き継がれない。シェル変数はシェル固有の値を、環境変数は言語などグローバルな値を持たせる。

sourceコマンド

sourceコマンドは、ファイルに書かれたコマンドを現在のシェルで実行する。シェルの設定を反映させるために使う。

初期化スクリプト

~/.bash_profile

ログインシェルとして起動したときに実行される。

~/.bashrc

対話的に起動したときに実行される。

~/.bash_logout

ログアウトのときに実行される。

シェルスクリプトの使い道

簡単な定型処理やバッチ処理、コマンド行のメモに使える

シェルスクリプトは、簡単な定型処理やバッチ処理、そしてコマンド行のメモに使えます。
たとえば、ホームページのデータを更新して、gitコミットし、lftpでサーバーに送信し、rsyncで同期し、tarでアーカイブしてコピーすると言った具合です。
行をたくさん書く必要は必ずしも無く、コマンドのヒストリーをカーソルキーで参照するように、「数行だけ書かれたシェルスクリプト」を作って、それをbashから実行すれば、まるでWindowsでショートカットアイコンをダブルクリックするように、ひとつのアクションでコマンドを実行できます。シェルでは「./hoge.sh」と実行するか、GNOMEなどではダブルクリックで実行できます。
lftpについては専用のスクリプト記法があるのでそれを参照すれば良いでしょう。lftpを参照のこと。他のUNIXコマンドについてはただそのコマンドを一行に書けばそれで実行できます。変数や条件分岐、繰り返しや関数呼び出しなどもできます。特に引数を指定してそれを変数として使えるようにスクリプトを書けば、状況によって別の処理を実行させられます。
また、システムの内部では、bashX11の初期化スクリプトや、デーモンやサービスを適切に実行させるRCスクリプト(SysV initの場合)でシェルスクリプトが使われているほか、automake/autoconfでもソフトウェアのコンパイル・インストールの際にシステムの構成をチェックして移植性を高めるためにシェルスクリプトが多用されています。またGentoo LinuxPortagePythonで書かれていますが、それぞれのパッケージのビルドやインストール情報を記述したebuildファイルはbashで書かれています。
ファイルのバックアップなどは、きちんと端末で入力するとさまざまなコマンドを覚えなければなりませんが、面倒ならシェルスクリプトに一度書いてしまいましょう。何度でも手軽に使えます。シェルスクリプトの利用は強制ではないので、使いたいコマンドだけ好きに使ってください。

シェルスクリプトは上手く使おう

シェルスクリプトは、上手く使いましょう。
たとえば、大事なファイルをUSBハードディスクにrsyncで同期しているとします。この時、対話型シェルでrsyncをかけると、コマンド行を間違えるかもしれません。ファイルが多いと、大変なことになります。
こうした時に、「間違えることのないようにシェルスクリプトに記述して、それを実行する」といったことができます。

コマンドで実行できることはシェルスクリプトに書ける

シェルスクリプトは、シェルのスクリプトです。よって、シェルの中でコマンドで実行できることは、シェルスクリプトに書いて実行できます。「シェルにおけるコマンド実行は、シェルスクリプトに書くのと同じ」であるため、「シェルで自分が行うことは全てスクリプトに書ける」と言えます。
たとえば、メールの送信は、sendmailコマンドをシェルスクリプトに記述することで可能です。
応用すれば、「何かのタイミングでメールを送信する」といったことも可能です。たとえばcronデーモンでスクリプトを定期実行したり、サーバーのCGIからエラーが発生した時にスクリプトを実行して、異常を感知した時にメールを管理者に送信する、といった用途が考えられます。

カーネルモジュール

カーネルモジュールの手動ロード

カーネルモジュールは*.koという拡張子で、/lib/modules/にある。
カレントディレクトリにあるkoファイルのロードは以下のようにする。

# insmod hello.ko

ロードされたドライバはlsmodで確認できる。

# lsmod
(ドライバが表示される)

アンロードはrmmodで行う。

# rmmod hello

modprobeコマンドを使うことで、カレントディレクトリのkoファイルではなく、「/lib/modules/`uname -r`」からドライバを探す。RCスクリプトなどでLinux起動時にドライバをロードしたい時などによく使われる。

カーネルモジュールの設定

カーネルモジュールを作るためには以下のドキュメントを読むことが推奨されている。

カーネルモジュールを手動で読み込むためには、/etc/modules-load.d/*.confに自動的にロードしなければならないモジュールを改行区切りで記載する。
モジュールのオプションは/etc/modprobe.d/*.confに記載する。
基本的にはudevが自動で検知したハードウェアのモジュールをロードするため、手作業で行う必要は必ずしもない。