GNU/Hurd ou la libération du noyau

Lorsque les sources de Linux grossissent de plus en plus, on peut se demander si un tel amalgame au niveau système est une bonne chose. Hurd propose de fournir le maximum de service en mode utilisateur, ce qui permet une grande modularité du système et l'utilisation d'outils personnalisés très puissants. Là où les Unix imposent des barrières, Hurd ne se borne à aucune limite.

Le Hurd est à la base du projet GNU, c'est un système multi-serveurs tournant sur le micro-noyau GnuMach. Il est le descendant naturel (bien que n'ayant aucun code en commun) du système mono-serveur 4.4 BSD Lite basé, lui aussi, sur un micro-noyau de type Mach. Contrairement aux autres systèmes qui restent sur les sentiers des Unix traditionnels, le Hurd minimise autant que possible la partie de code système. Il insère en mode utilisateur les différents services d'un système d'exploitation moderne, ce principe lui confère une grande modularité. Vous pouvez changer un service système dynamiquement sans rebooter votre machine et sans perturber les utilisateurs. Ces derniers peuvent aussi développer et utiliser leurs propres services systèmes.

Séquence de boot

La première chose qui diffère d'un système comme Linux, vous le verrez, c'est le démarrage : il se fait en plusieurs parties et seul Grub permet de spécifier les serveurs à lancer (lilo ne gère pas cela).

  • Première étape
    Lancement de Grub. Là, rien de nouveau. comme pour Linux, le boot loader se charge et exécute les commandes nécessaires au lancement du micro-noyau qui lui sont passées.

  • Deuxième étape
    Chargement du GnuMach. Jusqu'ici non plus rien de bien différent du boot Linux, si ce n'est le passage en paramètre à GnuMach de serverboot décrit dans la troisième étape. C'est donc GnuMach qui s'occupe de la détection et la prise en charge de votre matériel.

  • Troisième étape
    Lancement de serverboot (passé en option à Grub). C'est là que tout diffère. serverboot est le programme qui va s'occuper du chargement et de l'exécution de l'ensemble des serveurs du Hurd. serverboot est la première tâche que lance GnuMach. Il ne fournit pas de services utilisateurs; pourtant, il accède aux systèmes de fichiers (ext2, ffs ou minix) et lance les serveurs vitaux du Hurd.

    En effet, il fournit une compatibilité ELF et peut décompresser des fichiers. Cependant, les vrais serveurs qui assurent ces fonctionnalités au sein du système pour des tâches normales sont les traducteurs et le serveur exec. Il est à savoir que serverboot peut être lancé lorsqu'un Hurd tourne afin de tester un sous-Hurd. Comme il n'est pas possible de partager entre les deux instances du système des périphériques gérés par GnuMach, il s'agit juste d'une procédure de test afin d'effectuer une nouvelle mise en production. Mais cet élément est un des points forts du Hurd. Vous aurez alors le loisir de rebooter facilement sur votre nouvelle version.

    Les serveurs

    Un serveur est une tâche qui s'exécute en mode utilisateur. Dans le cas des serveurs du Hurd, il s'agit de rendre des services systèmes comme l'exécution, l'authentification ou l'accès au système de fichier. Chaque serveur est une tâche qui peut communiquer avec les programmes utilisateurs principalement grâce aux messages Mach envoyés au travers de ports (voir l'article sur Mach).

    Ces serveurs peuvent être multithreadés (rappelons que GnuMach possède une excellente gestion des threads) et fournir des services spécifiques au travers de divers protocoles de communication. Le Hurd permet à l'utilisateur de lancer ses propres services systèmes, donc ses propres serveurs. Il est alors possible de tester de nouvelles fonctionnalités sans perturber les autres utilisateurs et de changer dynamiquement un serveur.

    Pour le moment, les pilotes de périphériques sont implémentés dans GnuMach. Cependant, des tests ont été faits à l'université de Carnégie-Mellon pour pouvoir disposer de drivers dans l'espace utilisateur, surtout ceux relatifs au réseau, grâce à l'utilisation d'espace sur disque.

    La modularité fait de Hurd un système facilement distribuable. En effet, la transparence de la gestion des messages de GnuMach peut être étendue à l'utilisation sur un réseau grâce à un gestionnaire de messages approprié; ainsi, des tâches s'exécutant sur différentes machines donneront l'impression de s'exécuter en local. Les serveurs suivants sont pour la plupart lancés par serverboot et sont obligatoires au bon fonctionnement du Hurd :

    exec : Le serveur exec, bien plus puissant que la partie exec de serverboot, permet la création de nouvelles tâches à partir de fichiers images. Les images peuvent être de type a.out, ELF, ou tout autre format reconnu par la librairie BFD. Le serveur exec reconnaît également les images compressées aux formats gzip ou bzip2. Les futurs serveurs exec fourniront des compatibilités pour permettre l'exécution directe de programmes Linux, FreeBSD, Solaris, ou pourquoi pas, des programmes compilés pour d'autres plates-formes. Il permet aussi le lancement de l'interprétation des fichiers texte commençant par les caractères #!

    init : Le serveur init est lancé après exec. Il s'occupe de l'arrêt de Hurd et de Mach, lance le script /libexec/rc, amorce les autres serveurs importants et reboot en cas de crash des serveurs importants comme proc

    proc : Le serveur proc est chargé de la gestion des processus, il assigne les PID et gère les appels relatifs aux processus (wait, fork, implémentés au travers de la glibc). Il permet l'utilisation de la norme POSIX dans les programmes. Il assigne un PID à chaque tâche et permet leurs résolutions. C'est lui qui gère la gestion des signaux en utilisant des messages Mach. Ce serveur n'est pas obligatoire, il n'est là que par souci de compatibilité. Plusieurs serveurs proc peuvent cohabiter.

    auth : Il s'agit d'un des serveurs principaux du Hurd. Chaque nouveau serveur lancé par l'utilisateur doit s'authentifier auprès de auth. Un utilisateur peut cependant fournir ses serveurs auth pour ses propres besoins. Evidemment, un serveur auth tournant en root sera toujours présent.

    pfinet : Bien que n'étant pas indispensable à Hurd, pfinet est tout de même important car il assure la gestion réseau. Une version IPv6 verra bientôt le jour, tout comme un meilleur support de ppp. Ce serveur utilise la pile de Linux, il sera bientôt réécrit car il ne présente pas toute la modularité qu'offre un traducteur.

    Voilà pour les principaux serveurs; il en existe d'autres comme term qui fournit une gestion des terminaux POSIX, crash qui s'occupe des violations mémoire (segmentation fault), et qui permettra dans le futur de minimiser les risques de plantage par le biais d'airbags.

    Les traducteurs

    Il s'agit là d'un des points forts du Hurd. La communication entre utilisateurs et serveurs se fait à l'aide de ports (voir l'article sur Mach). Chaque fichier ou répertoire ouvert est lié à un port, ce port est créé par le traducteur puis renvoyé à l'utilisateur. Un traducteur peut donc "interpréter" ce port et, au lieu de donner le contenu du fichier, traduire celui-ci à l'utilisateur. On peut donc trouver des traducteurs simples ext2, ufs, isofs, et d'autres plus complexes comme FTPfs, qui traduit les accès aux fichiers/répertoires par des commandes FTP. Ainsi, vous pouvez éditer votre site Web en tapant simplement :

    emacs /mnt/ftp/www.monsite.org/index.html
    

    Il est à noter qu'un traducteur httpfs est en cours de développement. Les traducteurs peuvent être assignés à un fichier ou à un répertoire par l'utilisateur. Ils ne sont lancés qu'une seule fois pour gérer tous les accès à leur zone d'assignation dans le FS. Cela offre une grande modularité puisque, là où dans un système monolithique vous devez passer root, charger un module, ou bien rebooter sur un autre noyau, dans le système GNU, une commande lancée par un simple utilisateur suffit à charger différents types de systèmes de fichiers.

    La glibc

    Un noyau seul, vous vous en doutez, ne suffit pas, il faut pouvoir développer des programmes portables, et ce dans la plus grande homogénéité. Pour cela, le projet GNU fournit la GNU C Library. La glibc est la couche entre les programmes et GnuMach/Hurd. C'est elle qui implémente tous les appels POSIX et BSD. Malheureusement, les pthreads ne sont pas encore supportés correctement par la glibc; on peut cependant utiliser les cthreads de GnuMach.

    La glibc permet de porter facilement des programmes venant d'autres systèmes. Elle fait ressembler Hurd à Unix, bien que GNU's Not Unix. Les appels à la glibc sont convertis en succession d'appels à Hurd ou GnuMach. Pour la plupart d'entre eux, l'implémentation est assez complexe; par exemple, la glibc transforme un open() en une série d'appels à GnuMach (pour allouer les différents ports), et au serveur Term. Certains appels, par exemple fork(), sont implémentés quasiment entièrement dans la glibc : la nouvelle tâche est créée par des appels à task_create (GnuMach). Ensuite, la glibc est chargée de conserver les attributs du processus père pour les transmettre au fils. La gestion des droits se fait en collaboration avec le serveur proc.

    Si le développeur ne trouve pas son bonheur dans la glibc, il peut évidemment utiliser des appels à des serveurs ou à GnuMach. Pour cela, les développeurs de Mach ont conçu une interface commune permettant de faire communiquer les tâches entre elles : le Mach Interface Generator, ou MiG. Ce programme génère des fichiers permettant d'exporter des appels.

    Ainsi, les appels POSIX comme set*uid ou get*uid, importants lorsque l'on veut développer quelque chose de sécurisé, utiliseront les primitives du serveur auth (auth_user_authenticate(), auth_makeauth() ...). L'usage de MiG sera décrit dans de prochains articles. De gros serveurs comme proc utilisent, entre autres, le MiG mais fournissent aussi des bibliothèques à l'utilisateur (ex. libps pour proc).

    Un développeur peut donc utiliser les bibliothèques des serveurs, des appels POSIX, ou, s'il veut, des appels à GnuMach directement. Un exemple classique serait d'ouvrir et d'écrire dans un descripteur de fichier avec des appels comme hurd_new_fd, hurd_fd_write() ou même d'utiliser directement GnuMach. Ce choix peut se faire par souci de rapidité ou autre. Le système GNU laisse le champ libre au développeur, il ne l'enferme pas comme certains systèmes monolithiques :-)

    Nous espérons que cette introduction vous donnera envie de faire partie de la communauté Hurd, en attendant le prochain article qui traitera de MiG et des IPC :

    Happy hack !

    Liens

    Le projet Hurdfr
    http://www.hurdfr.org

    Le but du projet Hurdfr est de rassembler les gens passionnés du Hurd afin de créer une communauté de développeurs Hurd francophones grâce à divers moyens de communication : serveur web/ftp, mailing-list, mirror, CVS ... Nous ne voulons en aucun cas faire un autre site de news générales mais recentrer notre travail sur le développement et l'utilisation du Hurd. Nous comptons le plus tôt possible mettre une machine Hurd en ligne et migrer, petit à petit, la totalité des services que nous proposons sous cet OS :-)

    Page officielle GNU
    http://www.gnu.org/software/hurd/

    Le Hurd sur SourceForge
    http://hurd.sourceforge.net

    Projet Debian/Hurd
    http://www.debian.org/ports/hurd/

    Site de news sur le Hurd et quelques doc en français
    http://www.hurd-fr.org

    Le canal francophone #hurdfr sur Open Projects.

    Alexandre Fernandez alex@hurdfr.org
    Gibran Hasnaoui gibran@hurdfr.org

    Linux Magazine France n°28 - Mai 2001