How to make weak linking work with GCC?

I just looked into this and thought some others might be interested in my findings.

Weak linking with weak_import really only works well with dynamic libraries. You can get it to work with static linking (by specifying -undefined dynamic_lookup as suggested above) but this isn’t such a hot idea. It means that no undefined symbols will be detected until runtime. This is something I would avoid in production code, personally.

Here is a Mac OS X Terminal session showing how to make it work:

Here is f.c

int f(int n)
{
    return n * 7;
}

Here is whatnof.c

#include <stdio.h>
#include <stdlib.h>

extern int f (int) __attribute__((weak_import));

int main() {
    if(f == NULL)
        printf("what, no f?\n");
    else
        printf("f(8) is %d\n", f(8));
    exit(0);
}

Make a dynamic library from f.c:

$ cc -dynamiclib -o f.dylib f.c

Compile and link against the dynamic lib, list dynamic libs.

$ cc -o whatnof whatnof.c f.dylib
$ otool -L whatnof
whatnof:
       f.dylib (compatibility version 0.0.0, current version 0.0.0)
       /usr/lib/libSystem.B.dylib (compatibility version 1.0.0, current version 125.2.0)

Run whatnof to see what happens:

$ whatnof
f(8) is 56

Now replace f.dylib with an empty library (no symbols):

$ mv f.dylib f.dylib.real
$ touch null.c
$ cc -dynamiclib -o f.dylib null.c

Run same whatnof to see what happens:

$ whatnof
what, no f?

The basic idea (or “use case”) for weak_import is that it lets you link against a set of dynamic (shared) libraries, but then run the same code against earlier versions of the same libraries. You can check functions against NULL to see if they’re supported in the particular dynamic library that the code is currently running against. This seems to be part of the basic development model supported by Xcode. I hope this example is useful; it has helped put my mind at ease about this part of the Xcode design.

Leave a Comment