PoC pour le Masterserver des jeux Unreal Engine 2.X
Il y a des années, je jouais beaucoup sur XIII en ligne, au point d’être vraiment excellent dessus. Jusqu’au jour où son MasterServer était mort. Merci Ubi.conm. Heureusement, ce jeu a été réalisé avec l’Unreal Engine 2.0, alors on a crée des alternatives qui relient sur le protocole GameSpy. J’en avais aussi réalisé un avec un serveur web, du SQL, et une modification d’un fichier provenant du package IpDrv du jeu Unreal Engine en question.
Et puis il y a aussi d’autres jeux de ce même moteur qui ont aussi leurs propres MasterServers morts. Pariah. Warpath. Day of the Zombie/Land of the Dead, mais ce dernier à eu un serveur de remplacement en 2009, en ayant intelligemment capturé des paquets avant sa fermeture prématurée. Cerise sur le gâteau, nous n’avions aucun Commandlet permettant de faire un Masterserver, sinon ça serait trop facile.
Et c’est dommage, ces jeux cités au dessus sont grave cools. Surtout Pariah, et son mini-éditeur de niveaux qui permettaient de jouer en ligne avec des niveaux inédits, pour oublier ses 4 maps vides et inadaptées au multijoueur…
C’est la que je me suis donné une idée stupide, mais intéressante : et si j’essayais de refaire fonctionner ces jeux en ligne, juste en tant que Proof of Concept ?
Recherches
Pour commencer mes recherches, j’ai cherché des informations sur comment fonctionnait le Masterserver d’Unreal 1, et accessoirement, UT99. Par chance, non seulement il est encore en vie, et si le jeu mourrait, on a la possibilité de créer son propre serveur de remplacement.
Le site de 333Networks m’a fortement aidé à comprendre : ce protocole de communication est basé sur celui de GameSpy, la version 1.0 plus exactement. En fait, une fois la communication obtenue entre le client et le Masterserver, ce dernier envoie immédiatement une commande de vérification (\\secure\\), pour s’assurer que le client est valide. Une fois confirmée, le client demande la liste des serveurs, que le Masterserver lui donne, avant de terminer par un \final\.
Reverse-Engineering et recréation du Masterserver
Avec Wireshark, j’ai essayé de voir avec le jeu Land of the dead (vu qu’il marche toujours) pour savoir ce que le jeu envoyait, et si c’était identique à UT99.
Grossière erreur.
Un paquet bien différent que dit au dessus. Autrement dit, il envoie un message de 3 bytes (en plus de sa taille) demandant l’authentification du client. Ce qu’il répond :
Beaucoup de bytes. Certains facile à comprendre, d’autres bien plus compliqués, et j’en suis encore au stade de décryptage. Alors, on dirait qu’il y a un hash de clé CD. Pariah en demandait une d’ailleurs.
Si le client est accepté après un check de clé CD (qui n’est pas réalisé d’ailleurs dans mon PoC), le serveur nous envoie un message avec « APPROVED » ou « DENIED » dans l’autre cas. UT2003/2004 d’ailleurs vérifie avec un autre paquet si on est vraiment vérifiable avec un autre hash, et nous renvoie un « VERIFIED« .
Additionnellement, si le client n’est pas à jour, c’est un « UPDATE » qu’il renvoie. Et si on veut rafraichir la liste des Masterservers, « MSLIST » est retourné.
J’ai recrée du coup ces communications de base pour voir si le MasterServer était dit comme « accessible » pour Warpath (et Pariah, vu qu’ils sont exactement basés sur le même jeu).
Apparemment, j’ai du nouveau, mais toujours pas de Masterserver actif. Je ne peux pas cliquer sur quoique ce soit, et il reste toujours en attente d’une communication… Ce qui est confirmée en revérifiant ce que le client demande. Mais c’est un bon débu…
… Un envoi d’un seul byte « 01 » ? C’est nouveau tiens, ça serait une requête de MOTD, comme montré dans le code UnrealScript?
Après plusieurs heures à essayer de comprendre comment ce message est formé avec UT2003/2004 (qui proposent toujours un MOTD avec des updates), j’ai pu réussir à faire un envoi qui ne crashe pas le jeu (car si le paquet est malformé, erreur mémoire, et donc, crash immédiat)
Joli ! Et les menus sont accessibles (sans aucun serveur, mais c’est gratuitement obvious) \o/ .
Je n’ai pas désiré aller plus loin, mais je suis confiant sur le fait que la liste des serveurs ne devraient pas être trop dur à implémenter… Et il manque aussi les requêtes Server <=> MasterServer, et pas mal d’autres points en sécurité…
Bref, cliquez en dessous pour voir ce que j’ai pu faire.
(et en cadeau, un paquet de DOTZ, donc il restera une base pour nous quelque part)