My questions:
- Is function pointer equality guaranteed by the C standard?
- If the answer of (1) is yes. Is that the case regardless of the pointer being obtained in different final compilation units (e.g. main executable and a shared library)?
- How does the dynamic loader deal with that? (I can think about a few reasons for which this might be tricky, all related to PIC code (e.g. GOT tables in elf and whatever equivalent COFF uses for that)). Regardless of (1) and (2) the linux loader seems to guarantee this.
Here is an example. The questions above boil down to whether C guarantees what main.c
prints: "Function equality: 1"
or "Function equality: 0"
and, in the first case, how does the dynamic loader make that happen.
common.h:
extern void * getc_main;
extern void * getc_shared;
void assign_getc_shared();
main.c:
#include <stdio.h>
#include "common.h"
int main()
{
getc_main = (void*) getc;
assign_getc_shared();
printf("Function equality: %d\n", getc_main == getc_shared);
return 0;
}
shared.c:
#include <stdio.h>
#include "common.h"
void assign_getc_shared()
{
getc_shared = (void*) getc;
}
In Unix this would be compiled with the following commands:
cc -shared -fPIC -o libshared.so shared.c
cc -o main main.c -L. -lshared
And executed with:
LD_LIBRARY_PATH=. ./main