章節概述#
本章是全書的基礎章節,介紹在 Linux 系統中會用到的 Unix 指令與工具。內容涵蓋 shell 的使用、基本與中階指令、目錄導覽、環境變數、I/O 重導向、程序管理、檔案權限、壓縮封存,以及 Linux 目錄階層結構。即使你已有一定經驗,仍建議瀏覽本章,特別是 Section 2.19 的目錄階層部分。
本章使用 Unix 一詞多於 Linux,因為這些指令在 BSD 等其他 Unix 系統上同樣適用。
2.1 Bourne Shell: /bin/sh#
Shell 是 Unix 系統最重要的組件之一,它是一個執行指令的程式,同時也是一個小型的程式設計環境。
- 許多系統的重要部分其實是 shell scripts — 包含一系列 shell 指令的文字檔
- 所有 Unix shell 都源自 Bourne shell (
/bin/sh),這是 Bell Labs 開發的標準 shell - Linux 使用增強版的 Bourne shell,稱為 bash(Bourne-again shell),是大多數 Linux 發行版的預設 shell
/bin/sh通常是指向 bash 的連結
2.2 使用 Shell#
2.2.1 Shell 視窗 (The Shell Window)#
登入後開啟終端機視窗,shell 會顯示一個提示符號,通常以 $ 結尾。本書中的指令都以 $ 開頭表示。
- 以
#開頭的指令需要以 superuser (root) 身份執行 - 最佳實踐是使用
sudo來執行需要 root 權限的指令
2.2.2 cat#
cat 是最簡單的 Unix 指令之一,用來輸出一個或多個檔案的內容:
cat file1 file2 ...- 名稱來自 concatenation(串接),因為它可以串接多個檔案的內容
2.2.3 Standard Input 與 Standard Output#
Unix 程序使用 I/O streams 來讀寫資料:
- Standard input (stdin) — 程序的輸入來源,預設連接到終端機
- Standard output (stdout) — 程序的輸出目標,預設連接到終端機
- Standard error (stderr) — 第三個 I/O stream,用於診斷和除錯訊息
按 CTRL-D 可送出 EOF(end-of-file)訊號來結束 stdin 輸入。不要與 CTRL-C(終止程式)混淆。
2.3 基本指令#
2.3.1 ls#
列出目錄內容:
ls -l # 詳細列表(含權限、擁有者、大小、日期)
ls -F # 顯示檔案類型資訊2.3.2 cp#
複製檔案:
cp file1 file2 # 複製檔案
cp file dir # 複製到目錄
cp file1 file2 file3 dir # 複製多個檔案到目錄2.3.3 mv#
移動或重新命名檔案:
mv file1 file2 # 重新命名
mv file dir # 移動到目錄2.3.4 touch#
建立空檔案,或更新已存在檔案的修改時間戳記:
touch file2.3.5 rm#
刪除檔案。刪除後通常無法復原:
rm file2.3.6 echo#
將引數印到 standard output:
echo Hello again.- 對於查看 shell glob 展開結果和變數值非常有用
2.4 目錄導覽#
Unix 目錄階層從 /(root directory)開始,目錄分隔符號是 /(正斜線),不是 \。
- Absolute path(絕對路徑)— 以
/開頭,如/usr/lib - Relative path(相對路徑)— 不以
/開頭,相對於目前目錄 ..代表上層目錄,.代表目前目錄
2.4.1 cd#
切換 current working directory:
cd dir # 切換到指定目錄
cd # 回到 home directory
cd是 shell 內建指令(built-in),不是獨立程式。它無法作為子程序執行,因為子程序無法改變父程序的工作目錄。
2.4.2 mkdir#
建立新目錄:
mkdir dir2.4.3 rmdir#
刪除空目錄。若目錄不為空,可用 rm -r dir 遞迴刪除。
rm -r可能造成嚴重損害,尤其以 root 身份執行時。不要搭配 glob(如*)使用-r選項,執行前務必再三確認。
2.4.4 Shell Globbing(萬用字元)#
Shell 可以使用 globbing 來匹配檔案名稱模式:
*— 匹配任意數量的任意字元?— 匹配恰好一個任意字元- 用單引號可以防止 glob 展開:
echo '*'
在 Unix 中使用
*匹配所有檔案,而非*.*。*.*只會匹配名稱中包含.的檔案。
2.5 中階指令#
2.5.1 grep#
從檔案或輸入流中搜尋匹配的文字行:
grep root /etc/passwd
grep root /etc/*-i— 不區分大小寫-v— 反向搜尋(顯示不匹配的行)- 支援 regular expressions(正規表達式):
.*匹配任意字元序列,.+匹配一個以上字元,.匹配任一字元
2.5.2 less#
分頁瀏覽大型檔案或長輸出:
less /usr/share/dict/words
grep ie /usr/share/dict/words | less- 空白鍵往前翻頁,
b往回翻頁,q離開 /word向前搜尋,?word向後搜尋
2.5.3 pwd#
顯示目前工作目錄的完整路徑。使用 pwd -P 可以顯示真實路徑(排除 symbolic link 影響)。
2.5.4 diff#
比較兩個文字檔的差異:
diff file1 file2
diff -u file1 file2 # unified format,適合自動化工具2.5.5 file#
辨識檔案格式:
file file2.5.6 find 與 locate#
- find — 在目錄樹中即時搜尋檔案:
find dir -name file -print- locate — 透過預建索引搜尋,速度較快但可能不是最新的
2.5.7 head 與 tail#
快速檢視檔案的開頭或結尾:
head /etc/passwd # 前 10 行
head -5 /etc/passwd # 前 5 行
tail /etc/passwd # 最後 10 行
tail +n file # 從第 n 行開始顯示2.5.8 sort#
將文字檔按字母順序排序。-n 按數值排序,-r 反向排序。
2.6 變更密碼與 Shell#
- 使用
passwd指令變更密碼,建議使用 16 字元以上的長密碼 - 使用
chsh指令變更預設 shell(如 zsh、ksh、tcsh)
2.7 Dot Files(隱藏檔)#
Dot files 是以 . 開頭的檔案或目錄,如 .bashrc、.login、.ssh。
ls預設不會顯示它們,需使用ls -a- Shell glob 也不會匹配 dot files,除非明確使用
.*之類的模式
2.8 Environment 與 Shell Variables#
- Shell variable — 僅在目前 shell 中有效:
STUFF=blah- Environment variable — 會傳遞給子程序:
STUFF=blah
export STUFF賦值時
=前後不能有空格。
- 子程序會繼承父程序的 environment variables
- 許多程式會讀取 environment variables 作為設定(如
LESS環境變數)
2.9 The Command Path#
PATH 是一個特殊的 environment variable,包含 shell 搜尋指令時會查找的目錄清單,以冒號 : 分隔:
echo $PATH
# /usr/local/bin:/usr/bin:/bin
PATH=dir:$PATH # 在最前面加入目錄
PATH=$PATH:dir # 在最後面加入目錄修改
$PATH時若打錯字,可能會覆蓋整個 path。不過這不是永久性的,只要開啟新 shell 即可恢復。
2.10 Special Characters(特殊字元)#
常見的特殊字元及其用途:
| 字元 | 名稱 | 用途 |
|---|---|---|
* | star, asterisk | 正規表達式、glob |
. | dot | 目前目錄、檔名分隔符號 |
! | bang | 否定、指令歷史 |
| | pipe | 管線指令 |
/ | forward slash | 目錄分隔符號、搜尋 |
$ | dollar | 變數、行尾 |
' | single quote | 字面字串 |
` | backtick | 指令替換 |
" | double quote | 半字面字串 |
~ | tilde | 否定、home 目錄捷徑 |
# | hash, pound | 註解、前處理器 |
2.11 Command-Line Editing#
常用的命令列編輯快捷鍵:
| 按鍵 | 功能 |
|---|---|
| CTRL-B / CTRL-F | 左移 / 右移游標 |
| CTRL-P / CTRL-N | 上一個 / 下一個指令 |
| CTRL-A / CTRL-E | 移到行首 / 行尾 |
| CTRL-W | 刪除前一個單字 |
| CTRL-U / CTRL-K | 刪除到行首 / 行尾 |
| CTRL-Y | 貼上已刪除的文字 |
2.12 Text Editors#
學習 Unix 必須掌握至少一個文字編輯器:
- Emacs — 功能強大,有豐富的線上說明
- vi — 速度至上,操作風格像遊戲
雖然 nano、Pico 等編輯器較友善,但如果你想認真學習 Unix,建議學習 vi 或 Emacs。
2.13 Getting Online Help#
Manual Pages (man pages)#
man ls # 查看 ls 的手冊頁
man -k keyword # 按關鍵字搜尋手冊頁
man 5 passwd # 查看特定 section 的手冊頁手冊頁分為多個 section:
| Section | 說明 |
|---|---|
| 1 | 使用者指令 |
| 2 | Kernel system calls |
| 3 | 高階 Unix 程式庫文件 |
| 5 | 檔案描述(系統設定檔) |
| 8 | 系統管理指令與伺服器 |
其他取得幫助的方式:
command --help或command -hinfo command— GNU 的替代文件格式/usr/share/doc— 某些套件的文件目錄
2.14 Shell Input and Output#
Standard Output 重導向#
command > file # 輸出到檔案(覆蓋)
command >> file # 輸出到檔案(附加)Pipe(管線)#
head /proc/cpuinfo | tr a-z A-Z- 可以串接任意多個管線指令
2.14.1 Standard Error#
Standard error (stderr) 是獨立於 stdout 的輸出串流,stream ID 為 2:
ls /fffffffff > f 2> e # stdout 到 f,stderr 到 e
ls /fffffffff > f 2>&1 # stdout 和 stderr 都到 f2.14.2 Standard Input 重導向#
head < /proc/cpuinfo- 大多數 Unix 指令接受檔名作為引數,因此 stdin 重導向較不常用
2.15 Understanding Error Messages#
2.15.1 Unix 錯誤訊息的結構#
Unix 錯誤訊息通常包含三個部分:
- 程式名稱(如
ls) - 檔案名稱(如
/dsafsda) - 錯誤描述(如
No such file or directory)
排錯時,永遠先處理第一個錯誤訊息,後續錯誤可能是連鎖反應。
2.15.2 常見錯誤#
- No such file or directory — 最常見的錯誤,也稱為 ENOENT
- File exists — 嘗試建立已存在的檔案或目錄
- Not a directory / Is a directory — 將檔案當目錄用,或反之
- No space left on device — 磁碟空間已滿
- Permission denied — 權限不足
- Operation not permitted — 嘗試終止不屬於你的程序
- Segmentation fault / Bus error — 程式存取了不允許的記憶體區域
2.16 Listing and Manipulating Processes#
每個程序都有一個 process ID (PID):
ps # 列出你的程序
ps x # 列出所有你的程序
ps ax # 列出系統上所有程序
ps u # 詳細資訊
ps w # 顯示完整指令ps 輸出欄位:PID、TTY(終端設備)、STAT(程序狀態,S=sleeping、R=running)、TIME(CPU 時間)、COMMAND。
2.16.1 ps 指令選項#
支援三種風格:Unix、BSD、GNU。BSD 風格最常用,可組合使用如 ps auxw。
2.16.2 Process Termination#
使用 kill 發送 signal 給程序:
kill pid # 發送 TERM 信號
kill -STOP pid # 暫停程序
kill -CONT pid # 繼續執行
kill -KILL pid # 強制終止(最後手段)KILL 信號無法被忽略或處理,kernel 會直接終止程序並從記憶體中移除。僅在其他方法無效時使用。
2.16.3 Job Control#
Shell 支援 job control,可以暫停和切換程式:
- CTRL-Z — 發送 TSTP 信號暫停程式
fg— 將程式帶回前景bg— 將程式移到背景
2.16.4 Background Processes#
使用 & 將程序放到背景執行:
gunzip file.gz &- 建議將背景程序的輸出重導向到檔案,避免干擾終端機
2.17 File Modes and Permissions#
每個 Unix 檔案都有 permissions,透過 ls -l 查看:
-rw-r--r-- 1 juser somegroup 7041 Mar 26 19:34 endnotes.htmlMode 的四個部分:
- File type —
-一般檔案、d目錄、lsymbolic link - User permissions — 檔案擁有者的權限
- Group permissions — 檔案群組的權限
- Other permissions — 其他人的權限

Figure 2-1: The pieces of a file mode
權限符號:
- r — 可讀取
- w — 可寫入
- x — 可執行
- - — 無此權限
- s — setuid(執行時以檔案擁有者身份執行)
2.17.1 Modifying Permissions#
使用 chmod 修改權限:
chmod g+r file # 為 group 加上讀取權限
chmod go+r file # 為 group 和 other 加上讀取權限
chmod go-r file # 移除權限
chmod 644 file # 使用八進位數字設定(absolute mode)常用的 absolute mode:
| Mode | 意義 | 用途 |
|---|---|---|
| 644 | user: rw, group: r, other: r | 檔案 |
| 600 | user: rw, group: -, other: - | 檔案 |
| 755 | user: rwx, group: rx, other: rx | 目錄、程式 |
| 700 | user: rwx, group: -, other: - | 目錄、程式 |
- umask 指令可設定新檔案的預設權限遮罩(
022或077)
2.17.2 Working with Symbolic Links#
Symbolic link 是指向另一個檔案或目錄的檔案,類似 Windows 的捷徑:
ln -s target linkname不要忘記
-s選項。沒有-s的ln會建立 hard link,除非你了解 hard link 的機制(參見 Section 4.6),否則應避免使用。
- Symbolic link 可能產生 chained symbolic links,增加追蹤難度
- 建立時務必確認引數順序,並使用完整路徑
2.18 Archiving and Compressing Files#
2.18.1 gzip#
gzip (GNU Zip) 是標準的 Unix 壓縮工具:
gzip file # 壓縮(產生 file.gz)
gunzip file.gz # 解壓縮2.18.2 tar#
tar 用來將多個檔案和目錄打包成單一 archive 檔案:
tar cvf archive.tar file1 file2 ... # 建立 archive
tar xvf archive.tar # 解開 archive
tar tvf archive.tar # 列出 archive 內容c— create modex— extract modet— table-of-contents modev— verbose outputf— 指定 archive 檔名
解開前務必先用
t模式檢查內容,確認是否有合理的目錄結構,避免將大量檔案倒入目前目錄。
2.18.3 Compressed Archives (.tar.gz)#
gunzip file.tar.gz && tar xvf file.tar # 兩步驟解開2.18.4 zcat#
更有效率的方式是使用管線:
zcat file.tar.gz | tar xvf -或使用 tar 的 z 選項作為捷徑:
tar ztvf file.tar.gz # 檢視壓縮 archive 內容
tar zxvf file.tar.gz # 解開壓縮 archive2.18.5 Other Compression Utilities#
- xz / bzip2 — 壓縮率比 gzip 高,但速度稍慢,副檔名為
.xz和.bz2 - zip / unzip — 與 Windows ZIP 格式相容
.Z檔案是舊版compress程式產生的,gunzip可以解壓
2.19 Linux Directory Hierarchy Essentials#
Linux 目錄結構遵循 Filesystem Hierarchy Standard (FHS)。

Figure 2-2: Linux directory hierarchy
主要根目錄子目錄#
| 目錄 | 說明 |
|---|---|
| /bin | 基本可執行程式(ls、cp 等) |
| /dev | 裝置檔案 |
| /etc | 系統設定檔(密碼、開機、網路等) |
| /home | 一般使用者的家目錄 |
| /lib | 程式庫檔案(shared libraries) |
| /proc | 系統統計資訊的虛擬檔案系統 |
| /run | 系統執行期間的資料(PID、socket 等) |
| /sys | 裝置與系統介面(類似 /proc) |
| /sbin | 系統管理程式(通常需要 root) |
| /tmp | 暫存檔案(開機時可能被清除) |
| /usr | 大部分使用者空間程式和資料 |
| /var | 可變動的資料(日誌、快取等) |
2.19.1 Other Root Subdirectories#
- /boot — kernel boot loader 檔案
- /media — 可移除媒體的掛載點
- /opt — 第三方軟體(許多系統不使用)
2.19.2 /usr 目錄#
/usr 包含大部分使用者空間程式和資料:
- /usr/include — C 編譯器的 header 檔案
- /usr/local — 管理者自行安裝的軟體
- /usr/man — 手冊頁
- /usr/share — 跨平台共用的輔助資料檔案
/usr發音為 “user”,但實際上不包含使用者檔案。根目錄與/usr有相似的子目錄結構(如/bin與/usr/bin),這是歷史原因造成的 — 過去需要控制根目錄的磁碟空間使用量。
2.19.3 Kernel Location#
- Kernel 通常是
/vmlinuz或/boot/vmlinuz二進位檔案 - Boot loader 負責將 kernel 載入記憶體
- Loadable kernel modules 位於
/lib/modules,可在執行時動態載入和卸載
2.20 Running Commands as the Superuser#
不建議直接啟動 root shell,原因包括:
- 無法追蹤系統變更指令的記錄
- 無法辨識是哪位使用者執行了系統變更
- 無法使用一般使用者的 shell 環境
- 需要輸入 root 密碼
2.20.1 sudo#
sudo 讓管理者以自己的身份登入並以 root 執行指令:
sudo vipw- sudo 會透過 syslog 記錄所有操作
2.20.2 /etc/sudoers#
設定哪些使用者可以使用 sudo:
User_Alias ADMINS = user1, user2
ADMINS ALL = NOPASSWD: ALL
root ALL=(ALL) ALL務必使用
visudo指令來編輯/etc/sudoers,它會在儲存後檢查語法錯誤。
2.20.3 sudo Logs#
查看 sudo 日誌:
journalctl SYSLOG_IDENTIFIER=sudo在較舊的系統上,日誌位於 /var/log 或 /var/log/auth.log。
2.21 Looking Forward#
完成本章後,你應該能夠在命令列上執行程式、重導向輸出、操作檔案與目錄、檢視程序列表、閱讀手冊頁,以及以 superuser 身份執行指令。接下來的章節將結合 kernel 和 user-space 的系統組件,使用本章學到的命令列工具進行探索。