Página siguiente Página anterior Índice general

2. El sistema de archivos de red (NFS) de Sun.

En esta sección se analiza un ejemplo de sistema de archivo de red, el sistema de archivo de red de Sun Microsystems, conocido universalmente como NFS que fue diseñado e implantado por Sun en un principio para su uso en las estaciones de trabajo UNIX. Ahora, otros fabricantes lo soportan, tanto para UNIX como para otros sistemas operativos (incluido MS-DOS). NFS soporta sistemas heterogéneos; por ejemplo, clientes de MS-DOS que utilizan servidores UNIX. Ni siquiera es necesario que todas las máquinas utilicen el mismo hardware. Es común encontrar clientes de MS-DOS que utilizan CPU con Intel 386 y obtienen algún servicio de los servidores de archivos de UNIX que se ejecutan en Motorola 68030 o CPU SPARC de Sun.

Tres aspectos de NFS son de interés: la arquitectura, el protocolo y la implantación. Se analizan a continuación:

2.1 Arquitectura de NFS.

La idea básica detrás de NFS es permitir que una colección arbitraria de clientes y servidores compartan un sistema de archivos común. En la mayoría de los casos, todos los clientes y servidores están en la misma LAN, pero esto no es necesario. Es posible ejecutar NFS en una red de área amplia. Para simplificar la exposición se hablará de los clientes y servidores como si estuvieran en máquinas diferentes, pero de hecho, NFS permite que cada máquina sea cliente y servidor al mismo tiempo.

Cada servidor NFS exporta uno o más de sus directorios para su acceso por parte de los clientes remotos. Cuando se dispone de un directorio, también de todos sus subdirectorios, así que, de hecho, los árboles de directorios se exportan como una unidad. La lista de directorios que puede exportar un servidor se conserva en el archivo /etc/exports, de modo que estos directorios se pueden exportar de manera automática al arrancar el servidor.

Los clientes tienen acceso a los directorios exportados al montarlos. Cuando un cliente monta un directorio (remoto), éste se vuelve parte de su jerarquía de directorios. Muchas estaciones de trabajo Sun no tienen disco. Si así lo desea, un cliente sin disco puede montar un sistema de archivos remoto en su directorio raíz, lo que produce un sistema de archivos por completo soportado en un servidor remoto. Las estaciones de trabajo que sí tienen discos locales pueden montar directorios remotos en el sitio que deseen de su jerarquía local de directorios, lo que produce un sistema de archivos parcialmente local y parcialmente remoto. Para que los programas se ejecuten en la máquina cliente (casi) no existe diferencia entre un archivo localizado en un servidor de archivos remoto y un archivo localizado en el disco local.

Así, la característica básica de la arquitectura de NFS es que los servidores exportan directorios y los clientes los montan de manera remota. Si dos o más clientes montan el mismo directorio al mismo tiempo, se pueden comunicar compartiendo archivos en sus directorios comunes. Un programa en un cliente puede crear un archivo, y un programa en otro cliente puede leer el archivo. Una vez realizados los montajes, no hay que hacer nada especial para lograr compartir los archivos. Los archivos compartidos sólo están ahí, en la jerarquía de directorios de varias máquinas y pueden leerse y escribir en ellos de la manera usual. Esta sencillez es uno de los puntos fuertes de NFS.

2.2 Protocolos de NFS.

Puesto que uno de los objetivos de NFS es soportar un sistema heterogéneo, con clientes y servidores que tal vez ejecuten diferentes sistemas operativos con un hardware distinto, es esencial que la interfaz entre los clientes y los servidores esté bien definida. Sólo entonces es posible que cualquiera pueda escribir una nueva implantación cliente y espere que funcione de manera correcta con los servidores existentes y viceversa.

NFS logra este objetivo al definir dos protocolos cliente-servidor. Un protocolo es un conjunto de solicitudes enviadas por los clientes a los servidores, junto con las respuestas enviadas de regreso de los servidores a los clientes. Mientras un servidor reconozca y pueda controlar todas las solicitudes en los protocolos, no necesita saber nada de sus clientes. De manera análoga, los clientes pueden tratar a los servidores como "cajas negras" que aceptan y procesan un conjunto especifico de solicitudes. La forma en que lo hacen es asunto de ellos.

El primer protocolo NFS controla el anclaje. Un cliente puede enviar un nombre de ruta de acceso a un servidor y solicitar que monte ese directorio en alguna parte de su jerarquía de directorios. El lugar donde se montará no está contenido en el mensaje, ya que el servidor no se preocupa por dicho lugar. Si la ruta es válida y el directorio especificado ha sido exportado, el servidor regresa un identificador de archivo al cliente. El asa de archivo contiene campos que identifican de manera única al tipo de sistema de archivo, el disco, el número de inodo del directorio, e información de seguridad. Las llamadas posteriores para la lectura y escritura de archivos en el directorio montado utilizan el identificador del archivo.

Muchos clientes están configurados de modo que monten ciertos directorios remotos sin intervención manual. Por lo general, estos clientes contienen un archivo llamado /etc/rc, que es un shellscript que contiene las instrucciones para el montaje remoto. Este shellscript se ejecuta de manera automática cuando el cliente se arranca.

Otra alternativa a la versión de UNIX de Sun soporta también el automontaje. Esta característica permite asociar un conjunto de directorios con un directorio local. Ninguno de los directorios remotos se monta (ni se realiza el contacto con sus servidores) cuando arranca el cliente. En vez de esto, la primera vez que se abre un archivo remoto, el sistema operativo envía un mensaje a cada uno de los servidores. El primero en responder gana, y se monta su directorio.

El automontaje tiene dos ventajas principales sobre el montaje estático por medio del archivo /etc/rc. La primera es que si uno de los servidores NFS llamados en /etc/rc no está sirviendo peticiones, es imposible despertar al cliente, al menos no sin cierta dificultad, retraso y unos cuantos mensajes de error. Si el usuario ni siquiera necesita ese servidor por el momento, todo ese trabajo se desperdicia. En segundo lugar, al permitir que el cliente intente comunicarse con un conjunto de servidores en paralelo, se puede lograr cierto grado de tolerancia a fallos (puesto que sólo se necesita que uno de ellos esté activo) y se puede mejorar el desempeño (al elegir el primero que responda, que supuestamente tiene la menor carga).

Por otro lado, se supone de manera implícita que todos los sistemas de archivos especificados como alternativas para el automontaje son idénticos. Puesto que NFS no da soporte para la réplica de archivos o directorios, el usuario debe lograr que todos los sistemas de archivos sean iguales. En consecuencia, el automontaje se utiliza con más frecuencia para los sistemas de archivos exclusivos para lectura que contienen binarios del sistema y para otros archivos que rara vez cambian.

El segundo protocolo NFS es para el acceso a directorios y archivos. Los clientes pueden enviar mensajes a los servidores para que manejen los directorios y lean o escriban en archivos. Además, también pueden tener acceso a los atributos de un archivo, como el modo, tamaño y tiempo de su última modificación. La mayor parte de las llamadas al sistema UNIX son soportadas por NFS, con la probable sorpresa de OPEN y CLOSE.

La omisión de OPEN y CLOSE no es un accidente. Es por completo intencional. No es necesario abrir un archivo antes de leerlo, o cerrarlo al terminar. En vez de esto, para leer un archivo, un cliente envía al servidor un mensaje con el nombre del archivo, una solicitud para buscarlo y regresar un identificador de archivo, que es una estructura de identificación del archivo. A diferencia de una llamada OPEN,esta operación LOOKLJP no copia información a las tablas internas del sistema. La llamada READ contiene al identificador de archivo que se desea leer, el ajuste para determinar el punto de inicio de la lectura y el número de bytes deseados. Cada uno de estos mensajes está autocontenido. La ventaja de este esquema es que el servidor no tiene que recordar lo relativo a las conexiones abiertas entre las llamadas a él. Así, si un servidor falla y después se recupera, no se pierde información acerca de los archivos abiertos, puesto que no hay ninguno. Un servidor como éste, que no conserva información del estado de los archivos abiertos se denomina sin estado.

Por el contrario, en el sistema V de UNIX, el sistema de archivos remotos (RFS) requiere abrir un archivo antes de leerlo o escribir en él. El servidor crea entonces una entrada de tabla con un registro del hecho de que el archivo está abierto y la posición actual del lector, de modo que cada solicitud no necesita un ajuste. La desventaja de este esquema es que si un servidor falla y vuelve a arrancar rápidamente, se pierden todas las conexiones abiertas, y fallan los programas cliente. NFS no tiene esta característica.

Por desgracia, el método NFS dificulta el hecho de lograr la semántica de archivo propia de UNIX. Por ejemplo, en UNIX un archivo se puede abrir y bloquear para que otros procesos no tengan acceso a él. Al cerrar el archivo, se liberan los bloqueos. En un servidor sin estado como NFS, las cerraduras no se pueden asociar con los archivos abiertos, puesto que el servidor no sabe cuáles son los archivos están abiertos. Por lo tanto, NFS necesita un mecanismo independiente adicional para controlar los bloqueos.

NFS utiliza el mecanismo de protección de UNIX, con los bits rwx para el propietario, grupo y demás personas. En un principio, cada mensaje de solicitud sólo contenía los identificadores del usuario y del grupo de quien realizó la llamada, lo que utilizaba el servidor NFS para validar el acceso. De hecho, confiaba en que los clientes no mintieran. Varios años de experiencia han demostrado ampliamente que tal hipótesis era un tanto ingenua. Actualmente, se puede utilizar la criptografía de claves públicas para establecer una clave segura y validar al cliente y al servidor en cada solicitud y respuesta. Cuando esta opción se activa, un cliente malicioso no puede personificar a otro cliente, pues no conoce la clave secreta del mismo. Por cierto, la criptografía sólo se utiliza para autenticar a las partes. Los datos nunca se encriptan.

Todas las claves utilizadas para la autenticación, así como la demás información, son mantenidas por el NIS (servicio de información de la red). NIS se conocía antes como el directorio de páginas amarillas (yellow pages). Su función es la de guardar parejas (clave, valor). Cuando se proporciona una clave, regresa el valor correspondiente. No sólo controla las claves de cifrado, sino también la asociación de los nombres de usuario con las contraseñas (cifradas), así como la asociación de los nombres de las máquinas con las direcciones de la red, y otros elementos.

Los servidores de información de la red se duplican mediante un orden maestro/esclavo. Para leer sus datos, un proceso puede utilizar al maestro o cualquiera de sus copias (esclavos). Sin embargo, todas las modificaciones deben ser realizadas únicamente en el maestro, que entonces las propaga a los esclavos. Existe un breve intervalo después de una actualización en el que la base de datos es inconsistente.

2.3 Implantación de NFS

Aunque la implantación del código del cliente y el servidor es independiente de los protocolos NFS, es interesante echar un vistazo a la implantación de NFS. La capa superior es la capa de llamadas al sistema, la cual controla las llamadas como OPEN, READ y CLOSE. Después de analizar la llamada y verificar sus parámetros, llama a la segunda capa, la capa del sistema virtual de archivos (VFS).

La tarea de la capa VFS es mantener una tabla con una entrada por cada archivo abierto, análoga a la tabla de inodos para los archivos abiertos en UNIX. En el UNIX ordinario, un inodo queda indicado de manera única mediante una pareja (dispositivo, inodo). En vez de esto, la capa VFS tiene una entrada, llamada vnodo (inodo virtual), para cada archivo abierto. Los vnodos se utilizan para indicar si un archivo es local o remoto. Para los archivos remotos, se dispone de suficiente información para tener acceso a ellos.

Para ver la forma de utilizar los vnodos, sigamos una secuencia de llamadas al sistema MOUNT, OPEN y READ. Para montar un sistema remoto de archivos, el administrador del sistema llama al programa mount con la información del directorio remoto, el directorio local donde será montado y algunos otros datos adicionales. El programa mount analiza el nombre del directorio remoto por montar y descubre el nombre de la máquina donde se localiza dicho directorio. Entonces, entra en contacto con la máquina en la que se localiza el directorio remoto. Si el directorio existe y está disponible para su montaje remoto, el servidor regresa entonces un identificador de archivo para el directorio. Por último, llama a MOUNT para transferir el identificador del archivo al núcleo.

El núcleo construye entonces un vnodo para el directorio remoto y pide el código del cliente NFS para crear un rnodo (inodo remoto) en sus tablas internas, con el fin de mantener el identificador del archivo. El vnodo apunta al rnodo. Así, cada vnodo de la capa VFS contendrá en última instancia una referencia a un rnodo en el código del cliente NFS o una referencia a un inodo en el sistema operativo local. Así, es posible ver desde el vnodo si un archivo o directorio es local o remoto y, si es remoto, encontrar su identificador de archivo.

Al abrir un archivo remoto, en cierto momento durante el análisis del nombre de la ruta de acceso, el núcleo alcanza el directorio donde se desea montar el sistema de archivos remoto. Ve que este directorio es remoto y en el vnodo del directorio encuentra la referencia al rnodo. Le pide entonces al código del cliente NFS que abra el archivo. El código del cliente NFS busca en la parte restante del nombre de la ruta de acceso en el servidor remoto asociado con el directorio montado y regresa un identificador de archivo para él. Crea en sus tablas un rnodo para el archivo remoto y regresa a la capa VFS, la cual coloca en sus tablas un vnodo para el archivo que apunta al rnodo. De nuevo, vemos aquí que todo archivo o directorio abierto tiene un vnodo que apunta a un rnodo o a un inodo.

Quien hizo la llamada recibe un descriptor de archivo para el archivo remoto. Este descriptor de archivo se asocia con el vnodo mediante las tablas en la capa VFS. Observe que no se crean entradas en las tablas del lado del servidor. Aunque el servidor está listo para proporcionar los identificadores de archivo que le soliciten, no mantiene un registro de los archivos que tienen identificadores activos y los que no. Cuando se le envía un asa de archivo para el acceso a un archivo, verifica el identificador y, si éste es válida, sa utiliza. El proceso de validación puede incluir una clave de autenticación contenida en los encabezados RPC, si la seguridad está activada.

Cuando el descriptor de archivo se utiliza en una llamada posterior al sistema, por ejemplo, READ, la capa VFS localiza el vnodo correspondiente y por medio de él determina si es local o remoto y el inodo o rnodo que lo describe.

Por razones de eficiencia, las transferencias entre el cliente y el servidor se realizan en bloques grandes, por lo general de 8192 bytes, aunque se soliciten menos. Después de que la capa VFS del cliente ha obtenido el bloque de 8K que necesitaba, emite en forma automática una solicitud del siguiente bloque, por lo que lo recibirá rápidamente. Esta característica se conoce como lectura adelantada y mejora en forma considerable el rendimiento.

Se sigue una política análoga para la escritura. Si una llamada WRITE proporcióna menos de 8192 bytes de datos, los datos se acumulan en forma local. Sólo cuando el último pedazo de 8K está completo, se envía al servidor. Sin embargo, al cerrar un archivo, todos sus datos se envían al servidor de manera inmediata.

Otra de las técnicas que se utilizan para mejorar el rendimiento es el ocultamiento, como en el UNIX ordinario. Los servidores ocultan los datos para evitar el acceso al disco, pero esto es invisible para los clientes. Los clientes mantienen dos caches, uno para los atributos de archivo (inodos) y otro para los datos del archivo. Cuando se necesita un inodo o un bloque del archivo, primero hay que verificar si esta solicitud se puede satisfacer mediante el caché del cliente. En este caso, se evita el tráfico en la red.

Aunque el ocultamiento por parte del cliente ayuda en mucho a la tarea , también presenta algunos problemas molestos. Supongamos que dos clientes ocultan el mismo bloque del archivo y que uno de ellos lo modifica. Cuando el otro lee el bloque, obtiene el valor antiguo. El caché no es coherente.

Debido a la severidad potencial de este problema, la implantación de NFS hace varias cosas para mitigarlo. Una de ellas es que a cada bloque caché se le asocia un cronómetro. Cuando éste expira, la entrada se descarta. Por lo general, el tiempo es de 3 segundos para los bloques de datos y de 30 segundos para los bloques de directorio. Esto reduce un poco el riesgo. Además, al abrir un archivo con caché, se envía un mensaje al servidor para revisar la hora de la última modificación. Si la última modificación ocurrió antes de capturar en el caché la copia local, se descarta la copia del caché y se utiliza la nueva copia del servidor. Por último, el cronómetro del caché expira cada 30 segundos y todos los bloques sucios (es decir, modificados) en el caché se envían al servidor.

Aún así, NFS ha recibido amplias críticas por no implantar de manera adecuada la semántica apropiada de UNIX. Una escritura a un archivo de un cliente podría o no ser vista cuando otro cliente lea el archivo, según la sincronización. Además, al crear un archivo, esta acción podría no ser visible para el mundo exterior durante un periodo de 30 segundos. Existen otros problemas similares.

Por medio de este ejemplo, vemos que aunque NFS tiene un sistema compartido de archivos, como el sistema resultante es una especie de UNIX parchado, la semántica del acceso a los archivos no está por completo bien definida y la ejecución de un conjunto de programas que cooperen entre sí podría producir diversos resultados, según la sincronización. Además, lo único con lo que trata NFS es con el sistema de archivos. No hace referencia a otros aspectos, como la ejecución de un proceso. A pesar de todo, NFS es popular y tiene un uso muy extendido.


Página siguiente Página anterior Índice general