blob: 1f722c99afb9f3a12523315451a0758346396422 [file] [log] [blame]
Linus Torvalds1da177e2005-04-16 15:20:36 -07001/*******************************************************************************
2 *
3 * Linux ThunderLAN Driver
4 *
5 * tlan.c
6 * by James Banks
7 *
8 * (C) 1997-1998 Caldera, Inc.
9 * (C) 1998 James Banks
10 * (C) 1999-2001 Torben Mathiasen
11 * (C) 2002 Samuel Chessman
12 *
13 * This software may be used and distributed according to the terms
14 * of the GNU General Public License, incorporated herein by reference.
15 *
Linus Torvalds1da177e2005-04-16 15:20:36 -070016 ** Useful (if not required) reading:
17 *
18 * Texas Instruments, ThunderLAN Programmer's Guide,
19 * TI Literature Number SPWU013A
20 * available in PDF format from www.ti.com
21 * Level One, LXT901 and LXT970 Data Sheets
22 * available in PDF format from www.level1.com
23 * National Semiconductor, DP83840A Data Sheet
24 * available in PDF format from www.national.com
25 * Microchip Technology, 24C01A/02A/04A Data Sheet
26 * available in PDF format from www.microchip.com
27 *
Sakari Ailusc659c382011-01-21 10:59:30 +000028 ******************************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -070029
Joe Perches50624aa2011-03-01 06:56:33 +000030#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
31
Alexey Dobriyana6b7a402011-06-06 10:43:46 +000032#include <linux/hardirq.h>
Linus Torvalds1da177e2005-04-16 15:20:36 -070033#include <linux/module.h>
34#include <linux/init.h>
Alexey Dobriyana6b7a402011-06-06 10:43:46 +000035#include <linux/interrupt.h>
Linus Torvalds1da177e2005-04-16 15:20:36 -070036#include <linux/ioport.h>
37#include <linux/eisa.h>
38#include <linux/pci.h>
Domen Puncer1e7f0bd2005-06-26 18:22:14 -040039#include <linux/dma-mapping.h>
Linus Torvalds1da177e2005-04-16 15:20:36 -070040#include <linux/netdevice.h>
41#include <linux/etherdevice.h>
42#include <linux/delay.h>
43#include <linux/spinlock.h>
44#include <linux/workqueue.h>
45#include <linux/mii.h>
46
47#include "tlan.h"
48
Linus Torvalds1da177e2005-04-16 15:20:36 -070049
50/* For removing EISA devices */
Sakari Ailusc659c382011-01-21 10:59:30 +000051static struct net_device *tlan_eisa_devices;
Linus Torvalds1da177e2005-04-16 15:20:36 -070052
Sakari Ailusc659c382011-01-21 10:59:30 +000053static int tlan_devices_installed;
Linus Torvalds1da177e2005-04-16 15:20:36 -070054
55/* Set speed, duplex and aui settings */
56static int aui[MAX_TLAN_BOARDS];
57static int duplex[MAX_TLAN_BOARDS];
58static int speed[MAX_TLAN_BOARDS];
59static int boards_found;
Stephen Hemminger15efa9b2005-05-04 15:33:11 -070060module_param_array(aui, int, NULL, 0);
61module_param_array(duplex, int, NULL, 0);
62module_param_array(speed, int, NULL, 0);
63MODULE_PARM_DESC(aui, "ThunderLAN use AUI port(s) (0-1)");
Sakari Ailusc659c382011-01-21 10:59:30 +000064MODULE_PARM_DESC(duplex,
65 "ThunderLAN duplex setting(s) (0-default, 1-half, 2-full)");
Joe Perches50624aa2011-03-01 06:56:33 +000066MODULE_PARM_DESC(speed, "ThunderLAN port speed setting(s) (0,10,100)");
Linus Torvalds1da177e2005-04-16 15:20:36 -070067
68MODULE_AUTHOR("Maintainer: Samuel Chessman <chessman@tux.org>");
69MODULE_DESCRIPTION("Driver for TI ThunderLAN based ethernet PCI adapters");
70MODULE_LICENSE("GPL");
71
Linus Torvalds1da177e2005-04-16 15:20:36 -070072/* Turn on debugging. See Documentation/networking/tlan.txt for details */
73static int debug;
Stephen Hemminger15efa9b2005-05-04 15:33:11 -070074module_param(debug, int, 0);
75MODULE_PARM_DESC(debug, "ThunderLAN debug mask");
Linus Torvalds1da177e2005-04-16 15:20:36 -070076
Sakari Ailusc659c382011-01-21 10:59:30 +000077static const char tlan_signature[] = "TLAN";
Sakari Ailusfa6d5d42011-01-21 10:59:31 +000078static const char tlan_banner[] = "ThunderLAN driver v1.17\n";
Linus Torvalds1da177e2005-04-16 15:20:36 -070079static int tlan_have_pci;
80static int tlan_have_eisa;
81
Sakari Ailusc659c382011-01-21 10:59:30 +000082static const char * const media[] = {
83 "10BaseT-HD", "10BaseT-FD", "100baseTx-HD",
84 "100BaseTx-FD", "100BaseT4", NULL
Linus Torvalds1da177e2005-04-16 15:20:36 -070085};
86
87static struct board {
Sakari Ailusc659c382011-01-21 10:59:30 +000088 const char *device_label;
89 u32 flags;
90 u16 addr_ofs;
Linus Torvalds1da177e2005-04-16 15:20:36 -070091} board_info[] = {
92 { "Compaq Netelligent 10 T PCI UTP", TLAN_ADAPTER_ACTIVITY_LED, 0x83 },
Sakari Ailusc659c382011-01-21 10:59:30 +000093 { "Compaq Netelligent 10/100 TX PCI UTP",
94 TLAN_ADAPTER_ACTIVITY_LED, 0x83 },
Linus Torvalds1da177e2005-04-16 15:20:36 -070095 { "Compaq Integrated NetFlex-3/P", TLAN_ADAPTER_NONE, 0x83 },
Stephen Hemmingerdfc2c0a2008-05-30 09:49:58 -070096 { "Compaq NetFlex-3/P",
97 TLAN_ADAPTER_UNMANAGED_PHY | TLAN_ADAPTER_BIT_RATE_PHY, 0x83 },
Linus Torvalds1da177e2005-04-16 15:20:36 -070098 { "Compaq NetFlex-3/P", TLAN_ADAPTER_NONE, 0x83 },
Stephen Hemmingerdfc2c0a2008-05-30 09:49:58 -070099 { "Compaq Netelligent Integrated 10/100 TX UTP",
100 TLAN_ADAPTER_ACTIVITY_LED, 0x83 },
Sakari Ailusc659c382011-01-21 10:59:30 +0000101 { "Compaq Netelligent Dual 10/100 TX PCI UTP",
102 TLAN_ADAPTER_NONE, 0x83 },
103 { "Compaq Netelligent 10/100 TX Embedded UTP",
104 TLAN_ADAPTER_NONE, 0x83 },
Linus Torvalds1da177e2005-04-16 15:20:36 -0700105 { "Olicom OC-2183/2185", TLAN_ADAPTER_USE_INTERN_10, 0x83 },
Ondrej Zaryeb522bb2014-06-30 18:38:27 +0200106 { "Olicom OC-2325", TLAN_ADAPTER_ACTIVITY_LED |
107 TLAN_ADAPTER_UNMANAGED_PHY, 0xf8 },
108 { "Olicom OC-2326", TLAN_ADAPTER_ACTIVITY_LED |
109 TLAN_ADAPTER_USE_INTERN_10, 0xf8 },
Linus Torvalds1da177e2005-04-16 15:20:36 -0700110 { "Compaq Netelligent 10/100 TX UTP", TLAN_ADAPTER_ACTIVITY_LED, 0x83 },
Sakari Ailusc659c382011-01-21 10:59:30 +0000111 { "Compaq Netelligent 10 T/2 PCI UTP/coax", TLAN_ADAPTER_NONE, 0x83 },
Stephen Hemmingerdfc2c0a2008-05-30 09:49:58 -0700112 { "Compaq NetFlex-3/E",
Sakari Ailusc659c382011-01-21 10:59:30 +0000113 TLAN_ADAPTER_ACTIVITY_LED | /* EISA card */
Stephen Hemmingerdfc2c0a2008-05-30 09:49:58 -0700114 TLAN_ADAPTER_UNMANAGED_PHY | TLAN_ADAPTER_BIT_RATE_PHY, 0x83 },
Sakari Ailusc659c382011-01-21 10:59:30 +0000115 { "Compaq NetFlex-3/E",
116 TLAN_ADAPTER_ACTIVITY_LED, 0x83 }, /* EISA card */
Linus Torvalds1da177e2005-04-16 15:20:36 -0700117};
118
Benoit Taine9baa3c32014-08-08 15:56:03 +0200119static const struct pci_device_id tlan_pci_tbl[] = {
Linus Torvalds1da177e2005-04-16 15:20:36 -0700120 { PCI_VENDOR_ID_COMPAQ, PCI_DEVICE_ID_COMPAQ_NETEL10,
Sakari Ailusc659c382011-01-21 10:59:30 +0000121 PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
Linus Torvalds1da177e2005-04-16 15:20:36 -0700122 { PCI_VENDOR_ID_COMPAQ, PCI_DEVICE_ID_COMPAQ_NETEL100,
Sakari Ailusc659c382011-01-21 10:59:30 +0000123 PCI_ANY_ID, PCI_ANY_ID, 0, 0, 1 },
Linus Torvalds1da177e2005-04-16 15:20:36 -0700124 { PCI_VENDOR_ID_COMPAQ, PCI_DEVICE_ID_COMPAQ_NETFLEX3I,
Sakari Ailusc659c382011-01-21 10:59:30 +0000125 PCI_ANY_ID, PCI_ANY_ID, 0, 0, 2 },
Linus Torvalds1da177e2005-04-16 15:20:36 -0700126 { PCI_VENDOR_ID_COMPAQ, PCI_DEVICE_ID_COMPAQ_THUNDER,
Sakari Ailusc659c382011-01-21 10:59:30 +0000127 PCI_ANY_ID, PCI_ANY_ID, 0, 0, 3 },
Linus Torvalds1da177e2005-04-16 15:20:36 -0700128 { PCI_VENDOR_ID_COMPAQ, PCI_DEVICE_ID_COMPAQ_NETFLEX3B,
Sakari Ailusc659c382011-01-21 10:59:30 +0000129 PCI_ANY_ID, PCI_ANY_ID, 0, 0, 4 },
Linus Torvalds1da177e2005-04-16 15:20:36 -0700130 { PCI_VENDOR_ID_COMPAQ, PCI_DEVICE_ID_COMPAQ_NETEL100PI,
Sakari Ailusc659c382011-01-21 10:59:30 +0000131 PCI_ANY_ID, PCI_ANY_ID, 0, 0, 5 },
Linus Torvalds1da177e2005-04-16 15:20:36 -0700132 { PCI_VENDOR_ID_COMPAQ, PCI_DEVICE_ID_COMPAQ_NETEL100D,
Sakari Ailusc659c382011-01-21 10:59:30 +0000133 PCI_ANY_ID, PCI_ANY_ID, 0, 0, 6 },
Linus Torvalds1da177e2005-04-16 15:20:36 -0700134 { PCI_VENDOR_ID_COMPAQ, PCI_DEVICE_ID_COMPAQ_NETEL100I,
Sakari Ailusc659c382011-01-21 10:59:30 +0000135 PCI_ANY_ID, PCI_ANY_ID, 0, 0, 7 },
Linus Torvalds1da177e2005-04-16 15:20:36 -0700136 { PCI_VENDOR_ID_OLICOM, PCI_DEVICE_ID_OLICOM_OC2183,
Sakari Ailusc659c382011-01-21 10:59:30 +0000137 PCI_ANY_ID, PCI_ANY_ID, 0, 0, 8 },
Linus Torvalds1da177e2005-04-16 15:20:36 -0700138 { PCI_VENDOR_ID_OLICOM, PCI_DEVICE_ID_OLICOM_OC2325,
Sakari Ailusc659c382011-01-21 10:59:30 +0000139 PCI_ANY_ID, PCI_ANY_ID, 0, 0, 9 },
Linus Torvalds1da177e2005-04-16 15:20:36 -0700140 { PCI_VENDOR_ID_OLICOM, PCI_DEVICE_ID_OLICOM_OC2326,
Sakari Ailusc659c382011-01-21 10:59:30 +0000141 PCI_ANY_ID, PCI_ANY_ID, 0, 0, 10 },
Linus Torvalds1da177e2005-04-16 15:20:36 -0700142 { PCI_VENDOR_ID_COMPAQ, PCI_DEVICE_ID_NETELLIGENT_10_100_WS_5100,
Sakari Ailusc659c382011-01-21 10:59:30 +0000143 PCI_ANY_ID, PCI_ANY_ID, 0, 0, 11 },
Linus Torvalds1da177e2005-04-16 15:20:36 -0700144 { PCI_VENDOR_ID_COMPAQ, PCI_DEVICE_ID_NETELLIGENT_10_T2,
Sakari Ailusc659c382011-01-21 10:59:30 +0000145 PCI_ANY_ID, PCI_ANY_ID, 0, 0, 12 },
Linus Torvalds1da177e2005-04-16 15:20:36 -0700146 { 0,}
147};
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400148MODULE_DEVICE_TABLE(pci, tlan_pci_tbl);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700149
Sakari Ailusc659c382011-01-21 10:59:30 +0000150static void tlan_eisa_probe(void);
151static void tlan_eisa_cleanup(void);
152static int tlan_init(struct net_device *);
153static int tlan_open(struct net_device *dev);
154static netdev_tx_t tlan_start_tx(struct sk_buff *, struct net_device *);
155static irqreturn_t tlan_handle_interrupt(int, void *);
156static int tlan_close(struct net_device *);
157static struct net_device_stats *tlan_get_stats(struct net_device *);
158static void tlan_set_multicast_list(struct net_device *);
159static int tlan_ioctl(struct net_device *dev, struct ifreq *rq, int cmd);
160static int tlan_probe1(struct pci_dev *pdev, long ioaddr,
161 int irq, int rev, const struct pci_device_id *ent);
162static void tlan_tx_timeout(struct net_device *dev);
163static void tlan_tx_timeout_work(struct work_struct *work);
164static int tlan_init_one(struct pci_dev *pdev,
165 const struct pci_device_id *ent);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700166
Sakari Ailusc659c382011-01-21 10:59:30 +0000167static u32 tlan_handle_tx_eof(struct net_device *, u16);
168static u32 tlan_handle_stat_overflow(struct net_device *, u16);
169static u32 tlan_handle_rx_eof(struct net_device *, u16);
170static u32 tlan_handle_dummy(struct net_device *, u16);
171static u32 tlan_handle_tx_eoc(struct net_device *, u16);
172static u32 tlan_handle_status_check(struct net_device *, u16);
173static u32 tlan_handle_rx_eoc(struct net_device *, u16);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700174
Sakari Ailusc659c382011-01-21 10:59:30 +0000175static void tlan_timer(unsigned long);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700176
Sakari Ailusc659c382011-01-21 10:59:30 +0000177static void tlan_reset_lists(struct net_device *);
178static void tlan_free_lists(struct net_device *);
179static void tlan_print_dio(u16);
180static void tlan_print_list(struct tlan_list *, char *, int);
181static void tlan_read_and_clear_stats(struct net_device *, int);
182static void tlan_reset_adapter(struct net_device *);
183static void tlan_finish_reset(struct net_device *);
184static void tlan_set_mac(struct net_device *, int areg, char *mac);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700185
Sakari Ailusc659c382011-01-21 10:59:30 +0000186static void tlan_phy_print(struct net_device *);
187static void tlan_phy_detect(struct net_device *);
188static void tlan_phy_power_down(struct net_device *);
189static void tlan_phy_power_up(struct net_device *);
190static void tlan_phy_reset(struct net_device *);
191static void tlan_phy_start_link(struct net_device *);
192static void tlan_phy_finish_auto_neg(struct net_device *);
Ondrej Zaryc0a87c22014-06-30 18:38:28 +0200193static void tlan_phy_monitor(unsigned long);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700194
195/*
Sakari Ailusc659c382011-01-21 10:59:30 +0000196 static int tlan_phy_nop(struct net_device *);
197 static int tlan_phy_internal_check(struct net_device *);
198 static int tlan_phy_internal_service(struct net_device *);
199 static int tlan_phy_dp83840a_check(struct net_device *);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700200*/
201
Sakari Ailusc659c382011-01-21 10:59:30 +0000202static bool tlan_mii_read_reg(struct net_device *, u16, u16, u16 *);
203static void tlan_mii_send_data(u16, u32, unsigned);
204static void tlan_mii_sync(u16);
205static void tlan_mii_write_reg(struct net_device *, u16, u16, u16);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700206
Sakari Ailusc659c382011-01-21 10:59:30 +0000207static void tlan_ee_send_start(u16);
208static int tlan_ee_send_byte(u16, u8, int);
209static void tlan_ee_receive_byte(u16, u8 *, int);
210static int tlan_ee_read_byte(struct net_device *, u8, u8 *);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700211
212
Stephen Hemminger93e16842008-05-30 09:49:55 -0700213static inline void
Sakari Ailusc659c382011-01-21 10:59:30 +0000214tlan_store_skb(struct tlan_list *tag, struct sk_buff *skb)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700215{
216 unsigned long addr = (unsigned long)skb;
Stephen Hemminger93e16842008-05-30 09:49:55 -0700217 tag->buffer[9].address = addr;
218 tag->buffer[8].address = upper_32_bits(addr);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700219}
220
Stephen Hemminger93e16842008-05-30 09:49:55 -0700221static inline struct sk_buff *
Sakari Ailusc659c382011-01-21 10:59:30 +0000222tlan_get_skb(const struct tlan_list *tag)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700223{
Stephen Hemminger93e16842008-05-30 09:49:55 -0700224 unsigned long addr;
225
Robert Fitzsimons0d63bea2008-08-09 17:54:02 +0100226 addr = tag->buffer[9].address;
Benjamin Poirierda3a9e92012-04-25 04:49:20 +0000227 addr |= ((unsigned long) tag->buffer[8].address << 16) << 16;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700228 return (struct sk_buff *) addr;
229}
230
Sakari Ailusc659c382011-01-21 10:59:30 +0000231static u32
232(*tlan_int_vector[TLAN_INT_NUMBER_OF_INTS])(struct net_device *, u16) = {
Stephen Hemmingera3ccc782008-05-30 09:49:57 -0700233 NULL,
Sakari Ailusc659c382011-01-21 10:59:30 +0000234 tlan_handle_tx_eof,
235 tlan_handle_stat_overflow,
236 tlan_handle_rx_eof,
237 tlan_handle_dummy,
238 tlan_handle_tx_eoc,
239 tlan_handle_status_check,
240 tlan_handle_rx_eoc
Linus Torvalds1da177e2005-04-16 15:20:36 -0700241};
242
243static inline void
Sakari Ailusc659c382011-01-21 10:59:30 +0000244tlan_set_timer(struct net_device *dev, u32 ticks, u32 type)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700245{
Sakari Ailusc659c382011-01-21 10:59:30 +0000246 struct tlan_priv *priv = netdev_priv(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700247 unsigned long flags = 0;
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400248
Linus Torvalds1da177e2005-04-16 15:20:36 -0700249 if (!in_irq())
250 spin_lock_irqsave(&priv->lock, flags);
Sakari Ailusc659c382011-01-21 10:59:30 +0000251 if (priv->timer.function != NULL &&
252 priv->timer_type != TLAN_TIMER_ACTIVITY) {
Linus Torvalds1da177e2005-04-16 15:20:36 -0700253 if (!in_irq())
254 spin_unlock_irqrestore(&priv->lock, flags);
255 return;
256 }
Sakari Ailusc659c382011-01-21 10:59:30 +0000257 priv->timer.function = tlan_timer;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700258 if (!in_irq())
259 spin_unlock_irqrestore(&priv->lock, flags);
260
261 priv->timer.data = (unsigned long) dev;
Sakari Ailusc659c382011-01-21 10:59:30 +0000262 priv->timer_set_at = jiffies;
263 priv->timer_type = type;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700264 mod_timer(&priv->timer, jiffies + ticks);
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400265
Sakari Ailusc659c382011-01-21 10:59:30 +0000266}
Linus Torvalds1da177e2005-04-16 15:20:36 -0700267
268
269/*****************************************************************************
270******************************************************************************
271
Sakari Ailusc659c382011-01-21 10:59:30 +0000272ThunderLAN driver primary functions
Linus Torvalds1da177e2005-04-16 15:20:36 -0700273
Sakari Ailusc659c382011-01-21 10:59:30 +0000274these functions are more or less common to all linux network drivers.
Linus Torvalds1da177e2005-04-16 15:20:36 -0700275
276******************************************************************************
277*****************************************************************************/
278
279
280
281
282
Sakari Ailusc659c382011-01-21 10:59:30 +0000283/***************************************************************
284 * tlan_remove_one
285 *
286 * Returns:
287 * Nothing
288 * Parms:
289 * None
290 *
291 * Goes through the TLanDevices list and frees the device
292 * structs and memory associated with each device (lists
293 * and buffers). It also ureserves the IO port regions
294 * associated with this device.
295 *
296 **************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -0700297
298
Bill Pemberton36915872012-12-03 09:23:44 -0500299static void tlan_remove_one(struct pci_dev *pdev)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700300{
Sakari Ailusc659c382011-01-21 10:59:30 +0000301 struct net_device *dev = pci_get_drvdata(pdev);
302 struct tlan_priv *priv = netdev_priv(dev);
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400303
Sakari Ailusc659c382011-01-21 10:59:30 +0000304 unregister_netdev(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700305
Sakari Ailusc659c382011-01-21 10:59:30 +0000306 if (priv->dma_storage) {
307 pci_free_consistent(priv->pci_dev,
308 priv->dma_size, priv->dma_storage,
309 priv->dma_storage_dma);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700310 }
311
312#ifdef CONFIG_PCI
313 pci_release_regions(pdev);
314#endif
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400315
Sakari Ailusc659c382011-01-21 10:59:30 +0000316 free_netdev(dev);
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400317
Devendra Naga1e0a8b12013-04-16 01:30:38 +0000318 cancel_work_sync(&priv->tlan_tqueue);
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400319}
Linus Torvalds1da177e2005-04-16 15:20:36 -0700320
Sakari Ailusfa6d5d42011-01-21 10:59:31 +0000321static void tlan_start(struct net_device *dev)
322{
323 tlan_reset_lists(dev);
324 /* NOTE: It might not be necessary to read the stats before a
325 reset if you don't care what the values are.
326 */
327 tlan_read_and_clear_stats(dev, TLAN_IGNORE);
328 tlan_reset_adapter(dev);
329 netif_wake_queue(dev);
330}
331
332static void tlan_stop(struct net_device *dev)
333{
334 struct tlan_priv *priv = netdev_priv(dev);
335
Ondrej Zaryc0a87c22014-06-30 18:38:28 +0200336 del_timer_sync(&priv->media_timer);
Sakari Ailusfa6d5d42011-01-21 10:59:31 +0000337 tlan_read_and_clear_stats(dev, TLAN_RECORD);
338 outl(TLAN_HC_AD_RST, dev->base_addr + TLAN_HOST_CMD);
339 /* Reset and power down phy */
340 tlan_reset_adapter(dev);
341 if (priv->timer.function != NULL) {
342 del_timer_sync(&priv->timer);
343 priv->timer.function = NULL;
344 }
345}
346
347#ifdef CONFIG_PM
348
349static int tlan_suspend(struct pci_dev *pdev, pm_message_t state)
350{
351 struct net_device *dev = pci_get_drvdata(pdev);
352
353 if (netif_running(dev))
354 tlan_stop(dev);
355
356 netif_device_detach(dev);
357 pci_save_state(pdev);
358 pci_disable_device(pdev);
359 pci_wake_from_d3(pdev, false);
360 pci_set_power_state(pdev, PCI_D3hot);
361
362 return 0;
363}
364
365static int tlan_resume(struct pci_dev *pdev)
366{
367 struct net_device *dev = pci_get_drvdata(pdev);
Ondrej Zarye697b162014-06-30 18:38:36 +0200368 int rc = pci_enable_device(pdev);
Sakari Ailusfa6d5d42011-01-21 10:59:31 +0000369
Ondrej Zarye697b162014-06-30 18:38:36 +0200370 if (rc)
371 return rc;
Sakari Ailusfa6d5d42011-01-21 10:59:31 +0000372 pci_restore_state(pdev);
Yijing Wang1ca01512013-06-27 20:53:42 +0800373 pci_enable_wake(pdev, PCI_D0, 0);
Sakari Ailusfa6d5d42011-01-21 10:59:31 +0000374 netif_device_attach(dev);
375
376 if (netif_running(dev))
377 tlan_start(dev);
378
379 return 0;
380}
381
382#else /* CONFIG_PM */
383
384#define tlan_suspend NULL
385#define tlan_resume NULL
386
387#endif /* CONFIG_PM */
388
389
Linus Torvalds1da177e2005-04-16 15:20:36 -0700390static struct pci_driver tlan_driver = {
391 .name = "tlan",
392 .id_table = tlan_pci_tbl,
393 .probe = tlan_init_one,
Bill Pemberton36915872012-12-03 09:23:44 -0500394 .remove = tlan_remove_one,
Sakari Ailusfa6d5d42011-01-21 10:59:31 +0000395 .suspend = tlan_suspend,
396 .resume = tlan_resume,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700397};
398
399static int __init tlan_probe(void)
400{
Leonardo Potenza6c04a512008-02-04 23:47:16 -0800401 int rc = -ENODEV;
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400402
Joe Perches50624aa2011-03-01 06:56:33 +0000403 pr_info("%s", tlan_banner);
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400404
Linus Torvalds1da177e2005-04-16 15:20:36 -0700405 TLAN_DBG(TLAN_DEBUG_PROBE, "Starting PCI Probe....\n");
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400406
Linus Torvalds1da177e2005-04-16 15:20:36 -0700407 /* Use new style PCI probing. Now the kernel will
408 do most of this for us */
Leonardo Potenza6c04a512008-02-04 23:47:16 -0800409 rc = pci_register_driver(&tlan_driver);
410
411 if (rc != 0) {
Joe Perches50624aa2011-03-01 06:56:33 +0000412 pr_err("Could not register pci driver\n");
Leonardo Potenza6c04a512008-02-04 23:47:16 -0800413 goto err_out_pci_free;
414 }
Linus Torvalds1da177e2005-04-16 15:20:36 -0700415
416 TLAN_DBG(TLAN_DEBUG_PROBE, "Starting EISA Probe....\n");
Sakari Ailusc659c382011-01-21 10:59:30 +0000417 tlan_eisa_probe();
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400418
Joe Perches50624aa2011-03-01 06:56:33 +0000419 pr_info("%d device%s installed, PCI: %d EISA: %d\n",
420 tlan_devices_installed, tlan_devices_installed == 1 ? "" : "s",
421 tlan_have_pci, tlan_have_eisa);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700422
Sakari Ailusc659c382011-01-21 10:59:30 +0000423 if (tlan_devices_installed == 0) {
Leonardo Potenza6c04a512008-02-04 23:47:16 -0800424 rc = -ENODEV;
425 goto err_out_pci_unreg;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700426 }
427 return 0;
Leonardo Potenza6c04a512008-02-04 23:47:16 -0800428
429err_out_pci_unreg:
430 pci_unregister_driver(&tlan_driver);
431err_out_pci_free:
Leonardo Potenza6c04a512008-02-04 23:47:16 -0800432 return rc;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700433}
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400434
Linus Torvalds1da177e2005-04-16 15:20:36 -0700435
Bill Pemberton36915872012-12-03 09:23:44 -0500436static int tlan_init_one(struct pci_dev *pdev,
Sakari Ailusc659c382011-01-21 10:59:30 +0000437 const struct pci_device_id *ent)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700438{
Sakari Ailusc659c382011-01-21 10:59:30 +0000439 return tlan_probe1(pdev, -1, -1, 0, ent);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700440}
441
442
443/*
Sakari Ailusc659c382011-01-21 10:59:30 +0000444***************************************************************
445* tlan_probe1
446*
447* Returns:
448* 0 on success, error code on error
449* Parms:
450* none
451*
452* The name is lower case to fit in with all the rest of
453* the netcard_probe names. This function looks for
454* another TLan based adapter, setting it up with the
455* allocated device struct if one is found.
456* tlan_probe has been ported to the new net API and
457* now allocates its own device structure. This function
458* is also used by modules.
459*
460**************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -0700461
Greg Kroah-Hartman1dd06ae2012-12-06 14:30:56 +0000462static int tlan_probe1(struct pci_dev *pdev, long ioaddr, int irq, int rev,
463 const struct pci_device_id *ent)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700464{
465
466 struct net_device *dev;
Sakari Ailusc659c382011-01-21 10:59:30 +0000467 struct tlan_priv *priv;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700468 u16 device_id;
469 int reg, rc = -ENODEV;
470
Adrian Bunkad9f6712006-02-05 00:37:47 +0100471#ifdef CONFIG_PCI
Linus Torvalds1da177e2005-04-16 15:20:36 -0700472 if (pdev) {
473 rc = pci_enable_device(pdev);
474 if (rc)
475 return rc;
476
Sakari Ailusc659c382011-01-21 10:59:30 +0000477 rc = pci_request_regions(pdev, tlan_signature);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700478 if (rc) {
Joe Perches50624aa2011-03-01 06:56:33 +0000479 pr_err("Could not reserve IO regions\n");
Linus Torvalds1da177e2005-04-16 15:20:36 -0700480 goto err_out;
481 }
482 }
Adrian Bunkad9f6712006-02-05 00:37:47 +0100483#endif /* CONFIG_PCI */
Linus Torvalds1da177e2005-04-16 15:20:36 -0700484
Sakari Ailusc659c382011-01-21 10:59:30 +0000485 dev = alloc_etherdev(sizeof(struct tlan_priv));
Linus Torvalds1da177e2005-04-16 15:20:36 -0700486 if (dev == NULL) {
Linus Torvalds1da177e2005-04-16 15:20:36 -0700487 rc = -ENOMEM;
488 goto err_out_regions;
489 }
Linus Torvalds1da177e2005-04-16 15:20:36 -0700490 SET_NETDEV_DEV(dev, &pdev->dev);
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400491
Linus Torvalds1da177e2005-04-16 15:20:36 -0700492 priv = netdev_priv(dev);
493
Sakari Ailusc659c382011-01-21 10:59:30 +0000494 priv->pci_dev = pdev;
David Howellsc4028952006-11-22 14:57:56 +0000495 priv->dev = dev;
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400496
Linus Torvalds1da177e2005-04-16 15:20:36 -0700497 /* Is this a PCI device? */
498 if (pdev) {
Sakari Ailusc659c382011-01-21 10:59:30 +0000499 u32 pci_io_base = 0;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700500
501 priv->adapter = &board_info[ent->driver_data];
502
Yang Hongyang284901a2009-04-06 19:01:15 -0700503 rc = pci_set_dma_mask(pdev, DMA_BIT_MASK(32));
Linus Torvalds1da177e2005-04-16 15:20:36 -0700504 if (rc) {
Joe Perches50624aa2011-03-01 06:56:33 +0000505 pr_err("No suitable PCI mapping available\n");
Linus Torvalds1da177e2005-04-16 15:20:36 -0700506 goto err_out_free_dev;
507 }
508
Sakari Ailusc659c382011-01-21 10:59:30 +0000509 for (reg = 0; reg <= 5; reg++) {
Linus Torvalds1da177e2005-04-16 15:20:36 -0700510 if (pci_resource_flags(pdev, reg) & IORESOURCE_IO) {
511 pci_io_base = pci_resource_start(pdev, reg);
Sakari Ailusc659c382011-01-21 10:59:30 +0000512 TLAN_DBG(TLAN_DEBUG_GNRL,
513 "IO mapping is available at %x.\n",
514 pci_io_base);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700515 break;
516 }
517 }
518 if (!pci_io_base) {
Joe Perches50624aa2011-03-01 06:56:33 +0000519 pr_err("No IO mappings available\n");
Linus Torvalds1da177e2005-04-16 15:20:36 -0700520 rc = -EIO;
521 goto err_out_free_dev;
522 }
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400523
Linus Torvalds1da177e2005-04-16 15:20:36 -0700524 dev->base_addr = pci_io_base;
525 dev->irq = pdev->irq;
Sakari Ailusc659c382011-01-21 10:59:30 +0000526 priv->adapter_rev = pdev->revision;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700527 pci_set_master(pdev);
528 pci_set_drvdata(pdev, dev);
529
530 } else { /* EISA card */
531 /* This is a hack. We need to know which board structure
532 * is suited for this adapter */
533 device_id = inw(ioaddr + EISA_ID2);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700534 if (device_id == 0x20F1) {
Sakari Ailusc659c382011-01-21 10:59:30 +0000535 priv->adapter = &board_info[13]; /* NetFlex-3/E */
536 priv->adapter_rev = 23; /* TLAN 2.3 */
Linus Torvalds1da177e2005-04-16 15:20:36 -0700537 } else {
538 priv->adapter = &board_info[14];
Sakari Ailusc659c382011-01-21 10:59:30 +0000539 priv->adapter_rev = 10; /* TLAN 1.0 */
Linus Torvalds1da177e2005-04-16 15:20:36 -0700540 }
541 dev->base_addr = ioaddr;
542 dev->irq = irq;
543 }
544
545 /* Kernel parameters */
546 if (dev->mem_start) {
547 priv->aui = dev->mem_start & 0x01;
Stephen Hemmingerdfc2c0a2008-05-30 09:49:58 -0700548 priv->duplex = ((dev->mem_start & 0x06) == 0x06) ? 0
549 : (dev->mem_start & 0x06) >> 1;
550 priv->speed = ((dev->mem_start & 0x18) == 0x18) ? 0
551 : (dev->mem_start & 0x18) >> 3;
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400552
Sakari Ailusc659c382011-01-21 10:59:30 +0000553 if (priv->speed == 0x1)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700554 priv->speed = TLAN_SPEED_10;
Sakari Ailusc659c382011-01-21 10:59:30 +0000555 else if (priv->speed == 0x2)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700556 priv->speed = TLAN_SPEED_100;
Sakari Ailusc659c382011-01-21 10:59:30 +0000557
Linus Torvalds1da177e2005-04-16 15:20:36 -0700558 debug = priv->debug = dev->mem_end;
559 } else {
560 priv->aui = aui[boards_found];
561 priv->speed = speed[boards_found];
562 priv->duplex = duplex[boards_found];
563 priv->debug = debug;
564 }
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400565
Linus Torvalds1da177e2005-04-16 15:20:36 -0700566 /* This will be used when we get an adapter error from
567 * within our irq handler */
Sakari Ailusc659c382011-01-21 10:59:30 +0000568 INIT_WORK(&priv->tlan_tqueue, tlan_tx_timeout_work);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700569
570 spin_lock_init(&priv->lock);
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400571
Sakari Ailusc659c382011-01-21 10:59:30 +0000572 rc = tlan_init(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700573 if (rc) {
Joe Perches50624aa2011-03-01 06:56:33 +0000574 pr_err("Could not set up device\n");
Linus Torvalds1da177e2005-04-16 15:20:36 -0700575 goto err_out_free_dev;
576 }
577
578 rc = register_netdev(dev);
579 if (rc) {
Joe Perches50624aa2011-03-01 06:56:33 +0000580 pr_err("Could not register device\n");
Linus Torvalds1da177e2005-04-16 15:20:36 -0700581 goto err_out_uninit;
582 }
583
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400584
Sakari Ailusc659c382011-01-21 10:59:30 +0000585 tlan_devices_installed++;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700586 boards_found++;
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400587
Linus Torvalds1da177e2005-04-16 15:20:36 -0700588 /* pdev is NULL if this is an EISA device */
589 if (pdev)
590 tlan_have_pci++;
591 else {
Sakari Ailusc659c382011-01-21 10:59:30 +0000592 priv->next_device = tlan_eisa_devices;
593 tlan_eisa_devices = dev;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700594 tlan_have_eisa++;
595 }
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400596
Joe Perches50624aa2011-03-01 06:56:33 +0000597 netdev_info(dev, "irq=%2d, io=%04x, %s, Rev. %d\n",
598 (int)dev->irq,
599 (int)dev->base_addr,
600 priv->adapter->device_label,
601 priv->adapter_rev);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700602 return 0;
603
604err_out_uninit:
Sakari Ailusc659c382011-01-21 10:59:30 +0000605 pci_free_consistent(priv->pci_dev, priv->dma_size, priv->dma_storage,
606 priv->dma_storage_dma);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700607err_out_free_dev:
608 free_netdev(dev);
609err_out_regions:
610#ifdef CONFIG_PCI
611 if (pdev)
612 pci_release_regions(pdev);
613#endif
614err_out:
615 if (pdev)
616 pci_disable_device(pdev);
617 return rc;
618}
619
620
Sakari Ailusc659c382011-01-21 10:59:30 +0000621static void tlan_eisa_cleanup(void)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700622{
623 struct net_device *dev;
Sakari Ailusc659c382011-01-21 10:59:30 +0000624 struct tlan_priv *priv;
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400625
Sakari Ailusc659c382011-01-21 10:59:30 +0000626 while (tlan_have_eisa) {
627 dev = tlan_eisa_devices;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700628 priv = netdev_priv(dev);
Sakari Ailusc659c382011-01-21 10:59:30 +0000629 if (priv->dma_storage) {
630 pci_free_consistent(priv->pci_dev, priv->dma_size,
631 priv->dma_storage,
632 priv->dma_storage_dma);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700633 }
Sakari Ailusc659c382011-01-21 10:59:30 +0000634 release_region(dev->base_addr, 0x10);
635 unregister_netdev(dev);
636 tlan_eisa_devices = priv->next_device;
637 free_netdev(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700638 tlan_have_eisa--;
639 }
640}
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400641
642
Linus Torvalds1da177e2005-04-16 15:20:36 -0700643static void __exit tlan_exit(void)
644{
645 pci_unregister_driver(&tlan_driver);
646
647 if (tlan_have_eisa)
Sakari Ailusc659c382011-01-21 10:59:30 +0000648 tlan_eisa_cleanup();
Linus Torvalds1da177e2005-04-16 15:20:36 -0700649
Linus Torvalds1da177e2005-04-16 15:20:36 -0700650}
651
652
653/* Module loading/unloading */
654module_init(tlan_probe);
655module_exit(tlan_exit);
656
657
658
Sakari Ailusc659c382011-01-21 10:59:30 +0000659/**************************************************************
660 * tlan_eisa_probe
661 *
662 * Returns: 0 on success, 1 otherwise
663 *
664 * Parms: None
665 *
666 *
667 * This functions probes for EISA devices and calls
668 * TLan_probe1 when one is found.
669 *
670 *************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -0700671
Sakari Ailusc659c382011-01-21 10:59:30 +0000672static void __init tlan_eisa_probe(void)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700673{
Sakari Ailusc659c382011-01-21 10:59:30 +0000674 long ioaddr;
675 int rc = -ENODEV;
676 int irq;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700677 u16 device_id;
678
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400679 if (!EISA_bus) {
Linus Torvalds1da177e2005-04-16 15:20:36 -0700680 TLAN_DBG(TLAN_DEBUG_PROBE, "No EISA bus present\n");
681 return;
682 }
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400683
Linus Torvalds1da177e2005-04-16 15:20:36 -0700684 /* Loop through all slots of the EISA bus */
685 for (ioaddr = 0x1000; ioaddr < 0x9000; ioaddr += 0x1000) {
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400686
Sakari Ailusc659c382011-01-21 10:59:30 +0000687 TLAN_DBG(TLAN_DEBUG_PROBE, "EISA_ID 0x%4x: 0x%4x\n",
688 (int) ioaddr + 0xc80, inw(ioaddr + EISA_ID));
689 TLAN_DBG(TLAN_DEBUG_PROBE, "EISA_ID 0x%4x: 0x%4x\n",
690 (int) ioaddr + 0xc82, inw(ioaddr + EISA_ID2));
Linus Torvalds1da177e2005-04-16 15:20:36 -0700691
692
Sakari Ailusc659c382011-01-21 10:59:30 +0000693 TLAN_DBG(TLAN_DEBUG_PROBE,
694 "Probing for EISA adapter at IO: 0x%4x : ",
695 (int) ioaddr);
696 if (request_region(ioaddr, 0x10, tlan_signature) == NULL)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700697 goto out;
698
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400699 if (inw(ioaddr + EISA_ID) != 0x110E) {
Linus Torvalds1da177e2005-04-16 15:20:36 -0700700 release_region(ioaddr, 0x10);
701 goto out;
702 }
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400703
Linus Torvalds1da177e2005-04-16 15:20:36 -0700704 device_id = inw(ioaddr + EISA_ID2);
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400705 if (device_id != 0x20F1 && device_id != 0x40F1) {
Sakari Ailusc659c382011-01-21 10:59:30 +0000706 release_region(ioaddr, 0x10);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700707 goto out;
708 }
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400709
Sakari Ailusc659c382011-01-21 10:59:30 +0000710 /* check if adapter is enabled */
711 if (inb(ioaddr + EISA_CR) != 0x1) {
712 release_region(ioaddr, 0x10);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700713 goto out2;
714 }
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400715
716 if (debug == 0x10)
Joe Perches50624aa2011-03-01 06:56:33 +0000717 pr_info("Found one\n");
Linus Torvalds1da177e2005-04-16 15:20:36 -0700718
719
720 /* Get irq from board */
Sakari Ailusc659c382011-01-21 10:59:30 +0000721 switch (inb(ioaddr + 0xcc0)) {
722 case(0x10):
723 irq = 5;
724 break;
725 case(0x20):
726 irq = 9;
727 break;
728 case(0x40):
729 irq = 10;
730 break;
731 case(0x80):
732 irq = 11;
733 break;
734 default:
735 goto out;
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400736 }
737
738
Linus Torvalds1da177e2005-04-16 15:20:36 -0700739 /* Setup the newly found eisa adapter */
Sakari Ailusc659c382011-01-21 10:59:30 +0000740 rc = tlan_probe1(NULL, ioaddr, irq,
741 12, NULL);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700742 continue;
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400743
Sakari Ailusc659c382011-01-21 10:59:30 +0000744out:
745 if (debug == 0x10)
Joe Perches50624aa2011-03-01 06:56:33 +0000746 pr_info("None found\n");
Sakari Ailusc659c382011-01-21 10:59:30 +0000747 continue;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700748
Sakari Ailusc659c382011-01-21 10:59:30 +0000749out2:
750 if (debug == 0x10)
Joe Perches50624aa2011-03-01 06:56:33 +0000751 pr_info("Card found but it is not enabled, skipping\n");
Sakari Ailusc659c382011-01-21 10:59:30 +0000752 continue;
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400753
Linus Torvalds1da177e2005-04-16 15:20:36 -0700754 }
755
Sakari Ailusc659c382011-01-21 10:59:30 +0000756}
Linus Torvalds1da177e2005-04-16 15:20:36 -0700757
758#ifdef CONFIG_NET_POLL_CONTROLLER
Sakari Ailusc659c382011-01-21 10:59:30 +0000759static void tlan_poll(struct net_device *dev)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700760{
761 disable_irq(dev->irq);
Sakari Ailusc659c382011-01-21 10:59:30 +0000762 tlan_handle_interrupt(dev->irq, dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700763 enable_irq(dev->irq);
764}
765#endif
766
Sakari Ailusc659c382011-01-21 10:59:30 +0000767static const struct net_device_ops tlan_netdev_ops = {
768 .ndo_open = tlan_open,
769 .ndo_stop = tlan_close,
770 .ndo_start_xmit = tlan_start_tx,
771 .ndo_tx_timeout = tlan_tx_timeout,
772 .ndo_get_stats = tlan_get_stats,
Jiri Pirkoafc4b132011-08-16 06:29:01 +0000773 .ndo_set_rx_mode = tlan_set_multicast_list,
Sakari Ailusc659c382011-01-21 10:59:30 +0000774 .ndo_do_ioctl = tlan_ioctl,
Stephen Hemminger391c5e62009-01-07 17:27:15 -0800775 .ndo_change_mtu = eth_change_mtu,
Sakari Ailusc659c382011-01-21 10:59:30 +0000776 .ndo_set_mac_address = eth_mac_addr,
Stephen Hemminger391c5e62009-01-07 17:27:15 -0800777 .ndo_validate_addr = eth_validate_addr,
778#ifdef CONFIG_NET_POLL_CONTROLLER
Sakari Ailusc659c382011-01-21 10:59:30 +0000779 .ndo_poll_controller = tlan_poll,
Stephen Hemminger391c5e62009-01-07 17:27:15 -0800780#endif
781};
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400782
Ondrej Zarye36124d2014-06-30 18:38:29 +0200783static void tlan_get_drvinfo(struct net_device *dev,
784 struct ethtool_drvinfo *info)
785{
786 struct tlan_priv *priv = netdev_priv(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700787
Ondrej Zarye36124d2014-06-30 18:38:29 +0200788 strlcpy(info->driver, KBUILD_MODNAME, sizeof(info->driver));
789 if (priv->pci_dev)
790 strlcpy(info->bus_info, pci_name(priv->pci_dev),
791 sizeof(info->bus_info));
792 else
793 strlcpy(info->bus_info, "EISA", sizeof(info->bus_info));
794 info->eedump_len = TLAN_EEPROM_SIZE;
795}
796
797static int tlan_get_eeprom_len(struct net_device *dev)
798{
799 return TLAN_EEPROM_SIZE;
800}
801
802static int tlan_get_eeprom(struct net_device *dev,
803 struct ethtool_eeprom *eeprom, u8 *data)
804{
805 int i;
806
807 for (i = 0; i < TLAN_EEPROM_SIZE; i++)
808 if (tlan_ee_read_byte(dev, i, &data[i]))
809 return -EIO;
810
811 return 0;
812}
813
814static const struct ethtool_ops tlan_ethtool_ops = {
815 .get_drvinfo = tlan_get_drvinfo,
816 .get_link = ethtool_op_get_link,
817 .get_eeprom_len = tlan_get_eeprom_len,
818 .get_eeprom = tlan_get_eeprom,
819};
Linus Torvalds1da177e2005-04-16 15:20:36 -0700820
Sakari Ailusc659c382011-01-21 10:59:30 +0000821/***************************************************************
822 * tlan_init
823 *
824 * Returns:
825 * 0 on success, error code otherwise.
826 * Parms:
827 * dev The structure of the device to be
828 * init'ed.
829 *
830 * This function completes the initialization of the
831 * device structure and driver. It reserves the IO
832 * addresses, allocates memory for the lists and bounce
833 * buffers, retrieves the MAC address from the eeprom
834 * and assignes the device's methods.
835 *
836 **************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -0700837
Sakari Ailusc659c382011-01-21 10:59:30 +0000838static int tlan_init(struct net_device *dev)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700839{
840 int dma_size;
Sakari Ailusc659c382011-01-21 10:59:30 +0000841 int err;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700842 int i;
Sakari Ailusc659c382011-01-21 10:59:30 +0000843 struct tlan_priv *priv;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700844
845 priv = netdev_priv(dev);
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400846
Sakari Ailusc659c382011-01-21 10:59:30 +0000847 dma_size = (TLAN_NUM_RX_LISTS + TLAN_NUM_TX_LISTS)
848 * (sizeof(struct tlan_list));
849 priv->dma_storage = pci_alloc_consistent(priv->pci_dev,
850 dma_size,
851 &priv->dma_storage_dma);
852 priv->dma_size = dma_size;
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400853
Sakari Ailusc659c382011-01-21 10:59:30 +0000854 if (priv->dma_storage == NULL) {
Joe Perches50624aa2011-03-01 06:56:33 +0000855 pr_err("Could not allocate lists and buffers for %s\n",
Sakari Ailusc659c382011-01-21 10:59:30 +0000856 dev->name);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700857 return -ENOMEM;
858 }
Sakari Ailusc659c382011-01-21 10:59:30 +0000859 memset(priv->dma_storage, 0, dma_size);
860 priv->rx_list = (struct tlan_list *)
861 ALIGN((unsigned long)priv->dma_storage, 8);
862 priv->rx_list_dma = ALIGN(priv->dma_storage_dma, 8);
863 priv->tx_list = priv->rx_list + TLAN_NUM_RX_LISTS;
864 priv->tx_list_dma =
865 priv->rx_list_dma + sizeof(struct tlan_list)*TLAN_NUM_RX_LISTS;
Stephen Hemminger93e16842008-05-30 09:49:55 -0700866
Linus Torvalds1da177e2005-04-16 15:20:36 -0700867 err = 0;
Ondrej Zary59be4ad2014-06-30 18:38:30 +0200868 for (i = 0; i < ETH_ALEN; i++)
Sakari Ailusc659c382011-01-21 10:59:30 +0000869 err |= tlan_ee_read_byte(dev,
870 (u8) priv->adapter->addr_ofs + i,
871 (u8 *) &dev->dev_addr[i]);
872 if (err) {
Joe Perches50624aa2011-03-01 06:56:33 +0000873 pr_err("%s: Error reading MAC from eeprom: %d\n",
874 dev->name, err);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700875 }
Ondrej Zary59be4ad2014-06-30 18:38:30 +0200876 /* Olicom OC-2325/OC-2326 have the address byte-swapped */
877 if (priv->adapter->addr_ofs == 0xf8) {
878 for (i = 0; i < ETH_ALEN; i += 2) {
879 char tmp = dev->dev_addr[i];
880 dev->dev_addr[i] = dev->dev_addr[i + 1];
881 dev->dev_addr[i + 1] = tmp;
882 }
883 }
Linus Torvalds1da177e2005-04-16 15:20:36 -0700884
885 netif_carrier_off(dev);
886
887 /* Device methods */
Sakari Ailusc659c382011-01-21 10:59:30 +0000888 dev->netdev_ops = &tlan_netdev_ops;
Ondrej Zarye36124d2014-06-30 18:38:29 +0200889 dev->ethtool_ops = &tlan_ethtool_ops;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700890 dev->watchdog_timeo = TX_TIMEOUT;
891
892 return 0;
893
Sakari Ailusc659c382011-01-21 10:59:30 +0000894}
Linus Torvalds1da177e2005-04-16 15:20:36 -0700895
896
897
898
Sakari Ailusc659c382011-01-21 10:59:30 +0000899/***************************************************************
900 * tlan_open
901 *
902 * Returns:
903 * 0 on success, error code otherwise.
904 * Parms:
905 * dev Structure of device to be opened.
906 *
907 * This routine puts the driver and TLAN adapter in a
908 * state where it is ready to send and receive packets.
909 * It allocates the IRQ, resets and brings the adapter
910 * out of reset, and allows interrupts. It also delays
911 * the startup for autonegotiation or sends a Rx GO
912 * command to the adapter, as appropriate.
913 *
914 **************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -0700915
Sakari Ailusc659c382011-01-21 10:59:30 +0000916static int tlan_open(struct net_device *dev)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700917{
Sakari Ailusc659c382011-01-21 10:59:30 +0000918 struct tlan_priv *priv = netdev_priv(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700919 int err;
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400920
Sakari Ailusc659c382011-01-21 10:59:30 +0000921 priv->tlan_rev = tlan_dio_read8(dev->base_addr, TLAN_DEF_REVISION);
922 err = request_irq(dev->irq, tlan_handle_interrupt, IRQF_SHARED,
923 dev->name, dev);
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400924
Sakari Ailusc659c382011-01-21 10:59:30 +0000925 if (err) {
Joe Perches50624aa2011-03-01 06:56:33 +0000926 netdev_err(dev, "Cannot open because IRQ %d is already in use\n",
927 dev->irq);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700928 return err;
929 }
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400930
Linus Torvalds1da177e2005-04-16 15:20:36 -0700931 init_timer(&priv->timer);
Ondrej Zaryc0a87c22014-06-30 18:38:28 +0200932 init_timer(&priv->media_timer);
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400933
Sakari Ailusfa6d5d42011-01-21 10:59:31 +0000934 tlan_start(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700935
Sakari Ailusc659c382011-01-21 10:59:30 +0000936 TLAN_DBG(TLAN_DEBUG_GNRL, "%s: Opened. TLAN Chip Rev: %x\n",
937 dev->name, priv->tlan_rev);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700938
939 return 0;
940
Sakari Ailusc659c382011-01-21 10:59:30 +0000941}
Linus Torvalds1da177e2005-04-16 15:20:36 -0700942
943
944
Sakari Ailusc659c382011-01-21 10:59:30 +0000945/**************************************************************
946 * tlan_ioctl
947 *
948 * Returns:
949 * 0 on success, error code otherwise
950 * Params:
951 * dev structure of device to receive ioctl.
952 *
953 * rq ifreq structure to hold userspace data.
954 *
955 * cmd ioctl command.
956 *
957 *
958 *************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -0700959
Sakari Ailusc659c382011-01-21 10:59:30 +0000960static int tlan_ioctl(struct net_device *dev, struct ifreq *rq, int cmd)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700961{
Sakari Ailusc659c382011-01-21 10:59:30 +0000962 struct tlan_priv *priv = netdev_priv(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700963 struct mii_ioctl_data *data = if_mii(rq);
Sakari Ailusc659c382011-01-21 10:59:30 +0000964 u32 phy = priv->phy[priv->phy_num];
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400965
Sakari Ailusc659c382011-01-21 10:59:30 +0000966 if (!priv->phy_online)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700967 return -EAGAIN;
968
Sakari Ailusc659c382011-01-21 10:59:30 +0000969 switch (cmd) {
970 case SIOCGMIIPHY: /* get address of MII PHY in use. */
971 data->phy_id = phy;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700972
973
Sakari Ailusc659c382011-01-21 10:59:30 +0000974 case SIOCGMIIREG: /* read MII PHY register. */
975 tlan_mii_read_reg(dev, data->phy_id & 0x1f,
976 data->reg_num & 0x1f, &data->val_out);
977 return 0;
Jeff Garzik6aa20a22006-09-13 13:24:59 -0400978
Linus Torvalds1da177e2005-04-16 15:20:36 -0700979
Sakari Ailusc659c382011-01-21 10:59:30 +0000980 case SIOCSMIIREG: /* write MII PHY register. */
981 tlan_mii_write_reg(dev, data->phy_id & 0x1f,
982 data->reg_num & 0x1f, data->val_in);
983 return 0;
984 default:
985 return -EOPNOTSUPP;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700986 }
Sakari Ailusc659c382011-01-21 10:59:30 +0000987}
Linus Torvalds1da177e2005-04-16 15:20:36 -0700988
989
Sakari Ailusc659c382011-01-21 10:59:30 +0000990/***************************************************************
991 * tlan_tx_timeout
992 *
993 * Returns: nothing
994 *
995 * Params:
996 * dev structure of device which timed out
997 * during transmit.
998 *
999 **************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -07001000
Sakari Ailusc659c382011-01-21 10:59:30 +00001001static void tlan_tx_timeout(struct net_device *dev)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001002{
Jeff Garzik6aa20a22006-09-13 13:24:59 -04001003
Sakari Ailusc659c382011-01-21 10:59:30 +00001004 TLAN_DBG(TLAN_DEBUG_GNRL, "%s: Transmit timed out.\n", dev->name);
Jeff Garzik6aa20a22006-09-13 13:24:59 -04001005
Linus Torvalds1da177e2005-04-16 15:20:36 -07001006 /* Ok so we timed out, lets see what we can do about it...*/
Sakari Ailusc659c382011-01-21 10:59:30 +00001007 tlan_free_lists(dev);
1008 tlan_reset_lists(dev);
1009 tlan_read_and_clear_stats(dev, TLAN_IGNORE);
1010 tlan_reset_adapter(dev);
Eric Dumazet1ae5dc32010-05-10 05:01:31 -07001011 dev->trans_start = jiffies; /* prevent tx timeout */
Sakari Ailusc659c382011-01-21 10:59:30 +00001012 netif_wake_queue(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001013
1014}
Jeff Garzik6aa20a22006-09-13 13:24:59 -04001015
Linus Torvalds1da177e2005-04-16 15:20:36 -07001016
Sakari Ailusc659c382011-01-21 10:59:30 +00001017/***************************************************************
1018 * tlan_tx_timeout_work
1019 *
1020 * Returns: nothing
1021 *
1022 * Params:
1023 * work work item of device which timed out
1024 *
1025 **************************************************************/
David Howellsc4028952006-11-22 14:57:56 +00001026
Sakari Ailusc659c382011-01-21 10:59:30 +00001027static void tlan_tx_timeout_work(struct work_struct *work)
David Howellsc4028952006-11-22 14:57:56 +00001028{
Sakari Ailusc659c382011-01-21 10:59:30 +00001029 struct tlan_priv *priv =
1030 container_of(work, struct tlan_priv, tlan_tqueue);
David Howellsc4028952006-11-22 14:57:56 +00001031
Sakari Ailusc659c382011-01-21 10:59:30 +00001032 tlan_tx_timeout(priv->dev);
David Howellsc4028952006-11-22 14:57:56 +00001033}
1034
1035
Linus Torvalds1da177e2005-04-16 15:20:36 -07001036
Sakari Ailusc659c382011-01-21 10:59:30 +00001037/***************************************************************
1038 * tlan_start_tx
1039 *
1040 * Returns:
1041 * 0 on success, non-zero on failure.
1042 * Parms:
1043 * skb A pointer to the sk_buff containing the
1044 * frame to be sent.
1045 * dev The device to send the data on.
1046 *
1047 * This function adds a frame to the Tx list to be sent
1048 * ASAP. First it verifies that the adapter is ready and
1049 * there is room in the queue. Then it sets up the next
1050 * available list, copies the frame to the corresponding
1051 * buffer. If the adapter Tx channel is idle, it gives
1052 * the adapter a Tx Go command on the list, otherwise it
1053 * sets the forward address of the previous list to point
1054 * to this one. Then it frees the sk_buff.
1055 *
1056 **************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -07001057
Sakari Ailusc659c382011-01-21 10:59:30 +00001058static netdev_tx_t tlan_start_tx(struct sk_buff *skb, struct net_device *dev)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001059{
Sakari Ailusc659c382011-01-21 10:59:30 +00001060 struct tlan_priv *priv = netdev_priv(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001061 dma_addr_t tail_list_phys;
Sakari Ailusc659c382011-01-21 10:59:30 +00001062 struct tlan_list *tail_list;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001063 unsigned long flags;
Sakari Ailus8953f122008-12-16 01:44:05 -08001064 unsigned int txlen;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001065
Sakari Ailusc659c382011-01-21 10:59:30 +00001066 if (!priv->phy_online) {
1067 TLAN_DBG(TLAN_DEBUG_TX, "TRANSMIT: %s PHY is not ready\n",
1068 dev->name);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001069 dev_kfree_skb_any(skb);
Patrick McHardy6ed10652009-06-23 06:03:08 +00001070 return NETDEV_TX_OK;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001071 }
1072
Stephen Hemminger41873e92008-05-30 09:49:52 -07001073 if (skb_padto(skb, TLAN_MIN_FRAME_SIZE))
Patrick McHardy6ed10652009-06-23 06:03:08 +00001074 return NETDEV_TX_OK;
Sakari Ailus8953f122008-12-16 01:44:05 -08001075 txlen = max(skb->len, (unsigned int)TLAN_MIN_FRAME_SIZE);
Stephen Hemminger41873e92008-05-30 09:49:52 -07001076
Sakari Ailusc659c382011-01-21 10:59:30 +00001077 tail_list = priv->tx_list + priv->tx_tail;
1078 tail_list_phys =
1079 priv->tx_list_dma + sizeof(struct tlan_list)*priv->tx_tail;
Jeff Garzik6aa20a22006-09-13 13:24:59 -04001080
Sakari Ailusc659c382011-01-21 10:59:30 +00001081 if (tail_list->c_stat != TLAN_CSTAT_UNUSED) {
1082 TLAN_DBG(TLAN_DEBUG_TX,
1083 "TRANSMIT: %s is busy (Head=%d Tail=%d)\n",
1084 dev->name, priv->tx_head, priv->tx_tail);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001085 netif_stop_queue(dev);
Sakari Ailusc659c382011-01-21 10:59:30 +00001086 priv->tx_busy_count++;
Patrick McHardy5b548142009-06-12 06:22:29 +00001087 return NETDEV_TX_BUSY;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001088 }
1089
1090 tail_list->forward = 0;
1091
Sakari Ailusc659c382011-01-21 10:59:30 +00001092 tail_list->buffer[0].address = pci_map_single(priv->pci_dev,
Sakari Ailus5eeabf52008-12-16 15:24:05 -08001093 skb->data, txlen,
1094 PCI_DMA_TODEVICE);
Sakari Ailusc659c382011-01-21 10:59:30 +00001095 tlan_store_skb(tail_list, skb);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001096
Sakari Ailusc659c382011-01-21 10:59:30 +00001097 tail_list->frame_size = (u16) txlen;
Sakari Ailus8953f122008-12-16 01:44:05 -08001098 tail_list->buffer[0].count = TLAN_LAST_BUFFER | (u32) txlen;
Stephen Hemminger41873e92008-05-30 09:49:52 -07001099 tail_list->buffer[1].count = 0;
1100 tail_list->buffer[1].address = 0;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001101
1102 spin_lock_irqsave(&priv->lock, flags);
Sakari Ailusc659c382011-01-21 10:59:30 +00001103 tail_list->c_stat = TLAN_CSTAT_READY;
1104 if (!priv->tx_in_progress) {
1105 priv->tx_in_progress = 1;
1106 TLAN_DBG(TLAN_DEBUG_TX,
1107 "TRANSMIT: Starting TX on buffer %d\n",
1108 priv->tx_tail);
1109 outl(tail_list_phys, dev->base_addr + TLAN_CH_PARM);
1110 outl(TLAN_HC_GO, dev->base_addr + TLAN_HOST_CMD);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001111 } else {
Sakari Ailusc659c382011-01-21 10:59:30 +00001112 TLAN_DBG(TLAN_DEBUG_TX,
1113 "TRANSMIT: Adding buffer %d to TX channel\n",
1114 priv->tx_tail);
1115 if (priv->tx_tail == 0) {
1116 (priv->tx_list + (TLAN_NUM_TX_LISTS - 1))->forward
Stephen Hemmingerdfc2c0a2008-05-30 09:49:58 -07001117 = tail_list_phys;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001118 } else {
Sakari Ailusc659c382011-01-21 10:59:30 +00001119 (priv->tx_list + (priv->tx_tail - 1))->forward
Stephen Hemmingerdfc2c0a2008-05-30 09:49:58 -07001120 = tail_list_phys;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001121 }
1122 }
1123 spin_unlock_irqrestore(&priv->lock, flags);
1124
Sakari Ailusc659c382011-01-21 10:59:30 +00001125 CIRC_INC(priv->tx_tail, TLAN_NUM_TX_LISTS);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001126
Patrick McHardy6ed10652009-06-23 06:03:08 +00001127 return NETDEV_TX_OK;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001128
Sakari Ailusc659c382011-01-21 10:59:30 +00001129}
Linus Torvalds1da177e2005-04-16 15:20:36 -07001130
1131
1132
1133
Sakari Ailusc659c382011-01-21 10:59:30 +00001134/***************************************************************
1135 * tlan_handle_interrupt
1136 *
1137 * Returns:
1138 * Nothing
1139 * Parms:
1140 * irq The line on which the interrupt
1141 * occurred.
1142 * dev_id A pointer to the device assigned to
1143 * this irq line.
1144 *
1145 * This function handles an interrupt generated by its
1146 * assigned TLAN adapter. The function deactivates
1147 * interrupts on its adapter, records the type of
1148 * interrupt, executes the appropriate subhandler, and
1149 * acknowdges the interrupt to the adapter (thus
1150 * re-enabling adapter interrupts.
1151 *
1152 **************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -07001153
Sakari Ailusc659c382011-01-21 10:59:30 +00001154static irqreturn_t tlan_handle_interrupt(int irq, void *dev_id)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001155{
Stephen Hemmingera3ccc782008-05-30 09:49:57 -07001156 struct net_device *dev = dev_id;
Sakari Ailusc659c382011-01-21 10:59:30 +00001157 struct tlan_priv *priv = netdev_priv(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001158 u16 host_int;
Stephen Hemmingera3ccc782008-05-30 09:49:57 -07001159 u16 type;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001160
1161 spin_lock(&priv->lock);
1162
Sakari Ailusc659c382011-01-21 10:59:30 +00001163 host_int = inw(dev->base_addr + TLAN_HOST_INT);
1164 type = (host_int & TLAN_HI_IT_MASK) >> 2;
1165 if (type) {
Stephen Hemmingera3ccc782008-05-30 09:49:57 -07001166 u32 ack;
1167 u32 host_cmd;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001168
Sakari Ailusc659c382011-01-21 10:59:30 +00001169 outw(host_int, dev->base_addr + TLAN_HOST_INT);
1170 ack = tlan_int_vector[type](dev, host_int);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001171
Sakari Ailusc659c382011-01-21 10:59:30 +00001172 if (ack) {
1173 host_cmd = TLAN_HC_ACK | ack | (type << 18);
1174 outl(host_cmd, dev->base_addr + TLAN_HOST_CMD);
Stephen Hemmingera3ccc782008-05-30 09:49:57 -07001175 }
Linus Torvalds1da177e2005-04-16 15:20:36 -07001176 }
1177
1178 spin_unlock(&priv->lock);
1179
Stephen Hemmingera3ccc782008-05-30 09:49:57 -07001180 return IRQ_RETVAL(type);
Sakari Ailusc659c382011-01-21 10:59:30 +00001181}
Linus Torvalds1da177e2005-04-16 15:20:36 -07001182
1183
1184
1185
Sakari Ailusc659c382011-01-21 10:59:30 +00001186/***************************************************************
1187 * tlan_close
1188 *
1189 * Returns:
1190 * An error code.
1191 * Parms:
1192 * dev The device structure of the device to
1193 * close.
1194 *
1195 * This function shuts down the adapter. It records any
1196 * stats, puts the adapter into reset state, deactivates
1197 * its time as needed, and frees the irq it is using.
1198 *
1199 **************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -07001200
Sakari Ailusc659c382011-01-21 10:59:30 +00001201static int tlan_close(struct net_device *dev)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001202{
Sakari Ailusfa6d5d42011-01-21 10:59:31 +00001203 tlan_stop(dev);
Jeff Garzik6aa20a22006-09-13 13:24:59 -04001204
Sakari Ailusc659c382011-01-21 10:59:30 +00001205 free_irq(dev->irq, dev);
1206 tlan_free_lists(dev);
1207 TLAN_DBG(TLAN_DEBUG_GNRL, "Device %s closed.\n", dev->name);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001208
1209 return 0;
1210
Sakari Ailusc659c382011-01-21 10:59:30 +00001211}
Linus Torvalds1da177e2005-04-16 15:20:36 -07001212
1213
1214
1215
Sakari Ailusc659c382011-01-21 10:59:30 +00001216/***************************************************************
1217 * tlan_get_stats
1218 *
1219 * Returns:
1220 * A pointer to the device's statistics structure.
1221 * Parms:
1222 * dev The device structure to return the
1223 * stats for.
1224 *
1225 * This function updates the devices statistics by reading
1226 * the TLAN chip's onboard registers. Then it returns the
1227 * address of the statistics structure.
1228 *
1229 **************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -07001230
Sakari Ailusc659c382011-01-21 10:59:30 +00001231static struct net_device_stats *tlan_get_stats(struct net_device *dev)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001232{
Sakari Ailusc659c382011-01-21 10:59:30 +00001233 struct tlan_priv *priv = netdev_priv(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001234 int i;
1235
1236 /* Should only read stats if open ? */
Sakari Ailusc659c382011-01-21 10:59:30 +00001237 tlan_read_and_clear_stats(dev, TLAN_RECORD);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001238
Sakari Ailusc659c382011-01-21 10:59:30 +00001239 TLAN_DBG(TLAN_DEBUG_RX, "RECEIVE: %s EOC count = %d\n", dev->name,
1240 priv->rx_eoc_count);
1241 TLAN_DBG(TLAN_DEBUG_TX, "TRANSMIT: %s Busy count = %d\n", dev->name,
1242 priv->tx_busy_count);
1243 if (debug & TLAN_DEBUG_GNRL) {
1244 tlan_print_dio(dev->base_addr);
1245 tlan_phy_print(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001246 }
Sakari Ailusc659c382011-01-21 10:59:30 +00001247 if (debug & TLAN_DEBUG_LIST) {
1248 for (i = 0; i < TLAN_NUM_RX_LISTS; i++)
1249 tlan_print_list(priv->rx_list + i, "RX", i);
1250 for (i = 0; i < TLAN_NUM_TX_LISTS; i++)
1251 tlan_print_list(priv->tx_list + i, "TX", i);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001252 }
Jeff Garzik6aa20a22006-09-13 13:24:59 -04001253
Stephen Hemmingerf8f31542008-05-30 09:49:53 -07001254 return &dev->stats;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001255
Sakari Ailusc659c382011-01-21 10:59:30 +00001256}
Linus Torvalds1da177e2005-04-16 15:20:36 -07001257
1258
1259
1260
Sakari Ailusc659c382011-01-21 10:59:30 +00001261/***************************************************************
1262 * tlan_set_multicast_list
1263 *
1264 * Returns:
1265 * Nothing
1266 * Parms:
1267 * dev The device structure to set the
1268 * multicast list for.
1269 *
1270 * This function sets the TLAN adaptor to various receive
1271 * modes. If the IFF_PROMISC flag is set, promiscuous
1272 * mode is acitviated. Otherwise, promiscuous mode is
1273 * turned off. If the IFF_ALLMULTI flag is set, then
1274 * the hash table is set to receive all group addresses.
1275 * Otherwise, the first three multicast addresses are
1276 * stored in AREG_1-3, and the rest are selected via the
1277 * hash table, as necessary.
1278 *
1279 **************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -07001280
Sakari Ailusc659c382011-01-21 10:59:30 +00001281static void tlan_set_multicast_list(struct net_device *dev)
Jeff Garzik6aa20a22006-09-13 13:24:59 -04001282{
Jiri Pirko22bedad32010-04-01 21:22:57 +00001283 struct netdev_hw_addr *ha;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001284 u32 hash1 = 0;
1285 u32 hash2 = 0;
1286 int i;
1287 u32 offset;
1288 u8 tmp;
1289
Sakari Ailusc659c382011-01-21 10:59:30 +00001290 if (dev->flags & IFF_PROMISC) {
1291 tmp = tlan_dio_read8(dev->base_addr, TLAN_NET_CMD);
1292 tlan_dio_write8(dev->base_addr,
1293 TLAN_NET_CMD, tmp | TLAN_NET_CMD_CAF);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001294 } else {
Sakari Ailusc659c382011-01-21 10:59:30 +00001295 tmp = tlan_dio_read8(dev->base_addr, TLAN_NET_CMD);
1296 tlan_dio_write8(dev->base_addr,
1297 TLAN_NET_CMD, tmp & ~TLAN_NET_CMD_CAF);
1298 if (dev->flags & IFF_ALLMULTI) {
1299 for (i = 0; i < 3; i++)
1300 tlan_set_mac(dev, i + 1, NULL);
1301 tlan_dio_write32(dev->base_addr, TLAN_HASH_1,
1302 0xffffffff);
1303 tlan_dio_write32(dev->base_addr, TLAN_HASH_2,
1304 0xffffffff);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001305 } else {
Jiri Pirko567ec872010-02-23 23:17:07 +00001306 i = 0;
Jiri Pirko22bedad32010-04-01 21:22:57 +00001307 netdev_for_each_mc_addr(ha, dev) {
Sakari Ailusc659c382011-01-21 10:59:30 +00001308 if (i < 3) {
1309 tlan_set_mac(dev, i + 1,
Jiri Pirko22bedad32010-04-01 21:22:57 +00001310 (char *) &ha->addr);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001311 } else {
Sakari Ailusc659c382011-01-21 10:59:30 +00001312 offset =
1313 tlan_hash_func((u8 *)&ha->addr);
1314 if (offset < 32)
1315 hash1 |= (1 << offset);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001316 else
Sakari Ailusc659c382011-01-21 10:59:30 +00001317 hash2 |= (1 << (offset - 32));
Linus Torvalds1da177e2005-04-16 15:20:36 -07001318 }
Jiri Pirko567ec872010-02-23 23:17:07 +00001319 i++;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001320 }
Sakari Ailusc659c382011-01-21 10:59:30 +00001321 for ( ; i < 3; i++)
1322 tlan_set_mac(dev, i + 1, NULL);
1323 tlan_dio_write32(dev->base_addr, TLAN_HASH_1, hash1);
1324 tlan_dio_write32(dev->base_addr, TLAN_HASH_2, hash2);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001325 }
1326 }
1327
Sakari Ailusc659c382011-01-21 10:59:30 +00001328}
Linus Torvalds1da177e2005-04-16 15:20:36 -07001329
1330
1331
1332/*****************************************************************************
1333******************************************************************************
1334
Sakari Ailusc659c382011-01-21 10:59:30 +00001335ThunderLAN driver interrupt vectors and table
Linus Torvalds1da177e2005-04-16 15:20:36 -07001336
Sakari Ailusc659c382011-01-21 10:59:30 +00001337please see chap. 4, "Interrupt Handling" of the "ThunderLAN
1338Programmer's Guide" for more informations on handling interrupts
1339generated by TLAN based adapters.
Linus Torvalds1da177e2005-04-16 15:20:36 -07001340
1341******************************************************************************
1342*****************************************************************************/
1343
1344
Linus Torvalds1da177e2005-04-16 15:20:36 -07001345
1346
Sakari Ailusc659c382011-01-21 10:59:30 +00001347/***************************************************************
1348 * tlan_handle_tx_eof
1349 *
1350 * Returns:
1351 * 1
1352 * Parms:
1353 * dev Device assigned the IRQ that was
1354 * raised.
1355 * host_int The contents of the HOST_INT
1356 * port.
1357 *
1358 * This function handles Tx EOF interrupts which are raised
1359 * by the adapter when it has completed sending the
1360 * contents of a buffer. If detemines which list/buffer
1361 * was completed and resets it. If the buffer was the last
1362 * in the channel (EOC), then the function checks to see if
1363 * another buffer is ready to send, and if so, sends a Tx
1364 * Go command. Finally, the driver activates/continues the
1365 * activity LED.
1366 *
1367 **************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -07001368
Sakari Ailusc659c382011-01-21 10:59:30 +00001369static u32 tlan_handle_tx_eof(struct net_device *dev, u16 host_int)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001370{
Sakari Ailusc659c382011-01-21 10:59:30 +00001371 struct tlan_priv *priv = netdev_priv(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001372 int eoc = 0;
Sakari Ailusc659c382011-01-21 10:59:30 +00001373 struct tlan_list *head_list;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001374 dma_addr_t head_list_phys;
1375 u32 ack = 0;
Sakari Ailusc659c382011-01-21 10:59:30 +00001376 u16 tmp_c_stat;
Jeff Garzik6aa20a22006-09-13 13:24:59 -04001377
Sakari Ailusc659c382011-01-21 10:59:30 +00001378 TLAN_DBG(TLAN_DEBUG_TX,
1379 "TRANSMIT: Handling TX EOF (Head=%d Tail=%d)\n",
1380 priv->tx_head, priv->tx_tail);
1381 head_list = priv->tx_list + priv->tx_head;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001382
Sakari Ailusc659c382011-01-21 10:59:30 +00001383 while (((tmp_c_stat = head_list->c_stat) & TLAN_CSTAT_FRM_CMP)
1384 && (ack < 255)) {
1385 struct sk_buff *skb = tlan_get_skb(head_list);
Sakari Ailus5eeabf52008-12-16 15:24:05 -08001386
Linus Torvalds1da177e2005-04-16 15:20:36 -07001387 ack++;
Sakari Ailusc659c382011-01-21 10:59:30 +00001388 pci_unmap_single(priv->pci_dev, head_list->buffer[0].address,
Sakari Ailus5eeabf52008-12-16 15:24:05 -08001389 max(skb->len,
1390 (unsigned int)TLAN_MIN_FRAME_SIZE),
1391 PCI_DMA_TODEVICE);
1392 dev_kfree_skb_any(skb);
1393 head_list->buffer[8].address = 0;
1394 head_list->buffer[9].address = 0;
Jeff Garzik6aa20a22006-09-13 13:24:59 -04001395
Sakari Ailusc659c382011-01-21 10:59:30 +00001396 if (tmp_c_stat & TLAN_CSTAT_EOC)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001397 eoc = 1;
Jeff Garzik6aa20a22006-09-13 13:24:59 -04001398
Sakari Ailusc659c382011-01-21 10:59:30 +00001399 dev->stats.tx_bytes += head_list->frame_size;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001400
Sakari Ailusc659c382011-01-21 10:59:30 +00001401 head_list->c_stat = TLAN_CSTAT_UNUSED;
Jeff Garzik6aa20a22006-09-13 13:24:59 -04001402 netif_start_queue(dev);
Sakari Ailusc659c382011-01-21 10:59:30 +00001403 CIRC_INC(priv->tx_head, TLAN_NUM_TX_LISTS);
1404 head_list = priv->tx_list + priv->tx_head;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001405 }
1406
1407 if (!ack)
Joe Perches50624aa2011-03-01 06:56:33 +00001408 netdev_info(dev,
1409 "Received interrupt for uncompleted TX frame\n");
Jeff Garzik6aa20a22006-09-13 13:24:59 -04001410
Sakari Ailusc659c382011-01-21 10:59:30 +00001411 if (eoc) {
1412 TLAN_DBG(TLAN_DEBUG_TX,
1413 "TRANSMIT: handling TX EOC (Head=%d Tail=%d)\n",
1414 priv->tx_head, priv->tx_tail);
1415 head_list = priv->tx_list + priv->tx_head;
1416 head_list_phys = priv->tx_list_dma
1417 + sizeof(struct tlan_list)*priv->tx_head;
Sakari Ailusf45437e2011-02-09 10:25:06 +00001418 if ((head_list->c_stat & TLAN_CSTAT_READY)
1419 == TLAN_CSTAT_READY) {
Sakari Ailusc659c382011-01-21 10:59:30 +00001420 outl(head_list_phys, dev->base_addr + TLAN_CH_PARM);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001421 ack |= TLAN_HC_GO;
1422 } else {
Sakari Ailusc659c382011-01-21 10:59:30 +00001423 priv->tx_in_progress = 0;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001424 }
1425 }
Jeff Garzik6aa20a22006-09-13 13:24:59 -04001426
Sakari Ailusc659c382011-01-21 10:59:30 +00001427 if (priv->adapter->flags & TLAN_ADAPTER_ACTIVITY_LED) {
1428 tlan_dio_write8(dev->base_addr,
1429 TLAN_LED_REG, TLAN_LED_LINK | TLAN_LED_ACT);
1430 if (priv->timer.function == NULL) {
1431 priv->timer.function = tlan_timer;
1432 priv->timer.data = (unsigned long) dev;
1433 priv->timer.expires = jiffies + TLAN_TIMER_ACT_DELAY;
1434 priv->timer_set_at = jiffies;
1435 priv->timer_type = TLAN_TIMER_ACTIVITY;
1436 add_timer(&priv->timer);
1437 } else if (priv->timer_type == TLAN_TIMER_ACTIVITY) {
1438 priv->timer_set_at = jiffies;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001439 }
1440 }
1441
1442 return ack;
1443
Sakari Ailusc659c382011-01-21 10:59:30 +00001444}
Linus Torvalds1da177e2005-04-16 15:20:36 -07001445
1446
1447
1448
Sakari Ailusc659c382011-01-21 10:59:30 +00001449/***************************************************************
1450 * TLan_HandleStatOverflow
1451 *
1452 * Returns:
1453 * 1
1454 * Parms:
1455 * dev Device assigned the IRQ that was
1456 * raised.
1457 * host_int The contents of the HOST_INT
1458 * port.
1459 *
1460 * This function handles the Statistics Overflow interrupt
1461 * which means that one or more of the TLAN statistics
1462 * registers has reached 1/2 capacity and needs to be read.
1463 *
1464 **************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -07001465
Sakari Ailusc659c382011-01-21 10:59:30 +00001466static u32 tlan_handle_stat_overflow(struct net_device *dev, u16 host_int)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001467{
Sakari Ailusc659c382011-01-21 10:59:30 +00001468 tlan_read_and_clear_stats(dev, TLAN_RECORD);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001469
1470 return 1;
1471
Sakari Ailusc659c382011-01-21 10:59:30 +00001472}
Linus Torvalds1da177e2005-04-16 15:20:36 -07001473
1474
1475
1476
Sakari Ailusc659c382011-01-21 10:59:30 +00001477/***************************************************************
1478 * TLan_HandleRxEOF
1479 *
1480 * Returns:
1481 * 1
1482 * Parms:
1483 * dev Device assigned the IRQ that was
1484 * raised.
1485 * host_int The contents of the HOST_INT
1486 * port.
1487 *
1488 * This function handles the Rx EOF interrupt which
1489 * indicates a frame has been received by the adapter from
1490 * the net and the frame has been transferred to memory.
1491 * The function determines the bounce buffer the frame has
1492 * been loaded into, creates a new sk_buff big enough to
1493 * hold the frame, and sends it to protocol stack. It
1494 * then resets the used buffer and appends it to the end
1495 * of the list. If the frame was the last in the Rx
1496 * channel (EOC), the function restarts the receive channel
1497 * by sending an Rx Go command to the adapter. Then it
1498 * activates/continues the activity LED.
1499 *
1500 **************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -07001501
Sakari Ailusc659c382011-01-21 10:59:30 +00001502static u32 tlan_handle_rx_eof(struct net_device *dev, u16 host_int)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001503{
Sakari Ailusc659c382011-01-21 10:59:30 +00001504 struct tlan_priv *priv = netdev_priv(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001505 u32 ack = 0;
1506 int eoc = 0;
Sakari Ailusc659c382011-01-21 10:59:30 +00001507 struct tlan_list *head_list;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001508 struct sk_buff *skb;
Sakari Ailusc659c382011-01-21 10:59:30 +00001509 struct tlan_list *tail_list;
1510 u16 tmp_c_stat;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001511 dma_addr_t head_list_phys;
1512
Sakari Ailusc659c382011-01-21 10:59:30 +00001513 TLAN_DBG(TLAN_DEBUG_RX, "RECEIVE: handling RX EOF (Head=%d Tail=%d)\n",
1514 priv->rx_head, priv->rx_tail);
1515 head_list = priv->rx_list + priv->rx_head;
1516 head_list_phys =
1517 priv->rx_list_dma + sizeof(struct tlan_list)*priv->rx_head;
Jeff Garzik6aa20a22006-09-13 13:24:59 -04001518
Sakari Ailusc659c382011-01-21 10:59:30 +00001519 while (((tmp_c_stat = head_list->c_stat) & TLAN_CSTAT_FRM_CMP)
1520 && (ack < 255)) {
1521 dma_addr_t frame_dma = head_list->buffer[0].address;
1522 u32 frame_size = head_list->frame_size;
Sakari Ailus5eeabf52008-12-16 15:24:05 -08001523 struct sk_buff *new_skb;
1524
Linus Torvalds1da177e2005-04-16 15:20:36 -07001525 ack++;
Sakari Ailusc659c382011-01-21 10:59:30 +00001526 if (tmp_c_stat & TLAN_CSTAT_EOC)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001527 eoc = 1;
Jeff Garzik6aa20a22006-09-13 13:24:59 -04001528
Eric Dumazet89d71a62009-10-13 05:34:20 +00001529 new_skb = netdev_alloc_skb_ip_align(dev,
1530 TLAN_MAX_FRAME_SIZE + 5);
Sakari Ailusc659c382011-01-21 10:59:30 +00001531 if (!new_skb)
Sakari Ailus5eeabf52008-12-16 15:24:05 -08001532 goto drop_and_reuse;
Jeff Garzik6aa20a22006-09-13 13:24:59 -04001533
Sakari Ailusc659c382011-01-21 10:59:30 +00001534 skb = tlan_get_skb(head_list);
1535 pci_unmap_single(priv->pci_dev, frame_dma,
Sakari Ailus5eeabf52008-12-16 15:24:05 -08001536 TLAN_MAX_FRAME_SIZE, PCI_DMA_FROMDEVICE);
Sakari Ailusc659c382011-01-21 10:59:30 +00001537 skb_put(skb, frame_size);
Stephen Hemmingerdfc2c0a2008-05-30 09:49:58 -07001538
Sakari Ailusc659c382011-01-21 10:59:30 +00001539 dev->stats.rx_bytes += frame_size;
Jeff Garzik6aa20a22006-09-13 13:24:59 -04001540
Sakari Ailusc659c382011-01-21 10:59:30 +00001541 skb->protocol = eth_type_trans(skb, dev);
1542 netif_rx(skb);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001543
Sakari Ailusc659c382011-01-21 10:59:30 +00001544 head_list->buffer[0].address =
1545 pci_map_single(priv->pci_dev, new_skb->data,
1546 TLAN_MAX_FRAME_SIZE, PCI_DMA_FROMDEVICE);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001547
Sakari Ailusc659c382011-01-21 10:59:30 +00001548 tlan_store_skb(head_list, new_skb);
Stephen Hemmingerdfc2c0a2008-05-30 09:49:58 -07001549drop_and_reuse:
Linus Torvalds1da177e2005-04-16 15:20:36 -07001550 head_list->forward = 0;
Sakari Ailusc659c382011-01-21 10:59:30 +00001551 head_list->c_stat = 0;
1552 tail_list = priv->rx_list + priv->rx_tail;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001553 tail_list->forward = head_list_phys;
1554
Sakari Ailusc659c382011-01-21 10:59:30 +00001555 CIRC_INC(priv->rx_head, TLAN_NUM_RX_LISTS);
1556 CIRC_INC(priv->rx_tail, TLAN_NUM_RX_LISTS);
1557 head_list = priv->rx_list + priv->rx_head;
1558 head_list_phys = priv->rx_list_dma
1559 + sizeof(struct tlan_list)*priv->rx_head;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001560 }
1561
1562 if (!ack)
Joe Perches50624aa2011-03-01 06:56:33 +00001563 netdev_info(dev,
1564 "Received interrupt for uncompleted RX frame\n");
Linus Torvalds1da177e2005-04-16 15:20:36 -07001565
1566
Sakari Ailusc659c382011-01-21 10:59:30 +00001567 if (eoc) {
1568 TLAN_DBG(TLAN_DEBUG_RX,
1569 "RECEIVE: handling RX EOC (Head=%d Tail=%d)\n",
1570 priv->rx_head, priv->rx_tail);
1571 head_list = priv->rx_list + priv->rx_head;
1572 head_list_phys = priv->rx_list_dma
1573 + sizeof(struct tlan_list)*priv->rx_head;
1574 outl(head_list_phys, dev->base_addr + TLAN_CH_PARM);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001575 ack |= TLAN_HC_GO | TLAN_HC_RT;
Sakari Ailusc659c382011-01-21 10:59:30 +00001576 priv->rx_eoc_count++;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001577 }
1578
Sakari Ailusc659c382011-01-21 10:59:30 +00001579 if (priv->adapter->flags & TLAN_ADAPTER_ACTIVITY_LED) {
1580 tlan_dio_write8(dev->base_addr,
1581 TLAN_LED_REG, TLAN_LED_LINK | TLAN_LED_ACT);
1582 if (priv->timer.function == NULL) {
1583 priv->timer.function = tlan_timer;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001584 priv->timer.data = (unsigned long) dev;
1585 priv->timer.expires = jiffies + TLAN_TIMER_ACT_DELAY;
Sakari Ailusc659c382011-01-21 10:59:30 +00001586 priv->timer_set_at = jiffies;
1587 priv->timer_type = TLAN_TIMER_ACTIVITY;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001588 add_timer(&priv->timer);
Sakari Ailusc659c382011-01-21 10:59:30 +00001589 } else if (priv->timer_type == TLAN_TIMER_ACTIVITY) {
1590 priv->timer_set_at = jiffies;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001591 }
1592 }
1593
Linus Torvalds1da177e2005-04-16 15:20:36 -07001594 return ack;
1595
Sakari Ailusc659c382011-01-21 10:59:30 +00001596}
Linus Torvalds1da177e2005-04-16 15:20:36 -07001597
1598
1599
1600
Sakari Ailusc659c382011-01-21 10:59:30 +00001601/***************************************************************
1602 * tlan_handle_dummy
1603 *
1604 * Returns:
1605 * 1
1606 * Parms:
1607 * dev Device assigned the IRQ that was
1608 * raised.
1609 * host_int The contents of the HOST_INT
1610 * port.
1611 *
1612 * This function handles the Dummy interrupt, which is
1613 * raised whenever a test interrupt is generated by setting
1614 * the Req_Int bit of HOST_CMD to 1.
1615 *
1616 **************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -07001617
Sakari Ailusc659c382011-01-21 10:59:30 +00001618static u32 tlan_handle_dummy(struct net_device *dev, u16 host_int)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001619{
Joe Perches50624aa2011-03-01 06:56:33 +00001620 netdev_info(dev, "Test interrupt\n");
Linus Torvalds1da177e2005-04-16 15:20:36 -07001621 return 1;
1622
Sakari Ailusc659c382011-01-21 10:59:30 +00001623}
Linus Torvalds1da177e2005-04-16 15:20:36 -07001624
1625
1626
1627
Sakari Ailusc659c382011-01-21 10:59:30 +00001628/***************************************************************
1629 * tlan_handle_tx_eoc
1630 *
1631 * Returns:
1632 * 1
1633 * Parms:
1634 * dev Device assigned the IRQ that was
1635 * raised.
1636 * host_int The contents of the HOST_INT
1637 * port.
1638 *
1639 * This driver is structured to determine EOC occurrences by
1640 * reading the CSTAT member of the list structure. Tx EOC
1641 * interrupts are disabled via the DIO INTDIS register.
1642 * However, TLAN chips before revision 3.0 didn't have this
1643 * functionality, so process EOC events if this is the
1644 * case.
1645 *
1646 **************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -07001647
Sakari Ailusc659c382011-01-21 10:59:30 +00001648static u32 tlan_handle_tx_eoc(struct net_device *dev, u16 host_int)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001649{
Sakari Ailusc659c382011-01-21 10:59:30 +00001650 struct tlan_priv *priv = netdev_priv(dev);
1651 struct tlan_list *head_list;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001652 dma_addr_t head_list_phys;
1653 u32 ack = 1;
Jeff Garzik6aa20a22006-09-13 13:24:59 -04001654
Linus Torvalds1da177e2005-04-16 15:20:36 -07001655 host_int = 0;
Sakari Ailusc659c382011-01-21 10:59:30 +00001656 if (priv->tlan_rev < 0x30) {
1657 TLAN_DBG(TLAN_DEBUG_TX,
1658 "TRANSMIT: handling TX EOC (Head=%d Tail=%d) -- IRQ\n",
1659 priv->tx_head, priv->tx_tail);
1660 head_list = priv->tx_list + priv->tx_head;
1661 head_list_phys = priv->tx_list_dma
1662 + sizeof(struct tlan_list)*priv->tx_head;
Sakari Ailusf45437e2011-02-09 10:25:06 +00001663 if ((head_list->c_stat & TLAN_CSTAT_READY)
1664 == TLAN_CSTAT_READY) {
Linus Torvalds1da177e2005-04-16 15:20:36 -07001665 netif_stop_queue(dev);
Sakari Ailusc659c382011-01-21 10:59:30 +00001666 outl(head_list_phys, dev->base_addr + TLAN_CH_PARM);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001667 ack |= TLAN_HC_GO;
1668 } else {
Sakari Ailusc659c382011-01-21 10:59:30 +00001669 priv->tx_in_progress = 0;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001670 }
1671 }
1672
1673 return ack;
1674
Sakari Ailusc659c382011-01-21 10:59:30 +00001675}
Linus Torvalds1da177e2005-04-16 15:20:36 -07001676
1677
1678
1679
Sakari Ailusc659c382011-01-21 10:59:30 +00001680/***************************************************************
1681 * tlan_handle_status_check
1682 *
1683 * Returns:
1684 * 0 if Adapter check, 1 if Network Status check.
1685 * Parms:
1686 * dev Device assigned the IRQ that was
1687 * raised.
1688 * host_int The contents of the HOST_INT
1689 * port.
1690 *
1691 * This function handles Adapter Check/Network Status
1692 * interrupts generated by the adapter. It checks the
1693 * vector in the HOST_INT register to determine if it is
1694 * an Adapter Check interrupt. If so, it resets the
1695 * adapter. Otherwise it clears the status registers
1696 * and services the PHY.
1697 *
1698 **************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -07001699
Sakari Ailusc659c382011-01-21 10:59:30 +00001700static u32 tlan_handle_status_check(struct net_device *dev, u16 host_int)
Jeff Garzik6aa20a22006-09-13 13:24:59 -04001701{
Sakari Ailusc659c382011-01-21 10:59:30 +00001702 struct tlan_priv *priv = netdev_priv(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001703 u32 ack;
1704 u32 error;
1705 u8 net_sts;
1706 u32 phy;
1707 u16 tlphy_ctl;
1708 u16 tlphy_sts;
Jeff Garzik6aa20a22006-09-13 13:24:59 -04001709
Linus Torvalds1da177e2005-04-16 15:20:36 -07001710 ack = 1;
Sakari Ailusc659c382011-01-21 10:59:30 +00001711 if (host_int & TLAN_HI_IV_MASK) {
1712 netif_stop_queue(dev);
1713 error = inl(dev->base_addr + TLAN_CH_PARM);
Joe Perches50624aa2011-03-01 06:56:33 +00001714 netdev_info(dev, "Adaptor Error = 0x%x\n", error);
Sakari Ailusc659c382011-01-21 10:59:30 +00001715 tlan_read_and_clear_stats(dev, TLAN_RECORD);
1716 outl(TLAN_HC_AD_RST, dev->base_addr + TLAN_HOST_CMD);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001717
1718 schedule_work(&priv->tlan_tqueue);
1719
1720 netif_wake_queue(dev);
1721 ack = 0;
1722 } else {
Sakari Ailusc659c382011-01-21 10:59:30 +00001723 TLAN_DBG(TLAN_DEBUG_GNRL, "%s: Status Check\n", dev->name);
1724 phy = priv->phy[priv->phy_num];
Linus Torvalds1da177e2005-04-16 15:20:36 -07001725
Sakari Ailusc659c382011-01-21 10:59:30 +00001726 net_sts = tlan_dio_read8(dev->base_addr, TLAN_NET_STS);
1727 if (net_sts) {
1728 tlan_dio_write8(dev->base_addr, TLAN_NET_STS, net_sts);
1729 TLAN_DBG(TLAN_DEBUG_GNRL, "%s: Net_Sts = %x\n",
1730 dev->name, (unsigned) net_sts);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001731 }
Sakari Ailusc659c382011-01-21 10:59:30 +00001732 if ((net_sts & TLAN_NET_STS_MIRQ) && (priv->phy_num == 0)) {
1733 tlan_mii_read_reg(dev, phy, TLAN_TLPHY_STS, &tlphy_sts);
1734 tlan_mii_read_reg(dev, phy, TLAN_TLPHY_CTL, &tlphy_ctl);
1735 if (!(tlphy_sts & TLAN_TS_POLOK) &&
1736 !(tlphy_ctl & TLAN_TC_SWAPOL)) {
1737 tlphy_ctl |= TLAN_TC_SWAPOL;
1738 tlan_mii_write_reg(dev, phy, TLAN_TLPHY_CTL,
1739 tlphy_ctl);
1740 } else if ((tlphy_sts & TLAN_TS_POLOK) &&
1741 (tlphy_ctl & TLAN_TC_SWAPOL)) {
1742 tlphy_ctl &= ~TLAN_TC_SWAPOL;
1743 tlan_mii_write_reg(dev, phy, TLAN_TLPHY_CTL,
1744 tlphy_ctl);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001745 }
Sakari Ailusc659c382011-01-21 10:59:30 +00001746
1747 if (debug)
1748 tlan_phy_print(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001749 }
1750 }
1751
1752 return ack;
1753
Sakari Ailusc659c382011-01-21 10:59:30 +00001754}
Linus Torvalds1da177e2005-04-16 15:20:36 -07001755
1756
1757
1758
Sakari Ailusc659c382011-01-21 10:59:30 +00001759/***************************************************************
1760 * tlan_handle_rx_eoc
1761 *
1762 * Returns:
1763 * 1
1764 * Parms:
1765 * dev Device assigned the IRQ that was
1766 * raised.
1767 * host_int The contents of the HOST_INT
1768 * port.
1769 *
1770 * This driver is structured to determine EOC occurrences by
1771 * reading the CSTAT member of the list structure. Rx EOC
1772 * interrupts are disabled via the DIO INTDIS register.
1773 * However, TLAN chips before revision 3.0 didn't have this
1774 * CSTAT member or a INTDIS register, so if this chip is
1775 * pre-3.0, process EOC interrupts normally.
1776 *
1777 **************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -07001778
Sakari Ailusc659c382011-01-21 10:59:30 +00001779static u32 tlan_handle_rx_eoc(struct net_device *dev, u16 host_int)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001780{
Sakari Ailusc659c382011-01-21 10:59:30 +00001781 struct tlan_priv *priv = netdev_priv(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001782 dma_addr_t head_list_phys;
1783 u32 ack = 1;
1784
Sakari Ailusc659c382011-01-21 10:59:30 +00001785 if (priv->tlan_rev < 0x30) {
1786 TLAN_DBG(TLAN_DEBUG_RX,
1787 "RECEIVE: Handling RX EOC (head=%d tail=%d) -- IRQ\n",
1788 priv->rx_head, priv->rx_tail);
1789 head_list_phys = priv->rx_list_dma
1790 + sizeof(struct tlan_list)*priv->rx_head;
1791 outl(head_list_phys, dev->base_addr + TLAN_CH_PARM);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001792 ack |= TLAN_HC_GO | TLAN_HC_RT;
Sakari Ailusc659c382011-01-21 10:59:30 +00001793 priv->rx_eoc_count++;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001794 }
1795
1796 return ack;
1797
Sakari Ailusc659c382011-01-21 10:59:30 +00001798}
Linus Torvalds1da177e2005-04-16 15:20:36 -07001799
1800
1801
1802
1803/*****************************************************************************
1804******************************************************************************
1805
Sakari Ailusc659c382011-01-21 10:59:30 +00001806ThunderLAN driver timer function
Linus Torvalds1da177e2005-04-16 15:20:36 -07001807
1808******************************************************************************
1809*****************************************************************************/
1810
1811
Sakari Ailusc659c382011-01-21 10:59:30 +00001812/***************************************************************
1813 * tlan_timer
1814 *
1815 * Returns:
1816 * Nothing
1817 * Parms:
1818 * data A value given to add timer when
1819 * add_timer was called.
1820 *
1821 * This function handles timed functionality for the
1822 * TLAN driver. The two current timer uses are for
1823 * delaying for autonegotionation and driving the ACT LED.
1824 * - Autonegotiation requires being allowed about
1825 * 2 1/2 seconds before attempting to transmit a
1826 * packet. It would be a very bad thing to hang
1827 * the kernel this long, so the driver doesn't
1828 * allow transmission 'til after this time, for
1829 * certain PHYs. It would be much nicer if all
1830 * PHYs were interrupt-capable like the internal
1831 * PHY.
1832 * - The ACT LED, which shows adapter activity, is
1833 * driven by the driver, and so must be left on
1834 * for a short period to power up the LED so it
1835 * can be seen. This delay can be changed by
1836 * changing the TLAN_TIMER_ACT_DELAY in tlan.h,
1837 * if desired. 100 ms produces a slightly
1838 * sluggish response.
1839 *
1840 **************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -07001841
Sakari Ailusc659c382011-01-21 10:59:30 +00001842static void tlan_timer(unsigned long data)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001843{
1844 struct net_device *dev = (struct net_device *) data;
Sakari Ailusc659c382011-01-21 10:59:30 +00001845 struct tlan_priv *priv = netdev_priv(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001846 u32 elapsed;
1847 unsigned long flags = 0;
1848
1849 priv->timer.function = NULL;
1850
Sakari Ailusc659c382011-01-21 10:59:30 +00001851 switch (priv->timer_type) {
Sakari Ailusc659c382011-01-21 10:59:30 +00001852 case TLAN_TIMER_PHY_PDOWN:
1853 tlan_phy_power_down(dev);
1854 break;
1855 case TLAN_TIMER_PHY_PUP:
1856 tlan_phy_power_up(dev);
1857 break;
1858 case TLAN_TIMER_PHY_RESET:
1859 tlan_phy_reset(dev);
1860 break;
1861 case TLAN_TIMER_PHY_START_LINK:
1862 tlan_phy_start_link(dev);
1863 break;
1864 case TLAN_TIMER_PHY_FINISH_AN:
1865 tlan_phy_finish_auto_neg(dev);
1866 break;
1867 case TLAN_TIMER_FINISH_RESET:
1868 tlan_finish_reset(dev);
1869 break;
1870 case TLAN_TIMER_ACTIVITY:
1871 spin_lock_irqsave(&priv->lock, flags);
1872 if (priv->timer.function == NULL) {
1873 elapsed = jiffies - priv->timer_set_at;
1874 if (elapsed >= TLAN_TIMER_ACT_DELAY) {
1875 tlan_dio_write8(dev->base_addr,
1876 TLAN_LED_REG, TLAN_LED_LINK);
1877 } else {
1878 priv->timer.function = tlan_timer;
1879 priv->timer.expires = priv->timer_set_at
1880 + TLAN_TIMER_ACT_DELAY;
1881 spin_unlock_irqrestore(&priv->lock, flags);
1882 add_timer(&priv->timer);
1883 break;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001884 }
Sakari Ailusc659c382011-01-21 10:59:30 +00001885 }
1886 spin_unlock_irqrestore(&priv->lock, flags);
1887 break;
1888 default:
1889 break;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001890 }
1891
Sakari Ailusc659c382011-01-21 10:59:30 +00001892}
Linus Torvalds1da177e2005-04-16 15:20:36 -07001893
1894
Linus Torvalds1da177e2005-04-16 15:20:36 -07001895/*****************************************************************************
1896******************************************************************************
1897
Sakari Ailusc659c382011-01-21 10:59:30 +00001898ThunderLAN driver adapter related routines
Linus Torvalds1da177e2005-04-16 15:20:36 -07001899
1900******************************************************************************
1901*****************************************************************************/
1902
1903
Sakari Ailusc659c382011-01-21 10:59:30 +00001904/***************************************************************
1905 * tlan_reset_lists
1906 *
1907 * Returns:
1908 * Nothing
1909 * Parms:
1910 * dev The device structure with the list
1911 * stuctures to be reset.
1912 *
1913 * This routine sets the variables associated with managing
1914 * the TLAN lists to their initial values.
1915 *
1916 **************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -07001917
Sakari Ailusc659c382011-01-21 10:59:30 +00001918static void tlan_reset_lists(struct net_device *dev)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001919{
Sakari Ailusc659c382011-01-21 10:59:30 +00001920 struct tlan_priv *priv = netdev_priv(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001921 int i;
Sakari Ailusc659c382011-01-21 10:59:30 +00001922 struct tlan_list *list;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001923 dma_addr_t list_phys;
1924 struct sk_buff *skb;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001925
Sakari Ailusc659c382011-01-21 10:59:30 +00001926 priv->tx_head = 0;
1927 priv->tx_tail = 0;
1928 for (i = 0; i < TLAN_NUM_TX_LISTS; i++) {
1929 list = priv->tx_list + i;
1930 list->c_stat = TLAN_CSTAT_UNUSED;
Sakari Ailus5eeabf52008-12-16 15:24:05 -08001931 list->buffer[0].address = 0;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001932 list->buffer[2].count = 0;
1933 list->buffer[2].address = 0;
1934 list->buffer[8].address = 0;
1935 list->buffer[9].address = 0;
1936 }
1937
Sakari Ailusc659c382011-01-21 10:59:30 +00001938 priv->rx_head = 0;
1939 priv->rx_tail = TLAN_NUM_RX_LISTS - 1;
1940 for (i = 0; i < TLAN_NUM_RX_LISTS; i++) {
1941 list = priv->rx_list + i;
1942 list_phys = priv->rx_list_dma + sizeof(struct tlan_list)*i;
1943 list->c_stat = TLAN_CSTAT_READY;
1944 list->frame_size = TLAN_MAX_FRAME_SIZE;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001945 list->buffer[0].count = TLAN_MAX_FRAME_SIZE | TLAN_LAST_BUFFER;
Eric Dumazet89d71a62009-10-13 05:34:20 +00001946 skb = netdev_alloc_skb_ip_align(dev, TLAN_MAX_FRAME_SIZE + 5);
Joe Perches720a43e2013-03-08 15:03:25 +00001947 if (!skb)
Sakari Ailus5eeabf52008-12-16 15:24:05 -08001948 break;
Sakari Ailus5eeabf52008-12-16 15:24:05 -08001949
Sakari Ailusc659c382011-01-21 10:59:30 +00001950 list->buffer[0].address = pci_map_single(priv->pci_dev,
Sakari Ailus5eeabf52008-12-16 15:24:05 -08001951 skb->data,
1952 TLAN_MAX_FRAME_SIZE,
1953 PCI_DMA_FROMDEVICE);
Sakari Ailusc659c382011-01-21 10:59:30 +00001954 tlan_store_skb(list, skb);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001955 list->buffer[1].count = 0;
1956 list->buffer[1].address = 0;
Sakari Ailusc659c382011-01-21 10:59:30 +00001957 list->forward = list_phys + sizeof(struct tlan_list);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001958 }
1959
Stephen Hemminger9ded65a2008-05-30 09:49:56 -07001960 /* in case ran out of memory early, clear bits */
1961 while (i < TLAN_NUM_RX_LISTS) {
Sakari Ailusc659c382011-01-21 10:59:30 +00001962 tlan_store_skb(priv->rx_list + i, NULL);
Stephen Hemminger9ded65a2008-05-30 09:49:56 -07001963 ++i;
1964 }
1965 list->forward = 0;
1966
Sakari Ailusc659c382011-01-21 10:59:30 +00001967}
Linus Torvalds1da177e2005-04-16 15:20:36 -07001968
1969
Sakari Ailusc659c382011-01-21 10:59:30 +00001970static void tlan_free_lists(struct net_device *dev)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001971{
Sakari Ailusc659c382011-01-21 10:59:30 +00001972 struct tlan_priv *priv = netdev_priv(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001973 int i;
Sakari Ailusc659c382011-01-21 10:59:30 +00001974 struct tlan_list *list;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001975 struct sk_buff *skb;
1976
Sakari Ailusc659c382011-01-21 10:59:30 +00001977 for (i = 0; i < TLAN_NUM_TX_LISTS; i++) {
1978 list = priv->tx_list + i;
1979 skb = tlan_get_skb(list);
1980 if (skb) {
Sakari Ailus5eeabf52008-12-16 15:24:05 -08001981 pci_unmap_single(
Sakari Ailusc659c382011-01-21 10:59:30 +00001982 priv->pci_dev,
Sakari Ailus5eeabf52008-12-16 15:24:05 -08001983 list->buffer[0].address,
1984 max(skb->len,
1985 (unsigned int)TLAN_MIN_FRAME_SIZE),
1986 PCI_DMA_TODEVICE);
Sakari Ailusc659c382011-01-21 10:59:30 +00001987 dev_kfree_skb_any(skb);
Sakari Ailus5eeabf52008-12-16 15:24:05 -08001988 list->buffer[8].address = 0;
1989 list->buffer[9].address = 0;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001990 }
Sakari Ailus5eeabf52008-12-16 15:24:05 -08001991 }
Linus Torvalds1da177e2005-04-16 15:20:36 -07001992
Sakari Ailusc659c382011-01-21 10:59:30 +00001993 for (i = 0; i < TLAN_NUM_RX_LISTS; i++) {
1994 list = priv->rx_list + i;
1995 skb = tlan_get_skb(list);
1996 if (skb) {
1997 pci_unmap_single(priv->pci_dev,
Sakari Ailus5eeabf52008-12-16 15:24:05 -08001998 list->buffer[0].address,
1999 TLAN_MAX_FRAME_SIZE,
2000 PCI_DMA_FROMDEVICE);
Sakari Ailusc659c382011-01-21 10:59:30 +00002001 dev_kfree_skb_any(skb);
Sakari Ailus5eeabf52008-12-16 15:24:05 -08002002 list->buffer[8].address = 0;
2003 list->buffer[9].address = 0;
Linus Torvalds1da177e2005-04-16 15:20:36 -07002004 }
2005 }
Sakari Ailusc659c382011-01-21 10:59:30 +00002006}
Linus Torvalds1da177e2005-04-16 15:20:36 -07002007
2008
2009
2010
Sakari Ailusc659c382011-01-21 10:59:30 +00002011/***************************************************************
2012 * tlan_print_dio
2013 *
2014 * Returns:
2015 * Nothing
2016 * Parms:
2017 * io_base Base IO port of the device of
2018 * which to print DIO registers.
2019 *
2020 * This function prints out all the internal (DIO)
2021 * registers of a TLAN chip.
2022 *
2023 **************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -07002024
Sakari Ailusc659c382011-01-21 10:59:30 +00002025static void tlan_print_dio(u16 io_base)
Linus Torvalds1da177e2005-04-16 15:20:36 -07002026{
2027 u32 data0, data1;
2028 int i;
2029
Joe Perches50624aa2011-03-01 06:56:33 +00002030 pr_info("Contents of internal registers for io base 0x%04hx\n",
2031 io_base);
2032 pr_info("Off. +0 +4\n");
Sakari Ailusc659c382011-01-21 10:59:30 +00002033 for (i = 0; i < 0x4C; i += 8) {
2034 data0 = tlan_dio_read32(io_base, i);
2035 data1 = tlan_dio_read32(io_base, i + 0x4);
Joe Perches50624aa2011-03-01 06:56:33 +00002036 pr_info("0x%02x 0x%08x 0x%08x\n", i, data0, data1);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002037 }
2038
Sakari Ailusc659c382011-01-21 10:59:30 +00002039}
Linus Torvalds1da177e2005-04-16 15:20:36 -07002040
2041
2042
2043
Sakari Ailusc659c382011-01-21 10:59:30 +00002044/***************************************************************
2045 * TLan_PrintList
2046 *
2047 * Returns:
2048 * Nothing
2049 * Parms:
2050 * list A pointer to the struct tlan_list structure to
2051 * be printed.
2052 * type A string to designate type of list,
2053 * "Rx" or "Tx".
2054 * num The index of the list.
2055 *
2056 * This function prints out the contents of the list
2057 * pointed to by the list parameter.
2058 *
2059 **************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -07002060
Sakari Ailusc659c382011-01-21 10:59:30 +00002061static void tlan_print_list(struct tlan_list *list, char *type, int num)
Linus Torvalds1da177e2005-04-16 15:20:36 -07002062{
2063 int i;
2064
Joe Perches50624aa2011-03-01 06:56:33 +00002065 pr_info("%s List %d at %p\n", type, num, list);
2066 pr_info(" Forward = 0x%08x\n", list->forward);
2067 pr_info(" CSTAT = 0x%04hx\n", list->c_stat);
2068 pr_info(" Frame Size = 0x%04hx\n", list->frame_size);
Sakari Ailusc659c382011-01-21 10:59:30 +00002069 /* for (i = 0; i < 10; i++) { */
2070 for (i = 0; i < 2; i++) {
Joe Perches50624aa2011-03-01 06:56:33 +00002071 pr_info(" Buffer[%d].count, addr = 0x%08x, 0x%08x\n",
2072 i, list->buffer[i].count, list->buffer[i].address);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002073 }
2074
Sakari Ailusc659c382011-01-21 10:59:30 +00002075}
Linus Torvalds1da177e2005-04-16 15:20:36 -07002076
2077
2078
2079
Sakari Ailusc659c382011-01-21 10:59:30 +00002080/***************************************************************
2081 * tlan_read_and_clear_stats
2082 *
2083 * Returns:
2084 * Nothing
2085 * Parms:
2086 * dev Pointer to device structure of adapter
2087 * to which to read stats.
2088 * record Flag indicating whether to add
2089 *
2090 * This functions reads all the internal status registers
2091 * of the TLAN chip, which clears them as a side effect.
2092 * It then either adds the values to the device's status
2093 * struct, or discards them, depending on whether record
2094 * is TLAN_RECORD (!=0) or TLAN_IGNORE (==0).
2095 *
2096 **************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -07002097
Sakari Ailusc659c382011-01-21 10:59:30 +00002098static void tlan_read_and_clear_stats(struct net_device *dev, int record)
Linus Torvalds1da177e2005-04-16 15:20:36 -07002099{
Linus Torvalds1da177e2005-04-16 15:20:36 -07002100 u32 tx_good, tx_under;
2101 u32 rx_good, rx_over;
2102 u32 def_tx, crc, code;
2103 u32 multi_col, single_col;
2104 u32 excess_col, late_col, loss;
2105
Sakari Ailusc659c382011-01-21 10:59:30 +00002106 outw(TLAN_GOOD_TX_FRMS, dev->base_addr + TLAN_DIO_ADR);
2107 tx_good = inb(dev->base_addr + TLAN_DIO_DATA);
2108 tx_good += inb(dev->base_addr + TLAN_DIO_DATA + 1) << 8;
2109 tx_good += inb(dev->base_addr + TLAN_DIO_DATA + 2) << 16;
2110 tx_under = inb(dev->base_addr + TLAN_DIO_DATA + 3);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002111
Sakari Ailusc659c382011-01-21 10:59:30 +00002112 outw(TLAN_GOOD_RX_FRMS, dev->base_addr + TLAN_DIO_ADR);
2113 rx_good = inb(dev->base_addr + TLAN_DIO_DATA);
2114 rx_good += inb(dev->base_addr + TLAN_DIO_DATA + 1) << 8;
2115 rx_good += inb(dev->base_addr + TLAN_DIO_DATA + 2) << 16;
2116 rx_over = inb(dev->base_addr + TLAN_DIO_DATA + 3);
Jeff Garzik6aa20a22006-09-13 13:24:59 -04002117
Sakari Ailusc659c382011-01-21 10:59:30 +00002118 outw(TLAN_DEFERRED_TX, dev->base_addr + TLAN_DIO_ADR);
2119 def_tx = inb(dev->base_addr + TLAN_DIO_DATA);
2120 def_tx += inb(dev->base_addr + TLAN_DIO_DATA + 1) << 8;
2121 crc = inb(dev->base_addr + TLAN_DIO_DATA + 2);
2122 code = inb(dev->base_addr + TLAN_DIO_DATA + 3);
Jeff Garzik6aa20a22006-09-13 13:24:59 -04002123
Sakari Ailusc659c382011-01-21 10:59:30 +00002124 outw(TLAN_MULTICOL_FRMS, dev->base_addr + TLAN_DIO_ADR);
2125 multi_col = inb(dev->base_addr + TLAN_DIO_DATA);
2126 multi_col += inb(dev->base_addr + TLAN_DIO_DATA + 1) << 8;
2127 single_col = inb(dev->base_addr + TLAN_DIO_DATA + 2);
2128 single_col += inb(dev->base_addr + TLAN_DIO_DATA + 3) << 8;
Linus Torvalds1da177e2005-04-16 15:20:36 -07002129
Sakari Ailusc659c382011-01-21 10:59:30 +00002130 outw(TLAN_EXCESSCOL_FRMS, dev->base_addr + TLAN_DIO_ADR);
2131 excess_col = inb(dev->base_addr + TLAN_DIO_DATA);
2132 late_col = inb(dev->base_addr + TLAN_DIO_DATA + 1);
2133 loss = inb(dev->base_addr + TLAN_DIO_DATA + 2);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002134
Sakari Ailusc659c382011-01-21 10:59:30 +00002135 if (record) {
Stephen Hemmingerf8f31542008-05-30 09:49:53 -07002136 dev->stats.rx_packets += rx_good;
2137 dev->stats.rx_errors += rx_over + crc + code;
2138 dev->stats.tx_packets += tx_good;
2139 dev->stats.tx_errors += tx_under + loss;
Sakari Ailusc659c382011-01-21 10:59:30 +00002140 dev->stats.collisions += multi_col
2141 + single_col + excess_col + late_col;
Linus Torvalds1da177e2005-04-16 15:20:36 -07002142
Stephen Hemmingerf8f31542008-05-30 09:49:53 -07002143 dev->stats.rx_over_errors += rx_over;
2144 dev->stats.rx_crc_errors += crc;
2145 dev->stats.rx_frame_errors += code;
Linus Torvalds1da177e2005-04-16 15:20:36 -07002146
Stephen Hemmingerf8f31542008-05-30 09:49:53 -07002147 dev->stats.tx_aborted_errors += tx_under;
2148 dev->stats.tx_carrier_errors += loss;
Linus Torvalds1da177e2005-04-16 15:20:36 -07002149 }
Jeff Garzik6aa20a22006-09-13 13:24:59 -04002150
Sakari Ailusc659c382011-01-21 10:59:30 +00002151}
Linus Torvalds1da177e2005-04-16 15:20:36 -07002152
2153
2154
2155
Sakari Ailusc659c382011-01-21 10:59:30 +00002156/***************************************************************
2157 * TLan_Reset
2158 *
2159 * Returns:
2160 * 0
2161 * Parms:
2162 * dev Pointer to device structure of adapter
2163 * to be reset.
2164 *
2165 * This function resets the adapter and it's physical
2166 * device. See Chap. 3, pp. 9-10 of the "ThunderLAN
2167 * Programmer's Guide" for details. The routine tries to
2168 * implement what is detailed there, though adjustments
2169 * have been made.
2170 *
2171 **************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -07002172
Harvey Harrison98e0f522008-02-18 10:04:38 -08002173static void
Sakari Ailusc659c382011-01-21 10:59:30 +00002174tlan_reset_adapter(struct net_device *dev)
Linus Torvalds1da177e2005-04-16 15:20:36 -07002175{
Sakari Ailusc659c382011-01-21 10:59:30 +00002176 struct tlan_priv *priv = netdev_priv(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002177 int i;
2178 u32 addr;
2179 u32 data;
2180 u8 data8;
2181
Sakari Ailusc659c382011-01-21 10:59:30 +00002182 priv->tlan_full_duplex = false;
2183 priv->phy_online = 0;
Linus Torvalds1da177e2005-04-16 15:20:36 -07002184 netif_carrier_off(dev);
2185
2186/* 1. Assert reset bit. */
2187
2188 data = inl(dev->base_addr + TLAN_HOST_CMD);
2189 data |= TLAN_HC_AD_RST;
2190 outl(data, dev->base_addr + TLAN_HOST_CMD);
Jeff Garzik6aa20a22006-09-13 13:24:59 -04002191
Linus Torvalds1da177e2005-04-16 15:20:36 -07002192 udelay(1000);
2193
Sakari Ailusc659c382011-01-21 10:59:30 +00002194/* 2. Turn off interrupts. (Probably isn't necessary) */
Linus Torvalds1da177e2005-04-16 15:20:36 -07002195
2196 data = inl(dev->base_addr + TLAN_HOST_CMD);
2197 data |= TLAN_HC_INT_OFF;
2198 outl(data, dev->base_addr + TLAN_HOST_CMD);
2199
2200/* 3. Clear AREGs and HASHs. */
2201
Sakari Ailusc659c382011-01-21 10:59:30 +00002202 for (i = TLAN_AREG_0; i <= TLAN_HASH_2; i += 4)
2203 tlan_dio_write32(dev->base_addr, (u16) i, 0);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002204
2205/* 4. Setup NetConfig register. */
2206
2207 data = TLAN_NET_CFG_1FRAG | TLAN_NET_CFG_1CHAN | TLAN_NET_CFG_PHY_EN;
Sakari Ailusc659c382011-01-21 10:59:30 +00002208 tlan_dio_write16(dev->base_addr, TLAN_NET_CONFIG, (u16) data);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002209
2210/* 5. Load Ld_Tmr and Ld_Thr in HOST_CMD. */
2211
Sakari Ailusc659c382011-01-21 10:59:30 +00002212 outl(TLAN_HC_LD_TMR | 0x3f, dev->base_addr + TLAN_HOST_CMD);
2213 outl(TLAN_HC_LD_THR | 0x9, dev->base_addr + TLAN_HOST_CMD);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002214
2215/* 6. Unreset the MII by setting NMRST (in NetSio) to 1. */
2216
Sakari Ailusc659c382011-01-21 10:59:30 +00002217 outw(TLAN_NET_SIO, dev->base_addr + TLAN_DIO_ADR);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002218 addr = dev->base_addr + TLAN_DIO_DATA + TLAN_NET_SIO;
Sakari Ailusc659c382011-01-21 10:59:30 +00002219 tlan_set_bit(TLAN_NET_SIO_NMRST, addr);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002220
2221/* 7. Setup the remaining registers. */
2222
Sakari Ailusc659c382011-01-21 10:59:30 +00002223 if (priv->tlan_rev >= 0x30) {
Linus Torvalds1da177e2005-04-16 15:20:36 -07002224 data8 = TLAN_ID_TX_EOC | TLAN_ID_RX_EOC;
Sakari Ailusc659c382011-01-21 10:59:30 +00002225 tlan_dio_write8(dev->base_addr, TLAN_INT_DIS, data8);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002226 }
Sakari Ailusc659c382011-01-21 10:59:30 +00002227 tlan_phy_detect(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002228 data = TLAN_NET_CFG_1FRAG | TLAN_NET_CFG_1CHAN;
Jeff Garzik6aa20a22006-09-13 13:24:59 -04002229
Sakari Ailusc659c382011-01-21 10:59:30 +00002230 if (priv->adapter->flags & TLAN_ADAPTER_BIT_RATE_PHY) {
Linus Torvalds1da177e2005-04-16 15:20:36 -07002231 data |= TLAN_NET_CFG_BIT;
Sakari Ailusc659c382011-01-21 10:59:30 +00002232 if (priv->aui == 1) {
2233 tlan_dio_write8(dev->base_addr, TLAN_ACOMMIT, 0x0a);
2234 } else if (priv->duplex == TLAN_DUPLEX_FULL) {
2235 tlan_dio_write8(dev->base_addr, TLAN_ACOMMIT, 0x00);
2236 priv->tlan_full_duplex = true;
Linus Torvalds1da177e2005-04-16 15:20:36 -07002237 } else {
Sakari Ailusc659c382011-01-21 10:59:30 +00002238 tlan_dio_write8(dev->base_addr, TLAN_ACOMMIT, 0x08);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002239 }
2240 }
2241
Ondrej Zary7a72edd2014-06-30 18:38:35 +02002242 /* don't power down internal PHY if we're going to use it */
2243 if (priv->phy_num == 0 ||
2244 (priv->adapter->flags & TLAN_ADAPTER_USE_INTERN_10))
Linus Torvalds1da177e2005-04-16 15:20:36 -07002245 data |= TLAN_NET_CFG_PHY_EN;
Sakari Ailusc659c382011-01-21 10:59:30 +00002246 tlan_dio_write16(dev->base_addr, TLAN_NET_CONFIG, (u16) data);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002247
Sakari Ailusc659c382011-01-21 10:59:30 +00002248 if (priv->adapter->flags & TLAN_ADAPTER_UNMANAGED_PHY)
2249 tlan_finish_reset(dev);
2250 else
2251 tlan_phy_power_down(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002252
Sakari Ailusc659c382011-01-21 10:59:30 +00002253}
Linus Torvalds1da177e2005-04-16 15:20:36 -07002254
2255
2256
2257
Harvey Harrison98e0f522008-02-18 10:04:38 -08002258static void
Sakari Ailusc659c382011-01-21 10:59:30 +00002259tlan_finish_reset(struct net_device *dev)
Linus Torvalds1da177e2005-04-16 15:20:36 -07002260{
Sakari Ailusc659c382011-01-21 10:59:30 +00002261 struct tlan_priv *priv = netdev_priv(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002262 u8 data;
2263 u32 phy;
2264 u8 sio;
2265 u16 status;
2266 u16 partner;
2267 u16 tlphy_ctl;
Sakari Ailusc659c382011-01-21 10:59:30 +00002268 u16 tlphy_par;
Linus Torvalds1da177e2005-04-16 15:20:36 -07002269 u16 tlphy_id1, tlphy_id2;
Sakari Ailusc659c382011-01-21 10:59:30 +00002270 int i;
Linus Torvalds1da177e2005-04-16 15:20:36 -07002271
Sakari Ailusc659c382011-01-21 10:59:30 +00002272 phy = priv->phy[priv->phy_num];
Linus Torvalds1da177e2005-04-16 15:20:36 -07002273
2274 data = TLAN_NET_CMD_NRESET | TLAN_NET_CMD_NWRAP;
Sakari Ailusc659c382011-01-21 10:59:30 +00002275 if (priv->tlan_full_duplex)
Linus Torvalds1da177e2005-04-16 15:20:36 -07002276 data |= TLAN_NET_CMD_DUPLEX;
Sakari Ailusc659c382011-01-21 10:59:30 +00002277 tlan_dio_write8(dev->base_addr, TLAN_NET_CMD, data);
Jeff Garzik6aa20a22006-09-13 13:24:59 -04002278 data = TLAN_NET_MASK_MASK4 | TLAN_NET_MASK_MASK5;
Sakari Ailusc659c382011-01-21 10:59:30 +00002279 if (priv->phy_num == 0)
Jeff Garzik6aa20a22006-09-13 13:24:59 -04002280 data |= TLAN_NET_MASK_MASK7;
Sakari Ailusc659c382011-01-21 10:59:30 +00002281 tlan_dio_write8(dev->base_addr, TLAN_NET_MASK, data);
2282 tlan_dio_write16(dev->base_addr, TLAN_MAX_RX, ((1536)+7)&~7);
2283 tlan_mii_read_reg(dev, phy, MII_GEN_ID_HI, &tlphy_id1);
2284 tlan_mii_read_reg(dev, phy, MII_GEN_ID_LO, &tlphy_id2);
Jeff Garzik6aa20a22006-09-13 13:24:59 -04002285
Sakari Ailusc659c382011-01-21 10:59:30 +00002286 if ((priv->adapter->flags & TLAN_ADAPTER_UNMANAGED_PHY) ||
2287 (priv->aui)) {
Linus Torvalds1da177e2005-04-16 15:20:36 -07002288 status = MII_GS_LINK;
Joe Perches50624aa2011-03-01 06:56:33 +00002289 netdev_info(dev, "Link forced\n");
Linus Torvalds1da177e2005-04-16 15:20:36 -07002290 } else {
Sakari Ailusc659c382011-01-21 10:59:30 +00002291 tlan_mii_read_reg(dev, phy, MII_GEN_STS, &status);
2292 udelay(1000);
2293 tlan_mii_read_reg(dev, phy, MII_GEN_STS, &status);
Ondrej Zaryc0a87c22014-06-30 18:38:28 +02002294 if (status & MII_GS_LINK) {
2295 /* We only support link info on Nat.Sem. PHY's */
2296 if ((tlphy_id1 == NAT_SEM_ID1) &&
2297 (tlphy_id2 == NAT_SEM_ID2)) {
2298 tlan_mii_read_reg(dev, phy, MII_AN_LPA,
2299 &partner);
2300 tlan_mii_read_reg(dev, phy, TLAN_TLPHY_PAR,
2301 &tlphy_par);
Jeff Garzik6aa20a22006-09-13 13:24:59 -04002302
Ondrej Zaryc0a87c22014-06-30 18:38:28 +02002303 netdev_info(dev,
2304 "Link active, %s %uMbps %s-Duplex\n",
2305 !(tlphy_par & TLAN_PHY_AN_EN_STAT)
2306 ? "forced" : "Autonegotiation enabled,",
2307 tlphy_par & TLAN_PHY_SPEED_100
2308 ? 100 : 10,
2309 tlphy_par & TLAN_PHY_DUPLEX_FULL
2310 ? "Full" : "Half");
Joe Perches50624aa2011-03-01 06:56:33 +00002311
Ondrej Zaryc0a87c22014-06-30 18:38:28 +02002312 if (tlphy_par & TLAN_PHY_AN_EN_STAT) {
2313 netdev_info(dev, "Partner capability:");
2314 for (i = 5; i < 10; i++)
2315 if (partner & (1 << i))
2316 pr_cont(" %s",
2317 media[i-5]);
2318 pr_cont("\n");
2319 }
2320 } else
2321 netdev_info(dev, "Link active\n");
2322 /* Enabling link beat monitoring */
2323 priv->media_timer.function = tlan_phy_monitor;
2324 priv->media_timer.data = (unsigned long) dev;
2325 priv->media_timer.expires = jiffies + HZ;
2326 add_timer(&priv->media_timer);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002327 }
2328 }
2329
Sakari Ailusc659c382011-01-21 10:59:30 +00002330 if (priv->phy_num == 0) {
2331 tlan_mii_read_reg(dev, phy, TLAN_TLPHY_CTL, &tlphy_ctl);
2332 tlphy_ctl |= TLAN_TC_INTEN;
2333 tlan_mii_write_reg(dev, phy, TLAN_TLPHY_CTL, tlphy_ctl);
2334 sio = tlan_dio_read8(dev->base_addr, TLAN_NET_SIO);
2335 sio |= TLAN_NET_SIO_MINTEN;
2336 tlan_dio_write8(dev->base_addr, TLAN_NET_SIO, sio);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002337 }
2338
Sakari Ailusc659c382011-01-21 10:59:30 +00002339 if (status & MII_GS_LINK) {
2340 tlan_set_mac(dev, 0, dev->dev_addr);
2341 priv->phy_online = 1;
2342 outb((TLAN_HC_INT_ON >> 8), dev->base_addr + TLAN_HOST_CMD + 1);
2343 if (debug >= 1 && debug != TLAN_DEBUG_PROBE)
2344 outb((TLAN_HC_REQ_INT >> 8),
2345 dev->base_addr + TLAN_HOST_CMD + 1);
2346 outl(priv->rx_list_dma, dev->base_addr + TLAN_CH_PARM);
2347 outl(TLAN_HC_GO | TLAN_HC_RT, dev->base_addr + TLAN_HOST_CMD);
Ondrej Zaryc0a87c22014-06-30 18:38:28 +02002348 tlan_dio_write8(dev->base_addr, TLAN_LED_REG, TLAN_LED_LINK);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002349 netif_carrier_on(dev);
2350 } else {
Joe Perches50624aa2011-03-01 06:56:33 +00002351 netdev_info(dev, "Link inactive, will retry in 10 secs...\n");
Sakari Ailusc659c382011-01-21 10:59:30 +00002352 tlan_set_timer(dev, (10*HZ), TLAN_TIMER_FINISH_RESET);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002353 return;
2354 }
Sakari Ailusc659c382011-01-21 10:59:30 +00002355 tlan_set_multicast_list(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002356
Sakari Ailusc659c382011-01-21 10:59:30 +00002357}
Linus Torvalds1da177e2005-04-16 15:20:36 -07002358
2359
2360
2361
Sakari Ailusc659c382011-01-21 10:59:30 +00002362/***************************************************************
2363 * tlan_set_mac
2364 *
2365 * Returns:
2366 * Nothing
2367 * Parms:
2368 * dev Pointer to device structure of adapter
2369 * on which to change the AREG.
2370 * areg The AREG to set the address in (0 - 3).
2371 * mac A pointer to an array of chars. Each
2372 * element stores one byte of the address.
2373 * IE, it isn't in ascii.
2374 *
2375 * This function transfers a MAC address to one of the
2376 * TLAN AREGs (address registers). The TLAN chip locks
2377 * the register on writing to offset 0 and unlocks the
2378 * register after writing to offset 5. If NULL is passed
2379 * in mac, then the AREG is filled with 0's.
2380 *
2381 **************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -07002382
Sakari Ailusc659c382011-01-21 10:59:30 +00002383static void tlan_set_mac(struct net_device *dev, int areg, char *mac)
Linus Torvalds1da177e2005-04-16 15:20:36 -07002384{
2385 int i;
Jeff Garzik6aa20a22006-09-13 13:24:59 -04002386
Linus Torvalds1da177e2005-04-16 15:20:36 -07002387 areg *= 6;
2388
Sakari Ailusc659c382011-01-21 10:59:30 +00002389 if (mac != NULL) {
2390 for (i = 0; i < 6; i++)
2391 tlan_dio_write8(dev->base_addr,
2392 TLAN_AREG_0 + areg + i, mac[i]);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002393 } else {
Sakari Ailusc659c382011-01-21 10:59:30 +00002394 for (i = 0; i < 6; i++)
2395 tlan_dio_write8(dev->base_addr,
2396 TLAN_AREG_0 + areg + i, 0);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002397 }
2398
Sakari Ailusc659c382011-01-21 10:59:30 +00002399}
Linus Torvalds1da177e2005-04-16 15:20:36 -07002400
2401
2402
2403
2404/*****************************************************************************
2405******************************************************************************
2406
Sakari Ailusc659c382011-01-21 10:59:30 +00002407ThunderLAN driver PHY layer routines
Linus Torvalds1da177e2005-04-16 15:20:36 -07002408
2409******************************************************************************
2410*****************************************************************************/
2411
2412
2413
Sakari Ailusc659c382011-01-21 10:59:30 +00002414/*********************************************************************
2415 * tlan_phy_print
2416 *
2417 * Returns:
2418 * Nothing
2419 * Parms:
2420 * dev A pointer to the device structure of the
2421 * TLAN device having the PHYs to be detailed.
2422 *
2423 * This function prints the registers a PHY (aka transceiver).
2424 *
2425 ********************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -07002426
Sakari Ailusc659c382011-01-21 10:59:30 +00002427static void tlan_phy_print(struct net_device *dev)
Linus Torvalds1da177e2005-04-16 15:20:36 -07002428{
Sakari Ailusc659c382011-01-21 10:59:30 +00002429 struct tlan_priv *priv = netdev_priv(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002430 u16 i, data0, data1, data2, data3, phy;
2431
Sakari Ailusc659c382011-01-21 10:59:30 +00002432 phy = priv->phy[priv->phy_num];
Linus Torvalds1da177e2005-04-16 15:20:36 -07002433
Sakari Ailusc659c382011-01-21 10:59:30 +00002434 if (priv->adapter->flags & TLAN_ADAPTER_UNMANAGED_PHY) {
Joe Perches50624aa2011-03-01 06:56:33 +00002435 netdev_info(dev, "Unmanaged PHY\n");
Sakari Ailusc659c382011-01-21 10:59:30 +00002436 } else if (phy <= TLAN_PHY_MAX_ADDR) {
Joe Perches50624aa2011-03-01 06:56:33 +00002437 netdev_info(dev, "PHY 0x%02x\n", phy);
2438 pr_info(" Off. +0 +1 +2 +3\n");
Sakari Ailusc659c382011-01-21 10:59:30 +00002439 for (i = 0; i < 0x20; i += 4) {
Sakari Ailusc659c382011-01-21 10:59:30 +00002440 tlan_mii_read_reg(dev, phy, i, &data0);
Sakari Ailusc659c382011-01-21 10:59:30 +00002441 tlan_mii_read_reg(dev, phy, i + 1, &data1);
Sakari Ailusc659c382011-01-21 10:59:30 +00002442 tlan_mii_read_reg(dev, phy, i + 2, &data2);
Sakari Ailusc659c382011-01-21 10:59:30 +00002443 tlan_mii_read_reg(dev, phy, i + 3, &data3);
Joe Perches50624aa2011-03-01 06:56:33 +00002444 pr_info(" 0x%02x 0x%04hx 0x%04hx 0x%04hx 0x%04hx\n",
2445 i, data0, data1, data2, data3);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002446 }
2447 } else {
Joe Perches50624aa2011-03-01 06:56:33 +00002448 netdev_info(dev, "Invalid PHY\n");
Linus Torvalds1da177e2005-04-16 15:20:36 -07002449 }
2450
Sakari Ailusc659c382011-01-21 10:59:30 +00002451}
Linus Torvalds1da177e2005-04-16 15:20:36 -07002452
2453
2454
2455
Sakari Ailusc659c382011-01-21 10:59:30 +00002456/*********************************************************************
2457 * tlan_phy_detect
2458 *
2459 * Returns:
2460 * Nothing
2461 * Parms:
2462 * dev A pointer to the device structure of the adapter
2463 * for which the PHY needs determined.
2464 *
2465 * So far I've found that adapters which have external PHYs
2466 * may also use the internal PHY for part of the functionality.
2467 * (eg, AUI/Thinnet). This function finds out if this TLAN
2468 * chip has an internal PHY, and then finds the first external
2469 * PHY (starting from address 0) if it exists).
2470 *
2471 ********************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -07002472
Sakari Ailusc659c382011-01-21 10:59:30 +00002473static void tlan_phy_detect(struct net_device *dev)
Linus Torvalds1da177e2005-04-16 15:20:36 -07002474{
Sakari Ailusc659c382011-01-21 10:59:30 +00002475 struct tlan_priv *priv = netdev_priv(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002476 u16 control;
2477 u16 hi;
2478 u16 lo;
2479 u32 phy;
2480
Sakari Ailusc659c382011-01-21 10:59:30 +00002481 if (priv->adapter->flags & TLAN_ADAPTER_UNMANAGED_PHY) {
2482 priv->phy_num = 0xffff;
Linus Torvalds1da177e2005-04-16 15:20:36 -07002483 return;
2484 }
2485
Sakari Ailusc659c382011-01-21 10:59:30 +00002486 tlan_mii_read_reg(dev, TLAN_PHY_MAX_ADDR, MII_GEN_ID_HI, &hi);
Jeff Garzik6aa20a22006-09-13 13:24:59 -04002487
Sakari Ailusc659c382011-01-21 10:59:30 +00002488 if (hi != 0xffff)
Linus Torvalds1da177e2005-04-16 15:20:36 -07002489 priv->phy[0] = TLAN_PHY_MAX_ADDR;
Sakari Ailusc659c382011-01-21 10:59:30 +00002490 else
Linus Torvalds1da177e2005-04-16 15:20:36 -07002491 priv->phy[0] = TLAN_PHY_NONE;
Linus Torvalds1da177e2005-04-16 15:20:36 -07002492
2493 priv->phy[1] = TLAN_PHY_NONE;
Sakari Ailusc659c382011-01-21 10:59:30 +00002494 for (phy = 0; phy <= TLAN_PHY_MAX_ADDR; phy++) {
2495 tlan_mii_read_reg(dev, phy, MII_GEN_CTL, &control);
2496 tlan_mii_read_reg(dev, phy, MII_GEN_ID_HI, &hi);
2497 tlan_mii_read_reg(dev, phy, MII_GEN_ID_LO, &lo);
2498 if ((control != 0xffff) ||
2499 (hi != 0xffff) || (lo != 0xffff)) {
2500 TLAN_DBG(TLAN_DEBUG_GNRL,
2501 "PHY found at %02x %04x %04x %04x\n",
2502 phy, control, hi, lo);
2503 if ((priv->phy[1] == TLAN_PHY_NONE) &&
2504 (phy != TLAN_PHY_MAX_ADDR)) {
Linus Torvalds1da177e2005-04-16 15:20:36 -07002505 priv->phy[1] = phy;
2506 }
2507 }
2508 }
2509
Sakari Ailusc659c382011-01-21 10:59:30 +00002510 if (priv->phy[1] != TLAN_PHY_NONE)
2511 priv->phy_num = 1;
2512 else if (priv->phy[0] != TLAN_PHY_NONE)
2513 priv->phy_num = 0;
2514 else
Joe Perches50624aa2011-03-01 06:56:33 +00002515 netdev_info(dev, "Cannot initialize device, no PHY was found!\n");
Linus Torvalds1da177e2005-04-16 15:20:36 -07002516
Sakari Ailusc659c382011-01-21 10:59:30 +00002517}
Linus Torvalds1da177e2005-04-16 15:20:36 -07002518
2519
2520
2521
Sakari Ailusc659c382011-01-21 10:59:30 +00002522static void tlan_phy_power_down(struct net_device *dev)
Linus Torvalds1da177e2005-04-16 15:20:36 -07002523{
Sakari Ailusc659c382011-01-21 10:59:30 +00002524 struct tlan_priv *priv = netdev_priv(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002525 u16 value;
2526
Sakari Ailusc659c382011-01-21 10:59:30 +00002527 TLAN_DBG(TLAN_DEBUG_GNRL, "%s: Powering down PHY(s).\n", dev->name);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002528 value = MII_GC_PDOWN | MII_GC_LOOPBK | MII_GC_ISOLATE;
Sakari Ailusc659c382011-01-21 10:59:30 +00002529 tlan_mii_sync(dev->base_addr);
2530 tlan_mii_write_reg(dev, priv->phy[priv->phy_num], MII_GEN_CTL, value);
Ondrej Zary9162e7e2014-06-30 18:38:37 +02002531 if ((priv->phy_num == 0) && (priv->phy[1] != TLAN_PHY_NONE)) {
2532 /* if using internal PHY, the external PHY must be powered on */
2533 if (priv->adapter->flags & TLAN_ADAPTER_USE_INTERN_10)
2534 value = MII_GC_ISOLATE; /* just isolate it from MII */
Sakari Ailusc659c382011-01-21 10:59:30 +00002535 tlan_mii_sync(dev->base_addr);
2536 tlan_mii_write_reg(dev, priv->phy[1], MII_GEN_CTL, value);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002537 }
2538
2539 /* Wait for 50 ms and powerup
2540 * This is abitrary. It is intended to make sure the
2541 * transceiver settles.
2542 */
Nicholas Mc Guire51fd9472015-02-03 03:44:45 -05002543 tlan_set_timer(dev, msecs_to_jiffies(50), TLAN_TIMER_PHY_PUP);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002544
Sakari Ailusc659c382011-01-21 10:59:30 +00002545}
Linus Torvalds1da177e2005-04-16 15:20:36 -07002546
2547
2548
2549
Sakari Ailusc659c382011-01-21 10:59:30 +00002550static void tlan_phy_power_up(struct net_device *dev)
Linus Torvalds1da177e2005-04-16 15:20:36 -07002551{
Sakari Ailusc659c382011-01-21 10:59:30 +00002552 struct tlan_priv *priv = netdev_priv(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002553 u16 value;
2554
Sakari Ailusc659c382011-01-21 10:59:30 +00002555 TLAN_DBG(TLAN_DEBUG_GNRL, "%s: Powering up PHY.\n", dev->name);
2556 tlan_mii_sync(dev->base_addr);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002557 value = MII_GC_LOOPBK;
Sakari Ailusc659c382011-01-21 10:59:30 +00002558 tlan_mii_write_reg(dev, priv->phy[priv->phy_num], MII_GEN_CTL, value);
2559 tlan_mii_sync(dev->base_addr);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002560 /* Wait for 500 ms and reset the
2561 * transceiver. The TLAN docs say both 50 ms and
2562 * 500 ms, so do the longer, just in case.
2563 */
Sakari Ailusc659c382011-01-21 10:59:30 +00002564 tlan_set_timer(dev, (HZ/20), TLAN_TIMER_PHY_RESET);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002565
Sakari Ailusc659c382011-01-21 10:59:30 +00002566}
Linus Torvalds1da177e2005-04-16 15:20:36 -07002567
2568
2569
2570
Sakari Ailusc659c382011-01-21 10:59:30 +00002571static void tlan_phy_reset(struct net_device *dev)
Linus Torvalds1da177e2005-04-16 15:20:36 -07002572{
Sakari Ailusc659c382011-01-21 10:59:30 +00002573 struct tlan_priv *priv = netdev_priv(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002574 u16 phy;
2575 u16 value;
Ondrej Zary9cff4412014-06-30 18:38:34 +02002576 unsigned long timeout = jiffies + HZ;
Linus Torvalds1da177e2005-04-16 15:20:36 -07002577
Sakari Ailusc659c382011-01-21 10:59:30 +00002578 phy = priv->phy[priv->phy_num];
Linus Torvalds1da177e2005-04-16 15:20:36 -07002579
Masanari Iidafd9071e2012-04-13 04:33:20 +00002580 TLAN_DBG(TLAN_DEBUG_GNRL, "%s: Resetting PHY.\n", dev->name);
Sakari Ailusc659c382011-01-21 10:59:30 +00002581 tlan_mii_sync(dev->base_addr);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002582 value = MII_GC_LOOPBK | MII_GC_RESET;
Sakari Ailusc659c382011-01-21 10:59:30 +00002583 tlan_mii_write_reg(dev, phy, MII_GEN_CTL, value);
Ondrej Zary9cff4412014-06-30 18:38:34 +02002584 do {
Sakari Ailusc659c382011-01-21 10:59:30 +00002585 tlan_mii_read_reg(dev, phy, MII_GEN_CTL, &value);
Ondrej Zary9cff4412014-06-30 18:38:34 +02002586 if (time_after(jiffies, timeout)) {
2587 netdev_err(dev, "PHY reset timeout\n");
2588 return;
2589 }
2590 } while (value & MII_GC_RESET);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002591
2592 /* Wait for 500 ms and initialize.
2593 * I don't remember why I wait this long.
2594 * I've changed this to 50ms, as it seems long enough.
2595 */
Nicholas Mc Guire51fd9472015-02-03 03:44:45 -05002596 tlan_set_timer(dev, msecs_to_jiffies(50), TLAN_TIMER_PHY_START_LINK);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002597
Sakari Ailusc659c382011-01-21 10:59:30 +00002598}
Linus Torvalds1da177e2005-04-16 15:20:36 -07002599
2600
2601
2602
Sakari Ailusc659c382011-01-21 10:59:30 +00002603static void tlan_phy_start_link(struct net_device *dev)
Linus Torvalds1da177e2005-04-16 15:20:36 -07002604{
Sakari Ailusc659c382011-01-21 10:59:30 +00002605 struct tlan_priv *priv = netdev_priv(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002606 u16 ability;
2607 u16 control;
2608 u16 data;
2609 u16 phy;
2610 u16 status;
2611 u16 tctl;
2612
Sakari Ailusc659c382011-01-21 10:59:30 +00002613 phy = priv->phy[priv->phy_num];
2614 TLAN_DBG(TLAN_DEBUG_GNRL, "%s: Trying to activate link.\n", dev->name);
2615 tlan_mii_read_reg(dev, phy, MII_GEN_STS, &status);
2616 tlan_mii_read_reg(dev, phy, MII_GEN_STS, &ability);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002617
Sakari Ailusc659c382011-01-21 10:59:30 +00002618 if ((status & MII_GS_AUTONEG) &&
2619 (!priv->aui)) {
Linus Torvalds1da177e2005-04-16 15:20:36 -07002620 ability = status >> 11;
Sakari Ailusc659c382011-01-21 10:59:30 +00002621 if (priv->speed == TLAN_SPEED_10 &&
2622 priv->duplex == TLAN_DUPLEX_HALF) {
2623 tlan_mii_write_reg(dev, phy, MII_GEN_CTL, 0x0000);
2624 } else if (priv->speed == TLAN_SPEED_10 &&
2625 priv->duplex == TLAN_DUPLEX_FULL) {
2626 priv->tlan_full_duplex = true;
2627 tlan_mii_write_reg(dev, phy, MII_GEN_CTL, 0x0100);
2628 } else if (priv->speed == TLAN_SPEED_100 &&
2629 priv->duplex == TLAN_DUPLEX_HALF) {
2630 tlan_mii_write_reg(dev, phy, MII_GEN_CTL, 0x2000);
2631 } else if (priv->speed == TLAN_SPEED_100 &&
2632 priv->duplex == TLAN_DUPLEX_FULL) {
2633 priv->tlan_full_duplex = true;
2634 tlan_mii_write_reg(dev, phy, MII_GEN_CTL, 0x2100);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002635 } else {
Jeff Garzik6aa20a22006-09-13 13:24:59 -04002636
Linus Torvalds1da177e2005-04-16 15:20:36 -07002637 /* Set Auto-Neg advertisement */
Sakari Ailusc659c382011-01-21 10:59:30 +00002638 tlan_mii_write_reg(dev, phy, MII_AN_ADV,
2639 (ability << 5) | 1);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002640 /* Enablee Auto-Neg */
Sakari Ailusc659c382011-01-21 10:59:30 +00002641 tlan_mii_write_reg(dev, phy, MII_GEN_CTL, 0x1000);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002642 /* Restart Auto-Neg */
Sakari Ailusc659c382011-01-21 10:59:30 +00002643 tlan_mii_write_reg(dev, phy, MII_GEN_CTL, 0x1200);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002644 /* Wait for 4 sec for autonegotiation
Sakari Ailusc659c382011-01-21 10:59:30 +00002645 * to complete. The max spec time is less than this
2646 * but the card need additional time to start AN.
2647 * .5 sec should be plenty extra.
2648 */
Joe Perches50624aa2011-03-01 06:56:33 +00002649 netdev_info(dev, "Starting autonegotiation\n");
Sakari Ailusc659c382011-01-21 10:59:30 +00002650 tlan_set_timer(dev, (2*HZ), TLAN_TIMER_PHY_FINISH_AN);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002651 return;
2652 }
Jeff Garzik6aa20a22006-09-13 13:24:59 -04002653
2654 }
2655
Sakari Ailusc659c382011-01-21 10:59:30 +00002656 if ((priv->aui) && (priv->phy_num != 0)) {
2657 priv->phy_num = 0;
2658 data = TLAN_NET_CFG_1FRAG | TLAN_NET_CFG_1CHAN
2659 | TLAN_NET_CFG_PHY_EN;
2660 tlan_dio_write16(dev->base_addr, TLAN_NET_CONFIG, data);
Nicholas Mc Guire51fd9472015-02-03 03:44:45 -05002661 tlan_set_timer(dev, msecs_to_jiffies(40), TLAN_TIMER_PHY_PDOWN);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002662 return;
Sakari Ailusc659c382011-01-21 10:59:30 +00002663 } else if (priv->phy_num == 0) {
Linus Torvalds1da177e2005-04-16 15:20:36 -07002664 control = 0;
Sakari Ailusc659c382011-01-21 10:59:30 +00002665 tlan_mii_read_reg(dev, phy, TLAN_TLPHY_CTL, &tctl);
2666 if (priv->aui) {
2667 tctl |= TLAN_TC_AUISEL;
Jeff Garzik6aa20a22006-09-13 13:24:59 -04002668 } else {
Sakari Ailusc659c382011-01-21 10:59:30 +00002669 tctl &= ~TLAN_TC_AUISEL;
2670 if (priv->duplex == TLAN_DUPLEX_FULL) {
Linus Torvalds1da177e2005-04-16 15:20:36 -07002671 control |= MII_GC_DUPLEX;
Sakari Ailusc659c382011-01-21 10:59:30 +00002672 priv->tlan_full_duplex = true;
Linus Torvalds1da177e2005-04-16 15:20:36 -07002673 }
Sakari Ailusc659c382011-01-21 10:59:30 +00002674 if (priv->speed == TLAN_SPEED_100)
Linus Torvalds1da177e2005-04-16 15:20:36 -07002675 control |= MII_GC_SPEEDSEL;
Linus Torvalds1da177e2005-04-16 15:20:36 -07002676 }
Sakari Ailusc659c382011-01-21 10:59:30 +00002677 tlan_mii_write_reg(dev, phy, MII_GEN_CTL, control);
2678 tlan_mii_write_reg(dev, phy, TLAN_TLPHY_CTL, tctl);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002679 }
2680
2681 /* Wait for 2 sec to give the transceiver time
2682 * to establish link.
2683 */
Sakari Ailusc659c382011-01-21 10:59:30 +00002684 tlan_set_timer(dev, (4*HZ), TLAN_TIMER_FINISH_RESET);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002685
Sakari Ailusc659c382011-01-21 10:59:30 +00002686}
Linus Torvalds1da177e2005-04-16 15:20:36 -07002687
2688
2689
2690
Sakari Ailusc659c382011-01-21 10:59:30 +00002691static void tlan_phy_finish_auto_neg(struct net_device *dev)
Linus Torvalds1da177e2005-04-16 15:20:36 -07002692{
Sakari Ailusc659c382011-01-21 10:59:30 +00002693 struct tlan_priv *priv = netdev_priv(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002694 u16 an_adv;
2695 u16 an_lpa;
Linus Torvalds1da177e2005-04-16 15:20:36 -07002696 u16 mode;
2697 u16 phy;
2698 u16 status;
Jeff Garzik6aa20a22006-09-13 13:24:59 -04002699
Sakari Ailusc659c382011-01-21 10:59:30 +00002700 phy = priv->phy[priv->phy_num];
Linus Torvalds1da177e2005-04-16 15:20:36 -07002701
Sakari Ailusc659c382011-01-21 10:59:30 +00002702 tlan_mii_read_reg(dev, phy, MII_GEN_STS, &status);
2703 udelay(1000);
2704 tlan_mii_read_reg(dev, phy, MII_GEN_STS, &status);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002705
Sakari Ailusc659c382011-01-21 10:59:30 +00002706 if (!(status & MII_GS_AUTOCMPLT)) {
Linus Torvalds1da177e2005-04-16 15:20:36 -07002707 /* Wait for 8 sec to give the process
2708 * more time. Perhaps we should fail after a while.
2709 */
Ondrej Zary278e48b2014-06-30 18:38:33 +02002710 tlan_set_timer(dev, 2 * HZ, TLAN_TIMER_PHY_FINISH_AN);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002711 return;
2712 }
2713
Joe Perches50624aa2011-03-01 06:56:33 +00002714 netdev_info(dev, "Autonegotiation complete\n");
Sakari Ailusc659c382011-01-21 10:59:30 +00002715 tlan_mii_read_reg(dev, phy, MII_AN_ADV, &an_adv);
2716 tlan_mii_read_reg(dev, phy, MII_AN_LPA, &an_lpa);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002717 mode = an_adv & an_lpa & 0x03E0;
Sakari Ailusc659c382011-01-21 10:59:30 +00002718 if (mode & 0x0100)
2719 priv->tlan_full_duplex = true;
2720 else if (!(mode & 0x0080) && (mode & 0x0040))
2721 priv->tlan_full_duplex = true;
Linus Torvalds1da177e2005-04-16 15:20:36 -07002722
Ondrej Zary36bbe2f2014-06-30 18:38:31 +02002723 /* switch to internal PHY for 10 Mbps */
Sakari Ailusc659c382011-01-21 10:59:30 +00002724 if ((!(mode & 0x0180)) &&
2725 (priv->adapter->flags & TLAN_ADAPTER_USE_INTERN_10) &&
2726 (priv->phy_num != 0)) {
2727 priv->phy_num = 0;
Nicholas Mc Guire51fd9472015-02-03 03:44:45 -05002728 tlan_set_timer(dev, msecs_to_jiffies(400), TLAN_TIMER_PHY_PDOWN);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002729 return;
2730 }
2731
Sakari Ailusc659c382011-01-21 10:59:30 +00002732 if (priv->phy_num == 0) {
2733 if ((priv->duplex == TLAN_DUPLEX_FULL) ||
2734 (an_adv & an_lpa & 0x0040)) {
2735 tlan_mii_write_reg(dev, phy, MII_GEN_CTL,
2736 MII_GC_AUTOENB | MII_GC_DUPLEX);
Joe Perches50624aa2011-03-01 06:56:33 +00002737 netdev_info(dev, "Starting internal PHY with FULL-DUPLEX\n");
Linus Torvalds1da177e2005-04-16 15:20:36 -07002738 } else {
Sakari Ailusc659c382011-01-21 10:59:30 +00002739 tlan_mii_write_reg(dev, phy, MII_GEN_CTL,
2740 MII_GC_AUTOENB);
Joe Perches50624aa2011-03-01 06:56:33 +00002741 netdev_info(dev, "Starting internal PHY with HALF-DUPLEX\n");
Linus Torvalds1da177e2005-04-16 15:20:36 -07002742 }
2743 }
2744
2745 /* Wait for 100 ms. No reason in partiticular.
2746 */
Nicholas Mc Guire51fd9472015-02-03 03:44:45 -05002747 tlan_set_timer(dev, msecs_to_jiffies(100), TLAN_TIMER_FINISH_RESET);
Jeff Garzik6aa20a22006-09-13 13:24:59 -04002748
Sakari Ailusc659c382011-01-21 10:59:30 +00002749}
Linus Torvalds1da177e2005-04-16 15:20:36 -07002750
Linus Torvalds1da177e2005-04-16 15:20:36 -07002751
Sakari Ailusc659c382011-01-21 10:59:30 +00002752/*********************************************************************
2753 *
2754 * tlan_phy_monitor
2755 *
2756 * Returns:
2757 * None
2758 *
2759 * Params:
Ondrej Zaryc0a87c22014-06-30 18:38:28 +02002760 * data The device structure of this device.
Sakari Ailusc659c382011-01-21 10:59:30 +00002761 *
2762 *
2763 * This function monitors PHY condition by reading the status
Ondrej Zaryc0a87c22014-06-30 18:38:28 +02002764 * register via the MII bus, controls LINK LED and notifies the
2765 * kernel about link state.
Sakari Ailusc659c382011-01-21 10:59:30 +00002766 *
2767 *******************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -07002768
Ondrej Zaryc0a87c22014-06-30 18:38:28 +02002769static void tlan_phy_monitor(unsigned long data)
Linus Torvalds1da177e2005-04-16 15:20:36 -07002770{
Ondrej Zaryc0a87c22014-06-30 18:38:28 +02002771 struct net_device *dev = (struct net_device *) data;
Sakari Ailusc659c382011-01-21 10:59:30 +00002772 struct tlan_priv *priv = netdev_priv(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002773 u16 phy;
2774 u16 phy_status;
2775
Sakari Ailusc659c382011-01-21 10:59:30 +00002776 phy = priv->phy[priv->phy_num];
Linus Torvalds1da177e2005-04-16 15:20:36 -07002777
Sakari Ailusc659c382011-01-21 10:59:30 +00002778 /* Get PHY status register */
2779 tlan_mii_read_reg(dev, phy, MII_GEN_STS, &phy_status);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002780
Sakari Ailusc659c382011-01-21 10:59:30 +00002781 /* Check if link has been lost */
2782 if (!(phy_status & MII_GS_LINK)) {
Ondrej Zaryc0a87c22014-06-30 18:38:28 +02002783 if (netif_carrier_ok(dev)) {
Sakari Ailusc659c382011-01-21 10:59:30 +00002784 printk(KERN_DEBUG "TLAN: %s has lost link\n",
2785 dev->name);
Ondrej Zaryc0a87c22014-06-30 18:38:28 +02002786 tlan_dio_write8(dev->base_addr, TLAN_LED_REG, 0);
Sakari Ailusc659c382011-01-21 10:59:30 +00002787 netif_carrier_off(dev);
Ondrej Zary36bbe2f2014-06-30 18:38:31 +02002788 if (priv->adapter->flags & TLAN_ADAPTER_USE_INTERN_10) {
2789 /* power down internal PHY */
2790 u16 data = MII_GC_PDOWN | MII_GC_LOOPBK |
2791 MII_GC_ISOLATE;
2792
2793 tlan_mii_sync(dev->base_addr);
2794 tlan_mii_write_reg(dev, priv->phy[0],
2795 MII_GEN_CTL, data);
2796 /* set to external PHY */
2797 priv->phy_num = 1;
2798 /* restart autonegotiation */
Nicholas Mc Guire51fd9472015-02-03 03:44:45 -05002799 tlan_set_timer(dev, msecs_to_jiffies(400),
Ondrej Zary36bbe2f2014-06-30 18:38:31 +02002800 TLAN_TIMER_PHY_PDOWN);
2801 return;
2802 }
Linus Torvalds1da177e2005-04-16 15:20:36 -07002803 }
2804 }
2805
Sakari Ailusc659c382011-01-21 10:59:30 +00002806 /* Link restablished? */
Ondrej Zaryc0a87c22014-06-30 18:38:28 +02002807 if ((phy_status & MII_GS_LINK) && !netif_carrier_ok(dev)) {
2808 tlan_dio_write8(dev->base_addr, TLAN_LED_REG, TLAN_LED_LINK);
Sakari Ailusc659c382011-01-21 10:59:30 +00002809 printk(KERN_DEBUG "TLAN: %s has reestablished link\n",
2810 dev->name);
7d17c1d2005-05-12 19:45:25 -04002811 netif_carrier_on(dev);
Sakari Ailusc659c382011-01-21 10:59:30 +00002812 }
Ondrej Zaryc0a87c22014-06-30 18:38:28 +02002813 priv->media_timer.expires = jiffies + HZ;
2814 add_timer(&priv->media_timer);
Jeff Garzik6aa20a22006-09-13 13:24:59 -04002815}
Linus Torvalds1da177e2005-04-16 15:20:36 -07002816
Linus Torvalds1da177e2005-04-16 15:20:36 -07002817
2818/*****************************************************************************
2819******************************************************************************
2820
Sakari Ailusc659c382011-01-21 10:59:30 +00002821ThunderLAN driver MII routines
Linus Torvalds1da177e2005-04-16 15:20:36 -07002822
Sakari Ailusc659c382011-01-21 10:59:30 +00002823these routines are based on the information in chap. 2 of the
2824"ThunderLAN Programmer's Guide", pp. 15-24.
Linus Torvalds1da177e2005-04-16 15:20:36 -07002825
2826******************************************************************************
2827*****************************************************************************/
2828
2829
Sakari Ailusc659c382011-01-21 10:59:30 +00002830/***************************************************************
2831 * tlan_mii_read_reg
2832 *
2833 * Returns:
2834 * false if ack received ok
2835 * true if no ack received or other error
2836 *
2837 * Parms:
2838 * dev The device structure containing
2839 * The io address and interrupt count
2840 * for this device.
2841 * phy The address of the PHY to be queried.
2842 * reg The register whose contents are to be
2843 * retrieved.
2844 * val A pointer to a variable to store the
2845 * retrieved value.
2846 *
2847 * This function uses the TLAN's MII bus to retrieve the contents
2848 * of a given register on a PHY. It sends the appropriate info
2849 * and then reads the 16-bit register value from the MII bus via
2850 * the TLAN SIO register.
2851 *
2852 **************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -07002853
Sakari Ailusc659c382011-01-21 10:59:30 +00002854static bool
2855tlan_mii_read_reg(struct net_device *dev, u16 phy, u16 reg, u16 *val)
Linus Torvalds1da177e2005-04-16 15:20:36 -07002856{
2857 u8 nack;
2858 u16 sio, tmp;
Sakari Ailusc659c382011-01-21 10:59:30 +00002859 u32 i;
Joe Perches37fce432010-01-12 20:59:13 +00002860 bool err;
Linus Torvalds1da177e2005-04-16 15:20:36 -07002861 int minten;
Sakari Ailusc659c382011-01-21 10:59:30 +00002862 struct tlan_priv *priv = netdev_priv(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002863 unsigned long flags = 0;
2864
Joe Perches37fce432010-01-12 20:59:13 +00002865 err = false;
Linus Torvalds1da177e2005-04-16 15:20:36 -07002866 outw(TLAN_NET_SIO, dev->base_addr + TLAN_DIO_ADR);
2867 sio = dev->base_addr + TLAN_DIO_DATA + TLAN_NET_SIO;
Jeff Garzik6aa20a22006-09-13 13:24:59 -04002868
Linus Torvalds1da177e2005-04-16 15:20:36 -07002869 if (!in_irq())
2870 spin_lock_irqsave(&priv->lock, flags);
2871
Sakari Ailusc659c382011-01-21 10:59:30 +00002872 tlan_mii_sync(dev->base_addr);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002873
Sakari Ailusc659c382011-01-21 10:59:30 +00002874 minten = tlan_get_bit(TLAN_NET_SIO_MINTEN, sio);
2875 if (minten)
2876 tlan_clear_bit(TLAN_NET_SIO_MINTEN, sio);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002877
Sakari Ailusc659c382011-01-21 10:59:30 +00002878 tlan_mii_send_data(dev->base_addr, 0x1, 2); /* start (01b) */
2879 tlan_mii_send_data(dev->base_addr, 0x2, 2); /* read (10b) */
2880 tlan_mii_send_data(dev->base_addr, phy, 5); /* device # */
2881 tlan_mii_send_data(dev->base_addr, reg, 5); /* register # */
Linus Torvalds1da177e2005-04-16 15:20:36 -07002882
2883
Sakari Ailusc659c382011-01-21 10:59:30 +00002884 tlan_clear_bit(TLAN_NET_SIO_MTXEN, sio); /* change direction */
Linus Torvalds1da177e2005-04-16 15:20:36 -07002885
Sakari Ailusc659c382011-01-21 10:59:30 +00002886 tlan_clear_bit(TLAN_NET_SIO_MCLK, sio); /* clock idle bit */
2887 tlan_set_bit(TLAN_NET_SIO_MCLK, sio);
2888 tlan_clear_bit(TLAN_NET_SIO_MCLK, sio); /* wait 300ns */
Linus Torvalds1da177e2005-04-16 15:20:36 -07002889
Sakari Ailusc659c382011-01-21 10:59:30 +00002890 nack = tlan_get_bit(TLAN_NET_SIO_MDATA, sio); /* check for ACK */
2891 tlan_set_bit(TLAN_NET_SIO_MCLK, sio); /* finish ACK */
2892 if (nack) { /* no ACK, so fake it */
Linus Torvalds1da177e2005-04-16 15:20:36 -07002893 for (i = 0; i < 16; i++) {
Sakari Ailusc659c382011-01-21 10:59:30 +00002894 tlan_clear_bit(TLAN_NET_SIO_MCLK, sio);
2895 tlan_set_bit(TLAN_NET_SIO_MCLK, sio);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002896 }
2897 tmp = 0xffff;
Joe Perches37fce432010-01-12 20:59:13 +00002898 err = true;
Linus Torvalds1da177e2005-04-16 15:20:36 -07002899 } else { /* ACK, so read data */
2900 for (tmp = 0, i = 0x8000; i; i >>= 1) {
Sakari Ailusc659c382011-01-21 10:59:30 +00002901 tlan_clear_bit(TLAN_NET_SIO_MCLK, sio);
2902 if (tlan_get_bit(TLAN_NET_SIO_MDATA, sio))
Linus Torvalds1da177e2005-04-16 15:20:36 -07002903 tmp |= i;
Sakari Ailusc659c382011-01-21 10:59:30 +00002904 tlan_set_bit(TLAN_NET_SIO_MCLK, sio);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002905 }
2906 }
2907
2908
Sakari Ailusc659c382011-01-21 10:59:30 +00002909 tlan_clear_bit(TLAN_NET_SIO_MCLK, sio); /* idle cycle */
2910 tlan_set_bit(TLAN_NET_SIO_MCLK, sio);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002911
Sakari Ailusc659c382011-01-21 10:59:30 +00002912 if (minten)
2913 tlan_set_bit(TLAN_NET_SIO_MINTEN, sio);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002914
2915 *val = tmp;
Jeff Garzik6aa20a22006-09-13 13:24:59 -04002916
Linus Torvalds1da177e2005-04-16 15:20:36 -07002917 if (!in_irq())
2918 spin_unlock_irqrestore(&priv->lock, flags);
2919
2920 return err;
2921
Sakari Ailusc659c382011-01-21 10:59:30 +00002922}
Linus Torvalds1da177e2005-04-16 15:20:36 -07002923
2924
2925
2926
Sakari Ailusc659c382011-01-21 10:59:30 +00002927/***************************************************************
2928 * tlan_mii_send_data
2929 *
2930 * Returns:
2931 * Nothing
2932 * Parms:
2933 * base_port The base IO port of the adapter in
2934 * question.
2935 * dev The address of the PHY to be queried.
2936 * data The value to be placed on the MII bus.
2937 * num_bits The number of bits in data that are to
2938 * be placed on the MII bus.
2939 *
2940 * This function sends on sequence of bits on the MII
2941 * configuration bus.
2942 *
2943 **************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -07002944
Sakari Ailusc659c382011-01-21 10:59:30 +00002945static void tlan_mii_send_data(u16 base_port, u32 data, unsigned num_bits)
Linus Torvalds1da177e2005-04-16 15:20:36 -07002946{
2947 u16 sio;
2948 u32 i;
2949
Sakari Ailusc659c382011-01-21 10:59:30 +00002950 if (num_bits == 0)
Linus Torvalds1da177e2005-04-16 15:20:36 -07002951 return;
2952
Sakari Ailusc659c382011-01-21 10:59:30 +00002953 outw(TLAN_NET_SIO, base_port + TLAN_DIO_ADR);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002954 sio = base_port + TLAN_DIO_DATA + TLAN_NET_SIO;
Sakari Ailusc659c382011-01-21 10:59:30 +00002955 tlan_set_bit(TLAN_NET_SIO_MTXEN, sio);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002956
Sakari Ailusc659c382011-01-21 10:59:30 +00002957 for (i = (0x1 << (num_bits - 1)); i; i >>= 1) {
2958 tlan_clear_bit(TLAN_NET_SIO_MCLK, sio);
2959 (void) tlan_get_bit(TLAN_NET_SIO_MCLK, sio);
2960 if (data & i)
2961 tlan_set_bit(TLAN_NET_SIO_MDATA, sio);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002962 else
Sakari Ailusc659c382011-01-21 10:59:30 +00002963 tlan_clear_bit(TLAN_NET_SIO_MDATA, sio);
2964 tlan_set_bit(TLAN_NET_SIO_MCLK, sio);
2965 (void) tlan_get_bit(TLAN_NET_SIO_MCLK, sio);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002966 }
2967
Sakari Ailusc659c382011-01-21 10:59:30 +00002968}
Linus Torvalds1da177e2005-04-16 15:20:36 -07002969
2970
2971
2972
Sakari Ailusc659c382011-01-21 10:59:30 +00002973/***************************************************************
2974 * TLan_MiiSync
2975 *
2976 * Returns:
2977 * Nothing
2978 * Parms:
2979 * base_port The base IO port of the adapter in
2980 * question.
2981 *
2982 * This functions syncs all PHYs in terms of the MII configuration
2983 * bus.
2984 *
2985 **************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -07002986
Sakari Ailusc659c382011-01-21 10:59:30 +00002987static void tlan_mii_sync(u16 base_port)
Linus Torvalds1da177e2005-04-16 15:20:36 -07002988{
2989 int i;
2990 u16 sio;
2991
Sakari Ailusc659c382011-01-21 10:59:30 +00002992 outw(TLAN_NET_SIO, base_port + TLAN_DIO_ADR);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002993 sio = base_port + TLAN_DIO_DATA + TLAN_NET_SIO;
2994
Sakari Ailusc659c382011-01-21 10:59:30 +00002995 tlan_clear_bit(TLAN_NET_SIO_MTXEN, sio);
2996 for (i = 0; i < 32; i++) {
2997 tlan_clear_bit(TLAN_NET_SIO_MCLK, sio);
2998 tlan_set_bit(TLAN_NET_SIO_MCLK, sio);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002999 }
3000
Sakari Ailusc659c382011-01-21 10:59:30 +00003001}
Linus Torvalds1da177e2005-04-16 15:20:36 -07003002
3003
3004
3005
Sakari Ailusc659c382011-01-21 10:59:30 +00003006/***************************************************************
3007 * tlan_mii_write_reg
3008 *
3009 * Returns:
3010 * Nothing
3011 * Parms:
3012 * dev The device structure for the device
3013 * to write to.
3014 * phy The address of the PHY to be written to.
3015 * reg The register whose contents are to be
3016 * written.
3017 * val The value to be written to the register.
3018 *
3019 * This function uses the TLAN's MII bus to write the contents of a
3020 * given register on a PHY. It sends the appropriate info and then
3021 * writes the 16-bit register value from the MII configuration bus
3022 * via the TLAN SIO register.
3023 *
3024 **************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -07003025
Sakari Ailusc659c382011-01-21 10:59:30 +00003026static void
3027tlan_mii_write_reg(struct net_device *dev, u16 phy, u16 reg, u16 val)
Linus Torvalds1da177e2005-04-16 15:20:36 -07003028{
3029 u16 sio;
3030 int minten;
3031 unsigned long flags = 0;
Sakari Ailusc659c382011-01-21 10:59:30 +00003032 struct tlan_priv *priv = netdev_priv(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -07003033
3034 outw(TLAN_NET_SIO, dev->base_addr + TLAN_DIO_ADR);
3035 sio = dev->base_addr + TLAN_DIO_DATA + TLAN_NET_SIO;
Jeff Garzik6aa20a22006-09-13 13:24:59 -04003036
Linus Torvalds1da177e2005-04-16 15:20:36 -07003037 if (!in_irq())
3038 spin_lock_irqsave(&priv->lock, flags);
3039
Sakari Ailusc659c382011-01-21 10:59:30 +00003040 tlan_mii_sync(dev->base_addr);
Linus Torvalds1da177e2005-04-16 15:20:36 -07003041
Sakari Ailusc659c382011-01-21 10:59:30 +00003042 minten = tlan_get_bit(TLAN_NET_SIO_MINTEN, sio);
3043 if (minten)
3044 tlan_clear_bit(TLAN_NET_SIO_MINTEN, sio);
Linus Torvalds1da177e2005-04-16 15:20:36 -07003045
Sakari Ailusc659c382011-01-21 10:59:30 +00003046 tlan_mii_send_data(dev->base_addr, 0x1, 2); /* start (01b) */
3047 tlan_mii_send_data(dev->base_addr, 0x1, 2); /* write (01b) */
3048 tlan_mii_send_data(dev->base_addr, phy, 5); /* device # */
3049 tlan_mii_send_data(dev->base_addr, reg, 5); /* register # */
Linus Torvalds1da177e2005-04-16 15:20:36 -07003050
Sakari Ailusc659c382011-01-21 10:59:30 +00003051 tlan_mii_send_data(dev->base_addr, 0x2, 2); /* send ACK */
3052 tlan_mii_send_data(dev->base_addr, val, 16); /* send data */
Linus Torvalds1da177e2005-04-16 15:20:36 -07003053
Sakari Ailusc659c382011-01-21 10:59:30 +00003054 tlan_clear_bit(TLAN_NET_SIO_MCLK, sio); /* idle cycle */
3055 tlan_set_bit(TLAN_NET_SIO_MCLK, sio);
Linus Torvalds1da177e2005-04-16 15:20:36 -07003056
Sakari Ailusc659c382011-01-21 10:59:30 +00003057 if (minten)
3058 tlan_set_bit(TLAN_NET_SIO_MINTEN, sio);
Jeff Garzik6aa20a22006-09-13 13:24:59 -04003059
Linus Torvalds1da177e2005-04-16 15:20:36 -07003060 if (!in_irq())
3061 spin_unlock_irqrestore(&priv->lock, flags);
3062
Sakari Ailusc659c382011-01-21 10:59:30 +00003063}
Linus Torvalds1da177e2005-04-16 15:20:36 -07003064
3065
3066
3067
3068/*****************************************************************************
3069******************************************************************************
3070
Sakari Ailusc659c382011-01-21 10:59:30 +00003071ThunderLAN driver eeprom routines
Linus Torvalds1da177e2005-04-16 15:20:36 -07003072
Sakari Ailusc659c382011-01-21 10:59:30 +00003073the Compaq netelligent 10 and 10/100 cards use a microchip 24C02A
3074EEPROM. these functions are based on information in microchip's
3075data sheet. I don't know how well this functions will work with
3076other Eeproms.
Linus Torvalds1da177e2005-04-16 15:20:36 -07003077
3078******************************************************************************
3079*****************************************************************************/
3080
3081
Sakari Ailusc659c382011-01-21 10:59:30 +00003082/***************************************************************
3083 * tlan_ee_send_start
3084 *
3085 * Returns:
3086 * Nothing
3087 * Parms:
3088 * io_base The IO port base address for the
3089 * TLAN device with the EEPROM to
3090 * use.
3091 *
3092 * This function sends a start cycle to an EEPROM attached
3093 * to a TLAN chip.
3094 *
3095 **************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -07003096
Sakari Ailusc659c382011-01-21 10:59:30 +00003097static void tlan_ee_send_start(u16 io_base)
Linus Torvalds1da177e2005-04-16 15:20:36 -07003098{
3099 u16 sio;
3100
Sakari Ailusc659c382011-01-21 10:59:30 +00003101 outw(TLAN_NET_SIO, io_base + TLAN_DIO_ADR);
Linus Torvalds1da177e2005-04-16 15:20:36 -07003102 sio = io_base + TLAN_DIO_DATA + TLAN_NET_SIO;
3103
Sakari Ailusc659c382011-01-21 10:59:30 +00003104 tlan_set_bit(TLAN_NET_SIO_ECLOK, sio);
3105 tlan_set_bit(TLAN_NET_SIO_EDATA, sio);
3106 tlan_set_bit(TLAN_NET_SIO_ETXEN, sio);
3107 tlan_clear_bit(TLAN_NET_SIO_EDATA, sio);
3108 tlan_clear_bit(TLAN_NET_SIO_ECLOK, sio);
Linus Torvalds1da177e2005-04-16 15:20:36 -07003109
Sakari Ailusc659c382011-01-21 10:59:30 +00003110}
Linus Torvalds1da177e2005-04-16 15:20:36 -07003111
3112
3113
3114
Sakari Ailusc659c382011-01-21 10:59:30 +00003115/***************************************************************
3116 * tlan_ee_send_byte
3117 *
3118 * Returns:
3119 * If the correct ack was received, 0, otherwise 1
3120 * Parms: io_base The IO port base address for the
3121 * TLAN device with the EEPROM to
3122 * use.
3123 * data The 8 bits of information to
3124 * send to the EEPROM.
3125 * stop If TLAN_EEPROM_STOP is passed, a
3126 * stop cycle is sent after the
3127 * byte is sent after the ack is
3128 * read.
3129 *
3130 * This function sends a byte on the serial EEPROM line,
3131 * driving the clock to send each bit. The function then
3132 * reverses transmission direction and reads an acknowledge
3133 * bit.
3134 *
3135 **************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -07003136
Sakari Ailusc659c382011-01-21 10:59:30 +00003137static int tlan_ee_send_byte(u16 io_base, u8 data, int stop)
Linus Torvalds1da177e2005-04-16 15:20:36 -07003138{
3139 int err;
3140 u8 place;
3141 u16 sio;
3142
Sakari Ailusc659c382011-01-21 10:59:30 +00003143 outw(TLAN_NET_SIO, io_base + TLAN_DIO_ADR);
Linus Torvalds1da177e2005-04-16 15:20:36 -07003144 sio = io_base + TLAN_DIO_DATA + TLAN_NET_SIO;
3145
3146 /* Assume clock is low, tx is enabled; */
Sakari Ailusc659c382011-01-21 10:59:30 +00003147 for (place = 0x80; place != 0; place >>= 1) {
3148 if (place & data)
3149 tlan_set_bit(TLAN_NET_SIO_EDATA, sio);
Linus Torvalds1da177e2005-04-16 15:20:36 -07003150 else
Sakari Ailusc659c382011-01-21 10:59:30 +00003151 tlan_clear_bit(TLAN_NET_SIO_EDATA, sio);
3152 tlan_set_bit(TLAN_NET_SIO_ECLOK, sio);
3153 tlan_clear_bit(TLAN_NET_SIO_ECLOK, sio);
Linus Torvalds1da177e2005-04-16 15:20:36 -07003154 }
Sakari Ailusc659c382011-01-21 10:59:30 +00003155 tlan_clear_bit(TLAN_NET_SIO_ETXEN, sio);
3156 tlan_set_bit(TLAN_NET_SIO_ECLOK, sio);
3157 err = tlan_get_bit(TLAN_NET_SIO_EDATA, sio);
3158 tlan_clear_bit(TLAN_NET_SIO_ECLOK, sio);
3159 tlan_set_bit(TLAN_NET_SIO_ETXEN, sio);
Linus Torvalds1da177e2005-04-16 15:20:36 -07003160
Sakari Ailusc659c382011-01-21 10:59:30 +00003161 if ((!err) && stop) {
Stephen Hemmingerdfc2c0a2008-05-30 09:49:58 -07003162 /* STOP, raise data while clock is high */
Sakari Ailusc659c382011-01-21 10:59:30 +00003163 tlan_clear_bit(TLAN_NET_SIO_EDATA, sio);
3164 tlan_set_bit(TLAN_NET_SIO_ECLOK, sio);
3165 tlan_set_bit(TLAN_NET_SIO_EDATA, sio);
Linus Torvalds1da177e2005-04-16 15:20:36 -07003166 }
3167
Eric Dumazet807540b2010-09-23 05:40:09 +00003168 return err;
Linus Torvalds1da177e2005-04-16 15:20:36 -07003169
Sakari Ailusc659c382011-01-21 10:59:30 +00003170}
Linus Torvalds1da177e2005-04-16 15:20:36 -07003171
3172
3173
3174
Sakari Ailusc659c382011-01-21 10:59:30 +00003175/***************************************************************
3176 * tlan_ee_receive_byte
3177 *
3178 * Returns:
3179 * Nothing
3180 * Parms:
3181 * io_base The IO port base address for the
3182 * TLAN device with the EEPROM to
3183 * use.
3184 * data An address to a char to hold the
3185 * data sent from the EEPROM.
3186 * stop If TLAN_EEPROM_STOP is passed, a
3187 * stop cycle is sent after the
3188 * byte is received, and no ack is
3189 * sent.
3190 *
3191 * This function receives 8 bits of data from the EEPROM
3192 * over the serial link. It then sends and ack bit, or no
3193 * ack and a stop bit. This function is used to retrieve
3194 * data after the address of a byte in the EEPROM has been
3195 * sent.
3196 *
3197 **************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -07003198
Sakari Ailusc659c382011-01-21 10:59:30 +00003199static void tlan_ee_receive_byte(u16 io_base, u8 *data, int stop)
Linus Torvalds1da177e2005-04-16 15:20:36 -07003200{
3201 u8 place;
3202 u16 sio;
3203
Sakari Ailusc659c382011-01-21 10:59:30 +00003204 outw(TLAN_NET_SIO, io_base + TLAN_DIO_ADR);
Linus Torvalds1da177e2005-04-16 15:20:36 -07003205 sio = io_base + TLAN_DIO_DATA + TLAN_NET_SIO;
3206 *data = 0;
3207
3208 /* Assume clock is low, tx is enabled; */
Sakari Ailusc659c382011-01-21 10:59:30 +00003209 tlan_clear_bit(TLAN_NET_SIO_ETXEN, sio);
3210 for (place = 0x80; place; place >>= 1) {
3211 tlan_set_bit(TLAN_NET_SIO_ECLOK, sio);
3212 if (tlan_get_bit(TLAN_NET_SIO_EDATA, sio))
Linus Torvalds1da177e2005-04-16 15:20:36 -07003213 *data |= place;
Sakari Ailusc659c382011-01-21 10:59:30 +00003214 tlan_clear_bit(TLAN_NET_SIO_ECLOK, sio);
Linus Torvalds1da177e2005-04-16 15:20:36 -07003215 }
3216
Sakari Ailusc659c382011-01-21 10:59:30 +00003217 tlan_set_bit(TLAN_NET_SIO_ETXEN, sio);
3218 if (!stop) {
3219 tlan_clear_bit(TLAN_NET_SIO_EDATA, sio); /* ack = 0 */
3220 tlan_set_bit(TLAN_NET_SIO_ECLOK, sio);
3221 tlan_clear_bit(TLAN_NET_SIO_ECLOK, sio);
Linus Torvalds1da177e2005-04-16 15:20:36 -07003222 } else {
Sakari Ailusc659c382011-01-21 10:59:30 +00003223 tlan_set_bit(TLAN_NET_SIO_EDATA, sio); /* no ack = 1 (?) */
3224 tlan_set_bit(TLAN_NET_SIO_ECLOK, sio);
3225 tlan_clear_bit(TLAN_NET_SIO_ECLOK, sio);
Stephen Hemmingerdfc2c0a2008-05-30 09:49:58 -07003226 /* STOP, raise data while clock is high */
Sakari Ailusc659c382011-01-21 10:59:30 +00003227 tlan_clear_bit(TLAN_NET_SIO_EDATA, sio);
3228 tlan_set_bit(TLAN_NET_SIO_ECLOK, sio);
3229 tlan_set_bit(TLAN_NET_SIO_EDATA, sio);
Linus Torvalds1da177e2005-04-16 15:20:36 -07003230 }
3231
Sakari Ailusc659c382011-01-21 10:59:30 +00003232}
Linus Torvalds1da177e2005-04-16 15:20:36 -07003233
3234
3235
3236
Sakari Ailusc659c382011-01-21 10:59:30 +00003237/***************************************************************
3238 * tlan_ee_read_byte
3239 *
3240 * Returns:
3241 * No error = 0, else, the stage at which the error
3242 * occurred.
3243 * Parms:
3244 * io_base The IO port base address for the
3245 * TLAN device with the EEPROM to
3246 * use.
3247 * ee_addr The address of the byte in the
3248 * EEPROM whose contents are to be
3249 * retrieved.
3250 * data An address to a char to hold the
3251 * data obtained from the EEPROM.
3252 *
3253 * This function reads a byte of information from an byte
3254 * cell in the EEPROM.
3255 *
3256 **************************************************************/
Linus Torvalds1da177e2005-04-16 15:20:36 -07003257
Sakari Ailusc659c382011-01-21 10:59:30 +00003258static int tlan_ee_read_byte(struct net_device *dev, u8 ee_addr, u8 *data)
Linus Torvalds1da177e2005-04-16 15:20:36 -07003259{
3260 int err;
Sakari Ailusc659c382011-01-21 10:59:30 +00003261 struct tlan_priv *priv = netdev_priv(dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -07003262 unsigned long flags = 0;
Sakari Ailusc659c382011-01-21 10:59:30 +00003263 int ret = 0;
Linus Torvalds1da177e2005-04-16 15:20:36 -07003264
3265 spin_lock_irqsave(&priv->lock, flags);
3266
Sakari Ailusc659c382011-01-21 10:59:30 +00003267 tlan_ee_send_start(dev->base_addr);
3268 err = tlan_ee_send_byte(dev->base_addr, 0xa0, TLAN_EEPROM_ACK);
3269 if (err) {
3270 ret = 1;
Linus Torvalds1da177e2005-04-16 15:20:36 -07003271 goto fail;
3272 }
Sakari Ailusc659c382011-01-21 10:59:30 +00003273 err = tlan_ee_send_byte(dev->base_addr, ee_addr, TLAN_EEPROM_ACK);
3274 if (err) {
3275 ret = 2;
Linus Torvalds1da177e2005-04-16 15:20:36 -07003276 goto fail;
3277 }
Sakari Ailusc659c382011-01-21 10:59:30 +00003278 tlan_ee_send_start(dev->base_addr);
3279 err = tlan_ee_send_byte(dev->base_addr, 0xa1, TLAN_EEPROM_ACK);
3280 if (err) {
3281 ret = 3;
Linus Torvalds1da177e2005-04-16 15:20:36 -07003282 goto fail;
3283 }
Sakari Ailusc659c382011-01-21 10:59:30 +00003284 tlan_ee_receive_byte(dev->base_addr, data, TLAN_EEPROM_STOP);
Linus Torvalds1da177e2005-04-16 15:20:36 -07003285fail:
3286 spin_unlock_irqrestore(&priv->lock, flags);
3287
3288 return ret;
3289
Sakari Ailusc659c382011-01-21 10:59:30 +00003290}
Linus Torvalds1da177e2005-04-16 15:20:36 -07003291
3292
3293