Académique Documents
Professionnel Documents
Culture Documents
5 Gestión de Ficheros
Aníbal Ramírez García - Sistemas Operativos II - Departamento de Informática Aplicada - Capítulo V. Pag. nº 1
Escuela Universitaria de Informática - Universidad Politécnica de Madrid.
El Gestor de Ficheros de Minix 3, al igual que cualquier otros sistemas, debe tratar
aspectos como reserva y liberación de espacio para los ficheros, control de bloques
libres y asignados, control de acceso a los ficheros, etc. A lo largo de este capítulo
veremos algunos de los aspectos más relevantes de cómo se acomente la gestion
de ficheros en Minix 3.
El Gestor de ficheros (en adelante GF) de Minix 3 es un programa bastante grande
escrito en “C” que corre en espacio de usuario. Los procesos de usuario realizan
las llamadas al sistema relacionadas con ficheros , tales como abrir fichero, leer,
escribir, cerrar , etc, comunicándose con él mediante el envío y recepción de
mensajes, tal y como es habitual en Minix. El mecanismo es similar al empleado
por el Gestor de Procesos que ya se ha estudiado. Este diseño tiene algunas
implicaciones, por una parte, es posible modificar, ex-perimentar y testear el GF
casi completamente independientemente del resto de Minix. Por otra, es bastante
fácil portar el GF a otro ordenador dotado de un compilador de “C” . De este modo
podría se usado como un servidor de ficheros remoto. Los únicos cambios
requeridos afectarían a la forma en la que los mensajes se han de enviar y recibir,
la cual varía en cada sistema.
1
Gestión de ficheros - Minix 3
Visión general (1/4)
FUNCIONES BÁSICAS DEL GESTOR DE FICHEROS
• Tratar diversas llamadas al sistema
• Resolver las referencias a ficheros
• Comprobar el permiso de acceso a los recursos
• Ofrecer un tamaño de bloque lógico único
• Caché de bloques
• Asignación/liberación de espacio en dispositivos de bloques
• Gestión de errores
Aníbal Ramírez García - Sistemas Operativos II - Departamento de Informática Aplicada - Capítulo V. Pag. nº 2
Escuela Universitaria de Informática - Universidad Politécnica de Madrid.
- Tratar las llamadas al sistema relacionadas con ficheros tales como: creat, mknord, open,
close, read, write, lseek, stat, fstat, dup, pipe, ioctl, link unlink, mount, umount, sync, chdir,
chroot, chmod, chown, umask, acces, time stime, utime, times , etc.
- Resolver las referencias a ficheros. El GF debe saber qué dispositivo tiene asociado a un
fichero (disco, terminal, etc) para poder realizar las operaciones de E/S . Para ello guarda
en el I-nodo los números de dispositivo principal y secundario. El principal indientfica el
driver y el secundario el dispositivo propiamente dicho.
- Comprobar permisos de acceso a los recursos. Esto se realiza mendiante unos bits de
proteción que se mantienen en el I-nodo. Estos bits especifican entre otras cosas si el
objeto es un fichero o directorio, si tiene acceso de lectura, escritura o ejecución para los
diferentes ususarios y grupos, etc.
- Ofrecer un tamaño de bloque logico único para los dispositivos orientados a bloque. El
tamaño estándar de Minix 3 es de 4096 bytes.
- Almacenamiento intermedio de datos para dispositivos de bloques: Caché de bloques.
Este sistema agiliza la lectura/escritura de información, dado que la memoria en la que
reside la cache es más rápida que la de disco.
- Asignación y liberación del espacio en dispositivos de bloques. Para realizar este trabajo
Minix 3 utiliza mapas de bits de “zonas” (una zona es un número de bloques potencia de 2).
- Gestion y control de errores.
2
Gestión de ficheros - Minix 3
Mensajes proceso de usuario Parámetros de entrada Valor de respuesta
acces Nombre de fichero, modo de acceso Status
chdir Nombre nuevo directorio de trabajo Status
chmod Nombre fichero, nuevo modo Status
chown Nombre fichero, propietario, grupo Status
chroot Nombre del nuevo directorio Status
close Descriptor fichero a cerrar Status
creat Nombre fichero a crear, modo Descriptor de fichero
dup descriptor fichero (para dup2, 2 fds) Nuevo descriptor de fichero
fcntl descriptor fichero, código función, arg Depende de la funcion
fstat Nombre del fichero, buffer Status
ioctl Descriptor fichero, código función, arg Status
link Nombre fichero , nombre del enlace Status
lseek Descriptor fichero, desplazamiento, modo Nueva posición
mkdir Nombre fichero, modo Status
mknod Nombre Directorio especial, modo, dirección Status
mount Fichero especial., donde montar, “ro” flag Status
open Nombre fichero, “r/w“ flag Descriptor de fichero
pipe Puntero a descriptor de fichero [2] (modificado) Status
read Descriptor fichero, buffer, cuantos bytes Nº Bytes leidos
rename Nombre Fichero, nombre fichero Stauts
Aníbal Ramírez García - Sistemas Operativos II - Departamento de Informática Aplicada - Capítulo V. Pag. nº 3
Escuela Universitaria de Informática - Universidad Politécnica de Madrid.
3
Gestión de ficheros - Minix 3
Mensajes proceso de usuario Parámetros de entrada Valor de respuesta
rmdir Nombre de fichero Status
stat Nombre de fichero, buffer de estado Status
stime Puntero al tiempo actual Status
sync (nada) Siempre OK
time Dirección donde dejar el tiempo actual Status
times Buffer para tiempos de proceso e hijos Status
umask Complemento del modo mask Siempre OK
umount Nombre fichero especial a desmontar Status
unlink Nombre fichero a desenlazar Status
utime Nombre fichero, tiempos del fichero Siempre OK
write Descriptor de fichero, buffer, cuantos bytes Nº Bytes escritos
Mensajes del Gestor de Procesos
exec, exit Pid Status
fork Pid del padre, pid del hijo Status
Pid, real y efectivo (el uid y gid
setuid, setgid Status
respectivamente)
setsid Pid Status
Otros Mensajes
revive Proceso a revivir (sin respuesta)
unpause Proceso a chequear (explicación aparte)
Aníbal Ramírez García - Sistemas Operativos II - Departamento de Informática Aplicada - Capítulo V. Pag. nº 4
Escuela Universitaria de Informática - Universidad Politécnica de Madrid.
Cuando el GF realiza una operación de lectura por ejemplo sobre el terminal y ésta
no se puede completar, dado que el GF no puede quedarse bloqueado
indefinidamente a la espera de que haya suficientes caracteres en el terminal, el
driver de terminal toma nota de la operación pendiente y devuelve SUSPEND, para
que el GF no quede bloqueado. Más adelante, cuando se complete la operación
(suficientes teclas pulsadas), el driver de terminal envía el mensaje “revive” al GF
para que éste a su vez, desbloquee al proceso de usuario que originó el servicio.
4
Gestión de ficheros - Minix 3
Visión general (4/4)
PUBLIC int main() {
/* Bucle principal del gestor de ficheros. Consiste en tres actividades básicas:
Obtener trabajo, procesarlo y enviar una respuesta */
fs_init (); /* inicializacion */
while (TRUE) { /* bucle sin fin que obtiene y procesa el trabajo */
get_work (); /* devuelve “quien” y “nº llamada” */
if (call_nr==PROC_EVENT) { /* se comprueban mensajes de control especiales */
… /* tales como notificaciones y alarmas vencidas */
if (call_nr<0 || call_nr>= NCALLS) { /* comprobación de error en nº llamada */
….. /* se comprueban otros posibles errores como nº proceso ilegal */
} else
error = (*call_vec[call_nr]) ; /* se procesa la llamada (trabajo) */
}
return(OK); /* no se debería llegar aquí */
}
Aníbal Ramírez García - Sistemas Operativos II - Departamento de Informática Aplicada - Capítulo V. Pag. nº 5
Escuela Universitaria de Informática - Universidad Politécnica de Madrid.
5
Gestión de ficheros - Minix 3
Organización del sistema de ficheros (1/4)
Mapa de bits
de I-Nodos Mapa de bits
de zonas Formato de disco
……
Area de Area de
I-Nodos Datos
Bloque autorranque:
Programa de carga Superbloque:
del S.O -Número de I-nodos
-Número de bloques del mapa de bits de I-Nodos
-Número de bloques del mapa de bits de Zonas
-Primera zona de datos
-Log2 (tamaño zona/tamaño bloque)
-Tamaño máximo de fichero
-Número de zonas
-Tamaño del bloque
-Sub-version del Sistema de Ficheros
Aníbal Ramírez García - Sistemas Operativos II - Departamento de Informática Aplicada - Capítulo V. Pag. nº 6
Escuela Universitaria de Informática - Universidad Politécnica de Madrid.
6
Gestión de ficheros - Minix 3
Organización del sistema de ficheros (2/4)
Bloque
autoarranque Superbloque Formato de disco
……
Area de Area de
I-Nodos Datos
Mapas de bits :
1111101011 1100100011
0010011010 0111010011
I-Nodo
1100010010 1100101010 Zona
20
1001010111 0101001010 29
usado
0001010100 1100001010 libre
. . . . . . . . . .
0100000000 0000000000
Aníbal Ramírez García - Sistemas Operativos II - Departamento de Informática Aplicada - Capítulo V. Pag. nº 7
Escuela Universitaria de Informática - Universidad Politécnica de Madrid.
Minix 3 controla qué I-nodos y qué zonas están ocupados(as) o libres mediante mapas de
bits. Cuando se elimina un fichero, es fácil calcular en qué bloque del mapa de bits está el
bit asociado al I-nodo de dicho fichero y poner dicho bit a 0. Igualmente sucede para las
zonas. Cuando se crea un fichero el GF debe buscar un I-nodo libre. Para ello dispone de
un campo en la copia de memoria del superbloque que contiene la dirección del primer I-
nodo libre. Cuando el GF usa dicho I-nodo, debe actualizar el campo para que apunte al
siguiente I-nodo libre, que resultará ser el siguiente o uno posterior, buscándolo
secuencialmen-te y en adelante en el mapa de bits. Por otro lado, cuando se libera un I-
nodo, se comprueba si dicho I-nodo es anterior al apuntado, para actua-lizar el puntero si
así fuera. Si al buscar no se encuentra ningún I-nodo libre, la rutina devuelve el valor 0.
Esta es la razón por la que no se usa el 0 como número de I-nodo válido. Todo lo dicho
aquí para los I-nodos es aplicable también para las zonas; aunque lógicamente en este
caso, las búsquedas se efectúan cuando se requiere espacio de disco.
El propósito de la “zona” es mejorar el rendimiento de acceso secuencial haciendo que
bloques pertenecientes al mismo fichero se ubiquen en el mismo cilindro. Esto se consigue
al hacer que el fichero crezca y se ubique en unidades “zona”. La mayor parte del GF
trabaja con bloques. Las transferencias de disco son de bloque completo. La caché también
trabaja con bloques individuales.
El trabajar con zonas genera un problema que hay contemplar: Si por ejemplo, sobre un
fichero de 1 KB, en un sistema con bloque=1 KB y zona=4 KB, se efectúa una opera-ción
“lseek(32768)”, y a continuación se escribe 1 byte, el fichero crecería a 32769 bytes.
Posteriores lecturas más alla del byte 1024 podrían obtener información almacenada en el
sistema con anterioridad, lo que sería un fallo de seguridad a evitar. La solución es rellenar
a 0’s explícitamente, los bloques de la última zona que se ubica cuando un fichero crece.
7
Gestión de ficheros - Minix 3
Organización del sistema de ficheros (3/4)
Superbloque Formato de disco
……
Aníbal Ramírez García - Sistemas Operativos II - Departamento de Informática Aplicada - Capítulo V. Pag. nº 8
Escuela Universitaria de Informática - Universidad Politécnica de Madrid.
La función principal del I-nodo es indicar donde se encuentran los bloques del
fichero. El tamaño del I-Nodo en Minix 3 es de 64 bytes. Se usan 9 punteros a zona,
7 directos y 2 indirectos. Aunque hay espacio para uno más, la versión estándar no
lo soporta. Con un tamaño de bloques y zona de 4 KB, y puesto que los números de
zona son de 32 bits, en un bloque/zona de indices caben 1024 entradas
(apuntadores a zona). El doble indirecto da para 1024 x 1024 bloques/zonas,
haciendo que el tamaño máximo del fichero supere los 4GB. En la práctica el uso de
números de 32 bits para “offset” del fichero limita el tamaño del mismo a 4GB. Por
esta razón, al usar el estándar Minx 3 un tamaño de bloque/zona de 4KB, no se
requiere el uso del triple indirecto.
Los campos “tiempo ..“ son estándar, como en Unix. El último de ellos se actualiza
con casi todas las operaciónes excepto con la lectura del fichero.
El I-nodo tambien guarda información de modo, la cual informa del tipo de fichero
(regular, directorio, pipe, especial bloques, especial caracteres) y da los bits de
protección SETUID y SETGID. El campo “link” guarda cuantas entradas de
directorio apuntan al I-nodo.
El I-nodo puede usarse algunas veces de forma un poco especial, por ejemplo los
ficheros especiales de dispositvos de bloque y carácter no requieren los
apuntadores a zona y requieren en cambio los números “major” y “minor” de
dispositivo, por ello reutilizan el número de zona 0 para este propósito. Otro posible
uso, aunque Minix 3 no lo emplea, sería usar el I-nodo para guardar ficheros
pequeños inmediatos en el espacio para los números de zona.
8
Gestión de ficheros - Minix 3
Organización del sistema de ficheros (4/4) -Nº de I-nodos
-Nº de bloques del bitmap de I-Nodos
También en disco
-Modo y links
Tabla de I-nodos Tabla de superbloques -Nº de bloques del bitmap de Zonas
-Uid y Gid
-Primera zona de datos
-Tamaño fichero
-Log2 (tamaño zona/tamaño bloque)
-Tiempos acceso,
-Tamaño máximo de fichero
modificación y . . . . . . . . . . . . . . . .. ....................
-Nº de zonas
cambio status.
-Tamaño del bloque
-Zonas 0 a 6
-Sub-version del Sistema de Ficheros
-Zonas SI y DI
-Puntero a I-nodo del SF Montado
-Dispositivo Tabla flp -Puntero a I-nodo en el que se monta
-Nº I-nodo
- I-nodos / bloque
-Nº veces usado
-Número de dispositivo
-Limpio / sucio
-Flag sólo lectura
...............
-Montado (i_mount)
-Flag nativo o byte intercambiado
-Otros…
-Version del sistema ficheros
-Zonas directas / I-nodo
Tabla de procesos -Zonas indirectas / bloque indirecto
-Abierto para lectura/escritura
-Nº referencias de descrip. Fich.
.....
Tabla locks
....................
-Puntero a entrada Tbl. I-nodos
-Valor puntero L/E
-Máscara creacion ficheros ...............
Aníbal Ramírez García - Sistemas Operativos II - Departamento de Informática Aplicada - Capítulo V. Pag. nº 9
Escuela Universitaria de Informática - Universidad Politécnica de Madrid.
9
Gestión de ficheros - Minix 3
La cache de bloques Puntero Siguiente LRU
MRU Puntero Anterior LRU
LRU
1040 bloques Puntero Lista Hash
(Front) (Rear)
Número de bloque
Dispositivo (maj/min)
0 Limpio / Sucio
1 Contador de uso
2
Datos bloque
4096 bytes
-Para buscar un bloque se extrae su código hash
y se recorre su lista hash. Si no se encuentra se
2047
selecciona al primero de la LRU como víctima
Tabla hash
y le carga el bloque de disco en él, añadiendolo
a su lista hash correspondiente.
-En get_block, cuando se encuentra un bloque
se incrementa el contador de uso y se le quita Nº de bloque: 12345 (0x3039)
de la LRU. En put_block se decrementa el con-
000000000011000000111001
tador y se devuelve el bloque a la lista LRU.
-Al devolver un bloque a la LRU se inserta por
Código hash: 57 (0x39)
el final, excepto si es un bloque del disco RAM.
-Un bloque sucio se escribe en disco cuando:
Es elegido víctima o con la llamada “sync”.
Aníbal Ramírez García - Sistemas Operativos II - Departamento de Informática Aplicada - Capítulo V. Pag. nº 10
Escuela Universitaria de Informática - Universidad Politécnica de Madrid.
La caché de Minix 3 utiliza un “array” de un tamaño fijo de buffers. El tamaño de este array y el
tamaño del bloque dependen de la compilación de Minix. Para un PC típico este el array es de 1040
elementos y el bloque de 4 KB. Cada elemento, o buffer, contiene una cabecera y un bloque de
información. En la cabecera se encuentran los punteros para implementar las listas LRU, MRU y
Hash, el Nº de bloque, el dispositivo donde reside el bloque, el campo limpio/sucio (indica si ha
habido cambios desde que se cargó en memoria), y un contador de uso. Además de este array
existe otro llamado “tabla Hash” de 2048 elementos que sirve para determinar rápidamente si un
bloque está, o no, en la caché. Todos los buffers que contienen un bloque cuyo código hash es “k”,
están enlazados en una lista simple encabezada por la entrada “k” de la tabla hash. La función hash
calcula “k” extrayendo simplemente los “n” bits menos significativos del nº de bloque, con
independencia del dispositivo. Inicialmente todos los buffers están sin usar y enlazados a la lista hash
“0”. Las demás listas hash están vacías. Cuando el GF requiere un bloque llama a la función
“get_block”, la cual calcula el código hash y busca en su lista hash, discriminando el nº de dispositivo.
Si se encuentra, se incrementa el contador de uso, se quita de la lista LRU/MRU y se devuelve como
resultado un puntero al buffer. Si no se encuentra, se elige como víctima el primer buffer de la lista
LRU. Está garantizado que no estará en uso.
Antes de deshacerse de la victima hay que comprobar el flag limpio/sucio, para escribir o no el
bloque en consecuencia. En este punto se envía un mensaje al driver de disco para leer el bloque
requerido, quedando el GF a la espera de la respuesta. Cuando ésta llega el GF continúa y acaba
retornando un puntero al buffer con el bloque leido. Cuando el procedimiento que solicitó el bloque
completa su trabajo llama a la función “put_block” la cual decrementa el contador de uso y si queda
en 0 devuelve el bloque a la lista LRU.
Casi todos los bloques se insertan por el final de la lista LRU. La excepción son los bloques de disco
RAM. Un bloque no se escribe en disco hasta que sucede, bien que se alcanza el principio de la LRU
y se elige como victima, o bien se ha ejecutado la llamada al sistema “sync”. Esta función recorre el
array de buffers, no la lista LRU, evitando así la omisión de buffers “en uso” (que no están en la lista
LRU).
10
Gestión de ficheros - Minix 3
Directorios y rutas 1/2 Tabla de nodos-
nodos-i Formato de directorio
Nº de I-nodo
Tabla de procesos del GF (4 bytes)
Nombre de fichero
(60 bytes)
Resolució
Resolución de /user/pepe/f1
Punteros a los I-nodo 1 Direct. Raiz I-nodo 7
I-nodos asociados (direct. raí
raíz (bloque 120) (direct. User)
a los directorios 1 .
raíz y trabajo de Mode, links Mode, links
Uid, gid 1 .. Uid, gid
éste proceso.
Size, Times 2 dev Size, Times
Z0=120 7 user Z0=206
Aníbal Ramírez García - Sistemas Operativos II - Departamento de Informática Aplicada - Capítulo V. Pag. nº 11
Escuela Universitaria de Informática - Universidad Politécnica de Madrid.
En Minix 3 los directorios son ficheros estructurados en forma de tabla con elementos de 64 bytes.
Cada entrada consta de dos campos, el primero, de 32 bits, guarda el nº de I-nodo del fichero. El
segundo, un campo de 60 bytes, guarda el nombre del fichero en forma de array de caracteres
finalizados con el carácter 0. Hay gran cantidad de llamadas al sistema que utilizan como parámetro
una ruta ó camino a fichero. Todas ellas deben resolver dicha ruta para acceder al fichero, siguiendo
una serie de pasos. En la figura se muestra un ejemplo: Para conseguir el I-nodo del fichero
“/usr/pepe/f1” hay que acceder al I-nodo del directorio raiz. Todo proceso guarda en un campo de su
descriptor, en la Tabla de Procesos (TP), un puntero al mismo. En el ejemplo, el I-nodo 1. En dicho I-
nodo leemos el primer bloque (zona) de datos que es la 120. Accediendo a dicho bloque (zona), que
contiene el directorio raiz, buscamos la entrada “user”, la cual tiene de I-nodo el 7. Accedemos al I-
nodo 7 a través de la tabla de I-nodos (si no esturviera en la tabla habría que cargalo desde el area
de I-nodos del disco). Vemos en dicho I-nodo el primer bloque (zona) de datos que es el 206 y
seguimos así hasta conseguir que finalmente el I-nodo 44 se carge en la tabla de I-nodos. En todo
este proceso, al solicitar bloques de datos, se hace uso de la caché. Algunos bloques solicitados
estarán en ella y otros habrá que traerlos de disco a la misma. Los I-nodos de directorios se
descargan de la tabla de I-nodos una vez usados, excepto si estuvieran siendo usados por otro
proceso.
Cuando la ruta a resolver es relativa al directorio de trabajo, como por ejemplo “pepe\f1” el proceso
que se sigue es similar pero comienza con el puntero a I-nodo del directorio de trabajo del proceso, el
cual se encuentra también en su descriptor o entrada en la TP.
En el proceso descrito arriba no se ha contemplado si existe algún SF montado en algún directorio.
Veremos más adelante como se efectua la operación “mount” y como afecta a la busqueda o
recorrido de una ruta.
Hay que señalar también que durante el recorrido de la ruta, el GF ha de comprobar los permisos de
acceso a cada uno de los directorios de paso. Para todas la llamadas al sistema se utilizan los uid y
gid efectivos del proceso excepto para la llamada “access” que se usan los uid y gid reales.
11
Gestión de ficheros - Minix 3
Directorios y rutas 2/2 Sistema de
ficheros montado
Sistema de Sistema de
/
ficheros raíz ficheros a montar
/ /
lib bin user
Tabla de nodos-
nodos-i 2
Tabla de superbloques i_mount
4 activo
s_imount s_isup
5
3
1
I-nodo del directorio raíz del
Superbloque del sistema sistema de ficheros a montar
de ficheros a montar
Aníbal Ramírez García - Sistemas Operativos II - Departamento de Informática Aplicada - Capítulo V. Pag. nº 12
Escuela Universitaria de Informática - Universidad Politécnica de Madrid.
12
Gestión de ficheros - Minix 3
Gestión de Tablas (1/3)
Procedimiento Función
get_block Obtiene un bloque para lectura o escritura
put_block Devuelve un bloque previamente pedido por get_block
alloc_zone Reserva una nueva zona (para hacer un fichero mas grande)
free_zone Libera una zona (cuando se elimina un fichero)
rw_block Transfiere un bloque entre disco y caché
invalidate Purga todos los bloques de la caché de algún dispositivo
flushall Escribe todos los bloques sucios de un dispositivo
rw_scattered Lee o escribe datos dispersos a ó desde un dispositivo
rm_lru Quita un bloque de la lista LRU
Aníbal Ramírez García - Sistemas Operativos II - Departamento de Informática Aplicada - Capítulo V. Pag. nº 13
Escuela Universitaria de Informática - Universidad Politécnica de Madrid.
Los procedimientos básicos que soportan la cache son: Get_block. Se invoca con nº de bloque y
dispositivo. Sirve para obtener cualquier tipo de bloque. Ya se ha visto con anterioridad, aunque falta
decir que cuando se especifica only_search como parámetro de entrada, aunque no esté el bloque
en la caché, éste no se lee del disco. Con dicho parámetro se pretende, bien hacer un prefetch, o
bien escribir un bloque en su totalidad. En ambos casos es un desperdicio leer el bloque del disco.
Put_block. Se encarga de devolver el bloque a la lista LRU y en algunos casos escribirlo en disco.
También se ha mencionado con anterioridad. En versiones anteriores de Minix, dependiendo del tipo
de bloque, éste se escribía de forma inmediata o no, Actualmente, aunque se sigue haciendo la
comprobación, no se marca ningún bloque para escritura inmediata. Alloc_zone. Se encarga de
reservar una nueva zona en un dispositivo tomando como punto de partida otra zona que se le da
como parámetro. La reserva la hace buscando en el mapa de bits de zonas. Cuando un fichero crece,
el GF comprueba si es la primera zona, si es así utiliza el campo s_zsearch del superbloque, el cual
apunta siempre a la primera zona disponible del dispositivo. Si no fuera la primera zona, se busca la
siguiente zona a la última zona existente del fichero, para intentar con ello mantener las zonas de un
fichero juntas. Free_zone. Se encarga de devolver las zonas de un fichero al mapa de bits cuando
éste se borra. Lo hace llamando a free_bit, pasándole la posición del bit y el mapa de bits como
parámetros. free_bit también se utiliza para liberar I-nodos. Rw_block. Lee o escribe un bloque entre
disco y cache. Análo-gamente existe la función rw_inode para I-nodos. Invalidate. Elimina todods los
bloques de la caché del dispositivo que se le pasa como parámetro. Flushall. Escribe en disco todos
los bloques sucios de la caché del dispositivo que se le pasa como parámetro. Para hacerlo recorre
el array entero de buffers, evitando así omitir los buffers en uso. Rw_scattered. Los drivers de disco
de Minix 3 no implementan planificación de escritura en disco. Esta función proporciona una
alternativa a dicha carencia. Acepta como parámetros: un dispositivo, un array de punteros a buffers,
el tamaño del array, y un flag indicando lectura o escritura. Lo que hace es ordenar el array de
punteros a buffer según su nº de bloque y luego construye vectores de bloques contiguos para enviar
al driver. La única llamada a rw_scattered para escribir la hace flushall y la única llamada para leer
rahead. Rm_lru. Elimina un bloque de la lista LRU. Se usa desde get_block.
13
Gestión de ficheros - Minix 3
Gestión de Tablas (2/3)
Aníbal Ramírez García - Sistemas Operativos II - Departamento de Informática Aplicada - Capítulo V. Pag. nº 14
Escuela Universitaria de Informática - Universidad Politécnica de Madrid.
14
Gestión de ficheros - Minix 3
Gestión de Tablas (3/3)
Aníbal Ramírez García - Sistemas Operativos II - Departamento de Informática Aplicada - Capítulo V. Pag. nº 15
Escuela Universitaria de Informática - Universidad Politécnica de Madrid.
15
Gestión de ficheros - Minix 3
Ejemplo llamada al sistema, “read” (1/3)
Proceso
read(df, &buffer, n)
usuario
send_rec(GF, &mensaje)
1) Mensaje para escribir un
bloque sucio que se ha elegido
send(proc_usr, &respuesta)
como víctima. (pueden
producirse varios o ninguno).
Gestor 2) Mensaje para traer un bloque
send_rec(Driver,&mensaje) Ficheros de disco a caché (pueden
producirse varios o ninguno)
send_rec(Driver,&mensaje) 3) Mensaje para copiar datos a
espacio de usuario (pueden
send_rec(TS,&mensaje) producirse varios)
1
--------------------------------------
3 Driver Disco puede referirse al
Driver driver de disco RAM, al de floppy
Disco Tarea o disco duro.
2
del
send(GF,&respuesta) Sistema
Driver
Disco send(GF, &respuesta)
send(GF,&respuesta)
Aníbal Ramírez García - Sistemas Operativos II - Departamento de Informática Aplicada - Capítulo V. Pag. nº 16
Escuela Universitaria de Informática - Universidad Politécnica de Madrid.
Cuando un proceso de usuario ejecuta read (fd, buffer, nbytes) sobre un fichero ordinario,
la función de librería read construye un mensaje con estos tres parámetros junto con el
código read para el tipo de mensaje, envía el mensaje al GF y se bloquea esperando una
respuesta. Cuando el GF recibe el mensaje, usa el tipo como índice en la tabla de punteros
a procedimiento e invoca la función que trata la lectura (do_read). Esta función extrae el
descriptor de fichero del mensaje y lo usa para localizar la entrada filp y el I-nodo del fichero
a leer. La petición de bytes se divide en trozos que encajen en un bloque. Para cada trozo,
se comprueba si su bloque está en la caché. Si no está el GF selecciona el bloque (buffer)
menos re-cientemente usado que no esté en uso actual y lo reclama, enviando un mensaje
al driver de disco para escribirlo si estuviera sucio y pedirle al driver que obtenga el bloque
a leer (en el buffer seleccionado). Una vez que el bloque está en la caché, el GF envía un
mensaje a la Tarea de Sistema pidiéndole que copie los datos al lugar apropiado del
espacio de usuario, una vez copiados la TS responde con el nº de bytes copiados.
Cuando llega la respuesta al usuario, la funcion de librería read extrae el código de
respuesta y lo devuelve al llamador como valor de retorno de función.
Hay un paso extra que no forma parte de read. Después de que el GF complete la lectura y
envíe la respuesta, El GF inicia la lectura de bloques adicionales, siempre que la lectura
sea sobre un dispositivo de bloques y se cumplan algunas otras condiciones. Ya que la
lectura de ficheros secuencial es corriente, es razonable esperar que se pida el siguiente
bloque del fichero en la siguiente petición, y sería deseable que dicho bloque ya estuviera
en la caché. El número de bloques de lectura adelantada depende de la caché, pudiendo
ser de hasta 32 bloques. El driver no tiene porqué devolver tantos bloques y si devuelve
sólo uno se considera un éxito.
16
Gestión de ficheros - Minix 3
Ejemplo llamada al sistema, “read” (2/3)
Número de byte
0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28
Posición actual = 1
Trozo = 6
Trozo = 1
Aníbal Ramírez García - Sistemas Operativos II - Departamento de Informática Aplicada - Capítulo V. Pag. nº 17
Escuela Universitaria de Informática - Universidad Politécnica de Madrid.
El núcleo principal del mecanismo de lectura (de un fichero ordinario) lo constituye un bucle que
descompone la petición en trozos, cada uno de los cuales encaja en la lectura de un único
bloque. Un trozo comienza en la posición actual y se extiende hasta que se alcanza alguna de las
siguientes condiciones: 1) Se han leido todos los bytes, 2) se ha encontrado el final de un bloque
y 3) se ha alcanzado el fin de fichero. Estas reglas implican que nunca se requiere más de un
bloque para leer un trozo. El procedimiento que efectúa la lectura de un trozo es rw_chunk.
Cuando esta función devuelve el control, se incrementan varios contadores y punteros y
comienza la siguiente iteración. Cuando finaliza el bucle se actualizan el puntero a la posicion
actual y otras variables (por ejemplo, apuntadores pipe).
Finalmente, si se ejecuta la lectura adelantada, el I-nodo y la posición desde la que leer se
almacenan en variables globales, tal que después de haber enviado la respuesta al usuario, el GF
puede empezar a leer el siguiente bloque. En muchos casos el GF se bloqueará, esperando al
siguiente bloque del disco, mientras tanto el proceso de usuario podrá ir trabajando con los datos
recien recibidos. Con este sistema es posible solapar el procesador con la E/S y con ello mejorar
substancial-mente el rendimiento.
17
Gestión de ficheros - Minix 3
Ejemplo llamada al sistema, “read” (3/3)
Puntos de entrada
do_read do_write
dev_io
Aníbal Ramírez García - Sistemas Operativos II - Departamento de Informática Aplicada - Capítulo V. Pag. nº 18
Escuela Universitaria de Informática - Universidad Politécnica de Madrid.
18