[CMake] Redundant linking when modifying shared libraries

Craig Scott craig.scott at crascit.com
Thu Feb 14 05:38:48 EST 2019


On Thu, Feb 14, 2019 at 9:24 PM Itay Chamiel <itay.chamiel at orcam.com> wrote:

> Hi,
>
> I've asked this question on Stack Overflow almost a year ago with no
> useful responses (with the same topic if you wish to search for it), so I'm
> trying my luck here.
>
> I work on a large commercial C++ project comprised of a couple dozen
> dynamically linked shared libraries, each of which has many associated unit
> tests. Many libs are also dependent on other libs because a lib for some
> specific functionality will use the code from one of the more common libs.
> And finally of course there are the production executables which depend on
> the libs.
>
> There is no question that a change in the API (a header file) of some core
> common lib should trigger a major recompilation of nearly the entire
> system. But typically there is only a change in some function's
> implementation, and the only file compiled is the modified .cpp file, and
> in theory just the modified lib would need to be linked - thanks to dynamic
> linking there should be no need to relink anything else. But CMake goes
> ahead and does it anyway: after relinking the lib it relinks all the unit
> tests associated with that lib. Then it relinks all the libs in that lib's
> dependency tree and all their unit tests. Finally it relinks the production
> executables. Due to the scale of the project this takes a lot of precious
> time.
>
> I have reproduced this behavior with a simple project based on the example
> at cmake.org/examples (comments removed for brevity and lib type changed
> to shared). My system is Ubuntu 16 on an Intel PC and my CMake version is
> 3.5.1.
>
> Start with an empty directory. Create subdirectories Demo and Hello and
> then create these files:
>
> * CMakeLists.txt
>
> cmake_minimum_required (VERSION 2.8.11)
> project (HELLO)
> add_subdirectory (Hello)
> add_subdirectory (Demo)
>
> * Demo/CMakeLists.txt
>
> add_executable (helloDemo demo.cpp)
> target_link_libraries (helloDemo LINK_PUBLIC Hello)
>
> * Demo/demo.cpp
>
> #include "hello.h"
> int main() { hello(); }
>
> * Hello/CMakeLists.txt
>
> add_library (Hello SHARED hello.cpp)
> target_include_directories (Hello PUBLIC ${CMAKE_CURRENT_SOURCE_DIR})
>
> * Hello/hello.h
>
> void hello();
>
> * Hello/hello.cpp
>
> #include <stdio.h>
> void hello() { printf("hello!\n"); }
>
> * now run the commands:
>
> mkdir build
> cd build
> cmake ../
> make
>
> * You may now execute Demo/helloDemo and see hello!.
>
> Now, touch Hello/hello.cpp and make again. You will see that libHello is
> built and linked as expected, but then the helloDemo executable is also
> relinked ("Linking CXX executable helloDemo"). The latter step is
> completely redundant; even if hello.cpp is modified to print a different
> string the relinked executable remains binary identical.
>
> Is there a way to prevent these redundant build actions? This would be a
> huge time saver for us.
>


I think you might be looking for the LINK_DEPENDS_NO_SHARED
<https://cmake.org/cmake/help/latest/prop_tgt/LINK_DEPENDS_NO_SHARED.html>
target
property (or more likely its associated CMAKE_LINK_DEPENDS_NO_SHARED
<https://cmake.org/cmake/help/latest/variable/CMAKE_LINK_DEPENDS_NO_SHARED.html>
 variable).


-- 
Craig Scott
Melbourne, Australia
https://crascit.com

Get the hand-book for every CMake user: Professional CMake: A Practical
Guide <https://crascit.com/professional-cmake/>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <https://cmake.org/pipermail/cmake/attachments/20190214/98bcfb2f/attachment-0001.html>


More information about the CMake mailing list