Daniel Elliott

Statically linking particular libraries with gcc

If you want to statically link libraries with gcc you can pass the -static flag but that will statically link all of the code into the executable. But what if you want to statically link only particular libraries statically and leave the rest linked dynamically at runtime?

You might think you could specify the -L (capital L) and pass the path to the static library…

g++ -fopenmp main.cpp -L /mingw64/lib/gcc/x86_64-w64-mingw32/6.2.0/libstdc++.a

(or if your paths and includes are all setup then just the filename of the static library)

g++ -fopenmp main.cpp -static -L libstdc++.a

but that doesn’t seem to work. If you use the Linux tool ldd you can print a list of the dependencies (the libraries that the executable needs to link to in order to operate).

 

C:\Users\dokipen\Documents>ldd a.exe
ntdll.dll => /c/WINDOWS/SYSTEM32/ntdll.dll (0x7ff892040000)
KERNEL32.DLL => /c/WINDOWS/System32/KERNEL32.DLL (0x7ff8915b0000)
KERNELBASE.dll => /c/WINDOWS/System32/KERNELBASE.dll (0x7ff88e8c0000)
msvcrt.dll => /c/WINDOWS/System32/msvcrt.dll (0x7ff8916c0000)
libgomp-1.dll => /mingw64/bin/libgomp-1.dll (0x63600000)
USER32.dll => /c/WINDOWS/System32/USER32.dll (0x7ff88f700000)
win32u.dll => /c/WINDOWS/System32/win32u.dll (0x7ff88e8a0000)
GDI32.dll => /c/WINDOWS/System32/GDI32.dll (0x7ff88f920000)
gdi32full.dll => /c/WINDOWS/System32/gdi32full.dll (0x7ff88ec40000)
libstdc++-6.dll => /mingw64/bin/libstdc++-6.dll (0x6fc40000)
libwinpthread-1.dll => /mingw64/bin/libwinpthread-1.dll (0x64940000)
libgcc_s_seh-1.dll => /mingw64/bin/libgcc_s_seh-1.dll (0x61440000)

 

What we want to do it use the -Wl flag which passes options onto the linker itself. We pass the option -Bstatic. anything after that flag will be linked statically leaving the rest as a dynamic link.

g++ -fopenmp main.cpp -Wl,-Bstatic -L /mingw64/lib/gcc/x86_64-w64-mingw32/6.2.0/libstdc++.a

or

g++ -fopenmp main.cpp -Wl,-Bstatic -L libstdc++.a

OR the way to do it without passing on the filename is to use the lowercase l linking flag which passes the library name without the ‘lib’ as part of it or the

g++ -fopenmp main.cpp -Wl,-Bstatic -lstdc++<

the space after the -l flag can be left in or out so this is the same….

g++ -fopenmp main.cpp -Wl,-Bstatic -l stdc++<

Now when we print the dependencies using ldd, we see that that particular library has been linked statically but the rest have been left dynamic….

C:\Users\dokipen\Documents>ldd a.exe
ntdll.dll => /c/WINDOWS/SYSTEM32/ntdll.dll (0x7ff892040000)
KERNEL32.DLL => /c/WINDOWS/System32/KERNEL32.DLL (0x7ff8915b0000)
KERNELBASE.dll => /c/WINDOWS/System32/KERNELBASE.dll (0x7ff88e8c0000)
msvcrt.dll => /c/WINDOWS/System32/msvcrt.dll (0x7ff8916c0000)
USER32.dll => /c/WINDOWS/System32/USER32.dll (0x7ff88f700000)
win32u.dll => /c/WINDOWS/System32/win32u.dll (0x7ff88e8a0000)
GDI32.dll => /c/WINDOWS/System32/GDI32.dll (0x7ff88f920000)
gdi32full.dll => /c/WINDOWS/System32/gdi32full.dll (0x7ff88ec40000)
libgcc_s_seh-1.dll => /mingw64/bin/libgcc_s_seh-1.dll (0x61440000)
libwinpthread-1.dll => /mingw64/bin/libwinpthread-1.dll (0x64940000)<

This means that we can embed libraries in the executable and choose which ones we want to keep as .dll’s/.so’s.

but lib gomp is gone from that list which means its been linked statically.  SO we need to trail the command with -Wl,-Bdynamic to make sure all other libraries stay linked dynamically.

http://stackoverflow.com/questions/809794/use-both-static-and-dynamically-linked-libraries-in-gcc

Leave a Reply

Your email address will not be published. Required fields are marked *