Commit 8ccf3800 authored by Andrew Rybchenko's avatar Andrew Rybchenko Committed by David S. Miller

sfc: Add per-queue statistics in ethtool

Implement per channel software TX and RX packet counters
accessed as ethtool statistics.

This allows confirmation with MAC statistics.
Signed-off-by: default avatarShradha Shah <sshah@solarflare.com>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent 87b200e1
...@@ -359,6 +359,37 @@ static int efx_ethtool_fill_self_tests(struct efx_nic *efx, ...@@ -359,6 +359,37 @@ static int efx_ethtool_fill_self_tests(struct efx_nic *efx,
return n; return n;
} }
static size_t efx_describe_per_queue_stats(struct efx_nic *efx, u8 *strings)
{
size_t n_stats = 0;
struct efx_channel *channel;
efx_for_each_channel(channel, efx) {
if (efx_channel_has_tx_queues(channel)) {
n_stats++;
if (strings != NULL) {
snprintf(strings, ETH_GSTRING_LEN,
"tx-%u.tx_packets",
channel->tx_queue[0].queue /
EFX_TXQ_TYPES);
strings += ETH_GSTRING_LEN;
}
}
}
efx_for_each_channel(channel, efx) {
if (efx_channel_has_rx_queue(channel)) {
n_stats++;
if (strings != NULL) {
snprintf(strings, ETH_GSTRING_LEN,
"rx-%d.rx_packets", channel->channel);
strings += ETH_GSTRING_LEN;
}
}
}
return n_stats;
}
static int efx_ethtool_get_sset_count(struct net_device *net_dev, static int efx_ethtool_get_sset_count(struct net_device *net_dev,
int string_set) int string_set)
{ {
...@@ -367,8 +398,9 @@ static int efx_ethtool_get_sset_count(struct net_device *net_dev, ...@@ -367,8 +398,9 @@ static int efx_ethtool_get_sset_count(struct net_device *net_dev,
switch (string_set) { switch (string_set) {
case ETH_SS_STATS: case ETH_SS_STATS:
return efx->type->describe_stats(efx, NULL) + return efx->type->describe_stats(efx, NULL) +
EFX_ETHTOOL_SW_STAT_COUNT + EFX_ETHTOOL_SW_STAT_COUNT +
efx_ptp_describe_stats(efx, NULL); efx_describe_per_queue_stats(efx, NULL) +
efx_ptp_describe_stats(efx, NULL);
case ETH_SS_TEST: case ETH_SS_TEST:
return efx_ethtool_fill_self_tests(efx, NULL, NULL, NULL); return efx_ethtool_fill_self_tests(efx, NULL, NULL, NULL);
default: default:
...@@ -390,6 +422,8 @@ static void efx_ethtool_get_strings(struct net_device *net_dev, ...@@ -390,6 +422,8 @@ static void efx_ethtool_get_strings(struct net_device *net_dev,
strlcpy(strings + i * ETH_GSTRING_LEN, strlcpy(strings + i * ETH_GSTRING_LEN,
efx_sw_stat_desc[i].name, ETH_GSTRING_LEN); efx_sw_stat_desc[i].name, ETH_GSTRING_LEN);
strings += EFX_ETHTOOL_SW_STAT_COUNT * ETH_GSTRING_LEN; strings += EFX_ETHTOOL_SW_STAT_COUNT * ETH_GSTRING_LEN;
strings += (efx_describe_per_queue_stats(efx, strings) *
ETH_GSTRING_LEN);
efx_ptp_describe_stats(efx, strings); efx_ptp_describe_stats(efx, strings);
break; break;
case ETH_SS_TEST: case ETH_SS_TEST:
...@@ -409,6 +443,7 @@ static void efx_ethtool_get_stats(struct net_device *net_dev, ...@@ -409,6 +443,7 @@ static void efx_ethtool_get_stats(struct net_device *net_dev,
const struct efx_sw_stat_desc *stat; const struct efx_sw_stat_desc *stat;
struct efx_channel *channel; struct efx_channel *channel;
struct efx_tx_queue *tx_queue; struct efx_tx_queue *tx_queue;
struct efx_rx_queue *rx_queue;
int i; int i;
spin_lock_bh(&efx->stats_lock); spin_lock_bh(&efx->stats_lock);
...@@ -444,6 +479,25 @@ static void efx_ethtool_get_stats(struct net_device *net_dev, ...@@ -444,6 +479,25 @@ static void efx_ethtool_get_stats(struct net_device *net_dev,
spin_unlock_bh(&efx->stats_lock); spin_unlock_bh(&efx->stats_lock);
efx_for_each_channel(channel, efx) {
if (efx_channel_has_tx_queues(channel)) {
*data = 0;
efx_for_each_channel_tx_queue(tx_queue, channel) {
*data += tx_queue->tx_packets;
}
data++;
}
}
efx_for_each_channel(channel, efx) {
if (efx_channel_has_rx_queue(channel)) {
*data = 0;
efx_for_each_channel_rx_queue(rx_queue, channel) {
*data += rx_queue->rx_packets;
}
data++;
}
}
efx_ptp_update_stats(efx, data); efx_ptp_update_stats(efx, data);
} }
......
...@@ -249,6 +249,8 @@ struct efx_tx_queue { ...@@ -249,6 +249,8 @@ struct efx_tx_queue {
unsigned int tso_packets; unsigned int tso_packets;
unsigned int pushes; unsigned int pushes;
unsigned int pio_packets; unsigned int pio_packets;
/* Statistics to supplement MAC stats */
unsigned long tx_packets;
/* Members shared between paths and sometimes updated */ /* Members shared between paths and sometimes updated */
unsigned int empty_read_count ____cacheline_aligned_in_smp; unsigned int empty_read_count ____cacheline_aligned_in_smp;
...@@ -358,6 +360,8 @@ struct efx_rx_queue { ...@@ -358,6 +360,8 @@ struct efx_rx_queue {
unsigned int recycle_count; unsigned int recycle_count;
struct timer_list slow_fill; struct timer_list slow_fill;
unsigned int slow_fill_count; unsigned int slow_fill_count;
/* Statistics to supplement MAC stats */
unsigned long rx_packets;
}; };
enum efx_sync_events_state { enum efx_sync_events_state {
......
...@@ -530,6 +530,8 @@ void efx_rx_packet(struct efx_rx_queue *rx_queue, unsigned int index, ...@@ -530,6 +530,8 @@ void efx_rx_packet(struct efx_rx_queue *rx_queue, unsigned int index,
struct efx_channel *channel = efx_rx_queue_channel(rx_queue); struct efx_channel *channel = efx_rx_queue_channel(rx_queue);
struct efx_rx_buffer *rx_buf; struct efx_rx_buffer *rx_buf;
rx_queue->rx_packets++;
rx_buf = efx_rx_buffer(rx_queue, index); rx_buf = efx_rx_buffer(rx_queue, index);
rx_buf->flags |= flags; rx_buf->flags |= flags;
......
...@@ -452,6 +452,8 @@ netdev_tx_t efx_enqueue_skb(struct efx_tx_queue *tx_queue, struct sk_buff *skb) ...@@ -452,6 +452,8 @@ netdev_tx_t efx_enqueue_skb(struct efx_tx_queue *tx_queue, struct sk_buff *skb)
/* Pass off to hardware */ /* Pass off to hardware */
efx_nic_push_buffers(tx_queue); efx_nic_push_buffers(tx_queue);
tx_queue->tx_packets++;
efx_tx_maybe_stop_queue(tx_queue); efx_tx_maybe_stop_queue(tx_queue);
return NETDEV_TX_OK; return NETDEV_TX_OK;
...@@ -1245,6 +1247,8 @@ static int tso_start_new_packet(struct efx_tx_queue *tx_queue, ...@@ -1245,6 +1247,8 @@ static int tso_start_new_packet(struct efx_tx_queue *tx_queue,
++tx_queue->tso_packets; ++tx_queue->tso_packets;
++tx_queue->tx_packets;
return 0; return 0;
} }
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment