2008-10-29 4 views
1

J'essaye de construire une bibliothèque partagée (DLL) sur Windows, using MSVC 6 (rétro!) Et j'ai un problème de lien particulier que je dois résoudre. Ma bibliothèque partagée doit accéder à un état global, contrôlé par l'application de chargement.Comment contrôler les symboles qu'une DLL Windows importe à partir de l'application?

De façon générale, ce que j'ai est le suivant:

application.c:

static int g_private_value; 

int use_private_value() { 
    /* do something with g_private_value */ 
} 

int main (...) { 
    return shared_library_method(); 
} 

shared_library.c:

__declspec(dllexport) int __stdcall shared_library_method() { 
    use_private_value(); 
} 

(Mise à jour - J'ai oublié la partie __declspec(dllexport) int __stdcall, mais c'est là dans le vrai code)

Comment puis-je configurer shared_library.dll afin qu'il exporte shared_library_method et importe use_private_value?

Veuillez noter que A) Je suis un programmeur Unix, en général, et B) que je fais cela sans Visual Studio; notre infrastructure de construction automatisée pilote MSVC avec makefiles. Si j'omets quelque chose qui facilitera la réponse à la question, veuillez commenter et je le mettrai à jour dès que possible.

Répondre

1

Je commencerai par la moitié de la réponse.

En shared_library.c:

__declspec(dllexport) int __stdcall shared_library_method(void) 
{ 


} 

La MSDN article sur la fonction exportation de DLL: s.

+0

J'aurais dû inclure cela; mes déclarations dans la bibliothèque partagée ont cela. Mis à jour dans le post. –

2

Cela va être très difficile à obtenir. Sous Unix/Linux, vous pouvez faire en sorte que les objets partagés et les applications importent les symboles les uns des autres, mais sous Windows, vous ne pouvez pas importer de symboles de l'application qui le charge: le format exécutable Windows PE ne prend pas en charge cet idiome.

Je sais que le projet Cygwin a une sorte de solution pour résoudre ce problème, mais je ne crois pas que ce soit trivial. Sauf si vous voulez faire beaucoup de piratage lié à l'EP, vous ne voulez probablement pas y aller.

Une solution plus simple pourrait être d'avoir juste une sorte de méthode d'initialisation exportée de la DLL:

typedef int (*func_ptr)(); 
void init_library(func_ptr func); 

L'application doit appeler ce au démarrage, en passant dans l'adresse de la fonction que vous souhaitez partager . Pas vraiment élégant, mais ça devrait marcher.

1

Pour la seconde moitié, vous devez exporter les fonctions de votre application.c. Vous pouvez le faire dans l'éditeur de liens avec:

/export:[email protected] 

Cela devrait vous obtenir un lib fichier que vous construisez avec votre DLL.

L'option pour lier le fichier lib est d'utiliser GetProcAddress(). Comme DavidK l'a noté si vous n'avez que quelques fonctions, il est probablement plus facile de passer les pointeurs de fonction dans une fonction init. Il est cependant possible de faire ce que vous demandez.

Questions connexes