Cerramos el módulo 3 con una constatación incómoda: llevábamos tres módulos escribiendo /var/lib/meteora/lecturas/2026-08-31.dat como si esa cadena de texto fuera algo evidente, cuando en el módulo 2 dejamos el almacenamiento en un punto muy distinto. Allí, un SSD NVMe era un vector de bloques numerados de 0 a N, direccionables por LBA, sin nombres, sin carpetas, sin tamaños y sin dueños. Un array gigantesco de 512 o 4.096 bytes por casilla. Nada más.

Entre ese vector de bloques y la ruta /var/lib/meteora/lecturas/2026-08-31.dat hay una de las abstracciones más logradas de la informática: el sistema de archivos. Es la pieza que convierte "el bloque 8.394.271" en "el fichero de lecturas de ayer", que recuerda quién lo creó y cuándo, que sabe que ocupa 17 MB repartidos en miles de bloques dispersos, y que consigue que un programa en C pueda leerlo sin saber absolutamente nada de LBA, sectores ni geometría.

Esta lección construye esa abstracción desde abajo. Vamos a definir qué es un fichero con precisión, ver qué metadatos lleva y dónde viven, diseccionar el inodo —la estructura central de todo sistema UNIX—, recorrer la disposición física de un sistema de archivos sobre el dispositivo, calcular por qué el tamaño de bloque es un compromiso y no una casualidad, y terminar comparando las familias de sistemas de archivos que existen para decidir, con argumentos, cuál merece /var/lib/meteora.

Contenido

  1. Del bloque crudo al fichero: qué problema resuelve la abstracción
  2. Qué es un fichero: contenido, metadatos y nombre
  3. Los siete tipos de fichero de UNIX
  4. ls -l y stat interpretados campo a campo
  5. El inodo: qué contiene y qué no contiene
  6. Números de inodo, ls -i y el agotamiento con df -i
  7. Disposición física de un sistema de archivos en el dispositivo
  8. El tamaño de bloque y su compromiso, calculado
  9. Marcas de tiempo: atime, mtime, ctime, crtime y el porqué de noatime
  10. Familias de sistemas de archivos comparadas
  11. La decisión de Meteora para /var/lib/meteora

Del bloque crudo al fichero: qué problema resuelve la abstracción

Imagina por un momento que Meteora no tuviera sistema de archivos y trabajara directamente sobre /dev/nvme0n1, el dispositivo de bloques del módulo 2. El ingestor tendría que resolver, él solito, esta lista de problemas:

Problema Qué tendría que hacer el ingestor sin sistema de archivos
Ubicación Recordar en qué LBA empieza el día de hoy, y almacenarlo en algún sitio... ¿dónde?
Crecimiento Saber cuántos bloques reservar por adelantado, porque no puede "crecer" sobre un vecino
Espacio libre Llevar su propia contabilidad de qué bloques están usados y cuáles no
Nombres Inventar un índice propio que traduzca "31 de agosto" a un número de bloque
Concurrencia Coordinarse con el agregador y con meteo-api para no pisarse bloques
Permisos No hay: cualquiera con acceso al dispositivo lee y escribe todo
Persistencia de la contabilidad Si se corta la luz mientras actualiza su índice, lo pierde todo

Cada programa del servidor tendría que resolver los siete, cada uno a su manera, y ninguno podría cooperar con los demás. Es exactamente la situación que describimos en 01-01 al hablar del sistema operativo como máquina extendida: sin él, cada aplicación reimplementa el hardware.

El sistema de archivos resuelve los siete de golpe con una sola idea:

Un fichero es una secuencia de bytes con nombre, tamaño y propietario, que el sistema almacena donde quiere y el programa lee como si fuera continua.

Las cuatro palabras clave de esa definición merecen atención:

  • Secuencia de bytes. En UNIX un fichero no tiene estructura interna conocida por el sistema. No hay "registros", ni "campos", ni tipos. Que 2026-08-31.dat contenga 720.000 estructuras Lectura de 24 bytes es un acuerdo entre los programas de Meteora, invisible para el núcleo. Otros sistemas históricos (los de IBM, VMS) sí imponían estructura de registros, y la industria acabó dándole la razón al modelo plano de UNIX por su simplicidad.
  • Con nombre. El nombre es el asa por la que el usuario agarra el fichero. Veremos en el apartado 5 la sorpresa: el nombre no está dentro del fichero.
  • Donde quiere. El sistema decide qué bloques usa. Eso es lo que estudiaremos en Asignación de Espacio, Journaling e Integridad.
  • Como si fuera continua. Esta es la magia. 2026-08-31.dat ocupa 4.219 bloques que pueden estar desperdigados por todo el SSD, y sin embargo read() los entrega en orden como un chorro de bytes. Es la misma clase de ilusión que la memoria virtual del módulo 2: direcciones lógicas contiguas sobre almacenamiento físico disperso.

De hecho, el paralelismo con la memoria virtual es tan exacto que conviene fijarlo, porque te ahorrará esfuerzo en todo el módulo:

Memoria virtual (02-04) Sistema de archivos (módulo 4)
Espacio de direcciones virtual del proceso El fichero como secuencia de bytes 0..N
Página (4 KiB) Bloque lógico (4 KiB)
Marco de página en RAM Bloque físico en el dispositivo
Tabla de páginas Punteros/extents del inodo
MMU traduce virtual → físico El sistema de archivos traduce desplazamiento → LBA
Fallo de página trae la página de disco read() trae el bloque a la caché de páginas

Es la misma idea aplicada dos veces: una tabla de traducción que convierte un espacio lógico ordenado en un espacio físico desordenado.

Qué es un fichero: contenido, metadatos y nombre

Un fichero tiene tres partes, y viven en tres sitios distintos. Esta separación es la clave de todo lo demás:

graph LR
    subgraph DIR["Directorio (04-02)"]
        N["nombre: 2026-08-31.dat<br/>inodo: 1180934"]
    end
    subgraph INO["Inodo nº 1180934"]
        M["tipo, permisos, dueño,<br/>tamaño, fechas, punteros"]
    end
    subgraph DAT["Zona de datos"]
        D["4.219 bloques<br/>con los 17.280.000 bytes"]
    end
    N -->|apunta a| M
    M -->|apunta a| D
  • El contenido: los bytes en sí, en la zona de datos del dispositivo.
  • Los metadatos: todo lo que el sistema sabe sobre el fichero. Viven en el inodo.
  • El nombre: vive en el directorio que lo contiene, no en el fichero. Lo desarrollaremos en Estructuras de Directorios, pero necesitas saberlo ya para entender el inodo.

Los metadatos típicos de un fichero, con lo que significa cada uno:

Metadato Qué es Ejemplo en Meteora
Tipo Regular, directorio, enlace simbólico... Regular
Tamaño Bytes de contenido 17.280.000
Bloques Bloques de 512 B realmente ocupados 33.760
Propietario (UID) Usuario dueño meteora (UID 990)
Grupo (GID) Grupo dueño meteora (GID 990)
Permisos 12 bits de modo 0640
Contador de enlaces Cuántos nombres apuntan a este inodo 1
Marcas de tiempo Acceso, modificación, cambio, creación ver apartado 9
Punteros a datos Dónde están los bloques extents (04-05)

Fíjate en algo que ya se intuye: el nombre no aparece en esa lista. No es un olvido; es la decisión de diseño central de UNIX, y de ella salen los enlaces duros, el borrado diferido y media docena de comportamientos que sorprenden hasta que entiendes esto.

Los siete tipos de fichero de UNIX

En UNIX, la frase "todo es un fichero" se toma en serio. La misma interfaz —open, read, write, close— sirve para un fichero de datos, un teclado, una tubería o una conexión de red. Lo que cambia es el tipo, un campo de 4 bits en el inodo:

Símbolo en ls -l Tipo Qué es Ejemplo de Meteora
- Regular Secuencia de bytes en el disco /var/lib/meteora/lecturas/2026-08-31.dat
d Directorio Tabla de pares (nombre, inodo) /var/lib/meteora/lecturas/
l Enlace simbólico Fichero que contiene una ruta /var/lib/meteora/lecturas/hoy.dat
b Dispositivo de bloque Acceso por bloques, con caché /dev/nvme0n1, /dev/md0
c Dispositivo de carácter Acceso por bytes, sin caché /dev/null, /dev/random, /dev/tty
p FIFO (tubería con nombre) Canal en el sistema de archivos /run/meteora/lecturas.fifo
s Socket Punto de comunicación local /run/meteora/api.sock

Los tres últimos son viejos conocidos del módulo 3: la FIFO de /run/meteora/lecturas.fifo la usamos en Comunicación entre Procesos, y los sockets de dominio UNIX también. La diferencia es que allí los vimos como mecanismos de IPC y aquí los vemos como entradas del sistema de archivos: tienen inodo, permisos y nombre, pero su contenido no está en el disco —una FIFO tiene un búfer en memoria del núcleo, un socket tiene una cola de red—. Ocupan un inodo y cero bloques de datos.

Lo mismo pasa con los dispositivos de bloque y carácter, que vimos en Gestión de Dispositivos: su inodo no guarda punteros a datos, guarda el par (número mayor, número menor) que identifica al controlador. Un fichero de dispositivo es, literalmente, un inodo con un par de enteros dentro.

ls -l y stat interpretados campo a campo

Vamos a mirarlo de verdad. Este es el listado del directorio de Meteora en meteo-01:

$ ls -l /var/lib/meteora/lecturas/ /dev/nvme0n1 /dev/null /run/meteora/
-rw-r----- 1 meteora meteora 17280000 ago 31 23:59 2026-08-31.dat
-rw-r----- 1 meteora meteora 17280000 sep  1 12:40 2026-09-01.dat
lrwxrwxrwx 1 meteora meteora       14 sep  1 00:00 hoy.dat -> 2026-09-01.dat
drwxr-x--- 2 meteora meteora     4096 sep  1 00:00 archivo

brw-rw---- 1 root  disk    259, 0 sep  1 08:12 /dev/nvme0n1
crw-rw-rw- 1 root  root      1, 3 sep  1 08:12 /dev/null

prw-r----- 1 meteora meteora      0 sep  1 08:13 /run/meteora/lecturas.fifo
srwxr-xr-x 1 meteora meteora      0 sep  1 08:13 /run/meteora/api.sock

Los campos, de izquierda a derecha:

  1. Primer carácter: el tipo de la tabla anterior. -, l, d, b, c, p, s. De un vistazo ya sabes qué es cada cosa.
  2. Nueve caracteres siguientes: los permisos, que veremos en Seguridad y Permisos de Archivos.
  3. El número tras los permisos: el contador de enlaces. Vale 1 en los ficheros normales y 2 en el directorio archivo (lo explica 04-02).
  4. Usuario y grupo propietarios: meteora meteora.
  5. Tamaño: 17.280.000 bytes para las lecturas. Pero mira /dev/nvme0n1: donde debería estar el tamaño pone 259, 0. Son el mayor y el menor. Un fichero de dispositivo no tiene tamaño porque no tiene contenido; en su lugar ls muestra la pareja que identifica al controlador. Y la FIFO y el socket ponen 0, por la misma razón.
  6. Fecha: por defecto el mtime, no el de creación ni el de último acceso (apartado 9).
  7. Nombre, con el -> destino en el enlace simbólico.

ls -l es un resumen. Para verlo todo se usa stat:

$ stat /var/lib/meteora/lecturas/2026-08-31.dat
  Fichero: /var/lib/meteora/lecturas/2026-08-31.dat
  Tamaño: 17280000    Bloques: 33760      Bloque E/S: 4096   fichero regular
Dispositivo: 9,0      Nodo-i: 1180934     Enlaces: 1
Acceso: (0640/-rw-r-----)  Uid: (  990/meteora)   Gid: (  990/meteora)
Acceso:      2026-09-01 06:00:11.482913711 +0200
Modificación:2026-08-31 23:59:58.117204339 +0200
Cambio:      2026-08-31 23:59:58.117204339 +0200
Creación:    2026-08-31 00:00:00.004118220 +0200

Campo a campo, con lo que hay que entender de cada uno:

  • Tamaño: 17280000. Bytes lógicos del fichero: exactamente 720.000 lecturas × 24 bytes. Es el número que devuelve lseek(fd, 0, SEEK_END).
  • Bloques: 33760. Aquí hay una trampa clásica: stat cuenta bloques de 512 bytes, siempre, independientemente del tamaño de bloque real del sistema de archivos. 33.760 × 512 = 17.285.120 bytes ocupados en disco, algo más que los 17.280.000 lógicos. La diferencia son 5.120 bytes: 4 KiB del último bloque parcialmente usado más los metadatos del árbol de extents. Que "bloques × 512" sea menor que el tamaño es la firma de un fichero disperso (lo veremos en 04-04).
  • Bloque E/S: 4096. El tamaño de bloque preferido para las lecturas; leer en múltiplos de este número evita trabajo extra al núcleo.
  • Dispositivo: 9,0. Mayor 9, menor 0: /dev/md0, el RAID 1 que montamos en 02-05. Este par identifica en qué sistema de archivos vive el inodo, y la pareja (dispositivo, nodo-i) es lo único que identifica un fichero de forma única en toda la máquina.
  • Nodo-i: 1180934. El número de inodo. El apartado 6 se dedica a él.
  • Enlaces: 1. Un solo nombre apunta a este inodo (04-02).
  • Acceso (0640). Doce bits de modo, mostrados en octal y en simbólico (04-06).
  • Uid/Gid 990. El usuario y el grupo meteora. Ojo: el inodo guarda números, no nombres; la traducción a meteora la hace stat consultando /etc/passwd.
  • Las cuatro fechas: apartado 9.

El inodo: qué contiene y qué no contiene

El inodo (index node) es la estructura de datos que es el fichero. Todo lo demás son referencias a él. Vive en el disco, en una zona reservada, y tiene un tamaño fijo: 256 bytes en un ext4 moderno (128 en los antiguos, configurable al formatear).

Su contenido, agrupado:

Grupo Campos Bytes aprox.
Identidad Tipo (4 bits) + permisos (12 bits), UID, GID 8
Tamaño Tamaño lógico en bytes (64 bits), bloques ocupados 12
Enlaces Contador de nombres que lo referencian 2
Tiempos atime, mtime, ctime, dtime, crtime (con nanosegundos) 40
Datos 60 bytes de punteros/extents (04-05) 60
Extras Banderas (chattr), versión, checksum, atributos extendidos resto

Y ahora lo importante, que es lo que no está:

El nombre del fichero no está en el inodo. Tampoco está la ruta, ni el directorio al que pertenece, ni nada que lo relacione con /var/lib/meteora/lecturas/2026-08-31.dat.

El inodo 1180934 no sabe cómo se llama. Sabe que es un fichero regular de 17.280.000 bytes que pertenece al UID 990, que hay 1 nombre en algún sitio apuntando a él, y en qué bloques están sus datos. Nada más.

Esto no es una limitación: es la decisión de diseño de la que cuelga medio módulo. Sus consecuencias, que iremos desplegando:

Consecuencia Dónde se explica
Un mismo fichero puede tener varios nombres (enlaces duros) 04-02
Renombrar es instantáneo: solo cambia una entrada de directorio 04-02
Borrar es unlink: quitar un nombre, no destruir el fichero 04-02
Un fichero abierto sin ningún nombre sigue existiendo 04-02, 04-04
El nombre no tiene permisos; los permisos están en el inodo 04-06
Un fichero en uso puede sustituirse atómicamente con rename() 04-04

Guarda esta frase: el inodo es el fichero; el nombre es solo una etiqueta pegada desde fuera.

Números de inodo, ls -i y el agotamiento con df -i

Cada inodo tiene un número único dentro de su sistema de archivos. Se ve con ls -i:

$ ls -i /var/lib/meteora/lecturas/
1180934 2026-08-31.dat   1180935 2026-09-01.dat   1180936 hoy.dat

Dos ficheros del mismo sistema de archivos con el mismo número de inodo son el mismo fichero. Dos ficheros de sistemas de archivos distintos pueden compartir número sin tener nada que ver: por eso la identidad real es el par (dispositivo, inodo), st_dev + st_ino en stat. Es exactamente lo que comprueba find -samefile y lo que usa rsync para no copiar dos veces el mismo contenido enlazado.

Ahora lo práctico. En ext4, el número de inodos se fija al formatear y no se puede aumentar después. Se reservan por adelantado, con una relación por defecto de un inodo por cada 16 KiB de capacidad:

$ df -h /var/lib/meteora
S.ficheros     Tamaño Usados  Disp Uso% Montado en
/dev/md0         196G    41G  146G  22% /var/lib/meteora

$ df -i /var/lib/meteora
S.ficheros       Nodos-i NUsados  NLibres NUso% Montado en
/dev/md0        13107200    1834 13105366    1% /var/lib/meteora

Interpretación: el volumen tiene 13.107.200 inodos (200 GiB ÷ 16 KiB) y solo usa 1.834, porque Meteora guarda un fichero grande por día y lleva unos cinco años funcionando. Con esa política, en 100 años usaría 36.500 inodos: el 0,28 %.

Al revés, sin embargo, ocurre el fallo más desconcertante de la administración de sistemas:

$ df -h /var/spool/cache
S.ficheros     Tamaño Usados  Disp Uso% Montado en
/dev/sdb1         50G    12G   36G  26% /var/spool/cache      ← ¡74 % libre!

$ df -i /var/spool/cache
S.ficheros      Nodos-i NUsados NLibres NUso% Montado en
/dev/sdb1       3276800 3276800       0  100% /var/spool/cache ← 0 libres

$ touch /var/spool/cache/prueba
touch: no se puede efectuar `touch' sobre 'prueba': No queda espacio en el dispositivo

"No queda espacio en el dispositivo" con 36 GB libres. El error es ENOSPC y es literal desde el punto de vista del núcleo: no queda espacio de inodos. Un proceso que crea millones de ficheros diminutos —cachés, sesiones, colas de correo— agota la reserva de inodos mucho antes que los bloques. Regla de diagnóstico: ante un ENOSPC, ejecuta siempre df -h y df -i; si la primera no explica nada, la segunda lo hará.

Para localizar al culpable:

$ sudo find /var/spool/cache -xdev -type f -printf '%h\n' | sort | uniq -c | sort -rn | head -5
2984112 /var/spool/cache/sesiones
  12043 /var/spool/cache/tmp

El comando cuenta ficheros por directorio: -xdev evita saltar a otros sistemas de archivos, -printf '%h\n' imprime el directorio de cada fichero, y sort | uniq -c | sort -rn agrupa y ordena. Casi tres millones de ficheros en sesiones: ahí está el problema.

La solución no es agrandar el disco, porque los inodos no crecen: hay que borrar ficheros o reformatear con mkfs.ext4 -i 4096 (un inodo cada 4 KiB, cuatro veces más) o -N 8000000 (número explícito). Este es uno de los argumentos a favor de XFS y Btrfs, que asignan inodos dinámicamente y no sufren este problema.

Disposición física de un sistema de archivos en el dispositivo

Ya sabemos qué es un inodo. ¿Dónde está físicamente? Vamos a abrir el dispositivo por dentro. La jerarquía de unidades, de menor a mayor:

Unidad Tamaño típico Quién la define
Sector 512 B (lógico) / 4.096 B (físico) El hardware del disco
Bloque lógico 1, 2 o 4 KiB El sistema de archivos, al formatear
Grupo de bloques 128 MiB en ext4 El sistema de archivos
Sistema de archivos La partición entera El administrador

El sector es la unidad mínima que el dispositivo sabe leer o escribir; lo vimos en 02-05. El bloque lógico es la unidad mínima que el sistema de archivos sabe asignar: aunque el disco pueda leer 512 bytes, ext4 nunca asigna menos de un bloque a un fichero.

Un ext4 se divide en grupos de bloques de 128 MiB, cada uno con su propia contabilidad. La razón es de rendimiento y viene directa del módulo 2: mantener juntos los metadatos y los datos que se usan juntos reduce los desplazamientos del cabezal en un HDD y mejora la localidad en un SSD.

graph TB
    subgraph FS["/dev/md0 — ext4 de 200 GiB, 1.600 grupos de 128 MiB"]
        BOOT["Bloque 0<br/>1 KiB de arranque"]
        subgraph G0["Grupo de bloques 0"]
            SB["Superbloque<br/>(1 bloque)"]
            GD["Descriptores de grupo<br/>(N bloques)"]
            BB["Mapa de bits<br/>de BLOQUES<br/>(1 bloque)"]
            IB["Mapa de bits<br/>de INODOS<br/>(1 bloque)"]
            IT["Tabla de inodos<br/>(512 bloques)"]
            DZ["ZONA DE DATOS<br/>(~31.000 bloques)"]
        end
        G1["Grupo 1<br/>(igual estructura)"]
        GN["... Grupo 1.599"]
    end
    BOOT --> SB --> GD --> BB --> IB --> IT --> DZ --> G1 --> GN

Pieza por pieza:

El superbloque. Es la ficha de identidad del sistema de archivos, y ocupa un solo bloque. Contiene el número total de inodos y de bloques, cuántos quedan libres, el tamaño de bloque, el tamaño del inodo, el número de bloques por grupo, el UUID, la etiqueta, la fecha del último montaje, el contador de montajes y el estado (limpio o sucio, que será decisivo en 04-05). Sin superbloque no se puede montar nada, porque no se sabe ni dónde empiezan los inodos. Por eso ext4 guarda copias de seguridad en varios grupos:

$ sudo dumpe2fs /dev/md0 | grep -i superblock
Primary superblock at 0, Group descriptors at 1-13
  Backup superblock at 32768, Group descriptors at 32769-32781
  Backup superblock at 98304, Group descriptors at 98305-98317
  Backup superblock at 163840, ...

Si el primario se corrompe, se recupera con sudo e2fsck -b 32768 /dev/md0, que le dice a e2fsck que use el respaldo del bloque 32768. Es un comando que conviene tener anotado: salva volúmenes que parecían perdidos.

Los descriptores de grupo. Un array con una entrada por grupo, que dice dónde están los mapas de bits y la tabla de inodos de ese grupo y cuántos elementos libres tiene. Es el índice que permite encontrar todo lo demás.

El mapa de bits de bloques. Un bit por bloque del grupo: 1 = ocupado, 0 = libre. Con bloques de 4 KiB, un grupo de 128 MiB tiene 32.768 bloques, que son 32.768 bits = 4.096 bytes: exactamente un bloque. No es casualidad; el tamaño del grupo se elige precisamente para que su mapa de bits quepa en un bloque.

El mapa de bits de inodos. Lo mismo para los inodos del grupo.

La tabla de inodos. El array de inodos propiamente dicho. Si un grupo tiene 8.192 inodos de 256 bytes, ocupa 2 MiB = 512 bloques. Aquí es donde se calcula la posición de un inodo a partir de su número, con aritmética pura y sin buscar en ningún índice:

/* Localizar el inodo 1180934 en un ext4 con 8.192 inodos por grupo */
unsigned grupo   = (1180934 - 1) / 8192;      /* = 144  → grupo 144        */
unsigned indice  = (1180934 - 1) % 8192;      /* = 1157 → posición 1157    */
off_t    posicion = inicio_tabla_inodos[144] + (off_t)1157 * 256;

Dos divisiones y una multiplicación: eso es todo lo que cuesta pasar de un número de inodo a su posición en el disco. Los inodos se numeran desde 1, de ahí el - 1. Esta es la razón profunda de que el inodo sea un número y no un nombre: buscar un nombre exigiría recorrer una tabla; un número se resuelve con aritmética en nanosegundos.

La zona de datos. Todo lo demás: los bloques donde están los bytes de los ficheros.

Puedes verlo en tu máquina con dumpe2fs:

$ sudo dumpe2fs -h /dev/md0 | head -20
Filesystem volume name:   meteora-datos
Filesystem UUID:          9f3a1c22-7d4e-4a51-b7c8-2e5f0a1d6b93
Filesystem features:      has_journal ext_attr dir_index extent 64bit
Filesystem state:         clean
Inode count:              13107200
Block count:              52428800
Free blocks:              41156923
First block:              0
Block size:               4096
Blocks per group:         32768
Inodes per group:         8192
Inode size:               256

Cada línea es un campo del superbloque real. Block count: 52428800 × 4.096 = 200 GiB. Filesystem state: clean significa que se desmontó correctamente. Y dir_index y extent son características que aparecerán en 04-02 y 04-05.

El tamaño de bloque y su compromiso, calculado

El tamaño de bloque se elige al formatear y no se puede cambiar después. Es un compromiso genuino, y se ve con números.

El coste de un bloque grande: fragmentación interna. Como la asignación es por bloques enteros, el último bloque de cada fichero queda parcialmente vacío, y ese espacio se pierde. En promedio se desperdicia medio bloque por fichero.

El coste de un bloque pequeño: más bloques que gestionar. Más entradas en los metadatos, más trabajo de asignación, y peticiones de E/S más pequeñas.

Con los ficheros reales de Meteora (17.280.000 bytes):

Tamaño de bloque Bloques necesarios Espacio ocupado Desperdicio Mapa de bits para 200 GiB
1 KiB 16.875 17.280.000 B 0 B (exacto) 25 MiB
2 KiB 8.438 17.281.024 B 1.024 B 12,5 MiB
4 KiB 4.219 17.281.024 B 1.024 B 6,25 MiB
16 KiB 1.055 17.285.120 B 5.120 B 1,6 MiB
64 KiB 264 17.301.504 B 21.504 B 0,4 MiB

Para ficheros de 17 MB el desperdicio es irrelevante en todos los casos: 21 KB sobre 17 MB es el 0,12 %. Pero el número de bloques a gestionar cambia por un factor de 64.

Ahora el escenario contrario, un directorio con un millón de ficheros de 800 bytes (sesiones, no lecturas):

Tamaño de bloque Espacio ocupado por 1.000.000 ficheros Desperdicio
1 KiB 1.024 MB 224 MB (22 %)
4 KiB 4.096 MB 3.296 MB (80 %)
64 KiB 65.536 MB 64.736 MB (99 %)

Con bloques de 64 KiB, un millón de ficheros de 800 bytes ocuparía 64 GB para almacenar 800 MB. El mismo tamaño de bloque que era irrelevante para las lecturas es catastrófico aquí.

Por qué 4 KiB es el estándar universal, y no es una convención arbitraria:

  1. Coincide con el tamaño de página (módulo 2). La caché de páginas del núcleo trabaja en páginas de 4 KiB; si el bloque midiera lo mismo, un bloque = una página y no hay que trocear ni juntar nada. Un bloque mayor que la página no se puede mapear con mmap() de forma directa, que es precisamente lo que hace el agregador con 2026-08-31.dat (02-04). De hecho, Linux no soporta bloques mayores que el tamaño de página, así que en x86-64 el máximo es 4 KiB.
  2. Coincide con el sector físico de los discos modernos (Advanced Format, 4Kn), así que ninguna escritura provoca el ciclo leer-modificar-escribir.
  3. Equilibra el desperdicio para la distribución real de tamaños de ficheros en un sistema típico.

Regla práctica: usa 4 KiB salvo que tengas una razón medida para no hacerlo. La razón para bajar a 1 KiB es un volumen dedicado a millones de ficheros minúsculos; para subir tendrías que irse a XFS en arquitecturas con páginas mayores, o a sistemas de archivos con bigalloc.

Marcas de tiempo: atime, mtime, ctime, crtime y el porqué de noatime

Cuatro fechas, y tres de ellas se confunden constantemente:

Marca Nombre Se actualiza cuando... Se ve con
atime access time Se lee el contenido ls -lu, stat
mtime modify time Cambia el contenido ls -l (por defecto)
ctime change time Cambia el inodo ls -lc, stat
crtime creation time Se creó el fichero stat (ext4, XFS, Btrfs)

El error más frecuente es creer que ctime es creation time. No lo es: es change time, el momento en que cambió cualquier metadato. Cambiar los permisos con chmod, el dueño con chown o crear un enlace duro modifica el ctime pero no el mtime, porque el contenido no ha cambiado. Y como no se puede alterar hacia atrás (ni siquiera touch -d lo toca), el ctime es la marca que consulta un analista forense: quien manipula un fichero puede falsear atime y mtime, pero al hacerlo actualiza el ctime, delatándose. Volveremos a ello en el módulo 5.

Una tabla de qué toca cada operación sobre 2026-08-31.dat:

Operación atime mtime ctime
cat 2026-08-31.dat Sí No No
echo dato >> 2026-08-31.dat No Sí Sí
chmod 640 2026-08-31.dat No No Sí
chown meteora: 2026-08-31.dat No No Sí
mv 2026-08-31.dat viejo.dat No No No¹
ln 2026-08-31.dat copia.dat No No Sí²

¹ Renombrar cambia el directorio, no el inodo del fichero. ² Cambia el contador de enlaces, que está en el inodo.

Por qué noatime mejora el rendimiento

Aquí está el problema práctico. Actualizar el atime significa escribir en el disco al leer un fichero. Suena absurdo, y lo es: convierte una operación de solo lectura en una de lectura y escritura.

Los números para Meteora. meteo-api sirve unas 2.000 consultas por hora, cada una leyendo el fichero del día. Con atime estricto, eso son 2.000 escrituras por hora sobre el inodo de un fichero que nadie ha modificado: 48.000 escrituras diarias de metadatos, más su entrada correspondiente en el diario (04-05), sobre un RAID 1 donde cada escritura va a los dos discos. Y sobre un SSD, ciclos de escritura gastados para nada.

Las opciones de montaje disponibles, que aplicaremos en Particiones, Montaje y Sistema de Archivos Virtual:

Opción Comportamiento Coste
strictatime Actualiza el atime en cada lectura Máximo
relatime Solo si el atime es anterior al mtime/ctime, o tiene más de 24 h Bajo (por defecto desde 2009)
nodiratime Como el anterior, pero sin atime en directorios Bajo
noatime Nunca actualiza el atime Cero

relatime es el compromiso que adoptó Linux: mantiene la semántica que necesitan las herramientas que preguntan "¿se ha leído esto desde la última modificación?" (los clientes de correo, sobre todo) con una fracción del coste. noatime lo elimina del todo.

Meteora monta /var/lib/meteora con noatime, porque ningún programa del sistema consulta el atime de las lecturas y el ahorro es real. La regla general: en un volumen de datos de servidor, noatime es casi siempre correcto; en un volumen de usuarios con clientes de correo antiguos, quédate en relatime.

Familias de sistemas de archivos comparadas

Hay decenas. Estos son los que te vas a encontrar, con lo que de verdad los distingue:

Sistema Origen Estructura Diario / CoW Suma de verif. datos Máx. fichero Cuándo elegirlo
ext4 Linux, 2008 Inodos + extents Diario No (solo metadatos) 16 TiB Servidor Linux general. La opción segura
XFS SGI, 1994 Árboles B+ + extents Diario No (solo metadatos) 8 EiB Ficheros grandes, alto paralelismo, RHEL por defecto
Btrfs Linux, 2009 Árboles B CoW Copia al escribir Sí 16 EiB Instantáneas, sumas de verificación, RAID integrado
ZFS Sun, 2005 Árboles CoW + pools Copia al escribir Sí 16 EiB Almacenamiento serio. Licencia fuera del núcleo Linux
F2FS Samsung, 2012 Estructurado en registro Registro Opcional 16 TiB Memoria flash: móviles, tarjetas SD
NTFS Microsoft, 1993 MFT + árboles B Diario No 8 PiB Windows
APFS Apple, 2017 Árboles CoW Copia al escribir Solo metadatos 8 EiB macOS, iOS
FAT32 Microsoft, 1996 Tabla FAT No No 4 GiB Compatibilidad universal, arranque UEFI
exFAT Microsoft, 2006 Tabla FAT ampliada No No 128 PiB Tarjetas SD grandes entre sistemas
tmpfs Linux Solo en RAM N/A N/A RAM + swap /run, /dev/shm, ficheros temporales
NFS / SMB Red Cliente-servidor Del servidor Del servidor Del servidor Compartir por red (04-03)

Cuatro observaciones que valen más que la tabla entera:

FAT32 y el límite de 4 GiB. Es el límite real que más gente encuentra en su vida: copiar un vídeo de 5 GB a un pendrive falla, y no por falta de espacio. FAT32 guarda el tamaño en 32 bits, así que 2³² − 1 = 4.294.967.295 bytes es el techo absoluto. Y no tiene diario: un corte de luz en mitad de una escritura puede dejarlo incoherente sin forma automática de repararlo. Sobrevive porque lo lee absolutamente todo, incluida la UEFI de tu placa, que exige una partición FAT32 para arrancar.

tmpfs no es un disco. Vive en la caché de páginas y en swap: rapidísimo y volátil. Es lo que hay detrás de /dev/shm/meteora-cache (03-03) y de /run/meteora/. Que la caché de Meteora "sea un fichero" y a la vez esté en RAM no es una contradicción: es un fichero de un sistema de archivos que no tiene dispositivo detrás. Lo veremos con detalle en 04-03.

Copia al escribir frente a diario. Son dos filosofías distintas para el mismo problema —sobrevivir a un corte de luz—. El diario anota lo que va a hacer antes de hacerlo; la copia al escribir nunca sobrescribe un bloque vivo, escribe una copia nueva y cambia el puntero al final. Es el tema de Asignación de Espacio, Journaling e Integridad.

Sumas de verificación de datos. Solo Btrfs y ZFS verifican que los datos que devuelven son los que se escribieron. ext4 y XFS verifican sus metadatos y su diario, pero si un bit de tus lecturas se corrompe en el plato, te lo entregan corrupto sin avisar. Es la corrupción silenciosa, y también es de 04-05.

La decisión de Meteora para /var/lib/meteora

Con todo lo anterior, ya se puede argumentar la elección en lugar de copiarla de un tutorial. El perfil de carga de Meteora:

Característica de la carga Valor
Tamaño de fichero 17,3 MB, uno por día
Número de ficheros ~365 al año, unos 1.800 en total
Patrón de escritura Añadir al final, continuo, ~8 lecturas/segundo
Patrón de lectura Secuencial completo (agregador) y aleatorio por mmap (meteo-api)
Dispositivo RAID 1 por software sobre dos NVMe (02-05)
Requisito de integridad Alto: los datos no se pueden regenerar
Requisito de disponibilidad Alto: meteo-api sirve 24/7

Los candidatos y su descarte razonado:

Candidato Argumento a favor Por qué no se elige
XFS Excelente con ficheros grandes, muy paralelo, sin límite de inodos No se puede reducir; el volumen podría necesitar ajustes
Btrfs Sumas de verificación de datos, instantáneas nativas Rendimiento irregular con escrituras continuas; su RAID 5/6 no es fiable
ZFS El mejor en integridad Fuera del núcleo; complica el mantenimiento y las actualizaciones
F2FS Pensado para flash Orientado a móviles; menos rodaje en servidor
ext4 Maduro, predecible, extents, herramientas Sin sumas de verificación de datos

Decisión: ext4, con esta justificación:

  1. Madurez y previsibilidad. Es el sistema de archivos con más horas de vuelo del ecosistema Linux. Para datos irrecuperables, "aburrido y probado" vale más que "moderno y prometedor".
  2. Extents. Un fichero de 17 MB contiguo se describe con un solo extent en lugar de 4.219 punteros. Lo mediremos con filefrag en 04-05.
  3. Herramientas. dumpe2fs, debugfs, tune2fs, e2fsck y resize2fs (que sí reduce, a diferencia de XFS) forman el juego más completo. Cuando algo va mal a las tres de la mañana, eso pesa.
  4. El diario en modo ordered garantiza que nunca aparecerán datos de otro fichero dentro de las lecturas tras un fallo. Lo justificaremos en 04-05.
  5. Los inodos no son un problema en esta carga: 1.834 usados de 13 millones.
  6. La falta de sumas de verificación de datos se compensa por otra vía: md verifica el RAID 1 con un scrub semanal, y el ingestor guarda un CRC32 por lectura en su propio formato.

Los parámetros exactos del formateo:

sudo mkfs.ext4 \
    -b 4096 \                    # bloque de 4 KiB = tamaño de página
    -i 1048576 \                 # un inodo por MiB: pocos ficheros y grandes
    -m 1 \                       # solo 1 % reservado para root (por defecto 5 %)
    -L meteora-datos \           # etiqueta estable
    -O extent,dir_index,has_journal,metadata_csum,64bit \
    /dev/md0

Qué hace cada opción y por qué aquí:

  • -b 4096: coincide con la página y con el sector físico del NVMe; además permite mmap() directo.
  • -i 1048576: por defecto habría 13 millones de inodos, de los que se usan 1.834; con un inodo por MiB quedan 200.000, de sobra, y se ahorran unos 3 GiB de tabla de inodos que pasan a ser espacio útil. Es un ajuste seguro solo porque conocemos la carga.
  • -m 1: ext4 reserva el 5 % para root, para que un disco lleno no impida iniciar sesión ni operar. En un volumen de datos de 200 GiB eso son 10 GiB inmovilizados; con el 1 % son 2 GiB, suficiente margen. Ojo: en / nunca bajes de 5 %.
  • -O extent: extents en lugar de punteros indirectos (04-05).
  • -O dir_index: índices hash para directorios grandes (04-02).
  • -O metadata_csum: sumas de verificación de metadatos, que detectan corrupción del inodo o del mapa de bits.

Y así es como /var/lib/meteora/lecturas/2026-08-31.dat deja de ser una cadena mágica y pasa a ser el inodo 1180934 del ext4 etiquetado meteora-datos sobre /dev/md0.

Errores Comunes y Consejos

Creer que el ctime es la fecha de creación. Es change time: cambia con chmod, chown o al crear un enlace duro. La creación real es el crtime, que solo muestra stat en sistemas modernos. Confundirlos lleva a conclusiones falsas en cualquier análisis forense.

Interpretar mal el campo Bloques de stat. Siempre son bloques de 512 bytes, aunque el sistema use 4 KiB. Si multiplicas por 4.096 obtendrás un tamaño ocho veces mayor que el real.

No mirar df -i ante un ENOSPC. Un disco al 26 % que da "No queda espacio en el dispositivo" es casi siempre agotamiento de inodos. Comprueba siempre las dos.

Suponer que el número de inodos se puede ampliar. En ext4 se fija al formatear y no hay marcha atrás. Si prevés millones de ficheros pequeños, decide -i antes, o usa XFS o Btrfs, que los asignan dinámicamente.

Elegir un bloque grande "porque es más rápido". Con un millón de ficheros de 800 bytes, un bloque de 64 KiB desperdicia el 99 % del espacio. El tamaño de bloque depende de la distribución de tamaños de tus ficheros, no de una intuición sobre velocidad. Y en Linux no puede superar los 4 KiB de la página.

Formatear con mkfs la partición equivocada. mkfs no pregunta. Confirma siempre con lsblk y blkid antes de pulsar Intro; lo veremos en 04-03.

Consejo: guarda la salida de dumpe2fs -h de tus volúmenes. Tener a mano el UUID, el tamaño de bloque y las posiciones de los superbloques de respaldo convierte una recuperación de emergencia en un trámite de dos minutos.

Consejo: usa stat en lugar de ls -l cuando algo no cuadre. Muestra las cuatro fechas, el inodo, el dispositivo y los bloques reales. La mitad de los misterios con ficheros se resuelven leyendo un stat con calma.

Consejo: comprueba el tipo antes de asumir. Antes de cat sobre algo desconocido, mira el primer carácter de ls -l. Un cat sobre un dispositivo de bloque de 200 GiB, o sobre una FIFO sin escritor, no acaba como esperas.

Ejercicios

Ejercicio 1: identificar tipos y leer un stat

Sin usar ls -l, escribe un comando que clasifique todo lo que hay en /dev, /run y tu directorio personal por tipo de fichero, contando cuántos hay de cada uno. Después coge un fichero regular de al menos 10 MB, ejecútale stat, y responde: (a) ¿cuántos bloques de 4 KiB ocupa realmente?, (b) ¿cuánto espacio se desperdicia en el último bloque?, (c) ¿coinciden mtime y ctime, y qué significa que coincidan o que no?

Ejercicio 2: el compromiso del tamaño de bloque

Un volumen de 500 GiB va a albergar dos cargas posibles. Carga A: los ficheros diarios de Meteora, 17.280.000 bytes cada uno, durante 30 años. Carga B: 20 millones de ficheros de sesión de 600 bytes. Para tamaños de bloque de 1, 4 y 64 KiB, calcula en cada carga: bloques totales necesarios, espacio realmente ocupado, desperdicio absoluto y porcentaje. Después indica qué tamaño elegirías para cada carga y si un solo volumen puede servir para las dos.

Ejercicio 3: diagnosticar un ENOSPC engañoso

Un compañero te avisa: el servicio de sesiones de meteo-01 falla con "No queda espacio en el dispositivo", pero df -h muestra el volumen al 31 %. Escribe el procedimiento completo de diagnóstico —qué comandos ejecutas, en qué orden y qué esperas ver en cada uno—, la explicación técnica de por qué ocurre, la solución inmediata para restaurar el servicio y la solución definitiva para que no vuelva a pasar. Incluye el comando de formateo que usarías y justifica sus parámetros.

Soluciones

Solución 1

Clasificar por tipo se hace con find -type o, mejor, con el formato de stat:

for d in /dev /run "$HOME"; do
    echo "=== $d ==="
    find "$d" -maxdepth 1 -printf '%y\n' 2>/dev/null | sort | uniq -c | sort -rn
done

-printf '%y' imprime una sola letra con el tipo (f regular, d directorio, l enlace, b, c, p, s), y sort | uniq -c los cuenta. Salida típica:

=== /dev ===
    198 c        ← dispositivos de carácter: terminales, /dev/null, /dev/random
     42 b        ← dispositivos de bloque: discos y particiones
     28 d
     18 l
=== /run ===
     34 d
     12 s        ← sockets de los servicios, incluido /run/meteora/api.sock
      6 p        ← FIFO, incluida /run/meteora/lecturas.fifo

Para las preguntas, con un stat que da Tamaño: 17280000 y Bloques: 33760:

(a) stat cuenta bloques de 512 B: 33.760 × 512 = 17.285.120 bytes. En bloques de 4 KiB son 17.285.120 / 4.096 = 4.220 bloques. Los datos necesitan ⌈17.280.000 / 4.096⌉ = 4.219, así que el bloque extra son metadatos del árbol de extents.

(b) 17.280.000 = 4.218 bloques completos + 3.072 bytes. El último bloque usa 3.072 de 4.096, así que se desperdician 1.024 bytes: el 0,006 % del fichero. Irrelevante aquí, decisivo con ficheros de 800 bytes.

(c) Si mtime y ctime coinciden, la última operación fue una escritura de contenido (que actualiza los dos). Si el ctime es posterior, después de escribir se modificó algún metadato: un chmod, un chown o un ln. Un ctime posterior al mtime sin motivo conocido es exactamente lo que hace sospechar a un analista.

Solución 2

Carga A — un fichero de 17.280.000 B, 30 años × 365 = 10.950 ficheros:

Bloque Bloques/fichero Ocupado/fichero Desperdicio/fichero Desperdicio total
1 KiB 16.875 17.280.000 0 0
4 KiB 4.219 17.281.024 1.024 11,2 MB
64 KiB 264 17.301.504 21.504 235 MB

Sobre 189 GB de datos, incluso 235 MB es el 0,12 %. Con 4 KiB, el desperdicio es del 0,006 %: despreciable. Aquí manda el número de bloques a gestionar, y 4.219 se maneja mucho mejor que 16.875.

Carga B — 20.000.000 de ficheros de 600 B (12 GB de datos reales):

Bloque Ocupado/fichero Ocupado total Desperdicio % desperdiciado
1 KiB 1.024 20,5 GB 8,5 GB 41 %
4 KiB 4.096 81,9 GB 69,9 GB 85 %
64 KiB 65.536 1.310 GB 1.298 GB 99,1 %

Con 64 KiB no cabe: harían falta 1,3 TB en un volumen de 500 GiB para guardar 12 GB de datos.

Elección. Carga A: 4 KiB, por afinidad con la página y mmap(), con desperdicio nulo en la práctica. Carga B: 1 KiB, que ahorra 61 GB frente a 4 KiB. Y una advertencia importante para la carga B: 20 millones de ficheros necesitan 20 millones de inodos, y el mkfs por defecto daría 32,7 millones —justo—, así que hay que fijar -i 2048 o usar XFS.

¿Un solo volumen para las dos? Técnicamente sí, pero es mala idea: los requisitos son opuestos (bloque grande y pocos inodos frente a bloque pequeño y muchos inodos), y además mezclar cargas hace que los millones de ficheros pequeños fragmenten el espacio que necesitan los grandes. Dos volúmenes separados, que es justo el argumento del particionado que veremos en 04-03.

Solución 3

Procedimiento de diagnóstico, en orden:

df -h /var/spool/cache        # 1. espacio: 31 % → no es esto
df -i /var/spool/cache        # 2. inodos: 100 % → AQUÍ ESTÁ
findmnt /var/spool/cache      # 3. confirmar el dispositivo y las opciones
sudo find /var/spool/cache -xdev -type f -printf '%h\n' \
     | sort | uniq -c | sort -rn | head    # 4. quién los ha creado
sudo dumpe2fs -h /dev/sdb1 | grep -E 'Inode count|Free inodes|Inode size'

El paso 2 es el diagnóstico y el 4 identifica al culpable. -xdev es importante: sin él, find cruzaría a otros sistemas de archivos y contaría ficheros que no ocupan inodos de este volumen.

Explicación técnica. En ext4 el número de inodos es fijo y se decide al formatear, con un inodo por cada 16 KiB por defecto. Un volumen de 50 GiB tiene así 3.276.800 inodos. Cada fichero, por pequeño que sea, consume uno. Cuando se agotan, creat() y open(O_CREAT) devuelven ENOSPC —"No space left on device"— aunque queden bloques libres, porque el núcleo no distingue entre los dos recursos en el código de error. Los ficheros de sesión de 600 bytes ocupan un bloque de 4 KiB y un inodo cada uno: los inodos se agotan cuando llevas 3,2 millones, con solo 13 GB usados.

Solución inmediata (restaurar el servicio):

sudo find /var/spool/cache/sesiones -type f -mtime +7 -delete
df -i /var/spool/cache          # verificar que ya hay inodos libres
sudo systemctl restart sesiones

Borrar los ficheros de más de 7 días libera inodos de inmediato. Con millones de ficheros conviene find ... -delete en lugar de rm -rf, que puede desbordar la línea de comandos.

Solución definitiva, en tres capas:

  1. Purga automática: una unidad systemd con temporizador (módulo 7) o una entrada de tmpfiles.d que borre las sesiones caducadas cada hora.
  2. Reformatear con la densidad correcta, previa copia de seguridad:
sudo mkfs.ext4 -b 1024 -i 2048 -m 0 -L sesiones /dev/sdb1

-b 1024 porque los ficheros son de 600 bytes y con 4 KiB se desperdicia el 85 %; -i 2048 da un inodo por cada 2 KiB, es decir 26 millones de inodos, muy por encima de los 3,2 originales; -m 0 porque es un volumen de datos temporales donde no hace falta reserva para root.

  1. Vigilancia: alertar cuando df -i supere el 80 %, exactamente igual que se vigila el espacio. Casi ningún sistema de monitorización lo hace por defecto, y por eso este fallo sigue apareciendo.

Alternativa razonable: montar /var/spool/cache como tmpfs, ya que las sesiones son volátiles por naturaleza. Se acaban los dos problemas de golpe, a cambio de RAM y de perderlas al reiniciar (04-03).

Conclusión

Un fichero es una secuencia de bytes con nombre, tamaño y propietario que el sistema coloca donde quiere y el programa lee como si fuera continua. Esa abstracción resuelve de un golpe los siete problemas que tendría cualquier aplicación trabajando sobre el vector de bloques crudo del módulo 2, y lo hace con la misma estrategia que la memoria virtual: una tabla de traducción que convierte un espacio lógico ordenado en un espacio físico disperso.

El fichero tiene tres partes en tres sitios: el contenido en la zona de datos, los metadatos en el inodo, y el nombre en el directorio. La consecuencia central, de la que cuelga medio módulo, es que el nombre no está dentro del fichero: el inodo 1180934 no sabe que se llama 2026-08-31.dat.

En UNIX hay siete tipos de fichero —regular, directorio, enlace simbólico, dispositivo de bloque, dispositivo de carácter, FIFO y socket— y los cuatro últimos ocupan inodo pero cero bloques de datos: la FIFO /run/meteora/lecturas.fifo y el socket api.sock del módulo 3 son entradas del sistema de archivos cuyo contenido vive en el núcleo. ls -l los distingue por su primer carácter y stat lo cuenta todo: tamaño lógico, bloques de 512 bytes, dispositivo, inodo, contador de enlaces y las cuatro fechas.

Físicamente, un ext4 se divide en grupos de bloques de 128 MiB, cada uno con mapa de bits de bloques, mapa de bits de inodos, tabla de inodos y zona de datos, precedidos por el superbloque —la ficha de identidad, con copias de respaldo que salvan volúmenes— y los descriptores de grupo. Pasar del número de inodo a su posición en el disco cuesta dos divisiones y una multiplicación, y esa es la razón profunda de que el inodo sea un número.

El tamaño de bloque es un compromiso medible: 4 KiB es el estándar porque coincide con la página de memoria (y por tanto con la caché de páginas y con mmap()) y con el sector físico moderno; bajarlo tiene sentido con millones de ficheros diminutos y subirlo, en Linux, ni siquiera es posible. Los inodos, en ext4, se fijan al formatear: de ahí el ENOSPC con el disco medio vacío que solo df -i explica. Y las cuatro marcas de tiempo distinguen leer (atime), modificar contenido (mtime), modificar metadatos (ctime) y crear (crtime); noatime elimina 48.000 escrituras diarias inútiles en meteo-01.

Con la comparación de familias en la mano, Meteora elige ext4 para /var/lib/meteora: madurez frente a datos irrecuperables, extents para describir 17 MB en un solo tramo, el juego de herramientas más completo para las tres de la mañana, y un ajuste consciente de -i 1048576 y -m 1 que recupera unos 11 GiB para datos útiles.

Nos queda el cabo suelto que hemos ido dejando en cada apartado: el nombre. Sabemos que no está en el inodo, sabemos que vive "en el directorio", y hemos dicho que un directorio es "un fichero especial", pero no hemos abierto ninguno. ¿Qué hay exactamente dentro de /var/lib/meteora/lecturas/? ¿Cómo consigue el sistema convertir la cadena /var/lib/meteora/lecturas/2026-08-31.dat en el número 1180934, y cuántos accesos a disco le cuesta? ¿Por qué un enlace simbólico puede quedarse roto y uno duro no? ¿Y qué pasa cuando un directorio tiene cien mil ficheros dentro?

Todo eso es lo que abre la siguiente lección: Estructuras de Directorios.

Fundamentos de Sistemas Operativos

Módulo 1: Introducción a los Sistemas Operativos

Módulo 2: Gestión de Recursos

Módulo 3: Concurrencia

Módulo 4: Estructuras de Archivos

Módulo 5: Protección y Seguridad del Sistema

Módulo 6: Virtualización y Contenedores

Módulo 7: Administración y Diagnóstico en la Práctica

© Copyright 2026. Todos los derechos reservados