systemd介绍
systemd是一個(gè) Linux 系統(tǒng)基礎(chǔ)組件的集合,提供了一個(gè)系統(tǒng)和服務(wù)管理器,運(yùn)行為 PID 1 并負(fù)責(zé)啟動(dòng)其它程序。功能包括:支持并行化任務(wù);同時(shí)采用 socket 式與 D-Bus 總線式激活服務(wù);按需啟動(dòng)守護(hù)進(jìn)程(daemon);利用 Linux 的 cgroups 監(jiān)視進(jìn)程;支持快照和系統(tǒng)恢復(fù);維護(hù)掛載點(diǎn)和自動(dòng)掛載點(diǎn);各服務(wù)間基于依賴關(guān)系進(jìn)行精密控制。systemd 支持 SysV 和 LSB 初始腳本,可以替代 sysvinit。除此之外,功能還包括日志進(jìn)程、控制基礎(chǔ)系統(tǒng)配置,維護(hù)登陸用戶列表以及系統(tǒng)賬戶、運(yùn)行時(shí)目錄和設(shè)置,可以運(yùn)行容器和虛擬機(jī),可以簡單的管理網(wǎng)絡(luò)配置、網(wǎng)絡(luò)時(shí)間同步、日志轉(zhuǎn)發(fā)和名稱解析等。
1. 介紹
systemd 是 linux 系統(tǒng)中最新的初始化系統(tǒng)(init),它主要的設(shè)計(jì)目標(biāo)是克服 sysvinit 固有的缺點(diǎn),提高系統(tǒng)的啟動(dòng)速度。systemd 和 ubuntu 的 upstart 是競爭對(duì)手,但是時(shí)至今日 ubuntu 也采用了 systemd,所以 systemd 在競爭中勝出,大有一統(tǒng)天下的趨勢。其實(shí),systemd 的很多概念都來源于蘋果 Mac OS 操作系統(tǒng)上的 launchd。
systemd 的優(yōu)點(diǎn)是功能強(qiáng)大,使用方便,缺點(diǎn)是體系龐大,非常復(fù)雜,下圖展示了 systemd 的架構(gòu)(此圖來自互聯(lián)網(wǎng)):
systemd 能夠在與 upstart 的競爭中勝出自然有很多過人之處,接下來讓我們介紹一些 systemd 的主要優(yōu)點(diǎn)。
1.1. 兼容性
systemd 提供了和 sysvinit 兼容的特性。系統(tǒng)中已經(jīng)存在的服務(wù)和進(jìn)程無需修改。這降低了系統(tǒng)向 systemd 遷移的成本,使得 systemd 替換現(xiàn)有初始化系統(tǒng)成為可能。
1.2. 啟動(dòng)速度
systemd 提供了比?upstart?更激進(jìn)的并行啟動(dòng)能力,采用了 socket / D-Bus activation 等技術(shù)啟動(dòng)服務(wù)。一個(gè)顯而易見的結(jié)果就是:更快的啟動(dòng)速度。為了減少系統(tǒng)啟動(dòng)時(shí)間,systemd 的目標(biāo)是:
- 盡可能啟動(dòng)更少的進(jìn)程
- 盡可能將更多進(jìn)程并行啟動(dòng)
同樣地,upstart?也試圖實(shí)現(xiàn)這兩個(gè)目標(biāo)。下圖展示了?upstart?相對(duì)于 sysvinit 在并發(fā)啟動(dòng)這個(gè)方面的改進(jìn)(此圖來自互聯(lián)網(wǎng)):
upstart 增加了系統(tǒng)啟動(dòng)的并行性,從而提高了系統(tǒng)啟動(dòng)速度。但是在?upstart?中,有依賴關(guān)系的服務(wù)還是必須先后啟動(dòng)。比如任務(wù) A,B,(C,D)因?yàn)榇嬖谝蕾囮P(guān)系,所以在這個(gè)局部,還是串行執(zhí)行。
systemd 能夠更進(jìn)一步提高并發(fā)性,即便對(duì)于那些?upstart?認(rèn)為存在相互依賴而必須串行的服務(wù),比如 Avahi 和 D-Bus 也可以并發(fā)啟動(dòng)。從而實(shí)現(xiàn)如下圖所示的并發(fā)啟動(dòng)過程(此圖來自互聯(lián)網(wǎng)):
在 systemd 中,所有的任務(wù)都同時(shí)并發(fā)執(zhí)行,總的啟動(dòng)時(shí)間被進(jìn)一步降低為 T1。可見 systemd 比?upstart?更進(jìn)一步提高了并行啟動(dòng)能力,極大地加速了系統(tǒng)啟動(dòng)時(shí)間。
1.3. systemd 提供按需啟動(dòng)能力
當(dāng) sysvinit 系統(tǒng)初始化的時(shí)候,它會(huì)將所有可能用到的后臺(tái)服務(wù)進(jìn)程全部啟動(dòng)運(yùn)行。并且系統(tǒng)必須等待所有的服務(wù)都啟動(dòng)就緒之后,才允許用戶登錄。這種做法有兩個(gè)缺點(diǎn):首先是啟動(dòng)時(shí)間過長,其次是系統(tǒng)資源浪費(fèi)。
某些服務(wù)很可能在很長一段時(shí)間內(nèi),甚至整個(gè)服務(wù)器運(yùn)行期間都沒有被使用過。比如 CUPS,打印服務(wù)在多數(shù)服務(wù)器上很少被真正使用到。您可能沒有想到,在很多服務(wù)器上 SSHD 也是很少被真正訪問到的。花費(fèi)在啟動(dòng)這些服務(wù)上的時(shí)間是不必要的;同樣,花費(fèi)在這些服務(wù)上的系統(tǒng)資源也是一種浪費(fèi)。
systemd 可以提供按需啟動(dòng)的能力,只有在某個(gè)服務(wù)被真正請(qǐng)求的時(shí)候才啟動(dòng)它。當(dāng)該服務(wù)結(jié)束,systemd 可以關(guān)閉它,等待下次需要時(shí)再次啟動(dòng)它。
這有點(diǎn)類似于以前系統(tǒng)中的 inetd,并且有很多文章介紹如何把過去 inetd 管理的服務(wù)遷移到 systemd。
1.4. 采用 linux 的 cgroups 跟蹤和管理進(jìn)程的生命周期
systemd 利用了 Linux 內(nèi)核的特性即 cgroups 來完成跟蹤的任務(wù)。當(dāng)停止服務(wù)時(shí),通過查詢?cgroups?,systemd 可以確保找到所有的相關(guān)進(jìn)程,從而干凈地停止服務(wù)。
cgroups?已經(jīng)出現(xiàn)了很久,它主要用來實(shí)現(xiàn)系統(tǒng)資源配額管理。cgroups?提供了類似文件系統(tǒng)的接口,使用方便。當(dāng)進(jìn)程創(chuàng)建子進(jìn)程時(shí),子進(jìn)程會(huì)繼承父進(jìn)程的?cgroups?。因此無論服務(wù)如何啟動(dòng)新的子進(jìn)程,所有的這些相關(guān)進(jìn)程都會(huì)屬于同一個(gè)?cgroups?,systemd 只需要簡單地遍歷指定的?cgroups?即可正確地找到所有的相關(guān)進(jìn)程,將它們一一停止即可。
1.5. 啟動(dòng)掛載點(diǎn)和自動(dòng)掛載的管理
傳統(tǒng)的 linux 系統(tǒng)中,用戶可以用 /etc/fstab 文件來維護(hù)固定的文件系統(tǒng)掛載點(diǎn)。這些掛載點(diǎn)在系統(tǒng)啟動(dòng)過程中被自動(dòng)掛載,一旦啟動(dòng)過程結(jié)束,這些掛載點(diǎn)就會(huì)確保存在。這些掛載點(diǎn)都是對(duì)系統(tǒng)運(yùn)行至關(guān)重要的文件系統(tǒng),比如 HOME 目錄。和 sysvinit 一樣,Systemd 管理這些掛載點(diǎn),以便能夠在系統(tǒng)啟動(dòng)時(shí)自動(dòng)掛載它們。systemd 還兼容 /etc/fstab 文件,您可以繼續(xù)使用該文件管理掛載點(diǎn)。
有時(shí)候用戶還需要?jiǎng)討B(tài)掛載點(diǎn),比如打算訪問 DVD 或者 NFS 共享的內(nèi)容時(shí),才臨時(shí)執(zhí)行掛載以便訪問其中的內(nèi)容,而不訪問光盤時(shí)該掛載點(diǎn)被取消(umount),以便節(jié)約資源。傳統(tǒng)地,人們依賴 autofs 服務(wù)來實(shí)現(xiàn)這種功能。
systemd 內(nèi)建了自動(dòng)掛載服務(wù),無需另外安裝 autofs 服務(wù),可以直接使用 systemd 提供的自動(dòng)掛載管理能力來實(shí)現(xiàn) autofs 的功能。
1.6. 實(shí)現(xiàn)事務(wù)性依賴關(guān)系管理
系統(tǒng)啟動(dòng)過程是由很多的獨(dú)立工作共同組成的,這些工作之間可能存在依賴關(guān)系,比如掛載一個(gè) NFS 文件系統(tǒng)必須依賴網(wǎng)絡(luò)能夠正常工作。systemd 雖然能夠最大限度地并發(fā)執(zhí)行很多有依賴關(guān)系的工作,但是類似"掛載 NFS"和"啟動(dòng)網(wǎng)絡(luò)"這樣的工作還是存在天生的先后依賴關(guān)系,無法并發(fā)執(zhí)行。對(duì)于這些任務(wù),systemd 維護(hù)一個(gè)"事務(wù)一致性"的概念,保證所有相關(guān)的服務(wù)都可以正常啟動(dòng)而不會(huì)出現(xiàn)互相依賴,以至于死鎖的情況。
1.7. 日志服務(wù)
systemd 自帶日志服務(wù) journald,該日志服務(wù)的設(shè)計(jì)初衷是克服現(xiàn)有的 syslog 服務(wù)的缺點(diǎn)。比如:
- syslog 不安全,消息的內(nèi)容無法驗(yàn)證。每一個(gè)本地進(jìn)程都可以聲稱自己是 Apache PID 4711,而 syslog 也就相信并保存到磁盤上。
- 數(shù)據(jù)沒有嚴(yán)格的格式,非常隨意。自動(dòng)化的日志分析器需要分析人類語言字符串來識(shí)別消息。一方面此類分析困難低效;此外日志格式的變化會(huì)導(dǎo)致分析代碼需要更新甚至重寫。
systemd journal 用二進(jìn)制格式保存所有日志信息,用戶使用 journalctl 命令來查看日志信息。無需自己編寫復(fù)雜脆弱的字符串分析處理程序。
1.8. systemd journal 的優(yōu)點(diǎn)如下
簡單性:代碼少,依賴少,抽象開銷最小。
零維護(hù):日志是除錯(cuò)和監(jiān)控系統(tǒng)的核心功能,因此它自己不能再產(chǎn)生問題。舉例說,自動(dòng)管理磁盤空間,避免由于日志的不斷產(chǎn)生而將磁盤空間耗盡。
移植性:日志文件應(yīng)該在所有類型的 Linux 系統(tǒng)上可用,無論它使用的何種 CPU 或者字節(jié)序。
性能:添加和瀏覽日志非常快。
最小資源占用:日志數(shù)據(jù)文件需要較小。
統(tǒng)一化:各種不同的日志存儲(chǔ)技術(shù)應(yīng)該統(tǒng)一起來,將所有的可記錄事件保存在同一個(gè)數(shù)據(jù)存儲(chǔ)中。所以日志內(nèi)容的全局上下文都會(huì)被保存并且可供日后查詢。例如一條固件記錄后通常會(huì)跟隨一條內(nèi)核記錄,最終還會(huì)有一條用戶態(tài)記錄。重要的是當(dāng)保存到硬盤上時(shí)這三者之間的關(guān)系不會(huì)丟失。syslog 將不同的信息保存到不同的文件中,分析的時(shí)候很難確定哪些條目是相關(guān)的。
擴(kuò)展性:日志的適用范圍很廣,從嵌入式設(shè)備到超級(jí)計(jì)算機(jī)集群都可以滿足需求。
安全性:日志文件是可以驗(yàn)證的,讓無法檢測的修改不再可能。
2. 命令
systemd 并不是一個(gè)命令,而是一組命令,涉及到系統(tǒng)管理的方方面面,但最常用的命令是systemctl。
2.1. systemctl
systemctl是 Systemd 的主命令,用于管理系統(tǒng)。systemctl命令主要有兩大功能:控制systemd系統(tǒng)和管理系統(tǒng)上運(yùn)行的服務(wù)
# 重啟系統(tǒng) $ sudo systemctl reboot# 關(guān)閉系統(tǒng),切斷電源 $ sudo systemctl poweroff# CPU停止工作 $ sudo systemctl halt# 暫停系統(tǒng) $ sudo systemctl suspend# 讓系統(tǒng)進(jìn)入冬眠狀態(tài) $ sudo systemctl hibernate# 讓系統(tǒng)進(jìn)入交互式休眠狀態(tài) $ sudo systemctl hybrid-sleep# 啟動(dòng)進(jìn)入救援狀態(tài)(單用戶狀態(tài)) $ sudo systemctl rescue2.2. systemd-analyze
systemd-analyze命令用于查看啟動(dòng)耗時(shí)。
# 查看啟動(dòng)耗時(shí) $ systemd-analyze # 查看每個(gè)服務(wù)的啟動(dòng)耗時(shí) $ systemd-analyze blame# 顯示瀑布狀的啟動(dòng)過程流 $ systemd-analyze critical-chain# 顯示指定服務(wù)的啟動(dòng)流 $ systemd-analyze critical-chain atd.service2.3. hostnamectl
hostnamectl命令用于查看當(dāng)前主機(jī)的信息。
# 顯示當(dāng)前主機(jī)的信息 $ hostnamectl# 設(shè)置主機(jī)名。 $ sudo hostnamectl set-hostname rhel72.4. localectl
localectl命令用于查看本地化設(shè)置。
# 查看本地化設(shè)置 $ localectl# 設(shè)置本地化參數(shù)。 $ sudo localectl set-locale LANG=en_GB.utf8 $ sudo localectl set-keymap en_GB2.5. timedatectl
timedatectl命令用于查看當(dāng)前時(shí)區(qū)設(shè)置。
# 查看當(dāng)前時(shí)區(qū)設(shè)置 $ timedatectl# 顯示所有可用的時(shí)區(qū) $ timedatectl list-timezones # 設(shè)置當(dāng)前時(shí)區(qū) $ sudo timedatectl set-timezone America/New_York $ sudo timedatectl set-time YYYY-MM-DD $ sudo timedatectl set-time HH:MM:SS2.6. loginctl
loginctl命令用于查看當(dāng)前登錄的用戶。
# 列出當(dāng)前session $ loginctl list-sessions# 列出當(dāng)前登錄用戶 $ loginctl list-users# 列出顯示指定用戶的信息 $ loginctl show-user ruanyf3. Unit
3.1. 含義
Systemd 可以管理所有系統(tǒng)資源。不同的資源統(tǒng)稱為 Unit(單位)。
Unit 一共分成12種。
Service unit:系統(tǒng)服務(wù)
Target unit:多個(gè) Unit 構(gòu)成的一個(gè)組
Device Unit:硬件設(shè)備
Mount Unit:文件系統(tǒng)的掛載點(diǎn)
Automount Unit:自動(dòng)掛載點(diǎn)
Path Unit:文件或路徑
Scope Unit:不是由 Systemd 啟動(dòng)的外部進(jìn)程
Slice Unit:進(jìn)程組
Snapshot Unit:Systemd 快照,可以切回某個(gè)快照
Socket Unit:進(jìn)程間通信的 socket
Swap Unit:swap 文件
Timer Unit:定時(shí)器
systemctl list-units命令可以查看當(dāng)前系統(tǒng)的所有 Unit 。?
# 列出正在運(yùn)行的 Unit $ systemctl list-units# 列出所有Unit,包括沒有找到配置文件的或者啟動(dòng)失敗的 $ systemctl list-units --all# 列出所有沒有運(yùn)行的 Unit $ systemctl list-units --all --state=inactive# 列出所有加載失敗的 Unit $ systemctl list-units --failed# 列出所有正在運(yùn)行的、類型為 service 的 Unit $ systemctl list-units --type=service3.2. Unit 的狀態(tài)
systemctl status命令用于查看系統(tǒng)狀態(tài)和單個(gè) Unit 的狀態(tài)。
# 顯示系統(tǒng)狀態(tài) $ systemctl status# 顯示單個(gè) Unit 的狀態(tài) $ sysystemctl status bluetooth.service# 顯示遠(yuǎn)程主機(jī)的某個(gè) Unit 的狀態(tài) $ systemctl -H root@rhel7.example.com status httpd.service除了status命令,systemctl還提供了三個(gè)查詢狀態(tài)的簡單方法,主要供腳本內(nèi)部的判斷語句使用。
# 顯示某個(gè) Unit 是否正在運(yùn)行 $ systemctl is-active application.service# 顯示某個(gè) Unit 是否處于啟動(dòng)失敗狀態(tài) $ systemctl is-failed application.service# 顯示某個(gè) Unit 服務(wù)是否建立了啟動(dòng)鏈接 $ systemctl is-enabled application.service3.3 Unit 管理
對(duì)于用戶來說,最常用的是下面這些命令,用于啟動(dòng)和停止 Unit(主要是 service)。
# 立即啟動(dòng)一個(gè)服務(wù) $ sudo systemctl start apache.service# 立即停止一個(gè)服務(wù) $ sudo systemctl stop apache.service# 重啟一個(gè)服務(wù) $ sudo systemctl restart apache.service# 殺死一個(gè)服務(wù)的所有子進(jìn)程 $ sudo systemctl kill apache.service# 重新加載一個(gè)服務(wù)的配置文件 $ sudo systemctl reload apache.service# 重載所有修改過的配置文件 $ sudo systemctl daemon-reload# 顯示某個(gè) Unit 的所有底層參數(shù) $ systemctl show httpd.service# 顯示某個(gè) Unit 的指定屬性的值 $ systemctl show -p CPUShares httpd.service# 設(shè)置某個(gè) Unit 的指定屬性 $ sudo systemctl set-property httpd.service CPUShares=5003.4 依賴關(guān)系
Unit 之間存在依賴關(guān)系:A 依賴于 B,就意味著 Systemd 在啟動(dòng) A 的時(shí)候,同時(shí)會(huì)去啟動(dòng) B。
systemctl list-dependencies命令列出一個(gè) Unit 的所有依賴。
$ systemctl list-dependencies nginx.service上面命令的輸出結(jié)果之中,有些依賴是 Target 類型(詳見下文),默認(rèn)不會(huì)展開顯示。如果要展開 Target,就需要使用--all參數(shù)。
$ systemctl list-dependencies --all nginx.service4. Unit 的配置文件
4.1. 概述
每一個(gè) Unit 都有一個(gè)配置文件,告訴 Systemd 怎么啟動(dòng)這個(gè) Unit 。
Systemd 默認(rèn)從目錄/etc/systemd/system/讀取配置文件。但是,里面存放的大部分文件都是符號(hào)鏈接,指向目錄/usr/lib/systemd/system/,真正的配置文件存放在那個(gè)目錄。
systemctl enable命令用于在上面兩個(gè)目錄之間,建立符號(hào)鏈接關(guān)系。
$ sudo systemctl enable clamd@scan.service # 等同于 $ sudo ln -s '/usr/lib/systemd/system/clamd@scan.service' '/etc/systemd/system/multi-user.target.wants/clamd@scan.service'如果配置文件里面設(shè)置了開機(jī)啟動(dòng),systemctl enable命令相當(dāng)于激活開機(jī)啟動(dòng)。
與之對(duì)應(yīng)的,systemctl disable命令用于在兩個(gè)目錄之間,撤銷符號(hào)鏈接關(guān)系,相當(dāng)于撤銷開機(jī)啟動(dòng)。
$ sudo systemctl disable clamd@scan.service配置文件的后綴名,就是該 Unit 的種類,比如sshd.socket。如果省略,Systemd 默認(rèn)后綴名為.service,所以sshd會(huì)被理解成sshd.service。
4.2 配置文件的狀態(tài)
systemctl list-unit-files命令用于列出所有配置文件。
# 列出所有配置文件 $ systemctl list-unit-files# 列出指定類型的配置文件 $ systemctl list-unit-files --type=service這個(gè)命令會(huì)輸出一個(gè)列表。
$ systemctl list-unit-filesUNIT FILE STATEchronyd.service enabledclamd@.service staticclamd@scan.service disabled這個(gè)列表顯示每個(gè)配置文件的狀態(tài),一共有四種。
- enabled:已建立啟動(dòng)鏈接
- disabled:沒建立啟動(dòng)鏈接
- static:該配置文件沒有[Install]部分(無法執(zhí)行),只能作為其他配置文件的依賴
- masked:該配置文件被禁止建立啟動(dòng)鏈接
注意,從配置文件的狀態(tài)無法看出,該 Unit 是否正在運(yùn)行。這必須執(zhí)行前面提到的systemctl status命令。
$ systemctl status bluetooth.service一旦修改配置文件,就要讓 SystemD 重新加載配置文件,然后重新啟動(dòng),否則修改不會(huì)生效。?
$ sudo systemctl daemon-reload $ sudo systemctl restart httpd.service參考文獻(xiàn)
systemd詳解_哪有天生的學(xué)霸,一切都是厚積薄發(fā)的博客-CSDN博客_systemd
systemctl 詳解_Coding<_>的博客-CSDN博客_systemctl?
systemctl命令_別掉頭發(fā)啦的博客-CSDN博客?systemd 介紹_shliang310的博客-CSDN博客_systemd
總結(jié)
- 上一篇: opencv 基于ORB特征点图像拼接
- 下一篇: 【2021四川省赛】E.Don‘t Re