diff options
author | Dmitry Kravkov <dmitry@broadcom.com> | 2010-10-19 01:13:05 -0400 |
---|---|---|
committer | David S. Miller <davem@davemloft.net> | 2010-10-19 11:37:37 -0400 |
commit | a0fd065cd5d8f758b27c13cafabbbcf59d1eb8ec (patch) | |
tree | 709021cdad6ca4438c86074ff658920bdb56bc9a /drivers/net/bnx2x/bnx2x_main.c | |
parent | 8723e1b4ad9be4444423b4d41509ce859a629649 (diff) |
bnx2x: fix possible deadlock in HC hw block
The possible deadlock (on 57710 devices only) will prevent from the
device to generate interrupts.
Signed-off-by: Dmitry Kravkov <dmitry@broadcom.com>
Signed-off-by: Eilon Greenstein <eilong@broadcom.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'drivers/net/bnx2x/bnx2x_main.c')
-rw-r--r-- | drivers/net/bnx2x/bnx2x_main.c | 37 |
1 files changed, 29 insertions, 8 deletions
diff --git a/drivers/net/bnx2x/bnx2x_main.c b/drivers/net/bnx2x/bnx2x_main.c index 012c093cb432..3f49b551ff05 100644 --- a/drivers/net/bnx2x/bnx2x_main.c +++ b/drivers/net/bnx2x/bnx2x_main.c | |||
@@ -1111,14 +1111,19 @@ static void bnx2x_hc_int_enable(struct bnx2x *bp) | |||
1111 | HC_CONFIG_0_REG_INT_LINE_EN_0 | | 1111 | HC_CONFIG_0_REG_INT_LINE_EN_0 | |
1112 | HC_CONFIG_0_REG_ATTN_BIT_EN_0); | 1112 | HC_CONFIG_0_REG_ATTN_BIT_EN_0); |
1113 | 1113 | ||
1114 | DP(NETIF_MSG_INTR, "write %x to HC %d (addr 0x%x)\n", | 1114 | if (!CHIP_IS_E1(bp)) { |
1115 | val, port, addr); | 1115 | DP(NETIF_MSG_INTR, "write %x to HC %d (addr 0x%x)\n", |
1116 | val, port, addr); | ||
1116 | 1117 | ||
1117 | REG_WR(bp, addr, val); | 1118 | REG_WR(bp, addr, val); |
1118 | 1119 | ||
1119 | val &= ~HC_CONFIG_0_REG_MSI_MSIX_INT_EN_0; | 1120 | val &= ~HC_CONFIG_0_REG_MSI_MSIX_INT_EN_0; |
1121 | } | ||
1120 | } | 1122 | } |
1121 | 1123 | ||
1124 | if (CHIP_IS_E1(bp)) | ||
1125 | REG_WR(bp, HC_REG_INT_MASK + port*4, 0x1FFFF); | ||
1126 | |||
1122 | DP(NETIF_MSG_INTR, "write %x to HC %d (addr 0x%x) mode %s\n", | 1127 | DP(NETIF_MSG_INTR, "write %x to HC %d (addr 0x%x) mode %s\n", |
1123 | val, port, addr, (msix ? "MSI-X" : (msi ? "MSI" : "INTx"))); | 1128 | val, port, addr, (msix ? "MSI-X" : (msi ? "MSI" : "INTx"))); |
1124 | 1129 | ||
@@ -1212,10 +1217,26 @@ static void bnx2x_hc_int_disable(struct bnx2x *bp) | |||
1212 | u32 addr = port ? HC_REG_CONFIG_1 : HC_REG_CONFIG_0; | 1217 | u32 addr = port ? HC_REG_CONFIG_1 : HC_REG_CONFIG_0; |
1213 | u32 val = REG_RD(bp, addr); | 1218 | u32 val = REG_RD(bp, addr); |
1214 | 1219 | ||
1215 | val &= ~(HC_CONFIG_0_REG_SINGLE_ISR_EN_0 | | 1220 | /* |
1216 | HC_CONFIG_0_REG_MSI_MSIX_INT_EN_0 | | 1221 | * in E1 we must use only PCI configuration space to disable |
1217 | HC_CONFIG_0_REG_INT_LINE_EN_0 | | 1222 | * MSI/MSIX capablility |
1218 | HC_CONFIG_0_REG_ATTN_BIT_EN_0); | 1223 | * It's forbitten to disable IGU_PF_CONF_MSI_MSIX_EN in HC block |
1224 | */ | ||
1225 | if (CHIP_IS_E1(bp)) { | ||
1226 | /* Since IGU_PF_CONF_MSI_MSIX_EN still always on | ||
1227 | * Use mask register to prevent from HC sending interrupts | ||
1228 | * after we exit the function | ||
1229 | */ | ||
1230 | REG_WR(bp, HC_REG_INT_MASK + port*4, 0); | ||
1231 | |||
1232 | val &= ~(HC_CONFIG_0_REG_SINGLE_ISR_EN_0 | | ||
1233 | HC_CONFIG_0_REG_INT_LINE_EN_0 | | ||
1234 | HC_CONFIG_0_REG_ATTN_BIT_EN_0); | ||
1235 | } else | ||
1236 | val &= ~(HC_CONFIG_0_REG_SINGLE_ISR_EN_0 | | ||
1237 | HC_CONFIG_0_REG_MSI_MSIX_INT_EN_0 | | ||
1238 | HC_CONFIG_0_REG_INT_LINE_EN_0 | | ||
1239 | HC_CONFIG_0_REG_ATTN_BIT_EN_0); | ||
1219 | 1240 | ||
1220 | DP(NETIF_MSG_INTR, "write %x to HC %d (addr 0x%x)\n", | 1241 | DP(NETIF_MSG_INTR, "write %x to HC %d (addr 0x%x)\n", |
1221 | val, port, addr); | 1242 | val, port, addr); |