0. Preface
When the author provides a C + + dynamic link library to call WebSocket functionality, the client initially mistakenly identified the use of DLL libraries in a statically loaded manner, resulting in the inability of customers using other programming Languages. Given that customer service is often cross-lingual and cross-ide, the best way to use DLL libraries is to make dynamic calls, and to reduce the dependency libraries of DLL libraries and avoid calls to Windows vs own libraries. This paper presents a DLL writing note for dynamic Invocation.
1. Static calls and dynamic calls
1.1 Static Calls
To invoke the DLL library in this way (from an online url), Youapp is the project name of your DLL and requires the DLL\LIB\H header file:
① your YouApp.DLL to the debug directory of your target project (calls to YouApp.DLL project);
② your youApp.lib to your target project (call the YouApp.DLL Project) directory;
③ your youApp.h (including the definition of the output Function) to your target project (call the YouApp.DLL Project) directory;
④ Open your target project Select project, Select the Settings menu of the Project main menu of Visual C + +;
⑤ after performing the 4th step, the VC will pop up a dialog box to select the link page in the multi-page Display control of the dialog box. Then enter in the Object/library modules input box: youApp.lib
⑥ Select your target project head files join: youApp.h file;
⑦ finally contains your: #include "youApp.h" in your target project (*.cpp, which needs to call the function in the Dll)
The advantage of this method of invocation is that the function name of the DLL is found through The. H file and the Lib file, the actual interface name may not be the same as the function name, but it will not result in a situation where no entry is Found. The disadvantage of this is that non-c + + languages cannot load. h header files, and you will encounter various problems when crossing Languages.
1.2 Dynamic invocation
Dynamic invocation of the method, first loadlibrary, and then GetProcAddress (that is, Find the address of the DLL function), not after freelibrary. The specific sample code (excerpted from the Web) is as Follows:
{hinstance hdllinst = LoadLibrary ("youApp.DLL"); If (hdllinst) {typedef DWORD (WINAPI *myfunc) (dword,dword); MYFUNC Youfuntionnamealias = NULL; Youfuntionnamealias function Alias Youfuntionnamealias = (MYFUNC) GetProcAddress (hdllinst, "youfuntionname"); Youfuntionname the function name declared in the DLL if (youfuntionnamealias) {youfuntionnamealias (param1,param2); } FreeLibrary (hdllinst); }}
The advantage of dynamic invocation is that it is easier to rely On. H and Lib Files. The disadvantage is that the build DLL library interface name needs to match the function name, otherwise the entry point of the function cannot be found .
2. The relationship between DLL library interface name and function name
2.1 Interface name and function name analysis
If the interface name and function name are inconsistent, the function in the DLL cannot be found, and the "cannot locate the program input point" issue appears as shown IN.
For DLL libraries, You can use the depends tool to view its interface name, or contact me if Needed. Using depends, you can see the following example, in which the name of the function is the interface name, which is consistent with the function name so that the DLL can be called Normally.
While the function name and interface name inconsistency note forget to save, for example, SendMessage function name is [email protected], where the symbol "_" and "@12" cause the interface name and function name Inconsistent. In this case, the function entry point cannot be found using the function name as an argument in the GetProcAddress Function. therefore, when using dynamic invocation, it is best to ensure that the function name and interface name are Consistent.
2.2 How to ensure that the function name and interface name are consistent
When a C + + compiler builds a dll, the exported function is name-adapted, and the different compilers use the same adaptation rules, so the modified names are different (typically involving overloads in C + +, etc.). In general, there are two ways to build a dll, one is to use the Def file, and the second is to add _declspec (dllexport) before the function Definition. if you want to export a function in a C + + file and do not let the compiler alter the function name, export the function with a DEF file and add the extern "C" to the function Name.
Examples of DEF definitions are as Follows:
LIBRARY PrinterManagerEXPORTSinitPrinterManagersetRecvDataCallbacksendMessageclosePrinterManager
About DLL export name (from the online article url), if the use of extern "C" and def the function name and interface name consistent, C + + uses _declspec (dllexport) that is, the function name and interface name Consistent. Other cases the function name will be adapted by the Compiler.
3, parameter into the stack order (__stdcall and __cdecl), refer to the online article URL
interface functions are best used without the use of containers in std, such as String and Vector. This is because the computer passes parameters to this function, and the work of passing parameters must be coordinated by the function caller and the function itself, i.e.function passes parameters in a way that requires consistency in order to pass parameters correctly。 The computer uses the stack to support parameter passing, and when the function is called, the caller pushes the argument in sequence, then calls the function, the function is called, the data is obtained in the stack, and the calculation is Made. After the function calculation is finished, either the caller or the function itself modifies the stack to restore the stack to the Original.
The problem has arisen,When the number of arguments is more than one (the array is multiple parameters), in what order the parameters are pressed into the stack, after the function call, who will restore the stack originalIn high-level languages, these two problems are illustrated by function calling Conventions. Common calling conventions Are: stdcall, cdecl, fastcall, etc., This article only introduces stdcall and Cdecl.
3.1 __stdcall
Declaration Method: int __stdcall function (int a,int b)
The calling convention of the __stdcall means that: 1) The parameter is pressed from right to left into the stack, 2) the function itself modifies the stack 3) the letter name automatically adds a leading underscore followed by an @ symbol followed by the dimension of the Parameter.
It is necessary to declare __stdcall in the generated code of the DLL and in the Code Used.Cross-language Recommended use of this method。
3.2 __cdecl
The cdecl calling convention, also known as the C calling convention, is the C language default calling convention, and its definition syntax is:
int function (int a, int b)//no decoration is the c calling convention
int __cdecl function (int a,int b)//explicitly indicate c calling convention
Parameters are stacked from right to left, and the memory stack that transmits the parameters is maintained by the Caller.the _CEDCL convention function can only be called by C + +, this method should not be used across Languages.
4, reduce the DLL Library's dependency library, avoid the Windows vs Self-brought library calls
If the DLL library that is provided externally uses vs comes with a library, then other languages are likely to fail to run because there is no vs self-brought library.according to the Author's experience, the following two steps must be used to reduce the dependency of the DLL library。
4.1 Step one: Release Note use release method instead of debug
The selection method is as Follows:
4.2 Step two: Change the MD in the project to MT
/MT is "multithread, static version" means a multi-threaded static release, after defining it, the compiler placed LIBCMT.lib into the obj file, so that the linker uses LIBCMT.LIB to handle external symbols.
/MD is "multithread-and dll-specific version", meaning the multi-threaded DLL versions, after defining it, the compiler placed MSVCRT.lib into the obj file, the way it connects to the DLL is statically linked, Actually the library of work is MSVCR80.DLL.
therefore, using the MD method will use additional libraries, such as Vcruntime140.dll or msvcp140.dll, and these two libraries are most likely not in the Isv.
Modification Method:
① Open the Project's Property Pages Dialog box;
② Expand The "c + +" folder;
③ Select The code generation Property page;
④ Modify the run-library Property.
As shown in the Following:
5. Summary
The use of dynamic link libraries is complex, and many new contacts will fall into a variety of problems for no reason, so write this article to see the people to reduce their detours. Especially thanks to the help of Ali's intern colleagues, They gave me a lot of advice in my definite question.
A dynamic-link library for dynamic load mode