diff options
author | cbdev <cb@cbcdn.com> | 2020-04-21 00:13:51 +0200 |
---|---|---|
committer | cbdev <cb@cbcdn.com> | 2020-04-21 00:13:51 +0200 |
commit | 918fb606174dcf42553be65e3d2306996c52488f (patch) | |
tree | 98d0bc185c5d9cd2c0f3bbe6b0461ebbf1c8f502 | |
parent | 8773fca1f7d2ffed68b6af4967b537d989a1e5b5 (diff) | |
download | midimonster-918fb606174dcf42553be65e3d2306996c52488f.tar.gz midimonster-918fb606174dcf42553be65e3d2306996c52488f.tar.bz2 midimonster-918fb606174dcf42553be65e3d2306996c52488f.zip |
Implement recursive configuration file parsing (Fixes #59)
-rw-r--r-- | README.md | 4 | ||||
-rw-r--r-- | config.c | 25 | ||||
-rw-r--r-- | midimonster.c | 2 |
3 files changed, 28 insertions, 3 deletions
@@ -76,6 +76,10 @@ lines of the form `option = value`. Lines starting with a semicolon are treated as comments and ignored. Inline comments are not currently supported. +Configuration files may be included recursively in other configuration files using +the syntax `[include <file>]`. This will read the referenced configuration file as +if it were inserted at that point. + Example configuration files may be found in [configs/](configs/). ### Backend and instance configuration @@ -2,6 +2,11 @@ #include <ctype.h> #include <unistd.h> #include <errno.h> +#ifndef _WIN32 +#include <linux/limits.h> +#endif + +#define BACKEND_NAME "core/cfg" #include "midimonster.h" #include "config.h" #include "backend.h" @@ -349,6 +354,10 @@ static int config_line(char* line){ } } } + else if(!strncmp(line, "[include ", 9)){ + line[strlen(line) - 1] = 0; + return config_read(line + 9); + } else if(!strcmp(line, "[map]")){ //mapping configuration parser_state = map; @@ -493,7 +502,7 @@ int config_read(char* cfg_filepath){ char* line_raw = NULL; //create heap copy of file name because original might be in readonly memory - char* source_dir = strdup(cfg_filepath), *source_file = NULL; + char* source_dir = strdup(cfg_filepath), *source_file = NULL, original_dir[PATH_MAX * 2] = ""; #ifdef _WIN32 char path_separator = '\\'; #else @@ -510,6 +519,12 @@ int config_read(char* cfg_filepath){ if(source_file){ *source_file = 0; source_file++; + + if(!getcwd(original_dir, sizeof(original_dir))){ + fprintf(stderr, "Failed to read current working directory: %s\n", strerror(errno)); + goto bail; + } + if(chdir(source_dir)){ fprintf(stderr, "Failed to change to configuration file directory %s: %s\n", source_dir, strerror(errno)); goto bail; @@ -519,10 +534,11 @@ int config_read(char* cfg_filepath){ source_file = source_dir; } + fprintf(stderr, "Reading configuration file %s\n", cfg_filepath); source = fopen(source_file, "r"); if(!source){ - fprintf(stderr, "Failed to open configuration file for reading\n"); + fprintf(stderr, "Failed to open %s for reading\n", cfg_filepath); goto bail; } @@ -536,6 +552,11 @@ int config_read(char* cfg_filepath){ rv = 0; bail: + //change back to previous directory to allow recursive configuration file parsing + if(source_file && source_dir != source_file){ + chdir(original_dir); + } + free(source_dir); if(source){ fclose(source); diff --git a/midimonster.c b/midimonster.c index 8100607..1065e5c 100644 --- a/midimonster.c +++ b/midimonster.c @@ -482,7 +482,7 @@ int main(int argc, char** argv){ //read config if(config_read(cfg_file)){ - fprintf(stderr, "Failed to read configuration file %s\n", cfg_file); + fprintf(stderr, "Failed to parse master configuration file %s\n", cfg_file); backends_stop(); routing_cleanup(); fds_free(); |