Search code examples
cgccsdlstatic-librariessdl-2

Static link SDL2 on Linux


I am trying to statically link SDL2 on Linux, with the goal of creating a binary that doesn't require any libraries to be required on the system. I understand this will require statically linking more than just SDL2, such as SDL2's dependencies and things like libc, so help on that front would be appreciated as well. But right now I can't get SDL2 to statically link at all.

I am using GCC, and SDL 2.0.16 that I compiled and installed myself with the default configuration, which includes static libraries. I already had SDL2 installed through my package manager, so my installation went to /usr/local/include/SDL2 and /usr/local/lib.

Running /usr/local/bin/sdl2-config --cflags --static-libs gives:

-I/usr/local/include/SDL2 -D_REENTRANT
-L/usr/local/lib -lSDL2 -lm -ldl -lpthread -lrt

No amount of messing around with these flags and -static have been able to produce a binary that doesn't dynamically link to SDL2. How can I do it?

Other flags I am using for other reasons are -std=c89 -Wall -Wno-unknown-pragmas -DNDEBUG -Os -g0 -s

Being able to cross compile and do this would be great, but I understand that's a lot more complex. I've been trying to compile with zig cc as that would allow cross-compilation later, but couldn't get it to work. I was able to get a build that didn't dynamically link to SDL2, but it would segfault.


In response to comments:

Running pkg-config --static --cflags --libs /usr/local/lib/pkgconfig/sdl2.pc gives:

-I/usr/local/include/SDL2 -D_REENTRANT -L/usr/local/lib -Wl,-rpath,/usr/local/lib -Wl,--enable-new-dtags -lSDL2 -lm -ldl -lpthread -lrt

Using that creates a dynamically-linked executable, so not what I want. If I add -static I get the error:

/usr/bin/ld: /usr/local/lib/libSDL2.a(SDL_dynapi.o): in function `get_sdlapi_entry':
/home/makeworld/Software/SDL2-2.0.16/src/dynapi/SDL_dynapi.c:237: warning: Using 'dlopen' in statically linked applications requires at runtime the shared libraries from the glibc version used for linking

Solution

  • Thanks to @HolyBlackCat and @keltar, I have been able to statically link SDL2.

    I basically just used the output of pkg-config as provided in my question, but with the addition of -Wl,-Bstatic before -lSDL2 and -Wl,-Bdynamic after it. This statically links SDL2, but dynamically links all the other libraries.

    The final command is:

    gcc your_code.c -o your_executable -I/usr/local/include/SDL2 -D_REENTRANT \
    -L/usr/local/lib -Wl,-rpath,/usr/local/lib -Wl,--enable-new-dtags \
    -Wl,-Bstatic -lSDL2 -Wl,-Bdynamic -lm -ldl -lpthread -lrt
    

    If your build of SDL2 is installed elsewhere, just change the /usr/local/include/SDL2 and /usr/local/lib part of the command to point to where the header files and .a files are respectively.


    If I figure out how to cross-compile this setup, I will update this answer.