L'examen est composé de trois exercices indépendants qui peuvent être traités dans l'ordre que vous voulez.
Le premier exercice sera noté sur environ 9 points, le deuxième exercice 6 points et le troisième sur 5 points. Ce barème est fourni à titre indicatif et est susceptible d'évoluer. Il vous est donné pour vous permettre de répartir votre temps.
Rappel : vous devez créer un projet Java dont les sources seront stockées dans répertoire EXAM présent dans le home de votre session de TP noté (assurez-vous que c'est bien le cas du workspace d'Eclipse par défaut).
Vérifier bien que tous vos fichiers sont dans le répertoire EXAM. Tout ce qui n'est pas dans ce répertoire est perdu quand vous vous déconnectez (ou en cas de panne).
La Java doc est ici.
Toutes les classes de cet exercice doivent se trouver dans le package fr.uge.net.udp.exam2324.ex1.
Le but de l'exercice est de réaliser un client UDP bloquant pour protocole ClassRoom décrit ci-dessous.
00 00 00 07 4D 61 73 74 65 72 31Les paquets envoyés par le client ne peuvent pas dépasser 1024 octets. Le serveur va renvoyer autant de paquets qu'il y a d'étudiants dans la classe. S'il y a n étudiants dans la classe, les étudiants sont numérotés de 0 à n-1 et le serveur va renvoyer n paquets. Le paquet correspondant à l'étudiant numéro i contiendra :
Par exemple si la classe Master1 contient les quatre étudiants suivants :
0. Matthew Turner 1. Samuel Adams 2. Mason Green 3. Avery CampbellLe serveur va envoyer 4 paquets. Attention, ce protocole est un peu différent des protocoles vus en cours car un paquet envoyé par le client provoque l'émission de plusieurs paquets par le serveur. Le paquet correspondant à l'étudiant numéro 2 Mason Green sera le suivant :
00 00 00 02 00 00 00 04 00 00 00 05 4D 61 73 6F 6E 47 72 65 65 6Equi se décompose comme suit :
00 00 00 02 => numéro de l'étudiant 00 00 00 04 => nombre total d'étudiants 00 00 00 05 => taille de "Mason" encodé en UTF8 4D 61 73 6F 6E => "Mason" encodé en UTF8 47 72 65 65 6E => "Green" encodé en UTF8Les paquets envoyés par le serveur ne peuvent pas dépasser 2048 octets. On supposera que tous les paquets contiennent la même valeur pour le nombre total d'étudiants.
Dans un premier temps, on va supposer qu'aucun paquet ne peut être perdu ou retardé et vous implémenterez un client qui fonctionne dans ce cas là pour le protocole ClassRoom. Ce client prendra sur la ligne de commande le nom de la classe et affichera la liste des étudiants dans l'ordre fourni par le serveur. Si le paquet correspondant au nom de la classe dépasse la taille maximum du protocole ClassRoom, le client affichera une erreur et terminera.
Plus précisément, le client prendra en paramètres sur la ligne de commande les informations suivantes :
Dans une classe ClientClassRoom,
écrire un client UDP bloquant comme décrit ci-dessus.
Vous pouvez utiliser la trame suivante comme point de départ :
ClientClassRoom.java. Elle contient un record Student(String firstName, String lastName) et sa méthode launch doit renvoyer la liste des Student de la classe dans l'ordre donné par le serveur.
Vous testerez votre client en utilisant le serveur fourni ServerClassRoom.jar qui se démarre en fournissant le numéro de port d'écoute :
% java -jar ServerClassRoom.jar 7777
Si vous lancez votre client avec cette liste :
% java fr.uge.net.udp.exam2324.ex1.ClientClassRoom localhost 7777 Master1
vous devriez obtenir l'affichage suivant :
0. Matthew Turner 1. Samuel Adams 2. Mason Green 3. Avery Campbell
On veut maintenant prendre en compte le fait que des paquets UDP peuvent être perdus entre le client et le serveur, dans un sens comme dans l'autre.
On rappelle que le serveur répond avec tous les étudiants de la classe, dans des paquets séparés.
Au cas où au moins un paquet est perdu, votre client doit reposer sa question au bout de TIMEOUT millisecondes exactement.
Le TIMEOUT sera une constante de votre client qui vaudra 300.
Recopiez votre classe ClientClassRoom dans une nouvelle classe
ClientClassRoomFull que vous allez faire évoluer pour tenir compte des pertes de paquets.
Récupérez le jar UDPProxy.jar et démarrez-le entre votre client et le serveur. Dans trois fenêtres de terminal différentes, exécutez :
% java -jar ServerClassRoom.jar 4545
$ java -jar UDPProxy.jar 7777 localhost 4545 -no-swap
$ java fr.uge.net.udp.exam2324.ex1.ClientClassRoomFull localhost 7777 Master1
et vérifiez que l'affichage produit est correct. N'hésitez pas à tester avec des classes un peu plus grosses (par exemple, Master2 contient 9 étudiants)
Toutes les classes de cet exercice doivent se trouver dans le package fr.uge.net.udp.exam2324.ex2.
Dans cet exercice, on cherche à réaliser un serveur bloquant pour le protocole Stats décrit ci-après. Le protocole fournit un service extrêmement rudimentaire de statistiques en UDP.
Dans le protocole Stats, les clients envoient des paquets qui contiennent un int positif en BigEndian et le serveur répond avec un paquet contenant 2 ints et 2 longs en BigEndian. Plus précisément, les réponses du serveur sont de la forme suivante :
+-----------------------------------------------------------+ | min (INT) | max (INT) | average (LONG) | different (LONG) | +-----------------------------------------------------------+
avec :
Par exemple, si on démarre un serveur et qu'il reçoit de Bob l'INT 5, le serveur répondra avec [5 (INT) | 5 (INT) | 5 (LONG) | 1 (LONG)] car 5 est le plus petit entier reçu de Bob, 5 est aussi le plus grand entier reçu de Bob, la moyenne des entiers reçus de Bob est 5 et que le serveur n'a reçu qu'un seul nombre.
Si Bob envoie l'INT 4, le serveur répondra [4 (INT) | 5 (INT) | 4 (LONG) | 2 (LONG)] car 4 est le plus petit entier reçu de Bob, 5 est le plus grand entier reçu de Bob, la moyenne des entiers reçus de Bob est (4+5)/2=4 et que le serveur a reçu deux nombres distincts au total 4 et 5.
Si Bob envoie l'INT 1, le serveur répondra [1 (INT) | 5 (INT) | 3 (LONG) | 3 (LONG)] car 1 est le plus petit entier reçu de Bob, 5 est le plus grand entier reçu de Bob, la moyenne des entiers reçus de Bob est (1+4+5)/3=3 et que le serveur a reçu trois nombres distincts au total 1, 4 et 5.
Si Bob envoie à nouveau l'INT 1, le serveur répondra [1 (INT) | 5 (INT) | 2 (LONG) | 3 (LONG)] car 1 est le plus petit entier reçu de Bob, 5 est le plus grand reçu entier de Bob, la moyenne des entiers reçus de Bob est (1+1+4+5)/4=2 et que le serveur a reçu trois nombres distincts au total 1, 4 et 5.
Si un nouveau client Charlie envoie l'INT 4, le serveur répondra [4 (INT) | 4 (INT) | 4 (LONG) | 3 (LONG)] car 4 est le plus petit entier reçu de Charlie, 4 est le plus grand entier reçu de Bob, la moyenne des entiers reçus de Bob est (1+1+4+5)/4=2 et que le serveur a reçu trois nombres distincts au total 1, 4 et 5.
Dans une classe ServerStats,
écrire un serveur UDP bloquant pour le protocole Stats.
Vous pouvez utiliser la trame ci-après comme point de départ :
ServerStats.java.
Si vous lancez votre serveur comme ci-dessous :
% java fr.uge.net.udp.exam2324.ex2.ServerStats 7777
Vous pouvez le tester avec le client ClientStats.jar. Ce client prend en paramètre l'adresse du serveur.
% java -jar ClientStats.jar localhost 7777 Please enter your positive number: 5 févr. 14, 2024 9:50:22 PM fr.uge.net.udp.exam2324.ex2.ClientStats listener INFO: Received 24 bytes from /127.0.0.1:7777 Received the answer [min= 5; max= 5; average= 5; different= 1 ] from /127.0.0.1:7777 Please enter your positive number: 4 févr. 14, 2024 9:50:33 PM fr.uge.net.udp.exam2324.ex2.ClientStats listener INFO: Received 24 bytes from /127.0.0.1:7777 Received the answer [min= 4; max= 5; average= 4; different= 2 ] from /127.0.0.1:7777 Please enter your positive number: 3 févr. 14, 2024 9:50:39 PM fr.uge.net.udp.exam2324.ex2.ClientStats listener INFO: Received 24 bytes from /127.0.0.1:7777 Received the answer [min= 3; max= 5; average= 4; different= 3 ] from /127.0.0.1:7777
Toutes les classes de cet exercice doivent se trouver dans le package fr.uge.net.udp.exam2324.ex3.
Dans cet exercice, vous devez écrire un serveur UDP en mode non-bloquant qui implémente le protocole très simple décrit ci-après.
int en BigEndian
avec le premier int inférieur ou égal au second int.
Quand le serveur reçoit un de ces paquets contenant les int n1 et n2, il renvoie un paquet contenant l'int n1 en BigEndian, puis un paquet contenant l'int n1+1 en BigEndiant, et ainsi de suite jusqu'au paquet contenant l'int n2.
Si le serveur reçoit le paquet :
+-------------------------+
| 00 00 00 05 00 00 00 08 |
+-------------------------+
qui contient les int 5 et 8 ...
... alors le serveur renverra au client les quatre paquets suivants :
+-------------+
| 00 00 00 05 |
+-------------+
+-------------+
| 00 00 00 06 |
+-------------+
+-------------+
| 00 00 00 07 |
+-------------+
+-------------+
| 00 00 00 08 |
+-------------+
qui correspondent aux int 5, 6, 7 et 8 respectivement.
À partir du squelette de la classe
ServerRange.java,
écrivez un serveur en mode non-bloquant pour ce protocole.
Pour tester votre serveur, vous pouvez utiliser le client ClientRange.jar. Ce client prend en arguments l'adresse et le port du serveur. Il demande d'entrer au clavier les deux int à envoyer au serveur séparés par un point virgule. Il affiche les réponses reçues par le serveur.
Par exemple, si votre serveur est lancé sur le port 7777 :
$java fr.uge.net.udp.exam2324.ex3.ServerRange 7777
Vous pouvez le tester depuis un autre terminal (en gras, ce que l'utilisateur saisit sur l'entrée standard) :
$java -jar ClientRange.jar localhost 7777 Your input must be in the format int1;int2 with int1<=int2: 5;8 Sending the packet for [5, 8] févr. 14, 2024 7:05:55 PM fr.uge.net.udp.exam2324.ex3.ClientRange listener INFO: Received 4 bytes from /127.0.0.1:7777 Received packet [5] févr. 14, 2024 7:05:55 PM fr.uge.net.udp.exam2324.ex3.ClientRange listener INFO: Received 4 bytes from /127.0.0.1:7777 Received packet [6] févr. 14, 2024 7:05:55 PM fr.uge.net.udp.exam2324.ex3.ClientRange listener INFO: Received 4 bytes from /127.0.0.1:7777 Received packet [7] févr. 14, 2024 7:05:55 PM fr.uge.net.udp.exam2324.ex3.ClientRange listener INFO: Received 4 bytes from /127.0.0.1:7777 Received packet [8] Your input must be in the format int1;int2 with int1<=int2: ...