Linking local library in c++ (macOS High Sierra) - c++

I'm trying to link a library called apriltags to my c++ project. I've downloaded the source files, placed them in my project and set up the CMakeLists.txt such that the imports in my classes work fine. However, there is a referencing problem, such that I get the following error when using building with:
$ /Applications/CLion.app/Contents/bin/cmake/bin/cmake --build "/Users/petter/Desktop/MSc Project/autonomous-car/cmake-build-debug" --
target autonomous_car -- -j 2
Error:
[ 50%] Linking CXX executable bin/autonomous_car
Undefined symbols for architecture x86_64:
"AprilTags::TagDetector::extractTags(cv::Mat const&)", referenced from:
_main in main.cpp.o
"AprilTags::TagFamily::TagFamily(AprilTags::TagCodes const&)", referenced from:
AprilTags::TagDetector::TagDetector(AprilTags::TagCodes const&) in main.cpp.o
ld: symbol(s) not found for architecture x86_64
clang: error: linker command failed with exit code 1 (use -v to see invocation)
make[3]: *** [bin/autonomous_car] Error 1
make[2]: *** [CMakeFiles/autonomous_car.dir/all] Error 2
make[1]: *** [CMakeFiles/autonomous_car.dir/rule] Error 2
make: *** [autonomous_car] Error 2
Here is my code:
#include <iostream>
#include <cstring>
#include <vector>
#include <sys/time.h>
#include <AprilTags/TagDetector.h>
#include <AprilTags/Tag36h11.h>
#include <eigen3/Eigen/Dense>
using namespace AprilTags;
using namespace cv;
int main() {
VideoCapture cap(0); // open the default camera
if (!cap.isOpened()) // check if we succeeded
return -1;
namedWindow("view", 1);
TagCodes tag_codes = tagCodes36h11;
TagDetector* detector = NULL;
detector = new TagDetector(tag_codes);
for (;;) {
Mat frame;
cap >> frame; // get a new frame from camera
vector<TagDetection> det = detector->extractTags(frame);
imshow("view", frame);
if (waitKey(30) >= 0) break;
}
return 0;
}`
And here is my CMakeLists.txt:
cmake_minimum_required(VERSION 3.10)
project(autonomous_car)
set(SOURCE_FILES main.cpp )
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++11")
add_executable(autonomous_car ${SOURCE_FILES})
add_library(apriltags ${SOURCE_FILES})
find_package(OpenCV REQUIRED)
find_package(Sdl2 REQUIRED)
find_package(PkgConfig)
pkg_check_modules(EIGEN3 REQUIRED eigen3)
include_directories(${EIGEN3_INCLUDE_DIRS})
target_link_libraries(apriltags)
target_link_libraries(autonomous_car ${OpenCV_LIBS})
target_link_libraries(autonomous_car ${Eigen_LIBS})
target_link_libraries(autonomous_car ${Sdl2_LIBS})
include_directories(apriltags . )
include_directories(${Eigen_INCLUDE_DIRS})
include_directories(${OpenCV_INCLUDE_DIRS})
include_directories(${Sdl2_INCLUDE_DIRS})
Project structure:
project structure

Related

Clion Cmake & SDL2

I want to use Clion with SDL2 and after lot of tests, I already have an error.
there is my CmakeLists.txt :
cmake_minimum_required(VERSION 3.8)
project(sdl2-test)
#set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++11 -lmingw32")
#set(CMAKE_EXE_LINKER_FLAGS "-static-libgcc -static-libstdc++")
set(CMAKE_CXX_STANDARD 11)
include_directories(${PROJECT_SOURCE_DIR}/include)
link_directories(${PROJECT_SOURCE_DIR}/lib)
set(SOURCE_FILES main.cpp)
add_executable(sdl2-test ${SOURCE_FILES})
target_link_libraries(sdl2-test SDL2main SDL2)
my main.cpp
#include <iostream>
#include "include/SDL2/SDL.h"
using namespace std;
int main(int argc, char** argv) {
if(SDL_Init(SDL_INIT_EVERYTHING) == -1){
cout << "Something went wrong! " << SDL_GetError() << endl;
}
SDL_Window* window = SDL_CreateWindow("SDL_Demo", SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED,
1280, 720, SDL_WINDOW_OPENGL);
if(window == nullptr){
cout << "Something also went wrong here" << endl;
}
SDL_Delay(2000);
SDL_Quit();
return 0;
}
but when I build my project cmake Obviously Cmake work find but I haave some error :
C:\Users\paulp\AppData\Local\JetBrains\Toolbox\apps\CLion\ch-0\172.4343.16 \bin\cmake\bin\cmake.exe --build C:\Users\paulp\CLionProjects\sdl2-test\cmake- build-debug --target sdl2-test -- -j 4
[ 50%] Building CXX object CMakeFiles/sdl2-test.dir/main.cpp.obj
[100%] Linking CXX executable sdl2-test.exe
CMakeFiles\sdl2-test.dir/objects.a(main.cpp.obj): In function `SDL_main':
C:/Users/paulp/CLionProjects/sdl2-test/main.cpp:8: undefined reference to `SDL_Init'
C:/Users/paulp/CLionProjects/sdl2-test/main.cpp:9: undefined reference to `SDL_GetError'
C:/Users/paulp/CLionProjects/sdl2-test/main.cpp:13: undefined reference to `SDL_CreateWindow'
C:/Users/paulp/CLionProjects/sdl2-test/main.cpp:18: undefined reference to `SDL_Delay'
C:/Users/paulp/CLionProjects/sdl2-test/main.cpp:19: undefined reference to `SDL_Quit'
c:/mingw/bin/../lib/gcc/mingw32/6.3.0/../../../libmingw32.a(main.o):(.text.startup+0xa0): undefined reference to `WinMain#16'
collect2.exe: error: ld returned 1 exit status
CMakeFiles\sdl2-test.dir\build.make:96: recipe for target 'sdl2-test.exe' failed
mingw32-make.exe[3]: *** [sdl2-test.exe] Error 1
CMakeFiles\Makefile2:66: recipe for target 'CMakeFiles/sdl2-test.dir/all' failed
mingw32-make.exe[2]: *** [CMakeFiles/sdl2-test.dir/all] Error 2
CMakeFiles\Makefile2:78: recipe for target 'CMakeFiles/sdl2-test.dir/rule' failed
mingw32-make.exe[1]: *** [CMakeFiles/sdl2-test.dir/rule] Error 2
mingw32-make.exe: *** [sdl2-test] Error 2
Makefile:117: recipe for target 'sdl2-test' failed
any idea how to fix ?
The linking of your application has failed because the linker does not know the location of the sdl2-lib.
You need to search for the SDL2-libraries as well in your cmake-file and add the locations to your makefile:
find_file(SDL2_INCLUDE_DIR NAME SDL.h HINTS SDL2)
find_library(SDL2_LIBRARY NAME SDL2)
add_executable(ChickenShooter main.cpp)
target_include_directories(ChickenShooter ${SDL2_INCLUDE_DIR})
target_link_libraries(ChickenShooter ${SDL2_LIBRARY})
You can look into this post as well: How to dins SDL2 via cmake

Build error : undefined reference to `cv_bridge::CvImage::toImageMsg() const'

I am using ROS Kinetic and trying to write a program that would read two videos and publish them on two different topics. But I think I've made some mistake in linking OpenCV libraries. I am getting the following errors.
CMakeFiles/src.dir/src/src.cpp.o: In function `main':
src.cpp:(.text+0x3fd): undefined reference to `cv_bridge::CvImage::toImageMsg() const'
src.cpp:(.text+0x56d): undefined reference to `cv_bridge::CvImage::toImageMsg() const'
collect2: error: ld returned 1 exit status
MultiCamImages/CMakeFiles/src.dir/build.make:165: recipe for target 'MultiCamImages/src' failed
make[2]: *** [MultiCamImages/src] Error 1
CMakeFiles/Makefile2:1089: recipe for target 'MultiCamImages/CMakeFiles/src.dir/all' failed
make[1]: *** [MultiCamImages/CMakeFiles/src.dir/all] Error 2
Makefile:138: recipe for target 'all' failed
make: *** [all] Error 2
Invoking "make -j4 -l4" failed
This is my source file:
#include <ros/ros.h>
#include <cv_bridge/cv_bridge.h>
#include <image_transport/image_transport.h>
#include <sensor_msgs/image_encodings.h>
#include <opencv2/opencv.hpp>
#include <iostream>
#include <fstream>
using namespace std;
int main(int argc, char** argv){
ros::init(argc, argv, "PublishMultiCamImages");
ros::NodeHandle nh;
image_transport::ImageTransport it(nh);
image_transport::Publisher pub1 = it.advertise("/camera/image_raw1", 1);
image_transport::Publisher pub2 = it.advertise("/camera/image_raw2", 1);
cv::Mat im;
cv::String Path1("/home/akanksha/COSLAM_Dataset/EA-01/grayscale/*.jpg");
cv::String Path2("/home/akanksha/COSLAM_Dataset/EA-02/grayscale/*.jpg");
//time = ros::Time::now();
vector<cv::String> fn1;
vector<cv::String> fn2;
cv::glob(Path1,fn1, true); // recurse
cv::glob(Path2,fn2, true);
ros::Rate r(50);
int l1 = fn1.size();
int l2 = fn2.size();
int count1 = 0, count2 = 0;
bool flag;
while(ros::ok()){
flag = true;
if(count1 < l1){
cv::Mat image1 = cv::imread(fn1[count1]);
sensor_msgs::ImagePtr msg1 = cv_bridge::CvImage(std_msgs::Header(), "bgr8", image1).toImageMsg();
pub1.publish(msg1);
count1++;
flag = false;
}
if(count2 < l2){
cv::Mat image2 = cv::imread(fn2[count2]);
sensor_msgs::ImagePtr msg2 = cv_bridge::CvImage(std_msgs::Header(), "bgr8", image2).toImageMsg();
pub2.publish(msg2);
count2++;
flag = false;
}
if(flag)
break;
r.sleep();
}
ros::shutdown();
return 0;
}
This is my CMakeLists.txt
cmake_minimum_required(VERSION 2.8.3)
project(MultiCamImages)
find_package(catkin REQUIRED COMPONENTS
roscpp
image_transport
OpenCV
)
# find_package(OpenCV REQUIRED)
set(OpenCV_LIBS opencv_core opencv_imgproc opencv_calib3d opencv_video opencv_features2d opencv_ml opencv_highgui opencv_objdetect)
add_executable(src src/src.cpp)
target_link_libraries(src ${catkin_LIBRARIES} ${OpenCV_LIBS})
catkin_package(
# INCLUDE_DIRS include
# LIBRARIES MultiCamImages
# CATKIN_DEPENDS roscpp
# DEPENDS system_lib
)
include_directories(
${catkin_INCLUDE_DIRS}
)
And this is my pakage.xml
<?xml version="1.0"?>
<package>
<name>MultiCamImages</name>
<version>0.0.0</version>
<description>The MultiCamImages package</description>
<maintainer email="akanksha#todo.todo">akanksha</maintainer>
<buildtool_depend>catkin</buildtool_depend>
<build_depend>roscpp</build_depend>
<run_depend>roscpp</run_depend>
<build_depend>sensor_msgs</build_depend>
<run_depend>sensor_msgs</run_depend>
<build_depend>cv_bridge</build_depend>
<run_depend>cv_bridge</run_depend>
</package>
If you could point out the problem that would be a great help. Thanks!
It doesn't look like you are linking cv_bridge in the cmake file. Maybe you want this:
find_package(catkin REQUIRED COMPONENTS
cv_bridge
roscpp
image_transport
OpenCV
)
Actually the way Joseph uses OpenCV libraries for linking is not right, since OpenCV does not belong to the standard package of ROS as with cv_bridge. In this case, you need to separately use find_package for OpenCV as with boost like this:
find_package(OpenCV REQUIRED)
# Or you may add specific major portion of OpenCV version, e.g., OpenCV3
find_package(OpenCV 3 REQUIRED)

Using SDL2 with CLion on OS X

So I am trying to get SDL2 to work with CLion (So that I can experiment/learn).
My main code is as such:
#include <iostream>
#include <SDL.h>
const int SCREEN_WIDTH = 640;
const int SCREEN_HEIGHT = 480;
bool init();
SDL_Window* gWindow = NULL;
SDL_Surface* gScreenSurface = NULL;
SDL_Surface* gHelloWorld = NULL;
bool init(){
bool success = true;
/*if(SDL_Init(SDL_INIT_VIDEO)<0){
success = false;
}
else{
}*/
return success;
}
int main() {
std::cout << "Hello, World!" << std::endl;
return 0;
}
And my CMake file looks like this
cmake_minimum_required(VERSION 3.6)
project(SDL2_Lesson_1)
set(CMAKE_CXX_STANDARD 11)
# includes cmake/FindSDL2.cmake
set(CMAKE_MODULE_PATH ${PROJECT_SOURCE_DIR}/cmake)
find_package(SDL2 REQUIRED)
include_directories(${SDL2_INCLUDE_DIR})
set(SOURCE_FILES Lesson_1.cpp)
add_executable(SDL2_App ${SOURCE_FILES})
target_link_libraries(SDL2_App ${SDL2_LIBRARY})
set(SOURCE_FILES Lesson_1.cpp)
add_executable(SDL2_Lesson_1 ${SOURCE_FILES})
Also, I have a file FindSDL2.cmake from here in a folder cmake within the project folder.
Now, with the files as I have them posted, everything compiles and runs fine. BUT, when I uncomment the commented section within init(), the compilation breaks down and gives me the following error:
Undefined symbols for architecture x86_64:
"_SDL_Init", referenced from:
init() in Lesson_1.cpp.o
ld: symbol(s) not found for architecture x86_64
clang: error: linker command failed with exit code 1 (use -v to see invocation)
make[3]: *** [SDL2_Lesson_1] Error 1
make[2]: *** [CMakeFiles/SDL2_Lesson_1.dir/all] Error 2
make[1]: *** [CMakeFiles/SDL2_Lesson_1.dir/rule] Error 2
make: *** [SDL2_Lesson_1] Error 2
Note: Lesson_1.cpp is the file with the main code. Also, this is only part of the error.
Use find_library() instead of find_package()
find_library(SDL2_LIBRARY SDL2 "path/to/your/library_bundle")
find_library(SDL2_App ${SDL2_LIBRARY})

Tried boost::mpi::environment::processor_name(), get ld error

test.cpp:
#include <boost/mpi.hpp>
#include <string>
int main(void) {
std::string s = boost::mpi::environment::processor_name();
//std::cout << boost::mpi::environment::processor_name << "\n";
}
CMakeLists.txt:
project(test CXX)
set(CMAKE_CXX_STANDARD 14) # require C++14
find_package(Boost COMPONENTS mpi REQUIRED)
add_executable(test test.cpp)
target_link_libraries(
test
${Boost_LIBRARIES}
)
Error (g++ 6 and cmake):
Undefined symbols for architecture x86_64:
"boost::mpi::environment::processor_name[abi:cxx11]()", referenced from:
_main in test.o
ld: symbol(s) not found for architecture x86_64
collect2: error: ld returned 1 exit status
make[2]: *** [test] Error 1
make[1]: *** [CMakeFiles/test.dir/all] Error 2
make: *** [all] Error 2
Why the error?
By the way, when I use the commented out line std::cout << boost::mpi::environment::processor_name << "\n";, the program compiles and print out 1.
Here is the documentation on the processor_name function.

CLion: undefined "_get_driver_instance"

The IDE : CLion
System: OS X
Error messageļ¼š
Scanning dependencies of target librarySystem
[ 66%] Building CXX object CMakeFiles/librarySystem.dir/sqlConnection.cpp.o
[ 66%] Building CXX object CMakeFiles/librarySystem.dir/main.cpp.o
[100%] Linking CXX executable librarySystem
Undefined symbols for architecture x86_64:
"_get_driver_instance", referenced from:
sqlConnection::sqlConnection() in sqlConnection.cpp.o
ld: symbol(s) not found for architecture x86_64
clang: error: linker command failed with exit code 1 (use -v to see invocation)
make[2]: *** [librarySystem] Error 1
make[1]: *** [CMakeFiles/librarySystem.dir/all] Error 2
make: *** [all] Error 2
I write a class named sqlConnection to connect mysql.
sqlConection.h
#include "sqlConnection.h"
sqlConnection::sqlConnection() {
driver = get_driver_instance();
con = driver->connect("567aaffa1a70e.sh.cdb.myqcloud.com:xxxx", "xxxx", "xxxx");
con->setSchema("librarySys");
stmt = con->createStatement();
}
bool sqlConnection::ifConnected() {
bool isConnected = false;
if(!con->isClosed()){
std::cout << "Succeed to connect mysql";
isConnected = true;
}else{
std::cout << "fail to connect mysql";
}
return isConnected;
}
sqlConnection::~sqlConnection() {
delete stmt;
delete con;
}
The test in the main.cpp
main.cpp
#include <iostream>
#include "sqlConnection.h"
using namespace std;
int main() {
sqlConnection *sqlC = new sqlConnection();
sqlC->ifConnected();
return 0;
}
cmakeList:
cmake_minimum_required(VERSION 3.3)
project(librarySystem)
INCLUDE_DIRECTORIES(sqlFiles/include)
INCLUDE_DIRECTORIES(sqlFiles/lib)
INCLUDE_DIRECTORIES(sqlFiles/include/cppconn)
INCLUDE_DIRECTORIES(/usr/local/lib/libmysqlcppconn.so)
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++11")
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -std=c++0x")
set(SOURCE_FILES main.cpp sqlConnection.cpp sqlConnection.h)
add_executable(librarySystem ${SOURCE_FILES})
I used mysql connector-cpp to connect mysql.But the problem came.Have tried the solution on web,but they did't work.
Struggled with the same error and I got a small example to work with this CMakeLists.txt content. Maybe it's helpful for you even if its not same versions.
cmake_minimum_required(VERSION 3.5)
project(TestCPP)
#For mysql connector include..
INCLUDE_DIRECTORIES(/mypath/mysql-connector-c++-1.1.7-osx10.10-x86-64bit/include/)
#For Boost..
INCLUDE_DIRECTORIES(/opt/local/include/)
#For imported linking..
add_library(libmysqlcppconn STATIC IMPORTED)
set_property(TARGET libmysqlcppconn PROPERTY IMPORTED_LOCATION /mypath/mysql-connector-c++-1.1.7-osx10.10-x86-64bit/lib/libmysqlcppconn-static.a)
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++11")
set(SOURCE_FILES main.cpp)
add_executable(TestCPP ${SOURCE_FILES})
target_link_libraries (TestCPP libmysqlcppconn)