summaryrefslogtreecommitdiff
path: root/lib/libfrr.c
diff options
context:
space:
mode:
authorDavid Lamparter <equinox@opensourcerouting.org>2017-04-04 20:04:07 +0200
committerDavid Lamparter <equinox@opensourcerouting.org>2017-04-04 20:04:07 +0200
commit422f8d0ca9745a16b1f46710c621fc9f98200bcf (patch)
tree24e91ad38adfd824c624a4a46889e6102b913225 /lib/libfrr.c
parentb394fc99bc4b555aa3c78521439b28f1ff8886ef (diff)
parentb3cfe637a66a5de00c72125f5fa051155ccb4a29 (diff)
Merge branch 'master'
Diffstat (limited to 'lib/libfrr.c')
-rw-r--r--lib/libfrr.c38
1 files changed, 36 insertions, 2 deletions
diff --git a/lib/libfrr.c b/lib/libfrr.c
index b7ce0679c3..64f8be2ca6 100644
--- a/lib/libfrr.c
+++ b/lib/libfrr.c
@@ -28,6 +28,9 @@
#include "memory_vty.h"
#include "zclient.h"
#include "log_int.h"
+#include "module.h"
+
+DEFINE_HOOK(frr_late_init, (struct thread_master *tm), (tm))
const char frr_sysconfdir[] = SYSCONFDIR;
const char frr_vtydir[] = DAEMON_VTY_DIR;
@@ -64,14 +67,16 @@ static const struct option lo_always[] = {
{ "help", no_argument, NULL, 'h' },
{ "version", no_argument, NULL, 'v' },
{ "daemon", no_argument, NULL, 'd' },
+ { "module", no_argument, NULL, 'M' },
{ "vty_socket", required_argument, NULL, OPTION_VTYSOCK },
{ NULL }
};
static const struct optspec os_always = {
- "hvdi:",
+ "hvdM:",
" -h, --help Display this help and exit\n"
" -v, --version Print program version\n"
" -d, --daemon Runs in daemon mode\n"
+ " -M, --module Load specified module\n"
" --vty_socket Override vty socket path\n",
lo_always
};
@@ -184,12 +189,18 @@ void frr_help_exit(int status)
exit(status);
}
+struct option_chain {
+ struct option_chain *next;
+ const char *arg;
+};
+static struct option_chain *modules = NULL, **modnext = &modules;
static int errors = 0;
static int frr_opt(int opt)
{
static int vty_port_set = 0;
static int vty_addr_set = 0;
+ struct option_chain *oc;
char *err;
switch (opt) {
@@ -203,6 +214,13 @@ static int frr_opt(int opt)
case 'd':
di->daemon_mode = 1;
break;
+ case 'M':
+ oc = XMALLOC(MTYPE_TMP, sizeof(*oc));
+ oc->arg = optarg;
+ oc->next = NULL;
+ *modnext = oc;
+ modnext = &oc->next;
+ break;
case 'i':
if (di->flags & FRR_NO_CFG_PID_DRY)
return 1;
@@ -295,9 +313,12 @@ int frr_getopt(int argc, char * const argv[], int *longindex)
return opt;
}
+static struct thread_master *master;
struct thread_master *frr_init(void)
{
- struct thread_master *master;
+ struct option_chain *oc;
+ struct frrmod_runtime *module;
+ char moderr[256];
srandom(time(NULL));
@@ -307,6 +328,17 @@ struct thread_master *frr_init(void)
zlog_set_level (ZLOG_DEST_SYSLOG, zlog_default->default_lvl);
#endif
+ frrmod_init(di->module);
+ while (modules) {
+ modules = (oc = modules)->next;
+ module = frrmod_load(oc->arg, moderr, sizeof(moderr));
+ if (!module) {
+ fprintf(stderr, "%s\n", moderr);
+ exit(1);
+ }
+ XFREE(MTYPE_TMP, oc);
+ }
+
zprivs_init(di->privs);
master = thread_master_create();
@@ -324,6 +356,8 @@ struct thread_master *frr_init(void)
void frr_config_fork(void)
{
+ hook_call(frr_late_init, master);
+
if (di->instance) {
snprintf(config_default, sizeof(config_default), "%s/%s-%d.conf",
frr_sysconfdir, di->name, di->instance);