1

I have the following folder structure in my HOME:

- myproject/
    + src/
        + utilities.cpp
    + inc/
        + Executor.hpp
        + utilities.hpp
    + lib/
        + utilities.o
        + libutilities.so

- other_project/

    + main.cpp

The utilities.hpp contains:

#pragma once
#ifndef UTILITIES_HXX
#define UTILITIES_HXX

#include <string>
#include <iostream>
#include <map>
#include <vector>

namespace myproject{

void readFromCSV(const std::string& filename,char delimiter,const int nlines,std::map<int,std::vector<std::string>> & csv_contents);


}
#endif

and the utilities.cpp :

#include "utilities.hpp"
#include<fstream>
#include<algorithm>
#include<sstream>

const std::string readFileIntoString(const std::string & path){
        auto ss=std::ostringstream{};
        std::ifstream input_file(path);
        if(!input_file.is_open()){
                std::cout<<"Unable to open" << path;
                exit(0);
        }
        ss<<input_file.rdbuf();
        return ss.str();
}

void readFromCSV(const std::string& filename,char delimiter,const int nlines,std::map<int,std::vector<std::string>> & csv_contents){

        std::string file_contents=readFileIntoString(filename);
        std::istringstream sstream(file_contents);
        std::vector<std::string> items;
        std::string record;

        int counter=0;
        while(std::getline(sstream,record)&&(counter<nlines)){
                std::istringstream line(record);
                while(std::getline(line,record,delimiter)){
                        record.erase(std::remove_if(record.begin(), record.end(), isspace), record.end());
                        items.push_back(record);
                }
                csv_contents[counter]=items;
                items.clear();

                counter++;
        }

}

For creating the libutilities.so I executed the following bash script in $HOME/myproject:

g++ -I./inc -fPIC -c -o utilities.o src/utilities.cpp
gcc -shared -o libutilities.so utilities.o
mv libutilities.so lib/
mv utilities.o lib/

This compiles fine. So I want to use the utilities library in other_project/main.cpp:

#include "Executor.hpp"
#include "utilities.hpp"
using namespace myproject;
main(){
    //variable declaration and definition
    readFromCSV(setFilename(PATH_INPUT,SUFFIX_INPUT,batch_index),';',batches,p);
    //other code
}

So when I compile this as:

g++ -o main main.o -I$(HOME)/myproject/inc -L$(HOME)/myproject/lib -lutilities 

within the Makefile, I got the following error:

/usr/bin/ld: main.o: in function `main()': /my_home_directory/other_project/main.cpp:168: undefined reference to myproject::readFromCSV(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&, char, int, std::map<int, std::vector<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> >, std::allocator<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > > >, std::less<int>, std::allocator<std::pair<int const, std::vector<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> >, std::allocator<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > > > > > >&)'
pgacclnk: child process exit status 1: /usr/bin/ld

Any idea?

thanks

273K
  • 29,503
  • 10
  • 41
  • 64
alvarella
  • 81
  • 3
  • 1
    What do you see in the output of `nm -D libutilities.so | grep readFromCSV`? Maybe the problem is in using `g++` with `gcc` that results in different names mangling. – pptaszni Jul 28 '22 at 14:05
  • @pptaszni Would rather not assume name mangling – that should have been done on compilation of the source file already – for which g++ was used as well. – Aconcagua Jul 28 '22 at 14:06
  • You might want to read about [`using namespace ...`](https://stackoverflow.com/questions/1452721/why-is-using-namespace-std-considered-bad-practice) (there about `std`, but that actually applies for *all* namespaces). – Aconcagua Jul 29 '22 at 10:41

1 Answers1

1

You declare the function readFromCSV in the namespace myproject and define the function readFromCSV in the global namespace. Thus you get the error undefined reference to myproject::readFromCSV.

273K
  • 29,503
  • 10
  • 41
  • 64