mirror of
https://git.proxmox.com/git/mirror_frr
synced 2025-08-04 20:18:54 +00:00
Merge pull request #9689 from AnuradhaKaruppiah/bgp-evpn-lttng
bgpd: initial batch of evpn lttng tracepoints
This commit is contained in:
commit
a3e036f36a
@ -54,6 +54,7 @@
|
||||
#include "bgpd/bgp_mac.h"
|
||||
#include "bgpd/bgp_vty.h"
|
||||
#include "bgpd/bgp_nht.h"
|
||||
#include "bgpd/bgp_trace.h"
|
||||
|
||||
/*
|
||||
* Definitions and external declarations.
|
||||
@ -653,6 +654,9 @@ static int bgp_zebra_send_remote_macip(struct bgp *bgp, struct bgpevpn *vpn,
|
||||
&p->prefix.macip_addr.mac, &p->prefix.macip_addr.ip,
|
||||
flags, seq, &remote_vtep_ip);
|
||||
|
||||
frrtrace(5, frr_bgp, evpn_mac_ip_zsend, add, vpn, p, remote_vtep_ip,
|
||||
esi);
|
||||
|
||||
return zclient_send_message(zclient);
|
||||
}
|
||||
|
||||
@ -703,6 +707,8 @@ static int bgp_zebra_send_remote_vtep(struct bgp *bgp, struct bgpevpn *vpn,
|
||||
add ? "ADD" : "DEL", vpn->vni,
|
||||
&p->prefix.imet_addr.ip.ipaddr_v4);
|
||||
|
||||
frrtrace(3, frr_bgp, evpn_bum_vtep_zsend, add, vpn, p);
|
||||
|
||||
return zclient_send_message(zclient);
|
||||
}
|
||||
|
||||
|
@ -50,6 +50,7 @@
|
||||
#include "bgpd/bgp_label.h"
|
||||
#include "bgpd/bgp_nht.h"
|
||||
#include "bgpd/bgp_mpath.h"
|
||||
#include "bgpd/bgp_trace.h"
|
||||
|
||||
static void bgp_evpn_local_es_down(struct bgp *bgp,
|
||||
struct bgp_evpn_es *es);
|
||||
@ -1225,6 +1226,8 @@ static struct bgp_evpn_es_vtep *bgp_evpn_es_vtep_new(struct bgp_evpn_es *es,
|
||||
|
||||
es_vtep->es = es;
|
||||
es_vtep->vtep_ip.s_addr = vtep_ip.s_addr;
|
||||
inet_ntop(AF_INET, &es_vtep->vtep_ip, es_vtep->vtep_str,
|
||||
sizeof(es_vtep->vtep_str));
|
||||
listnode_init(&es_vtep->es_listnode, es_vtep);
|
||||
listnode_add_sort(es->es_vtep_list, &es_vtep->es_listnode);
|
||||
|
||||
@ -1301,6 +1304,8 @@ static int bgp_zebra_send_remote_es_vtep(struct bgp *bgp,
|
||||
zlog_debug("Tx %s Remote ESI %s VTEP %pI4", add ? "ADD" : "DEL",
|
||||
es->esi_str, &es_vtep->vtep_ip);
|
||||
|
||||
frrtrace(3, frr_bgp, evpn_mh_vtep_zsend, add, es, es_vtep);
|
||||
|
||||
return zclient_send_message(zclient);
|
||||
}
|
||||
|
||||
@ -2522,6 +2527,8 @@ static void bgp_evpn_l3nhg_zebra_add_v4_or_v6(struct bgp_evpn_es_vrf *es_vrf,
|
||||
es_vrf->bgp_vrf->vrf_id,
|
||||
v4_nhg ? "v4_nhg" : "v6_nhg", nhg_id);
|
||||
|
||||
frrtrace(4, frr_bgp, evpn_mh_nhg_zsend, true, v4_nhg, nhg_id, es_vrf);
|
||||
|
||||
/* only the gateway ip changes for each NH. rest of the params
|
||||
* are constant
|
||||
*/
|
||||
@ -2558,6 +2565,8 @@ static void bgp_evpn_l3nhg_zebra_add_v4_or_v6(struct bgp_evpn_es_vrf *es_vrf,
|
||||
zlog_debug("nhg %u vtep %pI4 l3-svi %d", api_nhg.id,
|
||||
&es_vtep->vtep_ip,
|
||||
es_vrf->bgp_vrf->l3vni_svi_ifindex);
|
||||
|
||||
frrtrace(3, frr_bgp, evpn_mh_nh_zsend, nhg_id, es_vtep, es_vrf);
|
||||
}
|
||||
|
||||
if (!api_nhg.nexthop_num)
|
||||
@ -2603,6 +2612,10 @@ static void bgp_evpn_l3nhg_zebra_del_v4_or_v6(struct bgp_evpn_es_vrf *es_vrf,
|
||||
es_vrf->es->esi_str, es_vrf->bgp_vrf->vrf_id,
|
||||
v4_nhg ? "v4_nhg" : "v6_nhg", api_nhg.id);
|
||||
|
||||
|
||||
frrtrace(4, frr_bgp, evpn_mh_nhg_zsend, false, v4_nhg, api_nhg.id,
|
||||
es_vrf);
|
||||
|
||||
zclient_nhg_send(zclient, ZEBRA_NHG_DEL, &api_nhg);
|
||||
}
|
||||
|
||||
@ -4202,6 +4215,8 @@ static void bgp_evpn_nh_zebra_update_send(struct bgp_evpn_nh *nh, bool add)
|
||||
nh->bgp_vrf->name, nh->nh_str);
|
||||
}
|
||||
|
||||
frrtrace(2, frr_bgp, evpn_mh_nh_rmac_zsend, add, nh);
|
||||
|
||||
zclient_send_message(zclient);
|
||||
}
|
||||
|
||||
|
@ -145,6 +145,8 @@ struct bgp_evpn_es_vtep {
|
||||
struct bgp_evpn_es *es; /* parent ES */
|
||||
struct in_addr vtep_ip;
|
||||
|
||||
char vtep_str[INET6_ADDRSTRLEN];
|
||||
|
||||
uint32_t flags;
|
||||
/* Rxed a Type4 route from this PE */
|
||||
#define BGP_EVPNES_VTEP_ESR (1 << 0)
|
||||
|
@ -36,6 +36,9 @@
|
||||
#include "bgpd/bgpd.h"
|
||||
#include "bgpd/bgp_attr.h"
|
||||
#include "lib/stream.h"
|
||||
#include "bgpd/bgp_evpn_private.h"
|
||||
#include "bgpd/bgp_evpn_mh.h"
|
||||
|
||||
|
||||
/* clang-format off */
|
||||
|
||||
@ -244,6 +247,93 @@ TRACEPOINT_EVENT(
|
||||
)
|
||||
TRACEPOINT_LOGLEVEL(frr_bgp, bgp_dest_unlock, TRACE_INFO)
|
||||
|
||||
TRACEPOINT_EVENT(
|
||||
frr_bgp,
|
||||
evpn_mac_ip_zsend,
|
||||
TP_ARGS(int, add, struct bgpevpn *, vpn,
|
||||
const struct prefix_evpn *, pfx,
|
||||
struct in_addr, vtep, esi_t *, esi),
|
||||
TP_FIELDS(
|
||||
ctf_string(action, add ? "add" : "del")
|
||||
ctf_integer(vni_t, vni, vpn->vni)
|
||||
ctf_array(unsigned char, mac, &pfx->prefix.macip_addr.mac,
|
||||
sizeof(struct ethaddr))
|
||||
ctf_array(unsigned char, ip, &pfx->prefix.macip_addr.ip,
|
||||
sizeof(struct ipaddr))
|
||||
ctf_integer_network_hex(unsigned int, vtep, vtep.s_addr)
|
||||
ctf_array(unsigned char, esi, esi, sizeof(esi_t))
|
||||
)
|
||||
)
|
||||
TRACEPOINT_LOGLEVEL(frr_bgp, evpn_mac_ip_zsend, TRACE_INFO)
|
||||
|
||||
TRACEPOINT_EVENT(
|
||||
frr_bgp,
|
||||
evpn_bum_vtep_zsend,
|
||||
TP_ARGS(int, add, struct bgpevpn *, vpn,
|
||||
const struct prefix_evpn *, pfx),
|
||||
TP_FIELDS(
|
||||
ctf_string(action, add ? "add" : "del")
|
||||
ctf_integer(vni_t, vni, vpn->vni)
|
||||
ctf_integer_network_hex(unsigned int, vtep,
|
||||
pfx->prefix.imet_addr.ip.ipaddr_v4.s_addr)
|
||||
)
|
||||
)
|
||||
TRACEPOINT_LOGLEVEL(frr_bgp, evpn_bum_vtep_zsend, TRACE_INFO)
|
||||
|
||||
TRACEPOINT_EVENT(
|
||||
frr_bgp,
|
||||
evpn_mh_vtep_zsend,
|
||||
TP_ARGS(bool, add, struct bgp_evpn_es *, es,
|
||||
struct bgp_evpn_es_vtep *, es_vtep),
|
||||
TP_FIELDS(
|
||||
ctf_string(action, add ? "add" : "del")
|
||||
ctf_string(esi, es->esi_str)
|
||||
ctf_string(vtep, es_vtep->vtep_str)
|
||||
)
|
||||
)
|
||||
TRACEPOINT_LOGLEVEL(frr_bgp, evpn_mh_vtep_zsend, TRACE_INFO)
|
||||
|
||||
TRACEPOINT_EVENT(
|
||||
frr_bgp,
|
||||
evpn_mh_nhg_zsend,
|
||||
TP_ARGS(bool, add, bool, type_v4, uint32_t, nhg_id,
|
||||
struct bgp_evpn_es_vrf *, es_vrf),
|
||||
TP_FIELDS(
|
||||
ctf_string(action, add ? "add" : "del")
|
||||
ctf_string(type, type_v4 ? "v4" : "v6")
|
||||
ctf_integer(unsigned int, nhg, nhg_id)
|
||||
ctf_string(esi, es_vrf->es->esi_str)
|
||||
ctf_integer(int, vrf, es_vrf->bgp_vrf->vrf_id)
|
||||
)
|
||||
)
|
||||
TRACEPOINT_LOGLEVEL(frr_bgp, evpn_mh_nhg_zsend, TRACE_INFO)
|
||||
|
||||
TRACEPOINT_EVENT(
|
||||
frr_bgp,
|
||||
evpn_mh_nh_zsend,
|
||||
TP_ARGS(uint32_t, nhg_id, struct bgp_evpn_es_vtep *, vtep,
|
||||
struct bgp_evpn_es_vrf *, es_vrf),
|
||||
TP_FIELDS(
|
||||
ctf_integer(unsigned int, nhg, nhg_id)
|
||||
ctf_string(vtep, vtep->vtep_str)
|
||||
ctf_integer(int, svi, es_vrf->bgp_vrf->l3vni_svi_ifindex)
|
||||
)
|
||||
)
|
||||
TRACEPOINT_LOGLEVEL(frr_bgp, evpn_mh_nh_zsend, TRACE_INFO)
|
||||
|
||||
TRACEPOINT_EVENT(
|
||||
frr_bgp,
|
||||
evpn_mh_nh_rmac_zsend,
|
||||
TP_ARGS(bool, add, struct bgp_evpn_nh *, nh),
|
||||
TP_FIELDS(
|
||||
ctf_string(action, add ? "add" : "del")
|
||||
ctf_integer(int, vrf, nh->bgp_vrf->vrf_id)
|
||||
ctf_string(nh, nh->nh_str)
|
||||
ctf_array(unsigned char, rmac, &nh->rmac,
|
||||
sizeof(struct ethaddr))
|
||||
)
|
||||
)
|
||||
TRACEPOINT_LOGLEVEL(frr_bgp, evpn_nh_rmac_zsend, TRACE_INFO)
|
||||
/* clang-format on */
|
||||
|
||||
#include <lttng/tracepoint-event.h>
|
||||
|
163
tools/frr_babeltrace.py
Executable file
163
tools/frr_babeltrace.py
Executable file
@ -0,0 +1,163 @@
|
||||
#!/usr/bin/env python3
|
||||
'''
|
||||
Usage: frr_babeltrace.py trace_path
|
||||
|
||||
FRR pushes data into lttng tracepoints in the least overhead way possible
|
||||
i.e. as binary-data/crf_arrays. These traces need to be converted into pretty
|
||||
strings for easy greping etc. This script is a babeltrace python plugin for
|
||||
that pretty printing.
|
||||
|
||||
Copyright (C) 2021 NVIDIA Corporation
|
||||
Anuradha Karuppiah
|
||||
|
||||
This program is free software; you can redistribute it and/or modify it
|
||||
under the terms of the GNU General Public License as published by the Free
|
||||
Software Foundation; either version 2 of the License, or (at your option)
|
||||
any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
|
||||
more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License along
|
||||
with this program; see the file COPYING; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
'''
|
||||
|
||||
import ipaddress
|
||||
import socket
|
||||
import sys
|
||||
|
||||
import babeltrace
|
||||
|
||||
########################### common parsers - start ############################
|
||||
def print_ip_addr(field_val):
|
||||
'''
|
||||
pretty print "struct ipaddr"
|
||||
'''
|
||||
if field_val[0] == socket.AF_INET:
|
||||
addr = [str(fv) for fv in field_val[4:8]]
|
||||
return str(ipaddress.IPv4Address('.'.join(addr)))
|
||||
|
||||
if field_val[0] == socket.AF_INET6:
|
||||
tmp = ''.join('%02x' % fb for fb in field_val[4:])
|
||||
addr = []
|
||||
while tmp:
|
||||
addr.append(tmp[:4])
|
||||
tmp = tmp[4:]
|
||||
addr = ':'.join(addr)
|
||||
return str(ipaddress.IPv6Address(addr))
|
||||
|
||||
if not field_val[0]:
|
||||
return ''
|
||||
|
||||
return field_val
|
||||
|
||||
|
||||
def print_mac(field_val):
|
||||
'''
|
||||
pretty print "u8 mac[6]"
|
||||
'''
|
||||
return ':'.join('%02x' % fb for fb in field_val)
|
||||
|
||||
def print_net_ipv4_addr(field_val):
|
||||
'''
|
||||
pretty print ctf_integer_network ipv4
|
||||
'''
|
||||
return str(ipaddress.IPv4Address(field_val))
|
||||
|
||||
def print_esi(field_val):
|
||||
'''
|
||||
pretty print ethernet segment id, esi_t
|
||||
'''
|
||||
return ':'.join('%02x' % fb for fb in field_val)
|
||||
|
||||
def get_field_list(event):
|
||||
'''
|
||||
only fetch fields added via the TP, skip metadata etc.
|
||||
'''
|
||||
return event.field_list_with_scope(babeltrace.CTFScope.EVENT_FIELDS)
|
||||
|
||||
def parse_event(event, field_parsers):
|
||||
'''
|
||||
Wild card event parser; doesn't make things any prettier
|
||||
'''
|
||||
field_list = get_field_list(event)
|
||||
field_info = {}
|
||||
for field in field_list:
|
||||
if field in field_parsers:
|
||||
field_parser = field_parsers.get(field)
|
||||
field_info[field] = field_parser(event.get(field))
|
||||
else:
|
||||
field_info[field] = event.get(field)
|
||||
print(event.name, field_info)
|
||||
############################ common parsers - end #############################
|
||||
|
||||
############################ evpn parsers - start #############################
|
||||
def parse_frr_bgp_evpn_mac_ip_zsend(event):
|
||||
'''
|
||||
bgp evpn mac-ip parser; raw format -
|
||||
ctf_array(unsigned char, mac, &pfx->prefix.macip_addr.mac,
|
||||
sizeof(struct ethaddr))
|
||||
ctf_array(unsigned char, ip, &pfx->prefix.macip_addr.ip,
|
||||
sizeof(struct ipaddr))
|
||||
ctf_integer_network_hex(unsigned int, vtep, vtep.s_addr)
|
||||
ctf_array(unsigned char, esi, esi, sizeof(esi_t))
|
||||
'''
|
||||
field_parsers = {'ip': print_ip_addr,
|
||||
'mac': print_mac,
|
||||
'esi': print_esi,
|
||||
'vtep': print_net_ipv4_addr}
|
||||
|
||||
parse_event(event, field_parsers)
|
||||
|
||||
def parse_frr_bgp_evpn_bum_vtep_zsend(event):
|
||||
'''
|
||||
bgp evpn bum-vtep parser; raw format -
|
||||
ctf_integer_network_hex(unsigned int, vtep,
|
||||
pfx->prefix.imet_addr.ip.ipaddr_v4.s_addr)
|
||||
|
||||
'''
|
||||
field_parsers = {'vtep': print_net_ipv4_addr}
|
||||
|
||||
parse_event(event, field_parsers)
|
||||
|
||||
def parse_frr_bgp_evpn_mh_nh_rmac_send(event):
|
||||
'''
|
||||
bgp evpn nh-rmac parser; raw format -
|
||||
ctf_array(unsigned char, rmac, &nh->rmac, sizeof(struct ethaddr))
|
||||
'''
|
||||
field_parsers = {'rmac': print_mac}
|
||||
|
||||
parse_event(event, field_parsers)
|
||||
|
||||
############################ evpn parsers - end #############################
|
||||
|
||||
def main():
|
||||
'''
|
||||
FRR lttng trace output parser; babel trace plugin
|
||||
'''
|
||||
event_parsers = {'frr_bgp:evpn_mac_ip_zsend':
|
||||
parse_frr_bgp_evpn_mac_ip_zsend,
|
||||
'frr_bgp:evpn_bum_vtep_zsend':
|
||||
parse_frr_bgp_evpn_bum_vtep_zsend,
|
||||
'frr_bgp:evpn_mh_nh_rmac_zsend':
|
||||
parse_frr_bgp_evpn_mh_nh_rmac_send}
|
||||
|
||||
# get the trace path from the first command line argument
|
||||
trace_path = sys.argv[1]
|
||||
|
||||
# grab events
|
||||
trace_collection = babeltrace.TraceCollection()
|
||||
trace_collection.add_traces_recursive(trace_path, 'ctf')
|
||||
|
||||
for event in trace_collection.events:
|
||||
if event.name in event_parsers:
|
||||
event_parser = event_parsers.get(event.name)
|
||||
event_parser(event)
|
||||
else:
|
||||
parse_event(event, {})
|
||||
|
||||
if __name__ == '__main__':
|
||||
main()
|
Loading…
Reference in New Issue
Block a user