This diffs adds timestamps similar to kdump to bgpctl show mrt output
when messages or states are shown.

Currently it looks like this:
1531425344.000000 153.5.146.105[23456] -> 62.48.0.253[0]: size 63
0.000000 153.5.146.105[23456] -> 62.48.0.253[0]: Connect -> OpenSent
0.000000 153.5.146.105[23456] -> 62.48.0.252[0]: size 63
0.000000 153.5.146.105[23456] -> 62.48.0.252[0]: Connect -> OpenSent
0.000000 153.5.146.105[196618] -> 62.48.0.253[8271]: size 19
0.000000 153.5.146.105[196618] -> 62.48.0.253[8271]: OpenSent -> OpenConfirm
0.000000 153.5.146.105[196618] -> 62.48.0.252[8271]: size 19
0.000000 153.5.146.105[196618] -> 62.48.0.252[8271]: OpenSent -> OpenConfirm
0.000000 153.5.146.105[196618] -> 62.48.0.253[8271]: OpenConfirm -> Established
0.000000 153.5.146.105[196618] -> 62.48.0.252[8271]: OpenConfirm -> Established
0.000000 153.5.146.105[196618] -> 62.48.0.253[8271]: size 23
0.000000 153.5.146.105[196618] -> 62.48.0.252[8271]: size 23

My dump did not include microseconds yet so they are all 0.

OK?
-- 
:wq Claudio

Index: bgpctl.c
===================================================================
RCS file: /cvs/src/usr.sbin/bgpctl/bgpctl.c,v
retrieving revision 1.205
diff -u -p -r1.205 bgpctl.c
--- bgpctl.c    12 Jul 2018 21:45:37 -0000      1.205
+++ bgpctl.c    17 Jul 2018 16:29:48 -0000
@@ -2010,6 +2010,20 @@ network_mrt_dump(struct mrt_rib *mr, str
        }
 }
 
+static const char *
+print_time(struct timespec *t)
+{
+       static char timebuf[32];
+       static struct timespec prevtime;
+       struct timespec temp;
+
+       timespecsub(t, &prevtime, &temp);
+       snprintf(timebuf, sizeof(timebuf), "%lld.%06ld",
+           (long long)temp.tv_sec, temp.tv_nsec / 1000);
+       prevtime = *t;
+       return (timebuf);
+}
+
 void
 show_mrt_state(struct mrt_bgp_state *ms, void *arg)
 {
@@ -2017,7 +2031,8 @@ show_mrt_state(struct mrt_bgp_state *ms,
 
        mrt_to_bgpd_addr(&ms->src, &src);
        mrt_to_bgpd_addr(&ms->dst, &dst);
-       printf("%s[%u] -> ", log_addr(&src), ms->src_as);
+       printf("%s %s[%u] -> ", print_time(&ms->time),
+           log_addr(&src), ms->src_as);
        printf("%s[%u]: %s -> %s\n", log_addr(&dst), ms->dst_as,
            statenames[ms->old_state], statenames[ms->new_state]);
 }
@@ -2029,7 +2044,8 @@ show_mrt_msg(struct mrt_bgp_msg *mm, voi
 
        mrt_to_bgpd_addr(&mm->src, &src);
        mrt_to_bgpd_addr(&mm->dst, &dst);
-       printf("%s[%u] -> ", log_addr(&src), mm->src_as);
+       printf("%s %s[%u] -> ", print_time(&mm->time),
+           log_addr(&src), mm->src_as);
        printf("%s[%u]: size %u\n", log_addr(&dst), mm->dst_as, mm->msg_len);
 }
 
Index: mrtparser.c
===================================================================
RCS file: /cvs/src/usr.sbin/bgpctl/mrtparser.c,v
retrieving revision 1.8
diff -u -p -r1.8 mrtparser.c
--- mrtparser.c 23 Dec 2015 20:42:20 -0000      1.8
+++ mrtparser.c 17 Jul 2018 16:26:09 -0000
@@ -23,6 +23,7 @@
 #include <stdlib.h>
 #include <stdio.h>
 #include <string.h>
+#include <time.h>
 #include <unistd.h>
 
 #include "mrt.h"
@@ -990,14 +991,26 @@ mrt_extract_addr(void *msg, u_int len, u
 struct mrt_bgp_state *
 mrt_parse_state(struct mrt_hdr *hdr, void *msg)
 {
+       struct timespec          t;
        struct mrt_bgp_state    *s;
        u_int8_t                *b = msg;
        u_int                    len = ntohl(hdr->length);
-       u_int32_t                sas, das;
+       u_int32_t                sas, das, usec;
        u_int16_t                tmp16, afi;
        int                      r;
        sa_family_t              af;
        
+       t.tv_sec = ntohl(hdr->timestamp);
+       t.tv_nsec = 0;
+
+       /* handle the microsec field for _ET header */
+       if (ntohs(hdr->type) == MSG_PROTOCOL_BGP4MP_ET) {
+               memcpy(&usec, b, sizeof(usec));
+               b += sizeof(usec);
+               len -= sizeof(usec);
+               t.tv_nsec = ntohl(usec) * 1000;
+       }
+
        switch (ntohs(hdr->subtype)) {
        case BGP4MP_STATE_CHANGE:
                if (len < 8)
@@ -1061,6 +1074,7 @@ mrt_parse_state(struct mrt_hdr *hdr, voi
 
        if ((s = calloc(1, sizeof(struct mrt_bgp_state))) == NULL)
                err(1, "calloc");
+       s->time = t;
        s->src_as = sas;
        s->dst_as = das;
 
@@ -1093,14 +1107,26 @@ fail:
 struct mrt_bgp_msg *
 mrt_parse_msg(struct mrt_hdr *hdr, void *msg)
 {
+       struct timespec          t;
        struct mrt_bgp_msg      *m;
        u_int8_t                *b = msg;
        u_int                    len = ntohl(hdr->length);
-       u_int32_t                sas, das;
+       u_int32_t                sas, das, usec;
        u_int16_t                tmp16, afi;
        int                      r;
        sa_family_t              af;
        
+       t.tv_sec = ntohl(hdr->timestamp);
+       t.tv_nsec = 0;
+
+       /* handle the microsec field for _ET header */
+       if (ntohs(hdr->type) == MSG_PROTOCOL_BGP4MP_ET) {
+               memcpy(&usec, b, sizeof(usec));
+               b += sizeof(usec);
+               len -= sizeof(usec);
+               t.tv_nsec = ntohl(usec) * 1000;
+       }
+
        switch (ntohs(hdr->subtype)) {
        case BGP4MP_MESSAGE:
                if (len < 8)
@@ -1164,6 +1190,7 @@ mrt_parse_msg(struct mrt_hdr *hdr, void 
 
        if ((m = calloc(1, sizeof(struct mrt_bgp_msg))) == NULL)
                err(1, "calloc");
+       m->time = t;
        m->src_as = sas;
        m->dst_as = das;
 
Index: mrtparser.h
===================================================================
RCS file: /cvs/src/usr.sbin/bgpctl/mrtparser.h,v
retrieving revision 1.1
diff -u -p -r1.1 mrtparser.h
--- mrtparser.h 21 Sep 2011 10:37:51 -0000      1.1
+++ mrtparser.h 17 Jul 2018 16:26:09 -0000
@@ -77,6 +77,7 @@ struct mrt_rib {
 
 /* data structures for the BGP4MP MESSAGE and STATE types */
 struct mrt_bgp_state {
+       struct timespec time;
        union mrt_addr  src;
        union mrt_addr  dst;
        u_int32_t       src_as;
@@ -86,6 +87,7 @@ struct mrt_bgp_state {
 };
 
 struct mrt_bgp_msg {
+       struct timespec  time;
        union mrt_addr   src;
        union mrt_addr   dst;
        u_int32_t        src_as;

Reply via email to