Source-Changes-HG archive
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]
[src/trunk]: src/sys/dev/pci/ixgbe Don't write EIMC directly. It is required ...
details: https://anonhg.NetBSD.org/src/rev/951cb907b235
branches: trunk
changeset: 831423:951cb907b235
user: knakahara <knakahara%NetBSD.org@localhost>
date: Fri Mar 30 03:58:20 2018 +0000
description:
Don't write EIMC directly. It is required to manage with struct ix_queue status.
XXX pullup-8
diffstat:
sys/dev/pci/ixgbe/ix_txrx.c | 6 +-
sys/dev/pci/ixgbe/ixgbe.c | 69 ++++++++++++++++++++++++++++++---------
sys/dev/pci/ixgbe/ixgbe.h | 11 ++++-
sys/dev/pci/ixgbe/ixgbe_api.h | 4 +-
sys/dev/pci/ixgbe/ixgbe_common.c | 24 ++++++++++++-
sys/dev/pci/ixgbe/ixv.c | 16 ++++----
6 files changed, 96 insertions(+), 34 deletions(-)
diffs (299 lines):
diff -r 421a42f7c670 -r 951cb907b235 sys/dev/pci/ixgbe/ix_txrx.c
--- a/sys/dev/pci/ixgbe/ix_txrx.c Fri Mar 30 03:56:38 2018 +0000
+++ b/sys/dev/pci/ixgbe/ix_txrx.c Fri Mar 30 03:58:20 2018 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: ix_txrx.c,v 1.36 2018/03/15 06:48:51 msaitoh Exp $ */
+/* $NetBSD: ix_txrx.c,v 1.37 2018/03/30 03:58:20 knakahara Exp $ */
/******************************************************************************
@@ -2298,8 +2298,8 @@
que->txr = &adapter->tx_rings[i];
que->rxr = &adapter->rx_rings[i];
- mutex_init(&que->im_mtx, MUTEX_DEFAULT, IPL_NET);
- que->im_nest = 0;
+ mutex_init(&que->dc_mtx, MUTEX_DEFAULT, IPL_NET);
+ que->disabled_count = 0;
}
return (0);
diff -r 421a42f7c670 -r 951cb907b235 sys/dev/pci/ixgbe/ixgbe.c
--- a/sys/dev/pci/ixgbe/ixgbe.c Fri Mar 30 03:56:38 2018 +0000
+++ b/sys/dev/pci/ixgbe/ixgbe.c Fri Mar 30 03:58:20 2018 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: ixgbe.c,v 1.138 2018/03/30 03:56:38 knakahara Exp $ */
+/* $NetBSD: ixgbe.c,v 1.139 2018/03/30 03:58:20 knakahara Exp $ */
/******************************************************************************
@@ -2410,8 +2410,8 @@
u64 queue = (u64)(1ULL << vector);
u32 mask;
- mutex_enter(&que->im_mtx);
- if (que->im_nest > 0 && --que->im_nest > 0)
+ mutex_enter(&que->dc_mtx);
+ if (que->disabled_count > 0 && --que->disabled_count > 0)
goto out;
if (hw->mac.type == ixgbe_mac_82598EB) {
@@ -2426,23 +2426,28 @@
IXGBE_WRITE_REG(hw, IXGBE_EIMS_EX(1), mask);
}
out:
- mutex_exit(&que->im_mtx);
+ mutex_exit(&que->dc_mtx);
} /* ixgbe_enable_queue */
/************************************************************************
- * ixgbe_disable_queue
+ * ixgbe_disable_queue_internal
************************************************************************/
static inline void
-ixgbe_disable_queue(struct adapter *adapter, u32 vector)
+ixgbe_disable_queue_internal(struct adapter *adapter, u32 vector, bool nestok)
{
struct ixgbe_hw *hw = &adapter->hw;
struct ix_queue *que = &adapter->queues[vector];
u64 queue = (u64)(1ULL << vector);
u32 mask;
- mutex_enter(&que->im_mtx);
- if (que->im_nest++ > 0)
- goto out;
+ mutex_enter(&que->dc_mtx);
+
+ if (que->disabled_count > 0) {
+ if (nestok)
+ que->disabled_count++;
+ goto out;
+ }
+ que->disabled_count++;
if (hw->mac.type == ixgbe_mac_82598EB) {
mask = (IXGBE_EIMS_RTX_QUEUE & queue);
@@ -2456,7 +2461,17 @@
IXGBE_WRITE_REG(hw, IXGBE_EIMC_EX(1), mask);
}
out:
- mutex_exit(&que->im_mtx);
+ mutex_exit(&que->dc_mtx);
+} /* ixgbe_disable_queue_internal */
+
+/************************************************************************
+ * ixgbe_disable_queue
+ ************************************************************************/
+static inline void
+ixgbe_disable_queue(struct adapter *adapter, u32 vector)
+{
+
+ ixgbe_disable_queue_internal(adapter, vector, true);
} /* ixgbe_disable_queue */
/************************************************************************
@@ -3511,7 +3526,7 @@
ixgbe_free_receive_structures(adapter);
for (int i = 0; i < adapter->num_queues; i++) {
struct ix_queue * que = &adapter->queues[i];
- mutex_destroy(&que->im_mtx);
+ mutex_destroy(&que->dc_mtx);
}
free(adapter->queues, M_DEVBUF);
free(adapter->mta, M_DEVBUF);
@@ -4295,11 +4310,11 @@
else if (queues != 0) { /* Force an IRQ on queues with work */
que = adapter->queues;
for (i = 0; i < adapter->num_queues; i++, que++) {
- mutex_enter(&que->im_mtx);
- if (que->im_nest == 0)
+ mutex_enter(&que->dc_mtx);
+ if (que->disabled_count == 0)
ixgbe_rearm_queues(adapter,
queues & ((u64)1 << i));
- mutex_exit(&que->im_mtx);
+ mutex_exit(&que->dc_mtx);
}
}
@@ -4697,10 +4712,10 @@
} /* ixgbe_enable_intr */
/************************************************************************
- * ixgbe_disable_intr
+ * ixgbe_disable_intr_internal
************************************************************************/
static void
-ixgbe_disable_intr(struct adapter *adapter)
+ixgbe_disable_intr_internal(struct adapter *adapter, bool nestok)
{
struct ix_queue *que = adapter->queues;
@@ -4711,13 +4726,33 @@
IXGBE_WRITE_REG(&adapter->hw, IXGBE_EIAC, 0);
for (int i = 0; i < adapter->num_queues; i++, que++)
- ixgbe_disable_queue(adapter, que->msix);
+ ixgbe_disable_queue_internal(adapter, que->msix, nestok);
IXGBE_WRITE_FLUSH(&adapter->hw);
+} /* ixgbe_do_disable_intr_internal */
+
+/************************************************************************
+ * ixgbe_disable_intr
+ ************************************************************************/
+static void
+ixgbe_disable_intr(struct adapter *adapter)
+{
+
+ ixgbe_disable_intr_internal(adapter, true);
} /* ixgbe_disable_intr */
/************************************************************************
+ * ixgbe_ensure_disabled_intr
+ ************************************************************************/
+void
+ixgbe_ensure_disabled_intr(struct adapter *adapter)
+{
+
+ ixgbe_disable_intr_internal(adapter, false);
+} /* ixgbe_ensure_disabled_intr */
+
+/************************************************************************
* ixgbe_legacy_irq - Legacy Interrupt Service routine
************************************************************************/
static int
diff -r 421a42f7c670 -r 951cb907b235 sys/dev/pci/ixgbe/ixgbe.h
--- a/sys/dev/pci/ixgbe/ixgbe.h Fri Mar 30 03:56:38 2018 +0000
+++ b/sys/dev/pci/ixgbe/ixgbe.h Fri Mar 30 03:58:20 2018 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: ixgbe.h,v 1.38 2018/03/30 03:56:38 knakahara Exp $ */
+/* $NetBSD: ixgbe.h,v 1.39 2018/03/30 03:58:20 knakahara Exp $ */
/******************************************************************************
SPDX-License-Identifier: BSD-3-Clause
@@ -339,8 +339,13 @@
char namebuf[32];
char evnamebuf[32];
- kmutex_t im_mtx; /* lock for im_nest and this queue's EIMS/EIMC bit */
- int im_nest;
+ kmutex_t dc_mtx; /* lock for disabled_count and this queue's EIMS/EIMC bit */
+ int disabled_count;/*
+ * means
+ * 0 : this queue is enabled
+ * > 0 : this queue is disabled
+ * the value is ixgbe_disable_queue() called count
+ */
};
/*
diff -r 421a42f7c670 -r 951cb907b235 sys/dev/pci/ixgbe/ixgbe_api.h
--- a/sys/dev/pci/ixgbe/ixgbe_api.h Fri Mar 30 03:56:38 2018 +0000
+++ b/sys/dev/pci/ixgbe/ixgbe_api.h Fri Mar 30 03:58:20 2018 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: ixgbe_api.h,v 1.11 2017/12/06 04:08:50 msaitoh Exp $ */
+/* $NetBSD: ixgbe_api.h,v 1.12 2018/03/30 03:58:20 knakahara Exp $ */
/******************************************************************************
SPDX-License-Identifier: BSD-3-Clause
@@ -227,4 +227,6 @@
s32 ixgbe_negotiate_fc(struct ixgbe_hw *hw, u32 adv_reg, u32 lp_reg,
u32 adv_sym, u32 adv_asm, u32 lp_sym, u32 lp_asm);
+void ixgbe_ensure_disabled_intr(struct adapter *);
+
#endif /* _IXGBE_API_H_ */
diff -r 421a42f7c670 -r 951cb907b235 sys/dev/pci/ixgbe/ixgbe_common.c
--- a/sys/dev/pci/ixgbe/ixgbe_common.c Fri Mar 30 03:56:38 2018 +0000
+++ b/sys/dev/pci/ixgbe/ixgbe_common.c Fri Mar 30 03:58:20 2018 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: ixgbe_common.c,v 1.18 2018/03/16 07:54:08 msaitoh Exp $ */
+/* $NetBSD: ixgbe_common.c,v 1.19 2018/03/30 03:58:20 knakahara Exp $ */
/******************************************************************************
SPDX-License-Identifier: BSD-3-Clause
@@ -1130,7 +1130,27 @@
ixgbe_disable_rx(hw);
/* Clear interrupt mask to stop interrupts from being generated */
- IXGBE_WRITE_REG(hw, IXGBE_EIMC, IXGBE_IRQ_CLEAR_MASK);
+ /*
+ * XXX
+ * This function is called in the state of both interrupt disabled
+ * and interrupt enabled, e.g.
+ * + interrupt disabled case:
+ * - ixgbe_stop()
+ * - ixgbe_disable_intr() // interrupt disabled here
+ * - ixgbe_stop_adapter()
+ * - hw->mac.ops.stop_adapter()
+ * == this function
+ * + interrupt enabled case:
+ * - ixgbe_local_timer1()
+ * - ixgbe_init_locked()
+ * - ixgbe_stop_adapter()
+ * - hw->mac.ops.stop_adapter()
+ * == this function
+ * Therefore, it causes nest status breaking to nest the status
+ * (that is, que->im_nest++) at all times. So, this function must
+ * use ixgbe_ensure_disabled_intr() instead of ixgbe_disable_intr().
+ */
+ ixgbe_ensure_disabled_intr(hw->back);
/* Clear any pending interrupts, flush previous writes */
IXGBE_READ_REG(hw, IXGBE_EICR);
diff -r 421a42f7c670 -r 951cb907b235 sys/dev/pci/ixgbe/ixv.c
--- a/sys/dev/pci/ixgbe/ixv.c Fri Mar 30 03:56:38 2018 +0000
+++ b/sys/dev/pci/ixgbe/ixv.c Fri Mar 30 03:58:20 2018 +0000
@@ -1,4 +1,4 @@
-/*$NetBSD: ixv.c,v 1.89 2018/03/20 09:50:33 knakahara Exp $*/
+/*$NetBSD: ixv.c,v 1.90 2018/03/30 03:58:20 knakahara Exp $*/
/******************************************************************************
@@ -694,7 +694,7 @@
ixgbe_free_receive_structures(adapter);
for (int i = 0; i < adapter->num_queues; i++) {
struct ix_queue *lque = &adapter->queues[i];
- mutex_destroy(&lque->im_mtx);
+ mutex_destroy(&lque->dc_mtx);
}
free(adapter->queues, M_DEVBUF);
@@ -839,14 +839,14 @@
u32 queue = 1 << vector;
u32 mask;
- mutex_enter(&que->im_mtx);
- if (que->im_nest > 0 && --que->im_nest > 0)
+ mutex_enter(&que->dc_mtx);
+ if (que->disabled_count > 0 && --que->disabled_count > 0)
goto out;
mask = (IXGBE_EIMS_RTX_QUEUE & queue);
IXGBE_WRITE_REG(hw, IXGBE_VTEIMS, mask);
out:
- mutex_exit(&que->im_mtx);
+ mutex_exit(&que->dc_mtx);
} /* ixv_enable_queue */
/************************************************************************
@@ -860,14 +860,14 @@
u64 queue = (u64)(1 << vector);
u32 mask;
- mutex_enter(&que->im_mtx);
- if (que->im_nest++ > 0)
+ mutex_enter(&que->dc_mtx);
+ if (que->disabled_count++ > 0)
goto out;
mask = (IXGBE_EIMS_RTX_QUEUE & queue);
IXGBE_WRITE_REG(hw, IXGBE_VTEIMC, mask);
out:
- mutex_exit(&que->im_mtx);
+ mutex_exit(&que->dc_mtx);
} /* ixv_disable_queue */
static inline void
Home |
Main Index |
Thread Index |
Old Index