Download raw body.
ice(4): add kstat counter
Hi,
This diff exports most hardware kstat counters from ice(4) interfaces.
So, we improve debugging of these interfaces.
ok?
bye,
jan
Index: dev/pci/if_ice.c
===================================================================
RCS file: /cvs/src/sys/dev/pci/if_ice.c,v
diff -u -p -r1.69 if_ice.c
--- dev/pci/if_ice.c 23 Jun 2026 14:40:40 -0000 1.69
+++ dev/pci/if_ice.c 7 Jul 2026 21:03:13 -0000
@@ -51,6 +51,7 @@
#include "bpfilter.h"
#include "vlan.h"
+#include "kstat.h"
#include <sys/param.h>
#include <sys/atomic.h>
@@ -70,6 +71,10 @@
#include <machine/bus.h>
#include <machine/intr.h>
+#if NKSTAT > 0
+#include <sys/kstat.h>
+#endif
+
#include <dev/pci/pcireg.h>
#include <dev/pci/pcivar.h>
#include <dev/pci/pcidevs.h>
@@ -340,6 +345,8 @@ struct ice_softc {
int rebuild_ticks;
int sw_intr[ICE_MAX_VECTORS];
+ struct kstat *sc_kstat_port;
+ struct kstat *sc_kstat_vsi;
};
static int ice_rxrinfo(struct ice_softc *, struct if_rxrinfo *);
@@ -24125,7 +24132,7 @@ ice_update_link_status(struct ice_softc
ice_set_default_local_lldp_mib(sc);
ifp->if_baudrate = baudrate;
- ifp->if_link_state = LINK_STATE_UP;
+ ifp->if_link_state = LINK_STATE_FULL_DUPLEX;
if_link_state_change(ifp);
#if 0
ice_rdma_link_change(sc, LINK_STATE_UP, baudrate);
@@ -28900,6 +28907,279 @@ ice_update_stats(struct ice_softc *sc)
#endif
}
+#if NKSTAT > 0
+
+/* Synced with struct ice_hw_port_stats */
+struct ice_kstat_port_counters {
+ /* struct ice_eth_stats eth; */
+ struct kstat_kv rx_bytes;
+ struct kstat_kv rx_unicast;
+ struct kstat_kv rx_multicast;
+ struct kstat_kv rx_broadcast;
+ struct kstat_kv rx_discards;
+ /* uint64_t rx_unknown_protocol; N/A */
+ struct kstat_kv tx_bytes;
+ struct kstat_kv tx_unicast;
+ struct kstat_kv tx_multicast;
+ struct kstat_kv tx_broadcast;
+ /* uint64_t tx_discards; N/A */
+ /* uint64_t tx_errors; N/A */
+ /* uint64_t rx_no_desc; N/A */
+ /* uint64_t rx_errors; N/A */
+
+ struct kstat_kv tx_dropped_link_down;
+ struct kstat_kv crc_errors;
+ struct kstat_kv illegal_bytes;
+ /* error_bytes N/A */
+ struct kstat_kv mac_local_faults;
+ struct kstat_kv mac_remote_faults;
+ struct kstat_kv rx_len_errors;
+ struct kstat_kv link_xon_rx;
+ struct kstat_kv link_xoff_rx;
+ struct kstat_kv link_xon_tx;
+ struct kstat_kv link_xoff_tx;
+ /* uint64_t priority_xon_rx[8]; skipped, too verbose */
+ /* uint64_t priority_xoff_rx[8]; skipped, too verbose */
+ /* uint64_t priority_xon_tx[8]; skipped, too verbose */
+ /* uint64_t priority_xoff_tx[8]; skipped, too verbose */
+ /* uint64_t priority_xon_2_xoff[8]; skipped, too verbose */
+ struct kstat_kv rx_size_64;
+ struct kstat_kv rx_size_127;
+ struct kstat_kv rx_size_255;
+ struct kstat_kv rx_size_511;
+ struct kstat_kv rx_size_1023;
+ struct kstat_kv rx_size_1522;
+ struct kstat_kv rx_size_big;
+ struct kstat_kv rx_undersize;
+ struct kstat_kv rx_fragments;
+ struct kstat_kv rx_oversize;
+ struct kstat_kv rx_jabber;
+ struct kstat_kv tx_size_64;
+ struct kstat_kv tx_size_127;
+ struct kstat_kv tx_size_255;
+ struct kstat_kv tx_size_511;
+ struct kstat_kv tx_size_1023;
+ struct kstat_kv tx_size_1522;
+ struct kstat_kv tx_size_big;
+ /* uint64_t mac_short_pkt_dropped; N/A */
+ /* uint32_t tx_lpi_status; N/A */
+ /* uint32_t rx_lpi_status; N/A */
+ /* uint64_t tx_lpi_count; N/A */
+ /* uint64_t rx_lpi_count; N/A */
+};
+
+static const struct ice_kstat_port_counters ice_kstat_port_counters_tpl = {
+ KSTAT_KV_UNIT_INITIALIZER("rx bytes", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_BYTES),
+ KSTAT_KV_UNIT_INITIALIZER("rx unicast", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("rx multicast", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("rx broadcast", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("rx discards", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("tx bytes", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_BYTES),
+ KSTAT_KV_UNIT_INITIALIZER("tx unicast", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("tx multicast", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("tx broadcast", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("tx drop no link", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("crc errors", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("illegal bytes", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("mac local errs", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_NONE),
+ KSTAT_KV_UNIT_INITIALIZER("mac remote errs", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_NONE),
+ KSTAT_KV_UNIT_INITIALIZER("rx len errors", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("link xon rx", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("link xoff rx", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("link xon tx", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("link xoff tx", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("rx size 64", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("rx size 127", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("rx size 255", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("rx size 511", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("rx size 1023", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("rx size 1522", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("rx size big", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("rx undersize", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("rx fragments", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("rx oversize", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("rx jabber", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("tx size 64", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("tx size 127", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("tx size 255", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("tx size 511", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("tx size 1023", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("tx size 1522", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("tx size big", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+};
+
+int
+ice_kstat_port_counters_copy(struct kstat *ks, void *dst)
+{
+ struct ice_softc *sc = ks->ks_softc;
+ struct ice_kstat_port_counters *data = dst;
+
+ *data = ice_kstat_port_counters_tpl;
+
+#define ICE_COPY_KSTAT_U64_PATH(path, name) \
+ kstat_kv_u64(&data->name) = sc->stats.cur.path.name
+
+#define ICE_COPY_KSTAT_U64(name) \
+ kstat_kv_u64(&data->name) = sc->stats.cur.name
+
+ ICE_COPY_KSTAT_U64_PATH(eth, rx_bytes);
+ ICE_COPY_KSTAT_U64_PATH(eth, rx_unicast);
+ ICE_COPY_KSTAT_U64_PATH(eth, rx_multicast);
+ ICE_COPY_KSTAT_U64_PATH(eth, rx_broadcast);
+ ICE_COPY_KSTAT_U64_PATH(eth, rx_discards);
+ ICE_COPY_KSTAT_U64_PATH(eth, tx_bytes);
+ ICE_COPY_KSTAT_U64_PATH(eth, tx_unicast);
+ ICE_COPY_KSTAT_U64_PATH(eth, tx_multicast);
+ ICE_COPY_KSTAT_U64_PATH(eth, tx_broadcast);
+
+ ICE_COPY_KSTAT_U64(tx_dropped_link_down);
+ ICE_COPY_KSTAT_U64(crc_errors);
+ ICE_COPY_KSTAT_U64(illegal_bytes);
+ ICE_COPY_KSTAT_U64(mac_local_faults);
+ ICE_COPY_KSTAT_U64(mac_remote_faults);
+ ICE_COPY_KSTAT_U64(rx_len_errors);
+ ICE_COPY_KSTAT_U64(link_xon_rx);
+ ICE_COPY_KSTAT_U64(link_xoff_rx);
+ ICE_COPY_KSTAT_U64(link_xon_tx);
+ ICE_COPY_KSTAT_U64(link_xoff_tx);
+ ICE_COPY_KSTAT_U64(rx_size_64);
+ ICE_COPY_KSTAT_U64(rx_size_127);
+ ICE_COPY_KSTAT_U64(rx_size_255);
+ ICE_COPY_KSTAT_U64(rx_size_511);
+ ICE_COPY_KSTAT_U64(rx_size_1023);
+ ICE_COPY_KSTAT_U64(rx_size_1522);
+ ICE_COPY_KSTAT_U64(rx_size_big);
+ ICE_COPY_KSTAT_U64(rx_undersize);
+ ICE_COPY_KSTAT_U64(rx_fragments);
+ ICE_COPY_KSTAT_U64(rx_oversize);
+ ICE_COPY_KSTAT_U64(rx_jabber);
+ ICE_COPY_KSTAT_U64(tx_size_64);
+ ICE_COPY_KSTAT_U64(tx_size_127);
+ ICE_COPY_KSTAT_U64(tx_size_255);
+ ICE_COPY_KSTAT_U64(tx_size_511);
+ ICE_COPY_KSTAT_U64(tx_size_1023);
+ ICE_COPY_KSTAT_U64(tx_size_1522);
+ ICE_COPY_KSTAT_U64(tx_size_big);
+
+#undef ICE_COPY_KSTAT_U64_PATH
+#undef ICE_COPY_KSTAT_U64
+
+ return (0);
+}
+
+/* Synced with struct ice_eth_stats */
+struct ice_kstat_vsi_counters {
+ struct kstat_kv rx_bytes;
+ struct kstat_kv rx_unicast;
+ struct kstat_kv rx_multicast;
+ struct kstat_kv rx_broadcast;
+ struct kstat_kv rx_discards;
+ /* uint64_t rx_unknown_protocol; N/A */
+ struct kstat_kv tx_bytes;
+ struct kstat_kv tx_unicast;
+ struct kstat_kv tx_multicast;
+ struct kstat_kv tx_broadcast;
+ /* uint64_t tx_discards; N/A */
+ struct kstat_kv tx_errors;
+ struct kstat_kv rx_no_desc;
+ struct kstat_kv rx_errors;
+};
+
+struct ice_kstat_vsi_counters ice_kstat_vsi_counters_tpl = {
+ KSTAT_KV_UNIT_INITIALIZER("rx bytes", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_BYTES),
+ KSTAT_KV_UNIT_INITIALIZER("rx unicast", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("rx multicast", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("rx broadcast", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("rx discards", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("tx bytes", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_BYTES),
+ KSTAT_KV_UNIT_INITIALIZER("tx unicast", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("tx multicast", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("tx broadcast", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("tx errors", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("rx no desc", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+ KSTAT_KV_UNIT_INITIALIZER("rx errors", KSTAT_KV_T_COUNTER64,
+ KSTAT_KV_U_PACKETS),
+};
+
+int
+ice_kstat_vsi_counters_copy(struct kstat *ks, void *dst)
+{
+ struct ice_softc *sc = ks->ks_softc;
+ struct ice_kstat_vsi_counters *data = dst;
+
+ *data = ice_kstat_vsi_counters_tpl;
+
+#define ICE_COPY_KSTAT_U64(name) \
+ kstat_kv_u64(&data->name) = sc->pf_vsi.hw_stats.cur.name
+
+ ICE_COPY_KSTAT_U64(rx_bytes);
+ ICE_COPY_KSTAT_U64(rx_unicast);
+ ICE_COPY_KSTAT_U64(rx_multicast);
+ ICE_COPY_KSTAT_U64(rx_broadcast);
+ ICE_COPY_KSTAT_U64(rx_discards);
+ ICE_COPY_KSTAT_U64(tx_bytes);
+ ICE_COPY_KSTAT_U64(tx_unicast);
+ ICE_COPY_KSTAT_U64(tx_multicast);
+ ICE_COPY_KSTAT_U64(tx_broadcast);
+ ICE_COPY_KSTAT_U64(tx_errors);
+ ICE_COPY_KSTAT_U64(rx_no_desc);
+ ICE_COPY_KSTAT_U64(rx_errors);
+
+#undef ICE_COPY_KSTAT_U64
+
+ return (0);
+}
+
+#endif /* NKSTAT > 0 */
+
/**
* ice_if_update_admin_status - update admin status
* @ctx: iflib ctx structure
@@ -30483,6 +30763,36 @@ ice_init_link_configuration(struct ice_s
}
}
+#if NKSTAT > 0
+
+int
+ice_kstat_attach(struct ice_softc *sc)
+{
+ sc->sc_kstat_port = kstat_create(sc->sc_dev.dv_xname, 0, "ice-port", 0,
+ KSTAT_T_KV, 0);
+ if (sc->sc_kstat_port == NULL)
+ return (-1);
+
+ sc->sc_kstat_port->ks_softc = sc;
+ sc->sc_kstat_port->ks_datalen = sizeof(ice_kstat_port_counters_tpl);
+ sc->sc_kstat_port->ks_copy = ice_kstat_port_counters_copy;
+ kstat_install(sc->sc_kstat_port);
+
+ sc->sc_kstat_vsi = kstat_create(sc->sc_dev.dv_xname, 0, "ice-vsi", 0,
+ KSTAT_T_KV, 0);
+ if (sc->sc_kstat_vsi == NULL)
+ return (-1);
+
+ sc->sc_kstat_vsi->ks_softc = sc;
+ sc->sc_kstat_vsi->ks_datalen = sizeof(ice_kstat_vsi_counters_tpl);
+ sc->sc_kstat_vsi->ks_copy = ice_kstat_vsi_counters_copy;
+ kstat_install(sc->sc_kstat_vsi);
+
+ return (0);
+}
+
+#endif
+
void
ice_attach_hook(struct device *self)
{
@@ -30727,6 +31037,11 @@ ice_attach_hook(struct device *self)
if (err)
printf("%s: could not set MAC address (error %d)\n",
sc->sc_dev.dv_xname, err);
+
+#if NKSTAT > 0
+ if (ice_kstat_attach(sc))
+ printf("%s: could not attach to kstat\n", sc->sc_dev.dv_xname);
+#endif
ice_clear_state(&sc->state, ICE_STATE_ATTACHING);
return;
ice(4): add kstat counter