aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/net/s2io.c
diff options
context:
space:
mode:
authorJon Mason <jon.mason@exar.com>2010-12-10 10:40:01 -0500
committerDavid S. Miller <davem@davemloft.net>2010-12-11 14:46:36 -0500
commit1853e2e15dc95ff3430530941b5856581251ef70 (patch)
tree0ae74601e624a49ebab41de725e2793fbfddb564 /drivers/net/s2io.c
parent9835fd7321a67feba6432e63bf2cba43f5a56bd9 (diff)
s2io: rx_ring_sz bounds checking
modparm rx_ring_sz can be set to be greater than the maximum allowable number of blocks. This results in an array overrun when probing the driver, and causes memory corruption. Also, the MAX_RX_DESC_1 multiply the max number of rings by max number of blocker per ring by 127, but the driver does the same calculation with 127+1. This results in the possibility of the value being set being larger than the maximum allowable value. Finally, clean-up the s2io_ethtool_gringparam code to be more intuitive. Signed-off-by: Jon Mason <jon.mason@exar.com> Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'drivers/net/s2io.c')
-rw-r--r--drivers/net/s2io.c40
1 files changed, 24 insertions, 16 deletions
diff --git a/drivers/net/s2io.c b/drivers/net/s2io.c
index 0f4219cb0be2..a6d3eaf44863 100644
--- a/drivers/net/s2io.c
+++ b/drivers/net/s2io.c
@@ -5568,30 +5568,27 @@ static void s2io_ethtool_gringparam(struct net_device *dev,
5568 struct s2io_nic *sp = netdev_priv(dev); 5568 struct s2io_nic *sp = netdev_priv(dev);
5569 int i, tx_desc_count = 0, rx_desc_count = 0; 5569 int i, tx_desc_count = 0, rx_desc_count = 0;
5570 5570
5571 if (sp->rxd_mode == RXD_MODE_1) 5571 if (sp->rxd_mode == RXD_MODE_1) {
5572 ering->rx_max_pending = MAX_RX_DESC_1; 5572 ering->rx_max_pending = MAX_RX_DESC_1;
5573 else if (sp->rxd_mode == RXD_MODE_3B) 5573 ering->rx_jumbo_max_pending = MAX_RX_DESC_1;
5574 } else {
5574 ering->rx_max_pending = MAX_RX_DESC_2; 5575 ering->rx_max_pending = MAX_RX_DESC_2;
5576 ering->rx_jumbo_max_pending = MAX_RX_DESC_2;
5577 }
5575 5578
5579 ering->rx_mini_max_pending = 0;
5576 ering->tx_max_pending = MAX_TX_DESC; 5580 ering->tx_max_pending = MAX_TX_DESC;
5577 for (i = 0 ; i < sp->config.tx_fifo_num ; i++)
5578 tx_desc_count += sp->config.tx_cfg[i].fifo_len;
5579 5581
5580 DBG_PRINT(INFO_DBG, "max txds: %d\n", sp->config.max_txds); 5582 for (i = 0; i < sp->config.rx_ring_num; i++)
5581 ering->tx_pending = tx_desc_count;
5582 rx_desc_count = 0;
5583 for (i = 0 ; i < sp->config.rx_ring_num ; i++)
5584 rx_desc_count += sp->config.rx_cfg[i].num_rxd; 5583 rx_desc_count += sp->config.rx_cfg[i].num_rxd;
5585
5586 ering->rx_pending = rx_desc_count; 5584 ering->rx_pending = rx_desc_count;
5587
5588 ering->rx_mini_max_pending = 0;
5589 ering->rx_mini_pending = 0;
5590 if (sp->rxd_mode == RXD_MODE_1)
5591 ering->rx_jumbo_max_pending = MAX_RX_DESC_1;
5592 else if (sp->rxd_mode == RXD_MODE_3B)
5593 ering->rx_jumbo_max_pending = MAX_RX_DESC_2;
5594 ering->rx_jumbo_pending = rx_desc_count; 5585 ering->rx_jumbo_pending = rx_desc_count;
5586 ering->rx_mini_pending = 0;
5587
5588 for (i = 0; i < sp->config.tx_fifo_num; i++)
5589 tx_desc_count += sp->config.tx_cfg[i].fifo_len;
5590 ering->tx_pending = tx_desc_count;
5591 DBG_PRINT(INFO_DBG, "max txds: %d\n", sp->config.max_txds);
5595} 5592}
5596 5593
5597/** 5594/**
@@ -7692,6 +7689,8 @@ static void s2io_init_pci(struct s2io_nic *sp)
7692static int s2io_verify_parm(struct pci_dev *pdev, u8 *dev_intr_type, 7689static int s2io_verify_parm(struct pci_dev *pdev, u8 *dev_intr_type,
7693 u8 *dev_multiq) 7690 u8 *dev_multiq)
7694{ 7691{
7692 int i;
7693
7695 if ((tx_fifo_num > MAX_TX_FIFOS) || (tx_fifo_num < 1)) { 7694 if ((tx_fifo_num > MAX_TX_FIFOS) || (tx_fifo_num < 1)) {
7696 DBG_PRINT(ERR_DBG, "Requested number of tx fifos " 7695 DBG_PRINT(ERR_DBG, "Requested number of tx fifos "
7697 "(%d) not supported\n", tx_fifo_num); 7696 "(%d) not supported\n", tx_fifo_num);
@@ -7750,6 +7749,15 @@ static int s2io_verify_parm(struct pci_dev *pdev, u8 *dev_intr_type,
7750 DBG_PRINT(ERR_DBG, "Defaulting to 1-buffer mode\n"); 7749 DBG_PRINT(ERR_DBG, "Defaulting to 1-buffer mode\n");
7751 rx_ring_mode = 1; 7750 rx_ring_mode = 1;
7752 } 7751 }
7752
7753 for (i = 0; i < MAX_RX_RINGS; i++)
7754 if (rx_ring_sz[i] > MAX_RX_BLOCKS_PER_RING) {
7755 DBG_PRINT(ERR_DBG, "Requested rx ring size not "
7756 "supported\nDefaulting to %d\n",
7757 MAX_RX_BLOCKS_PER_RING);
7758 rx_ring_sz[i] = MAX_RX_BLOCKS_PER_RING;
7759 }
7760
7753 return SUCCESS; 7761 return SUCCESS;
7754} 7762}
7755 7763