diff options
Diffstat (limited to 'drivers/net/ethernet/emulex/benet/be_main.c')
-rw-r--r-- | drivers/net/ethernet/emulex/benet/be_main.c | 29 |
1 files changed, 20 insertions, 9 deletions
diff --git a/drivers/net/ethernet/emulex/benet/be_main.c b/drivers/net/ethernet/emulex/benet/be_main.c index 9dca22be8125..5c995700e534 100644 --- a/drivers/net/ethernet/emulex/benet/be_main.c +++ b/drivers/net/ethernet/emulex/benet/be_main.c | |||
@@ -2026,19 +2026,30 @@ static irqreturn_t be_intx(int irq, void *dev) | |||
2026 | struct be_adapter *adapter = eqo->adapter; | 2026 | struct be_adapter *adapter = eqo->adapter; |
2027 | int num_evts = 0; | 2027 | int num_evts = 0; |
2028 | 2028 | ||
2029 | /* On Lancer, clear-intr bit of the EQ DB does not work. | 2029 | /* IRQ is not expected when NAPI is scheduled as the EQ |
2030 | * INTx is de-asserted only on notifying num evts. | 2030 | * will not be armed. |
2031 | * But, this can happen on Lancer INTx where it takes | ||
2032 | * a while to de-assert INTx or in BE2 where occasionaly | ||
2033 | * an interrupt may be raised even when EQ is unarmed. | ||
2034 | * If NAPI is already scheduled, then counting & notifying | ||
2035 | * events will orphan them. | ||
2031 | */ | 2036 | */ |
2032 | if (lancer_chip(adapter)) | 2037 | if (napi_schedule_prep(&eqo->napi)) { |
2033 | num_evts = events_get(eqo); | 2038 | num_evts = events_get(eqo); |
2039 | __napi_schedule(&eqo->napi); | ||
2040 | if (num_evts) | ||
2041 | eqo->spurious_intr = 0; | ||
2042 | } | ||
2043 | be_eq_notify(adapter, eqo->q.id, false, true, num_evts); | ||
2034 | 2044 | ||
2035 | /* The EQ-notify may not de-assert INTx rightaway, causing | 2045 | /* Return IRQ_HANDLED only for the the first spurious intr |
2036 | * the ISR to be invoked again. So, return HANDLED even when | 2046 | * after a valid intr to stop the kernel from branding |
2037 | * num_evts is zero. | 2047 | * this irq as a bad one! |
2038 | */ | 2048 | */ |
2039 | be_eq_notify(adapter, eqo->q.id, false, true, num_evts); | 2049 | if (num_evts || eqo->spurious_intr++ == 0) |
2040 | napi_schedule(&eqo->napi); | 2050 | return IRQ_HANDLED; |
2041 | return IRQ_HANDLED; | 2051 | else |
2052 | return IRQ_NONE; | ||
2042 | } | 2053 | } |
2043 | 2054 | ||
2044 | static irqreturn_t be_msix(int irq, void *dev) | 2055 | static irqreturn_t be_msix(int irq, void *dev) |