Imagine that you have an application with a plugin based architecture, where each plugin is a *.so file that is dynamically loaded with dlopen().
The main application can refer to symbols via dlsym(), and so it may call functions of the plugin. How can the plugin call functions of the main application?
I know that the main application could provide a struct full of function pointers, which the plugin could use to call into the application. Is there any easier way than that?
Edit: here's a minimal working example to show what I mean:
app.h:
#ifndef APP_H
#define APP_H
void app_utility(void);
#endif
app.c:
#include <dlfcn.h>
#include <stdio.h>
#include <stdlib.h>
#include "app.h"
void app_utility(void)
{
printf("app_utility()\n");
}
int main(int argc, char **argv)
{
void *handle;
void (*plugin_function)(void);
if (argc < 2) {
fprintf(stderr, "usage: ./app plugin.so\n");
exit(1);
}
handle = dlopen(argv[1], RTLD_NOW | RTLD_LOCAL);
if (!handle) {
fprintf(stderr, "error loading plugin: %s\n", dlerror());
exit(1);
}
plugin_function = dlsym(handle, "doit");
if (!plugin_function) {
fprintf(stderr, "error loading symbol: %s\n", dlerror());
dlclose(handle);
exit(1);
}
plugin_function();
dlclose(handle);
return 0;
}
plugin.c:
#include <stdio.h>
#include "app.h"
void doit(void)
{
printf("doit()\n");
app_utility();
printf("did it!\n");
}
Example usage:
$ gcc -o app app.c -ldl
$ gcc -shared -o plugin.so
$ ./app ./plugin.so
error loading plugin: ./plugin.so: undefined symbol: app_utility