I'm having a difficult problem to solve. I'm having two Qt-based applications, first one is in the main folder and the second one is located in it's subdirectory (yes, I'm forced to have it this way). The issue I'm facing is that I have to deliver 5 exact the same DLL's files for each application. I wouldn't have problem with that, if they wouldn't weight so much (10 DLL files = 60~ MB). Which is, definately too much.
On my debug build I am able to set the PATH variable within Visual Studio settings, and I will be not able to do so on production machines.
Is there any way I could set one of those application to rely on DLL files located in subdirectory?
I don't know what kind of an installer you're using, but the dlls should be stored only once in the archive, and the files should be hard linked on installation. So it's a non-issue unless your installer is broken or the install script is.
Related
Today I build my application and packaged the installer with QtIF. It worked nice on my computer but complained about missing msvcp140_1.dll in another computer.
Then I run find . -iname "msvcp140_1.dll" and found more than five different ones on my computer, I checked the md5sum.
Then I spend the time to try all of them on the other computer and all seem to work fine. No more complains about missing DLL.
How should I choose between the DLLs? Just pick any seems too easy.
Is there someway to inspect the DLLs, to check for a version?
I believe that DLL was a dependency from another binary included in my application, was not that the QtIF failed to include it.
Call the MS Redist Installer from your Installer. This can be done quietly, so that the end user does not notice it.
Find the vcredist_x64.exe file (or vcredist_x32 for 32 Bit applications), add it to your installer,
let it extract to the "TEMP" folder
and then call vcredist_x64.exe /quiet at the end of your install.
This has several advantages:
You will definitely copy all required files to the users computer.
Should new versions of the runtime library be released by Microsoft and should they already be on your users computer, your code will use the newer versions, which may include bugfixes.
Windows Update may also update the libraries.
That said, it is possible to copy the DLLs themselves, but you should make sure
a) you choose the right ones
b) they come from a trustworthy place, i.e. your VS installation folder
c) reside in the same directory as the executable - otherwise you will run into trouble with manifests.
The reason you might want to include the DLLs directly is if you want to reduce the overall size of your installer.
We did this a couple of years with our products, but finally gave in and simply used the vcredist_x64.exe, even if that increased the installer binary another couple of MB in size. But in the long run that's the easiest way.
I think (not sure), msvcp140_1.dll is an additional DLL for the VS 2019 runtime. VS 2017 runtime does not need this, but the new one does.
The non-redistributable method is to ship the DLL's that come with your compiler, i.e. the compiler that built your executable. After all, the DLL will be loaded into the same process as your EXE. It's only logical that these should match.
You'll find those DLL's in \Program Files*\Microsoft Visual Studio *\VC\Redist
I have made an allegro simple game . But when I open the *.exe file on another computer it says that there are many missing .dll files . How can I make my game to run on other computers without Visual Studio and Allegro 5 library installed ?
Longer version of my comment:
When you created your application, it links to certain DLL's that exist on your computer. When you distribute your game, you will either need to ZIP the DLL's along with your .exe or package them using package creators and ship it.
The best way to find which DLL's your exe depends on will be to use a tool like Dependency Walker. You don't need to copy absolutely all DLL's that your EXE depends on. Only the ones that you see are in non-standard paths like ones that are not in C:\Windows\System32. That being said, you might need to copy some from C:\Windows\System32. You will need to find that out on your own.
To package them all as a setup, you can use package creators like InnoSetup or NSIS. Otherwise, create a script that ZIPs it all up for you. AFAIK, there is no easy way to get all DLL's required that are missing from the other persons' system. You'll need to find them out by trial and error. It is a pain, unfortunately.
If you downloaded the pre-built binaries, link against the static, monolithic, mt build of Allegro. You'll need to adjust your compiler settings to match (/MT) and add ALLEGRO_STATICLINK to your list of preprocessor definitions.
If you do that, then you only need to distribute your executable file and your resources (images, sounds, etc).
Note that you should have at least two configurations: Debug & Release. When working on your application, you should use the Debug configuration (linking against the regular debug Allegro library). When distributing your application, you should use the Release configuration.
My application is built with C++/MFC and links dynamically with ImageMagick. I have to deploy 130 (!) ImageMagick DLLs alongside my files when installing the app!
I would like to have a single DLL for the entire ImageMagick library instead of 130. Any ideas for how to do that?
The DLL uses the serach path. Place the ImageMagick.DLL in one directory that is included in the PATH.
If that's not possible, you can change the PATH variable. Add a path to the directory where one instance of the DLL resides.
Hmm, nobody ever complains about having to run their code on an operating system that has three thousand DLLs. Deploying one DLL isn't any easier than deploying 130 of them. Your customer won't mind. Hacking a library whose source code changes so frequently is something you'll regret deeply some day.
I have compiled my Qt application and now have the following question - now my built project requires QtCore4.dll and QtGui4.dll to be located at the same folder where the .exe file is. (I built my project using MSVS2008 with Qt addon)
Q:
Is there any way to combine my final application with these .dll files so that they make one large .exe-file? (I simply don't want to have another bunch of dll files with my release - app)
Thank you.
You need to build and link to Qt statically.
Edit: Here's an updated link to at least similar information.
Bundle them into a self-extracting .exe (e.g. using 7zip) which extracts all files to a temporary directory, runs the program, then deletes the files after the program exits.
This will be easier, less time consuming and less legally constraining than statically linking Qt as previously suggested.
Of course you could statically link someway. But the point of using DLL should be to make program smaller (both on disk and in memory, if other apps are using Qt libs of course)... DLL such as those should be systemwide so that other apps needing them can use them. Basically you have to say to people wanting your program to work, to install the Qt framework.
Deploying the other way is explained here, read the part related to Static Linking.
I've got an SDK I'm working on and the previous developer just dropped the DLLs in System32 (Apparently a serious offense: see here)
So assuming I move them out into \Program Files\\SDK (or whatever), how do I make sure that all the apps that needs those DLLs can access them? And to clarify, all apps that access these are doing early (static) binding to the DLLs at compile time so I can't pass the full path to them or anything. They need to be able to find it just given the DLL filename only.
Along the same lines, what about including a particular version of MSVCR80.dll? They all depend on this but I need to make sure they get a specific version (the one I include).
Any ideas?
An SDK is by definition a development kit. It's not a deployment patch...
What this means is that the applications that depend on those assemblies should ship with them and install them into their local \program files.. directories.
The reason for this is let's say you decide to do a breaking change by eliminating an entry point for example. By installing your "SDK", it has the potential to stop older programs from functioning.
You could take a play from the Java handbook and update the PATH environment variable. Whenever a program makes a call to an external assembly it searches along that environment variable until it finds it.
Of course, this could still result in the problem showing up. So your best bet is to just install the SDK into Program Files and let the developers of the products that depend on your toolkit decide whether they want to update their versions or not.
UPDATE
As I'm thinking about this, one last possibility is to GAC your assemblies. In the event you do so, bear in mind that they should be strongly named and properly versioned so as not to step on each other. I don't recommend this route because it hides the actual locations of the assemblies and makes uninstalling a little more difficult then simply hitting delete on your directory.
I can't tell you about your own DLLs, but you should never redistribute Microsoft DLLs alone.
You always have to use Microsoft Redistributable Package.
For example, if your application depends on dll from Dev Studio 2005 SP1, you should redistribute your application with Microsoft Visual Studio 2005 SP1 redistributable. The same applies to 2008. MS provide MSI based installer and Merge Module to include in your own product installer.
You are asking about "DLL Hell", something I had thought every Windows developer was familiar with. The order of search for DLLs is:
the directory the exex that calls them was loaded from
the current directory
various Windows directories (as discussed in your previous question)
directories in the PATH variable
As the Windows directories should be ruled out, that leaves you with three options.
You can put your install path in the search path, which will allow the applications to find them.
Alternatively, you can deploy the DLL's into the same directory as the application that depends on them.
I believe the first is better from an SDK perspective - it'll make development easier. But I think the second is better for when the application gets deployed to end-users, unless you expect there may be many consumers on a single system so the disk and memory footprint of having copies of the DLL are prohibitive.
If you can't install the dlls into the same directory as the exe using them you could append your directory to the PATH environment variable.
You don't say which version of Windows you're using, as the details are slightly different from what I remember.
You could also put your version of MSVCR80.dll in the same folder. However, you'd have to ensure that your folder was before the system one on the path otherwise the linker would pick up the "standard" one first. However, if you adopted the "local" dlls approach then you wouldn't have this problem as Windows searches the local directory first and so will pick up your version of MSVCR80.dll.
Is your version the latest or a previous version? You might be better off getting your app to work with that version or later and then allow the users to update their machines as required. This also illustrates why you should never mess with the dlls in \Windows or \Windows\system32 as, as others have pointed out, you could break other applications by changing the version of this dll.