Linux操作系統在嵌入式、移動設備和服務器上取得巨大成功的原因之一是內核、相關服務和應用程序具有相當高的安全性。 但如果
Linux 安全模塊和 SELinux 的背景
安全增強型Linux是一套基於強制和基於角色的訪問模型的規則和訪問機制,旨在保護Linux系統免受潛在威脅,並糾正傳統Unix安全系統自主訪問控制(DAC)的缺點。 該項目起源於美國國家安全局內部,主要由承包商SecureComputingCorporation和MITRE以及多家研究實驗室直接開發。
Linux 安全模塊
Linus Torvalds 對 NSA 的新開發發表了許多評論,以便將它們包含在主線 Linux 內核中。 他描述了一個通用環境,其中包含一組攔截器來控制對象的操作,以及一組內核數據結構中的某些保護字段來存儲相應的屬性。 然後可加載內核模塊可以使用該環境來實現任何所需的安全模型。 LSM於2.6年全面進入Linux內核v2003。
LSM 框架在數據結構中包含保護字段,並在內核代碼的關鍵點調用攔截函數來操作它們並執行訪問控制。 它還添加了註冊安全模塊的功能。 /sys/kernel/security/lsm 接口包含系統上活動模塊的列表。 LSM 掛鉤存儲在按照 CONFIG_LSM 中指定的順序調用的列表中。 有關鉤子的詳細文檔包含在頭文件 include/linux/lsm_hooks.h 中。
LSM子系統使得SELinux與同版本的穩定Linux內核v2.6的完全集成成為可能。 幾乎立即,SELinux 成為安全 Linux 環境的事實標準,並包含在最流行的發行版中:RedHat Enterprise Linux、Fedora、Debian、Ubuntu。
SELinux 術語表
- 身分 — SELinux 用戶與通常的 Unix/Linux 用戶 ID 不同;它們可以共存於同一系統上,但本質上完全不同。 每個標準Linux 帳戶可以對應SELinux 中的一個或多個。 SELinux 身份是整體安全上下文的一部分,它決定您可以或不可以加入哪些域。
- 域名 - 在 SELinux 中,域是主體(即進程)的執行上下文。 域直接決定進程擁有的訪問權限。 域基本上是進程可以執行的操作或進程可以對不同類型執行的操作的列表。 域的一些示例包括用於系統管理的 sysadm_t 和普通的非特權用戶域 user_t。 init系統在init_t域中運行,named進程在named_t域中運行。
- 角色 — 充當域和 SELinux 用戶之間中介的角色。 角色決定用戶可以屬於哪些域以及他們可以訪問哪些類型的對象。 這種訪問控制機制可以防止權限升級攻擊的威脅。 角色被寫入 SELinux 中使用的基於角色的訪問控制 (RBAC) 安全模型中。
- 類型 — 分配給對象並確定誰可以訪問該對象的類型強制列表屬性。 與域定義類似,只不過域適用於進程,而類型適用於目錄、文件、套接字等對象。
- 主體和客體 - 進程是主體並在特定上下文或安全域中運行。 操作系統資源:文件、目錄、套接字等,是被分配某種類型(即隱私級別)的對象。
- SELinux 政策 — SELinux 使用多種策略來保護系統。 SELinux 策略定義用戶對角色、角色對域以及域對類型的訪問。 首先,用戶被授權獲得角色,然後角色被授權訪問域。 最後,域只能訪問某些類型的對象。
LSM 和 SELinux 架構
儘管有這個名稱,LSM 通常並不是可加載的 Linux 模塊。 然而,與 SELinux 一樣,它是直接集成到內核中的。 對 LSM 源代碼的任何更改都需要新的內核編譯。 必須在內核設置中啟用相應的選項,否則引導後LSM代碼將不會被激活。 但即使在這種情況下,也可以通過操作系統引導加載程序選項來啟用它。
LSM檢查堆棧
LSM 在核心內核函數中配備了與檢查相關的鉤子。 LSM 的主要特徵之一是它們是堆疊的。 因此,仍然執行標準檢查,LSM的每一層僅添加額外的控制和控制。 這意味著該禁令無法撤銷。 如圖所示;如果例行 DAC 檢查的結果是失敗,那麼問題甚至不會到達 LSM 掛鉤。
SELinux採用Fluke研究操作系統的Flask安全架構,特別是最小權限原則。 顧名思義,這個概念的本質是僅授予用戶或進程執行預期操作所需的權限。 該原理是使用強制訪問類型來實現的,因此 SELinux 中的訪問控制基於域 => 類型模型。
由於強制訪問類型,SELinux 比 Unix/Linux 操作系統中使用的傳統 DAC 模型具有更強的訪問控制功能。 例如,您可以限制 ftp 服務器連接的網絡端口號、允許寫入和更改某個文件夾中的文件,但不允許刪除它們。
SELinux 的主要組件有:
- 策略執行服務器 — 組織訪問控制的主要機制。
- 系統安全策略數據庫。
- 與 LSM 事件攔截器交互。
- 種子文件系統 - 偽FS,與/proc相同,掛載在/sys/fs/selinux中。 由 Linux 內核在運行時動態填充,並包含包含 SELinux 狀態信息的文件。
- 訪問向量緩存 ——提高生產力的輔助機制。
SELinux 的工作原理
一切都是這樣的。
- 在 SELinux 術語中,某個主體在 DAC 檢查後對對象執行允許的操作,如上圖所示。 該執行操作的請求將發送至 LSM 事件攔截器。
- 從那裡,請求連同主體和客體安全上下文一起被傳遞到 SELinux 抽象和鉤子邏輯模塊,該模塊負責與 LSM 交互。
- 主體訪問客體的決策機構是策略執行服務器,它從 SELinux AnHL 接收數據。
- 為了做出有關訪問或拒絕的決策,策略執行服務器會轉向訪問向量緩存 (AVC) 緩存子系統來獲取最常用的規則。
- 如果在緩存中沒有找到相應規則的解決方案,則將請求傳遞到安全策略數據庫。
- 來自數據庫和 AVC 的搜索結果返回到策略執行服務器。
- 如果找到的策略與請求的操作匹配,則允許該操作。 否則,禁止操作。
管理 SELinux 設置
SELinux 以三種模式之一運行:
- 執行 - 嚴格遵守安全策略。
- 允許 - 允許違反限制;在日誌中做出相應的註釋。
- 已禁用 — 安全策略未生效。
您可以使用以下命令查看 SELinux 處於什麼模式。
[admin@server ~]$ getenforce
Permissive
重啟前更改模式,例如設置為enforcing或1。permissive參數對應數字代碼0。
[admin@server ~]$ setenfoce enforcing
[admin@server ~]$ setenfoce 1 #то же самое
您還可以通過編輯文件來更改模式:
[admin@server ~]$ cat /etc/selinux/config
# This file controls the state of SELinux on the system.
# SELINUX= can take one of these three values:
# enforcing - SELinux security policy is enforced.
# permissive - SELinux prints warnings instead of enforcing.
# disabled - No SELinux policy is loaded.
SELINUX=enforcing
# SELINUXTYPE= can take one of three values:
# targeted - Targeted processes are protected,
# minimum - Modification of targeted policy. Only selected processes are protected.
# mls - Multi Level Security protection.
SELINUXTYPE=目標
與setenfoce的區別在於,當操作系統啟動時,會按照配置文件中SELINUX參數的值設置SELinux模式。 此外,對強制 <=> 禁用的更改只能通過編輯 /etc/selinux/config 文件並在重新引導後生效。
查看簡短的狀態報告:
[admin@server ~]$ sestatus
SELinux status: enabled
SELinuxfs mount: /sys/fs/selinux
SELinux root directory: /etc/selinux
Loaded policy name: targeted
Current mode: permissive
Mode from config file: enforcing
Policy MLS status: enabled
Policy deny_unknown status: allowed
Max kernel policy version: 31
要查看 SELinux 屬性,一些標準實用程序使用 -Z 參數。
[admin@server ~]$ ls -lZ /var/log/httpd/
-rw-r--r--. root root system_u:object_r:httpd_log_t:s0 access_log
-rw-r--r--. root root system_u:object_r:httpd_log_t:s0 access_log-20200920
-rw-r--r--. root root system_u:object_r:httpd_log_t:s0 access_log-20200927
-rw-r--r--. root root system_u:object_r:httpd_log_t:s0 access_log-20201004
-rw-r--r--. root root system_u:object_r:httpd_log_t:s0 access_log-20201011
[admin@server ~]$ ps -u apache -Z
LABEL PID TTY TIME CMD
system_u:system_r:httpd_t:s0 2914 ? 00:00:04 httpd
system_u:system_r:httpd_t:s0 2915 ? 00:00:00 httpd
system_u:system_r:httpd_t:s0 2916 ? 00:00:00 httpd
system_u:system_r:httpd_t:s0 2917 ? 00:00:00 httpd
...
system_u:system_r:httpd_t:s0 2918 ? 00:00:00 httpd
與 ls -l 的正常輸出相比,有幾個附加字段,格式如下:
<user>:<role>:<type>:<level>
最後一個字段表示類似於安全分類的內容,由兩個元素的組合組成:
- s0 - 顯著性,也寫為 lowlevel-highlevel 區間
- c0、c1…c1023 - 類別。
更改訪問配置
使用 semodule 加載、添加和刪除 SELinux 模塊。
[admin@server ~]$ semodule -l |wc -l #список всех модулей
408
[admin@server ~]$ semodule -e abrt #enable - активировать модуль
[admin@server ~]$ semodule -d accountsd #disable - отключить модуль
[admin@server ~]$ semodule -r avahi #remove - удалить модуль
一隊 管理登錄 將 SELinux 用戶連接到操作系統用戶,第二個顯示一個列表。 最後,帶有 -r 開關的最後一個命令刪除 SELinux 用戶到操作系統帳戶的映射。 MLS/MCS 範圍值的語法說明在上一節中。
[admin@server ~]$ semanage login -a -s user_u karol
[admin@server ~]$ semanage login -l
Login Name SELinux User MLS/MCS Range Service
__default__ unconfined_u s0-s0:c0.c1023 *
root unconfined_u s0-s0:c0.c1023 *
system_u system_u s0-s0:c0.c1023 *
[admin@server ~]$ semanage login -d karol
團隊 管理用戶 用於管理 SELinux 用戶和角色之間的映射。
[admin@server ~]$ semanage user -l
Labeling MLS/ MLS/
SELinux User Prefix MCS Level MCS Range SELinux Roles
guest_u user s0 s0 guest_r
staff_u staff s0 s0-s0:c0.c1023 staff_r sysadm_r
...
user_u user s0 s0 user_r
xguest_u user s0 s0 xguest_r
[admin@server ~]$ semanage user -a -R 'staff_r user_r'
[admin@server ~]$ semanage user -d test_u
命令參數:
- - 添加自定義角色映射條目;
- -l 匹配的用戶和角色列表;
- -d 刪除用戶角色映射條目;
- -R 附加到用戶的角色列表;
文件、端口和布爾值
每個 SELinux 模塊都提供一組文件標記規則,但如果需要,您也可以添加自己的規則。 例如,我們希望Web服務器具有/srv/www文件夾的訪問權限。
[admin@server ~]$ semanage fcontext -a -t httpd_sys_content_t "/srv/www(/.*)?
[admin@server ~]$ restorecon -R /srv/www/
第一個命令註冊新的標記規則,第二個命令根據當前規則重置或設置文件類型。
同樣,TCP/UDP 端口的標記方式使得只有適當的服務才能偵聽它們。 例如,為了讓Web服務器監聽8080端口,您需要運行以下命令。
[admin@server ~]$ semanage port -m -t http_port_t -p tcp 8080
許多 SELinux 模塊都具有可以採用布爾值的參數。 使用 getsebool -a 可以查看此類參數的完整列表。 您可以使用setsebool更改布爾值。
[admin@server ~]$ getsebool httpd_enable_cgi
httpd_enable_cgi --> on
[admin@server ~]$ setsebool -P httpd_enable_cgi off
[admin@server ~]$ getsebool httpd_enable_cgi
httpd_enable_homedirs --> off
研討會,訪問 Pgadmin-web 界面
讓我們看一個實際的例子:我們在 RHEL 7.6 上安裝了 pgadmin4-web 來管理 PostgreSQL 數據庫。 我們走了一點
我們從典型的嫌疑人開始,檢查 /var/log/httpd/error_log。 那裡有一些有趣的條目。
[timestamp] [core:notice] [pid 23689] SELinux policy enabled; httpd running as context system_u:system_r:httpd_t:s0
...
[timestamp] [wsgi:error] [pid 23690] [Errno 13] Permission denied: '/var/lib/pgadmin'
[timestamp] [wsgi:error] [pid 23690]
[timestamp] [wsgi:error] [pid 23690] HINT : You may need to manually set the permissions on
[timestamp] [wsgi:error] [pid 23690] /var/lib/pgadmin to allow apache to write to it.
此時,大多數 Linux 管理員都會強烈地想要運行 setencorce 0,然後就結束了。 坦白說,我第一次就是這麼做的。 這當然也是一種出路,但遠非最好。
儘管設計繁瑣,SELinux 仍然是用戶友好的。 只需安裝setroubleshoot包並查看系統日誌即可。
[admin@server ~]$ yum install setroubleshoot
[admin@server ~]$ journalctl -b -0
[admin@server ~]$ service restart auditd
請注意,儘管操作系統中存在 systemd,但審計服務必須以這種方式重新啟動,而不是使用 systemctl。 在系統日誌中 將會被指示 不僅包括阻塞的事實,還包括阻塞的原因和原因 克服禁令的方法.
我們執行這些命令:
[admin@server ~]$ setsebool -P httpd_can_network_connect 1
[admin@server ~]$ setsebool -P httpd_can_network_connect_db 1
我們檢查對 pgadmin4-web 網頁的訪問,一切正常。
來源: www.habr.com