• Aucun résultat trouvé

ISC DHCP : étude du code source des logiciels client et serveur

7.2 Implémentation de E-DHCP

7.2.1 ISC DHCP : étude du code source des logiciels client et serveur

Le logiciel DHCP de l'ISC [ISC] est une implantation du protocole DHCP qui comporte un ensemble d'outils (un serveur DHCP, un client DHCP, le support de DHCP pour les relais).

Pour le développement, seul le client et le serveur ont été utilisés. Le serveur relais ne devrait pas poser de problèmes particuliers dans le sens où il ne fait que transmettre les paquets sans prendre en compte le contenu des options.

Les sources de logiciel DHCP de l'ISC se présentent ainsi. Un répertoire « common » contient les fichiers de définition des fonctions communes au client et au serveur. Un répertoire « client » contient le code spécifique au client, tandis que le répertoire « server » contient le code source spécifique au serveur. « relay » contient les sources permettant de définir des serveurs relais. « includes » contient les fichiers de déclaration de fonctions (fichier *.h).

La compilation fait apparaître, du moins sur nos stations, un répertoire ./work.linux-2.2/ dans lequel se trouvent en particulier les exécutables.

Les attributions d'adresses IP sont stockées dans un fichier de « leases ». Ce fichier n'est pas créé par défaut, il est donc nécessaire de le rajouter pour permettre le fonctionnement du serveur DHCP. Le client demande un fichier de configuration, un fichier de leases "dhclient.leases", et un script de configuration correspondant à l'OS utilisé. Comme le client, le serveur DHCP réclame un fichier de leases "dhcpd.leases" (pour plus des détailles voir Annexe D).

7.2.1.1 Analyse du code commun au client et au serveur

Outre son répertoire spécifique, chacun des modules utilise le repertoire includes/ qui contient les déclarations des structures et des fonctions ainsi que le répertoire common qui contient les fonctions partagées par le client et le srveur DHCP. Le répertoire common/ contient quant à lui les fichiers de définition (*.c) correspondants.

7.2.1.1.1 dhcp.h

Ce fichier contient les déclarations relatives à la forme d'un paquet DHCP. En particulier, il définit les différentes tailles des champs du paquet ainsi que la liste des options supportées par le logiciel. La structure dhcp_packet contient les différents champs DHCP (op, htype, hlen, etc.) sous forme « brute », d'entiers ou de tableaux d'entiers. En particulier, et cela est très utile, si la variable packet est de type dhcp_packet*, alors un simple cast (unsigned char *) packet permet d'avoir un unique tableau d'entier qui est en fait le paquet.

Le fichier contient d'autres déclarations permettant de manipuler à l'intérieur du programme les différentes valeurs possibles pour les champs prenant leur valeur dans un ensemble de taille finie (type de matériel, drapeau, type du message...).

7.2.1.1.2 tree.h

Ce fichier contient les définitions d'un certain nombre de structure se présentant sous forme d'arbre dans le programme. Nous allons en présenter quelques-unes.

7.2.1.1.2.1 data_string et buffer

Ces deux structures sont fréquemment utilisées dans tout le code, y compris dans celui que nous avons rajouté. Elles se présentent ainsi :

struct buffer { int refcnt;

unsigned char data [1]; };

/* A string of data bytes, possibly accompanied by a larger buffer. */ struct data_string {

struct buffer *buffer; const unsigned char *data;

int terminated; };

Le champ data de data_string est défini comme constant, ce qui signifie que l'on est pas censé écrire dessus (d'ailleurs, un *(ds->data)='0' dans le code provoque un warning lors de la compilation). Très souvent dans le code, on rencontre une initialisation de la forme ds->data = ds->buffer->data. On peut donc interpréter ce champ comme un moyen de lecture et le buffer comme un moyen d'écriture.

Plusieurs data_string peuvent pointer vers un même buffer, et c'est le rôle du champ refcnt de les comptabiliser. Les fonctions buffer_reference et buffer_dereference de alloc.c le gèrent pour nous.

7.2.1.1.2.2 expression

La lecture de sa déclaration et du enum expr_op qui la précède est aisée et s'assimile presque à une grammaire BNF. Elle est utile car c'est dans ce type de structure que sont stockées les informations de configuration après lecture du fichier de configuration. Or, les données pour E-DHCP se trouveront avant tout dans le fichier de configuration (flag, certificat d'identité, ...) ; il est donc nécessaire de les retrouver dans les multiples structures du programme.

7.2.1.1.3 dhcpd.h

Ce fichier contient l'essentiel des déclarations des structures et des fonctions. Cela est utile si l'on recherche le prototype d'une fonction, ou éventuellement dans quel fichier une fonction donnée est définie. Certaines des structures déclarées sont également très utiles :

7.2.1.1.3.1 option_cache

Cette structure sert à manipuler, tout au long du programme, les options présentes dans les paquets DHCP. Avec cette structure, une option peut être décrite soit par une expression, soit par une data_string. Par exemple, si oc est de type option_cache*, on pourra trouver :

oc -> data -> data pour lire les données « brutes » de l'option (sans le code ni la longueur).

oc -> data -> buffer -> data pour écrire ces mêmes données.

oc -> data -> len pour connaître la longueur (sans le code ni la longueur, conformément à la

RFC).

oc -> option -> code pour obtenir le code de l'option.

7.2.1.1.3.2 lease et lease_state

Ces structures permettent de manipuler les baux proposés par le serveur ou reçus par le client. Lease contient un champ lease_state qui, côté serveur, représente le traitement en cours du bail (si le champ est nul, le bail est libre).

7.2.1.1.4 alloc.c

Ce fichier contient des fonctions permettant d'allouer et de désallouer de la mémoire pour les structures en particulier data_string et buffer.

La fonction buffer_allocate permet de créer un buffer de taille len. Les fonctions buffer_reference et buffer_dereference permettent de gérer la valeur de refcnt dans la structure buffer suivant que le buffer est manipulé ou non par une structure.

La fonction data_string_copy permet de copier le contenu d'une data_string dans une autre. Il n'y a pas d'allocation de mémoire mais simplement modification des valeurs des pointeurs et mise à jour du compteur pour le buffer. La fonction data_string_forget modifie la valeur du refcnt du buffer qui est désallouée si plus aucun objet ne pointe dessus. Tous les pointeurs de la structure sont initialisés à NUL. La fonction data_string_truncate permet de tronquer la longueur de la chaîne de caractères manipulée par modification de la valeur de len dans la structure.

7.2.1.1.5 tables.c

Le fichier tables.c permet de définir le format des données contenues par une option, et ce pour plusieurs « universes ». Dans notre cas, on ne s'intéresse qu'au dhcp_universe et aux dhcp_options.