跳转到内容

为应对本站因各种原因无法访问,建议用户安装 arch-wiki-docs-zh-cnCNRepo 或者 arch-wiki-docs-zh-twCNRepo 离线文档包备用,也可尝试使用经由Cloudflare CDN的替代版本aw.lilydjwg.me

SELinux

来自 Arch Linux 中文维基

安全增强型 Linux (Security-Enhanced Linux, SELinux)(又称安全增强式 Linux)是一项 Linux 特性,通过在 Linux 内核中使用Linux 安全模块(Linux Security Modules, LSM)提供多种安全策略,其中包括美国国防部风格的强制访问控制(Mandatory Access Control, MAC)。SELinux 并不是一个 Linux 发行版,而是一套可以应用于Linux和BSD等类 Unix 操作系统的修改补丁集。

在 Linux 发行版下运行 SELinux 需要满足三个条件:开启了 SELinux 支持的内核、SELinux 用户空间工具与库,以及 SELinux 策略(通常基于参考策略(Reference Policy))。一些常见的 Linux 程序还需要应用补丁或在编译时开启 SELinux 特性。

在 Arch Linux 中的状态

[编辑 | 编辑源代码]

SELinux 并不是 Arch Linux 官方支持的功能(参见[1][2])。非官方支持的状态如下:

名称 状态 获取渠道
SELinux 启用的内核 适用于所有官方支持的内核 自 4.18.8 版本以来已在官方仓库中提供
SELinux 用户空间工具和库 已在 AUR 中提供:https://aur.archlinux.org/packages/?O=0&K=selinux 相关开发工作正在 https://github.com/archlinuxhardened/selinux 进行
SELinux 策略 正在开发中,以 Reference Policy 作为基础 上游:https://github.com/SELinuxProject/refpolicy (自 20170805 版本以来,该策略已集成了对 systemd 和单一/usr/bin目录的支持)

与官方核心包相比,以下是 AUR 中的一些包的变更摘要:

名称 状态与说明
linux, linux-lts, linux-zen, linux-hardened 需要设置 lsm= 参数
coreutils 需要使用 --with-selinux 选项重新构建以链接 libselinux
cronie 需要使用 --with-selinux 选项重新构建
dbus 需要使用 --enable-libaudit--enable-selinux 选项重新构建
findutils 需要使用 libselinux 并重新构建以启用 SELinux 特定选项
iproute2 需要使用 --with-selinux 选项重新构建
logrotate 需要使用 --with-selinux 选项重新构建
openssh 需要使用 --with-selinux 选项重新构建
pam 对于 Linux-PAM,需要使用 --enable-selinux 编译选项重新构建;对于 pam_unix2 ,需要应用一个补丁,该补丁仅用于删除一个在近版本的 libselinux 中已实现的重复函数
pambase 修改配置,将 pam_selinux.so 添加到 /etc/pam.d/system-login
psmisc 需要使用 --with-selinux 选项重新构建
shadow 需要使用 --with-selinux 选项重新构建
sudo 需要使用 --with-selinux 选项重新构建
systemd 需要使用 --enable-audit--enable-selinux 选项重新构建
util-linux 需要使用 --with-selinux 选项重新构建

所有其他 SELinux 相关软件包均可直接引入,无需修改,且无安全风险。

概念:强制访问控制

[编辑 | 编辑源代码]

这一章节正在考虑移除。

原因: 通用概念科普内容,理应在主条目安全#强制访问控制或通用百科zhwp:强制访问控制中展开 (在 Talk:SELinux 讨论)
注意:本节面向初学者。如果您已了解 SELinux 的功能及其工作原理,可以跳过直接进入#安装部分

在启用 SELinux 之前,了解它的功能很有必要。简单直接的来说,SELinux在Linux上执行强制访问控制(MAC)。与之相对,传统的用户/组/rwx权限属于自主访问控制(DAC)。MAC与DAC的不同之处在于:安全策略和执行是完全分离的

sudo命令为例:在执行DAC时,sudo允许临时提权至root,从而赋予所产生的进程无限制的全系统访问权限。然而,在使用MAC时,如果安全管理员规定该进程只能访问某个文件集合,那么无论使用何种提权手段,除非更改安全策略本身,否则该进程仍将被限制在该文件范围内。因此,如果在运行SELinux的机器上尝试使用sudo让进程访问未授权的文件,该操作将会失败。

另一个例子是传统的(-rwxr-xr-x)类型权限。在DAC机制下,这些权限是用户可修改的。但在MAC下,安全管理员可以选择“冻结”特定文件的权限,除非更改相关策略,否则任何用户都无法修改这些权限。

正因如此,对于可能被攻破的进程(如Web服务器等)非常有用。如果使用DAC,一旦具备提权能力的程序被攻破,极有可能会对系统造成严重破坏。

欲了解更多信息,请访问维基百科: 强制访问控制

安装 SELinux

[编辑 | 编辑源代码]

软件包说明

[编辑 | 编辑源代码]

所有 SELinux 相关软件包都属于AUR中的selinux包组手动安装这些包之前,请先阅读#安装章节

支持 SELinux 的系统工具

[编辑 | 编辑源代码]
coreutils-selinuxAUR
经过修改的 coreutils 软件包,编译时已启用 SELinux 支持,它会替换coreutils软件包。
cronie-selinuxAUR
由 Fedora维护的 Vixie cron 派生版本,已启用 SELinux 支持。它会替换cronie软件包。
dbus-selinuxAUR
支持 SELinux 的 D-Bus 版本. 它会替换 dbus 软件包。
findutils-selinuxAUR
经过补丁修改并开启了 SELinux 支持的 findutils 软件包,使得按特定安全上下文搜索文件成为可能。它会替换 findutils 软件包。
iproute2-selinuxAUR
开启了 SELinux 支持的 iproute2 软件包;例如,它为ss命令增加了-Z选项。它会替换iproute2软件包
logrotate-selinuxAUR
开启了 SELinux 支持的 logrotate 软件包,它会替换logrotate软件包
openssh-selinuxAUR
开启了 SELinux 支持的OpenSSH软件包。它会替换openssh软件包
pam-selinuxAURpambase-selinuxAUR
包含pam_selinux.so的PAM软件包及其基础(base)软件包。它们分别替换pampambase软件包
psmisc-selinuxAUR
开启了 SELinux 支持的 psmisc 软件包;例如,它为killall增加了-Z选项。它会替换psmisc软件包
shadow-selinuxAUR
开启了 SELinux 支持的 shadow 软件包;包含修改后的 /etc/pam.d/login 文件,用于在用户登录后设置正确的安全上下文。它会替换 shadow 软件包。
sudo-selinuxAUR
经过修改且开启了 SELinux 支持的 sudo 软件包,可正确设置安全上下文。它会替换 sudo 软件包。
systemd-selinuxAUR
支持 SELinux 的 systemd 版本。它会替换 systemd 软件包。
util-linux-selinuxAUR
经过修改的 util-linux 软件包,编译时已启用 SELinux 支持。它会替换 util-linux 软件包。

SELinux 用户空间实用程序

[编辑 | 编辑源代码]
checkpolicyAUR
用于构建 SELinux 策略的工具。
mcstransAUR
供 libselinux 使用,用于转换 MCS 标签的守护进程。
libselinuxAUR
为支持安全感知的应用程序提供的库。现已包含 semanagesetools 所需的 Python 绑定。
libsemanageAUR
用于策略管理的库。现已包含 semanagesetools 所需的 Python 绑定。
libsepolAUR
用于操作二进制策略的库。
policycoreutilsAUR
SELinux 核心工具,例如 newrolesetfiles 等。
restorecondAUR
用于维护部分文件标签的守护进程。
secilcAUR
针对以 CIL(通用中间语言)编写的 SELinux 策略的编译器。
selinux-dbus-configAUR
允许管理 SELinux 配置的 DBus 服务。
selinux-guiAUR
SELinux 图形界面工具(system-config-selinux)。
selinux-pythonAUR
SELinux Python 工具与库(包含 semanagesepolgensepolicy 等)。
selinux-sandboxAUR
SELinux 沙箱工具。
semodule-utilsAUR
在构建策略时用于处理 SELinux 模块的工具。

SELinux 策略相关软件包

[编辑 | 编辑源代码]
selinux-refpolicy-srcAUR
参考策略(Reference Policy)的源码。
selinux-refpolicy-gitAUR
参考策略的 Git 主分支版本 (https://github.com/SELinuxProject/refpolicy) ,针对 Arch Linux的具体配置进行了构建,但是与 Arch Linux 软件包兼容并不完美。
selinux-refpolicy-archAUR
预编译的模块化参考策略,包含头文件和文档,但不含源码。该版本包含了正在开发中的 Arch Linux Refpolicy 补丁,用以修复路径标签和 systemd 支持的相关问题;在selinux-refpolicy-archAUR 中包含这些补丁,主要是为了在 Refpolicy 正式版发布间隙进行及时的滚动更新。

其他 SELinux工具

[编辑 | 编辑源代码]
setoolsAUR
用于管理SELinux的命令行和图形界面工具。
selinux-alpm-hookAUR
pacman 钩子;在安装和更新软件包时,根据 SELinux 策略自动为文件标记标签

安装所需的 SELinux 软件包共有三种方法:

通过 Github 上的二进制软件包

[编辑 | 编辑源代码]

所有软件包均可通过selinux非官方仓库获取。在系统安装阶段的arch-bootstrap阶段,可以使用base-selinux替换base软件包。

警告:目前该仓库不提供软件包签名,这意味着 pacman 将无法验证下载的二进制文件。这存在风险;慎重执行。

通过 Github 上的构建脚本

[编辑 | 编辑源代码]

该仓库还包含一个名为build_and_install_all.sh的脚本,它会按照所需顺序构建并安装(或更新)所有软件包。以下是在用户终端中使用该脚本安装所有软件包的实例(包含下载用于验证软件包源码的GPG密钥):

$ git clone https://github.com/archlinuxhardened/selinux.git
$ cd selinux
$ ./recv_gpg_keys.sh
$ ./build_and_install_all.sh

在运行脚本之前可以修改build_and_install_all.sh的内容;例如,若已经拥有支持 SELinux 的内核,则可以调整相关内容。

通过 AUR

[编辑 | 编辑源代码]

完成上述所有步骤后,可以安装支持 SELinux 的内核(如linux)以及相关策略(如selinux-refpolicy-archAURselinux-refpolicy-gitAUR)。

启用 SELinux LSM

[编辑 | 编辑源代码]

若要在每次启动时默认启用 SELinux 作为安全模型,需设置以下内核参数

lsm=landlock,lockdown,yama,integrity,selinux,bpf

注意:内核参数lsm=用于设置 Linux 安全模块的初始化顺序。可以通过zgrep CONFIG_LSM= /proc/config.gz查看内核配置的lsm=默认值,通过cat /sys/kernel/security/lsm查看当前运行时的值。
  • 确保selinux是列表中的第一个“主要(major)”模块。[1]有效值及其顺序的实例可以在security/Kconfig中找到。
  • capability应当从lsm=参数中省略,因为它总会自动隐式被包含。

自定义内核

[编辑 | 编辑源代码]

编译内核时,必须至少设置以下选项:

CONFIG_SECURITY_SELINUX=y

CONFIG_AUDIT=y

若需默认启用 SELinux 安全模型,从而省去手动设置内核参数的麻烦,需额外设置CONFIG_LSM选项,并将selinux指定为列表中第一个“主要(major)”模块:

CONFIG_LSM="landlock,lockdown,yama,integrity,selinux,bpf"

检查 PAM 配置

[编辑 | 编辑源代码]

正确配置PAM对于在登录状态后获得正确的安全上下文至关重要。检查/etc/pam.d/system-login文件中是否存在以下行:

# pam_selinux.so close 应当是会话(session)规则中的第一条
session         required        pam_selinux.so close
# pam_selinux.so open 之后应当只跟随需要在用户上下文中执行的会话(session)
session         required        pam_selinux.so open

安装策略

[编辑 | 编辑源代码]
警告:SELinuxProject提供的参考策略 (Reference Policy) 对 Arch Linux 的支持并不理想。大多数提交补丁以改进策略的人使用的是其他发行版(如 Debian、Gentoo、RHEL等),因此该策略与 Arch Linux 软件包的兼容并不完美(例如,策略可能不支持程序的最前沿特性),建议使用selinux-refpolicy-archAUR

策略是 SELinux 的支柱,决定了系统的行为,目前 AUR 中唯一可用的策略是参考策略(Reference Policy)。为了安装它,应采用以下方法:

使用 AUR 软件包

[编辑 | 编辑源代码]

这是最简单且快捷的方法。安装selinux-refpolicy-archAURselinux-refpolicy-gitAUR,该软件包会自动处理编译和基础配置。

手动安装

[编辑 | 编辑源代码]

需对策略源码进行深度定制时使用,可以通过安装selinux-refpolicy-srcAUR软件包获取,也可以从这里下载最新发行版本

# make bare
# make conf
# make install

上述命令将按原样安装参考策略。了解如何编写 SELinux 策略的用户可以在运行命令前根据喜好自行调整。编译过程需要一段时间,且会占满系统的一个 CPU 核心,这属于正常现象,无需担心。等待命令运行完成即可。

运行以下命令加载参考策略:

# make load

然后创建内容如下的/etc/selinux/config文件(仅当使用上述默认设置时才有效;若更改了策略名称,则需要对文件进行相应调整):

/etc/selinux/config
# 此文件控制系统上 SELinux 的状态。
# SELINUX= 可以取以下三个值之一:
#       enforcing - 强制执行 SELinux 安全策略。
#                   若 SELinux 已按预期配置完毕并且系统已经准备好部署,请设置此值。
#       permissive - SELinux 仅打印警告而非强制阻断.
#                    在部署前使用此模式来自定义 SELinux 策略和布尔值。
#       disabled - 不加载 SELinux 策略。
#                  不推荐此设置,可能导致文件标签(Labeling)问题
SELINUX=permissive
# SELINUXTYPE= 指定要使用的 SELinux 策略名称。
# 当前选项为:
#       refpolicy(原生参考策略)
#       <自定义策略> - 将<自定义策略>替换为需加载的任何自定义策略名称
SELINUXTYPE=refpolicy

现在可以重启系统了,重启系统后运行以下命令:

# restorecon -r /

以为文件系统标记标签。

接着,创建一个名为requiredmod.te的文件,内容如下

requiredmod.te
module requiredmod 1.0;

require {
        type devpts_t;
        type kernel_t;
        type device_t;
        type var_run_t;
        type udev_t;
        type hugetlbfs_t;
        type udev_tbl_t;
        type tmpfs_t;
        class sock_file write;
        class unix_stream_socket { read write ioctl };
        class capability2 block_suspend;
        class dir { write add_name };
        class filesystem associate;
}

#============= devpts_t ==============
allow devpts_t device_t:filesystem associate;

#============= hugetlbfs_t ==============
allow hugetlbfs_t device_t:filesystem associate;

#============= kernel_t ==============
allow kernel_t self:capability2 block_suspend;

#============= tmpfs_t ==============
allow tmpfs_t device_t:filesystem associate;

#============= udev_t ==============
allow udev_t kernel_t:unix_stream_socket { read write ioctl };
allow udev_t udev_tbl_t:dir { write add_name };
allow udev_t var_run_t:sock_file write;
警告:以下步骤是为了解决 Refpolicy 在 Arch Linux 上的兼容性报错,若系统正常且没有相关审计错误,可以跳过此步骤

接着运行以下命令:

# checkmodule -m -o requiredmod.mod requiredmod.te
# semodule_package -o requiredmod.pp -m requiredmod.mod
# semodule -i requiredmod.pp

这样做是为了消除/var/log/audit/audit.log中一些在参考策略(Reference Policy)里处理起来非常麻烦的干扰信息。这是一个非常“丑陋”的临时方案(Ugly hack);必须明确指出,这样安装策略仅仅是为了修补参考策略,从而掩盖因标签(Labeling)错误产生的影响。

在 Vagrant 虚拟机中进行测试

[编辑 | 编辑源代码]

可以使用Vagrant来配置一个预装并配置好 SELinux 的Arch Linux 虚拟机。这是一种在不修改当前系统的情况下,测试运行 SELinux 的 Arch Linux 系统的便捷方法。可通过以下命令实现:

$ git clone https://github.com/archlinuxhardened/selinux.git
$ cd selinux/_vagrant
$ vagrant up
$ vagrant ssh

安装后的后续步骤

[编辑 | 编辑源代码]

可以使用sestatus命令来检查 SELinux 是否正在正常运行。应看到类似如下的输出:

SELinux status:                 enabled
SELinuxfs mount:                /sys/fs/selinux
SELinux root directory:         /etc/selinux
Loaded policy name:             refpolicy
Current mode:                   permissive
Mode from config file:          permissive
Policy MLS status:              disabled
Policy deny_unknown status:     allowed
Max kernel policy version:      28

为了保证正确的安全上下文,可以启用restorecond.service服务。

若要在不重启系统的情况下切换到强制(enforcing)模式,可以使用以下命令:

# echo 1 > /sys/fs/selinux/enforce

交换文件

[编辑 | 编辑源代码]

若使用交换文件(swap file)而非交换分区(swap partition),需运行以下命令以设置正确的安全上下文:

# semanage fcontext -a -t swapfile_t "/path/to/swapfile"
# restorecon /path/to/swapfile

使用 SELinux

[编辑 | 编辑源代码]

SELinux 定义安全性的机制与传统的 Unix 访问控制(DAC)不同。理解它的最佳方式是通过实例。例如,Apache 主页文件的 SELinux 安全上下文如下所示:

$ ls -lZ /var/www/html/index.html
-rw-r--r--  username username system_u:object_r:httpd_sys_content_t /var/www/html/index.html

任何(Arch) Linux 用户都应该熟悉前三个字段和最后一个字段。第四字段是新增内容,格式如下:

用户(user):角色(role):类型(type)[:级别(level)]

解释:

  1. 用户(User): SELinux 用户身份。可以关联到一个或多个该用户允许使用的角色。
  2. 角色(Role): SELinux 角色。可以关联到一个或多个该用户允许访问的类型。
  3. 类型(Type): 当类型与进程关联时,它定义了该进程(即域/Domain)可以访问哪些资源。当类型与对象(如文件)关联时,它定义了主体对该对象拥有的访问权限。
  4. 级别(Level): 此可选字段也称为“范围(range)”,仅在策略支持 MCS 或 MLS 时出现。

若想了解如何构建自定义策略,这些基础知识至关重要,因为它们是 SELinux 的基本构建基块。但在大多数情况下无需深入了解,因为参考策略(Reference Policy)已经足够成熟。但对于高级用户或有非常特定需求的用户,学习如何制定自定义 SELinux 策略将是理想选择。

这系列文章是寻求理解如何使用 SELinux 的绝佳资源。

故障排除

[编辑 | 编辑源代码]

查找 SELinux 错误的主要地方是systemd/Journal。例如,若要查看与system_u:system_r:policykit_t:s0标签相关的 SELinux 消息,需运行:

# journalctl _SELINUX_CONTEXT=system_u:system_r:policykit_t:s0

实用工具

[编辑 | 编辑源代码]

以下是一些能对使用 SELinux 提供极大帮助的工具和命令:

restorecon
根据参考策略(Reference Policy)规则恢复文件或目录的上下文(配合-R参数可进行递归处理)。
chcon
修改特定文件的上下文。

报告问题

[编辑 | 编辑源代码]

请在Github上报告相关问题:https://github.com/archlinuxhardened/selinux/issues