I have a project that works great.
I created a new and independent .dll project that contains the origin project with some exported functions (copied the origin .h and .cpp files to the new project). I copied from the origin project all the lib dependencies and paths to those libs and additional include files. its the same setup.
The new program compiles but the problem is that when I try to run the code, I get that error msg:
The program can't start because xxx.dll is missing from your computer. Try reinstalling the program to fix this problem.
that xxx.lib is on the Additional dependencies list and its not the first one:
Additional Dependencies: aaa.lib; bbb.lib; ccc.lib; xxx.lib, zzz.lib
I guess that VS found the first three .lib otherwise I would get some error message.. so why can't it find xxx.lib? all the .lib files in the same folder..
thanks.
You appear to be misreading the error message. It says:
The program can't start because xxx.dll is missing from your computer. Try reinstalling the program to fix this problem.
Note that it says xxx.dll is missing, not xxx.lib!
On Windows, a LIB file is often used as an aid to the linker when using a DLL. The LIB contains import stubs for functions provided by the DLL. You need the LIB file when you build the binary; you don't need the LIB file on the machine to run the resulting binary. However, you do need the DLL!
The reason that this might be confusing is that, if you are going to statically link an object file, you only need the LIB. It contains all of the code, and there is no DLL required. But this is not the strategy you are using. The linker is using the xxx.lib file to arrange for the EXE to be dynamically linked to xxx.dll. Thus, the EXE requires the DLL to be present in order for it to run.
Copy xxx.dll into the same folder as your EXE, and then launch the application again. This has nothing to do with your compiler/linker/build settings.
Related
Situation
I learned a lot over the last year, but this is something I just could not wrap my head around. Project is C++. CMake 1.15.2. Visual Studio 2015.
I converted a whole Solution *.sln file with cmake-converter and wrote FindXXX.cmake Modules for all external *.libs defined in the *.vcxproj files.
Everytime I encountered an error: unresolved external I added the corresponding Target Sometarget::somecomponent to the target_link_libraries(ConsumingTarget ... ) call.
Now I have a build that works and produces no errors. Some executables say something along the lines of:
"Execution of code cannot be continued because somecomponent.dll is not found..."
I have
An original .sln file that produces executables only requiring .lib files
A CMake generated .sln file that produces executables requiring .dll files
Working FindXXX.cmake files which add_library(XXX::yyy UNKNOWN IMPORTED)
They find the headers and the .lib files (.dll files are not existing/intended/needed in the original VS .sln)
They create the corresponding Targets for all .lib files
Consuming Targets which target_link_libraries(ConsumingTarget PRIVATE XXX::yyy)
"A working build"
An error "before starting the main function".
What I have tried
I have tried defining an OBJECT Library and adding this to the sources of ConsumingTarget and removing Sometarget::somecomponent from the target_link_libraries call. CMake Doc on Object Libraries
I have tried reading and understanding the difference between module and library. Even the CMake documentation on imported Libraries couldn't help me understand my problem.
I have tried reading and understanding the difference between linking a static and shared library.
My Assumptions
Adding the imported library is done wrong by me.
Reason: DependenciesGui.exe shows different dependencies for the cmake-generated-executable and the original-sln-executable but the linker calls (shown in VisualStudio 2015) seem to be the same.
Whole Program Optimization in the CMake File does not work the same way it does in the original .sln file although the Flags are activated at all levels described in this answer.
Reason: compiling with the original file I noticed warning C4505: 'foobar': unreferenced local function has been removed - I don't seem to get those warnings with the cmake-generated build.
subassumption: Functions which won't be called are optimized away, thus removing the necessity for the .dll file.
I expect/hope for
ConsumingTarget.exe to run without asking for somecomponent.dll
another explanation on imported targets and how to link libraries where .dlls should not be necessary.
an explanation on how to analyze/compare the two binaries regarding their symbols(?) and map the seen information to CMake commands. (I am using DependenciesGui.exe to look for dependencies in the .exe file)
Possible reason for failure
One executable had no /DELAYLOAD... directive after conversion with cmake-converter. Opened Issue. Question Title still holds.
Edits:
1: Added possible reason for failure
I thought this should be straightforward but I am running into a bunch of linker errors like so:
Error 1 error LNK1104: cannot open file '...\Debug\Utils.lib' ...\LINK
where Utils is one of the C++ projects I want to keep as DLL.
If I change Configuration Properties->Configuration Type to Static Library(.lib) everything compiles and runs fine, but if I use .dll then its not working.
The whole solution is native C++ with the main project being a win32 console application.
Perhaps your library (Utils.lib) is not assembled as DLL and changes in console application project (that uses library) will not help.
Read carefully MSDN to see features of DLL's creation and usage.
It you try to link a .lib against another .lib, it doesn't really link. Instead, this instructs the final link to use both libraries.
For a DLL, this can't work, as the runtime linker cannot link the original .LIB. That means the link has to happen when the DLL is compiled.
As a result, a DLL project needs to have the .LIB directories set right.
I set up the project with a Debug library named libtesseract302d.lib. Additional library path is linked to the folder where libtesseract302d.lib is located. In the additional dependencies linker input, I set libtesseract302d.lib. But when I run the project, a system error comes out as The program can't start because libtesseract302.dll is missing from your computer. Try reinstalling the program to fix this problem. I don't have any linkage to this release lib libtesseract302.dll, but why this error has come out?
Thanks
A dll called libtesseract302.dll should have come with the library. This needs to be placed in the initial working directory of your executable, or you can place it in C:\Windows\System32 and register it.
So I am writing a plugin that will be using some .dll .lib packages. I've successfully got the plugin's Build.cs to include the .lib but it wont compile. I get an external symbol not found error that just wont go away. I've placed the .dll at all the locations I can think of where the linker should pick it up to no avail (Binary folders in and out of the plugin, (Win64 and "ThirdParty")), Public and Private Folders in the plugin, project root, you name it.
Does anyone know how to link a .dll for use in a plugin? (fyi, I just want to expose part of the .dll to Blueprints or use them in C++ functions that get exposed to Blueprints).
How do you know that your Build.cs includes the .lib file?
Also, you can not include just every lib file, it has to be compiled with the correct compiler options or the linker will not like it (see here).
Adding DLLs is more complicated than adding libs, because you have to do it at runtime: https://wiki.unrealengine.com/Linking_Dlls
I'm trying to understand what exactly all of these are and how they relate to each other (and most importantly, how to install them).
From what I've read, LIBs are libraries linked during the compilation of my project and DLLs are libraries linked during the runtime of my project.
So for me to use a LIB, I have to have the actual .LIB file somewhere in my computer, go to Project -> Properties -> VC++ Directories and add the path to the file in the Library Directories, and after this I have to go to Linker -> Input -> Additional Dependencies add the .lib name in there, and finally I need to type #include in my code, right?
So, some questions:
When I finish and build the release of my program, will the .exe only run if the target platform has the .lib installed in their PC as well? If yes, what steps do I need to do to make sure the .lib goes with the .exe?
When I get the source of a open source project, if I add them (using Add Existing Item...) to my project, can I use them just by using #include as if the files were mine and it would be the same as having the .lib installed? Or do I need to install the .lib file and still use these source files?
I have a project using OpenGL and I linked to glew32.lib, but I don't have the lib or any new directory added in the VC++ Directories, so I think this means I must've installed the .lib in the system folder or somewhere where the Visual Studio won't ask for another directory, should I worry about this when releasing a project?
How the above questions relate to DLLs and is there any reason why should I use DLLs over LIBs or the other way around?
I'm starting to use more and more libraries and I noticed I just dragged, copied and included it everywhere so I could use them but never really understood how they "fit" in the project. Especially those open source libraries where they provide so many files and I don't really know what to do with them...
You don't need to have LIB files along with your EXE file for running in another computer, LIB files are static files and DLL files are dynamic. So when you compile all static codes will be included in your EXE file, but DLL files will be loaded and used dynamically in runtime, so you just need to have your DLL files with your EXE file. This way, your code will work and run properly in other computers.
Just adding another project is not enough, you need to compile them and generate LIB files out of them. Then you add the generated LIB file to your final project and include external projects in your final binary. If you are compiling multiple projects together in a solution, you'll need to set project build order in solution properties in VS.
No, that's OK. It seems you've put LIB files in right folder and you don't need to have LIB file with your EXE file to run it in other computers.
DLLs are dynamic libraries, so you need to have them with your application. Installers usually install EXE files with DLL files in the same folder, so your app will run properly, but no need to include LIB files at all.
Also you can include LIB files like this:
#pragma comment(lib, "glew32.lib")
So you don't need to do it in project settings, but assuming you have your LIB file in "Library Directories" path.
Using DLL files can be done in two ways:
One is linking your application to DLL file and having DLL file's function entry in your EXE file's import table:
like using
#include <windows.h>
then
GetWindowsDirectory(windir, MAX_PATH);
So you'll have GetWindowsDirectory API entry in your EXE file's Import Table.
Also you can do it dynamically:
hinstDLL = LoadLibrary("kernel32.dll");
if (hinstDLL != NULL)
{
func_GetWindir = (DLLPROC) GetProcAddress(hinstDLL, "GetWindowsDirectoryA");
...
There is not much difference, only difference is:
In first method, as it's in your EXE file's Import Table, if there was no kernel32.dll or there was no GetWindowsDirectory entry in kernel32.dll, your EXE will not run at all, it will show a critical error and will not run. But in dynamic way (second way), your app will run, but as soon as your code try to use GetWindowsDirectoryA API, it will fail. You will have 0x00 in func_GetWindir. If you attempt to call it, then program will crash.