mardi 13 octobre 2009

Windows x64 et applications dotNet x64 avec DLLs x86

Les versions de Windows en 64 bits ont apporté bien des avantages, tels que la gestion de plus de 4Gb de mémoire Ram.
Mais des inconvénients existent aussi. Certains drivers ne sont pas compatibles par exemple. Mais les temps changent et l'arrivée de Windows Vista et de Seven favorise la sortie de drivers de nouvelle génération.

Cependant... Si vous développez des applications en dotNet, pensez à recompiler tout vos composants, y compris les DLLs utilisées.

Windows on Windows 64 (ou WoW64) permet d'émuler Windows 32 bits. Les applications compilées en 32 bits (ou x86) fonctionnent donc très bien. Si vos DLLs sont en x86, pas de problème, tout fonctionne.

En revanche, si l'exécutable est compilé en 64 bits (x64), il n'est pas émulé. Quand il fait appel à une DLL, il ne fera pas la différence entre une DLL en x86 et une en x64. Vous obtenez alors ce magnifique message d'erreur :

System.BadImageFormatException: Tentative de chargement d'un programme de format incorrect. (Exception de HRESULT : 0x8007000B)
La page MSDN relative à cette erreur est disponible ici.

Si vous voulez faire marcher votre application sur des architectures en x64, nous n'avez que trois possibilités :
  1. Recompiler votre application en portant l'intégralité de votre projet en x64.
  2. Recompiler votre exécutable en forçant le démarrage de votre application en x86.
  3. Utiliser "CorFlags", comme décrit ci-dessous, pour "patcher" l'exécutable et le forcer à s'exécuter en 32 bits.
Si vous ne disposez pas du code source de l'application, "CorFlags" va vous être très utile.
Ce petit utilitaire à utiliser en ligne de commande est disponible dans le SDK du Framework.
Si vous ne souhaitez pas télécharger tout le SDK, téléchargez l'exécutable directement en cliquant ici.
Enregistrez le fichier dans votre ordinateur.
Ouvrez une invite de commande.
Tapez "corflags Lettre:\Chemin\Vers\Exécutable\A\Patcher\programme.exe /32BIT+".

Pour plus d'informations sur CorFlags, rendez-vous sur cette page de MSDN.

3 commentaires:

Remi Serriere a dit…

Nouveau lien pour CorFlags.exe
http://www.apexsql.com/zips/CorFlags.zip

Anonyme a dit…

Bonjour,
Je rencontre un problème qui a l'air très similaire au votre. J'ai développé une appli en VB.Net sous VS2010. Elle fait appel à une Dll (OpcNetApi.dll) pour se connecter à un serveur OPC.
Je voudrais que l'ensemble fonctionne en 16bits sur une machine W7 64bits.
Au démarrage de mon application j'obtiens toujours le même message : impossible de charger le fichier ou l'assembly.......
Tentative de chargement d'un programme de format incorrrect
Auriez vous une idée pour me sortir de l'impasse svp ?
Cdlt

Remi a dit…

Bonjour,

Il n'est pas possible de charger des programmes ou DLL 16 bits sur un OS 64 bits...

Si c'est votre cible est le 32 bits, vous pouvez utiliser les options du compileur de VS2010 pour cibler la compilation sur des processeurs x86, et pas AnyCPU.