[lttng-dev] [RFC-patch 4/5] Add some extra data to net_* tracepoints

Geneviève Bastien gbastien+lttng at versatic.net
Wed Apr 24 16:14:19 EDT 2013


Add some packet header information to the tracepoint when available:
* ipv4/ipv6 network header
* tcp transport header

Signed-off-by: Geneviève Bastien <gbastien+lttng at versatic.net>
---
 instrumentation/events/lttng-module/net.h | 244 +++++++++++++++++++++++++++++-
 1 file changed, 237 insertions(+), 7 deletions(-)

diff --git a/instrumentation/events/lttng-module/net.h b/instrumentation/events/lttng-module/net.h
index e552cf7..b31aea4 100644
--- a/instrumentation/events/lttng-module/net.h
+++ b/instrumentation/events/lttng-module/net.h
@@ -7,8 +7,74 @@
 #include <linux/skbuff.h>
 #include <linux/netdevice.h>
 #include <linux/ip.h>
+#include <linux/tcp.h>
+#include <linux/ipv6.h>
 #include <linux/tracepoint.h>
 #include <linux/version.h>
+#include <net/sock.h>
+
+#ifndef _TRACE_NET_DEF_
+#define _TRACE_NET_DEF_
+
+enum network_header_types {
+	nhtype_none,
+	nhtype_ip,
+	nhtype_ip6,
+	NR_NH_TYPES,
+};
+
+enum transport_header_types {
+	thtype_none,
+	thtype_tcp,
+	NR_TH_TYPES,
+};
+
+static inline unsigned char __get_send_network_header_type(struct sk_buff *skb)
+{
+	if (skb->sk) {
+		if (skb->sk->sk_family == PF_INET)
+			return nhtype_ip;
+		else if (skb->sk->sk_family == PF_INET6)
+			return nhtype_ip6;
+	}
+	return nhtype_none;
+}
+
+static inline unsigned char __get_send_transport_header_type(struct sk_buff *skb)
+{
+	if (skb->sk) {
+		if (skb->sk->sk_protocol == IPPROTO_TCP)
+			return thtype_tcp;
+	}
+	return thtype_none;
+}
+
+static inline unsigned char __get_recv_network_header_type(struct sk_buff *skb)
+{
+	if (skb_network_header(skb) != skb->head) {
+		if (skb->protocol == htons(ETH_P_IPV6))
+			return nhtype_ip6;
+		else if (skb->protocol == htons(ETH_P_IP))
+			return nhtype_ip;
+	}
+	return nhtype_none;
+}
+
+static inline unsigned char __get_recv_transport_header_type(struct sk_buff *skb)
+{
+	if (skb_network_header(skb) != skb->head) {
+		if (!(skb->transport_header <= skb->network_header)) {
+			if ((skb->protocol == htons(ETH_P_IP) &&
+					(ip_hdr(skb)->protocol == IPPROTO_TCP)) ||
+				(skb->protocol == htons(ETH_P_IPV6) &&
+					(ipv6_hdr(skb)->nexthdr == IPPROTO_TCP)))
+				return thtype_tcp;
+		}
+	}
+	return thtype_none;
+}
+
+#endif /* _TRACE_NET_DEF_ */
 
 TRACE_EVENT(net_dev_xmit,
 
@@ -57,43 +123,207 @@ TRACE_EVENT(net_dev_xmit,
 		__get_str(name), __entry->skbaddr, __entry->len, __entry->rc)
 )
 
-DECLARE_EVENT_CLASS(net_dev_template,
+#ifdef TRACE_METADATA
+
+TRACEPOINT_ENUM(net, network_header, TP_TYPE(unsigned char),
+	TP_ENUM(
+		V(nhtype_none)
+		V(nhtype_ip)
+		V(nhtype_ip6)
+	)
+)
+
+TRACEPOINT_ENUM(net, transport_header, TP_TYPE(unsigned char),
+	TP_ENUM(
+		V(thtype_none)
+		V(thtype_tcp)
+	)
+)
+
+TRACEPOINT_STRUCT_RAW(net, empty_struct,
+
+	TP_PROTO(struct sk_buff *skb),
+
+	TP_ARGS(skb),
+
+	TP_FIELDS(
+	)
+)
+
+TRACEPOINT_STRUCT_RAW(net, ip_fields,
+
+	TP_PROTO(struct iphdr *hdr),
+
+	TP_ARGS(hdr),
+
+	TP_FIELDS(__field_hex(unsigned char,	ihl_version)
+		__field_network(unsigned char, tos)
+		__field_network(unsigned short, tot_len)
+		__field_network_hex(unsigned short, id)
+		__field_network(unsigned short, frag_off)
+		__field_network(unsigned char, ttl)
+		__field_network_hex(unsigned char, protocol)
+		__field_network_hex(unsigned short, checksum)
+		__field_network_hex(unsigned int, saddr)
+		__field_network_hex(unsigned int, daddr)
+	)
+)
+
+TRACEPOINT_STRUCT_RAW(net, ipv6_fields,
+
+	TP_PROTO(struct ipv6hdr *hdr),
+
+	TP_ARGS(hdr),
+
+	TP_FIELDS(__field_hex(unsigned char,	prio_version)
+		__array(char, flow_lbl, 3)
+		__field_network(unsigned short, payload_len)
+		__field_network_hex(unsigned char, nexthdr)
+		__field_network(unsigned char, hop_limit)
+		__array_hex(unsigned short, saddr, 8)
+		__array_hex(unsigned short, daddr, 8)
+	)
+)
+
+TRACEPOINT_STRUCT_RAW(net, tcp_fields,
+
+	TP_PROTO(struct tcphdr *hdr),
+
+	TP_ARGS(hdr),
+
+	TP_FIELDS(__field_network(unsigned short,	source)
+		__field_network(unsigned short,	dest)
+		__field_network_hex(unsigned int,	seq)
+		__field_network_hex(unsigned int,	ack_seq)
+		__field_network_hex(unsigned short,	flags)
+		__field_network_hex(unsigned short, window)
+		__field_network_hex(unsigned short, check)
+		__field_network_hex(unsigned short, urg_ptr)
+	)
+)
+
+TRACEPOINT_VARIANT(net, network,
+
+	TP_PROTO(unsigned char enum_val, struct sk_buff *skb),
+
+	TP_ARGS(skb),
+
+	net, network_header, enum_val,
+
+	TP_VARIANTS(
+		TP_VARIANT(nhtype_none, __struct(net, empty_struct, nhtype_none, skb))
+		TP_VARIANT(nhtype_ip, __struct(net, ip_fields, nhtype_ip, ip_hdr(skb)))
+		TP_VARIANT(nhtype_ip6, __struct(net, ipv6_fields, nhtype_ip6, ipv6_hdr(skb)))
+	),
+
+	TP_fast_assign(
+		TP_variants_assign(
+			TP_variant_assign(nhtype_none, tp_memcpy_struct(net, empty_struct, nhtype_none, skb))
+			TP_variant_assign(nhtype_ip, tp_memcpy_struct(net, ip_fields, nhtype_ip, ip_hdr(skb)))
+			TP_variant_assign(nhtype_ip6, tp_memcpy_struct(net, ipv6_fields, nhtype_ip6, ipv6_hdr(skb)))
+		)
+	)
+)
+
+TRACEPOINT_VARIANT(net, transport,
+
+	TP_PROTO(unsigned char enum_val, struct sk_buff *skb),
+
+	TP_ARGS(skb),
+
+	net, transport_header, enum_val,
+
+	TP_VARIANTS(
+		TP_VARIANT(thtype_none, __struct(net, empty_struct, thtype_none, skb))
+		TP_VARIANT(thtype_tcp, __struct(net, tcp_fields, thtype_tcp, tcp_hdr(skb)))
+	),
+
+	TP_fast_assign(
+		TP_variants_assign(
+			TP_variant_assign(thtype_none, tp_memcpy_struct(net, empty_struct, thtype_none, skb))
+			TP_variant_assign(thtype_tcp, tp_memcpy_struct(net, tcp_fields, thtype_tcp, tcp_hdr(skb)))
+		)
+	)
+)
+
+#endif
+
+DECLARE_EVENT_CLASS(net_dev_template_send,
 
 	TP_PROTO(struct sk_buff *skb),
 
 	TP_ARGS(skb),
 
 	TP_STRUCT__entry(
-		__field(	void *,		skbaddr		)
-		__field(	unsigned int,	len		)
-		__string(	name,		skb->dev->name	)
+		__field(void *, skbaddr)
+		__field(unsigned int, len)
+		__string(name, skb->dev->name)
+		__field_enum(net, network_header, unsigned char, network_header)
+		__variant(net, network, network_fields, network_header, __get_send_network_header_type(skb), skb)
+		__field_enum(net, transport_header, unsigned char, transport_header)
+		__variant(net, transport, transport_fields, transport_header, __get_send_transport_header_type(skb), skb)
+	),
+
+	TP_fast_assign(
+		tp_assign(skbaddr, skb)
+		tp_assign(len, skb->len)
+		tp_strcpy(name, skb->dev->name)
+		tp_assign(network_header, __get_send_network_header_type(skb))
+		tp_assign_variant(net, network, network_fields, __get_send_network_header_type(skb), skb)
+		tp_assign(transport_header, __get_send_transport_header_type(skb))
+		tp_assign_variant(net, transport, transport_fields, __get_send_transport_header_type(skb), skb)
+	),
+
+	TP_printk("dev=%s skbaddr=%p len=%u",
+		__get_str(name), __entry->skbaddr, __entry->len)
+)
+
+DECLARE_EVENT_CLASS(net_dev_template_recv,
+
+	TP_PROTO(struct sk_buff *skb),
+
+	TP_ARGS(skb),
+
+	TP_STRUCT__entry(
+		__field(void *, skbaddr)
+		__field(unsigned int, len)
+		__string(name, skb->dev->name)
+		__field_enum(net, network_header, unsigned char, network_header)
+		__variant(net, network, network_fields, network_header, __get_recv_network_header_type(skb), skb)
+		__field_enum(net, transport_header, unsigned char, transport_header)
+		__variant(net, transport, transport_fields, transport_header, __get_recv_transport_header_type(skb), skb)
+
 	),
 
 	TP_fast_assign(
 		tp_assign(skbaddr, skb)
 		tp_assign(len, skb->len)
 		tp_strcpy(name, skb->dev->name)
+		tp_assign(network_header, __get_recv_network_header_type(skb))
+		tp_assign_variant(net, network, network_fields, __get_recv_network_header_type(skb), skb)
+		tp_assign(transport_header, __get_recv_transport_header_type(skb))
+		tp_assign_variant(net, transport, transport_fields, __get_recv_transport_header_type(skb), skb)
 	),
 
 	TP_printk("dev=%s skbaddr=%p len=%u",
 		__get_str(name), __entry->skbaddr, __entry->len)
 )
 
-DEFINE_EVENT(net_dev_template, net_dev_queue,
+DEFINE_EVENT(net_dev_template_send, net_dev_queue,
 
 	TP_PROTO(struct sk_buff *skb),
 
 	TP_ARGS(skb)
 )
 
-DEFINE_EVENT(net_dev_template, netif_receive_skb,
+DEFINE_EVENT(net_dev_template_recv, netif_receive_skb,
 
 	TP_PROTO(struct sk_buff *skb),
 
 	TP_ARGS(skb)
 )
 
-DEFINE_EVENT(net_dev_template, netif_rx,
+DEFINE_EVENT(net_dev_template_recv, netif_rx,
 
 	TP_PROTO(struct sk_buff *skb),
 
-- 
1.8.2.1




More information about the lttng-dev mailing list