Práctica 4 — Arranque y Servicios
Setup — ejecutar una sola vez
Sección titulada “Setup — ejecutar una sola vez"mkdir -p ~/practica4/{work,entrega}sudo apt update && sudo apt install -y nginxmkdir -p ~/practica4/{work,entrega}sudo dnf install -y nginxmkdir -p ~/practica4/{work,entrega}sudo pacman -S nginxTodo lo que se pida “guardar” debe ir dentro de ~/practica4/entrega/.
Ejercicio 4.1 — Diagnóstico del proceso de arranque
Sección titulada “Ejercicio 4.1 — Diagnóstico del proceso de arranque"Contexto
Sección titulada “Contexto"Un sysadmin real no espera a que el sistema falle para aprender cómo arranca. Antes de intervenir quirúrgicamente en un servidor, necesitas saber leer su historia de arranque: cuánto tardó cada fase, qué servicio fue el más lento, qué mensajes emitió el kernel al despertar. Aquí aprenderás a usar las tres fuentes de información del arranque.
- Mide el tiempo de arranque del sistema. El comando
systemd-analyzedescompone el tiempo total en fases. Guarda en~/practica4/entrega/41_boot_time.txt:
systemd-analyzesystemd-analyze blame | head -20systemd-analyze critical-chainAñade un comentario # identificando qué servicio tardó más y en qué fase del arranque (firmware, loader, kernel, userspace).
- Lee los mensajes del kernel. El buffer de arranque del kernel contiene toda la comunicación interna de las primeras fases:
dmesg | head -30dmesg | grep -i "error\|fail\|warn" | head -15dmesg | grep -i "usb\|net\|eth\|ens" | head -10Guarda la salida en ~/practica4/entrega/41_dmesg.txt. Identifica con un comentario # si hay algún warning real o si el sistema arrancó limpio.
- Inspecciona el arranque actual con journalctl. A diferencia de
dmesg,journalctl -bincluye los mensajes de todos los servicios de systemd desde el último arranque:
# Resumen del arranque actualjournalctl -b --no-pager | wc -l
# Errores y advertencias del arranquejournalctl -b -p warning --no-pager | head -30
# Tiempo de arranque de los servicios más lentossystemd-analyze blame | head -10Guarda en ~/practica4/entrega/41_journal_boot.txt.
- Localiza los targets de systemd activos. Los targets reemplazan a los runlevels clásicos:
systemctl get-defaultsystemctl list-units --type=target --state=activeGuarda la salida en ~/practica4/entrega/41_targets.txt. Explica en un comentario # la diferencia entre multi-user.target y graphical.target.
Ejercicio 4.2 — GRUB y módulos del kernel
Sección titulada “Ejercicio 4.2 — GRUB y módulos del kernel"Contexto
Sección titulada “Contexto"GRUB es la puerta de entrada al sistema. Un sysadmin LFCS debe saber configurarlo de forma permanente y entender cómo el kernel carga sus drivers (módulos) de forma dinámica. Aquí practicarás ambas habilidades sin poner en riesgo el arranque.
- Audita la configuración actual de GRUB. Antes de tocar nada, documenta el estado actual:
cat /etc/default/grubls -la /boot/grub/Guarda en ~/practica4/entrega/42_grub_previo.txt. Identifica con comentarios # el valor actual de GRUB_TIMEOUT y los parámetros del kernel en GRUB_CMDLINE_LINUX_DEFAULT.
- Modifica el timeout de GRUB de forma permanente. Edita el fichero maestro de GRUB:
sudo nano /etc/default/grubCambia GRUB_TIMEOUT a 3 (de 5 a 3 segundos). Luego aplica el cambio:
sudo update-grubVerifica que el cambio se propagó al archivo binario compilado:
grep "set timeout" /boot/grub/grub.cfgGuarda los comandos y su salida en ~/practica4/entrega/42_grub_modificado.txt.
- Inspecciona los módulos del kernel activos. Los módulos son los drivers dinámicos del kernel:
# Lista todos los módulos cargadoslsmod | head -20
# Cuántos módulos hay activos en totallsmod | wc -l
# Información detallada de un módulo concretomodinfo usbcore | head -15Guarda en ~/practica4/entrega/42_lsmod.txt.
- Carga y descarga un módulo en caliente. Usa el módulo
dummy(un módulo de red virtual que no afecta al sistema):
# Comprueba que no está cargadolsmod | grep dummy
# Cárgalosudo modprobe dummy
# Verifica que aparece ahoralsmod | grep dummy
# Descárgalosudo modprobe -r dummy
# Verifica que ha desaparecidolsmod | grep dummy || echo "módulo descargado correctamente"Guarda los comandos y su salida en ~/practica4/entrega/42_modprobe.txt. Explica con un comentario # en qué se diferencia modprobe de insmod.
Ejercicio 4.3 — Control de servicios con systemctl
Sección titulada “Ejercicio 4.3 — Control de servicios con systemctl"Contexto
Sección titulada “Contexto"systemctl es el mando a distancia de todos los demonios del servidor. El error más frecuente en producción es usar restart cuando debería usarse reload, cortando conexiones activas innecesariamente. Aquí practicarás el ciclo de vida completo de un servicio real: nginx.
- Audita el estado inicial de nginx antes de tocarlo:
systemctl status nginxsystemctl is-active nginxsystemctl is-enabled nginxGuarda en ~/practica4/entrega/43_nginx_previo.txt. Identifica con comentarios # si está activo y si está habilitado para arrancar automáticamente.
- Practica el ciclo de vida completo. Ejecuta cada comando y guarda la salida de
statusdespués de cada cambio:
# Para el serviciosudo systemctl stop nginxsystemctl status nginx --no-pager | head -5
# Arráncalo de nuevosudo systemctl start nginxsystemctl status nginx --no-pager | head -5
# Deshabilita el arranque automáticosudo systemctl disable nginxsystemctl is-enabled nginx
# Habilítalo de nuevosudo systemctl enable nginxsystemctl is-enabled nginxGuarda todo en ~/practica4/entrega/43_ciclo_vida.txt.
- Demuestra la diferencia entre
restartyreload. Esta es la distinción más importante para producción.
Primero, observa el PID del proceso actual:
systemctl status nginx --no-pager | grep "Main PID"Luego haz restart y comprueba el PID:
sudo systemctl restart nginxsystemctl status nginx --no-pager | grep "Main PID"El PID cambió — se mató y creó un proceso nuevo.
Ahora haz reload y comprueba el PID:
sudo systemctl reload nginxsystemctl status nginx --no-pager | grep "Main PID"El PID no cambió — el proceso releyó la configuración sin morir.
Guarda los tres estados (PID inicial, tras restart, tras reload) en ~/practica4/entrega/43_restart_vs_reload.txt. Añade un comentario # explicando cuándo usarías cada uno en producción.
- Usa el modificador
--nowpara operaciones combinadas. En LFCS es habitual necesitar habilitar Y arrancar en un solo paso:
# Deshabilita y para en un solo comandosudo systemctl disable --now nginxsystemctl status nginx --no-pager | head -5
# Habilita y arranca en un solo comandosudo systemctl enable --now nginxsystemctl status nginx --no-pager | head -5Guarda en ~/practica4/entrega/43_now_flag.txt.
- Lista todos los servicios y filtra por estado:
# Servicios fallidos (si los hay)systemctl list-units --type=service --state=failed
# Servicios activossystemctl list-units --type=service --state=active | head -20Guarda en ~/practica4/entrega/43_list_services.txt.
Ejercicio 4.4 — Crear una unidad systemd y un timer
Sección titulada “Ejercicio 4.4 — Crear una unidad systemd y un timer"Contexto
Sección titulada “Contexto"Cualquier script puede convertirse en un servicio gestionado por systemd. Los timers son la alternativa moderna a cron, integrados con journalctl para auditoría. Aquí construirás una unidad desde cero y la automatizarás.
Setup — preparar el script que el servicio ejecutará
Sección titulada “Setup — preparar el script que el servicio ejecutará"sudo nano /usr/local/bin/monitor_disco.shEscribe exactamente este contenido:
#!/bin/bash# monitor_disco.sh — registra el uso del disco en un log
LOGFILE="/var/log/monitor_disco.log"FECHA=$(date '+%Y-%m-%d %H:%M:%S')USO=$(df -h / | tail -1 | awk '{print $5}')
echo "[$FECHA] Uso del disco raíz: $USO" >> "$LOGFILE"Dale permisos y prueba que funciona:
sudo chmod +x /usr/local/bin/monitor_disco.shsudo /usr/local/bin/monitor_disco.shcat /var/log/monitor_disco.log# Debe aparecer una línea con la fecha y el porcentaje de uso del discoTarea 1 — Crear la unidad de servicio
Sección titulada “Tarea 1 — Crear la unidad de servicio"Las unidades systemd viven en /etc/systemd/system/. Crea el archivo:
sudo nano /etc/systemd/system/monitor-disco.serviceEscribe:
[Unit]Description=Monitor de uso del discoDocumentation=man:df(1)
[Service]Type=oneshotExecStart=/usr/local/bin/monitor_disco.sh
[Install]WantedBy=multi-user.targetPrueba que el servicio funciona:
# Recarga la configuración de systemd (siempre después de crear/editar una unidad)sudo systemctl daemon-reload
# Ejecuta el servicio manualmentesudo systemctl start monitor-disco.service
# Verifica que se ejecutósystemctl status monitor-disco.servicecat /var/log/monitor_disco.log# Debe haber una línea nueva con la fecha actualTarea 2 — Crear el timer
Sección titulada “Tarea 2 — Crear el timer"El timer define cuándo ejecutar el servicio. Crea:
sudo nano /etc/systemd/system/monitor-disco.timerEscribe:
[Unit]Description=Timer para el monitor de disco (cada 5 minutos)
[Timer]OnCalendar=*:0/5Persistent=true
[Install]WantedBy=timers.targetActiva y arranca el timer:
sudo systemctl daemon-reloadsudo systemctl enable monitor-disco.timersudo systemctl start monitor-disco.timersystemctl status monitor-disco.timerVerifica que aparece en la lista de timers:
systemctl list-timers | grep monitorDeberías ver la próxima ejecución programada.
Tarea 3 — Forzar una ejecución y verificar el log
Sección titulada “Tarea 3 — Forzar una ejecución y verificar el log"# Fuerza ejecución inmediata del servicio (no del timer)sudo systemctl start monitor-disco.service
# Ve el log en tiempo realsudo tail -f /var/log/monitor_disco.log# (Pulsa Ctrl+C para salir)
# También puedes ver el historial de ejecuciones en journalctljournalctl -u monitor-disco.service -n 10 --no-pagerGuarda el estado final en ~/practica4/entrega/44_timer_verificacion.txt:
{ systemctl status monitor-disco.timer --no-pager echo "" systemctl list-timers | grep monitor echo "" tail -5 /var/log/monitor_disco.log echo "" cat /etc/systemd/system/monitor-disco.service echo "" cat /etc/systemd/system/monitor-disco.timer} > ~/practica4/entrega/44_timer_verificacion.txtEjercicio 4.5 — Auditoría forense con journalctl y /var/log
Sección titulada “Ejercicio 4.5 — Auditoría forense con journalctl y /var/log"Contexto
Sección titulada “Contexto"Un sysadmin senior nunca adivina. Cuando algo falla, va directamente a los logs con filtros precisos. Aquí aprenderás a interrogar el diario de systemd como un francotirador: por servicio, por tiempo, por severidad.
- Explora
/var/logantes de usar journalctl. Los logs de texto tradicionales siguen existiendo:
ls -lh /var/log/ls -lh /var/log/nginx/ 2>/dev/null || echo "nginx no tiene logs todavía"Lee los últimos 20 accesos a SSH:
sudo tail -20 /var/log/auth.logGuarda en ~/practica4/entrega/45_varlog.txt. Identifica con comentarios # qué contiene cada fichero que veas en /var/log.
- Filtra journalctl por servicio. Practica los filtros más usados en LFCS:
# Todos los logs de nginxjournalctl -u nginx --no-pager | wc -l
# Últimas 15 líneas de nginxjournalctl -u nginx -n 15 --no-pager
# Logs de SSH de la sesión actualjournalctl -u ssh -n 20 --no-pagerGuarda en ~/practica4/entrega/45_journal_servicios.txt.
- Filtra por tiempo. Esta es la habilidad más valiosa para diagnosticar incidentes:
# Logs de hoyjournalctl --since "today" --no-pager | wc -l
# Logs de la última horajournalctl --since "1 hour ago" --no-pager | tail -20
# Logs de nginx en un rango concreto (ajusta la hora a una que tenga entradas)journalctl -u nginx --since "$(date '+%Y-%m-%d') 00:00:00" --until "$(date '+%Y-%m-%d') 23:59:59" --no-pager | tail -10Guarda en ~/practica4/entrega/45_journal_tiempo.txt.
- Filtra por severidad. Los niveles van de 0 (emerg) a 7 (debug):
# Solo errores y superiores en todo el sistemajournalctl -p err --no-pager | tail -20
# Errores del arranque actualjournalctl -b -p warning --no-pager | tail -15
# La combinación definitiva: errores de un servicio en la última horajournalctl -u nginx -p warning --since "1 hour ago" --no-pagerGuarda en ~/practica4/entrega/45_journal_severidad.txt.
- Genera un informe de actividad SSH sospechosa. Simula una investigación de seguridad básica:
# Intentos de login fallidossudo grep "Failed password\|authentication failure" /var/log/auth.log | tail -10
# Logins exitosos recientessudo grep "Accepted\|session opened" /var/log/auth.log | tail -10
# Accesos con sudosudo grep "sudo" /var/log/auth.log | tail -10Guarda en ~/practica4/entrega/45_auditoria_ssh.txt. Añade comentarios # describiendo qué patrón representa cada bloque.
📤 Bloque de entrega
Sección titulada “📤 Bloque de entrega"Guarda la verificación del estado antes de empaquetar:
{ echo "=== ENTREGA PRÁCTICA 4 ===" echo "" echo "--- 4.1: Tiempo de arranque ---" systemd-analyze echo "" echo "--- 4.2: GRUB timeout configurado ---" grep "GRUB_TIMEOUT" /etc/default/grub echo "" echo "--- 4.3: Estado de nginx ---" systemctl status nginx --no-pager | head -8 echo "" echo "--- 4.4: Estado del timer ---" systemctl status monitor-disco.timer --no-pager | head -8 echo "" echo "--- 4.4: Próxima ejecución ---" systemctl list-timers | grep monitor echo "" echo "--- 4.4: Últimas entradas del log ---" tail -5 /var/log/monitor_disco.log echo "" echo "--- 4.5: Últimos errores del sistema ---" journalctl -p err --no-pager | tail -5} > ~/practica4/entrega/verificacion.txtPara empaquetar y enviar, sigue las instrucciones comunes: Cómo entregar las prácticas (usa N = 4).
🧨 Desafíos extra (MUY DIFÍCILES) — Troubleshooting de servicios
Sección titulada “🧨 Desafíos extra (MUY DIFÍCILES) — Troubleshooting de servicios"Estos ejercicios están diseñados para ser difíciles. No hay una sola pista mágica: tendrás que leer los logs, analizar la sintaxis, reproducir el error y corregirlo sistemáticamente.
Reglas:
- Solo puedes usar comandos de terminal y herramientas del módulo 4.
- No se permite borrar y recrear el servicio desde cero sin entender el error.
- Todo el trabajo se documenta en
~/practica4/entrega/.
Ejercicio 4.6 ⚡ EXTRA — Reparar una unidad systemd con errores
Sección titulada “Ejercicio 4.6 ⚡ EXTRA — Reparar una unidad systemd con errores"Contexto
Sección titulada “Contexto"Alguien creó una unidad systemd con errores tipográficos. El servicio no arranca. Tu trabajo es encontrar todos los errores usando las herramientas de diagnóstico de systemd y corregirlos.
Setup — crear el servicio roto
Sección titulada “Setup — crear el servicio roto"sudo nano /etc/systemd/system/app-demo.serviceCopia esto exactamente como está (con los errores):
[Unit]Description=Aplicación de demostraciónAfter=network.tarjet
[Service]ExecSart=/usr/local/bin/app-demoRestart=alwaysUser=nobody
[Instal]WantedBy=multi-user.targetsudo systemctl daemon-reloadDiagnóstico — encuentra los errores
Sección titulada “Diagnóstico — encuentra los errores"systemd te dará pistas, pero debes saber interpretarlas. Sigue este proceso:
Paso 1 — Intenta arrancar y observa el error:
sudo systemctl start app-demo.servicesystemctl status app-demo.servicePaso 2 — Verifica la sintaxis del archivo:
systemd-analyze verify /etc/systemd/system/app-demo.serviceEste comando muestra todos los problemas de sintaxis. Léelo con cuidado.
Paso 3 — Revisa los logs para más detalles:
journalctl -u app-demo.service -n 20 --no-pagerPista: hay exactamente 3 errores tipográficos en el archivo y 1 problema adicional (el binario no existe). Localiza y corrige cada uno:
- En
[Unit]: hay una dependencia con un typo - En
[Service]: hay una directiva con un typo - En
[Install]: hay un error al escribir el nombre de la sección
Una vez corregidos los typos, crea el binario que falta:
sudo nano /usr/local/bin/app-demoEscribe:
#!/bin/bash# Simula una aplicación en ejecución continuawhile true; do echo "$(date): app-demo en ejecución" >> /var/log/app-demo.log sleep 30donesudo chmod +x /usr/local/bin/app-demoPaso 4 — Repara el archivo y prueba:
sudo nano /etc/systemd/system/app-demo.service# Corrige los 3 typos
sudo systemctl daemon-reloadsudo systemctl start app-demo.servicesystemctl status app-demo.service# Debe aparecer como 'active (running)'Guarda en ~/practica4/entrega/46_reparacion.txt:
{ echo "--- Diagnóstico inicial ---" systemd-analyze verify /etc/systemd/system/app-demo.service 2>&1 || true echo "" echo "--- Servicio reparado ---" systemctl status app-demo.service --no-pager echo "" echo "--- Archivo corregido ---" cat /etc/systemd/system/app-demo.service} > ~/practica4/entrega/46_reparacion.txtEjercicio 4.7 ⚡ EXTRA — Diagnóstico de arranque con fallos sembrados
Sección titulada “Ejercicio 4.7 ⚡ EXTRA — Diagnóstico de arranque con fallos sembrados"Setup (ejecuta UNA sola vez)
Sección titulada “Setup (ejecuta UNA sola vez)"bash -lc 'set -euo pipefailbase="$HOME/practica4/work"mkdir -p "$base"
# Servicio 1: binario sin permisos de ejecucióncat > /tmp/svc_sinpermisos.sh << '"'"'EOF'"'"'#!/bin/bashecho "$(date): servicio ejecutado" >> /var/log/svc_sinpermisos.logEOFsudo cp /tmp/svc_sinpermisos.sh /usr/local/bin/svc_sinpermisos.shsudo chmod 644 /usr/local/bin/svc_sinpermisos.sh # Sin permiso de ejecución (el error)
sudo tee /etc/systemd/system/svc-sinpermisos.service > /dev/null << '"'"'EOF'"'"'[Unit]Description=Servicio con binario sin permisos de ejecuciónAfter=network.target
[Service]Type=oneshotExecStart=/usr/local/bin/svc_sinpermisos.shRemainAfterExit=yes
[Install]WantedBy=multi-user.targetEOF
# Servicio 2: dependencia de un target inexistentesudo tee /etc/systemd/system/svc-dependencia.service > /dev/null << '"'"'EOF'"'"'[Unit]Description=Servicio con dependencia inexistenteAfter=network.targetRequires=servicio-que-no-existe.service
[Service]Type=simpleExecStart=/bin/sleep 3600
[Install]WantedBy=multi-user.targetEOF
sudo systemctl daemon-reloadecho "Escenario 4.7 creado"echo "Servicios sembrados: svc-sinpermisos.service, svc-dependencia.service"'Objetivo
Sección titulada “Objetivo"Desde tu terminal, debes conseguir que:
svc-sinpermisos.servicearranque correctamente y escriba en su logsvc-dependencia.servicearranque correctamente (pista: la dependencia debe ser eliminada o corregida)- Ambos servicios aparezcan como
activeensystemctl status
Proceso de diagnóstico
Sección titulada “Proceso de diagnóstico"Sigue este flujo sistemático para cada servicio:
# Paso 1: intenta arrancar y observa el código de errorsudo systemctl start svc-sinpermisos.serviceecho "Código de salida: $?"
# Paso 2: lee el status completosystemctl status svc-sinpermisos.service --no-pager
# Paso 3: busca en el journal el motivo exactojournalctl -u svc-sinpermisos.service -n 30 --no-pager
# Paso 4: verifica el archivo unitsystemd-analyze verify /etc/systemd/system/svc-sinpermisos.service 2>&1 || trueRepite para svc-dependencia.service.
Entregables
Sección titulada “Entregables"Guarda en ~/practica4/entrega/47_solucion.txt:
- Los comandos de diagnóstico que ejecutaste (en orden)
- Qué estaba roto en cada servicio (causa exacta)
- Evidencia de que el objetivo se cumple (salida de
systemctl status)
{ echo "=== DIAGNÓSTICO Y SOLUCIÓN 4.7 ===" echo "" echo "--- svc-sinpermisos: estado final ---" systemctl status svc-sinpermisos.service --no-pager echo "" echo "--- svc-dependencia: estado final ---" systemctl status svc-dependencia.service --no-pager} >> ~/practica4/entrega/47_solucion.txt