Could it be that clang and gcc somehow implement -Bsymbolic
differently?
\\ exe.c
void f();
typedef void (*fptr)();
void compareFuncPtrs(fptr);
int main()
{
compareFuncPtrs(f);
return 0;
}
\\ shlib.c
#include <stdio.h>
void f() {}
typedef void (*fptr)();
void compareFuncPtrs(fptr pExe)
{
fptr pShlib = f;
printf(pExe == pShlib ? "Equal\n" : "Different\n");
}
# buildAndRun.sh
echo
echo 'clang + Bsymbolic'
echo '-----------------'
clang -shared -Wl,-Bsymbolic -fPIC -o libshlib.so shlib.c
clang -L. -Wl,-rpath,. -o exe exe.c -lshlib
./exe
echo
echo 'gcc + Bsymbolic'
echo '---------------'
gcc -shared -Wl,-Bsymbolic -fPIC -o libshlib.so shlib.c
gcc -L. -Wl,-rpath,. -o exe exe.c -lshlib
./exe
On my system $ buildAndRun.sh
gives:
clang + Bsymbolic
-----------------
Equal
gcc + Bsymbolic
---------------
Different
The test system has gcc 10.3.1 and clang 16.0.2. Can anyone reproduce this diff? What is the reason for it?
Edit: by @yugr's suggestion I diffed command lines and discovered that for some reason my clang adds -pie
to the build of the executable. Indeed, when adding it manually to the gcc build I get the behavior I expected:
# buildAndRun.sh
...
gcc -fpie -L. -Wl,-rpath,. -o exe exe.c -lshlib
./exe
gives -
clang + Bsymbolic
-----------------
Equal
gcc + Bsymbolic
---------------
Equal
Any insight on how -fpie
intervenes in Bsymbolic
s impact?
-Wl
flags are passed straight to the linker so I suggest to see if linker invocations are similar (you can emit them with-v
flag). The issue does not repro on Ubuntu 22.04 (clang 14, gcc 11.4).