Comment appeler des DLL C++ en C#
J'ai écrit une DLL dans dev C++. La DLL est le nom de "DllMain.dll" et il contient deux fonctions: HelloWorld
et ShowMe
. L'en-tête de fichier ressemble à ceci:
DLLIMPORT void HelloWorld();
DLLIMPORT void ShowMe();
Et la source du fichier ressemble à ceci:
DLLIMPORT void HelloWorld ()
{
MessageBox (0, "Hello World from DLL!\n", "Hi",MB_ICONINFORMATION);
}
DLLIMPORT void ShowMe()
{
MessageBox (0, "How are u?", "Hi", MB_ICONINFORMATION);
}
Je compile le code dans une DLL et appeler les deux fonctions de C#. Le C# code ressemble à ceci:
[DllImport("DllMain.dll", CallingConvention = CallingConvention.Cdecl)]
public static extern void HelloWorld();
[DllImport("DllMain.dll", CallingConvention = CallingConvention.Cdecl)]
public static extern void ShowMe();
Lorsque j'appelle la fonction "HelloWorld" il fonctionne bien et affiche une messageBox, mais quand j'appelle la fonction ShowMe
un EntryPointNotFoundException
se produit. Comment puis-je éviter cette exception? Ai-je besoin d'ajouter extern "C"
dans le fichier d'en-tête?
- Pouvez-vous s'il vous plaît poster votre code C++?
- Vous devrez probablement changer de la convention d'appel pour
CallingConvention.StdCall
.
Vous devez vous connecter pour publier un commentaire.
Le code suivant dans VS 2012 a bien fonctionné:
REMARQUE: Si je supprime le
extern "C"
- je obtenir de l'exception.extern "C"{}
, qui supprime juste un nom de déformation à partir d'un fichier de l'objet, mais vous ne savez toujours pas ce que le nom d'amputation 😀 En C++ compilateur ne peut pas le nom d'une fonction dans un objet comme «HelloWorld», car ici, c'est peut être deux de la fonction du même nom, qui reçoit différents types d'arguments. «Name mangling» est la chose pour résoudre ce problème: il ajoute que certains symboles le nom de la fonction sur la base de sa propre algorithme. Et ce algorithmes (et les noms qui en résultent) diffèrent dans les compilateurs.extern "C"{}
pour convertir la signature d'un code C qui est moins susceptible de rencontrer des problèmes de portabilité. Jusqu'à hier je n'avais aucune idée de pourquoi c'était le cas, mais grâce à vos commentaires et un peu de recherche je pense que je sais maintenant.extern "C"
doit être utilisé pour des fonctions exportées (qui omet d'amputation).extern "C" {}
très souvent ne pouvaient pas être utilisés. Et c'est mon cas: j'ai beaucoup de classes qui ont de nombreuses fonctions du même nom et des arguments différents. Si je voulais supprimer un nom d'amputation, j'ai besoin de réécrire 1/₁₅ de mon code.extern "C"{}
et autres problèmes n'était pas prise en compte.des choses qui m'a aidé:
L': extern "C" { déclarations de fonction ici dans h fichier } désactiver le C++ nom de l'encodage. donc, c# trouverez la fonction
Utilisation __stdcall pour la déclaration en C ou CallingConvention.Cdecl dans l'
C# déclaration
peut-être utiliser BSTR/_bstr_t comme type de chaîne et d'utiliser d'autres vb types. http://support.microsoft.com/kb/177218/EN-US
télécharger "PInvoke Interop Assistant" https://clrinterop.codeplex.com/releases/view/14120
coller déclaration de fonction de .h fichier dans le 3ème onglet = c#
de la déclaration. remplacer par nom de fichier dll.