diff options
Diffstat (limited to 'src/util/plugin.c')
-rw-r--r-- | src/util/plugin.c | 244 |
1 files changed, 123 insertions, 121 deletions
diff --git a/src/util/plugin.c b/src/util/plugin.c index 2b11e5c3c..bb310ada8 100644 --- a/src/util/plugin.c +++ b/src/util/plugin.c | |||
@@ -28,12 +28,13 @@ | |||
28 | #include <ltdl.h> | 28 | #include <ltdl.h> |
29 | #include "gnunet_util_lib.h" | 29 | #include "gnunet_util_lib.h" |
30 | 30 | ||
31 | #define LOG(kind, ...) GNUNET_log_from(kind, "util-plugin", __VA_ARGS__) | 31 | #define LOG(kind, ...) GNUNET_log_from (kind, "util-plugin", __VA_ARGS__) |
32 | 32 | ||
33 | /** | 33 | /** |
34 | * Linked list of active plugins. | 34 | * Linked list of active plugins. |
35 | */ | 35 | */ |
36 | struct PluginList { | 36 | struct PluginList |
37 | { | ||
37 | /** | 38 | /** |
38 | * This is a linked list. | 39 | * This is a linked list. |
39 | */ | 40 | */ |
@@ -71,40 +72,40 @@ static struct PluginList *plugins; | |||
71 | * Setup libtool paths. | 72 | * Setup libtool paths. |
72 | */ | 73 | */ |
73 | static void | 74 | static void |
74 | plugin_init() | 75 | plugin_init () |
75 | { | 76 | { |
76 | int err; | 77 | int err; |
77 | const char *opath; | 78 | const char *opath; |
78 | char *path; | 79 | char *path; |
79 | char *cpath; | 80 | char *cpath; |
80 | 81 | ||
81 | err = lt_dlinit(); | 82 | err = lt_dlinit (); |
82 | if (err > 0) | 83 | if (err > 0) |
83 | { | 84 | { |
84 | fprintf(stderr, | 85 | fprintf (stderr, |
85 | _("Initialization of plugin mechanism failed: %s!\n"), | 86 | _ ("Initialization of plugin mechanism failed: %s!\n"), |
86 | lt_dlerror()); | 87 | lt_dlerror ()); |
87 | return; | 88 | return; |
88 | } | 89 | } |
89 | opath = lt_dlgetsearchpath(); | 90 | opath = lt_dlgetsearchpath (); |
90 | if (NULL != opath) | 91 | if (NULL != opath) |
91 | old_dlsearchpath = GNUNET_strdup(opath); | 92 | old_dlsearchpath = GNUNET_strdup (opath); |
92 | path = GNUNET_OS_installation_get_path(GNUNET_OS_IPK_LIBDIR); | 93 | path = GNUNET_OS_installation_get_path (GNUNET_OS_IPK_LIBDIR); |
93 | if (NULL != path) | 94 | if (NULL != path) |
95 | { | ||
96 | if (NULL != opath) | ||
94 | { | 97 | { |
95 | if (NULL != opath) | 98 | GNUNET_asprintf (&cpath, "%s:%s", opath, path); |
96 | { | 99 | lt_dlsetsearchpath (cpath); |
97 | GNUNET_asprintf(&cpath, "%s:%s", opath, path); | 100 | GNUNET_free (path); |
98 | lt_dlsetsearchpath(cpath); | 101 | GNUNET_free (cpath); |
99 | GNUNET_free(path); | ||
100 | GNUNET_free(cpath); | ||
101 | } | ||
102 | else | ||
103 | { | ||
104 | lt_dlsetsearchpath(path); | ||
105 | GNUNET_free(path); | ||
106 | } | ||
107 | } | 102 | } |
103 | else | ||
104 | { | ||
105 | lt_dlsetsearchpath (path); | ||
106 | GNUNET_free (path); | ||
107 | } | ||
108 | } | ||
108 | } | 109 | } |
109 | 110 | ||
110 | 111 | ||
@@ -112,15 +113,15 @@ plugin_init() | |||
112 | * Shutdown libtool. | 113 | * Shutdown libtool. |
113 | */ | 114 | */ |
114 | static void | 115 | static void |
115 | plugin_fini() | 116 | plugin_fini () |
116 | { | 117 | { |
117 | lt_dlsetsearchpath(old_dlsearchpath); | 118 | lt_dlsetsearchpath (old_dlsearchpath); |
118 | if (NULL != old_dlsearchpath) | 119 | if (NULL != old_dlsearchpath) |
119 | { | 120 | { |
120 | GNUNET_free(old_dlsearchpath); | 121 | GNUNET_free (old_dlsearchpath); |
121 | old_dlsearchpath = NULL; | 122 | old_dlsearchpath = NULL; |
122 | } | 123 | } |
123 | lt_dlexit(); | 124 | lt_dlexit (); |
124 | } | 125 | } |
125 | 126 | ||
126 | 127 | ||
@@ -132,22 +133,22 @@ plugin_fini() | |||
132 | * @return NULL if the symbol was not found | 133 | * @return NULL if the symbol was not found |
133 | */ | 134 | */ |
134 | static GNUNET_PLUGIN_Callback | 135 | static GNUNET_PLUGIN_Callback |
135 | resolve_function(struct PluginList *plug, const char *name) | 136 | resolve_function (struct PluginList *plug, const char *name) |
136 | { | 137 | { |
137 | char *initName; | 138 | char *initName; |
138 | void *mptr; | 139 | void *mptr; |
139 | 140 | ||
140 | GNUNET_asprintf(&initName, "_%s_%s", plug->name, name); | 141 | GNUNET_asprintf (&initName, "_%s_%s", plug->name, name); |
141 | mptr = lt_dlsym(plug->handle, &initName[1]); | 142 | mptr = lt_dlsym (plug->handle, &initName[1]); |
142 | if (NULL == mptr) | 143 | if (NULL == mptr) |
143 | mptr = lt_dlsym(plug->handle, initName); | 144 | mptr = lt_dlsym (plug->handle, initName); |
144 | if (NULL == mptr) | 145 | if (NULL == mptr) |
145 | LOG(GNUNET_ERROR_TYPE_ERROR, | 146 | LOG (GNUNET_ERROR_TYPE_ERROR, |
146 | _("`%s' failed to resolve method '%s' with error: %s\n"), | 147 | _ ("`%s' failed to resolve method '%s' with error: %s\n"), |
147 | "lt_dlsym", | 148 | "lt_dlsym", |
148 | &initName[1], | 149 | &initName[1], |
149 | lt_dlerror()); | 150 | lt_dlerror ()); |
150 | GNUNET_free(initName); | 151 | GNUNET_free (initName); |
151 | return mptr; | 152 | return mptr; |
152 | } | 153 | } |
153 | 154 | ||
@@ -162,30 +163,30 @@ resolve_function(struct PluginList *plug, const char *name) | |||
162 | * @return #GNUNET_YES if the plugin exists, #GNUNET_NO if not | 163 | * @return #GNUNET_YES if the plugin exists, #GNUNET_NO if not |
163 | */ | 164 | */ |
164 | int | 165 | int |
165 | GNUNET_PLUGIN_test(const char *library_name) | 166 | GNUNET_PLUGIN_test (const char *library_name) |
166 | { | 167 | { |
167 | void *libhandle; | 168 | void *libhandle; |
168 | GNUNET_PLUGIN_Callback init; | 169 | GNUNET_PLUGIN_Callback init; |
169 | struct PluginList plug; | 170 | struct PluginList plug; |
170 | 171 | ||
171 | if (!initialized) | 172 | if (! initialized) |
172 | { | 173 | { |
173 | initialized = GNUNET_YES; | 174 | initialized = GNUNET_YES; |
174 | plugin_init(); | 175 | plugin_init (); |
175 | } | 176 | } |
176 | libhandle = lt_dlopenext(library_name); | 177 | libhandle = lt_dlopenext (library_name); |
177 | if (NULL == libhandle) | 178 | if (NULL == libhandle) |
178 | return GNUNET_NO; | 179 | return GNUNET_NO; |
179 | plug.handle = libhandle; | 180 | plug.handle = libhandle; |
180 | plug.name = (char *)library_name; | 181 | plug.name = (char *) library_name; |
181 | init = resolve_function(&plug, "init"); | 182 | init = resolve_function (&plug, "init"); |
182 | if (NULL == init) | 183 | if (NULL == init) |
183 | { | 184 | { |
184 | GNUNET_break(0); | 185 | GNUNET_break (0); |
185 | lt_dlclose(libhandle); | 186 | lt_dlclose (libhandle); |
186 | return GNUNET_NO; | 187 | return GNUNET_NO; |
187 | } | 188 | } |
188 | lt_dlclose(libhandle); | 189 | lt_dlclose (libhandle); |
189 | return GNUNET_YES; | 190 | return GNUNET_YES; |
190 | } | 191 | } |
191 | 192 | ||
@@ -203,42 +204,42 @@ GNUNET_PLUGIN_test(const char *library_name) | |||
203 | * @return whatever the initialization function returned | 204 | * @return whatever the initialization function returned |
204 | */ | 205 | */ |
205 | void * | 206 | void * |
206 | GNUNET_PLUGIN_load(const char *library_name, void *arg) | 207 | GNUNET_PLUGIN_load (const char *library_name, void *arg) |
207 | { | 208 | { |
208 | void *libhandle; | 209 | void *libhandle; |
209 | struct PluginList *plug; | 210 | struct PluginList *plug; |
210 | GNUNET_PLUGIN_Callback init; | 211 | GNUNET_PLUGIN_Callback init; |
211 | void *ret; | 212 | void *ret; |
212 | 213 | ||
213 | if (!initialized) | 214 | if (! initialized) |
214 | { | 215 | { |
215 | initialized = GNUNET_YES; | 216 | initialized = GNUNET_YES; |
216 | plugin_init(); | 217 | plugin_init (); |
217 | } | 218 | } |
218 | libhandle = lt_dlopenext(library_name); | 219 | libhandle = lt_dlopenext (library_name); |
219 | if (libhandle == NULL) | 220 | if (libhandle == NULL) |
220 | { | 221 | { |
221 | LOG(GNUNET_ERROR_TYPE_ERROR, | 222 | LOG (GNUNET_ERROR_TYPE_ERROR, |
222 | _("`%s' failed for library `%s' with error: %s\n"), | 223 | _ ("`%s' failed for library `%s' with error: %s\n"), |
223 | "lt_dlopenext", | 224 | "lt_dlopenext", |
224 | library_name, | 225 | library_name, |
225 | lt_dlerror()); | 226 | lt_dlerror ()); |
226 | return NULL; | 227 | return NULL; |
227 | } | 228 | } |
228 | plug = GNUNET_new(struct PluginList); | 229 | plug = GNUNET_new (struct PluginList); |
229 | plug->handle = libhandle; | 230 | plug->handle = libhandle; |
230 | plug->name = GNUNET_strdup(library_name); | 231 | plug->name = GNUNET_strdup (library_name); |
231 | plug->next = plugins; | 232 | plug->next = plugins; |
232 | plugins = plug; | 233 | plugins = plug; |
233 | init = resolve_function(plug, "init"); | 234 | init = resolve_function (plug, "init"); |
234 | if ((init == NULL) || (NULL == (ret = init(arg)))) | 235 | if ((init == NULL) || (NULL == (ret = init (arg)))) |
235 | { | 236 | { |
236 | lt_dlclose(libhandle); | 237 | lt_dlclose (libhandle); |
237 | GNUNET_free(plug->name); | 238 | GNUNET_free (plug->name); |
238 | plugins = plug->next; | 239 | plugins = plug->next; |
239 | GNUNET_free(plug); | 240 | GNUNET_free (plug); |
240 | return NULL; | 241 | return NULL; |
241 | } | 242 | } |
242 | return ret; | 243 | return ret; |
243 | } | 244 | } |
244 | 245 | ||
@@ -252,7 +253,7 @@ GNUNET_PLUGIN_load(const char *library_name, void *arg) | |||
252 | * @return whatever the shutdown function returned | 253 | * @return whatever the shutdown function returned |
253 | */ | 254 | */ |
254 | void * | 255 | void * |
255 | GNUNET_PLUGIN_unload(const char *library_name, void *arg) | 256 | GNUNET_PLUGIN_unload (const char *library_name, void *arg) |
256 | { | 257 | { |
257 | struct PluginList *pos; | 258 | struct PluginList *pos; |
258 | struct PluginList *prev; | 259 | struct PluginList *prev; |
@@ -261,30 +262,30 @@ GNUNET_PLUGIN_unload(const char *library_name, void *arg) | |||
261 | 262 | ||
262 | prev = NULL; | 263 | prev = NULL; |
263 | pos = plugins; | 264 | pos = plugins; |
264 | while ((NULL != pos) && (0 != strcmp(pos->name, library_name))) | 265 | while ((NULL != pos) && (0 != strcmp (pos->name, library_name))) |
265 | { | 266 | { |
266 | prev = pos; | 267 | prev = pos; |
267 | pos = pos->next; | 268 | pos = pos->next; |
268 | } | 269 | } |
269 | if (NULL == pos) | 270 | if (NULL == pos) |
270 | return NULL; | 271 | return NULL; |
271 | 272 | ||
272 | done = resolve_function(pos, "done"); | 273 | done = resolve_function (pos, "done"); |
273 | ret = NULL; | 274 | ret = NULL; |
274 | if (NULL != done) | 275 | if (NULL != done) |
275 | ret = done(arg); | 276 | ret = done (arg); |
276 | if (NULL == prev) | 277 | if (NULL == prev) |
277 | plugins = pos->next; | 278 | plugins = pos->next; |
278 | else | 279 | else |
279 | prev->next = pos->next; | 280 | prev->next = pos->next; |
280 | lt_dlclose(pos->handle); | 281 | lt_dlclose (pos->handle); |
281 | GNUNET_free(pos->name); | 282 | GNUNET_free (pos->name); |
282 | GNUNET_free(pos); | 283 | GNUNET_free (pos); |
283 | if (NULL == plugins) | 284 | if (NULL == plugins) |
284 | { | 285 | { |
285 | plugin_fini(); | 286 | plugin_fini (); |
286 | initialized = GNUNET_NO; | 287 | initialized = GNUNET_NO; |
287 | } | 288 | } |
288 | return ret; | 289 | return ret; |
289 | } | 290 | } |
290 | 291 | ||
@@ -292,7 +293,8 @@ GNUNET_PLUGIN_unload(const char *library_name, void *arg) | |||
292 | /** | 293 | /** |
293 | * Closure for #find_libraries(). | 294 | * Closure for #find_libraries(). |
294 | */ | 295 | */ |
295 | struct LoadAllContext { | 296 | struct LoadAllContext |
297 | { | ||
296 | /** | 298 | /** |
297 | * Prefix the plugin names we find have to match. | 299 | * Prefix the plugin names we find have to match. |
298 | */ | 300 | */ |
@@ -325,7 +327,7 @@ struct LoadAllContext { | |||
325 | * @return #GNUNET_OK (continue loading) | 327 | * @return #GNUNET_OK (continue loading) |
326 | */ | 328 | */ |
327 | static int | 329 | static int |
328 | find_libraries(void *cls, const char *filename) | 330 | find_libraries (void *cls, const char *filename) |
329 | { | 331 | { |
330 | struct LoadAllContext *lac = cls; | 332 | struct LoadAllContext *lac = cls; |
331 | const char *slashpos; | 333 | const char *slashpos; |
@@ -336,20 +338,20 @@ find_libraries(void *cls, const char *filename) | |||
336 | size_t n; | 338 | size_t n; |
337 | 339 | ||
338 | libname = filename; | 340 | libname = filename; |
339 | while (NULL != (slashpos = strstr(libname, DIR_SEPARATOR_STR))) | 341 | while (NULL != (slashpos = strstr (libname, DIR_SEPARATOR_STR))) |
340 | libname = slashpos + 1; | 342 | libname = slashpos + 1; |
341 | n = strlen(libname); | 343 | n = strlen (libname); |
342 | if (0 != strncmp(lac->basename, libname, strlen(lac->basename))) | 344 | if (0 != strncmp (lac->basename, libname, strlen (lac->basename))) |
343 | return GNUNET_OK; /* wrong name */ | 345 | return GNUNET_OK; /* wrong name */ |
344 | if ((n > 3) && (0 == strcmp(&libname[n - 3], ".la"))) | 346 | if ((n > 3) && (0 == strcmp (&libname[n - 3], ".la"))) |
345 | return GNUNET_OK; /* .la file */ | 347 | return GNUNET_OK; /* .la file */ |
346 | basename = GNUNET_strdup(libname); | 348 | basename = GNUNET_strdup (libname); |
347 | if (NULL != (dot = strstr(basename, "."))) | 349 | if (NULL != (dot = strstr (basename, "."))) |
348 | *dot = '\0'; | 350 | *dot = '\0'; |
349 | lib_ret = GNUNET_PLUGIN_load(basename, lac->arg); | 351 | lib_ret = GNUNET_PLUGIN_load (basename, lac->arg); |
350 | if (NULL != lib_ret) | 352 | if (NULL != lib_ret) |
351 | lac->cb(lac->cb_cls, basename, lib_ret); | 353 | lac->cb (lac->cb_cls, basename, lib_ret); |
352 | GNUNET_free(basename); | 354 | GNUNET_free (basename); |
353 | return GNUNET_OK; | 355 | return GNUNET_OK; |
354 | } | 356 | } |
355 | 357 | ||
@@ -367,27 +369,27 @@ find_libraries(void *cls, const char *filename) | |||
367 | * @param cb_cls closure for @a cb | 369 | * @param cb_cls closure for @a cb |
368 | */ | 370 | */ |
369 | void | 371 | void |
370 | GNUNET_PLUGIN_load_all(const char *basename, | 372 | GNUNET_PLUGIN_load_all (const char *basename, |
371 | void *arg, | 373 | void *arg, |
372 | GNUNET_PLUGIN_LoaderCallback cb, | 374 | GNUNET_PLUGIN_LoaderCallback cb, |
373 | void *cb_cls) | 375 | void *cb_cls) |
374 | { | 376 | { |
375 | struct LoadAllContext lac; | 377 | struct LoadAllContext lac; |
376 | char *path; | 378 | char *path; |
377 | 379 | ||
378 | path = GNUNET_OS_installation_get_path(GNUNET_OS_IPK_LIBDIR); | 380 | path = GNUNET_OS_installation_get_path (GNUNET_OS_IPK_LIBDIR); |
379 | if (NULL == path) | 381 | if (NULL == path) |
380 | { | 382 | { |
381 | GNUNET_log(GNUNET_ERROR_TYPE_ERROR, | 383 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, |
382 | _("Could not determine plugin installation path.\n")); | 384 | _ ("Could not determine plugin installation path.\n")); |
383 | return; | 385 | return; |
384 | } | 386 | } |
385 | lac.basename = basename; | 387 | lac.basename = basename; |
386 | lac.arg = arg; | 388 | lac.arg = arg; |
387 | lac.cb = cb; | 389 | lac.cb = cb; |
388 | lac.cb_cls = cb_cls; | 390 | lac.cb_cls = cb_cls; |
389 | GNUNET_DISK_directory_scan(path, &find_libraries, &lac); | 391 | GNUNET_DISK_directory_scan (path, &find_libraries, &lac); |
390 | GNUNET_free(path); | 392 | GNUNET_free (path); |
391 | } | 393 | } |
392 | 394 | ||
393 | 395 | ||