diff options
author | Ron Mercer <ron.mercer@qlogic.com> | 2009-03-02 03:07:31 -0500 |
---|---|---|
committer | David S. Miller <davem@davemloft.net> | 2009-03-03 01:45:24 -0500 |
commit | cdca8d02ea4229c2ccf3c27fb537b150843f67c9 (patch) | |
tree | e3fbc1f5e7f924f94eac26a0e06c7a11434aa037 | |
parent | ca0413b66ab44ee0ea40d04eab44ff0fdaf32a1d (diff) |
qlge: Add support for device ID 8000.
This device has more firmware support for link management, setting
TX and RX maximum frame sizes.
Signed-off-by: Ron Mercer <ron.mercer@qlogic.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
-rw-r--r-- | drivers/net/qlge/qlge.h | 37 | ||||
-rw-r--r-- | drivers/net/qlge/qlge_main.c | 64 |
2 files changed, 100 insertions, 1 deletions
diff --git a/drivers/net/qlge/qlge.h b/drivers/net/qlge/qlge.h index 7bf18c6d7bc0..5f60ec4efb3c 100644 --- a/drivers/net/qlge/qlge.h +++ b/drivers/net/qlge/qlge.h | |||
@@ -29,7 +29,7 @@ | |||
29 | 29 | ||
30 | #define QLGE_VENDOR_ID 0x1077 | 30 | #define QLGE_VENDOR_ID 0x1077 |
31 | #define QLGE_DEVICE_ID_8012 0x8012 | 31 | #define QLGE_DEVICE_ID_8012 0x8012 |
32 | 32 | #define QLGE_DEVICE_ID_8000 0x8000 | |
33 | #define MAX_CPUS 8 | 33 | #define MAX_CPUS 8 |
34 | #define MAX_TX_RINGS MAX_CPUS | 34 | #define MAX_TX_RINGS MAX_CPUS |
35 | #define MAX_RX_RINGS ((MAX_CPUS * 2) + 1) | 35 | #define MAX_RX_RINGS ((MAX_CPUS * 2) + 1) |
@@ -808,8 +808,42 @@ struct flash_params_8012 { | |||
808 | __le16 res; | 808 | __le16 res; |
809 | }; | 809 | }; |
810 | 810 | ||
811 | /* 8000 device's flash is a different structure | ||
812 | * at a different offset in flash. | ||
813 | */ | ||
814 | #define FUNC0_FLASH_OFFSET 0x140200 | ||
815 | #define FUNC1_FLASH_OFFSET 0x140600 | ||
816 | |||
817 | /* Flash related data structures. */ | ||
818 | struct flash_params_8000 { | ||
819 | u8 dev_id_str[4]; /* "8000" */ | ||
820 | __le16 ver; | ||
821 | __le16 size; | ||
822 | __le16 csum; | ||
823 | __le16 reserved0; | ||
824 | __le16 total_size; | ||
825 | __le16 entry_count; | ||
826 | u8 data_type0; | ||
827 | u8 data_size0; | ||
828 | u8 mac_addr[6]; | ||
829 | u8 data_type1; | ||
830 | u8 data_size1; | ||
831 | u8 mac_addr1[6]; | ||
832 | u8 data_type2; | ||
833 | u8 data_size2; | ||
834 | __le16 vlan_id; | ||
835 | u8 data_type3; | ||
836 | u8 data_size3; | ||
837 | __le16 last; | ||
838 | u8 reserved1[464]; | ||
839 | __le16 subsys_ven_id; | ||
840 | __le16 subsys_dev_id; | ||
841 | u8 reserved2[4]; | ||
842 | }; | ||
843 | |||
811 | union flash_params { | 844 | union flash_params { |
812 | struct flash_params_8012 flash_params_8012; | 845 | struct flash_params_8012 flash_params_8012; |
846 | struct flash_params_8000 flash_params_8000; | ||
813 | }; | 847 | }; |
814 | 848 | ||
815 | /* | 849 | /* |
@@ -1535,6 +1569,7 @@ void ql_queue_asic_error(struct ql_adapter *qdev); | |||
1535 | u32 ql_enable_completion_interrupt(struct ql_adapter *qdev, u32 intr); | 1569 | u32 ql_enable_completion_interrupt(struct ql_adapter *qdev, u32 intr); |
1536 | void ql_set_ethtool_ops(struct net_device *ndev); | 1570 | void ql_set_ethtool_ops(struct net_device *ndev); |
1537 | int ql_read_xgmac_reg64(struct ql_adapter *qdev, u32 reg, u64 *data); | 1571 | int ql_read_xgmac_reg64(struct ql_adapter *qdev, u32 reg, u64 *data); |
1572 | int ql_mb_get_fw_state(struct ql_adapter *qdev); | ||
1538 | 1573 | ||
1539 | #if 1 | 1574 | #if 1 |
1540 | #define QL_ALL_DUMP | 1575 | #define QL_ALL_DUMP |
diff --git a/drivers/net/qlge/qlge_main.c b/drivers/net/qlge/qlge_main.c index b4c6fd7a7616..29334d99b430 100644 --- a/drivers/net/qlge/qlge_main.c +++ b/drivers/net/qlge/qlge_main.c | |||
@@ -76,6 +76,7 @@ MODULE_PARM_DESC(irq_type, "0 = MSI-X, 1 = MSI, 2 = Legacy."); | |||
76 | 76 | ||
77 | static struct pci_device_id qlge_pci_tbl[] __devinitdata = { | 77 | static struct pci_device_id qlge_pci_tbl[] __devinitdata = { |
78 | {PCI_DEVICE(PCI_VENDOR_ID_QLOGIC, QLGE_DEVICE_ID_8012)}, | 78 | {PCI_DEVICE(PCI_VENDOR_ID_QLOGIC, QLGE_DEVICE_ID_8012)}, |
79 | {PCI_DEVICE(PCI_VENDOR_ID_QLOGIC, QLGE_DEVICE_ID_8000)}, | ||
79 | /* required last entry */ | 80 | /* required last entry */ |
80 | {0,} | 81 | {0,} |
81 | }; | 82 | }; |
@@ -669,6 +670,57 @@ exit: | |||
669 | return status; | 670 | return status; |
670 | } | 671 | } |
671 | 672 | ||
673 | static int ql_get_8000_flash_params(struct ql_adapter *qdev) | ||
674 | { | ||
675 | u32 i, size; | ||
676 | int status; | ||
677 | __le32 *p = (__le32 *)&qdev->flash; | ||
678 | u32 offset; | ||
679 | |||
680 | /* Get flash offset for function and adjust | ||
681 | * for dword access. | ||
682 | */ | ||
683 | if (!qdev->func) | ||
684 | offset = FUNC0_FLASH_OFFSET / sizeof(u32); | ||
685 | else | ||
686 | offset = FUNC1_FLASH_OFFSET / sizeof(u32); | ||
687 | |||
688 | if (ql_sem_spinlock(qdev, SEM_FLASH_MASK)) | ||
689 | return -ETIMEDOUT; | ||
690 | |||
691 | size = sizeof(struct flash_params_8000) / sizeof(u32); | ||
692 | for (i = 0; i < size; i++, p++) { | ||
693 | status = ql_read_flash_word(qdev, i+offset, p); | ||
694 | if (status) { | ||
695 | QPRINTK(qdev, IFUP, ERR, "Error reading flash.\n"); | ||
696 | goto exit; | ||
697 | } | ||
698 | } | ||
699 | |||
700 | status = ql_validate_flash(qdev, | ||
701 | sizeof(struct flash_params_8000) / sizeof(u16), | ||
702 | "8000"); | ||
703 | if (status) { | ||
704 | QPRINTK(qdev, IFUP, ERR, "Invalid flash.\n"); | ||
705 | status = -EINVAL; | ||
706 | goto exit; | ||
707 | } | ||
708 | |||
709 | if (!is_valid_ether_addr(qdev->flash.flash_params_8000.mac_addr)) { | ||
710 | QPRINTK(qdev, IFUP, ERR, "Invalid MAC address.\n"); | ||
711 | status = -EINVAL; | ||
712 | goto exit; | ||
713 | } | ||
714 | |||
715 | memcpy(qdev->ndev->dev_addr, | ||
716 | qdev->flash.flash_params_8000.mac_addr, | ||
717 | qdev->ndev->addr_len); | ||
718 | |||
719 | exit: | ||
720 | ql_sem_unlock(qdev, SEM_FLASH_MASK); | ||
721 | return status; | ||
722 | } | ||
723 | |||
672 | static int ql_get_8012_flash_params(struct ql_adapter *qdev) | 724 | static int ql_get_8012_flash_params(struct ql_adapter *qdev) |
673 | { | 725 | { |
674 | int i; | 726 | int i; |
@@ -783,6 +835,11 @@ exit: | |||
783 | return status; | 835 | return status; |
784 | } | 836 | } |
785 | 837 | ||
838 | static int ql_8000_port_initialize(struct ql_adapter *qdev) | ||
839 | { | ||
840 | return ql_mb_get_fw_state(qdev); | ||
841 | } | ||
842 | |||
786 | /* Take the MAC Core out of reset. | 843 | /* Take the MAC Core out of reset. |
787 | * Enable statistics counting. | 844 | * Enable statistics counting. |
788 | * Take the transmitter/receiver out of reset. | 845 | * Take the transmitter/receiver out of reset. |
@@ -3557,6 +3614,11 @@ static struct nic_operations qla8012_nic_ops = { | |||
3557 | .port_initialize = ql_8012_port_initialize, | 3614 | .port_initialize = ql_8012_port_initialize, |
3558 | }; | 3615 | }; |
3559 | 3616 | ||
3617 | static struct nic_operations qla8000_nic_ops = { | ||
3618 | .get_flash = ql_get_8000_flash_params, | ||
3619 | .port_initialize = ql_8000_port_initialize, | ||
3620 | }; | ||
3621 | |||
3560 | 3622 | ||
3561 | static void ql_get_board_info(struct ql_adapter *qdev) | 3623 | static void ql_get_board_info(struct ql_adapter *qdev) |
3562 | { | 3624 | { |
@@ -3579,6 +3641,8 @@ static void ql_get_board_info(struct ql_adapter *qdev) | |||
3579 | qdev->device_id = qdev->pdev->device; | 3641 | qdev->device_id = qdev->pdev->device; |
3580 | if (qdev->device_id == QLGE_DEVICE_ID_8012) | 3642 | if (qdev->device_id == QLGE_DEVICE_ID_8012) |
3581 | qdev->nic_ops = &qla8012_nic_ops; | 3643 | qdev->nic_ops = &qla8012_nic_ops; |
3644 | else if (qdev->device_id == QLGE_DEVICE_ID_8000) | ||
3645 | qdev->nic_ops = &qla8000_nic_ops; | ||
3582 | } | 3646 | } |
3583 | 3647 | ||
3584 | static void ql_release_all(struct pci_dev *pdev) | 3648 | static void ql_release_all(struct pci_dev *pdev) |