How to build static libraries with cmake (and more)?
Brad King
brad.king at kitware.com
Tue May 16 17:55:52 CEST 2006
Friedrich W. H. Kossebau wrote:
> Am Samstag, 13. Mai 2006 18:37, schrieb Alexander Neundorf:
>>Different targets could be built with different flags etc., so the object
>>files could differ. That's why the object files are not reused.
>
> Yes, _could_. But what if I know and want that they are not? See the example
> above: I want to create from the very same object files a static lib next to
> the linked dynamic one because this seems to be needed for convenient unit
> testing (due to symbol visibility, see the reference below).
To clarify: you want an archive of the object files in a shared library
so that you can link them to an executable statically, correct?
This may not be too hard to add to cmake. Perhaps we could add a target
property to specify that such an extra archive should be created. The
generator would then add the call to the archiver/ranlib after linking
the shared library to produce an archive with the same object files.
This is easy in the makefile generators, but I'm not sure how to do it
in Visual Studio and Xcode builds. We will probably have to create an
extra target (project file) that depends on the original and then just
links together all the object files.
I just tried this on windows by hand and it has some interesting
effects. The static .lib file that is produced is full of objects that
have dllexport tags. When it is linked into an executable, say foo.exe,
the linker produces a foo.lib import library. Another problem on
windows is that the static library cannot have the same name as the dll
or it will clobber the import library paired with the dll. This means
that any target property we create to specify this behavior will also
have to specify an alternative name for the archive.
Out of curiosity, why do the tests need access to non-public symbols?
Shouldn't they test using the libraries the same way user code is
expected to use them, through the public API?
>>So you link to libkfoosomething.so, and when running the app, it links to
>>the installed lib instead of the not-yet-installed one ?
>>Then use the RUN_UNINSTALLED option for KDE4_ADD_EXECUTABLE:
>>KDE4_ADD_EXECUTABLE(kfoo RUN_UNINSTALLED srcs...)
>
> I do this already, and yes, it links to the uninstalled in the build, then
> binds(?) to the installed if running!
> Test yourself:
> 1. remove some visibility flag for a class in a lib, compile, install
> 2. put flag back, compile and link lib, but do not install
> 3. compile and link some not installed executable (e.g. a test) which needs
> that class symbol
> 4. run executable -> symbol lookup error
> 5. install new lib from above -> executable runs fine...
Build with "make VERBOSE=1" and log the output. Then look for
-Wl,-rpath options to see what runtime library search path is used by
your executable.
> I am looking for convenient adhoc testing which can be applied in the middle
> of some development session without effects on the rest of that session. E.g.
> for test-driven development.
> Workflow: Edit, compile, edit, compile and run tests ->fails, edit again,
> compile and run tests ->ok, edit, compile, edit, compile, edit, compile and
> run test ->ok, edit, compile, edit, ...
>
> So this is a different use case from what seems supported now only, namely
> nightly automatic builds. Can you better guess now what I (and others)
> want? :)
There is much more than just nightly testing: ctest allows tests to be
run in the build tree by hand. After finishing the build, try this:
Run all tests:
ctest
List all tests
ctest -N
Run a subset of tests by regex:
ctest -R mytest
See the ctest manpage for details. In order to build just one
executable and things it needs, specify the target name to make:
make mytest_exe
You can also run a whole build/test stage and report results to the
dashboard using the "Experimental" testing mode. Try this:
make Experimental
> auto*'s "make" and "make check" do fit nicely there. The default target(s) do
> not include dependencies on the test targets. Only on the target "check" all
> test dependencies are run, then automatically the tests executed.
This is exactly what ctest --build-and-test provides: the ability to
have tests that build some code (that is not built during the normal
build) and run an executable. Alex may have to explore creating a few
such tests as examples.
-Brad
More information about the Kde-buildsystem
mailing list