4

I have a copy of OpenCV2.4.0 installed in /usr/local/lib

My program compiled properly but when the linker is evoked, it gave errors such as:

/home/zhouw/moos-ivp-zhouw/trunk/src/pATRTest/mst.cpp:661: undefined reference to 'cv::_OutputArray::_OutputArray(cv::Mat const&)'
CMakeFiles/pATR.dir/mst.cpp.o:/home/zhouw/moos-ivp-zhouw/trunk/src/pATRTest/mst.cpp:675: more undefined references to `cv::_OutputArray::_OutputArray(cv::Mat const&)' 
collect2: ld returned 1 exit status
make[2]: *** [../bin/pATR] Error 1
make[1]: *** [src/pATRTest/CMakeFiles/pATR.dir/all] Error 2
make: *** [all] Error 2

The strange thing is my program uses opencv intensively, if CMake has trouble finding the libraries, it should have complained a lot more undefined references than jsut a few.

I tried adding LINK_DIRECTORIES("/usr/local/lib") in my cmake file but it didn't help. There's another library called POCO is also installed under /usr/local/lib. My program also links to the POCO libraries, but CMake seems having no trouble finding them.

If I manually link with -L/usr/local/lib, it would link properly without error.

The CMakeLists.txt looks like this

PROJECT(pATR)

#what files are needed?
SET(SRCS
spline.hpp
utils.hpp utils.cpp
mst.hpp mst.cpp
cluster.hpp cluster.cpp
target.hpp target.cpp
detector.hpp detector.cpp
classifier.hpp classifier.cpp
atr.hpp atr.cpp
MOOSAtr.h MOOSAtr.cpp
main.cpp
)

ADD_EXECUTABLE(pATR ${SRCS})

# indicate how to link
#LINK_DIRECTORIES("/usr/local/lib")
TARGET_LINK_LIBRARIES(pATR opencv_core opencv_highgui opencv_imgproc MOOS)

INSTALL(TARGETS
pATR
RUNTIME DESTINATION ${CMAKE_INSTALL_PREFIX}/bin
)

Any idea what's going on? Many thanks!

jww
  • 97,681
  • 90
  • 411
  • 885
Silmarilli
  • 308
  • 1
  • 3
  • 11
  • Also see [Why use add_library({tgt} IMPORTED) versus target_link_libraries( -l {.so | .a})?](https://stackoverflow.com/q/49482691/608639) – jww Dec 18 '18 at 10:48

3 Answers3

3

If you have CMake 2.8, I recommend using find_package(OpenCV) to load the libraries.

There is an example at http://docs.opencv.org/doc/tutorials/introduction/linux_gcc_cmake/linux_gcc_cmake.html

The CMake file:

cmake_minimum_required(VERSION 2.8)
project( DisplayImage )
find_package( OpenCV REQUIRED )
add_executable( DisplayImage DisplayImage.cpp )
target_link_libraries( DisplayImage ${OpenCV_LIBS} )
user149100
  • 1,089
  • 3
  • 12
  • 16
  • I tried with find_package(OpenCV REQUIRED) before I posted the question, somehow I didn't link the libraries as ${OpenCV_LIBS} but still used their individual names, i.e. opencv_core opencv_highgui opencv_imgproc. Thanks, it all works now! – Silmarilli May 29 '13 at 03:55
  • 1
    A bizarre thing happened today. I copied the entire directory tree of my software over to a different linux machine with the same versions of everything and same installation of OpenCV. The link error returned! – Silmarilli May 30 '13 at 05:07
  • I added SET(OpenCV_LIBS opencv_core opencv_highgui opencv_imgproc) to make it work this time. what does this imply? find_package didn't work properly? – Silmarilli May 30 '13 at 05:28
  • I can't think of a simple explanation that setting it explicitly would make it work. Perhaps someone with more experience with CMake could shed some light on this. – user149100 May 31 '13 at 04:24
2

You're after:

find_package(OPENCV COMPONENTS core imgproc highgui REQUIRED)

From the docs:

Packages with components

Some libraries are not monolithic, but come with one or more dependent libraries or components. A notable example for this is the Qt library, which ships (among others) with the components QtOpenGL and QtXml. To use both of these components, use the following the find_package command:

find_package(Qt COMPONENTS QtOpenGL QtXml REQUIRED)

also, for more info you may check out the following link.

https://gitlab.kitware.com/cmake/community/wikis/doc/tutorials/How-To-Find-Libraries

F14
  • 67
  • 2
  • 6
Alex Hodge
  • 33
  • 3
1

I am not sure if it makes sense that CMake can't find the linking libraries. CMake finds your dependencies and generates the Makefile, but it doesn't actually compile and link for you.

Your error are not from CMake, right? They are from make.

I always link manually with this

g++ -o myopencvapp `pkg-config --cflags --libs opencv` myopencvapp.cpp`

when invoking g++.

BW0
  • 757
  • 8
  • 14
  • Thanks for your reply! Yes, manual linking works. I just thought that /usr/local/lib is a default directory for cmake to look for libraries – Silmarilli May 29 '13 at 04:00