mirror of https://github.com/ipxe/ipxe.git
Add trivial net device statistics (TX and RX packet count), reported
via UNDI API and also by ifstat command; may be useful for debugging.pull/1/head
parent
071356d976
commit
4968caab82
|
@ -128,6 +128,17 @@ struct ll_protocol {
|
||||||
const uint8_t *ll_broadcast;
|
const uint8_t *ll_broadcast;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Network device statistics
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
struct net_device_stats {
|
||||||
|
/** Count of successfully completed transmissions */
|
||||||
|
unsigned int tx_count;
|
||||||
|
/** Count of successfully received packets */
|
||||||
|
unsigned int rx_count;
|
||||||
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* A network device
|
* A network device
|
||||||
*
|
*
|
||||||
|
@ -215,6 +226,8 @@ struct net_device {
|
||||||
struct list_head tx_queue;
|
struct list_head tx_queue;
|
||||||
/** RX packet queue */
|
/** RX packet queue */
|
||||||
struct list_head rx_queue;
|
struct list_head rx_queue;
|
||||||
|
/** Device statistics */
|
||||||
|
struct net_device_stats stats;
|
||||||
|
|
||||||
/** Driver private data */
|
/** Driver private data */
|
||||||
void *priv;
|
void *priv;
|
||||||
|
|
|
@ -343,28 +343,33 @@ PXENV_EXIT_t pxenv_undi_get_information ( struct s_PXENV_UNDI_GET_INFORMATION
|
||||||
|
|
||||||
/* PXENV_UNDI_GET_STATISTICS
|
/* PXENV_UNDI_GET_STATISTICS
|
||||||
*
|
*
|
||||||
* Status: won't implement (would require driver API changes for no
|
* Status: working
|
||||||
* real benefit)
|
|
||||||
*/
|
*/
|
||||||
PXENV_EXIT_t pxenv_undi_get_statistics ( struct s_PXENV_UNDI_GET_STATISTICS
|
PXENV_EXIT_t pxenv_undi_get_statistics ( struct s_PXENV_UNDI_GET_STATISTICS
|
||||||
*undi_get_statistics ) {
|
*undi_get_statistics ) {
|
||||||
DBG ( "PXENV_UNDI_GET_STATISTICS" );
|
DBG ( "PXENV_UNDI_GET_STATISTICS" );
|
||||||
|
|
||||||
undi_get_statistics->Status = PXENV_STATUS_UNSUPPORTED;
|
undi_get_statistics->XmtGoodFrames = pxe_netdev->stats.tx_count;
|
||||||
return PXENV_EXIT_FAILURE;
|
undi_get_statistics->RcvGoodFrames = pxe_netdev->stats.rx_count;
|
||||||
|
undi_get_statistics->RcvCRCErrors = 0;
|
||||||
|
undi_get_statistics->RcvResourceErrors = 0;
|
||||||
|
|
||||||
|
undi_get_statistics->Status = PXENV_STATUS_SUCCESS;
|
||||||
|
return PXENV_EXIT_SUCCESS;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* PXENV_UNDI_CLEAR_STATISTICS
|
/* PXENV_UNDI_CLEAR_STATISTICS
|
||||||
*
|
*
|
||||||
* Status: won't implement (would require driver API changes for no
|
* Status: working
|
||||||
* real benefit)
|
|
||||||
*/
|
*/
|
||||||
PXENV_EXIT_t pxenv_undi_clear_statistics ( struct s_PXENV_UNDI_CLEAR_STATISTICS
|
PXENV_EXIT_t pxenv_undi_clear_statistics ( struct s_PXENV_UNDI_CLEAR_STATISTICS
|
||||||
*undi_clear_statistics ) {
|
*undi_clear_statistics ) {
|
||||||
DBG ( "PXENV_UNDI_CLEAR_STATISTICS" );
|
DBG ( "PXENV_UNDI_CLEAR_STATISTICS" );
|
||||||
|
|
||||||
undi_clear_statistics->Status = PXENV_STATUS_UNSUPPORTED;
|
memset ( &pxe_netdev->stats, 0, sizeof ( pxe_netdev->stats ) );
|
||||||
return PXENV_EXIT_FAILURE;
|
|
||||||
|
undi_clear_statistics->Status = PXENV_STATUS_SUCCESS;
|
||||||
|
return PXENV_EXIT_SUCCESS;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* PXENV_UNDI_INITIATE_DIAGS
|
/* PXENV_UNDI_INITIATE_DIAGS
|
||||||
|
|
|
@ -95,8 +95,12 @@ void netdev_tx_complete ( struct net_device *netdev, struct io_buffer *iobuf ) {
|
||||||
assert ( iobuf->list.next != NULL );
|
assert ( iobuf->list.next != NULL );
|
||||||
assert ( iobuf->list.prev != NULL );
|
assert ( iobuf->list.prev != NULL );
|
||||||
|
|
||||||
|
/* Dequeue and free I/O buffer */
|
||||||
list_del ( &iobuf->list );
|
list_del ( &iobuf->list );
|
||||||
free_iob ( iobuf );
|
free_iob ( iobuf );
|
||||||
|
|
||||||
|
/* Update statistics counter */
|
||||||
|
netdev->stats.tx_count++;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -140,7 +144,12 @@ static void netdev_tx_flush ( struct net_device *netdev ) {
|
||||||
void netdev_rx ( struct net_device *netdev, struct io_buffer *iobuf ) {
|
void netdev_rx ( struct net_device *netdev, struct io_buffer *iobuf ) {
|
||||||
DBGC ( netdev, "NETDEV %p received %p (%p+%zx)\n",
|
DBGC ( netdev, "NETDEV %p received %p (%p+%zx)\n",
|
||||||
netdev, iobuf, iobuf->data, iob_len ( iobuf ) );
|
netdev, iobuf, iobuf->data, iob_len ( iobuf ) );
|
||||||
|
|
||||||
|
/* Enqueue packet */
|
||||||
list_add_tail ( &iobuf->list, &netdev->rx_queue );
|
list_add_tail ( &iobuf->list, &netdev->rx_queue );
|
||||||
|
|
||||||
|
/* Update statistics counter */
|
||||||
|
netdev->stats.rx_count++;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
|
@ -61,7 +61,8 @@ void ifclose ( struct net_device *netdev ) {
|
||||||
* @v netdev Network device
|
* @v netdev Network device
|
||||||
*/
|
*/
|
||||||
void ifstat ( struct net_device *netdev ) {
|
void ifstat ( struct net_device *netdev ) {
|
||||||
printf ( "%s: %s on %s (%s)\n",
|
printf ( "%s: %s on %s (%s) TX:%d RX:%d\n",
|
||||||
netdev->name, netdev_hwaddr ( netdev ), netdev->dev->name,
|
netdev->name, netdev_hwaddr ( netdev ), netdev->dev->name,
|
||||||
( ( netdev->state & NETDEV_OPEN ) ? "open" : "closed" ) );
|
( ( netdev->state & NETDEV_OPEN ) ? "open" : "closed" ),
|
||||||
|
netdev->stats.tx_count, netdev->stats.rx_count );
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue