2010-05-17 7 views
8

Dans le monde non géré, j'ai pu écrire un __declspec (dllexport) ou, alternativement, utiliser un fichier .DEF pour exposer une fonction pour pouvoir appeler une DLL. (En raison du nom mangling en C++ pour le __stdcall, j'ai mis des alias dans le fichier .DEF afin que certaines applications puissent réutiliser certaines fonctions DLL exportées.) Maintenant, je suis intéressé à pouvoir exposer une seule fonction d'entrée d'un Assembly .NET, de manière non gérée, mais il doit entrer dans les fonctions de style .NET dans la DLL. Est-ce possible, d'une manière simple et directe?Comment puis-je appeler des DLL C++/CLI (.NET) à partir d'applications non-standard non-gérées?

Ce que j'ai est un programme tiers que j'ai étendu via des DLL (plugins) qui implémentent des mathématiques complexes. Cependant, le programme tiers n'a aucun moyen pour visualiser les calculs. Je veux en quelque sorte prendre ces fonctions mathématiques pré-écrites, les compiler dans une DLL séparée (mais en utilisant C++/CLI dans .NET), mais ensuite ajouter des crochets aux fonctions afin que je puisse rendre ce qui se passe sous le capot dans un .NET contrôle de l'utilisateur. Je ne sais pas comment combiner les éléments .NET avec les éléments non gérés, ou ce que Google doit accomplir pour accomplir cette tâche.

Des suggestions spécifiques concernant le pont géré/non géré, ou d'autres méthodes pour accomplir le rendu de la manière que j'ai décrite seraient utiles. Je vous remercie.

Répondre

4

Utilisez-vous C++/CLI parce que vous le souhaitez ou parce que vous pensez que vous devez exporter des fonctions?

Dans le cas de ce dernier, consultez mon unmanaged exports, qui vous permet de déclarer des exportations non gérées en C# équivalent au fonctionnement de DllImport.

internal class Sample 
{ 
    [DllExport("_export_test", CallingConvention.Cdecl)] 
    static int Test(int a) 
    { 
    return a + 1; 
    } 
} 
+0

Je voulais utiliser C++/CLI parce que la bibliothèque tiers compilerait automatiquement en utilisant simplement l'option/clr. Ensuite, ajouter des liens vers le framework .NET rendrait la vie bien meilleure (je pense.) Votre exemple semble être une approche raisonnable. Je vous remercie. – user343400

+0

Je ne suis pas sûr de vous suivre ici. Lorsque vous prenez mon modèle de projet, il se compilera automatiquement (il créera même un fichier .lib). Sauf si je vous ai mal compris, et que vous voulez réellement utiliser C++/CLI. –

4

Eh bien, le compilateur C++/CLI rend assez facile. Écrivez simplement une fonction gérée statique et attribuez-la à __declspec (dllexport). Le compilateur injecte un bouchon qui charge automatiquement le CLR pour exécuter le code managé.

C'est une approche utilisable, ce n'est pas très extensible et ce ne sera pas très rapide. L'étape suivante consiste à écrire une classe ref avec l'attribut [ComVisible (true)]. Après l'avoir enregistré avec Regasm.exe, n'importe quel client conscient non géré peut utiliser ce serveur. L'hébergement du CLR vous-même (CorBindToRuntimeEx) est généralement le dernier choix, mais le plus universel.


code Exemple:

ref class ManagedClass { 
public: 
    static void StaticFunc() {} 
}; 

extern "C" __declspec(dllexport) 
void __stdcall UnmanagedFunc() { 
    ManagedClass::StaticFunc(); 
} 
+0

Si j'ai besoin de __stdcall sur le nom et que je veux me débarrasser du @number sur le nom mangling et que j'ai besoin de créer un alias dans un fichier .DEF, comment faire dans ce cas? Ce dont j'ai besoin, c'est d'une signature externe de style "C" pour pouvoir être appelée par un type spécifique d'application tierce. – user343400

+0

Utilisez simplement extern "C" et les __stdcall déclarateurs sur l'exportation. Vous n'avez pas besoin d'un fichier .def. Échantillon posté. –

+0

@HansPassant Que voulez-vous dire par "compilateur injecte un talon"? Est-ce que le compilateur génère un .lib (et l'appelant de UnmanagedFunc() aurait besoin de se lier avec le lib)? – qqqqq

Questions connexes