From 2d7f0d76c6298e1a59646bcb028412f678dbceee Mon Sep 17 00:00:00 2001 From: Donald Sharp Date: Thu, 30 Mar 2017 15:37:22 -0400 Subject: [PATCH 1/5] lib, zebra: Add ability to pass interface speed up from zebra This is a prepatory commit for future improvements. Add a change to the zapi to pass the interface speed up. Signed-off-by: Donald Sharp --- lib/if.h | 3 +++ lib/zclient.c | 3 +++ zebra/zserv.c | 1 + 3 files changed, 7 insertions(+) diff --git a/lib/if.h b/lib/if.h index 49f2a52478..d7ec495636 100644 --- a/lib/if.h +++ b/lib/if.h @@ -229,6 +229,9 @@ struct interface /* Interface metric */ uint32_t metric; + /* Interface Speed */ + uint32_t speed; + /* Interface MTU. */ unsigned int mtu; /* IPv4 MTU */ unsigned int mtu6; /* IPv6 MTU - probably, but not neccessarily same as mtu */ diff --git a/lib/zclient.c b/lib/zclient.c index 4455644345..71b95ae7db 100644 --- a/lib/zclient.c +++ b/lib/zclient.c @@ -1003,6 +1003,8 @@ zebra_router_id_update_read (struct stream *s, struct prefix *rid) * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ * | metric | * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + * | speed | + * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ * | ifmtu | * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ * | ifmtu6 | @@ -1185,6 +1187,7 @@ zebra_interface_if_set_value (struct stream *s, struct interface *ifp) ifp->ptm_enable = stream_getc (s); ifp->ptm_status = stream_getc (s); ifp->metric = stream_getl (s); + ifp->speed = stream_getl (s); ifp->mtu = stream_getl (s); ifp->mtu6 = stream_getl (s); ifp->bandwidth = stream_getl (s); diff --git a/zebra/zserv.c b/zebra/zserv.c index f9205a12c8..85fdd53122 100644 --- a/zebra/zserv.c +++ b/zebra/zserv.c @@ -167,6 +167,7 @@ zserv_encode_interface (struct stream *s, struct interface *ifp) stream_putc (s, ifp->ptm_enable); stream_putc (s, ifp->ptm_status); stream_putl (s, ifp->metric); + stream_putl (s, ifp->speed); stream_putl (s, ifp->mtu); stream_putl (s, ifp->mtu6); stream_putl (s, ifp->bandwidth); From 535fe877a9b70084db581e4897452fb4a8dd4e85 Mon Sep 17 00:00:00 2001 From: Donald Sharp Date: Thu, 30 Mar 2017 15:51:29 -0400 Subject: [PATCH 2/5] zebra: Retrieve interface speed when creating interface When we get notification from the kernel about the creation of a new interface, retrieve the speed of it from the kernel Signed-off-by: Donald Sharp --- zebra/if_netlink.c | 42 ++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 42 insertions(+) diff --git a/zebra/if_netlink.c b/zebra/if_netlink.c index 0a1cafd87e..b1d4dd81d9 100644 --- a/zebra/if_netlink.c +++ b/zebra/if_netlink.c @@ -22,6 +22,8 @@ #include #include +#include +#include #include "linklist.h" #include "if.h" @@ -298,6 +300,45 @@ netlink_vrf_change (struct nlmsghdr *h, struct rtattr *tb, const char *name) } } +static int +get_iflink_speed (const char *ifname) +{ + struct ifreq ifdata; + struct ethtool_cmd ecmd; + int sd; + int rc; + + /* initialize struct */ + memset(&ifdata, 0, sizeof(ifdata)); + + /* set interface name */ + strcpy(ifdata.ifr_name, ifname); + + /* initialize ethtool interface */ + memset(&ecmd, 0, sizeof(ecmd)); + ecmd.cmd = ETHTOOL_GSET; /* ETHTOOL_GLINK */ + ifdata.ifr_data = (__caddr_t) &ecmd; + + /* use ioctl to get IP address of an interface */ + sd = socket(PF_INET, SOCK_DGRAM, IPPROTO_IP); + if(sd < 0) { + zlog_debug ("Failure to read interface %s speed: %d %s", + ifname, errno, safe_strerror(errno)); + return 0; + } + + /* Get the current link state for the interface */ + rc = ioctl(sd, SIOCETHTOOL, (char *)&ifdata); + if(rc < 0) { + zlog_debug ("IOCTL failure to read interface %s speed: %d %s", + ifname, errno, safe_strerror(errno)); + } + + close(sd); + + return (ecmd.speed_hi << 16 ) | ecmd.speed; +} + /* Called from interface_lookup_netlink(). This function is only used during bootstrap. */ static int @@ -382,6 +423,7 @@ netlink_interface (struct sockaddr_nl *snl, struct nlmsghdr *h, SET_FLAG(ifp->status, ZEBRA_INTERFACE_VRF_LOOPBACK); ifp->mtu6 = ifp->mtu = *(uint32_t *) RTA_DATA (tb[IFLA_MTU]); ifp->metric = 0; + ifp->speed = get_iflink_speed (name); ifp->ptm_status = ZEBRA_PTM_STATUS_UNKNOWN; /* Hardware type and address. */ From 6f4c7f7476b0124e024f51f32392792efd116b4d Mon Sep 17 00:00:00 2001 From: Donald Sharp Date: Thu, 30 Mar 2017 16:54:15 -0400 Subject: [PATCH 3/5] zebra: Display new speed information in 'show int..' command Signed-off-by: Donald Sharp --- zebra/interface.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/zebra/interface.c b/zebra/interface.c index e9c54a629b..adcc78095b 100644 --- a/zebra/interface.c +++ b/zebra/interface.c @@ -1056,8 +1056,8 @@ if_dump_vty (struct vty *vty, struct interface *ifp) return; } - vty_out (vty, " index %d metric %d mtu %d ", - ifp->ifindex, ifp->metric, ifp->mtu); + vty_out (vty, " index %d metric %d mtu %d speed %d ", + ifp->ifindex, ifp->metric, ifp->mtu, ifp->speed); if (ifp->mtu6 != ifp->mtu) vty_out (vty, "mtu6 %d ", ifp->mtu6); vty_out (vty, "%s flags: %s%s", VTY_NEWLINE, From eb649b7ff38df75fb2b5fc20a552b9a6d1f78063 Mon Sep 17 00:00:00 2001 From: Donald Sharp Date: Mon, 3 Apr 2017 18:28:26 -0400 Subject: [PATCH 4/5] lib, zebra: Fix CR comments lib -> Add a bit of documentation about what units we are in. zebra -> Fix failure case to be a bit better. Signed-off-by: Donald Sharp --- lib/if.h | 2 +- zebra/if_netlink.c | 6 ++++-- 2 files changed, 5 insertions(+), 3 deletions(-) diff --git a/lib/if.h b/lib/if.h index d7ec495636..e8e84ffc88 100644 --- a/lib/if.h +++ b/lib/if.h @@ -229,7 +229,7 @@ struct interface /* Interface metric */ uint32_t metric; - /* Interface Speed */ + /* Interface Speed in Mb/s */ uint32_t speed; /* Interface MTU. */ diff --git a/zebra/if_netlink.c b/zebra/if_netlink.c index b1d4dd81d9..28538fabdf 100644 --- a/zebra/if_netlink.c +++ b/zebra/if_netlink.c @@ -330,8 +330,10 @@ get_iflink_speed (const char *ifname) /* Get the current link state for the interface */ rc = ioctl(sd, SIOCETHTOOL, (char *)&ifdata); if(rc < 0) { - zlog_debug ("IOCTL failure to read interface %s speed: %d %s", - ifname, errno, safe_strerror(errno)); + zlog_debug("IOCTL failure to read interface %s speed: %d %s", + ifname, errno, safe_strerror(errno)); + ecmd.speed_hi = 0; + ecmd.speed = 0; } close(sd); From 97d2cd8d0c54279407cef16f070231912ef85a00 Mon Sep 17 00:00:00 2001 From: Donald Sharp Date: Tue, 4 Apr 2017 07:50:31 -0400 Subject: [PATCH 5/5] zebra: Fix printf formatting Signed-off-by: Donald Sharp --- zebra/interface.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/zebra/interface.c b/zebra/interface.c index adcc78095b..1d015e8588 100644 --- a/zebra/interface.c +++ b/zebra/interface.c @@ -1056,7 +1056,7 @@ if_dump_vty (struct vty *vty, struct interface *ifp) return; } - vty_out (vty, " index %d metric %d mtu %d speed %d ", + vty_out (vty, " index %d metric %d mtu %d speed %u ", ifp->ifindex, ifp->metric, ifp->mtu, ifp->speed); if (ifp->mtu6 != ifp->mtu) vty_out (vty, "mtu6 %d ", ifp->mtu6);