]> git.puffer.fish Git - matthieu/frr.git/commitdiff
zebra: add a start callback for dplane plugins
authorMark Stapp <mjs@voltanet.io>
Fri, 12 Apr 2019 15:27:13 +0000 (11:27 -0400)
committerMark Stapp <mjs@voltanet.io>
Tue, 28 May 2019 12:16:22 +0000 (08:16 -0400)
Add a callback called at start time, once the dplane pthread
and thread_master are available. The callback is optional.

Signed-off-by: Mark Stapp <mjs@voltanet.io>
zebra/zebra_dplane.c
zebra/zebra_dplane.h

index 6fc62147c815c6c9ac4663bf1b08c160bdb6f3fa..92a401b7e8bb9f092b3ed4ff330fd2988e2061ce 100644 (file)
@@ -222,6 +222,8 @@ struct zebra_dplane_provider {
        /* Flags */
        int dp_flags;
 
+       int (*dp_start)(struct zebra_dplane_provider *prov);
+
        int (*dp_fp)(struct zebra_dplane_provider *prov);
 
        int (*dp_fini)(struct zebra_dplane_provider *prov, bool early_p);
@@ -1823,6 +1825,7 @@ int dplane_show_provs_helper(struct vty *vty, bool detailed)
 int dplane_provider_register(const char *name,
                             enum dplane_provider_prio prio,
                             int flags,
+                            int (*start_fp)(struct zebra_dplane_provider *),
                             int (*fp)(struct zebra_dplane_provider *),
                             int (*fini_fp)(struct zebra_dplane_provider *,
                                            bool early),
@@ -1853,6 +1856,7 @@ int dplane_provider_register(const char *name,
 
        p->dp_priority = prio;
        p->dp_fp = fp;
+       p->dp_start = start_fp;
        p->dp_fini = fini_fp;
        p->dp_data = data;
 
@@ -2320,7 +2324,7 @@ static void dplane_provider_init(void)
 
        ret = dplane_provider_register("Kernel",
                                       DPLANE_PRIO_KERNEL,
-                                      DPLANE_PROV_FLAGS_DEFAULT,
+                                      DPLANE_PROV_FLAGS_DEFAULT, NULL,
                                       kernel_dplane_process_func,
                                       NULL,
                                       NULL, NULL);
@@ -2333,7 +2337,7 @@ static void dplane_provider_init(void)
        /* Optional test provider ... */
        ret = dplane_provider_register("Test",
                                       DPLANE_PRIO_PRE_KERNEL,
-                                      DPLANE_PROV_FLAGS_DEFAULT,
+                                      DPLANE_PROV_FLAGS_DEFAULT, NULL,
                                       test_dplane_process_func,
                                       test_dplane_shutdown_func,
                                       NULL /* data */, NULL);
@@ -2717,13 +2721,14 @@ static void zebra_dplane_init_internal(void)
  */
 void zebra_dplane_start(void)
 {
-       /* Start dataplane pthread */
-
+       struct zebra_dplane_provider *prov;
        struct frr_pthread_attr pattr = {
                .start = frr_pthread_attr_default.start,
                .stop = frr_pthread_attr_default.stop
        };
 
+       /* Start dataplane pthread */
+
        zdplane_info.dg_pthread = frr_pthread_new(&pattr, "Zebra dplane thread",
                                                  "Zebra dplane");
 
@@ -2735,6 +2740,23 @@ void zebra_dplane_start(void)
        thread_add_event(zdplane_info.dg_master, dplane_thread_loop, NULL, 0,
                         &zdplane_info.dg_t_update);
 
+       /* Call start callbacks for registered providers */
+
+       DPLANE_LOCK();
+       prov = TAILQ_FIRST(&zdplane_info.dg_providers_q);
+       DPLANE_UNLOCK();
+
+       while (prov) {
+
+               if (prov->dp_start)
+                       (prov->dp_start)(prov);
+
+               /* Locate next provider */
+               DPLANE_LOCK();
+               prov = TAILQ_NEXT(prov, dp_prov_link);
+               DPLANE_UNLOCK();
+       }
+
        frr_pthread_run(zdplane_info.dg_pthread, NULL);
 }
 
index d45628fdd04c9be3dac3ce5053da5e07188dc4fc..1d4056c815aba0c7400379beec5c2634f9cb5b81 100644 (file)
@@ -363,7 +363,13 @@ enum dplane_provider_prio {
  * then checks the provider's outbound queue for completed work.
  */
 
-/* Providers offer an entry-point for shutdown and cleanup. This is called
+/*
+ * Providers can offer a 'start' callback; if present, the dataplane will
+ * call it when it is starting - when its pthread and event-scheduling
+ * thread_master are available.
+ */
+
+/* Providers can offer an entry-point for shutdown and cleanup. This is called
  * with 'early' during shutdown, to indicate that the dataplane subsystem
  * is allowing work to move through the providers and finish.
  * When called without 'early', the provider should release
@@ -372,6 +378,7 @@ enum dplane_provider_prio {
 int dplane_provider_register(const char *name,
                             enum dplane_provider_prio prio,
                             int flags,
+                            int (*start_fp)(struct zebra_dplane_provider *),
                             int (*fp)(struct zebra_dplane_provider *),
                             int (*fini_fp)(struct zebra_dplane_provider *,
                                            bool early),