Sujet : Implémentation d'un système de cache de fichiers, sous forme d'une
modification du noyau Linux.

Le but de ce projet est de fournir une interface au système de fichiers
préexistant nommé NFS. Ce système est un système d'accès à des fichiers
situés sur un serveur distant (serveur NFS), par l'intermédiaire d'un réseau.
L'un des inconvénients de ce système est la lenteur des accès qu'impose le
réseau, comparativement à un accès à un fichier sur un disque local.

C'est pourquoi on envisage de fournir un accès aux fichiers d'un serveur NFS,
cependant on va le coupler avec un système de cache local, qui permettra
d'accélérer significativement les accès ultérieurs à ces données.

L'implémentation demandée est basée non pas sur les fichiers entiers, mais à
un niveau en-dessous, c'est à dire au niveau du bloc de données.
Cependant étant donné que le projet consiste à réaliser une interface entre
deux systèmes de fichiers (un local servant de cache et le système NFS), et que
ces deux systèmes n'ont pas forcément la même taille de bloc, l'implémentation
réalisée se base plutot sur des plages d'octets.

C'est à dire que si l'utilisateur lit les octets 1024 à 5869, exactement ces octets seront mis en cache pour un accès ultérieur. La plupart des programmes
accédant aux fichiers par l'intermédiaire de la libC (par exemple \i{fread()}),
ce choix de conception ne sera pas pénalisant (car la libC utilise un système de
buffers, et effectue des appels systèmes de type \i{read()} avec des valeurs
"rondes".

\chapter{Utilisation}

L'interface est réalisée sous la forme d'un système de fichiers, on la met donc
en place grace au moyen standard d'interaction avec les systèmes de fichiers,
c'est a dire \i{mount}. Le noyau a besoin de 4 choses pour pouvoir monter un
système de fichiers: un \i{point de montage}, un identifiant de
\i{périphérique}, un nom de \i{système de fichiers}, et eventuellement des
\i{options}.

Le projet à été réalisé sous la forme d'une interface générique entre 2
systèmes de fichiers, un \i{local} et un \i{remote}.

Le système \i{remote} est celui qui sert de référence, par défaut tous les
fichiers qu'il sert sont accessible par le système virtuel. Il n'est pas
envisagé de gestion de changements dans ses fichiers.

Le système \i{local} est celui qui sert de cache, il contient toute
l'arborescence offerte par le système remote, et il est monté de manière
read-only par rapport à l'utilisateur (c'est à dire que l'écriture ou la
modification des permissions des fichiers est interdite). Il a toutefois été
prévu le problème de désynchronisation avec le serveur, et l'opération
\i{unlink} (delete) est autorisée, elle a pour unique effet de supprimer toute
les informations du cache relatives au fichier ciblé. Le fichier sera toujours
accessible, s'il est toujours présent sur le \i{remote}.
Ce système doit être vierge avant le premier montage, il contient tous les
fichiers déjà accédés, ainsi que des fichiers contenant les information d'état
du cache (non accessible pour l'utilisateur quand le système est monté par
l'interface virtuelle, et si le système est monté comme étant de son type natif,
ce sont les fichiers .yaka*, qu'il est fortement déconseillé de modifier).

Le moyen retenu pour passer les paramètres au noyau pour pouvoir monter les
systèmes \i{remote} et \i{local} est l'utilisation des options de montage du
système virtuel. Les systèmes n'étant pas accessibles par l'utilisateur, il est
inutile de leur fournir un \i{point de montage}. Chaque parametre à passer aux
système subordonnés et passé au moyen d'une option de 2 lettres au système
virtuel.

La première lettre identifie le système cible: `r' pour \i{remote} et `l' pour \i{local}.

La deuxième lettre identifie le type de paramètre: `o' pour \i{option}, `t' pour type du système de fichier, `d' pour \i{device}, ainsi que le paramètre spécial
`n' qui indique que le système n'est pas disponible. Attention, les options
doivent être passées une par une.

Exemple: Pour monter un système virtuel, ayant pour remote un système `ext2',
le périphérique `/dev/hda1', en lui passant les options
`ro,nosuid,check=strict', et sans système local, on invoquera:
\i{mount -t yakafs none /path/to/mountpoint -o ln,rt=ext2,rd=/dev/hda1,ro=ro,ro=nosuid,ro=check=strict}
Le parsage de la chaine d'option étant faite en mode noyau pour les systèmes
subordonnés alors qu'elle est normalement réalisée en mode utilisateur par le
programme \i{mount}, le type de montage 'loopback' (pour monter un système de
fichiers stocké dans un fichier) est déconseillé, et non réalisable pour à
la fois le local et le remote. Si l'on veut l'utiliser, il faut spécifier
le nom du fichier comme device pour yakafs, '/dev/loopX' comme device pour
le système cible, et ajouter 'loop' comme option à mount, ce qui lui fait faire
le mappage du fichier et du device de loop. L'utilisateur doit calculer
lui-même le X (en général 0, sauf si d'autres systèmes sont déjà montés en
\i{loopback}). Exemple: \i{mount -t yakafs /path/to/file /mountpoint
-o loop,ln,rd=/dev/loop0,rt=ext2}
