3

I have some "simple" code in C++ to connect to a MySQL database (which is localhost, btw).

#include <stdlib.h>
#include <iostream>
#include "mysql/include/mysql/jdbc.h"


using namespace sql;


int main() {

  std::cout << "Test"<< std::endl;

  try {
   sql::Driver *myDriver;
   sql::Connection *myConn;
   sql::Statement *myStmt;
   sql::ResultSet *myRes;

   myDriver = sql::mysql::get_mysql_driver_instance();
   myConn = myDriver ->connect("tcp://127.0.0.1", "root", "");
   myConn->setSchema("root");

   myStmt = myConn->createStatement();
   myRes = myStmt->executeQuery("SELECT 'Hello World' AS _message");

   while (myRes->next()) {
     std::cout << myRes->getString("_message") << std::endl;
   }
   delete myRes;
   delete myStmt;
   delete myConn;

 } catch (sql::SQLException &e) {
   std::cout << "Filed connect to Database" << std::endl;
   std::cout << "Error: " << e.what() << std::endl;
   std::cout << "Error code: " << e.getErrorCode() << std::endl;
 }
}

The file jdbc.h is just a lot of different #include for header files.

I use 2 commands to compile: g++ -c -Wall -I/usr/include/cppconn connect.cpp -o connect.o and g++ -lm -L/usr/lib/x86_64-linux-gnu -lmysqlcppconn connect.o -o connect

Which produced this linking error:

/usr/bin/ld: connect.o: in function "check_lib()':
connect.cpp:(.text+0x2c): undefined reference to `check(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&)"
/usr/bin/ld: connect.cpp:(.text+0x77): undefined reference to "check(std::map<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> >, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> >, std::less<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > >, std::allocator<std::pair<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > > > > const&)"
/usr/bin/ld: connect.o: in function `sql::mysql::get_driver_instance_by_name(char const*)':
connect.cpp:(.text+0xfa): undefined reference to   "sql::mysql::_get_driver_instance_by_name(char const*)"
collect2: error: ld returned 1 exit status

Which I kinda resolved using this answer: https://stackoverflow.com/a/33395489/14814564 , essentially by putting #define _GLIBCXX_USE_CXX11_ABI 0 at the top of the file, which after compilation, produces this linking error:

/usr/bin/ld: connect.o: in function "check_lib()':
connect.cpp:(.text+0x2c): undefined reference to "check(std::string const&)'
/usr/bin/ld: connect.cpp:(.text+0x77): undefined reference to "check(std::map<std::string, std::string, std::less<std::string>, std::allocator<std::pair<std::string const, std::string> > > const&)'
/usr/bin/ld: connect.o: in function `sql::mysql::get_driver_instance_by_name(char const*)':
connect.cpp:(.text+0xfa): undefined reference to "sql::mysql::_get_driver_instance_by_name(char const*)'
collect2: error: ld returned 1 exit status

Why does this linking error keep popping up and how do I resolve it?

Kostas M
  • 59
  • 8
  • You're not linking something, that needs to be linked against. This error is avoidable by using cmake's find_package and link_libraries for example. I strongly recommend to not command line your compiling/linking manually (at least for projects which consist of more than 1 source file or use more than zero 3rd party libraries). – nada Aug 11 '21 at 08:46
  • `-lmysqlcppconn connect.o` -> `connect.o -lmysqlcppconn`? – KamilCuk Aug 11 '21 at 08:51
  • @KamilCuk no changes at all :/ – Kostas M Aug 11 '21 at 08:58
  • @nada I will check cmake out. Yeah, I don't always compile through my terminal, I just did for now because I wanna have a taste of how the program is compiled. Why did you recommend I use those functions exactly? – Kostas M Aug 11 '21 at 09:01
  • Because if you wanna use MySQL in your C++ project with CMake you would simply do `find_package(MySQL)` and `target_link_library(your_project_name ${MYSQL_LIBRARY})`. It's as easy as that. – nada Aug 11 '21 at 09:18
  • 1
    Are you sure `-lmysqlcppconn` locates at the path `/usr/lib/x86_64-linux-gnu` ?? – nhatnq Aug 11 '21 at 09:47
  • Tbh @nhatnq, I don't know. I just found the commands online, from a Youtube tutorial and copied them. Do you know of any ways to check that `-lmysqlcppconn` is in the path `/usr/lib/x86_64-linux-gun/`?? – Kostas M Aug 11 '21 at 10:34
  • 1
    @KostasM That's why it does not always work well when you try something You need to get better. The linker will try to find the `libmysqlcppconn.so` in the library search path specified by `-L` as well as in the standard paths – nhatnq Aug 11 '21 at 10:43
  • @nhatnq Sorry for the late response. I just checked the `usr/lib/x86_64-linux-gnu` path, and there are a `libmysqlconn.so` as well as a `libmysqlconn.so.7`, a `libmysqlconn.so.7.1.1.12` and a `libmysqlconn.a` library. Do you think I should link another library? Or do you reckon the linking error is somewhere else? – Kostas M Aug 12 '21 at 08:45
  • `libmysqlconn.so` -> `-lmysqlconn` ?? – nhatnq Aug 12 '21 at 09:36
  • Are you suggesting I change the file name in the folder or change the linking command? didn't quite catch that, unfortunately – Kostas M Aug 12 '21 at 09:54
  • I think they meant because of the file name change the command line accordingly. Because the filename misses the 'cpp' (which is perhaps just some change between distributions or versions or could be a different library altogether), which was there on the command line. – Sebastian Nov 23 '22 at 07:33
  • Using the command line, especially for such a simple project, is good! Better to understand than just use cmake & co. and not being able to understand, debug or extend it. A programmer should get to know the compilation workflow and the commands involved. – Sebastian Nov 23 '22 at 07:35
  • Probably both problems can be solved by installing or just downloading a newer version of the mysql libraries. The library filename change could have been done exactly because of the ABI change and using the compatibility define could create problems with other libraries. – Sebastian Nov 23 '22 at 07:41

1 Answers1

0

I had the same problem, I solved it by building a Makefile`

 MYSQL_CONCPP_DIR = ./mysql
 CPPFLAGS=-I $(MYSQL_CONCPP_DIR)/include/mysql -L $(MYSQL_CONCPP_DIR)/lib64
 LDLIBS=-lmysqlcppconn
 CXXFLAGS=-std=c++11
 out.exe:test.cpp
     g++ test.cpp ${LDLIBS} ${CXXFLAGS} ${CPPFLAGS} -o out.exe

You have there #include "mysql/include/mysql/jdbc.h"

In my case include needs to be done like this` #include <jdbc.h>

NoName
  • 1
  • 1
  • In this case the 'libmysqlcppconn.so' is missing (see comments to question), so the LDLIBS probably would have to be changed. – Sebastian Nov 23 '22 at 07:38