HOWTO create Shared Object(Run Time)This is a featured page

Follow each and every step carefully to create the shared object(run time). Also, following example is just for understanding. You can always tweak it for your personal R&D:

a) Make a header file for library functions. Declare all your library functions here:
vi arithmetic.h

================================================================
#ifndef _ARITHMETIC_H_
#define _ARITHMETIC_H_

int add(int, int);
int sub(int, int);
int mul(int, int);
int div(int, int);

#endif
================================================================

b) Make a source file for library functions and put the function definitions for the functions which you declared in the header file:
vi arithmetic.c


================================================================
int add(int, int);
int sub(int, int);
int mul(int, int);
int div(int, int);

int add(int a, int b)
{
return a + b;
}

int sub(int a, int b)
{
return a - b;
}

int mul(int a, int b)
{
return a * b;
}

int div(int a, int b)
{
return a / b;
}
================================================================

c) Now compile it to create a ".o" file. Please note it, you have to only create a ".o" file:
gcc -c arithmetic.c

d) Now, make one directory in the current directory, named as RunTime:
mkdir RunTime

Its not compulsory to make this directory, but it would be preferred as it will give you an idea about some options which we have to specify to run the application.

e) Now, use the library functions in main application by including the library header file and using the library functions. Create this file in RunTime directory:
vi ./RunTime/main.c


================================================================
#include <stdio.h>
#include <dlfcn.h>

typedef int (*func)(int, int);
func add, sub, mul, div;

int main()
{
int a = 5, b = 4;
void *arithHandle = NULL;

arithHandle = dlopen("libarithmetic.so", RTLD_NOW);
if ( NULL == arithHandle )
{
printf("Arithmetic library cant be opened\n");
}

add = (func) dlsym (arithHandle, "add");
sub = (func) dlsym (arithHandle, "sub");
mul = (func) dlsym (arithHandle, "mul");
div = (func) dlsym (arithHandle, "div");

printf("Add :: %d\n", add(a, b));
printf("Sub :: %d\n", sub(a, b));
printf("Mul :: %d\n", mul(a, b));
printf("Div :: %d\n", div(a, b));

dlclose(arithHandle); //Its important to call dlclose() when you are done
return 0;
}
================================================================

f) Create the dynamic library for load time:
gcc -shared -o libarithmetic.so.1.0.0 *.o

-shared: produces a shared object which can then be linked with other objects to form an executable.

g) Create soft links to this library:
ln -s libarithmetic.so.1.0.0 libarithmetic.so.1
ln -s libarithmetic.so.1 libarithmetic.so

*.so: required by loader
*.so.<major-version>: required by no one but we make it for version control
*.so.<major-version>.<minor-version>.<release-no>: required by linker

h) Now, change to the directory RunTime
cd ./RunTime

i) Build the main application:
gcc -o main main.c -ldl
or
gcc main.c -ldl (application will be named as a.out)

Note:
-L <path>: -L is a directory option which tells the path of library to linker
-l<libraryname>: -l is an option to linker which indicates the name of library
<libraryname>: In above example, we are using library libdl.so. So, <libraryname> will be <dl>. Don't forget to link the main application with this library else who will provide the definition of functions dlopen(), dlsym() and dlclose().

So, basically we are not linking libarithmetic.so to application here. We are doing at run time. So, in this case no information will be inserted in the ELF32 as done in the case of load time shared objects. You can always verify this by running following command:

[piyushkansal@localhost RunTime]$ ldd main
libdl.so.2 => /lib/libdl.so.2 (0x00b74000)
libc.so.6 => /lib/tls/libc.so.6 (0x00a15000)
/lib/ld-linux.so.2 => /lib/ld-linux.so.2 (0x009fd000)


ldd means loader dependency. What this command does is basically reads a section in the ELF32 file i.e main application which lists the what all libraries are needed by this application to run properly and displays that information on the shell. So, we are not getting any entry like libarithmetic.so here.

So, if you want to check whether an application uses the run time linking or not then use ldd and see if there is an entry for libdl.so.*. Eg, in prev. case:

j) Let loader know the path of the library, our library "libarithmetic". This step is really important:
export LD_LIBRARY_PATH=..

Also, the application is present in RunTime folder and the library is in its parent directory. So, this path is always given with reference to application.

k) Execute the main application:
./main

This finished up the process of creating the run time shared objects. Now, here is the explanation of some of the things you must be looking for:

a) dlopen() and dlclose(): basically increments a counter that how many times a particular library has been opened while dlclose() decrements that count. When count becomes 0 and no other loaded libraries use symbol in it then the library is removed from the memory. libc is the one which maintains this count.

b) RTLD_NOW: loads the library and gives all the symbol information immediately. Due to this, dlopen() becomes slow while dlsym() becomes fast. There are other options as well which we can specify in place of it. They are:

RTLD_LAZY:
loads the library and symbol table construction is deferred till we use first dlsym() function. So, dlopen() becomes fast while dlsym() becomes slow.

RTLD_GLOBAL: external references in the library are resolved using the libraries in that library’s dependency list and any other libraries previously opened with the RTLD_GLOBAL flag. If the executable was linked with the flag "-rdynamic", then the global symbols in the executable will also be used to resolve references in a dynamically loaded library. Optionally, RTLD_GLOBAL may be or’ed with flag, in which case the external symbols defined in the library will be made available to subsequently loaded libraries.


Libraries
HOWTO create Static Library
HOWTO create Shared Object(Load Time)

Note: If you have any doubts or suggestions, please feel free to add comments on my page below. I will try my level best to get back to your queries soon and will definitely implement the suggestions, if relevant.



piyush.kansal
piyush.kansal
Latest page update: made by piyush.kansal , Jul 7 2007, 3:48 PM EDT (about this update About This Update piyush.kansal Changes will only be done by me - piyush.kansal

No content added or deleted.

- complete history)
More Info: links to this page
There are no threads for this page.  Be the first to start a new thread.

Related Content

  (what's this?Related ContentThanks to keyword tags, links to related pages and threads are added to the bottom of your pages. Up to 15 links are shown, determined by matching tags and by how recently the content was updated; keeping the most current at the top. Share your feedback on Wetpaint Central.)