1 de octubre de 2008

Lo más básico de la seguridad en GNU/Linux

Hoy precisamente vi el blog de mi amigo José (Cuetzpallin), escribió un artículo muy interesante sobre varios tips de FreeBSD/Linux/Solaris. En uno de los apartados habla sobre los permisos que se pueden imponer a los scripts de shell con limits. En él, hace referencia al archivo de límites de PAM. Eso me llevó a recordar que hace tiempo impartí un curso de Linux en el que entre otras cosas hablé sobre los detalles más básicos del fortalecimiento de un servidor.
Sobre esto, sucede que los administradores nos preocupamos mucho en cuanto al aseguramiento del perímetro del servidor, poniéndole firewalls y cuanta cosa encontramos en la red y olvidamos lo que podríamos hacer si es que alguien logra obtener un shell por medio de una cuenta de usuario. Afortunadamente el propio sistema operativo trae algunas herramientas simples que nos pueden ayudar en nuestra tarea:

1. Archivo /etc/lilo.conf

Este es el archivo de configuración del LInux Loader (Cargador de Linux), de ahí su nombre (LILO).
Página manual: man 5 lilo.conf

Para asegurar que se teclee un password cuando se quiera arrancar un kernel, es necesario usar el keyword:
password=
Si se agrega esta opción es necesario hacer que el archivo sea de lectura sólo por el root.
Esto se logra con un: chmod 600 /etc/lilo.conf

restricted. Indica que se requerirá de un password durante el proceso de inicio del sistema si es que se especifica algún parámetro del kernel en la línea de comandos, como single.

Para que los cambios tengan efecto es necesario re compilar el archivo de inicio con el comando: lilo -v

2. Archivo /etc/inittab

El archivo inittab describe qué procesos se inician durante la inicialización del sistema y la operación normal. Es aquí en donde se distinguen múltiples run levels (niveles de ejecución), cada uno de los que pueden tener sus propios conjuntos de procesos para ser iniciados.
Página manual: man 5 inittab

Hay que buscar una línea parecida a:

ca:ctrlaltdel:/sbin/shutdown –t5 –r now

En la que se especifica cómo responderá el sistema al recibir la combinación de teclas Ctrl.+Alt+Del, la cual típicamente se usa para reiniciar el sistema.

Al final de esta línea se observa el comando que se ejecutará al recibir esta señal. La idea aquí es modificar las opciones del comando shutdown, el cual tiene un modificador (-a), que indica al sistema que deberá buscar en el archivo /etc/shutdown.allow la lista de usuarios con privilegios de reiniciar el sistema mediante esta combinación de teclas (véase man 8 shutdown).

Hay que modificar esta línea para que quede así:
ca:ctrlaltdel:/sbin/shutdown –t5 –a –r now
Crear el archive /etc/shutdown.allow y escriba el nombre de usuario de aquellos usuarios privilegiados, típicamente sólo se le permitirá al root. De tal forma, nadie más podrá reiniciar el sistema con este método.


3. Archivo /etc/fstab

El fstab o tabla de sistemas de archivos (file systems table), controla la manera en la que son tratados los sistemas de archivos, las opciones con las que se montan, el orden y la frecuencia con la que se revisan.
Página manual: man 5 fstab

Un archivo fstab se compone típicamente de 6 columnas de datos, mediante las cuales se definen los sistemas de archivos de una máquina Linux.
En una máquina personal, este archivo suele tener entradas como estas:

/dev/sda2 swap swap defaults 0 0
/dev/sda3 / ext3 defaults 1 1
/dev/sda1 /root ext3 defaults 1 2
/dev/cdrom /mnt/cdrom auto noauto,owner,ro 0 0
/dev/fd0 /mnt/floppy auto noaout,owner 0 0
devpts /dev/pts devpts gid=5,mode=620 0 0
proc /proc proc defaults 0 0

La primera columna indica la partición, la segunda es el punto de montaje, la tercera es el sistema de archivos, la cuarta son las opciones con las que se monta (véase también man 8 mount para una lista completa de las opciones de montaje), la quinta columna indica si el sistema de archivos debe ser revisado por el fsck y la última indica el orden en que debe hacerse esta revisión.

Ahora, en el caso de un servidor generalmente se recomienda tener más particiones, por lo que un esquema recomendable podría ser:

/dev/sda2 swap swap defaults 0 0
/dev/sda3 / ext3 defaults 1 1
/dev/sda1 /root ext3 defaults 1 2
/dev/sda4 /boot ext3 ro,nosuid,noexec,nouser 1 3
/dev/sda5 /tmp ext3 nosuid,noexec,nouser 1 4
/dev/sda6 /var/log ext3 nosuid,noexec,nouser 1 5
/dev/sda7 /usr/local ext3 defaults 1 6
/dev/sda8 /home ext3 defaults 0 0
/dev/cdrom /mnt/cdrom auto noauto,owner,ro 0 0
/dev/fd0 /mnt/floppy auto noaout,owner 0 0
devpts /dev/pts devpts gid=5,mode=620 0 0
proc /proc proc defaults 0 0

Las razones para poner tantas particiones son varias:

1. Según la definición de la LFH (http://tldp.org/LDP/Linux-Filesystem-Hierarchy/html/index.html), los directorios que se encuentran definidos aquí como particiones (o al menos la mayoría), no son necesarios para la inicialización de un sistema y por lo tanto pueden quedar como particiones independientes.
2. En un sentido más práctico, /root es en donde el administrador puede guardar todos sus archivos sin inundar el resto de la /. Lo mismo sucede con /home. /boot es en donde se guardan todos los archivos necesarios para el proceso de arranque del sistema, entre otras cosas, guarda la imagen del kernel, si bien aún existen dudas sobre si es sabio o no ponerlo como partición independiente, en este esquema se presenta así a fin de ponerle otorgar permisos de sólo lectura (ro), no ejecución de binairios suid (nosuid), no ejecución de programas (noexec), no manipulación de usuarios (nouser). Ya que nadie realmente más que el administrador debería modificar las imágenes del kernel.
Algo similar se aplica para /tmp, pues es esta partición en la que todos los usuarios pueden escribir, lo cual se torna potencialmente peligroso ya que aquí se pueden subir ciertos programas maliciosos mediante los cuales lanzar ataques internos al servidor. Por otro lado, se podría intentar una saturación del espacio libre desde esta partición.
En /var/log se guardan las bitácoras del sistema y no es buena idea que cualquiera puede ejecutar cosas en él. /usr/local es en donde generalmente (al menos en el caso de Slackware) se instalan los servidores de web /usr/local/apache, bases de datos (/usr/local/mysql y /usr/local/pgsql) y en general el software opcional.

En general, cada administrador puede crear el esquema de particionamiento que mejor le acomode, dependiendo sobre todo del propósito que va a tener el sistema que va a instalar.

4. Archivo /etc/login.defs

Este archivo define la configuración para la suite de programas que manejan los passwords del sistema, en este caso hablamos de la suite de shadow.

Página manual: man 5 login.defs

Este archivo típicamente trae entradas como las siguientes:

DIAPLUS_CHECK_ENAB yes
FAILLOG_ENAB yes
LOCK_UNFAIL_ENAB yes
LOG_OK_LOGINS yes
LASTLOG_ENAB yes
MAIL_CHECK_ENAB yes
OBSCURE_CHECKS_ENAB yes
PORTTIME_CHECKS_ENAB yes
QUOTAS_ENAB yes
SYSLOG_SU_ENAB yes
SYSLOG_SG_ENAB yes
CONSOLE /etc/securetty
MOTD_FILE /etc/motd
FTMP_FILE /var/log/btmp
NOLOGINS_FILE /etc/nologin
SU_NAME su
MAILDIR /var/spool/mail

5. Archivo /etc/securetty

El archive securetty contiene una lista con las terminales virtuales desde las cuales el administrador o root, puede entrar al sistema.

Página manual: man 5 securetty

En este archivo se definen todas aquellas terminales virtuales, tanto locales como remotas a través de las cuales un administrator del sistema puede acceder al mismo.

Por ejemplo, en le caso de las terminales locales se listan de la tty1 a la tty6, es decir, el administrator puede alejar cualquiera de las 6 terminales virtuales locales para poder acceder al servidor. Supóngase que queremos que el administrador solamente se conecte por medio de la tercera terminal local virtual (tty3).

Recordemos que para acceder a alguna de las terminales virtuales locales basta teclear la combinación Alt_FX, donde X es el número de la terminal a la que queremos entrar. Para el ejemplo, a fin de acceder a la tercera terminal local virtual deberemos teclear: Alt_F3 en donde veremos un prompt parecido a este:

Welcome to Linux 2.4.33.3 (tty3)
nunki login:

Ahora, para que esto tenga efecto es necesario dejar sin comentar en el archivo la línea referente al tty3. De tal manera, el usuario administrador del sistema no se podrá firmar en el sistema más que por la terminal local mencionada.


6. Archivo /etc/porttime

Este archive contiene una lista de los tty’s, los nombres de usuario y sus respectivas horas a las que tienen permitido entrar al sistema.

Página manual: man 5 porttime

Cada entrada del archivo consiste en tres campos separados por dos puntos (:) en donde el primer campo es una lista de terminales virtuales (separadas por coma), el segundo campo es una lista de nombres de usuario (separados por coma). En ambos casos puede utilizarse el comodín asterisco (*), que significa “todos”. Todos los nombres de usuario o bien, todas las terminales virtuales.
El tercer campo es una lista separada por coma de las horas y días en los cuales se permite el acceso.

Cada una de estas entradas se constuye a partir de cero o más días de la semana. Su, Mo, Tu, We, Th, Fr y Sa, seguidos de un par de horas separadas por un guión. También podemos usar la abreviación Wk (weekdays, o bien, entre semana), para representar los días de lunes a viernes; lo mismo Al que significa “todos los días”. Si no se especifica ningún día de la semana, se asume que se trata de Al.

Una entrada de la forma:

*:curso01:Wk0900-1700

Significa que el usuario curso01 puede acceder al sistema por medio de cualquier Terminal virtual, en cualquier día entre semana (de lunes a viernes), de las 9:00 AM a las 5:00 PM.

En el siguiente ejemplo se permite el acceso a los usuarios root y oper desde /dev/console en cualquier momento:

console:root,oper:Al0000-2400
console:*:

En cambio, la segunda línea especifica que el resto de los usuarios no tendrán acceso al sistema en ningún momento.

Como ejemplo final:

*:curso01:Wk1700-0900,SaSu0000-2400

Se describe una entrada que especifica que el usuario curso01 puede entrar al sistema desde cualquier terminal virtual fuera de horas de oficina (en este caso desde las 5:00 PM a las 9:00AM), así como los fines de semana durante todo el día.


7. Archivo /etc/limits

El archivo limits define las cotas superiores del uso de los recursos del sistema. En pocas palabras, cuánto y de qué pueden usar los usuarios.

Página manual: man 5 limits

Aquí describimos los límites que deseamos imponer a los usuarios en cuanto al uso de los recursos del sistema. Por defecto, el usuario root no tiene ningún tipo de cotas de hecho no exíste una manera de imponer límites a cuentas de usuario de tipo administrador (aquellas cuyo UID sea igual a cero).

Cada línea describe un límite para usuario de la forma:

usuario LIMITES

La cadena LIMITES se construye mediante la concatenación de límites de recursos. Cada límite consiste en una letra identificadora seguida de un límite numérico.

Los identificadores válidos son:

A: Máximo espacio de direcciones en Kb
C: Tamaño máximo de los archivos de volcado de memoria (core), en Kb.
D: Tamaño máximo de datos, en Kb.
F: Tamaño máximo de archivo, en Kb.
M: Tamaño máximo de direcciones bloqueadas en memoria (locked-in-memory), en Kb.
N: Tamaño máximo de archivos abiertos
R: Tamaño máximo de conjunto residente, en Kb.
S: Tamaño máximo del stack, en Kb.
T: Tiempo máximo del CPU (mins)
U: Número máximo de procesos
K: Máscara de creación de archivos, ver man 2 umask
L: Número máximo de logins en el sistema para el usuario.
P: Prioridad de los procesos, véase man 2 setpriority

Por ejemplo, L2D2048N5 es una cadena de límites válida. Para propósitos de facilitar la lectura, las siguientes entradas son equivalentes:

usuario L2D2048N5
usuario L2 D2048 N5

Debe tener en cuenta que cualquier cosa después del nombre del usuario se tomará como una cadena de límites y que no se permiten los comentarios. Así mismo, cualquier cadena con límites inválidos no será considerada.

La entrada por defecto se denota por el nombre de usuario ‘*’. Si se tienen varias reglas por defecto entonces se toma la última.

Por favor, note que estos limites son por login, no son globales ni permanentes.


8. Archivo /etc/nologin

El archivo nologin sirve para denegar de manera amistosa, el acceso de los usuarios al sistema.

Página manual: man 8 nologin

Si existe el archivo /etc/nologin, este comando despliega el contenido al usuario en lugar del mensaje por defecto del sistema.


Claro, exísten muchas otras maneras de asegurar el sistema y me parece que este es un buen inicio.

No hay comentarios.: