用DLL链接静态库的正确方法 [英] Proper way to link static libraries with dll

查看:250
本文介绍了用DLL链接静态库的正确方法的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我的项目通过几个静态库构建,这些静态库应该链接到主dll库,从而获得一个单独的dll。

My project builds through few static libraries which should linked to main dll library gain one single dll as a result.

使用 __ declspec(dllexport )属性不会导致将静态库的指定功能显示为dll,而根本没有与dll链接的库。

Using __declspec(dllexport) attribute does not lead to appearance of specified functions of static libraries to dll, libraries not linked with dll at all.

然后,我尝试构建每个共享库,以获取导出函数的正确名称,并基于它们创建.def文件。使用.def文件导致结果。

Then I tried to build each library as shared for getting proper names of exported functions and created .def file based on them. Using .def file leaded to result.


  1. 应该 __ declspec(dllexport) .def文件在我的情况下是否同样起作用?

  1. Should __declspec(dllexport) and .def-file act equally in my case?

是否可以从源代码生成.def文件?由于我有C ++代码,由于API中的损坏和状态类,我无法自己编写.def文件,因此上述使用临时生成的dll的方法在生产中是不一致的。

Is it possible to generate a .def file from sources? Since I have C++ code I'm not able to write .def file by myself because of mangling and presence classes in API, the approach described above with temporary generated dlls is inconsistent for production.



更新



我想详细解释一下我的项目的结构。该解决方案由几个项目(模块)组成。

Update

I'd like to explain in detail about the structure of my project. The solution consists of a few projects (modules).

+ 
|    
+-+ static_lib1                                          
|       +                                                
|       +--+ src                                         
|                                                        
+-+ static_lib2                                          
|       +                                                
|       +--+ src                                         
|                                                        
+-+ dynamic_lib (linked with static_lib1 and static_lib2)
        +                                                
        +--+ src

每个子项目几乎都依赖于其他项目,为了清楚起见,我们假设它们未连接。每个模块都有自己的公共接口。我想将所有模块都作为单个动态库,因此我的工件是 dynamic_lib.dll ,但实际上静态库未与其链接。

Each sub-project weakly depends on others, let's assume they are not connected for clearness. Each module has own public interface. I want to have all modules as single dynamic library so my artifact is dynamic_lib.dll, but in fact static libraries are not linked with it.

推荐答案

静态库不应包含任何 __ declspec __ attribute((dll .. 。)东西。它们不过是多个目标文件(通常是 *。obj *。o ),它们组成一个文件,一个文件文件。

Static libraries should not contain any __declspec or __attribute((dll...)) things. They are nothing more than multiple object files (usually *.obj or *.o), composed into one, single file.

使用此类库所需要做的一切(在 .exe 或<$ c中$ c> .dll )是要包含适当的头并将其链接-使用Visual Studio相当容易。

All you need to do in order to use such library (either in .exe or .dll) is to include proper headers and link them - with Visual Studio it's pretty easy.

首先,您需要了解 1)静态库的位置以及 2)的确切名称。转到项目属性,然后选择常规目标名称包含输出文件的名称,而输出目录表示在哪个文件夹中。 lib 将被放置。

First of all, you need to know 1) where your static libraries are placed and 2) their exact names. Go to project properties and then General. Target name contains name for the output file, while Output directory indicates in which folder your .lib will be placed.

注意: 项目!对于多项目解决方案,我总是将其设置为通用路径以避免配置问题。

Note: This path may be different for every project! For multi-project solution, I always set this to a common path to avoid configuration problems.

现在,转到项目的属性,这将消耗此库(链接为它)。转到链接器-> 输入,然后添加 .lib 其他依赖项(条目之间用分号分隔):

Now, go to properties of project, that will consume this library (link with it). Go to Linker -> Input and then add name of your .lib to Additional dependencies (entries are separated with semicolon):

您需要添加所有要链接的库。而且,文件夹这些库所在的位置,必须添加到链接器-> 常规-> 附加库目录。如果所有 .lib 都放在同一位置-很好,否则将它们复制到共享位置或将多个条目添加到其他库目录列表。

You need to add all libraries you want have linked in. Also, folder, in which these libraries are placed, must added to Linker -> General -> Additional library directories. If all .libs are placed in the same place - good, otherwise copy them into shared location or add multiple entries to Additional library directories list.

最后一件事-请记住,您还需要包括要使用的带有函数和对象声明的标头。我知道基本的东西,但必须提及。

And the last thing - remember, that you also need to include headers with declarations of functions and objects, that you want to use. Basic thing, I know, but has to be mentioned.

更新


在外部项目中尝试使用dll库时未解析的外部

unresolved external when trying to use dll library in an external prodjects

您的问题根本与链接无关。问题是,您误解了什么,链接静态库确实确实

Your problem is not related to linking at all. The thing is, that you misunderstood what, linking a static library exactly does.

我猜,该函数报告为 unsolved 不是您的 DLL 使用的,对吗?但是,您希望它们位于其中,对吗?

I am guessing, that functions reported as unresolved are not used by your DLL, right? But you expect them to be inside it, right?

当您的 DLL 引用外部内容(例如函数)时,或变量),它会在链接时连同所有依赖项一起解析。 但是就这些。如果您的静态库具有名为 print_sample_string()的函数,则但您的 DLL 不使用它 strong>,它将不会附加到 DLL 图片。

When your DLL refers to an external content (like function or variable), it is resolved at linking time - together with all dependencies. But that's all. If your static library has a function named print_sample_string(), but your DLL does not use it, it won't be attached to DLL image. Think about this carefully - why should it be?

甚至更多-未明确赢得 dllexport 功能的函数?无论如何都不可见。函数默认具有外部存储-因此,基本上,它们是私有 DLL 的内容。

Even more - functions, that are not dllexported explicitly won't be visible anyway. Functions have by default external storage - so basically, they are private DLL's content.

所以要回答您的问题直接提问-如果您需要使用 static_lib1.lib 中的函数/变量,请将其附加到客户端应用程序-就像您现在将其附加到 dynamic_lib 。没有别的办法了。 (*)

So to answer your question directly - if you need to use functions/variables from static_lib1.lib, attach it to client application - just like you are attaching it now to dynamic_lib. There is no other way. (*)

(*)是。您可以在 DLL 中创建中间函数,然后将其导出并在其中调用所需的函数:

(*) Truly speaking - there is. You can create intermediate function in DLL, that is exported and call desired function inside:

dynamic_lib

Somewhere in dynamic_lib:

DLL_EXP_IMP long CallFunctionFromA_Lib()
{
     return some_function(); //this function is from static_lib1.lib
}

<$>中的某个位置c $ c> .exe

Somewhere in .exe:

long result = CallFunctionFromA_Lib(); //internally this will call function from static_lib1.lib

调用函数,但是我无法想象,为什么您想要执行此操作,而不仅仅是链接 A.lib 并直接使用它。

I can't imagine, however, why would you want to do this and not simply link A.lib and use it directly.

这篇关于用DLL链接静态库的正确方法的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆