]> git.sesse.net Git - vlc/commitdiff
Read configuration file in a single pass (instead of one per module).
authorRémi Denis-Courmont <rem@videolan.org>
Wed, 22 Nov 2006 21:58:42 +0000 (21:58 +0000)
committerRémi Denis-Courmont <rem@videolan.org>
Wed, 22 Nov 2006 21:58:42 +0000 (21:58 +0000)
(I get about hundred time faster config load here, but right, there are
 much slower operations in libvlc startup anyway
 -- and the plugin cache breakage is not going to help).

src/misc/configuration.c

index cd4774e6bb3fa54301edc9de44c57d6ebea917c1..86e7cfa66478eef7e85745c238a0da114d82d2fa 100644 (file)
@@ -808,8 +808,6 @@ int __config_LoadConfigFile( vlc_object_t *p_this, const char *psz_module_name )
 {
     vlc_list_t *p_list;
     FILE *file;
-    char *p_index;
-    int i_index;
 
     file = config_OpenConfigFile (p_this, "rt");
     if (file == NULL)
@@ -821,152 +819,142 @@ int __config_LoadConfigFile( vlc_object_t *p_this, const char *psz_module_name )
     /* Look for the selected module, if NULL then save everything */
     p_list = vlc_list_find( p_this, VLC_OBJECT_MODULE, FIND_ANYWHERE );
 
-    for( i_index = 0; i_index < p_list->i_count; i_index++ )
+    /* Look for UTF-8 Byte Order Mark */
+    char * (*convert) (const char *) = strdupnull;
+    char bom[3];
+
+    if ((fread (bom, 1, 3, file) != 3)
+     || memcmp (bom, "\xEF\xBB\xBF", 3))
     {
-        module_t *p_parser = (module_t *)p_list->p_values[i_index].p_object ;
-        char line[1024];
+        convert = FromLocaleDup;
+        rewind (file); // no BOM, rewind
+    }
+
+    module_t *module = NULL;
+    char line[1024], section[1022];
+    section[0] = '\0';
 
-        if( psz_module_name
-             && strcmp( psz_module_name, p_parser->psz_object_name ) )
+    while (fgets (line, 1024, file) != NULL)
+    {
+        // Ignore comments and empty lines
+        switch (line[0])
         {
-            continue;
+            case '#':
+            case '\n':
+            case '\0':
+                continue;
         }
 
-        /* The config file is organized in sections, one per module. Look for
-         * the interesting section ( a section is of the form [foo] ) */
-        fseek( file, 0L, SEEK_SET );
+        if (line[0] == '[')
+        {
+            char *ptr = strchr (line, ']');
+            if (ptr == NULL)
+                continue; // syntax error;
+            *ptr = '\0';
 
-        /* Look for UTF-8 Byte Order Mark */
-        char * (*convert) (const char *) = FromLocaleDup;
-        char bom[3];
+            // New section ( = a given module)
+            strcpy (section, line + 1);
+            module = NULL;
 
-        if ((fread (bom, 1, 3, file) == 3)
-         && (memcmp (bom, "\xEF\xBB\xBF", 3) == 0))
-            convert = strdupnull;
-        else
-            rewind (file); // no BOM, rewind
-
-        while( fgets( line, 1024, file ) )
-        {
-            if( (line[0] == '[')
-               && (p_index = strchr(line,']'))
-               && (p_index - &line[1]
-                    == (int)strlen(p_parser->psz_object_name))
-               && !memcmp( &line[1], p_parser->psz_object_name,
-                           strlen(p_parser->psz_object_name) ) )
+            if ((psz_module_name == NULL)
+             || (strcmp (psz_module_name, section) == 0))
             {
-#if 0
-                msg_Dbg( p_this, "loading config for module \"%s\"",
-                                 p_parser->psz_object_name );
-#endif
+                for (int i = 0; i < p_list->i_count; i++)
+                {
+                    module_t *m = (module_t *)p_list->p_values[i].p_object;
 
-                break;
+                    if ((strcmp (section, m->psz_object_name) == 0)
+                     && (m->i_config_items > 0)) // ignore config-less modules
+                    {
+                        module = m;
+                        if (psz_module_name != NULL)
+                            msg_Dbg (p_this,
+                                     "loading config for module \"%s\"",
+                                     section);
+                        break;
+                    }
+                }
             }
+
+            continue;
         }
-        /* either we found the section or we're at the EOF */
 
-        /* Now try to load the options in this section */
-        while( fgets( line, 1024, file ) )
-        {
-            const char *psz_option_name, *psz_option_value;
-            module_config_t *p_item, *p_end;
+        if (module == NULL)
+            continue; // no need to parse if there is no matching module
 
-            if( line[0] == '[' ) break; /* end of section */
+        char *ptr = strchr (line, '\n');
+        if (ptr != NULL)
+            *ptr = '\0';
 
-            /* ignore comments or empty lines */
-            if( (line[0] == '#') || (line[0] == '\n') || (line[0] == (char)0) )
-                continue;
+        /* look for option name */
+        const char *psz_option_name = line;
 
-            /* get rid of line feed */
-            if( line[strlen(line)-1] == '\n' )
-                line[strlen(line)-1] = (char)0;
+        ptr = strchr (line, '=');
+        if (ptr == NULL)
+            continue; // syntax error
 
-            /* look for option name */
-            psz_option_name = line;
-            psz_option_value = NULL;
-            p_index = strchr( line, '=' );
-            if( !p_index ) break; /* this ain't an option!!! */
+        *ptr = '\0';
+        const char *psz_option_value = ptr + 1;
 
-            *p_index = (char)0;
-            psz_option_value = p_index + 1;
+        /* try to match this option with one of the module's options */
+        for (size_t i = 0; i < module->confsize; i++)
+        {
+            module_config_t *p_item = module->p_config + i;
 
-            if( !p_parser->i_config_items )
-            {
+            if ((p_item->i_type & CONFIG_HINT)
+             || strcmp (p_item->psz_name, psz_option_name))
                 continue;
-            }
 
-            /* try to match this option with one of the module's options */
-            for( p_item = p_parser->p_config, p_end = p_item + p_parser->confsize;
-                 p_item < p_end;
-                 p_item++ )
+            /* We found it */
+            switch( p_item->i_type )
             {
-                if( p_item->i_type & CONFIG_HINT )
-                    /* ignore hints */
-                    continue;
+                case CONFIG_ITEM_BOOL:
+                case CONFIG_ITEM_INTEGER:
+                    if( !*psz_option_value )
+                        break;                    /* ignore empty option */
+                    p_item->value.i = strtol( psz_option_value, 0, 0 );
+                    p_item->saved.i = p_item->value.i;
 
-                if( !strcmp( p_item->psz_name, psz_option_name ) )
-                {
-                    /* We found it */
-                    switch( p_item->i_type )
-                    {
-                    case CONFIG_ITEM_BOOL:
-                    case CONFIG_ITEM_INTEGER:
-                        if( !*psz_option_value )
-                            break;                    /* ignore empty option */
-                        p_item->value.i = strtol( psz_option_value, 0, 0 );
-                        p_item->saved.i = p_item->value.i;
-#if 0
-                        msg_Dbg( p_this, "option \"%s\", value %i",
-                                 p_item->psz_name, p_item->i_value );
-#endif
-                        break;
+                    /*msg_Dbg (p_this, "option \"%s\", value %i",
+                             psz_option_name, p_item->value.i);*/
+                    break;
 
-                    case CONFIG_ITEM_FLOAT:
-                        if( !*psz_option_value )
-                            break;                    /* ignore empty option */
-                        p_item->value.f = (float)i18n_atof( psz_option_value);
-                        p_item->saved.f = p_item->value.f;
-#if 0
-                        msg_Dbg( p_this, "option \"%s\", value %f",
-                                 p_item->psz_name, (double)p_item->f_value );
-#endif
-                        break;
-                    case CONFIG_ITEM_KEY:
-                        if( !*psz_option_value )
-                            break;                    /* ignore empty option */
-                        p_item->value.i = ConfigStringToKey(psz_option_value);
-                        p_item->saved.i = p_item->value.i;
-                        break;
+                case CONFIG_ITEM_FLOAT:
+                    if( !*psz_option_value )
+                        break;                    /* ignore empty option */
+                    p_item->value.f = (float)i18n_atof( psz_option_value);
+                    p_item->saved.f = p_item->value.f;
 
-                    default:
-                        vlc_mutex_lock( p_item->p_lock );
+                    /*msg_Dbg (p_this, "option \"%s\", value %f",
+                             psz_option_name, (double)p_item->value.f);*/
+                    break;
 
-                        /* free old string */
-                        freenull (p_item->value.psz);
+                case CONFIG_ITEM_KEY:
+                    if( !*psz_option_value )
+                        break;                    /* ignore empty option */
+                    p_item->value.i = ConfigStringToKey(psz_option_value);
+                    p_item->saved.i = p_item->value.i;
+                    break;
 
-                        p_item->value.psz = convert (psz_option_value);
+                default:
+                    vlc_mutex_lock( p_item->p_lock );
 
-                        freenull (p_item->saved.psz);
-                        p_item->saved.psz = NULL;
+                    /* free old string */
+                    free (p_item->value.psz);
+                    free (p_item->saved.psz);
 
-                        if( !p_item->value.psz || !p_item->orig.psz ||
-                            (p_item->value.psz && p_item->orig.psz &&
-                             strcmp(p_item->value.psz, p_item->orig.psz)))
-                            p_item->saved.psz = convert (p_item->value.psz);
+                    p_item->value.psz = convert (psz_option_value);
+                    p_item->saved.psz = strdupnull (p_item->value.psz);
 
-                        vlc_mutex_unlock( p_item->p_lock );
+                    vlc_mutex_unlock( p_item->p_lock );
 
-#if 0
-                        msg_Dbg( p_this, "option \"%s\", value \"%s\"",
-                                 p_item->psz_name,
-                                 p_item->psz_value ? p_item->psz_value : "" );
-#endif
-                        break;
-                    }
-                }
+                    /*msg_Dbg (p_this, "option \"%s\", value \"%s\"",
+                             psz_option_name, psz_option_value ?: "");*/
+                    break;
             }
-        }
 
+            break;
+        }
     }
 
     vlc_list_release( p_list );