Nous avons testé pour vous Halcyon Inet 

 

Introduction

Suite à l'article paru sur DotNet-Fr concernant le produit Halcyon Inet, nous n'avons pas résisté à l'envie de vous faire partager nos premiers tests de cet outil essentiellement destiné à exécuter des applications .NET dans une machine virtuelle Java par conversion du MSIL. 

Attention, concernant l'outil d'Alcyon, outre le fait que le produit présente des caractéristiques techniques intéressantes à étudier, l'annonce revêt une importance capitale de par son impact "politique". Jusque là, c'est toujours Microsoft qui a cherché à intégrer Java dans sa plate-forme (J++,J#, ..) et aujourd'hui, un premier éditeur tente de réaliser l'opération inverse. 

En tant que passionnés du développement .NET et Java, nous ne pouvions qu'être agréablement surpris par cette annonce. Imaginez les diminutions de coûts de migration que procurerait un tel produit dans le cas où une entreprise décidait en cours de route (!) de passer à Java. Sans chercher très loin, imaginez d'utiliser toute la puissance du Framework .NET associé à la puissance des APIs Java en ayant le choix à tout moment, quel programme ! Bref, arrêtons de rêvasser et regardons de plus près Alcyon.

Installation, configuration et exécution

Tout d'abord, l'installation du produit se fait de manière classique, il vous suffit de récupérer la béta 1 du produit à l'adresse suivante. Vous avez la possibilité de récupérer un bundle complet incluant une machine virtuelle et Mysql pour la connectivité aux bases, ou alors une version "allégée" avec uniquement le socle du produit. Nous avons choisi la seconde option par souci de simplicité. Après avoir défini l'emplacement de la machine virtuelle, vous spécifiez la nature du serveur web installé sur votre système. Disposant d'une version de Oracle 9i AS par hasard ;-), nous avons fait le test avec ce produit. L'étape suivante consiste à configurer le plug-in IL2Java permettant de convertir du byte-code .NET en Java. Nous acceptons la proposition de l'installer sous la forme de plug-in sous Visual Studio .NET.

Une fois l'installation terminée, il est difficile de se retenir à l'envie de tester la conversion d'une assembly .NET en Java. Pour cela, nous utilisons IL2Java proposant un browser de fichiers  rudimentaire, mais qu'importe, l'essentiel étant que le produit réponde à nos attentes.

Nous nous empressons de choisir notre fameux fichier hello2.dll et là ........... 

........... Ô stupeur, après 15 secondes de "crépitement" du disque, quelle agréable surprise de voir apparaître un ensemble de fichiers .class et .Java !!!

L'ensemble des classes C# ont été extraites sous la forme de fichier .java et .class. Non seulement l'outil a traduit le code MSIL en Byte-code mais il s'est aussi empressé de nous décompiler la classe en code source Java !! Un peu abasourdi (pas vraiment mais c'est pour donner du piment au récit ;-) ) nous nous dépêchons de vérifier le contenu du source Java en question.

Et là, petite déception de voir que le code HelloWorld C#, à la base si simple se transforme en Japonais (pardon en JavaPonais). Plus sérieusement, l'étape de décompilation s'est traduite par la génération de code supplémentaire lié à plusieurs facteurs. Tout d'abord, une nouvelle classe mère apparaît en lieu et place de la classe java Object : ObjectPeer. Ensuite, le nommage des variables temporaires résultants de la décompilation tendent à polluer légèrement la lisibilité du code. 

Après une étude plus poussée, nous découvrons avec émerveillement que Halcyon a totalement converti les APIs du Framework .NET en classes Java. Ainsi vous trouverez system.Collections, system.Web, system.XML... rien n'a été laissé au hasard, même pas les WinForms. Vous avez la possibilité de lancer des samples de WinForms C# affichant des Frames en Java !! intrigués, nous jetons un oeil sur les sources de Halcyon. Nous procédons par décompilation (à notre tour) des librairies à l'aide de l'outil Jad tout en focalisant notre attention sur une classe clé du Framework : Form.java. Après analyse, il résulte que Halcyon a utilisé les APIs  java.awt et javax.swing pour afficher les Forms. Notre supposition était donc bien fondée, aucune utilisation de code natif, aucune entourloupe cachée, Halcyon a fait un travail remarquable à ce niveau.

Concernant la classe ObjectPeer, il apparaît qu'elle est en fait une implémentation d'une interface existante dans Halcyon : l'interface system.object (!!) elle-même destinée à représenter la classe object de .NET dans le monde Java. Pour des raisons techniques il est interdit de modifier l'implémentation de la super classe mère object. Halcyon a donc préféré ré-implémenter une branche parallèle intégrant les spécificités de la classe object .NET. Nous ne pouvons que déplorer ce fait car cela nuit à la transparence des traitements alors que les deux classes ne sont pas si différentes que ça dans leur comportement respectif.

Autre déception, l'utilisation abusive de l'API system.reflexion à tous les niveaux dans le but de garantir le mapping entre les types Java et .NET. 

Halcyon supporte aussi les ValueType en mettant en place un mécanisme complexe représenté par des classes intermédiaires. Aussi, la classe AssemblyInfo possède son équivalent en Java et hérite du type Type. Quant à la compilation du HelloWorld, elle nécessite d'intégrer les librairies Halcyon dans le classpath (placé dans l'archive inet.jar). Cela est logique car Inet fournit l'ensemble du Framework .NET en Java. 

Enfin, pourquoi ne pas au moins tester les custom attributes (attributs de Runtime) histoire

de voir ce que l'outil propose comme mapping ? Aussitôt dit, aussitôt fait, nous écrivons le bout de code suivant et avec l'aide de l'outil IL2Java nous réalisons la conversion. La figure ci-contre nous montre le code source en C#, rien de bien compliqué, un simple appel à l'attribut Serializable déja présent dans le Runtime. Et là, déception, alors que nous nous attendions à voir "class MySeriaTest implements java.io.Serializable",  nous avons droit au code suivant...... Impossible donc de rendre serializable notre classe par dérivation de java.io.Serializable, c'est bien dommage, d'autant plus que RMI impose ce typage pour le passage de paramètres par valeur, Soap aussi, etc ... le modèle de développement est donc brisé.

En fait, nous venons de toucher un point sensible de l'outil que la conversion de code binaire ne résout pas. Ce point n'a apparemment pas été résolu par les équipes d'Halcyon et reste toujours en suspens. 

Nous aurions voulu tester des dizaines de fonctionnalités supplémentaires mais il aurait fallu écrire un livre au lieu de cet article. Enfin, pour votre réflexion personnelle, comment Halcyon gère t-il le fait que Java, contrairement à C# possède toutes ces méthodes virtuelles ? 

Conclusion

Bref, l'engouement du départ laisse place à une légère déception, non pas que le produit ne réponde pas à nos attentes, mais la décompilation est un processus qui laisse en chemin énormément de choses intéressantes provenant du code source initial... De plus, toute conversion de code binaire ne peut se faire de manière cohérente que si les APIs mises en oeuvre de part et d'autre sont semblables. Malheureusement, ce n'est pas le cas de Java et .NET sur plusieurs points que nous n'aborderons pas ici. Nous n'avons pas voulu tester la conversion d'un composant .NET transactionnel et distribué tant il reste de chemins à parcourir pour que Alcyon Inet devienne un véritable outil de conversion opérationnel. A sa décharge il faut noter la version béta 1 du produit. Gageons qu'à l'avenir, le processus de conversion prendra en compte un parsing complet du code source C# (ou VB) afin de générer des squelettes intermédiaires de classes suivant le modèle de développement Java.   

 

Auteur : Sami JABER