diff options
Diffstat (limited to 'drivers/net/starfire.c')
| -rw-r--r-- | drivers/net/starfire.c | 54 |
1 files changed, 48 insertions, 6 deletions
diff --git a/drivers/net/starfire.c b/drivers/net/starfire.c index f54ac2389da2..57fb1f71c47b 100644 --- a/drivers/net/starfire.c +++ b/drivers/net/starfire.c | |||
| @@ -42,11 +42,11 @@ | |||
| 42 | #include <linux/mii.h> | 42 | #include <linux/mii.h> |
| 43 | #include <linux/if_vlan.h> | 43 | #include <linux/if_vlan.h> |
| 44 | #include <linux/mm.h> | 44 | #include <linux/mm.h> |
| 45 | #include <linux/firmware.h> | ||
| 45 | #include <asm/processor.h> /* Processor type for cache alignment. */ | 46 | #include <asm/processor.h> /* Processor type for cache alignment. */ |
| 46 | #include <asm/uaccess.h> | 47 | #include <asm/uaccess.h> |
| 47 | #include <asm/io.h> | 48 | #include <asm/io.h> |
| 48 | 49 | ||
| 49 | #include "starfire_firmware.h" | ||
| 50 | /* | 50 | /* |
| 51 | * The current frame processor firmware fails to checksum a fragment | 51 | * The current frame processor firmware fails to checksum a fragment |
| 52 | * of length 1. If and when this is fixed, the #define below can be removed. | 52 | * of length 1. If and when this is fixed, the #define below can be removed. |
| @@ -173,6 +173,10 @@ static int full_duplex[MAX_UNITS] = {0, }; | |||
| 173 | #define skb_first_frag_len(skb) skb_headlen(skb) | 173 | #define skb_first_frag_len(skb) skb_headlen(skb) |
| 174 | #define skb_num_frags(skb) (skb_shinfo(skb)->nr_frags + 1) | 174 | #define skb_num_frags(skb) (skb_shinfo(skb)->nr_frags + 1) |
| 175 | 175 | ||
| 176 | /* Firmware names */ | ||
| 177 | #define FIRMWARE_RX "adaptec/starfire_rx.bin" | ||
| 178 | #define FIRMWARE_TX "adaptec/starfire_tx.bin" | ||
| 179 | |||
| 176 | /* These identify the driver base version and may not be removed. */ | 180 | /* These identify the driver base version and may not be removed. */ |
| 177 | static char version[] = | 181 | static char version[] = |
| 178 | KERN_INFO "starfire.c:v1.03 7/26/2000 Written by Donald Becker <becker@scyld.com>\n" | 182 | KERN_INFO "starfire.c:v1.03 7/26/2000 Written by Donald Becker <becker@scyld.com>\n" |
| @@ -182,6 +186,8 @@ MODULE_AUTHOR("Donald Becker <becker@scyld.com>"); | |||
| 182 | MODULE_DESCRIPTION("Adaptec Starfire Ethernet driver"); | 186 | MODULE_DESCRIPTION("Adaptec Starfire Ethernet driver"); |
| 183 | MODULE_LICENSE("GPL"); | 187 | MODULE_LICENSE("GPL"); |
| 184 | MODULE_VERSION(DRV_VERSION); | 188 | MODULE_VERSION(DRV_VERSION); |
| 189 | MODULE_FIRMWARE(FIRMWARE_RX); | ||
| 190 | MODULE_FIRMWARE(FIRMWARE_TX); | ||
| 185 | 191 | ||
| 186 | module_param(max_interrupt_work, int, 0); | 192 | module_param(max_interrupt_work, int, 0); |
| 187 | module_param(mtu, int, 0); | 193 | module_param(mtu, int, 0); |
| @@ -902,9 +908,12 @@ static void mdio_write(struct net_device *dev, int phy_id, int location, int val | |||
| 902 | 908 | ||
| 903 | static int netdev_open(struct net_device *dev) | 909 | static int netdev_open(struct net_device *dev) |
| 904 | { | 910 | { |
| 911 | const struct firmware *fw_rx, *fw_tx; | ||
| 912 | const __be32 *fw_rx_data, *fw_tx_data; | ||
| 905 | struct netdev_private *np = netdev_priv(dev); | 913 | struct netdev_private *np = netdev_priv(dev); |
| 906 | void __iomem *ioaddr = np->base; | 914 | void __iomem *ioaddr = np->base; |
| 907 | int i, retval; | 915 | int i, retval; |
| 916 | size_t tx_size, rx_size; | ||
| 908 | size_t tx_done_q_size, rx_done_q_size, tx_ring_size, rx_ring_size; | 917 | size_t tx_done_q_size, rx_done_q_size, tx_ring_size, rx_ring_size; |
| 909 | 918 | ||
| 910 | /* Do we ever need to reset the chip??? */ | 919 | /* Do we ever need to reset the chip??? */ |
| @@ -1040,11 +1049,40 @@ static int netdev_open(struct net_device *dev) | |||
| 1040 | writel(ETH_P_8021Q, ioaddr + VlanType); | 1049 | writel(ETH_P_8021Q, ioaddr + VlanType); |
| 1041 | #endif /* VLAN_SUPPORT */ | 1050 | #endif /* VLAN_SUPPORT */ |
| 1042 | 1051 | ||
| 1052 | retval = request_firmware(&fw_rx, FIRMWARE_RX, &np->pci_dev->dev); | ||
| 1053 | if (retval) { | ||
| 1054 | printk(KERN_ERR "starfire: Failed to load firmware \"%s\"\n", | ||
| 1055 | FIRMWARE_RX); | ||
| 1056 | return retval; | ||
| 1057 | } | ||
| 1058 | if (fw_rx->size % 4) { | ||
| 1059 | printk(KERN_ERR "starfire: bogus length %zu in \"%s\"\n", | ||
| 1060 | fw_rx->size, FIRMWARE_RX); | ||
| 1061 | retval = -EINVAL; | ||
| 1062 | goto out_rx; | ||
| 1063 | } | ||
| 1064 | retval = request_firmware(&fw_tx, FIRMWARE_TX, &np->pci_dev->dev); | ||
| 1065 | if (retval) { | ||
| 1066 | printk(KERN_ERR "starfire: Failed to load firmware \"%s\"\n", | ||
| 1067 | FIRMWARE_TX); | ||
| 1068 | goto out_rx; | ||
| 1069 | } | ||
| 1070 | if (fw_tx->size % 4) { | ||
| 1071 | printk(KERN_ERR "starfire: bogus length %zu in \"%s\"\n", | ||
| 1072 | fw_tx->size, FIRMWARE_TX); | ||
| 1073 | retval = -EINVAL; | ||
| 1074 | goto out_tx; | ||
| 1075 | } | ||
| 1076 | fw_rx_data = (const __be32 *)&fw_rx->data[0]; | ||
| 1077 | fw_tx_data = (const __be32 *)&fw_tx->data[0]; | ||
| 1078 | rx_size = fw_rx->size / 4; | ||
| 1079 | tx_size = fw_tx->size / 4; | ||
| 1080 | |||
| 1043 | /* Load Rx/Tx firmware into the frame processors */ | 1081 | /* Load Rx/Tx firmware into the frame processors */ |
| 1044 | for (i = 0; i < FIRMWARE_RX_SIZE * 2; i++) | 1082 | for (i = 0; i < rx_size; i++) |
| 1045 | writel(firmware_rx[i], ioaddr + RxGfpMem + i * 4); | 1083 | writel(be32_to_cpup(&fw_rx_data[i]), ioaddr + RxGfpMem + i * 4); |
| 1046 | for (i = 0; i < FIRMWARE_TX_SIZE * 2; i++) | 1084 | for (i = 0; i < tx_size; i++) |
| 1047 | writel(firmware_tx[i], ioaddr + TxGfpMem + i * 4); | 1085 | writel(be32_to_cpup(&fw_tx_data[i]), ioaddr + TxGfpMem + i * 4); |
| 1048 | if (enable_hw_cksum) | 1086 | if (enable_hw_cksum) |
| 1049 | /* Enable the Rx and Tx units, and the Rx/Tx frame processors. */ | 1087 | /* Enable the Rx and Tx units, and the Rx/Tx frame processors. */ |
| 1050 | writel(TxEnable|TxGFPEnable|RxEnable|RxGFPEnable, ioaddr + GenCtrl); | 1088 | writel(TxEnable|TxGFPEnable|RxEnable|RxGFPEnable, ioaddr + GenCtrl); |
| @@ -1056,7 +1094,11 @@ static int netdev_open(struct net_device *dev) | |||
| 1056 | printk(KERN_DEBUG "%s: Done netdev_open().\n", | 1094 | printk(KERN_DEBUG "%s: Done netdev_open().\n", |
| 1057 | dev->name); | 1095 | dev->name); |
| 1058 | 1096 | ||
| 1059 | return 0; | 1097 | out_tx: |
| 1098 | release_firmware(fw_tx); | ||
| 1099 | out_rx: | ||
| 1100 | release_firmware(fw_rx); | ||
| 1101 | return retval; | ||
| 1060 | } | 1102 | } |
| 1061 | 1103 | ||
| 1062 | 1104 | ||
