summaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/config.c78
-rw-r--r--src/config.y33
-rw-r--r--src/fastd.h2
-rw-r--r--src/peer.c9
-rw-r--r--src/peer.h1
5 files changed, 86 insertions, 37 deletions
diff --git a/src/config.c b/src/config.c
index 3f18ea0..2cf7494 100644
--- a/src/config.c
+++ b/src/config.c
@@ -135,7 +135,11 @@ void fastd_read_config_dir(fastd_context *ctx, fastd_config *conf, const char *d
fastd_peer_config_new(ctx, conf);
conf->peers->name = strdup(result->d_name);
- fastd_read_config(ctx, conf, result->d_name, true, depth);
+
+ if (!fastd_read_config(ctx, conf, result->d_name, true, depth)) {
+ pr_warn(ctx, "peer config %s will be ignored", result->d_name);
+ fastd_peer_config_delete(ctx, conf);
+ }
}
closedir(dirh);
@@ -144,40 +148,47 @@ void fastd_read_config_dir(fastd_context *ctx, fastd_config *conf, const char *d
free(oldcwd);
}
-void fastd_read_config(fastd_context *ctx, fastd_config *conf, const char *filename, bool peer_config, int depth) {
+bool fastd_read_config(fastd_context *ctx, fastd_config *conf, const char *filename, bool peer_config, int depth) {
if (depth >= MAX_CONFIG_DEPTH)
exit_error(ctx, "maximum config include depth exceeded");
+ bool ret = true;
+ char *oldcwd = get_current_dir_name();
+ char *filename2 = NULL;
+ char *dir = NULL;
FILE *file;
+ yyscan_t scanner;
+ fastd_config_pstate *ps;
+ fastd_config_str *strings = NULL;
+
+ fastd_config_yylex_init(&scanner);
+ ps = fastd_config_pstate_new();
+
if (!filename) {
file = stdin;
}
else {
file = fopen(filename, "r");
- if (!file)
- exit_error(ctx, "can't open config file `%s': %s", filename, strerror(errno));
+ if (!file) {
+ pr_error(ctx, "can't open config file `%s': %s", filename, strerror(errno));
+ ret = false;
+ goto end_free;
+ }
}
-
- char *oldcwd = get_current_dir_name();
-
- char *filename2 = NULL;
- char *dir = NULL;
+ fastd_config_yyset_in(file, scanner);
if (filename) {
filename2 = strdup(filename);
dir = dirname(filename2);
- if (chdir(dir))
- exit_error(ctx, "change from directory `%s' to `%s' failed", oldcwd, dir);
+ if (chdir(dir)) {
+ pr_error(ctx, "change from directory `%s' to `%s' failed", oldcwd, dir);
+ ret = false;
+ goto end_free;
+ }
}
- yyscan_t scanner;
- fastd_config_yylex_init(&scanner);
- fastd_config_yyset_in(file, scanner);
-
- fastd_config_pstate *ps = fastd_config_pstate_new();
-
int token;
YYSTYPE token_val;
YYLTYPE loc = {1, 0, 1, 0};
@@ -187,20 +198,29 @@ void fastd_read_config(fastd_context *ctx, fastd_config *conf, const char *filen
else
token = START_CONFIG;
- fastd_config_str *strings = NULL;
+ int parse_ret = fastd_config_push_parse(ps, token, &token_val, &loc, ctx, conf, filename, depth+1);
- while(fastd_config_push_parse(ps, token, &token_val, &loc, ctx, conf, filename, depth+1) == YYPUSH_MORE) {
+ while(parse_ret == YYPUSH_MORE) {
token = fastd_config_yylex(&token_val, &loc, scanner);
- if (token < 0)
- exit_error(ctx, "config error: %s at %s:%i:%i", token_val.error, filename, loc.first_line, loc.first_column);
+ if (token < 0) {
+ pr_error(ctx, "config error: %s at %s:%i:%i", token_val.error, filename, loc.first_line, loc.first_column);
+ ret = false;
+ goto end_free;
+ }
if (token == TOK_STRING) {
token_val.str->next = strings;
strings = token_val.str;
}
+
+ parse_ret = fastd_config_push_parse(ps, token, &token_val, &loc, ctx, conf, filename, depth+1);
}
+ if (parse_ret)
+ ret = false;
+
+ end_free:
fastd_config_str_free(strings);
fastd_config_pstate_delete(ps);
@@ -211,8 +231,10 @@ void fastd_read_config(fastd_context *ctx, fastd_config *conf, const char *filen
free(filename2);
free(oldcwd);
- if (filename)
+ if (filename && file)
fclose(file);
+
+ return ret;
}
#define IF_OPTION(args...) if(config_match(argv[i], args, NULL) && (++i))
@@ -258,16 +280,20 @@ void fastd_configure(fastd_context *ctx, fastd_config *conf, int argc, char *con
}
IF_OPTION_ARG("-c", "--config") {
+ const char *filename = arg;
if (!strcmp(arg, "-"))
- fastd_read_config(ctx, conf, NULL, false, 0);
- else
- fastd_read_config(ctx, conf, arg, false, 0);
+ filename = NULL;
+
+ if (!fastd_read_config(ctx, conf, filename, false, 0))
+ exit(1);
continue;
}
IF_OPTION_ARG("--config-peer") {
fastd_peer_config_new(ctx, conf);
- fastd_read_config(ctx, conf, arg, true, 0);
+
+ if(!fastd_read_config(ctx, conf, arg, true, 0))
+ exit(1);
continue;
}
diff --git a/src/config.y b/src/config.y
index cbb58c7..df46f20 100644
--- a/src/config.y
+++ b/src/config.y
@@ -174,14 +174,18 @@ mode: TOK_TAP { conf->mode = MODE_TAP; }
;
protocol: TOK_STRING {
- if (!strcmp($1->str, "null"))
+ if (!strcmp($1->str, "null")) {
conf->protocol = &fastd_protocol_null;
+ }
#ifdef WITH_PROTOCOL_ECFXP
- else if (!strcmp($1->str, "ecfxp"))
+ else if (!strcmp($1->str, "ecfxp")) {
conf->protocol = &fastd_protocol_ec25519_fhmqvc_xsalsa20_poly1305;
+ }
#endif
- else
- exit_error(ctx, "config error: invalid protocol `%s'", $1->str);
+ else {
+ fastd_config_error(&@$, ctx, conf, filename, depth, "invalid protocol");
+ YYERROR;
+ }
}
;
@@ -227,7 +231,10 @@ peer_address: TOK_ADDR ':' port {
peer_key: TOK_STRING { free(conf->peers->key); conf->peers->key = strdup($1->str); }
;
-peer_include: TOK_STRING { fastd_read_config(ctx, conf, $1->str, true, depth); }
+peer_include: TOK_STRING {
+ if (!fastd_read_config(ctx, conf, $1->str, true, depth))
+ YYERROR;
+ }
;
@@ -239,12 +246,16 @@ include: TOK_PEER TOK_STRING maybe_as {
fastd_peer_config_new(ctx, conf);
conf->peers->name = strdup($3->str);
- fastd_read_config(ctx, conf, $2->str, true, depth);
+ if (!fastd_read_config(ctx, conf, $2->str, true, depth))
+ YYERROR;
}
| TOK_PEERS TOK_FROM TOK_STRING {
fastd_read_config_dir(ctx, conf, $3->str, depth);
}
- | TOK_STRING { fastd_read_config(ctx, conf, $1->str, false, depth); }
+ | TOK_STRING {
+ if (!fastd_read_config(ctx, conf, $1->str, false, depth))
+ YYERROR;
+ }
;
@@ -265,12 +276,14 @@ boolean: TOK_YES { $$ = true; }
;
port: TOK_INTEGER {
- if ($1 < 0 || $1 > 65635)
- exit_error(ctx, "config error: invalid port %i", $1);
+ if ($1 < 0 || $1 > 65635) {
+ fastd_config_error(&@$, ctx, conf, filename, depth, "invalid port");
+ YYERROR;
+ }
$$ = htons($1);
}
;
%%
void fastd_config_error(YYLTYPE *loc, fastd_context *ctx, fastd_config *conf, const char *filename, int depth, char *s) {
- exit_error(ctx, "config error: %s at %s:%i:%i", s, filename, loc->first_line, loc->first_column);
+ pr_error(ctx, "config error: %s at %s:%i:%i", s, filename, loc->first_line, loc->first_column);
}
diff --git a/src/fastd.h b/src/fastd.h
index f402be8..6eab856 100644
--- a/src/fastd.h
+++ b/src/fastd.h
@@ -140,7 +140,7 @@ struct _fastd_config_str {
void fastd_printf(const fastd_context *ctx, const char *format, ...);
void fastd_read_config_dir(fastd_context *ctx, fastd_config *conf, const char *dir, int depth);
-void fastd_read_config(fastd_context *ctx, fastd_config *conf, const char *filename, bool peer_config, int depth);
+bool fastd_read_config(fastd_context *ctx, fastd_config *conf, const char *filename, bool peer_config, int depth);
void fastd_configure(fastd_context *ctx, fastd_config *conf, int argc, char *const argv[]);
void fastd_random_bytes(fastd_context *ctx, void *buffer, size_t len, bool secure);
diff --git a/src/peer.c b/src/peer.c
index c88152d..92e6aa5 100644
--- a/src/peer.c
+++ b/src/peer.c
@@ -93,6 +93,15 @@ fastd_peer_config* fastd_peer_config_new(fastd_context *ctx, fastd_config *conf)
return peer;
}
+void fastd_peer_config_delete(fastd_context *ctx, fastd_config *conf) {
+ fastd_peer_config *peer = conf->peers, *next = peer->next;
+
+ free(peer->name);
+ free(peer->key);
+ free(peer);
+
+ conf->peers = next;
+}
void fastd_peer_reset(fastd_context *ctx, fastd_peer *peer) {
pr_debug(ctx, "resetting peer %P", peer);
diff --git a/src/peer.h b/src/peer.h
index 1ffa18b..54f6ca8 100644
--- a/src/peer.h
+++ b/src/peer.h
@@ -71,6 +71,7 @@ struct _fastd_peer_eth_addr {
fastd_peer_config* fastd_peer_config_new(fastd_context *ctx, fastd_config *conf);
+void fastd_peer_config_delete(fastd_context *ctx, fastd_config *conf);
void fastd_peer_reset(fastd_context *ctx, fastd_peer *peer);
fastd_peer* fastd_peer_add(fastd_context *ctx, fastd_peer_config *conf);