From 6b98d34fdfeeafeb51887044f02f2496d2807bfd Mon Sep 17 00:00:00 2001 From: Donald Sharp Date: Wed, 2 Jan 2019 14:38:15 -0500 Subject: [PATCH 1/3] sharpd: Abstract the route install/delete functions a bit Abstract the route install/delete functions a bit to allow me to expand on them in the with future commits. Signed-off-by: Donald Sharp --- sharpd/sharp_vty.c | 21 ++++------------- sharpd/sharp_zebra.c | 55 ++++++++++++++++++++++++++++++++++++++++++-- sharpd/sharp_zebra.h | 6 +++++ 3 files changed, 63 insertions(+), 19 deletions(-) diff --git a/sharpd/sharp_vty.c b/sharpd/sharp_vty.c index 3aed8eb123..abc2c720ce 100644 --- a/sharpd/sharp_vty.c +++ b/sharpd/sharp_vty.c @@ -80,6 +80,8 @@ DEFPY(watch_nexthop_v4, watch_nexthop_v4_cmd, return CMD_SUCCESS; } + + DEFPY (install_routes, install_routes_cmd, "sharp install routes A.B.C.D$start |nexthop-group NAME$nexthop_group> (1-1000000)$routes [instance (0-255)$instance]", @@ -96,11 +98,9 @@ DEFPY (install_routes, "Instance to use\n" "Instance\n") { - int i; struct prefix p; struct nexthop nhop; struct nexthop_group nhg; - uint32_t temp; total_routes = routes; installed_routes = 0; @@ -134,13 +134,8 @@ DEFPY (install_routes, nhg.nexthop = &nhop; } - zlog_debug("Inserting %ld routes", routes); - temp = ntohl(p.u.prefix4.s_addr); - for (i = 0; i < routes; i++) { - route_add(&p, (uint8_t)instance, &nhg); - p.u.prefix4.s_addr = htonl(++temp); - } + sharp_install_routes_helper(&p, instance, &nhg, routes); return CMD_SUCCESS; } @@ -186,9 +181,7 @@ DEFPY (remove_routes, "instance to use\n" "Value of instance\n") { - int i; struct prefix p; - uint32_t temp; total_routes = routes; removed_routes = 0; @@ -198,13 +191,7 @@ DEFPY (remove_routes, p.prefixlen = 32; p.u.prefix4 = start; - zlog_debug("Removing %ld routes", routes); - - temp = ntohl(p.u.prefix4.s_addr); - for (i = 0; i < routes; i++) { - route_delete(&p, (uint8_t)instance); - p.u.prefix4.s_addr = htonl(++temp); - } + sharp_remove_routes_helper(&p, instance, routes); return CMD_SUCCESS; } diff --git a/sharpd/sharp_zebra.c b/sharpd/sharp_zebra.c index 4a88b6c8ee..72e1eb2b21 100644 --- a/sharpd/sharp_zebra.c +++ b/sharpd/sharp_zebra.c @@ -133,6 +133,53 @@ extern uint32_t total_routes; extern uint32_t installed_routes; extern uint32_t removed_routes; +void sharp_install_routes_helper(struct prefix *p, uint8_t instance, + struct nexthop_group *nhg, + uint32_t routes) +{ + uint32_t temp, i; + + zlog_debug("Inserting %u routes", routes); + + temp = ntohl(p->u.prefix4.s_addr); + for (i = 0; i < routes; i++) { + route_add(p, (uint8_t)instance, nhg); + p->u.prefix4.s_addr = htonl(++temp); + } +} + +void sharp_remove_routes_helper(struct prefix *p, uint8_t instance, + uint32_t routes) +{ + uint32_t temp, i; + + zlog_debug("Removing %u routes", routes); + + temp = ntohl(p->u.prefix4.s_addr); + for (i = 0; i < routes; i++) { + route_delete(p, (uint8_t)instance); + p->u.prefix4.s_addr = htonl(++temp); + } +} + +static int handle_repeated(bool installed) +{ + repeat--; + + if (repeat <= 0) + return; + + if (installed) { + removed_routes = 0; + sharp_remove_routes_helper(&prefix, inst, total_routes); + } + + if (!installed) { + installed_routes = 0; + sharp_remove_routes + } +} + static int route_notify_owner(int command, struct zclient *zclient, zebra_size_t length, vrf_id_t vrf_id) { @@ -146,8 +193,10 @@ static int route_notify_owner(int command, struct zclient *zclient, switch (note) { case ZAPI_ROUTE_INSTALLED: installed_routes++; - if (total_routes == installed_routes) + if (total_routes == installed_routes) { zlog_debug("Installed All Items"); + handle_repeated(true); + } break; case ZAPI_ROUTE_FAIL_INSTALL: zlog_debug("Failed install of route"); @@ -157,8 +206,10 @@ static int route_notify_owner(int command, struct zclient *zclient, break; case ZAPI_ROUTE_REMOVED: removed_routes++; - if (total_routes == removed_routes) + if (total_routes == removed_routes) { zlog_debug("Removed all Items"); + handle_repeated(false); + } break; case ZAPI_ROUTE_REMOVE_FAIL: zlog_debug("Route removal Failure"); diff --git a/sharpd/sharp_zebra.h b/sharpd/sharp_zebra.h index ffe21df9b8..7326056cae 100644 --- a/sharpd/sharp_zebra.h +++ b/sharpd/sharp_zebra.h @@ -29,4 +29,10 @@ extern void route_add(struct prefix *p, uint8_t instance, struct nexthop_group *nhg); extern void route_delete(struct prefix *p, uint8_t instance); extern void sharp_zebra_nexthop_watch(struct prefix *p, bool watch); + +extern void sharp_install_routes_helper(struct prefix *p, uint8_t instance, + struct nexthop_group *nhg, + uint32_t routes); +extern void sharp_remove_routes_helper(struct prefix *p, uint8_t instance, + uint32_t routes); #endif From b939f6ff513808aba46f4797a4349d85989ae01b Mon Sep 17 00:00:00 2001 From: Donald Sharp Date: Thu, 3 Jan 2019 09:49:15 -0500 Subject: [PATCH 2/3] sharpd: Add code to allow install/uninstall repeatedly Add a bit of test code to allow the tester to install/uninstall the routes via: sharp install routes A.B.C.D nexthop Y.Z.M.D 1000000 repeat 100 This will install 1000000 routes wait for them to be finished then uninstall them then start installation over 100 times. Signed-off-by: Donald Sharp |nexthop-group NAME$nexthop_group> (1-1000000)$routes [instance (0-255)$instance]", + "sharp install routes A.B.C.D$start |nexthop-group NAME$nexthop_group> (1-1000000)$routes [instance (0-255)$instance] [repeat (2-1000)$rpt]", "Sharp routing Protocol\n" "install some routes\n" "Routes to install\n" @@ -96,22 +102,27 @@ DEFPY (install_routes, "The Name of the nexthop-group\n" "How many to create\n" "Instance to use\n" - "Instance\n") + "Instance\n" + "Should we repeat this command\n" + "How many times to repeat this command\n") { - struct prefix p; - struct nexthop nhop; - struct nexthop_group nhg; - total_routes = routes; installed_routes = 0; - memset(&p, 0, sizeof(p)); - memset(&nhop, 0, sizeof(nhop)); - memset(&nhg, 0, sizeof(nhg)); + if (rpt >= 2) + repeat = rpt * 2; + else + repeat = 0; - p.family = AF_INET; - p.prefixlen = 32; - p.u.prefix4 = start; + memset(&prefix, 0, sizeof(prefix)); + memset(&orig_prefix, 0, sizeof(orig_prefix)); + memset(&nhop, 0, sizeof(nhop)); + memset(&nhop_group, 0, sizeof(nhop_group)); + + prefix.family = AF_INET; + prefix.prefixlen = 32; + prefix.u.prefix4 = start; + orig_prefix = prefix; if (nexthop_group) { struct nexthop_group_cmd *nhgc = nhgc_find(nexthop_group); @@ -122,7 +133,7 @@ DEFPY (install_routes, return CMD_WARNING; } - nhg.nexthop = nhgc->nhg.nexthop; + nhop_group.nexthop = nhgc->nhg.nexthop; } else { if (nexthop4.s_addr != INADDR_ANY) { nhop.gate.ipv4 = nexthop4; @@ -132,10 +143,12 @@ DEFPY (install_routes, nhop.type = NEXTHOP_TYPE_IPV6; } - nhg.nexthop = &nhop; + nhop_group.nexthop = &nhop; } - sharp_install_routes_helper(&p, instance, &nhg, routes); + inst = instance; + rts = routes; + sharp_install_routes_helper(&prefix, inst, &nhop_group, rts); return CMD_SUCCESS; } @@ -181,17 +194,18 @@ DEFPY (remove_routes, "instance to use\n" "Value of instance\n") { - struct prefix p; total_routes = routes; removed_routes = 0; - memset(&p, 0, sizeof(p)); + memset(&prefix, 0, sizeof(prefix)); - p.family = AF_INET; - p.prefixlen = 32; - p.u.prefix4 = start; + prefix.family = AF_INET; + prefix.prefixlen = 32; + prefix.u.prefix4 = start; - sharp_remove_routes_helper(&p, instance, routes); + inst = instance; + rts = routes; + sharp_remove_routes_helper(&prefix, inst, rts); return CMD_SUCCESS; } diff --git a/sharpd/sharp_zebra.c b/sharpd/sharp_zebra.c index 72e1eb2b21..37591fa41f 100644 --- a/sharpd/sharp_zebra.c +++ b/sharpd/sharp_zebra.c @@ -132,6 +132,10 @@ static int interface_state_down(int command, struct zclient *zclient, extern uint32_t total_routes; extern uint32_t installed_routes; extern uint32_t removed_routes; +extern int32_t repeat; +extern struct prefix orig_prefix; +extern struct nexthop_group nhop_group; +extern uint8_t inst; void sharp_install_routes_helper(struct prefix *p, uint8_t instance, struct nexthop_group *nhg, @@ -162,8 +166,9 @@ void sharp_remove_routes_helper(struct prefix *p, uint8_t instance, } } -static int handle_repeated(bool installed) +static void handle_repeated(bool installed) { + struct prefix p = orig_prefix; repeat--; if (repeat <= 0) @@ -171,12 +176,13 @@ static int handle_repeated(bool installed) if (installed) { removed_routes = 0; - sharp_remove_routes_helper(&prefix, inst, total_routes); + sharp_remove_routes_helper(&p, inst, total_routes); } if (!installed) { installed_routes = 0; - sharp_remove_routes + sharp_install_routes_helper(&p, inst, &nhop_group, + total_routes); } } From 413908931cd477d58beb300235d9d8b919e36d2d Mon Sep 17 00:00:00 2001 From: Donald Sharp Date: Thu, 3 Jan 2019 09:57:06 -0500 Subject: [PATCH 3/3] doc: Update documentation to new functionality Update sharp.rst to reflect new functionality in the `sharp install ..` command. Signed-off-by: Donald Sharp --- doc/user/sharp.rst | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/doc/user/sharp.rst b/doc/user/sharp.rst index 8831c0159b..c2d32a718e 100644 --- a/doc/user/sharp.rst +++ b/doc/user/sharp.rst @@ -33,16 +33,20 @@ All sharp commands are under the enable node and preceeded by the ``sharp`` keyword. At present, no sharp commands will be preserved in the config. .. index:: sharp install -.. clicmd:: sharp install routes A.B.C.D nexthop (1-1000000) +.. clicmd:: sharp install routes A.B.C.D |nexthop-group NAME> (1-1000000) [instance (0-255)] [repeat (2-1000)] Install up to 1,000,000 (one million) /32 routes starting at ``A.B.C.D`` with specified nexthop ``E.F.G.H`` or ``X:X::X:X``. The nexthop is a ``NEXTHOP_TYPE_IPV4`` or ``NEXTHOP_TYPE_IPV6`` and must be reachable - to be installed into the kernel. The routes are installed into zebra as - ``ZEBRA_ROUTE_SHARP`` and can be used as part of a normal route + to be installed into the kernel. Alternatively a nexthop-group NAME + can be specified and used as the nexthops. The routes are installed into + zebra as ``ZEBRA_ROUTE_SHARP`` and can be used as part of a normal route redistribution. Route installation time is noted in the debug log. When zebra successfully installs a route into the kernel and SHARP receives success notifications for all routes this is logged as well. + Instance (0-255) if specified causes the routes to be installed in a different + instance. If repeat is used then we will install/uninstall the routes the + number of times specified. .. index:: sharp remove .. clicmd:: sharp remove routes A.B.C.D (1-1000000)