summaryrefslogtreecommitdiffstats
path: root/pbrd
diff options
context:
space:
mode:
Diffstat (limited to '')
-rw-r--r--pbrd/pbr_main.c28
-rw-r--r--pbrd/pbr_nht.c13
-rw-r--r--pbrd/pbr_nht.h2
-rw-r--r--pbrd/pbr_vty.c3
-rw-r--r--pbrd/pbr_zebra.c48
-rw-r--r--pbrd/pbr_zebra.h1
6 files changed, 55 insertions, 40 deletions
diff --git a/pbrd/pbr_main.c b/pbrd/pbr_main.c
index c4708d3..6695b53 100644
--- a/pbrd/pbr_main.c
+++ b/pbrd/pbr_main.c
@@ -71,6 +71,8 @@ static void sigint(void)
pbr_vrf_terminate();
+ pbr_zebra_destroy();
+
frr_fini();
exit(0);
@@ -101,26 +103,26 @@ struct frr_signal_t pbr_signals[] = {
},
};
-#define PBR_VTY_PORT 2615
-
static const struct frr_yang_module_info *const pbrd_yang_modules[] = {
&frr_filter_info,
&frr_interface_info,
&frr_vrf_info,
};
-FRR_DAEMON_INFO(pbrd, PBR, .vty_port = PBR_VTY_PORT,
-
- .proghelp = "Implementation of PBR.",
+/* clang-format off */
+FRR_DAEMON_INFO(pbrd, PBR,
+ .vty_port = PBR_VTY_PORT,
+ .proghelp = "Implementation of PBR.",
- .signals = pbr_signals,
- .n_signals = array_size(pbr_signals),
+ .signals = pbr_signals,
+ .n_signals = array_size(pbr_signals),
- .privs = &pbr_privs,
+ .privs = &pbr_privs,
- .yang_modules = pbrd_yang_modules,
- .n_yang_modules = array_size(pbrd_yang_modules),
+ .yang_modules = pbrd_yang_modules,
+ .n_yang_modules = array_size(pbrd_yang_modules),
);
+/* clang-format on */
int main(int argc, char **argv, char **envp)
{
@@ -158,8 +160,10 @@ int main(int argc, char **argv, char **envp)
access_list_init();
pbr_nht_init();
pbr_map_init();
- if_zapi_callbacks(pbr_ifp_create, pbr_ifp_up,
- pbr_ifp_down, pbr_ifp_destroy);
+ hook_register_prio(if_real, 0, pbr_ifp_create);
+ hook_register_prio(if_up, 0, pbr_ifp_up);
+ hook_register_prio(if_down, 0, pbr_ifp_down);
+ hook_register_prio(if_unreal, 0, pbr_ifp_destroy);
pbr_zebra_init();
pbr_vrf_init();
pbr_vty_init();
diff --git a/pbrd/pbr_nht.c b/pbrd/pbr_nht.c
index 4f7882f..ff252f8 100644
--- a/pbrd/pbr_nht.c
+++ b/pbrd/pbr_nht.c
@@ -534,6 +534,7 @@ void pbr_nht_set_seq_nhg_data(struct pbr_map_sequence *pbrms,
case NEXTHOP_TYPE_IPV4:
case NEXTHOP_TYPE_IPV4_IFINDEX:
pbrms->family = AF_INET;
+ break;
case NEXTHOP_TYPE_IFINDEX:
case NEXTHOP_TYPE_BLACKHOLE:
break;
@@ -649,7 +650,15 @@ static void pbr_nht_release_individual_nexthop(struct pbr_map_sequence *pbrms)
void pbr_nht_delete_individual_nexthop(struct pbr_map_sequence *pbrms)
{
- pbr_map_delete_nexthops(pbrms);
+ struct pbr_map *pbrm = pbrms->parent;
+
+ /* The idea here is to send a delete command to zebra only once,
+ * and set 'valid' and 'installed' to false only when the last
+ * rule is being deleted. In other words, the pbr common should be
+ * updated only when the last rule is being updated or deleted.
+ */
+ if (pbrm->seqnumbers->count == 1)
+ pbr_map_delete_nexthops(pbrms);
pbr_nht_release_individual_nexthop(pbrms);
}
@@ -889,7 +898,7 @@ static void pbr_nht_individual_nexthop_update(struct pbr_nexthop_cache *pnhc,
pbr_nht_individual_nexthop_interface_update(pnhc, pnhi);
break;
}
- /* Intentional fall thru */
+ fallthrough;
case NEXTHOP_TYPE_IPV4_IFINDEX:
case NEXTHOP_TYPE_IPV4:
case NEXTHOP_TYPE_IPV6:
diff --git a/pbrd/pbr_nht.h b/pbrd/pbr_nht.h
index 9b67492..a702a57 100644
--- a/pbrd/pbr_nht.h
+++ b/pbrd/pbr_nht.h
@@ -36,7 +36,7 @@ struct pbr_nexthop_cache {
struct pbr_nexthop_group_cache *parent;
char vrf_name[VRF_NAMSIZ + 1];
- char intf_name[INTERFACE_NAMSIZ + 1];
+ char intf_name[IFNAMSIZ + 1];
struct nexthop nexthop;
diff --git a/pbrd/pbr_vty.c b/pbrd/pbr_vty.c
index 9589e5b..64d8884 100644
--- a/pbrd/pbr_vty.c
+++ b/pbrd/pbr_vty.c
@@ -1667,8 +1667,7 @@ static void vty_json_pbrms(json_object *j, struct vty *vty,
json_object_int_add(jpbrm, "sequenceNumber", pbrms->seqno);
json_object_int_add(jpbrm, "ruleNumber", pbrms->ruleno);
json_object_boolean_add(jpbrm, "vrfUnchanged", pbrms->vrf_unchanged);
- json_object_boolean_add(jpbrm, "installed",
- pbr_nht_get_installed(nhg_name));
+ json_object_boolean_add(jpbrm, "installed", pbrms->installed);
json_object_string_add(jpbrm, "installedReason",
pbrms->reason ? rbuf : "Valid");
diff --git a/pbrd/pbr_zebra.c b/pbrd/pbr_zebra.c
index 30eaf62..dd15bea 100644
--- a/pbrd/pbr_zebra.c
+++ b/pbrd/pbr_zebra.c
@@ -178,7 +178,7 @@ static int rule_notify_owner(ZAPI_CALLBACK_ARGS)
enum zapi_rule_notify_owner note;
struct pbr_map_sequence *pbrms;
struct pbr_map_interface *pmi;
- char ifname[INTERFACE_NAMSIZ + 1];
+ char ifname[IFNAMSIZ + 1];
uint64_t installed;
if (!zapi_rule_notify_decode(zclient->ibuf, &seqno, &priority, &unique,
@@ -222,6 +222,8 @@ static int rule_notify_owner(ZAPI_CALLBACK_ARGS)
static void zebra_connected(struct zclient *zclient)
{
DEBUGD(&pbr_dbg_zebra, "%s: Registering for fun and profit", __func__);
+
+ zebra_route_notify_send(ZEBRA_ROUTE_NOTIFY_REQUEST, zclient, true);
zclient_send_reg_requests(zclient, VRF_DEFAULT);
}
@@ -364,38 +366,30 @@ void route_delete(struct pbr_nexthop_group_cache *pnhgc, afi_t afi)
}
}
-static int pbr_zebra_nexthop_update(ZAPI_CALLBACK_ARGS)
+static void pbr_zebra_nexthop_update(struct vrf *vrf, struct prefix *matched,
+ struct zapi_route *nhr)
{
- struct zapi_route nhr;
- struct prefix matched;
uint32_t i;
- if (!zapi_nexthop_update_decode(zclient->ibuf, &matched, &nhr)) {
- zlog_err("Failure to decode Nexthop update message");
- return 0;
- }
-
if (DEBUG_MODE_CHECK(&pbr_dbg_zebra, DEBUG_MODE_ALL)) {
-
DEBUGD(&pbr_dbg_zebra,
"%s: Received Nexthop update: %pFX against %pFX",
- __func__, &matched, &nhr.prefix);
+ __func__, matched, &nhr->prefix);
DEBUGD(&pbr_dbg_zebra, "%s: (Nexthops(%u)", __func__,
- nhr.nexthop_num);
+ nhr->nexthop_num);
- for (i = 0; i < nhr.nexthop_num; i++) {
+ for (i = 0; i < nhr->nexthop_num; i++) {
DEBUGD(&pbr_dbg_zebra,
"%s: Type: %d: vrf: %d, ifindex: %d gate: %pI4",
- __func__, nhr.nexthops[i].type,
- nhr.nexthops[i].vrf_id, nhr.nexthops[i].ifindex,
- &nhr.nexthops[i].gate.ipv4);
+ __func__, nhr->nexthops[i].type,
+ nhr->nexthops[i].vrf_id, nhr->nexthops[i].ifindex,
+ &nhr->nexthops[i].gate.ipv4);
}
}
- nhr.prefix = matched;
- pbr_nht_nexthop_update(&nhr);
- return 1;
+ nhr->prefix = *matched;
+ pbr_nht_nexthop_update(nhr);
}
extern struct zebra_privs_t pbr_privs;
@@ -405,18 +399,26 @@ static zclient_handler *const pbr_handlers[] = {
[ZEBRA_INTERFACE_ADDRESS_DELETE] = interface_address_delete,
[ZEBRA_ROUTE_NOTIFY_OWNER] = route_notify_owner,
[ZEBRA_RULE_NOTIFY_OWNER] = rule_notify_owner,
- [ZEBRA_NEXTHOP_UPDATE] = pbr_zebra_nexthop_update,
};
void pbr_zebra_init(void)
{
- struct zclient_options opt = { .receive_notify = true };
-
- zclient = zclient_new(master, &opt, pbr_handlers,
+ zclient = zclient_new(master, &zclient_options_default, pbr_handlers,
array_size(pbr_handlers));
zclient_init(zclient, ZEBRA_ROUTE_PBR, 0, &pbr_privs);
zclient->zebra_connected = zebra_connected;
+ zclient->nexthop_update = pbr_zebra_nexthop_update;
+}
+
+void pbr_zebra_destroy(void)
+{
+ if (zclient == NULL)
+ return;
+
+ zclient_stop(zclient);
+ zclient_free(zclient);
+ zclient = NULL;
}
void pbr_send_rnh(struct nexthop *nhop, bool reg)
diff --git a/pbrd/pbr_zebra.h b/pbrd/pbr_zebra.h
index ef844ef..5cbb1fd 100644
--- a/pbrd/pbr_zebra.h
+++ b/pbrd/pbr_zebra.h
@@ -14,6 +14,7 @@ struct pbr_interface {
extern struct event_loop *master;
extern void pbr_zebra_init(void);
+extern void pbr_zebra_destroy(void);
extern void route_add(struct pbr_nexthop_group_cache *pnhgc,
struct nexthop_group nhg, afi_t install_afi);