diff options
-rw-r--r-- | src/vnet/dpo/replicate_dpo.c | 7 | ||||
-rw-r--r-- | src/vnet/fib/fib_table.c | 4 | ||||
-rw-r--r-- | src/vnet/ip/ip.api | 10 | ||||
-rw-r--r-- | src/vnet/ip/ip_api.c | 61 | ||||
-rw-r--r-- | src/vnet/mfib/mfib_entry.c | 10 | ||||
-rw-r--r-- | src/vnet/mfib/mfib_entry.h | 1 | ||||
-rw-r--r-- | test/test_ip_mcast.py | 7 | ||||
-rw-r--r-- | test/vpp_ip_route.py | 29 |
8 files changed, 91 insertions, 38 deletions
diff --git a/src/vnet/dpo/replicate_dpo.c b/src/vnet/dpo/replicate_dpo.c index 95d7f9748ab..8c8206c4a0c 100644 --- a/src/vnet/dpo/replicate_dpo.c +++ b/src/vnet/dpo/replicate_dpo.c @@ -59,7 +59,12 @@ replicate_t *replicate_pool; /** * The one instance of replicate main */ -replicate_main_t replicate_main; +replicate_main_t replicate_main = { + .repm_counters = { + .name = "mroutes", + .stat_segment_name = "/net/mroute", + }, +}; static inline index_t replicate_get_index (const replicate_t *rep) diff --git a/src/vnet/fib/fib_table.c b/src/vnet/fib/fib_table.c index 47f2011b7aa..69746d96912 100644 --- a/src/vnet/fib/fib_table.c +++ b/src/vnet/fib/fib_table.c @@ -886,8 +886,8 @@ fib_table_entry_delete_index (fib_node_index_t fib_entry_index, } u32 -fib_table_entry_get_stats_index(u32 fib_index, - const fib_prefix_t *prefix) +fib_table_entry_get_stats_index (u32 fib_index, + const fib_prefix_t *prefix) { return (fib_entry_get_stats_index( fib_table_lookup_exact_match(fib_index, prefix))); diff --git a/src/vnet/ip/ip.api b/src/vnet/ip/ip.api index 7c7f656d2e6..71ad1c189c1 100644 --- a/src/vnet/ip/ip.api +++ b/src/vnet/ip/ip.api @@ -440,7 +440,7 @@ define ip_add_del_route_reply @param next_hop_afi - Use dpo_proto_t FIXME */ -autoreply define ip_mroute_add_del +define ip_mroute_add_del { u32 client_index; u32 context; @@ -460,6 +460,13 @@ autoreply define ip_mroute_add_del u8 nh_address[16]; }; +define ip_mroute_add_del_reply +{ + u32 context; + i32 retval; + u32 stats_index; +}; + /** \brief Dump IP multicast fib table @param client_index - opaque cookie to identify the sender */ @@ -487,6 +494,7 @@ manual_endian manual_print define ip_mfib_details u8 grp_address[4]; u8 src_address[4]; u32 count; + u32 stats_index; vl_api_fib_path_t path[count]; }; diff --git a/src/vnet/ip/ip_api.c b/src/vnet/ip/ip_api.c index 477090d07f1..5dbc02d5c59 100644 --- a/src/vnet/ip/ip_api.c +++ b/src/vnet/ip/ip_api.c @@ -1203,7 +1203,7 @@ add_del_mroute_check (fib_protocol_t table_proto, return (0); } -static int +static fib_node_index_t mroute_add_del_handler (u8 is_add, u8 is_local, u32 fib_index, @@ -1214,6 +1214,8 @@ mroute_add_del_handler (u8 is_add, u32 next_hop_sw_if_index, ip46_address_t * nh, u32 itf_flags, u32 bier_imp) { + fib_node_index_t mfib_entry_index = ~0; + stats_dslock_with_hint (1 /* release hint */ , 2 /* tag */ ); fib_route_path_t path = { @@ -1232,15 +1234,17 @@ mroute_add_del_handler (u8 is_add, } else if (!is_local && ~0 == next_hop_sw_if_index) { - mfib_table_entry_update (fib_index, prefix, - MFIB_SOURCE_API, rpf_id, entry_flags); + mfib_entry_index = mfib_table_entry_update (fib_index, prefix, + MFIB_SOURCE_API, + rpf_id, entry_flags); goto done; } if (is_add) { - mfib_table_entry_path_update (fib_index, prefix, - MFIB_SOURCE_API, &path, itf_flags); + mfib_entry_index = mfib_table_entry_path_update (fib_index, prefix, + MFIB_SOURCE_API, + &path, itf_flags); } else { @@ -1250,12 +1254,14 @@ mroute_add_del_handler (u8 is_add, done: stats_dsunlock (); - return (0); + return (mfib_entry_index); } static int -api_mroute_add_del_t_handler (vl_api_ip_mroute_add_del_t * mp) +api_mroute_add_del_t_handler (vl_api_ip_mroute_add_del_t * mp, + u32 * stats_index) { + fib_node_index_t mfib_entry_index; fib_protocol_t fproto; dpo_proto_t nh_proto; ip46_address_t nh; @@ -1295,32 +1301,43 @@ api_mroute_add_del_t_handler (vl_api_ip_mroute_add_del_t * mp) clib_memcpy (&nh.ip6, mp->nh_address, sizeof (nh.ip6)); } - return (mroute_add_del_handler (mp->is_add, - mp->is_local, - fib_index, &pfx, - nh_proto, - ntohl (mp->entry_flags), - ntohl (mp->rpf_id), - ntohl (mp->next_hop_sw_if_index), - &nh, - ntohl (mp->itf_flags), - ntohl (mp->bier_imp))); + mfib_entry_index = mroute_add_del_handler (mp->is_add, + mp->is_local, + fib_index, &pfx, + nh_proto, + ntohl (mp->entry_flags), + ntohl (mp->rpf_id), + ntohl (mp->next_hop_sw_if_index), + &nh, + ntohl (mp->itf_flags), + ntohl (mp->bier_imp)); + + if (~0 != mfib_entry_index) + *stats_index = mfib_entry_get_stats_index (mfib_entry_index); + + return (rv); } void vl_api_ip_mroute_add_del_t_handler (vl_api_ip_mroute_add_del_t * mp) { vl_api_ip_mroute_add_del_reply_t *rmp; + vnet_main_t *vnm; + u32 stats_index; int rv; - vnet_main_t *vnm = vnet_get_main (); + vnm = vnet_get_main (); vnm->api_errno = 0; + stats_index = ~0; - rv = api_mroute_add_del_t_handler (mp); + rv = api_mroute_add_del_t_handler (mp, &stats_index); - rv = (rv == 0) ? vnm->api_errno : rv; - - REPLY_MACRO (VL_API_IP_MROUTE_ADD_DEL_REPLY); + /* *INDENT-OFF* */ + REPLY_MACRO2 (VL_API_IP_MROUTE_ADD_DEL_REPLY, + ({ + rmp->stats_index = htonl (stats_index); + })); + /* *INDENT-ON* */ } static void diff --git a/src/vnet/mfib/mfib_entry.c b/src/vnet/mfib/mfib_entry.c index a88f375ec19..7427334fa17 100644 --- a/src/vnet/mfib/mfib_entry.c +++ b/src/vnet/mfib/mfib_entry.c @@ -1106,6 +1106,16 @@ mfib_entry_last_lock_gone (fib_node_t *node) pool_put(mfib_entry_pool, mfib_entry); } +u32 +mfib_entry_get_stats_index (fib_node_index_t fib_entry_index) +{ + mfib_entry_t *mfib_entry; + + mfib_entry = mfib_entry_get(fib_entry_index); + + return (mfib_entry->mfe_rep.dpoi_index); +} + /* * mfib_entry_back_walk_notify * diff --git a/src/vnet/mfib/mfib_entry.h b/src/vnet/mfib/mfib_entry.h index a1d5acf9066..880c1e2933c 100644 --- a/src/vnet/mfib/mfib_entry.h +++ b/src/vnet/mfib/mfib_entry.h @@ -132,6 +132,7 @@ extern void mfib_entry_get_prefix(fib_node_index_t fib_entry_index, extern u32 mfib_entry_get_fib_index(fib_node_index_t fib_entry_index); extern int mfib_entry_is_sourced(fib_node_index_t fib_entry_index, mfib_source_t source); +extern u32 mfib_entry_get_stats_index(fib_node_index_t fib_entry_index); extern const dpo_id_t*mfib_entry_contribute_ip_forwarding( fib_node_index_t mfib_entry_index); diff --git a/test/test_ip_mcast.py b/test/test_ip_mcast.py index 64eb304a29e..1a39e9a9d81 100644 --- a/test/test_ip_mcast.py +++ b/test/test_ip_mcast.py @@ -273,6 +273,9 @@ class TestIPMcast(VppTestCase): self.pg_enable_capture(self.pg_interfaces) self.pg_start() + self.assertEqual(route_1_1_1_1_232_1_1_1.get_stats()['packets'], + len(tx)) + # We expect replications on Pg1->7 self.verify_capture_ip4(self.pg1, tx) self.verify_capture_ip4(self.pg2, tx) @@ -299,6 +302,9 @@ class TestIPMcast(VppTestCase): self.verify_capture_ip4(self.pg1, tx) self.verify_capture_ip4(self.pg2, tx) + self.assertEqual(route_1_1_1_1_232_1_1_1.get_stats()['packets'], + 2*len(tx)) + # no replications on Pg0 self.pg0.assert_nothing_captured( remark="IP multicast packets forwarded on PG0") @@ -339,6 +345,7 @@ class TestIPMcast(VppTestCase): # We expect replications on Pg1 only self.verify_capture_ip4(self.pg1, tx) + self.assertEqual(route_232.get_stats()['packets'], len(tx)) # no replications on Pg0, Pg2 not Pg3 self.pg0.assert_nothing_captured( diff --git a/test/vpp_ip_route.py b/test/vpp_ip_route.py index d24e4b1e487..00a79f44232 100644 --- a/test/vpp_ip_route.py +++ b/test/vpp_ip_route.py @@ -362,18 +362,19 @@ class VppIpMRoute(VppObject): def add_vpp_config(self): for path in self.paths: - self._test.vapi.ip_mroute_add_del(self.src_addr, - self.grp_addr, - self.grp_addr_len, - self.e_flags, - path.proto, - path.nh_itf, - path.nh_addr, - path.nh_i_flags, - bier_imp=path.bier_imp, - rpf_id=self.rpf_id, - table_id=self.table_id, - is_ipv6=self.is_ip6) + r = self._test.vapi.ip_mroute_add_del(self.src_addr, + self.grp_addr, + self.grp_addr_len, + self.e_flags, + path.proto, + path.nh_itf, + path.nh_addr, + path.nh_i_flags, + bier_imp=path.bier_imp, + rpf_id=self.rpf_id, + table_id=self.table_id, + is_ipv6=self.is_ip6) + self.stats_index = r.stats_index self._test.registry.register(self, self._test.logger) def remove_vpp_config(self): @@ -459,6 +460,10 @@ class VppIpMRoute(VppObject): inet_ntop(AF_INET, self.grp_addr), self.grp_addr_len)) + def get_stats(self): + c = self._test.statistics.get_counter("/net/mroute") + return c[0][self.stats_index] + class VppMFibSignal(object): def __init__(self, test, route, interface, packet): |