8.2. init 程序

init 程式是程序 ID 1 的程序,其負責以指定方式來啟始系統。因此,init 在此扮演一個特別的角色。它是由核心直接啟動並拒絕訊息 9,因為這個訊息通常會刪除程序。所有其他程式是直接透過 init 或它其中一個子程序啟動。

init 主要是在 /etc/inittab 檔案中設定,runlevels 即是在該檔案中定義的 (請參閱節 8.2.1, "Runlevel")。這個檔案還會指定每一個層次可以使用的服務和精靈。視 /etc/inittab 中的項目而定,init 會執行數個程序檔。為避免混淆,這些稱做 init 程序檔 的程序檔都位於目錄 /etc/init.d 中 (請參閱節 8.2.2, "Init 程序檔")。

啟動系統和關閉系統的整個程序是由 init 維護。依此觀點,核心可以視為背景程序,它的工作是維護所有其他程序,並根據其他程式的要求來調整 CPU 時間和硬體存取。

8.2.1. Runlevel

在 Linux 中是由 runlevel 定義啟動系統的方式,以及在所執行的系統可以使用哪些服務。開機之後,系統會按照 /etc/inittab 中的 initdefault 這一行文字的定義而啟動。一般是 35。另請參閱表格 8.1, "可用的 Runlevel"。還有一種方法是,runlevel 可以在開機期間指定 (例如,在開機提示時)。非經由核心直接評估的所有參數,都會傳送給 init。

表格 8.1. 可用的 Runlevel

Runlevel

說明

0

系統暫停

S

單一使用者模式;從開機提示,只能使用使用美式鍵盤對應

1

單一使用者模式

2

本地多重使用者模式,不包含遠端網路 (NFS 等)

3

完整的多重使用者模式,包含網路

4

未使用

5

完整多重使用者模式,包含網路、X 顯示管理員-- KDM、GDM 或 XDM

6

系統重新開機

[Important]避免透過 NFS 裝載分割區的 Runlevel 2

如果系統會透過 NFS 裝載例如 /usr 等分割區,您就不應該使用 runlevel 2。如果程式檔案或是程式庫因 runlevel 2 (本地多重使用者模式,無遠端網路) 無法提供 NFS 服務而發生遺失,系統可能無法正常運作。

若要在系統執行時變更 runlevel,請輸入 telinit 以及當成引數的對應數字。只有系統管理員可以執行此動作。以下清單列出 runlevel 區域中最重要的指令摘要。

telinit 1shutdown now

系統變更為單一使用者模式。此模式是用於系統維護和管理工作。

telinit 3

可以啟動所有主要的程式和服務 (包括網路),且可讓一般使用者登入並在非圖形環境下使用該系統。

telinit 5

啟用圖形式環境。通常這時會啟動例如 XDM、GDM 或 KDM 的顯示管理員。如果已啟用自動登入,本機使用者就可以登入事先選定的視窗管理員 (GNOME、KDE 或是任何其他視窗管理員)。

telinit 0shutdown -h now

暫停系統。

telinit 6shutdown -r now

暫停系統後重新開機

所有 SUSE Linux 標準安裝中,預設都使用 Runlevel 5。使用者會在提示之下使用圖形介面登入,或是依預設自動登入。如果預設 runlevel 是 3,這時 X 視窗系統必須依據章 14, X Window System所述適當設定,才能將 runlevel 切換至 5。完成這個動作之後,請輸入 telinit 5 來檢查系統是否已依指定方式運作。如果一切都如預期,您可以使用 YaST,將預設 runlevel 設定成 5

通常,當您變更 runlevel 時會發生兩件事。首先,啟動目前 runlevel 中的停止程序檔,關閉對目前 runlevel 很重要的一些程式。然後啟動新 runlevel 的啟動程序檔。在大部份的情況下,此時也會啟動一些程式。例如,從 runlevel 3 變更成 5 時,會發生以下事件:

  1. 管理員 (root) 可以輸入 telinit 5,要求 init 變更為不同的 runlevel。

  2. init 會檢查它的組態檔 (/etc/inittab) 然後決定是否以新的 runlevel 為參數來啟動 /etc/init.d/rc

  3. 現在 rc 會呼叫目前 runlevel 的所有停止程序檔,但只限新的 runlevel 沒有啟動的程序檔。在此範例中的所有程序檔,都位於 /etc/init.d/rc3.d (舊的 runlevel 是 3),而且開頭是 KK 後面的號碼指定啟動順序,因為還有一些相關因素要考量。

  4. 新的 runlevel 啟動程序檔,會最後才啟動。在此範例中的所有程序檔,都位於 /etc/init.d/rc5.d,而且開頭是 S。啟動順序的相同程序,也會適用於此。

變更成與目前 runlevel 相同的 runlevel 時,init 只會檢查 /etc/inittab 是否變更,並啟動適當的步驟,例如,在另一個介面啟動 getty。使用指令 telinit q 也可以完成相同功能。

8.2.2. Init 程序檔

/etc/init.d 中的程序檔有兩種類型:

由 init 直接執行的程序檔

這種狀況僅出現於開機程序或立即關閉系統 (電源中斷或使用者按下 Ctrl-Alt-Del) 時。請在 /etc/inittab 中定義這些要執行的程序檔。

由 init 間接執行的程序檔

這些程序檔在變更 runlevel 時就會執行,而且永遠會呼叫主要程序檔 /etc/init.d/rc,以保證相關程序檔的順序正確。

所有程序檔都位於 /etc/init.d。在開機階段執行的程序檔,可以經由 /etc/init.d/boot.d 的符號連結進行呼叫。用於變更 runlevel 的程序也可以透過其中一個子目錄 (/etc/init.d/rc0.d/etc/init.d/rc6.d) 的符號連結來呼叫。這樣的安排是為了明確執行,避免當程序檔用於多個 runlevel 時的重複執行。因為每一個程序檔都可當成啟動程序檔和停止程序檔來執行,所以這些程序檔必須了解參數 startstop。程序檔也了解 restartreloadforce-reloadstatus 選項。這些不同選項在 表格 8.2, "可能的 init 程序檔選項" 都有說明。直接由 init 執行的程序檔沒有這些連結。這些程序檔可在需要時從 Runlevel 獨立執行。

表格 8.2. 可能的 init 程序檔選項

選項

說明

start

啟動服務。

stop

停止服務。

restart

如果服務在執行中,先停止,再重新啟動。如果服務沒有執行,請啟動它。

reload

不需停止和重新啟動服務,就可以重新載入組態。

force-reload

如果服務支援,請重新載入組態。否則,執行與 restart 相同的動作。

status

顯示目前狀態。

每一個特定 runlevel 子目錄中的連結,可以將程序檔與不同 runlevel 產生關聯。安裝或解除安裝套件時,可以透過程式 insserv 的協助,新增和移除這些連結 (或透過 /usr/lib/lsb/install_initd,它是一個會呼叫該程式的程序檔)。如需詳細資訊,請參閱 insserv(8) 線上文件。

簡介最先啟動的開機及最後啟動的停止程序檔,並說明維護程序檔。

開機

使用 init 直接啟動系統時會執行。它與所選的 runlevel 無關,而且只會執行一次。此時,會裝載 procpts 檔案系統,啟動 blogd (開機記錄精靈)。如果系統是更新或安裝之後第一次開機,會啟動啟始系統組態。

任何其他服務啟動之前,blogd 精靈是透過開機和 rc 啟動的服務。上述程序檔觸發的動作 (例如,執行一些子程序檔) 完成後,blogd 精靈就會停止,並將螢幕的所有輸出寫入 /var/log/boot.msg 記錄檔,但這只發生在 /var 裝載成讀寫時。否則,blogd 會緩衝處理所有螢幕資料,直到 /var 可以使用為止。 您可以在 blogd(8) 線上文件取得進一步資訊。

程序檔 boot 也負責啟動 /etc/init.d/boot.d 中,名稱開頭是 S 的所有程序檔。在該處,會檢查檔案系統,並在需要時設定迴圈設備。也會設定系統時間。如果自動檢查和修復檔案系統時發生錯誤,系統管理員輸入管理員密碼後即可介入。最後執行的是程序檔 boot.local

boot.local

在此輸入開機時要執行的其他指令 (進入 runlevel 之前)。它就像是 DOS 系統的 AUTOEXEC.BAT

boot.setup

從單一使用者模式變更成任何其他 runlevel 時會執行此程序檔,它負責一些基本設定,例如鍵盤配置和虛擬主控台的啟始化。

halt

只有進入 runlevel 0 或 6 時,才會執行此程序檔。在此,它是以 暫停重新開機 的方式執行。系統是否關閉或重新啟動,取決於呼叫 halt 的方式。

rc

此程序檔會呼叫目前 runlevel 的適當停止程序檔,以及新選取 runlevel 的啟動程序檔。

您可以建立自己的程序檔,並輕鬆將它們整合至上述配置。如需關於格式化、命名以及組織自訂程序檔的指示,請參閱 LSB 的規格和 initinit.d 以及 insserv 的 man 頁面。另請參閱 startprockillproc 的 man 頁面。

[Warning]錯誤的 init 程序檔可能會暫停系統

錯誤的 init 程序檔可能會讓您的機器暫停。編輯類似程序檔要格外小心,可能的話,讓它們在多重使用者環境下密集測試。關於 init 程序檔的一些有用資訊,請參閱節 8.2.1, "Runlevel"

若要為指定的程式或服務建立自訂 init 程序檔,請將檔案 /etc/init.d/skeleton 當成樣板。使用新名稱儲存此檔案副本,編輯所需相關程式和檔案名稱、路徑,以及其他詳細資料。您也可能需要使用自己的組件來強化程式檔,好讓 init 程序觸發正確的動作。

上方的 INIT INFO 區塊是程序檔的必要組件,因此必須進行編輯。請參閱範例 8.1, "迷你 INIT INFO 區塊"

範例 8.1. 迷你 INIT INFO 區塊

### BEGIN INIT INFO
# Provides:          FOO
# Required-Start:    $syslog $remote_fs
# Required-Stop:     $syslog $remote_fs
# Default-Start:     3 5
# Default-Stop:      0 1 2 6
# Description:       Start FOO to allow XY and provide YZ
### END INIT INFO
    

請在 INFO 區塊的第一行中、Provides: 後面,為此 init 程序檔所控制的程式或服務指定名稱。在 Required-Start:Required-Stop:這兩行,在服務本身啟動或停止前,指定要啟動或停止的所有服務。此資訊以後會用來產生程序檔名稱的編號,這些就是在 runlevel 目錄可以找到的編號。在 Default-Start:Default-Stop: 之後,指定應該自動啟動或停止服務的 runlevel。最後,會在 Description: 簡要說明討論中的服務。

若要建立由 runlevel 目錄 (/etc/init.d/rc?.d/) 對應到 /etc/init.d/ 相關程序檔的連結,請輸入指令 insserv new-script-name。insserv 程式會評估 INIT INFO 標題,為 runlevel 目錄 (/etc/init.d/rc?.d/) 中的啟動和停止程序檔建立必要的連結。該程式也會為這些連結的名稱加上必要的編號,即可依正確順序啟動和停止每一個 runlevel。如果您偏好以圖形工具來建立類似連結,請使用 YaST 提供的 runlevel 編輯器 (請參閱 節 8.2.3, "使用 YaST 設定系統服務 (Runlevel)")。

如果 /etc/init.d/ 裡已經有程序檔,應該整合至現有的 runlevel 配置,使用 insserv 在 runlevel 目錄中立即建立連結,或者在 YaST 的 runlevel 編輯器中啟用對應的服務。下次重新啟動時,將會套用您所做的變更 - 新服務會自動啟動。

請勿手動設定這些連結。如果 INFO 區塊發生錯誤,稍後執行某些其他服務的 insserv 將會發生問題。手動加入的服務在下次執行 insserv 時將會移除。

8.2.3. 使用 YaST 設定系統服務 (Runlevel)

使用 YaST+系統+系統服務 (Runlevel) 啟動 YaST 模組後,會出現一個概觀清單,其中會列出所有可用的服務和每個服務目前的狀態 (停用或啟用)。決定要以 簡單模式進階模式 使用模組。大部份情況下,預設的 簡單模式 應該都已夠用。左欄顯示服務的名稱,中間欄顯示它的目前狀態,而右欄提供簡短說明。視窗下方為選取的服務提供更詳細的說明。若要啟用服務,在表格中選取它,然後選取 啟用。停用服務的步驟也一樣。

圖形 8.1. 系統服務 (Runlevel)

系統服務 (Runlevel)

要更仔細控制啟動或停止服務的 runlevel,或者變更預設的 runlevel,請先選取 進階模式。目前預設的 Runlevel 或 "initdefault" (系統開機時預設裝載的 Runlevel) 會出現在視窗上方。一般情況下,SUSE Linux 系統的預設 Runlevel 是 Runlevel 5 (含網路和 X 的完整多重使用者模式)。合適的替代方法可能是 Runlevel 3 (含網路的完整多重使用者模式)。

您可以在此 YaST 對話方塊中選取其中一個 Runlevel 選項 (如表格 8.1, "可用的 Runlevel"所列) 做為新的預設值。還可使用此視窗中的表格,啟用或停用個別服務和精靈。表格會列示可用的服務和精靈,顯示目前在您的系統上它們是否啟用,如果啟用,是哪一個 runlevel。使用滑鼠選取其中一列後,按一下代表 Runlevel 的核取方塊 (B012356S) 來定義 Runlevel,以便在該處執行選取的服務或精靈。Runlevel 4 一開始並未定義,以便建立自訂 runlevel。表格概觀的正下方,提供目前所選服務或精靈的簡要說明。

使用 啟動、停止或重新整理,決定是否啟動服務。重新整理狀態 檢查目前狀態。您可以使用 設定或重設 來做選擇,將您的變更套用至系統,或復原啟動 runlevel 編輯器之前的設定。選取完成,就會將變更的設定儲存至磁碟。

[Warning]錯誤的 Runlevel 設定可能會造成系統損害

錯誤的 Runlevel 設定可能會造成系統無法使用。在您套用變更之前,請務必確定您知道它們的後果。