Ir al contenido

7.3 Auditoría de Puertos

tutorial.getReady

  • Entenderás cómo funciona un “Demonio en Escucha” (Sockets, IP, Puertos). - Sabrás utilizar ss para examinar todas las conexiones TCP y UDP de la máquina. - Dominarás el legendario lsof para descubrir qué proceso humano está usando el puerto 80.

Imagina que tu servidor es un edificio corporativo enorme con la Dirección IP 192.168.1.10. Si un ordenador externo intenta enviar un paquete a ese edificio, el paquete llega a la puerta principal y choca contra un muro. ¿A quién iba dirigido el paquete? ¿Al servidor web? ¿Al servidor de correo? ¿Al chat?

Para solucionar esto existen Los Puertos (Numerados típicamente del 1 al 65535). Son como las “extensiones telefónicas” del edificio. Cuando un paquete llega a la IP del servidor, el sistema operativo examina el número de puerto en el encabezado del paquete y lo redirige al proceso que está “escuchando” en ese puerto.

Clasificación de puertos:

RangoDescripciónEjemplos
1-1023Puertos privilegiados (solo procesos con privilegios de root pueden usar)22 (SSH), 80 (HTTP), 443 (HTTPS)
1024-49151Puertos registrados (asignados a servicios específicos)3306 (MySQL), 5432 (PostgreSQL)
49152-65535Puertos dinámicos/ephemeral (para conexiones salientes)Usados por clientes, no por servidores

El proceso de “escucha” (Bind):

Cuando un demonio (servicio) se inicia, realiza una operación llamada bind (atar) en un puerto específico. Esto reserva ese puerto para el proceso, y el proceso queda en estado LISTEN (escucha), esperando que lleguen paquetes destinados a ese puerto.

ventana terminal
# Ejemplo conceptual: Un servidor web se ata al puerto 80
# El sistema operativo asigna el puerto 80 al proceso nginx (PID 1055)
# Cualquier paquete que llegue al puerto 80 será entregado a nginx

¿Por qué es importante auditar los puertos?

  • Seguridad: Un puerto abierto innecesariamente es una superficie de ataque. Si no estás usando un servicio, deberías cerrar su puerto o limitar su acceso.
  • Resolución de conflictos: Dos servicios no pueden usar el mismo puerto al mismo tiempo. Si un servicio no arranca, puede ser porque otro está ocupando su puerto.
  • Cumplimiento normativo: Auditorías de seguridad (como PCI-DSS) requieren que solo los puertos necesarios estén abiertos.
  • Detección de intrusiones: Un puerto abierto inesperadamente podría indicar la presencia de malware o un backdoor.

En la antigüedad se usaba el comando netstat. Hoy en día (y en tu examen LFCS), está obsoleto por lento y ha sido reemplazado por Socket Statistics (ss) del paquete de redes (iproute2).

ss a pelo te lanzaría un millón de líneas con cada conexión interna de red. Los Sysadmins usamos siempre la misma composición de letras inamovibles: -tulpn

ventana terminal
sudo ss -tulpn

Desglose detallado de las opciones:

OpciónDescripciónEjemplo de uso
-tMuestra conexiones TCP (protocolo con confirmación, usado en web, SSH, bases de datos)Ver servicios web o SSH
-uMuestra conexiones UDP (protocolo sin confirmación, usado en DNS, streaming, gaming)Ver servicios DNS o NTP
-lLISTEN - Solo muestra puertos en modo escucha, oculta conexiones ya establecidasEnfocarse en servicios activos, no en clientes
-pPROGRAM - Muestra el PID y nombre del proceso dueño del puertoIdentificar qué programa está usando cada puerto
-nNUMERIC - Muestra puertos como números, evita resolver nombres de servicioVer :22 en lugar de :ssh, más rápido y claro

Interpretación de la salida de ss:

ventana terminal
tcp LISTEN 0 128 0.0.0.0:80 0.0.0.0:* users:(("nginx",pid=1055,fd=6))
CampoSignificadoEjemplo
ProtocoloTCP o UDPtcp
EstadoLISTEN (escuchando), ESTABLISHED (establecida), etc.LISTEN
Recv-QBytes recibidos en cola sin procesar0 (sin datos pendientes)
Send-QBytes enviados en cola sin confirmar128 (tamaño de la cola)
Dirección LocalIP y puerto donde el proceso está escuchando (0.0.0.0 = todas las interfaces)0.0.0.0:80
Dirección RemotaIP y puerto del cliente (si hay conexión establecida)0.0.0.0:* (cualquier cliente)
ProcesoPrograma dueño del puerto, con su PID y descriptor de archivo(“nginx”,pid=1055,fd=6)

Análisis de “Dirección Atada” (la clave de seguridad):

Dirección AtadaSignificadoNivel de Exposición
0.0.0.0:80Escucha en todas las interfaces de red (públicas y privadas). Accesible desde Internet.🔴 ALTO
127.0.0.1:80Escucha solo en localhost (bucle interno). Solo accesible desde el mismo servidor.🟢 BAJO
192.168.1.10:80Escucha en una IP específica de la red interna. Accesible solo desde esa red.🟡 MEDIO

Ejemplo de un servidor mal configurado:

ventana terminal
# MySQL escuchando en todas las interfaces (PELIGROSO)
tcp LISTEN 0 128 0.0.0.0:3306 0.0.0.0:* users:(("mysqld",pid=1234,fd=10))
# MySQL bien configurado (solo localhost)
tcp LISTEN 0 128 127.0.0.1:3306 0.0.0.0:* users:(("mysqld",pid=1234,fd=10))

Si ss es la visión general del país, List Open Files (lsof) es el láser milimétrico enfocado a una sola ciudad.

El principio fundamental de Unix:

Casos de uso comunes de lsof:

  1. Resolver conflictos de puertos:

    ventana terminal
    # ¿Quién está usando el puerto 80?
    sudo lsof -i :80
    # Salida:
    # nginx 1055 root 6u IPv4 12345 0t0 TCP *:http (LISTEN)
  2. Ver qué procesos están usando un archivo específico:

    ventana terminal
    # ¿Quién está usando el archivo de configuración de Apache?
    sudo lsof /etc/apache2/apache2.conf
  3. Listar todas las conexiones de red de un usuario específico:

    ventana terminal
    # ¿Qué conexiones de red tiene abiertas el usuario <usuario>?
    sudo lsof -u <usuario> -i
  4. Ver qué archivos tiene abiertos un proceso específico:

    ventana terminal
    # ¿Qué archivos tiene abiertos nginx?
    sudo lsof -p 1055
  5. Combinar con grep para búsquedas específicas:

    ventana terminal
    # Buscar procesos que escuchan en puertos altos (posibles backdoors)
    sudo lsof -i | grep LISTEN | grep -E ':[0-9]{5}'

Estructura de la salida de lsof:

ventana terminal
COMMAND PID USER FD TYPE DEVICE SIZE/OFF NODE NAME
nginx 1055 root 6u IPv4 12345 0t0 TCP *:http (LISTEN)
nginx 1056 www-data 7u IPv4 12346 0t0 TCP *:http (LISTEN)
CampoSignificado
COMMANDNombre del comando/proceso
PIDID del proceso
USERPropietario del proceso
FDDescriptor de archivo (6u = archivo abierto en modo lectura-escritura)
TYPETipo de archivo (IPv4, IPv6, REG = regular, DIR = directorio)
DEVICENúmero de dispositivo
SIZE/OFFTamaño del archivo o offset
NODENúmero de inodo
NAMENombre del archivo o dirección IP:puerto

Solución de problemas comunes con puertos:

ventana terminal
# Escenario: Apache no arranca porque el puerto 80 está ocupado
# Paso 1: Verificar quién está usando el puerto 80
sudo lsof -i :80
# Salida:
# nginx 1055 root 6u IPv4 12345 0t0 TCP *:http (LISTEN)
# Paso 2: Decidir si detener nginx o cambiar el puerto de Apache
sudo systemctl stop nginx
# Paso 3: Verificar que el puerto está libre
sudo ss -tulpn | grep :80
# No debe haber salida
# Paso 4: Iniciar Apache
sudo systemctl start apache2
# Opción alternativa: Matar el proceso directamente (con cuidado)
sudo kill -9 1055

4. Otros Comandos Útiles para Auditoría de Puertos

Sección titulada “4. Otros Comandos Útiles para Auditoría de Puertos"

1. nmap (escaneo de puertos remoto):

ventana terminal
# Escanear puertos comunes en un servidor remoto (desde otra máquina)
nmap -sS -p 22,80,443,3306 192.168.1.10
# Escaneo rápido de los 1000 puertos más comunes
nmap -T4 -F 192.168.1.10

2. netstat (obsoleto pero aún presente):

ventana terminal
# Alternativa antigua a ss (no recomendada para el examen LFCS)
netstat -tulpn

3. fuser (identificar procesos por puerto o archivo):

ventana terminal
# Identificar el proceso que usa el puerto 80
sudo fuser -v 80/tcp
# Matar el proceso que usa el puerto 80
sudo fuser -k 80/tcp

4. journalctl (logs de servicios):

ventana terminal
# Ver logs relacionados con fallos de bind (puerto en uso)
sudo journalctl -u apache2 -f

5. Buenas Prácticas para la Auditoría de Puertos

Sección titulada “5. Buenas Prácticas para la Auditoría de Puertos"
  1. Auditar regularmente los puertos abiertos:

    ventana terminal
    # Script simple para revisar puertos abiertos diariamente
    sudo ss -tulpn > /var/log/port_audit_$(date +%Y%m%d).log
  2. Usar firewalls para limitar el acceso:

    ventana terminal
    # Permitir solo SSH desde la red local
    sudo ufw allow from 192.168.1.0/24 to any port 22
  3. Configurar servicios para que escuchen solo en localhost cuando sea posible:

    ventana terminal
    # En /etc/mysql/mysql.conf.d/mysqld.cnf
    bind-address = 127.0.0.1
  4. Monitorear cambios inesperados en los puertos:

    ventana terminal
    # Comparar estado actual con una línea base
    sudo ss -tulpn | diff - /var/log/port_audit_baseline.log
  5. Documentar todos los puertos abiertos y su propósito:

PuertoServicioPropósitoResponsable
22SSHAdministración remotaSysadmin
80HTTPServidor webDev Team
443HTTPSServidor web seguroDev Team
3306MySQLBase de datos (solo localhost)DBA

Comprueba tus conocimientos (Versión Mejorada)

Sección titulada “Comprueba tus conocimientos (Versión Mejorada)"
  1. Contexto: Acabas de instalar un servidor de base de datos PostgreSQL en tu servidor de producción. Después de iniciar el servicio, ejecutas sudo ss -tulpn y ves la siguiente línea: tcp LISTEN 0 128 0.0.0.0:5432 0.0.0.0:* users:(("postgres",pid=456,fd=3)). Analizando la dirección de atado (0.0.0.0:5432), ¿cuál es tu evaluación de seguridad?

  2. Contexto: Un desarrollador te reporta que su aplicación Java no puede iniciarse porque el puerto 8080 ya está en uso. Necesitas identificar rápidamente qué proceso está ocupando ese puerto para detenerlo o reconfigurarlo. De los siguientes comandos, ¿cuál es el más efectivo para obtener información precisa (PID, nombre del proceso, usuario) de forma directa y sin ruido?

  3. Contexto: Estás realizando una auditoría de seguridad en tu servidor y encuentras un servicio llamado redis-server escuchando en el puerto 6379 con la siguiente salida de ss -tulpn: tcp LISTEN 0 128 127.0.0.1:6379 0.0.0.0:* users:(("redis-server",pid=789,fd=6)). Además, notas que el archivo de configuración de Redis tiene bind 0.0.0.0 y protected-mode no. ¿Cuál es la mejor acción a tomar?