From: Jeff Kirsher <jeffrey.t.kirsher@intel.com>
To: davem@davemloft.net
Cc: Shota Suzuki <suzuki_shota_t3@lab.ntt.co.jp>,
netdev@vger.kernel.org, nhorman@redhat.com, sassmann@redhat.com,
jogreene@redhat.com, stable <stable@vger.kernel.org>,
Jeff Kirsher <jeffrey.t.kirsher@intel.com>
Subject: [net-next 01/15] igb: Fix oops caused by missing queue pairing
Date: Tue, 18 Aug 2015 14:09:08 -0700 [thread overview]
Message-ID: <1439932162-1995-2-git-send-email-jeffrey.t.kirsher@intel.com> (raw)
In-Reply-To: <1439932162-1995-1-git-send-email-jeffrey.t.kirsher@intel.com>
From: Shota Suzuki <suzuki_shota_t3@lab.ntt.co.jp>
When initializing igb driver (e.g. 82576, I350), IGB_FLAG_QUEUE_PAIRS is
set if adapter->rss_queues exceeds half of max_rss_queues in
igb_init_queue_configuration().
On the other hand, IGB_FLAG_QUEUE_PAIRS is not set even if the number of
queues exceeds half of max_combined in igb_set_channels() when changing
the number of queues by "ethtool -L".
In this case, if numvecs is larger than MAX_MSIX_ENTRIES (10), the size
of adapter->msix_entries[], an overflow can occur in
igb_set_interrupt_capability(), which in turn leads to an oops.
Fix this problem as follows:
- When changing the number of queues by "ethtool -L", set
IGB_FLAG_QUEUE_PAIRS in the same way as initializing igb driver.
- When increasing the size of q_vector, reallocate it appropriately.
(With IGB_FLAG_QUEUE_PAIRS set, the size of q_vector gets larger.)
Another possible way to fix this problem is to cap the queues at its
initial number, which is the number of the initial online cpus. But this
is not the optimal way because we cannot increase queues when another
cpu becomes online.
Note that before commit cd14ef54d25b ("igb: Change to use statically
allocated array for MSIx entries"), this problem did not cause oops
but just made the number of queues become 1 because of entering msi_only
mode in igb_set_interrupt_capability().
Fixes: 907b7835799f ("igb: Add ethtool support to configure number of channels")
CC: stable <stable@vger.kernel.org>
Signed-off-by: Shota Suzuki <suzuki_shota_t3@lab.ntt.co.jp>
Tested-by: Aaron Brown <aaron.f.brown@intel.com>
Signed-off-by: Jeff Kirsher <jeffrey.t.kirsher@intel.com>
---
drivers/net/ethernet/intel/igb/igb.h | 1 +
drivers/net/ethernet/intel/igb/igb_ethtool.c | 5 ++++-
drivers/net/ethernet/intel/igb/igb_main.c | 16 ++++++++++++++--
3 files changed, 19 insertions(+), 3 deletions(-)
diff --git a/drivers/net/ethernet/intel/igb/igb.h b/drivers/net/ethernet/intel/igb/igb.h
index c2bd4f9..212d668 100644
--- a/drivers/net/ethernet/intel/igb/igb.h
+++ b/drivers/net/ethernet/intel/igb/igb.h
@@ -540,6 +540,7 @@ void igb_ptp_rx_pktstamp(struct igb_q_vector *q_vector, unsigned char *va,
struct sk_buff *skb);
int igb_ptp_set_ts_config(struct net_device *netdev, struct ifreq *ifr);
int igb_ptp_get_ts_config(struct net_device *netdev, struct ifreq *ifr);
+void igb_set_flag_queue_pairs(struct igb_adapter *, const u32);
#ifdef CONFIG_IGB_HWMON
void igb_sysfs_exit(struct igb_adapter *adapter);
int igb_sysfs_init(struct igb_adapter *adapter);
diff --git a/drivers/net/ethernet/intel/igb/igb_ethtool.c b/drivers/net/ethernet/intel/igb/igb_ethtool.c
index b7b9c67..7426276 100644
--- a/drivers/net/ethernet/intel/igb/igb_ethtool.c
+++ b/drivers/net/ethernet/intel/igb/igb_ethtool.c
@@ -3008,6 +3008,7 @@ static int igb_set_channels(struct net_device *netdev,
{
struct igb_adapter *adapter = netdev_priv(netdev);
unsigned int count = ch->combined_count;
+ unsigned int max_combined = 0;
/* Verify they are not requesting separate vectors */
if (!count || ch->rx_count || ch->tx_count)
@@ -3018,11 +3019,13 @@ static int igb_set_channels(struct net_device *netdev,
return -EINVAL;
/* Verify the number of channels doesn't exceed hw limits */
- if (count > igb_max_channels(adapter))
+ max_combined = igb_max_channels(adapter);
+ if (count > max_combined)
return -EINVAL;
if (count != adapter->rss_queues) {
adapter->rss_queues = count;
+ igb_set_flag_queue_pairs(adapter, max_combined);
/* Hardware has to reinitialize queues and interrupts to
* match the new configuration.
diff --git a/drivers/net/ethernet/intel/igb/igb_main.c b/drivers/net/ethernet/intel/igb/igb_main.c
index 41e2740..7b97e847 100644
--- a/drivers/net/ethernet/intel/igb/igb_main.c
+++ b/drivers/net/ethernet/intel/igb/igb_main.c
@@ -1205,10 +1205,14 @@ static int igb_alloc_q_vector(struct igb_adapter *adapter,
/* allocate q_vector and rings */
q_vector = adapter->q_vector[v_idx];
- if (!q_vector)
+ if (!q_vector) {
q_vector = kzalloc(size, GFP_KERNEL);
- else
+ } else if (size > ksize(q_vector)) {
+ kfree_rcu(q_vector, rcu);
+ q_vector = kzalloc(size, GFP_KERNEL);
+ } else {
memset(q_vector, 0, size);
+ }
if (!q_vector)
return -ENOMEM;
@@ -2888,6 +2892,14 @@ static void igb_init_queue_configuration(struct igb_adapter *adapter)
adapter->rss_queues = min_t(u32, max_rss_queues, num_online_cpus());
+ igb_set_flag_queue_pairs(adapter, max_rss_queues);
+}
+
+void igb_set_flag_queue_pairs(struct igb_adapter *adapter,
+ const u32 max_rss_queues)
+{
+ struct e1000_hw *hw = &adapter->hw;
+
/* Determine if we need to pair queues. */
switch (hw->mac.type) {
case e1000_82575:
--
2.4.3
next prev parent reply other threads:[~2015-08-18 21:09 UTC|newest]
Thread overview: 17+ messages / expand[flat|nested] mbox.gz Atom feed top
2015-08-18 21:09 [net-next 00/15][pull request] Intel Wired LAN Driver Updates 2015-08-18 Jeff Kirsher
2015-08-18 21:09 ` Jeff Kirsher [this message]
2015-08-18 21:09 ` [net-next 02/15] igb: missing rtnl_unlock in igb_sriov_reinit() Jeff Kirsher
2015-08-18 21:09 ` [net-next 03/15] igb: do not re-init SR-IOV during probe Jeff Kirsher
2015-08-18 21:09 ` [net-next 04/15] igb: implement high frequency periodic output signals Jeff Kirsher
2015-08-18 21:09 ` [net-next 05/15] igb: add support for 1512 PHY Jeff Kirsher
2015-08-18 21:09 ` [net-next 06/15] igb: Teardown SR-IOV before unregister_netdev() Jeff Kirsher
2015-08-18 21:09 ` [net-next 07/15] e100: Add a check after pci_pool_create to avoid null pointer dereference Jeff Kirsher
2015-08-18 21:09 ` [net-next 08/15] e100: Release skb when DMA mapping is failed in e100_xmit_prepare Jeff Kirsher
2015-08-18 21:09 ` [net-next 09/15] igb: Fix a deadlock in igb_sriov_reinit Jeff Kirsher
2015-08-18 21:09 ` [net-next 10/15] e1000e: Modify Tx/Rx configurations to avoid null pointer dereferences in e1000_open Jeff Kirsher
2015-08-18 21:09 ` [net-next 11/15] igb: Fix a memory leak in igb_probe Jeff Kirsher
2015-08-18 21:09 ` [net-next 12/15] igbvf: clear buffer_info->dma after dma_unmap_single() Jeff Kirsher
2015-08-18 21:09 ` [net-next 13/15] igb: make sure SR-IOV init uses the right number of queues Jeff Kirsher
2015-08-18 21:09 ` [net-next 14/15] ixgbe: Simplify port-specific macros Jeff Kirsher
2015-08-18 21:09 ` [net-next 15/15] ixgbe: TRIVIAL fix up double 'the' and comment style Jeff Kirsher
2015-08-19 3:21 ` [net-next 00/15][pull request] Intel Wired LAN Driver Updates 2015-08-18 David Miller
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=1439932162-1995-2-git-send-email-jeffrey.t.kirsher@intel.com \
--to=jeffrey.t.kirsher@intel.com \
--cc=davem@davemloft.net \
--cc=jogreene@redhat.com \
--cc=netdev@vger.kernel.org \
--cc=nhorman@redhat.com \
--cc=sassmann@redhat.com \
--cc=stable@vger.kernel.org \
--cc=suzuki_shota_t3@lab.ntt.co.jp \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).