Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

in gcc how to force symbol resolution at runtime

My first post on this site with huge hope:: I am trying to understand static linking,dynamic linking,shared libraries,static libraries etc, with gcc. Everytime I try to delve into this topic, I have something which I don't quite understand.

Some hands-on work:

bash$ cat main.c

#include "printhello.h"
#include "printbye.h"

void main()
{
PrintHello();
PrintBye();
}

bash$ cat printhello.h
void PrintHello();

bash$ cat printbye.h
void PrintBye();

bash$ cat printbye.c
#include <stdio.h>

void PrintBye()
{
printf("Bye bye\n");
}

bash$ cat printhello.c
#include <stdio.h>

void PrintHello()
{
printf("Hello World\n");
}

gcc -Wall -fPIC -c *.c -I.
gcc -shared -Wl,-soname,libcgreet.so.1 -o libcgreet.so.1.0   *.o
ln -sf libcgreet.so.1.0 libcgreet.so
ln -sf libcgreet.so.1.0 libcgreet.so.1

So I have created a shared library. Now I want to link this shared library with my main program to create an executable.

gcc -Wall -L. main.c -lcgreet -o greet

It very well works and if I set the LD_LIBRARY_PATH before running greet( or link it with rpath option) I can make it work.

My question is however different: Since I am anyway using shared library, is it not possible to force symbol resolution at runtime (not sure about the terminology but perhaps called dynamic linking as per the book "Linkers and Loaders"). I understand that we may not want to do it because this makes the program run slow and has overhead everytime we want to run the program, but I am trying to understand this to clear my concepts.

Does gcc linker provide any option to delay symbol resolution at runtime? (to do it with the library we are actually going to run the program with)(as library available at compile time may be different than the one available at runtime if any changes in the library) I want to be able to do sth like:

bash$ gcc main.c -I.

(what option needed here?) so that I don't have to give the library name, and just tell it that I want to do symbol resolution at runtime, so headers are good enough for now, actual library names are not needed.

Thanks, Learner For Ever.

like image 329
xyz Avatar asked Jul 01 '10 12:07

xyz


People also ask

What is Rdynamic?

-rdynamic. Pass the flag -export-dynamic to the ELF linker, on targets that support it. This instructs the linker to add all symbols, not only used ones, to the dynamic symbol table.

What is meant by symbol resolution in compiler design?

In its simplest form, symbol resolution involves the use of a precedence relationship that has defined symbols dominating tentative symbols, which in turn dominate undefined symbols. The following C code example shows how these symbol types can be generated.

What is linking in gcc?

Linking is performed when the input file are object files " .o " (instead of source file " . cpp " or " . c "). GCC uses a separate linker program (called ld.exe ) to perform the linking.

What is global text symbol?

Global symbols can be referenced from other objects besides the object that contains the symbol definition. After collection and resolution, global symbols are added to the symbol tables being created in the output object.


1 Answers

Any linker (gcc, ld or any other) only resolves links at compile-time. That is because the ELF standard (as most others) do not define 'run-time' linkage as you describe. They either link statically (i.e. lib.a) or at start-up time (lib.so, which must be present when the ELF is loaded). However, if you use a dynamic link, the linker will only put in the ELF the name of the file and the symbols it must find, it does not link the file directly. So, if you want to upgrade the lib to a newer version later, you can do so, as long as system can find the same filename (the path can actually be different) and the same symbol names.

The other option, to get symbols at run-time, is to use dlopen, which has nothing to do with gcc or ld. dlopen simply put, opens a dynamic link library, just like fopen might, and returns you a handle, which then you pass to dlsym with the name of the symbol you want, which might be a function name for example. dlsym will then pass you a pointer to that symbol, which you can then use to call the function or use as a variable. This is how plugins are implemented.

like image 69
Gianni Avatar answered Oct 21 '22 01:10

Gianni