Понимание работы и режимов SELinux
Если SELinux включен и ничего больше не настроено, все системные вызовы отклоняются. Чтобы указать, что именно разрешено, используется политика. В этой политике правила определяют, к какому исходному домену разрешен доступ к какому целевому домену. Исходный домен — это объект, который пытается получить доступ к чему-либо. Как правило, это процесс или пользователь. Целевой домен — это объект, к которому осуществляется доступ. Как правило, это файл, каталог или сетевой порт, чтобы точно определить, что разрешено; используются контекстные метки. Использование этих меток является сущностью SELinux, поскольку эти метки используются для определения правил доступа.
Основные элементы SELinux
Элемент |
Описание элемента |
Policy |
Набор правил, которые определяют, какой источник имеет доступ к какой цели. |
Source domain |
Объект, который пытается получить доступ к цели. Обычно пользователь или процесс. |
Target domain |
То, к чему пытается обратиться исходный домен. Обычно это файл или порт. |
Context |
Метка безопасности, которая используется для классификации объектов в SELinux. |
Rule |
Определенная часть политики, которая определяет, какой исходный домен имеет какие права доступа к какому целевому домену. |
Labels |
То же, что и метка контекста, определенная для определения того, какой исходный домен имеет доступ к какому целевому домену. |
SELinux для процессов и файлов
Цель SELinux – защитить процессы доступа к файлам в среде Linux. Без SELinux процесс или приложение, такое как демон Apache, будет запускаться в контексте пользователя, который его запустил. Таким образом, если ваша система скомпрометирована мошенническим приложением, работающим под пользователем root, приложение может делать все, что захочет, поскольку root имеет всеохватывающие права на каждый файл.
SELinux пытается пойти еще дальше и устранить этот риск. С SELinux процесс или приложение будут иметь только те права, которые ему необходимы, и НИЧЕГО больше. Политика SELinux для приложения будет определять, к каким типам файлов требуется доступ, и к каким процессам она может трансформировать. Политики SELinux написаны разработчиками приложений и поставляются вместе с дистрибутивом Linux, который его поддерживает. Политика – это набор правил, которые отображают процессы и пользователей в соответствии с их правами.
Первая часть безопасности ставит label для каждого объекта в системе Linux. Метка похожа на любой другой атрибут файла или процесса (владелец, группа, дата создания и т. Д.); он показывает context ресурса. Так в чем же контекст? Проще говоря, контекст – это набор информации, связанной с безопасностью, которая помогает SELinux принимать решения по управлению доступом. Все в системе Linux может иметь контекст безопасности: учетная запись пользователя, файл, каталог, демон или порт могут иметь свои контексты безопасности. Однако контекст безопасности будет означать разные вещи для разных типов объектов.
1 |
ls -Z /etc/*.conf |
Теперь у нас есть дополнительный столбец информации после владения пользователем и группой:
1 2 3 4 5 6 |
... -rw-r--r--. root root system_u:object_r:locale_t:s0 /etc/locale.conf -rw-r--r--. root root system_u:object_r:etc_t:s0 /etc/logrotate.conf -rw-r--r--. root root system_u:object_r:etc_t:s0 /etc/man_db.conf -rw-r--r--. root root system_u:object_r:etc_t:s0 /etc/mke2fs.conf ... |
Этот столбец показывает контексты безопасности файлов. Говорят, что файл был labelled с его контекстом безопасности, когда у вас есть эта информация для него. Давайте внимательнее посмотрим на один из контекстов безопасности.
1 |
-rw-r--r--. root root system_u:object_r:etc_t:s0 /etc/logrotate.conf |
Контекст безопасности – это часть:
1 |
system_u:object_r:etc_t:s0 |
Есть четыре части, и каждая часть контекста безопасности отделена двоеточием (:). Первая часть – это контекст SELinux user для файла. Мы обсудим пользователей SELinux позже, но сейчас мы видим, что это * system_u *. Каждая учетная запись пользователя Linux сопоставляется с пользователем SELinux, и в этом случае пользователь * root *, которому принадлежит файл, сопоставляется с пользователем * system_u * SELinux. Это сопоставление выполняется политикой SELinux.
Вторая часть определяет SELinux role, которая является * object_r *. Чтобы освежить в памяти роли SELinux, вернитесь к первой статье SELinux.
Здесь важнее всего третья часть, type файла, который указан здесь как * etc_t *. Это та часть, которая определяет, к какому типу относится файл или каталог. Мы видим, что большинство файлов относятся к типу * etc_t * в каталоге + / etc +
. Гипотетически вы можете думать о типе как о «группе» или attribute для файла: это способ классификации файла.
Мы также видим, что некоторые файлы могут принадлежать другим типам, например + locale.conf +
, который имеет тип * locale_t *. Даже если все файлы, перечисленные здесь, имеют одинаковых пользователей и владельцев групп, их типы могут быть разными.
Контексты процесса SELinux
Давайте теперь поговорим о контексте безопасности процесса.
Запустите службы Apache и SFTP. Мы установили эти службы в первом руководстве по SELinux.
1 2 |
service httpd start service vsftpd start |
Мы можем запустить команду + ps +
с несколькими флагами, чтобы показать процессы Apache и SFTP, запущенные на нашем сервере:
1 |
ps -efZ | grep 'httpd\|vsftpd' |
Еще раз флаг -Z используется для отображения контекстов SELinux. Выходные данные показывают пользователя, выполняющего процесс, идентификатор процесса и идентификатор родительского процесса:
1 2 3 4 5 6 7 8 |
system_u:system_r:httpd_t:s0 root 7126 1 0 16:50 ? 00:00:00 /usr/sbin/httpd -DFOREGROUND system_u:system_r:httpd_t:s0 apache 7127 7126 0 16:50 ? 00:00:00 /usr/sbin/httpd -DFOREGROUND system_u:system_r:httpd_t:s0 apache 7128 7126 0 16:50 ? 00:00:00 /usr/sbin/httpd -DFOREGROUND system_u:system_r:httpd_t:s0 apache 7129 7126 0 16:50 ? 00:00:00 /usr/sbin/httpd -DFOREGROUND system_u:system_r:httpd_t:s0 apache 7130 7126 0 16:50 ? 00:00:00 /usr/sbin/httpd -DFOREGROUND system_u:system_r:httpd_t:s0 apache 7131 7126 0 16:50 ? 00:00:00 /usr/sbin/httpd -DFOREGROUND system_u:system_r:ftpd_t:s0-s0:c0.c1023 root 7209 1 0 16:54 ? 00:00:00 /usr/sbin/vsftpd /etc/vsftpd/vsftpd.conf unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c1023 root 7252 2636 0 16:57 pts/0 00:00:00 grep --color=auto httpd\|vsftpd |
Контекст безопасности – это часть:
1 |
system_u:system_r:httpd_t:s0 |
Контекст безопасности состоит из четырех частей: пользователь, роль, домен и чувствительность. Пользователь, роль и чувствительность работают так же, как и для файлов (объяснение в предыдущем разделе). Домен уникален для процессов.
В приведенном выше примере мы видим, что несколько процессов выполняются в домене * httpd_t *, а один – в домене * ftpd_t *.
Так что домен делает для процессов? Это дает процессу контекст для запуска. Это как пузырь вокруг процесса, который confines его. Он сообщает процессу, что он может сделать, а что нет. Это ограничение гарантирует, что каждый домен процесса может работать только с определенными типами файлов и ничего более.
Используя эту модель, даже если процесс захвачен другим вредоносным процессом или пользователем, худшее, что он может сделать, это повредить файлы, к которым у него есть доступ. Например, демон vsftp не будет иметь доступа к файлам, используемым, скажем, sendmail или samba. Это ограничение реализовано на уровне ядра: оно применяется, когда политика SELinux загружается в память, и, таким образом, контроль доступа становится mandatory.
Соглашения об именах
Прежде чем идти дальше, обратите внимание на соглашение об именах SELinux. SELinux Для пользователей добавляется суффикс «_u», для ролей – «_r», а для типов (для файлов) или доменов (для процессов) – «_t».
Как процессы получают доступ к ресурсам
До сих пор мы видели, что файлы и процессы могут иметь разные контексты, и что они ограничены их собственными типами или доменами. Так как же работает процесс? Для запуска процесс должен получить доступ к своим файлам и выполнить с ними некоторые действия (открыть, прочитать, изменить или выполнить). Мы также узнали, что каждый процесс может иметь доступ только к определенным типам ресурсов (файлы, каталоги, порты и т. Д.).
SELinux устанавливает эти правила доступа в политике. Правила доступа следуют стандартной структуре allow Statement:
1 |
allow <domain> <type>:<class> { <permissions> }; |
Мы уже говорили о доменах и типах. * Class * определяет, что на самом деле представляет ресурс (файл, каталог, символическая ссылка, устройство, порты, курсор и т. Д.)
Вот что означает этот общий оператор allow:
-
Если процесс относится к определенной области
-
И объект ресурса, к которому он пытается получить доступ, имеет определенный класс и тип
-
Затем разрешите доступ
-
Остальное запретить доступ
В системе Linux вы можете включить или отключить SELinux. Когда SELinux включен, загружается поддержка ядра для SELinux, и некоторые приложения, осведомленные о SELinux, меняют свое поведение, потому что в системе, в которой включен SELinux, используются определенные библиотеки. Если SELinux отключен, никаких действий SELinux вообще не будет. Переключение между включенным SELinux и отключенным режимом SELinux требует перезагрузки вашей системы. Это потому, что SELinux — это функция, тесно связанная с ядром Linux.
Если в системе включен SELinux, вы можете выбрать перевод SELinux в принудительный режим (enforcing mode) или в разрешающий режим (permissive mode). В принудительном режиме SELinux полностью работает и обеспечивает соблюдение всех правил SELinux в политике. Если SELinux находится в разрешающем режиме, все действия, связанные с SELinux, регистрируются, но доступ не блокируется. Это делает разрешающий режим SELinux отличным режимом для устранения неполадок. Разрешительный режим также является отличным способом сделать что-то и увидеть результат с точки зрения SELinux. Это может помочь в создании новой и более эффективной политики.
Чтобы установить режим SELinux по умолчанию во время загрузки, используйте файл /etc/sysconfig/selinux.
1 2 3 4 5 6 7 8 9 10 11 12 |
[root@server1 ~]# <b>cat /etc/sysconfig/selinux</b> # 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 these two values: # targeted - Targeted processes are protected, # minimum - Modification of targeted policy. Only selected processes are protected. # mls - Multi Level Security protection. SELINUXTYPE=targeted |
Как вы можете видеть, в этом файле, который читается во время загрузки, вы можете установить SELinux в принудительном, разрешающем или отключенном режиме.
На сервере, на котором в данный момент включен SELinux, вы можете использовать команду getenforce, чтобы увидеть, находится ли он в принудительном или разрешительном режиме. Для переключения между разрешающим и принудительным режимом вы можете использовать setenforce. Команда setenforce 0 переводит SELinux в разрешающий режим, а setenforce 1 переводит SELinux в принудительный режим.
Еще одна полезная команда — sestatus. При использовании с параметром -v эта команда отображает подробную информацию о текущем состоянии SELinux на сервере. Ниже показаны выходные данные команды sestatus -v. Он не только показывает, какие части SELinux включены, но также показывает текущую версию загруженной политики и метки контекста для некоторых критических частей системы.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 |
[root@server1 log]# <b>sestatus -v</b> SELinux status: enabled SELinuxfs mount: /sys/fs/selinux SELinux root directory: /etc/selinux Loaded policy name: targeted Current mode: enforcing Mode from config file: enforcing Policy MLS status: enabled Policy deny_unknown status: allowed Max kernel policy version: 28 Process contexts: Current context: unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c1023 Init context: system_u:system_r:init_t:s0 /usr/sbin/sshd system_u:system_r:sshd_t:s0-s0:c0.c1023 File contexts: Controlling terminal: unconfined_u:object_r:user_devpts_t:s0 /etc/passwd system_u:object_r:passwd_file_t:s0 /etc/shadow system_u:object_r:shadow_t:s0 /bin/bash system_u:object_r:shell_exec_t:s0 /bin/login system_u:object_r:login_exec_t:s0 /bin/sh system_u:object_r:bin_t:s0 -> system_u:object_r:shell_exec_t:s0 /sbin/agetty system_u:object_r:getty_exec_t:s0 /sbin/init system_u:object_r:bin_t:s0 -> system_u:object_r:init_exec_t:s0 /usr/sbin/sshd system_u:object_r:sshd_exec_t:s0 |
Управление режимами SELinux
1. Откройте консоль под рутом и введите getenforce. Обычно вы видите, что SELinux находится в enforcing mode.
2. Введите setenforce 0 и снова введите getenforce. SELinux теперь переключается в permissive mode.
3. Откройте файл /etc/sysconfig/selinux в редакторе и измените строку SELINUX= так, чтобы он читал SELINUX=disabled. Перезагрузите сервер.
4. После перезагрузки снова войдите под рутом и введите getenforce. Вы увидите, что SELinux теперь в disabled mode.
5. Попробуйте использовать команду setenforce 1. Вы увидите сообщение «setenforce: SELinux is disabled». Вы не можете переключаться между disabled mode и enforcing mode без перезагрузки сервера.
6. Снова откройте файл /etc/sysconfig/selinux и измените строку SELINUX=disabled обратно на SELINUX=enforcing. Перезагрузите вашу систему снова.
7. После перезагрузки введите sestatus -v и прочитайте информацию о текущем состоянии SELinux.
Обратите внимание, что на реальных серверах иногда отключается SELinux. Перевод SELinux в режим disabled, безусловно, облегчает администраторам запуск своих приложений. Тем не менее, это также делает его менее безопасным. Часто нет причины, кроме незнания системного администратора, переводить SELinux в отключенный режим, даже если разработчики некоторых приложений сообщают, что приложение поддерживается только в том случае, если SELinux отключен.
С другой стороны, полноценная система особенно важна, если доступ к вашему серверу получают пользователи напрямую из Интернета. Если ваш сервер не может быть доступен напрямую из Интернета, но находится в безопасной внутренней сети, не обязательно включать SELinux.
SELinux часто отключается на серверах из-за лени и потому, что поставщики приложений просто не знают, как с этим бороться. Во многих случаях даже приложения, которые не знают, как работать с SELinux, могут быть полностью функциональными на сервере с SELinux. Требуется немного больше работы, чтобы выяснить дополнительные правила в политике, которые необходимо создать, чтобы использовать приложение в системе с поддержкой SELinux.
Понимание настроек контекста и политики
Настройки контекста являются важной частью операций SELinux.
Контекст — это метка, которая может быть применена к различным элементам:
- файлы и каталоги
- порты
- процессы
- пользователи
Метки контекста определяют природу элемента, а правила SELinux создаются для сопоставления меток контекста исходных объектов с метками контекста целевых объектов. Таким образом, установка правильных меток контекста является очень важным навыком для системных администраторов.
Мониторинг текущих контекстных меток
Чтобы увидеть текущие настройки контекста для этих объектов, многие команды предлагают поддержку опции –Z. Ниже показано, как ls -Z показывает настройки контекста для некоторых каталогов в /. Другие команды также поддерживают параметр -Z для отображения текущих настроек меток контекста.
Некоторыми примерами являются ps Zaux, который показывает список всех процессов, включая их метку контекста, или netstat -Ztulpen, который показывает все сетевые порты и метку текущего контекста, связанную с каждым портом.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 |
[root@server1 /]# <b>ls -Z</b> lrwxrwxrwx. root root system_u:object_r:bin_t:s0 bin -> usr/bin dr-xr-xr-x. root root system_u:object_r:boot_t:s0 boot drwxr-xr-x root root ? dev drwxr-xr-x. root root system_u:object_r:etc_t:s0 etc drwxr-xr-x. root root system_u:object_r:home_root_t:s0 home lrwxrwxrwx. root root system_u:object_r:lib_t:s0 lib -> usr/lib lrwxrwxrwx. root root system_u:object_r:lib_t:s0 lib64 -> usr/ lib64 drwxr-xr-x. root root system_u:object_r:mnt_t:s0 media drwxr-xr-x. root root system_u:object_r:mnt_t:s0 mnt drwxr-xr-x. root root system_u:object_r:usr_t:s0 opt dr-xr-xr-x root root ? proc dr-xr-x---. root root system_u:object_r:admin_home_t:s0 root drwxr-xr-x root root ? run lrwxrwxrwx. root root system_u:object_r:bin_t:s0 sbin -> usr/sbin drwxr-xr-x. root root system_u:object_r:var_t:s0 srv dr-xr-xr-x root root ? sys drwxrwxrwt. root root system_u:object_r:tmp_t:s0 tmp drwxr-xr-x. root root system_u:object_r:usr_t:s0 usr drwxr-xr-x. root root system_u:object_r:var_t:s0 var drwxr-xr-x. root root unconfined_u:object_r:httpd_sys_content_t:s0 web |
Каждая контекстная метка всегда состоит из трех разных частей:
User: |
user может быть распознан как _u в метке контекста; для большинства каталогов, установлено значение system_u. |
Role: |
role может быть распознана как _r в метке контекста. Большинство объектов помечены ролью object_r. В расширенном управлении SELinux конкретным пользователям SELinux могут быть назначены разрешения для определенных ролей SELinux. |
Type: |
контекст type может быть распознан как _t в метке контекста. Вы можете видеть, что к каталогам в / применяется широкий спектр типов контекста. |
Установка типов контекста
Как администратор, важно, чтобы вы знали, как устанавливать типы контекста. Вы можете установить эти типы контекста для файлов и каталогов и других объектов, таких как сетевые порты.
Вы можете использовать две команды для установки типа контекста:
- semanage: это команда, которую вы должны использовать. Команда semanage записывает новый контекст в политику SELinux, из которой он применяется к файловой системе.
- chcon: эта команда предназначена для использования только в определенных случаях и обычно ее следует избегать. Команда chcon записывает новый контекст в файловую систему, а не в политику. Все, что применяется с chcon, перезаписывается, когда файловая система перемаркируется (relabel), или исходный контекст восстанавливается из политики в файловую систему. Не используйте эту команду!
Чтобы установить контекст с помощью semanage, сначала нужно найти соответствующий контекст (более подробно эта тема будет рассмотрена в следующем разделе «Поиск нужного типа контекста»). Простой способ найти подходящий контекст — посмотреть на настройки контекста по умолчанию для уже существующих элементов. Например, если вы хотите изменить контекст для веб-сервера, введите ls -Z /var/www, чтобы увидеть настройки контекста:
1 2 3 |
root@server1 /]# <b>ls -Z /var/www</b> drwxr-xr-x. root root system_u:object_r:httpd_sys_script_exec_t:s0 cgi-bin drwxr-xr-x. root root system_u:object_r:httpd_sys_content_t:s0 html |
Как видите, настройки контекста в /var/www/html установлены на httpd_sys_content_t.
Чтобы установить для этого типа контекста любой новый каталог, к которому вы хотите получить доступ веб-сервером Apache, используйте следующую команду:
1 |
semanage fcontext -a -t httpd_sys_content_t "/mydir(/.*)?" |
В этой команде параметр -a используется для добавления типа контекста. Это то, что вам нужно сделать для всех каталогов, которые вы создали вручную. Затем вы используете -t для изменения типа контекста (в отличие от пользователя и роли). Последняя часть команды представляет собой регулярное выражение, которое используется для ссылки на каталог /mydir и все, что может существовать под этим каталогом.
Стоит также отметить что команды:semanage fcontext -a -t httpd_sys_content_t "/mydir/"
semanage fcontext -a -t httpd_sys_content_t "/mydir(/.*)"
semanage fcontext -a -t httpd_sys_content_t "/mydir(/.*)?"
Не идентичны!!!! Важно понимать первая меняет контекст только для конкретной директории (но ели внутри директории уже есть файлы то их контекст изменен не будет). Вторая команда поменяет контекст только для подкаталогов и файлов внутри папки но при этом не затронит саму папку. Третья же меняет контекст как и для папки так и дальше по иерархии.
Однако такой настройки контекста недостаточно, поскольку вы будете записывать его только в политику, а не в файловую систему. Чтобы завершить команду, вам нужно применить параметр политики к файловой системе следующим образом:
1 |
restorecon -R -v / mydir |
Вы увидите, что теперь применяется новый контекст, который позволяет процессу httpd получать доступ к каталогу.
Контекстное наследование для файлов и каталогов
SELinux обеспечивает то, что мы можем назвать «наследованием контекста». Это означает, что, если это не указано в политике, процессы и файлы создаются с учетом контекста их родителей.
Таким образом, если у нас есть процесс с именем «proc_a», порождающий другой процесс с именем «proc_b», то этот процесс будет запущен в том же домене, что и «proc_a», если иное не указано политикой SELinux.
Аналогично, если у нас есть каталог с типом «some_context_t», любой файл или каталог, созданный в нем, будет иметь тот же тип контекста, если в политике не указано иное.
Пример. Настройка меток контекста в Nondefault Apache Document Root.
1. Зайдите под рутом и введите yum install httpd elinks –y, чтобы установить httpd и elinks.
2. Создайте папку mkdir /web.
3. Введите vi /web/index.html и поместите в файл следующее содержимое: welcome to my web server.
4. Введите vi /etc/httpd/conf/httpd.conf, чтобы открыть файл конфигурации Apache и найти параметр DocumentRoot. Измените его так, чтобы оно читало DocumentRoot «/web».
5. В тот же файл конфигурации httpd.conf добавьте следующий раздел:
1 2 3 4 |
<Directory "/web"> AllowOverride None Require all granted </Directory> |
6. Введите systemctl restart httpd; systemctl enable httpd.
7. Введите elinks http://localhost. Вы увидите веб-страницу по умолчанию, а не содержимое только что созданного файла index.html.
8. Введите setenforce 0, чтобы переключить SELinux в режим permissive.
9. Повторите Шаг 7. Теперь вы получите доступ к своей пользовательской веб-странице, которая доказывает, что SELinux что-то делал для блокирования доступа.
10. Введите semanage fcontext -a -t httpd_sys_content_t «/web (/.*)?», чтобы применить новую метку контекста к /web.
11. Введите restorecon -R -v /web. Опция -v (подробный) гарантирует, что вы видите, что происходит, и что вы увидите, что новый контекст применяется к /web.
12. Установите SELinux обратно в enforcing mode, используя setenforce 1.
13. Наберите elinks http://localhost. Теперь вы получите доступ к своей пользовательской веб-странице.
Поиск нужного типа контекста SELinux
Одна из сложных частей настройки контекста SELinux — найти нужный вам контекст.
Грубо говоря, есть три подхода:
- Посмотреть на среду по умолчанию.
- Читать файлы конфигурации.
- Использовать man -k _selinux для поиска справочных страниц по SELinux для вашего сервиса.
Наиболее эффективный способ получения необходимой информации SELinux — использование man -k _selinux, который ищет в базе данных man-страниц man-страницы, которые соответствуют _selinux в названии или описании man-страницы. Однако на RHEL 7/CentOS 7 эти справочные страницы не установлены по умолчанию. Чтобы установить их, вам нужно установить пакет policycoreutils-devel, после чего вы можете использовать команду sepolicy manpage -a -p /usr/share/man/man8 для установки справочных страниц SELinux.
Ниже пройдемся по шагам установки справочных страниц SELinux:
1. Введите man -k _selinux. Вы, вероятно, увидите только одну или две справочные страницы.
2. Введите yum whatprovides * /sepolicy. Результат этой команды покажет вам имя RPM, который содержит бинарный файл sepolicy, который называется policycoreutils-devel.
3. Введите yum -y install policycoreutils-devel для установки этого пакета.
4. Введите sepolicy manpage -a -p /usr/share/man/man8 для установки страниц справки.
5. Введите man -k _selinux. Вы пока не увидите никаких изменений.
6. Введите mandb, чтобы обновить базу данных, которая содержит имена и описания всех установленных man-страниц.
7. После завершения команды mandb (это может занять несколько минут), введите man -k _selinux. Теперь вы увидите длинный список страниц.
8. Введите man -k _selinux | grep http, чтобы найти справочную страницу, которая документирует настройки SELinux для сервиса httpd. Обратите внимание, что это полный список всего, что вы можете сделать с SELinux в сервисе httpd.
Восстановление файловых контекстов SELinux по умолчанию
Выше вы узнали, как применять типы контекста, используя semanage. Вы также применили параметры контекста из политики к файловой системе, используя restorecon. Команда restorecon — полезная команда, потому что в политике параметры по умолчанию определены для большинства файлов и каталогов.
Если неверный параметр контекста применяется когда-либо, вам просто нужно ввести restorecon, чтобы повторно применить его из политики в файловую систему.
Использование restorecon таким способом может быть полезно для исправления проблем с новыми файлами. Прежде чем объяснить, как это сделать, давайте посмотрим, как применяются новые настройки контекста:
- Если создается новый файл, он наследует настройки контекста из родительского каталога.
- Если файл копируется в каталог, это считается новым файлом, поэтому он наследует настройки контекста из родительского каталога.
- Если файл перемещен или скопирован с сохранением его свойств (с помощью cp -a), применяются исходные параметры контекста файла.
Особенно последняя из этих трех ситуаций легко исправляется с помощью restorecon.
Также возможно перемаркировать всю файловую систему. При этом все параметры контекста применяются к файловой системе, как указано в политике. Поскольку политика всегда должна быть ведущей и содержать правильные параметры контекста, хорошей идеей может быть перемаркировка файловой системы. Чтобы перемаркировать файловую систему, вы можете использовать команду restorecon -Rv / или создать файл с именем /.autorelabel. При следующем перезапуске сервера файловая система будет автоматически перемаркирована.
Действие по перемаркировке иногда происходит спонтанно. Если при устранении неполадок с сервером вы запустили сервер в режиме, в котором SELinux был отключен, и применили изменения к файловой системе, SELinux обнаружит, что файловая система изменилась, без SELinux, отслеживая ее. Это приведет к автоматической перемаркировке всей файловой системы. Обратите внимание, что на больших файловых системах перемаркировка файловой системы может занимать значительное количество времени.
Использование restorecon для перемаркировки файлов
1. По рутом введите ls -Z /etc/hosts. Вы увидите, что файл имеет контекстную метку net_config_t.
2. Введите cp /etc/hosts ~, чтобы скопировать файл в корневой домашний каталог. Поскольку копирование считается созданием нового файла, настройка контекста в файле ~/hosts установлена как admin_home_t. Используйте ls -Z ~/hosts, чтобы проверить это.
3. Используйте mv ~/hosts/etc и подтвердите, что вы хотите перезаписать существующий файл.
4. Введите ls -Z /etc/hosts, чтобы подтвердить, что для типа контекста все еще задано значение admin_home_t.
5. Используйте restorecon -v /etc/hosts, чтобы повторно применить правильный тип контекста. Опция -vпоказывает вам, что происходит.
6. Введите touch /.autorelabel и перезапустите сервер. При перезапуске обязательно нажимайте клавишу Esc на клавиатуре, чтобы увидеть загрузочные сообщения.
Вы увидите, что файловая система автоматически перемаркируется.
Использование логических (boolean) настроек для изменения настроек SELinux
В политике SELinux есть много правил. Некоторые из этих правил разрешают определенную деятельность, тогда как другие правила запрещают эту деятельность. Изменить правила нелегко, и поэтому предоставляются булевы значения SELinux, чтобы легко изменить поведение правила.
Примером логического значения является ftpd_anon_write, который по умолчанию выключен. Это означает, что даже если вы настроили свой FTP-сервер для разрешения анонимных записей, логическое значение все равно будет отказывать, и анонимный пользователь не сможет загружать какие-либо файлы. Если существует конфликт между настройкой параметра в файле конфигурации службы и логическим значением, логическое значение всегда имеет приоритет. Но булевы значения легко изменить.
Чтобы получить список логических значений в вашей системе, используйте getsebool -a. Если вы ищете логические значения, установленные для конкретной службы, используйте grep для фильтрации результатов. Ниже вы можете увидеть, как эта команда используется для отображения текущих логических значений, соответствующих FTP.
Альтернативный способ показать текущие логические настройки — использовать команду semanage boolean -l. Эта команда предоставляет некоторые дополнительные сведения, потому что она показывает текущее логическое значение и значение по умолчанию.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 |
root<span class="variable">@server1</span> ~]<span class="comment"># <b>getsebool -a | grep ftp</b></span><b></b> ftp_home_dir --> off ftpd_anon_write --> off ftpd_connect_all_unreserved --> off ftpd_connect_db --> off ftpd_full_access --> off ftpd_use_cifs --> off ftpd_use_fusefs --> off ftpd_use_nfs --> off ftpd_use_passive_mode --> off httpd_can_connect_ftp --> off httpd_enable_ftp_server --> off sftpd_anon_write --> off sftpd_enable_homedirs --> off sftpd_full_access --> off sftpd_write_ssh_home --> off tftp_anon_write --> off tftp_home_dir --> off |
Чтобы изменить логическое значение, вы можете использовать setsebool. Если вы хотите переключить логическое значение ftpd_anon_write, чтобы разрешить, например, анонимную запись, используйте setsebool ftpd_anon_write. Это изменяет значение среды выполнения логического значения, но не меняет его постоянно. Чтобы применить постоянные изменения к логическому значению, используйте setsebool -P. Обратите внимание, что это занимает больше времени, потому что части политики должны быть перекомпилированы для применения изменения.
Давайте воспользуемся этими командами, чтобы увидеть, как работают логические значения.
1. Под рутом введите getsebool -a | grep ftp. Вы увидите логическое значение ftpd_anon_write с его текущим значением off.
2. Введите setsebool ftpd_anon_write on. Это меняет значение во время выполнения.
3. Введите getsebool ftpd_anon_write. Показывает значение логического значения как on.
4. Введите semanage boolean -l | grep ftpd_anon. Обратите внимание, что эта команда показывает, что конфигурация среды выполнения включена, но постоянная настройка по-прежнему выключена.
5. Введите setsebool -P ftpd_anon_write on, чтобы включить среду выполнения и настройку по умолчанию.
6. Повторите semanage boolean -l | grep ftpd_anon. Обратите внимание, что теперь он включен в положение on.
Диагностика и устранение нарушений политики SELinux
Конфигурирование системы с помощью SELinux может быть сложной задачей. Чтобы облегчить понимание происходящего, SELinux регистрирует все, что делает. Основным источником получения информации журнала является журнал аудита, который находится в /var/log/audit/audit.log. Сообщения SELinux записываются с type=AVC в журнале аудита. Итак, чтобы увидеть, что делает SELinux, вы можете использовать команду grep AVC /var/log/audit/audit.log.
Если сообщения SELinux были зарегистрированы, эта команда показывает результат, как показано ниже:
1 2 3 4 5 |
[root@server1 audit]<span class="comment"># <b>grep AVC audit.log</b></span><b></b> type=USER_<b>AVC</b> msg=audit(<span class="number">1414933364.949</span>:<span class="number">11</span>): pid=<span class="number">1</span> uid=<span class="number">0</span> auid=<span class="number">4294967295</span> ses=<span class="number">4294967295</span> subj=system_u:system_r:init_t:s0 msg=<span class="string">'avc: received setenforce notice (enforcing=0) exe="/usr/lib/systemd/systemd" sauid=0 hostname=? addr=? terminal=?'</span> type=<b>AVC</b> msg=audit(<span class="number">1414933365.304</span>:<span class="number">13</span>): avc: denied { read } <span class="keyword">for</span> pid=<span class="number">1330</span> comm=<span class="string">"alsactl"</span> name=<span class="string">"asound.state"</span> dev=<span class="string">"dm-1"</span> ino=<span class="number">72731037</span> scontext=system_u:system_ r:alsa_t:s0-s0:c0.c1023 tcontext=system_u:object_r:file_t:s0 tclass=file type=<b>AVC</b> msg=audit(<span class="number">1414933365.304</span>:<span class="number">13</span>): avc: denied { open } <span class="keyword">for</span> pid=<span class="number">1330</span> comm=<span class="string">"alsactl"</span> path=<span class="string">"/var/lib/alsa/asound.state"</span> dev=<span class="string">"dm-1"</span> ino=<span class="number">72731037</span> scontext= system_u:system_r:alsa_t: s0-s0:c0.c1023 tcontext=system_u:object_r:file_t:s0 tclass=file type=<b>AVC</b> msg=audit(<span class="number">1414933365.304</span>:<span class="number">14</span>): avc: denied { getattr } <span class="keyword">for</span> pid=<span class="number">1330</span> comm=<span class="string">"alsactl"</span> path=<span class="string">"/var/lib/alsa/asound.state"</span> dev=<span class="string">"dm-1"</span> ino=<span class="number">72731037</span> scontext= system_u:system_r:alsa_t:s0-s0:c0.c1023 tcontext=system_u:object_r:file_t:s0 tclass=file |
На первый взгляд, сообщения журнала SELinux выглядят сложными. Если вы посмотрите немного ближе, они не так сложны для понимания.
Давайте внимательнее посмотрим на последнюю строку в файле журнала:
1 |
<span class="setting">type=<span class="value">AVC msg=audit(<span class="number">1414933365.304</span>:<span class="number">14</span>): avc: denied { getattr } for pid=<span class="number">1330</span> comm=<span class="string">"alsactl"</span> path=<span class="string">"/var/lib/alsa/asound.state"</span> dev=<span class="string">"dm-1"</span> ino=<span class="number">72731037</span> scontext=system_u:system_r:alsa_t:s0-s0:c0.c1023 tcontext=system_u:object_r:file_t:s0 tclass=file</span></span> |
Первая соответствующая часть в этой строке — это текст avc: denies {gettattr}. Это означает, что запрос getattr был отклонен, поэтому какой-то процесс попытался прочитать атрибуты файла, и это было отклонено. После этого сообщения мы можем увидеть comm=alsactl, что означает, что команда, пытающаяся выполнить запрос getattr, была alsactl, и мы можем увидеть path=”/var/lib/alsa/asound.state«, который является файлом, к которому этот процесс пытался получить доступ.
В последней части строки журнала мы можем получить информацию об исходном контексте и целевом контексте. Исходный контекст (который является параметром контекста команды alsactl) установлен в alsa_t, а целевой контекст (который является параметром контекста файла asound.state) установлен в file_t. И, видимо, SELinux это не очень понравилось.
Упрощение анализа SELinux
На основании информации, которую вы найдете в audit.log, вы можете решить, что вам нужно сделать, чтобы решить проблему. Если вы не можете этого сделать, то есть sealert. Во-первых, вам нужно установить sealert с помощью yum -y install setroubleshoot-server. Затем рекомендуется перезапустить сервер, чтобы убедиться, что все задействованные процессы перезапущены правильно. В следующий раз, когда сообщение SELinux записывается в журнал аудита, более простое для понимания сообщение записывается в системный журнал и по умолчанию может быть прочитано в /var/log/messages.
Ниже показан пример вывода:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 |
Nov <span class="number">2</span> <span class="number">10</span>:<span class="number">01</span>:<span class="number">40</span> server1 setroubleshoot: Plugin Exception restorecon Nov <span class="number">2</span> <span class="number">10</span>:<span class="number">01</span>:<span class="number">40</span> server1 setroubleshoot: SELinux is preventing <span class="regexp">/usr/sbin</span><span class="regexp">/httpd from getattr access on the file. For complete SELinux messages. run sealert -l 0ed02423-1149-4561-b6a08ea-2957329ea Nov 2 10:01:40 server1 python: SELinux is preventing /usr</span><span class="regexp">/sbin/httpd</span> from getattr access on the file. <span class="variable">**</span><span class="variable">**</span>* Plugin catchall_labels (<span class="number">83.8</span> confidence) suggests <span class="variable">**</span><span class="variable">**</span><span class="variable">**</span><span class="variable">**</span><span class="variable">**</span><span class="variable">**</span><span class="variable">**</span><span class="variable">**</span><span class="variable">**</span>* If you want to allow httpd to have getattr access on the file Then you need to change the label on <span class="variable">$FIX_TARGET_PATH</span> Do <span class="comment"># semanage fcontext -a -t FILE_TYPE '$FIX_TARGET_PATH'</span> where FILE_TYPE is one of the following: NetworkManager_exec_t, NetworkManager_log_t, --removed <span class="number">5</span> pages of the <span class="string">"one of the following"</span> output -- Then execute: restorecon <span class="operator">-v</span> <span class="string">'$FIX_TARGET_PATH'</span> <span class="variable">**</span><span class="variable">**</span>* Plugin catchall (<span class="number">17.1</span> confidence) suggests <span class="variable">**</span><span class="variable">**</span><span class="variable">**</span><span class="variable">**</span><span class="variable">**</span><span class="variable">**</span><span class="variable">**</span><span class="variable">**</span><span class="variable">**</span><span class="variable">**</span><span class="variable">**</span><span class="variable">**</span><span class="variable">**</span> If you believe that httpd should be allowed getattr access on the file by default. Then you should report this as a bug. You can generate a <span class="keyword">local</span> policy module to allow this access. Do allow this access <span class="keyword">for</span> now by executing: <span class="comment"># grep httpd /var/log/audit/audit.log | audit2allow -M mypol</span> <span class="comment"># semodule -i mypol.pp</span> |
Полезность в sealert состоит в том, что он пытается проанализировать то, что произошло, и на основе анализа он предлагает то, что вам нужно сделать, чтобы решить проблему. Не очень полезная часть заключается в том, что в некоторых случаях (как было в этом примере) отображаются сотни возможных типов контекста, и администратор должен выбрать правильный.
Работая с sealert, вы видите, что вызываются разные плагины, и каждый плагин имеет показатель достоверности. Если, как в примере, приведенном выше, один плагин дает оценку достоверности 83,8%, а другой дает оценку достоверности 17,1%, может быть очевидно, что первым подходом является то, что вам следует делать. К сожалению, однако, это не всегда так легко читается.
Итак. Если вы не уверены, что SELinux пытается вам рассказать, установите setroubleshoot-serverи проанализируйте, что показывает sealert. Информация, которую показывает sealert, часто намного более читабельна. Иногда это совсем не поможет, а иногда информация может оказаться весьма полезной.
Переход домена
До сих пор мы видели, как процессы обращаются к ресурсам файловой системы. Теперь посмотрим, как процессы получают доступ к другим процессам.
Domain transition – это метод, при котором процесс меняет свой контекст с одного домена на другой. Чтобы понять это, допустим, у вас есть процесс с именем proc_a, работающий в контексте contexta_t. При переходе домена proc_a может запускать приложение (программу или исполняемый скрипт) с именем app_x, которое может вызвать другой процесс. Этот новый процесс может называться proc_b, и он может выполняться в домене contextb_t. Таким образом, contexta_t transitioning для contextb_t через app_x. Исполняемый файл app_x работает как entrypoint для contextb_t.
Случай перехода домена довольно распространен в SELinux. Давайте рассмотрим процесс vsftpd, работающий на нашем сервере. Если он не запущен, мы можем запустить команду + service vsftpd start +
, чтобы запустить демон.
Далее мы рассмотрим процесс systemd. Это предок всех процессов. Это замена процесса инициализации System V и выполняется в контексте * init_t *. :
1 |
ps -eZ | grep init |
1 2 |
system_u:system_r:init_t:s0 1 ? 00:00:02 systemd system_u:system_r:mdadm_t:s0 773 ? 00:00:00 iprinit |
Процесс, выполняющийся в домене * init_t *, является недолговечным: он вызывает двоичный исполняемый файл + / usr / sbin / vsftpd +
, который имеет контекст типа * ftpd_exec_t *. Когда двоичный исполняемый файл запускается, он становится самим демоном vsftpd и запускается в домене * ftpd_t *.
Мы можем проверить доменные контексты файлов и процессов:
1 |
ls -Z /usr/sbin/vsftpd |
Показывает нам:
1 |
-rwxr-xr-x. root root system_u:object_r:ftpd_exec_t:s0 /usr/sbin/vsftpd |
Проверка процесса:
1 |
ps -eZ | grep vsftpd |
Показывает нам:
1 |
system_u:system_r:ftpd_t:s0-s0:c0.c1023 7708 ? 00:00:00 vsftpd |
Итак, процесс, запущенный в домене * init_t *, выполняет двоичный файл с типом * ftpd_exec_t *. Этот файл запускает демон в домене * ftpd_t *.
Этот переход не является чем-то, что приложение или пользователь может контролировать. Это было оговорено в политике SELinux, которая загружается в память при загрузке системы. На не-SELinux сервере пользователь может запустить процесс, переключившись на более мощную учетную запись (при условии, что он или она имеет на это право). В SELinux такой доступ контролируется предварительно написанными политиками. И это еще одна причина, по которой SELinux внедряет обязательный контроль доступа.
Переход домена зависит от трех строгих правил:
-
Родительский процесс исходного домена должен иметь разрешение на выполнение для приложения, расположенного между обоими доменами (это entrypoint).
-
Контекст файла для приложения должен быть идентифицирован как entrypoint для целевого домена.
-
Исходный домен должен быть разрешен для перехода в целевой домен.
Взяв приведенный выше пример демона vsftpd, давайте запустим команду + sesearch +
с различными ключами, чтобы проверить, соответствует ли демон этим трем правилам.
Во-первых, исходный домен init_t должен иметь разрешение на выполнение приложения точки входа с контекстом ftpd_exec_t. Так что, если мы запустим следующую команду:
1 |
sesearch -s init_t -t ftpd_exec_t -c file -p execute -Ad |
Результат показывает, что процессы в домене init_t могут читать, получать атрибуты, выполнять и открывать файлы контекста ftpd_exec_t:
1 2 |
Found 1 semantic av rules: allow init_t ftpd_exec_t : file { read getattr execute open } ; |
Далее мы проверяем, является ли двоичный файл точкой входа для целевого домена ftpd_t:
1 |
sesearch -s ftpd_t -t ftpd_exec_t -c file -p entrypoint -Ad |
И действительно, это так:
1 2 |
Found 1 semantic av rules: allow ftpd_t ftpd_exec_t : file { ioctl read getattr lock execute execute_no_trans entrypoint open } ; |
И, наконец, исходный домен init_t должен иметь разрешение на переход в целевой домен ftpd_t:
1 |
sesearch -s init_t -t ftpd_t -c process -p transition -Ad |
Как мы видим ниже, исходный домен имеет такое разрешение:
1 2 |
Found 1 semantic av rules: allow init_t ftpd_t : process transition ; |
Неопределенные домены
Когда мы представили концепцию доменов, мы сравнили ее с гипотетическим пузырем вокруг процесса: тем, что определяет, что процесс может и не может делать. Это то, что ограничивает процесс.
SELinux также имеет процессы, которые выполняются в неограниченных доменах. Как вы можете себе представить, неограниченные процессы будут иметь все типы доступа в системе. Даже тогда этот полный доступ не является произвольным: полный доступ также указывается в политике SELinux.
Примером неограниченного домена процесса будет undefined_t. Это тот же домен, в который вошли пользователи, запускающие их процессы по умолчанию. Мы поговорим о пользователях и их доступах для обработки доменов в следующих разделах.
Особенности работы пользователей и их контексты
Пользователи SELinux отличаются от обычных учетных записей пользователей Linux, включая учетную запись root. Пользователь SELinux – это не то, что вы создаете с помощью специальной команды, и у него нет собственного доступа для входа на сервер. Вместо этого пользователи SELinux определены в политике, которая загружается в память во время загрузки, и таких пользователей всего несколько. Имена пользователей заканчиваются на _u, так же как типы или имена доменов заканчиваются на _t, а роли заканчиваются на _r. Разные пользователи SELinux имеют разные права в системе, и это делает их полезными.
Пользователь SELinux, указанный в первой части контекста безопасности файла, является владельцем этого файла. Это похоже на то, как вы видите владельца файла в обычном выводе команды ls -l. Метка пользователя в контексте процесса показывает привилегию пользователя SELinux, с которой выполняется процесс.
Когда применяется SELinux, каждая учетная запись обычного пользователя Linux сопоставляется с учетной записью пользователя SELinux. С одним пользователем SELinux может быть сопоставлено несколько учетных записей пользователей. Это сопоставление позволяет обычной учетной записи наследовать разрешение своего аналога SELinux.
Для просмотра соотвествия пользователей и политик служит команда:
1 2 |
semanage login -l |
В CentOS 7, вы увидите что-то подобное:
1 2 3 4 5 |
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 * |
по мотивам:
https://max-ko.ru/14-upravlenie-selinux.html
https://www.codeflow.site/ru/article/an-introduction-to-selinux-on-centos-7-part-2-files-and-processes
Примечание
В моей системе CentOs 8 сообщения об ошибках SELinux не содержат путей к файлам:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 |
sealert -l ef5b16f8-4b5d-498d-a91f-215a821b05d3 SELinux запрещает php-fpm доступ write к каталог images. ***** Модуль httpd_write_content предлагает (точность 92.2) **************** Если вы хотите разрешить php-fpm иметь write доступ к images $TARGET_УЧЕБНЫЙ КЛАСС То необходимо изменить метку на «images» Сделать # semanage fcontext -a -t httpd_sys_rw_content_t 'images' # restorecon -v 'images' ***** Модуль catchall_boolean предлагает (точность 7.83) ******************* Если хотите allow httpd to unified То вы должны сообщить SELinux об этом, включив переключатель «httpd_unified». Сделать setsebool -P httpd_unified 1 ***** Модуль catchall предлагает (точность 1.41) *************************** Если вы считаете, что php-fpm должно быть разрешено write доступ к images directory по умолчанию. То рекомендуется создать отчет об ошибке. Чтобы разрешить доступ, можно создать локальный модуль политики. Сделать разрешить этот доступ сейчас, выполнив: # ausearch -c 'php-fpm'--raw | audit2allow -M my-phpfpm # semodule -X 300 -i my-phpfpm.pp Дополнительные сведения: Исходный контекст system_u:system_r:httpd_t:s0 Целевой контекст system_u:object_r:httpd_sys_content_t:s0 Целевые объекты images [ dir ] Источник php-fpm Путь к источнику php-fpm Порт <Unknown> Узел web-server Исходные пакеты RPM Целевые пакеты RPM Пакет регламента selinux-policy-3.14.3-41.el8_2.6.noarch SELinux активен True Тип регламента targeted Режим Enforcing Построчный вывод сообщений аудита type=AVC msg=audit(1604054231.594:371605): avc: denied { write } for pid=877659 comm="php-fpm" name="images" dev="dm-3" ino=395698 scontext=system_u:system_r:httpd_t:s0 tcontext=system_u:object_r:httpd_sys_content_t:s0 tclass=dir permissive=0 Hash: php-fpm,httpd_t,httpd_sys_content_t,dir,write |
Для нахождения имени файла используется find
find / -inum 395698