LinuxQuestions.org
Download your favorite Linux distribution at LQ ISO.
Home Forums Tutorials Articles Register
Go Back   LinuxQuestions.org > Forums > Non-*NIX Forums > Programming
User Name
Password
Programming This forum is for all programming questions.
The question does not have to be directly related to Linux and any language is fair game.

Notices


Reply
  Search this Thread
Old 07-28-2005, 08:55 AM   #1
Thinking
Member
 
Registered: Oct 2003
Posts: 249

Rep: Reputation: 30
how to use shared libraries?


hiho@ll

i want to make my own shared library
the first step worked: creating the library
i have a file of my own class: libmyclass.so

the problem is how do i use it in my main program?

the problem is that gcc says it can't find myclass.h file and coresponding function/class definitions!
well i think it's in libmyclass.so!
so why he can't find it?

./main = my main program path
./main/mymain.cpp = my app
./main/libmyclass.so = the library i need to link the main app

the mymain.cpp file includes #include "myclass.h"
i have no myclass.h in ./main because i think libmyclass.so should be enough to compile and link the prog!?

but if i copy the whole source of myclass into ./main
gcc finds everything he needs
but i thought a library should/can replace the source files, so i only need the library!?

or did i something wrong?
thx
 
Old 07-28-2005, 02:29 PM   #2
acid_kewpie
Moderator
 
Registered: Jun 2001
Location: UK
Distribution: Gentoo, RHEL, Fedora, Centos
Posts: 43,417

Rep: Reputation: 1985Reputation: 1985Reputation: 1985Reputation: 1985Reputation: 1985Reputation: 1985Reputation: 1985Reputation: 1985Reputation: 1985Reputation: 1985Reputation: 1985
unfortunately, you so need the header to actually compile something against a library. the header serves as a declaration of what functions and resources are going to available as and when the given piece of code is compiled. it provides the confidents to blindly link against an object and be able to run ok. gcc can't just see what's avaible inside an shared object.

so the library does replace the source, but the header isn't the source. you should have dealt with -devel rpms when you want to compile source against normal rpms. here the normal rpm contains the executables and libraries, the -devel primarily provides the headers to compile against.
 
Old 07-29-2005, 04:13 PM   #3
Mara
Moderator
 
Registered: Feb 2002
Location: Grenoble
Distribution: Debian
Posts: 9,696

Rep: Reputation: 232Reputation: 232Reputation: 232
If you want to load the library dynamically, use dlopen/dlsym calls, don't link with the lib. You don't need header file when using this way.
 
Old 07-30-2005, 02:31 PM   #4
Hano
Member
 
Registered: Sep 2001
Location: Venezuela, Caracas
Distribution: RedHat 9.0
Posts: 196

Rep: Reputation: 30
Quote:
Originally posted by Mara
If you want to load the library dynamically, use dlopen/dlsym calls, don't link with the lib. You don't need header file when using this way.

look at this example which you can use as a base:


//-------------Base.h
// this is were the abstract interface is defined
Code:
#ifndef __PE_H
#define __PE_H

#include <iostream>

using namespace std;

struct Base {


public:
   Base() {  cout << "Building Base "<< endl; };
   virtual ~Base() { cout << "Destroying Base "<< endl;  };

   virtual void Do() = 0;
   virtual void Put(double a) = 0;
};

// the types of the class factories
typedef Base* Create_t();
typedef void Destroy_t(Base*);

#endif

//------------------ example.h
// example.h and example.cpp is a plugin that implements the Base abstract class.
Code:
#include <iostream>
using namespace std;

#include "base.h"

struct iExample : public Base
{

 iExample()
 {
  cout << "initializing iExample "<< endl;
 };

 virtual ~iExample()
 {
  cout <<" destroying iExample "<< endl;
 };

double somedata;

virtual void Do();

virtual void Put(double a);

};

//------------- example.cpp
Code:
#include "example.h"

void iExample :: Do() { cout << somedata << endl; }
void iExample :: Put(double a) { somedata = a; }

// the class factories

extern "C" Base* Create() {
    return new iExample;
}

extern "C" void Destroy(Base* p) {
    delete p;
}
To compile the 'example' plugin you need to do:

g++ -fPIC -c example.cpp
g++ -shared -o libexample.so example.o



//---------------- plug_test.cpp
// this is a test application where you load the plugin and use it.
// Note that this requires the base.h header to compile
Code:
#include "base.h"

#include <iostream>
#include <dlfcn.h>

using namespace std;

int main()
{
 // load the iExample plugin

    cout << "loading " << endl;
    void* example = dlopen("./libexample.so", RTLD_LAZY);
    if (!example) {
        cerr << "Cannot load library: " << dlerror() << '\n';
        return 1;
    }
    cout << " done " << endl;

    // load the symbols
    Create_t* create_example = (Create_t*) dlsym(example, "Create");
    Destroy_t* destroy_example = (Destroy_t*) dlsym(example, "Destroy");

    if (!create_example || !destroy_example) {
        cerr << "Cannot load symbols: " << dlerror() << '\n';
        return 1;
    }
    cout << "symbols loaded " << endl;
    // create an instance of the class
    Base* poly = create_example();

    // use the class
    poly->Put(7);
    poly->Do();

    // destroy the class
    destroy_example(poly);

    // unload the iExample plugin Factory
    dlclose(example);


};
executable compilation:
g++ -c plug_test.cpp
g++ -rdynamic -ldl -Wall plug_test.o -o plug_test.x


Note also, that is possible to extract the symbols in a plugin library and reconstruct a header file, but this is only needed when the actual header file was lost. In most circumstances you won't need to do that. If that's what u need, there is a command to dump the symbols inside a shared object but i don't remember (anyone?) after that, you will need to demangle each symbol with c++filt. With that information you have all you need to reconstruct a lost header

Last edited by Hano; 07-30-2005 at 02:59 PM.
 
Old 09-12-2005, 10:39 AM   #5
Hano
Member
 
Registered: Sep 2001
Location: Venezuela, Caracas
Distribution: RedHat 9.0
Posts: 196

Rep: Reputation: 30
ah i remember now, the tool is nm. do

>nm -C mylib.so

and you get all symbols in the library demangled
 
Old 09-12-2005, 06:39 PM   #6
johnMG
Member
 
Registered: Jul 2003
Location: CT, USA
Distribution: Debian Sarge (server), Etch (work/home)
Posts: 601

Rep: Reputation: 32
http://wiki.linuxquestions.org/wiki/...ands_and_Files
 
  


Reply



Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is Off
HTML code is Off



Similar Threads
Thread Thread Starter Forum Replies Last Post
error while loading shared libraries: libstdc++.so.5: cannot open shared object file: Franziss Linux - Newbie 10 06-28-2010 05:47 AM
Urgent !!! rpm: error while loading shared libraries: libelf.so.1: cannot open shared tinaa Linux - Software 5 12-02-2008 03:19 PM
error while loading shared libraries: libdb-4.1.so: cannot open shared object file putquery8581 Linux - Software 1 10-01-2004 07:03 AM
mplayer: error while loading shared libraries: libdvdread.so.3: cannot open shared ob Bruce Hill Slackware 6 12-11-2003 08:34 AM
linux init error in loading shared shared libraries akaran Linux - Software 1 05-28-2003 04:40 AM

LinuxQuestions.org > Forums > Non-*NIX Forums > Programming

All times are GMT -5. The time now is 06:50 PM.

Main Menu
Advertisement
My LQ
Write for LQ
LinuxQuestions.org is looking for people interested in writing Editorials, Articles, Reviews, and more. If you'd like to contribute content, let us know.
Main Menu
Syndicate
RSS1  Latest Threads
RSS1  LQ News
Twitter: @linuxquestions
Open Source Consulting | Domain Registration