Serie RHCSA: Esenciales de control de acceso obligatorio con SELinux en RHEL 7 - Parte 13


Durante esta serie, hemos explorado en detalle al menos dos métodos de control de acceso: permisos ugo/rwx estándar (Configurar ACL en sistemas de archivos - Parte 7).

Aunque son necesarios como permisos de primer nivel y mecanismos de control de acceso, tienen algunas limitaciones que son abordadas por Security Enhanced Linux (también conocido como SELinux para abreviar).

Una de esas limitaciones es que un usuario puede exponer un archivo o directorio a una brecha de seguridad a través de un comando chmod mal elaborado y, por lo tanto, causar una propagación inesperada de los derechos de acceso. Como resultado, cualquier proceso iniciado por ese usuario puede hacer lo que quiera con los archivos propiedad del usuario, donde finalmente un software malicioso o comprometido puede lograr acceso de nivel raíz a todo el sistema.

Con esas limitaciones en mente, la Agencia de Seguridad Nacional de los Estados Unidos (NSA) diseñó primero SELinux, un método flexible de control de acceso obligatorio, para restringir la capacidad de los procesos para acceder o realizar otras operaciones en los objetos del sistema (como archivos, directorios, puertos de red). , etc.) al modelo de menor permiso, que se puede modificar más adelante según sea necesario. En pocas palabras, a cada elemento del sistema se le da solo el acceso requerido para funcionar.

En RHEL 7, SELinux está incorporado en el propio kernel y está habilitado en el modo Enforcing de forma predeterminada. En este artículo explicaremos brevemente los conceptos básicos asociados con SELinux y su funcionamiento.

Modos SELinux

SELinux puede operar de tres formas diferentes:

  1. Aplicación: SELinux niega el acceso según las reglas de política de SELinux, un conjunto de pautas que controlan el motor de seguridad.
  2. Permisivo: SELinux no niega el acceso, pero las denegaciones se registran para acciones que se habrían denegado si se ejecutaran en modo de aplicación.
  3. Discapacitado (se explica por sí mismo).

El comando getenforce muestra el modo actual de SELinux, mientras que setenforce (seguido de un 1 o un 0) se usa para cambiar el modo a Enforcing o Permissive, respectivamente, durante el sesión actual solamente.

Para lograr la persistencia entre cierres de sesión y reinicios, deberá editar el archivo /etc/selinux/config y establecer la variable SELINUX en forzado, permisivo o deshabilitado:

# getenforce
# setenforce 0
# getenforce
# setenforce 1
# getenforce
# cat /etc/selinux/config

Por lo general, usará setenforce para alternar entre los modos SELinux (forzar a permisivo y viceversa) como primer paso de solución de problemas. Si SELinux está configurado actualmente para hacer cumplir mientras experimenta un cierto problema, y lo mismo desaparece cuando lo configura como permisivo, puede estar seguro de que está viendo un problema de permisos de SELinux.

Contextos de SELinux

Un contexto de SELinux consiste en un entorno de control de acceso donde las decisiones se toman en función del usuario, el rol y el tipo de SELinux (y, opcionalmente, un nivel):

  1. Un usuario de SELinux complementa una cuenta de usuario de Linux normal asignándola a una cuenta de usuario de SELinux, que a su vez se utiliza en el contexto de SELinux para los procesos en esa sesión, con el fin de definir explícitamente sus roles y niveles permitidos.
  2. El concepto de rol actúa como intermediario entre los dominios y los usuarios de SELinux, ya que define a qué dominios de proceso y tipos de archivos se puede acceder. Esto protegerá su sistema contra la vulnerabilidad a los ataques de escalada de privilegios.
  3. Un tipo define un tipo de archivo SELinux o un dominio de proceso SELinux. En circunstancias normales, se impide que los procesos accedan a los archivos que utilizan otros procesos y que accedan a otros procesos, por lo que el acceso solo se permite si existe una regla de política SELinux específica que lo permita.

Veamos cómo funciona todo eso a través de los siguientes ejemplos.

En Asegurar SSH - Parte 8 explicamos que cambiar el puerto predeterminado donde escucha sshd es una de las primeras medidas de seguridad para proteger su servidor contra ataques externos. Editemos el archivo /etc/ssh/sshd_config y establezcamos el puerto en 9999:

Port 9999

Guarde los cambios y reinicie sshd:

# systemctl restart sshd
# systemctl status sshd

Como puede ver, sshd no pudo iniciarse. ¿Pero qué pasó?

Una inspección rápida de /var/log/audit/audit.log indica que a sshd se le han negado los permisos para iniciarse en el puerto 9999 (los mensajes de registro de SELinux incluyen la palabra "AVC" para que puedan identificarse fácilmente de otros mensajes) porque ese es un puerto reservado para el servicio JBoss Management:

# cat /var/log/audit/audit.log | grep AVC | tail -1

En este punto, puede deshabilitar SELinux (¡pero no lo haga!) Como se explicó anteriormente e intentar iniciar sshd nuevamente, y debería funcionar. Sin embargo, la utilidad semanage puede decirnos qué necesitamos cambiar para que podamos iniciar sshd en cualquier puerto que elijamos sin problemas.

Correr,

# semanage port -l | grep ssh

para obtener una lista de los puertos donde SELinux permite que sshd escuche.

Así que cambiemos el puerto en /etc/ssh/sshd_config al puerto 9998, agreguemos el puerto al contexto ssh_port_t y luego reiniciemos el servicio:

# semanage port -a -t ssh_port_t -p tcp 9998
# systemctl restart sshd
# systemctl is-active sshd

Como puede ver, el servicio se inició con éxito esta vez. Este ejemplo ilustra el hecho de que SELinux controla el número de puerto TCP a sus propias definiciones internas de tipo de puerto.

Este es un ejemplo de SELinux administrando un proceso accediendo a otro proceso. Si tuviera que implementar mod_security y mod_evasive junto con Apache en su servidor RHEL 7, debe permitir que httpd acceda a sendmail para enviar una notificación por correo después de un ataque (D) DoS. En el siguiente comando, omita la marca -P si no desea que el cambio sea persistente entre reinicios.

# semanage boolean -1 | grep httpd_can_sendmail
# setsebool -P httpd_can_sendmail 1
# semanage boolean -1 | grep httpd_can_sendmail

Como puede ver en el ejemplo anterior, las configuraciones booleanas de SELinux (o simplemente booleanas) son reglas de verdadero/falso incrustadas en las políticas de SELinux. Puede enumerar todos los valores booleanos con semanage boolean -l y, alternativamente, canalizarlos a grep para filtrar la salida.

Suponga que está sirviendo un sitio web estático usando un directorio diferente al predeterminado (/var/www/html ), digamos/websites (este podría ser el caso si está almacenando sus archivos web en un unidad de red compartida, por ejemplo, y necesita montarla en/websites).

a). Cree un archivo index.html dentro de/websites con el siguiente contenido:

<html>
<h2>SELinux test</h2>
</html>

Si lo haces,

# ls -lZ /websites/index.html

verá que el archivo index.html ha sido etiquetado con el tipo default_t SELinux, al que Apache no puede acceder:

B). Cambie la directiva DocumentRoot en /etc/httpd/conf/httpd.conf a/websites y no olvide actualizar el bloque de directorio correspondiente. Luego, reinicie Apache.

C). Vaya a http:// y debería obtener una respuesta HTTP prohibida 503.

D). A continuación, cambie la etiqueta de/websites, de forma recursiva, al tipo httpd_sys_content_t para otorgar a Apache acceso de solo lectura a ese directorio y su contenido:

# semanage fcontext -a -t httpd_sys_content_t "/websites(/.*)?"

mi). Finalmente, aplique la política de SELinux creada en d):

# restorecon -R -v /websites

Ahora reinicie Apache y busque http:// nuevamente y verá que el archivo html se muestra correctamente:

Resumen

En este artículo hemos analizado los conceptos básicos de SELinux. Tenga en cuenta que debido a la amplitud del tema, no es posible una explicación detallada completa en un solo artículo, pero creemos que los principios descritos en esta guía lo ayudarán a pasar a temas más avanzados si así lo desea.

Si puedo, permítame recomendarle dos recursos esenciales para comenzar: la guía del usuario y del administrador de RHEL 7 SELinux.

No dude en informarnos si tiene alguna pregunta o comentario.