Linux 命令 man 全知全會

hedzr發表於2021-12-26
摘要
對 man 的各種用法做一次整理,順便也可以當作參考手冊。
<!--MORE-->

引子

man 是一個 Linux 命令列實用程式,用於顯示 linux 命令、系統呼叫、庫函式等的幫助手冊。

手冊頁,即 Manual pages,又稱作 man page,是在 Unix類Unix 作業系統 線上 軟體文件 的一種普遍的形式。 內容包括計算機程式(包括系統呼叫),正式的標準和慣例,甚至是抽象的概念。使用者可以通過執行man命令)呼叫手冊頁。

man 手冊頁被設計成獨立的文件,不能引用其它手冊頁面。這與支援超連結的 Info 文件 形成鮮明對比,GNU正在將 man 手冊替換成 info 文件。

手冊頁的預設格式是troff,使用man巨集軟體包(著重展現)或mdoc巨集軟體包(著重語義)。可以把手冊頁排版成PostScriptPDF和其他各種格式進行檢視或列印。

安裝

man-db 提供了 man 命令,lessman 的預設分頁器。

image-20211226010348217

man-pages 提供了 Linux man 頁面的內容。

image-20211226010416504

下面是一些語言的翻譯版本:

下面程式也可以用來閱讀手冊:

  • GNOME HelpGNOME 幫助閱讀程式。 通過 yelp man:<name>Ctrl+L 快捷鍵閱讀手冊頁面。
  • KHelpCenterKDE 幫助閱讀程式,可以通過 khelpcenter man:<name> 閱讀手冊。
  • Konqueror — KDE 檔案和網頁瀏覽器,也可以通過 man:<name> 顯示手冊。
  • xman — 可以分類檢視手冊。

對於 Linux 發行版來說,man 是標準配置,任何一個最小系統均包含了 man 命令(即,man-db 包總是被預裝的),但手冊頁的文件內容部分則不一定了,根據實際情況進行選裝。

對於像 Ubuntu 這樣的系統來說,應用程式的手冊頁常常以字尾 -doc 的獨立包方式存在,例如 flex 包的配套手冊頁為 flex-doc 包。

sudo apt install flex flex-doc
sudo apt install bison bison-doc
sudo apt install git git-doc

對於 POSIX 可移植性較為關注的人,可能會需要安裝:

sudo apt install manpages-poxis*

然後就可以查閱 POSIX 呼叫,例如:

man 3p connect

等等。

閱讀手冊頁

通過以下命令閱讀man手冊頁:

$ man 手冊名

man 手冊頁分為很多區塊。完整的列表可以參考: man-pages(7)

man 手冊頁通過名稱和所屬分類標識。有些不同分類的 man 手冊頁名字可能相同,比如 man(1) 和 man(7),這時需要額外指明分類以訪問需要的手冊。例如:

$ man 5 passwd

會顯示有關檔案/etc/passwd,而非命令 passwd,的內容。

快捷鍵(less

在手冊頁閱讀介面中,可以使用快捷鍵來幫助閱讀。

由於手冊頁的顯示是使用作業系統 Shell 環境中的預設 PAGER 來完成的,所以快捷鍵遵循相應 PAGER 的功能對映。

大多數系統中現在預設採用 less 作為預設 PAGER,因此請參考 less 命令全知全會

佈局

所有的手冊頁遵循一個常見的佈局,其為通過簡單的ASCII文字展示而優化,而這種情況下可能沒有任何形式的高亮或字型控制。一般包括以下部分內容:

  • NAME(名稱)

    該命令或函式的名稱,接著是一行簡介。

  • SYNOPSIS(概要)

    對於命令),正式的描述它如何執行,以及需要什麼樣的命令列引數。對於函式,介紹函式所需的引數,以及哪個標頭檔案包含該函式的定義。

  • DESCRIPTION(說明)

    命令或函式功能的文字描述。

  • EXAMPLES(示例)

    常用的一些示例。

  • SEE ALSO(參見)

    相關命令或函式的列表。

也可能存在其他部分內容,但這些部分沒有得到跨手冊頁的標準化。常見的例子包括:OPTIONS(選項),EXIT STATUS(退出狀態),ENVIRONMENT(環境),BUGS(程式漏洞),FILES(檔案),AUTHOR(作者),REPORTING BUGS(已知漏洞),HISTORY(歷史)和COPYRIGHT(著作權)。

你可以在 man-pages(7) 查閱到這些手冊頁內的區塊的描述,如同我們前文中所描述的那樣。

一個較完整的列表節錄如下:

NAME
SYNOPSIS
CONFIGURATION[Normally only in Section 4]
DESCRIPTION
OPTIONS[Normally only in Sections 1, 8]
EXIT STATUS[Normally only in Sections 1, 8]
RETURN VALUE[Normally only in Sections 2, 3]
ERRORS[Typically only in Sections 2, 3]
ENVIRONMENT
FILES
VERSIONS[Normally only in Sections 2, 3]
ATTRIBUTES[Normally only in Sections 2, 3]
CONFORMING TO
NOTES
BUGS
EXAMPLES
AUTHORS[Discouraged]
REPORTING BUGS[Not used in man-pages]
COPYRIGHT[Not used in man-pages]
SEE ALSO

手冊區塊

在作業系統中,所有的手冊頁被按照其主題分類劃分為多個區塊,例如系統呼叫,Shell 命令,C 庫函式等等。這些區塊主要定位在 /usr/share/man/man1/usr/share/man/man9 資料夾中。

在 Arch Linux、Research UnixBSDOS XLinux 中,手冊通常被分為8個區塊,安排如下:

區塊說明
1一般命令)
2系統呼叫
3函式,涵蓋C標準函式庫
4特殊檔案(通常是/dev中的裝置)和驅動程式
5檔案格式和約定
6遊戲屏保
7雜項
8系統管理命令)和守護程式

Unix System V 採用了類似的編號方案,但順序不同:

區塊說明
1一般命令)
1M系統管理命令)和守護程式
2系統呼叫
3C函式庫函式
4檔案格式和約定
5雜項
6遊戲屏保
7特殊檔案(通常是/dev中的裝置)和驅動程式

在某些系統中還有下述的區塊可用:

區塊描述
0C函式庫標頭檔案
9核心例程
nTcl/Tk關鍵字
xX視窗系統

一些區塊利用字尾進一步細分了。例如在一些系統中,區塊3C是C函式庫呼叫,3M是數學(Math)函式庫,等等。這樣做的結果是區塊8(系統管理命令)有時也被移動到區塊1M(作為命令)區塊的子區塊)。一些子區塊字尾有跨區塊的一般含義:

子區塊說明
pPOSIX規範
xX視窗系統文件
pmPerl Module 函式

綜述

綜上所述,手冊頁的主要的類別和對應的編號有:

0     Header files
0p    Header files (POSIX)
1     Executable programs or shell commands
1p    Executable programs or shell commands (POSIX)
2     System calls (functions provided by the kernel)
3     Library calls (functions within program libraries)
3n    Network Functions
3p,3pm    Perl Modules
4     Special files (usually found in /dev)
5     File formats and conventions eg /etc/passwd
6     Games
7     Miscellaneous  (including  macro  packages and conventions), e.g. man(7), groff(7)
8     System administration commands (usually only for root)
9     Kernel routines
l     Local documentation
n     New manpages

翻譯過來粗略是:

  • 0, 0p:已過時,相應的條目已經被合併到 section 3 之中了。
  • l, n:基本上不存在於發行版中,但開發者可以用於開發週期中。
  • 1:可執行程式或是 shell 指令。
  • 2:系統呼叫(system calls,Linux 核心所提供的函式)。
  • 3:一般庫函式,C 庫函式。
  • 4:特殊檔案(通常位於 /dev 之中)。
  • 5:檔案格式於協定,如 /etc/passwd
  • 6:遊戲。
  • 7:雜項(巨集處理等,如 man(7)groff(7))。
  • 8:系統管理員指令(通常是管理者 root 專用指令)。
  • 9:Kernel routines(非標準)。

注意前文已經提及,絕大多數系統中,只有區塊 1 到 8 這幾個類別。你可以在 man-pages(7) 查閱到這些區塊的描述,如同我們前文中所描述的那樣。

在手冊頁系統中的會用小括號來註明手冊所屬的區塊,例如 ls(1) 表示 Shell 命令 ls 隸屬於區塊 1。

有時候一個主題名稱可能會在不同的區塊中有不同的說明檔案,若是查詢一個主題時未能在指定區塊中找到,那麼 man 會依照 1 n l 8 3 2 3posix 3pm 3perl 5 4 9 6 7 的順序依次檢索相應的其它區塊,然後顯示第一個搜尋到的章節內容。

例如 passwd 這個主題 passwd(1)passwd(5) 兩個章節,如果不指定章節的話:

man passwd

會顯示 passwd(1),而若要查詢 passwd(5) 的話,就應該明確指定區塊編號:

man 5 passwd

如果你對這種語法感到困惑的話,可以採用如下的格式:

man passwd.5

兩者是等效的。

列出所有章節

由於具體主題的複雜性,所以有的條目未必在你以為的分割槽中,例如 recv C 函式的參考並不是在分割槽 3 中,而是在分割槽 2 中,因為它是 Linux 核心呼叫之一。這種情況在系統呼叫和 C 庫函式重名時常常可見。

有時候我們對某主題很感興趣,但卻並不知道該主題有哪些章節可以被查詢,這時候就可以用 -aw 引數進行查詢:

man -aw printf

典型的結果可能是這樣:

/usr/share/man/man1/printf.1.gz
/usr/share/man/man1/printf.1posix.gz
/usr/share/man/man3/printf.3.gz
/usr/share/man/man3/printf.3posix.gz

但你或許更喜歡 whatis 返回的結果:

$ whatis printf
printf (1)           - format and print data
printf (3)           - formatted output conversion
printf (1posix)      - write formatted output
printf (3posix)      - print formatted output

它更直觀。

whatis 等價於 man -f

$ man -f printf
printf (1)           - format and print data
printf (3)           - formatted output conversion
printf (1posix)      - write formatted output
printf (3posix)      - print formatted output

一次查閱所有章節

如果要一次性查閱某個主題的所有章節,可以用 -a 引數,這會令 man 依次顯示所有章節:

man -a printf

當你看完一個章節並按 q 退出之後,man 會顯示:

--Man-- next: printf(3) [ view (return) | skip (Ctrl-D) | quit (Ctrl-C) ]

j簡單地回車(按下 Enter 鍵)就可以繼續閱讀下一個章節。你也可以用 Ctrl-C 終止 man 返回到 Shell 提示符狀態。

搜尋手冊頁

如果使用者壓根兒不知道要查閱的手冊的名稱,該怎麼辦呢?沒事,通過 -k 或者 --apropos 引數就可以按給定關鍵詞搜尋相關手冊。例如,要查閱有關密碼的手冊(“password”):

$ man -k password
chage (1)            - change user password expiry information
chgpasswd (8)        - update group passwords in batch mode
chpasswd (8)         - update passwords in batch mode
...
pam_unix (8)         - Module for traditional password authentication
passwd (1)           - change user password
passwd (1ssl)        - compute password hashes
passwd (5)           - the password file
passwd2des (3)       - RFS password encryption
...
pwd.h (7posix)       - password structure
...
shadow (5)           - shadowed password file
shadowconfig (8)     - toggle shadow passwords on and off
smbpasswd (5)        - The Samba encrypted password file
smbpasswd (8)        - change a user's SMB password
...
xdecrypt (3)         - RFS password encryption
xencrypt (3)         - RFS password encryption

man -k 會篩選主題名稱以及簡短描述文字來嘗試匹配給定的關鍵字。

現在你可以開始搜尋了。 例如,要查閱有關密碼的手冊(“password”),可以使用下面的命令:

$ man -k password
$ man --apropos password
$ apropos password

它們是同義詞。

關鍵字可以使用正規表示式。

例如

$ man -k sprintf
asprintf (3)         - print to allocated string
sprintf (3)          - formatted output conversion
Text::sprintfn (3pm) - Drop-in replacement for sprintf(), with named parameter support
vasprintf (3)        - print to allocated string
vsprintf (3)         - formatted output conversion

注意得到上面的結果需要首先安裝:

sudo apt install libtext-sprintfn-perl

以保證 Text::sprintfn (3pm) 條目已經存在。

/usr/share/man/man3/Text::sprintfn.3pm.gz

全文檢索某個關鍵字

如果你想全文搜尋的話,你可以用-K選項:

$ man -K sprintf

它會開啟第一個手冊頁供你閱讀,你可以 q 退出閱讀介面,而後會有一個提示:

--Man-- next: gcc-7(1) [ view (return) | skip (Ctrl-D) | quit (Ctrl-C) ]

此時你可以回車(Enter)閱讀下一個匹配的手冊頁,也可以 Ctrl-C 退出 man -K 狀態。

其它功能

在瀏覽器中顯示手冊頁

man -Hfirefox printf

此功能可能需要 groff 命令能夠在 PATH 路徑中可被搜尋到。所以你也許需要顯式地安裝 groff

sudo apt-get install groff

指定分頁程式(PAGER)

我們提到過顯示主題內容使用的是通過環境變數 PAGER 指定的分頁程式,預設時為 less。但你可以顯式地指定其它分頁程式作為顯示工具,這是通過命令列引數 -P 來指定的:

man -P more printf

轉換為純文字、網頁或 PDF

純文字
man printf | col -b > printf.txt
網頁

首先,安裝軟體包 man2html

然後使用它轉換 man 手冊頁:

$ man free | man2html -compress -cgiurl man$section/$title.$section$subsection.html > ~/man/free.html

此外,man2html 還可以把 man 頁轉換為便於列印的文字檔案:

$ man free | man2html -bare > ~/free.txt

另一種方式是直接通過 groff 來做:

zcat `man -w printf` | groff -mandoc -T html > printf.html
PDF

將手冊頁轉換為 PDF:

man -t printf | ps2pdf - printf.pdf

man pages 是可以列印的,遵循 troff 格式,本來就是一種列印設定語言,安裝 ghostscript 後,可以用下面命令將 man 頁面轉換為 PDF man -t <manpage> | ps2pdf - <pdf>.

注意這裡僅能使用 Times 字型,沒有超連結,有些手冊是轉為終端設計,PS 或 PDF 格式看起來不太正常。

指定文字語言

你可以安裝 manpages-zh 包來提供中文手冊頁支援。

在終端中,設定 LANG 環境變數為 UTF-8.zh_CN,則 man 會以中文方式顯示主題章節內容。不過如果沒有中文版的話,還是會 fallback 到英文版。

如果你不想改變環境變數,也可以通過命令列引數 -L 來達到目的,例如

man -L en 5 passwd
man -L zh_CN 5 passwd

其它資訊

手冊頁儲存在哪裡?

典型的位置在 /usr/share/man/usr/local/share/man 中。

此外,常常會有 /usr/man/usr/local/man 的符號連結。

manpath 命令是獲知確切的儲存位置的正確方法:

$ manpath
/usr/local/man:/usr/local/share/man:/usr/share/man

manpath 命令或者 man 命令都是通過 /etc/manpath.config 或者 /etc/man_db.conf 配置檔案來取得正確的儲存位置集合的。但對於多數人來說我們不建議你去探究這些配置檔案,它們遵循一定的格式約定,但分析和抽取結果往往對於 Shell 指令碼來說過於繁雜了,遠不如分析 manpath 返回的結果來得簡單易用。

要獲知 /etc/manpath.config 的更多資訊,可以檢視手冊頁 man manpath

有的時候,$MANPATH$ 環境變數可能包含了正確的值。但絕大多數情況下可能它都是空值。

另一種方法是通過 whereis 命令來間接獲知:

$ whereis man
man: /usr/bin/man /usr/local/man /usr/share/man /usr/share/man/man1/man.1.gz /usr/share/man/man7/man.7.gz

/usr/share/man-db/chconfig 是一個 perl 執行指令碼,會重新生成 /etc/manpath.config ,這是系統級的內部行為。

使用線上手冊頁

許多網站提供線上man手冊頁,詳細列表參見:Wikipedia:Man_page#Repositories_of_manual_pages

參考

後記

本文中有的內容完全複製於參考連結中。

?

相關文章