Trying to find a shared library using CMake - cmake

I'm trying to find the avformat library for my project using CMake. My first option was to use a FIND_PACKAGE(...) but I couldn't find any CMake Module for it in $CMAKE_ROOT/Modules. Now I'm trying to find it using FIND_LIBRARY(...).
The library is in /usr/lib/libavformat.so.52.
This is my CMake code for finding it:
find_library(AVFORMAT_LIBRARY avformat PATHS /usr/lib DOC "avformat library")
if(NOT AVFORMAT_LIBRARY)
message(FATAL_ERROR "Library avformat required, but not found!")
endif(NOT AVFORMAT_LIBRARY)
However, I can't find it. Why do you think that is?
I could type the specific library name (i.e. libavformat.so.52), but that would tie the code to that specific version, which I wouldn't want.
EDIT: I just tried typing the exact library name libavformat.so.52 and that didn't work either. :S
What are your suggestions?
Thank you.

So I found what the problem was.
If you do a search for 'avformat' in aptitude/synaptic you get a couple results but no libavformat-dev. So I thought there was none! However, if you search for 'libavformat' then the library appears! I swear I thought that aptitude/synaptic did a regular expression search, not just for the beginning. -.-
Now it all works! :D

Related

CMAKE - find_library find_path find_file all not working

So I have a library here /path/to/CMSIS/libarm_cortexM4lf_math.a
I can't seem to find it using find_library with Cmake. Further more I can't find a simple text file with find_file or find_path.
I've tried the following (and many iterations thereof):
find_library(CMSIS_LIB libarm_cortexM4lf_math.a PATHS /path/to/CMSIS)
So then I thought I'd do something more simple and saved a file to /home/user/happy.txt and tried to
find_path(TEST_FILE happy.txt /home/user)
In all cases my variables are NOTFOUND.
I've read the cmake documentation for find_library, most of find_path, and skimmed find_file. They all seem to work the same way and I can't get any of them to work.
What am I missing here?

Replace AC_CHECK_LIB in CMake

I'm converting a project from Autotools to CMake.
We have a configure.ac file, with the statement:
AC_CHECK_LIB([gsuffix], [gsuffix_create], [], AC_MSG_ERROR([Can not find gsuffix library]))
I want to replace it to cmake, and not sure how (it doesn't have pkg-config)
What I need is:
check libgsuffix exists and find path.
Check gsuffix_create exists in libgsuffix
Add -lgsuffix to compilation - this I think I know how to do.
Can anyone point me to the right direction?
There is no one to one translation. In general, with CMake you don't check whether every header and every library actually works. If you find the file, you assume it will do the trick.
Maybe find_package is right for you, depending someone already wrote such a test or your library provides an according config file.
Find_library is meant to find libraries, but by name.
If you really have to check that your library works, use CheckLibraryExists.
As mentioned, did not find anyway to do this with one command.
I didn't have enough time to understand how to do something completely generic, so I can give my skeleton for a FindGSUFFIX.cmake:
FIND_LIBRARY(GSUFFIX_LIBRARY NAMES gsuffix)
INCLUDE(CheckLibraryExists)
CHECK_LIBRARY_EXISTS(gsuffix gsuffix_create ${GSUFFIX_LIBRARY} GSUFFIX_VERIFIED)
# Handle the QUIETLY and REQUIRED arguments and set PCRE_FOUND to TRUE if all listed variables are TRUE.
INCLUDE(FindPackageHandleStandardArgs)
FIND_PACKAGE_HANDLE_STANDARD_ARGS(GSUFFIX DEFAULT_MSG GSUFFIX_LIBRARY GSUFFIX_VERIFIED)
MARK_AS_ADVANCED(GSUFFIX_LIBRARY)

Cmake library prefix/suffix

I need to link with a third-party pre-built shared library. On Windows, that means linking with Third_party.lib, and on Linux/Android, that means linking with libThird_party.so. So in the interest of cross-platformness, I tried to write that as:
${CMAKE_IMPORT_LIBRARY_PREFIX}Third_party${CMAKE_IMPORT_LIBRARY_SUFFIX}
Which works fine on Windows, but on Linux/Android, these variables are blank. I get that Linux/Android doesn't have import libraries, but nonetheless these variables being blank is actually a big nuisance. And changing the variables to CMAKE_SHARED_LIBRARY_... doesn't work either, because even though Linux/Android would then look for lib/.so like I want, Windows will look for .dll, which I don't want.
It seems like I can fix this by populating the import library variables (only on Linux) with values from the shared library variables. But... is this really the best way? I can't possibly be the first person to bump into this.
Usually you let CMake and its helpers do that job of figuring the right name out. Quite possibly, for your third party library, there's already a Find<Library>.cmake script out there.
If there isn't: Here's something taken from FindUSB.cmake from GNU Radio
if(NOT LIBUSB_FOUND)
pkg_check_modules (LIBUSB_PKG libusb-1.0)
find_path(LIBUSB_INCLUDE_DIR NAMES libusb.h
PATHS
${LIBUSB_PKG_INCLUDE_DIRS}
/usr/include/libusb-1.0
/usr/include
/usr/local/include
)
find_library(LIBUSB_LIBRARIES NAMES usb-1.0 usb
PATHS
${LIBUSB_PKG_LIBRARY_DIRS}
/usr/lib
/usr/local/lib
)
if(LIBUSB_INCLUDE_DIR AND LIBUSB_LIBRARIES)
set(LIBUSB_FOUND TRUE CACHE INTERNAL "libusb-1.0 found")
message(STATUS "Found libusb-1.0: ${LIBUSB_INCLUDE_DIR}, ${LIBUSB_LIBRARIES}")
else(LIBUSB_INCLUDE_DIR AND LIBUSB_LIBRARIES)
set(LIBUSB_FOUND FALSE CACHE INTERNAL "libusb-1.0 found")
message(STATUS "libusb-1.0 not found.")
endif(LIBUSB_INCLUDE_DIR AND LIBUSB_LIBRARIES)
mark_as_advanced(LIBUSB_INCLUDE_DIR LIBUSB_LIBRARIES)
endif(NOT LIBUSB_FOUND)
Notice the pkg_check_modules directive and the find_library directive that take care of giving you the right things without you hand-appending suffixes etc.
You'll probably want to add the path you expect your .dll to be to the PATHS arguments of find_path and find_library (those are pointers for CMake to know where to look).

CMake does not find CxxTest package

I wrote the following CMakeLists.txt in order to build a tester using CxxTest (it's almost the standard example provided by FindCxxTest):
cmake_minimum_required(VERSION 2.8)
project(tester)
set(CMAKE_INCLUDE_PATH "${CMAKE_CURRENT_SOURCE_DIR}")
find_package(CxxTest REQUIRED)
if(CXXTEST_FOUND)
include_directories(${CXXTEST_INCLUDE_DIR})
enable_testing()
CXXTEST_ADD_TEST(tester_executable runner.cpp
${CMAKE_CURRENT_SOURCE_DIR}/myTestsuite.h)
endif()
The problem is that CxxTest is not found although I have the folder cxxtest and the file cxxtest/TestSuite.h inside the directory where CMakeLists.txt exists.
I already looked into the source code of FindCxxTest.cmake to see how far it gets, but it doesn't even find the path CXXTEST_INCLUDE_DIR.
Do I have to set another search path or something? I'm testing on Windows.
find_path does not search the current list directory. That is, just because a relative path is reachable from the current CMakeLists.txt, does not mean that it will be found. You can find a complete description of the search order in the manual.
A quick and dirty solution is to add the respective directory to your CMAKE_PREFIX_PATH:
set(CMAKE_PREFIX_PATH ${CMAKE_CURRENT_LIST_DIR})
find_package(CxxTest)
More fine grained control is available via the CMAKE_SYSTEM_PREFIX_PATH, CMAKE_INCLUDE_PATH, CMAKE_LIBRARY_PATH and CMAKE_PROGRAM_PATH variables. Also, some find scripts provide means of injecting search hints without having to pollute the global variables (although FindCxxTest does not seem to offer this).
Another option is, if you anyway include the CxxTest sources at a fixed place in your source tree, to not use the the find script at all, but hardcode the paths instead.
This may feel like a dirty solution at first, but if you can really rely on the sources always being there, it's actually the cleanest and most robust way to solve this. Find scripts really only make sense when you can not say where exactly on the system the files are located.

find libavahi with cmake

I need to add libavahi-client3 to cmake dependency of my project. Also need to check libavahi-client3 and libavahi-common3 existence. Problems only with current library(avahi)
Trying to do these things:
find_package(libavahi-common3)
if(NOT libavahi-common3_FOUND)
message(ERROR " libavahi-common3 is not found")
endif(NOT libavahi-common3_FOUND)
OR this variant:
find_library(AVAHI_COMMON_LIBRARY NAMES libavahi-common3)
if(NOT AVAHI_COMMON_LIBRARY_FOUND)
message(ERROR " libavahi-common3 is not found")
endif(NOT AVAHI_COMMON_LIBRARY_FOUND)
Both do not work, i searched for something like findAvahi.cmake, but found nothing. So should i write my own search module or there is another better option?
There is currently no find script for avahi shipping with CMake, which is why your first example does not work. It is important to understand that find_package simply runs an external find script, it does not perform any searching by itself.
Your second example is broken, mixing idioms from find_library and find_package. Please read up on the documentation of find_library and find_path which will help you find the required libraries and include paths.
If you want you can turn that into a find script later (look at the scripts in CMake's module directory to get an idea what such a script should look like), which will allow you to use the more compact find_package for locating the library again. Note that writing a find script that works reasonably well on different platforms is a complex task that will require some research effort to get it right.