初识SELinux

发布时间:2026/6/25 21:49:03
初识SELinux SELinux 在测试环境一般禁用了但是在生产环境会影响安全等级保护测评结果。在AI的帮助下认识一下SELinux。SELinux的构成及命令方式SELinux 的构成SELinuxSecurity-Enhanced Linux由美国国家安全局NSA开发是 Linux 内核中的强制访问控制MAC安全模块。其架构主要由以下核心组件构成安全上下文Security ContextSELinux 为系统中的每个对象进程、文件、端口等分配一个安全标签格式为user:role:type:level示例system_u:object_r:httpd_sys_content_t:s0字段说明重要性userSELinux 用户身份决定用户可担任的角色role角色决定可进入的域domaintype类型最核心字段决定访问控制规则level安全级别敏感度用于 MLS/MCS 策略策略Policy策略是 SELinux 的规则集合定义哪些主体进程可以访问哪些客体文件、端口等。主要策略类型策略类型说明适用场景targeted仅保护关键网络服务默认大多数服务器环境mls多级安全策略军事/涉密系统minimum最小化策略轻量保护需求策略的生成流程多个策略源模块 → 聚合为policy.conf→ 经checkpolicy编译为二进制文件policy.xx→ 通过security_load_policy载入内核。访问向量缓存AVC内核中的 AVC 模块负责缓存策略决策结果当进程发起访问请求时AVC 根据主体和客体的安全上下文查询策略判断允许或拒绝并将拒绝事件记录到审计日志。访问决策流程主体进程发起访问请求内核获取主体和客体的安全上下文AVC 查询策略判断是否允许允许 → 正常访问拒绝 → 阻止并记录日志三种工作模式模式说明用途Enforcing强制执行策略违规操作被阻止并记录生产环境Permissive仅记录违规日志不阻止操作调试/策略开发Disabled完全关闭 SELinux不推荐配置文件/etc/selinux/configSELINUXenforcing # enforcing / permissive / disabled SELINUXTYPEtargeted # targeted / mls / minimumSELinux 常用命令状态查看# 查看 SELinux 整体状态模式、策略类型、加载模块数等 sestatus # 查看当前模式输出 Enforcing/Permissive/Disabled getenforce # 判断 SELinux 是否启用返回 0 表示启用 selinuxenabled echo enabled || echo disabled模式切换# 临时切换重启后失效 setenforce 1 # 切换到 Enforcing setenforce 0 # 切换到 Permissive # 永久修改需重启生效 sudo sed -i s/^SELINUX.*/SELINUXenforcing/ /etc/selinux/config安全上下文查看# 查看文件的安全上下文 ls -Z /etc/passwd # 查看进程的安全上下文 ps -eZ # 查看当前用户的安全上下文 id -Z安全上下文修改# 临时修改文件上下文重启或 restorecon 后失效 chcon -t httpd_sys_content_t /var/www/html/index.html # 复制源文件的上下文到目标文件 chcon --reference /var/www/html /custom/web # 永久修改上下文规则推荐 semanage fcontext -a -t httpd_sys_content_t /custom/web(/.*)? # 恢复文件默认上下文配合 semanage 使用 restorecon -Rv /custom/web布尔值管理布尔值是策略规则的快捷开关控制特定功能的启停# 查看所有布尔值 getsebool -a # 查看某个布尔值 getsebool httpd_can_network_connect # 临时设置布尔值 setsebool httpd_can_network_connect on # 永久设置布尔值-P 写入策略 setsebool -P httpd_can_network_connect on端口管理# 查看端口标签 semanage port -l # 添加端口到策略 semanage port -a -t http_port_t -p tcp 8080 # 删除端口 semanage port -d -t http_port_t -p tcp 8080策略模块管理# 列出已加载的策略模块 semodule -l # 安装自定义策略模块 semodule -i mypolicy.pp # 移除策略模块 semodule -r mypolicy日志与调试# 查看 AVC 拒绝日志 ausearch -m avc -ts today # 解释拒绝原因 audit2why /var/log/audit/audit.log # 生成允许规则 audit2allow -a -M mypolicy # 查看被拒绝的操作摘要 audit2allow -w -a命令速查表目的命令查看状态sestatus、getenforce切换模式setenforce 1/0查看上下文ls -Z、ps -eZ、id -Z修改上下文临时chcon修改上下文永久semanage fcontextrestorecon管理布尔值getsebool、setsebool -P管理端口semanage port管理策略模块semodule -i/-r/-l调试排错ausearch、audit2why、audit2allowsemanage fcontext 命令详解semanage fcontext -a -t httpd_sys_content_t /custom/web(/.*)?表格部分含义semanageSELinux 策略管理工具用于永久修改策略规则fcontext子命令表示操作对象是文件上下文file context-a操作类型添加一条新的上下文规则-t httpd_sys_content_t指定目标**类型type**为httpd_sys_content_t即 Apache/Nginx 可读的 Web 内容类型/custom/web(/.*)?正则表达式定义规则的匹配范围正则表达式(/.*)?详解这是整条命令中最关键也最容易混淆的部分/custom/web(/.*)?拆解如下表格片段含义/custom/web匹配/custom/web目录本身(/.*)?可选组匹配该目录下的所有内容子目录、子文件递归()分组/.*/开头后跟任意字符任意次数即目录下所有路径?整个分组是可选的即同时匹配/custom/web本身和/custom/web/xxx所以这条规则的实际匹配范围是/custom/web目录本身/custom/web/index.html/custom/web/css/style.css/custom/web/subdir/file.php……递归匹配所有子路径这条命令做了什么它只是在 SELinux 策略数据库中写入了一条规则声明凡是路径匹配/custom/web(/.*)?的文件或目录其默认安全上下文类型应为httpd_sys_content_t。⚠️关键点这条命令不会立即改变任何现有文件的上下文。它只是定义了默认规则相当于告诉系统以后对这些路径执行restorecon时应该用什么类型。完整操作流程# 1. 写入默认上下文规则永久生效写入策略库 semanage fcontext -a -t httpd_sys_content_t /custom/web(/.*)? # 2. 将规则应用到现有文件必须执行否则现有文件上下文不变 restorecon -Rv /custom/web # 3. 验证 ls -Zd /custom/web ls -Z /custom/web/执行后输出示例drwxr-xr-x. root root system_u:object_r:httpd_sys_content_t:s0 /custom/web -rw-r--r--. root root system_u:object_r:httpd_sys_content_t:s0 /custom/web/index.html规则存储位置semanage fcontext -a写入的规则保存在cat /etc/selinux/targeted/contexts/files/file_contexts.local文件内容示例# This file is auto-generated by libsemanage # Please use the semanage command to make changes /custom/web(/.*)? system_u:object_r:httpd_sys_content_t:s0重启系统后规则仍然有效。其他常用操作# 查看已添加的规则 semanage fcontext -l | grep /custom/web # 修改已有规则如更换类型 semanage fcontext -m -t httpd_sys_rw_content_t /custom/web(/.*)? # 删除规则 semanage fcontext -d /custom/web(/.*)? # 仅匹配目录本身不包含子内容 semanage fcontext -a -t httpd_sys_content_t /custom/web # 仅匹配普通文件不包含目录 semanage fcontext -a -f f -t httpd_sys_content_t /custom/web(/.*)?其中-f参数可指定文件类型表格-f值匹配对象a所有文件默认f普通文件d目录l符号链接c字符设备b块设备s套接字p命名管道注意事项规则冲突如果存在多条规则匹配同一文件SELinux 优先匹配**更具体更长**的规则。例如同时存在/etc(/.*)?和/etc/myconf(/.*)?则/etc/myconf/test.conf会匹配后者。同一file_spec只能有一条规则重复执行-a会报错需要修改用-m需要先删除再用-d。chconvssemanagechcon是临时修改执行restorecon后会被覆盖semanage fcontext是永久规则restorecon会按此规则恢复。semodule -i mypolicy.pp 这里的mypolicy.pp 是什么格式如何生成的.pp 文件是什么.pp是SELinux Policy Package策略包的缩写是经过编译后的二进制策略模块文件。它不能直接编辑只能由源文件编译生成。生成 .pp 文件的完整流程第一步编写策略源文件.te 文件.teType Enforcement文件是策略的核心源文件用 SELinux 策略语言编写。典型场景你的 Web 服务需要连接数据库SELinux 默认阻止了通过ausearch发现拒绝日志后生成自定义策略bash编辑# 先用 audit2allow 分析拒绝日志自动生成 .te 文件 grep denied /var/log/audit/audit.log | audit2allow -M mypolicy这条命令会自动生成两个文件mypolicy.te和mypolicy.pp。如果你想手动编写mypolicy.te内容示例te编辑policy_module(mypolicy, 1.0) # 声明需要的类型 require { type httpd_t; type mysqld_port_t; class tcp_socket name_connect; } # 允许 httpd 进程连接 MySQL 端口 allow httpd_t mysqld_port_t:tcp_socket name_connect;第二步编译 .te 为 .conf 文件使用checkpolicy将.te源文件编译为中间二进制文件bash编辑checkpolicy -M -c 10 -o mypolicy.mod mypolicy.te表格参数含义-M生成模块而非单文件策略-c 10指定策略版本用semodule -l查看当前系统版本-o mypolicy.mod输出编译后的模块文件第三步打包为 .pp 文件使用semodule_package将.mod文件打包为.ppbash编辑semodule_package -o mypolicy.pp -m mypolicy.mod表格参数含义-o mypolicy.pp输出的 .pp 包文件-m mypolicy.mod输入的编译后模块文件可选参数-f file_contexts附加文件上下文规则对应.fc文件-u mypolicy.if附加接口定义对应.if文件第四步安装策略模块bash编辑sudo semodule -i mypolicy.pp一键生成最常用实际工作中通常不需要手动执行以上三步用audit2allow一条命令搞定# 分析审计日志自动生成 .te 和 .pp grep denied /var/log/audit/audit.log | audit2allow -M mypolicy # 安装 sudo semodule -i mypolicy.pp-M参数会自动完成分析日志 → 生成.te→ 编译为.mod→ 打包为.pp。完整文件关系图audit.log拒绝日志 │ ▼ audit2allow mypolicy.te策略源文件人类可读 │ ▼ checkpolicy mypolicy.mod编译后模块二进制 │ ▼ semodule_package mypolicy.pp策略包二进制 │ ▼ semodule -i 内核加载策略生效其他管理命令# 查看已安装的模块 semodule -l # 查看某个模块的详细信息 semodule -l | grep mypolicy # 临时禁用模块不删除 semodule -d mypolicy # 重新启用模块 semodule -e mypolicy # 卸载模块 semodule -r mypolicy注意事项audit2allow生成的规则可能过于宽泛建议生成后检查.te文件内容确认allow规则是否精确避免过度放权。.pp文件与策略版本绑定不同内核策略版本编译的.pp可能不兼容跨系统使用时需重新编译。优先用布尔值解决在安装自定义策略前先检查是否已有现成的布尔值可以开启例如setsebool -P httpd_can_network_connect on这比自定义策略更安全、更易维护。sudo semodule -i mypolicy.pp 之后是否要执行 restorecon?已完成分析不需要。两者作用于不同的层面互不依赖。原因表格命令作用层面做什么semodule -i mypolicy.pp策略规则告诉内核允许哪些操作例如允许 httpd 连接数据库端口restorecon文件上下文根据file_contexts规则恢复文件的类型标签semodule -i安装的是访问控制规则allow/deny不涉及文件标签所以无需执行restorecon。什么时候才需要 restorecon只有当你修改了文件上下文规则时才需要执行restorecon具体场景bash编辑# 场景你用 semanage 修改了文件的默认上下文规则 semanage fcontext -a -t httpd_sys_content_t /custom/web(/.*)? # 此时规则已写入策略库但现有文件的上下文还没变 # 必须执行 restorecon 才能生效 restorecon -Rv /custom/web总结你做了什么是否需要 restoreconsemodule -i mypolicy.pp安装策略规则❌ 不需要setsebool -P xxx on修改布尔值❌ 不需要semanage fcontext -a ...修改文件上下文规则✅ 需要chcon临时修改文件上下文❌ 不需要但会被 restorecon 覆盖chcon和semanage修改文件上下文有何区别已完成分析核心区别表格对比项chconsemanage fcontextrestorecon持久性临时重启或执行restorecon后失效永久写入策略库重启后仍有效作用对象直接修改文件的当前上下文修改策略中的默认规则再通过restorecon应用到文件与restorecon的关系会被restorecon覆盖是restorecon的依据适用场景临时调试、测试生产环境正式配置举例说明假设你把/custom/web的类型从default_t改为httpd_sys_content_t用 chcon临时bash编辑chcon -t httpd_sys_content_t /custom/web/index.html # 此时文件上下文已改变 ls -Z /custom/web/index.html # system_u:object_r:httpd_sys_content_t:s0 # 但执行 restorecon 后会被打回原形 restorecon /custom/web/index.html ls -Z /custom/web/index.html # system_u:object_r:default_t:s0 ← 恢复为默认值用 semanage永久bash编辑# 写入默认规则 semanage fcontext -a -t httpd_sys_content_t /custom/web(/.*)? # 应用到文件 restorecon -Rv /custom/web # 此时文件上下文已改变 ls -Z /custom/web/index.html # system_u:object_r:httpd_sys_content_t:s0 # 即使再次执行 restorecon也不会被覆盖 restorecon /custom/web/index.html ls -Z /custom/web/index.html # system_u:object_r:httpd_sys_content_t:s0 ← 保持不变存储位置对比表格命令修改内容存储在哪里chcon直接写入文件的扩展属性xattr不写入任何策略文件semanage fcontext写入/etc/selinux/targeted/contexts/files/file_contexts.local选择建议表格场景推荐命令临时测试某个服务能否正常访问文件chcon生产环境正式部署semanage fcontextrestorecon不确定上下文是否正确先试一下先chcon验证确认无误后再用semanage固化批量修改整个目录树semanage fcontextrestorecon -R简单记忆chcon是改一次管一次semanage是改规则永久生效。生产环境始终用semanage。