When manually compiling the OpenCV library, one has to select what he/she wants to include by specifying in CMake all the things to include. If, for instance, I would like to include an additional library (for example CUDA support), can I just compile that separately or do I have to recompile the entire library? If former is the answer, how do I do this?
Let's go with CUDA as an example. Library's some dll and lib files will have some dependices to CUDA and some won't. When you use Cmake to configure and generate make files it does create this files with your supplied configuration, CUDA on or off. So but later you want to change this configuration and recompile it again. This is what make is for. When you want to change something within the library and not want to compile it from beginnig.
So you should use Cmake again to generate new make files with your new configuration. You should use the same folders of first compilation to reduce required compile time. So when you change the configuration and generate new make files, it will have probably less compiling time than compiling the all library, because not every library has dependicies with new configuration.
But there is an important issue here. CUDA is a highly dependent library. When I checked source code there are defines which indicates if cuda is on or off. So in this case a change in CUDA configuration affects so much. If you ask me not just for CUDA for all other configuration changes, use a new fresh folder for new configuration and compilation. Because when you encounter a problem you would be at least sure that you have no compilation problems.
Related
When compiling multiple libraries with MSVC, the compilation process can execute in parallel for each library.
On the other hand, If I have a dll that link together a handful of static libraries, the dll compilation process must wait until all libraries finish their compilation. At least with the workflow I'm currently using.
I know of 2 possible options to specify this type of link dependency with MSVC:
Add the libraries as references in the dll project.
link the libraries manually either via Poperty Pages -> Input -> Additional Dependencies or pragma statement such as #pragma comment(lib, "mylib.lib").
When using option 1, Visual C++ waits until all the libraries are compiled before it initiates the dll compilation. In my view this is a waste since these are only link time dependencies.
When using the second option, I am not sure that Visual C++ will wait until the dependencies compilation is complete before attempting to link them.
So is it possible to specify that a static library dependency is a link time dependency only and interleave static libraries and dependent dll compilation?
Unless you have edited the library's source code, MSVC doesn't compile it (again). But if you have edited it, then obviously you will have to one way or the other (well if you want the features to be in the build). If you edit just the dependent, unless your not talking about circular dependencies, the dependencies wont be recompiled.
When using option 1, Visual C++ waits until all the libraries are compiled before it initiates the dll compilation. In my view this is a waste since these are only link time dependencies.
Yes, you have to build its dependencies before compiling the dependent. What if you have something in the dependent which is something you added recently, after the prior build? You'll have to compile the dependency again right?..
When using the second option, I am not sure that Visual C++ will wait until the dependencies compilation is complete before attempting to link them.
Nope Visual Studio doesn't check if the library exists before compiling it. But then, you have to make sure that the dependencies are compiled before the dependent. Yet again, if you have something new in the dependency, you'll have to compile it.
So is it possible to specify that a static library dependency is a link time dependency only and interleave static libraries and dependent dll compilation?
That's how static libraries work. Libraries are linked at link time, not compile time. The way Visual Studio builds the dependencies is that they maintain a dependency graph. When compiling, it checks if a library needs to be recompiled and if not, leave it.
MSVC also doesn't compile .obj files which aren't changed. So if you want to speed up build time, move (movable) header definitions to source files so that specific source file will be recompiled, rather than all the included source files (the source files which include the header file).
The bottom line is, if your working with a lot of libraries, or even one big library, all the edited sources will be recompiled. Multithreading the build is the only way to speed up compilation. Or you could invest in a dedicated machine to compile it for you (server or something).
I'm using
#include <boost/numeric/ublas/matrix.hpp>
in fact that's the only boost file I've included. Now I want to ship the source code and I was hoping not have to include all hundreds of MBs of boost_1_67_0.
How to deal with this issue?
This is simply something you would add to the list of build-dependencies of your C++ source code.
This kind of dependency could be made technically "bound" to your source code distribution via your version control system. In Git, for example, you could link to certain Boost libraries via a sub-module that links to their official git mirrors (github.com/boostorg as of this writing). When cloning your repository, it would then be an option to take in the Boost libraries at the same time.
Though, taking the size of the Boost headers into consideration, having them installed as a system-wide library, might be less complicated. Tools like CMake can help you write the logic for header-inclusion so you can support different header locations.
Of course, if what you seek is to create a fully isolated copy of your source code, the approach to bake all code into one massive header-file might be an option as well (but it should not be necessary).
You can preprocess the one header file you need, which will expand all its #includes:
c++ -E /usr/include/boost/numeric/ublas/matrix.hpp -o boost_numeric_ublas_matrix.hpp
Be aware though: this will expand even your system header files, so it assumes your users will build on the same platform. If they might compile on different platforms, you should simply omit the Boost code from your project and let the users install it themselves in whatever manner they choose.
I have got a C++ Library A. A can be installed in a multitude of ways depending on which external dependencies are used. This also changes depending on whether the library is build in debug or release mode. This means that some features might not be available or some types/defines need to be changed in order to link to the library.
Now I want to link A to a local project B. I have set up a ProjectConfig.cmake file for A which is located at /path/lib/CMake/A/AConfig.cmake which is found and works fine in a minimal build. However as soon as I add definitions to the compilation or include some packages, this information is not automatically exported. This makes linking to A hard as for example I need to know that OpenMP was used to have a coherent build.
Is there a way to export this information the same way the ProjectConfig.cmake does it?
Generate the ProjectConfig.cmake file to contain what you need it to contain.
http://www.cmake.org/cmake/help/v3.0/manual/cmake-packages.7.html
Note that if you set the usage requirements of the targets, you have less need to generate the file.
http://www.cmake.org/cmake/help/v3.0/manual/cmake-buildsystem.7.html
I have a program which statically links to another library in linux using -L(mylib.a) when compiling (using eclipse cdt).
To my meager understanding, the fact that the link is static means that the library is inserted into my binary. Does this mean that if I make a change to mylib I need to recompile my binary?
I assume so, but I wanted to make sure, as it is a big overhead in time. Note that if a change was made to mylib, then eclipse recognizes that it needs to be recompiled, but it doesn't recognize that the binary itself needs to be recompiled, even though it links to the mylib.
If you did not change the interface of the library (i.e. the headers), only a re-link is enough.
Yes, You should rebuild your code with the modified library to produce the binary which links to the new and updated library.
The building of a project can be broken in to two milestone phases:
Compilation:
During this stage the compiler compiles each Translation Unit. It checks the source code for valid syntax etc and produces object files.These object files contain the assembly code output of the source code.
Linking:
During this stage the linker links together the object files and the libraries to generate an executable.
When a application or project uses a static library it includes the header file which is typically called as library interface which contains the list of api and other construct which the application uses.The application also needs to link against the library file.
Obviously, if the interfaces are intact ie the library header file included by your application is unchanged, a compilation is not required but you just need to link to the updated library.
However, I dont think there is a way to just relink updated libraries through eclipse IDE so you should rebuild your project which would essentially do the needful.
i.e:
recompile your project and relink the new library to it or
just relink the new library to your project.
Im helping on a c++ application. The application is very large and is spread out between different sub directories. It uses a script to auto generate qt .pro files for each project directory and uses qmake to then generate make files. Currently the libraries are being compiled in alphabetical order.. which is obviously causing linking errors when a library its trying to link isn't built yet.. Is there some kind of g++ flag i can set so it wont error out if a library its trying to link hasn't been built yet? or a way to make it build dependencies first through the qt .pro file?
NOTE:
This script works fine on ubuntu 10.10 because the statements to build the shared libraries didnt require that i use -l(libraryname) to link to my other libraries but ubuntu 11.10 does so it was giving me undefined reference errors when compiling on 11.10.
Have you looked into using Qt Creator as a build environment and IDE? I've personally never used it for development on Ubuntu, but I have used it on Windows with g++, and it works great there. And it appears its already available as a package in the repository.
Some of the advantages you get by using it are:
Qt Creator will (generally) manage the .pro files for you. (If you're like me, you can still add lots of extra stuff here, but it will automatically add .cpp, .h, and .ui files as they are added to the project.)
You can set up inter-project dependencies that will build projects in whatever order they need to link.
You can use its integration with gdb to step through and debug code, as well as jump to the code.
You get autocomplete on Qt signals and slots, as well as inline syntax highlighting and some error checking.
If you're doing GUIs, you can use the integrated designer to visually layout and design your forms.
Referring back to your actual question, I don't think it's possible for a flag to tell gcc to not error when a link fails simply because there is no way for the linker to lazily link libraries. If its linking to static libraries (.a), then it needs to be able to actually copy the implementation of that code into the executable/library. If its dynamically linking (.so), it still needs to verify that the required functions actually exist in the library. If it can't link it during the linkage step, when can it link?
As a bit of an afterthought, if there are cyclic dependencies in your compile process (A depends on B, B on C, and C on A), then you might need to have a fake version of a library get built first, which only has empty stubs for the implementation of each function, and the full definition for each class or object. Then, build everything else while linking to that, and at the end, build the real version of the fake library, and link it to all the other versions that were already linked. I think this would only work on dynamic linking, though.
You could use a subdirs project to have control over the build order (no matter whether the other dev wants it or not :) ).
E.g.
build_all.pro
TEMPLATE=subdirs
CONFIG+=ordered
SUBDIRS=lib2/lib2.pro lib1/lib1.pro app/app.pro
The lib1.pro, lib2.pro, ... are your generated pro files.
Then run qmake once for the build_all.pro and also run make in that directory. This will build lib2 before lib1 and then app.