plugins marked with a '!' are handled as critical: cancel if loading fails
authorMartin Willi <martin@strongswan.org>
Tue, 1 Sep 2009 14:08:28 +0000 (16:08 +0200)
committerMartin Willi <martin@strongswan.org>
Tue, 1 Sep 2009 14:08:28 +0000 (16:08 +0200)
src/libstrongswan/plugins/plugin_loader.c
src/libstrongswan/plugins/plugin_loader.h

index 459ba9b..49e643f 100644 (file)
@@ -110,26 +110,45 @@ static plugin_t* load_plugin(private_plugin_loader_t *this,
 /**
  * Implementation of plugin_loader_t.load_plugins.
  */
-static int load(private_plugin_loader_t *this, char *path, char *list)
+static bool load(private_plugin_loader_t *this, char *path, char *list)
 {
-       plugin_t *plugin;
        enumerator_t *enumerator;
        char *token;
-       int count = 0;
+       bool critical_failed = FALSE;
        
        enumerator = enumerator_create_token(list, " ", " ");
-       while (enumerator->enumerate(enumerator, &token))
+       while (!critical_failed && enumerator->enumerate(enumerator, &token))
        {
+               plugin_t *plugin;
+               bool critical = FALSE;
+               int len;
+               
+               token = strdup(token);
+               len = strlen(token);
+               if (token[len-1] == '!')
+               {
+                       critical = TRUE;
+                       token[len-1] = '\0';
+               }
                plugin = load_plugin(this, path, token);
                if (plugin)
-               {       /* insert in front to destroy them in reverse order */
+               {
+                       /* insert in front to destroy them in reverse order */
                        this->plugins->insert_last(this->plugins, plugin);
-                       this->names->insert_last(this->names, strdup(token));
-                       count++;
+                       this->names->insert_last(this->names, token);
+               }
+               else
+               {
+                       if (critical)
+                       {
+                               critical_failed = TRUE;
+                               DBG1("loading critical plugin '%s' failed", token);
+                       }
+                       free(token);
                }
        }
        enumerator->destroy(enumerator);
-       return count;
+       return !critical_failed;
 }
 
 /**
@@ -176,7 +195,7 @@ plugin_loader_t *plugin_loader_create()
 {
        private_plugin_loader_t *this = malloc_thing(private_plugin_loader_t);
        
-       this->public.load = (int(*)(plugin_loader_t*, char *path, char *prefix))load;
+       this->public.load = (bool(*)(plugin_loader_t*, char *path, char *prefix))load;
        this->public.unload = (void(*)(plugin_loader_t*))unload;
        this->public.create_plugin_enumerator = (enumerator_t*(*)(plugin_loader_t*))create_plugin_enumerator;
        this->public.destroy = (void(*)(plugin_loader_t*))destroy;
index 6230f9d..3429e92 100644 (file)
@@ -33,11 +33,15 @@ struct plugin_loader_t {
        /**
         * Load a list of plugins from a directory.
         *
+        * Each plugin in list may have a ending exclamation mark (!) to mark it
+        * as a critical plugin. If loading a critical plugin fails, plugin loading
+        * is aborted and FALSE is returned.
+        *
         * @param path                  path containing loadable plugins
         * @param list                  space separated list of plugins to load
-        * @return                              number of successfully loaded plugins
+        * @return                              TRUE if all critical plugins loaded successfully
         */
-       int (*load)(plugin_loader_t *this, char *path, char *list);
+       bool (*load)(plugin_loader_t *this, char *path, char *list);
        
        /**
         * Unload all loaded plugins.
@@ -52,9 +56,9 @@ struct plugin_loader_t {
        enumerator_t* (*create_plugin_enumerator)(plugin_loader_t *this);
        
        /**
-     * Unload loaded plugins, destroy plugin_loader instance.
-     */
-    void (*destroy)(plugin_loader_t *this);
+        * Unload loaded plugins, destroy plugin_loader instance.
+        */
+       void (*destroy)(plugin_loader_t *this);
 };
 
 /**