diff options
Diffstat (limited to 'drivers/net/qlcnic/qlcnic_main.c')
-rw-r--r-- | drivers/net/qlcnic/qlcnic_main.c | 435 |
1 files changed, 249 insertions, 186 deletions
diff --git a/drivers/net/qlcnic/qlcnic_main.c b/drivers/net/qlcnic/qlcnic_main.c index 234dab1f9982..1003eb76fda3 100644 --- a/drivers/net/qlcnic/qlcnic_main.c +++ b/drivers/net/qlcnic/qlcnic_main.c | |||
@@ -61,6 +61,10 @@ static int auto_fw_reset = AUTO_FW_RESET_ENABLED; | |||
61 | module_param(auto_fw_reset, int, 0644); | 61 | module_param(auto_fw_reset, int, 0644); |
62 | MODULE_PARM_DESC(auto_fw_reset, "Auto firmware reset (0=disabled, 1=enabled"); | 62 | MODULE_PARM_DESC(auto_fw_reset, "Auto firmware reset (0=disabled, 1=enabled"); |
63 | 63 | ||
64 | static int load_fw_file; | ||
65 | module_param(load_fw_file, int, 0644); | ||
66 | MODULE_PARM_DESC(load_fw_file, "Load firmware from (0=flash, 1=file"); | ||
67 | |||
64 | static int __devinit qlcnic_probe(struct pci_dev *pdev, | 68 | static int __devinit qlcnic_probe(struct pci_dev *pdev, |
65 | const struct pci_device_id *ent); | 69 | const struct pci_device_id *ent); |
66 | static void __devexit qlcnic_remove(struct pci_dev *pdev); | 70 | static void __devexit qlcnic_remove(struct pci_dev *pdev); |
@@ -84,6 +88,7 @@ static void qlcnic_remove_sysfs_entries(struct qlcnic_adapter *adapter); | |||
84 | static void qlcnic_create_diag_entries(struct qlcnic_adapter *adapter); | 88 | static void qlcnic_create_diag_entries(struct qlcnic_adapter *adapter); |
85 | static void qlcnic_remove_diag_entries(struct qlcnic_adapter *adapter); | 89 | static void qlcnic_remove_diag_entries(struct qlcnic_adapter *adapter); |
86 | 90 | ||
91 | static void qlcnic_idc_debug_info(struct qlcnic_adapter *adapter, u8 encoding); | ||
87 | static void qlcnic_clr_all_drv_state(struct qlcnic_adapter *adapter); | 92 | static void qlcnic_clr_all_drv_state(struct qlcnic_adapter *adapter); |
88 | static int qlcnic_can_start_firmware(struct qlcnic_adapter *adapter); | 93 | static int qlcnic_can_start_firmware(struct qlcnic_adapter *adapter); |
89 | 94 | ||
@@ -208,6 +213,9 @@ qlcnic_napi_enable(struct qlcnic_adapter *adapter) | |||
208 | struct qlcnic_host_sds_ring *sds_ring; | 213 | struct qlcnic_host_sds_ring *sds_ring; |
209 | struct qlcnic_recv_context *recv_ctx = &adapter->recv_ctx; | 214 | struct qlcnic_recv_context *recv_ctx = &adapter->recv_ctx; |
210 | 215 | ||
216 | if (adapter->is_up != QLCNIC_ADAPTER_UP_MAGIC) | ||
217 | return; | ||
218 | |||
211 | for (ring = 0; ring < adapter->max_sds_rings; ring++) { | 219 | for (ring = 0; ring < adapter->max_sds_rings; ring++) { |
212 | sds_ring = &recv_ctx->sds_rings[ring]; | 220 | sds_ring = &recv_ctx->sds_rings[ring]; |
213 | napi_enable(&sds_ring->napi); | 221 | napi_enable(&sds_ring->napi); |
@@ -222,6 +230,9 @@ qlcnic_napi_disable(struct qlcnic_adapter *adapter) | |||
222 | struct qlcnic_host_sds_ring *sds_ring; | 230 | struct qlcnic_host_sds_ring *sds_ring; |
223 | struct qlcnic_recv_context *recv_ctx = &adapter->recv_ctx; | 231 | struct qlcnic_recv_context *recv_ctx = &adapter->recv_ctx; |
224 | 232 | ||
233 | if (adapter->is_up != QLCNIC_ADAPTER_UP_MAGIC) | ||
234 | return; | ||
235 | |||
225 | for (ring = 0; ring < adapter->max_sds_rings; ring++) { | 236 | for (ring = 0; ring < adapter->max_sds_rings; ring++) { |
226 | sds_ring = &recv_ctx->sds_rings[ring]; | 237 | sds_ring = &recv_ctx->sds_rings[ring]; |
227 | qlcnic_disable_int(sds_ring); | 238 | qlcnic_disable_int(sds_ring); |
@@ -233,67 +244,6 @@ qlcnic_napi_disable(struct qlcnic_adapter *adapter) | |||
233 | static void qlcnic_clear_stats(struct qlcnic_adapter *adapter) | 244 | static void qlcnic_clear_stats(struct qlcnic_adapter *adapter) |
234 | { | 245 | { |
235 | memset(&adapter->stats, 0, sizeof(adapter->stats)); | 246 | memset(&adapter->stats, 0, sizeof(adapter->stats)); |
236 | return; | ||
237 | } | ||
238 | |||
239 | static int qlcnic_set_dma_mask(struct qlcnic_adapter *adapter) | ||
240 | { | ||
241 | struct pci_dev *pdev = adapter->pdev; | ||
242 | u64 mask, cmask; | ||
243 | |||
244 | adapter->pci_using_dac = 0; | ||
245 | |||
246 | mask = DMA_BIT_MASK(39); | ||
247 | cmask = mask; | ||
248 | |||
249 | if (pci_set_dma_mask(pdev, mask) == 0 && | ||
250 | pci_set_consistent_dma_mask(pdev, cmask) == 0) { | ||
251 | adapter->pci_using_dac = 1; | ||
252 | return 0; | ||
253 | } | ||
254 | |||
255 | return -EIO; | ||
256 | } | ||
257 | |||
258 | /* Update addressable range if firmware supports it */ | ||
259 | static int | ||
260 | qlcnic_update_dma_mask(struct qlcnic_adapter *adapter) | ||
261 | { | ||
262 | int change, shift, err; | ||
263 | u64 mask, old_mask, old_cmask; | ||
264 | struct pci_dev *pdev = adapter->pdev; | ||
265 | |||
266 | change = 0; | ||
267 | |||
268 | shift = QLCRD32(adapter, CRB_DMA_SHIFT); | ||
269 | if (shift > 32) | ||
270 | return 0; | ||
271 | |||
272 | if (shift > 9) | ||
273 | change = 1; | ||
274 | |||
275 | if (change) { | ||
276 | old_mask = pdev->dma_mask; | ||
277 | old_cmask = pdev->dev.coherent_dma_mask; | ||
278 | |||
279 | mask = DMA_BIT_MASK(32+shift); | ||
280 | |||
281 | err = pci_set_dma_mask(pdev, mask); | ||
282 | if (err) | ||
283 | goto err_out; | ||
284 | |||
285 | err = pci_set_consistent_dma_mask(pdev, mask); | ||
286 | if (err) | ||
287 | goto err_out; | ||
288 | dev_info(&pdev->dev, "using %d-bit dma mask\n", 32+shift); | ||
289 | } | ||
290 | |||
291 | return 0; | ||
292 | |||
293 | err_out: | ||
294 | pci_set_dma_mask(pdev, old_mask); | ||
295 | pci_set_consistent_dma_mask(pdev, old_cmask); | ||
296 | return err; | ||
297 | } | 247 | } |
298 | 248 | ||
299 | static void qlcnic_set_port_mode(struct qlcnic_adapter *adapter) | 249 | static void qlcnic_set_port_mode(struct qlcnic_adapter *adapter) |
@@ -512,13 +462,6 @@ qlcnic_setup_pci_map(struct qlcnic_adapter *adapter) | |||
512 | struct pci_dev *pdev = adapter->pdev; | 462 | struct pci_dev *pdev = adapter->pdev; |
513 | int pci_func = adapter->ahw.pci_func; | 463 | int pci_func = adapter->ahw.pci_func; |
514 | 464 | ||
515 | /* | ||
516 | * Set the CRB window to invalid. If any register in window 0 is | ||
517 | * accessed it should set the window to 0 and then reset it to 1. | ||
518 | */ | ||
519 | adapter->ahw.crb_win = -1; | ||
520 | adapter->ahw.ocm_win = -1; | ||
521 | |||
522 | /* remap phys address */ | 465 | /* remap phys address */ |
523 | mem_base = pci_resource_start(pdev, 0); /* 0 is for BAR 0 */ | 466 | mem_base = pci_resource_start(pdev, 0); /* 0 is for BAR 0 */ |
524 | mem_len = pci_resource_len(pdev, 0); | 467 | mem_len = pci_resource_len(pdev, 0); |
@@ -556,7 +499,9 @@ static void get_brd_name(struct qlcnic_adapter *adapter, char *name) | |||
556 | qlcnic_boards[i].device == pdev->device && | 499 | qlcnic_boards[i].device == pdev->device && |
557 | qlcnic_boards[i].sub_vendor == pdev->subsystem_vendor && | 500 | qlcnic_boards[i].sub_vendor == pdev->subsystem_vendor && |
558 | qlcnic_boards[i].sub_device == pdev->subsystem_device) { | 501 | qlcnic_boards[i].sub_device == pdev->subsystem_device) { |
559 | strcpy(name, qlcnic_boards[i].short_name); | 502 | sprintf(name, "%pM: %s" , |
503 | adapter->mac_addr, | ||
504 | qlcnic_boards[i].short_name); | ||
560 | found = 1; | 505 | found = 1; |
561 | break; | 506 | break; |
562 | } | 507 | } |
@@ -605,22 +550,10 @@ qlcnic_check_options(struct qlcnic_adapter *adapter) | |||
605 | brd_name, adapter->ahw.revision_id); | 550 | brd_name, adapter->ahw.revision_id); |
606 | } | 551 | } |
607 | 552 | ||
608 | if (adapter->fw_version < QLCNIC_VERSION_CODE(3, 4, 216)) { | 553 | dev_info(&pdev->dev, "firmware v%d.%d.%d\n", |
609 | adapter->driver_mismatch = 1; | 554 | fw_major, fw_minor, fw_build); |
610 | dev_warn(&pdev->dev, "firmware version %d.%d.%d unsupported\n", | ||
611 | fw_major, fw_minor, fw_build); | ||
612 | return; | ||
613 | } | ||
614 | |||
615 | i = QLCRD32(adapter, QLCNIC_SRE_MISC); | ||
616 | adapter->ahw.cut_through = (i & 0x8000) ? 1 : 0; | ||
617 | |||
618 | dev_info(&pdev->dev, "firmware v%d.%d.%d [%s]\n", | ||
619 | fw_major, fw_minor, fw_build, | ||
620 | adapter->ahw.cut_through ? "cut-through" : "legacy"); | ||
621 | 555 | ||
622 | if (adapter->fw_version >= QLCNIC_VERSION_CODE(4, 0, 222)) | 556 | adapter->capabilities = QLCRD32(adapter, CRB_FW_CAPABILITIES_1); |
623 | adapter->capabilities = QLCRD32(adapter, CRB_FW_CAPABILITIES_1); | ||
624 | 557 | ||
625 | adapter->flags &= ~QLCNIC_LRO_ENABLED; | 558 | adapter->flags &= ~QLCNIC_LRO_ENABLED; |
626 | 559 | ||
@@ -637,7 +570,6 @@ qlcnic_check_options(struct qlcnic_adapter *adapter) | |||
637 | 570 | ||
638 | adapter->num_txd = MAX_CMD_DESCRIPTORS; | 571 | adapter->num_txd = MAX_CMD_DESCRIPTORS; |
639 | 572 | ||
640 | adapter->num_lro_rxd = 0; | ||
641 | adapter->max_rds_rings = 2; | 573 | adapter->max_rds_rings = 2; |
642 | } | 574 | } |
643 | 575 | ||
@@ -646,11 +578,10 @@ qlcnic_start_firmware(struct qlcnic_adapter *adapter) | |||
646 | { | 578 | { |
647 | int val, err, first_boot; | 579 | int val, err, first_boot; |
648 | 580 | ||
649 | err = qlcnic_set_dma_mask(adapter); | 581 | err = qlcnic_can_start_firmware(adapter); |
650 | if (err) | 582 | if (err < 0) |
651 | return err; | 583 | return err; |
652 | 584 | else if (!err) | |
653 | if (!qlcnic_can_start_firmware(adapter)) | ||
654 | goto wait_init; | 585 | goto wait_init; |
655 | 586 | ||
656 | first_boot = QLCRD32(adapter, QLCNIC_CAM_RAM(0x1fc)); | 587 | first_boot = QLCRD32(adapter, QLCNIC_CAM_RAM(0x1fc)); |
@@ -658,7 +589,10 @@ qlcnic_start_firmware(struct qlcnic_adapter *adapter) | |||
658 | /* This is the first boot after power up */ | 589 | /* This is the first boot after power up */ |
659 | QLCWR32(adapter, QLCNIC_CAM_RAM(0x1fc), QLCNIC_BDINFO_MAGIC); | 590 | QLCWR32(adapter, QLCNIC_CAM_RAM(0x1fc), QLCNIC_BDINFO_MAGIC); |
660 | 591 | ||
661 | qlcnic_request_firmware(adapter); | 592 | if (load_fw_file) |
593 | qlcnic_request_firmware(adapter); | ||
594 | else | ||
595 | adapter->fw_type = QLCNIC_FLASH_ROMIMAGE; | ||
662 | 596 | ||
663 | err = qlcnic_need_fw_reset(adapter); | 597 | err = qlcnic_need_fw_reset(adapter); |
664 | if (err < 0) | 598 | if (err < 0) |
@@ -672,7 +606,6 @@ qlcnic_start_firmware(struct qlcnic_adapter *adapter) | |||
672 | msleep(1); | 606 | msleep(1); |
673 | } | 607 | } |
674 | 608 | ||
675 | QLCWR32(adapter, CRB_DMA_SHIFT, 0x55555555); | ||
676 | QLCWR32(adapter, QLCNIC_PEG_HALT_STATUS1, 0); | 609 | QLCWR32(adapter, QLCNIC_PEG_HALT_STATUS1, 0); |
677 | QLCWR32(adapter, QLCNIC_PEG_HALT_STATUS2, 0); | 610 | QLCWR32(adapter, QLCNIC_PEG_HALT_STATUS2, 0); |
678 | 611 | ||
@@ -696,16 +629,18 @@ wait_init: | |||
696 | goto err_out; | 629 | goto err_out; |
697 | 630 | ||
698 | QLCWR32(adapter, QLCNIC_CRB_DEV_STATE, QLCNIC_DEV_READY); | 631 | QLCWR32(adapter, QLCNIC_CRB_DEV_STATE, QLCNIC_DEV_READY); |
699 | 632 | qlcnic_idc_debug_info(adapter, 1); | |
700 | qlcnic_update_dma_mask(adapter); | ||
701 | 633 | ||
702 | qlcnic_check_options(adapter); | 634 | qlcnic_check_options(adapter); |
703 | 635 | ||
704 | adapter->need_fw_reset = 0; | 636 | adapter->need_fw_reset = 0; |
705 | 637 | ||
706 | /* fall through and release firmware */ | 638 | qlcnic_release_firmware(adapter); |
639 | return 0; | ||
707 | 640 | ||
708 | err_out: | 641 | err_out: |
642 | QLCWR32(adapter, QLCNIC_CRB_DEV_STATE, QLCNIC_DEV_FAILED); | ||
643 | dev_err(&adapter->pdev->dev, "Device state set to failed\n"); | ||
709 | qlcnic_release_firmware(adapter); | 644 | qlcnic_release_firmware(adapter); |
710 | return err; | 645 | return err; |
711 | } | 646 | } |
@@ -937,6 +872,7 @@ void qlcnic_diag_free_res(struct net_device *netdev, int max_sds_rings) | |||
937 | struct qlcnic_host_sds_ring *sds_ring; | 872 | struct qlcnic_host_sds_ring *sds_ring; |
938 | int ring; | 873 | int ring; |
939 | 874 | ||
875 | clear_bit(__QLCNIC_DEV_UP, &adapter->state); | ||
940 | if (adapter->diag_test == QLCNIC_INTERRUPT_TEST) { | 876 | if (adapter->diag_test == QLCNIC_INTERRUPT_TEST) { |
941 | for (ring = 0; ring < adapter->max_sds_rings; ring++) { | 877 | for (ring = 0; ring < adapter->max_sds_rings; ring++) { |
942 | sds_ring = &adapter->recv_ctx.sds_rings[ring]; | 878 | sds_ring = &adapter->recv_ctx.sds_rings[ring]; |
@@ -950,11 +886,11 @@ void qlcnic_diag_free_res(struct net_device *netdev, int max_sds_rings) | |||
950 | adapter->max_sds_rings = max_sds_rings; | 886 | adapter->max_sds_rings = max_sds_rings; |
951 | 887 | ||
952 | if (qlcnic_attach(adapter)) | 888 | if (qlcnic_attach(adapter)) |
953 | return; | 889 | goto out; |
954 | 890 | ||
955 | if (netif_running(netdev)) | 891 | if (netif_running(netdev)) |
956 | __qlcnic_up(adapter, netdev); | 892 | __qlcnic_up(adapter, netdev); |
957 | 893 | out: | |
958 | netif_device_attach(netdev); | 894 | netif_device_attach(netdev); |
959 | } | 895 | } |
960 | 896 | ||
@@ -976,8 +912,10 @@ int qlcnic_diag_alloc_res(struct net_device *netdev, int test) | |||
976 | adapter->diag_test = test; | 912 | adapter->diag_test = test; |
977 | 913 | ||
978 | ret = qlcnic_attach(adapter); | 914 | ret = qlcnic_attach(adapter); |
979 | if (ret) | 915 | if (ret) { |
916 | netif_device_attach(netdev); | ||
980 | return ret; | 917 | return ret; |
918 | } | ||
981 | 919 | ||
982 | if (adapter->diag_test == QLCNIC_INTERRUPT_TEST) { | 920 | if (adapter->diag_test == QLCNIC_INTERRUPT_TEST) { |
983 | for (ring = 0; ring < adapter->max_sds_rings; ring++) { | 921 | for (ring = 0; ring < adapter->max_sds_rings; ring++) { |
@@ -985,6 +923,7 @@ int qlcnic_diag_alloc_res(struct net_device *netdev, int test) | |||
985 | qlcnic_enable_int(sds_ring); | 923 | qlcnic_enable_int(sds_ring); |
986 | } | 924 | } |
987 | } | 925 | } |
926 | set_bit(__QLCNIC_DEV_UP, &adapter->state); | ||
988 | 927 | ||
989 | return 0; | 928 | return 0; |
990 | } | 929 | } |
@@ -1010,23 +949,19 @@ qlcnic_reset_context(struct qlcnic_adapter *adapter) | |||
1010 | if (netif_running(netdev)) { | 949 | if (netif_running(netdev)) { |
1011 | err = qlcnic_attach(adapter); | 950 | err = qlcnic_attach(adapter); |
1012 | if (!err) | 951 | if (!err) |
1013 | err = __qlcnic_up(adapter, netdev); | 952 | __qlcnic_up(adapter, netdev); |
1014 | |||
1015 | if (err) | ||
1016 | goto done; | ||
1017 | } | 953 | } |
1018 | 954 | ||
1019 | netif_device_attach(netdev); | 955 | netif_device_attach(netdev); |
1020 | } | 956 | } |
1021 | 957 | ||
1022 | done: | ||
1023 | clear_bit(__QLCNIC_RESETTING, &adapter->state); | 958 | clear_bit(__QLCNIC_RESETTING, &adapter->state); |
1024 | return err; | 959 | return err; |
1025 | } | 960 | } |
1026 | 961 | ||
1027 | static int | 962 | static int |
1028 | qlcnic_setup_netdev(struct qlcnic_adapter *adapter, | 963 | qlcnic_setup_netdev(struct qlcnic_adapter *adapter, |
1029 | struct net_device *netdev) | 964 | struct net_device *netdev, u8 pci_using_dac) |
1030 | { | 965 | { |
1031 | int err; | 966 | int err; |
1032 | struct pci_dev *pdev = adapter->pdev; | 967 | struct pci_dev *pdev = adapter->pdev; |
@@ -1049,7 +984,7 @@ qlcnic_setup_netdev(struct qlcnic_adapter *adapter, | |||
1049 | netdev->features |= (NETIF_F_IPV6_CSUM | NETIF_F_TSO6); | 984 | netdev->features |= (NETIF_F_IPV6_CSUM | NETIF_F_TSO6); |
1050 | netdev->vlan_features |= (NETIF_F_IPV6_CSUM | NETIF_F_TSO6); | 985 | netdev->vlan_features |= (NETIF_F_IPV6_CSUM | NETIF_F_TSO6); |
1051 | 986 | ||
1052 | if (adapter->pci_using_dac) { | 987 | if (pci_using_dac) { |
1053 | netdev->features |= NETIF_F_HIGHDMA; | 988 | netdev->features |= NETIF_F_HIGHDMA; |
1054 | netdev->vlan_features |= NETIF_F_HIGHDMA; | 989 | netdev->vlan_features |= NETIF_F_HIGHDMA; |
1055 | } | 990 | } |
@@ -1079,6 +1014,22 @@ qlcnic_setup_netdev(struct qlcnic_adapter *adapter, | |||
1079 | return 0; | 1014 | return 0; |
1080 | } | 1015 | } |
1081 | 1016 | ||
1017 | static int qlcnic_set_dma_mask(struct pci_dev *pdev, u8 *pci_using_dac) | ||
1018 | { | ||
1019 | if (!pci_set_dma_mask(pdev, DMA_BIT_MASK(64)) && | ||
1020 | !pci_set_consistent_dma_mask(pdev, DMA_BIT_MASK(64))) | ||
1021 | *pci_using_dac = 1; | ||
1022 | else if (!pci_set_dma_mask(pdev, DMA_BIT_MASK(32)) && | ||
1023 | !pci_set_consistent_dma_mask(pdev, DMA_BIT_MASK(32))) | ||
1024 | *pci_using_dac = 0; | ||
1025 | else { | ||
1026 | dev_err(&pdev->dev, "Unable to set DMA mask, aborting\n"); | ||
1027 | return -EIO; | ||
1028 | } | ||
1029 | |||
1030 | return 0; | ||
1031 | } | ||
1032 | |||
1082 | static int __devinit | 1033 | static int __devinit |
1083 | qlcnic_probe(struct pci_dev *pdev, const struct pci_device_id *ent) | 1034 | qlcnic_probe(struct pci_dev *pdev, const struct pci_device_id *ent) |
1084 | { | 1035 | { |
@@ -1087,6 +1038,7 @@ qlcnic_probe(struct pci_dev *pdev, const struct pci_device_id *ent) | |||
1087 | int err; | 1038 | int err; |
1088 | int pci_func_id = PCI_FUNC(pdev->devfn); | 1039 | int pci_func_id = PCI_FUNC(pdev->devfn); |
1089 | uint8_t revision_id; | 1040 | uint8_t revision_id; |
1041 | uint8_t pci_using_dac; | ||
1090 | 1042 | ||
1091 | err = pci_enable_device(pdev); | 1043 | err = pci_enable_device(pdev); |
1092 | if (err) | 1044 | if (err) |
@@ -1097,6 +1049,10 @@ qlcnic_probe(struct pci_dev *pdev, const struct pci_device_id *ent) | |||
1097 | goto err_out_disable_pdev; | 1049 | goto err_out_disable_pdev; |
1098 | } | 1050 | } |
1099 | 1051 | ||
1052 | err = qlcnic_set_dma_mask(pdev, &pci_using_dac); | ||
1053 | if (err) | ||
1054 | goto err_out_disable_pdev; | ||
1055 | |||
1100 | err = pci_request_regions(pdev, qlcnic_driver_name); | 1056 | err = pci_request_regions(pdev, qlcnic_driver_name); |
1101 | if (err) | 1057 | if (err) |
1102 | goto err_out_disable_pdev; | 1058 | goto err_out_disable_pdev; |
@@ -1115,6 +1071,7 @@ qlcnic_probe(struct pci_dev *pdev, const struct pci_device_id *ent) | |||
1115 | adapter = netdev_priv(netdev); | 1071 | adapter = netdev_priv(netdev); |
1116 | adapter->netdev = netdev; | 1072 | adapter->netdev = netdev; |
1117 | adapter->pdev = pdev; | 1073 | adapter->pdev = pdev; |
1074 | adapter->dev_rst_time = jiffies; | ||
1118 | adapter->ahw.pci_func = pci_func_id; | 1075 | adapter->ahw.pci_func = pci_func_id; |
1119 | 1076 | ||
1120 | revision_id = pdev->revision; | 1077 | revision_id = pdev->revision; |
@@ -1139,21 +1096,23 @@ qlcnic_probe(struct pci_dev *pdev, const struct pci_device_id *ent) | |||
1139 | goto err_out_iounmap; | 1096 | goto err_out_iounmap; |
1140 | } | 1097 | } |
1141 | 1098 | ||
1099 | if (qlcnic_read_mac_addr(adapter)) | ||
1100 | dev_warn(&pdev->dev, "failed to read mac addr\n"); | ||
1101 | |||
1102 | if (qlcnic_setup_idc_param(adapter)) | ||
1103 | goto err_out_iounmap; | ||
1142 | 1104 | ||
1143 | err = qlcnic_start_firmware(adapter); | 1105 | err = qlcnic_start_firmware(adapter); |
1144 | if (err) | 1106 | if (err) { |
1107 | dev_err(&pdev->dev, "Loading fw failed.Please Reboot\n"); | ||
1145 | goto err_out_decr_ref; | 1108 | goto err_out_decr_ref; |
1146 | 1109 | } | |
1147 | /* | ||
1148 | * See if the firmware gave us a virtual-physical port mapping. | ||
1149 | */ | ||
1150 | adapter->physical_port = adapter->portnum; | ||
1151 | 1110 | ||
1152 | qlcnic_clear_stats(adapter); | 1111 | qlcnic_clear_stats(adapter); |
1153 | 1112 | ||
1154 | qlcnic_setup_intr(adapter); | 1113 | qlcnic_setup_intr(adapter); |
1155 | 1114 | ||
1156 | err = qlcnic_setup_netdev(adapter, netdev); | 1115 | err = qlcnic_setup_netdev(adapter, netdev, pci_using_dac); |
1157 | if (err) | 1116 | if (err) |
1158 | goto err_out_disable_msi; | 1117 | goto err_out_disable_msi; |
1159 | 1118 | ||
@@ -1304,9 +1263,6 @@ qlcnic_resume(struct pci_dev *pdev) | |||
1304 | pci_set_master(pdev); | 1263 | pci_set_master(pdev); |
1305 | pci_restore_state(pdev); | 1264 | pci_restore_state(pdev); |
1306 | 1265 | ||
1307 | adapter->ahw.crb_win = -1; | ||
1308 | adapter->ahw.ocm_win = -1; | ||
1309 | |||
1310 | err = qlcnic_start_firmware(adapter); | 1266 | err = qlcnic_start_firmware(adapter); |
1311 | if (err) { | 1267 | if (err) { |
1312 | dev_err(&pdev->dev, "failed to start firmware\n"); | 1268 | dev_err(&pdev->dev, "failed to start firmware\n"); |
@@ -1334,6 +1290,7 @@ err_out_detach: | |||
1334 | qlcnic_detach(adapter); | 1290 | qlcnic_detach(adapter); |
1335 | err_out: | 1291 | err_out: |
1336 | qlcnic_clr_all_drv_state(adapter); | 1292 | qlcnic_clr_all_drv_state(adapter); |
1293 | netif_device_attach(netdev); | ||
1337 | return err; | 1294 | return err; |
1338 | } | 1295 | } |
1339 | #endif | 1296 | #endif |
@@ -1570,6 +1527,11 @@ qlcnic_xmit_frame(struct sk_buff *skb, struct net_device *netdev) | |||
1570 | int frag_count, no_of_desc; | 1527 | int frag_count, no_of_desc; |
1571 | u32 num_txd = tx_ring->num_desc; | 1528 | u32 num_txd = tx_ring->num_desc; |
1572 | 1529 | ||
1530 | if (!test_bit(__QLCNIC_DEV_UP, &adapter->state)) { | ||
1531 | netif_stop_queue(netdev); | ||
1532 | return NETDEV_TX_BUSY; | ||
1533 | } | ||
1534 | |||
1573 | frag_count = skb_shinfo(skb)->nr_frags + 1; | 1535 | frag_count = skb_shinfo(skb)->nr_frags + 1; |
1574 | 1536 | ||
1575 | /* 4 fragments per cmd des */ | 1537 | /* 4 fragments per cmd des */ |
@@ -1586,8 +1548,10 @@ qlcnic_xmit_frame(struct sk_buff *skb, struct net_device *netdev) | |||
1586 | 1548 | ||
1587 | pdev = adapter->pdev; | 1549 | pdev = adapter->pdev; |
1588 | 1550 | ||
1589 | if (qlcnic_map_tx_skb(pdev, skb, pbuf)) | 1551 | if (qlcnic_map_tx_skb(pdev, skb, pbuf)) { |
1552 | adapter->stats.tx_dma_map_error++; | ||
1590 | goto drop_packet; | 1553 | goto drop_packet; |
1554 | } | ||
1591 | 1555 | ||
1592 | pbuf->skb = skb; | 1556 | pbuf->skb = skb; |
1593 | pbuf->frag_count = frag_count; | 1557 | pbuf->frag_count = frag_count; |
@@ -1739,6 +1703,7 @@ static void qlcnic_tx_timeout_task(struct work_struct *work) | |||
1739 | request_reset: | 1703 | request_reset: |
1740 | adapter->need_fw_reset = 1; | 1704 | adapter->need_fw_reset = 1; |
1741 | clear_bit(__QLCNIC_RESETTING, &adapter->state); | 1705 | clear_bit(__QLCNIC_RESETTING, &adapter->state); |
1706 | QLCDB(adapter, DRV, "Resetting adapter\n"); | ||
1742 | } | 1707 | } |
1743 | 1708 | ||
1744 | static struct net_device_stats *qlcnic_get_stats(struct net_device *netdev) | 1709 | static struct net_device_stats *qlcnic_get_stats(struct net_device *netdev) |
@@ -1750,7 +1715,7 @@ static struct net_device_stats *qlcnic_get_stats(struct net_device *netdev) | |||
1750 | 1715 | ||
1751 | stats->rx_packets = adapter->stats.rx_pkts + adapter->stats.lro_pkts; | 1716 | stats->rx_packets = adapter->stats.rx_pkts + adapter->stats.lro_pkts; |
1752 | stats->tx_packets = adapter->stats.xmitfinished; | 1717 | stats->tx_packets = adapter->stats.xmitfinished; |
1753 | stats->rx_bytes = adapter->stats.rxbytes; | 1718 | stats->rx_bytes = adapter->stats.rxbytes + adapter->stats.lrobytes; |
1754 | stats->tx_bytes = adapter->stats.txbytes; | 1719 | stats->tx_bytes = adapter->stats.txbytes; |
1755 | stats->rx_dropped = adapter->stats.rxdropped; | 1720 | stats->rx_dropped = adapter->stats.rxdropped; |
1756 | stats->tx_dropped = adapter->stats.txdropped; | 1721 | stats->tx_dropped = adapter->stats.txdropped; |
@@ -1944,7 +1909,20 @@ static void qlcnic_poll_controller(struct net_device *netdev) | |||
1944 | #endif | 1909 | #endif |
1945 | 1910 | ||
1946 | static void | 1911 | static void |
1947 | qlcnic_set_drv_state(struct qlcnic_adapter *adapter, int state) | 1912 | qlcnic_idc_debug_info(struct qlcnic_adapter *adapter, u8 encoding) |
1913 | { | ||
1914 | u32 val; | ||
1915 | |||
1916 | val = adapter->portnum & 0xf; | ||
1917 | val |= encoding << 7; | ||
1918 | val |= (jiffies - adapter->dev_rst_time) << 8; | ||
1919 | |||
1920 | QLCWR32(adapter, QLCNIC_CRB_DRV_SCRATCH, val); | ||
1921 | adapter->dev_rst_time = jiffies; | ||
1922 | } | ||
1923 | |||
1924 | static int | ||
1925 | qlcnic_set_drv_state(struct qlcnic_adapter *adapter, u8 state) | ||
1948 | { | 1926 | { |
1949 | u32 val; | 1927 | u32 val; |
1950 | 1928 | ||
@@ -1952,18 +1930,20 @@ qlcnic_set_drv_state(struct qlcnic_adapter *adapter, int state) | |||
1952 | state != QLCNIC_DEV_NEED_QUISCENT); | 1930 | state != QLCNIC_DEV_NEED_QUISCENT); |
1953 | 1931 | ||
1954 | if (qlcnic_api_lock(adapter)) | 1932 | if (qlcnic_api_lock(adapter)) |
1955 | return ; | 1933 | return -EIO; |
1956 | 1934 | ||
1957 | val = QLCRD32(adapter, QLCNIC_CRB_DRV_STATE); | 1935 | val = QLCRD32(adapter, QLCNIC_CRB_DRV_STATE); |
1958 | 1936 | ||
1959 | if (state == QLCNIC_DEV_NEED_RESET) | 1937 | if (state == QLCNIC_DEV_NEED_RESET) |
1960 | val |= ((u32)0x1 << (adapter->portnum * 4)); | 1938 | QLC_DEV_SET_RST_RDY(val, adapter->portnum); |
1961 | else if (state == QLCNIC_DEV_NEED_QUISCENT) | 1939 | else if (state == QLCNIC_DEV_NEED_QUISCENT) |
1962 | val |= ((u32)0x1 << ((adapter->portnum * 4) + 1)); | 1940 | QLC_DEV_SET_QSCNT_RDY(val, adapter->portnum); |
1963 | 1941 | ||
1964 | QLCWR32(adapter, QLCNIC_CRB_DRV_STATE, val); | 1942 | QLCWR32(adapter, QLCNIC_CRB_DRV_STATE, val); |
1965 | 1943 | ||
1966 | qlcnic_api_unlock(adapter); | 1944 | qlcnic_api_unlock(adapter); |
1945 | |||
1946 | return 0; | ||
1967 | } | 1947 | } |
1968 | 1948 | ||
1969 | static int | 1949 | static int |
@@ -1975,7 +1955,7 @@ qlcnic_clr_drv_state(struct qlcnic_adapter *adapter) | |||
1975 | return -EBUSY; | 1955 | return -EBUSY; |
1976 | 1956 | ||
1977 | val = QLCRD32(adapter, QLCNIC_CRB_DRV_STATE); | 1957 | val = QLCRD32(adapter, QLCNIC_CRB_DRV_STATE); |
1978 | val &= ~((u32)0x3 << (adapter->portnum * 4)); | 1958 | QLC_DEV_CLR_RST_QSCNT(val, adapter->portnum); |
1979 | QLCWR32(adapter, QLCNIC_CRB_DRV_STATE, val); | 1959 | QLCWR32(adapter, QLCNIC_CRB_DRV_STATE, val); |
1980 | 1960 | ||
1981 | qlcnic_api_unlock(adapter); | 1961 | qlcnic_api_unlock(adapter); |
@@ -1992,14 +1972,14 @@ qlcnic_clr_all_drv_state(struct qlcnic_adapter *adapter) | |||
1992 | goto err; | 1972 | goto err; |
1993 | 1973 | ||
1994 | val = QLCRD32(adapter, QLCNIC_CRB_DEV_REF_COUNT); | 1974 | val = QLCRD32(adapter, QLCNIC_CRB_DEV_REF_COUNT); |
1995 | val &= ~((u32)0x1 << (adapter->portnum * 4)); | 1975 | QLC_DEV_CLR_REF_CNT(val, adapter->portnum); |
1996 | QLCWR32(adapter, QLCNIC_CRB_DEV_REF_COUNT, val); | 1976 | QLCWR32(adapter, QLCNIC_CRB_DEV_REF_COUNT, val); |
1997 | 1977 | ||
1998 | if (!(val & 0x11111111)) | 1978 | if (!(val & 0x11111111)) |
1999 | QLCWR32(adapter, QLCNIC_CRB_DEV_STATE, QLCNIC_DEV_COLD); | 1979 | QLCWR32(adapter, QLCNIC_CRB_DEV_STATE, QLCNIC_DEV_COLD); |
2000 | 1980 | ||
2001 | val = QLCRD32(adapter, QLCNIC_CRB_DRV_STATE); | 1981 | val = QLCRD32(adapter, QLCNIC_CRB_DRV_STATE); |
2002 | val &= ~((u32)0x3 << (adapter->portnum * 4)); | 1982 | QLC_DEV_CLR_RST_QSCNT(val, adapter->portnum); |
2003 | QLCWR32(adapter, QLCNIC_CRB_DRV_STATE, val); | 1983 | QLCWR32(adapter, QLCNIC_CRB_DRV_STATE, val); |
2004 | 1984 | ||
2005 | qlcnic_api_unlock(adapter); | 1985 | qlcnic_api_unlock(adapter); |
@@ -2009,6 +1989,7 @@ err: | |||
2009 | clear_bit(__QLCNIC_RESETTING, &adapter->state); | 1989 | clear_bit(__QLCNIC_RESETTING, &adapter->state); |
2010 | } | 1990 | } |
2011 | 1991 | ||
1992 | /* Grab api lock, before checking state */ | ||
2012 | static int | 1993 | static int |
2013 | qlcnic_check_drv_state(struct qlcnic_adapter *adapter) | 1994 | qlcnic_check_drv_state(struct qlcnic_adapter *adapter) |
2014 | { | 1995 | { |
@@ -2024,73 +2005,103 @@ qlcnic_check_drv_state(struct qlcnic_adapter *adapter) | |||
2024 | return 1; | 2005 | return 1; |
2025 | } | 2006 | } |
2026 | 2007 | ||
2008 | static int qlcnic_check_idc_ver(struct qlcnic_adapter *adapter) | ||
2009 | { | ||
2010 | u32 val = QLCRD32(adapter, QLCNIC_CRB_DRV_IDC_VER); | ||
2011 | |||
2012 | if (val != QLCNIC_DRV_IDC_VER) { | ||
2013 | dev_warn(&adapter->pdev->dev, "IDC Version mismatch, driver's" | ||
2014 | " idc ver = %x; reqd = %x\n", QLCNIC_DRV_IDC_VER, val); | ||
2015 | } | ||
2016 | |||
2017 | return 0; | ||
2018 | } | ||
2019 | |||
2027 | static int | 2020 | static int |
2028 | qlcnic_can_start_firmware(struct qlcnic_adapter *adapter) | 2021 | qlcnic_can_start_firmware(struct qlcnic_adapter *adapter) |
2029 | { | 2022 | { |
2030 | u32 val, prev_state; | 2023 | u32 val, prev_state; |
2031 | int cnt = 0; | 2024 | u8 dev_init_timeo = adapter->dev_init_timeo; |
2032 | int portnum = adapter->portnum; | 2025 | u8 portnum = adapter->portnum; |
2026 | u8 ret; | ||
2027 | |||
2028 | if (test_and_clear_bit(__QLCNIC_START_FW, &adapter->state)) | ||
2029 | return 1; | ||
2033 | 2030 | ||
2034 | if (qlcnic_api_lock(adapter)) | 2031 | if (qlcnic_api_lock(adapter)) |
2035 | return -1; | 2032 | return -1; |
2036 | 2033 | ||
2037 | val = QLCRD32(adapter, QLCNIC_CRB_DEV_REF_COUNT); | 2034 | val = QLCRD32(adapter, QLCNIC_CRB_DEV_REF_COUNT); |
2038 | if (!(val & ((int)0x1 << (portnum * 4)))) { | 2035 | if (!(val & (1 << (portnum * 4)))) { |
2039 | val |= ((u32)0x1 << (portnum * 4)); | 2036 | QLC_DEV_SET_REF_CNT(val, portnum); |
2040 | QLCWR32(adapter, QLCNIC_CRB_DEV_REF_COUNT, val); | 2037 | QLCWR32(adapter, QLCNIC_CRB_DEV_REF_COUNT, val); |
2041 | } else if (test_and_clear_bit(__QLCNIC_START_FW, &adapter->state)) { | ||
2042 | goto start_fw; | ||
2043 | } | 2038 | } |
2044 | 2039 | ||
2045 | prev_state = QLCRD32(adapter, QLCNIC_CRB_DEV_STATE); | 2040 | prev_state = QLCRD32(adapter, QLCNIC_CRB_DEV_STATE); |
2041 | QLCDB(adapter, HW, "Device state = %u\n", prev_state); | ||
2046 | 2042 | ||
2047 | switch (prev_state) { | 2043 | switch (prev_state) { |
2048 | case QLCNIC_DEV_COLD: | 2044 | case QLCNIC_DEV_COLD: |
2049 | start_fw: | 2045 | QLCWR32(adapter, QLCNIC_CRB_DEV_STATE, QLCNIC_DEV_INITIALIZING); |
2050 | QLCWR32(adapter, QLCNIC_CRB_DEV_STATE, QLCNIC_DEV_INITALIZING); | 2046 | QLCWR32(adapter, QLCNIC_CRB_DRV_IDC_VER, QLCNIC_DRV_IDC_VER); |
2047 | qlcnic_idc_debug_info(adapter, 0); | ||
2051 | qlcnic_api_unlock(adapter); | 2048 | qlcnic_api_unlock(adapter); |
2052 | return 1; | 2049 | return 1; |
2053 | 2050 | ||
2054 | case QLCNIC_DEV_READY: | 2051 | case QLCNIC_DEV_READY: |
2052 | ret = qlcnic_check_idc_ver(adapter); | ||
2055 | qlcnic_api_unlock(adapter); | 2053 | qlcnic_api_unlock(adapter); |
2056 | return 0; | 2054 | return ret; |
2057 | 2055 | ||
2058 | case QLCNIC_DEV_NEED_RESET: | 2056 | case QLCNIC_DEV_NEED_RESET: |
2059 | val = QLCRD32(adapter, QLCNIC_CRB_DRV_STATE); | 2057 | val = QLCRD32(adapter, QLCNIC_CRB_DRV_STATE); |
2060 | val |= ((u32)0x1 << (portnum * 4)); | 2058 | QLC_DEV_SET_RST_RDY(val, portnum); |
2061 | QLCWR32(adapter, QLCNIC_CRB_DRV_STATE, val); | 2059 | QLCWR32(adapter, QLCNIC_CRB_DRV_STATE, val); |
2062 | break; | 2060 | break; |
2063 | 2061 | ||
2064 | case QLCNIC_DEV_NEED_QUISCENT: | 2062 | case QLCNIC_DEV_NEED_QUISCENT: |
2065 | val = QLCRD32(adapter, QLCNIC_CRB_DRV_STATE); | 2063 | val = QLCRD32(adapter, QLCNIC_CRB_DRV_STATE); |
2066 | val |= ((u32)0x1 << ((portnum * 4) + 1)); | 2064 | QLC_DEV_SET_QSCNT_RDY(val, portnum); |
2067 | QLCWR32(adapter, QLCNIC_CRB_DRV_STATE, val); | 2065 | QLCWR32(adapter, QLCNIC_CRB_DRV_STATE, val); |
2068 | break; | 2066 | break; |
2069 | 2067 | ||
2070 | case QLCNIC_DEV_FAILED: | 2068 | case QLCNIC_DEV_FAILED: |
2069 | dev_err(&adapter->pdev->dev, "Device in failed state.\n"); | ||
2071 | qlcnic_api_unlock(adapter); | 2070 | qlcnic_api_unlock(adapter); |
2072 | return -1; | 2071 | return -1; |
2072 | |||
2073 | case QLCNIC_DEV_INITIALIZING: | ||
2074 | case QLCNIC_DEV_QUISCENT: | ||
2075 | break; | ||
2073 | } | 2076 | } |
2074 | 2077 | ||
2075 | qlcnic_api_unlock(adapter); | 2078 | qlcnic_api_unlock(adapter); |
2076 | msleep(1000); | 2079 | |
2077 | while ((QLCRD32(adapter, QLCNIC_CRB_DEV_STATE) != QLCNIC_DEV_READY) && | 2080 | do { |
2078 | ++cnt < 20) | ||
2079 | msleep(1000); | 2081 | msleep(1000); |
2082 | prev_state = QLCRD32(adapter, QLCNIC_CRB_DEV_STATE); | ||
2083 | |||
2084 | if (prev_state == QLCNIC_DEV_QUISCENT) | ||
2085 | continue; | ||
2086 | } while ((prev_state != QLCNIC_DEV_READY) && --dev_init_timeo); | ||
2080 | 2087 | ||
2081 | if (cnt >= 20) | 2088 | if (!dev_init_timeo) { |
2089 | dev_err(&adapter->pdev->dev, | ||
2090 | "Waiting for device to initialize timeout\n"); | ||
2082 | return -1; | 2091 | return -1; |
2092 | } | ||
2083 | 2093 | ||
2084 | if (qlcnic_api_lock(adapter)) | 2094 | if (qlcnic_api_lock(adapter)) |
2085 | return -1; | 2095 | return -1; |
2086 | 2096 | ||
2087 | val = QLCRD32(adapter, QLCNIC_CRB_DRV_STATE); | 2097 | val = QLCRD32(adapter, QLCNIC_CRB_DRV_STATE); |
2088 | val &= ~((u32)0x3 << (portnum * 4)); | 2098 | QLC_DEV_CLR_RST_QSCNT(val, portnum); |
2089 | QLCWR32(adapter, QLCNIC_CRB_DRV_STATE, val); | 2099 | QLCWR32(adapter, QLCNIC_CRB_DRV_STATE, val); |
2090 | 2100 | ||
2101 | ret = qlcnic_check_idc_ver(adapter); | ||
2091 | qlcnic_api_unlock(adapter); | 2102 | qlcnic_api_unlock(adapter); |
2092 | 2103 | ||
2093 | return 0; | 2104 | return ret; |
2094 | } | 2105 | } |
2095 | 2106 | ||
2096 | static void | 2107 | static void |
@@ -2098,44 +2109,84 @@ qlcnic_fwinit_work(struct work_struct *work) | |||
2098 | { | 2109 | { |
2099 | struct qlcnic_adapter *adapter = container_of(work, | 2110 | struct qlcnic_adapter *adapter = container_of(work, |
2100 | struct qlcnic_adapter, fw_work.work); | 2111 | struct qlcnic_adapter, fw_work.work); |
2101 | int dev_state; | 2112 | u32 dev_state = 0xf; |
2102 | 2113 | ||
2103 | if (++adapter->fw_wait_cnt > FW_POLL_THRESH) | 2114 | if (qlcnic_api_lock(adapter)) |
2104 | goto err_ret; | 2115 | goto err_ret; |
2105 | 2116 | ||
2106 | if (test_bit(__QLCNIC_START_FW, &adapter->state)) { | 2117 | dev_state = QLCRD32(adapter, QLCNIC_CRB_DEV_STATE); |
2118 | if (dev_state == QLCNIC_DEV_QUISCENT) { | ||
2119 | qlcnic_api_unlock(adapter); | ||
2120 | qlcnic_schedule_work(adapter, qlcnic_fwinit_work, | ||
2121 | FW_POLL_DELAY * 2); | ||
2122 | return; | ||
2123 | } | ||
2124 | |||
2125 | if (adapter->fw_wait_cnt++ > adapter->reset_ack_timeo) { | ||
2126 | dev_err(&adapter->pdev->dev, "Reset:Failed to get ack %d sec\n", | ||
2127 | adapter->reset_ack_timeo); | ||
2128 | goto skip_ack_check; | ||
2129 | } | ||
2130 | |||
2131 | if (!qlcnic_check_drv_state(adapter)) { | ||
2132 | skip_ack_check: | ||
2133 | dev_state = QLCRD32(adapter, QLCNIC_CRB_DEV_STATE); | ||
2107 | 2134 | ||
2108 | if (qlcnic_check_drv_state(adapter)) { | 2135 | if (dev_state == QLCNIC_DEV_NEED_QUISCENT) { |
2109 | qlcnic_schedule_work(adapter, | 2136 | QLCWR32(adapter, QLCNIC_CRB_DEV_STATE, |
2110 | qlcnic_fwinit_work, FW_POLL_DELAY); | 2137 | QLCNIC_DEV_QUISCENT); |
2138 | qlcnic_schedule_work(adapter, qlcnic_fwinit_work, | ||
2139 | FW_POLL_DELAY * 2); | ||
2140 | QLCDB(adapter, DRV, "Quiscing the driver\n"); | ||
2141 | qlcnic_idc_debug_info(adapter, 0); | ||
2142 | |||
2143 | qlcnic_api_unlock(adapter); | ||
2111 | return; | 2144 | return; |
2112 | } | 2145 | } |
2113 | 2146 | ||
2147 | if (dev_state == QLCNIC_DEV_NEED_RESET) { | ||
2148 | QLCWR32(adapter, QLCNIC_CRB_DEV_STATE, | ||
2149 | QLCNIC_DEV_INITIALIZING); | ||
2150 | set_bit(__QLCNIC_START_FW, &adapter->state); | ||
2151 | QLCDB(adapter, DRV, "Restarting fw\n"); | ||
2152 | qlcnic_idc_debug_info(adapter, 0); | ||
2153 | } | ||
2154 | |||
2155 | qlcnic_api_unlock(adapter); | ||
2156 | |||
2114 | if (!qlcnic_start_firmware(adapter)) { | 2157 | if (!qlcnic_start_firmware(adapter)) { |
2115 | qlcnic_schedule_work(adapter, qlcnic_attach_work, 0); | 2158 | qlcnic_schedule_work(adapter, qlcnic_attach_work, 0); |
2116 | return; | 2159 | return; |
2117 | } | 2160 | } |
2118 | |||
2119 | goto err_ret; | 2161 | goto err_ret; |
2120 | } | 2162 | } |
2121 | 2163 | ||
2164 | qlcnic_api_unlock(adapter); | ||
2165 | |||
2122 | dev_state = QLCRD32(adapter, QLCNIC_CRB_DEV_STATE); | 2166 | dev_state = QLCRD32(adapter, QLCNIC_CRB_DEV_STATE); |
2167 | QLCDB(adapter, HW, "Func waiting: Device state=%u\n", dev_state); | ||
2168 | |||
2123 | switch (dev_state) { | 2169 | switch (dev_state) { |
2124 | case QLCNIC_DEV_READY: | 2170 | case QLCNIC_DEV_QUISCENT: |
2125 | if (!qlcnic_start_firmware(adapter)) { | 2171 | case QLCNIC_DEV_NEED_QUISCENT: |
2126 | qlcnic_schedule_work(adapter, qlcnic_attach_work, 0); | 2172 | case QLCNIC_DEV_NEED_RESET: |
2127 | return; | 2173 | qlcnic_schedule_work(adapter, |
2128 | } | 2174 | qlcnic_fwinit_work, FW_POLL_DELAY); |
2175 | return; | ||
2129 | case QLCNIC_DEV_FAILED: | 2176 | case QLCNIC_DEV_FAILED: |
2130 | break; | 2177 | break; |
2131 | 2178 | ||
2132 | default: | 2179 | default: |
2133 | qlcnic_schedule_work(adapter, | 2180 | if (!qlcnic_start_firmware(adapter)) { |
2134 | qlcnic_fwinit_work, 2 * FW_POLL_DELAY); | 2181 | qlcnic_schedule_work(adapter, qlcnic_attach_work, 0); |
2135 | return; | 2182 | return; |
2183 | } | ||
2136 | } | 2184 | } |
2137 | 2185 | ||
2138 | err_ret: | 2186 | err_ret: |
2187 | dev_err(&adapter->pdev->dev, "Fwinit work failed state=%u " | ||
2188 | "fw_wait_cnt=%u\n", dev_state, adapter->fw_wait_cnt); | ||
2189 | netif_device_attach(adapter->netdev); | ||
2139 | qlcnic_clr_all_drv_state(adapter); | 2190 | qlcnic_clr_all_drv_state(adapter); |
2140 | } | 2191 | } |
2141 | 2192 | ||
@@ -2163,7 +2214,8 @@ qlcnic_detach_work(struct work_struct *work) | |||
2163 | if (adapter->temp == QLCNIC_TEMP_PANIC) | 2214 | if (adapter->temp == QLCNIC_TEMP_PANIC) |
2164 | goto err_ret; | 2215 | goto err_ret; |
2165 | 2216 | ||
2166 | qlcnic_set_drv_state(adapter, adapter->dev_state); | 2217 | if (qlcnic_set_drv_state(adapter, adapter->dev_state)) |
2218 | goto err_ret; | ||
2167 | 2219 | ||
2168 | adapter->fw_wait_cnt = 0; | 2220 | adapter->fw_wait_cnt = 0; |
2169 | 2221 | ||
@@ -2172,10 +2224,14 @@ qlcnic_detach_work(struct work_struct *work) | |||
2172 | return; | 2224 | return; |
2173 | 2225 | ||
2174 | err_ret: | 2226 | err_ret: |
2227 | dev_err(&adapter->pdev->dev, "detach failed; status=%d temp=%d\n", | ||
2228 | status, adapter->temp); | ||
2229 | netif_device_attach(netdev); | ||
2175 | qlcnic_clr_all_drv_state(adapter); | 2230 | qlcnic_clr_all_drv_state(adapter); |
2176 | 2231 | ||
2177 | } | 2232 | } |
2178 | 2233 | ||
2234 | /*Transit to RESET state from READY state only */ | ||
2179 | static void | 2235 | static void |
2180 | qlcnic_dev_request_reset(struct qlcnic_adapter *adapter) | 2236 | qlcnic_dev_request_reset(struct qlcnic_adapter *adapter) |
2181 | { | 2237 | { |
@@ -2186,9 +2242,10 @@ qlcnic_dev_request_reset(struct qlcnic_adapter *adapter) | |||
2186 | 2242 | ||
2187 | state = QLCRD32(adapter, QLCNIC_CRB_DEV_STATE); | 2243 | state = QLCRD32(adapter, QLCNIC_CRB_DEV_STATE); |
2188 | 2244 | ||
2189 | if (state != QLCNIC_DEV_INITALIZING && state != QLCNIC_DEV_NEED_RESET) { | 2245 | if (state == QLCNIC_DEV_READY) { |
2190 | QLCWR32(adapter, QLCNIC_CRB_DEV_STATE, QLCNIC_DEV_NEED_RESET); | 2246 | QLCWR32(adapter, QLCNIC_CRB_DEV_STATE, QLCNIC_DEV_NEED_RESET); |
2191 | set_bit(__QLCNIC_START_FW, &adapter->state); | 2247 | QLCDB(adapter, DRV, "NEED_RESET state set\n"); |
2248 | qlcnic_idc_debug_info(adapter, 0); | ||
2192 | } | 2249 | } |
2193 | 2250 | ||
2194 | qlcnic_api_unlock(adapter); | 2251 | qlcnic_api_unlock(adapter); |
@@ -2233,9 +2290,8 @@ qlcnic_attach_work(struct work_struct *work) | |||
2233 | qlcnic_config_indev_addr(netdev, NETDEV_UP); | 2290 | qlcnic_config_indev_addr(netdev, NETDEV_UP); |
2234 | } | 2291 | } |
2235 | 2292 | ||
2236 | netif_device_attach(netdev); | ||
2237 | |||
2238 | done: | 2293 | done: |
2294 | netif_device_attach(netdev); | ||
2239 | adapter->fw_fail_cnt = 0; | 2295 | adapter->fw_fail_cnt = 0; |
2240 | clear_bit(__QLCNIC_RESETTING, &adapter->state); | 2296 | clear_bit(__QLCNIC_RESETTING, &adapter->state); |
2241 | 2297 | ||
@@ -2253,10 +2309,8 @@ qlcnic_check_health(struct qlcnic_adapter *adapter) | |||
2253 | if (qlcnic_check_temp(adapter)) | 2309 | if (qlcnic_check_temp(adapter)) |
2254 | goto detach; | 2310 | goto detach; |
2255 | 2311 | ||
2256 | if (adapter->need_fw_reset) { | 2312 | if (adapter->need_fw_reset) |
2257 | qlcnic_dev_request_reset(adapter); | 2313 | qlcnic_dev_request_reset(adapter); |
2258 | goto detach; | ||
2259 | } | ||
2260 | 2314 | ||
2261 | state = QLCRD32(adapter, QLCNIC_CRB_DEV_STATE); | 2315 | state = QLCRD32(adapter, QLCNIC_CRB_DEV_STATE); |
2262 | if (state == QLCNIC_DEV_NEED_RESET || state == QLCNIC_DEV_NEED_QUISCENT) | 2316 | if (state == QLCNIC_DEV_NEED_RESET || state == QLCNIC_DEV_NEED_QUISCENT) |
@@ -2285,8 +2339,11 @@ detach: | |||
2285 | QLCNIC_DEV_NEED_RESET; | 2339 | QLCNIC_DEV_NEED_RESET; |
2286 | 2340 | ||
2287 | if ((auto_fw_reset == AUTO_FW_RESET_ENABLED) && | 2341 | if ((auto_fw_reset == AUTO_FW_RESET_ENABLED) && |
2288 | !test_and_set_bit(__QLCNIC_RESETTING, &adapter->state)) | 2342 | !test_and_set_bit(__QLCNIC_RESETTING, &adapter->state)) { |
2343 | |||
2289 | qlcnic_schedule_work(adapter, qlcnic_detach_work, 0); | 2344 | qlcnic_schedule_work(adapter, qlcnic_detach_work, 0); |
2345 | QLCDB(adapter, DRV, "fw recovery scheduled.\n"); | ||
2346 | } | ||
2290 | 2347 | ||
2291 | return 1; | 2348 | return 1; |
2292 | } | 2349 | } |
@@ -2387,14 +2444,21 @@ static int | |||
2387 | qlcnic_sysfs_validate_crb(struct qlcnic_adapter *adapter, | 2444 | qlcnic_sysfs_validate_crb(struct qlcnic_adapter *adapter, |
2388 | loff_t offset, size_t size) | 2445 | loff_t offset, size_t size) |
2389 | { | 2446 | { |
2447 | size_t crb_size = 4; | ||
2448 | |||
2390 | if (!(adapter->flags & QLCNIC_DIAG_ENABLED)) | 2449 | if (!(adapter->flags & QLCNIC_DIAG_ENABLED)) |
2391 | return -EIO; | 2450 | return -EIO; |
2392 | 2451 | ||
2393 | if ((size != 4) || (offset & 0x3)) | 2452 | if (offset < QLCNIC_PCI_CRBSPACE) { |
2394 | return -EINVAL; | 2453 | if (ADDR_IN_RANGE(offset, QLCNIC_PCI_CAMQM, |
2454 | QLCNIC_PCI_CAMQM_END)) | ||
2455 | crb_size = 8; | ||
2456 | else | ||
2457 | return -EINVAL; | ||
2458 | } | ||
2395 | 2459 | ||
2396 | if (offset < QLCNIC_PCI_CRBSPACE) | 2460 | if ((size != crb_size) || (offset & (crb_size-1))) |
2397 | return -EINVAL; | 2461 | return -EINVAL; |
2398 | 2462 | ||
2399 | return 0; | 2463 | return 0; |
2400 | } | 2464 | } |
@@ -2406,14 +2470,20 @@ qlcnic_sysfs_read_crb(struct kobject *kobj, struct bin_attribute *attr, | |||
2406 | struct device *dev = container_of(kobj, struct device, kobj); | 2470 | struct device *dev = container_of(kobj, struct device, kobj); |
2407 | struct qlcnic_adapter *adapter = dev_get_drvdata(dev); | 2471 | struct qlcnic_adapter *adapter = dev_get_drvdata(dev); |
2408 | u32 data; | 2472 | u32 data; |
2473 | u64 qmdata; | ||
2409 | int ret; | 2474 | int ret; |
2410 | 2475 | ||
2411 | ret = qlcnic_sysfs_validate_crb(adapter, offset, size); | 2476 | ret = qlcnic_sysfs_validate_crb(adapter, offset, size); |
2412 | if (ret != 0) | 2477 | if (ret != 0) |
2413 | return ret; | 2478 | return ret; |
2414 | 2479 | ||
2415 | data = QLCRD32(adapter, offset); | 2480 | if (ADDR_IN_RANGE(offset, QLCNIC_PCI_CAMQM, QLCNIC_PCI_CAMQM_END)) { |
2416 | memcpy(buf, &data, size); | 2481 | qlcnic_pci_camqm_read_2M(adapter, offset, &qmdata); |
2482 | memcpy(buf, &qmdata, size); | ||
2483 | } else { | ||
2484 | data = QLCRD32(adapter, offset); | ||
2485 | memcpy(buf, &data, size); | ||
2486 | } | ||
2417 | return size; | 2487 | return size; |
2418 | } | 2488 | } |
2419 | 2489 | ||
@@ -2424,14 +2494,20 @@ qlcnic_sysfs_write_crb(struct kobject *kobj, struct bin_attribute *attr, | |||
2424 | struct device *dev = container_of(kobj, struct device, kobj); | 2494 | struct device *dev = container_of(kobj, struct device, kobj); |
2425 | struct qlcnic_adapter *adapter = dev_get_drvdata(dev); | 2495 | struct qlcnic_adapter *adapter = dev_get_drvdata(dev); |
2426 | u32 data; | 2496 | u32 data; |
2497 | u64 qmdata; | ||
2427 | int ret; | 2498 | int ret; |
2428 | 2499 | ||
2429 | ret = qlcnic_sysfs_validate_crb(adapter, offset, size); | 2500 | ret = qlcnic_sysfs_validate_crb(adapter, offset, size); |
2430 | if (ret != 0) | 2501 | if (ret != 0) |
2431 | return ret; | 2502 | return ret; |
2432 | 2503 | ||
2433 | memcpy(&data, buf, size); | 2504 | if (ADDR_IN_RANGE(offset, QLCNIC_PCI_CAMQM, QLCNIC_PCI_CAMQM_END)) { |
2434 | QLCWR32(adapter, offset, data); | 2505 | memcpy(&qmdata, buf, size); |
2506 | qlcnic_pci_camqm_write_2M(adapter, offset, qmdata); | ||
2507 | } else { | ||
2508 | memcpy(&data, buf, size); | ||
2509 | QLCWR32(adapter, offset, data); | ||
2510 | } | ||
2435 | return size; | 2511 | return size; |
2436 | } | 2512 | } |
2437 | 2513 | ||
@@ -2553,24 +2629,12 @@ qlcnic_remove_diag_entries(struct qlcnic_adapter *adapter) | |||
2553 | 2629 | ||
2554 | #define is_qlcnic_netdev(dev) (dev->netdev_ops == &qlcnic_netdev_ops) | 2630 | #define is_qlcnic_netdev(dev) (dev->netdev_ops == &qlcnic_netdev_ops) |
2555 | 2631 | ||
2556 | static int | ||
2557 | qlcnic_destip_supported(struct qlcnic_adapter *adapter) | ||
2558 | { | ||
2559 | if (adapter->ahw.cut_through) | ||
2560 | return 0; | ||
2561 | |||
2562 | return 1; | ||
2563 | } | ||
2564 | |||
2565 | static void | 2632 | static void |
2566 | qlcnic_config_indev_addr(struct net_device *dev, unsigned long event) | 2633 | qlcnic_config_indev_addr(struct net_device *dev, unsigned long event) |
2567 | { | 2634 | { |
2568 | struct in_device *indev; | 2635 | struct in_device *indev; |
2569 | struct qlcnic_adapter *adapter = netdev_priv(dev); | 2636 | struct qlcnic_adapter *adapter = netdev_priv(dev); |
2570 | 2637 | ||
2571 | if (!qlcnic_destip_supported(adapter)) | ||
2572 | return; | ||
2573 | |||
2574 | indev = in_dev_get(dev); | 2638 | indev = in_dev_get(dev); |
2575 | if (!indev) | 2639 | if (!indev) |
2576 | return; | 2640 | return; |
@@ -2591,7 +2655,6 @@ qlcnic_config_indev_addr(struct net_device *dev, unsigned long event) | |||
2591 | } endfor_ifa(indev); | 2655 | } endfor_ifa(indev); |
2592 | 2656 | ||
2593 | in_dev_put(indev); | 2657 | in_dev_put(indev); |
2594 | return; | ||
2595 | } | 2658 | } |
2596 | 2659 | ||
2597 | static int qlcnic_netdev_event(struct notifier_block *this, | 2660 | static int qlcnic_netdev_event(struct notifier_block *this, |
@@ -2650,7 +2713,7 @@ recheck: | |||
2650 | 2713 | ||
2651 | adapter = netdev_priv(dev); | 2714 | adapter = netdev_priv(dev); |
2652 | 2715 | ||
2653 | if (!adapter || !qlcnic_destip_supported(adapter)) | 2716 | if (!adapter) |
2654 | goto done; | 2717 | goto done; |
2655 | 2718 | ||
2656 | if (adapter->is_up != QLCNIC_ADAPTER_UP_MAGIC) | 2719 | if (adapter->is_up != QLCNIC_ADAPTER_UP_MAGIC) |