# Calling ROS libraries from external CPP

I want to call the ROS libraries (shared object .so files) from external CPP program. Below are the ROS libraries, which I copied from /opt/ros/indigo/lib/ to a sub-directory-

1. /opt/ros/indigo/lib/libkdl_parser.so
2. /opt/ros/indigo/lib/liborocos-kdl.so.1.3.0

I used g++ to compile the main code i.e., test.cpp with following command-

g++ -Iinclude -I/usr/include/eigen3 -Lshared -lorocos-kdl -lkdl_parser -std=c++11 test.cpp -o test


but it is not working, since few more dependencies need to satisfy. Below is the error -

test@test:~/Desktop/calll/calling_so$g++ -Iinclude -I/usr/include/eigen3 -Lshared -lorocos-kdl -lkdl_parser -std=c++11 test.cpp -o test /tmp/ccVP6thR.o: In function main': test.cpp:(.text+0x103): undefined reference to KDL::Tree::Tree(std::string const&)' test.cpp:(.text+0x13a): undefined reference to kdl_parser::treeFromFile(std::string const&, KDL::Tree&)' test.cpp:(.text+0x164): undefined reference to KDL::Chain::Chain()' test.cpp:(.text+0x188): undefined reference to KDL::Tree::getChain(std::string const&, std::string const&, KDL::Chain&) const' test.cpp:(.text+0x1f4): undefined reference to KDL::ChainDynParam::ChainDynParam(KDL::Chain const&, KDL::Vector)' test.cpp:(.text+0x216): undefined reference to KDL::JntArray::JntArray(unsigned int)' test.cpp:(.text+0x238): undefined reference to KDL::JntSpaceInertiaMatrix::JntSpaceInertiaMatrix(int)' test.cpp:(.text+0x258): undefined reference to KDL::ChainDynParam::JntToMass(KDL::JntArray const&, KDL::JntSpaceInertiaMatrix&)' test.cpp:(.text+0x271): undefined reference to KDL::JntSpaceInertiaMatrix::operator()(unsigned int, unsigned int)' test.cpp:(.text+0x2a6): undefined reference to KDL::JntSpaceInertiaMatrix::~JntSpaceInertiaMatrix()' test.cpp:(.text+0x2b5): undefined reference to KDL::JntArray::~JntArray()' test.cpp:(.text+0x2c4): undefined reference to KDL::ChainDynParam::~ChainDynParam()' test.cpp:(.text+0x2d3): undefined reference to KDL::Chain::~Chain()' test.cpp:(.text+0x39b): undefined reference to KDL::JntSpaceInertiaMatrix::~JntSpaceInertiaMatrix()' test.cpp:(.text+0x3af): undefined reference to KDL::JntArray::~JntArray()' test.cpp:(.text+0x3c3): undefined reference to KDL::ChainDynParam::~ChainDynParam()' test.cpp:(.text+0x3d7): undefined reference to KDL::Chain::~Chain()' /tmp/ccVP6thR.o: In function KDL::TreeElement::~TreeElement()': test.cpp:(.text._ZN3KDL11TreeElementD2Ev[_ZN3KDL11TreeElementD5Ev]+0x26): undefined reference to KDL::Segment::~Segment()' collect2: error: ld returned 1 exit status test@test:~/Desktop/calll/calling_so$


Below is test.cpp-

#include <iostream>
#include <kdl/jntarray.hpp>
#include <kdl/chaindynparam.hpp>
#include <kdl_parser/kdl_parser.hpp>
#include <kdl/jntspaceinertiamatrix.hpp>

int main(int argc, char** argv)
{
std::string urdf_file = "robot.urdf";

KDL::Tree tree;
if (!kdl_parser::treeFromFile(urdf_file, tree)) {
printf("Failed to construct kdl tree\n");
return -1;
}

KDL::Chain chain;

KDL::ChainDynParam dyn(chain, KDL::Vector::Zero());

KDL::JntArray q(chain.getNrOfJoints()); //dummy value
KDL::JntSpaceInertiaMatrix H(chain.getNrOfJoints());
dyn.JntToMass(q, H);

printf("(0,0) element of Inertia Matrix %f\n", H(0,0));
return 0;
}


The robot.urdf is kept along with test.cpp and headers are kept in a sub-directory. Below is the directory structure-

test@test:~/Desktop/calll/calling_so$tree ... edit retag close merge delete ## 2 Answers Sort by » oldest newest most voted I solved the problem. It is little strange at first. Below is the command, I tried and it worked- g++ -L/opt/ros/indigo/lib -Iinclude -I/usr/include/eigen3 test.cpp -lorocos-kdl -lkdl_parser -o test  After compiling using above command, make sure the libraries are visible. export LD_LIBRARY_PATH=/opt/ros/indigo/lib:$LD_LIBRARY_PATH

more
error: ‘shared_ptr’ in namespace ‘std’ does not name a type
typedef std::shared_ptr<ModelInterface> ModelInterfaceSharedPtr;


This looks more like a C++11 vs Boost problem than anything else. Looks like urdf::ModelInterfaceSharedPtr is using std::shared_ptr (changed from boost::shared_ptr), but your compiler doesn't support it (or support hasn't been enabled).

Note btw that KDL is a stand-alone library: orocos.org/kdl. Only if you want to use the URDF parser(s) do you need to depend on kdl_parser (part of robot_model).

more

Hi gvdhoorn, thank you very much. There were some mismatch with the header files, which I have rectified just now. I updated the question. Can you please have a look again? Apologize for the inconvenience.

( 2016-11-13 04:31:35 -0600 )edit

You'll have to figure out which libraries provide those symbols and link those in as well.

( 2016-11-14 04:38:51 -0600 )edit

One other thing: C++11 objects aren't necessarily binary compatible with non-C++11 objects / libraries. If liborocos-kdl.so is a C++03 binary, linking as you're doing might not work.

And btw: completely rewriting your question isn't really nice, I can't refer back to the errors you had before.

( 2016-11-14 04:40:30 -0600 )edit

Thanks a lot. I understand your concern. I tried compiling without C++11 and got the same errors. AFAIK all KDL:: are provided by orocos-kdl and kdl_parser:: are provided by kdl_parser. Also, I get exactly same errors after removing -L and -l compiler option. Weird. Isn't it?

( 2016-11-14 05:03:46 -0600 )edit

I solved it. I posted my answer here . Thank you very much.

( 2016-11-15 00:40:15 -0600 )edit
1

If you posted the solution to an external site, could you please answer your own question here, and include the relevant bits of whatever you posted externally? That keeps this site self-contained. If the external site ever goes down, we don't have an answer here otherwise.

( 2016-11-15 01:41:57 -0600 )edit