Skip to content

Commit

Permalink
ip: add tracing for ip nodes
Browse files Browse the repository at this point in the history
Implement tracing functions for ip nodes.
Update tests to enable and show traces.

Signed-off-by: Christophe Fontaine <cfontain@redhat.com>
  • Loading branch information
christophefontaine committed Oct 11, 2024
1 parent c5a44ad commit 09e1c0e
Show file tree
Hide file tree
Showing 8 changed files with 109 additions and 7 deletions.
9 changes: 9 additions & 0 deletions modules/ip/datapath/gr_ip4_datapath.h
Original file line number Diff line number Diff line change
Expand Up @@ -57,4 +57,13 @@ static inline void ip_set_fields(struct rte_ipv4_hdr *ip, struct ip_local_mbuf_d
#define GR_IP_ICMP_DEST_UNREACHABLE 3
#define GR_IP_ICMP_TTL_EXCEEDED 11

struct trace_ip_data {
ip4_addr_t src;
ip4_addr_t dst;
uint8_t proto;
uint8_t ttl;
};

int format_ip_data(void *data, char *buf, size_t);

#endif
5 changes: 5 additions & 0 deletions modules/ip/datapath/ip_error.c
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@
#include <gr_ip4_datapath.h>
#include <gr_log.h>
#include <gr_mbuf.h>
#include <gr_trace.h>

#include <rte_common.h>
#include <rte_graph_worker.h>
Expand Down Expand Up @@ -38,6 +39,7 @@ ip_error_process(struct rte_graph *graph, struct rte_node *node, void **objs, ui

ip = rte_pktmbuf_mtod(mbuf, struct rte_ipv4_hdr *);
icmp = (struct rte_icmp_hdr *)rte_pktmbuf_prepend(mbuf, sizeof(*icmp));

if (unlikely(icmp == NULL)) {
edge = NO_HEADROOM;
goto next;
Expand Down Expand Up @@ -71,6 +73,9 @@ ip_error_process(struct rte_graph *graph, struct rte_node *node, void **objs, ui

edge = ICMP_OUTPUT;
next:
if (unlikely(gr_mbuf_trace_is_set(mbuf))) {
gr_trace_add(node, mbuf, 0);
}
rte_node_enqueue_x1(graph, node, edge, mbuf);
}

Expand Down
12 changes: 12 additions & 0 deletions modules/ip/datapath/ip_forward.c
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,8 @@
// Copyright (c) 2024 Robin Jarry

#include <gr_graph.h>
#include <gr_ip4_datapath.h>
#include <gr_trace.h>

#include <rte_fib.h>
#include <rte_graph_worker.h>
Expand Down Expand Up @@ -33,6 +35,15 @@ ip_forward_process(struct rte_graph *graph, struct rte_node *node, void **objs,
csum = ip->hdr_checksum + RTE_BE16(0x0100);
csum += csum >= 0xffff;
ip->hdr_checksum = csum;

if (unlikely(gr_mbuf_trace_is_set(mbuf))) {
struct trace_ip_data *t = gr_trace_add(node, mbuf, sizeof(*t));
t->src = ip->src_addr;
t->dst = ip->dst_addr;
t->proto = ip->next_proto_id;
t->ttl = ip->time_to_live;
}

rte_node_enqueue_x1(graph, node, OUTPUT, mbuf);
}

Expand All @@ -53,6 +64,7 @@ static struct rte_node_register forward_node = {

static struct gr_node_info info = {
.node = &forward_node,
.ext_funcs.format_trace = format_ip_data,
};

GR_NODE_REGISTER(info);
58 changes: 58 additions & 0 deletions modules/ip/datapath/ip_input.c
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
#include <gr_ip4_control.h>
#include <gr_ip4_datapath.h>
#include <gr_log.h>
#include <gr_trace.h>

#include <rte_byteorder.h>
#include <rte_errno.h>
Expand All @@ -26,6 +27,55 @@ enum edges {
EDGE_COUNT,
};

int format_ip_data(void *data, char *buf, size_t len) {
struct trace_ip_data *t = data;
static const char *protos[UINT8_MAX] = {
[0] = "IPv6 Hop-by-Hop",
[1] = "ICMP",
[2] = "IGMP",
[4] = "IP in IP",
[6] = "TCP",
[17] = "UDP",
[27] = "Reliable Data Protocol",
[41] = "IPv6 Encapsulation",
[43] = "IPv6 Routing Header",
[44] = "IPv6 Fragment Header",
[47] = "GRE",
[50] = "ESP",
[51] = "Authentication Header",
[58] = "IPv6 ICMP",
[59] = "IPv6 No Next Header",
[60] = "IPv6 Destination Options",
[89] = "OSPF",
[112] = "VRRP",
[132] = "SCTP",
[136] = "UDP Lite",
[137] = "MPLS In IP",
[145] = "NSH",
};

if (protos[t->proto] == 0)
return snprintf(
buf,
len,
IP4_ADDR_FMT " -> " IP4_ADDR_FMT " next proto: %d ttl %d",
IP4_ADDR_SPLIT(&t->src),
IP4_ADDR_SPLIT(&t->dst),
t->proto,
t->ttl
);
else
return snprintf(
buf,
len,
IP4_ADDR_FMT " -> " IP4_ADDR_FMT " next proto: %s ttl %d",
IP4_ADDR_SPLIT(&t->src),
IP4_ADDR_SPLIT(&t->dst),
protos[t->proto],
t->ttl
);
}

static uint16_t
ip_input_process(struct rte_graph *graph, struct rte_node *node, void **objs, uint16_t nb_objs) {
struct eth_input_mbuf_data *e;
Expand Down Expand Up @@ -111,6 +161,13 @@ ip_input_process(struct rte_graph *graph, struct rte_node *node, void **objs, ui
else
edge = FORWARD;
next:
if (unlikely(gr_mbuf_trace_is_set(mbuf))) {
struct trace_ip_data *t = gr_trace_add(node, mbuf, sizeof(*t));
t->src = ip->src_addr;
t->dst = ip->dst_addr;
t->proto = ip->next_proto_id;
t->ttl = ip->time_to_live;
}
// Store the resolved next hop for ip_output to avoid a second route lookup.
d->nh = nh;
d->input_iface = iface;
Expand Down Expand Up @@ -143,6 +200,7 @@ static struct rte_node_register input_node = {
static struct gr_node_info info = {
.node = &input_node,
.register_callback = ip_input_register,
.ext_funcs.format_trace = format_ip_data,
};

GR_NODE_REGISTER(info);
Expand Down
5 changes: 5 additions & 0 deletions modules/ip/datapath/ip_local.c
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
#include <gr_graph.h>
#include <gr_ip4_datapath.h>
#include <gr_log.h>
#include <gr_trace.h>

#include <rte_graph_worker.h>
#include <rte_ip.h>
Expand Down Expand Up @@ -34,6 +35,10 @@ static uint16_t ip_input_local_process(
for (i = 0; i < nb_objs; i++) {
mbuf = objs[i];
ip = rte_pktmbuf_mtod(mbuf, struct rte_ipv4_hdr *);

if (unlikely(gr_mbuf_trace_is_set(mbuf)))
gr_trace_add(node, mbuf, 0);

edge = edges[ip->next_proto_id];
if (edge != UNKNOWN_PROTO) {
const struct iface *iface = ip_output_mbuf_data(mbuf)->input_iface;
Expand Down
11 changes: 10 additions & 1 deletion modules/ip/datapath/ip_output.c
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@
#include <gr_ip4_datapath.h>
#include <gr_log.h>
#include <gr_mbuf.h>
#include <gr_trace.h>

#include <rte_byteorder.h>
#include <rte_ether.h>
Expand Down Expand Up @@ -86,8 +87,8 @@ ip_output_process(struct rte_graph *graph, struct rte_node *node, void **objs, u
for (i = 0; i < nb_objs; i++) {
mbuf = objs[i];
ip = rte_pktmbuf_mtod(mbuf, struct rte_ipv4_hdr *);

nh = ip_output_mbuf_data(mbuf)->nh;

if (nh == NULL) {
edge = NO_ROUTE;
goto next;
Expand Down Expand Up @@ -145,6 +146,13 @@ ip_output_process(struct rte_graph *graph, struct rte_node *node, void **objs, u
eth_data->iface = iface;
sent++;
next:
if (unlikely(gr_mbuf_trace_is_set(mbuf))) {
struct trace_ip_data *t = gr_trace_add(node, mbuf, sizeof(*t));
t->src = ip->src_addr;
t->dst = ip->dst_addr;
t->proto = ip->next_proto_id;
t->ttl = ip->time_to_live;
}
rte_node_enqueue_x1(graph, node, edge, mbuf);
}

Expand All @@ -165,6 +173,7 @@ static struct rte_node_register output_node = {

static struct gr_node_info info = {
.node = &output_node,
.ext_funcs.format_trace = format_ip_data,
};

GR_NODE_REGISTER(info);
Expand Down
6 changes: 4 additions & 2 deletions smoke/ip_forward_test.sh
Original file line number Diff line number Diff line change
Expand Up @@ -7,8 +7,8 @@
p0=${run_id}0
p1=${run_id}1

grcli add interface port $p0 devargs net_tap0,iface=$p0 mac f0:0d:ac:dc:00:00
grcli add interface port $p1 devargs net_tap1,iface=$p1 mac f0:0d:ac:dc:00:01
grcli add interface port $p0 devargs net_tap0,iface=$p0 mac f0:0d:ac:dc:00:00 trace on
grcli add interface port $p1 devargs net_tap1,iface=$p1 mac f0:0d:ac:dc:00:01 trace on
grcli add ip address 172.16.0.1/24 iface $p0
grcli add ip address 172.16.1.1/24 iface $p1

Expand All @@ -30,3 +30,5 @@ ip netns exec $p0 ping -i0.01 -c3 172.16.0.1
ip netns exec $p1 ping -i0.01 -c3 172.16.1.1
ip netns exec $p0 traceroute -N1 172.16.1.2
ip netns exec $p1 traceroute -N1 172.16.0.2

grcli show trace
10 changes: 6 additions & 4 deletions smoke/vlan_forward_test.sh
Original file line number Diff line number Diff line change
Expand Up @@ -9,10 +9,10 @@ p1=${run_id}1
v0=$p0.42
v1=$p1.43

grcli add interface port $p0 devargs net_tap0,iface=$p0 mac f0:0d:ac:dc:00:00
grcli add interface port $p1 devargs net_tap1,iface=$p1 mac f0:0d:ac:dc:00:01
grcli add interface vlan $v0 parent $p0 vlan_id 42
grcli add interface vlan $v1 parent $p1 vlan_id 43
grcli add interface port $p0 devargs net_tap0,iface=$p0 mac f0:0d:ac:dc:00:00 trace on
grcli add interface port $p1 devargs net_tap1,iface=$p1 mac f0:0d:ac:dc:00:01 trace on
grcli add interface vlan $v0 parent $p0 vlan_id 42 trace on
grcli add interface vlan $v1 parent $p1 vlan_id 43 trace on
grcli add ip address 172.16.0.1/24 iface $v0
grcli add ip address 172.16.1.1/24 iface $v1

Expand All @@ -33,3 +33,5 @@ done

ip netns exec $p0 ping -i0.01 -c3 172.16.1.2
ip netns exec $p1 ping -i0.01 -c3 172.16.0.2

grcli show trace

0 comments on commit 09e1c0e

Please sign in to comment.