How do you pack a visual studio c++ project for release? - c++

I'm wondering how to make a release build that includes all necessary dll files into the .exe so the program can be run on a non-development machine without it having to install the microsoft redistributable on the target machine.
Without doing this you get the error message that the application configuration is not correct and to reinstall.

Choose Project -> Properties
Select Configuration -> General
In the box for how you should link MFC, choose to statically link it.
Choose Linker -> Input. Under Additional Dependencies, add any libraries you need your app to statically link in.

You need to set the run-time library (Under C/C++ -> Code Generation) for ALL projects to static linkage, which correlates to the following default building configurations:
Multithreaded Debug/Release
Singlethreaded Debug/Release
As opposed to the "DLL" versions of those libraries.
Even if you do that, depending on the libraries you're using, you might have to install a Merge Module/framework/etc. It depends on whether static LIB versions of your dependencies are available.

Be aware that Microsoft do not recommend that you static link the runtime into your project, as this prevents it from being serviced by windows update to fix critical security bugs. There are also potential problems if you are passing memory between your main .exe and .dll files as if each of these static links the runtime you can end up with malloc/free mismatch problems.
You can include the DLLs with the executable, without compiling them into the .exe and without running the redist tool - this is what I do and it seems to work fine.
The only fly in the ointment is that you need to include the files twice if you're distributing for a wide range of Windows versions - newer OSs need the files in manifest-defined directories, and older ones want all the files in the program directory.

You'd be looking to static link (as opposed to dynamically link)
I'm not sure how many of the MS redistributables statically link in.

If you are looking to find out which dll's your target machine is missing then use depends.exe which used to come with MSDev, but can also be found here. Testing this on a few target machines should tell you which dll's you need to package with your application.

You should use a static link and add all libraries you need under additional dependencies.

Related

Building a static lib without C/C++ runtime in Visual Studio

Is there a way to build a static library without specifying the version of C/C++ runtime?
I'm using Visual Studio 2017 to build a static lib, and I have to specify a version for "Runtime Library" in the "Code Generation" option page (\MD or \MT). If I choose one version and the application using my lib chooses another, Visual Studio will spit out the error: mismatch detected for 'RuntimeLibrary': value 'MD_DynamicRelease' doesn't match value 'MT_StaticRelease'.
I know, when building an EXE, I can use the linker switch \NODEFAULTLIB to not include C/C++ runtime, but I'm building a static lib here which doesn't even have the Linker option page in its Properties window.
It seems that Simple DirectMedia Layer found a way to do.
Update: I later realized that I could actually turn on \NODEFAULTLIB switch in the Librarian option page in the static lib's Properties window.
You do it by NOT using any Runtime libraries. If you don't use any of the runtime libraries then the "Code Generation" option is meaningless as the runtime stubs are not pulled into obj file.
SDL basically say this on there web site:
On Windows, SDL does not depend on a C runtime at all, not even for
malloc().
As soon as you use any system include supplied by Microsoft VS then you are using there runtime library.
So if you only use the Windows SDK and the API supplied by the Win32 API then you don't need the VC runtime.
If you build a static library, it refers to your own library and not to the application as a whole. If you want to distribute the application, it just means that you will not need to distribute a separate dll. So do not set NODEFAULTLIB.
If you run the application on a machine where there is no Visual Studio 2017 installed, you might get an error message. The missing dlls are system libraries that are needed to run vs applications that are compiled with VS2017. You can get the missing libraries from: https://support.microsoft.com/en-gb/help/2977003/the-latest-supported-visual-c-downloads (this link is not guaranteed to be correct in the future). The redistributable dlls can be distributed freely. They are called vc_redist.x86.exe and vc_redist.x64.exe. Choose vc_redist.x86.exe if you have compiled you code for 32-bits. It does not refer to the machine on which the app is run.

Ensure all dependency dlls are packaged into executable

I thought if you compile a Visual-studio 2013 Win32 project using /MT Code Generation->Runtime library then it will automatically package all dependency dll's - including 3rd party dll's - into the executable?
Currently certain users get an error when running my .exe. Its related to not having a 3rd party dll (OpenSSL):
The program can't start because LIBEAY32.dll is missing from your computer
This error has occurred for users using my .exe on Windows 10 OS's. How can I ensure all dependency dll's are packaged into my .exe?
I currently compile my application on my 64bit Windows 8.1 OS. The win32 visual-studio project is compiled using the following project properties:
Character Set: Unicode char set
Use of MFC: Use standard windows libraries
Whole Program Optimisation: Use Link Time Code Generation
Debug info format: none
Code Generation->Runtime library: /MT
/MT indicates that you are using multithread, static version of the run-time library. This doesn't affect third party dependency, e.g. OpenSSL is still linked dynamically.
To check your dll's dependency I prefer Dependency Walker tool. It will show if some of dependency is missed.
To ensure all dependency linked into your .exe file use static linking for all your third party dependency, e.g. for OpenSSL you should use libeay32MT.lib library.
Nikita is right, use Dependency Walker and I'd add that you're missing some knowledge about what a DLL really is. No offence meant, I know dlls can be a pita. What is a DLL?
By definition a DLL is not included in your .exe but it is loaded at runtime and could be shared amongst several applications. If you want to include it in your .exe it will require some extra non trivial work to embed them into your exe, unpack and load at runtime.
See this post
I'd suggest to use an installer instead, much easier to handle! Just create an installer (you know the click click click "yes-yes-I agree-Ok-Done" wizard installer) that will include your .exe and all needed dependency files. As a reference Inno setup is quite great.

Add to Path Visual Studio Release Build

Background:
I have a program that links to a third party library. There are two versions of the library, so I have created two solutions that point to the same code. This may seem odd, but the code doesn't have to be different. Only the settings within the solution need to be different (i.e. library names are different and the CRT version is different).
SolutionA uses versionA of the third party library (uses CRT version 8.0).
SolutionB uses versionB of the third party library (uses CRT version 9.0).
Both SolutionA and SolutionB point to the same code.
I have set up a Macro in the Project Property Sheets that points to the correct version of the library. The library files are not located within the solution folders. This Macro allows the projects to build correctly.
In order to get the executable to run, I have to tell it where the third party libraries are located. In order to do this, I can go to Configuration Properties-> Debugging -> Environment and add the path to the libraries to the %PATH% environment variable.
Question:
This works fine but is limited to debug mode. How can I add to the %PATH% environment variable in release mode? Can this be done using Project Property Sheets?
Notes: When the program is deployed, a batch file sets up the environment before it runs. However, I would like to be able to run the release executable within Visual Studio to keep things consistent (it would be easier for other developers).
Someone will probably ask why I don't have the libraries in the solution folders or why I don't throw them in with the executable. I hesitant to do so because one version of the libraries takes up about 180 MB. I only need two versions right now, but that is sure to change.
You do not need to create separate solutions with separate properties. For one solution, you can create several configuration. Each configuration have its own compile parameters.
Right Click on your project -> Properties -> Configuration Manager -> New.
Regarding "This works fine but is limited to debug mode". Yes, you are setting parameters for Debug mode only. So this is normal it works in Debug mode only.
For you libraries, if they are static:
Properties -> Linker -> Input -> Additional Dependencies
Properties -> Linker -> General -> Additional Library Directories
The way we've gotten around this problem is to run visual studio itself using a batch file which sets up any environment variables (e.g., PATH) prior to the start of Visual Studio which inherits the environment. This allows for the environment settings to be temporary to the run of VS and inherited across all build configurations.
This works for Debug, Release, and any custom build configurations you may have.

Should i use MinGW for C++/CMake project to minimize dependencies of MS's DLLs?

When i use Visual Studio, my executables depends on microsoft redistributable package - the package that deploys MS's runtime DLLs. That is annoying to me. What disatwantages my executable would have if i would use MinGW?
I also want to try link with lib- avcodec/avformat, that are built by MinGW and i have no my own mind power to build them in VS from src.
In case of using MinGW you will depend on DLLs that are shipped with mingw. It is not big deal to change one vendor to another.
If you already have MS project, review possibility to statically link MS libraries (it is option is provided for some of VisualStudio projects on creation time in project options)
You can link everything statically with MinGW. Use the -static linker flag.
No need for redistributing any DLL's, but you have to make sure that in the c++, there's no exceptions being passed over DLL boundaries (so make sure every C++ library is linked statically in this case).

Build C++ project to include ALL msvc dlls

I have a simple C++ program. I want to just build the exe and give it to a person on another complete non-development box. Is there a way to build such a simple, single-source file to an executable in Visual Studio without needing all the crap ? I have changed the program to compile in MT mode, instead of MTD which statically linked the msvcr.dll file, but now it is looking for msvcp.dll file. How can I compile so that my executable either 1) doesnt include all this junk or 2) statically links it all so that I have exactly one file to transfer to another Windows PC to run
Thanks
If compiling with /MT is requiring msvcr100.dll, something included in your application is probably trying to link with it, possibly a third party component. I would check any third party libraries and related.
MSVCP100.DLL is the C++ standard library. You might want to double check that it's not looking for MSVCP100D.DLL, which is the debug version; mixing release and debug mode libraries could cause this.
MSVCRT100.DLL is the C run-time library, and MSVCP100.DLL is the C++ standard library. Both should go away if you build with /MT, in that case static versions of these libraries should have been used.
My guess is that you either did not fully rebuild your app after switching to /MT, or that one or more files in your project have custom settings that include /MD. You may want to open the properties dialog box on the page that shows the /MT and then click on all your source files one by one to verify that none of them still show /MD.